[PATCH 2/3] sched/core: Add sched_stack_end_check= boot parameter

Peter Zijlstra peterz at infradead.org
Tue Oct 27 03:17:03 PDT 2026


On Tue, Oct 27, 2026 at 02:36:21PM +0800, Chris Down wrote:
> CONFIG_SCHED_STACK_END_CHECK makes schedule_debug() check the magic at
> the end of the outgoing task's stack and panic if it has been
> overwritten.
> 
> Right now this can only be configured by setting the Kconfig option at
> build time. At Meta we have it on for some hosts and off for others,
> since it is helpful but adds cost on context switching. That means today
> we have to build separate kernels for each, which is less than ideal.
> 
> So let's make this configurable at boot time. In benchmarking sched pipe
> and sched messaging performance is unaffected.
> 
> Signed-off-by: Chris Down <chris at chrisdown.name>
> ---
>  .../admin-guide/kernel-parameters.txt         |  8 +++++
>  kernel/sched/core.c                           | 33 +++++++++++++++----
>  2 files changed, 35 insertions(+), 6 deletions(-)
> 
> diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt
> index fbee7b544903..95911d33c0fe 100644
> --- a/Documentation/admin-guide/kernel-parameters.txt
> +++ b/Documentation/admin-guide/kernel-parameters.txt
> @@ -6811,6 +6811,14 @@ Kernel parameters
>  			core priority to both SMT siblings, so this option
>  			does not favor either sibling.
>  
> +	sched_stack_end_check= [KNL]
> +			Format: <bool>
> +			Check the magic value at the end of the outgoing
> +			task's stack (and its shadow call stack, if any) on
> +			every call to schedule(), and panic if it has been
> +			overwritten.
> +			Default set by CONFIG_SCHED_STACK_END_CHECK.
> +
>  	sched_verbose	[KNL,EARLY] Enables verbose scheduler debug messages.
>  
>  	schedstats=	[KNL,X86] Enable or disable scheduled statistics.
> diff --git a/kernel/sched/core.c b/kernel/sched/core.c
> index fc269fd10192..c1fb86b813bb 100644
> --- a/kernel/sched/core.c
> +++ b/kernel/sched/core.c
> @@ -6143,18 +6143,39 @@ static noinline void __schedule_bug(struct task_struct *prev)
>  	add_taint(TAINT_WARN, LOCKDEP_STILL_OK);
>  }
>  
> +static DEFINE_STATIC_KEY_MAYBE_RO(CONFIG_SCHED_STACK_END_CHECK, sched_stack_end_check);
> +
> +static int __init setup_sched_stack_end_check(char *str)
> +{
> +	bool enable;
> +
> +	if (kstrtobool(str, &enable)) {
> +		pr_warn("Unable to parse sched_stack_end_check=\n");
> +		return 0;
> +	}
> +
> +	if (enable)
> +		static_branch_enable(&sched_stack_end_check);
> +	else
> +		static_branch_disable(&sched_stack_end_check);
> +
> +	return 1;
> +}
> +__setup("sched_stack_end_check=", setup_sched_stack_end_check);
> +
>  /*
>   * Various schedule()-time debugging checks and statistics:
>   */
>  static inline void schedule_debug(struct task_struct *prev, bool preempt)
>  {
> -#ifdef CONFIG_SCHED_STACK_END_CHECK
> -	if (task_stack_end_corrupted(prev))
> -		panic("corrupted stack end detected inside scheduler\n");
> +	if (static_branch_maybe(CONFIG_SCHED_STACK_END_CHECK,
> +				&sched_stack_end_check)) {
> +		if (task_stack_end_corrupted(prev))
> +			panic("corrupted stack end detected inside scheduler\n");
>  
> -	if (scs_is_enabled() && task_scs_end_corrupted(prev))
> -		panic("corrupted shadow stack detected inside scheduler\n");
> -#endif
> +		if (scs_is_enabled() && task_scs_end_corrupted(prev))
> +			panic("corrupted shadow stack detected inside scheduler\n");
> +	}

I just noticed that there's a number of task_stack_end_corrupted()
checks that:

 - do not also do task_scs_end_corrupted(); should
   task_scs_end_corrupted() be put inside task_stack_end_corrupted() to
   make sure they're always done in tandem and the shadow stack check
   isn't lost?

 - should these other sites also respect this switch? It seems weird to
   only have this one site affected.



More information about the linux-arm-kernel mailing list