[RFC,07/11] powerpc/tm: Do not recheckpoint at sigreturn

Message ID 1536781219-13938-8-git-send-email-leitao@debian.org
State RFC
Headers show
Series
  • New TM Model
Related show

Checks

Context Check Description
snowpatch_ozlabs/checkpatch success Test checkpatch on branch next
snowpatch_ozlabs/apply_patch success next/apply_patch Successfully applied

Commit Message

Breno Leitao Sept. 12, 2018, 7:40 p.m.
Do not recheckpoint at signal code return. Just make sure TIF_RESTORE_TM is
set, which will restore on the exit to userspace by restore_tm_state.

All the FP and VEC lazy restore was already done by tm_reclaim_current(),
where it checked if FP/VEC was set, and filled out the ckfp and ckvr
registers area to the expected value.

The current FP/VEC restoration is not necessary, since the transaction will
be aborted and the checkpointed values will be restore.

Signed-off-by: Breno Leitao <leitao@debian.org>
---
 arch/powerpc/kernel/signal_32.c | 23 +++--------------------
 arch/powerpc/kernel/signal_64.c | 15 ++-------------
 2 files changed, 5 insertions(+), 33 deletions(-)

Comments

Michael Neuling Sept. 18, 2018, 5:32 a.m. | #1
On Wed, 2018-09-12 at 16:40 -0300, Breno Leitao wrote:
> Do not recheckpoint at signal code return. Just make sure TIF_RESTORE_TM is
> set, which will restore on the exit to userspace by restore_tm_state.

Cool, but what about the same for reclaim? Why not avoid treclaim since it's
done on entry?

Mikey

> 
> All the FP and VEC lazy restore was already done by tm_reclaim_current(),
> where it checked if FP/VEC was set, and filled out the ckfp and ckvr
> registers area to the expected value.
> 
> The current FP/VEC restoration is not necessary, since the transaction will
> be aborted and the checkpointed values will be restore.
> 
> Signed-off-by: Breno Leitao <leitao@debian.org>
> ---
>  arch/powerpc/kernel/signal_32.c | 23 +++--------------------
>  arch/powerpc/kernel/signal_64.c | 15 ++-------------
>  2 files changed, 5 insertions(+), 33 deletions(-)
> 
> diff --git a/arch/powerpc/kernel/signal_32.c b/arch/powerpc/kernel/signal_32.c
> index e6474a45cef5..4a1b17409bf3 100644
> --- a/arch/powerpc/kernel/signal_32.c
> +++ b/arch/powerpc/kernel/signal_32.c
> @@ -850,28 +850,11 @@ static long restore_tm_user_regs(struct pt_regs *regs,
>  		return 1;
>  	/* Pull in the MSR TM bits from the user context */
>  	regs->msr = (regs->msr & ~MSR_TS_MASK) | (msr_hi & MSR_TS_MASK);
> -	/* Now, recheckpoint.  This loads up all of the checkpointed (older)
> -	 * registers, including FP and V[S]Rs.  After recheckpointing, the
> -	 * transactional versions should be loaded.
> -	 */
> -	tm_enable();
> +
>  	/* Make sure the transaction is marked as failed */
>  	current->thread.tm_texasr |= TEXASR_FS;
> -	/* This loads the checkpointed FP/VEC state, if used */
> -	tm_recheckpoint(&current->thread);
> -
> -	/* This loads the speculative FP/VEC state, if used */
> -	msr_check_and_set(msr & (MSR_FP | MSR_VEC));
> -	if (msr & MSR_FP) {
> -		load_fp_state(&current->thread.fp_state);
> -		regs->msr |= (MSR_FP | current->thread.fpexc_mode);
> -	}
> -#ifdef CONFIG_ALTIVEC
> -	if (msr & MSR_VEC) {
> -		load_vr_state(&current->thread.vr_state);
> -		regs->msr |= MSR_VEC;
> -	}
> -#endif
> +	/* Make sure restore_tm_state will be called */
> +	set_thread_flag(TIF_RESTORE_TM);
>  
>  	return 0;
>  }
> diff --git a/arch/powerpc/kernel/signal_64.c b/arch/powerpc/kernel/signal_64.c
> index 83d51bf586c7..32402aa23a5e 100644
> --- a/arch/powerpc/kernel/signal_64.c
> +++ b/arch/powerpc/kernel/signal_64.c
> @@ -569,21 +569,10 @@ static long restore_tm_sigcontexts(struct task_struct
> *tsk,
>  		}
>  	}
>  #endif
> -	tm_enable();
>  	/* Make sure the transaction is marked as failed */
>  	tsk->thread.tm_texasr |= TEXASR_FS;
> -	/* This loads the checkpointed FP/VEC state, if used */
> -	tm_recheckpoint(&tsk->thread);
> -
> -	msr_check_and_set(msr & (MSR_FP | MSR_VEC));
> -	if (msr & MSR_FP) {
> -		load_fp_state(&tsk->thread.fp_state);
> -		regs->msr |= (MSR_FP | tsk->thread.fpexc_mode);
> -	}
> -	if (msr & MSR_VEC) {
> -		load_vr_state(&tsk->thread.vr_state);
> -		regs->msr |= MSR_VEC;
> -	}
> +	/* Guarantee that restore_tm_state() will be called */
> +	set_thread_flag(TIF_RESTORE_TM);
>  
>  	return err;
>  }

