Move the exception vector table (so-called "page0" data) into exception.S
and eliminate vectors.S. All low-level exception handling is now consolidated into exception.S. Along with moving the default FIQ handler, change it to disable FIQs before returning. An FIQ should never happen, but if it does, it's got to be disabled as part of ignoring it. In general, we have hand-wavy support for FIQs that probably hasn't been used for 10 years and probably doesn't work (almost certainly doesn't work for SMP because it only updates the vector on the current cpu). This change doesn't really make the overall situation any better or worse.
This commit is contained in:
parent
5e4e1d4995
commit
0e255c3294
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=262980
@ -148,7 +148,7 @@ _C_LABEL(data_abort_handler_address):
|
||||
END(data_abort_entry)
|
||||
|
||||
/*
|
||||
* address_exception_entry:
|
||||
* addr_exception_entry:
|
||||
*
|
||||
* Handler for the Address Exception exception.
|
||||
*
|
||||
@ -156,17 +156,17 @@ END(data_abort_entry)
|
||||
* print a warning message to the console and then treat
|
||||
* it like a Data Abort.
|
||||
*/
|
||||
ASENTRY_NP(address_exception_entry)
|
||||
ASENTRY_NP(addr_exception_entry)
|
||||
mrs r1, cpsr
|
||||
mrs r2, spsr
|
||||
mov r3, lr
|
||||
adr r0, Laddress_exception_msg
|
||||
adr r0, Laddr_exception_msg
|
||||
bl _C_LABEL(printf) /* XXX CLOBBERS LR!! */
|
||||
b data_abort_entry
|
||||
Laddress_exception_msg:
|
||||
Laddr_exception_msg:
|
||||
.asciz "Address Exception CPSR=0x%08x SPSR=0x%08x LR=0x%08x\n"
|
||||
.balign 4
|
||||
END(address_exception_entry)
|
||||
END(addr_exception_entry)
|
||||
|
||||
/*
|
||||
* General exception exit handler
|
||||
@ -234,3 +234,63 @@ Lundefined_handler_address:
|
||||
_C_LABEL(undefined_handler_address):
|
||||
.word undefinedinstruction_bounce
|
||||
|
||||
/*
|
||||
* Entry point for FIQ interrupts.
|
||||
*
|
||||
* We don't currently support FIQ handlers very much. Something can
|
||||
* install itself in the FIQ vector using code (that may or may not work
|
||||
* these days) in fiq.c. If nobody does that and an FIQ happens, this
|
||||
* default handler just disables FIQs and otherwise ignores it.
|
||||
*/
|
||||
ASENTRY_NP(fiq_entry)
|
||||
mrs r8, cpsr /* FIQ handling isn't supported, */
|
||||
bic r8, #(F32_bit) /* just disable FIQ and return. */
|
||||
msr cpsr_c, r8 /* The r8 we trash here is the */
|
||||
subs pc, lr, #4 /* banked FIQ-mode r8. */
|
||||
END(fiq_entry)
|
||||
|
||||
/*
|
||||
* page0 and page0_data -- An image of the ARM vectors which is copied to
|
||||
* the ARM vectors page (high or low) as part of CPU initialization. The
|
||||
* code that does the copy assumes that page0_data holds one 32-bit word
|
||||
* of data for each of the predefined ARM vectors. It also assumes that
|
||||
* page0_data follows the vectors in page0, but other stuff can appear
|
||||
* between the two. We currently leave room between the two for some fiq
|
||||
* handler code to be copied in.
|
||||
*/
|
||||
.global _C_LABEL(page0), _C_LABEL(page0_data)
|
||||
|
||||
_C_LABEL(page0):
|
||||
ldr pc, .Lreset_entry
|
||||
ldr pc, .Lundefined_entry
|
||||
ldr pc, .Lswi_entry
|
||||
ldr pc, .Lprefetch_abort_entry
|
||||
ldr pc, .Ldata_abort_entry
|
||||
ldr pc, .Laddr_exception_entry
|
||||
ldr pc, .Lirq_entry
|
||||
.fiqv: ldr pc, .Lfiq_entry
|
||||
.space 256 /* room for some fiq handler code */
|
||||
|
||||
_C_LABEL(page0_data):
|
||||
.Lreset_entry: .word reset_entry
|
||||
.Lundefined_entry: .word undefined_entry
|
||||
.Lswi_entry: .word swi_entry
|
||||
.Lprefetch_abort_entry: .word prefetch_abort_entry
|
||||
.Ldata_abort_entry: .word data_abort_entry
|
||||
.Laddr_exception_entry: .word addr_exception_entry
|
||||
.Lirq_entry: .word irq_entry
|
||||
.Lfiq_entry: .word fiq_entry
|
||||
|
||||
/*
|
||||
* These items are used by the code in fiq.c to install what it calls the
|
||||
* "null" handler. It's actually our default vector entry that just jumps
|
||||
* to the default handler which just disables FIQs and returns.
|
||||
*/
|
||||
.global _C_LABEL(fiq_nullhandler_code), _C_LABEL(fiq_nullhandler_size)
|
||||
|
||||
_C_LABEL(fiq_nullhandler_code):
|
||||
.word .fiqv
|
||||
_C_LABEL(fiq_nullhandler_size):
|
||||
.word 4
|
||||
|
||||
|
||||
|
@ -51,8 +51,8 @@ __FBSDID("$FreeBSD$");
|
||||
TAILQ_HEAD(, fiqhandler) fiqhandler_stack =
|
||||
TAILQ_HEAD_INITIALIZER(fiqhandler_stack);
|
||||
|
||||
extern char fiqvector[];
|
||||
extern char fiq_nullhandler[], fiq_nullhandler_end[];
|
||||
extern char *fiq_nullhandler_code;
|
||||
extern uint32_t fiq_nullhandler_size;
|
||||
|
||||
#define IRQ_BIT I32_bit
|
||||
#define FIQ_BIT F32_bit
|
||||
@ -61,6 +61,9 @@ extern char fiq_nullhandler[], fiq_nullhandler_end[];
|
||||
* fiq_installhandler:
|
||||
*
|
||||
* Actually install the FIQ handler down at the FIQ vector.
|
||||
*
|
||||
* The FIQ vector is fixed by the hardware definition as the
|
||||
* seventh 32-bit word in the vector page.
|
||||
*
|
||||
* Note: If the FIQ is invoked via an extra layer of
|
||||
* indirection, the actual FIQ code store lives in the
|
||||
@ -70,11 +73,13 @@ extern char fiq_nullhandler[], fiq_nullhandler_end[];
|
||||
static void
|
||||
fiq_installhandler(void *func, size_t size)
|
||||
{
|
||||
const uint32_t fiqvector = 7 * sizeof(uint32_t);
|
||||
|
||||
#if !defined(__ARM_FIQ_INDIRECT)
|
||||
vector_page_setprot(VM_PROT_READ|VM_PROT_WRITE);
|
||||
#endif
|
||||
|
||||
memcpy(vector_page + fiqvector, func, size);
|
||||
memcpy((void *)(vector_page + fiqvector), func, size);
|
||||
|
||||
#if !defined(__ARM_FIQ_INDIRECT)
|
||||
vector_page_setprot(VM_PROT_READ);
|
||||
@ -159,8 +164,7 @@ fiq_release(struct fiqhandler *fh)
|
||||
|
||||
if (TAILQ_FIRST(&fiqhandler_stack) == NULL) {
|
||||
/* Copy the NULL handler back down into the vector. */
|
||||
fiq_installhandler(fiq_nullhandler,
|
||||
(size_t)(fiq_nullhandler_end - fiq_nullhandler));
|
||||
fiq_installhandler(fiq_nullhandler_code, fiq_nullhandler_size);
|
||||
|
||||
/* Make sure FIQs are disabled when we return. */
|
||||
oldirqstate |= FIQ_BIT;
|
||||
|
@ -91,13 +91,3 @@ ENTRY(fiq_setregs)
|
||||
RET
|
||||
END(fiq_setregs)
|
||||
|
||||
/*
|
||||
* fiq_nullhandler:
|
||||
*
|
||||
* Null handler copied down to the FIQ vector when the last
|
||||
* FIQ handler is removed.
|
||||
*/
|
||||
.global _C_LABEL(fiq_nullhandler), _C_LABEL(fiq_nullhandler_end)
|
||||
_C_LABEL(fiq_nullhandler):
|
||||
subs pc, lr, #4
|
||||
_C_LABEL(fiq_nullhandler_end):
|
||||
|
@ -1,104 +0,0 @@
|
||||
/* $NetBSD: vectors.S,v 1.4 2002/08/17 16:36:32 thorpej Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (C) 1994-1997 Mark Brinicombe
|
||||
* Copyright (C) 1994 Brini
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by Brini.
|
||||
* 4. The name of Brini may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY BRINI ``AS IS'' AND ANY EXPRESS OR
|
||||
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
||||
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
* IN NO EVENT SHALL BRINI BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
|
||||
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
|
||||
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
|
||||
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
|
||||
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <machine/asm.h>
|
||||
__FBSDID("$FreeBSD$");
|
||||
|
||||
/*
|
||||
* These are the exception vectors copied down to page 0.
|
||||
*
|
||||
* Note that FIQs are special; rather than using a level of
|
||||
* indirection, we actually copy the FIQ code down into the
|
||||
* vector page.
|
||||
*/
|
||||
|
||||
.text
|
||||
.align 0
|
||||
.global _C_LABEL(page0), _C_LABEL(page0_data), _C_LABEL(page0_end)
|
||||
.global _C_LABEL(fiqvector)
|
||||
|
||||
_C_LABEL(page0):
|
||||
ldr pc, .Lreset_target
|
||||
ldr pc, .Lundefined_target
|
||||
ldr pc, .Lswi_target
|
||||
ldr pc, .Lprefetch_abort_target
|
||||
ldr pc, .Ldata_abort_target
|
||||
ldr pc, .Laddress_exception_target
|
||||
ldr pc, .Lirq_target
|
||||
#ifdef __ARM_FIQ_INDIRECT
|
||||
ldr pc, .Lfiq_target
|
||||
#else
|
||||
.Lfiqvector:
|
||||
.set _C_LABEL(fiqvector), . - _C_LABEL(page0)
|
||||
subs pc, lr, #4
|
||||
.org .Lfiqvector + 0x100
|
||||
#endif
|
||||
|
||||
_C_LABEL(page0_data):
|
||||
.Lreset_target:
|
||||
.word reset_entry
|
||||
|
||||
.Lundefined_target:
|
||||
.word undefined_entry
|
||||
|
||||
.Lswi_target:
|
||||
.word swi_entry
|
||||
|
||||
.Lprefetch_abort_target:
|
||||
.word prefetch_abort_entry
|
||||
|
||||
.Ldata_abort_target:
|
||||
.word data_abort_entry
|
||||
|
||||
.Laddress_exception_target:
|
||||
.word address_exception_entry
|
||||
|
||||
.Lirq_target:
|
||||
.word irq_entry
|
||||
|
||||
#ifdef __ARM_FIQ_INDIRECT
|
||||
.Lfiq_target:
|
||||
.word _C_LABEL(fiqvector)
|
||||
#else
|
||||
.word 0 /* pad it out */
|
||||
#endif
|
||||
_C_LABEL(page0_end):
|
||||
|
||||
#ifdef __ARM_FIQ_INDIRECT
|
||||
.data
|
||||
.align 0
|
||||
_C_LABEL(fiqvector):
|
||||
subs pc, lr, #4
|
||||
.org _C_LABEL(fiqvector) + 0x100
|
||||
#endif
|
@ -50,7 +50,6 @@ arm/arm/sys_machdep.c standard
|
||||
arm/arm/trap.c standard
|
||||
arm/arm/uio_machdep.c standard
|
||||
arm/arm/undefined.c standard
|
||||
arm/arm/vectors.S standard
|
||||
arm/arm/vm_machdep.c standard
|
||||
arm/arm/vfp.c standard
|
||||
board_id.h standard \
|
||||
|
Loading…
Reference in New Issue
Block a user