]>
Commit | Line | Data |
---|---|---|
83d290c5 | 1 | /* SPDX-License-Identifier: GPL-2.0+ */ |
0b02b184 DB |
2 | /* |
3 | * armboot - Startup Code for OMAP3530/ARM Cortex CPU-core | |
4 | * | |
5 | * Copyright (c) 2004 Texas Instruments <[email protected]> | |
6 | * | |
7 | * Copyright (c) 2001 Marius Gröger <[email protected]> | |
8 | * Copyright (c) 2002 Alex Züpke <[email protected]> | |
792a09eb | 9 | * Copyright (c) 2002 Gary Jennejohn <[email protected]> |
0b02b184 DB |
10 | * Copyright (c) 2003 Richard Woodruff <[email protected]> |
11 | * Copyright (c) 2003 Kshitij <[email protected]> | |
12 | * Copyright (c) 2006-2008 Syed Mohammed Khasim <[email protected]> | |
0b02b184 DB |
13 | */ |
14 | ||
25ddd1fb | 15 | #include <asm-offsets.h> |
0b02b184 | 16 | #include <config.h> |
a8c68639 | 17 | #include <asm/system.h> |
74236aca | 18 | #include <linux/linkage.h> |
d31d4a2d | 19 | #include <asm/armv7.h> |
0b02b184 | 20 | |
0b02b184 DB |
21 | /************************************************************************* |
22 | * | |
23 | * Startup Code (reset vector) | |
24 | * | |
003b09da PM |
25 | * Do important init only if we don't start from memory! |
26 | * Setup memory and board specific bits prior to relocation. | |
27 | * Relocate armboot to ram. Setup stack. | |
0b02b184 DB |
28 | * |
29 | *************************************************************************/ | |
30 | ||
41623c91 | 31 | .globl reset |
e11c6c27 | 32 | .globl save_boot_params_ret |
ff143d55 | 33 | .type save_boot_params_ret,%function |
d31d4a2d K |
34 | #ifdef CONFIG_ARMV7_LPAE |
35 | .global switch_to_hypervisor_ret | |
36 | #endif | |
561142af HS |
37 | |
38 | reset: | |
e11c6c27 SG |
39 | /* Allow the board to save important registers */ |
40 | b save_boot_params | |
41 | save_boot_params_ret: | |
d31d4a2d K |
42 | #ifdef CONFIG_ARMV7_LPAE |
43 | /* | |
44 | * check for Hypervisor support | |
45 | */ | |
46 | mrc p15, 0, r0, c0, c1, 1 @ read ID_PFR1 | |
47 | and r0, r0, #CPUID_ARM_VIRT_MASK @ mask virtualization bits | |
48 | cmp r0, #(1 << CPUID_ARM_VIRT_SHIFT) | |
49 | beq switch_to_hypervisor | |
50 | switch_to_hypervisor_ret: | |
51 | #endif | |
561142af | 52 | /* |
c4a4e2e2 AP |
53 | * disable interrupts (FIQ and IRQ), also set the cpu to SVC32 mode, |
54 | * except if in HYP mode already | |
561142af HS |
55 | */ |
56 | mrs r0, cpsr | |
c4a4e2e2 AP |
57 | and r1, r0, #0x1f @ mask mode bits |
58 | teq r1, #0x1a @ test for HYP mode | |
59 | bicne r0, r0, #0x1f @ clear all mode bits | |
60 | orrne r0, r0, #0x13 @ set SVC mode | |
61 | orr r0, r0, #0xc0 @ disable FIQ and IRQ | |
561142af HS |
62 | msr cpsr,r0 |
63 | ||
a8c68639 A |
64 | /* |
65 | * Setup vector: | |
66 | * (OMAP4 spl TEXT_BASE is not 32 byte aligned. | |
67 | * Continue to use ROM code vector only in OMAP4 spl) | |
68 | */ | |
840fe95c | 69 | #if !(defined(CONFIG_OMAP44XX) && defined(CONFIG_SPL_BUILD)) |
0f274f53 PF |
70 | /* Set V=0 in CP15 SCTLR register - for VBAR to point to vector */ |
71 | mrc p15, 0, r0, c1, c0, 0 @ Read CP15 SCTLR Register | |
a8c68639 | 72 | bic r0, #CR_V @ V = 0 |
0f274f53 | 73 | mcr p15, 0, r0, c1, c0, 0 @ Write CP15 SCTLR Register |
a8c68639 A |
74 | |
75 | /* Set vector address in CP15 VBAR register */ | |
76 | ldr r0, =_start | |
77 | mcr p15, 0, r0, c12, c0, 0 @Set VBAR | |
78 | #endif | |
79 | ||
561142af HS |
80 | /* the mask ROM code should have PLL and others stable */ |
81 | #ifndef CONFIG_SKIP_LOWLEVEL_INIT | |
80433c9a | 82 | bl cpu_init_cp15 |
b5bd0982 | 83 | #ifndef CONFIG_SKIP_LOWLEVEL_INIT_ONLY |
561142af | 84 | bl cpu_init_crit |
b5bd0982 | 85 | #endif |
561142af HS |
86 | #endif |
87 | ||
e05e5de7 | 88 | bl _main |
561142af HS |
89 | |
90 | /*------------------------------------------------------------------------------*/ | |
91 | ||
e05e5de7 | 92 | ENTRY(c_runtime_cpu_setup) |
c2dd0d45 A |
93 | /* |
94 | * If I-cache is enabled invalidate it | |
95 | */ | |
96 | #ifndef CONFIG_SYS_ICACHE_OFF | |
97 | mcr p15, 0, r0, c7, c5, 0 @ invalidate icache | |
98 | mcr p15, 0, r0, c7, c10, 4 @ DSB | |
99 | mcr p15, 0, r0, c7, c5, 4 @ ISB | |
100 | #endif | |
f8b9d1d3 | 101 | |
e05e5de7 AA |
102 | bx lr |
103 | ||
104 | ENDPROC(c_runtime_cpu_setup) | |
c3d3a541 | 105 | |
6f0dba85 TK |
106 | /************************************************************************* |
107 | * | |
108 | * void save_boot_params(u32 r0, u32 r1, u32 r2, u32 r3) | |
109 | * __attribute__((weak)); | |
110 | * | |
111 | * Stack pointer is not yet initialized at this moment | |
112 | * Don't save anything to stack even if compiled with -O0 | |
113 | * | |
114 | *************************************************************************/ | |
115 | ENTRY(save_boot_params) | |
e11c6c27 | 116 | b save_boot_params_ret @ back to my caller |
6f0dba85 TK |
117 | ENDPROC(save_boot_params) |
118 | .weak save_boot_params | |
119 | ||
d31d4a2d K |
120 | #ifdef CONFIG_ARMV7_LPAE |
121 | ENTRY(switch_to_hypervisor) | |
122 | b switch_to_hypervisor_ret | |
123 | ENDPROC(switch_to_hypervisor) | |
124 | .weak switch_to_hypervisor | |
125 | #endif | |
126 | ||
0b02b184 DB |
127 | /************************************************************************* |
128 | * | |
80433c9a | 129 | * cpu_init_cp15 |
0b02b184 | 130 | * |
80433c9a SG |
131 | * Setup CP15 registers (cache, MMU, TLBs). The I-cache is turned on unless |
132 | * CONFIG_SYS_ICACHE_OFF is defined. | |
0b02b184 DB |
133 | * |
134 | *************************************************************************/ | |
74236aca | 135 | ENTRY(cpu_init_cp15) |
0b02b184 DB |
136 | /* |
137 | * Invalidate L1 I/D | |
138 | */ | |
139 | mov r0, #0 @ set up for MCR | |
140 | mcr p15, 0, r0, c8, c7, 0 @ invalidate TLBs | |
141 | mcr p15, 0, r0, c7, c5, 0 @ invalidate icache | |
c2dd0d45 A |
142 | mcr p15, 0, r0, c7, c5, 6 @ invalidate BP array |
143 | mcr p15, 0, r0, c7, c10, 4 @ DSB | |
144 | mcr p15, 0, r0, c7, c5, 4 @ ISB | |
0b02b184 DB |
145 | |
146 | /* | |
147 | * disable MMU stuff and caches | |
148 | */ | |
149 | mrc p15, 0, r0, c1, c0, 0 | |
150 | bic r0, r0, #0x00002000 @ clear bits 13 (--V-) | |
151 | bic r0, r0, #0x00000007 @ clear bits 2:0 (-CAM) | |
152 | orr r0, r0, #0x00000002 @ set bit 1 (--A-) Align | |
c2dd0d45 A |
153 | orr r0, r0, #0x00000800 @ set bit 11 (Z---) BTB |
154 | #ifdef CONFIG_SYS_ICACHE_OFF | |
155 | bic r0, r0, #0x00001000 @ clear bit 12 (I) I-cache | |
156 | #else | |
157 | orr r0, r0, #0x00001000 @ set bit 12 (I) I-cache | |
158 | #endif | |
0b02b184 | 159 | mcr p15, 0, r0, c1, c0, 0 |
0678587f | 160 | |
c5d4752c SW |
161 | #ifdef CONFIG_ARM_ERRATA_716044 |
162 | mrc p15, 0, r0, c1, c0, 0 @ read system control register | |
163 | orr r0, r0, #1 << 11 @ set bit #11 | |
164 | mcr p15, 0, r0, c1, c0, 0 @ write system control register | |
165 | #endif | |
166 | ||
f71cbfe3 | 167 | #if (defined(CONFIG_ARM_ERRATA_742230) || defined(CONFIG_ARM_ERRATA_794072)) |
0678587f SW |
168 | mrc p15, 0, r0, c15, c0, 1 @ read diagnostic register |
169 | orr r0, r0, #1 << 4 @ set bit #4 | |
170 | mcr p15, 0, r0, c15, c0, 1 @ write diagnostic register | |
171 | #endif | |
172 | ||
173 | #ifdef CONFIG_ARM_ERRATA_743622 | |
174 | mrc p15, 0, r0, c15, c0, 1 @ read diagnostic register | |
175 | orr r0, r0, #1 << 6 @ set bit #6 | |
176 | mcr p15, 0, r0, c15, c0, 1 @ write diagnostic register | |
177 | #endif | |
178 | ||
179 | #ifdef CONFIG_ARM_ERRATA_751472 | |
180 | mrc p15, 0, r0, c15, c0, 1 @ read diagnostic register | |
181 | orr r0, r0, #1 << 11 @ set bit #11 | |
182 | mcr p15, 0, r0, c15, c0, 1 @ write diagnostic register | |
183 | #endif | |
b7588e3b NG |
184 | #ifdef CONFIG_ARM_ERRATA_761320 |
185 | mrc p15, 0, r0, c15, c0, 1 @ read diagnostic register | |
186 | orr r0, r0, #1 << 21 @ set bit #21 | |
187 | mcr p15, 0, r0, c15, c0, 1 @ write diagnostic register | |
188 | #endif | |
0678587f | 189 | |
11d94319 PF |
190 | #ifdef CONFIG_ARM_ERRATA_845369 |
191 | mrc p15, 0, r0, c15, c0, 1 @ read diagnostic register | |
192 | orr r0, r0, #1 << 22 @ set bit #22 | |
193 | mcr p15, 0, r0, c15, c0, 1 @ write diagnostic register | |
194 | #endif | |
195 | ||
c616a0df NM |
196 | mov r5, lr @ Store my Caller |
197 | mrc p15, 0, r1, c0, c0, 0 @ r1 has Read Main ID Register (MIDR) | |
198 | mov r3, r1, lsr #20 @ get variant field | |
199 | and r3, r3, #0xf @ r3 has CPU variant | |
200 | and r4, r1, #0xf @ r4 has CPU revision | |
201 | mov r2, r3, lsl #4 @ shift variant field for combined value | |
202 | orr r2, r4, r2 @ r2 has combined CPU variant + revision | |
203 | ||
204 | #ifdef CONFIG_ARM_ERRATA_798870 | |
205 | cmp r2, #0x30 @ Applies to lower than R3p0 | |
206 | bge skip_errata_798870 @ skip if not affected rev | |
207 | cmp r2, #0x20 @ Applies to including and above R2p0 | |
208 | blt skip_errata_798870 @ skip if not affected rev | |
209 | ||
210 | mrc p15, 1, r0, c15, c0, 0 @ read l2 aux ctrl reg | |
211 | orr r0, r0, #1 << 7 @ Enable hazard-detect timeout | |
212 | push {r1-r5} @ Save the cpu info registers | |
213 | bl v7_arch_cp15_set_l2aux_ctrl | |
214 | isb @ Recommended ISB after l2actlr update | |
215 | pop {r1-r5} @ Restore the cpu info - fall through | |
216 | skip_errata_798870: | |
b45c48a7 NM |
217 | #endif |
218 | ||
a615d0be NM |
219 | #ifdef CONFIG_ARM_ERRATA_801819 |
220 | cmp r2, #0x24 @ Applies to lt including R2p4 | |
221 | bgt skip_errata_801819 @ skip if not affected rev | |
222 | cmp r2, #0x20 @ Applies to including and above R2p0 | |
223 | blt skip_errata_801819 @ skip if not affected rev | |
224 | mrc p15, 0, r0, c0, c0, 6 @ pick up REVIDR reg | |
225 | and r0, r0, #1 << 3 @ check REVIDR[3] | |
226 | cmp r0, #1 << 3 | |
227 | beq skip_errata_801819 @ skip erratum if REVIDR[3] is set | |
228 | ||
229 | mrc p15, 0, r0, c1, c0, 1 @ read auxilary control register | |
230 | orr r0, r0, #3 << 27 @ Disables streaming. All write-allocate | |
231 | @ lines allocate in the L1 or L2 cache. | |
232 | orr r0, r0, #3 << 25 @ Disables streaming. All write-allocate | |
233 | @ lines allocate in the L1 cache. | |
234 | push {r1-r5} @ Save the cpu info registers | |
235 | bl v7_arch_cp15_set_acr | |
236 | pop {r1-r5} @ Restore the cpu info - fall through | |
237 | skip_errata_801819: | |
238 | #endif | |
239 | ||
b45c48a7 | 240 | #ifdef CONFIG_ARM_ERRATA_454179 |
d852600e SS |
241 | mrc p15, 0, r0, c1, c0, 1 @ Read ACR |
242 | ||
b45c48a7 | 243 | cmp r2, #0x21 @ Only on < r2p1 |
d852600e | 244 | orrlt r0, r0, #(0x3 << 6) @ Set DBSM(BIT7) and IBE(BIT6) bits |
b45c48a7 | 245 | |
b45c48a7 NM |
246 | push {r1-r5} @ Save the cpu info registers |
247 | bl v7_arch_cp15_set_acr | |
248 | pop {r1-r5} @ Restore the cpu info - fall through | |
5902f4ce NM |
249 | #endif |
250 | ||
251 | #ifdef CONFIG_ARM_ERRATA_430973 | |
d852600e SS |
252 | mrc p15, 0, r0, c1, c0, 1 @ Read ACR |
253 | ||
5902f4ce | 254 | cmp r2, #0x21 @ Only on < r2p1 |
d852600e | 255 | orrlt r0, r0, #(0x1 << 6) @ Set IBE bit |
5902f4ce | 256 | |
5902f4ce NM |
257 | push {r1-r5} @ Save the cpu info registers |
258 | bl v7_arch_cp15_set_acr | |
259 | pop {r1-r5} @ Restore the cpu info - fall through | |
9b4d65f9 NM |
260 | #endif |
261 | ||
262 | #ifdef CONFIG_ARM_ERRATA_621766 | |
d852600e SS |
263 | mrc p15, 0, r0, c1, c0, 1 @ Read ACR |
264 | ||
9b4d65f9 | 265 | cmp r2, #0x21 @ Only on < r2p1 |
d852600e | 266 | orrlt r0, r0, #(0x1 << 5) @ Set L1NEON bit |
9b4d65f9 | 267 | |
9b4d65f9 NM |
268 | push {r1-r5} @ Save the cpu info registers |
269 | bl v7_arch_cp15_set_acr | |
270 | pop {r1-r5} @ Restore the cpu info - fall through | |
19a75b8c SS |
271 | #endif |
272 | ||
273 | #ifdef CONFIG_ARM_ERRATA_725233 | |
d852600e SS |
274 | mrc p15, 1, r0, c9, c0, 2 @ Read L2ACR |
275 | ||
19a75b8c | 276 | cmp r2, #0x21 @ Only on < r2p1 (Cortex A8) |
d852600e | 277 | orrlt r0, r0, #(0x1 << 27) @ L2 PLD data forwarding disable |
19a75b8c | 278 | |
19a75b8c SS |
279 | push {r1-r5} @ Save the cpu info registers |
280 | bl v7_arch_cp15_set_l2aux_ctrl | |
281 | pop {r1-r5} @ Restore the cpu info - fall through | |
c616a0df NM |
282 | #endif |
283 | ||
8776350d NM |
284 | #ifdef CONFIG_ARM_ERRATA_852421 |
285 | mrc p15, 0, r0, c15, c0, 1 @ read diagnostic register | |
286 | orr r0, r0, #1 << 24 @ set bit #24 | |
287 | mcr p15, 0, r0, c15, c0, 1 @ write diagnostic register | |
288 | #endif | |
289 | ||
290 | #ifdef CONFIG_ARM_ERRATA_852423 | |
291 | mrc p15, 0, r0, c15, c0, 1 @ read diagnostic register | |
292 | orr r0, r0, #1 << 12 @ set bit #12 | |
293 | mcr p15, 0, r0, c15, c0, 1 @ write diagnostic register | |
294 | #endif | |
295 | ||
c616a0df | 296 | mov pc, r5 @ back to my caller |
74236aca | 297 | ENDPROC(cpu_init_cp15) |
0b02b184 | 298 | |
b5bd0982 SG |
299 | #if !defined(CONFIG_SKIP_LOWLEVEL_INIT) && \ |
300 | !defined(CONFIG_SKIP_LOWLEVEL_INIT_ONLY) | |
80433c9a SG |
301 | /************************************************************************* |
302 | * | |
303 | * CPU_init_critical registers | |
304 | * | |
305 | * setup important registers | |
306 | * setup memory timing | |
307 | * | |
308 | *************************************************************************/ | |
74236aca | 309 | ENTRY(cpu_init_crit) |
0b02b184 DB |
310 | /* |
311 | * Jump to board specific initialization... | |
312 | * The Mask ROM will have already initialized | |
313 | * basic memory. Go here to bump up clock rate and handle | |
314 | * wake up conditions. | |
315 | */ | |
63ee53a7 | 316 | b lowlevel_init @ go setup pll,mux,memory |
74236aca | 317 | ENDPROC(cpu_init_crit) |
22193540 | 318 | #endif |