1*91f16700Schasinglulu/* 2*91f16700Schasinglulu * Copyright (c) 2013-2017, ARM Limited and Contributors. All rights reserved. 3*91f16700Schasinglulu * 4*91f16700Schasinglulu * SPDX-License-Identifier: BSD-3-Clause 5*91f16700Schasinglulu */ 6*91f16700Schasinglulu 7*91f16700Schasinglulu#include <arch.h> 8*91f16700Schasinglulu#include <asm_macros.S> 9*91f16700Schasinglulu#include <common/bl_common.h> 10*91f16700Schasinglulu#include <cortex_a53.h> 11*91f16700Schasinglulu#include <cortex_a57.h> 12*91f16700Schasinglulu#include <cortex_a72.h> 13*91f16700Schasinglulu#include <cpu_macros.S> 14*91f16700Schasinglulu#include <platform_def.h> 15*91f16700Schasinglulu 16*91f16700Schasinglulu .globl plat_reset_handler 17*91f16700Schasinglulu .globl plat_arm_calc_core_pos 18*91f16700Schasinglulu#if JUNO_AARCH32_EL3_RUNTIME 19*91f16700Schasinglulu .globl plat_get_my_entrypoint 20*91f16700Schasinglulu .globl juno_reset_to_aarch32_state 21*91f16700Schasinglulu#endif 22*91f16700Schasinglulu 23*91f16700Schasinglulu#define JUNO_REVISION(rev) REV_JUNO_R##rev 24*91f16700Schasinglulu#define JUNO_HANDLER(rev) plat_reset_handler_juno_r##rev 25*91f16700Schasinglulu#define JUMP_TO_HANDLER_IF_JUNO_R(revision) \ 26*91f16700Schasinglulu jump_to_handler JUNO_REVISION(revision), JUNO_HANDLER(revision) 27*91f16700Schasinglulu 28*91f16700Schasinglulu /* -------------------------------------------------------------------- 29*91f16700Schasinglulu * Helper macro to jump to the given handler if the board revision 30*91f16700Schasinglulu * matches. 31*91f16700Schasinglulu * Expects the Juno board revision in x0. 32*91f16700Schasinglulu * -------------------------------------------------------------------- 33*91f16700Schasinglulu */ 34*91f16700Schasinglulu .macro jump_to_handler _revision, _handler 35*91f16700Schasinglulu cmp x0, #\_revision 36*91f16700Schasinglulu b.eq \_handler 37*91f16700Schasinglulu .endm 38*91f16700Schasinglulu 39*91f16700Schasinglulu /* -------------------------------------------------------------------- 40*91f16700Schasinglulu * Platform reset handler for Juno R0. 41*91f16700Schasinglulu * 42*91f16700Schasinglulu * Juno R0 has the following topology: 43*91f16700Schasinglulu * - Quad core Cortex-A53 processor cluster; 44*91f16700Schasinglulu * - Dual core Cortex-A57 processor cluster. 45*91f16700Schasinglulu * 46*91f16700Schasinglulu * This handler does the following: 47*91f16700Schasinglulu * - Implement workaround for defect id 831273 by enabling an event 48*91f16700Schasinglulu * stream every 65536 cycles. 49*91f16700Schasinglulu * - Set the L2 Data RAM latency to 2 (i.e. 3 cycles) for Cortex-A57 50*91f16700Schasinglulu * - Set the L2 Tag RAM latency to 2 (i.e. 3 cycles) for Cortex-A57 51*91f16700Schasinglulu * -------------------------------------------------------------------- 52*91f16700Schasinglulu */ 53*91f16700Schasinglulufunc JUNO_HANDLER(0) 54*91f16700Schasinglulu /* -------------------------------------------------------------------- 55*91f16700Schasinglulu * Enable the event stream every 65536 cycles 56*91f16700Schasinglulu * -------------------------------------------------------------------- 57*91f16700Schasinglulu */ 58*91f16700Schasinglulu mov x0, #(0xf << EVNTI_SHIFT) 59*91f16700Schasinglulu orr x0, x0, #EVNTEN_BIT 60*91f16700Schasinglulu msr CNTKCTL_EL1, x0 61*91f16700Schasinglulu 62*91f16700Schasinglulu /* -------------------------------------------------------------------- 63*91f16700Schasinglulu * Nothing else to do on Cortex-A53. 64*91f16700Schasinglulu * -------------------------------------------------------------------- 65*91f16700Schasinglulu */ 66*91f16700Schasinglulu jump_if_cpu_midr CORTEX_A53_MIDR, 1f 67*91f16700Schasinglulu 68*91f16700Schasinglulu /* -------------------------------------------------------------------- 69*91f16700Schasinglulu * Cortex-A57 specific settings 70*91f16700Schasinglulu * -------------------------------------------------------------------- 71*91f16700Schasinglulu */ 72*91f16700Schasinglulu mov x0, #((CORTEX_A57_L2_DATA_RAM_LATENCY_3_CYCLES << CORTEX_A57_L2CTLR_DATA_RAM_LATENCY_SHIFT) | \ 73*91f16700Schasinglulu (CORTEX_A57_L2_TAG_RAM_LATENCY_3_CYCLES << CORTEX_A57_L2CTLR_TAG_RAM_LATENCY_SHIFT)) 74*91f16700Schasinglulu msr CORTEX_A57_L2CTLR_EL1, x0 75*91f16700Schasinglulu1: 76*91f16700Schasinglulu isb 77*91f16700Schasinglulu ret 78*91f16700Schasingluluendfunc JUNO_HANDLER(0) 79*91f16700Schasinglulu 80*91f16700Schasinglulu /* -------------------------------------------------------------------- 81*91f16700Schasinglulu * Platform reset handler for Juno R1. 82*91f16700Schasinglulu * 83*91f16700Schasinglulu * Juno R1 has the following topology: 84*91f16700Schasinglulu * - Quad core Cortex-A53 processor cluster; 85*91f16700Schasinglulu * - Dual core Cortex-A57 processor cluster. 86*91f16700Schasinglulu * 87*91f16700Schasinglulu * This handler does the following: 88*91f16700Schasinglulu * - Set the L2 Data RAM latency to 2 (i.e. 3 cycles) for Cortex-A57 89*91f16700Schasinglulu * 90*91f16700Schasinglulu * Note that: 91*91f16700Schasinglulu * - The default value for the L2 Tag RAM latency for Cortex-A57 is 92*91f16700Schasinglulu * suitable. 93*91f16700Schasinglulu * - Defect #831273 doesn't affect Juno R1. 94*91f16700Schasinglulu * -------------------------------------------------------------------- 95*91f16700Schasinglulu */ 96*91f16700Schasinglulufunc JUNO_HANDLER(1) 97*91f16700Schasinglulu /* -------------------------------------------------------------------- 98*91f16700Schasinglulu * Nothing to do on Cortex-A53. 99*91f16700Schasinglulu * -------------------------------------------------------------------- 100*91f16700Schasinglulu */ 101*91f16700Schasinglulu jump_if_cpu_midr CORTEX_A57_MIDR, A57 102*91f16700Schasinglulu ret 103*91f16700Schasinglulu 104*91f16700SchasingluluA57: 105*91f16700Schasinglulu /* -------------------------------------------------------------------- 106*91f16700Schasinglulu * Cortex-A57 specific settings 107*91f16700Schasinglulu * -------------------------------------------------------------------- 108*91f16700Schasinglulu */ 109*91f16700Schasinglulu mov x0, #(CORTEX_A57_L2_DATA_RAM_LATENCY_3_CYCLES << CORTEX_A57_L2CTLR_DATA_RAM_LATENCY_SHIFT) 110*91f16700Schasinglulu msr CORTEX_A57_L2CTLR_EL1, x0 111*91f16700Schasinglulu isb 112*91f16700Schasinglulu ret 113*91f16700Schasingluluendfunc JUNO_HANDLER(1) 114*91f16700Schasinglulu 115*91f16700Schasinglulu /* -------------------------------------------------------------------- 116*91f16700Schasinglulu * Platform reset handler for Juno R2. 117*91f16700Schasinglulu * 118*91f16700Schasinglulu * Juno R2 has the following topology: 119*91f16700Schasinglulu * - Quad core Cortex-A53 processor cluster; 120*91f16700Schasinglulu * - Dual core Cortex-A72 processor cluster. 121*91f16700Schasinglulu * 122*91f16700Schasinglulu * This handler does the following: 123*91f16700Schasinglulu * - Set the L2 Data RAM latency to 2 (i.e. 3 cycles) for Cortex-A72 124*91f16700Schasinglulu * - Set the L2 Tag RAM latency to 1 (i.e. 2 cycles) for Cortex-A72 125*91f16700Schasinglulu * 126*91f16700Schasinglulu * Note that: 127*91f16700Schasinglulu * - Defect #831273 doesn't affect Juno R2. 128*91f16700Schasinglulu * -------------------------------------------------------------------- 129*91f16700Schasinglulu */ 130*91f16700Schasinglulufunc JUNO_HANDLER(2) 131*91f16700Schasinglulu /* -------------------------------------------------------------------- 132*91f16700Schasinglulu * Nothing to do on Cortex-A53. 133*91f16700Schasinglulu * -------------------------------------------------------------------- 134*91f16700Schasinglulu */ 135*91f16700Schasinglulu jump_if_cpu_midr CORTEX_A72_MIDR, A72 136*91f16700Schasinglulu ret 137*91f16700Schasinglulu 138*91f16700SchasingluluA72: 139*91f16700Schasinglulu /* -------------------------------------------------------------------- 140*91f16700Schasinglulu * Cortex-A72 specific settings 141*91f16700Schasinglulu * -------------------------------------------------------------------- 142*91f16700Schasinglulu */ 143*91f16700Schasinglulu mov x0, #((CORTEX_A72_L2_DATA_RAM_LATENCY_3_CYCLES << CORTEX_A72_L2CTLR_DATA_RAM_LATENCY_SHIFT) | \ 144*91f16700Schasinglulu (CORTEX_A72_L2_TAG_RAM_LATENCY_2_CYCLES << CORTEX_A72_L2CTLR_TAG_RAM_LATENCY_SHIFT)) 145*91f16700Schasinglulu msr CORTEX_A57_L2CTLR_EL1, x0 146*91f16700Schasinglulu isb 147*91f16700Schasinglulu ret 148*91f16700Schasingluluendfunc JUNO_HANDLER(2) 149*91f16700Schasinglulu 150*91f16700Schasinglulu /* -------------------------------------------------------------------- 151*91f16700Schasinglulu * void plat_reset_handler(void); 152*91f16700Schasinglulu * 153*91f16700Schasinglulu * Determine the Juno board revision and call the appropriate reset 154*91f16700Schasinglulu * handler. 155*91f16700Schasinglulu * -------------------------------------------------------------------- 156*91f16700Schasinglulu */ 157*91f16700Schasinglulufunc plat_reset_handler 158*91f16700Schasinglulu /* Read the V2M SYS_ID register */ 159*91f16700Schasinglulu mov_imm x0, (V2M_SYSREGS_BASE + V2M_SYS_ID) 160*91f16700Schasinglulu ldr w1, [x0] 161*91f16700Schasinglulu /* Extract board revision from the SYS_ID */ 162*91f16700Schasinglulu ubfx x0, x1, #V2M_SYS_ID_REV_SHIFT, #4 163*91f16700Schasinglulu 164*91f16700Schasinglulu JUMP_TO_HANDLER_IF_JUNO_R(0) 165*91f16700Schasinglulu JUMP_TO_HANDLER_IF_JUNO_R(1) 166*91f16700Schasinglulu JUMP_TO_HANDLER_IF_JUNO_R(2) 167*91f16700Schasinglulu 168*91f16700Schasinglulu /* Board revision is not supported */ 169*91f16700Schasinglulu no_ret plat_panic_handler 170*91f16700Schasinglulu 171*91f16700Schasingluluendfunc plat_reset_handler 172*91f16700Schasinglulu 173*91f16700Schasinglulu /* ----------------------------------------------------- 174*91f16700Schasinglulu * void juno_do_reset_to_aarch32_state(void); 175*91f16700Schasinglulu * 176*91f16700Schasinglulu * Request warm reset to AArch32 mode. 177*91f16700Schasinglulu * ----------------------------------------------------- 178*91f16700Schasinglulu */ 179*91f16700Schasinglulufunc juno_do_reset_to_aarch32_state 180*91f16700Schasinglulu mov x0, #RMR_EL3_RR_BIT 181*91f16700Schasinglulu dsb sy 182*91f16700Schasinglulu msr rmr_el3, x0 183*91f16700Schasinglulu isb 184*91f16700Schasinglulu wfi 185*91f16700Schasinglulu b plat_panic_handler 186*91f16700Schasingluluendfunc juno_do_reset_to_aarch32_state 187*91f16700Schasinglulu 188*91f16700Schasinglulu /* ----------------------------------------------------- 189*91f16700Schasinglulu * unsigned int plat_arm_calc_core_pos(u_register_t mpidr) 190*91f16700Schasinglulu * Helper function to calculate the core position. 191*91f16700Schasinglulu * ----------------------------------------------------- 192*91f16700Schasinglulu */ 193*91f16700Schasinglulufunc plat_arm_calc_core_pos 194*91f16700Schasinglulu b css_calc_core_pos_swap_cluster 195*91f16700Schasingluluendfunc plat_arm_calc_core_pos 196*91f16700Schasinglulu 197*91f16700Schasinglulu#if JUNO_AARCH32_EL3_RUNTIME 198*91f16700Schasinglulu /* --------------------------------------------------------------------- 199*91f16700Schasinglulu * uintptr_t plat_get_my_entrypoint (void); 200*91f16700Schasinglulu * 201*91f16700Schasinglulu * Main job of this routine is to distinguish between a cold and a warm 202*91f16700Schasinglulu * boot. On JUNO platform, this distinction is based on the contents of 203*91f16700Schasinglulu * the Trusted Mailbox. It is initialised to zero by the SCP before the 204*91f16700Schasinglulu * AP cores are released from reset. Therefore, a zero mailbox means 205*91f16700Schasinglulu * it's a cold reset. If it is a warm boot then a request to reset to 206*91f16700Schasinglulu * AArch32 state is issued. This is the only way to reset to AArch32 207*91f16700Schasinglulu * in EL3 on Juno. A trampoline located at the high vector address 208*91f16700Schasinglulu * has already been prepared by BL1. 209*91f16700Schasinglulu * 210*91f16700Schasinglulu * This functions returns the contents of the mailbox, i.e.: 211*91f16700Schasinglulu * - 0 for a cold boot; 212*91f16700Schasinglulu * - request warm reset in AArch32 state for warm boot case; 213*91f16700Schasinglulu * --------------------------------------------------------------------- 214*91f16700Schasinglulu */ 215*91f16700Schasinglulufunc plat_get_my_entrypoint 216*91f16700Schasinglulu mov_imm x0, PLAT_ARM_TRUSTED_MAILBOX_BASE 217*91f16700Schasinglulu ldr x0, [x0] 218*91f16700Schasinglulu cbz x0, return 219*91f16700Schasinglulu b juno_do_reset_to_aarch32_state 220*91f16700Schasinglulureturn: 221*91f16700Schasinglulu ret 222*91f16700Schasingluluendfunc plat_get_my_entrypoint 223*91f16700Schasinglulu 224*91f16700Schasinglulu/* 225*91f16700Schasinglulu * Emit a "movw r0, #imm16" which moves the lower 226*91f16700Schasinglulu * 16 bits of `_val` into r0. 227*91f16700Schasinglulu */ 228*91f16700Schasinglulu.macro emit_movw _reg_d, _val 229*91f16700Schasinglulu mov_imm \_reg_d, (0xe3000000 | \ 230*91f16700Schasinglulu ((\_val & 0xfff) | \ 231*91f16700Schasinglulu ((\_val & 0xf000) << 4))) 232*91f16700Schasinglulu.endm 233*91f16700Schasinglulu 234*91f16700Schasinglulu/* 235*91f16700Schasinglulu * Emit a "movt r0, #imm16" which moves the upper 236*91f16700Schasinglulu * 16 bits of `_val` into r0. 237*91f16700Schasinglulu */ 238*91f16700Schasinglulu.macro emit_movt _reg_d, _val 239*91f16700Schasinglulu mov_imm \_reg_d, (0xe3400000 | \ 240*91f16700Schasinglulu (((\_val & 0x0fff0000) >> 16) | \ 241*91f16700Schasinglulu ((\_val & 0xf0000000) >> 12))) 242*91f16700Schasinglulu.endm 243*91f16700Schasinglulu 244*91f16700Schasinglulu/* 245*91f16700Schasinglulu * This function writes the trampoline code at HI-VEC (0xFFFF0000) 246*91f16700Schasinglulu * address which loads r0 with the entrypoint address for 247*91f16700Schasinglulu * BL32 (a.k.a SP_MIN) when EL3 is in AArch32 mode. A warm reset 248*91f16700Schasinglulu * to AArch32 mode is then requested by writing into RMR_EL3. 249*91f16700Schasinglulu */ 250*91f16700Schasinglulufunc juno_reset_to_aarch32_state 251*91f16700Schasinglulu /* 252*91f16700Schasinglulu * Invalidate all caches before the warm reset to AArch32 state. 253*91f16700Schasinglulu * This is required on the Juno AArch32 boot flow because the L2 254*91f16700Schasinglulu * unified cache may contain code and data from when the processor 255*91f16700Schasinglulu * was still executing in AArch64 state. This code only runs on 256*91f16700Schasinglulu * the primary core, all other cores are powered down. 257*91f16700Schasinglulu */ 258*91f16700Schasinglulu mov x0, #DCISW 259*91f16700Schasinglulu bl dcsw_op_all 260*91f16700Schasinglulu 261*91f16700Schasinglulu emit_movw w0, BL32_BASE 262*91f16700Schasinglulu emit_movt w1, BL32_BASE 263*91f16700Schasinglulu /* opcode "bx r0" to branch using r0 in AArch32 mode */ 264*91f16700Schasinglulu mov_imm w2, 0xe12fff10 265*91f16700Schasinglulu 266*91f16700Schasinglulu /* Write the above opcodes at HI-VECTOR location */ 267*91f16700Schasinglulu mov_imm x3, HI_VECTOR_BASE 268*91f16700Schasinglulu str w0, [x3], #4 269*91f16700Schasinglulu str w1, [x3], #4 270*91f16700Schasinglulu str w2, [x3] 271*91f16700Schasinglulu 272*91f16700Schasinglulu b juno_do_reset_to_aarch32_state 273*91f16700Schasingluluendfunc juno_reset_to_aarch32_state 274*91f16700Schasinglulu 275*91f16700Schasinglulu#endif /* JUNO_AARCH32_EL3_RUNTIME */ 276