2014-08-27 3 views
2

공유 라이브러리가로드되는 프로세스에서 함수를 호출 할 수있게하려고합니다. 라이브러리는 C++의 "커널"인 C로 작성됩니다.dlopen cant demangled symbols

kernel.cpp :

#include <stdio.h> 
#include <dlfcn.h> 

typedef void(*func_t)(); 

extern "C" { 
     void test(); 
} 

int main() { 
     char *error; 
     void *handle = dlopen("./library.so", RTLD_LAZY); 
     if((error = dlerror()) != NULL) { 
       fprintf(stderr, "%s\n", error); 
       return 1; 
     } 
     func_t init = (func_t)dlsym(handle, "init"); 
     if((error = dlerror()) != NULL) { 
       fprintf(stderr, "%s\n", error); 
       return 1; 
     } 
     init(); 

     return 0; 
} 

void test() { 
     fprintf(stderr, "test() called.\n"); 
} 

library.c :

#include <stdio.h> 

void test(); 

void init() { 
     fprintf(stderr, "init() called.\n"); 
     test(); 
} 

메이크 :

all: 
     g++ -ldl kernel.cpp -o kernel 
     gcc -fpic -shared library.c -o library.so 
     ./kernel 

objdump를 -x 커널

SYMBOL TABLE: 
... 
000000000040088b g  F .text 0000000000000024 test 
나는 다음과 같은 출력 얻을 프로그램을 실행

는 :

init() called. 
./kernel: symbol lookup error: ./library.so: undefined symbol: test 

내가 RTLD_NOW를 사용하는 dlopen을 변경하는 경우를, 내가 얻을 :

./library.so: undefined symbol: test 

왜 도서관은 명확 때 기호를 찾는 데 어려움이있다 엉망이 아니라, 바로 거기에 앉아 있니?

+1

:

g++ -ldl -Wl,-export-dynamic kernel.C -o kernel 

정확한 시나리오를 설명 LD 남자 페이지에서 인용 :

당신은 실행 파일을 연결하기위한 -export-동적 링커 플래그를 필요 'extern "C"'하지만, 그것을 정의 할 때는 그렇지 않습니다. – doctorlove

답변

5

실행 파일의 기호는 기본적으로 내보내지지 않습니다. 당신이 말하는 당신이 그것을 선언 할 때

If you use "dlopen" to load a dynamic object which needs to refer 
back to the symbols defined by the program, rather than some other 
dynamic object, then you will probably need to use this option when 
linking the program itself. 
+0

'-rdynamic'은'-Wl, -export-dynamic'과 동일하기 때문에'g ++ -Wall -rdynamic kernel.C -o kernel -ldl'을 사용할 수 있습니다. –

+0

아직이 문제는 해결되지 않았지만 이번에는 library.so : 정의되지 않은 심볼 : 초기화 이며 파일 이름이 kernel.C가 아닙니다. kernel.cpp – Adarsh

+0

도움을 주셔서 감사합니다! -rdynamic이 내가 필요한 전부 였어. –