[PATCH] powerpc/tm: Save and restore AMR on treclaim and trechkpt

Aneesh Kumar K.V aneesh.kumar at linux.ibm.com
Fri Sep 18 14:20:47 AEST 2020


On 9/18/20 9:35 AM, Gustavo Romero wrote:
> Althought AMR is stashed on the checkpoint area, currently we don't save
> it to the per thread checkpoint struct after a treclaim and so we don't
> restore it either from that struct when we trechkpt. As a consequence when
> the transaction is later rolled back kernel space AMR value when the
> trechkpt was done appears in userspace.
> 
> That commit saves and restores AMR accordingly on treclaim and trechkpt.
> Since AMR value is also used in kernel space in other functions, it also
> takes care of stashing kernel live AMR into PACA before treclaim and before
> trechkpt, restoring it later, just before returning from tm_reclaim and
> __tm_recheckpoint.
> 
> Is also fixes two nonrelated comments about CR and MSR.
> 
> Signed-off-by: Gustavo Romero <gromero at linux.ibm.com>
> ---
>   arch/powerpc/include/asm/paca.h      |  1 +
>   arch/powerpc/include/asm/processor.h |  1 +
>   arch/powerpc/kernel/asm-offsets.c    |  2 ++
>   arch/powerpc/kernel/tm.S             | 31 +++++++++++++++++++++++-----
>   4 files changed, 30 insertions(+), 5 deletions(-)
> 
> diff --git a/arch/powerpc/include/asm/paca.h b/arch/powerpc/include/asm/paca.h
> index 9454d29ff4b4..44c605181529 100644
> --- a/arch/powerpc/include/asm/paca.h
> +++ b/arch/powerpc/include/asm/paca.h
> @@ -179,6 +179,7 @@ struct paca_struct {
>   	u64 sprg_vdso;			/* Saved user-visible sprg */
>   #ifdef CONFIG_PPC_TRANSACTIONAL_MEM
>   	u64 tm_scratch;                 /* TM scratch area for reclaim */
> +	u64 tm_amr;			/* Saved Kernel AMR for treclaim/trechkpt */
>   #endif
>   
>   #ifdef CONFIG_PPC_POWERNV
> diff --git a/arch/powerpc/include/asm/processor.h b/arch/powerpc/include/asm/processor.h
> index ed0d633ab5aa..9f4f6cc033ac 100644
> --- a/arch/powerpc/include/asm/processor.h
> +++ b/arch/powerpc/include/asm/processor.h
> @@ -220,6 +220,7 @@ struct thread_struct {
>   	unsigned long	tm_tar;
>   	unsigned long	tm_ppr;
>   	unsigned long	tm_dscr;
> +	unsigned long   tm_amr;
>   
>   	/*
>   	 * Checkpointed FP and VSX 0-31 register set.
> diff --git a/arch/powerpc/kernel/asm-offsets.c b/arch/powerpc/kernel/asm-offsets.c
> index 8711c2164b45..cf1a6d68a91f 100644
> --- a/arch/powerpc/kernel/asm-offsets.c
> +++ b/arch/powerpc/kernel/asm-offsets.c
> @@ -170,12 +170,14 @@ int main(void)
>   
>   #ifdef CONFIG_PPC_TRANSACTIONAL_MEM
>   	OFFSET(PACATMSCRATCH, paca_struct, tm_scratch);
> +	OFFSET(PACATMAMR, paca_struct, tm_amr);
>   	OFFSET(THREAD_TM_TFHAR, thread_struct, tm_tfhar);
>   	OFFSET(THREAD_TM_TEXASR, thread_struct, tm_texasr);
>   	OFFSET(THREAD_TM_TFIAR, thread_struct, tm_tfiar);
>   	OFFSET(THREAD_TM_TAR, thread_struct, tm_tar);
>   	OFFSET(THREAD_TM_PPR, thread_struct, tm_ppr);
>   	OFFSET(THREAD_TM_DSCR, thread_struct, tm_dscr);
> +	OFFSET(THREAD_TM_AMR, thread_struct, tm_amr);
>   	OFFSET(PT_CKPT_REGS, thread_struct, ckpt_regs);
>   	OFFSET(THREAD_CKVRSTATE, thread_struct, ckvr_state.vr);
>   	OFFSET(THREAD_CKVRSAVE, thread_struct, ckvrsave);
> diff --git a/arch/powerpc/kernel/tm.S b/arch/powerpc/kernel/tm.S
> index 6ba0fdd1e7f8..e178ddb43619 100644
> --- a/arch/powerpc/kernel/tm.S
> +++ b/arch/powerpc/kernel/tm.S
> @@ -152,6 +152,10 @@ _GLOBAL(tm_reclaim)
>   	li	r5, 0
>   	mtmsrd	r5, 1
>   
> +        /* Save AMR since it's used elsewhere in kernel space */
> +	mfspr	r8, SPRN_AMR
> +	std	r8, PACATMAMR(r13)


Can we save this in stack instead of PACA?


> +
>   	/*
>   	 * BE CAREFUL HERE:
>   	 * At this point we can't take an SLB miss since we have MSR_RI
> @@ -245,7 +249,7 @@ _GLOBAL(tm_reclaim)
>   	 * but is used in signal return to 'wind back' to the abort handler.
>   	 */
>   
> -	/* ******************** CR,LR,CCR,MSR ********** */
> +	/* ***************** CTR, LR, CR, XER ********** */
>   	mfctr	r3
>   	mflr	r4
>   	mfcr	r5
> @@ -256,7 +260,6 @@ _GLOBAL(tm_reclaim)
>   	std	r5, _CCR(r7)
>   	std	r6, _XER(r7)
>   
> -
>   	/* ******************** TAR, DSCR ********** */
>   	mfspr	r3, SPRN_TAR
>   	mfspr	r4, SPRN_DSCR
> @@ -264,6 +267,10 @@ _GLOBAL(tm_reclaim)
>   	std	r3, THREAD_TM_TAR(r12)
>   	std	r4, THREAD_TM_DSCR(r12)
>   
> +        /* ******************** AMR **************** */
> +        mfspr	r3, SPRN_AMR
> +        std	r3, THREAD_TM_AMR(r12)
> +
>   	/*
>   	 * MSR and flags: We don't change CRs, and we don't need to alter MSR.
>   	 */
> @@ -308,8 +315,6 @@ _GLOBAL(tm_reclaim)
>   	std	r3, THREAD_TM_TFHAR(r12)
>   	std	r4, THREAD_TM_TFIAR(r12)
>   
> -	/* AMR is checkpointed too, but is unsupported by Linux. */
> -
>   	/* Restore original MSR/IRQ state & clear TM mode */
>   	ld	r14, TM_FRAME_L0(r1)		/* Orig MSR */
>   
> @@ -330,6 +335,10 @@ _GLOBAL(tm_reclaim)
>   	ld	r0, PACA_DSCR_DEFAULT(r13)
>   	mtspr	SPRN_DSCR, r0
>   
> +        /* Restore kernel saved AMR */
> +	ld	r4, PACATMAMR(r13)
> +	mtspr	SPRN_AMR, r4
> +
>   	blr
>   
>   
> @@ -355,6 +364,10 @@ _GLOBAL(__tm_recheckpoint)
>   	 */
>   	SAVE_NVGPRS(r1)
>   
> +	/* Save kernel AMR since it's used elsewhare in kernel space */
> +	mfspr	r8, SPRN_AMR
> +	std	r8, PACATMAMR(r13)
> +
>   	/* Load complete register state from ts_ckpt* registers */
>   
>   	addi	r7, r3, PT_CKPT_REGS		/* Thread's ckpt_regs */
> @@ -404,7 +417,7 @@ _GLOBAL(__tm_recheckpoint)
>   
>   restore_gprs:
>   
> -	/* ******************** CR,LR,CCR,MSR ********** */
> +	/* ****************** CTR, LR, XER ************* */
>   	ld	r4, _CTR(r7)
>   	ld	r5, _LINK(r7)
>   	ld	r8, _XER(r7)
> @@ -417,6 +430,10 @@ restore_gprs:
>   	ld	r4, THREAD_TM_TAR(r3)
>   	mtspr	SPRN_TAR,	r4
>   
> +	/* ******************** AMR ******************** */
> +	ld	r4, THREAD_TM_AMR(r3)
> +	mtspr	SPRN_AMR, r4
> +
>   	/* Load up the PPR and DSCR in GPRs only at this stage */
>   	ld	r5, THREAD_TM_DSCR(r3)
>   	ld	r6, THREAD_TM_PPR(r3)
> @@ -522,6 +539,10 @@ restore_gprs:
>   	ld	r0, PACA_DSCR_DEFAULT(r13)
>   	mtspr	SPRN_DSCR, r0
>   
> +	/* Restore kernel saved AMR */
> +	ld	r4, PACATMAMR(r13)
> +	mtspr	SPRN_AMR, r4
> +
>   	blr
>   
>   	/* ****************************************************************** */
> 



More information about the Linuxppc-dev mailing list