Usermode/ld-acess - Adding elf64 support
authorJohn Hodge <[email protected]>
Mon, 26 Sep 2011 05:07:53 +0000 (13:07 +0800)
committerJohn Hodge <[email protected]>
Mon, 26 Sep 2011 05:07:53 +0000 (13:07 +0800)
- Created stub library file for linking against
 > Stops ld-acess having to be compiled with -fPIC

14 files changed:
Usermode/Libraries/ld-acess.so_src/Makefile
Usermode/Libraries/ld-acess.so_src/_stublib.c [new file with mode: 0644]
Usermode/Libraries/ld-acess.so_src/arch/x86.asm.h
Usermode/Libraries/ld-acess.so_src/arch/x86.ld
Usermode/Libraries/ld-acess.so_src/arch/x86_64.asm.h
Usermode/Libraries/ld-acess.so_src/arch/x86_64.ld
Usermode/Libraries/ld-acess.so_src/common.h
Usermode/Libraries/ld-acess.so_src/elf.c
Usermode/Libraries/ld-acess.so_src/elf32.h
Usermode/Libraries/ld-acess.so_src/elf64.h [new file with mode: 0644]
Usermode/Libraries/ld-acess.so_src/lib.c
Usermode/Libraries/ld-acess.so_src/loadlib.c
Usermode/Libraries/ld-acess.so_src/main.c
Usermode/Libraries/ld-acess.so_src/pe.c

index 4b99ecd..a29dd4b 100644 (file)
@@ -16,9 +16,11 @@ LDFLAGS  = -g -T arch/$(ARCHDIR).ld -Map map.txt --export-dynamic
 include ../Makefile.tpl
 
 # create libld-acess.so
-$(_XBIN): $(_BIN)
+$(_XBIN): $(_OBJPREFIX)_stublib.o
        @echo [LD] -o -shared libld-acess.so
-       @$(LD) $(LDFLAGS) -shared -o $@ $(OBJ)
+       $(LD) -shared -o $@ $<
+#      @$(LD) $(LDFLAGS) -o $@ $(OBJ)
+
 
 # Override .ao to look in the object prefix for the source
 %.ao: %.asm
diff --git a/Usermode/Libraries/ld-acess.so_src/_stublib.c b/Usermode/Libraries/ld-acess.so_src/_stublib.c
new file mode 100644 (file)
index 0000000..6107c69
--- /dev/null
@@ -0,0 +1,13 @@
+
+int _errno;
+
+#define SYSCALL0(name,num)     void name(void){}
+#define SYSCALL1(name,num)     void name(void){}
+#define SYSCALL2(name,num)     void name(void){}
+#define SYSCALL3(name,num)     void name(void){}
+#define SYSCALL4(name,num)     void name(void){}
+#define SYSCALL5(name,num)     void name(void){}
+#define SYSCALL6(name,num)     void name(void){}
+
+#include "arch/syscalls.s.h"
+
index 9e45273..a569637 100644 (file)
 _errno:        dw      0
 
 [section .text]
+[global _start]
+[extern SoMain]
+_start:
+       call SoMain
+
+       add esp, 4
+       call eax
+
+       push eax
+       call _exit
+
 ; DEST
 ; SRC
 _memcpy:
index cffe74c..fdfe5e9 100644 (file)
@@ -7,6 +7,20 @@
 [bits 64]
 
 [section .text]
+[global _start]
+[extern SoMain]
+_start:
+       pop rdi
+       call SoMain
+       
+       mov rdi, [rsp]
+       mov rsi, [rsp+8]
+       mov rdx, [rsp+16]
+       call rax
+       
+       mov rdi, rax
+       call _exit
+
 ; DEST
 ; SRC
 _memcpy:
index 7d95540..941baf3 100644 (file)
@@ -37,11 +37,11 @@ typedef struct {
 extern tLoadedLib      gLoadedLibraries[MAX_LOADED_LIBRARIES];
 
 // === Main ===
-extern void    *DoRelocate(void *Base, char **envp, char *Filename);
+extern void    *DoRelocate(void *Base, char **envp, const char *Filename);
 
 // === Library/Symbol Manipulation ==
-extern void    *LoadLibrary(char *filename, char *SearchDir, char **envp);
-extern void    AddLoaded(char *File, void *base);
+extern void    *LoadLibrary(const char *Filename, const char *SearchDir, char **envp);
+extern void    AddLoaded(const char *File, void *base);
 extern void    *GetSymbol(const char *name);
 extern int     GetSymbolFromBase(void *base, const char *name, void **ret);
 
@@ -50,7 +50,7 @@ extern char   *strcpy(char *dest, const char *src);
 extern char    *strcat(char *dest, const char *src);
 extern int     strcmp(const char *s1, const char *s2);
 extern int     strlen(const char *str);
-extern int     file_exists(char *filename);
+extern int     file_exists(const char *filename);
 
 // === System Calls ===
 extern void    _exit(int retval);
@@ -66,6 +66,6 @@ extern int    close(int fd);
 extern int     ElfGetSymbol(void *Base, const char *name, void **ret);
 
 // === PE Loader ===
-extern int     PE_GetSymbol(void *Base, char *Name, void **ret);
+extern int     PE_GetSymbol(void *Base, const char *Name, void **ret);
 
 #endif
index b969a19..c45c481 100644 (file)
@@ -5,11 +5,12 @@
 #include "common.h"
 #include <stdint.h>
 #include "elf32.h"
+#include "elf64.h"
 
-#define DEBUG  0
+#define DEBUG  1
 
 #if DEBUG
-# define       DEBUGS(v...)    SysDebug(v)
+# define       DEBUGS(v...)    SysDebug("ld-acess - " v)
 #else
 # define       DEBUGS(...)     
 #endif
@@ -21,14 +22,220 @@ static const char  *csaR_NAMES[] = {"R_386_NONE", "R_386_32", "R_386_PC32", "R_38
 #endif
 
 // === PROTOTYPES ===
-Uint32 ElfHashString(const char *name);
+void   *ElfRelocate(void *Base, char **envp, const char *Filename);
+void   *Elf32Relocate(void *Base, char **envp, const char *Filename);
+void   *Elf64Relocate(void *Base, char **envp, const char *Filename);
+Uint32 ElfHashString(const char *name);
 
 // === CODE ===
 /**
- \fn int ElfRelocate(void *Base, char **envp, char *Filename)
- \brief Relocates a loaded ELF Executable
-*/
-void *ElfRelocate(void *Base, char **envp, char *Filename)
+ * \fn int ElfRelocate(void *Base, char **envp, const char *Filename)
+ * \brief Relocates a loaded ELF Executable
+ */
+void *ElfRelocate(void *Base, char **envp, const char *Filename)
+{
+       Elf32_Ehdr      *hdr = Base;
+       
+       switch(hdr->e_ident[4])
+       {
+       case ELFCLASS32:
+               return Elf32Relocate(Base, envp, Filename);
+       case ELFCLASS64:
+               return Elf64Relocate(Base, envp, Filename);
+       default:
+               SysDebug("ld-acess - ElfRelocate: Unknown file class %i", hdr->e_ident[4]);
+               return NULL;
+       }
+}
+
+void *Elf64Relocate(void *Base, char **envp, const char *Filename)
+{
+        int    i;
+       Elf64_Ehdr      *hdr = Base;
+       Elf64_Phdr      *phtab;
+       Elf64_Dyn       *dyntab;
+       Elf64_Addr      compiledBase = -1, baseDiff;
+       Elf64_Sym       *symtab = NULL;
+       char    *strtab = NULL;
+       Elf64_Word      *hashtab = NULL;
+       Elf64_Rel       *rel = NULL;
+        int    rel_count = 0;
+       Elf64_Rela      *rela = NULL;
+        int    rela_count = 0;
+       void    *pltrel = NULL;
+        int    plt_size = 0, plt_type = 0;
+
+       DEBUGS("Elf64Relocate: e_ident = '%.16s'", hdr->e_ident);
+       DEBUGS("Elf64Relocate: e_phoff = %i, e_phnum = %i",
+               hdr->e_phoff, hdr->e_phnum);
+
+       // Scan for the dynamic table (and find the compiled base)
+       phtab = Base + hdr->e_phoff;
+       for( i = 0; i < hdr->e_phnum; i ++ )
+       {
+               if(phtab[i].p_type == PT_DYNAMIC)
+                       dyntab = (void *)phtab[i].p_vaddr;
+               if(phtab[i].p_type == PT_LOAD && compiledBase > phtab[i].p_vaddr)
+                       compiledBase = phtab[i].p_vaddr;
+       }
+
+       baseDiff = (Elf64_Addr)Base - compiledBase;
+
+       DEBUGS("baseDiff = %p", baseDiff);
+
+       if(dyntab == NULL) {
+               SysDebug(" Elf64Relocate: No PT_DYNAMIC segment in image %p, returning", Base);
+               return (void *)(hdr->e_entry + baseDiff);
+       }
+
+       dyntab = (void *)((Elf64_Addr)dyntab + baseDiff);
+
+       // Parse the dynamic table (first pass)
+       // - Search for String, Symbol and Hash tables
+       for(i = 0; dyntab[i].d_tag != DT_NULL; i ++)
+       {
+               switch(dyntab[i].d_tag)
+               {
+               case DT_SYMTAB:
+                       dyntab[i].d_un.d_ptr += baseDiff;
+                       symtab = (void *)dyntab[i].d_un.d_ptr;
+                       break;
+               case DT_STRTAB:
+                       dyntab[i].d_un.d_ptr += baseDiff;
+                       strtab = (void *)dyntab[i].d_un.d_ptr;
+                       break;
+               case DT_HASH:
+                       dyntab[i].d_un.d_ptr += baseDiff;
+                       hashtab = (void *)dyntab[i].d_un.d_ptr;
+                       break;
+               }
+       }
+
+       if( !symtab || !strtab || !hashtab ) {
+               SysDebug("ld-acess - Elf64Relocate: Missing Symbol, string or hash table");
+               return NULL;
+       }
+
+       // Ready for symbol use 
+       AddLoaded( Filename, Base );
+
+       // Second pass on dynamic table
+       for(i = 0; dyntab[i].d_tag != DT_NULL; i ++)
+       {
+               switch(dyntab[i].d_tag)
+               {
+               case DT_SONAME: break;
+
+               case DT_NEEDED: {
+                       char *libPath = strtab + dyntab[i].d_un.d_val;
+                       if(LoadLibrary(libPath, NULL, envp) == 0) {
+                               SysDebug("ld-acess - Elf64Relocate: Unable to load '%s'", libPath);
+                               return NULL;
+                       }
+                       } break;
+               
+               // Relocation entries
+               case DT_REL:
+                       dyntab[i].d_un.d_ptr += baseDiff;
+                       rel = (void *)dyntab[i].d_un.d_ptr;
+                       break;
+               case DT_RELSZ:
+                       rel_count = dyntab[i].d_un.d_val / sizeof(Elf64_Rel);
+                       break;
+               case DT_RELENT:
+                       if( dyntab[i].d_un.d_val != sizeof(Elf64_Rel) ) {
+                               SysDebug("ld-acess - Elf64Relocate: DT_RELENT(%i) != sizeof(Elf64_Rel)(%i)",
+                                       dyntab[i].d_un.d_val, sizeof(Elf64_Rel));
+                               return NULL;
+                       }
+                       break;
+               case DT_RELA:
+                       dyntab[i].d_un.d_ptr += baseDiff;
+                       rela = (void *)dyntab[i].d_un.d_ptr;
+                       break;
+               case DT_RELASZ:
+                       rela_count = dyntab[i].d_un.d_val / sizeof(Elf64_Rela);
+                       break;
+               case DT_RELAENT:
+                       if( dyntab[i].d_un.d_val != sizeof(Elf64_Rela) ) {
+                               SysDebug("ld-acess - Elf64Relocate: DT_RELAENT(%i) != sizeof(Elf64_Rela)(%i)",
+                                       dyntab[i].d_un.d_val, sizeof(Elf64_Rela));
+                               return NULL;
+                       }
+                       break;
+               case DT_JMPREL:
+                       dyntab[i].d_un.d_ptr += baseDiff;
+                       pltrel = (void *)dyntab[i].d_un.d_ptr;
+                       break;
+               case DT_PLTREL:
+                       plt_type = dyntab[i].d_un.d_val;
+                       break;
+               case DT_PLTRELSZ:
+                       plt_size = dyntab[i].d_un.d_val;
+                       break;
+               }
+       }
+
+       // Relocation function
+       void _Elf64DoReloc(Elf64_Xword r_info, void *ptr, Elf64_Sxword addend)
+       {
+                int    sym = ELF64_R_SYM(r_info);
+                int    type = ELF64_R_TYPE(r_info);
+               const char      *symname = strtab + symtab[sym].st_name;
+               switch( type )
+               {
+               case R_X86_64_NONE:
+                       break;
+               case R_X86_64_64:
+                       *(uint64_t*)ptr = (uint64_t)GetSymbol(symname) + addend;
+                       break;
+               default:
+                       SysDebug("ld-acess - _Elf64DoReloc: Unknown relocation type %i", type);
+               }
+       }
+
+       if( rel )
+       {
+               for( i = 0; i < rel_count; i ++ )
+               {
+                       uint64_t *ptr = (void *)( rel[i].r_offset + baseDiff );
+                       _Elf64DoReloc( rel[i].r_info, ptr, *ptr);
+               }
+       }
+
+       if( rela )
+       {
+               for( i = 0; i < rela_count; i ++ )
+               {
+                       _Elf64DoReloc( rela[i].r_info, (void *)( rela[i].r_offset + baseDiff ), rela[i].r_addend );
+               }
+       }
+
+       if( pltrel && plt_type )
+       {
+               if( plt_type == DT_REL ) {
+                       Elf64_Rel       *plt = pltrel;
+                        int    count = plt_size / sizeof(Elf64_Rel);
+                       for( i = 0; i < count; i ++ )
+                       {
+                               uint64_t *ptr = (void *)( plt[i].r_offset + baseDiff );
+                               _Elf64DoReloc( plt[i].r_info, ptr, *ptr);
+                       }
+               }
+               else {
+                       Elf64_Rela      *plt = pltrel;
+                        int    count = plt_size / sizeof(Elf64_Rela);
+                       for( i = 0; i < count; i ++ )
+                       {
+                               _Elf64DoReloc( plt[i].r_info, (void *)(plt[i].r_offset + baseDiff), plt[i].r_addend);
+                       }
+               }
+       }
+
+       return (void *)(hdr->e_entry + baseDiff);
+}
+
+void *Elf32Relocate(void *Base, char **envp, const char *Filename)
 {
        Elf32_Ehdr      *hdr = Base;
        Elf32_Phdr      *phtab;
@@ -155,7 +362,7 @@ void *ElfRelocate(void *Base, char **envp, char *Filename)
                        DEBUGS(" Required Library '%s'", libPath);
                        if(LoadLibrary(libPath, NULL, envp) == 0) {
                                #if DEBUG
-                                       DEBUGS(" elf_relocate: Unable to load '%s'", libPath);
+                               DEBUGS(" elf_relocate: Unable to load '%s'", libPath);
                                #else
                                SysDebug("Unable to load required library '%s'", libPath);
                                #endif
@@ -216,7 +423,7 @@ void *ElfRelocate(void *Base, char **envp, char *Filename)
                        DEBUGS(" elf_doRelocate: #%i: '%s'", sym, symname);
                        val = (intptr_t) GetSymbol( symname );
                        DEBUGS(" elf_doRelocate: R_386_PC32 *0x%x = 0x%x + 0x%x - 0x%x",
-                               ptr, *ptr, val, (Uint)ptr );
+                               ptr, *ptr, val, (intptr_t)ptr );
                        *ptr = val + addend - (intptr_t)ptr;
                        //*ptr = val + addend - ((Uint)ptr - iBaseDiff);
                        break;
@@ -343,7 +550,7 @@ int ElfGetSymbol(void *Base, const char *Name, void **ret)
                        if(phtab[i].Type == PT_LOAD && iBaseDiff > phtab[i].VAddr)
                                iBaseDiff = phtab[i].VAddr;
                        if( phtab[i].Type == PT_DYNAMIC ) {
-                               dynTab = (void*)phtab[i].VAddr;
+                               dynTab = (void*)(intptr_t)phtab[i].VAddr;
                        }
                }
                if( !dynTab ) {
index 5e43987..983917b 100644 (file)
-/**\r
- Acess v1\r
- \file elf32.h\r
- \brief ELF Exeutable Loader\r
-*/\r
-#ifndef _ELF32_H\r
-#define _ELF32_H\r
-\r
-/**\r
- \struct elf_header_s\r
- \brief ELF File Header\r
-*/\r
-struct sElf32_Ehdr {\r
-       union {\r
-               char    ident[16];      //!< Identifier Bytes\r
-               struct {\r
-                       Uint32  Ident1;\r
-                       Uint32  StrTab;\r
-                       Uint32  HashTable;\r
-                       Uint32  SymTable;\r
-               } misc;\r
-       };\r
-       Uint16  filetype;       //!< File Type\r
-       Uint16  machine;        //!< Machine / Arch\r
-       Uint32  version;        //!< Version (File?)\r
-       Uint32  entrypoint;     //!< Entry Point\r
-       Uint32  phoff;  //!< Program Header Offset\r
-       Uint32  shoff;  //!< Section Header Offset\r
-       Uint32  flags;  //!< Flags\r
-       Uint16  headersize;     //!< Header Size\r
-       Uint16  phentsize;      //!< Program Header Entry Size\r
-       Uint16  phentcount;     //!< Program Header Entry Count\r
-       Uint16  shentsize;      //!< Section Header Entry Size\r
-       Uint16  shentcount;     //!< Section Header Entry Count\r
-       Uint16  shstrindex;     //!< Section Header String Table Index\r
-};\r
-\r
-/**\r
- \name Executable Types\r
- \{\r
-*/\r
-#define        ET_NONE         0       //!< NULL Type\r
-#define        ET_REL          1       //!< Relocatable (Object)\r
-#define ET_EXEC                2       //!< Executable\r
-#define ET_DYN         3       //!< Dynamic Library\r
-#define ET_CORE                4       //!< Core?\r
-#define ET_LOPROC      0xFF00  //!< Low Impl Defined\r
-#define ET_HIPROC      0xFFFF  //!< High Impl Defined\r
-//! \}\r
-\r
-/**\r
- \name Section IDs\r
- \{\r
-*/\r
-#define SHN_UNDEF              0       //!< Undefined Section\r
-#define SHN_LORESERVE  0xFF00  //!< Low Reserved\r
-#define SHN_LOPROC             0xFF00  //!< Low Impl Defined\r
-#define SHN_HIPROC             0xFF1F  //!< High Impl Defined\r
-#define SHN_ABS                        0xFFF1  //!< Absolute Address (Base: 0, Size: -1)\r
-#define SHN_COMMON             0xFFF2  //!< Common\r
-#define SHN_HIRESERVE  0xFFFF  //!< High Reserved\r
-//! \}\r
-\r
-/**\r
- \enum eElfSectionTypes\r
- \brief ELF Section Types\r
-*/\r
-enum eElfSectionTypes {\r
-       SHT_NULL,       //0\r
-       SHT_PROGBITS,   //1\r
-       SHT_SYMTAB,     //2\r
-       SHT_STRTAB,     //3\r
-       SHT_RELA,       //4\r
-       SHT_HASH,       //5\r
-       SHT_DYNAMIC,    //6\r
-       SHT_NOTE,       //7\r
-       SHT_NOBITS,     //8\r
-       SHT_REL,        //9\r
-       SHT_SHLIB,      //A\r
-       SHT_DYNSYM,     //B\r
-       SHT_LAST,       //C\r
-       SHT_LOPROC = 0x70000000,\r
-       SHT_HIPROC = 0x7fffffff,\r
-       SHT_LOUSER = 0x80000000,\r
-       SHT_HIUSER = 0xffffffff\r
-};\r
-\r
-#define SHF_WRITE      0x1\r
-#define SHF_ALLOC      0x2\r
-#define SHF_EXECINSTR  0x4\r
-#define SHF_MASKPROC   0xf0000000\r
-\r
-struct sElf32_Shent {\r
-       Uint32  name;\r
-       Uint32  type;\r
-       Uint32  flags;\r
-       Uint32  address;\r
-       Uint32  offset;\r
-       Uint32  size;\r
-       Uint32  link;\r
-       Uint32  info;\r
-       Uint32  addralign;\r
-       Uint32  entsize;\r
-};     //sizeof = 40\r
-\r
+/**
+ Acess v1
+ \file elf32.h
+ \brief ELF Exeutable Loader
+*/
+#ifndef _ELF32_H
+#define _ELF32_H
+
+#define ELFCLASS32     1
+
+/**
+ \struct elf_header_s
+ \brief ELF File Header
+*/
+struct sElf32_Ehdr {
+       Uint8   e_ident[16];    //!< Identifier Bytes
+       Uint16  filetype;       //!< File Type
+       Uint16  machine;        //!< Machine / Arch
+       Uint32  version;        //!< Version (File?)
+       Uint32  entrypoint;     //!< Entry Point
+       Uint32  phoff;  //!< Program Header Offset
+       Uint32  shoff;  //!< Section Header Offset
+       Uint32  flags;  //!< Flags
+       Uint16  headersize;     //!< Header Size
+       Uint16  phentsize;      //!< Program Header Entry Size
+       Uint16  phentcount;     //!< Program Header Entry Count
+       Uint16  shentsize;      //!< Section Header Entry Size
+       Uint16  shentcount;     //!< Section Header Entry Count
+       Uint16  shstrindex;     //!< Section Header String Table Index
+};
+
+/**
+ \name Executable Types
+ \{
+*/
+#define        ET_NONE         0       //!< NULL Type
+#define        ET_REL          1       //!< Relocatable (Object)
+#define ET_EXEC                2       //!< Executable
+#define ET_DYN         3       //!< Dynamic Library
+#define ET_CORE                4       //!< Core?
+#define ET_LOPROC      0xFF00  //!< Low Impl Defined
+#define ET_HIPROC      0xFFFF  //!< High Impl Defined
+//! \}
+
+/**
+ \name Section IDs
+ \{
+*/
+#define SHN_UNDEF              0       //!< Undefined Section
+#define SHN_LORESERVE  0xFF00  //!< Low Reserved
+#define SHN_LOPROC             0xFF00  //!< Low Impl Defined
+#define SHN_HIPROC             0xFF1F  //!< High Impl Defined
+#define SHN_ABS                        0xFFF1  //!< Absolute Address (Base: 0, Size: -1)
+#define SHN_COMMON             0xFFF2  //!< Common
+#define SHN_HIRESERVE  0xFFFF  //!< High Reserved
+//! \}
+
+/**
+ \enum eElfSectionTypes
+ \brief ELF Section Types
+*/
+enum eElfSectionTypes {
+       SHT_NULL,       //0
+       SHT_PROGBITS,   //1
+       SHT_SYMTAB,     //2
+       SHT_STRTAB,     //3
+       SHT_RELA,       //4
+       SHT_HASH,       //5
+       SHT_DYNAMIC,    //6
+       SHT_NOTE,       //7
+       SHT_NOBITS,     //8
+       SHT_REL,        //9
+       SHT_SHLIB,      //A
+       SHT_DYNSYM,     //B
+       SHT_LAST,       //C
+       SHT_LOPROC = 0x70000000,
+       SHT_HIPROC = 0x7fffffff,
+       SHT_LOUSER = 0x80000000,
+       SHT_HIUSER = 0xffffffff
+};
+
+#define SHF_WRITE      0x1
+#define SHF_ALLOC      0x2
+#define SHF_EXECINSTR  0x4
+#define SHF_MASKPROC   0xf0000000
+
+struct sElf32_Shent {
+       Uint32  name;
+       Uint32  type;
+       Uint32  flags;
+       Uint32  address;
+       Uint32  offset;
+       Uint32  size;
+       Uint32  link;
+       Uint32  info;
+       Uint32  addralign;
+       Uint32  entsize;
+};     //sizeof = 40
+
 struct elf_sym_s {
        Uint32  nameOfs;
-       Uint32  value;  //Address\r
-       Uint32  size;\r
-       Uint8   info;\r
-       Uint8   other;\r
-       Uint16  shndx;\r
-};\r
-#define        STN_UNDEF       0       // Undefined Symbol\r
-\r
-enum {\r
-       PT_NULL,        //0\r
-       PT_LOAD,        //1\r
-       PT_DYNAMIC,     //2\r
-       PT_INTERP,      //3\r
-       PT_NOTE,        //4\r
-       PT_SHLIB,       //5\r
-       PT_PHDR,        //6\r
-       PT_LOPROC = 0x70000000,\r
-       PT_HIPROC = 0x7fffffff\r
-};\r
-\r
-struct sElf32_Phdr {\r
-       Uint32  Type;\r
-       Uint    Offset;\r
-       Uint    VAddr;\r
-       Uint    PAddr;\r
-       Uint32  FileSize;\r
-       Uint32  MemSize;\r
-       Uint32  Flags;\r
-       Uint32  Align;\r
-};\r
-\r
-struct elf32_rel_s {\r
-       Uint32  r_offset;\r
-       Uint32  r_info;\r
-};\r
-\r
-struct elf32_rela_s {\r
-       Uint32  r_offset;\r
-       Uint32  r_info;\r
-       Sint32  r_addend;\r
-};\r
-\r
-enum {\r
-       R_386_NONE=0,   // none\r
-       R_386_32,       // S+A\r
-       R_386_PC32,     // S+A-P\r
-       R_386_GOT32,    // G+A-P\r
-       R_386_PLT32,    // L+A-P\r
-       R_386_COPY,     // none\r
-       R_386_GLOB_DAT, // S\r
-       R_386_JMP_SLOT, // S\r
-       R_386_RELATIVE, // B+A\r
-       R_386_GOTOFF,   // S+A-GOT\r
-       R_386_GOTPC,    // GOT+A-P\r
-       R_386_LAST      // none\r
-};\r
-\r
-#define        ELF32_R_SYM(i)  ((i)>>8)        // Takes an info value and returns a symbol index\r
-#define        ELF32_R_TYPE(i) ((i)&0xFF)      // Takes an info value and returns a type\r
-#define        ELF32_R_INFO(s,t)       (((s)<<8)+((t)&0xFF))   // Takes a type and symbol index and returns an info value\r
-\r
-struct elf32_dyn_s {\r
-       Uint16  d_tag;\r
-       Uint32  d_val;  //Also d_ptr\r
-};\r
-\r
-enum {\r
-       DT_NULL,        //!< Marks End of list\r
-       DT_NEEDED,      //!< Offset in strtab to needed library\r
-       DT_PLTRELSZ,    //!< Size in bytes of PLT\r
-       DT_PLTGOT,      //!< Address of PLT/GOT\r
-       DT_HASH,        //!< Address of symbol hash table\r
-       DT_STRTAB,      //!< String Table address\r
-       DT_SYMTAB,      //!< Symbol Table address\r
-       DT_RELA,        //!< Relocation table address\r
-       DT_RELASZ,      //!< Size of relocation table\r
-       DT_RELAENT,     //!< Size of entry in relocation table\r
-       DT_STRSZ,       //!< Size of string table\r
-       DT_SYMENT,      //!< Size of symbol table entry\r
-       DT_INIT,        //!< Address of initialisation function\r
-       DT_FINI,        //!< Address of termination function\r
-       DT_SONAME,      //!< String table offset of so name\r
-       DT_RPATH,       //!< String table offset of library path\r
-       DT_SYMBOLIC,//!< Reverse order of symbol searching for library, search libs first then executable\r
-       DT_REL,         //!< Relocation Entries (Elf32_Rel instead of Elf32_Rela)\r
-       DT_RELSZ,       //!< Size of above table (bytes)\r
-       DT_RELENT,      //!< Size of entry in above table\r
-       DT_PLTREL,      //!< Relocation entry of PLT\r
-       DT_DEBUG,       //!< Debugging Entry - Unknown contents\r
-       DT_TEXTREL,     //!< Indicates that modifcations to a non-writeable segment may occur\r
-       DT_JMPREL,      //!< Address of PLT only relocation entries\r
-       DT_LOPROC = 0x70000000, //!< Low Definable\r
-       DT_HIPROC = 0x7FFFFFFF  //!< High Definable\r
-};\r
-\r
-typedef struct sElf32_Ehdr     Elf32_Ehdr;\r
-typedef struct sElf32_Phdr     Elf32_Phdr;\r
-typedef struct sElf32_Shent    Elf32_Shent;\r
-typedef struct elf_sym_s       elf_symtab;\r
-typedef struct elf_sym_s       Elf32_Sym;\r
-typedef struct elf32_rel_s     Elf32_Rel;\r
-typedef struct elf32_rela_s    Elf32_Rela;\r
-typedef struct elf32_dyn_s     Elf32_Dyn;\r
-\r
-#endif // defined(_EXE_ELF_H)\r
+       Uint32  value;  //Address
+       Uint32  size;
+       Uint8   info;
+       Uint8   other;
+       Uint16  shndx;
+};
+#define        STN_UNDEF       0       // Undefined Symbol
+
+enum {
+       PT_NULL,        //0
+       PT_LOAD,        //1
+       PT_DYNAMIC,     //2
+       PT_INTERP,      //3
+       PT_NOTE,        //4
+       PT_SHLIB,       //5
+       PT_PHDR,        //6
+       PT_LOPROC = 0x70000000,
+       PT_HIPROC = 0x7fffffff
+};
+
+struct sElf32_Phdr {
+       Uint32  Type;
+       Uint    Offset;
+       Uint    VAddr;
+       Uint    PAddr;
+       Uint32  FileSize;
+       Uint32  MemSize;
+       Uint32  Flags;
+       Uint32  Align;
+};
+
+struct elf32_rel_s {
+       Uint32  r_offset;
+       Uint32  r_info;
+};
+
+struct elf32_rela_s {
+       Uint32  r_offset;
+       Uint32  r_info;
+       Sint32  r_addend;
+};
+
+enum {
+       R_386_NONE=0,   // none
+       R_386_32,       // S+A
+       R_386_PC32,     // S+A-P
+       R_386_GOT32,    // G+A-P
+       R_386_PLT32,    // L+A-P
+       R_386_COPY,     // none
+       R_386_GLOB_DAT, // S
+       R_386_JMP_SLOT, // S
+       R_386_RELATIVE, // B+A
+       R_386_GOTOFF,   // S+A-GOT
+       R_386_GOTPC,    // GOT+A-P
+       R_386_LAST      // none
+};
+
+#define        ELF32_R_SYM(i)  ((i)>>8)        // Takes an info value and returns a symbol index
+#define        ELF32_R_TYPE(i) ((i)&0xFF)      // Takes an info value and returns a type
+#define        ELF32_R_INFO(s,t)       (((s)<<8)+((t)&0xFF))   // Takes a type and symbol index and returns an info value
+
+struct elf32_dyn_s {
+       Uint16  d_tag;
+       Uint32  d_val;  //Also d_ptr
+};
+
+enum {
+       DT_NULL,        //!< Marks End of list
+       DT_NEEDED,      //!< Offset in strtab to needed library
+       DT_PLTRELSZ,    //!< Size in bytes of PLT
+       DT_PLTGOT,      //!< Address of PLT/GOT
+       DT_HASH,        //!< Address of symbol hash table
+       DT_STRTAB,      //!< String Table address
+       DT_SYMTAB,      //!< Symbol Table address
+       DT_RELA,        //!< Relocation table address
+       DT_RELASZ,      //!< Size of relocation table
+       DT_RELAENT,     //!< Size of entry in relocation table
+       DT_STRSZ,       //!< Size of string table
+       DT_SYMENT,      //!< Size of symbol table entry
+       DT_INIT,        //!< Address of initialisation function
+       DT_FINI,        //!< Address of termination function
+       DT_SONAME,      //!< String table offset of so name
+       DT_RPATH,       //!< String table offset of library path
+       DT_SYMBOLIC,//!< Reverse order of symbol searching for library, search libs first then executable
+       DT_REL,         //!< Relocation Entries (Elf32_Rel instead of Elf32_Rela)
+       DT_RELSZ,       //!< Size of above table (bytes)
+       DT_RELENT,      //!< Size of entry in above table
+       DT_PLTREL,      //!< Relocation entry of PLT
+       DT_DEBUG,       //!< Debugging Entry - Unknown contents
+       DT_TEXTREL,     //!< Indicates that modifcations to a non-writeable segment may occur
+       DT_JMPREL,      //!< Address of PLT only relocation entries
+       DT_LOPROC = 0x70000000, //!< Low Definable
+       DT_HIPROC = 0x7FFFFFFF  //!< High Definable
+};
+
+typedef struct sElf32_Ehdr     Elf32_Ehdr;
+typedef struct sElf32_Phdr     Elf32_Phdr;
+typedef struct sElf32_Shent    Elf32_Shent;
+typedef struct elf_sym_s       elf_symtab;
+typedef struct elf_sym_s       Elf32_Sym;
+typedef struct elf32_rel_s     Elf32_Rel;
+typedef struct elf32_rela_s    Elf32_Rela;
+typedef struct elf32_dyn_s     Elf32_Dyn;
+
+#endif // defined(_EXE_ELF_H)
diff --git a/Usermode/Libraries/ld-acess.so_src/elf64.h b/Usermode/Libraries/ld-acess.so_src/elf64.h
new file mode 100644 (file)
index 0000000..237b75c
--- /dev/null
@@ -0,0 +1,113 @@
+/*
+ * Acess2 Dynamic Linker
+ *
+ * elf64.h
+ */
+
+#ifndef _ELF64_H_
+#define _ELF64_H_
+
+#define ELFCLASS64     2
+
+typedef uint16_t       Elf64_Half;
+typedef uint32_t       Elf64_Word;
+typedef uint64_t       Elf64_Addr;
+typedef uint64_t       Elf64_Off;
+typedef uint64_t       Elf64_Xword;
+typedef  int64_t       Elf64_Sxword;
+
+typedef struct
+{
+       unsigned char   e_ident[16];
+       Elf64_Half      e_type;
+       Elf64_Half      e_machine;
+       Elf64_Word      e_version;
+       Elf64_Addr      e_entry;
+       Elf64_Off       e_phoff;
+       Elf64_Off       e_shoff;
+       Elf64_Word      e_flags;
+       Elf64_Half      e_ehsize;
+       Elf64_Half      e_phentsize;
+       Elf64_Half      e_phnum;
+       Elf64_Half      e_shentsize;
+       Elf64_Half      e_shnum;
+       Elf64_Half      e_shstrndx;
+} Elf64_Ehdr;
+
+typedef struct
+{
+       Elf64_Word      sh_name;
+       Elf64_Word      sh_type;
+       Elf64_Xword     sh_flags;
+       Elf64_Addr      sh_addr;
+       Elf64_Off       sh_offset;
+       Elf64_Xword     sh_size;
+       Elf64_Word      sh_link;
+       Elf64_Word      sh_info;
+       Elf64_Xword     sh_addralign;
+       Elf64_Xword     sh_entsize;
+} Elf64_Shdr;
+
+typedef struct
+{
+       Elf64_Word      p_type;
+       Elf64_Word      p_flags;
+       Elf64_Off       p_offset;
+       Elf64_Addr      p_vaddr;
+       Elf64_Addr      p_paddr;
+       Elf64_Xword     p_filesz;
+       Elf64_Xword     p_memsz;
+       Elf64_Xword     p_align;
+} Elf64_Phdr;
+
+typedef struct
+{
+       Elf64_Sxword    d_tag;
+       union {
+               Elf64_Xword     d_val;
+               Elf64_Addr      d_ptr;
+       } d_un;
+} Elf64_Dyn;
+
+typedef struct
+{
+       Elf64_Word      st_name;
+       uint8_t         st_info;
+       uint8_t         st_other;
+       Elf64_Half      st_shndx;
+       Elf64_Addr      st_value;
+       Elf64_Xword     st_size;
+} Elf64_Sym;
+
+typedef struct
+{
+       Elf64_Addr      r_offset;
+       Elf64_Xword     r_info;
+} Elf64_Rel;
+
+typedef struct
+{
+       Elf64_Addr      r_offset;
+       Elf64_Xword     r_info;
+       Elf64_Sxword    r_addend;
+} Elf64_Rela;
+
+#define ELF64_R_SYM(info)      ((info) >> 32)
+#define ELF64_R_TYPE(info)     ((info) & 0xFFFFFFFF)
+
+enum eElf64_RelocTypes_x86_64
+{
+       R_X86_64_NONE,
+       R_X86_64_64,    // 64, S + A
+       R_X86_64_PC32,  // 32, S + A - P
+       R_X86_64_GOT32, // 32, G + A
+       R_X86_64_PLT32, // 32, L + A - P
+       R_X86_64_COPY,
+       R_X86_64_GLOB_DAT,      // 64, S
+       R_X86_64_JUMP_SLOT,     // 64, S
+       R_X86_64_RELATIVE,      // 64, B + A
+       // TODO: Rest
+};
+
+#endif
+
index 28fb467..6d66da0 100644 (file)
@@ -47,11 +47,21 @@ int strlen(const char *str)
        return len;
 }
 
+int memcmp(const void *p1, const void *p2, int len)
+{
+       const char      *b1 = p1, *b2 = p2;
+       while(len --)
+       {
+               if(b1 != b2)    return b1 - b2;
+       }
+       return 0;
+}
+
 /**
  * \fn int file_exists(char *filename)
  * \brief Checks if a file exists
  */
-int file_exists(char *filename)
+int file_exists(const char *filename)
 {
         int    fd;
         //fd = open(filename, OPENFLAG_READ);
index 88297d5..529e0a0 100644 (file)
@@ -13,7 +13,7 @@
 #endif
 
 // === PROTOTYPES ===
-void   *IsFileLoaded(char *file);
+void   *IsFileLoaded(const char *file);
  int   GetSymbolFromBase(void *base, const char *name, void **ret);
 
 // === IMPORTS ===
@@ -30,7 +30,7 @@ char  *gsNextAvailString = gsLoadedStrings;
 //tLoadLib     *gpLoadedLibraries = NULL;
 
 // === CODE ===
-char *FindLibrary(char *DestBuf, char *SoName, char *ExtraSearchDir)
+const char *FindLibrary(char *DestBuf, const char *SoName, const char *ExtraSearchDir)
 {      
        // -- #1: Executable Specified
        if(ExtraSearchDir)
@@ -54,10 +54,10 @@ char *FindLibrary(char *DestBuf, char *SoName, char *ExtraSearchDir)
 
 /**
  */
-void *LoadLibrary(char *SoName, char *SearchDir, char **envp)
+void *LoadLibrary(const char *SoName, const char *SearchDir, char **envp)
 {
        char    sTmpName[1024];
-       char    *filename;
+       const char      *filename;
        void    *base;
        void    (*fEntry)(void *, int, char *[], char**);
        
@@ -98,7 +98,7 @@ void *LoadLibrary(char *SoName, char *SearchDir, char **envp)
  * \fn Uint IsFileLoaded(char *file)
  * \brief Determine if a file is already loaded
  */
-void *IsFileLoaded(char *file)
+void *IsFileLoaded(const char *file)
 {
         int    i;
        DEBUGS("IsFileLoaded: (file='%s')", file);
@@ -119,7 +119,7 @@ void *IsFileLoaded(char *file)
  * \fn void AddLoaded(char *File, Uint base)
  * \brief Add a file to the loaded list
  */
-void AddLoaded(char *File, void *base)
+void AddLoaded(const char *File, void *base)
 {
         int    i, length;
        char    *name = gsNextAvailString;
index dfb1b61..ccdf6b4 100644 (file)
@@ -6,10 +6,10 @@
 #include "common.h"\r
 \r
 // === PROTOTYPES ===\r
-void   *DoRelocate(void *base, char **envp, char *Filename);\r
+void   *DoRelocate(void *base, char **envp, const char *Filename);\r
  int   CallUser(void *Entry, void *SP);\r
-void   *ElfRelocate(void *Base, char *envp[], char *Filename);\r
-void   *PE_Relocate(void *Base, char *envp[], char *Filename);\r
+void   *ElfRelocate(void *Base, char **envp, const char *Filename);\r
+void   *PE_Relocate(void *Base, char **envp, const char *Filename);\r
 \r
 // === Imports ===\r
 extern void    gLinkedBase;\r
@@ -21,7 +21,7 @@ extern tLoadedLib     gLoadedLibraries[];
  \brief Library entry point\r
  \note This is the entrypoint for the library\r
 */\r
-int SoMain(void *base, void *arg1)\r
+void *SoMain(void *base)\r
 {\r
        void    *ret;\r
         \r
@@ -50,28 +50,29 @@ int SoMain(void *base, void *arg1)
                _exit(-1);\r
                for(;;);\r
        }\r
-       \r
-       // And call user\r
-       //SysDebug("Calling User at 0x%x\n", ret);\r
-       CallUser( ret, &arg1 );\r
-       \r
-       return 0;\r
+\r
+       SysDebug("ld-acess - SoMain: ret = %p", ret);   \r
+       return ret;\r
 }\r
 \r
 /**\r
  \fn int DoRelocate(void *base, char **envp)\r
  \brief Relocates an in-memory image\r
 */\r
-void *DoRelocate(void *base, char **envp, char *Filename)\r
+void *DoRelocate(void *base, char **envp, const char *Filename)\r
 {\r
+       Uint8   *hdr = base;\r
        // Load Executable\r
-       if(*(Uint32*)base == (0x7F|('E'<<8)|('L'<<16)|('F'<<24)))\r
+       if(memcmp(base, "\x7F""ELF", 4) == 0)\r
                return ElfRelocate(base, envp, Filename);\r
-       if(*(Uint16*)base == ('M'|('Z'<<8)))\r
+       if(hdr[0] == 0x7F && hdr[1] == 'E' && hdr[2] == 'L' && hdr[3] == 'F')\r
+               return ElfRelocate(base, envp, Filename);\r
+\r
+       if(hdr[0] == 'M' && hdr[1] == 'Z')\r
                return PE_Relocate(base, envp, Filename);\r
        \r
        SysDebug("ld-acess - DoRelocate: Unkown file format '0x%x 0x%x 0x%x 0x%x'\n",\r
-               *(Uint8*)(base), *(Uint8*)(base+1), *(Uint8*)(base+2), *(Uint8*)(base+3) );\r
+               hdr[0], hdr[1], hdr[2], hdr[3] );\r
        SysDebug("ld-acess - DoRelocate: File '%s'\n", Filename);\r
        _exit(-1);\r
        for(;;);\r
index afcb4ce..d567ed1 100644 (file)
@@ -89,9 +89,9 @@ int PE_Relocate(void *Base, char *envp[], char *Filename)
 }\r
 \r
 /**\r
- * \fn int PE_GetSymbol(Uint Base, char *Name, Uint *Ret)\r
+ * \fn int PE_GetSymbol(Uint Base, const char *Name, Uint *Ret)\r
  */\r
-int PE_GetSymbol(void *Base, char *Name, void **Ret)\r
+int PE_GetSymbol(void *Base, const char *Name, void **Ret)\r
 {\r
        tPE_DOS_HEADER          *dosHdr = Base;\r
        tPE_IMAGE_HEADERS       *peHeaders;\r

UCC git Repository :: git.ucc.asn.au