Commit c0d7dcf8 authored by Nicholas Piggin's avatar Nicholas Piggin Committed by Michael Ellerman
Browse files

powerpc/64/kuap: Move kuap checks out of MSR[RI]=0 regions of exit code



Any kind of WARN causes a program check that will crash with
unrecoverable exception if it occurs when RI is clear.

Fixes: 68b34588 ("powerpc/64/sycall: Implement syscall entry/exit logic in C")
Signed-off-by: default avatarNicholas Piggin <npiggin@gmail.com>
Signed-off-by: default avatarMichael Ellerman <mpe@ellerman.id.au>
Link: https://lore.kernel.org/r/20200429065654.1677541-2-npiggin@gmail.com
parent 0094368e
Loading
Loading
Loading
Loading
+8 −6
Original line number Diff line number Diff line
@@ -35,6 +35,8 @@ notrace long system_call_exception(long r3, long r4, long r5,
	BUG_ON(!FULL_REGS(regs));
	BUG_ON(regs->softe != IRQS_ENABLED);

	kuap_check_amr();

	account_cpu_user_entry();

#ifdef CONFIG_PPC_SPLPAR
@@ -47,8 +49,6 @@ notrace long system_call_exception(long r3, long r4, long r5,
	}
#endif

	kuap_check_amr();

	/*
	 * This is not required for the syscall exit path, but makes the
	 * stack frame look nicer. If this was initialised in the first stack
@@ -117,6 +117,8 @@ notrace unsigned long syscall_exit_prepare(unsigned long r3,
	unsigned long ti_flags;
	unsigned long ret = 0;

	kuap_check_amr();

	regs->result = r3;

	/* Check whether the syscall is issued inside a restartable sequence */
@@ -204,8 +206,6 @@ again:
	local_paca->tm_scratch = regs->msr;
#endif

	kuap_check_amr();

	account_cpu_user_exit();

	return ret;
@@ -228,6 +228,8 @@ notrace unsigned long interrupt_exit_user_prepare(struct pt_regs *regs, unsigned
	BUG_ON(!FULL_REGS(regs));
	BUG_ON(regs->softe != IRQS_ENABLED);

	kuap_check_amr();

	local_irq_save(flags);

again:
@@ -292,8 +294,6 @@ again:
	local_paca->tm_scratch = regs->msr;
#endif

	kuap_check_amr();

	account_cpu_user_exit();

	return ret;
@@ -313,6 +313,8 @@ notrace unsigned long interrupt_exit_kernel_prepare(struct pt_regs *regs, unsign
	BUG_ON(regs->msr & MSR_PR);
	BUG_ON(!FULL_REGS(regs));

	kuap_check_amr();

	if (unlikely(*ti_flagsp & _TIF_EMULATE_STACK_STORE)) {
		clear_bits(_TIF_EMULATE_STACK_STORE, ti_flagsp);
		ret = 1;