summaryrefslogtreecommitdiffstats
path: root/sys/boot/i386
diff options
context:
space:
mode:
authorrpaulo <rpaulo@FreeBSD.org>2012-12-07 07:02:39 +0000
committerrpaulo <rpaulo@FreeBSD.org>2012-12-07 07:02:39 +0000
commit5bdf25a9c88254f5640d9463486c7c9bad8652d8 (patch)
tree47db7818f6ec0bfed2696ae433b16bb7501505de /sys/boot/i386
parent59b6b1dc68694b70ded1201a7781b360d23da79c (diff)
downloadFreeBSD-src-5bdf25a9c88254f5640d9463486c7c9bad8652d8.zip
FreeBSD-src-5bdf25a9c88254f5640d9463486c7c9bad8652d8.tar.gz
Make this work for 64 bit binaries.
Diffstat (limited to 'sys/boot/i386')
-rw-r--r--sys/boot/i386/efi/reloc.c31
1 files changed, 22 insertions, 9 deletions
diff --git a/sys/boot/i386/efi/reloc.c b/sys/boot/i386/efi/reloc.c
index 96f9241..22c6642 100644
--- a/sys/boot/i386/efi/reloc.c
+++ b/sys/boot/i386/efi/reloc.c
@@ -28,21 +28,31 @@
__FBSDID("$FreeBSD$");
#include <sys/types.h>
-#include <sys/elf32.h>
+#include <elf.h>
#include <efi.h>
#include <bootstrap.h>
+#ifdef __i386__
+#define ElfW_Rel Elf32_Rel
+#define ElfW_Dyn Elf32_Dyn
+#define ELFW_R_TYPE ELF32_R_TYPE
+#elif __amd64__
+#define ElfW_Rel Elf64_Rel
+#define ElfW_Dyn Elf64_Dyn
+#define ELFW_R_TYPE ELF64_R_TYPE
+#endif
+
/*
- * A simple relocator for IA32 EFI binaries.
+ * A simple relocator for IA32/AMD64 EFI binaries.
*/
EFI_STATUS
-_reloc(unsigned long ImageBase, Elf32_Dyn *dynamic, EFI_HANDLE image_handle,
+_reloc(unsigned long ImageBase, ElfW_Dyn *dynamic, EFI_HANDLE image_handle,
EFI_SYSTEM_TABLE *system_table)
{
unsigned long relsz, relent;
unsigned long *newaddr;
- Elf32_Rel *rel;
- Elf32_Dyn *dynp;
+ ElfW_Rel *rel;
+ ElfW_Dyn *dynp;
/*
* Find the relocation address, its size and the relocation entry.
@@ -51,14 +61,17 @@ _reloc(unsigned long ImageBase, Elf32_Dyn *dynamic, EFI_HANDLE image_handle,
relent = 0;
for (dynp = dynamic; dynp->d_tag != DT_NULL; dynp++) {
switch (dynp->d_tag) {
+ case DT_RELA:
case DT_REL:
- rel = (Elf32_Rel *) ((unsigned long) dynp->d_un.d_ptr +
+ rel = (ElfW_Rel *) ((unsigned long) dynp->d_un.d_ptr +
ImageBase);
break;
case DT_RELSZ:
+ case DT_RELASZ:
relsz = dynp->d_un.d_val;
break;
case DT_RELENT:
+ case DT_RELAENT:
relent = dynp->d_un.d_val;
break;
default:
@@ -74,7 +87,7 @@ _reloc(unsigned long ImageBase, Elf32_Dyn *dynamic, EFI_HANDLE image_handle,
CTASSERT(R_386_NONE == R_X86_64_NONE);
CTASSERT(R_386_RELATIVE == R_X86_64_RELATIVE);
for (; relsz > 0; relsz -= relent) {
- switch (ELF32_R_TYPE(rel->r_info)) {
+ switch (ELFW_R_TYPE(rel->r_info)) {
case R_386_NONE:
/* No relocation needs be performed. */
break;
@@ -85,9 +98,9 @@ _reloc(unsigned long ImageBase, Elf32_Dyn *dynamic, EFI_HANDLE image_handle,
break;
default:
/* XXX: do we need other relocations ? */
- return (EFI_LOAD_ERROR);
+ break;
}
- rel = (Elf32_Rel *) ((caddr_t) rel + relent);
+ rel = (ElfW_Rel *) ((caddr_t) rel + relent);
}
return (EFI_SUCCESS);
OpenPOWER on IntegriCloud