* [PATCH] rseq: fix hard lockup on granted time slice extension
@ 2026-08-02 12:44 Niels Pressel
2026-08-03 7:19 ` Peter Zijlstra
0 siblings, 1 reply; 3+ messages in thread
From: Niels Pressel @ 2026-08-02 12:44 UTC (permalink / raw)
To: Mathieu Desnoyers, Peter Zijlstra, Paul E . McKenney, Boqun Feng
Cc: linux-kernel, Niels Pressel
In __exit_to_user_mode_loop, TSE eligibility is checked while
IRQs are enabled. Granting a TSE might involve rearming the
hrtimers. However, hrtimer_rearm_deferred_tif is expected to be
called with IRQs disabled (see include/linux/hrtimer_rearm.h:17).
Calling the function with IRQs enabled can lead to a hard lockup
because __hrtimer_rearm_deferred acquires a raw spinlock (without
disabling IRQs) that is also acquired in hard IRQ context within
hrtimer_run_queues.
Lockdep flags the issue when running the rseq selftests on the
7.2-rc5 release:
WARNING: ./include/linux/hrtimer_rearm.h:17 at irqentry_exit, CPU#1: slice_test
================================
WARNING: inconsistent lock state
7.2.0-rc5 #1 Tainted: G W
--------------------------------
inconsistent {IN-HARDIRQ-W} -> {HARDIRQ-ON-W} usage.
slice_test [HC0[0]:SC0[0]:HE1:SE1] takes:
ffff95b82ec5c698 (hrtimer_bases.lock){?.-.}-{2:2}, at: __hrtimer_rearm_deferred
{IN-HARDIRQ-W} state was registered at:
lock_acquire
_raw_spin_lock_irqsave
hrtimer_run_queues
update_process_times
tick_periodic
tick_handle_periodic
timer_interrupt
__handle_irq_event_percpu
handle_irq_event_percpu
handle_irq_event
handle_level_irq
__common_interrupt
common_interrupt
asm_common_interrupt
_raw_spin_unlock_irqrestore
__setup_irq
request_threaded_irq
hpet_time_init
x86_late_time_init
start_kernel
x86_64_start_reservations
x86_64_start_kernel
common_startup_64
Possible unsafe locking scenario:
CPU0
----
lock(hrtimer_bases.lock);
<Interrupt>
lock(hrtimer_bases.lock);
*** DEADLOCK ***
Call Trace:
<TASK>
dump_stack_lvl
print_usage_bug
mark_lock.part.0
__lock_acquire
lock_acquire
_raw_spin_lock
__hrtimer_rearm_deferred
irqentry_exit
asm_sysvec_apic_timer_interrupt
</TASK>
Originally, the issue was discovered because of intermittent lockups
when heavily using rseq TSEs.
Fix this potential lockup by disabling IRQs around the timer rearm function
call. Tested the fix using the rseq selftests.
Fixes: 15dd3a948855 ("hrtimer: Push reprogramming timers into the interrupt return path")
Signed-off-by: Niels Pressel <npressel@ethz.ch>
---
include/linux/rseq_entry.h | 1 +
1 file changed, 1 insertion(+)
diff --git a/include/linux/rseq_entry.h b/include/linux/rseq_entry.h
index ed9da6e41a2a..31ce349ed42c 100644
--- a/include/linux/rseq_entry.h
+++ b/include/linux/rseq_entry.h
@@ -233,6 +233,7 @@ static __always_inline bool __rseq_grant_slice_extension(bool work_pending)
static __always_inline bool rseq_grant_slice_extension(unsigned long ti_work, unsigned long mask)
{
if (unlikely(__rseq_grant_slice_extension(ti_work & mask))) {
+ guard(irq)();
hrtimer_rearm_deferred_tif(ti_work);
return true;
}
base-commit: f5098b6bae761e346ebcd9da7f95622c04733cff
--
2.50.1 (Apple Git-155)
^ permalink raw reply related [flat|nested] 3+ messages in thread* Re: [PATCH] rseq: fix hard lockup on granted time slice extension
2026-08-02 12:44 [PATCH] rseq: fix hard lockup on granted time slice extension Niels Pressel
@ 2026-08-03 7:19 ` Peter Zijlstra
2026-08-04 9:35 ` Niels Pressel
0 siblings, 1 reply; 3+ messages in thread
From: Peter Zijlstra @ 2026-08-03 7:19 UTC (permalink / raw)
To: Niels Pressel, Thomas Gleixner
Cc: Mathieu Desnoyers, Paul E . McKenney, Boqun Feng, linux-kernel,
x86
On Sun, Aug 02, 2026 at 02:44:23PM +0200, Niels Pressel wrote:
> In __exit_to_user_mode_loop, TSE eligibility is checked while
> IRQs are enabled. Granting a TSE might involve rearming the
> hrtimers. However, hrtimer_rearm_deferred_tif is expected to be
> called with IRQs disabled (see include/linux/hrtimer_rearm.h:17).
>
> Calling the function with IRQs enabled can lead to a hard lockup
> because __hrtimer_rearm_deferred acquires a raw spinlock (without
> disabling IRQs) that is also acquired in hard IRQ context within
> hrtimer_run_queues.
>
> Lockdep flags the issue when running the rseq selftests on the
> 7.2-rc5 release:
>
> Originally, the issue was discovered because of intermittent lockups
> when heavily using rseq TSEs.
>
> Fix this potential lockup by disabling IRQs around the timer rearm function
> call. Tested the fix using the rseq selftests.
>
> Fixes: 15dd3a948855 ("hrtimer: Push reprogramming timers into the interrupt return path")
> Signed-off-by: Niels Pressel <npressel@ethz.ch>
> ---
> include/linux/rseq_entry.h | 1 +
> 1 file changed, 1 insertion(+)
>
> diff --git a/include/linux/rseq_entry.h b/include/linux/rseq_entry.h
> index ed9da6e41a2a..31ce349ed42c 100644
> --- a/include/linux/rseq_entry.h
> +++ b/include/linux/rseq_entry.h
> @@ -233,6 +233,7 @@ static __always_inline bool __rseq_grant_slice_extension(bool work_pending)
> static __always_inline bool rseq_grant_slice_extension(unsigned long ti_work, unsigned long mask)
> {
> if (unlikely(__rseq_grant_slice_extension(ti_work & mask))) {
> + guard(irq)();
> hrtimer_rearm_deferred_tif(ti_work);
> return true;
> }
Argh!
Thomas, previously we would call hrtimer_rearm_deferred() before
re-enabling IRQs, but here it slipped past. And while disabling it will
cure the splat, I'm thinking it makes sense to reflow
__exit_to_user_mode_loop() to instead delay enabling IRQs.
Something a little like the below, but let me go find more wake-up juice
and double check.
---
kernel/entry/common.c | 11 ++++++-----
1 file changed, 6 insertions(+), 5 deletions(-)
diff --git a/kernel/entry/common.c b/kernel/entry/common.c
index e3d381fd3d25..f8c9216cbcea 100644
--- a/kernel/entry/common.c
+++ b/kernel/entry/common.c
@@ -48,11 +48,12 @@ static __always_inline unsigned long __exit_to_user_mode_loop(struct pt_regs *re
*/
while (ti_work & EXIT_TO_USER_MODE_WORK_LOOP) {
- local_irq_enable();
-
- if (ti_work & (_TIF_NEED_RESCHED | _TIF_NEED_RESCHED_LAZY)) {
- if (!rseq_grant_slice_extension(ti_work, TIF_SLICE_EXT_DENY))
- schedule();
+ if ((ti_work & (_TIF_NEED_RESCHED | _TIF_NEED_RESCHED_LAZY)) &&
+ (!rseq_grant_slice_extension(ti_work, TIF_SLICE_EXT_DENY))) {
+ local_irq_enable();
+ schedule();
+ } else {
+ local_irq_enable();
}
if (ti_work & _TIF_UPROBE)
^ permalink raw reply related [flat|nested] 3+ messages in thread* Re: [PATCH] rseq: fix hard lockup on granted time slice extension
2026-08-03 7:19 ` Peter Zijlstra
@ 2026-08-04 9:35 ` Niels Pressel
0 siblings, 0 replies; 3+ messages in thread
From: Niels Pressel @ 2026-08-04 9:35 UTC (permalink / raw)
To: Peter Zijlstra
Cc: Thomas Gleixner, Mathieu Desnoyers, Paul E. McKenney, Boqun Feng,
linux-kernel
On Mon, Aug 03, 2026 at 09:19:40AM +0100, Peter Zijlstra wrote:
> And while disabling it will cure the splat, I'm thinking it makes
> sense to reflow __exit_to_user_mode_loop() to instead delay enabling
> IRQs.
Thanks for the input, I agree. Will address this in v2.
^ permalink raw reply [flat|nested] 3+ messages in thread
end of thread, other threads:[~2026-08-04 9:35 UTC | newest]
Thread overview: 3+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-08-02 12:44 [PATCH] rseq: fix hard lockup on granted time slice extension Niels Pressel
2026-08-03 7:19 ` Peter Zijlstra
2026-08-04 9:35 ` Niels Pressel
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox