[PATCH v2 2/3] nptl: Add libc allocated shadow stack for new threads

Mark Brown broonie@kernel.org
Thu Sep 18 20:09:23 GMT 2025


On Thu, Sep 18, 2025 at 06:30:08PM +0100, Catalin Marinas wrote:
> On Thu, Sep 18, 2025 at 06:27:15PM +0100, Catalin Marinas wrote:
> > > On Wed, Sep 17, 2025 at 04:29:36PM -0300, Adhemerval Zanella Netto wrote:
> [... lots of text trimmed ...]

> > > There is no requirement to use this interface at all, if userspace
> > > doesn't use this interface it will continue to see the existing
> > > behaviour.

> I'd like to have at least a user of such interface, otherwise we just
> maintain a user-kernel ABI that never gets exercised, other than
> kselftests.

Yes, clearly we want to end up with something that can be actually used.

> Given that the kernel patches are possibly going into 6.18, we need some
> quick decision on:

> 1. Defer the kernel patches to 6.19 (or later) until the glibc
>    discussion settles

Ideally we'll be able to come to a conclusion fairly rapidly and not
have to defer.

> 2. Keep the clone3() interface as is and separately add a patch to
>    re-instate the token on the shadow stack to facilitate reuse

> 3. Another mechanism that allows shadow stack reuse independent of the
>    clone3() interface

I think a shadow stack reuse is a reasonable request, especially if we
make it optional so that non-glibc userspaces can avoid it it it's not
desired (though I'm not sure how big a concern that is so perhaps it's
more trouble than it's worth).

My specific suggestion here was to model this like stack pivoting (as we
do for starting a thread in this series) so that when a thread exits we
write a pivot token to the current pointer, allowing the stack to be
used by another thread.  This would align with glibc's existing reuse of
normal stacks, the initial feedback on the glibc patches was broadly
"we're trying to have a thread stack cache here".  glibc already unwinds
the userspace stack as part of a normal thread exit which would fit
nicely with this approach.  If we want to make this optional then a flag
on PR_SHADOW_STACK_STATUS seems sensible.

AFAICT this is most closely aligned with what glibc is currently trying
to do and it's straightforward enough to implement on the kernel side.

> 4. Change the clone3() interface to allow a NULL shadow stack pointer
>    but introduce a size to struct clone_args (it implies (1) above). The
>    kernel would allocate the shadow stack accordingly

To clarify we already allow a NULL shadow stack pointer (this gets you a
kernel managed shadow stack as per the exitsting ABI), the change here
would be to allow userspace to control the size of that kernel managed
shadow stack.  I think this should be usable for userspace but does mean
that it's not possible to do the cache of thread stacks, it was
suggested as a "if we can't do reuse..." thing.

My main concern with this approach is that it's only offering limited
control to userspace so I think even if we don't now we will inevitably
end up wanting to make userspace managed allocation work, the existing
glibc thread stack cache is a current example and I can imagine a
runtime wanting to do things like switching green threads to real
threads.

> 5. Any other option? This likely implies (1)

I guess there's also option allowing configuration of stack size only
(without the ability for userspace to manage the allocation).  That has
the same limitations as configuring the stack size.

I don't think I've seen any other suggestions.

> The prctl() to set a default shadow stack size is a good discussion to
> have but complementary to the clone3() interface.

I agree, that idea is mainly directed at the userspaces that find they
need to block clone3().

> So, if Yury's nptl patches using clone3() aren't going in, I'd rather
> opt for (1) w.r.t. the kernel patches. I know we had these patches
> around for nearly two years but I also like to see some users of the
> interface longer term.

If we can agree that that the interface in the current series is a good
one for thread creation it would be good to get it merged, so long as we
have a clear plan for what needs to be added.  That would be helpful for
both cleanup work on the shadow stack support (I've got a bit of a list
there, largely pulling stuff out into common code but some general
improvements too) and the RISC-V support (which is itself almost there,
it'd be good if it could have clone3() from day one).  The less code we
have in flight, and the simpler the decisions involved in the code that
is in flight, the easier it will be to get the many different people who
need to look at this stuff to do so.
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 488 bytes
Desc: not available
URL: <https://sourceware.org/pipermail/libc-alpha/attachments/20250918/37fb2941/attachment-0001.sig>


More information about the Libc-alpha mailing list