OSDN Git Service

2019/01/20(Sun) 21:30
authorKoine Yuusuke(koinec) <koinec@users.osdn.me>
Sun, 20 Jan 2019 12:30:07 +0000 (21:30 +0900)
committerKoine Yuusuke(koinec) <koinec@users.osdn.me>
Sun, 20 Jan 2019 12:30:07 +0000 (21:30 +0900)
 (LibGoblin)
  * WorkBackup

libgoblin/drd64_libgoblin_elf.c
libgoblin/drd64_libgoblin_elf_dynamic.c
libgoblin/drd64_libgoblin_elf_dynamic.h
libgoblin/drd64_libgoblin_elf_proghdr.c
libgoblin/drd64_libgoblin_type.h
libgoblin/test_libgoblin_objinfo.c

index db6d20c..5acfa65 100644 (file)
@@ -109,6 +109,9 @@ int
 
        /* Analyze ELF Basical Struct & data -----*/
        if( LIBGOBLIN_BINFO_TYPE_ELF64 == p_binfo->b_type )             {
+               // XXX 2019/01/20 
+               i_result        = ELF64_Dynamic_GetDynStrSection_fromProgHdr( p_binfo );
+
                i_result        = LibGoblin_Elf64_SetSectionInfo( p_binfo );
        }
        else if( LIBGOBLIN_BINFO_TYPE_ELF32 == p_binfo->b_type )        {
index b186d31..734322c 100644 (file)
@@ -37,6 +37,168 @@ Comment:
 #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;
+}
 
 /*----------------------------------------------------------------------
 ----------------------------------------------------------------------*/
@@ -98,17 +260,95 @@ int
                        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 );
index f0defd8..4bbd06b 100644 (file)
@@ -44,7 +44,8 @@ Comment:
 #else
        #define LIBGOBLIN_ELF_DYNAMIC_EXTERN    extern
 #endif
-
+LIBGOBLIN_ELF_DYNAMIC_EXTERN
+       int ELF64_Dynamic_GetDynStrSection_fromProgHdr( LibGoblin_BinaryInfo *p_binfo );
 LIBGOBLIN_ELF_DYNAMIC_EXTERN
        int LibGoblin_Elf_Dynamic_ReadDynamicSection(
                        LibGoblin_BinaryInfo *p_binfo );
index 6eb9ff0..c3cfd4a 100644 (file)
@@ -47,7 +47,6 @@ int
                LibGoblin_BinaryInfo    *p_binfo )
 {
        int                                             i_cnt;
-       int                                             i_result;
        int                                             i_phdrnum;
        int                                             i_phdrsize;
        Byte                                    *pb_data;
index 8b773c8..5caa02f 100644 (file)
@@ -41,9 +41,10 @@ Comment:
 /*=====================================================================*/
 typedef struct {
        Byte    *pb_sechdr;
-       Byte    *pb_data;
-       char    *pstr_secname;
+       Byte    *pb_data;               // FileLocation (Offset)
+       Ptr             ptr_address;
        QWord   qw_size;
+       char    *pstr_secname;
        int             i_fid;
 } LibGoblin_SectionInfo;
 
index 07ad80e..83f7b19 100644 (file)
@@ -462,12 +462,7 @@ void Test_ObjectInfo_InsetDelete_test00_004_Alloc(
 void Test_ObjectInfo_InsetDelete_test00_004(
                LibGoblin_ProgramInfo   *p_pginfo )
 {
-       int                                             i_cnt;
-       QWord                                   qw_addr;
-       QWord                                   qw_size;
        LibGoblin_ObjectInfo    *p_objinfo;
-       LibGoblin_ObjectInfo    *p_objparent;
-       LibGoblin_ObjectInfo    *p_objmaster;
 
        // Scenery 1 ......................................................
        Test_ObjectInfo_InsetDelete_test00_004_Alloc( p_pginfo );