xref: /plan9/sys/src/9/bcm/l.s (revision 5d9de2d38d2503efca29e12e0e32036368a7a75f)
1/*
2 * Broadcom bcm2835 SoC, as used in Raspberry Pi
3 * arm1176jzf-s processor (armv6)
4 */
5
6#include "arm.s"
7
8TEXT _start(SB), 1, $-4
9	/*
10	 * load physical base for SB addressing while mmu is off
11	 * keep a handy zero in R0 until first function call
12	 */
13	MOVW	$setR12(SB), R12
14	SUB	$KZERO, R12
15	ADD	$PHYSDRAM, R12
16	MOVW	$0, R0
17
18	/*
19	 * SVC mode, interrupts disabled
20	 */
21	MOVW	$(PsrDirq|PsrDfiq|PsrMsvc), R1
22	MOVW	R1, CPSR
23
24	/*
25	 * disable the mmu and L1 caches
26	 * invalidate caches and tlb
27	 */
28	MRC	CpSC, 0, R1, C(CpCONTROL), C(0), CpMainctl
29	BIC	$(CpCdcache|CpCicache|CpCpredict|CpCmmu), R1
30	MCR	CpSC, 0, R1, C(CpCONTROL), C(0), CpMainctl
31	MCR	CpSC, 0, R0, C(CpCACHE), C(CpCACHEinvu), CpCACHEall
32	MCR	CpSC, 0, R0, C(CpTLB), C(CpTLBinvu), CpTLBinv
33	ISB
34
35	/*
36	 * clear mach and page tables
37	 */
38	MOVW	$PADDR(MACHADDR), R1
39	MOVW	$PADDR(KTZERO), R2
40_ramZ:
41	MOVW	R0, (R1)
42	ADD	$4, R1
43	CMP	R1, R2
44	BNE	_ramZ
45
46	/*
47	 * start stack at top of mach (physical addr)
48	 * set up page tables for kernel
49	 */
50	MOVW	$PADDR(MACHADDR+MACHSIZE-4), R13
51	BL	,mmuinit(SB)
52
53	/*
54	 * set up domain access control and page table base
55	 */
56	MOVW	$Client, R1
57	MCR	CpSC, 0, R1, C(CpDAC), C(0)
58	MOVW	$PADDR(L1), R1
59	MCR	CpSC, 0, R1, C(CpTTB), C(0)
60
61	/*
62	 * enable caches, mmu, and high vectors
63	 */
64	MRC	CpSC, 0, R0, C(CpCONTROL), C(0), CpMainctl
65	ORR	$(CpChv|CpCdcache|CpCicache|CpCmmu), R0
66	MCR	CpSC, 0, R0, C(CpCONTROL), C(0), CpMainctl
67	ISB
68
69	/*
70	 * switch SB, SP, and PC into KZERO space
71	 */
72	MOVW	$setR12(SB), R12
73	MOVW	$(MACHADDR+MACHSIZE-4), R13
74	MOVW	$_startpg(SB), R15
75
76TEXT _startpg(SB), 1, $-4
77
78	/*
79	 * enable cycle counter
80	 */
81	MOVW	$1, R1
82	MCR	CpSC, 0, R1, C(CpSPM), C(CpSPMperf), CpSPMctl
83
84	/*
85	 * call main and loop forever if it returns
86	 */
87	BL	,main(SB)
88	B	,0(PC)
89
90	BL	_div(SB)		/* hack to load _div, etc. */
91
92TEXT fsrget(SB), 1, $-4				/* data fault status */
93	MRC	CpSC, 0, R0, C(CpFSR), C(0), CpFSRdata
94	RET
95
96TEXT ifsrget(SB), 1, $-4			/* instruction fault status */
97	MRC	CpSC, 0, R0, C(CpFSR), C(0), CpFSRinst
98	RET
99
100TEXT farget(SB), 1, $-4				/* fault address */
101	MRC	CpSC, 0, R0, C(CpFAR), C(0x0)
102	RET
103
104TEXT lcycles(SB), 1, $-4
105	MRC	CpSC, 0, R0, C(CpSPM), C(CpSPMperf), CpSPMcyc
106	RET
107
108TEXT splhi(SB), 1, $-4
109	MOVW	$(MACHADDR+4), R2		/* save caller pc in Mach */
110	MOVW	R14, 0(R2)
111
112	MOVW	CPSR, R0			/* turn off irqs (but not fiqs) */
113	ORR	$(PsrDirq), R0, R1
114	MOVW	R1, CPSR
115	RET
116
117TEXT splfhi(SB), 1, $-4
118	MOVW	$(MACHADDR+4), R2		/* save caller pc in Mach */
119	MOVW	R14, 0(R2)
120
121	MOVW	CPSR, R0			/* turn off irqs and fiqs */
122	ORR	$(PsrDirq|PsrDfiq), R0, R1
123	MOVW	R1, CPSR
124	RET
125
126TEXT splflo(SB), 1, $-4
127	MOVW	CPSR, R0			/* turn on fiqs */
128	BIC	$(PsrDfiq), R0, R1
129	MOVW	R1, CPSR
130	RET
131
132TEXT spllo(SB), 1, $-4
133	MOVW	CPSR, R0			/* turn on irqs and fiqs */
134	BIC	$(PsrDirq|PsrDfiq), R0, R1
135	MOVW	R1, CPSR
136	RET
137
138TEXT splx(SB), 1, $-4
139	MOVW	$(MACHADDR+0x04), R2		/* save caller pc in Mach */
140	MOVW	R14, 0(R2)
141
142	MOVW	R0, R1				/* reset interrupt level */
143	MOVW	CPSR, R0
144	MOVW	R1, CPSR
145	RET
146
147TEXT spldone(SB), 1, $0				/* end marker for devkprof.c */
148	RET
149
150TEXT islo(SB), 1, $-4
151	MOVW	CPSR, R0
152	AND	$(PsrDirq), R0
153	EOR	$(PsrDirq), R0
154	RET
155
156TEXT	tas(SB), $-4
157TEXT	_tas(SB), $-4
158	MOVW	R0,R1
159	MOVW	$1,R0
160	SWPW	R0,(R1)			/* fix: deprecated in armv6 */
161	RET
162
163TEXT setlabel(SB), 1, $-4
164	MOVW	R13, 0(R0)		/* sp */
165	MOVW	R14, 4(R0)		/* pc */
166	MOVW	$0, R0
167	RET
168
169TEXT gotolabel(SB), 1, $-4
170	MOVW	0(R0), R13		/* sp */
171	MOVW	4(R0), R14		/* pc */
172	MOVW	$1, R0
173	RET
174
175TEXT getcallerpc(SB), 1, $-4
176	MOVW	0(R13), R0
177	RET
178
179TEXT idlehands(SB), $-4
180	BARRIERS
181	MOVW	CPSR, R3
182	BIC	$(PsrDirq|PsrDfiq), R3, R1		/* spllo */
183	MOVW	R1, CPSR
184
185	MOVW	$0, R0				/* wait for interrupt */
186	MCR	CpSC, 0, R0, C(CpCACHE), C(CpCACHEintr), CpCACHEwait
187	ISB
188
189	MOVW	R3, CPSR			/* splx */
190	RET
191
192
193TEXT coherence(SB), $-4
194	BARRIERS
195	RET
196
197/*
198 * invalidate tlb
199 */
200TEXT mmuinvalidate(SB), 1, $-4
201	MOVW	$0, R0
202	MCR	CpSC, 0, R0, C(CpTLB), C(CpTLBinvu), CpTLBinv
203	BARRIERS
204	RET
205
206/*
207 * mmuinvalidateaddr(va)
208 *   invalidate tlb entry for virtual page address va, ASID 0
209 */
210TEXT mmuinvalidateaddr(SB), 1, $-4
211	MCR	CpSC, 0, R0, C(CpTLB), C(CpTLBinvu), CpTLBinvse
212	BARRIERS
213	RET
214
215/*
216 * drain write buffer
217 * writeback and invalidate data cache
218 */
219TEXT cachedwbinv(SB), 1, $-4
220	DSB
221	MOVW	$0, R0
222	MCR	CpSC, 0, R0, C(CpCACHE), C(CpCACHEwbi), CpCACHEall
223	RET
224
225/*
226 * cachedwbinvse(va, n)
227 *   drain write buffer
228 *   writeback and invalidate data cache range [va, va+n)
229 */
230TEXT cachedwbinvse(SB), 1, $-4
231	MOVW	R0, R1		/* DSB clears R0 */
232	DSB
233	MOVW	n+4(FP), R2
234	ADD	R1, R2
235	SUB	$1, R2
236	BIC	$(CACHELINESZ-1), R1
237	BIC	$(CACHELINESZ-1), R2
238	MCRR(CpSC, 0, 2, 1, CpCACHERANGEdwbi)
239	RET
240
241/*
242 * cachedwbse(va, n)
243 *   drain write buffer
244 *   writeback data cache range [va, va+n)
245 */
246TEXT cachedwbse(SB), 1, $-4
247	MOVW	R0, R1		/* DSB clears R0 */
248	DSB
249	MOVW	n+4(FP), R2
250	ADD	R1, R2
251	BIC	$(CACHELINESZ-1), R1
252	BIC	$(CACHELINESZ-1), R2
253	MCRR(CpSC, 0, 2, 1, CpCACHERANGEdwb)
254	RET
255
256/*
257 * drain write buffer and prefetch buffer
258 * writeback and invalidate data cache
259 * invalidate instruction cache
260 */
261TEXT cacheuwbinv(SB), 1, $-4
262	BARRIERS
263	MOVW	$0, R0
264	MCR	CpSC, 0, R0, C(CpCACHE), C(CpCACHEwbi), CpCACHEall
265	MCR	CpSC, 0, R0, C(CpCACHE), C(CpCACHEinvi), CpCACHEall
266	RET
267
268/*
269 * invalidate instruction cache
270 */
271TEXT cacheiinv(SB), 1, $-4
272	MOVW	$0, R0
273	MCR	CpSC, 0, R0, C(CpCACHE), C(CpCACHEinvi), CpCACHEall
274	RET
275