#define DRD64_SRC_LIBGOBLIN_ELF_DYNAMIC
#include"drd64_libgoblin.h"
+/*----------------------------------------------------------------------
+----------------------------------------------------------------------*/
+Elf64_Phdr *
+ ELF64_ProgramHeader_Search_Dynamic(
+ LibGoblin_BinaryInfo *p_binfo )
+{
+ int i_cnt;
+ int i_phdrnum;
+ int i_phdrsize;
+ Byte *pb_data;
+ Elf64_Ehdr *p_elfhdr;
+ Elf64_Phdr *p_proghdr;
+ LibGoblin_BinaryFile *p_bfile;
+
+ assert( NULL != p_binfo );
+ p_bfile = BinaryFile_GetBinaryFile( p_binfo->i_binfile );
+ pb_data = p_bfile->pb_binary;
+ assert( NULL != pb_data );
+
+ // Search DYNAMIC segment in Program Header ---
+ p_elfhdr = (Elf64_Ehdr *)pb_data;
+ i_phdrnum = p_elfhdr->e_phnum;
+ i_phdrsize = p_elfhdr->e_phentsize;
+
+ p_proghdr = (Elf64_Phdr *)(pb_data + p_elfhdr->e_phoff);
+ for( i_cnt = 0; i_cnt < i_phdrnum; i_cnt++ ) {
+ if( PT_DYNAMIC == p_proghdr->p_type ) { break; }
+ // for Next-Loop proc.
+ p_proghdr = (Elf64_Phdr *)(pb_data + p_elfhdr->e_phoff + (i_cnt * i_phdrsize));
+ }
+
+ if( i_phdrnum == i_cnt ) {
+ return NULL;
+ }
+
+ return p_proghdr;
+}
+
+
+/*----------------------------------------------------------------------
+----------------------------------------------------------------------*/
+Elf64_Phdr *
+ ELF64_ProgramHeader_Search_inRange(
+ LibGoblin_BinaryInfo *p_binfo,
+ Ptr ptr_address,
+ QWord qw_size )
+{
+ int i_cnt;
+ int i_phdrnum;
+ int i_phdrsize;
+ Byte *pb_data;
+ QWord qw_szrange;
+ Elf64_Ehdr *p_elfhdr;
+ Elf64_Phdr *p_proghdr;
+ Elf64_Phdr *p_pghrange;
+ LibGoblin_BinaryFile *p_bfile;
+
+ assert( NULL != p_binfo );
+ p_bfile = BinaryFile_GetBinaryFile( p_binfo->i_binfile );
+ pb_data = p_bfile->pb_binary;
+ assert( NULL != pb_data );
+
+ p_elfhdr = (Elf64_Ehdr *)pb_data;
+ i_phdrnum = p_elfhdr->e_phnum;
+ i_phdrsize = p_elfhdr->e_phentsize;
+
+ p_proghdr = (Elf64_Phdr *)(pb_data + p_elfhdr->e_phoff);
+ p_pghrange = NULL;
+ qw_szrange = 0xffffffffffffffff;
+ for( i_cnt = 0; i_cnt < i_phdrnum; i_cnt++ ) {
+ if(( p_proghdr->p_vaddr <= ptr_address )
+ && ((ptr_address + qw_size) <= (p_proghdr->p_vaddr + p_proghdr->p_memsz) ) ) {
+ p_pghrange = p_proghdr;
+ qw_szrange = p_proghdr->p_memsz;
+ }
+ // for Next-Loop proc.
+ p_proghdr = (Elf64_Phdr *)(pb_data + p_elfhdr->e_phoff + (i_cnt * i_phdrsize));
+ }
+
+ return p_pghrange;
+}
+
+
+/*----------------------------------------------------------------------
+----------------------------------------------------------------------*/
+LIBGOBLIN_ELF_DYNAMIC_EXTERN
+int
+ ELF64_Dynamic_GetDynStrSection_fromProgHdr(
+ LibGoblin_BinaryInfo *p_binfo )
+{
+ int i_phdrnum;
+ int i_phdrsize;
+ Byte *pb_data;
+ Byte *pb_dynamic;
+ QWord qw_tag;
+ QWord qw_value;
+ QWord qw_dynsize;
+ Ptr ptr_addr;
+ Ptr ptr_dynaddr;
+ Elf64_Ehdr *p_elfhdr;
+ Elf64_Phdr *p_pghdr_dynamic;
+ Elf64_Phdr *p_pghdr_dynstr;
+ Elf64_Dyn *p_dyn64;
+ LibGoblin_BinaryFile *p_bfile;
+ LibGoblin_SectionInfo *p_sec_dynstr;
+ LibGoblin_ProgramInfo *p_pginfo;
+
+ assert( NULL != p_binfo );
+ p_bfile = BinaryFile_GetBinaryFile( p_binfo->i_binfile );
+ p_pginfo = ProgInfo_GetProgInfo( p_binfo->i_pginfo );
+
+ pb_data = p_bfile->pb_binary;
+ assert( NULL != pb_data );
+
+
+ p_elfhdr = (Elf64_Ehdr *)pb_data;
+ i_phdrnum = p_elfhdr->e_phnum;
+ i_phdrsize = p_elfhdr->e_phentsize;
+
+
+ // Search DYNAMIC segment in Program Header ---
+ p_pghdr_dynamic = ELF64_ProgramHeader_Search_Dynamic( p_binfo );
+ if( NULL == p_pghdr_dynamic ) {
+ return -0x01;
+ }
+
+ // Seearch & Setting .dynstr section info. ---
+ ptr_dynaddr = 0x0000000000000000;
+ qw_dynsize = 0;
+ pb_dynamic = pb_data + p_pghdr_dynamic->p_offset;
+ do {
+ p_dyn64 = (Elf64_Dyn *)pb_dynamic;
+ qw_tag = (QWord)p_dyn64->d_tag;
+ qw_value = (QWord)p_dyn64->d_un.d_val;
+ ptr_addr = (Ptr)p_dyn64->d_un.d_ptr;
+
+ /* 05 - Address of string table. */
+ if( DT_STRTAB == qw_tag ) { ptr_dynaddr = qw_value; }
+ /* 10 - Size of string table. */
+ else if( DT_STRSZ == qw_tag ) { qw_dynsize = qw_value; }
+
+ pb_dynamic += sizeof( Elf64_Dyn );
+ }while( DT_NULL != qw_tag );
+
+ p_sec_dynstr = NULL;
+ if(( 0 < ptr_dynaddr ) && ( 0 < qw_dynsize )) {
+ // Search ProgHdr in .dynstr section ---
+ p_pghdr_dynstr = ELF64_ProgramHeader_Search_inRange( p_binfo, ptr_dynaddr, qw_dynsize );
+ assert( NULL != p_pghdr_dynstr );
+
+ p_sec_dynstr = LibGoblin_Section_GetSectionInfo( p_pginfo, LIBGOBLIN_SECTION_ID_DYNSTR );
+ p_sec_dynstr->qw_size = qw_dynsize;
+ p_sec_dynstr->ptr_address = ptr_dynaddr;
+ p_sec_dynstr->pb_data = pb_data
+ + (ptr_dynaddr - p_pghdr_dynstr->p_vaddr)
+ + p_pghdr_dynstr->p_offset;
+ p_sec_dynstr->pb_sechdr = NULL;
+ p_sec_dynstr->i_fid = -0x01; // Temporary.
+ }
+
+ return 0x00;
+}
/*----------------------------------------------------------------------
----------------------------------------------------------------------*/
ptr_addr = (Ptr)p_dyn32->d_un.d_ptr;
}
+ /* 01 - String table offset of a needed shared library. */
if( DT_NEEDED == qw_tag ) {
p_bintmp = ProgInfo_AddBinaryInfo(
p_pginfo, ((char *)(pb_dynstr + qw_value)), p_binfo->i_id );
}
+ /* 15 - String table offset of library path. [sup] */
else if( DT_RPATH == qw_tag ) {
BinaryInfo_SetRPath( p_binfo, (const char *)(pb_dynstr + qw_value) );
}
+ /* 29 - String table offset of a null-terminated library search path string. */
else if( DT_RUNPATH == qw_tag ) {
BinaryInfo_SetRunPath( p_binfo, (const char *)(pb_dynstr + qw_value) );
}
- //else if( DT_SONAME == qw_tag ) { }
+
+ /* 02 - Total size in bytes of PLT relocations. */
+ else if( DT_PLTRELSZ == qw_tag ) {
+ //p_secnow = LibGoblin_Section_GetSectionInfo( p_pginfo, LIBGOBLIN_SECTION_ID_RELA_PLT );
+ //p_secnow->qw_size = qw_value;
+ //p_sec_dynstr->pb_data = pb_data + qw_offset;
+ //p_secnow->pb_sechdr = NULL;
+ //p_secnow->i_fid = -0x01; // Temporary.
+ }
+ /* 03 - Processor-dependent address. */
+ else if( DT_PLTGOT == qw_tag ) {
+ }
+ /* 04 - Address of symbol hash table. */
+ else if( DT_HASH == qw_tag ) {
+ }
+ /* 06 - Address of symbol table. */
+ else if( DT_SYMTAB == qw_tag ) {
+ }
+ /* 07 - Address of ElfNN_Rela relocations. */
+ else if( DT_RELA == qw_tag ) {
+ }
+ /* 08 - Total size of ElfNN_Rela relocations. */
+ else if( DT_RELASZ == qw_tag ) { }
+ /* 09 - Size of each ElfNN_Rela relocation entry. */
+ else if( DT_RELAENT == qw_tag ) { }
+ /* 11 - Size of each symbol table entry. */
+ else if( DT_SYMENT == qw_tag ) { }
+ /* 12 - Address of initialization function. */
+ else if( DT_INIT == qw_tag ) { }
+ /* 13 - Address of finalization function. */
+ else if( DT_FINI == qw_tag ) { }
+ /* 14 - String table offset of shared object name. */
+ else if( DT_SONAME == qw_tag ) { }
+ /* 16 - Indicates "symbolic" linking. [sup] */
+ else if( DT_SYMBOLIC == qw_tag ) { }
+ /* 17 - Address of ElfNN_Rel relocations. */
+ else if( DT_REL == qw_tag ) { }
+ /* 18 - Total size of ElfNN_Rel relocations. */
+ else if( DT_RELSZ == qw_tag ) { }
+ /* 19 - Size of each ElfNN_Rel relocation. */
+ else if( DT_RELENT == qw_tag ) { }
+ /* 20 - Type of relocation used for PLT. */
+ else if( DT_PLTREL == qw_tag ) { }
+ /* 21 - Reserved (not used). */
+ else if( DT_DEBUG == qw_tag ) { }
+ /* 22 - Indicates there may be relocations in non-writable segments. [sup] */
+ else if( DT_TEXTREL == qw_tag ) { }
+ /* 23 - Address of PLT relocations. */
+ else if( DT_JMPREL == qw_tag ) { }
+ /* 24 - [sup] */
+ else if( DT_BIND_NOW == qw_tag ) { }
+ /* 25 - Address of the array of pointers to initialization functions */
+ else if( DT_INIT_ARRAY == qw_tag ) { }
+ /* 26 - Address of the array of pointers to termination functions */
+ else if( DT_FINI_ARRAY == qw_tag ) { }
+ /* 27 - Size in bytes of the array of initialization functions. */
+ else if( DT_INIT_ARRAYSZ == qw_tag ) { }
+ /* 28 - Size in bytes of the array of termination functions. */
+ else if( DT_FINI_ARRAYSZ == qw_tag ) { }
+ /* 30 - Object specific flag values. */
+ else if( DT_FLAGS == qw_tag ) { }
+ /* 32 - Values greater than or equal to DT_ENCODING and less than DT_LOOS follow the rules for the interpretation of the d_un union as follows: even == 'd_ptr', odd == 'd_val' or none */
+ else if( DT_ENCODING == qw_tag ) { }
+ /* 32 - Address of the array of pointers to pre-initialization functions. */
+ else if( DT_PREINIT_ARRAY == qw_tag ) { }
+ /* 33 - Size in bytes of the array of pre-initialization functions. */
+ else if( DT_PREINIT_ARRAYSZ == qw_tag ) { }
+ /* 34 - number of positive tags */
+ else if( DT_MAXPOSTAGS == qw_tag ) { }
+ // #define DT_LOOS 0x6000000d // First OS-specific
+ // #define DT_SUNW_AUXILIARY 0x6000000d // symbol auxiliary name
+ // #define DT_SUNW_RTLDINF 0x6000000e // ld.so.1 info (private)
+ // #define DT_SUNW_FILTER 0x6000000f // symbol filter name
+ // #define DT_SUNW_CAP 0x60000010 // hardware/software
+ // #define DT_SUNW_ASLR 0x60000023 // ASLR control
+ // #define DT_HIOS 0x6ffff000 // Last OS-specific
pb_data += i_sz_elfdyn;
}while( DT_NULL != qw_tag );