Code:
//a.c I don't use header files as this is just for demo purpose.
extern void function_b(int num);
void function_a(int num) {
function_b(num)
}
//b.c
void function_b(int num) {
...
}
//dll.c
#include <dlfcn.h>
int main() {
void *handle_a;
void *handle_b;
void (*pfunc_a)(int);
...
handle_a = dlopen("./a.so", RTLD_LAZY);
...
pfunc_a = dlsym(handle_a, "function_a");
...
handle_b = dlopen("./b.so", RTLD_GLOBAL);
...
pfunc_a(2020);
...
return 0;
}
We can see that dll.c tries to load shared library in run time and module a has a reference on function_b and module b has the definition of function_b. Let's say we have already created shared libraries a.so, and b.so so those shared libraries exist on disk before the program runs, but when I run the program, it throws an symbol lookup error:
./a.so:undefined symbol: function_b
but for this line of code handle_a = dlopen("./a.so", RTLD_LAZY);
since I use RTLD_LAZY here, the runtime linker doesn't try to resolve the symbol function_b, and there's an opportunity for me to call dlopen("b.so", RTLD_GLOBAL) before calling function_a. This way the dynamic linker will modify the reference in a.so with the definition of function_b in b.so.
My questions are:
Is my understanding correct that the dynamic linker is supposed to modify the
.gotor.got.pltsection ofa.soso that it can be linked/relocated to the instruction address of function_b in the.textsection ofb.so.If my understanding is correct, then why couldn't the dynamic linker still resolve
function_bin this case?