aboutsummaryrefslogtreecommitdiff
path: root/sysdeps
diff options
context:
space:
mode:
authorJakub Jelinek <jakub@redhat.com>2020-12-03 13:33:44 +0100
committerFlorian Weimer <fweimer@redhat.com>2020-12-03 13:48:55 +0100
commit1d9cbb96082e646de7515a1667efa041ffb79958 (patch)
treeb52e641f97c37dfed401538a038a4ae058ea87ce /sysdeps
parent7c331116971d38e57703af4097ed13ab6bef91d0 (diff)
downloadglibc-1d9cbb96082e646de7515a1667efa041ffb79958.tar
glibc-1d9cbb96082e646de7515a1667efa041ffb79958.tar.gz
glibc-1d9cbb96082e646de7515a1667efa041ffb79958.tar.bz2
glibc-1d9cbb96082e646de7515a1667efa041ffb79958.zip
x86: Fix THREAD_SELF definition to avoid ld.so crash (bug 27004)
The previous definition of THREAD_SELF did not tell the compiler that %fs (or %gs) usage is invalid for the !DL_LOOKUP_GSCOPE_LOCK case in _dl_lookup_symbol_x. As a result, ld.so could try to use the TCB before it was initialized. As the comment in tls.h explains, asm volatile is undesirable here. Using the __seg_fs (or __seg_gs) namespace does not interfere with optimization, and expresses that THREAD_SELF is potentially trapping.
Diffstat (limited to 'sysdeps')
-rw-r--r--sysdeps/i386/nptl/tls.h7
-rw-r--r--sysdeps/x86_64/nptl/tls.h7
2 files changed, 12 insertions, 2 deletions
diff --git a/sysdeps/i386/nptl/tls.h b/sysdeps/i386/nptl/tls.h
index b74347bacd..ab98c24a02 100644
--- a/sysdeps/i386/nptl/tls.h
+++ b/sysdeps/i386/nptl/tls.h
@@ -234,11 +234,16 @@ tls_fill_user_desc (union user_desc_init *desc,
assignments like
pthread_descr self = thread_self();
do not get optimized away. */
-# define THREAD_SELF \
+# if __GNUC_PREREQ (6, 0)
+# define THREAD_SELF \
+ (*(struct pthread *__seg_gs *) offsetof (struct pthread, header.self))
+# else
+# define THREAD_SELF \
({ struct pthread *__self; \
asm ("movl %%gs:%c1,%0" : "=r" (__self) \
: "i" (offsetof (struct pthread, header.self))); \
__self;})
+# endif
/* Magic for libthread_db to know how to do THREAD_SELF. */
# define DB_THREAD_SELF \
diff --git a/sysdeps/x86_64/nptl/tls.h b/sysdeps/x86_64/nptl/tls.h
index a08bf972de..ccb5f24d92 100644
--- a/sysdeps/x86_64/nptl/tls.h
+++ b/sysdeps/x86_64/nptl/tls.h
@@ -180,11 +180,16 @@ _Static_assert (offsetof (tcbhead_t, __glibc_unused2) == 0x80,
assignments like
pthread_descr self = thread_self();
do not get optimized away. */
-# define THREAD_SELF \
+# if __GNUC_PREREQ (6, 0)
+# define THREAD_SELF \
+ (*(struct pthread *__seg_fs *) offsetof (struct pthread, header.self))
+# else
+# define THREAD_SELF \
({ struct pthread *__self; \
asm ("mov %%fs:%c1,%0" : "=r" (__self) \
: "i" (offsetof (struct pthread, header.self))); \
__self;})
+# endif
/* Magic for libthread_db to know how to do THREAD_SELF. */
# define DB_THREAD_SELF_INCLUDE <sys/reg.h> /* For the FS constant. */