Commit Graph

112 Commits

Author SHA1 Message Date
Rich Felker e17b9d7474 ldso: fix TLSDESC addend processing on archs with backwards descriptors
presently this only affects 32-bit arm. despite correctly reversing
the function pointer and argument fields based on the
TLSDESC_BACKWARDS macro, we did not read the addend from the
swapped-order argument field, so nonzero addends were lost, producing
wrong runtime addresses for TLS objects needing an addend.

based on report and patch by Rui Ueyama.
2023-11-06 21:50:37 -05:00
Rich Felker 039d3c34f2 ldso: convert TLSDESC_BACKWARDS from "#ifdef" to "if" logic
this style is preferred because it allows the code to be
compile-checked even on archs where it is not used.
2023-11-06 21:48:02 -05:00
Rich Felker 5baf2d92d3 ldso: use __ehdr_start if available to locate its own ELF headers
previously, the relative load address was used as the address at which
to find the ELF headers. this only works if two conditions are met:
ldso is linked to start at a virtual address of 0, and the linker is
cooperative and includes the main ELF headers in a loadable segment.

while in practice these are always met, modern linkers provide a
__ehdr_start symbol pointing to the ELF headers, and can in principle
use the reference to this symbol as an indication that they need to be
mapped in a segment. this also should make it possible to link for a
different starting virtual address, if that's ever desirable.
2023-11-06 12:59:34 -05:00
Rich Felker 7c41047285 fix inadvertently static local var in dynlink get_lfs64
commit 246f1c8114 inadvertently
introduced the local variable p as static by declaring it together
with lfs64_list. the function is only reachable under lock, and is not
called reentrantly, so this is not a functional bug, but it is
confusing and inefficient. fix by separating the declarations.
2023-04-11 09:06:27 -04:00
Rich Felker f897461d4f fix debugger tracking of shared libraries on mips with PIE main program
mips has its own mechanisms for DT_DEBUG because it makes _DYNAMIC
read-only, and the original mechanism, DT_MIPS_RLD_MAP, was
PIE-incompatible. DT_MIPS_RLD_MAP_REL was added to remedy this, but we
never implemented support for it. add it now using the same idioms for
mips-specific ldso logic.
2023-01-18 10:32:14 -05:00
Rich Felker f47a8cdd25 ldso: fix invalid early references to extern-linkage libc.page_size
when PAGE_SIZE is not constant, internal/libc.h defines it to expand
to libc.page_size. however, kernel_mapped_dso, reachable from stage 2
of the dynamic linker bootstrap (__dls2), needs PAGE_SIZE to interpret
the relro range. at this point the libc object is both uninitialized
and invalid to access according to our model for bootstrapping, which
does not assume any external-linkage objects are accessible until
stages 2b/3. in practice it likely worked because hidden visibility
tends to behave like internal linkage, but this is not a property that
the dynamic linker was designed to rely upon.

this bug likely manifested as relro malfunction on archs with variable
page size, due to incorrect mask when aligning the relro bounds to
page boundaries.

while there are certainly more direct ways to fix the known problem
point here, a maximally future-proof way is to just bypass the libc.h
PAGE_SIZE definition in the dynamic linker and instead have dynlink.c
define its own internal-linkage object for variable page size. then,
if anything else in stage 2 ever ends up referencing PAGE_SIZE, it
will just automatically work right.
2022-11-30 19:07:34 -05:00
Rich Felker 29e4319178 fix double-processing of DT_RELR relocations in ldso relocating itself
this is analogous to skip_relative logic in do_relocs -- because
relative relocations for the dynamic linker itself were already
performed at entry (stage 1), they must not be applied again.
2022-11-10 09:02:02 -05:00
Rich Felker 246f1c8114 remove LFS64 symbol aliases; replace with dynamic linker remapping
originally the namespace-infringing "large file support" interfaces
were included as part of glibc-ABI-compat, with the intent that they
not be used for linking, since our off_t is and always has been
unconditionally 64-bit and since we usually do not aim to support
nonstandard interfaces when there is an equivalent standard interface.

unfortunately, having the symbols present and available for linking
caused configure scripts to detect them and attempt to use them
without declarations, producing all the expected ill effects that
entails.

as a result, commit 2dd8d5e1b8 was made
to prevent this, using macros to redirect the LFS64 names to the
standard names, conditional on _GNU_SOURCE or _LARGEFILE64_SOURCE.
however, this has turned out to be a source of further problems,
especially since g++ defines _GNU_SOURCE by default. in particular,
the presence of these names as macros breaks a lot of valid code.

