diff --git a/0001-Extend-struct-r_debug-to-support-multiple-namespaces.patch b/0001-Extend-struct-r_debug-to-support-multiple-namespaces.patch new file mode 100644 index 0000000000000000000000000000000000000000..c41ae2c1300b312c87cfe986ee54d489a8501cd5 --- /dev/null +++ b/0001-Extend-struct-r_debug-to-support-multiple-namespaces.patch @@ -0,0 +1,624 @@ +From a93d9e03a31ec14405cb3a09aa95413b67067380 Mon Sep 17 00:00:00 2001 +From: "H.J. Lu" +Date: Tue, 17 Aug 2021 19:35:48 -0700 +Subject: [PATCH] Extend struct r_debug to support multiple namespaces [BZ + #15971] + +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 +Signed-off-by: wuxu_wu +--- + NEWS | 11 ++++- + csu/Makefile | 3 ++ + csu/rtld-sizes.sym | 6 +++ + elf/Makefile | 7 ++- + elf/dl-close.c | 2 +- + elf/dl-debug-symbols.S | 36 +++++++++++++++ + elf/dl-debug.c | 81 +++++++++++++++++++++++++-------- + elf/dl-load.c | 2 +- + elf/dl-open.c | 10 ++-- + elf/dl-reloc-static-pie.c | 2 +- + elf/link.h | 35 ++++++++++---- + elf/rtld-debugger-interface.txt | 15 ++++++ + elf/rtld.c | 4 +- + elf/tst-dlmopen4.c | 72 +++++++++++++++++++++++++++++ + include/link.h | 4 ++ + sysdeps/generic/ldsodefs.h | 12 +++-- + 16 files changed, 257 insertions(+), 45 deletions(-) + create mode 100644 csu/rtld-sizes.sym + create mode 100644 elf/dl-debug-symbols.S + create mode 100644 elf/tst-dlmopen4.c + +diff --git a/NEWS b/NEWS +index 838381f562..3e3c074238 100644 +--- a/NEWS ++++ b/NEWS +@@ -9,6 +9,9 @@ Version 2.35 + + Major new features: + ++* Bump r_version in the debugger interface to 2 and add a new field, ++ r_next, support multiple namespaces. ++ + * Support for the C.UTF-8 locale has been added to glibc. The locale + supports full code-point sorting for all valid Unicode code points. A + limitation in the framework for fnmatch, regexec, and regcomp requires +@@ -28,7 +31,13 @@ Major new features: + + Deprecated and removed features, and other changes affecting compatibility: + +- [Add deprecations, removals and changes affecting compatibility here] ++* The r_version update in the debugger interface makes the glibc binary ++ incompatible with GDB binaries built without the following commits: ++ ++ c0154a4a21a gdb: Don't assume r_ldsomap when r_version > 1 on Linux ++ 4eb629d50d4 gdbserver: Check r_version < 1 for Linux debugger interface ++ ++ when audit modules or dlmopen are used. + + Changes to build and runtime requirements: + +diff --git a/csu/Makefile b/csu/Makefile +index 3054329cea..e2390e4a7d 100644 +--- a/csu/Makefile ++++ b/csu/Makefile +@@ -88,6 +88,9 @@ endif + before-compile += $(objpfx)abi-tag.h + generated += abi-tag.h + ++# Put it here to generate it earlier. ++gen-as-const-headers += rtld-sizes.sym ++ + # These are the special initializer/finalizer files. They are always the + # first and last file in the link. crti.o ... crtn.o define the global + # "functions" _init and _fini to run the .init and .fini sections. +diff --git a/csu/rtld-sizes.sym b/csu/rtld-sizes.sym +new file mode 100644 +index 0000000000..13924d5efd +--- /dev/null ++++ b/csu/rtld-sizes.sym +@@ -0,0 +1,6 @@ ++#include ++ ++-- ++R_DEBUG_SIZE sizeof (struct r_debug) ++R_DEBUG_EXTENDED_SIZE sizeof (struct r_debug_extended) ++R_DEBUG_EXTENDED_ALIGN __alignof (struct r_debug_extended) +diff --git a/elf/Makefile b/elf/Makefile +index 9f3fadc37e..835b85bd7c 100644 +--- a/elf/Makefile ++++ b/elf/Makefile +@@ -35,7 +35,8 @@ dl-routines = $(addprefix dl-,load lookup object reloc deps \ + execstack open close trampoline \ + exception sort-maps lookup-direct \ + call-libc-early-init write \ +- thread_gscope_wait tls_init_tp) ++ thread_gscope_wait tls_init_tp \ ++ debug-symbols) + ifeq (yes,$(use-ldconfig)) + dl-routines += dl-cache + endif +@@ -203,7 +204,7 @@ tests += restest1 preloadtest loadfail multiload origtest resolvfail \ + tst-tls16 tst-tls17 tst-tls18 tst-tls19 tst-tls-dlinfo \ + tst-align tst-align2 \ + tst-dlmodcount tst-dlopenrpath tst-deep1 \ +- tst-dlmopen1 tst-dlmopen3 \ ++ tst-dlmopen1 tst-dlmopen3 tst-dlmopen4 \ + unload3 unload4 unload5 unload6 unload7 unload8 tst-global1 order2 \ + tst-audit1 tst-audit2 tst-audit8 tst-audit9 \ + tst-addr1 tst-thrlock \ +@@ -1244,6 +1245,8 @@ $(objpfx)tst-dlmopen2.out: $(objpfx)tst-dlmopen1mod.so + + $(objpfx)tst-dlmopen3.out: $(objpfx)tst-dlmopen1mod.so + ++$(objpfx)tst-dlmopen4.out: $(objpfx)tst-dlmopen1mod.so ++ + $(objpfx)tst-audit1.out: $(objpfx)tst-auditmod1.so + tst-audit1-ENV = LD_AUDIT=$(objpfx)tst-auditmod1.so + +diff --git a/elf/dl-close.c b/elf/dl-close.c +index f39001cab9..93ff5c96e9 100644 +--- a/elf/dl-close.c ++++ b/elf/dl-close.c +@@ -500,7 +500,7 @@ _dl_close_worker (struct link_map *map, bool force) + #endif + + /* Notify the debugger we are about to remove some loaded objects. */ +- struct r_debug *r = _dl_debug_initialize (0, nsid); ++ struct r_debug *r = _dl_debug_update (nsid); + r->r_state = RT_DELETE; + _dl_debug_state (); + LIBC_PROBE (unmap_start, 2, nsid, r); +diff --git a/elf/dl-debug-symbols.S b/elf/dl-debug-symbols.S +new file mode 100644 +index 0000000000..b7e9f5d947 +--- /dev/null ++++ b/elf/dl-debug-symbols.S +@@ -0,0 +1,36 @@ ++/* Define symbols used to communicate dynamic linker state to the ++ debugger at runtime. ++ Copyright (C) 2021 Free Software Foundation, Inc. ++ This file is part of the GNU C Library. ++ ++ The GNU C Library is free software; you can redistribute it and/or ++ modify it under the terms of the GNU Lesser General Public ++ License as published by the Free Software Foundation; either ++ version 2.1 of the License, or (at your option) any later version. ++ ++ The GNU C Library is distributed in the hope that it will be useful, ++ but WITHOUT ANY WARRANTY; without even the implied warranty of ++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU ++ Lesser General Public License for more details. ++ ++ You should have received a copy of the GNU Lesser General Public ++ License along with the GNU C Library; if not, see ++ . */ ++ ++#include ++ ++/* Define 2 symbols, _r_debug_extended and _r_debug, which is an alias ++ of _r_debug_extended, but with the size of struct r_debug. */ ++ ++ .globl _r_debug ++ .type _r_debug, %object ++ .size _r_debug, R_DEBUG_SIZE ++ .hidden _r_debug_extended ++ .globl _r_debug_extended ++ .type _r_debug_extended, %object ++ .size _r_debug_extended, R_DEBUG_EXTENDED_SIZE ++ .section .bss ++ .balign R_DEBUG_EXTENDED_ALIGN ++_r_debug: ++_r_debug_extended: ++ .zero R_DEBUG_EXTENDED_SIZE +diff --git a/elf/dl-debug.c b/elf/dl-debug.c +index 2cd5f09753..f637d4bb8d 100644 +--- a/elf/dl-debug.c ++++ b/elf/dl-debug.c +@@ -30,37 +30,80 @@ extern const int verify_link_map_members[(VERIFY_MEMBER (l_addr) + && VERIFY_MEMBER (l_prev)) + ? 1 : -1]; + +-/* This structure communicates dl state to the debugger. The debugger +- normally finds it via the DT_DEBUG entry in the dynamic section, but in +- a statically-linked program there is no dynamic section for the debugger +- to examine and it looks for this particular symbol name. */ +-struct r_debug _r_debug; ++/* Update the `r_map' member and return the address of `struct r_debug' ++ of the namespace NS. */ + ++struct r_debug * ++_dl_debug_update (Lmid_t ns) ++{ ++ struct r_debug_extended *r; ++ if (ns == LM_ID_BASE) ++ r = &_r_debug_extended; ++ else ++ r = &GL(dl_ns)[ns]._ns_debug; ++ if (r->base.r_map == NULL) ++ atomic_store_release (&r->base.r_map, ++ (void *) GL(dl_ns)[ns]._ns_loaded); ++ return &r->base; ++} + +-/* Initialize _r_debug if it has not already been done. The argument is +- the run-time load address of the dynamic linker, to be put in +- _r_debug.r_ldbase. Returns the address of _r_debug. */ ++/* Initialize _r_debug_extended for the namespace NS. LDBASE is the ++ run-time load address of the dynamic linker, to be put in ++ _r_debug_extended.r_ldbase. Return the address of _r_debug. */ + + struct r_debug * + _dl_debug_initialize (ElfW(Addr) ldbase, Lmid_t ns) + { +- struct r_debug *r; ++ struct r_debug_extended *r, **pp = NULL; + + if (ns == LM_ID_BASE) +- r = &_r_debug; +- else +- r = &GL(dl_ns)[ns]._ns_debug; ++ { ++ r = &_r_debug_extended; ++ /* Initialize r_version to 1. */ ++ if (_r_debug_extended.base.r_version == 0) ++ _r_debug_extended.base.r_version = 1; ++ } ++ else if (DL_NNS > 1) ++ { ++ r = &GL(dl_ns)[ns]._ns_debug; ++ if (r->base.r_brk == 0) ++ { ++ /* Add the new namespace to the linked list. After a namespace ++ is initialized, r_brk becomes non-zero. A namespace becomes ++ empty (r_map == NULL) when it is unused. But it is never ++ removed from the linked list. */ ++ struct r_debug_extended *p; ++ for (pp = &_r_debug_extended.r_next; ++ (p = *pp) != NULL; ++ pp = &p->r_next) ++ ; ++ ++ r->base.r_version = 2; ++ } ++ } ++ ++ if (r->base.r_brk == 0) ++ { ++ /* Tell the debugger where to find the map of loaded objects. ++ This function is called from dlopen. Initialize the namespace ++ only once. */ ++ r->base.r_ldbase = ldbase ?: _r_debug_extended.base.r_ldbase; ++ r->base.r_brk = (ElfW(Addr)) &_dl_debug_state; ++ r->r_next = NULL; ++ } ++ ++ if (r->base.r_map == NULL) ++ atomic_store_release (&r->base.r_map, ++ (void *) GL(dl_ns)[ns]._ns_loaded); + +- if (r->r_map == NULL || ldbase != 0) ++ if (pp != NULL) + { +- /* Tell the debugger where to find the map of loaded objects. */ +- r->r_version = 1 /* R_DEBUG_VERSION XXX */; +- r->r_ldbase = ldbase ?: _r_debug.r_ldbase; +- r->r_map = (void *) GL(dl_ns)[ns]._ns_loaded; +- r->r_brk = (ElfW(Addr)) &_dl_debug_state; ++ atomic_store_release (pp, r); ++ /* Bump r_version to 2 for the new namespace. */ ++ atomic_store_release (&_r_debug_extended.base.r_version, 2); + } + +- return r; ++ return &r->base; + } + + +diff --git a/elf/dl-load.c b/elf/dl-load.c +index 650e4edc35..39e0d074b4 100644 +--- a/elf/dl-load.c ++++ b/elf/dl-load.c +@@ -949,7 +949,7 @@ _dl_map_object_from_fd (const char *name, const char *origname, int fd, + /* Initialize to keep the compiler happy. */ + const char *errstring = NULL; + int errval = 0; +- struct r_debug *r = _dl_debug_initialize (0, nsid); ++ struct r_debug *r = _dl_debug_update (nsid); + bool make_consistent = false; + + /* Get file information. To match the kernel behavior, do not fill +diff --git a/elf/dl-open.c b/elf/dl-open.c +index ec386626f9..a25443f6d1 100644 +--- a/elf/dl-open.c ++++ b/elf/dl-open.c +@@ -574,7 +574,7 @@ dl_open_worker (void *a) + if ((mode & RTLD_GLOBAL) && new->l_global == 0) + add_to_global_update (new); + +- assert (_dl_debug_initialize (0, args->nsid)->r_state == RT_CONSISTENT); ++ assert (_dl_debug_update (args->nsid)->r_state == RT_CONSISTENT); + + return; + } +@@ -630,7 +630,7 @@ dl_open_worker (void *a) + #endif + + /* Notify the debugger all new objects are now ready to go. */ +- struct r_debug *r = _dl_debug_initialize (0, args->nsid); ++ struct r_debug *r = _dl_debug_update (args->nsid); + r->r_state = RT_CONSISTENT; + _dl_debug_state (); + LIBC_PROBE (map_complete, 3, args->nsid, r, new); +@@ -830,7 +830,7 @@ no more namespaces available for dlmopen()")); + ++GL(dl_nns); + } + +- _dl_debug_initialize (0, nsid)->r_state = RT_CONSISTENT; ++ _dl_debug_update (nsid)->r_state = RT_CONSISTENT; + } + /* Never allow loading a DSO in a namespace which is empty. Such + direct placements is only causing problems. Also don't allow +@@ -899,7 +899,7 @@ no more namespaces available for dlmopen()")); + the flag here. */ + } + +- assert (_dl_debug_initialize (0, args.nsid)->r_state == RT_CONSISTENT); ++ assert (_dl_debug_update (args.nsid)->r_state == RT_CONSISTENT); + + /* Release the lock. */ + __rtld_lock_unlock_recursive (GL(dl_load_lock)); +@@ -908,7 +908,7 @@ no more namespaces available for dlmopen()")); + _dl_signal_exception (errcode, &exception, NULL); + } + +- assert (_dl_debug_initialize (0, args.nsid)->r_state == RT_CONSISTENT); ++ assert (_dl_debug_update (args.nsid)->r_state == RT_CONSISTENT); + + /* Release the lock. */ + __rtld_lock_unlock_recursive (GL(dl_load_lock)); +diff --git a/elf/dl-reloc-static-pie.c b/elf/dl-reloc-static-pie.c +index d5bd2f31e9..289651b341 100644 +--- a/elf/dl-reloc-static-pie.c ++++ b/elf/dl-reloc-static-pie.c +@@ -51,7 +51,7 @@ _dl_relocate_static_pie (void) + ELF_DYNAMIC_RELOCATE (main_map, 0, 0, 0); + main_map->l_relocated = 1; + +- /* Initialize _r_debug. */ ++ /* Initialize _r_debug_extended. */ + struct r_debug *r = _dl_debug_initialize (0, LM_ID_BASE); + r->r_state = RT_CONSISTENT; + +diff --git a/elf/link.h b/elf/link.h +index ff3a85c847..200d40c9c6 100644 +--- a/elf/link.h ++++ b/elf/link.h +@@ -34,14 +34,13 @@ + #include /* Defines __ELF_NATIVE_CLASS. */ + #include + +-/* Rendezvous structure used by the run-time dynamic linker to communicate +- details of shared object loading to the debugger. If the executable's +- dynamic section has a DT_DEBUG element, the run-time linker sets that +- element's value to the address where this structure can be found. */ ++/* The legacy rendezvous structure used by the run-time dynamic linker to ++ communicate details of shared object loading to the debugger. */ + + struct r_debug + { +- int r_version; /* Version number for this protocol. */ ++ /* Version number for this protocol. It should be greater than 0. */ ++ int r_version; + + struct link_map *r_map; /* Head of the chain of loaded objects. */ + +@@ -63,16 +62,34 @@ struct r_debug + ElfW(Addr) r_ldbase; /* Base address the linker is loaded at. */ + }; + +-/* This is the instance of that structure used by the dynamic linker. */ ++/* This is the symbol of that structure provided by the dynamic linker. */ + extern struct r_debug _r_debug; + ++/* The extended rendezvous structure used by the run-time dynamic linker ++ to communicate details of shared object loading to the debugger. If ++ the executable's dynamic section has a DT_DEBUG element, the run-time ++ linker sets that element's value to the address where this structure ++ can be found. */ ++ ++struct r_debug_extended ++ { ++ struct r_debug base; ++ ++ /* The following field is added by r_version == 2. */ ++ ++ /* Link to the next r_debug_extended structure. Each r_debug_extended ++ structure represents a different namespace. The first ++ r_debug_extended structure is for the default namespace. */ ++ struct r_debug_extended *r_next; ++ }; ++ + /* This symbol refers to the "dynamic structure" in the `.dynamic' section + of whatever module refers to `_DYNAMIC'. So, to find its own +- `struct r_debug', a program could do: ++ `struct r_debug_extended', a program could do: + for (dyn = _DYNAMIC; dyn->d_tag != DT_NULL; ++dyn) + if (dyn->d_tag == DT_DEBUG) +- r_debug = (struct r_debug *) dyn->d_un.d_ptr; +- */ ++ r_debug_extended = (struct r_debug_extended *) dyn->d_un.d_ptr; ++ */ + extern ElfW(Dyn) _DYNAMIC[]; + + /* Structure describing a loaded shared object. The `l_next' and `l_prev' +diff --git a/elf/rtld-debugger-interface.txt b/elf/rtld-debugger-interface.txt +index 61bc99e4b0..f3476d8308 100644 +--- a/elf/rtld-debugger-interface.txt ++++ b/elf/rtld-debugger-interface.txt +@@ -9,6 +9,9 @@ structure can be found. + + The r_debug structure contains (amongst others) the following fields: + ++ int r_version: ++ Version number for this protocol. It should be greater than 0. ++ + struct link_map *r_map: + A linked list of loaded objects. + +@@ -32,6 +35,18 @@ but there is no way for the debugger to discover whether any of the + objects in the link-map have been relocated or not. + + ++Extension to the r_debug structure ++================================== ++ ++The r_debug_extended structure is an extension of the r_debug interface. ++If r_version is 2, one additional field is available: ++ ++ struct r_debug_extended *r_next; ++ Link to the next r_debug_extended structure. Each r_debug_extended ++ structure represents a different namespace. A namespace is active ++ if its r_map field isn't NULL. The first r_debug_extended structure ++ is for the default namespace. ++ + Probe-based debugger interface + ============================== + +diff --git a/elf/rtld.c b/elf/rtld.c +index 878e6480f4..742c413c48 100644 +--- a/elf/rtld.c ++++ b/elf/rtld.c +@@ -1660,7 +1660,7 @@ dl_main (const ElfW(Phdr) *phdr, + objects. */ + call_init_paths (&state); + +- /* Initialize _r_debug. */ ++ /* Initialize _r_debug_extended. */ + struct r_debug *r = _dl_debug_initialize (GL(dl_rtld_map).l_addr, + LM_ID_BASE); + r->r_state = RT_CONSISTENT; +@@ -2491,7 +2491,7 @@ dl_main (const ElfW(Phdr) *phdr, + + /* Notify the debugger all new objects are now ready to go. We must re-get + the address since by now the variable might be in another object. */ +- r = _dl_debug_initialize (0, LM_ID_BASE); ++ r = _dl_debug_update (LM_ID_BASE); + r->r_state = RT_CONSISTENT; + _dl_debug_state (); + LIBC_PROBE (init_complete, 2, LM_ID_BASE, r); +diff --git a/elf/tst-dlmopen4.c b/elf/tst-dlmopen4.c +new file mode 100644 +index 0000000000..3fe150e50b +--- /dev/null ++++ b/elf/tst-dlmopen4.c +@@ -0,0 +1,72 @@ ++/* Test struct r_debug_extended via DT_DEBUG. ++ Copyright (C) 2021 Free Software Foundation, Inc. ++ This file is part of the GNU C Library. ++ ++ The GNU C Library is free software; you can redistribute it and/or ++ modify it under the terms of the GNU Lesser General Public ++ License as published by the Free Software Foundation; either ++ version 2.1 of the License, or (at your option) any later version. ++ ++ The GNU C Library is distributed in the hope that it will be useful, ++ but WITHOUT ANY WARRANTY; without even the implied warranty of ++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU ++ Lesser General Public License for more details. ++ ++ You should have received a copy of the GNU Lesser General Public ++ License along with the GNU C Library; if not, see ++ . */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#ifndef ELF_MACHINE_GET_R_DEBUG ++# define ELF_MACHINE_GET_R_DEBUG(d) \ ++ (__extension__ ({ \ ++ struct r_debug_extended *debug; \ ++ if ((d)->d_tag == DT_DEBUG) \ ++ debug = (struct r_debug_extended *) (d)->d_un.d_ptr; \ ++ else \ ++ debug = NULL; \ ++ debug; })) ++#endif ++ ++static int ++do_test (void) ++{ ++ ElfW(Dyn) *d; ++ struct r_debug_extended *debug = NULL; ++ ++ for (d = _DYNAMIC; d->d_tag != DT_NULL; ++d) ++ { ++ debug = ELF_MACHINE_GET_R_DEBUG (d); ++ if (debug != NULL) ++ break; ++ } ++ ++ TEST_VERIFY_EXIT (debug != NULL); ++ TEST_COMPARE (debug->base.r_version, 1); ++ TEST_VERIFY_EXIT (debug->r_next == NULL); ++ ++ void *h = xdlmopen (LM_ID_NEWLM, "$ORIGIN/tst-dlmopen1mod.so", ++ RTLD_LAZY); ++ ++ TEST_COMPARE (debug->base.r_version, 2); ++ TEST_VERIFY_EXIT (debug->r_next != NULL); ++ TEST_VERIFY_EXIT (debug->r_next->r_next == NULL); ++ TEST_VERIFY_EXIT (debug->r_next->base.r_map != NULL); ++ TEST_VERIFY_EXIT (debug->r_next->base.r_map->l_name != NULL); ++ const char *name = basename (debug->r_next->base.r_map->l_name); ++ TEST_COMPARE_STRING (name, "tst-dlmopen1mod.so"); ++ ++ xdlclose (h); ++ ++ return 0; ++} ++ ++#include +diff --git a/include/link.h b/include/link.h +index 4af16cb596..7b8250db36 100644 +--- a/include/link.h ++++ b/include/link.h +@@ -353,6 +353,10 @@ struct auditstate + }; + + ++/* This is the hidden instance of struct r_debug_extended used by the ++ dynamic linker. */ ++extern struct r_debug_extended _r_debug_extended attribute_hidden; ++ + #if __ELF_NATIVE_CLASS == 32 + # define symbind symbind32 + #elif __ELF_NATIVE_CLASS == 64 +diff --git a/sysdeps/generic/ldsodefs.h b/sysdeps/generic/ldsodefs.h +index fd67871f4b..6e50fcd7cd 100644 +--- a/sysdeps/generic/ldsodefs.h ++++ b/sysdeps/generic/ldsodefs.h +@@ -355,7 +355,7 @@ struct rtld_global + void (*free) (void *); + } _ns_unique_sym_table; + /* Keep track of changes to each namespace' list. */ +- struct r_debug _ns_debug; ++ struct r_debug_extended _ns_debug; + } _dl_ns[DL_NNS]; + /* One higher than index of last used namespace. */ + EXTERN size_t _dl_nns; +@@ -1099,12 +1099,16 @@ extern void _dl_sort_maps (struct link_map **maps, unsigned int nmaps, + extern void _dl_debug_state (void); + rtld_hidden_proto (_dl_debug_state) + +-/* Initialize `struct r_debug' if it has not already been done. The +- argument is the run-time load address of the dynamic linker, to be put +- in the `r_ldbase' member. Returns the address of the structure. */ ++/* Initialize `struct r_debug_extended' for the namespace NS. LDBASE ++ is the run-time load address of the dynamic linker, to be put in the ++ `r_ldbase' member. Return the address of the structure. */ + extern struct r_debug *_dl_debug_initialize (ElfW(Addr) ldbase, Lmid_t ns) + attribute_hidden; + ++/* Update the `r_map' member and return the address of `struct r_debug' ++ of the namespace NS. */ ++extern struct r_debug *_dl_debug_update (Lmid_t ns) attribute_hidden; ++ + /* Initialize the basic data structure for the search paths. SOURCE + is either "LD_LIBRARY_PATH" or "--library-path". + GLIBC_HWCAPS_PREPEND adds additional glibc-hwcaps subdirectories to +-- +2.25.1 + diff --git a/glibc.spec b/glibc.spec index a8b1ad52c0af178a356dfce229e6d86e0fb70bba..5f7f045259079a893e9f7aaea0b90657273f0534 100644 --- a/glibc.spec +++ b/glibc.spec @@ -128,6 +128,7 @@ Patch41: nptl-Avoid-setxid-deadlock-with-blocked-signals-in-t.patch Patch42: nptl-pthread_kill-must-send-signals-to-a-specific-th.patch Patch43: iconvconfig-Fix-behaviour-with-prefix-BZ-28199.patch Patch44: gconv-Do-not-emit-spurious-NUL-character-in-ISO-2022.patch +Patch45: 0001-Extend-struct-r_debug-to-support-multiple-namespaces.patch #Patch9000: turn-REP_STOSB_THRESHOLD-from-2k-to-1M.patch Patch9001: delete-no-hard-link-to-avoid-all_language-package-to.patch @@ -1317,6 +1318,10 @@ fi %endif %changelog +* Thu Nov 12 2021 wuxu - 2.34-24 +- elf: Extend struct r_debug to support multiple namespaces + uplink: https://sourceware.org/bugzilla/show_bug.cgi?id=28236 + * Wed Nov 10 2021 Qingqing Li - 2.34-23 - gconv: Do not emit spurious NUL character in ISO-2022-JP-3, this also fix CVE-2021-43396.