xref: /openbsd-src/sys/arch/arm/arm/exception.S (revision 8162193374858e8d7dceca506657f13b21b8be44)
1/*	$OpenBSD: exception.S,v 1.11 2022/12/08 01:25:44 guenther Exp $	*/
2/*	$NetBSD: exception.S,v 1.13 2003/10/31 16:30:15 scw Exp $	*/
3
4/*
5 * Copyright (c) 1994-1997 Mark Brinicombe.
6 * Copyright (c) 1994 Brini.
7 * All rights reserved.
8 *
9 * This code is derived from software written for Brini by Mark Brinicombe
10 *
11 * Redistribution and use in source and binary forms, with or without
12 * modification, are permitted provided that the following conditions
13 * are met:
14 * 1. Redistributions of source code must retain the above copyright
15 *    notice, this list of conditions and the following disclaimer.
16 * 2. Redistributions in binary form must reproduce the above copyright
17 *    notice, this list of conditions and the following disclaimer in the
18 *    documentation and/or other materials provided with the distribution.
19 * 3. All advertising materials mentioning features or use of this software
20 *    must display the following acknowledgement:
21 *	This product includes software developed by Brini.
22 * 4. The name of the company nor the name of the author may be used to
23 *    endorse or promote products derived from this software without specific
24 *    prior written permission.
25 *
26 * THIS SOFTWARE IS PROVIDED BY BRINI ``AS IS'' AND ANY EXPRESS OR IMPLIED
27 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
28 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
29 * IN NO EVENT SHALL BRINI OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
30 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
31 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
32 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
33 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
34 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
35 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
36 * SUCH DAMAGE.
37 *
38 * RiscBSD kernel project
39 *
40 * exception.S
41 *
42 * Low level handlers for exception vectors
43 *
44 * Created      : 24/09/94
45 *
46 * Based on kate/display/abort.s
47 */
48
49#include "assym.h"
50
51#include <machine/asm.h>
52#include <machine/frame.h>
53#include <arm/armreg.h>
54
55	.text
56	.align	2
57
58#define RESTOREVFP							 \
59	ldr	r0, [sp]		/* Get the SPSR from stack */	;\
60	and	r0, r0, #(PSR_MODE)	/* Returning to USR mode? */	;\
61	cmp	r0, #(PSR_USR32_MODE)					;\
62	bne	1f							;\
63	bl	vfp_enable						;\
641:
65
66AST_LOCALS
67
68/*
69 * reset_entry:
70 *
71 *	Handler for Reset exception.
72 */
73ASENTRY_NP(reset_entry)
74	adr	r0, Lreset_panicmsg
75	mov	r1, lr
76	bl	panic
77	/* NOTREACHED */
78Lreset_panicmsg:
79	.asciz	"Reset vector called, LR = 0x%08x"
80	.balign	4
81
82/*
83 * swi_entry
84 *
85 *	Handler for the Software Interrupt exception.
86 */
87ASENTRY_NP(swi_entry)
88	PUSHFRAME
89
90	mov	r0, sp			/* Pass the frame to any function */
91	bl	swi_handler		/* It's a SWI ! */
92
93	DO_AST
94	PULLFRAME
95	movs	pc, lr			/* Exit */
96	dsb	nsh
97	isb
98
99/*
100 * prefetch_abort_entry:
101 *
102 *	Handler for the Prefetch Abort exception.
103 */
104ASENTRY_NP(prefetch_abort_entry)
105        sub     lr, lr, #0x00000004     /* Adjust the lr */
106
107	PUSHFRAMEINSVC
108
109	ldr	r1, Lprefetch_abort_handler_address
110	adr	lr, exception_exit
111 	mov	r0, sp			/* pass the stack pointer as r0 */
112	ldr	pc, [r1]
113
114Lprefetch_abort_handler_address:
115	.word	prefetch_abort_handler_address
116
117	.data
118	.global	prefetch_abort_handler_address
119
120prefetch_abort_handler_address:
121	.word	abortprefetch
122
123	.text
124abortprefetch:
125        adr     r0, abortprefetchmsg
126	b	panic
127
128abortprefetchmsg:
129        .asciz  "abortprefetch"
130        .align  2
131
132/*
133 * data_abort_entry:
134 *
135 *	Handler for the Data Abort exception.
136 */
137ASENTRY_NP(data_abort_entry)
138        sub     lr, lr, #0x00000008     /* Adjust the lr */
139
140	PUSHFRAMEINSVC			/* Push trap frame and switch */
141					/* to SVC32 mode */
142
143	ldr	r1, Ldata_abort_handler_address
144	adr	lr, exception_exit
145	mov	r0, sp			/* pass the stack pointer as r0 */
146	ldr	pc, [r1]
147
148Ldata_abort_handler_address:
149	.word	data_abort_handler_address
150
151	.data
152	.global	data_abort_handler_address
153data_abort_handler_address:
154	.word	abortdata
155
156	.text
157abortdata:
158        adr     r0, abortdatamsg
159	b	panic
160
161abortdatamsg:
162        .asciz  "abortdata"
163        .align  2
164
165/*
166 * address_exception_entry:
167 *
168 *	Handler for the Address Exception exception.
169 *
170 *	NOTE: This exception isn't really used on arm32.  We
171 *	print a warning message to the console and then treat
172 *	it like a Data Abort.
173 */
174ASENTRY_NP(address_exception_entry)
175	mrs	r1, cpsr
176	mrs	r2, spsr
177	mov	r3, lr
178	adr	r0, Laddress_exception_msg
179	bl	printf			/* XXX CLOBBERS LR!! */
180	b	data_abort_entry
181Laddress_exception_msg:
182	.asciz	"Address Exception CPSR=0x%08x SPSR=0x%08x LR=0x%08x\n"
183	.balign	4
184
185/*
186 * General exception exit handler
187 * (Placed here to be within range of all the references to it)
188 *
189 * It exits straight away if not returning to USR mode.
190 * This loops around delivering any pending ASTs.
191 * Interrupts are disabled at suitable points to avoid ASTs
192 * being posted between testing and exit to user mode.
193 *
194 * This function uses PULLFRAMEFROMSVCANDEXIT and DO_AST thus should
195 * only be called if the exception handler used PUSHFRAMEINSVC.
196 */
197
198exception_exit:
199	DO_AST
200	RESTOREVFP
201	PULLFRAMEFROMSVCANDEXIT
202
203/*
204 * undefined_entry:
205 *
206 *	Handler for the Undefined Instruction exception.
207 *
208 *	We indirect the undefined vector via the handler address
209 *	in the data area.  Entry to the undefined handler must
210 *	look like direct entry from the vector.
211 */
212ASENTRY_NP(undefined_entry)
213	stmfd	sp!, {r0, r1}
214	ldr	r0, Lundefined_handler_indirection
215	ldr	r1, [sp], #0x0004
216	str	r1, [r0, #0x0000]
217	ldr	r1, [sp], #0x0004
218	str	r1, [r0, #0x0004]
219	ldmia	r0, {r0, r1, pc}
220
221Lundefined_handler_indirection:
222	.word	Lundefined_handler_indirection_data
223
224/*
225 * assembly bounce code for calling the kernel
226 * undefined instruction handler. This uses
227 * a standard trap frame and is called in SVC mode.
228 */
229
230ENTRY_NP(undefinedinstruction_bounce)
231	PUSHFRAMEINSVC
232
233	mov	r0, sp
234	adr	lr, exception_exit
235	b	undefinedinstruction
236
237	.data
238	.align	2
239
240/*
241 * Indirection data
242 * 2 words use for preserving r0 and r1
243 * 3rd word contains the undefined handler address.
244 */
245
246Lundefined_handler_indirection_data:
247	.word	0
248	.word	0
249
250	.global	undefined_handler_address
251undefined_handler_address:
252	.word	undefinedinstruction_bounce
253