mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
From: K Prateek Nayak <kprateek.nayak@amd.com>
To: Peter Zijlstra <peterz@infradead.org>
Cc: John Stultz <jstultz@google.com>,
	Joel Fernandes <joelagnelf@nvidia.com>,
	Qais Yousef <qyousef@layalina.io>, Ingo Molnar <mingo@redhat.com>,
	Juri Lelli <juri.lelli@redhat.com>,
	Vincent Guittot <vincent.guittot@linaro.org>,
	Dietmar Eggemann <dietmar.eggemann@arm.com>,
	Valentin Schneider <vschneid@redhat.com>,
	Steven Rostedt <rostedt@goodmis.org>,
	Ben Segall <bsegall@google.com>,
	Zimuzo Ezeozue <zezeozue@google.com>,
	Will Deacon <will@kernel.org>, Waiman Long <longman@redhat.com>,
	Boqun Feng <boqun.feng@gmail.com>,
	"Paul E. McKenney" <paulmck@kernel.org>,
	Metin Kaya <Metin.Kaya@arm.com>,
	Xuewen Yan <xuewen.yan94@gmail.com>,
	Thomas Gleixner <tglx@linutronix.de>,
	Daniel Lezcano <daniel.lezcano@linaro.org>,
	Suleiman Souhlal <suleiman@google.com>,
	kuyo chang <kuyo.chang@mediatek.com>, hupu <hupu.gm@gmail.com>,
	<linux-kernel@vger.kernel.org>, Mike Galbraith <efault@gmx.de>
Subject: Re: [PATCH 1/6] sched/proxy: Remove superfluous clear_task_blocked_in()
Date: Fri, 29 May 2026 16:24:06 +0530	[thread overview]
Message-ID: <e5e356cb-8feb-4518-81c0-5243deaa764f@amd.com> (raw)
In-Reply-To: <20260529100649.GB3144646@noisy.programming.kicks-ass.net>



On 5/29/2026 3:36 PM, Peter Zijlstra wrote:
> On Fri, May 29, 2026 at 01:28:45PM +0530, K Prateek Nayak wrote:
>> Hello John,
>>
>> On 5/29/2026 12:18 PM, John Stultz wrote:
>>> Bascially we can get in a situation where (sorry this gets a bit convoluted):
>>>
>>> 1) On CPU1,  __mutex_lock_common, we set task A
>>> blocked_on/TASK_UNINTERRUPTABLE, and call into __schedule().
>>>
>>> 2) On CPU2, task B who holds the mutex calls __mutex_unlock_slowpath()
>>> and sets task A as PROXY_WAKING and starts to call into
>>> wake_up_task().
>>>
>>> 3) On CPU1, in __schedule() we pick_next_task(), which returns task A,
>>> which is_blocked. We call find_proxy_task() and note task A is
>>> PROXY_WAKING. Since its also current, we take the short-cut and clear
>>> is_blocked and blocked_on and return task A to run.
>>>
>>> 4) On CPU2,  try_to_wake_up() hits ttwu_runnable(), and
>>> proxy_needs_return() returns false as A->blocked_on is zero.
>>>
>>> 5) On CPU 1, task A is running, it grabs the lock it was waiting for
>>> and exits __mutex_lock_common. It then enters __mutex_lock_common to
>>> grab a different mutex that is already locked. It sets itself
>>> blocked_on/TASK_INTERRUPTABLE and calls into __schedule()
>>>
>>> 6) On CPU2,  ttwu_runnable() continues, and calls ttwu_do_wakeup(),
>>> which clears A->is_blocked and sets the A->__state TASK_RUNNING
>>>
>>> 7) On CPU3, task C that holds the mutex A is waiting on, calls
>>> __mutex_unlock_slowpath, setting A as PROXY_WAKING and calls into
>>> wake_up_task()
>>>
>>> 8) On CPU1, in __schedule() pick_next_task() again returns task A. But
>>> is_blocked is now zero, so we just return task A, even though
>>> blocked_on is PROXY_WAKING.
>>>
>>> 9) On CPU1, task A gets back to the __mutex_lock_common() loop, calls
>>> set_task_blocked_on() and trips warnings as A->blocked_on is still
>>> PROXY_WAKING.
>>
>> Oh geez! Me tries to visualize:
> 
> Thanks!, I too need pictures, prose will forever confuse me :/
> 
>>
>>                 CPU1                                         CPU2                                         CPU3
>>                 ====                                         ====                                         ====
>>
>> __mutex_lock_common(MutexA)
>>   set_task_blocked_on(TaskA, MutexA)
>>   set_current_state(TASK_UNINTERRUPTABLE)      __mutex_unlock_slowpath(MutexA)
>>   ...                                            set_task_blocked_on_waking(TaskA)
>>   schedule_preempt_disabled()                    wake_up_process(TaskA)
>>     __schedule() /* (1) */                       ... /* (2) */
>>
>>     if (prev_state &..) 
>>       TaskA->is_blocked = 0;
> 
> Should this be: TaskA->is_blocked = 1? Otherwise I'm not following.

