From: Koine Yuusuke(koinec) Date: Tue, 1 Jan 2019 04:15:57 +0000 (+0900) Subject: 2019/01/01(Tue) 13:16 X-Git-Url: http://git.osdn.net/view?a=commitdiff_plain;h=cbe3ded86991b8efd9f8f81f9c2be29fc1096872;p=drdeamon64%2Fdrdeamon64.git 2019/01/01(Tue) 13:16 (LibGoblin) * Support for DT_RUNPATH (.dynamic Section) --- diff --git a/libgoblin/drd64_libgoblin_api.c b/libgoblin/drd64_libgoblin_api.c index f73f8ba..2165e52 100644 --- a/libgoblin/drd64_libgoblin_api.c +++ b/libgoblin/drd64_libgoblin_api.c @@ -103,8 +103,10 @@ int if( -1 < p_binfo->i_parent_bid ) { p_binfo_parent = BinaryInfo_GetBinInfo( p_binfo->i_parent_bid ); p_bfile = BinaryFile_GetBinaryFile( p_binfo_parent->i_binfile ); - if( NULL != p_bfile ) - { strncpy( p_objpath->str_rpath, p_bfile->str_rpath, DRD64_MAX_PATH ); } + if( NULL != p_bfile ) { + strncpy( p_objpath->str_rpath, p_bfile->str_rpath, DRD64_MAX_PATH ); + strncpy( p_objpath->str_runpath, p_bfile->str_runpath, DRD64_MAX_PATH ); + } } i_result = 0x01; diff --git a/libgoblin/drd64_libgoblin_binfo.c b/libgoblin/drd64_libgoblin_binfo.c index e0ce57f..6209b44 100644 --- a/libgoblin/drd64_libgoblin_binfo.c +++ b/libgoblin/drd64_libgoblin_binfo.c @@ -250,6 +250,57 @@ int /*---------------------------------------------------------------------- +----------------------------------------------------------------------*/ +LIBGOBLIN_BINFO_EXTERN +int + BinaryInfo_SetRunPath( + LibGoblin_BinaryInfo *p_binfo, + const char *pstr_runpath ) +{ + int i_len; + char str_src[MAXPATHLEN]; + char str_dest[MAXPATHLEN]; + char *pstr_result; + char *pstr_rbasepath; + LibGoblin_BinaryFile *p_binfile; + + if( LIBGOBLIN_BINFO_PHASE_SETPROG > p_binfo->b_phase ) { + return -0x01; + } + + p_binfile = BinaryFile_GetBinaryFile( p_binfo->i_binfile ); + assert( NULL != p_binfile ); + + memset( str_src, 0x00, MAXPATHLEN ); + + // p_binfo->str_path is current path + if( 0x00 != p_binfile->str_remotepath[0] ) + { pstr_rbasepath = p_binfile->str_remotepath; } + else + { pstr_rbasepath = p_binfile->str_localpath; } + + + i_len = strnlen( pstr_rbasepath, DRD64_MAX_PATH ); + strncpy( str_src, pstr_rbasepath, i_len + 1 ); + str_src[ i_len ] = '/'; + strncat( str_src, pstr_runpath, (MAXPATHLEN - i_len - 1) ); + + pstr_result = realpath( str_src, str_dest ); + if( NULL == pstr_result ) { + return -0x02; + } + + i_len = strnlen( str_dest, MAXPATHLEN ); + if( DRD64_MAX_PATH <= i_len ) { + return -0x03; + } + strncpy( p_binfile->str_runpath, str_dest, DRD64_MAX_PATH ); + + return 0x00; +} + + +/*---------------------------------------------------------------------- pstr_progpath: Absolute & Relative Path in this-machine program. Absolute Path ONLY in remote-machine program. * pstr_progpath != pstr_realpath is remote-machine program. @@ -393,7 +444,6 @@ int LibGoblin_BinaryInfo *p_binfo ) { int i_binfoid; - int i_result; LibGoblin_BinaryFile *p_binfile; if( NULL == p_binfo ) { return 0x01; } diff --git a/libgoblin/drd64_libgoblin_binfo.h b/libgoblin/drd64_libgoblin_binfo.h index 1b149fb..ac6a488 100644 --- a/libgoblin/drd64_libgoblin_binfo.h +++ b/libgoblin/drd64_libgoblin_binfo.h @@ -72,6 +72,9 @@ LIBGOBLIN_BINFO_EXTERN int BinaryInfo_SetRPath( LibGoblin_BinaryInfo *p_binfo, const char *pstr_rpath ); LIBGOBLIN_BINFO_EXTERN + int BinaryInfo_SetRunPath( + LibGoblin_BinaryInfo *p_binfo, const char *pstr_runpath ); +LIBGOBLIN_BINFO_EXTERN int BinaryInfo_SetProgramPath( LibGoblin_BinaryInfo *p_binfo, const char *pstr_progpath, const char *pstr_realpath ); LIBGOBLIN_BINFO_EXTERN diff --git a/libgoblin/drd64_libgoblin_elf_dynver.c b/libgoblin/drd64_libgoblin_elf_dynver.c index 1f2931a..3f7aa49 100644 --- a/libgoblin/drd64_libgoblin_elf_dynver.c +++ b/libgoblin/drd64_libgoblin_elf_dynver.c @@ -105,6 +105,9 @@ int else if( DT_RPATH == qw_tag ) { BinaryInfo_SetRPath( p_binfo, (const char *)(pb_dynstr + qw_value) ); } + else if( DT_RUNPATH == qw_tag ) { + BinaryInfo_SetRunPath( p_binfo, (const char *)(pb_dynstr + qw_value) ); + } //else if( DT_SONAME == qw_tag ) { } pb_data += i_sz_elfdyn; diff --git a/libgoblin/drd64_libgoblin_type.h b/libgoblin/drd64_libgoblin_type.h index 916de91..4a356bc 100644 --- a/libgoblin/drd64_libgoblin_type.h +++ b/libgoblin/drd64_libgoblin_type.h @@ -109,6 +109,8 @@ typedef struct { // .dynamic Section - rpath (.so location path - converted real-path) char str_rpath[DRD64_MAX_PATH]; + // .dynamic Section - runpath (.so location path - converted real-path) + char str_runpath[DRD64_MAX_PATH]; LibFileType_FileType t_ftype; diff --git a/libgoblin/test_libgoblin_loadprog.c b/libgoblin/test_libgoblin_loadprog.c index d81d519..1721160 100644 --- a/libgoblin/test_libgoblin_loadprog.c +++ b/libgoblin/test_libgoblin_loadprog.c @@ -46,6 +46,7 @@ void Test_LibGoblin_LoadProg_API_LoadProgram_test00_001( void ) int i_pgid; int i_result; char *pstr_ldpath; + char *pstr_env_ldlibpath; LibGoblin_ObjectFilePath t_objpath; @@ -56,6 +57,8 @@ void Test_LibGoblin_LoadProg_API_LoadProgram_test00_001( void ) if( NULL == pstr_ldpath ) { goto goto_Test_LibGoblin_LoadProg_API_LoadProgram_test00_001_post; } + pstr_env_ldlibpath = getenv("LD_LIBRARY_PATH"); + i_result = LibGoblin_Init(); CU_ASSERT( 0x00 == i_result ); @@ -69,14 +72,19 @@ void Test_LibGoblin_LoadProg_API_LoadProgram_test00_001( void ) while( 0x00 < LibGoblin_GetUnresolv_ObjectFilePath( i_pgid, &t_objpath ) ) { i_result = LibBrownie_GetLibraryPath( t_objpath.str_localpath, - t_objpath.str_filename, t_objpath.str_rpath, pstr_ldpath ); - - CU_ASSERT( 0x00 == i_result ); - if( 0x00 != i_result ) + t_objpath.str_filename, + t_objpath.str_rpath, + t_objpath.str_runpath, + pstr_env_ldlibpath, + pstr_ldpath ); + + CU_ASSERT( 0x00 < i_result ); + if( 0x00 >= i_result ) { goto goto_Test_LibGoblin_LoadProg_API_LoadProgram_test00_001_post; } - printf(" file= %s, rpath= %s\n => localpath: %s\n", - t_objpath.str_filename, t_objpath.str_rpath, t_objpath.str_localpath ); + printf(" file= %s, DT_RPATH= %s, DT_RUNPATH=%s\n => localpath: %s\n", + t_objpath.str_filename, t_objpath.str_rpath, + t_objpath.str_runpath, t_objpath.str_localpath ); i_result = LibGoblin_SetPathAndLoad_ObjectFilePath( &t_objpath ); CU_ASSERT( 0x00 == i_result );