aboutsummaryrefslogtreecommitdiff
path: root/elf/dl-open.c
AgeCommit message (Collapse)AuthorFilesLines
2025-03-11elf: Test dlopen (NULL, RTLD_LAZY) from an ELF constructorFlorian Weimer1-0/+10
This call must not complete initialization of all shared objects in the global scope because the ELF constructor which makes the call likely has not finished initialization. Calling more constructors at this point would expose those to a partially constructed dependency. This completes the revert of commit 9897ced8e78db5d813166a7ccccfd5a ("elf: Run constructors on cyclic recursive dlopen (bug 31986)").
2025-02-02elf: Use _dl_find_object instead of _dl_find_dso_for_object in dlopenFlorian Weimer1-2/+4
The _dl_find_object function uses a binary search and is faster if there are many objects.
2025-02-02elf: Add fast path to dlopen for fully-opened mapsFlorian Weimer1-5/+31
If the map is already fully open (has matching flags and its own scope allocated), it is not necessary to unprotected memory during dlopen.
2025-02-02elf: Determine the caller link map in _dl_openFlorian Weimer1-28/+19
No functional change expected. This is in preparation of adding a fast path to dlopen in case no link map changes are required.
2025-02-02elf: Add l_soname accessor function for DT_SONAME valuesFlorian Weimer1-3/+1
It's not necessary to introduce temporaries because the compiler is able to evaluate l_soname just once in constracts like: l_soname (l) != NULL && strcmp (l_soname (l), LIBC_SO) != 0
2025-01-01Update copyright dates with scripts/update-copyrightsPaul Eggert1-1/+1
2024-10-28Revert "elf: Run constructors on cyclic recursive dlopen (bug 31986)"Florian Weimer1-8/+0
This reverts commit 9897ced8e78db5d813166a7ccccfd5a42c69ef20. Adjust the test expectations in elf/tst-dlopen-auditdup-auditmod.c accordingly.
2024-10-25elf: Fix map_complete Systemtap probe in dl_open_workerFlorian Weimer1-1/+1
The refactoring did not take the change of variable into account. Fixes commit 43db5e2c0672cae7edea7c9685b22317eae25471 ("elf: Signal RT_CONSISTENT after relocation processing in dlopen (bug 31986)").
2024-10-25elf: Signal RT_CONSISTENT after relocation processing in dlopen (bug 31986)Florian Weimer1-15/+29
Previously, a la_activity audit event was generated before relocation processing completed. This does did not match what happened during initial startup in elf/rtld.c (towards the end of dl_main). It also caused various problems if an auditor tried to open the same shared object again using dlmopen: If it was the directly loaded object, it had a search scope associated with it, so the early exit in dl_open_worker_begin was taken even though the object was unrelocated. This caused the r_state == RT_CONSISTENT assert to fail. Avoidance of the assert also depends on reversing the order of r_state update and auditor event (already implemented in a previous commit). At the later point, args->map can be NULL due to failure, so use the assigned namespace ID instead if that is available. Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
2024-10-25elf: Signal LA_ACT_CONSISTENT to auditors after RT_CONSISTENT switchFlorian Weimer1-5/+5
Auditors can call into the dynamic loader again if LA_ACT_CONSISTENT, and those recursive calls could observe r_state != RT_CONSISTENT. We should consider failing dlopen/dlmopen/dlclose if r_state != RT_CONSISTENT. The dynamic linker is probably not in a state in which it can handle reentrant calls. This needs further investigation. Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
2024-10-25elf: Run constructors on cyclic recursive dlopen (bug 31986)Florian Weimer1-0/+8
This is conceptually similar to the reported bug, but does not depend on auditing. The fix is simple: just complete execution of the constructors. This exposed the fact that the link map for statically linked executables does not have l_init_called set, even though constructors have run. Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
2024-08-08elf: Remove struct dl_init_args from elf/dl-open.cFlorian Weimer1-23/+3
It is completely redundant with struct dl_open_args.
2024-08-05elf: Avoid re-initializing already allocated TLS in dlopen (bug 31717)Florian Weimer1-30/+5
The old code used l_init_called as an indicator for whether TLS initialization was complete. However, it is possible that TLS for an object is initialized, written to, and then dlopen for this object is called again, and l_init_called is not true at this point. Previously, this resulted in TLS being initialized twice, discarding any interim writes (technically introducing a use-after-free bug even). This commit introduces an explicit per-object flag, l_tls_in_slotinfo. It indicates whether _dl_add_to_slotinfo has been called for this object. This flag is used to avoid double-initialization of TLS. In update_tls_slotinfo, the first_static_tls micro-optimization is removed because preserving the initalization flag for subsequent use by the second loop for static TLS is a bit complicated, and another per-object flag does not seem to be worth it. Furthermore, the l_init_called flag is dropped from the second loop (for static TLS initialization) because l_need_tls_init on its own prevents double-initialization. The remaining l_init_called usage in resize_scopes and update_scopes is just an optimization due to the use of scope_has_map, so it is not changed in this commit. The isupper check ensures that libc.so.6 is TLS is not reverted. Such a revert happens if l_need_tls_init is not cleared in _dl_allocate_tls_init for the main_thread case, now that l_init_called is not checked anymore in update_tls_slotinfo in elf/dl-open.c. Reported-by: Jonathon Anderson <janderson@rice.edu> Reviewed-by: Carlos O'Donell <carlos@redhat.com>
2024-01-01Update copyright dates with scripts/update-copyrightsPaul Eggert1-1/+1
2023-11-27elf: Relocate libc.so early during startup and dlmopen (bug 31083)Florian Weimer1-0/+11
This makes it more likely that objects without dependencies can use IFUNC resolvers in libc.so. Reviewed-by: Carlos O'Donell <carlos@redhat.com>
2023-11-27elf: Introduce the _dl_open_relocate_one_object functionFlorian Weimer1-39/+47
It is extracted from dl_open_worker_begin. Reviewed-by: Carlos O'Donell <carlos@redhat.com>
2023-09-01elf: Fix slow tls access after dlopen [BZ #19924]Szabolcs Nagy1-4/+4
In short: __tls_get_addr checks the global generation counter and if the current dtv is older then _dl_update_slotinfo updates dtv up to the generation of the accessed module. So if the global generation is newer than generation of the module then __tls_get_addr keeps hitting the slow dtv update path. The dtv update path includes a number of checks to see if any update is needed and this already causes measurable tls access slow down after dlopen. It may be possible to detect up-to-date dtv faster. But if there are many modules loaded (> TLS_SLOTINFO_SURPLUS) then this requires at least walking the slotinfo list. This patch tries to update the dtv to the global generation instead, so after a dlopen the tls access slow path is only hit once. The modules with larger generation than the accessed one were not necessarily synchronized before, so additional synchronization is needed. This patch uses acquire/release synchronization when accessing the generation counter. Note: in the x86_64 version of dl-tls.c the generation is only loaded once, since relaxed mo is not faster than acquire mo load. I have not benchmarked this. Tested by Adhemerval Zanella on aarch64, powerpc, sparc, x86 who reported that it fixes the performance issue of bug 19924. Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
2023-03-26Minor: don't call _dl_debug_update (which can have side effects) inside assertPaul Pluzhnikov1-2/+6
2023-01-06Update copyright dates with scripts/update-copyrightsJoseph Myers1-1/+1
2022-10-14elf: Do not completely clear reused namespace in dlmopen (bug 29600)Florian Weimer1-8/+6
The data in the _ns_debug member must be preserved, otherwise _dl_debug_initialize enters an infinite loop. To be conservative, only clear the libc_map member for now, to fix bug 29528. Fixes commit d0e357ff45a75553dee3b17ed7d303bfa544f6fe ("elf: Call __libc_early_init for reused namespaces (bug 29528)"), by reverting most of it. Reviewed-by: Carlos O'Donell <carlos@redhat.com> Tested-by: Carlos O'Donell <carlos@redhat.com>
2022-08-26elf: Call __libc_early_init for reused namespaces (bug 29528)Florian Weimer1-5/+8
libc_map is never reset to NULL, neither during dlclose nor on a dlopen call which reuses the namespace structure. As a result, if a namespace is reused, its libc is not initialized properly. The most visible result is a crash in the <ctype.h> functions. To prevent similar bugs on namespace reuse from surfacing, unconditionally initialize the chosen namespace to zero using memset.
2022-08-25Revert "Detect ld.so and libc.so version inconsistency during startup"Florian Weimer1-2/+2
This reverts commit 6f85dbf102ad7982409ba0fe96886caeb6389fef. Once this change hits the release branches, it will require relinking of all statically linked applications before static dlopen works again, for the majority of updates on release branches: The NEWS file is regularly updated with bug references, so the __libc_early_init suffix changes, and static dlopen cannot find the function anymore. While this ABI check is still technically correct (we do require rebuilding & relinking after glibc updates to keep static dlopen working), it is too drastic for stable release branches. Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
2022-08-24Detect ld.so and libc.so version inconsistency during startupFlorian Weimer1-2/+2
The files NEWS, include/link.h, and sysdeps/generic/ldsodefs.h contribute to the version fingerprint used for detection. The fingerprint can be further refined using the --with-extra-version-id configure argument. _dl_call_libc_early_init is replaced with _dl_lookup_libc_early_init. The new function is used store a pointer to libc.so's __libc_early_init function in the libc_map_early_init member of the ld.so namespace structure. This function pointer can then be called directly, so the separate invocation function is no longer needed. The versioned symbol lookup needs the symbol versioning data structures, so the initialization of libc_map and libc_map_early_init is now done from _dl_check_map_versions, after this information becomes available. (_dl_map_object_from_fd does not set this up in time, so the initialization code had to be moved from there.) This means that the separate initialization code can be removed from dl_main because _dl_check_map_versions covers all maps, including the initial executable loaded by the kernel. The lookup still happens before relocation and the invocation of IFUNC resolvers, so IFUNC resolvers are protected from ABI mismatch. The __libc_early_init function pointer is not protected because so little code runs between the pointer write and the invocation (only dynamic linker code and IFUNC resolvers). Reviewed-by: Carlos O'Donell <carlos@redhat.com>
2022-01-01Update copyright dates with scripts/update-copyrightsPaul Eggert1-1/+1
I used these shell commands: ../glibc/scripts/update-copyrights $PWD/../gnulib/build-aux/update-copyright (cd ../glibc && git commit -am"[this commit message]") and then ignored the output, which consisted lines saying "FOO: warning: copyright statement not found" for each of 7061 files FOO. I then removed trailing white space from math/tgmath.h, support/tst-support-open-dev-null-range.c, and sysdeps/x86_64/multiarch/strlen-vec.S, to work around the following obscure pre-commit check failure diagnostics from Savannah. I don't know why I run into these diagnostics whereas others evidently do not. remote: *** 912-#endif remote: *** 913: remote: *** 914- remote: *** error: lines with trailing whitespace found ... remote: *** error: sysdeps/unix/sysv/linux/statx_cp.c: trailing lines
2021-12-28elf: Add _dl_find_object functionFlorian Weimer1-0/+5
It can be used to speed up the libgcc unwinder, and the internal _dl_find_dso_for_object function (which is used for caller identification in dlopen and related functions, and in dladdr). _dl_find_object is in the internal namespace due to bug 28503. If libgcc switches to _dl_find_object, this namespace issue will be fixed. It is located in libc for two reasons: it is necessary to forward the call to the static libc after static dlopen, and there is a link ordering issue with -static-libgcc and libgcc_eh.a because libc.so is not a linker script that includes ld.so in the glibc build tree (so that GCC's internal -lc after libgcc_eh.a does not pick up ld.so). It is necessary to do the i386 customization in the sysdeps/x86/bits/dl_find_object.h header shared with x86-64 because otherwise, multilib installations are broken. The implementation uses software transactional memory, as suggested by Torvald Riegel. Two copies of the supporting data structures are used, also achieving full async-signal-safety. Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
2021-12-28elf: Do not fail for failed dlmopen on audit modules (BZ #28061)Adhemerval Zanella1-2/+0
The dl_main sets the LM_ID_BASE to RT_ADD just before starting to add load new shared objects. The state is set to RT_CONSISTENT just after all objects are loaded. However if a audit modules tries to dlmopen an inexistent module, the _dl_open will assert that the namespace is in an inconsistent state. This is different than dlopen, since first it will not use LM_ID_BASE and second _dl_map_object_from_fd is the sole responsible to set and reset the r_state value. So the assert on _dl_open can not really be seen if the state is consistent, since _dt_main resets it. This patch removes the assert. Checked on x86_64-linux-gnu, i686-linux-gnu, and aarch64-linux-gnu. Reviewed-by: Florian Weimer <fweimer@redhat.com>
2021-12-28elf: Add _dl_audit_activity_map and _dl_audit_activity_nsidAdhemerval Zanella1-19/+1
It consolidates the code required to call la_activity audit callback. Also for a new Lmid_t the namespace link_map list are empty, so it requires to check if before using it. This can happen for when audit module is used along with dlmopen. Checked on x86_64-linux-gnu, i686-linux-gnu, and aarch64-linux-gnu. Reviewed-by: Florian Weimer <fweimer@redhat.com>
2021-10-04elf: Avoid deadlock between pthread_create and ctors [BZ #28357]Szabolcs Nagy1-1/+34
The fix for bug 19329 caused a regression such that pthread_create can deadlock when concurrent ctors from dlopen are waiting for it to finish. Use a new GL(dl_load_tls_lock) in pthread_create that is not taken around ctors in dlopen. The new lock is also used in __tls_get_addr instead of GL(dl_load_lock). The new lock is held in _dl_open_worker and _dl_close_worker around most of the logic before/after the init/fini routines. When init/fini routines are running then TLS is in a consistent, usable state. In _dl_open_worker the new lock requires catching and reraising dlopen failures that happen in the critical section. The new lock is reinitialized in a fork child, to keep the existing behaviour and it is kept recursive in case malloc interposition or TLS access from signal handlers can retake it. It is not obvious if this is necessary or helps, but avoids changing the preexisting behaviour. The new lock may be more appropriate for dl_iterate_phdr too than GL(dl_load_write_lock), since TLS state of an incompletely loaded module may be accessed. If the new lock can replace the old one, that can be a separate change. Fixes bug 28357. Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
2021-09-30elf: Replace nsid with args.nsid [BZ #27609]H.J. Lu1-1/+1
commit ec935dea6332cb22f9881cd1162bad156173f4b0 Author: Florian Weimer <fweimer@redhat.com> Date: Fri Apr 24 22:31:15 2020 +0200 elf: Implement __libc_early_init has @@ -856,6 +876,11 @@ no more namespaces available for dlmopen()")); /* See if an error occurred during loading. */ if (__glibc_unlikely (exception.errstring != NULL)) { + /* Avoid keeping around a dangling reference to the libc.so link + map in case it has been cached in libc_map. */ + if (!args.libc_already_loaded) + GL(dl_ns)[nsid].libc_map = NULL; + do_dlopen calls _dl_open with nsid == __LM_ID_CALLER (-2), which calls dl_open_worker with args.nsid = nsid. dl_open_worker updates args.nsid if it is __LM_ID_CALLER. After dl_open_worker returns, it is wrong to use nsid. Replace nsid with args.nsid after dl_open_worker returns. This fixes BZ #27609.
2021-09-19Extend struct r_debug to support multiple namespaces [BZ #15971]H.J. Lu1-5/+5
Glibc does not provide an interface for debugger to access libraries loaded in multiple namespaces via dlmopen. The current rtld-debugger interface is described in the file: elf/rtld-debugger-interface.txt under the "Standard debugger interface" heading. This interface only provides access to the first link-map (LM_ID_BASE). 1. Bump r_version to 2 when multiple namespaces are used. This triggers the GDB bug: https://sourceware.org/bugzilla/show_bug.cgi?id=28236 2. Add struct r_debug_extended to extend struct r_debug into a linked-list, where each element correlates to an unique namespace. 3. Initialize the r_debug_extended structure. Bump r_version to 2 for the new namespace and add the new namespace to the namespace linked list. 4. Add _dl_debug_update to return the address of struct r_debug' of a namespace. 5. Add a hidden symbol, _r_debug_extended, for struct r_debug_extended. 6. Provide the symbol, _r_debug, with size of struct r_debug, as an alias of _r_debug_extended, for programs which reference _r_debug. This fixes BZ #15971. Reviewed-by: Florian Weimer <fweimer@redhat.com>
2021-07-30elf: Fix audit regressionAdhemerval Zanella1-9/+2
Commit 03e187a41d9 added a regression when an audit module does not have libc as DT_NEEDED (although unusual it is possible). Checked on x86_64-linux-gnu.
2021-07-14elf: Fix DTV gap reuse logic (BZ #27135)Adhemerval Zanella1-10/+0
This is updated version of the 572bd547d57a (reverted by 40ebfd016ad2) that fixes the _dl_next_tls_modid issues. This issue with 572bd547d57a patch is the DTV entry will be only update on dl_open_worker() with the update_tls_slotinfo() call after all dependencies are being processed by _dl_map_object_deps(). However _dl_map_object_deps() itself might call _dl_next_tls_modid(), and since the _dl_tls_dtv_slotinfo_list::map is not yet set the entry will be wrongly reused. This patch fixes by renaming the _dl_next_tls_modid() function to _dl_assign_tls_modid() and by passing the link_map so it can set the slotinfo value so a subsequente _dl_next_tls_modid() call will see the entry as allocated. The intermediary value is cleared up on remove_slotinfo() for the case a library fails to load with RTLD_NOW. This patch fixes BZ #27135. Checked on x86_64-linux-gnu. Reviewed-by: Szabolcs Nagy <szabolcs.nagy@arm.com>
2021-06-25elf: Disable most of TLS modid gaps processing [BZ #27135]Florian Weimer1-0/+10
Revert "elf: Fix DTV gap reuse logic [BZ #27135]" This reverts commit 572bd547d57a39b6cf0ea072545dc4048921f4c3. It turns out that the _dl_next_tls_modid in _dl_map_object_from_fd keeps returning the same modid over and over again if there is a gap and more than TLS-using module is loaded in one dlopen call. This corrupts TLS data structures. The bug is still present after a revert, but empirically it is much more difficult to trigger (because it involves a dlopen failure).
2021-05-17elf: Remove DL_STATIC_INITFlorian Weimer1-4/+0
All users have been converted to the __rtld_static_init mechanism. Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
2021-05-17elf: Partially initialize ld.so after static dlopen (bug 20802)Florian Weimer1-2/+15
After static dlopen, a copy of ld.so is loaded into the inner namespace, but that copy is not initialized at all. Some architectures run into serious problems as result, which is why the _dl_var_init mechanism was invented. With libpthread moving into libc and parts into ld.so, more architectures impacted, so it makes sense to switch to a generic mechanism which performs the partial initialization. As a result, getauxval now works after static dlopen (bug 20802). Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
2021-05-11elf: Fix DTV gap reuse logic [BZ #27135]Szabolcs Nagy1-10/+0
For some reason only dlopen failure caused dtv gaps to be reused. It is possible that the intent was to never reuse modids for a different module, but after dlopen failure all gaps are reused not just the ones caused by the unfinished dlopened. So the code has to handle reused modids already which seems to work, however the data races at thread creation and tls access (see bug 19329 and bug 27111) may be more severe if slots are reused so this is scheduled after those fixes. I think fixing the races are not simpler if reuse is disallowed and reuse has other benefits, so set GL(dl_tls_dtv_gaps) whenever entries are removed from the middle of the slotinfo list. The value does not have to be correct: incorrect true value causes the next modid query to do a slotinfo walk, incorrect false will leave gaps and new entries are added at the end. Fixes bug 27135. Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
2021-05-11elf: Use relaxed atomics for racy accesses [BZ #19329]Szabolcs Nagy1-1/+4
This is a follow up patch to the fix for bug 19329. This adds relaxed MO atomics to accesses that were previously data races but are now race conditions, and where relaxed MO is sufficient. The race conditions all follow the pattern that the write is behind the dlopen lock, but a read can happen concurrently (e.g. during tls access) without holding the lock. For slotinfo entries the read value only matters if it reads from a synchronized write in dlopen or dlclose, otherwise the related dtv entry is not valid to access so it is fine to leave it in an inconsistent state. The same applies for GL(dl_tls_max_dtv_idx) and GL(dl_tls_generation), but there the algorithm relies on the fact that the read of the last synchronized write is an increasing value. Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
2021-05-05elf, nptl: Initialize static TLS directly in ld.soFlorian Weimer1-1/+1
The stack list is available in ld.so since commit 1daccf403b1bd86370eb94edca794dc106d02039 ("nptl: Move stack list variables into _rtld_global"), so it's possible to walk the stack list directly in ld.so and perform the initialization there. This eliminates an unprotected function pointer from _rtld_global and reduces the libpthread initialization code.
2021-01-02Update copyright dates with scripts/update-copyrightsPaul Eggert1-1/+1
I used these shell commands: ../glibc/scripts/update-copyrights $PWD/../gnulib/build-aux/update-copyright (cd ../glibc && git commit -am"[this commit message]") and then ignored the output, which consisted lines saying "FOO: warning: copyright statement not found" for each of 6694 files FOO. I then removed trailing white space from benchtests/bench-pthread-locks.c and iconvdata/tst-iconv-big5-hkscs-to-2ucs4.c, to work around this diagnostic from Savannah: remote: *** pre-commit check failed ... remote: *** error: lines with trailing whitespace found remote: error: hook declined to update refs/heads/master
2020-12-16Replace __libc_multiple_libcs with __libc_initial flagFlorian Weimer1-6/+0
Change sbrk to fail for !__libc_initial (in the generic implementation). As a result, sbrk is (relatively) safe to use for the __libc_initial case (from the main libc). It is therefore no longer necessary to avoid using it in that case (or updating the brk cache), and the __libc_initial flag does not need to be updated as part of dlmopen or static dlopen. As before, direct brk system calls on Linux may lead to memory corruption. Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
2020-05-12elf: Remove redundant add_to_global_resize_failure call from dl_open_argsFlorian Weimer1-5/+0
The second call does not do anything because the data structures have already been resized by the call that comes before the demarcation point. Fixes commit a509eb117fac1d764b15eba64993f4bdb63d7f3c ("Avoid late dlopen failure due to scope, TLS slotinfo updates [BZ #25112]"). Reviewed-by: Carlos O'Donell <carlos@redhat.com>
2020-04-29elf: Add initial flag argument to __libc_early_initFlorian Weimer1-2/+15
The rseq initialization should happen only for the libc in the base namespace (in the dynamic case) or the statically linked libc. The __libc_multiple_libcs flag does not quite cover this case at present, so this commit introduces a flag argument to __libc_early_init, indicating whether the libc being libc is the primary one (of the main program). Reviewed-by: Carlos O'Donell <carlos@redhat.com>
2020-04-24elf: Implement __libc_early_initFlorian Weimer1-0/+25
This function is defined in libc.so, and the dynamic loader calls right after relocation has been finished, before any ELF constructors or the preinit function is invoked. It is also used in the static build for initializing parts of the static libc. To locate __libc_early_init, a direct symbol lookup function is used, _dl_lookup_direct. It does not search the entire symbol scope and consults merely a single link map. This function could also be used to implement lookups in the vDSO (as an optimization). A per-namespace variable (libc_map) is added for locating libc.so, to avoid repeated traversals of the search scope. It is similar to GL(dl_initfirst). An alternative would have been to thread a context argument from _dl_open down to _dl_map_object_from_fd (where libc.so is identified). This could have avoided the global variable, but the change would be larger as a result. It would not have been possible to use this to replace GL(dl_initfirst) because that global variable is used to pass the function pointer past the stack switch from dl_main to the main program. Replacing that requires adding a new argument to _dl_init, which in turn needs changes to the architecture-specific libc.so startup code written in assembler. __libc_early_init should not be used to replace _dl_var_init (as it exists today on some architectures). Instead, _dl_lookup_direct should be used to look up a new variable symbol in libc.so, and that should then be initialized from the dynamic loader, immediately after the object has been loaded in _dl_map_object_from_fd (before relocation is run). This way, more IFUNC resolvers which depend on these variables will work