Yup! My bad.

> 
>>     next = TaskA
>>     find_proxy_task(TaskA)
>>       /* TaskA-> blocked_on == TASK_WAKING */
>>       clear_task_blocked_on(TaskA, NULL);
>>       TaskA->is_blocked = 0;        
>>                                                  ...
>>     next = TaskA /* (3) */                       
>>     rq_unlock(CPU1)                              try_to_wake_up(TaskA)
>>                                                    rq_lock(CPU1)
>>                                                    ttwu_runnable()
>>                                                      /* TaskA->blocked_on == 0 (4) */
>>                                                    ...
>>   set_curent_state(TASK_RUNNING)
>> ...
>>
>> mutex_lock(MutexB)
>>   __mutex_lock_common(MutexB)
>>     ...
>>     set_task_blocked_on(TaskA, MutexB)
>>     set_current_state(TASK_UNINTERRUPTABLE)
>>     schedule_preempt_disabled()
>>       __schedule() /* (5) */                         ...                                       __mutex_unlock_slowpath(MutexB)
>>                                                      ttwu_do_wakeup(TaskA) /* (6) */             set_task_blocked_on_waking(TaskA) /* (7) */
>>                                                      rq_unlock(CPU1)
>>
>>         rq_lock(CPU1)
>>         /* TaskA->__state == TASK_RUNNING */
>>         next = TasKA;
>>
>>         if (TaskA->is_blocked /* False */ && TaskA->blocked_on /* PROXY_WAKING */)
>>           /* Skip */
>>         next = TaskA; /* (8) */
>>
>>     set_task_blocked_on(p, MutexB)
>>
>>       !!! p->blocked_on != MutexB  !!!
>>
>>
>> Yup! That is a concern too then!
>>
>> I think we can just squash the PROXY_WAKING removal with "p->is_blocked"
>> introduction and a part of this problem should go away since unlocks
>> always clear task->blocked_on then.
> 
> While staring at this, I noted that the PROXY_WAKING removal patch
> should also remove the clear_task_blocked_on() line in the very last
> hunk.
> 
> That said, I do have a note to double check the lockless access to
> p->blocked_on there.

Now that PROXY_WAKING is gone, the only reason we locklessly inspect
p->blocked_on is with the intention of clearing it.

If we see a valid p->blocked_on, we take the lock and inspect it
again. If it is cleared, no other entity except the task can set it
for itself so it will remain blocked until the time task is
selected to run on CPU and the blocked donors don't run until they
are woken up.

> 
> Anyway, yes, the hunk removed in patch 1 cures this by clearing
> TaskA->blocked_on (because prev == current == TaskA). I don't think we
> need to squash everything into one giant patch over this if we just
> reorder things.
> 
> The Changelog of patch 1 needs an extra few links to this discussion,
> but that should be it, no?

Sure! That should do just fine.

-- 
Thanks and Regards,
Prateek


  reply	other threads:[~2026-05-29 10:54 UTC|newest]