this commit removes all the LFS64 symbols and replaces them with a
mechanism in the dynamic linker symbol lookup failure path to retry
with the spurious "64" removed from the symbol name. in the future,
if/when the rest of glibc-ABI-compat is moved out of libc, this can be
removed.
2022-10-19 14:01:31 -04:00
Rich Felker 6f3ead0ae1 process DT_RELR relocations in ldso-startup/static-pie
commit d32dadd60e added DT_RELR
processing for programs and shared libraries processed by the dynamic
linker, but left them unsupported in the dynamic linker itseld and in
static pie binaries, which self-relocate via code in dlstart.c.

add the equivalent processing to this code path so that there are not
arbitrary restrictions on where the new packed relative relocation
form can be used.
2022-09-12 08:30:36 -04:00
Érico Nogueira 379b18218d ldso: make exit condition clearer in fixup_rpath
breaking out of the switch-case when l==-1 means the conditional below
will necessarily be true (-1 >= buf_size, a size_t variable) and the
function will return 0. it is, however, somewhat unclear that that's
what's happening. simply returning there is simpler
2022-08-17 19:49:54 -04:00
Rich Felker bf99258564 ldso: process RELR only for non-FDPIC archs
the way RELR is applied is not a meaningful operation for FDPIC (there
is no single "base" address). it seems unlikely RELR would ever be
added for FDPIC, but if it ever is, the behavior and possibly data
format will need to be different, so guard against calling the
non-FDPIC code.
2022-08-02 17:29:01 -04:00
Fangrui Song d32dadd60e ldso: support DT_RELR relative relocation format
this resolves DT_RELR relocations in non-ldso, dynamic-linked objects.
2022-08-02 17:27:45 -04:00
Rich Felker d16d7b1099 early stage ldso: remove symbolic references via error handling function
while the error handling function should not be reached in stage 2
(assuming ldso itself was linked correctly), this was not statically
determinate from the compiler's perspective, and in theory a compiler
performing LTO could lift the TLS references (errno and other things)
out of the printf-family functions called in a stage where TLS is not
yet initialized.

instead, perform the call via a static-storage, internal-linkage
function pointer which will be set to a no-op function until the stage
where the real error handling function should be reachable.

inspired by commit 63c67053a3.
2022-07-19 19:00:53 -04:00
Alex Xu (Hello71) 63c67053a3 in early stage ldso before __dls2b, call mprotect with __syscall
if LTO is enabled, gcc hoists the call to ___errno_location outside the
loop even though the access to errno is gated behind head != &ldso
because ___errno_location is marked __attribute__((const)). this causes
the program to crash because TLS is not yet initialized when called from
__dls2. this is also possible if LTO is not enabled; even though gcc 11
doesn't do it, it is still wrong to use errno here.

since the start and end are already aligned, we can simply call
__syscall instead of using global errno.

Fixes: e13a2b8953 ("implement PT_GNU_RELRO support")
2022-07-02 16:12:04 -04:00
Érico Nogueira b7a130e0b9 remove unnecessary cast for map_library return
the function already returns (void *)
2021-04-20 15:40:27 -04:00
Rich Felker aad50fcd79 fix regression in dl_iterate_phdr reporting of modules with no TLS
__tls_get_addr should not be called with an invalid TLS module id of
0. in practice it probably "works", returning the DTV length as if it
were a pointer, and the callback should probably not inspect
dlpi_tls_data in this case, but it's likely that some real-world
callbacks use a check on dlpi_tls_data being non-null, rather than on
dlpi_tls_modid being nonzero, to conclude that the module has TLS.
2021-04-16 10:20:46 -04:00
Rich Felker 521b4d27a0 fix dl_iterate_phdr dlpi_tls_data reporting to match spec
dl_iterate_phdr was wrongly reporting the address of the DSO's PT_TLS
image rather than the calling thread's instance of the TLS. the man
page, which is essentially normative for a nonstandard function of
this sort, clearly specifies the latter. it does not clarify where
exactly within/relative-to the image the pointer should point, but the
reasonable thing to do is match the ABI's DTP offset, and this seems
to be what other implementations do.
2021-03-26 13:35:41 -04:00
Rich Felker cfdfd5ea3c don't fail to map library/executable with zero-length segment maps
reportedly the GNU linker can emit such segments, causing spurious
failure to load due to mmap with a length of zero producing EINVAL.
no action is required for such a load map (it's effectively a nop in
the program headers table) so just treat it as always successful.
2021-03-05 11:13:02 -05:00
Rich Felker 167390f055 lift child restrictions after multi-threaded fork
as the outcome of Austin Group tracker issue #62, future editions of
POSIX have dropped the requirement that fork be AS-safe. this allows
but does not require implementations to synchronize fork with internal
locks and give forked children of multithreaded parents a partly or
fully unrestricted execution environment where they can continue to
use the standard library (per POSIX, they can only portably use
AS-safe functions).

