Why do Glibc needs to hold a lock in tls_get_addr_tail?
Maxim
chefmax7@gmail.com
Tue Dec 20 10:18:00 GMT 2016
I'm sorry, it seems that my mail client malformed the message .
On 20/12/16 12:55, Maxim Ostapenko wrote:
> Hi Glibc developers,
>
> I had several issues with TLS on our system (BZ #17620 and BZ #18457
> actually) and fortunately was able to fix them with corresponding
> patches.
> However, during investigation, I tried to understand details of TLS
> implementation in Glibc (I was looking to current trunk) and was
> confused by some code paths.
> In particular, I can't understand following comment in
> tls_get_addr_tail function:
>
> static void *
> __attribute_noinline__
> tls_get_addr_tail (GET_ADDR_ARGS, dtv_t *dtv, struct link_map *the_map)
> {
> [...]
> /* Make sure that, if a dlopen running in parallel forces the
> variable into static storage, we'll wait until the address in the
> static TLS block is set up, and use that. If we're undecided
> yet, make sure we make the decision holding the lock as well. */
> if (__glibc_unlikely (the_map->l_tls_offset
> != FORCED_DYNAMIC_TLS_OFFSET))
> {
> __rtld_lock_lock_recursive (GL(dl_load_lock));
> if (__glibc_likely (the_map->l_tls_offset == NO_TLS_OFFSET))
> {
> the_map->l_tls_offset = FORCED_DYNAMIC_TLS_OFFSET;
> __rtld_lock_unlock_recursive (GL(dl_load_lock));
> }
> else if (__glibc_likely (the_map->l_tls_offset
> != FORCED_DYNAMIC_TLS_OFFSET))
> {
>
>
> How could it be that dynamic linker resolves thread local symbol to a
> library that still not loaded (dlopen still running)?
> The only case I can imagine here is something like this:
>
> Thread 1
> Thread 2
>
> while (!sym)
> dlopen ("libfoo.so". RTLD_GLOBAL);
> sym = dlsym (RTLD_DEFAULT, "foo");
> *sym = ...
>
> where "foo" is defined in libfoo.so library.
The testcase I was talking about looks like this:
Thread 1:
while (!sym)
sym = dlsym (RTLD_DEFAULT, "foo");
*sym = ...
Thread 2:
dlopen ("libfoo.so". RTLD_GLOBAL);
...
where "foo" is defined in libfoo.so library.
>
> Is that the case we need to protect with lock inside
> tls_get_addr_tail? Or maybe there is another test case for this code
> path (perhaps in Glibc testsuite)?
>
> Thanks,
> -Maxim
More information about the Libc-help
mailing list