Page MenuHomeFreeBSD

D33353.id.diff
No OneTemporary

D33353.id.diff

diff --git a/lib/libc/gen/tls.c b/lib/libc/gen/tls.c
--- a/lib/libc/gen/tls.c
+++ b/lib/libc/gen/tls.c
@@ -72,18 +72,6 @@
void *__libc_allocate_tls(void *oldtls, size_t tcbsize, size_t tcbalign);
void __libc_free_tls(void *tls, size_t tcbsize, size_t tcbalign);
-#if defined(__amd64__) || defined(__aarch64__) || defined(__riscv)
-#define TLS_TCB_ALIGN 16
-#elif defined(__arm__) || defined(__mips__)
-#define TLS_TCB_ALIGN 8
-#elif defined(__powerpc__)
-#define TLS_TCB_ALIGN TLS_TCB_SIZE
-#elif defined(__i386__)
-#define TLS_TCB_ALIGN 4
-#else
-#error TLS_TCB_ALIGN undefined for target architecture
-#endif
-
#ifndef PIC
static size_t libc_tls_static_space;
@@ -95,11 +83,10 @@
void *
__libc_tls_get_addr(void *vti)
{
- Elf_Addr **dtvp, *dtv;
+ uintptr_t *dtv;
tls_index *ti;
- dtvp = _get_tp();
- dtv = *dtvp;
+ dtv = _tcb_get()->tcb_dtv;
ti = vti;
return ((char *)(dtv[ti->ti_module + 1] + ti->ti_offset) +
TLS_DTV_OFFSET);
@@ -165,7 +152,7 @@
* described in [3] where TP points (with bias) to TLS and TCB immediately
* precedes TLS without any alignment gap[4]. Only TLS should be aligned.
* The TCB[0] points to DTV vector and DTV values are biased by constant
- * value (0x8000) from real addresses[5].
+ * value (TLS_DTV_OFFSET) from real addresses[5].
*
* [1] Ulrich Drepper: ELF Handling for Thread-Local Storage
* www.akkadia.org/drepper/tls.pdf
@@ -178,7 +165,7 @@
* https://members.openpowerfoundation.org/document/dl/576
*
* [4] Its unclear if "without any alignment gap" is hard ABI requirement,
- * but we must follow this rule due to suboptimal _set_tp()
+ * but we must follow this rule due to suboptimal _tcb_set()
* (aka <ARCH>_SET_TP) implementation. This function doesn't expect TP but
* TCB as argument.
*
@@ -310,8 +297,6 @@
#ifdef TLS_VARIANT_II
-#define TLS_TCB_SIZE (3 * sizeof(Elf_Addr))
-
/*
* Free Static TLS using the Variant II method.
*/
@@ -465,6 +450,6 @@
}
tls = _rtld_allocate_tls(NULL, TLS_TCB_SIZE, TLS_TCB_ALIGN);
- _set_tp(tls);
+ _tcb_set(tls);
#endif
}
diff --git a/libexec/rtld-elf/aarch64/reloc.c b/libexec/rtld-elf/aarch64/reloc.c
--- a/libexec/rtld-elf/aarch64/reloc.c
+++ b/libexec/rtld-elf/aarch64/reloc.c
@@ -516,7 +516,6 @@
void
allocate_initial_tls(Obj_Entry *objs)
{
- Elf_Addr **tp;
/*
* Fix the size of the static TLS block by using the maximum
@@ -526,16 +525,14 @@
tls_static_space = tls_last_offset + tls_last_size +
RTLD_STATIC_TLS_EXTRA;
- tp = (Elf_Addr **) allocate_tls(objs, NULL, TLS_TCB_SIZE, 16);
-
- asm volatile("msr tpidr_el0, %0" : : "r"(tp));
+ _tcb_set(allocate_tls(objs, NULL, TLS_TCB_SIZE, TLS_TCB_ALIGN));
}
void *
__tls_get_addr(tls_index* ti)
{
- Elf_Addr **dtvp;
+ uintptr_t **dtvp;
- dtvp = _get_tp();
+ dtvp = &_tcb_get()->tcb_dtv;
return (tls_get_addr_common(dtvp, ti->ti_module, ti->ti_offset));
}
diff --git a/libexec/rtld-elf/aarch64/rtld_machdep.h b/libexec/rtld-elf/aarch64/rtld_machdep.h
--- a/libexec/rtld-elf/aarch64/rtld_machdep.h
+++ b/libexec/rtld-elf/aarch64/rtld_machdep.h
@@ -35,6 +35,7 @@
#include <sys/types.h>
#include <machine/atomic.h>
+#include <machine/tls.h>
struct Struct_Obj_Entry;
@@ -79,7 +80,6 @@
#define calculate_tls_post_size(align) \
round(TLS_TCB_SIZE, align) - TLS_TCB_SIZE
-#define TLS_TCB_SIZE 16
typedef struct {
unsigned long ti_module;
unsigned long ti_offset;
@@ -92,7 +92,4 @@
#define md_abi_variant_hook(x)
-#define TLS_VARIANT_I 1
-#define TLS_DTV_OFFSET 0
-
#endif
diff --git a/libexec/rtld-elf/amd64/reloc.c b/libexec/rtld-elf/amd64/reloc.c
--- a/libexec/rtld-elf/amd64/reloc.c
+++ b/libexec/rtld-elf/amd64/reloc.c
@@ -530,7 +530,12 @@
*/
tls_static_space = tls_last_offset + RTLD_STATIC_TLS_EXTRA;
- addr = allocate_tls(objs, 0, 3 * sizeof(Elf_Addr), 16);
+ addr = allocate_tls(objs, 0, TLS_TCB_SIZE, TLS_TCB_ALIGN);
+
+ /*
+ * This does not use _tcb_set() as it calls amd64_set_fsbase()
+ * which is an ifunc and rtld must not use ifuncs.
+ */
if (__getosreldate() >= P_OSREL_WRFSBASE &&
(cpu_stdext_feature & CPUID_STDEXT_FSGSBASE) != 0)
wrfsbase((uintptr_t)addr);
@@ -541,9 +546,9 @@
void *
__tls_get_addr(tls_index *ti)
{
- Elf_Addr **dtvp;
+ uintptr_t **dtvp;
- dtvp = _get_tp();
+ dtvp = &_tcb_get()->tcb_dtv;
return (tls_get_addr_common(dtvp, ti->ti_module, ti->ti_offset));
}
diff --git a/libexec/rtld-elf/amd64/rtld_machdep.h b/libexec/rtld-elf/amd64/rtld_machdep.h
--- a/libexec/rtld-elf/amd64/rtld_machdep.h
+++ b/libexec/rtld-elf/amd64/rtld_machdep.h
@@ -33,6 +33,7 @@
#include <sys/types.h>
#include <machine/atomic.h>
+#include <machine/tls.h>
struct Struct_Obj_Entry;
@@ -73,9 +74,6 @@
#define md_abi_variant_hook(x)
-#define TLS_VARIANT_II 1
-#define TLS_DTV_OFFSET 0
-
size_t calculate_first_tls_offset(size_t size, size_t align, size_t offset);
size_t calculate_tls_offset(size_t prev_offset, size_t prev_size, size_t size,
size_t align, size_t offset);
diff --git a/libexec/rtld-elf/arm/reloc.c b/libexec/rtld-elf/arm/reloc.c
--- a/libexec/rtld-elf/arm/reloc.c
+++ b/libexec/rtld-elf/arm/reloc.c
@@ -499,17 +499,14 @@
tls_static_space = tls_last_offset + tls_last_size + RTLD_STATIC_TLS_EXTRA;
- sysarch(ARM_SET_TP, allocate_tls(objs, NULL, TLS_TCB_SIZE, 8));
+ _tcb_set(allocate_tls(objs, NULL, TLS_TCB_SIZE, TLS_TCB_ALIGN));
}
void *
__tls_get_addr(tls_index* ti)
{
- char *p;
- void *_tp;
- __asm __volatile("mrc p15, 0, %0, c13, c0, 3" \
- : "=r" (_tp));
- p = tls_get_addr_common((Elf_Addr **)(_tp), ti->ti_module, ti->ti_offset);
+ uintptr_t **dtvp;
- return (p);
+ dtvp = &_tcb_get()->tcb_dtv;
+ return (tls_get_addr_common(dtvp, ti->ti_module, ti->ti_offset));
}
diff --git a/libexec/rtld-elf/arm/rtld_machdep.h b/libexec/rtld-elf/arm/rtld_machdep.h
--- a/libexec/rtld-elf/arm/rtld_machdep.h
+++ b/libexec/rtld-elf/arm/rtld_machdep.h
@@ -34,6 +34,7 @@
#include <sys/types.h>
#include <machine/atomic.h>
#include <machine/acle-compat.h>
+#include <machine/tls.h>
struct Struct_Obj_Entry;
@@ -56,7 +57,6 @@
#define call_ifunc_resolver(ptr) \
(((Elf_Addr (*)(void))ptr)())
-#define TLS_TCB_SIZE 8
typedef struct {
unsigned long ti_module;
unsigned long ti_offset;
@@ -84,7 +84,4 @@
#define md_abi_variant_hook(x)
#endif
-#define TLS_VARIANT_I 1
-#define TLS_DTV_OFFSET 0
-
#endif
diff --git a/libexec/rtld-elf/i386/reloc.c b/libexec/rtld-elf/i386/reloc.c
--- a/libexec/rtld-elf/i386/reloc.c
+++ b/libexec/rtld-elf/i386/reloc.c
@@ -513,8 +513,8 @@
* use.
*/
tls_static_space = tls_last_offset + RTLD_STATIC_TLS_EXTRA;
- tls = allocate_tls(objs, NULL, 3*sizeof(Elf_Addr), sizeof(Elf_Addr));
- i386_set_gsbase(tls);
+ tls = allocate_tls(objs, NULL, TLS_TCB_SIZE, TLS_TCB_ALIGN);
+ _tcb_set(tls);
}
/* GNU ABI */
@@ -522,9 +522,9 @@
void *
___tls_get_addr(tls_index *ti)
{
- Elf_Addr **dtvp;
+ uintptr_t **dtvp;
- dtvp = _get_tp();
+ dtvp = &_tcb_get()->tcb_dtv;
return (tls_get_addr_common(dtvp, ti->ti_module, ti->ti_offset));
}
@@ -532,9 +532,9 @@
void *
__tls_get_addr(tls_index *ti)
{
- Elf_Addr **dtvp;
+ uintptr_t **dtvp;
- dtvp = _get_tp();
+ dtvp = &_tcb_get()->tcb_dtv;
return (tls_get_addr_common(dtvp, ti->ti_module, ti->ti_offset));
}
diff --git a/libexec/rtld-elf/i386/rtld_machdep.h b/libexec/rtld-elf/i386/rtld_machdep.h
--- a/libexec/rtld-elf/i386/rtld_machdep.h
+++ b/libexec/rtld-elf/i386/rtld_machdep.h
@@ -33,6 +33,7 @@
#include <sys/types.h>
#include <machine/atomic.h>
+#include <machine/tls.h>
struct Struct_Obj_Entry;
@@ -74,9 +75,6 @@
#define md_abi_variant_hook(x)
-#define TLS_VARIANT_II 1
-#define TLS_DTV_OFFSET 0
-
size_t calculate_first_tls_offset(size_t size, size_t align, size_t offset);
size_t calculate_tls_offset(size_t prev_offset, size_t prev_size, size_t size,
size_t align, size_t offset);
diff --git a/libexec/rtld-elf/mips/reloc.c b/libexec/rtld-elf/mips/reloc.c
--- a/libexec/rtld-elf/mips/reloc.c
+++ b/libexec/rtld-elf/mips/reloc.c
@@ -762,7 +762,6 @@
void
allocate_initial_tls(Obj_Entry *objs)
{
- char *tls;
/*
* Fix the size of the static TLS block by using the maximum
@@ -771,19 +770,17 @@
*/
tls_static_space = tls_last_offset + tls_last_size + RTLD_STATIC_TLS_EXTRA;
- tls = (char *) allocate_tls(objs, NULL, TLS_TCB_SIZE, 8);
-
- sysarch(MIPS_SET_TLS, tls);
+ _tcb_set(allocate_tls(objs, NULL, TLS_TCB_SIZE, TLS_TCB_ALIGN));
}
void *
__tls_get_addr(tls_index* ti)
{
- Elf_Addr **tls;
+ uintptr_t **dtvp;
char *p;
- tls = _get_tp();
- p = tls_get_addr_common(tls, ti->ti_module, ti->ti_offset);
+ dtvp = &_tcb_get()->tcb_dtv;
+ p = tls_get_addr_common(dtvp, ti->ti_module, ti->ti_offset);
return (p + TLS_DTV_OFFSET);
}
diff --git a/libexec/rtld-elf/mips/rtld_machdep.h b/libexec/rtld-elf/mips/rtld_machdep.h
--- a/libexec/rtld-elf/mips/rtld_machdep.h
+++ b/libexec/rtld-elf/mips/rtld_machdep.h
@@ -77,6 +77,4 @@
#define md_abi_variant_hook(x)
-#define TLS_VARIANT_I 1
-
#endif
diff --git a/libexec/rtld-elf/powerpc/reloc.c b/libexec/rtld-elf/powerpc/reloc.c
--- a/libexec/rtld-elf/powerpc/reloc.c
+++ b/libexec/rtld-elf/powerpc/reloc.c
@@ -812,7 +812,6 @@
void
allocate_initial_tls(Obj_Entry *list)
{
- Elf_Addr **tp;
/*
* Fix the size of the static TLS block by using the maximum
@@ -822,25 +821,17 @@
tls_static_space = tls_last_offset + tls_last_size + RTLD_STATIC_TLS_EXTRA;
- tp = (Elf_Addr **)((char *) allocate_tls(list, NULL, TLS_TCB_SIZE, 8)
- + TLS_TP_OFFSET + TLS_TCB_SIZE);
-
- /*
- * XXX gcc seems to ignore 'tp = _tp;'
- */
-
- __asm __volatile("mr 2,%0" :: "r"(tp));
+ _tcb_set(allocate_tls(list, NULL, TLS_TCB_SIZE, TLS_TCB_ALIGN));
}
void*
__tls_get_addr(tls_index* ti)
{
- register Elf_Addr **tp;
+ uintptr_t **dtvp;
char *p;
- __asm __volatile("mr %0,2" : "=r"(tp));
- p = tls_get_addr_common((Elf_Addr**)((Elf_Addr)tp - TLS_TP_OFFSET
- - TLS_TCB_SIZE), ti->ti_module, ti->ti_offset);
+ dtvp = &_tcb_get()->tcb_dtv;
+ p = tls_get_addr_common(dtvp, ti->ti_module, ti->ti_offset);
return (p + TLS_DTV_OFFSET);
}
diff --git a/libexec/rtld-elf/powerpc/rtld_machdep.h b/libexec/rtld-elf/powerpc/rtld_machdep.h
--- a/libexec/rtld-elf/powerpc/rtld_machdep.h
+++ b/libexec/rtld-elf/powerpc/rtld_machdep.h
@@ -33,6 +33,7 @@
#include <sys/types.h>
#include <machine/atomic.h>
+#include <machine/tls.h>
struct Struct_Obj_Entry;
@@ -73,11 +74,6 @@
* TLS
*/
-#define TLS_VARIANT_I 1
-#define TLS_TP_OFFSET 0x7000
-#define TLS_DTV_OFFSET 0x8000
-#define TLS_TCB_SIZE 8
-
#define round(size, align) \
(((size) + (align) - 1) & ~((align) - 1))
#define calculate_first_tls_offset(size, align, offset) \
diff --git a/libexec/rtld-elf/powerpc64/reloc.c b/libexec/rtld-elf/powerpc64/reloc.c
--- a/libexec/rtld-elf/powerpc64/reloc.c
+++ b/libexec/rtld-elf/powerpc64/reloc.c
@@ -709,7 +709,6 @@
void
allocate_initial_tls(Obj_Entry *list)
{
- Elf_Addr **tp;
/*
* Fix the size of the static TLS block by using the maximum
@@ -719,21 +718,17 @@
tls_static_space = tls_last_offset + tls_last_size + RTLD_STATIC_TLS_EXTRA;
- tp = (Elf_Addr **)((char *)allocate_tls(list, NULL, TLS_TCB_SIZE, 16)
- + TLS_TP_OFFSET + TLS_TCB_SIZE);
-
- __asm __volatile("mr 13,%0" :: "r"(tp));
+ _tcb_set(allocate_tls(list, NULL, TLS_TCB_SIZE, TLS_TCB_ALIGN));
}
void*
__tls_get_addr(tls_index* ti)
{
- Elf_Addr **tp;
+ uintptr_t **dtvp;
char *p;
- __asm __volatile("mr %0,13" : "=r"(tp));
- p = tls_get_addr_common((Elf_Addr**)((Elf_Addr)tp - TLS_TP_OFFSET
- - TLS_TCB_SIZE), ti->ti_module, ti->ti_offset);
+ dtvp = &_tcb_get()->tcb_dtv;
+ p = tls_get_addr_common(dtvp, ti->ti_module, ti->ti_offset);
return (p + TLS_DTV_OFFSET);
}
diff --git a/libexec/rtld-elf/powerpc64/rtld_machdep.h b/libexec/rtld-elf/powerpc64/rtld_machdep.h
--- a/libexec/rtld-elf/powerpc64/rtld_machdep.h
+++ b/libexec/rtld-elf/powerpc64/rtld_machdep.h
@@ -33,6 +33,7 @@
#include <sys/types.h>
#include <machine/atomic.h>
+#include <machine/tls.h>
struct Struct_Obj_Entry;
@@ -65,11 +66,6 @@
* TLS
*/
-#define TLS_VARIANT_I 1
-#define TLS_TP_OFFSET 0x7000
-#define TLS_DTV_OFFSET 0x8000
-#define TLS_TCB_SIZE 16
-
#define round(size, align) \
(((size) + (align) - 1) & ~((align) - 1))
#define calculate_first_tls_offset(size, align, offset) \
diff --git a/libexec/rtld-elf/riscv/reloc.c b/libexec/rtld-elf/riscv/reloc.c
--- a/libexec/rtld-elf/riscv/reloc.c
+++ b/libexec/rtld-elf/riscv/reloc.c
@@ -387,7 +387,6 @@
void
allocate_initial_tls(Obj_Entry *objs)
{
- Elf_Addr **tp;
/*
* Fix the size of the static TLS block by using the maximum
@@ -397,19 +396,16 @@
tls_static_space = tls_last_offset + tls_last_size +
RTLD_STATIC_TLS_EXTRA;
- tp = (Elf_Addr **)((char *)allocate_tls(objs, NULL, TLS_TCB_SIZE, 16)
- + TLS_TP_OFFSET + TLS_TCB_SIZE);
-
- __asm __volatile("mv tp, %0" :: "r"(tp));
+ _tcb_set(allocate_tls(objs, NULL, TLS_TCB_SIZE, TLS_TCB_ALIGN));
}
void *
__tls_get_addr(tls_index* ti)
{
- Elf_Addr **dtvp;
+ uintptr_t **dtvp;
void *p;
- dtvp = _get_tp();
+ dtvp = &_tcb_get()->tcb_dtv;
p = tls_get_addr_common(dtvp, ti->ti_module, ti->ti_offset);
return ((char*)p + TLS_DTV_OFFSET);
diff --git a/libexec/rtld-elf/riscv/rtld_machdep.h b/libexec/rtld-elf/riscv/rtld_machdep.h
--- a/libexec/rtld-elf/riscv/rtld_machdep.h
+++ b/libexec/rtld-elf/riscv/rtld_machdep.h
@@ -40,6 +40,7 @@
#include <sys/types.h>
#include <machine/atomic.h>
+#include <machine/tls.h>
struct Struct_Obj_Entry;
@@ -82,10 +83,6 @@
/*
* TLS
*/
-#define TLS_VARIANT_I 1
-#define TLS_TP_OFFSET 0x0
-#define TLS_DTV_OFFSET 0x800
-#define TLS_TCB_SIZE 16
#define round(size, align) \
(((size) + (align) - 1) & ~((align) - 1))
diff --git a/libexec/rtld-elf/rtld-libc/Makefile.inc b/libexec/rtld-elf/rtld-libc/Makefile.inc
--- a/libexec/rtld-elf/rtld-libc/Makefile.inc
+++ b/libexec/rtld-elf/rtld-libc/Makefile.inc
@@ -67,8 +67,6 @@
_libc_other_objects+=syncicache
.endif
-_libc_other_objects+=_get_tp
-
# Extract all the .o files from libc_nossp_pic.a. This ensures that
# we don't accidentally pull in the interposing table or similar by linking
# directly against libc_nossp_pic.a
diff --git a/libexec/rtld-elf/rtld.h b/libexec/rtld-elf/rtld.h
--- a/libexec/rtld-elf/rtld.h
+++ b/libexec/rtld-elf/rtld.h
@@ -396,7 +396,7 @@
void *rtld_resolve_ifunc(const Obj_Entry *obj, const Elf_Sym *def);
void symlook_init(SymLook *, const char *);
int symlook_obj(SymLook *, const Obj_Entry *);
-void *tls_get_addr_common(Elf_Addr** dtvp, int index, size_t offset);
+void *tls_get_addr_common(uintptr_t **dtvp, int index, size_t offset);
void *allocate_tls(Obj_Entry *, void *, size_t, size_t);
void free_tls(void *, size_t, size_t);
void *allocate_module_tls(int index);
@@ -404,7 +404,6 @@
void free_tls_offset(Obj_Entry *obj);
const Ver_Entry *fetch_ventry(const Obj_Entry *obj, unsigned long);
int convert_prot(int elfflags);
-void *_get_tp(void); /* libc implementation */
bool check_elf_headers(const Elf_Ehdr *hdr, const char *path);
/*
diff --git a/libexec/rtld-elf/rtld.c b/libexec/rtld-elf/rtld.c
--- a/libexec/rtld-elf/rtld.c
+++ b/libexec/rtld-elf/rtld.c
@@ -4171,14 +4171,14 @@
static void
rtld_fill_dl_phdr_info(const Obj_Entry *obj, struct dl_phdr_info *phdr_info)
{
- Elf_Addr **dtvp;
+ uintptr_t **dtvp;
phdr_info->dlpi_addr = (Elf_Addr)obj->relocbase;
phdr_info->dlpi_name = obj->path;
phdr_info->dlpi_phdr = obj->phdr;
phdr_info->dlpi_phnum = obj->phsize / sizeof(obj->phdr[0]);
phdr_info->dlpi_tls_modid = obj->tlsindex;
- dtvp = _get_tp();
+ dtvp = &_tcb_get()->tcb_dtv;
phdr_info->dlpi_tls_data = (char *)tls_get_addr_slow(dtvp,
obj->tlsindex, 0, true) + TLS_DTV_OFFSET;
phdr_info->dlpi_adds = obj_loads;
@@ -5175,9 +5175,9 @@
}
void *
-tls_get_addr_common(Elf_Addr **dtvp, int index, size_t offset)
+tls_get_addr_common(uintptr_t **dtvp, int index, size_t offset)
{
- Elf_Addr *dtv;
+ uintptr_t *dtv;
dtv = *dtvp;
/* Check dtv generation in case new modules have arrived */

File Metadata

Mime Type
text/plain
Expires
Mon, May 18, 10:41 AM (6 h, 34 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
33244522
Default Alt Text
D33353.id.diff (15 KB)

Event Timeline