I was trying out dynamic linking of libraries. This is a toy program I wrote:
// prog.c
#include<stdio.h>
int sum(int, int);
int diff(int, int);
int main(int argc, char* argv[]) {
int a = 10, b = 5;
printf("Sum: %d\n", sum(a, b));
printf("Diff: %d\n", diff(a, b));
}
// sum.c
int sum(int a, int b) {
return a b;
}
// diff.c
int diff(int a, int b) {
return a - b;
}
Compiled using these commands:
$ gcc -fPIC -c sum.c diff.c
$ gcc -shared -o libdtest.so sum.o diff.o
$ gcc prog.c -L. -l dtest
When I tried to run this, it says ./a.out: error while loading shared libraries: libdtest.so: cannot open shared object file: No such file or directory
. The file libdtest.so is still in my folder. What is the mistake here?
I used readelf to read a.out file. There, in the dynamic section, linked libraries were libdtest.so and libc.so.6 . But I couldn't find any reference to their full paths. How does program interpreter locate those files and load them?
CodePudding user response:
The dynamic library loader have a fixed set of paths that it uses to search for libraries. If you have a custom library which isn't in that set then the library won't be found and you get an error.
Unfortunately the linker doesn't automatically add the path to the libraries it links with by default to the finished executable. Instead you must specify a special option to add the path: -rpath
.
You can't use -rpath
directly with the gcc
front-end program, it's a linker-specific option. You need to use the -Wl
option:
$ gcc prog.c -L. -l dtest -Wl,-rpath=.
Other possible solution includes adding the path to the set the dynamic loader uses (not recommended for uncommon paths), or setting the LD_LIBRARY_PATH
environment variable (which is not recommended at all).