From: Peter Zijlstra <peterz@infradead.org>
To: Manfred Spraul <manfred@colorfullife.com>
Cc: LKML <linux-kernel@vger.kernel.org>,
Davidlohr Bueso <dave@stgolabs.net>,
Waiman Long <longman@redhat.com>,
1vier1@web.de, Andrew Morton <akpm@linux-foundation.org>,
Jonathan Corbet <corbet@lwn.net>
Subject: Re: [PATCH 1/6] wake_q: Cleanup + Documentation update.
Date: Mon, 14 Oct 2019 14:04:23 +0200 [thread overview]
Message-ID: <20191014120423.GD2328@hirez.programming.kicks-ass.net> (raw)
In-Reply-To: <20191012054958.3624-2-manfred@colorfullife.com>
On Sat, Oct 12, 2019 at 07:49:53AM +0200, Manfred Spraul wrote:
> 1) wake_q_add() contains a memory barrier, and callers such as
> ipc/mqueue.c rely on this barrier.
> Unfortunately, this is documented in ipc/mqueue.c, and not in the
> description of wake_q_add().
> Therefore: Update the documentation.
> Removing/updating ipc/mqueue.c will happen with the next patch in the
> series.
>
> 2) wake_q_add() ends with get_task_struct(), which is an
> unordered refcount increase. Add a clear comment that the callers
> are responsible for a barrier: most likely spin_unlock() or
> smp_store_release().
>
> 3) wake_up_q() relies on the memory barrier in try_to_wake_up().
> Add a comment, to simplify searching.
>
> 4) wake_q.next is accessed without synchroniyation by wake_q_add(),
> using cmpxchg_relaxed(), and by wake_up_q().
> Therefore: Use WRITE_ONCE in wake_up_q(), to ensure that the
> compiler doesn't perform any tricks.
>
> Signed-off-by: Manfred Spraul <manfred@colorfullife.com>
> Cc: Davidlohr Bueso <dave@stgolabs.net>
> ---
> kernel/sched/core.c | 17 ++++++++++++++---
> 1 file changed, 14 insertions(+), 3 deletions(-)
>
> diff --git a/kernel/sched/core.c b/kernel/sched/core.c
> index dd05a378631a..60ae574317fd 100644
> --- a/kernel/sched/core.c
> +++ b/kernel/sched/core.c
> @@ -440,8 +440,16 @@ static bool __wake_q_add(struct wake_q_head *head, struct task_struct *task)
> * @task: the task to queue for 'later' wakeup
> *
> * Queue a task for later wakeup, most likely by the wake_up_q() call in the
> - * same context, _HOWEVER_ this is not guaranteed, the wakeup can come
> - * instantly.
> + * same context, _HOWEVER_ this is not guaranteed. Especially, the wakeup
> + * may happen before the function returns.
> + *
> + * What is guaranteed is that there is a memory barrier before the wakeup,
> + * callers may rely on this barrier.
I would like to stress that this (wake_q_add) provides the same ordering
guarantees as a 'normal' wakeup.
> + *
> + * On the other hand, the caller must guarantee that @task does not disappear
> + * before wake_q_add() completed. wake_q_add() does not contain any memory
> + * barrier to ensure ordering, thus the caller may need to use
> + * smp_store_release().
Like Davidlohr, I'm slightly puzzled by this last paragraph.
> *
> * This function must be used as-if it were wake_up_process(); IOW the task
> * must be ready to be woken at this location.
> @@ -486,11 +494,14 @@ void wake_up_q(struct wake_q_head *head)
> BUG_ON(!task);
> /* Task can safely be re-inserted now: */
> node = node->next;
> - task->wake_q.next = NULL;
> +
> + WRITE_ONCE(task->wake_q.next, NULL);
>
> /*
> * wake_up_process() executes a full barrier, which pairs with
> * the queueing in wake_q_add() so as not to miss wakeups.
> + * The barrier is the smp_mb__after_spinlock() in
> + * try_to_wake_up().
We already have wake_up_process() documented as implying this barrier;
why do we want to mention the specifics here? That is, have a look at
the comments before try_to_wake_up().
> */
> wake_up_process(task);
> put_task_struct(task);
> --
> 2.21.0
>
next prev parent reply other threads:[~2019-10-14 12:04 UTC|newest]
Thread overview: 23+ messages / expand[flat|nested] mbox.gz Atom feed top
2019-10-12 5:49 [PATCH 0/6] V2: Clarify/standardize memory barriers for ipc Manfred Spraul
2019-10-12 5:49 ` [PATCH 1/6] wake_q: Cleanup + Documentation update Manfred Spraul
2019-10-14 6:34 ` Davidlohr Bueso
2019-10-14 12:04 ` Peter Zijlstra [this message]
2019-10-12 5:49 ` [PATCH 2/6] ipc/mqueue.c: Remove duplicated code Manfred Spraul
2019-10-14 6:35 ` Davidlohr Bueso
2019-10-14 12:37 ` Peter Zijlstra
2019-10-12 5:49 ` [PATCH 3/6] ipc/mqueue.c: Update/document memory barriers Manfred Spraul
2019-10-14 6:38 ` Davidlohr Bueso
2019-10-14 12:59 ` Peter Zijlstra
2019-10-14 13:58 ` Peter Zijlstra
2019-10-14 18:06 ` Manfred Spraul
2019-10-12 5:49 ` [PATCH 4/6] ipc/msg.c: Update and document " Manfred Spraul
2019-10-12 5:49 ` [PATCH 5/6] ipc/sem.c: Document and update " Manfred Spraul
2019-10-12 5:49 ` [PATCH 6/6] Documentation/memory-barriers.txt: Clarify cmpxchg() Manfred Spraul
2019-10-14 13:03 ` Peter Zijlstra
2019-10-14 17:49 ` Manfred Spraul
2019-10-14 19:03 ` Davidlohr Bueso
2019-10-15 7:45 ` Peter Zijlstra
2019-10-15 20:31 ` Waiman Long
2019-10-15 1:26 ` Davidlohr Bueso
2019-10-15 7:19 ` Peter Zijlstra
2019-10-15 16:26 ` Davidlohr Bueso
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=20191014120423.GD2328@hirez.programming.kicks-ass.net \
--to=peterz@infradead.org \
--cc=1vier1@web.de \
--cc=akpm@linux-foundation.org \
--cc=corbet@lwn.net \
--cc=dave@stgolabs.net \
--cc=linux-kernel@vger.kernel.org \
--cc=longman@redhat.com \
--cc=manfred@colorfullife.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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.