diff options
author | Nicholas Piggin <npiggin@gmail.com> | 2021-06-18 01:51:10 +1000 |
---|---|---|
committer | Michael Ellerman <mpe@ellerman.id.au> | 2021-06-25 00:06:56 +1000 |
commit | 9d1988ca87dd90ecf80a0601c7fd13071fbb1a83 (patch) | |
tree | efef71434955ee8cfe2edd8414fde31434040d5f /arch/powerpc/include | |
parent | 862fa563524b9f92d7e89fe332732bd3421772db (diff) |
powerpc/64: treat low kernel text as irqs soft-masked
Treat code below __end_soft_masked as soft-masked for the purpose
of alternate return. 64s already mostly does this for scv entry.
This will be used to exit from interrupts without disabling MSR[EE].
Signed-off-by: Nicholas Piggin <npiggin@gmail.com>
Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
Link: https://lore.kernel.org/r/20210617155116.2167984-12-npiggin@gmail.com
Diffstat (limited to 'arch/powerpc/include')
-rw-r--r-- | arch/powerpc/include/asm/interrupt.h | 11 |
1 files changed, 8 insertions, 3 deletions
diff --git a/arch/powerpc/include/asm/interrupt.h b/arch/powerpc/include/asm/interrupt.h index a4bf6c0013bb..832079e824bd 100644 --- a/arch/powerpc/include/asm/interrupt.h +++ b/arch/powerpc/include/asm/interrupt.h @@ -146,8 +146,13 @@ static inline void interrupt_enter_prepare(struct pt_regs *regs, struct interrup * CT_WARN_ON comes here via program_check_exception, * so avoid recursion. */ - if (TRAP(regs) != INTERRUPT_PROGRAM) + if (TRAP(regs) != INTERRUPT_PROGRAM) { CT_WARN_ON(ct_state() != CONTEXT_KERNEL); + BUG_ON(regs->nip < (unsigned long)__end_soft_masked); + } + /* Move this under a debugging check */ + if (arch_irq_disabled_regs(regs)) + BUG_ON(search_kernel_restart_table(regs->nip)); } #endif @@ -238,8 +243,8 @@ static inline void interrupt_nmi_enter_prepare(struct pt_regs *regs, struct inte local_paca->irq_happened |= PACA_IRQ_HARD_DIS; if (IS_ENABLED(CONFIG_PPC_BOOK3S_64) && !(regs->msr & MSR_PR) && - regs->nip < (unsigned long)__end_interrupts) { - // Kernel code running below __end_interrupts is + regs->nip < (unsigned long)__end_soft_masked) { + // Kernel code running below __end_soft_masked is // implicitly soft-masked. regs->softe = IRQS_ALL_DISABLED; } |