exception.S revision 1.1.8.4 1 1.1.8.4 thorpej /* $NetBSD: exception.S,v 1.1.8.4 2002/08/19 21:39:02 thorpej Exp $ */
2 1.1.8.2 nathanw
3 1.1.8.2 nathanw /*
4 1.1.8.2 nathanw * Copyright (c) 1994-1997 Mark Brinicombe.
5 1.1.8.2 nathanw * Copyright (c) 1994 Brini.
6 1.1.8.2 nathanw * All rights reserved.
7 1.1.8.2 nathanw *
8 1.1.8.2 nathanw * This code is derived from software written for Brini by Mark Brinicombe
9 1.1.8.2 nathanw *
10 1.1.8.2 nathanw * Redistribution and use in source and binary forms, with or without
11 1.1.8.2 nathanw * modification, are permitted provided that the following conditions
12 1.1.8.2 nathanw * are met:
13 1.1.8.2 nathanw * 1. Redistributions of source code must retain the above copyright
14 1.1.8.2 nathanw * notice, this list of conditions and the following disclaimer.
15 1.1.8.2 nathanw * 2. Redistributions in binary form must reproduce the above copyright
16 1.1.8.2 nathanw * notice, this list of conditions and the following disclaimer in the
17 1.1.8.2 nathanw * documentation and/or other materials provided with the distribution.
18 1.1.8.2 nathanw * 3. All advertising materials mentioning features or use of this software
19 1.1.8.2 nathanw * must display the following acknowledgement:
20 1.1.8.2 nathanw * This product includes software developed by Brini.
21 1.1.8.2 nathanw * 4. The name of the company nor the name of the author may be used to
22 1.1.8.2 nathanw * endorse or promote products derived from this software without specific
23 1.1.8.2 nathanw * prior written permission.
24 1.1.8.2 nathanw *
25 1.1.8.2 nathanw * THIS SOFTWARE IS PROVIDED BY BRINI ``AS IS'' AND ANY EXPRESS OR IMPLIED
26 1.1.8.2 nathanw * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
27 1.1.8.2 nathanw * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
28 1.1.8.2 nathanw * IN NO EVENT SHALL BRINI OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
29 1.1.8.2 nathanw * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
30 1.1.8.2 nathanw * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
31 1.1.8.2 nathanw * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
32 1.1.8.2 nathanw * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
33 1.1.8.2 nathanw * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
34 1.1.8.2 nathanw * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
35 1.1.8.2 nathanw * SUCH DAMAGE.
36 1.1.8.2 nathanw *
37 1.1.8.2 nathanw * RiscBSD kernel project
38 1.1.8.2 nathanw *
39 1.1.8.2 nathanw * exception.S
40 1.1.8.2 nathanw *
41 1.1.8.2 nathanw * Low level handlers for exception vectors
42 1.1.8.2 nathanw *
43 1.1.8.2 nathanw * Created : 24/09/94
44 1.1.8.2 nathanw *
45 1.1.8.2 nathanw * Based on kate/display/abort.s
46 1.1.8.2 nathanw */
47 1.1.8.2 nathanw
48 1.1.8.2 nathanw #include "opt_ipkdb.h"
49 1.1.8.2 nathanw #include <machine/asm.h>
50 1.1.8.2 nathanw #include <machine/cpu.h>
51 1.1.8.2 nathanw #include <machine/frame.h>
52 1.1.8.2 nathanw #include "assym.h"
53 1.1.8.2 nathanw
54 1.1.8.2 nathanw .text
55 1.1.8.2 nathanw .align 0
56 1.1.8.2 nathanw
57 1.1.8.2 nathanw Lastpending:
58 1.1.8.2 nathanw .word _C_LABEL(astpending)
59 1.1.8.2 nathanw
60 1.1.8.2 nathanw /*
61 1.1.8.2 nathanw * General exception exit handler
62 1.1.8.2 nathanw *
63 1.1.8.2 nathanw * It exits straight away if not returning to USR mode.
64 1.1.8.2 nathanw * This loops around delivering any pending ASTs.
65 1.1.8.2 nathanw * Interrupts are disabled at suitable points to avoid ASTs
66 1.1.8.2 nathanw * being posted between testing and exit to user mode.
67 1.1.8.2 nathanw *
68 1.1.8.2 nathanw * This function uses PULLFRAMEFROMSVCANDEXIT thus should
69 1.1.8.2 nathanw * only be called if the exception handler used PUSHFRAMEINSVC
70 1.1.8.2 nathanw */
71 1.1.8.2 nathanw
72 1.1.8.2 nathanw exception_exit:
73 1.1.8.4 thorpej mrs r4, cpsr /* Get CPSR */
74 1.1.8.2 nathanw
75 1.1.8.2 nathanw ldr r0, [sp] /* Get the SPSR from stack */
76 1.1.8.2 nathanw and r0, r0, #(PSR_MODE) /* Test for USR32 mode before the AST */
77 1.1.8.2 nathanw teq r0, #(PSR_USR32_MODE)
78 1.1.8.4 thorpej bne .Ldo_exit /* Not USR mode so no AST delivery */
79 1.1.8.2 nathanw
80 1.1.8.2 nathanw ldr r5, Lastpending /* Get address of astpending */
81 1.1.8.2 nathanw
82 1.1.8.2 nathanw Lexception_exit_loop:
83 1.1.8.2 nathanw orr r0, r4, #(I32_bit) /* Block IRQs */
84 1.1.8.2 nathanw msr cpsr_all, r0
85 1.1.8.2 nathanw
86 1.1.8.2 nathanw ldr r1, [r5] /* Do we have an AST pending */
87 1.1.8.2 nathanw teq r1, #0x00000000
88 1.1.8.4 thorpej bne .Ldo_ast
89 1.1.8.2 nathanw
90 1.1.8.2 nathanw PULLFRAMEFROMSVCANDEXIT /* No AST so exit */
91 1.1.8.2 nathanw
92 1.1.8.4 thorpej .Ldo_ast:
93 1.1.8.2 nathanw mov r1, #0x00000000 /* Clear ast pending */
94 1.1.8.2 nathanw str r1, [r5]
95 1.1.8.2 nathanw
96 1.1.8.2 nathanw msr cpsr_all, r4 /* Restore interrupts */
97 1.1.8.2 nathanw
98 1.1.8.2 nathanw mov r0, sp /* arg 0 = trap frame */
99 1.1.8.2 nathanw bl _C_LABEL(ast) /* call the AST handler */
100 1.1.8.2 nathanw b Lexception_exit_loop /* Try and exit again */
101 1.1.8.2 nathanw
102 1.1.8.4 thorpej .Ldo_exit:
103 1.1.8.2 nathanw orr r0, r4, #(I32_bit) /* Disable interupts */
104 1.1.8.2 nathanw msr cpsr_all, r0
105 1.1.8.2 nathanw
106 1.1.8.2 nathanw PULLFRAMEFROMSVCANDEXIT /* Restore the trap frame and exit */
107 1.1.8.2 nathanw
108 1.1.8.2 nathanw /*
109 1.1.8.2 nathanw * reset_entry:
110 1.1.8.2 nathanw *
111 1.1.8.2 nathanw * Handler for Reset exception.
112 1.1.8.2 nathanw */
113 1.1.8.2 nathanw ASENTRY_NP(reset_entry)
114 1.1.8.2 nathanw adr r0, Lreset_panicmsg
115 1.1.8.2 nathanw mov r1, lr
116 1.1.8.2 nathanw bl _C_LABEL(panic)
117 1.1.8.2 nathanw /* NOTREACHED */
118 1.1.8.2 nathanw Lreset_panicmsg:
119 1.1.8.2 nathanw .asciz "Reset vector called, LR = 0x%08x"
120 1.1.8.2 nathanw .balign 4
121 1.1.8.2 nathanw
122 1.1.8.2 nathanw /*
123 1.1.8.2 nathanw * swi_entry
124 1.1.8.2 nathanw *
125 1.1.8.2 nathanw * Handler for the Software Interrupt exception.
126 1.1.8.2 nathanw */
127 1.1.8.2 nathanw ASENTRY_NP(swi_entry)
128 1.1.8.2 nathanw PUSHFRAME
129 1.1.8.2 nathanw
130 1.1.8.2 nathanw mov r0, sp /* Pass the frame to any function */
131 1.1.8.2 nathanw
132 1.1.8.3 nathanw bl _C_LABEL(swi_handler) /* It's a SWI ! */
133 1.1.8.2 nathanw
134 1.1.8.2 nathanw ldr r5, Lastpending /* Get address of astpending */
135 1.1.8.4 thorpej mrs r4, cpsr /* Get CPSR */
136 1.1.8.2 nathanw
137 1.1.8.4 thorpej .Lswi_exit_loop:
138 1.1.8.2 nathanw orr r0, r4, #(I32_bit) /* Disable IRQs */
139 1.1.8.2 nathanw msr cpsr_all, r0
140 1.1.8.2 nathanw
141 1.1.8.2 nathanw ldr r1, [r5] /* Do we have an AST pending */
142 1.1.8.2 nathanw teq r1, #0x00000000
143 1.1.8.4 thorpej bne .Ldo_swi_ast
144 1.1.8.2 nathanw
145 1.1.8.2 nathanw PULLFRAME
146 1.1.8.2 nathanw movs pc, lr /* Exit */
147 1.1.8.2 nathanw
148 1.1.8.4 thorpej .Ldo_swi_ast:
149 1.1.8.2 nathanw mov r1, #0x00000000 /* Clear ast pending */
150 1.1.8.2 nathanw str r1, [r5]
151 1.1.8.2 nathanw
152 1.1.8.2 nathanw msr cpsr_all, r4 /* Restore interrupts */
153 1.1.8.2 nathanw
154 1.1.8.2 nathanw mov r0, sp /* arg 0 = trap frame */
155 1.1.8.2 nathanw bl _C_LABEL(ast) /* call the AST handler */
156 1.1.8.4 thorpej b .Lswi_exit_loop /* Try and exit again */
157 1.1.8.2 nathanw
158 1.1.8.2 nathanw /*
159 1.1.8.2 nathanw * prefetch_abort_entry:
160 1.1.8.2 nathanw *
161 1.1.8.2 nathanw * Handler for the Prefetch Abort exception.
162 1.1.8.2 nathanw */
163 1.1.8.2 nathanw ASENTRY_NP(prefetch_abort_entry)
164 1.1.8.2 nathanw sub lr, lr, #0x00000004 /* Adjust the lr */
165 1.1.8.2 nathanw
166 1.1.8.2 nathanw PUSHFRAMEINSVC
167 1.1.8.2 nathanw
168 1.1.8.2 nathanw mov r0, sp /* pass the stack pointer as r0 */
169 1.1.8.2 nathanw
170 1.1.8.2 nathanw add lr, pc, #exception_exit - . - 8
171 1.1.8.2 nathanw ldr r1, Lprefetch_abort_handler_address
172 1.1.8.2 nathanw ldr pc, [r1]
173 1.1.8.2 nathanw
174 1.1.8.2 nathanw Lprefetch_abort_handler_address:
175 1.1.8.2 nathanw .word _C_LABEL(prefetch_abort_handler_address)
176 1.1.8.2 nathanw
177 1.1.8.2 nathanw .data
178 1.1.8.2 nathanw .global _C_LABEL(prefetch_abort_handler_address)
179 1.1.8.2 nathanw
180 1.1.8.2 nathanw _C_LABEL(prefetch_abort_handler_address):
181 1.1.8.2 nathanw .word abortprefetch
182 1.1.8.2 nathanw
183 1.1.8.2 nathanw .text
184 1.1.8.2 nathanw abortprefetch:
185 1.1.8.2 nathanw add r0, pc, #abortprefetchmsg - . - 8
186 1.1.8.2 nathanw b _C_LABEL(panic)
187 1.1.8.2 nathanw
188 1.1.8.2 nathanw abortprefetchmsg:
189 1.1.8.2 nathanw .asciz "abortprefetch"
190 1.1.8.2 nathanw .align 0
191 1.1.8.2 nathanw
192 1.1.8.2 nathanw /*
193 1.1.8.2 nathanw * data_abort_entry:
194 1.1.8.2 nathanw *
195 1.1.8.2 nathanw * Handler for the Data Abort exception.
196 1.1.8.2 nathanw */
197 1.1.8.2 nathanw ASENTRY_NP(data_abort_entry)
198 1.1.8.2 nathanw sub lr, lr, #0x00000008 /* Adjust the lr */
199 1.1.8.2 nathanw
200 1.1.8.2 nathanw PUSHFRAMEINSVC /* Push trap frame and switch */
201 1.1.8.2 nathanw /* to SVC32 mode */
202 1.1.8.2 nathanw
203 1.1.8.2 nathanw mov r0, sp /* pass the stack pointer as r0 */
204 1.1.8.2 nathanw
205 1.1.8.2 nathanw add lr, pc, #exception_exit - . - 8
206 1.1.8.2 nathanw ldr r1, Ldata_abort_handler_address
207 1.1.8.2 nathanw ldr pc, [r1]
208 1.1.8.2 nathanw
209 1.1.8.2 nathanw Ldata_abort_handler_address:
210 1.1.8.2 nathanw .word _C_LABEL(data_abort_handler_address)
211 1.1.8.2 nathanw
212 1.1.8.2 nathanw .data
213 1.1.8.2 nathanw .global _C_LABEL(data_abort_handler_address)
214 1.1.8.2 nathanw _C_LABEL(data_abort_handler_address):
215 1.1.8.2 nathanw .word abortdata
216 1.1.8.2 nathanw
217 1.1.8.2 nathanw .text
218 1.1.8.2 nathanw abortdata:
219 1.1.8.2 nathanw add r0, pc, #abortdatamsg - . - 8
220 1.1.8.2 nathanw b _C_LABEL(panic)
221 1.1.8.2 nathanw
222 1.1.8.2 nathanw abortdatamsg:
223 1.1.8.2 nathanw .asciz "abortdata"
224 1.1.8.2 nathanw .align 0
225 1.1.8.2 nathanw
226 1.1.8.2 nathanw /*
227 1.1.8.2 nathanw * address_exception_entry:
228 1.1.8.2 nathanw *
229 1.1.8.2 nathanw * Handler for the Address Exception exception.
230 1.1.8.2 nathanw *
231 1.1.8.2 nathanw * NOTE: This exception isn't really used on arm32. We
232 1.1.8.2 nathanw * print a warning message to the console and then treat
233 1.1.8.2 nathanw * it like a Data Abort.
234 1.1.8.2 nathanw */
235 1.1.8.2 nathanw ASENTRY_NP(address_exception_entry)
236 1.1.8.2 nathanw mrs r1, cpsr_all
237 1.1.8.2 nathanw mrs r2, spsr_all
238 1.1.8.2 nathanw mov r3, lr
239 1.1.8.2 nathanw adr r0, Laddress_exception_msg
240 1.1.8.2 nathanw bl _C_LABEL(printf) /* XXX CLOBBERS LR!! */
241 1.1.8.2 nathanw b data_abort_entry
242 1.1.8.2 nathanw Laddress_exception_msg:
243 1.1.8.2 nathanw .asciz "Address Exception CPSR=0x%08x SPSR=0x%08x LR=0x%08x\n"
244 1.1.8.2 nathanw .balign 4
245 1.1.8.2 nathanw
246 1.1.8.2 nathanw /*
247 1.1.8.2 nathanw * undefined_entry:
248 1.1.8.2 nathanw *
249 1.1.8.2 nathanw * Handler for the Undefined Instruction exception.
250 1.1.8.2 nathanw *
251 1.1.8.2 nathanw * We indirect the undefined vector via the handler address
252 1.1.8.2 nathanw * in the data area. Entry to the undefined handler must
253 1.1.8.2 nathanw * look like direct entry from the vector.
254 1.1.8.2 nathanw */
255 1.1.8.2 nathanw ASENTRY_NP(undefined_entry)
256 1.1.8.2 nathanw #ifdef IPKDB
257 1.1.8.2 nathanw /*
258 1.1.8.2 nathanw * IPKDB must be hooked in at the earliest possible entry point.
259 1.1.8.2 nathanw *
260 1.1.8.2 nathanw */
261 1.1.8.2 nathanw /*
262 1.1.8.2 nathanw * Make room for all registers saving real r0-r7 and r15.
263 1.1.8.2 nathanw * The remaining registers are updated later.
264 1.1.8.2 nathanw */
265 1.1.8.2 nathanw stmfd sp!, {r0,r1} /* psr & spsr */
266 1.1.8.2 nathanw stmfd sp!, {lr} /* pc */
267 1.1.8.2 nathanw stmfd sp!, {r0-r14} /* r0-r7, r8-r14 */
268 1.1.8.2 nathanw /*
269 1.1.8.2 nathanw * Get previous psr.
270 1.1.8.2 nathanw */
271 1.1.8.2 nathanw mrs r7, cpsr_all
272 1.1.8.2 nathanw mrs r0, spsr_all
273 1.1.8.2 nathanw str r0, [sp, #(16*4)]
274 1.1.8.2 nathanw /*
275 1.1.8.2 nathanw * Test for user mode.
276 1.1.8.2 nathanw */
277 1.1.8.2 nathanw tst r0, #0xf
278 1.1.8.4 thorpej bne .Lprenotuser_push
279 1.1.8.2 nathanw add r1, sp, #(8*4)
280 1.1.8.2 nathanw stmia r1,{r8-r14}^ /* store user mode r8-r14*/
281 1.1.8.4 thorpej b .Lgoipkdb
282 1.1.8.2 nathanw /*
283 1.1.8.2 nathanw * Switch to previous mode to get r8-r13.
284 1.1.8.2 nathanw */
285 1.1.8.4 thorpej .Lprenotuser_push:
286 1.1.8.2 nathanw orr r0, r0, #(I32_bit) /* disable interrupts */
287 1.1.8.2 nathanw msr cpsr_all, r0
288 1.1.8.2 nathanw mov r1, r8
289 1.1.8.2 nathanw mov r2, r9
290 1.1.8.2 nathanw mov r3, r10
291 1.1.8.2 nathanw mov r4, r11
292 1.1.8.2 nathanw mov r5, r12
293 1.1.8.2 nathanw mov r6, r13
294 1.1.8.2 nathanw msr cpsr_all, r7 /* back to undefined mode */
295 1.1.8.2 nathanw add r8, sp, #(8*4)
296 1.1.8.2 nathanw stmia r8, {r1-r6} /* r8-r13 */
297 1.1.8.2 nathanw /*
298 1.1.8.2 nathanw * Now back to previous mode to get r14 and spsr.
299 1.1.8.2 nathanw */
300 1.1.8.2 nathanw msr cpsr_all, r0
301 1.1.8.2 nathanw mov r1, r14
302 1.1.8.2 nathanw mrs r2, spsr
303 1.1.8.2 nathanw msr cpsr_all, r7 /* back to undefined mode */
304 1.1.8.2 nathanw str r1, [sp, #(14*4)] /* r14 */
305 1.1.8.2 nathanw str r2, [sp, #(17*4)] /* spsr */
306 1.1.8.2 nathanw /*
307 1.1.8.2 nathanw * Now to IPKDB.
308 1.1.8.2 nathanw */
309 1.1.8.4 thorpej .Lgoipkdb:
310 1.1.8.2 nathanw mov r0, sp
311 1.1.8.2 nathanw bl _C_LABEL(ipkdb_trap_glue)
312 1.1.8.4 thorpej ldr r1, .Lipkdb_trap_return
313 1.1.8.2 nathanw str r0,[r1]
314 1.1.8.2 nathanw /*
315 1.1.8.2 nathanw * Have to load all registers from the stack.
316 1.1.8.2 nathanw *
317 1.1.8.2 nathanw * Start with spsr and pc.
318 1.1.8.2 nathanw */
319 1.1.8.2 nathanw ldr r0, [sp, #(16*4)] /* spsr */
320 1.1.8.2 nathanw ldr r1, [sp, #(15*4)] /* r15 */
321 1.1.8.2 nathanw msr spsr_all, r0
322 1.1.8.2 nathanw mov r14, r1
323 1.1.8.2 nathanw /*
324 1.1.8.2 nathanw * Test for user mode.
325 1.1.8.2 nathanw */
326 1.1.8.2 nathanw tst r0, #0xf
327 1.1.8.4 thorpej bne .Lprenotuser_pull
328 1.1.8.2 nathanw add r1, sp, #(8*4)
329 1.1.8.2 nathanw ldmia r1, {r8-r14}^ /* load user mode r8-r14 */
330 1.1.8.4 thorpej b .Lpull_r0r7
331 1.1.8.4 thorpej .Lprenotuser_pull:
332 1.1.8.2 nathanw /*
333 1.1.8.2 nathanw * Now previous mode spsr and r14.
334 1.1.8.2 nathanw */
335 1.1.8.2 nathanw ldr r1, [sp, #(17*4)] /* spsr */
336 1.1.8.2 nathanw ldr r2, [sp, #(14*4)] /* r14 */
337 1.1.8.2 nathanw orr r0, r0, #(I32_bit)
338 1.1.8.2 nathanw msr cpsr_all, r0 /* switch to previous mode */
339 1.1.8.2 nathanw msr spsr_all, r1
340 1.1.8.2 nathanw mov r14, r2
341 1.1.8.2 nathanw msr cpsr_all, r7 /* back to undefined mode */
342 1.1.8.2 nathanw /*
343 1.1.8.2 nathanw * Now r8-r13.
344 1.1.8.2 nathanw */
345 1.1.8.2 nathanw add r8, sp, #(8*4)
346 1.1.8.2 nathanw ldmia r8, {r1-r6} /* r8-r13 */
347 1.1.8.2 nathanw msr cpsr_all, r0
348 1.1.8.2 nathanw mov r8, r1
349 1.1.8.2 nathanw mov r9, r2
350 1.1.8.2 nathanw mov r10, r3
351 1.1.8.2 nathanw mov r11, r4
352 1.1.8.2 nathanw mov r12, r5
353 1.1.8.2 nathanw mov r13, r6
354 1.1.8.2 nathanw msr cpsr_all, r7
355 1.1.8.4 thorpej .Lpull_r0r7:
356 1.1.8.2 nathanw /*
357 1.1.8.2 nathanw * Now the rest of the registers.
358 1.1.8.2 nathanw */
359 1.1.8.2 nathanw ldr r1,Lipkdb_trap_return
360 1.1.8.2 nathanw ldr r0,[r1]
361 1.1.8.2 nathanw tst r0,r0
362 1.1.8.2 nathanw ldmfd sp!, {r0-r7} /* r0-r7 */
363 1.1.8.2 nathanw add sp, sp, #(10*4) /* adjust sp */
364 1.1.8.2 nathanw
365 1.1.8.2 nathanw /*
366 1.1.8.2 nathanw * Did IPKDB handle it?
367 1.1.8.2 nathanw */
368 1.1.8.2 nathanw movnes pc, lr /* return */
369 1.1.8.2 nathanw
370 1.1.8.2 nathanw #endif
371 1.1.8.2 nathanw stmfd sp!, {r0, r1}
372 1.1.8.2 nathanw ldr r0, Lundefined_handler_indirection
373 1.1.8.2 nathanw ldr r1, [sp], #0x0004
374 1.1.8.2 nathanw str r1, [r0, #0x0000]
375 1.1.8.2 nathanw ldr r1, [sp], #0x0004
376 1.1.8.2 nathanw str r1, [r0, #0x0004]
377 1.1.8.2 nathanw ldmia r0, {r0, r1, pc}
378 1.1.8.2 nathanw
379 1.1.8.2 nathanw #ifdef IPKDB
380 1.1.8.2 nathanw Lipkdb_trap_return:
381 1.1.8.2 nathanw .word Lipkdb_trap_return_data
382 1.1.8.2 nathanw #endif
383 1.1.8.2 nathanw
384 1.1.8.2 nathanw Lundefined_handler_indirection:
385 1.1.8.2 nathanw .word Lundefined_handler_indirection_data
386 1.1.8.2 nathanw
387 1.1.8.2 nathanw /*
388 1.1.8.2 nathanw * assembly bounce code for calling the kernel
389 1.1.8.2 nathanw * undefined instruction handler. This uses
390 1.1.8.2 nathanw * a standard trap frame and is called in SVC mode.
391 1.1.8.2 nathanw */
392 1.1.8.2 nathanw
393 1.1.8.2 nathanw ENTRY_NP(undefinedinstruction_bounce)
394 1.1.8.2 nathanw PUSHFRAMEINSVC
395 1.1.8.2 nathanw mov r0, sp
396 1.1.8.2 nathanw bl _C_LABEL(undefinedinstruction)
397 1.1.8.2 nathanw
398 1.1.8.2 nathanw b exception_exit
399 1.1.8.2 nathanw
400 1.1.8.2 nathanw .data
401 1.1.8.2 nathanw .align 0
402 1.1.8.2 nathanw
403 1.1.8.2 nathanw #ifdef IPKDB
404 1.1.8.2 nathanw Lipkdb_trap_return_data:
405 1.1.8.2 nathanw .word 0
406 1.1.8.2 nathanw #endif
407 1.1.8.2 nathanw
408 1.1.8.2 nathanw /*
409 1.1.8.2 nathanw * Indirection data
410 1.1.8.2 nathanw * 2 words use for preserving r0 and r1
411 1.1.8.2 nathanw * 3rd word contains the undefined handler address.
412 1.1.8.2 nathanw */
413 1.1.8.2 nathanw
414 1.1.8.2 nathanw Lundefined_handler_indirection_data:
415 1.1.8.2 nathanw .word 0
416 1.1.8.2 nathanw .word 0
417 1.1.8.2 nathanw
418 1.1.8.2 nathanw .global _C_LABEL(undefined_handler_address)
419 1.1.8.2 nathanw _C_LABEL(undefined_handler_address):
420 1.1.8.2 nathanw .word _C_LABEL(undefinedinstruction_bounce)
421