powerpc/32: Dismantle EXC_XFER_STD/LITE/TEMPLATE
In order to get more control in exception prolog, dismantle all non standard exception macros, finishing with EXC_XFER_STD and EXC_XFER_LITE and EXC_XFER_TEMPLATE. Also remove transfer_to_handler_full and ret_from_except and ret_from_except_full as they are not used anymore. Last parameter of EXCEPTION() is now ignored, will be removed in a later patch to avoid too much churn. Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu> Signed-off-by: Michael Ellerman <mpe@ellerman.id.au> Link: https://lore.kernel.org/r/ca5795d04a220586b7037dbbbe6951dfa9e768eb.1615552867.git.christophe.leroy@csgroup.eu
This commit is contained in:
Родитель
8f6ff5bd9b
Коммит
4c0104a83f
|
@ -48,30 +48,6 @@
|
|||
*/
|
||||
.align 12
|
||||
|
||||
#ifdef CONFIG_BOOKE
|
||||
.globl mcheck_transfer_to_handler
|
||||
mcheck_transfer_to_handler:
|
||||
/* fall through */
|
||||
_ASM_NOKPROBE_SYMBOL(mcheck_transfer_to_handler)
|
||||
|
||||
.globl debug_transfer_to_handler
|
||||
debug_transfer_to_handler:
|
||||
/* fall through */
|
||||
_ASM_NOKPROBE_SYMBOL(debug_transfer_to_handler)
|
||||
|
||||
.globl crit_transfer_to_handler
|
||||
crit_transfer_to_handler:
|
||||
/* fall through */
|
||||
_ASM_NOKPROBE_SYMBOL(crit_transfer_to_handler)
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_40x
|
||||
.globl crit_transfer_to_handler
|
||||
crit_transfer_to_handler:
|
||||
/* fall through */
|
||||
_ASM_NOKPROBE_SYMBOL(crit_transfer_to_handler)
|
||||
#endif
|
||||
|
||||
/*
|
||||
* This code finishes saving the registers to the exception frame
|
||||
* and jumps to the appropriate handler for the exception, turning
|
||||
|
@ -79,13 +55,6 @@ _ASM_NOKPROBE_SYMBOL(crit_transfer_to_handler)
|
|||
* Note that we rely on the caller having set cr0.eq iff the exception
|
||||
* occurred in kernel mode (i.e. MSR:PR = 0).
|
||||
*/
|
||||
.globl transfer_to_handler_full
|
||||
transfer_to_handler_full:
|
||||
_ASM_NOKPROBE_SYMBOL(transfer_to_handler_full)
|
||||
/* fall through */
|
||||
|
||||
.globl transfer_to_handler
|
||||
transfer_to_handler:
|
||||
.globl prepare_transfer_to_handler
|
||||
prepare_transfer_to_handler:
|
||||
SAVE_NVGPRS(r11)
|
||||
|
@ -136,7 +105,6 @@ transfer_to_handler_cont:
|
|||
b fast_exception_return
|
||||
#endif
|
||||
_ASM_NOKPROBE_SYMBOL(prepare_transfer_to_handler)
|
||||
_ASM_NOKPROBE_SYMBOL(transfer_to_handler)
|
||||
_ASM_NOKPROBE_SYMBOL(transfer_to_handler_cont)
|
||||
|
||||
.globl transfer_to_syscall
|
||||
|
@ -352,18 +320,10 @@ _ASM_NOKPROBE_SYMBOL(fast_exception_return)
|
|||
3:
|
||||
li r10,-1
|
||||
stw r10,_TRAP(r11)
|
||||
bl transfer_to_handler_full
|
||||
prepare_transfer_to_handler
|
||||
bl unrecoverable_exception
|
||||
trap /* should not get here */
|
||||
|
||||
.globl ret_from_except_full
|
||||
ret_from_except_full:
|
||||
/* fall through */
|
||||
|
||||
.globl ret_from_except
|
||||
ret_from_except:
|
||||
_ASM_NOKPROBE_SYMBOL(ret_from_except)
|
||||
|
||||
.globl interrupt_return
|
||||
interrupt_return:
|
||||
lwz r4,_MSR(r1)
|
||||
|
|
|
@ -189,20 +189,9 @@ label:
|
|||
#define EXCEPTION(n, label, hdlr, xfer) \
|
||||
START_EXCEPTION(n, label) \
|
||||
EXCEPTION_PROLOG n label; \
|
||||
xfer(n, hdlr)
|
||||
|
||||
#define EXC_XFER_TEMPLATE(hdlr, trap, msr, tfer, ret) \
|
||||
bl tfer; \
|
||||
bl hdlr; \
|
||||
b ret
|
||||
|
||||
#define EXC_XFER_STD(n, hdlr) \
|
||||
EXC_XFER_TEMPLATE(hdlr, n, MSR_KERNEL, transfer_to_handler_full, \
|
||||
ret_from_except_full)
|
||||
|
||||
#define EXC_XFER_LITE(n, hdlr) \
|
||||
EXC_XFER_TEMPLATE(hdlr, n, MSR_KERNEL, transfer_to_handler, \
|
||||
ret_from_except)
|
||||
prepare_transfer_to_handler; \
|
||||
bl hdlr; \
|
||||
b interrupt_return
|
||||
|
||||
.macro vmap_stack_overflow_exception
|
||||
__HEAD
|
||||
|
@ -218,7 +207,9 @@ vmap_stack_overflow:
|
|||
lwz r1, emergency_ctx@l(r1)
|
||||
addi r1, r1, THREAD_SIZE - INT_FRAME_SIZE
|
||||
EXCEPTION_PROLOG_2 0 vmap_stack_overflow
|
||||
EXC_XFER_STD(0, stack_overflow_exception)
|
||||
prepare_transfer_to_handler
|
||||
bl stack_overflow_exception
|
||||
b interrupt_return
|
||||
.endm
|
||||
|
||||
#endif /* __HEAD_32_H__ */
|
||||
|
|
|
@ -187,8 +187,9 @@ _ASM_NOKPROBE_SYMBOL(\name\()_virt)
|
|||
#define CRITICAL_EXCEPTION(n, label, hdlr) \
|
||||
START_EXCEPTION(n, label); \
|
||||
CRITICAL_EXCEPTION_PROLOG n label; \
|
||||
EXC_XFER_TEMPLATE(hdlr, n+2, (MSR_KERNEL & ~(MSR_ME|MSR_DE|MSR_CE)), \
|
||||
crit_transfer_to_handler, ret_from_crit_exc)
|
||||
prepare_transfer_to_handler; \
|
||||
bl hdlr; \
|
||||
b ret_from_crit_exc
|
||||
|
||||
/*
|
||||
* 0x0100 - Critical Interrupt Exception
|
||||
|
@ -209,7 +210,9 @@ _ASM_NOKPROBE_SYMBOL(\name\()_virt)
|
|||
*/
|
||||
START_EXCEPTION(0x0300, DataStorage)
|
||||
EXCEPTION_PROLOG 0x300 DataStorage handle_dar_dsisr=1
|
||||
EXC_XFER_LITE(0x300, do_page_fault)
|
||||
prepare_transfer_to_handler
|
||||
bl do_page_fault
|
||||
b interrupt_return
|
||||
|
||||
/*
|
||||
* 0x0400 - Instruction Storage Exception
|
||||
|
@ -220,7 +223,9 @@ _ASM_NOKPROBE_SYMBOL(\name\()_virt)
|
|||
li r5,0
|
||||
stw r5, _ESR(r11) /* Zero ESR */
|
||||
stw r12, _DEAR(r11) /* SRR0 as DEAR */
|
||||
EXC_XFER_LITE(0x400, do_page_fault)
|
||||
prepare_transfer_to_handler
|
||||
bl do_page_fault
|
||||
b interrupt_return
|
||||
|
||||
/* 0x0500 - External Interrupt Exception */
|
||||
EXCEPTION(0x0500, HardwareInterrupt, do_IRQ, EXC_XFER_LITE)
|
||||
|
@ -499,9 +504,9 @@ _ASM_NOKPROBE_SYMBOL(\name\()_virt)
|
|||
/* continue normal handling for a critical exception... */
|
||||
2: mfspr r4,SPRN_DBSR
|
||||
stw r4,_ESR(r11) /* DebugException takes DBSR in _ESR */
|
||||
EXC_XFER_TEMPLATE(DebugException, 0x2002, \
|
||||
(MSR_KERNEL & ~(MSR_ME|MSR_DE|MSR_CE)), \
|
||||
crit_transfer_to_handler, ret_from_crit_exc)
|
||||
prepare_transfer_to_handler
|
||||
bl DebugException
|
||||
b ret_from_crit_exc
|
||||
|
||||
/* Programmable Interval Timer (PIT) Exception. (from 0x1000) */
|
||||
__HEAD
|
||||
|
@ -509,21 +514,25 @@ Decrementer:
|
|||
EXCEPTION_PROLOG 0x1000 Decrementer
|
||||
lis r0,TSR_PIS@h
|
||||
mtspr SPRN_TSR,r0 /* Clear the PIT exception */
|
||||
EXC_XFER_LITE(0x1000, timer_interrupt)
|
||||
prepare_transfer_to_handler
|
||||
bl timer_interrupt
|
||||
b interrupt_return
|
||||
|
||||
/* Fixed Interval Timer (FIT) Exception. (from 0x1010) */
|
||||
__HEAD
|
||||
FITException:
|
||||
EXCEPTION_PROLOG 0x1010 FITException
|
||||
EXC_XFER_STD(0x1010, unknown_exception)
|
||||
prepare_transfer_to_handler
|
||||
bl unknown_exception
|
||||
b interrupt_return
|
||||
|
||||
/* Watchdog Timer (WDT) Exception. (from 0x1020) */
|
||||
__HEAD
|
||||
WDTException:
|
||||
CRITICAL_EXCEPTION_PROLOG 0x1020 WDTException
|
||||
EXC_XFER_TEMPLATE(WatchdogException, 0x1020+2,
|
||||
(MSR_KERNEL & ~(MSR_ME|MSR_DE|MSR_CE)),
|
||||
crit_transfer_to_handler, ret_from_crit_exc)
|
||||
prepare_transfer_to_handler
|
||||
bl WatchdogException
|
||||
b ret_from_crit_exc
|
||||
|
||||
/* Other PowerPC processors, namely those derived from the 6xx-series
|
||||
* have vectors from 0x2100 through 0x2F00 defined, but marked as reserved.
|
||||
|
|
|
@ -123,7 +123,9 @@ instruction_counter:
|
|||
/* Machine check */
|
||||
START_EXCEPTION(0x200, MachineCheck)
|
||||
EXCEPTION_PROLOG 0x200 MachineCheck handle_dar_dsisr=1
|
||||
EXC_XFER_STD(0x200, machine_check_exception)
|
||||
prepare_transfer_to_handler
|
||||
bl machine_check_exception
|
||||
b interrupt_return
|
||||
|
||||
/* External interrupt */
|
||||
EXCEPTION(0x500, HardwareInterrupt, do_IRQ, EXC_XFER_LITE)
|
||||
|
@ -314,7 +316,9 @@ instruction_counter:
|
|||
.Litlbie:
|
||||
stw r12, _DAR(r11)
|
||||
stw r5, _DSISR(r11)
|
||||
EXC_XFER_LITE(0x400, do_page_fault)
|
||||
prepare_transfer_to_handler
|
||||
bl do_page_fault
|
||||
b interrupt_return
|
||||
|
||||
/* This is the data TLB error on the MPC8xx. This could be due to
|
||||
* many reasons, including a dirty update to a pte. We bail out to
|
||||
|
@ -335,7 +339,9 @@ DARFixed:/* Return from dcbx instruction bug workaround */
|
|||
beq+ .Ldtlbie
|
||||
tlbie r4
|
||||
.Ldtlbie:
|
||||
EXC_XFER_LITE(0x300, do_page_fault)
|
||||
prepare_transfer_to_handler
|
||||
bl do_page_fault
|
||||
b interrupt_return
|
||||
|
||||
#ifdef CONFIG_VMAP_STACK
|
||||
vmap_stack_overflow_exception
|
||||
|
|
|
@ -271,7 +271,9 @@ __secondary_hold_acknowledge:
|
|||
beq cr1, 1f
|
||||
twi 31, 0, 0
|
||||
#endif
|
||||
1: EXC_XFER_STD(0x200, machine_check_exception)
|
||||
1: prepare_transfer_to_handler
|
||||
bl machine_check_exception
|
||||
b interrupt_return
|
||||
|
||||
/* Data access exception. */
|
||||
START_EXCEPTION(0x300, DataAccess)
|
||||
|
@ -296,12 +298,13 @@ ALT_MMU_FTR_SECTION_END_IFSET(MMU_FTR_HPTE_TABLE)
|
|||
1: EXCEPTION_PROLOG_0 handle_dar_dsisr=1
|
||||
EXCEPTION_PROLOG_1
|
||||
EXCEPTION_PROLOG_2 0x300 DataAccess handle_dar_dsisr=1
|
||||
prepare_transfer_to_handler
|
||||
lwz r5, _DSISR(r11)
|
||||
andis. r0, r5, DSISR_DABRMATCH@h
|
||||
bne- 1f
|
||||
EXC_XFER_LITE(0x300, do_page_fault)
|
||||
1: prepare_transfer_to_handler
|
||||
bl do_break
|
||||
bl do_page_fault
|
||||
b interrupt_return
|
||||
1: bl do_break
|
||||
REST_NVGPRS(r1)
|
||||
b interrupt_return
|
||||
|
||||
|
@ -331,7 +334,9 @@ END_MMU_FTR_SECTION_IFSET(MMU_FTR_HPTE_TABLE)
|
|||
andis. r5,r9,DSISR_SRR1_MATCH_32S@h /* Filter relevant SRR1 bits */
|
||||
stw r5, _DSISR(r11)
|
||||
stw r12, _DAR(r11)
|
||||
EXC_XFER_LITE(0x400, do_page_fault)
|
||||
prepare_transfer_to_handler
|
||||
bl do_page_fault
|
||||
b interrupt_return
|
||||
|
||||
/* External interrupt */
|
||||
EXCEPTION(0x500, HardwareInterrupt, do_IRQ, EXC_XFER_LITE)
|
||||
|
@ -366,7 +371,9 @@ END_FTR_SECTION_IFSET(CPU_FTR_FPU_UNAVAILABLE)
|
|||
beq 1f
|
||||
bl load_up_fpu /* if from user, just load it up */
|
||||
b fast_exception_return
|
||||
1: EXC_XFER_LITE(0x800, kernel_fp_unavailable_exception)
|
||||
1: prepare_transfer_to_handler
|
||||
bl kernel_fp_unavailable_exception
|
||||
b interrupt_return
|
||||
#else
|
||||
b ProgramCheck
|
||||
#endif
|
||||
|
@ -730,12 +737,16 @@ AltiVecUnavailable:
|
|||
bl load_up_altivec /* if from user, just load it up */
|
||||
b fast_exception_return
|
||||
#endif /* CONFIG_ALTIVEC */
|
||||
1: EXC_XFER_LITE(0xf20, altivec_unavailable_exception)
|
||||
1: prepare_transfer_to_handler
|
||||
bl altivec_unavailable_exception
|
||||
b interrupt_return
|
||||
|
||||
__HEAD
|
||||
PerformanceMonitor:
|
||||
EXCEPTION_PROLOG 0xf00 PerformanceMonitor
|
||||
EXC_XFER_STD(0xf00, performance_monitor_exception)
|
||||
prepare_transfer_to_handler
|
||||
bl performance_monitor_exception
|
||||
b interrupt_return
|
||||
|
||||
|
||||
__HEAD
|
||||
|
|
|
@ -302,15 +302,18 @@ label:
|
|||
#define EXCEPTION(n, intno, label, hdlr, xfer) \
|
||||
START_EXCEPTION(label); \
|
||||
NORMAL_EXCEPTION_PROLOG(n, intno); \
|
||||
xfer(n, hdlr)
|
||||
prepare_transfer_to_handler; \
|
||||
bl hdlr; \
|
||||
b interrupt_return
|
||||
|
||||
#define CRITICAL_EXCEPTION(n, intno, label, hdlr) \
|
||||
START_EXCEPTION(label); \
|
||||
CRITICAL_EXCEPTION_PROLOG(n, intno); \
|
||||
SAVE_MMU_REGS; \
|
||||
SAVE_xSRR(SRR); \
|
||||
EXC_XFER_TEMPLATE(hdlr, n+2, (MSR_KERNEL & ~(MSR_ME|MSR_DE|MSR_CE)), \
|
||||
crit_transfer_to_handler, ret_from_crit_exc)
|
||||
prepare_transfer_to_handler; \
|
||||
bl hdlr; \
|
||||
b ret_from_crit_exc
|
||||
|
||||
#define MCHECK_EXCEPTION(n, label, hdlr) \
|
||||
START_EXCEPTION(label); \
|
||||
|
@ -321,21 +324,9 @@ label:
|
|||
SAVE_xSRR(CSRR); \
|
||||
SAVE_MMU_REGS; \
|
||||
SAVE_xSRR(SRR); \
|
||||
EXC_XFER_TEMPLATE(hdlr, n+4, (MSR_KERNEL & ~(MSR_ME|MSR_DE|MSR_CE)), \
|
||||
mcheck_transfer_to_handler, ret_from_mcheck_exc)
|
||||
|
||||
#define EXC_XFER_TEMPLATE(hdlr, trap, msr, tfer, ret) \
|
||||
bl tfer; \
|
||||
prepare_transfer_to_handler; \
|
||||
bl hdlr; \
|
||||
b ret; \
|
||||
|
||||
#define EXC_XFER_STD(n, hdlr) \
|
||||
EXC_XFER_TEMPLATE(hdlr, n, MSR_KERNEL, transfer_to_handler_full, \
|
||||
ret_from_except_full)
|
||||
|
||||
#define EXC_XFER_LITE(n, hdlr) \
|
||||
EXC_XFER_TEMPLATE(hdlr, n, MSR_KERNEL, transfer_to_handler, \
|
||||
ret_from_except)
|
||||
b ret_from_mcheck_exc
|
||||
|
||||
/* Check for a single step debug exception while in an exception
|
||||
* handler before state has been saved. This is to catch the case
|
||||
|
@ -404,7 +395,9 @@ label:
|
|||
SAVE_xSRR(CSRR); \
|
||||
SAVE_MMU_REGS; \
|
||||
SAVE_xSRR(SRR); \
|
||||
EXC_XFER_TEMPLATE(DebugException, 0x2008, (MSR_KERNEL & ~(MSR_ME|MSR_DE|MSR_CE)), debug_transfer_to_handler, ret_from_debug_exc)
|
||||
prepare_transfer_to_handler; \
|
||||
bl DebugException; \
|
||||
b ret_from_debug_exc
|
||||
|
||||
#define DEBUG_CRIT_EXCEPTION \
|
||||
START_EXCEPTION(DebugCrit); \
|
||||
|
@ -459,7 +452,9 @@ label:
|
|||
stw r4,_ESR(r11); /* DebugException takes DBSR in _ESR */\
|
||||
SAVE_MMU_REGS; \
|
||||
SAVE_xSRR(SRR); \
|
||||
EXC_XFER_TEMPLATE(DebugException, 0x2002, (MSR_KERNEL & ~(MSR_ME|MSR_DE|MSR_CE)), crit_transfer_to_handler, ret_from_crit_exc)
|
||||
prepare_transfer_to_handler; \
|
||||
bl DebugException; \
|
||||
b ret_from_crit_exc
|
||||
|
||||
#define DATA_STORAGE_EXCEPTION \
|
||||
START_EXCEPTION(DataStorage) \
|
||||
|
@ -468,7 +463,9 @@ label:
|
|||
stw r5,_ESR(r11); \
|
||||
mfspr r4,SPRN_DEAR; /* Grab the DEAR */ \
|
||||
stw r4, _DEAR(r11); \
|
||||
EXC_XFER_LITE(0x0300, do_page_fault)
|
||||
prepare_transfer_to_handler; \
|
||||
bl do_page_fault; \
|
||||
b interrupt_return
|
||||
|
||||
#define INSTRUCTION_STORAGE_EXCEPTION \
|
||||
START_EXCEPTION(InstructionStorage) \
|
||||
|
@ -476,7 +473,9 @@ label:
|
|||
mfspr r5,SPRN_ESR; /* Grab the ESR and save it */ \
|
||||
stw r5,_ESR(r11); \
|
||||
stw r12, _DEAR(r11); /* Pass SRR0 as arg2 */ \
|
||||
EXC_XFER_LITE(0x0400, do_page_fault)
|
||||
prepare_transfer_to_handler; \
|
||||
bl do_page_fault; \
|
||||
b interrupt_return
|
||||
|
||||
#define ALIGNMENT_EXCEPTION \
|
||||
START_EXCEPTION(Alignment) \
|
||||
|
@ -503,7 +502,9 @@ label:
|
|||
NORMAL_EXCEPTION_PROLOG(0x900, DECREMENTER); \
|
||||
lis r0,TSR_DIS@h; /* Setup the DEC interrupt mask */ \
|
||||
mtspr SPRN_TSR,r0; /* Clear the DEC interrupt */ \
|
||||
EXC_XFER_LITE(0x0900, timer_interrupt)
|
||||
prepare_transfer_to_handler; \
|
||||
bl timer_interrupt; \
|
||||
b interrupt_return
|
||||
|
||||
#define FP_UNAVAILABLE_EXCEPTION \
|
||||
START_EXCEPTION(FloatingPointUnavailable) \
|
||||
|
@ -511,7 +512,9 @@ label:
|
|||
beq 1f; \
|
||||
bl load_up_fpu; /* if from user, just load it up */ \
|
||||
b fast_exception_return; \
|
||||
1: EXC_XFER_STD(0x800, kernel_fp_unavailable_exception)
|
||||
1: prepare_transfer_to_handler; \
|
||||
bl kernel_fp_unavailable_exception; \
|
||||
b interrupt_return
|
||||
|
||||
#else /* __ASSEMBLY__ */
|
||||
struct exception_regs {
|
||||
|
|
|
@ -370,9 +370,13 @@ interrupt_base:
|
|||
stw r4, _DEAR(r11)
|
||||
andis. r10,r5,(ESR_ILK|ESR_DLK)@h
|
||||
bne 1f
|
||||
EXC_XFER_LITE(0x0300, do_page_fault)
|
||||
prepare_transfer_to_handler
|
||||
bl do_page_fault
|
||||
b interrupt_return
|
||||
1:
|
||||
EXC_XFER_LITE(0x0300, CacheLockingException)
|
||||
prepare_transfer_to_handler
|
||||
bl CacheLockingException
|
||||
b interrupt_return
|
||||
|
||||
/* Instruction Storage Interrupt */
|
||||
INSTRUCTION_STORAGE_EXCEPTION
|
||||
|
@ -617,7 +621,9 @@ END_BTB_FLUSH_SECTION
|
|||
beq 1f
|
||||
bl load_up_spe
|
||||
b fast_exception_return
|
||||
1: EXC_XFER_LITE(0x2010, KernelSPE)
|
||||
1: prepare_transfer_to_handler
|
||||
bl KernelSPE
|
||||
b interrupt_return
|
||||
#elif defined(CONFIG_SPE_POSSIBLE)
|
||||
EXCEPTION(0x2020, SPE_UNAVAIL, SPEUnavailable, \
|
||||
unknown_exception, EXC_XFER_STD)
|
||||
|
@ -860,7 +866,7 @@ KernelSPE:
|
|||
lwz r5,_NIP(r1)
|
||||
bl printk
|
||||
#endif
|
||||
b ret_from_except
|
||||
b interrupt_return
|
||||
#ifdef CONFIG_PRINTK
|
||||
87: .string "SPE used in kernel (task=%p, pc=%x) \n"
|
||||
#endif
|
||||
|
|
Загрузка…
Ссылка в новой задаче