Thread overview: 45+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-05-26 11:16 [PATCH 0/6] sched/proxy: doodles Peter Zijlstra
2026-05-26 11:16 ` [PATCH 1/6] sched/proxy: Remove superfluous clear_task_blocked_in() Peter Zijlstra
2026-05-26 23:39   ` John Stultz
2026-05-26 23:54     ` John Stultz
2026-05-27  8:59       ` Peter Zijlstra
2026-05-28 23:20     ` John Stultz
2026-05-29  6:45       ` K Prateek Nayak
2026-05-29  7:14         ` John Stultz
2026-05-29  8:24           ` K Prateek Nayak
2026-05-29  8:47         ` Peter Zijlstra
2026-05-29  8:50           ` Peter Zijlstra
2026-05-29 10:46           ` K Prateek Nayak
2026-05-30  2:56             ` John Stultz
2026-05-29  9:33         ` Peter Zijlstra
2026-05-29  6:48       ` John Stultz
2026-05-29  7:58         ` K Prateek Nayak
2026-05-29 10:06           ` Peter Zijlstra
2026-05-29 10:54             ` K Prateek Nayak [this message]
2026-06-04 18:45   ` [tip: sched/core] " tip-bot2 for Peter Zijlstra
2026-05-26 11:16 ` [PATCH 2/6] sched/proxy: Optimize try_to_wake_up() Peter Zijlstra
2026-05-27  1:56   ` John Stultz
2026-06-04 18:45   ` [tip: sched/core] " tip-bot2 for Peter Zijlstra
2026-05-26 11:16 ` [PATCH 3/6] sched: Be more strict about p->is_blocked Peter Zijlstra
2026-05-27  1:56   ` John Stultz
2026-06-04 18:45   ` [tip: sched/core] " tip-bot2 for Peter Zijlstra
2026-05-26 11:16 ` [PATCH 4/6] sched/proxy: Switch proxy to use p->is_blocked Peter Zijlstra
2026-05-26 14:57   ` Peter Zijlstra
2026-05-26 19:48     ` John Stultz
2026-05-27  2:25   ` John Stultz
2026-05-27  8:29     ` Peter Zijlstra
2026-06-04 18:45       ` [tip: sched/core] sched/proxy: Only return migrate when needed tip-bot2 for Peter Zijlstra
2026-06-04 18:45   ` [tip: sched/core] sched/proxy: Switch proxy to use p->is_blocked tip-bot2 for Peter Zijlstra
2026-05-26 11:16 ` [PATCH 5/6] sched/proxy: Remove PROXY_WAKING Peter Zijlstra
2026-06-01 10:54   ` Peter Zijlstra
2026-06-01 20:32     ` John Stultz
2026-06-02  5:22       ` K Prateek Nayak
2026-06-02  6:58         ` John Stultz
2026-06-02 10:02         ` Peter Zijlstra
2026-06-04 18:29           ` John Stultz
2026-06-04 18:41             ` Peter Zijlstra
2026-06-02  3:19     ` K Prateek Nayak
2026-06-04 18:45   ` [tip: sched/core] " tip-bot2 for K Prateek Nayak
2026-05-26 11:16 ` [PATCH 6/6] sched: Simplify ttwu_runnable() Peter Zijlstra
2026-06-04 18:45   ` [tip: sched/core] " tip-bot2 for Peter Zijlstra
2026-05-26 11:45 ` [PATCH 0/6] sched/proxy: doodles Peter Zijlstra

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=e5e356cb-8feb-4518-81c0-5243deaa764f@amd.com \
    --to=kprateek.nayak@amd.com \
    --cc=Metin.Kaya@arm.com \
    --cc=boqun.feng@gmail.com \
    --cc=bsegall@google.com \
    --cc=daniel.lezcano@linaro.org \
    --cc=dietmar.eggemann@arm.com \
    --cc=efault@gmx.de \
    --cc=hupu.gm@gmail.com \
    --cc=joelagnelf@nvidia.com \
    --cc=jstultz@google.com \
    --cc=juri.lelli@redhat.com \
    --cc=kuyo.chang@mediatek.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=longman@redhat.com \
    --cc=mingo@redhat.com \
    --cc=paulmck@kernel.org \
    --cc=peterz@infradead.org \
    --cc=qyousef@layalina.io \
    --cc=rostedt@goodmis.org \
    --cc=suleiman@google.com \
    --cc=tglx@linutronix.de \
    --cc=vincent.guittot@linaro.org \
    --cc=vschneid@redhat.com \
    --cc=will@kernel.org \
    --cc=xuewen.yan94@gmail.com \
    --cc=zezeozue@google.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

Powered by JetHome