up until recently, taking this allowance did not seem desirable.
however, commit 8ed2bd8bfc exposed the
extent to which applications and libraries are depending on the
ability to use malloc and other non-AS-safe interfaces in MT-forked
children, by converting latent very-low-probability catastrophic state
corruption into predictable deadlock. dealing with the fallout has
been a huge burden for users/distros.

while it looks like most of the non-portable usage in applications
could be fixed given sufficient effort, at least some of it seems to
occur in language runtimes which are exposing the ability to run
unrestricted code in the child as part of the contract with the
programmer. any attempt at fixing such contracts is not just a
technical problem but a social one, and is probably not tractable.

this patch extends the fork function to take locks for all libc
singletons in the parent, and release or reset those locks in the
child, so that when the underlying fork operation takes place, the
state protected by these locks is consistent and ready for the child
to use. locking is skipped in the case where the parent is
single-threaded so as not to interfere with legacy AS-safety property
of fork in single-threaded programs. lock order is mostly arbitrary,
but the malloc locks (including bump allocator in case it's used) must
be taken after the locks on any subsystems that might use malloc, and
non-AS-safe locks cannot be taken while the thread list lock is held,
imposing a requirement that it be taken last.
2020-11-11 15:55:30 -05:00
Rich Felker 34952fe5de convert malloc use under libc-internal locks to use internal allocator
this change lifts undocumented restrictions on calls by replacement
mallocs to libc functions that might take these locks, and sets the
stage for lifting restrictions on the child execution environment
after multithreaded fork.

care is taken to #define macros to replace all four functions (malloc,
calloc, realloc, free) even if not all of them will be used, using an
undefined symbol name for the ones intended not to be used so that any
inadvertent future use will be caught at compile time rather than
directed to the wrong implementation.
2020-11-11 13:31:50 -05:00
Rich Felker c1e5d243b7 drop use of getdelim/stdio in dynamic linker
the only place stdio was used here was for reading the ldso path file,
taking advantage of getdelim to automatically allocate and resize the
buffer. the motivation for use here was that, with shared libraries,
stdio is already available anyway and free to use. this has long been
a nuisance to users because getdelim's use of realloc here triggered a
valgrind bug, but removing it doesn't really fix that; on some archs
even calling the valgrind-interposed malloc at this point will crash.

the actual motivation for this change is moving towards getting rid of
use of application-provided malloc in parts of libc where it would be
called with libc-internal locks held, leading to the possibility of
deadlock if the malloc implementation doesn't follow unwritten rules
about which libc functions are safe for it to call. since getdelim is
required to produce a pointer as if by malloc (i.e. that can be passed
to reallor or free), it necessarily must use the public malloc.

