How To Install and Access Shared Libraries (C And C++)
Following on from last week, you should have been able to build your own .so library file and link to it with a separate executable. This week we’ll look at installing the shared library (see last week for the source files. This week’s commands follow on from there). Basically we have three options when it comes to building and including shared libraries.
Option 1: rpath
You’ve already seen one option, which is to specify the location of the library with -L and also pass an -rpath to the linker so that it embeds that path in the executable stating where the library can be found (so the loader will be able to locate it at runtime).
Problems with rpath
Using rpath is fine, but if you share your shared library with others, they all need to make sure it lives in the same directory that you have specified. In my case, the library was located in my home directory, faye, which wouldn’t be much good if I wanted anyone else to use my program on their computer!
Option 2: LD_LIBRARY_PATH
This second method uses the environment variable LD_LIBRARY_PATH. You can see what it is currently set to with the command:
echo $LD_LIBRARY_PATH
This should be blank (unless you have previously used it for something!). To use it, you just need to set it to also include the location of your shared object:
export LD_LIBRARY_PATH=/home/faye:$LD_LIBRARY_PATH
Now if we echo the command we see:
/home/faye:
And at compile time, we can create an executable that links to the library with the following line:
g++ -Wall -L/home/faye/sotest main.cpp -lpal
We pass the path to the linker with the -L option above and the LD_LIBRARY_PATH variable tells the loader where to find the library when we run the executable (so we no longer need the rpath option to embed the path into the executable).
Problems with LD_LIBRARY_PATH
LD_LIBRARY_PATH isn’t really the optimal solution – it’s good for testing because you don’t need root access to use it, but you probably don’t want to distribute code that relies on LD_LIBRARY_PATH being set. Before we move on, clear the LD_LIBRARY_PATH variable with:
unset LD_LIBRARY_PATH
Option 3: ldconfig
This is the ‘official’ way to install your shared library, and it requires root privileges. First of all, the location we’re going to use is the standard /usr/lib. You need to copy the library to that location (which you will need to use sudo for, or login as root to perform):
sudo mv /home/faye/libpal.so /usr/lib
Next run ldconfig, which will update the cache of libraries available in the standard system directories:
sudo ldconfig
You can check if the cache has been updated by requesting the cache and grepping it for our libpal library:
ldconfig -p | grep libpal libpal.so (libc6,x86-64) => /lib/libpal.so //here it is!
Now we can compile our executable exactly as we would normally (and as we originally tried last week):
g++ -Wall main.cpp -lpal
We don’t need the rpath (the loader finds the library via the ldconfig cache), we don’t need the -L option (the linker finds the library in the standard search paths), and it runs exactly as it should. Hooray!