+ // Sanity check\r
+ if( Header->e_phoff == 0 )\r
+ {\r
+ Log_Warning("ELF", "No program header, panic!");\r
+ return NULL;\r
+ }\r
+ if( Header->e_shentsize != sizeof(Elf64_Shdr) ) {\r
+ Log_Warning("ELF", "Header gives shentsize as %i, my type is %i",\r
+ Header->e_shentsize, sizeof(Elf64_Shdr) );\r
+ }\r
+ if( Header->e_phentsize != sizeof(Elf64_Phdr) ) {\r
+ Log_Warning("ELF", "Header gives phentsize as %i, my type is %i",\r
+ Header->e_phentsize, sizeof(Elf64_Phdr) );\r
+ }\r
+\r
+ LOG("Header = {");\r
+ LOG(" e_ident = %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x",\r
+ Header->e_ident[0], Header->e_ident[1], Header->e_ident[2], Header->e_ident[3],\r
+ Header->e_ident[4], Header->e_ident[5], Header->e_ident[6], Header->e_ident[7],\r
+ Header->e_ident[8], Header->e_ident[9], Header->e_ident[10], Header->e_ident[11],\r
+ Header->e_ident[12], Header->e_ident[13], Header->e_ident[14], Header->e_ident[15]\r
+ );\r
+ LOG(" e_type = %i", Header->e_type);\r
+ LOG(" e_machine = %i", Header->e_machine);\r
+ LOG(" e_version = %i", Header->e_version);\r
+ LOG(" e_entry = 0x%llx", Header->e_entry);\r
+ LOG(" e_phoff = 0x%llx", Header->e_phoff);\r
+ LOG(" e_shoff = 0x%llx", Header->e_shoff);\r
+ LOG(" e_flags = 0x%x", Header->e_flags);\r
+ LOG(" e_ehsize = %i", Header->e_ehsize);\r
+ LOG(" e_phentsize = %i", Header->e_phentsize);\r
+ LOG(" e_phnum = %i", Header->e_phnum);\r
+ LOG(" e_shentsize = %i", Header->e_shentsize);\r
+ LOG(" e_shnum = %i", Header->e_shnum);\r
+ LOG(" e_shstrndx = %i", Header->e_shstrndx);\r
+ LOG("}");\r
+\r
+ // Load Program Header table\r
+ VFS_Seek(FD, Header->e_phoff, SEEK_SET);\r
+ VFS_Read(FD, sizeof(Elf64_Phdr)*Header->e_phnum, phtab);\r
+\r
+ // Count load segments\r
+ nLoadSegments = 0;\r
+ for( i = 0; i < Header->e_phnum; i ++ )\r
+ {\r
+ if( phtab[i].p_type != PT_LOAD ) continue ;\r
+ nLoadSegments ++;\r
+ }\r
+ \r
+ // Allocate Information Structure\r
+ ret = malloc( sizeof(tBinary) + sizeof(tBinarySection)*nLoadSegments );\r
+ // Fill Info Struct\r
+ ret->Entry = Header->e_entry;\r
+ ret->Base = -1; // Set Base to maximum value\r
+ ret->NumSections = nLoadSegments;\r
+ ret->Interpreter = NULL;\r
+\r
+ j = 0; // LoadSections[] index\r
+ for( i = 0; i < Header->e_phnum; i ++ )\r
+ {\r
+ LOG("phtab[%i] = {", i);\r
+ LOG(" .p_type = %i", phtab[i].p_type);\r
+ LOG(" .p_flags = 0x%x", phtab[i].p_flags);\r
+ LOG(" .p_offset = 0x%llx", phtab[i].p_offset);\r
+ LOG(" .p_vaddr = 0x%llx", phtab[i].p_vaddr);\r
+ LOG(" .p_paddr = 0x%llx", phtab[i].p_paddr);\r
+ LOG(" .p_filesz = 0x%llx", phtab[i].p_filesz);\r
+ LOG(" .p_memsz = 0x%llx", phtab[i].p_memsz);\r
+ LOG(" .p_align = 0x%llx", phtab[i].p_align);\r
+ LOG("}");\r
+\r
+ // Get Interpreter Name\r
+ if( phtab[i].p_type == PT_INTERP )\r
+ {\r
+ char *tmp;\r
+ if(ret->Interpreter) continue;\r
+ tmp = malloc(phtab[i].p_filesz);\r
+ VFS_Seek(FD, phtab[i].p_offset, 1);\r
+ VFS_Read(FD, phtab[i].p_filesz, tmp);\r
+ ret->Interpreter = Binary_RegInterp(tmp);\r
+ LOG("Interpreter '%s'", tmp);\r
+ free(tmp);\r
+ continue;\r
+ }\r
+ \r
+ if( phtab[i].p_type != PT_LOAD ) continue ;\r
+ \r
+ // Find the executable base\r
+ if( phtab[i].p_vaddr < ret->Base ) ret->Base = phtab[i].p_vaddr;\r
+\r
+ ret->LoadSections[j].Offset = phtab[i].p_offset;\r
+ ret->LoadSections[j].Virtual = phtab[i].p_vaddr;\r
+ ret->LoadSections[j].FileSize = phtab[i].p_filesz;\r
+ ret->LoadSections[j].MemSize = phtab[i].p_memsz;\r
+ \r
+ ret->LoadSections[j].Flags = 0;\r
+ if( !(phtab[i].p_flags & PF_W) )\r
+ ret->LoadSections[j].Flags |= BIN_SECTFLAG_RO;\r
+ if( phtab[i].p_flags & PF_X )\r
+ ret->LoadSections[j].Flags |= BIN_SECTFLAG_EXEC;\r
+ j ++;\r
+ }\r
+\r
+ return ret;\r
+}\r
+\r
+tBinary *Elf_Load32(int FD, Elf32_Ehdr *Header)\r
+{\r
+ tBinary *ret;\r
+ Elf32_Phdr *phtab;\r
+ int i, j;\r
+ int iLoadCount;\r
+\r
+ ENTER("xFD", FD);\r
+\r
+ // Check architecture with current CPU\r
+ // - TODO: Support kernel level emulation\r
+ #if ARCH_IS_x86\r
+ if( Header->machine != EM_386 )\r
+ {\r
+ Log_Warning("ELF", "Unknown architecure on ELF-32");\r
+ LEAVE_RET('n');\r
+ return NULL;\r
+ }\r
+ #endif\r
+\r