instead of performing a realloc loop as the path file is read, first
query its size with fstat and allocate only once. this produces
slightly different truncation behavior when racing with writes to a
file, but neither behavior is or could be made safe anyway; on a live
system, ldso path files should be replaced by atomic rename only. the
change should also reduce memory waste.
2020-11-11 10:55:13 -05:00
rcombs ccba23459e ldso: notify the debugger when we're doing a dlopen
Otherwise lldb doesn't notice the new library and stack traces
containing it get cut off unhelpfully.
2020-10-27 01:10:29 -04:00
Rich Felker 50716702d4 ldso: use pthread_t rather than kernel tid to track ctor visitor
commit 188759bbee documented the intent
to allow recursive dlopen based on tracking ctor_visitor, but used a
kernel tid rather than the pthread_t to identify the caller. as a
result, it would not behave as intended under fork by a ctor, where
the child tid would not match.
2020-10-14 20:27:12 -04:00
Rich Felker 1efc8eb2c7 fix stale lock when allocation of ctor queue fails during dlopen
queue_ctors should not be called with the init_fini_lock held, since
it may longjmp out on allocation failure. this introduces a minor
TOCTOU race with p->constructed, but one already exists further down
anyway, and by design it's okay to run through the queue more than
once anyway. the only reason we bother to check p->constructed at all
is to avoid spurious failure of dlopen when the library is already
fully loaded and constructed.
2020-10-14 20:27:12 -04:00
Rich Felker 57f6e85c9d remove redundant pthread struct members repeated for layout purposes
dtv_copy, canary2, and canary_at_end existed solely to match multiple
ABI and asm-accessed layouts simultaneously. now that pthread_arch.h
can be included before struct __pthread is defined, the struct layout
can depend on macros defined by pthread_arch.h.
2020-08-27 18:36:45 -04:00
Rich Felker e9f4fd1185 have ldso track replacement of aligned_alloc
this is in preparation for improving behavior of malloc interposition.
2020-06-10 22:02:45 -04:00
Rich Felker cee88b76f7 move declaration of interfaces between malloc and ldso to dynlink.h
this eliminates consumers of malloc_impl.h outside of the malloc
implementation.
2020-06-02 21:38:25 -04:00
Fangrui Song 72658c658b ldso: remove redundant switch case for REL_NONE
as a result of commit b6a6cd703f,
the REL_NONE case is now redundant.
2020-03-20 12:35:38 -04:00
Rich Felker 0ff18be208 fix incorrect __hwcap seen in dynamic-linked __set_thread_area
the bug fixed in commit b82cd6c78d was
mostly masked on arm because __hwcap was zero at the point of the call
from the dynamic linker to __set_thread_area, causing the access to
libc.auxv to be skipped and kuser_helper versions of TLS access and
atomics to be used instead of the armv6 or v7 versions. however, on
kernels with kuser_helper removed for hardening it would crash.

since __set_thread_area potentially uses __hwcap, it must be
initialized before the function is called. move the AT_HWCAP lookup
from stage 3 to stage 2b.
2020-01-15 16:15:49 -05:00
Rich Felker d6bbea2acf fix fdpic regression in dynamic linker with overly smart compilers
at least gcc 9 broke execution of DT_INIT/DT_FINI for fdpic archs
(presently only sh) by recognizing that the stores to the
compound-literal function descriptor constructed to call them were
dead stores. there's no way to make a "may_alias function", so instead
launder the descriptor through an asm-statement barrier. in practice
just making the compound literal volatile seemed to have worked too,
but this should be less of a hack and more accurately convey the
semantics of what transformations are not valid.
2020-01-01 00:15:04 -05:00
Rich Felker b82cd6c78d fix crashing ldso on archs where __set_thread_area examines auxv
commit 1c84c99913 moved the call to
__init_tp above the initialization of libc.auxv, inadvertently
breaking archs where __set_thread_area examines auxv for the sake of
determining the TLS/atomic model needed at runtime. this broke armv6
and sh2.
2019-12-31 21:59:07 -05:00
Rich Felker b529ec9b52 move stage3_func typedef out of shared internal dynlink.h header
this interface contract is entirely internal to dynlink.c.
2019-12-31 21:51:07 -05:00
Rich Felker 22daaea39f add time64 redirect for, and redirecting implementation of, dlsym
if symbols are being redirected to provide the new time64 ABI, dlsym
must perform matching redirections; otherwise, it would poke a hole in
the magic and return pointers to functions that are not safe to call
from a caller using time64 types.

rather than duplicating a table of redirections, use the time64
symbols present in libc's symbol table to derive the decision for
whether a particular symbol needs to be redirected.
2019-11-02 18:30:56 -04:00
Rich Felker 9d35fec9e1 fix regression whereby main thread didn't get TLS relocations
commit ffab43602b broke this by moving
relocations after not only the allocation of storage for the main
thread's static TLS, but after the copying of the TLS image. thus,
relocation results were not reflected in the main thread's copy. this
could be fixed by calling __reset_tls after relocations, but instead
split the allocation and installation before/after relocations so that
there's not a redundant copy.

due to commit 71af530987, updating of
static_tls_cnt needs to be kept with allocation of static TLS, before
relocations, rather than after installation.
2019-08-13 21:53:30 -04:00
Szabolcs Nagy f2435263d7 make relocation time symbol lookup and dlsym consistent
Using common code path for all symbol lookups fixes three dlsym issues:

- st_shndx of STT_TLS symbols were not checked and thus an undefined
  tls symbol reference could be incorrectly treated as a definition
  (the sysv hash lookup returns undefined symbols, gnu does not, so should
  be rare in practice).

