Re: [PATCH] futex: Make FUTEX_WAITERS state consistent for robust futex unlock

From: Thomas Gleixner

Date: Fri Jul 31 2026 - 06:50:44 EST


On Fri, Jul 31 2026 at 00:36, Keno Fischer wrote:
> Thanks for the detailed changelog - I think it lays everything out very nicely.
> The optimization added in this revision isn't quite sound as written, but should
> be easy to fix - see below. Just a few minor nits on the changelog language
> otherwise.
>
> On Thu, Jul 30, 2026 at 6:15 PM Thomas Gleixner <tglx@xxxxxxxxxx> wrote:
>> Keno reported another subtle futex exit race, which is neither handled by
>> commit 3ca9595d9fb6 ("futex: Add support for unlocking robust futexes") nor
>> by the recent efforts around commit 3ca9595d9fb6 ("futex: Add support for
>> unlocking robust futexes").
>
> Duplicate shas - ca16d5bee598 ("futex: Prevent robust futex exit
> race") for the first one?

Wanted to referrence ca16d5bee598 ("futex: Prevent robust futex exit
race") obviously.

>> Amend that proceedure so it does the following steps:
>
> typo
>
>> 4) Try to unlock the user space lock value either with 0 or
>> FUTEX_WAITERS according to the result of #3
>
> I think it would be good to note here (or in robust-futex-ABI.rst)
> that this is a change to the non-PI futex protocol ABI so that userspace
> can appropriately coordinate the ABI versioning when adopting
> FUTEX_ROBUST_UNLOCK.

Makes sense

>> As #3 and #6 seem to be redundant operations they are not because as
>> explained above the elegible waiters cannot be collected into the wake
>> queue before the to be set state of the FUTEX_WAITERS bit has been
>> established.
>
> typo 'elegible' -> 'eligible'; same in the paragraph below this
>
>> + /*
>> + * Waiters are counted independent of the bitset match. Stop the
>> + * list walk when the total number of waiters becomes larger
>> + * than the number of to be woken up tasks. In that case it does
>> + * not matter how many wakees have been found. There will be
>> + * waiters queued after the wake up no matter what.
>> + */
>> + if (++waiters > nr_wake)
>> + return 1;
>
> On bitset mismatch, this will early-out before caching the wakee below, losing
> the wake.

Duh. Heat induced brain fart.

>> + /*
>> + * This should never happen because evaluate_waiters() would
>> + * have detected a PI futex mixup already.
>> + */
>> + if (WARN_ON_ONCE(nr_woken < 0))
>> + return nr_woken;
>
> I missed this before, but the same issue makes this WARN reachable. If there's
> a bunch of bitset-mismatched waiters at the start of the queue, then the check
> will early out and the PI mixup will not be discovered until the second walk.

Yes, but that has been the case forever and it's done opportunisticly to
avoid full hash bucket walks wherever possible.

Thanks,

tglx