Patch

diff --git a/arch/powerpc/kernel/signal_32.c b/arch/powerpc/kernel/signal_32.c
index e6474a45cef5..4a1b17409bf3 100644
--- a/arch/powerpc/kernel/signal_32.c
+++ b/arch/powerpc/kernel/signal_32.c
@@ -850,28 +850,11 @@  static long restore_tm_user_regs(struct pt_regs *regs,
 		return 1;
 	/* Pull in the MSR TM bits from the user context */
 	regs->msr = (regs->msr & ~MSR_TS_MASK) | (msr_hi & MSR_TS_MASK);
-	/* Now, recheckpoint.  This loads up all of the checkpointed (older)
-	 * registers, including FP and V[S]Rs.  After recheckpointing, the
-	 * transactional versions should be loaded.
-	 */
-	tm_enable();
+
 	/* Make sure the transaction is marked as failed */
 	current->thread.tm_texasr |= TEXASR_FS;
-	/* This loads the checkpointed FP/VEC state, if used */
-	tm_recheckpoint(&current->thread);
-
-	/* This loads the speculative FP/VEC state, if used */
-	msr_check_and_set(msr & (MSR_FP | MSR_VEC));
-	if (msr & MSR_FP) {
-		load_fp_state(&current->thread.fp_state);
-		regs->msr |= (MSR_FP | current->thread.fpexc_mode);
-	}
-#ifdef CONFIG_ALTIVEC
-	if (msr & MSR_VEC) {
-		load_vr_state(&current->thread.vr_state);
-		regs->msr |= MSR_VEC;
-	}
-#endif
+	/* Make sure restore_tm_state will be called */
+	set_thread_flag(TIF_RESTORE_TM);
 
 	return 0;
 }
diff --git a/arch/powerpc/kernel/signal_64.c b/arch/powerpc/kernel/signal_64.c
index 83d51bf586c7..32402aa23a5e 100644
--- a/arch/powerpc/kernel/signal_64.c
+++ b/arch/powerpc/kernel/signal_64.c
@@ -569,21 +569,10 @@  static long restore_tm_sigcontexts(struct task_struct *tsk,
 		}
 	}
 #endif
-	tm_enable();
 	/* Make sure the transaction is marked as failed */
 	tsk->thread.tm_texasr |= TEXASR_FS;
-	/* This loads the checkpointed FP/VEC state, if used */
-	tm_recheckpoint(&tsk->thread);
-
-	msr_check_and_set(msr & (MSR_FP | MSR_VEC));
-	if (msr & MSR_FP) {
-		load_fp_state(&tsk->thread.fp_state);
-		regs->msr |= (MSR_FP | tsk->thread.fpexc_mode);
-	}
-	if (msr & MSR_VEC) {
-		load_vr_state(&tsk->thread.vr_state);
-		regs->msr |= MSR_VEC;
-	}
+	/* Guarantee that restore_tm_state() will be called */
+	set_thread_flag(TIF_RESTORE_TM);
 
 	return err;
 }