summaryrefslogtreecommitdiffstats
path: root/libexec
diff options
context:
space:
mode:
authorjake <jake@FreeBSD.org>2003-07-04 00:05:15 +0000
committerjake <jake@FreeBSD.org>2003-07-04 00:05:15 +0000
commit151e14e2da5e1512f32502b7ad34944e43e35c8f (patch)
tree859d240ec400844a7362d33581c44ad51def1e8f /libexec
parentd79bb2b0f8355fbfdd85ffaeda3a2ac2d9ad6caf (diff)
downloadFreeBSD-src-151e14e2da5e1512f32502b7ad34944e43e35c8f.zip
FreeBSD-src-151e14e2da5e1512f32502b7ad34944e43e35c8f.tar.gz
Avoid using the global offset table to get the address of _DYNAMIC in
rtld. When _DYNAMIC is referenced normally from C the global offset table is used implicitly, but newer versions of binutils don't initialize it statically in the binary, so this doesn't work until rtld is relocated, which _DYNAMIC is needed for... So, as on other systems with the same problem, we disassemble a call instruction to _DYNAMIC in order to get its address.
Diffstat (limited to 'libexec')
-rw-r--r--libexec/rtld-elf/sparc64/rtld_machdep.h2
-rw-r--r--libexec/rtld-elf/sparc64/rtld_start.S17
2 files changed, 18 insertions, 1 deletions
diff --git a/libexec/rtld-elf/sparc64/rtld_machdep.h b/libexec/rtld-elf/sparc64/rtld_machdep.h
index 9efadca..d92055c 100644
--- a/libexec/rtld-elf/sparc64/rtld_machdep.h
+++ b/libexec/rtld-elf/sparc64/rtld_machdep.h
@@ -37,7 +37,7 @@
struct Struct_Obj_Entry;
/* Return the address of the .dynamic section in the dynamic linker. */
-#define rtld_dynamic(obj) ((Elf_Dyn *)(((char *)&_DYNAMIC) + (vm_offset_t)(obj)->relocbase))
+Elf_Dyn *rtld_dynamic(const struct Struct_Obj_Entry *);
Elf_Addr reloc_jmpslot(Elf_Addr *, Elf_Addr,
const struct Struct_Obj_Entry *,
diff --git a/libexec/rtld-elf/sparc64/rtld_start.S b/libexec/rtld-elf/sparc64/rtld_start.S
index f9d05b7..146c6314 100644
--- a/libexec/rtld-elf/sparc64/rtld_start.S
+++ b/libexec/rtld-elf/sparc64/rtld_start.S
@@ -67,6 +67,23 @@ ENTRY(.rtld_start)
mov %l0, %o0
END(.rtld_start)
+/*
+ * Find the address of _DYNAMIC by disassembling a call instruction to it.
+ * Binutils may not fill in the GOT as expected on other architectures.
+ */
+
+ENTRY(rtld_dynamic)
+ save %sp, -CCFSZ, %sp
+ call 1f
+ nop
+ call _DYNAMIC + 8
+1: lduw [%o7 + 8], %o0
+ sll %o0, 2, %o0
+ sra %o0, 0, %o0
+ ret
+ restore %o0, %o7, %o0
+END(rtld_dynamic)
+
/*
* We have two separate entry points to the runtime linker.
* I'm implementing this following the SPARC v9 ABI spec.
OpenPOWER on IntegriCloud