- symbol binding was not checked so a hidden symbol may be returned
  (in principle STB_LOCAL symbols may appear in the dynamic symbol table
  for hidden symbols, but linkers most likely don't produce it).

- mips specific behaviour was not applied (ARCH_SYM_REJECT_UND) so
  undefined symbols may be returned on mips.

always_inline is used to avoid relocation performance regression, the
code generation for find_sym should not be affected.
2019-08-12 18:25:38 -04:00
Rich Felker 1f060ed2fb ldso: correct condition for local symbol handling in do_relocs
commit 7a9669e977 added use of the
symbol reference as the definition, in place of performing a lookup,
for STT_SECTION symbol references that were first found used in FDPIC.
such references may happen in certain other cases, such as
local-dynamic TLS and with relocation types that require a symbol but
that are being used for non-symbolic purposes, like the powerpc
unaligned address relocations.

in all such cases I'm aware of, the symbol referenced is a section
symbol (STT_SECTION); however, the important semantic property is not
its being a section, but rather its binding local (STB_LOCAL). check
the latter instead of the former for greater generality and semantic
correctness.
2019-08-12 18:19:38 -04:00
Samuel Holland 08869deb7e add support for powerpc/powerpc64 unaligned relocations
R_PPC_UADDR32 (R_PPC64_UADDR64) has the same meaning as R_PPC_ADDR32
(R_PPC64_ADDR64), except that its address need not be aligned. For
powerpc64, BFD ld(1) will automatically convert between ADDR<->UADDR
relocations when the address is/isn't at its native alignment. This
will happen if, for example, there is a pointer in a packed struct.

gold and lld do not currently generate R_PPC64_UADDR64, but pass
through misaligned R_PPC64_ADDR64 relocations from object files,
possibly relaxing them to misaligned R_PPC64_RELATIVE. In both cases
(relaxed or not) this violates the PSABI, which defines the relevant
field type as "a 64-bit field occupying 8 bytes, the alignment of
which is 8 bytes unless otherwise specified."

All three linkers violate the PSABI on 32-bit powerpc, where the only
difference is that the field is 32 bits wide, aligned to 4 bytes.

Currently musl fails to load executables linked by BFD ld containing
R_PPC64_UADDR64, with the error "unsupported relocation type 43".
This change provides compatibility with BFD ld on powerpc64, and any
static linker on either architecture that starts following the PSABI
more closely.
2019-08-11 17:43:57 -04:00
Rich Felker 71af530987 ldso: remove redundant runtime checks in static TLS logic
as a result of commit ffab43602b,
static_tls_cnt is now valid during relocations at program startup, so
it's no longer necessary to condition the check against static_tls_cnt
on this being a runtime (dlopen) relocation.
2019-08-11 11:57:38 -04:00
Rich Felker ffab43602b ldso: fix calloc misuse allocating initial tls
this is analogous to commit 2f1f51ae7b,
and should have been caught at the same time since it was right next
to the code moved in that commit. between final stage 3 reloc_all and
the jump to the main program's entry point, it is not valid to call
any functions which may be interposed by the application; doing so
results in execution of application code before ctors have run, and on
fdpic archs, before the main program's fdpic self-fixups have taken
place, which will produce runaway wrong execution.
2019-08-11 11:48:06 -04:00
Rich Felker 9b83182069 fix inadvertent use of uninitialized variable in dladdr
commit c8b49b2fbc introduced code that
checked bestsym to determine whether a matching symbol was found, but
bestsym is uninitialized if not. instead use best, consistent with use
in the rest of the function.

simplified from bug report and patch by Cheng Liu.
2019-07-06 17:47:43 -04:00
Rich Felker 54b7564b72 remove unnecessary and problematic _Noreturn from crt/ldso startup
after commit a48ccc159a removed the use
of _Noreturn on the stage3_func type (which only worked due to it
being defined to the "GNU C" attribute in C99 mode), GCC could no
longer assume that the ends of __dls2 and __dls2b are unreachable, and
produced a warning that a function marked _Noreturn returns.

also, since commit 4390383b32, the
_Noreturn declaration for __libc_start_main in crt1/rcrt1 has been not
only inconsistent with the definition, but wrong. formally,
__libc_start_main does return, via a (hopefully) tail call to a helper
function after the barrier. incorrect usage of _Noreturn in the
declaration was probably formal UB.

the _Noreturn specifiers were not useful in any of these places, so
remove them all. now, the only remaining usage of _Noreturn is in
public interfaces where _Noreturn is part of their contract.
2019-06-25 19:05:40 -04:00
Szabolcs Nagy a60b9e0686 fix tls offsets when p_vaddr%p_align != 0 on TLS_ABOVE_TP targets
currently the bfd linker does not seem to create tls segments where
p_vaddr%p_align != 0, but this is valid in ELF and then the runtime
computed tls offset must satisfy

  offset%p_align == (base+p_vaddr)%p_align

and in case of local exec tls (main executable) the smallest such
offset must be used (otherwise it is incompatible with the offset
computed by the static linker). the !TLS_ABOVE_TP case is handled
correctly (the offset is negative then in the formula).

the ldso code for TLS_ABOVE_TP is changed so the static tls offset
of each module satisfies the formula.
2019-05-16 21:48:39 -04:00
Szabolcs Nagy 6104dae908 fix static tls offsets of shared libs on TLS_ABOVE_TP targets
tls_offset should always point to the end of the allocated static tls
area, but this was not handled correctly on "tls variant 1" targets
in the dynamic linker:

after application tls was allocated, tls_offset was aligned up,
potentially wasting tls space. (alignment may be needed at the
begining of the tls area, not at the end, but that will be fixed
separately as it is unlikely to affect real binaries.)

when static tls was allocated for a shared library, tls_offset was
only updated with the size of the tls segment which does not include
alignment gaps, which can easily happen if the tls size update for
one library leaves tls_offset misaligned for the next one. this can
cause oob access in __copy_tls or arbitrary breakage at tls access.
(the issue was observed on aarch64 with rust binaries)
2019-05-16 20:12:56 -04:00
Fangrui Song f450c150d3 remove unused struct dso members from dynlink.c
maintainer's note: commit 9d44b6460a
removed their use.
2019-05-12 09:51:45 -04:00
Rich Felker 22e5bbd0de overhaul i386 syscall mechanism not to depend on external asm source
this is the first part of a series of patches intended to make
__syscall fully self-contained in the object file produced using
syscall.h, which will make it possible for crt1 code to perform
syscalls.

the (confusingly named) i386 __vsyscall mechanism, which this commit
removes, was introduced before the presence of a valid thread pointer
was mandatory; back then the thread pointer was setup lazily only if
threads were used. the intent was to be able to perform syscalls using
the kernel's fast entry point in the VDSO, which can use the sysenter
(Intel) or syscall (AMD) instruction instead of int $128, but without
inlining an access to the __syscall global at the point of each
syscall, which would incur a significant size cost from PIC setup
everywhere. the mechanism also shuffled registers/calling convention
around to avoid spills of call-saved registers, and to avoid
allocating ebx or ebp via asm constraints, since there are plenty of
broken-but-supported compiler versions which are incapable of
allocating ebx with -fPIC or ebp with -fno-omit-frame-pointer.

the new mechanism preserves the properties of avoiding spills and
avoiding allocation of ebx/ebp in constraints, but does it inline,
using some fairly simple register shuffling, and uses a field of the
thread structure rather than global data for the vdso-provided syscall
code address.

for now, the external __syscall function is refactored not to use the
old __vsyscall so it can be kept, but the intent is to remove it too.
2019-04-10 17:10:36 -04:00
Ilya Matveychikov 7784680072 fix the use of syscall result in dl_mmap 2019-04-06 09:38:49 -04:00
Ray 086a12b920 delete a redundant if in dynamic linker ctor execution loop 2019-04-02 10:36:49 -04:00
Rich Felker 50cd02386b fix invalid-/double-/use-after-free in new dlopen ctor execution
this affected the error path where dlopen successfully found and
loaded the requested dso and all its dependencies, but failed to
resolve one or more relocations, causing the operation to fail after
storage for the ctor queue was allocated.

commit 188759bbee wrongly put the free
for the ctor_queue array in the error path inside a loop over each
loaded dso that needed to be backed-out, rather than just doing it
once. in addition, the exit path also observed the ctor_queue pointer
still being nonzero, and would attempt to call ctors on the backed-out
dsos unless the double-free crashed the process first.
2019-03-10 13:16:59 -04:00
Rich Felker 43e7efb465 avoid malloc of ctor queue for programs with no external deps
together with the previous two commits, this completes restoration of
the property that dynamic-linked apps with no external deps and no tls
have no failure paths before entry.
2019-03-03 13:24:23 -05:00
Rich Felker f034f145bd avoid malloc of deps arrays for ldso and vdso
neither has or can have any dependencies, but since commit
4035556907, gratuitous zero-length deps
arrays were being allocated for them. use a dummy array instead.
2019-03-03 12:45:23 -05:00