This is the mail archive of the
libc-alpha@sources.redhat.com
mailing list for the glibc project.
[patch] unaligned traps in dynamic linker on alpha
- To: libc-alpha at sources dot redhat dot com
- Subject: [patch] unaligned traps in dynamic linker on alpha
- From: Ivan Kokshaysky <ink at jurassic dot park dot msu dot ru>
- Date: Mon, 18 Sep 2000 19:35:56 +0400
Hi!
Regarding the change in sysdeps/alpha/dl-machine.h:
(elf_machine_rela) [r_type == R_ALPHA_REFQUAD]: Use memcpy to load and
store value from relocation address to prevent unaligned trap.
Probably it was an attempt to fix long standing problem with
unaligned traps in dynamic linker loading libstdc++. There are
unaligned relocations in libstdc++ from gcc-2.95 and later
(dwarf2 info), but their type is R_ALPHA_RELATIVE, not R_ALPHA_REFQUAD.
Here is a fix.
Ivan.
2000-09-13 Ivan Kokshaysky <ink@jurassic.park.msu.ru>
* sysdeps/alpha/dl-machine.h (elf_machine_rela)
[r_type == R_ALPHA_RELATIVE]: Use memcpy to load and
store value from relocation address to prevent unaligned
traps. Back out change for R_ALPHA_REFQUAD.
Index: dl-machine.h
===================================================================
RCS file: /cvs/glibc/libc/sysdeps/alpha/dl-machine.h,v
retrieving revision 1.44
diff -u -r1.44 dl-machine.h
--- dl-machine.h 2000/07/18 14:14:51 1.44
+++ dl-machine.h 2000/09/13 16:30:58
@@ -482,7 +482,17 @@
/* Already done in dynamic linker. */
if (map != &_dl_rtld_map)
#endif
- *reloc_addr += map->l_addr;
+ {
+ void *reloc_addr_1 = reloc_addr;
+ Elf64_Addr reloc_addr_val;
+
+ /* Load value without causing unaligned trap. */
+ memcpy (&reloc_addr_val, reloc_addr_1, 8);
+ reloc_addr_val += map->l_addr;
+
+ /* Store value without causing unaligned trap. */
+ memcpy (reloc_addr_1, &reloc_addr_val, 8);
+ }
}
else if (r_type == R_ALPHA_NONE)
return;
@@ -500,12 +510,7 @@
elf_machine_fixup_plt (map, 0, reloc, reloc_addr, sym_value);
else if (r_type == R_ALPHA_REFQUAD)
{
- void *reloc_addr_1 = reloc_addr;
- Elf64_Addr reloc_addr_val;
-
- /* Load value without causing unaligned trap. */
- memcpy (&reloc_addr_val, reloc_addr_1, 8);
- sym_value += reloc_addr_val;
+ sym_value += *reloc_addr;
#ifndef RTLD_BOOTSTRAP
if (map == &_dl_rtld_map)
{
@@ -521,8 +526,7 @@
sym_value -= reloc->r_addend;
}
#endif
- /* Store value without causing unaligned trap. */
- memcpy (reloc_addr_1, &sym_value, 8);
+ *reloc_addr = sym_value;
}
else
_dl_reloc_bad_type (map, r_type, 0);