* [PATCH 0/2] x86: Support shstk via prctl @ 2026-07-14 15:47 Bill Roberts 2026-07-14 15:47 ` [PATCH 1/2] x86/shstk: support " Bill Roberts 2026-07-14 15:47 ` [PATCH 2/2] selftests/x86: add generic prctl shadow stack test Bill Roberts 0 siblings, 2 replies; 13+ messages in thread From: Bill Roberts @ 2026-07-14 15:47 UTC (permalink / raw) To: H. Peter Anvin, Albert Ou, Alexandre Ghiti, Borislav Petkov, Dave Hansen, Ingo Molnar, Palmer Dabbelt, Paul Walmsley, Shuah Khan, Thomas Gleixner, x86 Cc: linux-kernel, linux-kselftest, linux-riscv, Bill Roberts The motivation for having a common interface between x86 and others is: 1. Common permission checking for an LSM (future patches) 2. Common userspace This leaves the arch_prctl interface intact, so older userspaces will continue to work. However, for item 1, when we introduce LSM hooks, they will need to reside on both the prctl and arch_prctl interfaces but will both call into the LSM with all of the same permission bits and checks. The SE Linux patches will follow these, after I address any feedback on these patches, since they can stand alone. Bill Roberts (2): x86/shstk: support via prctl selftests/x86: add generic prctl shadow stack test arch/x86/kernel/shstk.c | 35 ++++++++++++ tools/testing/selftests/x86/Makefile | 3 +- .../testing/selftests/x86/test_shadow_stack.c | 55 +++++++++++++++---- .../selftests/x86/test_shadow_stack_prctl.c | 3 + 4 files changed, 85 insertions(+), 11 deletions(-) create mode 100644 tools/testing/selftests/x86/test_shadow_stack_prctl.c -- 2.54.0 ^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH 1/2] x86/shstk: support via prctl 2026-07-14 15:47 [PATCH 0/2] x86: Support shstk via prctl Bill Roberts @ 2026-07-14 15:47 ` Bill Roberts 2026-07-29 13:29 ` Edgecombe, Rick P 2026-07-14 15:47 ` [PATCH 2/2] selftests/x86: add generic prctl shadow stack test Bill Roberts 1 sibling, 1 reply; 13+ messages in thread From: Bill Roberts @ 2026-07-14 15:47 UTC (permalink / raw) To: H. Peter Anvin, Albert Ou, Alexandre Ghiti, Borislav Petkov, Dave Hansen, Ingo Molnar, Palmer Dabbelt, Paul Walmsley, Shuah Khan, Thomas Gleixner, x86 Cc: linux-kernel, linux-kselftest, linux-riscv, Bill Roberts Historically, managing the user-space shadow stack state on x86 has been handled exclusively through the arch_prctl() interface via the ARCH_SHSTK_* operations. However, other architectures (such as arm64 and riscv) do not implement arch_prctl() and instead utilize the newer, arch-agnostic, prctl() interface (i.e. PR_GET_SHADOW_STACK_STATUS and PR_SET_SHADOW_STACK_STATUS). To provide language runtimes, toolchains, and libc implementations with a consistent, cross-architecture interface for managing control-flow integrity, wire up the generic shadow stack prctl handlers for x86. Map the generic PR_SHADOW_STACK_ENABLE, PR_SHADOW_STACK_DISABLE, and PR_SHADOW_STACK_LOCK operations onto the underlying x86 internal CET helper routines. This allows portable userspace applications to toggle or query shadow stack states without relying on architecture-specific system calls, while maintaining backward compatibility with existing arch_prctl() calls. Signed-off-by: Bill Roberts <bill.roberts@arm.com> --- arch/x86/kernel/shstk.c | 35 +++++++++++++++++++++++++++++++++++ 1 file changed, 35 insertions(+) diff --git a/arch/x86/kernel/shstk.c b/arch/x86/kernel/shstk.c index 0ca64900192f..ef3db94eec6a 100644 --- a/arch/x86/kernel/shstk.c +++ b/arch/x86/kernel/shstk.c @@ -18,6 +18,7 @@ #include <linux/sizes.h> #include <linux/user.h> #include <linux/syscalls.h> +#include <linux/prctl.h> #include <asm/msr.h> #include <asm/fpu/xstate.h> #include <asm/fpu/types.h> @@ -630,3 +631,37 @@ bool shstk_is_enabled(void) { return features_enabled(ARCH_SHSTK_SHSTK); } + +/* We assume the prctl() feature bits line up with the arch_prctl() specific ones. */ +static_assert(PR_SHADOW_STACK_ENABLE == ARCH_SHSTK_SHSTK); +static_assert(PR_SHADOW_STACK_WRITE == ARCH_SHSTK_WRSS); + +/* Handles the generic prctl interface for PR_SET_SHADOW_STACK_STATUS and its feature bits */ +int arch_set_shadow_stack_status(struct task_struct *t, unsigned long status) +{ + int rc; + + /* x86 arch_prctl is single bit at a time, so handle these one at time */ + if (!status & PR_SHADOW_STACK_ENABLE) + return shstk_prctl(t, ARCH_SHSTK_DISABLE, ARCH_SHSTK_SHSTK); + + rc = shstk_prctl(t, ARCH_SHSTK_ENABLE, ARCH_SHSTK_SHSTK); + if (rc) + return rc; + + if (status & PR_SHADOW_STACK_WRITE) + return shstk_prctl(t, ARCH_SHSTK_ENABLE, ARCH_SHSTK_WRSS); + + return shstk_prctl(t, ARCH_SHSTK_DISABLE, ARCH_SHSTK_WRSS); +} + +/* Handles the generic prctl interface for PR_LOCK_SHADOW_STACK_STATUS and its feature bits */ +int arch_lock_shadow_stack_status(struct task_struct *t, unsigned long status) +{ + return shstk_prctl(t, ARCH_SHSTK_LOCK, status); +} + +int arch_get_shadow_stack_status(struct task_struct *t, unsigned long __user *status) +{ + return shstk_prctl(t, ARCH_SHSTK_STATUS, (unsigned long)status); +} -- 2.54.0 ^ permalink raw reply related [flat|nested] 13+ messages in thread
* Re: [PATCH 1/2] x86/shstk: support via prctl 2026-07-14 15:47 ` [PATCH 1/2] x86/shstk: support " Bill Roberts @ 2026-07-29 13:29 ` Edgecombe, Rick P 2026-08-03 17:41 ` Bill Roberts 0 siblings, 1 reply; 13+ messages in thread From: Edgecombe, Rick P @ 2026-07-29 13:29 UTC (permalink / raw) To: x86@kernel.org, bp@alien8.de, dave.hansen@linux.intel.com, pjw@kernel.org, hpa@zytor.com, aou@eecs.berkeley.edu, mingo@redhat.com, alex@ghiti.fr, palmer@dabbelt.com, bill.roberts@arm.com, shuah@kernel.org, tglx@kernel.org Cc: linux-riscv@lists.infradead.org, linux-kernel@vger.kernel.org, linux-kselftest@vger.kernel.org On Tue, 2026-07-14 at 10:47 -0500, Bill Roberts wrote: > Historically, managing the user-space shadow stack state on x86 has > been handled exclusively through the arch_prctl() interface via the > ARCH_SHSTK_* operations. However, other architectures (such as arm64 and > riscv) do not implement arch_prctl() and instead utilize the newer, > arch-agnostic, prctl() interface (i.e. PR_GET_SHADOW_STACK_STATUS and > PR_SET_SHADOW_STACK_STATUS). > > To provide language runtimes, toolchains, and libc implementations with a > consistent, cross-architecture interface for managing control-flow > integrity, wire up the generic shadow stack prctl handlers for x86. I think glibc doesn't handles this in arch code, right? So the point of this is only your SE Linux patches. Or is there other cross-arch code that wants to handle shadow stack? BTW, for non security module people, can you explain why it needs this design? > > Map the generic PR_SHADOW_STACK_ENABLE, PR_SHADOW_STACK_DISABLE, and > PR_SHADOW_STACK_LOCK operations onto the underlying x86 internal CET helper > routines. This allows portable userspace applications to toggle or query > shadow stack states without relying on architecture-specific system calls, > while maintaining backward compatibility with existing arch_prctl() calls. Can you explain why not to include ARCH_SHSTK_UNLOCK? https://lore.kernel.org/lkml/e1362732ba86990b7707d3f5b785358b77c5f896.camel@intel.com/ > > Signed-off-by: Bill Roberts <bill.roberts@arm.com> > --- > arch/x86/kernel/shstk.c | 35 +++++++++++++++++++++++++++++++++++ > 1 file changed, 35 insertions(+) > > diff --git a/arch/x86/kernel/shstk.c b/arch/x86/kernel/shstk.c > index 0ca64900192f..ef3db94eec6a 100644 > --- a/arch/x86/kernel/shstk.c > +++ b/arch/x86/kernel/shstk.c > @@ -18,6 +18,7 @@ > #include <linux/sizes.h> > #include <linux/user.h> > #include <linux/syscalls.h> > +#include <linux/prctl.h> > #include <asm/msr.h> > #include <asm/fpu/xstate.h> > #include <asm/fpu/types.h> > @@ -630,3 +631,37 @@ bool shstk_is_enabled(void) > { > return features_enabled(ARCH_SHSTK_SHSTK); > } > + > +/* We assume the prctl() feature bits line up with the arch_prctl() specific > ones. */ > +static_assert(PR_SHADOW_STACK_ENABLE == ARCH_SHSTK_SHSTK); > +static_assert(PR_SHADOW_STACK_WRITE == ARCH_SHSTK_WRSS); This is only needed for arch_get_shadow_stack_status()? So can we put it near by and explain why? > + > +/* Handles the generic prctl interface for PR_SET_SHADOW_STACK_STATUS and its > feature bits */ > +int arch_set_shadow_stack_status(struct task_struct *t, unsigned long status) > +{ > + int rc; It needs to reject invalid options for status. > + > + /* x86 arch_prctl is single bit at a time, so handle these one at > time */ > + if (!status & PR_SHADOW_STACK_ENABLE) > + return shstk_prctl(t, ARCH_SHSTK_DISABLE, ARCH_SHSTK_SHSTK); > + > + rc = shstk_prctl(t, ARCH_SHSTK_ENABLE, ARCH_SHSTK_SHSTK); > + if (rc) > + return rc; > + > + if (status & PR_SHADOW_STACK_WRITE) > + return shstk_prctl(t, ARCH_SHSTK_ENABLE, ARCH_SHSTK_WRSS); > + > + return shstk_prctl(t, ARCH_SHSTK_DISABLE, ARCH_SHSTK_WRSS); > +} > + > +/* Handles the generic prctl interface for PR_LOCK_SHADOW_STACK_STATUS and > its feature bits */ > +int arch_lock_shadow_stack_status(struct task_struct *t, unsigned long > status) > +{ > + return shstk_prctl(t, ARCH_SHSTK_LOCK, status); > +} > + > +int arch_get_shadow_stack_status(struct task_struct *t, unsigned long __user > *status) > +{ > + return shstk_prctl(t, ARCH_SHSTK_STATUS, (unsigned long)status); > +} ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 1/2] x86/shstk: support via prctl 2026-07-29 13:29 ` Edgecombe, Rick P @ 2026-08-03 17:41 ` Bill Roberts 2026-08-03 18:14 ` Edgecombe, Rick P 0 siblings, 1 reply; 13+ messages in thread From: Bill Roberts @ 2026-08-03 17:41 UTC (permalink / raw) To: Edgecombe, Rick P, x86@kernel.org, bp@alien8.de, dave.hansen@linux.intel.com, pjw@kernel.org, hpa@zytor.com, aou@eecs.berkeley.edu, mingo@redhat.com, alex@ghiti.fr, palmer@dabbelt.com, shuah@kernel.org, tglx@kernel.org Cc: linux-riscv@lists.infradead.org, linux-kernel@vger.kernel.org, linux-kselftest@vger.kernel.org On 7/29/26 8:29 AM, Edgecombe, Rick P wrote: > On Tue, 2026-07-14 at 10:47 -0500, Bill Roberts wrote: >> Historically, managing the user-space shadow stack state on x86 has >> been handled exclusively through the arch_prctl() interface via the >> ARCH_SHSTK_* operations. However, other architectures (such as arm64 and >> riscv) do not implement arch_prctl() and instead utilize the newer, >> arch-agnostic, prctl() interface (i.e. PR_GET_SHADOW_STACK_STATUS and >> PR_SET_SHADOW_STACK_STATUS). >> >> To provide language runtimes, toolchains, and libc implementations with a >> consistent, cross-architecture interface for managing control-flow >> integrity, wire up the generic shadow stack prctl handlers for x86. > I think glibc doesn't handles this in arch code, right? Did you mean "I think glibc does handle this in arch code, right?". If so, yes, glibc handles this in arch code. It would be nice if could also merge this for all architectures in the future. > So the point of this is > only your SE Linux patches. Or is there other cross-arch code that wants to > handle shadow stack? > > BTW, for non security module people, can you explain why it needs this design? Yes will add this to the commit message for v2. But as you know, the gist would be, if we lock the front door of the house, we should lock the back door too or the lock is useless. > >> Map the generic PR_SHADOW_STACK_ENABLE, PR_SHADOW_STACK_DISABLE, and >> PR_SHADOW_STACK_LOCK operations onto the underlying x86 internal CET helper >> routines. This allows portable userspace applications to toggle or query >> shadow stack states without relying on architecture-specific system calls, >> while maintaining backward compatibility with existing arch_prctl() calls. > Can you explain why not to include ARCH_SHSTK_UNLOCK? > https://lore.kernel.org/lkml/e1362732ba86990b7707d3f5b785358b77c5f896.camel@intel.com From what I can tell, there is no analogous operation in the common flow, you lock the thread features, and the features are locked in perpetuity for the thread. If you need fluid changes to these bits, you just don't lock it. If in the future the generic interface gets this, then it would make sense for sure. > >> Signed-off-by: Bill Roberts <bill.roberts@arm.com> >> --- >> arch/x86/kernel/shstk.c | 35 +++++++++++++++++++++++++++++++++++ >> 1 file changed, 35 insertions(+) >> >> diff --git a/arch/x86/kernel/shstk.c b/arch/x86/kernel/shstk.c >> index 0ca64900192f..ef3db94eec6a 100644 >> --- a/arch/x86/kernel/shstk.c >> +++ b/arch/x86/kernel/shstk.c >> @@ -18,6 +18,7 @@ >> #include <linux/sizes.h> >> #include <linux/user.h> >> #include <linux/syscalls.h> >> +#include <linux/prctl.h> >> #include <asm/msr.h> >> #include <asm/fpu/xstate.h> >> #include <asm/fpu/types.h> >> @@ -630,3 +631,37 @@ bool shstk_is_enabled(void) >> { >> return features_enabled(ARCH_SHSTK_SHSTK); >> } >> + >> +/* We assume the prctl() feature bits line up with the arch_prctl() specific >> ones. */ >> +static_assert(PR_SHADOW_STACK_ENABLE == ARCH_SHSTK_SHSTK); >> +static_assert(PR_SHADOW_STACK_WRITE == ARCH_SHSTK_WRSS); > This is only needed for arch_get_shadow_stack_status()? So can we put it near by > and explain why? > >> + >> +/* Handles the generic prctl interface for PR_SET_SHADOW_STACK_STATUS and its >> feature bits */ >> +int arch_set_shadow_stack_status(struct task_struct *t, unsigned long status) >> +{ >> + int rc; > It needs to reject invalid options for status. > >> + >> + /* x86 arch_prctl is single bit at a time, so handle these one at >> time */ >> + if (!status & PR_SHADOW_STACK_ENABLE) >> + return shstk_prctl(t, ARCH_SHSTK_DISABLE, ARCH_SHSTK_SHSTK); >> + >> + rc = shstk_prctl(t, ARCH_SHSTK_ENABLE, ARCH_SHSTK_SHSTK); >> + if (rc) >> + return rc; >> + >> + if (status & PR_SHADOW_STACK_WRITE) >> + return shstk_prctl(t, ARCH_SHSTK_ENABLE, ARCH_SHSTK_WRSS); >> + >> + return shstk_prctl(t, ARCH_SHSTK_DISABLE, ARCH_SHSTK_WRSS); >> +} >> + >> +/* Handles the generic prctl interface for PR_LOCK_SHADOW_STACK_STATUS and >> its feature bits */ >> +int arch_lock_shadow_stack_status(struct task_struct *t, unsigned long >> status) >> +{ >> + return shstk_prctl(t, ARCH_SHSTK_LOCK, status); >> +} >> + >> +int arch_get_shadow_stack_status(struct task_struct *t, unsigned long __user >> *status) >> +{ >> + return shstk_prctl(t, ARCH_SHSTK_STATUS, (unsigned long)status); >> +} ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 1/2] x86/shstk: support via prctl 2026-08-03 17:41 ` Bill Roberts @ 2026-08-03 18:14 ` Edgecombe, Rick P 2026-08-04 18:23 ` Bill Roberts 0 siblings, 1 reply; 13+ messages in thread From: Edgecombe, Rick P @ 2026-08-03 18:14 UTC (permalink / raw) To: shuah@kernel.org, dave.hansen@linux.intel.com, bp@alien8.de, pjw@kernel.org, hpa@zytor.com, mingo@redhat.com, aou@eecs.berkeley.edu, x86@kernel.org, palmer@dabbelt.com, bill.roberts@arm.com, alex@ghiti.fr, tglx@kernel.org Cc: linux-riscv@lists.infradead.org, linux-kernel@vger.kernel.org, linux-kselftest@vger.kernel.org On Mon, 2026-08-03 at 12:41 -0500, Bill Roberts wrote: > > > Map the generic PR_SHADOW_STACK_ENABLE, PR_SHADOW_STACK_DISABLE, and > > > PR_SHADOW_STACK_LOCK operations onto the underlying x86 internal CET > > > helper > > > routines. This allows portable userspace applications to toggle or query > > > shadow stack states without relying on architecture-specific system calls, > > > while maintaining backward compatibility with existing arch_prctl() calls. > > Can you explain why not to include ARCH_SHSTK_UNLOCK? > > https://lore.kernel.org/lkml/e1362732ba86990b7707d3f5b785358b77c5f896.camel@intel.com > From what I can tell, there is no analogous operation in the common > flow, you lock the thread features, and > the features are locked in perpetuity for the thread. If you need fluid > changes to these bits, you just don't lock > it. If in the future the generic interface gets this, then it would make > sense for sure. ptrace has as special handling for arch_prctl. So to unlock for CRIU (where unlock came from), it needs to go via arch_prctl. I wonder what the other arch's will do for this. If we unify the ABI, it seems the generic one that is getting implemented in this series is incomplete. Unless the API will be split always between the two syscalls. ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 1/2] x86/shstk: support via prctl 2026-08-03 18:14 ` Edgecombe, Rick P @ 2026-08-04 18:23 ` Bill Roberts 2026-08-04 18:49 ` Edgecombe, Rick P 0 siblings, 1 reply; 13+ messages in thread From: Bill Roberts @ 2026-08-04 18:23 UTC (permalink / raw) To: Edgecombe, Rick P, shuah@kernel.org, dave.hansen@linux.intel.com, bp@alien8.de, pjw@kernel.org, hpa@zytor.com, mingo@redhat.com, aou@eecs.berkeley.edu, x86@kernel.org, palmer@dabbelt.com, alex@ghiti.fr, tglx@kernel.org Cc: linux-riscv@lists.infradead.org, linux-kernel@vger.kernel.org, linux-kselftest@vger.kernel.org On 8/3/26 1:14 PM, Edgecombe, Rick P wrote: > On Mon, 2026-08-03 at 12:41 -0500, Bill Roberts wrote: >>>> Map the generic PR_SHADOW_STACK_ENABLE, PR_SHADOW_STACK_DISABLE, and >>>> PR_SHADOW_STACK_LOCK operations onto the underlying x86 internal CET >>>> helper >>>> routines. This allows portable userspace applications to toggle or query >>>> shadow stack states without relying on architecture-specific system calls, >>>> while maintaining backward compatibility with existing arch_prctl() calls. >>> Can you explain why not to include ARCH_SHSTK_UNLOCK? >>> https://lore.kernel.org/lkml/e1362732ba86990b7707d3f5b785358b77c5f896.camel@intel.com >> From what I can tell, there is no analogous operation in the common >> flow, you lock the thread features, and >> the features are locked in perpetuity for the thread. If you need fluid >> changes to these bits, you just don't lock >> it. If in the future the generic interface gets this, then it would make >> sense for sure. > ptrace has as special handling for arch_prctl. So to unlock for CRIU (where > unlock came from), it needs to go via arch_prctl. I wonder what the other arch's > will do for this. If we unify the ABI, it seems the generic one that is getting > implemented in this series is incomplete. Unless the API will be split always > between the two syscalls. When they add unlock to the generic interface, then that will be the time to rectify that. Just looking through patches and stuff, I think that side is still in flight, eg https://lkml.org/lkml/2026/4/3/1651. It also looks like the model is slightly different, in that there is a window when all of this should be handled, and then locked permanently. I know on our side of the house, locking isn't really being used yet. But that's criu, right now, the main things I would like to coalesce is libc's. As MUSL and others get patches, it would be much simpler to have one interface to do this in, and right now unlock is unused (even in the test suite :-p). Ill spin out a v2 with the comments, but the one thing left to be addressed, afaik, is the testing patch do you want that? I'll drop it, but I think that's a bad approach. ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 1/2] x86/shstk: support via prctl 2026-08-04 18:23 ` Bill Roberts @ 2026-08-04 18:49 ` Edgecombe, Rick P 2026-08-04 20:43 ` Bill Roberts 0 siblings, 1 reply; 13+ messages in thread From: Edgecombe, Rick P @ 2026-08-04 18:49 UTC (permalink / raw) To: tglx@kernel.org, dave.hansen@linux.intel.com, bp@alien8.de, pjw@kernel.org, hpa@zytor.com, mingo@redhat.com, aou@eecs.berkeley.edu, shuah@kernel.org, palmer@dabbelt.com, bill.roberts@arm.com, alex@ghiti.fr, x86@kernel.org Cc: linux-riscv@lists.infradead.org, linux-kernel@vger.kernel.org, linux-kselftest@vger.kernel.org On Tue, 2026-08-04 at 13:23 -0500, Bill Roberts wrote: > When they add unlock to the generic interface, then that will be the > time to rectify that. Just looking > through patches and stuff, I think that side is still in flight, eg > https://lkml.org/lkml/2026/4/3/1651. This looks like it is about clearing lock bits after exec. What I am talking about is "PTRACE_ARCH_PRCTL". It's a special ptrace capability that only can poke at arch_prtcl and not regular prctl. > It also looks like the model is slightly different, in that there is a > window when all of this should be > handled, and then locked permanently. I know on our side of the house, > locking isn't really being > used yet. But that's criu, right now, the main things I would like to > coalesce is libc's. > IIRC CRIU needed to unlock shadow stack during the save. Because it's tricks for saving the process involved messing with the stack. So it needs to be able to unlock but *only* via ptrace. Apps cannot be allowed to unlock themselves. Because, well, obviously.. > As MUSL and > others get patches, it would be much simpler to have one interface to do > this in, and right now > unlock is unused (even in the test suite :-p). I think I raised this on the other arch's APIs originally. x86 went first, and then later arm/riscv wanted a unified approach, but didn't solve this ptrace unlock part. So we didn't join. AFAICT the situation hasn't changed. So I'm worried it's too soon to unify. Or we might need to do multiple steps of unifications. Also looking forward to understanding the security module problem statement better. > > Ill spin out a v2 with the comments, but the one thing left to be > addressed, afaik, is the testing patch > do you want that? I'll drop it, but I think that's a bad approach. Yea, I hear your point. It is good to test more, but #including c files with pre-processor switches seems too hacky. Is there anything we could do to make it in one c file? Like not the templated tricks to generate two test binaries? For example embed the switch between the two APIs in a macros in the single file. Like say we have SHSTK_ENABLE(). Inside it does either ARCH_PRCTL() or regular. Then have a global or something that switches between the two behaviors. Pull out the parts in main() into something that could be run twice? ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 1/2] x86/shstk: support via prctl 2026-08-04 18:49 ` Edgecombe, Rick P @ 2026-08-04 20:43 ` Bill Roberts 2026-08-04 21:59 ` Edgecombe, Rick P 0 siblings, 1 reply; 13+ messages in thread From: Bill Roberts @ 2026-08-04 20:43 UTC (permalink / raw) To: Edgecombe, Rick P, tglx@kernel.org, dave.hansen@linux.intel.com, bp@alien8.de, pjw@kernel.org, hpa@zytor.com, mingo@redhat.com, aou@eecs.berkeley.edu, shuah@kernel.org, palmer@dabbelt.com, alex@ghiti.fr, x86@kernel.org Cc: linux-riscv@lists.infradead.org, linux-kernel@vger.kernel.org, linux-kselftest@vger.kernel.org On 8/4/26 1:49 PM, Edgecombe, Rick P wrote: > On Tue, 2026-08-04 at 13:23 -0500, Bill Roberts wrote: >> When they add unlock to the generic interface, then that will be the >> time to rectify that. Just looking >> through patches and stuff, I think that side is still in flight, eg >> https://lkml.org/lkml/2026/4/3/1651. > This looks like it is about clearing lock bits after exec. What I am talking > about is "PTRACE_ARCH_PRCTL". It's a special ptrace capability that only can > poke at arch_prtcl and not regular prctl. Ahh, Ok thanks for clarifying that. >> It also looks like the model is slightly different, in that there is a >> window when all of this should be >> handled, and then locked permanently. I know on our side of the house, >> locking isn't really being >> used yet. But that's criu, right now, the main things I would like to >> coalesce is libc's. >> > IIRC CRIU needed to unlock shadow stack during the save. Because it's tricks for > saving the process involved messing with the stack. So it needs to be able to > unlock but *only* via ptrace. Apps cannot be allowed to unlock themselves. > Because, well, obviously.. > > As MUSL and > others get patches, it would be much simpler to have one interface to do > this in, and right now > unlock is unused (even in the test suite :-p). > I think I raised this on the other arch's APIs originally. x86 went first, and > then later arm/riscv wanted a unified approach, but didn't solve this ptrace > unlock part. So we didn't join. AFAICT the situation hasn't changed. So I'm > worried it's too soon to unify. Or we might need to do multiple steps of > unifications. At this point, the only remaining semantic difference is support for unlocking a locked shadow stack during ptrace/CRIU restore. Arm64 and RISC-V don't currently expose a generic unlock operation because they use architecture-specific ptrace mechanisms for state restoration. If those architectures eventually converge on a common unlock model for CRIU, I think it would make sense to unify that interface as well. Until then, I don't think the lack of a generic unlock should prevent unifying the parts of the ABI that already have equivalent semantics. Especially considering how it unifies the loader/libc side of the house. > Also looking forward to understanding the security module problem > statement better. Right now all the controls are opt in, and requires support in glibc, via per arch tunable flags for both enabling and locking. The glibc folks are starting to balk at the amount of flags. Additionally, it would be nice to have MAC controls on them, and the best way for that is via LSM into SE Linux. Normal applications can be placed in a domain where they can never remove protections, and things like CRIU will have these elevated perms, if they are ever needed, since right now they go through a different channel. The LSM actually removes the need for lock flags in essence, but yeah we can't count on that. The lore is here: https://sourceware.org/pipermail/libc-alpha/2025-December/173636.html For the following LSM piece, there is no hard dependency on this. I can put the LSM hooks into arch_prctl for x86 and things would work fine, in fact there is no getting around that or the arch_prctl interface for x86 wouldn't get the LSM protections. I want x86 to get the LSM protections. I also want to coalesce what we can around the around the current generic interfaces for glibc. Work could be done there to start dropping arch tunables around this too. I am sitting on these patches right now, because they have a soft dependency on conflicts. >> Ill spin out a v2 with the comments, but the one thing left to be >> addressed, afaik, is the testing patch >> do you want that? I'll drop it, but I think that's a bad approach. > Yea, I hear your point. It is good to test more, but #including c files with > pre-processor switches seems too hacky. Is there anything we could do to make it > in one c file? Like not the templated tricks to generate two test binaries? For > example embed the switch between the two APIs in a macros in the single file. > Like say we have SHSTK_ENABLE(). Inside it does either ARCH_PRCTL() or regular. > Then have a global or something that switches between the two behaviors. Pull > out the parts in main() into something that could be run twice? > Anything is possible, but is the juice worth the squeeze here? This approach is used already in tree: - bpf/progs/arena_htab_asm.c - bpf/progs/test_cls_redirect_subprogs.c - bpf/progs/test_sk_assign_libbpf.c - kvm/lib/rbtree.c - kvm/rseq_test.c - livepatch/test_modules/test_klp_state3.c - powerpc/vphn/test-vphn.c - x86/test_shadow_stack_prctl.c I am generally a fan of doing the simplest, most obvious thing first that follows existing conventions unless a really big reason can be made to not do it. I can refactor it if it's a show stopper, but IMHO not worth it here. But if you want it refactored, sure. ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 1/2] x86/shstk: support via prctl 2026-08-04 20:43 ` Bill Roberts @ 2026-08-04 21:59 ` Edgecombe, Rick P 2026-08-05 17:16 ` Bill Roberts 0 siblings, 1 reply; 13+ messages in thread From: Edgecombe, Rick P @ 2026-08-04 21:59 UTC (permalink / raw) To: x86@kernel.org, dave.hansen@linux.intel.com, bp@alien8.de, pjw@kernel.org, hpa@zytor.com, mingo@redhat.com, aou@eecs.berkeley.edu, shuah@kernel.org, tglx@kernel.org, bill.roberts@arm.com, alex@ghiti.fr, palmer@dabbelt.com Cc: linux-riscv@lists.infradead.org, linux-kernel@vger.kernel.org, linux-kselftest@vger.kernel.org On Tue, 2026-08-04 at 15:43 -0500, Bill Roberts wrote: > > IIRC CRIU needed to unlock shadow stack during the save. Because it's tricks > > for > > saving the process involved messing with the stack. So it needs to be able > > to > > unlock but *only* via ptrace. Apps cannot be allowed to unlock themselves. > > Because, well, obviously.. > > > > As MUSL and > > others get patches, it would be much simpler to have one interface to do > > this in, and right now > > unlock is unused (even in the test suite :-p). > > I think I raised this on the other arch's APIs originally. x86 went first, > > and then later arm/riscv wanted a unified approach, but didn't solve this > > ptrace unlock part. So we didn't join. AFAICT the situation hasn't changed. > > So I'm worried it's too soon to unify. Or we might need to do multiple steps > > of unifications. > > At this point, the only remaining semantic difference is support for > unlocking a locked shadow stack during ptrace/CRIU restore. Arm64 and RISC-V > don't currently expose a generic unlock operation because they use > architecture-specific ptrace mechanisms for state restoration. If those > architectures eventually converge on a common unlock model for CRIU, I think > it would make sense to unify that interface as well. Until then, I don't think > the lack of a generic unlock should prevent unifying the parts of the ABI that > already have equivalent semantics. Especially considering how it unifies the > loader/libc side of the house. The locking needs to be done after the linked DSOs are checked for shadow stack compatibility. > > > Also looking forward to understanding the security module problem > > statement better. > > Right now all the controls are opt in, and requires support in glibc, via > per arch tunable flags for both enabling and locking. x86 glibc was originally supposed to have two modes for shadow stack. A normal mode and a permissive mode. The normal mode would first check all the ldd DSOs for shadow stack compatibility. If they all have shadow stack, it enables shadow stack and does the lock on the main thread, which then gets inherited by all the child tasks. If dlopen() is later made with a DSO that does not shadow stack, the dlopen() call is failed. In permissive mode, it did the enablement checks like the normal mode, except it did not lock shadow stack. Then if dlopen() call was made with a non supporting DSO, it would disable shadow stack on the calling thread. This didn't really work, because the other threads in the app still had shadow stack enabled. Why didn't it just disable it shadow stack for the full app? Lots of races with apps doing shadow stack specific stuff while the support gets disabled out from under them. To fix permissive mode, there was a proposal (I don't know if it ever made it into glibc) where the shadow stack would get disabled on the first dlopen() to a non-compatible shadow stack OR the first thread was spawned. This was questionable to me. But there was a desire to minimize the compatibility hit first so it could be enabled widely. Then tighten it up over time. But in any case, lock is still needed for the normal mode right? You need to decide in the loader whether you want to have shadow stack for the app. Or we are talking about another mode, like a forced-on mode where the app will do something else if it finds the linked DSOs don't support shadow stack. Like exit with an error or something. But if that's the case, it's a decent amount of new stuff to me, so please explain. > The glibc folks are > starting to balk at the amount of flags. Additionally, it would be nice to > have MAC controls on them, and the best way for that is via LSM into > SE Linux. Normal applications can be placed in a domain where > they can never remove protections, and things like CRIU will have these > elevated > perms, if they are ever needed, since right now they go through a > different channel. This sounds like a new paradigm. If we have enough shadow stack support out there, seems interesting to me. But I would like to hear more details about how it works. I'm just speculating above. > The LSM actually removes the need for lock flags in essence, but yeah we > can't count > on that. ? > The lore is here: > https://sourceware.org/pipermail/libc-alpha/2025-December/173636.html This seems to be about other shadow stack knobs. Stack size, etc. > > For the following LSM piece, there is no hard dependency on this. I can > put the LSM hooks into arch_prctl for x86 and things would work fine, in fact > there is no getting around that or the arch_prctl interface for x86 wouldn't > get the LSM protections. I want x86 to get the LSM protections. I also want to > coalesce what we can around the around the current generic interfaces for > glibc. Work could be done there to start dropping arch tunables around this > too. I am sitting on these patches right now, because they have a soft > dependency on conflicts. > > > > Ill spin out a v2 with the comments, but the one thing left to be > > > addressed, afaik, is the testing patch > > > do you want that? I'll drop it, but I think that's a bad approach. > > Yea, I hear your point. It is good to test more, but #including c files with > > pre-processor switches seems too hacky. Is there anything we could do to > > make it > > in one c file? Like not the templated tricks to generate two test binaries? > > For > > example embed the switch between the two APIs in a macros in the single > > file. > > Like say we have SHSTK_ENABLE(). Inside it does either ARCH_PRCTL() or > > regular. > > Then have a global or something that switches between the two behaviors. > > Pull > > out the parts in main() into something that could be run twice? > > > Anything is possible, but is the juice worth the squeeze here? This > approach is used > already in tree: > - bpf/progs/arena_htab_asm.c > - bpf/progs/test_cls_redirect_subprogs.c > - bpf/progs/test_sk_assign_libbpf.c > - kvm/lib/rbtree.c > - kvm/rseq_test.c > - livepatch/test_modules/test_klp_state3.c > - powerpc/vphn/test-vphn.c > - x86/test_shadow_stack_prctl.c Uhh... that is your own changes. :) > > I am generally a fan of doing the simplest, most obvious thing first > that follows existing conventions > unless a really big reason can be made to not do it. I can refactor it > if it's a show stopper, but IMHO > not worth it here. But if you want it refactored, sure. We'll we can leave it to x86 maintainers to weigh in on the style thing. I don't like it, but won't throw a fit. ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 1/2] x86/shstk: support via prctl 2026-08-04 21:59 ` Edgecombe, Rick P @ 2026-08-05 17:16 ` Bill Roberts 0 siblings, 0 replies; 13+ messages in thread From: Bill Roberts @ 2026-08-05 17:16 UTC (permalink / raw) To: Edgecombe, Rick P, x86@kernel.org, dave.hansen@linux.intel.com, bp@alien8.de, pjw@kernel.org, hpa@zytor.com, mingo@redhat.com, aou@eecs.berkeley.edu, shuah@kernel.org, tglx@kernel.org, alex@ghiti.fr, palmer@dabbelt.com Cc: linux-riscv@lists.infradead.org, linux-kernel@vger.kernel.org, linux-kselftest@vger.kernel.org On 8/4/26 4:59 PM, Edgecombe, Rick P wrote: > On Tue, 2026-08-04 at 15:43 -0500, Bill Roberts wrote: >>> IIRC CRIU needed to unlock shadow stack during the save. Because it's tricks >>> for >>> saving the process involved messing with the stack. So it needs to be able >>> to >>> unlock but *only* via ptrace. Apps cannot be allowed to unlock themselves. >>> Because, well, obviously.. >>> >>> As MUSL and >>> others get patches, it would be much simpler to have one interface to do >>> this in, and right now >>> unlock is unused (even in the test suite :-p). >>> I think I raised this on the other arch's APIs originally. x86 went first, >>> and then later arm/riscv wanted a unified approach, but didn't solve this >>> ptrace unlock part. So we didn't join. AFAICT the situation hasn't changed. >>> So I'm worried it's too soon to unify. Or we might need to do multiple steps >>> of unifications. >> At this point, the only remaining semantic difference is support for >> unlocking a locked shadow stack during ptrace/CRIU restore. Arm64 and RISC-V >> don't currently expose a generic unlock operation because they use >> architecture-specific ptrace mechanisms for state restoration. If those >> architectures eventually converge on a common unlock model for CRIU, I think >> it would make sense to unify that interface as well. Until then, I don't think >> the lack of a generic unlock should prevent unifying the parts of the ABI that >> already have equivalent semantics. Especially considering how it unifies the >> loader/libc side of the house. > The locking needs to be done after the linked DSOs are checked for shadow stack > compatibility. Correction, "Locking *may* be done after...", this is a policy based on per-arch tunables. > >>> Also looking forward to understanding the security module problem >>> statement better. >> Right now all the controls are opt in, and requires support in glibc, via >> per arch tunable flags for both enabling and locking. > x86 glibc was originally supposed to have two modes for shadow stack. A normal > mode and a permissive mode. The normal mode would first check all the ldd DSOs > for shadow stack compatibility. If they all have shadow stack, it enables shadow > stack and does the lock on the main thread, which then gets inherited by all the > child tasks. If dlopen() is later made with a DSO that does not shadow stack, > the dlopen() call is failed. > > In permissive mode, it did the enablement checks like the normal mode, except it > did not lock shadow stack. Then if dlopen() call was made with a non supporting > DSO, it would disable shadow stack on the calling thread. This didn't really > work, because the other threads in the app still had shadow stack enabled. Why > didn't it just disable it shadow stack for the full app? Lots of races with apps > doing shadow stack specific stuff while the support gets disabled out from under > them. > > To fix permissive mode, there was a proposal (I don't know if it ever made it > into glibc) where the shadow stack would get disabled on the first dlopen() to a > non-compatible shadow stack OR the first thread was spawned. This was > questionable to me. But there was a desire to minimize the compatibility hit > first so it could be enabled widely. Then tighten it up over time. > > But in any case, lock is still needed for the normal mode right? You need to > decide in the loader whether you want to have shadow stack for the app. Or we > are talking about another mode, like a forced-on mode where the app will do > something else if it finds the linked DSOs don't support shadow stack. Like exit > with an error or something. But if that's the case, it's a decent amount of new > stuff to me, so please explain. Everything you mentioned here is correct AFAIK. Besides background, I am not seeing how this is relevant here. Some of this is more a conversation about policy vs mechanism. Am I missing something you're trying to convey? A lot of this conversation is about the other things tangential to the patch which is good, I just want to make sure we don't get too off topic here. >> The glibc folks are >> starting to balk at the amount of flags. Additionally, it would be nice to >> have MAC controls on them, and the best way for that is via LSM into >> SE Linux. Normal applications can be placed in a domain where >> they can never remove protections, and things like CRIU will have these >> elevated >> perms, if they are ever needed, since right now they go through a >> different channel. > This sounds like a new paradigm. If we have enough shadow stack support out > there, seems interesting to me. But I would like to hear more details about how > it works. I'm just speculating above. No, it's not a new paradigm, the "permissions" around shadow stack are granted to domains, ie groups of processes, based on a collection of tunables. You need an elevated permission domain granted by CAP_SYS_PTRACE to unlock and then a call to disable the feature, like shadow stack. The only difference is, that we can do this with SE Linux controls. Plus we can also limit what can have capability ptrace to even touch that. In SE Linux policy, it could be something like this: neverallow { domain - criu } self:process disable_shadow_stack; allow criu self:process disable_shadow_stack; >> The LSM actually removes the need for lock flags in essence, but yeah we >> can't count >> on that. > ? In selinux, after my changes, nothing on the system will have the ability to disable shadow stack via prctl or arch_prctl *except for things explicitly granted these perms*. Because of that, it functions as an implicit call to a lock. However, that doesn't mean we don't support the locked feature via prctl/arch_prctl, we need to support non-lsm and non-selinux systems. So that begs the question, why hook it via LSMs and add support to SE Linux? LSMs - Opting out of shadow stack is a security decision, so LSMs should be able to reason about these state changes. SE Linux - Central policy, auditablity, logs, least privilege, etc, all the good benefits that it provides. Now that we have multiple arch's in tree doing this, with a generic interface, it makes sense, and good hygiene, to rectify this division. >> The lore is here: >> https://sourceware.org/pipermail/libc-alpha/2025-December/173636.html > This seems to be about other shadow stack knobs. Stack size, etc. > >> For the following LSM piece, there is no hard dependency on this. I can >> put the LSM hooks into arch_prctl for x86 and things would work fine, in fact >> there is no getting around that or the arch_prctl interface for x86 wouldn't >> get the LSM protections. I want x86 to get the LSM protections. I also want to >> coalesce what we can around the around the current generic interfaces for >> glibc. Work could be done there to start dropping arch tunables around this >> too. I am sitting on these patches right now, because they have a soft >> dependency on conflicts. >> >>>> Ill spin out a v2 with the comments, but the one thing left to be >>>> addressed, afaik, is the testing patch >>>> do you want that? I'll drop it, but I think that's a bad approach. >>> Yea, I hear your point. It is good to test more, but #including c files with >>> pre-processor switches seems too hacky. Is there anything we could do to >>> make it >>> in one c file? Like not the templated tricks to generate two test binaries? >>> For >>> example embed the switch between the two APIs in a macros in the single >>> file. >>> Like say we have SHSTK_ENABLE(). Inside it does either ARCH_PRCTL() or >>> regular. >>> Then have a global or something that switches between the two behaviors. >>> Pull >>> out the parts in main() into something that could be run twice? >>> >> Anything is possible, but is the juice worth the squeeze here? This >> approach is used >> already in tree: >> - bpf/progs/arena_htab_asm.c >> - bpf/progs/test_cls_redirect_subprogs.c >> - bpf/progs/test_sk_assign_libbpf.c >> - kvm/lib/rbtree.c >> - kvm/rseq_test.c >> - livepatch/test_modules/test_klp_state3.c >> - powerpc/vphn/test-vphn.c >> - x86/test_shadow_stack_prctl.c > Uhh... that is your own changes. :) I literally went back and forth including my change... I just included it as a, "See I am joining a long list". >> I am generally a fan of doing the simplest, most obvious thing first >> that follows existing conventions >> unless a really big reason can be made to not do it. I can refactor it >> if it's a show stopper, but IMHO >> not worth it here. But if you want it refactored, sure. > We'll we can leave it to x86 maintainers to weigh in on the style thing. I don't > like it, but won't throw a fit. Could you nudge one of em? But lastly, I just want to get back to your non-structural/style concerns around this patch series, which to paraphrase and summarize poorly are: What about UNLOCK and how does that fit in with the future and whats the risk of not being able to rectify that gap? To answer that, unlock can be easily rectified by mirroring the arch_prctl interface into prctl when/if needed. Considering that this split between APIs using arch_prctl and prctl was initially discussed when adding the generic prctl interface, and the arch_prctl interface was very easy to map onto prctl (in this PR), I don't see any reason why unlock would be a problem if we need it. In full disclosure, unlock will remain a blind spot to LSMs, and things with ptrace capability, will be able to unlock feature bits. But this is no different then the current state now (and it's idempotent with an LSM involved), and we gain the ability to see/control what domains in the system need to actually twiddle the shadow stack bits off or make it write able. But back to this patch series, it merely accomplishes a unified prctl interface for shadow stack locking, status getting and enabling. From there, libc's and other consumers can start to unify around generic interfaces, which will help promote things like generic tunables in the case of glibc while preserving all backwards compatible interfaces. If I don't hear back with concerns that would block this, ill spin a V2 later this week if that works for you? ^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH 2/2] selftests/x86: add generic prctl shadow stack test 2026-07-14 15:47 [PATCH 0/2] x86: Support shstk via prctl Bill Roberts 2026-07-14 15:47 ` [PATCH 1/2] x86/shstk: support " Bill Roberts @ 2026-07-14 15:47 ` Bill Roberts 2026-07-29 13:31 ` Edgecombe, Rick P 1 sibling, 1 reply; 13+ messages in thread From: Bill Roberts @ 2026-07-14 15:47 UTC (permalink / raw) To: H. Peter Anvin, Albert Ou, Alexandre Ghiti, Borislav Petkov, Dave Hansen, Ingo Molnar, Palmer Dabbelt, Paul Walmsley, Shuah Khan, Thomas Gleixner, x86 Cc: linux-kernel, linux-kselftest, linux-riscv, Bill Roberts Run the same test suite for arch_prctl, against prctl, to ensure consisteny and correctness between the interfaces. Signed-off-by: Bill Roberts <bill.roberts@arm.com> --- tools/testing/selftests/x86/Makefile | 3 +- .../testing/selftests/x86/test_shadow_stack.c | 55 +++++++++++++++---- .../selftests/x86/test_shadow_stack_prctl.c | 3 + 3 files changed, 50 insertions(+), 11 deletions(-) create mode 100644 tools/testing/selftests/x86/test_shadow_stack_prctl.c diff --git a/tools/testing/selftests/x86/Makefile b/tools/testing/selftests/x86/Makefile index 434065215d12..6a505b42ff66 100644 --- a/tools/testing/selftests/x86/Makefile +++ b/tools/testing/selftests/x86/Makefile @@ -19,7 +19,8 @@ TARGETS_C_32BIT_ONLY := entry_from_vm86 test_syscall_vdso unwind_vdso \ test_FCMOV test_FCOMI test_FISTTP \ vdso_restorer TARGETS_C_64BIT_ONLY := fsgsbase sysret_rip syscall_numbering \ - corrupt_xstate_header amx lam test_shadow_stack avx apx + corrupt_xstate_header amx lam test_shadow_stack avx apx \ + test_shadow_stack_prctl # Some selftests require 32bit support enabled also on 64bit systems TARGETS_C_32BIT_NEEDED := ldt_gdt ptrace_syscall diff --git a/tools/testing/selftests/x86/test_shadow_stack.c b/tools/testing/selftests/x86/test_shadow_stack.c index 3d6ca33edba4..0d14a7f444aa 100644 --- a/tools/testing/selftests/x86/test_shadow_stack.c +++ b/tools/testing/selftests/x86/test_shadow_stack.c @@ -92,6 +92,7 @@ static inline unsigned long __attribute__((always_inline)) get_ssp(void) * Based on code from nolibc.h. Keep a copy here because this can't pull in all * of nolibc.h. */ + #ifndef BUILD_PRCTL #define ARCH_PRCTL(arg1, arg2) \ ({ \ long _ret; \ @@ -109,6 +110,40 @@ static inline unsigned long __attribute__((always_inline)) get_ssp(void) _ret; \ }) +#define SHADOW_STACK_DISABLE() ARCH_PRCTL(ARCH_SHSTK_DISABLE, ARCH_SHSTK_SHSTK) +#define SHADOW_STACK_ENABLE() ARCH_PRCTL(ARCH_SHSTK_ENABLE, ARCH_SHSTK_SHSTK) +#define SHADOW_STACK_ENABLE_WRITE() ARCH_PRCTL(ARCH_SHSTK_ENABLE, ARCH_SHSTK_WRSS) + +#else + +#define PRCTL(option, arg2, arg3, arg4, arg5) \ +({ \ + long _ret; \ + register long _num asm("rax") = __NR_prctl; \ + register long _arg1 asm("rdi") = (long)(option); \ + register long _arg2 asm("rsi") = (long)(arg2); \ + register long _arg3 asm("rdx") = (long)(arg3); \ + register long _arg4 asm("r10") = (long)(arg4); \ + register long _arg5 asm("r8") = (long)(arg5); \ + \ + asm volatile ( \ + "syscall" \ + : "=a"(_ret) \ + : "0"(_num), \ + "r"(_arg1), "r"(_arg2), "r"(_arg3), \ + "r"(_arg4), "r"(_arg5) \ + : "rcx", "r11", "memory", "cc" \ + ); \ + _ret; \ +}) + +#define SHADOW_STACK_DISABLE() PRCTL(PR_SET_SHADOW_STACK_STATUS, 0, 0, 0, 0) +#define SHADOW_STACK_ENABLE() PRCTL(PR_SET_SHADOW_STACK_STATUS, PR_SHADOW_STACK_ENABLE, 0, 0, 0) +#define SHADOW_STACK_ENABLE_WRITE() \ + PRCTL(PR_SET_SHADOW_STACK_STATUS, PR_SHADOW_STACK_ENABLE|PR_SHADOW_STACK_WRITE, 0, 0, 0) + +#endif + void *create_shstk(void *addr) { return (void *)syscall(__NR_map_shadow_stack, addr, SS_SIZE, SHADOW_STACK_SET_TOKEN); @@ -691,7 +726,7 @@ void segv_gp_handler(int signum, siginfo_t *si, void *uc) * To work with old glibc, this can't rely on siglongjmp working with * shadow stack enabled, so disable shadow stack before siglongjmp(). */ - ARCH_PRCTL(ARCH_SHSTK_DISABLE, ARCH_SHSTK_SHSTK); + SHADOW_STACK_DISABLE(); siglongjmp(jmp_buffer, -1); } @@ -854,7 +889,7 @@ static int test_uretprobe(void) if (sigsetjmp(jmp_buffer, 1)) goto out; - ARCH_PRCTL(ARCH_SHSTK_ENABLE, ARCH_SHSTK_SHSTK); + SHADOW_STACK_ENABLE(); /* * This either segfaults and goes through sigsetjmp above @@ -866,7 +901,7 @@ static int test_uretprobe(void) err = 0; out: - ARCH_PRCTL(ARCH_SHSTK_DISABLE, ARCH_SHSTK_SHSTK); + SHADOW_STACK_DISABLE(); signal(SIGSEGV, SIG_DFL); if (fd) close(fd); @@ -933,7 +968,7 @@ static int test_uprobe_call(void) if (sigsetjmp(jmp_buffer, 1)) goto out; - if (ARCH_PRCTL(ARCH_SHSTK_ENABLE, ARCH_SHSTK_SHSTK)) + if (SHADOW_STACK_ENABLE()) goto out; /* @@ -946,7 +981,7 @@ static int test_uprobe_call(void) err = 0; out: - ARCH_PRCTL(ARCH_SHSTK_DISABLE, ARCH_SHSTK_SHSTK); + SHADOW_STACK_DISABLE(); signal(SIGSEGV, SIG_DFL); if (fd >= 0) close(fd); @@ -1059,22 +1094,22 @@ int main(int argc, char *argv[]) { int ret = 0; - if (ARCH_PRCTL(ARCH_SHSTK_ENABLE, ARCH_SHSTK_SHSTK)) { + if (SHADOW_STACK_ENABLE()) { printf("[SKIP]\tCould not enable Shadow stack\n"); return 1; } - if (ARCH_PRCTL(ARCH_SHSTK_DISABLE, ARCH_SHSTK_SHSTK)) { + if (SHADOW_STACK_DISABLE()) { ret = 1; printf("[FAIL]\tDisabling shadow stack failed\n"); } - if (ARCH_PRCTL(ARCH_SHSTK_ENABLE, ARCH_SHSTK_SHSTK)) { + if (SHADOW_STACK_ENABLE()) { printf("[SKIP]\tCould not re-enable Shadow stack\n"); return 1; } - if (ARCH_PRCTL(ARCH_SHSTK_ENABLE, ARCH_SHSTK_WRSS)) { + if (SHADOW_STACK_ENABLE_WRITE()) { printf("[SKIP]\tCould not enable WRSS\n"); ret = 1; goto out; @@ -1164,7 +1199,7 @@ int main(int argc, char *argv[]) * Disable shadow stack before the function returns, or there will be a * shadow stack violation. */ - if (ARCH_PRCTL(ARCH_SHSTK_DISABLE, ARCH_SHSTK_SHSTK)) { + if (SHADOW_STACK_DISABLE()) { ret = 1; printf("[FAIL]\tDisabling shadow stack failed\n"); } diff --git a/tools/testing/selftests/x86/test_shadow_stack_prctl.c b/tools/testing/selftests/x86/test_shadow_stack_prctl.c new file mode 100644 index 000000000000..9c9e2728a9f9 --- /dev/null +++ b/tools/testing/selftests/x86/test_shadow_stack_prctl.c @@ -0,0 +1,3 @@ +// SPDX-License-Identifier: GPL-2.0 +#define BUILD_PRCTL 1 +#include "test_shadow_stack.c" -- 2.54.0 ^ permalink raw reply related [flat|nested] 13+ messages in thread
* Re: [PATCH 2/2] selftests/x86: add generic prctl shadow stack test 2026-07-14 15:47 ` [PATCH 2/2] selftests/x86: add generic prctl shadow stack test Bill Roberts @ 2026-07-29 13:31 ` Edgecombe, Rick P 2026-08-03 17:50 ` Bill Roberts 0 siblings, 1 reply; 13+ messages in thread From: Edgecombe, Rick P @ 2026-07-29 13:31 UTC (permalink / raw) To: x86@kernel.org, bp@alien8.de, dave.hansen@linux.intel.com, pjw@kernel.org, hpa@zytor.com, aou@eecs.berkeley.edu, mingo@redhat.com, alex@ghiti.fr, palmer@dabbelt.com, bill.roberts@arm.com, shuah@kernel.org, tglx@kernel.org Cc: linux-riscv@lists.infradead.org, linux-kernel@vger.kernel.org, linux-kselftest@vger.kernel.org On Tue, 2026-07-14 at 10:47 -0500, Bill Roberts wrote: > diff --git a/tools/testing/selftests/x86/test_shadow_stack_prctl.c > b/tools/testing/selftests/x86/test_shadow_stack_prctl.c > new file mode 100644 > index 000000000000..9c9e2728a9f9 > --- /dev/null > +++ b/tools/testing/selftests/x86/test_shadow_stack_prctl.c > @@ -0,0 +1,3 @@ > +// SPDX-License-Identifier: GPL-2.0 > +#define BUILD_PRCTL 1 > +#include "test_shadow_stack.c" > -- Hmm, do we really need a full re-test for the different prctl routing? ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 2/2] selftests/x86: add generic prctl shadow stack test 2026-07-29 13:31 ` Edgecombe, Rick P @ 2026-08-03 17:50 ` Bill Roberts 0 siblings, 0 replies; 13+ messages in thread From: Bill Roberts @ 2026-08-03 17:50 UTC (permalink / raw) To: Edgecombe, Rick P, x86@kernel.org, bp@alien8.de, dave.hansen@linux.intel.com, pjw@kernel.org, hpa@zytor.com, aou@eecs.berkeley.edu, mingo@redhat.com, alex@ghiti.fr, palmer@dabbelt.com, shuah@kernel.org, tglx@kernel.org Cc: linux-riscv@lists.infradead.org, linux-kernel@vger.kernel.org, linux-kselftest@vger.kernel.org On 7/29/26 8:31 AM, Edgecombe, Rick P wrote: > On Tue, 2026-07-14 at 10:47 -0500, Bill Roberts wrote: >> diff --git a/tools/testing/selftests/x86/test_shadow_stack_prctl.c >> b/tools/testing/selftests/x86/test_shadow_stack_prctl.c >> new file mode 100644 >> index 000000000000..9c9e2728a9f9 >> --- /dev/null >> +++ b/tools/testing/selftests/x86/test_shadow_stack_prctl.c >> @@ -0,0 +1,3 @@ >> +// SPDX-License-Identifier: GPL-2.0 >> +#define BUILD_PRCTL 1 >> +#include "test_shadow_stack.c" >> -- > Hmm, do we really need a full re-test for the different prctl routing? Bear with me, I am quite perplexed, usually tests are meant with fanfare. Yes we want this! It ensures all regressions are caught and features are working as intended through both interfaces. This means, nothing broke for x86 in this change. Tests are cheap, I have no idea why we wouldn't want this. Now, what I did want to propose in the future, is moving a generic test up out of arch specific tests that would run on all systems. This will require me to look at all 3 arches and build a test suite. However, I wanted to ensure that nothing broke for x86, this ensures that. I was going to roll those patches after the LSM changes go up. As an aside and hearkening back to your comment on UNLOCK in patch 1, the test never tests UNLOCK. ^ permalink raw reply [flat|nested] 13+ messages in thread
end of thread, other threads:[~2026-08-05 17:17 UTC | newest] Thread overview: 13+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2026-07-14 15:47 [PATCH 0/2] x86: Support shstk via prctl Bill Roberts 2026-07-14 15:47 ` [PATCH 1/2] x86/shstk: support " Bill Roberts 2026-07-29 13:29 ` Edgecombe, Rick P 2026-08-03 17:41 ` Bill Roberts 2026-08-03 18:14 ` Edgecombe, Rick P 2026-08-04 18:23 ` Bill Roberts 2026-08-04 18:49 ` Edgecombe, Rick P 2026-08-04 20:43 ` Bill Roberts 2026-08-04 21:59 ` Edgecombe, Rick P 2026-08-05 17:16 ` Bill Roberts 2026-07-14 15:47 ` [PATCH 2/2] selftests/x86: add generic prctl shadow stack test Bill Roberts 2026-07-29 13:31 ` Edgecombe, Rick P 2026-08-03 17:50 ` Bill Roberts
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox