076f82
commit b19de59d620b3a9e6adf937f322f4281b67fc712
076f82
Author: Fangrui Song <maskray@google.com>
076f82
Date:   Thu Oct 7 11:55:02 2021 -0700
076f82
076f82
    elf: Avoid nested functions in the loader [BZ #27220]
076f82
    
076f82
    dynamic-link.h is included more than once in some elf/ files (rtld.c,
076f82
    dl-conflict.c, dl-reloc.c, dl-reloc-static-pie.c) and uses GCC nested
076f82
    functions. This harms readability and the nested functions usage
076f82
    is the biggest obstacle prevents Clang build (Clang doesn't support GCC
076f82
    nested functions).
076f82
    
076f82
    The key idea for unnesting is to add extra parameters (struct link_map
076f82
    *and struct r_scope_elm *[]) to RESOLVE_MAP,
076f82
    ELF_MACHINE_BEFORE_RTLD_RELOC, ELF_DYNAMIC_RELOCATE, elf_machine_rel[a],
076f82
    elf_machine_lazy_rel, and elf_machine_runtime_setup. (This is inspired
076f82
    by Stan Shebs' ppc64/x86-64 implementation in the
076f82
    google/grte/v5-2.27/master which uses mixed extra parameters and static
076f82
    variables.)
076f82
    
076f82
    Future simplification:
076f82
    * If mips elf_machine_runtime_setup no longer needs RESOLVE_GOTSYM,
076f82
      elf_machine_runtime_setup can drop the `scope` parameter.
076f82
    * If TLSDESC no longer need to be in elf_machine_lazy_rel,
076f82
      elf_machine_lazy_rel can drop the `scope` parameter.
076f82
    
076f82
    Tested on aarch64, i386, x86-64, powerpc64le, powerpc64, powerpc32,
076f82
    sparc64, sparcv9, s390x, s390, hppa, ia64, armhf, alpha, and mips64.
076f82
    In addition, tested build-many-glibcs.py with {arc,csky,microblaze,nios2}-linux-gnu
076f82
    and riscv64-linux-gnu-rv64imafdc-lp64d.
076f82
    
076f82
    Reviewed-by: Adhemerval Zanella  <adhemerval.zanella@linaro.org>
076f82
    (cherry picked from commit 490e6c62aa31a8aa5c4a059f6e646ede121edf0a)
076f82
076f82
diff --git a/elf/dl-conflict.c b/elf/dl-conflict.c
076f82
index 31a2f90770ce2a55..5c8e51d19ae095d6 100644
076f82
--- a/elf/dl-conflict.c
076f82
+++ b/elf/dl-conflict.c
076f82
@@ -27,20 +27,12 @@
076f82
 #include <sys/types.h>
076f82
 #include "dynamic-link.h"
076f82
 
076f82
-void
076f82
-_dl_resolve_conflicts (struct link_map *l, ElfW(Rela) *conflict,
076f82
-		       ElfW(Rela) *conflictend)
076f82
-{
076f82
-#if ! ELF_MACHINE_NO_RELA
076f82
-  if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_RELOC))
076f82
-    _dl_debug_printf ("\nconflict processing: %s\n", DSO_FILENAME (l->l_name));
076f82
-
076f82
-  {
076f82
-    /* Do the conflict relocation of the object and library GOT and other
076f82
-       data.  */
076f82
+/* Used at loading time solely for prelink executable.  It is not called
076f82
+   concurrently so it is be safe to defined as static.  */
076f82
+static struct link_map *resolve_conflict_map __attribute__ ((__unused__));
076f82
 
076f82
     /* This macro is used as a callback from the ELF_DYNAMIC_RELOCATE code.  */
076f82
-#define RESOLVE_MAP(ref, version, flags) (*ref = NULL, NULL)
076f82
+#define RESOLVE_MAP(map, scope, ref, version, flags) (*ref = NULL, NULL)
076f82
 #define RESOLVE(ref, version, flags) (*ref = NULL, 0)
076f82
 #define RESOLVE_CONFLICT_FIND_MAP(map, r_offset) \
076f82
   do {									      \
076f82
@@ -51,12 +43,23 @@ _dl_resolve_conflicts (struct link_map *l, ElfW(Rela) *conflict,
076f82
     (map) = resolve_conflict_map;					      \
076f82
   } while (0)
076f82
 
076f82
+#include "dynamic-link.h"
076f82
+
076f82
+void
076f82
+_dl_resolve_conflicts (struct link_map *l, ElfW(Rela) *conflict,
076f82
+		       ElfW(Rela) *conflictend)
076f82
+{
076f82
+#if ! ELF_MACHINE_NO_RELA
076f82
+  if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_RELOC))
076f82
+    _dl_debug_printf ("\nconflict processing: %s\n", DSO_FILENAME (l->l_name));
076f82
+
076f82
+  {
076f82
+    /* Do the conflict relocation of the object and library GOT and other
076f82
+       data.  */
076f82
+
076f82
     /* Prelinking makes no sense for anything but the main namespace.  */
076f82
     assert (l->l_ns == LM_ID_BASE);
076f82
-    struct link_map *resolve_conflict_map __attribute__ ((__unused__))
076f82
-      = GL(dl_ns)[LM_ID_BASE]._ns_loaded;
076f82
-
076f82
-#include "dynamic-link.h"
076f82
+    resolve_conflict_map = GL(dl_ns)[LM_ID_BASE]._ns_loaded;
076f82
 
076f82
     /* Override these, defined in dynamic-link.h.  */
076f82
 #undef CHECK_STATIC_TLS
076f82
@@ -67,8 +70,8 @@ _dl_resolve_conflicts (struct link_map *l, ElfW(Rela) *conflict,
076f82
     GL(dl_num_cache_relocations) += conflictend - conflict;
076f82
 
076f82
     for (; conflict < conflictend; ++conflict)
076f82
-      elf_machine_rela (l, conflict, NULL, NULL, (void *) conflict->r_offset,
076f82
-			0);
076f82
+      elf_machine_rela (l, NULL, conflict, NULL, NULL,
076f82
+			(void *) conflict->r_offset, 0);
076f82
   }
076f82
 #endif
076f82
 }
076f82
diff --git a/elf/dl-reloc-static-pie.c b/elf/dl-reloc-static-pie.c
076f82
index 2fb02d727654c87d..a52ba8aeb8b573cb 100644
076f82
--- a/elf/dl-reloc-static-pie.c
076f82
+++ b/elf/dl-reloc-static-pie.c
076f82
@@ -19,8 +19,14 @@
076f82
 #if ENABLE_STATIC_PIE
076f82
 /* Mark symbols hidden in static PIE for early self relocation to work.  */
076f82
 # pragma GCC visibility push(hidden)
076f82
+#include <assert.h>
076f82
 #include <unistd.h>
076f82
 #include <ldsodefs.h>
076f82
+
076f82
+#include <dl-machine.h>
076f82
+
076f82
+#define STATIC_PIE_BOOTSTRAP
076f82
+#define RESOLVE_MAP(map, scope, sym, version, flags) map
076f82
 #include "dynamic-link.h"
076f82
 
076f82
 /* Relocate static executable with PIE.  */
076f82
@@ -30,11 +36,6 @@ _dl_relocate_static_pie (void)
076f82
 {
076f82
   struct link_map *main_map = _dl_get_dl_main_map ();
076f82
 
076f82
-# define STATIC_PIE_BOOTSTRAP
076f82
-# define BOOTSTRAP_MAP (main_map)
076f82
-# define RESOLVE_MAP(sym, version, flags) BOOTSTRAP_MAP
076f82
-# include "dynamic-link.h"
076f82
-
076f82
   /* Figure out the run-time load address of static PIE.  */
076f82
   main_map->l_addr = elf_machine_load_address ();
076f82
 
076f82
@@ -53,12 +54,12 @@ _dl_relocate_static_pie (void)
076f82
   elf_get_dynamic_info (main_map);
076f82
 
076f82
 # ifdef ELF_MACHINE_BEFORE_RTLD_RELOC
076f82
-  ELF_MACHINE_BEFORE_RTLD_RELOC (main_map->l_info);
076f82
+  ELF_MACHINE_BEFORE_RTLD_RELOC (main_map, main_map->l_info);
076f82
 # endif
076f82
 
076f82
   /* Relocate ourselves so we can do normal function calls and
076f82
      data access using the global offset table.  */
076f82
-  ELF_DYNAMIC_RELOCATE (main_map, 0, 0, 0);
076f82
+  ELF_DYNAMIC_RELOCATE (main_map, NULL, 0, 0, 0);
076f82
   main_map->l_relocated = 1;
076f82
 
076f82
   /* Initialize _r_debug.  */
076f82
diff --git a/elf/dl-reloc.c b/elf/dl-reloc.c
076f82
index e13a672ade6d7a28..3447de7f3536cd70 100644
076f82
--- a/elf/dl-reloc.c
076f82
+++ b/elf/dl-reloc.c
076f82
@@ -162,6 +162,32 @@ _dl_nothread_init_static_tls (struct link_map *map)
076f82
 }
076f82
 #endif /* !THREAD_GSCOPE_IN_TCB */
076f82
 
076f82
+/* This macro is used as a callback from the ELF_DYNAMIC_RELOCATE code.  */
076f82
+#define RESOLVE_MAP(l, scope, ref, version, r_type)			      \
076f82
+    ((ELFW(ST_BIND) ((*ref)->st_info) != STB_LOCAL			      \
076f82
+      && __glibc_likely (!dl_symbol_visibility_binds_local_p (*ref)))	      \
076f82
+     ? ((__glibc_unlikely ((*ref) == l->l_lookup_cache.sym)		      \
076f82
+	 && elf_machine_type_class (r_type) == l->l_lookup_cache.type_class)  \
076f82
+	? (bump_num_cache_relocations (),				      \
076f82
+	   (*ref) = l->l_lookup_cache.ret,				      \
076f82
+	   l->l_lookup_cache.value)					      \
076f82
+	: ({ lookup_t _lr;						      \
076f82
+	     int _tc = elf_machine_type_class (r_type);			      \
076f82
+	     l->l_lookup_cache.type_class = _tc;			      \
076f82
+	     l->l_lookup_cache.sym = (*ref);				      \
076f82
+	     const struct r_found_version *v = NULL;			      \
076f82
+	     if ((version) != NULL && (version)->hash != 0)		      \
076f82
+	       v = (version);						      \
076f82
+	     _lr = _dl_lookup_symbol_x ((const char *) D_PTR (l, l_info[DT_STRTAB]) + (*ref)->st_name, \
076f82
+					l, (ref), scope, v, _tc,	      \
076f82
+					DL_LOOKUP_ADD_DEPENDENCY	      \
076f82
+					| DL_LOOKUP_FOR_RELOCATE, NULL);      \
076f82
+	     l->l_lookup_cache.ret = (*ref);				      \
076f82
+	     l->l_lookup_cache.value = _lr; }))				      \
076f82
+     : l)
076f82
+
076f82
+#include "dynamic-link.h"
076f82
+
076f82
 void
076f82
 _dl_relocate_object (struct link_map *l, struct r_scope_elem *scope[],
076f82
 		     int reloc_mode, int consider_profiling)
076f82
@@ -243,36 +269,7 @@ _dl_relocate_object (struct link_map *l, struct r_scope_elem *scope[],
076f82
   {
076f82
     /* Do the actual relocation of the object's GOT and other data.  */
076f82
 
076f82
-    /* String table object symbols.  */
076f82
-    const char *strtab = (const void *) D_PTR (l, l_info[DT_STRTAB]);
076f82
-
076f82
-    /* This macro is used as a callback from the ELF_DYNAMIC_RELOCATE code.  */
076f82
-#define RESOLVE_MAP(ref, version, r_type) \
076f82
-    ((ELFW(ST_BIND) ((*ref)->st_info) != STB_LOCAL			      \
076f82
-      && __glibc_likely (!dl_symbol_visibility_binds_local_p (*ref)))	      \
076f82
-     ? ((__builtin_expect ((*ref) == l->l_lookup_cache.sym, 0)		      \
076f82
-	 && elf_machine_type_class (r_type) == l->l_lookup_cache.type_class)  \
076f82
-	? (bump_num_cache_relocations (),				      \
076f82
-	   (*ref) = l->l_lookup_cache.ret,				      \
076f82
-	   l->l_lookup_cache.value)					      \
076f82
-	: ({ lookup_t _lr;						      \
076f82
-	     int _tc = elf_machine_type_class (r_type);			      \
076f82
-	     l->l_lookup_cache.type_class = _tc;			      \
076f82
-	     l->l_lookup_cache.sym = (*ref);				      \
076f82
-	     const struct r_found_version *v = NULL;			      \
076f82
-	     if ((version) != NULL && (version)->hash != 0)		      \
076f82
-	       v = (version);						      \
076f82
-	     _lr = _dl_lookup_symbol_x (strtab + (*ref)->st_name, l, (ref),   \
076f82
-					scope, v, _tc,			      \
076f82
-					DL_LOOKUP_ADD_DEPENDENCY	      \
076f82
-					| DL_LOOKUP_FOR_RELOCATE, NULL);      \
076f82
-	     l->l_lookup_cache.ret = (*ref);				      \
076f82
-	     l->l_lookup_cache.value = _lr; }))				      \
076f82
-     : l)
076f82
-
076f82
-#include "dynamic-link.h"
076f82
-
076f82
-    ELF_DYNAMIC_RELOCATE (l, lazy, consider_profiling, skip_ifunc);
076f82
+    ELF_DYNAMIC_RELOCATE (l, scope, lazy, consider_profiling, skip_ifunc);
076f82
 
076f82
 #ifndef PROF
076f82
     if (__glibc_unlikely (consider_profiling)
076f82
diff --git a/elf/do-rel.h b/elf/do-rel.h
076f82
index 321ac2b359c1028c..f441b749190c2641 100644
076f82
--- a/elf/do-rel.h
076f82
+++ b/elf/do-rel.h
076f82
@@ -37,8 +37,8 @@
076f82
    relocations; they should be set up to call _dl_runtime_resolve, rather
076f82
    than fully resolved now.  */
076f82
 
076f82
-auto inline void __attribute__ ((always_inline))
076f82
-elf_dynamic_do_Rel (struct link_map *map,
076f82
+static inline void __attribute__ ((always_inline))
076f82
+elf_dynamic_do_Rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		    ElfW(Addr) reladdr, ElfW(Addr) relsize,
076f82
 		    __typeof (((ElfW(Dyn) *) 0)->d_un.d_val) nrelative,
076f82
 		    int lazy, int skip_ifunc)
076f82
@@ -68,13 +68,13 @@ elf_dynamic_do_Rel (struct link_map *map,
076f82
 	  }
076f82
 	else
076f82
 # endif
076f82
-	  elf_machine_lazy_rel (map, l_addr, r, skip_ifunc);
076f82
+	  elf_machine_lazy_rel (map, scope, l_addr, r, skip_ifunc);
076f82
 
076f82
 # ifdef ELF_MACHINE_IRELATIVE
076f82
       if (r2 != NULL)
076f82
 	for (; r2 <= end2; ++r2)
076f82
 	  if (ELFW(R_TYPE) (r2->r_info) == ELF_MACHINE_IRELATIVE)
076f82
-	    elf_machine_lazy_rel (map, l_addr, r2, skip_ifunc);
076f82
+	    elf_machine_lazy_rel (map, scope, l_addr, r2, skip_ifunc);
076f82
 # endif
076f82
     }
076f82
   else
076f82
@@ -134,7 +134,7 @@ elf_dynamic_do_Rel (struct link_map *map,
076f82
 #endif
076f82
 
076f82
 	      ElfW(Half) ndx = version[ELFW(R_SYM) (r->r_info)] & 0x7fff;
076f82
-	      elf_machine_rel (map, r, &symtab[ELFW(R_SYM) (r->r_info)],
076f82
+	      elf_machine_rel (map, scope, r, &symtab[ELFW(R_SYM) (r->r_info)],
076f82
 			       &map->l_versions[ndx],
076f82
 			       (void *) (l_addr + r->r_offset), skip_ifunc);
076f82
 	    }
076f82
@@ -146,7 +146,7 @@ elf_dynamic_do_Rel (struct link_map *map,
076f82
 		{
076f82
 		  ElfW(Half) ndx
076f82
 		    = version[ELFW(R_SYM) (r2->r_info)] & 0x7fff;
076f82
-		  elf_machine_rel (map, r2,
076f82
+		  elf_machine_rel (map, scope, r2,
076f82
 				   &symtab[ELFW(R_SYM) (r2->r_info)],
076f82
 				   &map->l_versions[ndx],
076f82
 				   (void *) (l_addr + r2->r_offset),
076f82
@@ -167,14 +167,14 @@ elf_dynamic_do_Rel (struct link_map *map,
076f82
 	      }
076f82
 	    else
076f82
 # endif
076f82
-	      elf_machine_rel (map, r, &symtab[ELFW(R_SYM) (r->r_info)], NULL,
076f82
+	      elf_machine_rel (map, scope, r, &symtab[ELFW(R_SYM) (r->r_info)], NULL,
076f82
 			       (void *) (l_addr + r->r_offset), skip_ifunc);
076f82
 
076f82
 # ifdef ELF_MACHINE_IRELATIVE
076f82
 	  if (r2 != NULL)
076f82
 	    for (; r2 <= end2; ++r2)
076f82
 	      if (ELFW(R_TYPE) (r2->r_info) == ELF_MACHINE_IRELATIVE)
076f82
-		elf_machine_rel (map, r2, &symtab[ELFW(R_SYM) (r2->r_info)],
076f82
+		elf_machine_rel (map, scope, r2, &symtab[ELFW(R_SYM) (r2->r_info)],
076f82
 				 NULL, (void *) (l_addr + r2->r_offset),
076f82
 				 skip_ifunc);
076f82
 # endif
076f82
diff --git a/elf/dynamic-link.h b/elf/dynamic-link.h
076f82
index 3eb24ba3a6cee40b..7cc30211649d3820 100644
076f82
--- a/elf/dynamic-link.h
076f82
+++ b/elf/dynamic-link.h
076f82
@@ -59,31 +59,33 @@ int _dl_try_allocate_static_tls (struct link_map *map, bool optional)
076f82
    copying memory, breaking the very code written to handle the
076f82
    unaligned cases.  */
076f82
 # if ! ELF_MACHINE_NO_REL
076f82
-auto inline void __attribute__((always_inline))
076f82
-elf_machine_rel (struct link_map *map, const ElfW(Rel) *reloc,
076f82
-		 const ElfW(Sym) *sym, const struct r_found_version *version,
076f82
+static inline void __attribute__((always_inline))
076f82
+elf_machine_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		 const ElfW(Rel) *reloc, const ElfW(Sym) *sym,
076f82
+		 const struct r_found_version *version,
076f82
 		 void *const reloc_addr, int skip_ifunc);
076f82
-auto inline void __attribute__((always_inline))
076f82
+static inline void __attribute__((always_inline))
076f82
 elf_machine_rel_relative (ElfW(Addr) l_addr, const ElfW(Rel) *reloc,
076f82
 			  void *const reloc_addr);
076f82
 # endif
076f82
 # if ! ELF_MACHINE_NO_RELA
076f82
-auto inline void __attribute__((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
-		  const ElfW(Sym) *sym, const struct r_found_version *version,
076f82
-		  void *const reloc_addr, int skip_ifunc);
076f82
-auto inline void __attribute__((always_inline))
076f82
+static inline void __attribute__((always_inline))
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const ElfW(Rela) *reloc, const ElfW(Sym) *sym,
076f82
+		  const struct r_found_version *version, void *const reloc_addr,
076f82
+		  int skip_ifunc);
076f82
+static inline void __attribute__((always_inline))
076f82
 elf_machine_rela_relative (ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
 			   void *const reloc_addr);
076f82
 # endif
076f82
 # if ELF_MACHINE_NO_RELA || defined ELF_MACHINE_PLT_REL
076f82
-auto inline void __attribute__((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+static inline void __attribute__((always_inline))
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      ElfW(Addr) l_addr, const ElfW(Rel) *reloc,
076f82
 		      int skip_ifunc);
076f82
 # else
076f82
-auto inline void __attribute__((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+static inline void __attribute__((always_inline))
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
 		      int skip_ifunc);
076f82
 # endif
076f82
@@ -114,7 +116,7 @@ elf_machine_lazy_rel (struct link_map *map,
076f82
    consumes precisely the very end of the DT_REL*, or DT_JMPREL and DT_REL*
076f82
    are completely separate and there is a gap between them.  */
076f82
 
076f82
-# define _ELF_DYNAMIC_DO_RELOC(RELOC, reloc, map, do_lazy, skip_ifunc, test_rel) \
076f82
+# define _ELF_DYNAMIC_DO_RELOC(RELOC, reloc, map, scope, do_lazy, skip_ifunc, test_rel) \
076f82
   do {									      \
076f82
     struct { ElfW(Addr) start, size;					      \
076f82
 	     __typeof (((ElfW(Dyn) *) 0)->d_un.d_val) nrelative; int lazy; }  \
076f82
@@ -152,18 +154,18 @@ elf_machine_lazy_rel (struct link_map *map,
076f82
       }									      \
076f82
 									      \
076f82
     if (ELF_DURING_STARTUP)						      \
076f82
-      elf_dynamic_do_##reloc ((map), ranges[0].start, ranges[0].size,	      \
076f82
-			      ranges[0].nrelative, 0, skip_ifunc);	      \
076f82
+      elf_dynamic_do_##reloc ((map), scope, ranges[0].start, ranges[0].size,  \
076f82
+			      ranges[0].nrelative, 0, skip_ifunc);  \
076f82
     else								      \
076f82
       {									      \
076f82
 	int ranges_index;						      \
076f82
 	for (ranges_index = 0; ranges_index < 2; ++ranges_index)	      \
076f82
-	  elf_dynamic_do_##reloc ((map),				      \
076f82
+	  elf_dynamic_do_##reloc ((map), scope,				      \
076f82
 				  ranges[ranges_index].start,		      \
076f82
 				  ranges[ranges_index].size,		      \
076f82
 				  ranges[ranges_index].nrelative,	      \
076f82
 				  ranges[ranges_index].lazy,		      \
076f82
-				  skip_ifunc);				      \
076f82
+				  skip_ifunc);		      \
076f82
       }									      \
076f82
   } while (0)
076f82
 
076f82
@@ -175,29 +177,29 @@ elf_machine_lazy_rel (struct link_map *map,
076f82
 
076f82
 # if ! ELF_MACHINE_NO_REL
076f82
 #  include "do-rel.h"
076f82
-#  define ELF_DYNAMIC_DO_REL(map, lazy, skip_ifunc) \
076f82
-  _ELF_DYNAMIC_DO_RELOC (REL, Rel, map, lazy, skip_ifunc, _ELF_CHECK_REL)
076f82
+#  define ELF_DYNAMIC_DO_REL(map, scope, lazy, skip_ifunc)	      \
076f82
+  _ELF_DYNAMIC_DO_RELOC (REL, Rel, map, scope, lazy, skip_ifunc, _ELF_CHECK_REL)
076f82
 # else
076f82
-#  define ELF_DYNAMIC_DO_REL(map, lazy, skip_ifunc) /* Nothing to do.  */
076f82
+#  define ELF_DYNAMIC_DO_REL(map, scope, lazy, skip_ifunc) /* Nothing to do.  */
076f82
 # endif
076f82
 
076f82
 # if ! ELF_MACHINE_NO_RELA
076f82
 #  define DO_RELA
076f82
 #  include "do-rel.h"
076f82
-#  define ELF_DYNAMIC_DO_RELA(map, lazy, skip_ifunc) \
076f82
-  _ELF_DYNAMIC_DO_RELOC (RELA, Rela, map, lazy, skip_ifunc, _ELF_CHECK_REL)
076f82
+#  define ELF_DYNAMIC_DO_RELA(map, scope, lazy, skip_ifunc)	      \
076f82
+  _ELF_DYNAMIC_DO_RELOC (RELA, Rela, map, scope, lazy, skip_ifunc, _ELF_CHECK_REL)
076f82
 # else
076f82
-#  define ELF_DYNAMIC_DO_RELA(map, lazy, skip_ifunc) /* Nothing to do.  */
076f82
+#  define ELF_DYNAMIC_DO_RELA(map, scope, lazy, skip_ifunc) /* Nothing to do.  */
076f82
 # endif
076f82
 
076f82
 /* This can't just be an inline function because GCC is too dumb
076f82
    to inline functions containing inlines themselves.  */
076f82
-# define ELF_DYNAMIC_RELOCATE(map, lazy, consider_profile, skip_ifunc) \
076f82
+# define ELF_DYNAMIC_RELOCATE(map, scope, lazy, consider_profile, skip_ifunc) \
076f82
   do {									      \
076f82
-    int edr_lazy = elf_machine_runtime_setup ((map), (lazy),		      \
076f82
+    int edr_lazy = elf_machine_runtime_setup ((map), (scope), (lazy),	      \
076f82
 					      (consider_profile));	      \
076f82
-    ELF_DYNAMIC_DO_REL ((map), edr_lazy, skip_ifunc);			      \
076f82
-    ELF_DYNAMIC_DO_RELA ((map), edr_lazy, skip_ifunc);			      \
076f82
+    ELF_DYNAMIC_DO_REL ((map), (scope), edr_lazy, skip_ifunc);		      \
076f82
+    ELF_DYNAMIC_DO_RELA ((map), (scope), edr_lazy, skip_ifunc);		      \
076f82
   } while (0)
076f82
 
076f82
 #endif
076f82
diff --git a/elf/get-dynamic-info.h b/elf/get-dynamic-info.h
076f82
index 4aa2058abf6443c9..15c316b38c05a90c 100644
076f82
--- a/elf/get-dynamic-info.h
076f82
+++ b/elf/get-dynamic-info.h
076f82
@@ -16,18 +16,15 @@
076f82
    License along with the GNU C Library; if not, see
076f82
    <https://www.gnu.org/licenses/>.  */
076f82
 
076f82
-/* This file is included multiple times and therefore lacks a header
076f82
-   file inclusion guard.  */
076f82
+/* Populate dynamic tags in l_info.  */
076f82
+
076f82
+#ifndef _GET_DYNAMIC_INFO_H
076f82
+#define _GET_DYNAMIC_INFO_H
076f82
 
076f82
 #include <assert.h>
076f82
 #include <libc-diag.h>
076f82
 
076f82
-#ifndef RESOLVE_MAP
076f82
-static
076f82
-#else
076f82
-auto
076f82
-#endif
076f82
-inline void __attribute__ ((unused, always_inline))
076f82
+static inline void __attribute__ ((unused, always_inline))
076f82
 elf_get_dynamic_info (struct link_map *l)
076f82
 {
076f82
 #if __ELF_NATIVE_CLASS == 32
076f82
@@ -165,3 +162,5 @@ elf_get_dynamic_info (struct link_map *l)
076f82
     info[DT_RPATH] = NULL;
076f82
 #endif
076f82
 }
076f82
+
076f82
+#endif
076f82
diff --git a/elf/rtld.c b/elf/rtld.c
076f82
index 84eac9a8df7125a6..ee45657aeac14f3c 100644
076f82
--- a/elf/rtld.c
076f82
+++ b/elf/rtld.c
076f82
@@ -502,13 +502,9 @@ _dl_start_final (void *arg, struct dl_start_final_info *info)
076f82
   return start_addr;
076f82
 }
076f82
 
076f82
-static ElfW(Addr) __attribute_used__
076f82
-_dl_start (void *arg)
076f82
-{
076f82
 #ifdef DONT_USE_BOOTSTRAP_MAP
076f82
 # define bootstrap_map GL(dl_rtld_map)
076f82
 #else
076f82
-  struct dl_start_final_info info;
076f82
 # define bootstrap_map info.l
076f82
 #endif
076f82
 
076f82
@@ -517,13 +513,16 @@ _dl_start (void *arg)
076f82
      Since ld.so must not have any undefined symbols the result
076f82
      is trivial: always the map of ld.so itself.  */
076f82
 #define RTLD_BOOTSTRAP
076f82
-#define BOOTSTRAP_MAP (&bootstrap_map)
076f82
-#define RESOLVE_MAP(sym, version, flags) BOOTSTRAP_MAP
076f82
+#define RESOLVE_MAP(map, scope, sym, version, flags) map
076f82
 #include "dynamic-link.h"
076f82
 
076f82
+static ElfW(Addr) __attribute_used__
076f82
+_dl_start (void *arg)
076f82
+{
076f82
 #ifdef DONT_USE_BOOTSTRAP_MAP
076f82
   rtld_timer_start (&start_time);
076f82
 #else
076f82
+  struct dl_start_final_info info;
076f82
   rtld_timer_start (&info.start_time);
076f82
 #endif
076f82
 
076f82
@@ -557,7 +556,7 @@ _dl_start (void *arg)
076f82
 #endif
076f82
 
076f82
 #ifdef ELF_MACHINE_BEFORE_RTLD_RELOC
076f82
-  ELF_MACHINE_BEFORE_RTLD_RELOC (bootstrap_map.l_info);
076f82
+  ELF_MACHINE_BEFORE_RTLD_RELOC (&bootstrap_map, bootstrap_map.l_info);
076f82
 #endif
076f82
 
076f82
   if (bootstrap_map.l_addr || ! bootstrap_map.l_info[VALIDX(DT_GNU_PRELINKED)])
076f82
@@ -565,7 +564,7 @@ _dl_start (void *arg)
076f82
       /* Relocate ourselves so we can do normal function calls and
076f82
 	 data access using the global offset table.  */
076f82
 
076f82
-      ELF_DYNAMIC_RELOCATE (&bootstrap_map, 0, 0, 0);
076f82
+      ELF_DYNAMIC_RELOCATE (&bootstrap_map, NULL, 0, 0, 0);
076f82
     }
076f82
   bootstrap_map.l_relocated = 1;
076f82
 
076f82
diff --git a/sysdeps/aarch64/dl-machine.h b/sysdeps/aarch64/dl-machine.h
076f82
index d29d827ab32a78ee..34c0790b893a529b 100644
076f82
--- a/sysdeps/aarch64/dl-machine.h
076f82
+++ b/sysdeps/aarch64/dl-machine.h
076f82
@@ -65,7 +65,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int __attribute__ ((unused))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   if (l->l_info[DT_JMPREL] && lazy)
076f82
     {
076f82
@@ -243,10 +244,11 @@ elf_machine_plt_value (struct link_map *map,
076f82
 
076f82
 #ifdef RESOLVE_MAP
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
-		  const ElfW(Sym) *sym, const struct r_found_version *version,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const ElfW(Rela) *reloc, const ElfW(Sym) *sym,
076f82
+		  const struct r_found_version *version,
076f82
 		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   ElfW(Addr) *const reloc_addr = reloc_addr_arg;
076f82
@@ -259,7 +261,8 @@ elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
   else
076f82
     {
076f82
       const ElfW(Sym) *const refsym = sym;
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       ElfW(Addr) value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
       if (sym != NULL
076f82
@@ -383,9 +386,9 @@ elf_machine_rela_relative (ElfW(Addr) l_addr,
076f82
   *reloc_addr = l_addr + reloc->r_addend;
076f82
 }
076f82
 
076f82
-inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      ElfW(Addr) l_addr,
076f82
 		      const ElfW(Rela) *reloc,
076f82
 		      int skip_ifunc)
076f82
@@ -412,7 +415,7 @@ elf_machine_lazy_rel (struct link_map *map,
076f82
 		    (const void *)D_PTR (map, l_info[VERSYMIDX (DT_VERSYM)]);
076f82
 		  version = &map->l_versions[vernum[symndx] & 0x7fff];
076f82
 		}
076f82
-	      elf_machine_rela (map, reloc, sym, version, reloc_addr,
076f82
+	      elf_machine_rela (map, scope, reloc, sym, version, reloc_addr,
076f82
 				skip_ifunc);
076f82
 	      return;
076f82
 	    }
076f82
@@ -439,7 +442,8 @@ elf_machine_lazy_rel (struct link_map *map,
076f82
 
076f82
       /* Always initialize TLS descriptors completely, because lazy
076f82
 	 initialization requires synchronization at every TLS access.  */
076f82
-      elf_machine_rela (map, reloc, sym, version, reloc_addr, skip_ifunc);
076f82
+      elf_machine_rela (map, scope, reloc, sym, version, reloc_addr,
076f82
+			skip_ifunc);
076f82
     }
076f82
   else if (__glibc_unlikely (r_type == AARCH64_R(IRELATIVE)))
076f82
     {
076f82
diff --git a/sysdeps/alpha/dl-machine.h b/sysdeps/alpha/dl-machine.h
076f82
index 2cd2213d9ab25287..66e1db524bb378f6 100644
076f82
--- a/sysdeps/alpha/dl-machine.h
076f82
+++ b/sysdeps/alpha/dl-machine.h
076f82
@@ -70,7 +70,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int
076f82
-elf_machine_runtime_setup (struct link_map *map, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *map, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   extern char _dl_runtime_resolve_new[] attribute_hidden;
076f82
   extern char _dl_runtime_profile_new[] attribute_hidden;
076f82
@@ -361,9 +362,9 @@ elf_machine_plt_value (struct link_map *map, const Elf64_Rela *reloc,
076f82
 
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully resolved).
076f82
    MAP is the object containing the reloc.  */
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		  const Elf64_Rela *reloc,
076f82
 		  const Elf64_Sym *sym,
076f82
 		  const struct r_found_version *version,
076f82
@@ -411,7 +412,8 @@ elf_machine_rela (struct link_map *map,
076f82
       return;
076f82
   else
076f82
     {
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       Elf64_Addr sym_value;
076f82
       Elf64_Addr sym_raw_value;
076f82
 
076f82
@@ -489,7 +491,7 @@ elf_machine_rela (struct link_map *map,
076f82
    can be skipped.  */
076f82
 #define ELF_MACHINE_REL_RELATIVE 1
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
 elf_machine_rela_relative (Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
@@ -506,9 +508,9 @@ elf_machine_rela_relative (Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
   memcpy (reloc_addr_arg, &reloc_addr_val, 8);
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/arc/dl-machine.h b/sysdeps/arc/dl-machine.h
076f82
index e6ce7f0ff6d9ac34..4b64ffec256b7f3b 100644
076f82
--- a/sysdeps/arc/dl-machine.h
076f82
+++ b/sysdeps/arc/dl-machine.h
076f82
@@ -122,7 +122,8 @@ elf_machine_load_address (void)
076f82
 
076f82
 static inline int
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   extern void _dl_runtime_resolve (void);
076f82
 
076f82
@@ -228,10 +229,11 @@ elf_machine_fixup_plt (struct link_map *map, lookup_t t,
076f82
 
076f82
 #ifdef RESOLVE_MAP
076f82
 
076f82
-inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
-                  const ElfW(Sym) *sym, const struct r_found_version *version,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const ElfW(Rela) *reloc, const ElfW(Sym) *sym,
076f82
+		  const struct r_found_version *version,
076f82
                   void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   ElfW(Addr) r_info = reloc->r_info;
076f82
@@ -245,7 +247,8 @@ elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
   else
076f82
     {
076f82
       const ElfW(Sym) *const refsym = sym;
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       ElfW(Addr) value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
       switch (r_type)
076f82
@@ -326,8 +329,9 @@ elf_machine_rela_relative (ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
 
076f82
 inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map, ElfW(Addr) l_addr,
076f82
-                      const ElfW(Rela) *reloc, int skip_ifunc)
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		      ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
+		      int skip_ifunc)
076f82
 {
076f82
   ElfW(Addr) *const reloc_addr = (void *) (l_addr + reloc->r_offset);
076f82
   const unsigned int r_type = ELFW (R_TYPE) (reloc->r_info);
076f82
diff --git a/sysdeps/arm/dl-machine.h b/sysdeps/arm/dl-machine.h
076f82
index ff5e09e207f7986b..7e6761bbe87540d5 100644
076f82
--- a/sysdeps/arm/dl-machine.h
076f82
+++ b/sysdeps/arm/dl-machine.h
076f82
@@ -84,7 +84,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int __attribute__ ((unused))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   Elf32_Addr *got;
076f82
   extern void _dl_runtime_resolve (Elf32_Word);
076f82
@@ -303,7 +304,7 @@ elf_machine_plt_value (struct link_map *map, const Elf32_Rel *reloc,
076f82
 
076f82
 #ifdef RESOLVE_MAP
076f82
 /* Handle a PC24 reloc, including the out-of-range case.  */
076f82
-auto void
076f82
+static void
076f82
 relocate_pc24 (struct link_map *map, Elf32_Addr value,
076f82
                Elf32_Addr *const reloc_addr, Elf32_Sword addend)
076f82
 {
076f82
@@ -357,10 +358,11 @@ relocate_pc24 (struct link_map *map, Elf32_Addr value,
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully resolved).
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rel (struct link_map *map, const Elf32_Rel *reloc,
076f82
-		 const Elf32_Sym *sym, const struct r_found_version *version,
076f82
+elf_machine_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
+                 const Elf32_Rel *reloc, const Elf32_Sym *sym,
076f82
+                 const struct r_found_version *version,
076f82
 		 void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf32_Addr *const reloc_addr = reloc_addr_arg;
076f82
@@ -391,7 +393,8 @@ elf_machine_rel (struct link_map *map, const Elf32_Rel *reloc,
076f82
 #endif
076f82
     {
076f82
       const Elf32_Sym *const refsym = sym;
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       Elf32_Addr value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
       if (sym != NULL
076f82
@@ -535,10 +538,11 @@ elf_machine_rel (struct link_map *map, const Elf32_Rel *reloc,
076f82
 }
076f82
 
076f82
 # ifndef RTLD_BOOTSTRAP
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
-		  const Elf32_Sym *sym, const struct r_found_version *version,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+                  const Elf32_Rela *reloc, const Elf32_Sym *sym,
076f82
+                  const struct r_found_version *version,
076f82
 		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf32_Addr *const reloc_addr = reloc_addr_arg;
076f82
@@ -553,7 +557,7 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
 # ifndef RESOLVE_CONFLICT_FIND_MAP
076f82
       const Elf32_Sym *const refsym = sym;
076f82
 # endif
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version, r_type);
076f82
       Elf32_Addr value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
       if (sym != NULL
076f82
@@ -628,7 +632,7 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
 }
076f82
 # endif
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
 elf_machine_rel_relative (Elf32_Addr l_addr, const Elf32_Rel *reloc,
076f82
 			  void *const reloc_addr_arg)
076f82
@@ -638,7 +642,7 @@ elf_machine_rel_relative (Elf32_Addr l_addr, const Elf32_Rel *reloc,
076f82
 }
076f82
 
076f82
 # ifndef RTLD_BOOTSTRAP
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
 elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
@@ -648,9 +652,9 @@ elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 }
076f82
 # endif
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf32_Addr l_addr, const Elf32_Rel *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
@@ -680,7 +684,7 @@ elf_machine_lazy_rel (struct link_map *map,
076f82
 
076f82
       /* Always initialize TLS descriptors completely, because lazy
076f82
 	 initialization requires synchronization at every TLS access.  */
076f82
-      elf_machine_rel (map, reloc, sym, version, reloc_addr, skip_ifunc);
076f82
+      elf_machine_rel (map, scope, reloc, sym, version, reloc_addr, skip_ifunc);
076f82
     }
076f82
   else
076f82
     _dl_reloc_bad_type (map, r_type, 1);
076f82
diff --git a/sysdeps/csky/dl-machine.h b/sysdeps/csky/dl-machine.h
076f82
index b08f06d74ca6f8d1..ec22f875772b1291 100644
076f82
--- a/sysdeps/csky/dl-machine.h
076f82
+++ b/sysdeps/csky/dl-machine.h
076f82
@@ -58,7 +58,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int __attribute__ ((always_inline))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   Elf32_Addr *got;
076f82
   extern void _dl_runtime_resolve (Elf32_Word);
076f82
@@ -215,9 +216,10 @@ elf_machine_plt_value (struct link_map *map, const Elf32_Rela *reloc,
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully resolved).
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void __attribute__ ((unused, always_inline))
076f82
-elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
-		  const Elf32_Sym *sym, const struct r_found_version *version,
076f82
+static inline void __attribute__ ((unused, always_inline))
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const Elf32_Rela *reloc, const Elf32_Sym *sym,
076f82
+		  const struct r_found_version *version,
076f82
 		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf32_Addr *const reloc_addr = reloc_addr_arg;
076f82
@@ -230,7 +232,8 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
   else
076f82
     {
076f82
       const Elf32_Sym *const refsym = sym;
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       ElfW(Addr) value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
       opcode16_addr = (unsigned short *)reloc_addr;
076f82
 
076f82
@@ -331,7 +334,7 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void __attribute__ ((unused, always_inline))
076f82
+static inline void __attribute__ ((unused, always_inline))
076f82
 elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
 {
076f82
@@ -339,8 +342,8 @@ elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
   *reloc_addr = l_addr + reloc->r_addend;
076f82
 }
076f82
 
076f82
-auto inline void __attribute__ ((unused, always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+static inline void __attribute__ ((unused, always_inline))
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/hppa/dl-machine.h b/sysdeps/hppa/dl-machine.h
076f82
index 24f0f47d8f1e25cd..088931f67065250c 100644
076f82
--- a/sysdeps/hppa/dl-machine.h
076f82
+++ b/sysdeps/hppa/dl-machine.h
076f82
@@ -70,8 +70,8 @@ __hppa_init_bootstrap_fdesc_table (struct link_map *map)
076f82
   map->l_mach.fptr_table = boot_table;
076f82
 }
076f82
 
076f82
-#define ELF_MACHINE_BEFORE_RTLD_RELOC(dynamic_info)		\
076f82
-	__hppa_init_bootstrap_fdesc_table (BOOTSTRAP_MAP);	\
076f82
+#define ELF_MACHINE_BEFORE_RTLD_RELOC(map, dynamic_info)	\
076f82
+	__hppa_init_bootstrap_fdesc_table (map);		\
076f82
 	_dl_fptr_init();
076f82
 
076f82
 /* Return nonzero iff ELF header is compatible with the running host.  */
076f82
@@ -182,7 +182,8 @@ elf_machine_main_map (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   Elf32_Addr *got = NULL;
076f82
   Elf32_Addr l_addr, iplt, jmprel, end_jmprel, r_type, r_sym;
076f82
@@ -564,8 +565,8 @@ dl_platform_init (void)
076f82
   (  (((as14) & 0x1fff) << 1) \
076f82
    | (((as14) & 0x2000) >> 13))
076f82
 
076f82
-auto void __attribute__((always_inline))
076f82
-elf_machine_rela (struct link_map *map,
076f82
+static void __attribute__((always_inline))
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		  const Elf32_Rela *reloc,
076f82
 		  const Elf32_Sym *sym,
076f82
 		  const struct r_found_version *version,
076f82
@@ -594,11 +595,9 @@ elf_machine_rela (struct link_map *map,
076f82
      zeros, and an all zero Elf32_Sym has a binding of STB_LOCAL.)
076f82
      See RESOLVE_MAP definition in elf/dl-reloc.c  */
076f82
 # ifdef RTLD_BOOTSTRAP
076f82
-  /* RESOLVE_MAP in rtld.c doesn't have the local sym test.  */
076f82
-  sym_map = (ELF32_ST_BIND (sym->st_info) != STB_LOCAL
076f82
-	     ? RESOLVE_MAP (&sym, version, r_type) : map);
076f82
+  sym_map = map;
076f82
 # else
076f82
-  sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+  sym_map = RESOLVE_MAP (map, scope, &sym, version, r_type);
076f82
 # endif
076f82
 
076f82
   if (sym_map)
076f82
@@ -756,7 +755,7 @@ elf_machine_rela (struct link_map *map,
076f82
 
076f82
 /* hppa doesn't have an R_PARISC_RELATIVE reloc, but uses relocs with
076f82
    ELF32_R_SYM (info) == 0 for a similar purpose.  */
076f82
-auto void __attribute__((always_inline))
076f82
+static void __attribute__((always_inline))
076f82
 elf_machine_rela_relative (Elf32_Addr l_addr,
076f82
 			   const Elf32_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
@@ -809,8 +808,8 @@ elf_machine_rela_relative (Elf32_Addr l_addr,
076f82
   *reloc_addr = value;
076f82
 }
076f82
 
076f82
-auto void __attribute__((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+static void __attribute__((always_inline))
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/i386/dl-machine.h b/sysdeps/i386/dl-machine.h
076f82
index 590b41d8d7e35005..78ce890c0ff333ca 100644
076f82
--- a/sysdeps/i386/dl-machine.h
076f82
+++ b/sysdeps/i386/dl-machine.h
076f82
@@ -61,7 +61,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int __attribute__ ((unused, always_inline))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   Elf32_Addr *got;
076f82
   extern void _dl_runtime_resolve (Elf32_Word) attribute_hidden;
076f82
@@ -291,9 +292,10 @@ elf_machine_plt_value (struct link_map *map, const Elf32_Rel *reloc,
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully resolved).
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute ((always_inline))
076f82
-elf_machine_rel (struct link_map *map, const Elf32_Rel *reloc,
076f82
+elf_machine_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		 const Elf32_Rel *reloc,
076f82
 		 const Elf32_Sym *sym, const struct r_found_version *version,
076f82
 		 void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
@@ -327,7 +329,8 @@ elf_machine_rel (struct link_map *map, const Elf32_Rel *reloc,
076f82
 # ifndef RTLD_BOOTSTRAP
076f82
       const Elf32_Sym *const refsym = sym;
076f82
 # endif
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       Elf32_Addr value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
       if (sym != NULL
076f82
@@ -498,10 +501,11 @@ and creates an unsatisfiable circular dependency.\n",
076f82
 }
076f82
 
076f82
 # ifndef RTLD_BOOTSTRAP
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
-		  const Elf32_Sym *sym, const struct r_found_version *version,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const Elf32_Rela *reloc, const Elf32_Sym *sym,
076f82
+		  const struct r_found_version *version,
076f82
 		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf32_Addr *const reloc_addr = reloc_addr_arg;
076f82
@@ -514,7 +518,8 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
 #  ifndef RESOLVE_CONFLICT_FIND_MAP
076f82
       const Elf32_Sym *const refsym = sym;
076f82
 #  endif
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       Elf32_Addr value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
       if (sym != NULL
076f82
@@ -647,7 +652,7 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
 }
076f82
 # endif	/* !RTLD_BOOTSTRAP */
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute ((always_inline))
076f82
 elf_machine_rel_relative (Elf32_Addr l_addr, const Elf32_Rel *reloc,
076f82
 			  void *const reloc_addr_arg)
076f82
@@ -658,7 +663,7 @@ elf_machine_rel_relative (Elf32_Addr l_addr, const Elf32_Rel *reloc,
076f82
 }
076f82
 
076f82
 # ifndef RTLD_BOOTSTRAP
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
 elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
@@ -668,9 +673,9 @@ elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 }
076f82
 # endif	/* !RTLD_BOOTSTRAP */
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf32_Addr l_addr, const Elf32_Rel *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
@@ -705,13 +710,13 @@ elf_machine_lazy_rel (struct link_map *map,
076f82
 	  const ElfW(Half) *const version =
076f82
 	    (const void *) D_PTR (map, l_info[VERSYMIDX (DT_VERSYM)]);
076f82
 	  ElfW(Half) ndx = version[ELFW(R_SYM) (r->r_info)] & 0x7fff;
076f82
-	  elf_machine_rel (map, r, &symtab[ELFW(R_SYM) (r->r_info)],
076f82
+	  elf_machine_rel (map, scope, r, &symtab[ELFW(R_SYM) (r->r_info)],
076f82
 			   &map->l_versions[ndx],
076f82
 			   (void *) (l_addr + r->r_offset), skip_ifunc);
076f82
 	}
076f82
 # ifndef RTLD_BOOTSTRAP
076f82
       else
076f82
-	elf_machine_rel (map, r, &symtab[ELFW(R_SYM) (r->r_info)], NULL,
076f82
+	elf_machine_rel (map, scope, r, &symtab[ELFW(R_SYM) (r->r_info)], NULL,
076f82
 			 (void *) (l_addr + r->r_offset), skip_ifunc);
076f82
 # endif
076f82
     }
076f82
@@ -728,9 +733,9 @@ elf_machine_lazy_rel (struct link_map *map,
076f82
 
076f82
 # ifndef RTLD_BOOTSTRAP
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rela (struct link_map *map,
076f82
+elf_machine_lazy_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		       Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 		       int skip_ifunc)
076f82
 {
076f82
@@ -754,7 +759,8 @@ elf_machine_lazy_rela (struct link_map *map,
076f82
 
076f82
       /* Always initialize TLS descriptors completely at load time, in
076f82
 	 case static TLS is allocated for it that requires locking.  */
076f82
-      elf_machine_rela (map, reloc, sym, version, reloc_addr, skip_ifunc);
076f82
+      elf_machine_rela (map, scope, reloc, sym, version, reloc_addr,
076f82
+			skip_ifunc);
076f82
     }
076f82
   else if (__glibc_unlikely (r_type == R_386_IRELATIVE))
076f82
     {
076f82
diff --git a/sysdeps/ia64/dl-machine.h b/sysdeps/ia64/dl-machine.h
076f82
index 4403e7767af83546..2217d0b556c17683 100644
076f82
--- a/sysdeps/ia64/dl-machine.h
076f82
+++ b/sysdeps/ia64/dl-machine.h
076f82
@@ -44,8 +44,8 @@ __ia64_init_bootstrap_fdesc_table (struct link_map *map)
076f82
   map->l_mach.fptr_table = boot_table;
076f82
 }
076f82
 
076f82
-#define ELF_MACHINE_BEFORE_RTLD_RELOC(dynamic_info)		\
076f82
-	__ia64_init_bootstrap_fdesc_table (BOOTSTRAP_MAP);
076f82
+#define ELF_MACHINE_BEFORE_RTLD_RELOC(map, dynamic_info)		\
076f82
+	__ia64_init_bootstrap_fdesc_table (map);
076f82
 
076f82
 /* Return nonzero iff ELF header is compatible with the running host.  */
076f82
 static inline int __attribute__ ((unused))
076f82
@@ -98,7 +98,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int __attribute__ ((unused, always_inline))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   extern void _dl_runtime_resolve (void);
076f82
   extern void _dl_runtime_profile (void);
076f82
@@ -371,9 +372,9 @@ elf_machine_plt_value (struct link_map *map, const Elf64_Rela *reloc,
076f82
 
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully
076f82
    resolved).  MAP is the object containing the reloc.  */
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute ((always_inline))
076f82
-elf_machine_rela (struct link_map *map,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		  const Elf64_Rela *reloc,
076f82
 		  const Elf64_Sym *sym,
076f82
 		  const struct r_found_version *version,
076f82
@@ -414,10 +415,11 @@ elf_machine_rela (struct link_map *map,
076f82
       return;
076f82
   else
076f82
     {
076f82
-      struct link_map *sym_map;
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
 
076f82
       /* RESOLVE_MAP() will return NULL if it fail to locate the symbol.  */
076f82
-      if ((sym_map = RESOLVE_MAP (&sym, version, r_type)))
076f82
+      if (sym_map != NULL)
076f82
 	{
076f82
 	  value = SYMBOL_ADDRESS (sym_map, sym, true) + reloc->r_addend;
076f82
 
076f82
@@ -476,7 +478,7 @@ elf_machine_rela (struct link_map *map,
076f82
    can be skipped.  */
076f82
 #define ELF_MACHINE_REL_RELATIVE 1
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute ((always_inline))
076f82
 elf_machine_rela_relative (Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
@@ -489,9 +491,9 @@ elf_machine_rela_relative (Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
 }
076f82
 
076f82
 /* Perform a RELATIVE reloc on the .got entry that transfers to the .plt.  */
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/m68k/dl-machine.h b/sysdeps/m68k/dl-machine.h
076f82
index 86a8c67e2a1b9f77..5e34c4784e348b19 100644
076f82
--- a/sysdeps/m68k/dl-machine.h
076f82
+++ b/sysdeps/m68k/dl-machine.h
076f82
@@ -68,7 +68,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int __attribute__ ((always_inline))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   Elf32_Addr *got;
076f82
   extern void _dl_runtime_resolve (Elf32_Word);
076f82
@@ -215,9 +216,10 @@ elf_machine_plt_value (struct link_map *map, const Elf32_Rela *reloc,
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully resolved).
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void __attribute__ ((unused, always_inline))
076f82
-elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
-		  const Elf32_Sym *sym, const struct r_found_version *version,
076f82
+static inline void __attribute__ ((unused, always_inline))
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const Elf32_Rela *reloc, const Elf32_Sym *sym,
076f82
+		  const struct r_found_version *version,
076f82
 		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf32_Addr *const reloc_addr = reloc_addr_arg;
076f82
@@ -228,7 +230,8 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
   else
076f82
     {
076f82
       const Elf32_Sym *const refsym = sym;
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       Elf32_Addr value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
       switch (r_type)
076f82
@@ -303,7 +306,7 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void __attribute__ ((unused, always_inline))
076f82
+static inline void __attribute__ ((unused, always_inline))
076f82
 elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
 {
076f82
@@ -311,8 +314,8 @@ elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
   *reloc_addr = l_addr + reloc->r_addend;
076f82
 }
076f82
 
076f82
-auto inline void __attribute__ ((unused, always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+static inline void __attribute__ ((unused, always_inline))
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/microblaze/dl-machine.h b/sysdeps/microblaze/dl-machine.h
076f82
index e460f6f195561da1..3fd4988e6093be1c 100644
076f82
--- a/sysdeps/microblaze/dl-machine.h
076f82
+++ b/sysdeps/microblaze/dl-machine.h
076f82
@@ -69,7 +69,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int __attribute__ ((always_inline))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   extern void _dl_runtime_resolve (Elf32_Word);
076f82
   extern void _dl_runtime_profile (Elf32_Word);
076f82
@@ -207,9 +208,10 @@ elf_machine_plt_value (struct link_map *map, const Elf32_Rela *reloc,
076f82
     ((unsigned short *)(rel_addr))[3] = (val) & 0xffff; \
076f82
   } while (0)
076f82
 
076f82
-auto inline void __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
-		  const Elf32_Sym *sym, const struct r_found_version *version,
076f82
+static inline void __attribute__ ((always_inline))
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const Elf32_Rela *reloc, const Elf32_Sym *sym,
076f82
+		  const struct r_found_version *version,
076f82
 		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf32_Addr *const reloc_addr = reloc_addr_arg;
076f82
@@ -222,7 +224,8 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
   else
076f82
     {
076f82
       const Elf32_Sym *const refsym = sym;
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       Elf32_Addr value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
       value += reloc->r_addend;
076f82
@@ -277,7 +280,7 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
 {
076f82
@@ -285,8 +288,8 @@ elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
   PUT_REL_64 (reloc_addr, l_addr + reloc->r_addend);
076f82
 }
076f82
 
076f82
-auto inline void
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+static inline void
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/mips/dl-machine.h b/sysdeps/mips/dl-machine.h
076f82
index d9c6d33d0cbf1f50..7a821ceb8e518cef 100644
076f82
--- a/sysdeps/mips/dl-machine.h
076f82
+++ b/sysdeps/mips/dl-machine.h
076f82
@@ -188,9 +188,9 @@ elf_machine_load_address (void)
076f82
 
076f82
 /* We can't rely on elf_machine_got_rel because _dl_object_relocation_scope
076f82
    fiddles with global data.  */
076f82
-#define ELF_MACHINE_BEFORE_RTLD_RELOC(dynamic_info)			\
076f82
+#define ELF_MACHINE_BEFORE_RTLD_RELOC(bootstrap_map, dynamic_info)	\
076f82
 do {									\
076f82
-  struct link_map *map = BOOTSTRAP_MAP;					\
076f82
+  struct link_map *map = bootstrap_map;					\
076f82
   ElfW(Sym) *sym;							\
076f82
   ElfW(Addr) *got;							\
076f82
   int i, n;								\
076f82
@@ -475,11 +475,12 @@ elf_machine_plt_value (struct link_map *map, const ElfW(Rel) *reloc,
076f82
    by RELOC_ADDR.  SYM is the relocation symbol specified by R_INFO and
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_reloc (struct link_map *map, ElfW(Addr) r_info,
076f82
-		   const ElfW(Sym) *sym, const struct r_found_version *version,
076f82
-		   void *reloc_addr, ElfW(Addr) r_addend, int inplace_p)
076f82
+elf_machine_reloc (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		   ElfW(Addr) r_info, const ElfW(Sym) *sym,
076f82
+		   const struct r_found_version *version, void *reloc_addr,
076f82
+		   ElfW(Addr) r_addend, int inplace_p)
076f82
 {
076f82
   const unsigned long int r_type = ELFW(R_TYPE) (r_info);
076f82
   ElfW(Addr) *addr_field = (ElfW(Addr) *) reloc_addr;
076f82
@@ -507,7 +508,8 @@ elf_machine_reloc (struct link_map *map, ElfW(Addr) r_info,
076f82
     case R_MIPS_TLS_TPREL32:
076f82
 # endif
076f82
       {
076f82
-	struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+	struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+						r_type);
076f82
 
076f82
 	switch (r_type)
076f82
 	  {
076f82
@@ -647,7 +649,7 @@ elf_machine_reloc (struct link_map *map, ElfW(Addr) r_info,
076f82
 	  _dl_signal_error (0, map->l_name, NULL,
076f82
 			    "found jump slot relocation with non-zero addend");
076f82
 
076f82
-	sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+	sym_map = RESOLVE_MAP (map, scope, &sym, version, r_type);
076f82
 	value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 	*addr_field = value;
076f82
 
076f82
@@ -661,7 +663,7 @@ elf_machine_reloc (struct link_map *map, ElfW(Addr) r_info,
076f82
 	ElfW(Addr) value;
076f82
 
076f82
 	/* Calculate the address of the symbol.  */
076f82
-	sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+	sym_map = RESOLVE_MAP (map, scope, &sym, version, r_type);
076f82
 	value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
 	if (__builtin_expect (sym == NULL, 0))
076f82
@@ -708,16 +710,17 @@ elf_machine_reloc (struct link_map *map, ElfW(Addr) r_info,
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully resolved).
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rel (struct link_map *map, const ElfW(Rel) *reloc,
076f82
-		 const ElfW(Sym) *sym, const struct r_found_version *version,
076f82
-		 void *const reloc_addr, int skip_ifunc)
076f82
+elf_machine_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		 const ElfW(Rel) *reloc, const ElfW(Sym) *sym,
076f82
+		 const struct r_found_version *version, void *const reloc_addr,
076f82
+		 int skip_ifunc)
076f82
 {
076f82
-  elf_machine_reloc (map, reloc->r_info, sym, version, reloc_addr, 0, 1);
076f82
+  elf_machine_reloc (map, scope, reloc->r_info, sym, version, reloc_addr, 0, 1);
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__((always_inline))
076f82
 elf_machine_rel_relative (ElfW(Addr) l_addr, const ElfW(Rel) *reloc,
076f82
 			  void *const reloc_addr)
076f82
@@ -725,9 +728,9 @@ elf_machine_rel_relative (ElfW(Addr) l_addr, const ElfW(Rel) *reloc,
076f82
   /* XXX Nothing to do.  There is no relative relocation, right?  */
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      ElfW(Addr) l_addr, const ElfW(Rel) *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
@@ -748,17 +751,17 @@ elf_machine_lazy_rel (struct link_map *map,
076f82
     _dl_reloc_bad_type (map, r_type, 1);
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[], const ElfW(Rela) *reloc,
076f82
 		  const ElfW(Sym) *sym, const struct r_found_version *version,
076f82
 		  void *const reloc_addr, int skip_ifunc)
076f82
 {
076f82
-  elf_machine_reloc (map, reloc->r_info, sym, version, reloc_addr,
076f82
+  elf_machine_reloc (map, scope, reloc->r_info, sym, version, reloc_addr,
076f82
 		     reloc->r_addend, 0);
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__((always_inline))
076f82
 elf_machine_rela_relative (ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
 			   void *const reloc_addr)
076f82
@@ -767,9 +770,9 @@ elf_machine_rela_relative (ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
 
076f82
 #ifndef RTLD_BOOTSTRAP
076f82
 /* Relocate GOT. */
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__((always_inline))
076f82
-elf_machine_got_rel (struct link_map *map, int lazy)
076f82
+elf_machine_got_rel (struct link_map *map, struct r_scope_elem *scope[], int lazy)
076f82
 {
076f82
   ElfW(Addr) *got;
076f82
   ElfW(Sym) *sym;
076f82
@@ -782,7 +785,7 @@ elf_machine_got_rel (struct link_map *map, int lazy)
076f82
       const struct r_found_version *version __attribute__ ((unused))	  \
076f82
 	= vernum ? &map->l_versions[vernum[sym_index] & 0x7fff] : NULL;	  \
076f82
       struct link_map *sym_map;						  \
076f82
-      sym_map = RESOLVE_MAP (&ref, version, reloc);			  \
076f82
+      sym_map = RESOLVE_MAP (map, scope, &ref, version, reloc);		  \
076f82
       SYMBOL_ADDRESS (sym_map, ref, true);				  \
076f82
     })
076f82
 
076f82
@@ -868,9 +871,10 @@ elf_machine_got_rel (struct link_map *map, int lazy)
076f82
 /* Set up the loaded object described by L so its stub function
076f82
    will jump to the on-demand fixup code __dl_runtime_resolve.  */
076f82
 
076f82
-auto inline int
076f82
+static inline int
076f82
 __attribute__((always_inline))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
 # ifndef RTLD_BOOTSTRAP
076f82
   ElfW(Addr) *got;
076f82
@@ -900,7 +904,7 @@ elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
     }
076f82
 
076f82
   /* Relocate global offset table.  */
076f82
-  elf_machine_got_rel (l, lazy);
076f82
+  elf_machine_got_rel (l, scope, lazy);
076f82
 
076f82
   /* If using PLTs, fill in the first two entries of .got.plt.  */
076f82
   if (l->l_info[DT_JMPREL] && lazy)
076f82
diff --git a/sysdeps/nios2/dl-machine.h b/sysdeps/nios2/dl-machine.h
076f82
index e000cd081f18a12b..4de602b13d5500f6 100644
076f82
--- a/sysdeps/nios2/dl-machine.h
076f82
+++ b/sysdeps/nios2/dl-machine.h
076f82
@@ -67,7 +67,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int __attribute__ ((always_inline))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   extern void _dl_runtime_resolve (Elf32_Word);
076f82
 
076f82
@@ -234,10 +235,11 @@ elf_machine_plt_value (struct link_map *map, const Elf32_Rela *reloc,
076f82
    LOADADDR is the load address of the object; INFO is an array indexed
076f82
    by DT_* of the .dynamic section info.  */
076f82
 
076f82
-auto inline void __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
-                  const ElfW(Sym) *sym, const struct r_found_version *version,
076f82
-                  void *const reloc_addr_arg, int skip_ifunc)
076f82
+static inline void __attribute__ ((always_inline))
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const ElfW(Rela) *reloc, const ElfW(Sym) *sym,
076f82
+		  const struct r_found_version *version,
076f82
+		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf32_Addr *const reloc_addr = reloc_addr_arg;
076f82
   const unsigned int r_type = ELF32_R_TYPE (reloc->r_info);
076f82
@@ -249,7 +251,8 @@ elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
   else
076f82
     {
076f82
       const Elf32_Sym *const refsym = sym;
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       Elf32_Addr value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
       switch (r_type)
076f82
@@ -314,7 +317,7 @@ elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void __attribute__((always_inline))
076f82
+static inline void __attribute__((always_inline))
076f82
 elf_machine_rela_relative (ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
 {
076f82
@@ -322,8 +325,8 @@ elf_machine_rela_relative (ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
   *reloc_addr = l_addr + reloc->r_addend;
076f82
 }
076f82
 
076f82
-auto inline void __attribute__((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+static inline void __attribute__((always_inline))
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/powerpc/powerpc32/dl-machine.h b/sysdeps/powerpc/powerpc32/dl-machine.h
076f82
index b93cf486b6cda5fd..cda012dc1b822254 100644
076f82
--- a/sysdeps/powerpc/powerpc32/dl-machine.h
076f82
+++ b/sysdeps/powerpc/powerpc32/dl-machine.h
076f82
@@ -170,7 +170,7 @@ extern int __elf_machine_runtime_setup (struct link_map *map,
076f82
 					int lazy, int profile);
076f82
 
076f82
 static inline int
076f82
-elf_machine_runtime_setup (struct link_map *map,
076f82
+elf_machine_runtime_setup (struct link_map *map, struct r_scope_elem *scope[],
076f82
 			   int lazy, int profile)
076f82
 {
076f82
   if (map->l_info[DT_JMPREL] == 0)
076f82
@@ -284,9 +284,10 @@ extern void _dl_reloc_overflow (struct link_map *map,
076f82
    LOADADDR is the load address of the object; INFO is an array indexed
076f82
    by DT_* of the .dynamic section info.  */
076f82
 
076f82
-auto inline void __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
-		  const Elf32_Sym *sym, const struct r_found_version *version,
076f82
+static inline void __attribute__ ((always_inline))
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const Elf32_Rela *reloc, const Elf32_Sym *sym,
076f82
+		  const struct r_found_version *version,
076f82
 		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf32_Addr *const reloc_addr = reloc_addr_arg;
076f82
@@ -315,7 +316,7 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
     }
076f82
   else
076f82
     {
076f82
-      sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      sym_map = RESOLVE_MAP (map, scope, &sym, version, r_type);
076f82
       value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
     }
076f82
   value += reloc->r_addend;
076f82
@@ -439,7 +440,7 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void __attribute__ ((always_inline))
076f82
+static inline void __attribute__ ((always_inline))
076f82
 elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
 {
076f82
@@ -447,8 +448,8 @@ elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
   *reloc_addr = l_addr + reloc->r_addend;
076f82
 }
076f82
 
076f82
-auto inline void __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+static inline void __attribute__ ((always_inline))
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/powerpc/powerpc64/dl-machine.h b/sysdeps/powerpc/powerpc64/dl-machine.h
076f82
index b3f3352bcf5a52b0..3f92fbb369eb5023 100644
076f82
--- a/sysdeps/powerpc/powerpc64/dl-machine.h
076f82
+++ b/sysdeps/powerpc/powerpc64/dl-machine.h
076f82
@@ -343,7 +343,8 @@ dl_platform_init (void)
076f82
 /* Set up the loaded object described by MAP so its unrelocated PLT
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 static inline int __attribute__ ((always_inline))
076f82
-elf_machine_runtime_setup (struct link_map *map, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *map, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   if (map->l_info[DT_JMPREL])
076f82
     {
076f82
@@ -618,7 +619,7 @@ extern void attribute_hidden _dl_reloc_overflow (struct link_map *map,
076f82
 						 Elf64_Addr *const reloc_addr,
076f82
 						 const Elf64_Sym *refsym);
076f82
 
076f82
-auto inline void __attribute__ ((always_inline))
076f82
+static inline void __attribute__ ((always_inline))
076f82
 elf_machine_rela_relative (Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
 {
076f82
@@ -627,7 +628,7 @@ elf_machine_rela_relative (Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
 }
076f82
 
076f82
 /* This computes the value used by TPREL* relocs.  */
076f82
-auto inline Elf64_Addr __attribute__ ((always_inline, const))
076f82
+static inline Elf64_Addr __attribute__ ((always_inline, const))
076f82
 elf_machine_tprel (struct link_map *map,
076f82
 		   struct link_map *sym_map,
076f82
 		   const Elf64_Sym *sym,
076f82
@@ -646,7 +647,7 @@ elf_machine_tprel (struct link_map *map,
076f82
 }
076f82
 
076f82
 /* Call function at address VALUE (an OPD entry) to resolve ifunc relocs.  */
076f82
-auto inline Elf64_Addr __attribute__ ((always_inline))
076f82
+static inline Elf64_Addr __attribute__ ((always_inline))
076f82
 resolve_ifunc (Elf64_Addr value,
076f82
 	       const struct link_map *map, const struct link_map *sym_map)
076f82
 {
076f82
@@ -676,8 +677,8 @@ resolve_ifunc (Elf64_Addr value,
076f82
 
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully
076f82
    resolved).  MAP is the object containing the reloc.  */
076f82
-auto inline void __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map,
076f82
+static inline void __attribute__ ((always_inline))
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		  const Elf64_Rela *reloc,
076f82
 		  const Elf64_Sym *sym,
076f82
 		  const struct r_found_version *version,
076f82
@@ -705,7 +706,7 @@ elf_machine_rela (struct link_map *map,
076f82
 
076f82
   /* We need SYM_MAP even in the absence of TLS, for elf_machine_fixup_plt
076f82
      and STT_GNU_IFUNC.  */
076f82
-  struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+  struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version, r_type);
076f82
   Elf64_Addr value = SYMBOL_ADDRESS (sym_map, sym, true) + reloc->r_addend;
076f82
 
076f82
   if (sym != NULL
076f82
@@ -1035,8 +1036,8 @@ elf_machine_rela (struct link_map *map,
076f82
   MODIFIED_CODE_NOQUEUE (reloc_addr);
076f82
 }
076f82
 
076f82
-auto inline void __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+static inline void __attribute__ ((always_inline))
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/riscv/dl-machine.h b/sysdeps/riscv/dl-machine.h
076f82
index 951268923da26a37..343c0feb6b437001 100644
076f82
--- a/sysdeps/riscv/dl-machine.h
076f82
+++ b/sysdeps/riscv/dl-machine.h
076f82
@@ -168,17 +168,18 @@ elf_machine_fixup_plt (struct link_map *map, lookup_t t,
076f82
    by RELOC_ADDR.  SYM is the relocation symbol specified by R_INFO and
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
-		  const ElfW(Sym) *sym, const struct r_found_version *version,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const ElfW(Rela) *reloc, const ElfW(Sym) *sym,
076f82
+		  const struct r_found_version *version,
076f82
 		  void *const reloc_addr, int skip_ifunc)
076f82
 {
076f82
   ElfW(Addr) r_info = reloc->r_info;
076f82
   const unsigned long int r_type = ELFW (R_TYPE) (r_info);
076f82
   ElfW(Addr) *addr_field = (ElfW(Addr) *) reloc_addr;
076f82
   const ElfW(Sym) *const __attribute__ ((unused)) refsym = sym;
076f82
-  struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+  struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version, r_type);
076f82
   ElfW(Addr) value = 0;
076f82
   if (sym_map != NULL)
076f82
     value = SYMBOL_ADDRESS (sym_map, sym, true) + reloc->r_addend;
076f82
@@ -286,7 +287,7 @@ elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
 elf_machine_rela_relative (ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
 			  void *const reloc_addr)
076f82
@@ -294,10 +295,11 @@ elf_machine_rela_relative (ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
   *(ElfW(Addr) *) reloc_addr = l_addr + reloc->r_addend;
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map, ElfW(Addr) l_addr,
076f82
-		      const ElfW(Rela) *reloc, int skip_ifunc)
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		      ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
+		      int skip_ifunc)
076f82
 {
076f82
   ElfW(Addr) *const reloc_addr = (void *) (l_addr + reloc->r_offset);
076f82
   const unsigned int r_type = ELFW (R_TYPE) (reloc->r_info);
076f82
@@ -327,9 +329,10 @@ elf_machine_lazy_rel (struct link_map *map, ElfW(Addr) l_addr,
076f82
 /* Set up the loaded object described by L so its stub function
076f82
    will jump to the on-demand fixup code __dl_runtime_resolve.  */
076f82
 
076f82
-auto inline int
076f82
+static inline int
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
 #ifndef RTLD_BOOTSTRAP
076f82
   /* If using PLTs, fill in the first two entries of .got.plt.  */
076f82
diff --git a/sysdeps/s390/s390-32/dl-machine.h b/sysdeps/s390/s390-32/dl-machine.h
076f82
index d0ccd69261c8f55b..96a5e80c846c816a 100644
076f82
--- a/sysdeps/s390/s390-32/dl-machine.h
076f82
+++ b/sysdeps/s390/s390-32/dl-machine.h
076f82
@@ -85,7 +85,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int __attribute__ ((unused))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   extern void _dl_runtime_resolve (Elf32_Word);
076f82
   extern void _dl_runtime_profile (Elf32_Word);
076f82
@@ -321,10 +322,11 @@ elf_machine_plt_value (struct link_map *map, const Elf32_Rela *reloc,
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully resolved).
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
-		  const Elf32_Sym *sym, const struct r_found_version *version,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const Elf32_Rela *reloc, const Elf32_Sym *sym,
076f82
+		  const struct r_found_version *version,
076f82
 		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf32_Addr *const reloc_addr = reloc_addr_arg;
076f82
@@ -357,7 +359,8 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
       /* Only needed for R_390_COPY below.  */
076f82
       const Elf32_Sym *const refsym = sym;
076f82
 #endif
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       Elf32_Addr value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
       if (sym != NULL
076f82
@@ -484,7 +487,7 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
 elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
@@ -493,9 +496,9 @@ elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
   *reloc_addr = l_addr + reloc->r_addend;
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/s390/s390-64/dl-machine.h b/sysdeps/s390/s390-64/dl-machine.h
076f82
index 543361c83637c071..c94d09b9c8512738 100644
076f82
--- a/sysdeps/s390/s390-64/dl-machine.h
076f82
+++ b/sysdeps/s390/s390-64/dl-machine.h
076f82
@@ -75,7 +75,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int __attribute__ ((unused))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   extern void _dl_runtime_resolve (Elf64_Word);
076f82
   extern void _dl_runtime_profile (Elf64_Word);
076f82
@@ -268,10 +269,11 @@ elf_machine_plt_value (struct link_map *map, const Elf64_Rela *reloc,
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully resolved).
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const Elf64_Rela *reloc,
076f82
-		  const Elf64_Sym *sym, const struct r_found_version *version,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const Elf64_Rela *reloc, const Elf64_Sym *sym,
076f82
+		  const struct r_found_version *version,
076f82
 		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf64_Addr *const reloc_addr = reloc_addr_arg;
076f82
@@ -304,7 +306,8 @@ elf_machine_rela (struct link_map *map, const Elf64_Rela *reloc,
076f82
       /* Only needed for R_390_COPY below.  */
076f82
       const Elf64_Sym *const refsym = sym;
076f82
 #endif
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       Elf64_Addr value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
       if (sym != NULL
076f82
@@ -438,7 +441,7 @@ elf_machine_rela (struct link_map *map, const Elf64_Rela *reloc,
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
 elf_machine_rela_relative (Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
@@ -447,9 +450,9 @@ elf_machine_rela_relative (Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
   *reloc_addr = l_addr + reloc->r_addend;
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/sh/dl-machine.h b/sysdeps/sh/dl-machine.h
076f82
index 122b417a17e2ef9b..0c22dfd8487a516e 100644
076f82
--- a/sysdeps/sh/dl-machine.h
076f82
+++ b/sysdeps/sh/dl-machine.h
076f82
@@ -69,7 +69,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int __attribute__ ((unused, always_inline))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   Elf32_Addr *got;
076f82
   extern void _dl_runtime_resolve (Elf32_Word);
076f82
@@ -259,10 +260,11 @@ elf_machine_plt_value (struct link_map *map, const Elf32_Rela *reloc,
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully resolved).
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
-		  const Elf32_Sym *sym, const struct r_found_version *version,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const Elf32_Rela *reloc, const Elf32_Sym *sym,
076f82
+		  const struct r_found_version *version,
076f82
 		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf32_Addr *const reloc_addr = reloc_addr_arg;
076f82
@@ -318,7 +320,8 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
   else
076f82
     {
076f82
       const Elf32_Sym *const refsym = sym;
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
 
076f82
       value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
       value += reloc->r_addend;
076f82
@@ -424,7 +427,7 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
 elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
@@ -443,9 +446,9 @@ elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 #undef COPY_UNALIGNED_WORD
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/sparc/sparc32/dl-machine.h b/sysdeps/sparc/sparc32/dl-machine.h
076f82
index 0269e458ea2b3bca..6361cfae9eb8fa58 100644
076f82
--- a/sysdeps/sparc/sparc32/dl-machine.h
076f82
+++ b/sysdeps/sparc/sparc32/dl-machine.h
076f82
@@ -97,7 +97,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   Elf32_Addr *plt;
076f82
   extern void _dl_runtime_resolve (Elf32_Word);
076f82
@@ -327,10 +328,11 @@ elf_machine_plt_value (struct link_map *map, const Elf32_Rela *reloc,
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully resolved).
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
-		  const Elf32_Sym *sym, const struct r_found_version *version,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const Elf32_Rela *reloc, const Elf32_Sym *sym,
076f82
+		  const struct r_found_version *version,
076f82
 		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf32_Addr *const reloc_addr = reloc_addr_arg;
076f82
@@ -381,7 +383,7 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
     }
076f82
   else
076f82
     {
076f82
-      sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      sym_map = RESOLVE_MAP (map, scope, &sym, version, r_type);
076f82
       value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
     }
076f82
 #else
076f82
@@ -536,7 +538,7 @@ elf_machine_rela (struct link_map *map, const Elf32_Rela *reloc,
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
 elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
@@ -545,9 +547,9 @@ elf_machine_rela_relative (Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
   *reloc_addr += l_addr + reloc->r_addend;
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf32_Addr l_addr, const Elf32_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/sparc/sparc64/dl-machine.h b/sysdeps/sparc/sparc64/dl-machine.h
076f82
index bbd4566d8a595f93..3fd18c6e5ef21e38 100644
076f82
--- a/sysdeps/sparc/sparc64/dl-machine.h
076f82
+++ b/sysdeps/sparc/sparc64/dl-machine.h
076f82
@@ -126,7 +126,8 @@ elf_machine_plt_value (struct link_map *map, const Elf64_Rela *reloc,
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   if (l->l_info[DT_JMPREL] && lazy)
076f82
     {
076f82
@@ -354,10 +355,11 @@ elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully resolved).
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const Elf64_Rela *reloc,
076f82
-		  const Elf64_Sym *sym, const struct r_found_version *version,
076f82
+elf_machine_rela (struct link_map *map, struct r_scope_elem *scope[],
076f82
+		  const Elf64_Rela *reloc, const Elf64_Sym *sym,
076f82
+		  const struct r_found_version *version,
076f82
 		  void *const reloc_addr_arg, int skip_ifunc)
076f82
 {
076f82
   Elf64_Addr *const reloc_addr = reloc_addr_arg;
076f82
@@ -408,7 +410,7 @@ elf_machine_rela (struct link_map *map, const Elf64_Rela *reloc,
076f82
     }
076f82
   else
076f82
     {
076f82
-      sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      sym_map = RESOLVE_MAP (map, scope, &sym, version, r_type);
076f82
       value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
     }
076f82
 #else
076f82
@@ -646,7 +648,7 @@ elf_machine_rela (struct link_map *map, const Elf64_Rela *reloc,
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
 elf_machine_rela_relative (Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
@@ -655,9 +657,9 @@ elf_machine_rela_relative (Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
   *reloc_addr = l_addr + reloc->r_addend;
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute__ ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      Elf64_Addr l_addr, const Elf64_Rela *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
diff --git a/sysdeps/x86_64/dl-machine.h b/sysdeps/x86_64/dl-machine.h
076f82
index a8596aa3fa489eff..d3fcbb37bf1f4f7c 100644
076f82
--- a/sysdeps/x86_64/dl-machine.h
076f82
+++ b/sysdeps/x86_64/dl-machine.h
076f82
@@ -62,7 +62,8 @@ elf_machine_load_address (void)
076f82
    entries will jump to the on-demand fixup code in dl-runtime.c.  */
076f82
 
076f82
 static inline int __attribute__ ((unused, always_inline))
076f82
-elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
076f82
+elf_machine_runtime_setup (struct link_map *l, struct r_scope_elem *scope[],
076f82
+			   int lazy, int profile)
076f82
 {
076f82
   Elf64_Addr *got;
076f82
   extern void _dl_runtime_resolve_fxsave (ElfW(Word)) attribute_hidden;
076f82
@@ -258,12 +259,11 @@ elf_machine_plt_value (struct link_map *map, const ElfW(Rela) *reloc,
076f82
 /* Perform the relocation specified by RELOC and SYM (which is fully resolved).
076f82
    MAP is the object containing the reloc.  */
076f82
 
076f82
-auto inline void
076f82
-__attribute__ ((always_inline))
076f82
-elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
-		  const ElfW(Sym) *sym, const struct r_found_version *version,
076f82
-		  void *const reloc_addr_arg, int skip_ifunc)
076f82
-{
076f82
+static inline void __attribute__((always_inline))
076f82
+elf_machine_rela(struct link_map *map, struct r_scope_elem *scope[],
076f82
+		 const ElfW(Rela) *reloc, const ElfW(Sym) *sym,
076f82
+		 const struct r_found_version *version,
076f82
+		 void *const reloc_addr_arg, int skip_ifunc) {
076f82
   ElfW(Addr) *const reloc_addr = reloc_addr_arg;
076f82
   const unsigned long int r_type = ELFW(R_TYPE) (reloc->r_info);
076f82
 
076f82
@@ -300,7 +300,8 @@ elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
076f82
 # ifndef RTLD_BOOTSTRAP
076f82
       const ElfW(Sym) *const refsym = sym;
076f82
 # endif
076f82
-      struct link_map *sym_map = RESOLVE_MAP (&sym, version, r_type);
076f82
+      struct link_map *sym_map = RESOLVE_MAP (map, scope, &sym, version,
076f82
+					      r_type);
076f82
       ElfW(Addr) value = SYMBOL_ADDRESS (sym_map, sym, true);
076f82
 
076f82
       if (sym != NULL
076f82
@@ -525,7 +526,7 @@ and creates an unsatisfiable circular dependency.\n",
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute ((always_inline))
076f82
 elf_machine_rela_relative (ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
 			   void *const reloc_addr_arg)
076f82
@@ -544,9 +545,9 @@ elf_machine_rela_relative (ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
     }
076f82
 }
076f82
 
076f82
-auto inline void
076f82
+static inline void
076f82
 __attribute ((always_inline))
076f82
-elf_machine_lazy_rel (struct link_map *map,
076f82
+elf_machine_lazy_rel (struct link_map *map, struct r_scope_elem *scope[],
076f82
 		      ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
076f82
 		      int skip_ifunc)
076f82
 {
076f82
@@ -580,7 +581,7 @@ elf_machine_lazy_rel (struct link_map *map,
076f82
 
076f82
       /* Always initialize TLS descriptors completely at load time, in
076f82
 	 case static TLS is allocated for it that requires locking.  */
076f82
-      elf_machine_rela (map, reloc, sym, version, reloc_addr, skip_ifunc);
076f82
+      elf_machine_rela (map, scope, reloc, sym, version, reloc_addr, skip_ifunc);
076f82
     }
076f82
   else if (__glibc_unlikely (r_type == R_X86_64_IRELATIVE))
076f82
     {