[PATCH 2/2] x86_64: Use __seg_fs qualifiers in NPTL accessors
Uros Bizjak
ubizjak@gmail.com
Wed Aug 20 12:01:30 GMT 2025
On Wed, Aug 20, 2025 at 8:02 AM Uros Bizjak <ubizjak@gmail.com> wrote:
>
> On Wed, Aug 20, 2025 at 5:19 AM H.J. Lu <hjl.tools@gmail.com> wrote:
> >
> > On Tue, Aug 19, 2025 at 8:06 PM H.J. Lu <hjl.tools@gmail.com> wrote:
> > >
> > > On Sun, Aug 17, 2025 at 8:50 AM Uros Bizjak <ubizjak@gmail.com> wrote:
> > > >
> > > > Use __seg_fs named address space qualifiers to cast NPTL accessors
> > > > to %fs: prefixed addresses. Use volatile access only where
> > > > strictly necessary.
> > > >
> > > > Signed-off-by: Uros Bizjak <ubizjak@gmail.com>
> > > > Cc: H.J.Lu <hjl.tools@gmail.com>
> > > > Cc: Florian Weimer <fweimer@redhat.com>
> > > > Cc: Carlos O'Donell <carlos@redhat.com>
> > > > ---
> > > > sysdeps/x86_64/nptl/rseq-access.h | 82 ++++++++-----------
> > > > sysdeps/x86_64/nptl/tcb-access.h | 127 ++++++++----------------------
> > > > 2 files changed, 66 insertions(+), 143 deletions(-)
> > > >
> > > > diff --git a/sysdeps/x86_64/nptl/rseq-access.h b/sysdeps/x86_64/nptl/rseq-access.h
> > > > index bc966b2972..214cb96797 100644
> > > > --- a/sysdeps/x86_64/nptl/rseq-access.h
> > > > +++ b/sysdeps/x86_64/nptl/rseq-access.h
> > > > @@ -16,34 +16,38 @@
> > > > License along with the GNU C Library; if not, see
> > > > <https://www.gnu.org/licenses/>. */
> > > >
> > > > +/* Read member of the RSEQ area directly. */
> > > > +#define RSEQ_GETMEM(member) \
> > > > + ({ \
> > > > + _Static_assert (sizeof (RSEQ_SELF()->member) == 1 \
> > > > + || sizeof (RSEQ_SELF()->member) == 4 \
> > > > + || sizeof (RSEQ_SELF()->member) == 8, \
> > > > + "size of rseq data"); \
> > > > + (*(__typeof (RSEQ_SELF()->member) __seg_fs *) \
> > > > + (__rseq_offset + offsetof (struct rseq_area, member))); \
> >
> > info: __rseq_offset: -192
> >
> > %fs + negative offset doesn't work for x32.
>
> That is unfortunate, and also means that named address space handling
> is fundamentally broken in GCC for x32:
>
> --cut here--
> extern const long __rseq_offset;
>
> struct rseq_area
> {
> int a;
> int b;
> int c;
> };
>
> int read_rseq (void)
> {
> int val = (*(volatile int __seg_fs *)
> (__rseq_offset + __builtin_offsetof (struct rseq_area, c)));
> return val;
> }
> --cut here--
>
> gcc -O2 -mx32:
>
> read_rseq:
> movl __rseq_offset(%rip), %eax
> movl %fs:8(%eax), %eax
> ret
Hm, the original approach does this:
asm volatile ("movl %%fs:%P1(%q2),%0"
: "=r" (__value)
: "i" (offsetof (struct rseq_area, member)),
"r" ((long long int) __rseq_offset));
Won't this also segfault with negative __rseq_offset?
Uros.
More information about the Libc-alpha
mailing list