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

powerpc/64s/exception: machine check restructure to reuse common macros



Follow the pattern of sreset and HMI handlers more closely: use
EXCEPTION_PROLOG_COMMON_1 rather than open-coding it, and run the
handler at the relocated location.

This helps later simplification and code sharing.

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/20190802105709.27696-12-npiggin@gmail.com
parent 272f6364
Loading
Loading
Loading
Loading
+36 −35
Original line number Diff line number Diff line
@@ -934,17 +934,23 @@ EXC_COMMON_BEGIN(system_reset_common)

EXC_REAL_BEGIN(machine_check, 0x200, 0x100)
	EXCEPTION_PROLOG_0 PACA_EXMC
	b	machine_check_common_early
	EXCEPTION_PROLOG_1 EXC_STD, PACA_EXMC, 0, 0x200, 1, 1, 0
	mfctr	r10			/* save ctr, even for !RELOCATABLE */
	BRANCH_TO_C000(r11, machine_check_early_common)
	/*
	 * MSR_RI is not enabled, because PACA_EXMC is being used, so a
	 * nested machine check corrupts it. machine_check_common enables
	 * MSR_RI.
	 */
EXC_REAL_END(machine_check, 0x200, 0x100)
EXC_VIRT_NONE(0x4200, 0x100)
TRAMP_REAL_BEGIN(machine_check_common_early)
	EXCEPTION_PROLOG_1 EXC_STD, PACA_EXMC, 0, 0x200, 0, 0, 0

EXC_COMMON_BEGIN(machine_check_early_common)
	mtctr	r10			/* Restore ctr */
	mfspr	r11,SPRN_SRR0
	mfspr	r12,SPRN_SRR1

	/*
	 * Register contents:
	 * R13		= PACA
	 * R9		= CR
	 * Original R9 to R13 is saved on PACA_EXMC
	 *
	 * Switch to mc_emergency stack and handle re-entrancy (we limit
	 * the nested MCE upto level 4 to avoid stack overflow).
	 * Save MCE registers srr1, srr0, dar and dsisr and then set ME=1
@@ -965,32 +971,30 @@ TRAMP_REAL_BEGIN(machine_check_common_early)
	 * the machine check is handled then the idle wakeup code is called
	 * to restore state.
	 */
	mr	r11,r1			/* Save r1 */
	lhz	r10,PACA_IN_MCE(r13)
	cmpwi	r10,0			/* Are we in nested machine check */
	bne	0f			/* Yes, we are. */
	/* First machine check entry */
	ld	r1,PACAMCEMERGSP(r13)	/* Use MC emergency stack */
0:	subi	r1,r1,INT_FRAME_SIZE	/* alloc stack frame */
	cmpwi	cr1,r10,MAX_MCE_DEPTH	/* Are we at maximum nesting */
	addi	r10,r10,1		/* increment paca->in_mce */
	sth	r10,PACA_IN_MCE(r13)

	mr	r10,r1			/* Save r1 */
	bne	1f
	/* First machine check entry */
	ld	r1,PACAMCEMERGSP(r13)	/* Use MC emergency stack */
1:	subi	r1,r1,INT_FRAME_SIZE	/* alloc stack frame */
	/* Limit nested MCE to level 4 to avoid stack overflow */
	cmpwi	r10,MAX_MCE_DEPTH
	bgt	2f			/* Check if we hit limit of 4 */
	std	r11,GPR1(r1)		/* Save r1 on the stack. */
	std	r11,0(r1)		/* make stack chain pointer */
	mfspr	r11,SPRN_SRR0		/* Save SRR0 */
	std	r11,_NIP(r1)
	mfspr	r11,SPRN_SRR1		/* Save SRR1 */
	std	r11,_MSR(r1)
	mfspr	r11,SPRN_DAR		/* Save DAR */
	std	r11,_DAR(r1)
	mfspr	r11,SPRN_DSISR		/* Save DSISR */
	std	r11,_DSISR(r1)
	std	r9,_CCR(r1)		/* Save CR in stackframe */
	bge	cr1,2f			/* Check if we hit limit of 4 */

	EXCEPTION_PROLOG_COMMON_1()
	/* We don't touch AMR here, we never go to virtual mode */
	/* Save r9 through r13 from EXMC save area to stack frame. */
	EXCEPTION_PROLOG_COMMON_2(PACA_EXMC)
	EXCEPTION_PROLOG_COMMON_3(0x200)

	ld	r3,PACA_EXMC+EX_DAR(r13)
	lwz	r4,PACA_EXMC+EX_DSISR(r13)
	std	r3,_DAR(r1)
	std	r4,_DSISR(r1)

	mfmsr	r11			/* get MSR value */
BEGIN_FTR_SECTION
	ori	r11,r11,MSR_ME		/* turn on ME bit */
@@ -1016,8 +1020,11 @@ END_FTR_SECTION_IFSET(CPU_FTR_HVMODE)

#ifdef CONFIG_PPC_PSERIES
TRAMP_REAL_BEGIN(machine_check_fwnmi)
	/* See comment at machine_check exception, don't turn on RI */
	EXCEPTION_PROLOG_0 PACA_EXMC
	b	machine_check_common_early
	EXCEPTION_PROLOG_1 EXC_STD, PACA_EXMC, 0, 0x200, 1, 1, 0
	mfctr	r10		/* save ctr */
	BRANCH_TO_C000(r11, machine_check_early_common)
#endif

TRAMP_KVM_SKIP(PACA_EXMC, 0x200)
@@ -1088,8 +1095,6 @@ EXC_COMMON_BEGIN(machine_check_idle_common)
	 * ME=1, MMU (IR=0 and DR=0) off and using MC emergency stack.
	 */
EXC_COMMON_BEGIN(machine_check_handle_early)
	std	r0,GPR0(r1)	/* Save r0 */
	EXCEPTION_PROLOG_COMMON_3(0x200)
	bl	save_nvgprs
	addi	r3,r1,STACK_FRAME_OVERHEAD
	bl	machine_check_early
@@ -1180,14 +1185,10 @@ BEGIN_FTR_SECTION
	mtspr	SPRN_CFAR,r10
END_FTR_SECTION_IFSET(CPU_FTR_CFAR)
	MACHINE_CHECK_HANDLER_WINDUP
	/* See comment at machine_check exception, don't turn on RI */
	EXCEPTION_PROLOG_0 PACA_EXMC
	EXCEPTION_PROLOG_1 EXC_STD, PACA_EXMC, 1, 0x200, 1, 1, 0
	EXCEPTION_PROLOG_2_REAL machine_check_common, EXC_STD, 0
	/*
	 * MSR_RI is not enabled, because PACA_EXMC is being used, so a
	 * nested machine check corrupts it. machine_check_common enables
	 * MSR_RI.
	 */

EXC_COMMON_BEGIN(unrecover_mce)
	/* Invoke machine_check_exception to print MCE event and panic. */