lowlevel.S 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561
  1. /*
  2. * (C) Copyright 2014-2015 Freescale Semiconductor
  3. *
  4. * SPDX-License-Identifier: GPL-2.0+
  5. *
  6. * Extracted from armv8/start.S
  7. */
  8. #include <config.h>
  9. #include <linux/linkage.h>
  10. #include <asm/gic.h>
  11. #include <asm/macro.h>
  12. #include <asm/arch-fsl-layerscape/soc.h>
  13. #ifdef CONFIG_MP
  14. #include <asm/arch/mp.h>
  15. #endif
  16. #ifdef CONFIG_FSL_LSCH3
  17. #include <asm/arch-fsl-layerscape/immap_lsch3.h>
  18. #endif
  19. #include <asm/u-boot.h>
  20. /* Get GIC offset
  21. * For LS1043a rev1.0, GIC base address align with 4k.
  22. * For LS1043a rev1.1, if DCFG_GIC400_ALIGN[GIC_ADDR_BIT]
  23. * is set, GIC base address align with 4K, or else align
  24. * with 64k.
  25. * output:
  26. * x0: the base address of GICD
  27. * x1: the base address of GICC
  28. */
  29. ENTRY(get_gic_offset)
  30. ldr x0, =GICD_BASE
  31. #ifdef CONFIG_GICV2
  32. ldr x1, =GICC_BASE
  33. #endif
  34. #ifdef CONFIG_HAS_FEATURE_GIC64K_ALIGN
  35. ldr x2, =DCFG_CCSR_SVR
  36. ldr w2, [x2]
  37. rev w2, w2
  38. mov w3, w2
  39. ands w3, w3, #SVR_WO_E << 8
  40. mov w4, #SVR_LS1043A << 8
  41. cmp w3, w4
  42. b.ne 1f
  43. ands w2, w2, #0xff
  44. cmp w2, #REV1_0
  45. b.eq 1f
  46. ldr x2, =SCFG_GIC400_ALIGN
  47. ldr w2, [x2]
  48. rev w2, w2
  49. tbnz w2, #GIC_ADDR_BIT, 1f
  50. ldr x0, =GICD_BASE_64K
  51. #ifdef CONFIG_GICV2
  52. ldr x1, =GICC_BASE_64K
  53. #endif
  54. 1:
  55. #endif
  56. ret
  57. ENDPROC(get_gic_offset)
  58. ENTRY(smp_kick_all_cpus)
  59. /* Kick secondary cpus up by SGI 0 interrupt */
  60. #if defined(CONFIG_GICV2) || defined(CONFIG_GICV3)
  61. mov x29, lr /* Save LR */
  62. bl get_gic_offset
  63. bl gic_kick_secondary_cpus
  64. mov lr, x29 /* Restore LR */
  65. #endif
  66. ret
  67. ENDPROC(smp_kick_all_cpus)
  68. ENTRY(lowlevel_init)
  69. mov x29, lr /* Save LR */
  70. #ifdef CONFIG_FSL_LSCH3
  71. /* Set Wuo bit for RN-I 20 */
  72. #ifdef CONFIG_ARCH_LS2080A
  73. ldr x0, =CCI_AUX_CONTROL_BASE(20)
  74. ldr x1, =0x00000010
  75. bl ccn504_set_aux
  76. /*
  77. * Set forced-order mode in RNI-6, RNI-20
  78. * This is required for performance optimization on LS2088A
  79. * LS2080A family does not support setting forced-order mode,
  80. * so skip this operation for LS2080A family
  81. */
  82. bl get_svr
  83. lsr w0, w0, #16
  84. ldr w1, =SVR_DEV_LS2080A
  85. cmp w0, w1
  86. b.eq 1f
  87. ldr x0, =CCI_AUX_CONTROL_BASE(6)
  88. ldr x1, =0x00000020
  89. bl ccn504_set_aux
  90. ldr x0, =CCI_AUX_CONTROL_BASE(20)
  91. ldr x1, =0x00000020
  92. bl ccn504_set_aux
  93. 1:
  94. #endif
  95. /* Add fully-coherent masters to DVM domain */
  96. ldr x0, =CCI_MN_BASE
  97. ldr x1, =CCI_MN_RNF_NODEID_LIST
  98. ldr x2, =CCI_MN_DVM_DOMAIN_CTL_SET
  99. bl ccn504_add_masters_to_dvm
  100. /* Set all RN-I ports to QoS of 15 */
  101. ldr x0, =CCI_S0_QOS_CONTROL_BASE(0)
  102. ldr x1, =0x00FF000C
  103. bl ccn504_set_qos
  104. ldr x0, =CCI_S1_QOS_CONTROL_BASE(0)
  105. ldr x1, =0x00FF000C
  106. bl ccn504_set_qos
  107. ldr x0, =CCI_S2_QOS_CONTROL_BASE(0)
  108. ldr x1, =0x00FF000C
  109. bl ccn504_set_qos
  110. ldr x0, =CCI_S0_QOS_CONTROL_BASE(2)
  111. ldr x1, =0x00FF000C
  112. bl ccn504_set_qos
  113. ldr x0, =CCI_S1_QOS_CONTROL_BASE(2)
  114. ldr x1, =0x00FF000C
  115. bl ccn504_set_qos
  116. ldr x0, =CCI_S2_QOS_CONTROL_BASE(2)
  117. ldr x1, =0x00FF000C
  118. bl ccn504_set_qos
  119. ldr x0, =CCI_S0_QOS_CONTROL_BASE(6)
  120. ldr x1, =0x00FF000C
  121. bl ccn504_set_qos
  122. ldr x0, =CCI_S1_QOS_CONTROL_BASE(6)
  123. ldr x1, =0x00FF000C
  124. bl ccn504_set_qos
  125. ldr x0, =CCI_S2_QOS_CONTROL_BASE(6)
  126. ldr x1, =0x00FF000C
  127. bl ccn504_set_qos
  128. ldr x0, =CCI_S0_QOS_CONTROL_BASE(12)
  129. ldr x1, =0x00FF000C
  130. bl ccn504_set_qos
  131. ldr x0, =CCI_S1_QOS_CONTROL_BASE(12)
  132. ldr x1, =0x00FF000C
  133. bl ccn504_set_qos
  134. ldr x0, =CCI_S2_QOS_CONTROL_BASE(12)
  135. ldr x1, =0x00FF000C
  136. bl ccn504_set_qos
  137. ldr x0, =CCI_S0_QOS_CONTROL_BASE(16)
  138. ldr x1, =0x00FF000C
  139. bl ccn504_set_qos
  140. ldr x0, =CCI_S1_QOS_CONTROL_BASE(16)
  141. ldr x1, =0x00FF000C
  142. bl ccn504_set_qos
  143. ldr x0, =CCI_S2_QOS_CONTROL_BASE(16)
  144. ldr x1, =0x00FF000C
  145. bl ccn504_set_qos
  146. ldr x0, =CCI_S0_QOS_CONTROL_BASE(20)
  147. ldr x1, =0x00FF000C
  148. bl ccn504_set_qos
  149. ldr x0, =CCI_S1_QOS_CONTROL_BASE(20)
  150. ldr x1, =0x00FF000C
  151. bl ccn504_set_qos
  152. ldr x0, =CCI_S2_QOS_CONTROL_BASE(20)
  153. ldr x1, =0x00FF000C
  154. bl ccn504_set_qos
  155. #endif
  156. #ifdef SMMU_BASE
  157. /* Set the SMMU page size in the sACR register */
  158. ldr x1, =SMMU_BASE
  159. ldr w0, [x1, #0x10]
  160. orr w0, w0, #1 << 16 /* set sACR.pagesize to indicate 64K page */
  161. str w0, [x1, #0x10]
  162. #endif
  163. /* Initialize GIC Secure Bank Status */
  164. #if defined(CONFIG_GICV2) || defined(CONFIG_GICV3)
  165. branch_if_slave x0, 1f
  166. bl get_gic_offset
  167. bl gic_init_secure
  168. 1:
  169. #ifdef CONFIG_GICV3
  170. ldr x0, =GICR_BASE
  171. bl gic_init_secure_percpu
  172. #elif defined(CONFIG_GICV2)
  173. bl get_gic_offset
  174. bl gic_init_secure_percpu
  175. #endif
  176. #endif
  177. branch_if_master x0, x1, 2f
  178. #if defined(CONFIG_MP) && defined(CONFIG_ARMV8_MULTIENTRY)
  179. ldr x0, =secondary_boot_func
  180. blr x0
  181. #endif
  182. 2:
  183. #ifdef CONFIG_FSL_TZPC_BP147
  184. /* Set Non Secure access for all devices protected via TZPC */
  185. ldr x1, =TZPCDECPROT_0_SET_BASE /* Decode Protection-0 Set Reg */
  186. orr w0, w0, #1 << 3 /* DCFG_RESET is accessible from NS world */
  187. str w0, [x1]
  188. isb
  189. dsb sy
  190. #endif
  191. #ifdef CONFIG_FSL_TZASC_400
  192. /*
  193. * LS2080 and its personalities does not support TZASC
  194. * So skip TZASC related operations
  195. */
  196. bl get_svr
  197. lsr w0, w0, #16
  198. ldr w1, =SVR_DEV_LS2080A
  199. cmp w0, w1
  200. b.eq 1f
  201. /* Set TZASC so that:
  202. * a. We use only Region0 whose global secure write/read is EN
  203. * b. We use only Region0 whose NSAID write/read is EN
  204. *
  205. * NOTE: As per the CCSR map doc, TZASC 3 and TZASC 4 are just
  206. * placeholders.
  207. */
  208. #ifdef CONFIG_FSL_TZASC_1
  209. ldr x1, =TZASC_GATE_KEEPER(0)
  210. ldr w0, [x1] /* Filter 0 Gate Keeper Register */
  211. orr w0, w0, #1 << 0 /* Set open_request for Filter 0 */
  212. str w0, [x1]
  213. ldr x1, =TZASC_REGION_ATTRIBUTES_0(0)
  214. ldr w0, [x1] /* Region-0 Attributes Register */
  215. orr w0, w0, #1 << 31 /* Set Sec global write en, Bit[31] */
  216. orr w0, w0, #1 << 30 /* Set Sec global read en, Bit[30] */
  217. str w0, [x1]
  218. ldr x1, =TZASC_REGION_ID_ACCESS_0(0)
  219. ldr w0, [x1] /* Region-0 Access Register */
  220. mov w0, #0xFFFFFFFF /* Set nsaid_wr_en and nsaid_rd_en */
  221. str w0, [x1]
  222. #endif
  223. #ifdef CONFIG_FSL_TZASC_2
  224. ldr x1, =TZASC_GATE_KEEPER(1)
  225. ldr w0, [x1] /* Filter 0 Gate Keeper Register */
  226. orr w0, w0, #1 << 0 /* Set open_request for Filter 0 */
  227. str w0, [x1]
  228. ldr x1, =TZASC_REGION_ATTRIBUTES_0(1)
  229. ldr w0, [x1] /* Region-1 Attributes Register */
  230. orr w0, w0, #1 << 31 /* Set Sec global write en, Bit[31] */
  231. orr w0, w0, #1 << 30 /* Set Sec global read en, Bit[30] */
  232. str w0, [x1]
  233. ldr x1, =TZASC_REGION_ID_ACCESS_0(1)
  234. ldr w0, [x1] /* Region-1 Attributes Register */
  235. mov w0, #0xFFFFFFFF /* Set nsaid_wr_en and nsaid_rd_en */
  236. str w0, [x1]
  237. #endif
  238. isb
  239. dsb sy
  240. #endif
  241. 1:
  242. #ifdef CONFIG_ARCH_LS1046A
  243. /* Initialize the L2 RAM latency */
  244. mrs x1, S3_1_c11_c0_2
  245. mov x0, #0x1C7
  246. /* Clear L2 Tag RAM latency and L2 Data RAM latency */
  247. bic x1, x1, x0
  248. /* Set L2 data ram latency bits [2:0] */
  249. orr x1, x1, #0x2
  250. /* set L2 tag ram latency bits [8:6] */
  251. orr x1, x1, #0x80
  252. msr S3_1_c11_c0_2, x1
  253. isb
  254. #endif
  255. #if defined(CONFIG_FSL_LSCH2) && !defined(CONFIG_SPL_BUILD)
  256. bl fsl_ocram_init
  257. #endif
  258. mov lr, x29 /* Restore LR */
  259. ret
  260. ENDPROC(lowlevel_init)
  261. #if defined(CONFIG_FSL_LSCH2) && !defined(CONFIG_SPL_BUILD)
  262. ENTRY(fsl_ocram_init)
  263. mov x28, lr /* Save LR */
  264. bl fsl_clear_ocram
  265. bl fsl_ocram_clear_ecc_err
  266. mov lr, x28 /* Restore LR */
  267. ret
  268. ENDPROC(fsl_ocram_init)
  269. ENTRY(fsl_clear_ocram)
  270. /* Clear OCRAM */
  271. ldr x0, =CONFIG_SYS_FSL_OCRAM_BASE
  272. ldr x1, =(CONFIG_SYS_FSL_OCRAM_BASE + CONFIG_SYS_FSL_OCRAM_SIZE)
  273. mov x2, #0
  274. clear_loop:
  275. str x2, [x0]
  276. add x0, x0, #8
  277. cmp x0, x1
  278. b.lo clear_loop
  279. ret
  280. ENDPROC(fsl_clear_ocram)
  281. ENTRY(fsl_ocram_clear_ecc_err)
  282. /* OCRAM1/2 ECC status bit */
  283. mov w1, #0x60
  284. ldr x0, =DCSR_DCFG_SBEESR2
  285. str w1, [x0]
  286. ldr x0, =DCSR_DCFG_MBEESR2
  287. str w1, [x0]
  288. ret
  289. ENDPROC(fsl_ocram_init)
  290. #endif
  291. #ifdef CONFIG_FSL_LSCH3
  292. .globl get_svr
  293. get_svr:
  294. ldr x1, =FSL_LSCH3_SVR
  295. ldr w0, [x1]
  296. ret
  297. hnf_pstate_poll:
  298. /* x0 has the desired status, return 0 for success, 1 for timeout
  299. * clobber x1, x2, x3, x4, x6, x7
  300. */
  301. mov x1, x0
  302. mov x7, #0 /* flag for timeout */
  303. mrs x3, cntpct_el0 /* read timer */
  304. add x3, x3, #1200 /* timeout after 100 microseconds */
  305. mov x0, #0x18
  306. movk x0, #0x420, lsl #16 /* HNF0_PSTATE_STATUS */
  307. mov w6, #8 /* HN-F node count */
  308. 1:
  309. ldr x2, [x0]
  310. cmp x2, x1 /* check status */
  311. b.eq 2f
  312. mrs x4, cntpct_el0
  313. cmp x4, x3
  314. b.ls 1b
  315. mov x7, #1 /* timeout */
  316. b 3f
  317. 2:
  318. add x0, x0, #0x10000 /* move to next node */
  319. subs w6, w6, #1
  320. cbnz w6, 1b
  321. 3:
  322. mov x0, x7
  323. ret
  324. hnf_set_pstate:
  325. /* x0 has the desired state, clobber x1, x2, x6 */
  326. mov x1, x0
  327. /* power state to SFONLY */
  328. mov w6, #8 /* HN-F node count */
  329. mov x0, #0x10
  330. movk x0, #0x420, lsl #16 /* HNF0_PSTATE_REQ */
  331. 1: /* set pstate to sfonly */
  332. ldr x2, [x0]
  333. and x2, x2, #0xfffffffffffffffc /* & HNFPSTAT_MASK */
  334. orr x2, x2, x1
  335. str x2, [x0]
  336. add x0, x0, #0x10000 /* move to next node */
  337. subs w6, w6, #1
  338. cbnz w6, 1b
  339. ret
  340. ENTRY(__asm_flush_l3_dcache)
  341. /*
  342. * Return status in x0
  343. * success 0
  344. * tmeout 1 for setting SFONLY, 2 for FAM, 3 for both
  345. */
  346. mov x29, lr
  347. mov x8, #0
  348. dsb sy
  349. mov x0, #0x1 /* HNFPSTAT_SFONLY */
  350. bl hnf_set_pstate
  351. mov x0, #0x4 /* SFONLY status */
  352. bl hnf_pstate_poll
  353. cbz x0, 1f
  354. mov x8, #1 /* timeout */
  355. 1:
  356. dsb sy
  357. mov x0, #0x3 /* HNFPSTAT_FAM */
  358. bl hnf_set_pstate
  359. mov x0, #0xc /* FAM status */
  360. bl hnf_pstate_poll
  361. cbz x0, 1f
  362. add x8, x8, #0x2
  363. 1:
  364. mov x0, x8
  365. mov lr, x29
  366. ret
  367. ENDPROC(__asm_flush_l3_dcache)
  368. #endif
  369. #ifdef CONFIG_MP
  370. /* Keep literals not used by the secondary boot code outside it */
  371. .ltorg
  372. /* Using 64 bit alignment since the spin table is accessed as data */
  373. .align 4
  374. .global secondary_boot_code
  375. /* Secondary Boot Code starts here */
  376. secondary_boot_code:
  377. .global __spin_table
  378. __spin_table:
  379. .space CONFIG_MAX_CPUS*SPIN_TABLE_ELEM_SIZE
  380. .align 2
  381. ENTRY(secondary_boot_func)
  382. /*
  383. * MPIDR_EL1 Fields:
  384. * MPIDR[1:0] = AFF0_CPUID <- Core ID (0,1)
  385. * MPIDR[7:2] = AFF0_RES
  386. * MPIDR[15:8] = AFF1_CLUSTERID <- Cluster ID (0,1,2,3)
  387. * MPIDR[23:16] = AFF2_CLUSTERID
  388. * MPIDR[24] = MT
  389. * MPIDR[29:25] = RES0
  390. * MPIDR[30] = U
  391. * MPIDR[31] = ME
  392. * MPIDR[39:32] = AFF3
  393. *
  394. * Linear Processor ID (LPID) calculation from MPIDR_EL1:
  395. * (We only use AFF0_CPUID and AFF1_CLUSTERID for now
  396. * until AFF2_CLUSTERID and AFF3 have non-zero values)
  397. *
  398. * LPID = MPIDR[15:8] | MPIDR[1:0]
  399. */
  400. mrs x0, mpidr_el1
  401. ubfm x1, x0, #8, #15
  402. ubfm x2, x0, #0, #1
  403. orr x10, x2, x1, lsl #2 /* x10 has LPID */
  404. ubfm x9, x0, #0, #15 /* x9 contains MPIDR[15:0] */
  405. /*
  406. * offset of the spin table element for this core from start of spin
  407. * table (each elem is padded to 64 bytes)
  408. */
  409. lsl x1, x10, #6
  410. ldr x0, =__spin_table
  411. /* physical address of this cpus spin table element */
  412. add x11, x1, x0
  413. ldr x0, =__real_cntfrq
  414. ldr x0, [x0]
  415. msr cntfrq_el0, x0 /* set with real frequency */
  416. str x9, [x11, #16] /* LPID */
  417. mov x4, #1
  418. str x4, [x11, #8] /* STATUS */
  419. dsb sy
  420. #if defined(CONFIG_GICV3)
  421. gic_wait_for_interrupt_m x0
  422. #elif defined(CONFIG_GICV2)
  423. bl get_gic_offset
  424. mov x0, x1
  425. gic_wait_for_interrupt_m x0, w1
  426. #endif
  427. slave_cpu:
  428. wfe
  429. ldr x0, [x11]
  430. cbz x0, slave_cpu
  431. #ifndef CONFIG_ARMV8_SWITCH_TO_EL1
  432. mrs x1, sctlr_el2
  433. #else
  434. mrs x1, sctlr_el1
  435. #endif
  436. tbz x1, #25, cpu_is_le
  437. rev x0, x0 /* BE to LE conversion */
  438. cpu_is_le:
  439. ldr x5, [x11, #24]
  440. ldr x6, =IH_ARCH_DEFAULT
  441. cmp x6, x5
  442. b.eq 1f
  443. #ifdef CONFIG_ARMV8_SWITCH_TO_EL1
  444. adr x4, secondary_switch_to_el1
  445. ldr x5, =ES_TO_AARCH64
  446. #else
  447. ldr x4, [x11]
  448. ldr x5, =ES_TO_AARCH32
  449. #endif
  450. bl secondary_switch_to_el2
  451. 1:
  452. #ifdef CONFIG_ARMV8_SWITCH_TO_EL1
  453. adr x4, secondary_switch_to_el1
  454. #else
  455. ldr x4, [x11]
  456. #endif
  457. ldr x5, =ES_TO_AARCH64
  458. bl secondary_switch_to_el2
  459. ENDPROC(secondary_boot_func)
  460. ENTRY(secondary_switch_to_el2)
  461. switch_el x6, 1f, 0f, 0f
  462. 0: ret
  463. 1: armv8_switch_to_el2_m x4, x5, x6
  464. ENDPROC(secondary_switch_to_el2)
  465. ENTRY(secondary_switch_to_el1)
  466. mrs x0, mpidr_el1
  467. ubfm x1, x0, #8, #15
  468. ubfm x2, x0, #0, #1
  469. orr x10, x2, x1, lsl #2 /* x10 has LPID */
  470. lsl x1, x10, #6
  471. ldr x0, =__spin_table
  472. /* physical address of this cpus spin table element */
  473. add x11, x1, x0
  474. ldr x4, [x11]
  475. ldr x5, [x11, #24]
  476. ldr x6, =IH_ARCH_DEFAULT
  477. cmp x6, x5
  478. b.eq 2f
  479. ldr x5, =ES_TO_AARCH32
  480. bl switch_to_el1
  481. 2: ldr x5, =ES_TO_AARCH64
  482. switch_to_el1:
  483. switch_el x6, 0f, 1f, 0f
  484. 0: ret
  485. 1: armv8_switch_to_el1_m x4, x5, x6
  486. ENDPROC(secondary_switch_to_el1)
  487. /* Ensure that the literals used by the secondary boot code are
  488. * assembled within it (this is required so that we can protect
  489. * this area with a single memreserve region
  490. */
  491. .ltorg
  492. /* 64 bit alignment for elements accessed as data */
  493. .align 4
  494. .global __real_cntfrq
  495. __real_cntfrq:
  496. .quad COUNTER_FREQUENCY
  497. .globl __secondary_boot_code_size
  498. .type __secondary_boot_code_size, %object
  499. /* Secondary Boot Code ends here */
  500. __secondary_boot_code_size:
  501. .quad .-secondary_boot_code
  502. #endif