rtld: use _get_tp() in __tls_get_addr()
This eliminates some non-trivial amount of code duplication, where done. Only x86 and mips are handled right now. Tested by: bdragon (powerpc), mhorne (riscv) Sponsored by: The FreeBSD Foundation MFC after: 1 week Differential revision: https://reviews.freebsd.org/D29623
This commit is contained in:
parent
7cb32a0d03
commit
e8b9c508b7
@ -541,11 +541,10 @@ allocate_initial_tls(Obj_Entry *objs)
|
||||
void *
|
||||
__tls_get_addr(tls_index *ti)
|
||||
{
|
||||
Elf_Addr** segbase;
|
||||
Elf_Addr **dtvp;
|
||||
|
||||
__asm __volatile("movq %%fs:0, %0" : "=r" (segbase));
|
||||
|
||||
return tls_get_addr_common(&segbase[1], ti->ti_module, ti->ti_offset);
|
||||
dtvp = _get_tp();
|
||||
return (tls_get_addr_common(dtvp, ti->ti_module, ti->ti_offset));
|
||||
}
|
||||
|
||||
size_t
|
||||
|
@ -522,22 +522,20 @@ __attribute__((__regparm__(1)))
|
||||
void *
|
||||
___tls_get_addr(tls_index *ti)
|
||||
{
|
||||
Elf_Addr** segbase;
|
||||
Elf_Addr **dtvp;
|
||||
|
||||
__asm __volatile("movl %%gs:0, %0" : "=r" (segbase));
|
||||
|
||||
return tls_get_addr_common(&segbase[1], ti->ti_module, ti->ti_offset);
|
||||
dtvp = _get_tp();
|
||||
return (tls_get_addr_common(dtvp, ti->ti_module, ti->ti_offset));
|
||||
}
|
||||
|
||||
/* Sun ABI */
|
||||
void *
|
||||
__tls_get_addr(tls_index *ti)
|
||||
{
|
||||
Elf_Addr** segbase;
|
||||
Elf_Addr **dtvp;
|
||||
|
||||
__asm __volatile("movl %%gs:0, %0" : "=r" (segbase));
|
||||
|
||||
return tls_get_addr_common(&segbase[1], ti->ti_module, ti->ti_offset);
|
||||
dtvp = _get_tp();
|
||||
return (tls_get_addr_common(dtvp, ti->ti_module, ti->ti_offset));
|
||||
}
|
||||
|
||||
size_t
|
||||
|
@ -776,69 +776,15 @@ allocate_initial_tls(Obj_Entry *objs)
|
||||
sysarch(MIPS_SET_TLS, tls);
|
||||
}
|
||||
|
||||
#ifdef __mips_n64
|
||||
void *
|
||||
_mips_get_tls(void)
|
||||
{
|
||||
uint64_t _rv;
|
||||
|
||||
__asm__ __volatile__ (
|
||||
".set\tpush\n\t"
|
||||
".set\tmips64r2\n\t"
|
||||
"rdhwr\t%0, $29\n\t"
|
||||
".set\tpop"
|
||||
: "=r" (_rv));
|
||||
/*
|
||||
* XXXSS See 'git show c6be4f4d2d1b71c04de5d3bbb6933ce2dbcdb317'
|
||||
*
|
||||
* Remove the offset since this really a request to get the TLS
|
||||
* pointer via sysarch() (in theory). Of course, this may go away
|
||||
* once the TLS code is rewritten.
|
||||
*/
|
||||
_rv = _rv - TLS_TP_OFFSET - TLS_TCB_SIZE;
|
||||
|
||||
return (void *)_rv;
|
||||
}
|
||||
|
||||
#else /* mips 32 */
|
||||
|
||||
void *
|
||||
_mips_get_tls(void)
|
||||
{
|
||||
uint32_t _rv;
|
||||
|
||||
__asm__ __volatile__ (
|
||||
".set\tpush\n\t"
|
||||
".set\tmips32r2\n\t"
|
||||
"rdhwr\t%0, $29\n\t"
|
||||
".set\tpop"
|
||||
: "=r" (_rv));
|
||||
/*
|
||||
* XXXSS See 'git show c6be4f4d2d1b71c04de5d3bbb6933ce2dbcdb317'
|
||||
*
|
||||
* Remove the offset since this really a request to get the TLS
|
||||
* pointer via sysarch() (in theory). Of course, this may go away
|
||||
* once the TLS code is rewritten.
|
||||
*/
|
||||
_rv = _rv - TLS_TP_OFFSET - TLS_TCB_SIZE;
|
||||
|
||||
return (void *)_rv;
|
||||
}
|
||||
#endif /* ! __mips_n64 */
|
||||
|
||||
void *
|
||||
__tls_get_addr(tls_index* ti)
|
||||
{
|
||||
Elf_Addr** tls;
|
||||
Elf_Addr **tls;
|
||||
char *p;
|
||||
|
||||
#ifdef TLS_USE_SYSARCH
|
||||
sysarch(MIPS_GET_TLS, &tls);
|
||||
#else
|
||||
tls = _mips_get_tls();
|
||||
#endif
|
||||
|
||||
p = tls_get_addr_common(tls, ti->ti_module, ti->ti_offset + TLS_DTP_OFFSET);
|
||||
tls = _get_tp();
|
||||
p = tls_get_addr_common(tls, ti->ti_module, ti->ti_offset +
|
||||
TLS_DTP_OFFSET);
|
||||
|
||||
return (p);
|
||||
}
|
||||
|
@ -44,8 +44,6 @@ Elf_Addr reloc_jmpslot(Elf_Addr *where, Elf_Addr target,
|
||||
const struct Struct_Obj_Entry *defobj, const struct Struct_Obj_Entry *obj,
|
||||
const Elf_Rel *rel);
|
||||
Elf_Addr _mips_rtld_bind(struct Struct_Obj_Entry *obj, Elf_Size reloff);
|
||||
void *_mips_get_tls(void);
|
||||
|
||||
|
||||
#define make_function_pointer(def, defobj) \
|
||||
((defobj)->relocbase + (def)->st_value)
|
||||
|
Loading…
Reference in New Issue
Block a user