Statically (lib.a) - The program contains the library code within its own main file. The drawback with this method is that the resultant file is large and therefore consumes large amounts of disc space and RAM when loaded. Also, the greater the number of other applications that use this library, the more resources are used and, if the library code needs changing, each program using the code must be re-linked.
Dynamic (lib.so) - Like a Dynamic Linked Library in Windows, they are a much more useful and efficient way of using shared functionality. This method means that the required libraries are loaded into RAM only when the program needs them. It reduces the file size of the executable, allows the library to only run in memory once whilst simultaneously being used by multiple programs, and if the functionality changes or is improved in the library, it only needs to be updated once. However, there are also some downsides with using Dynamic Libraries; 1) If you make a change to the shared library and obviously many programs use this library, this change may be incompatible with some of the programs that use it, 2) Configuration files and environmental variables must be set correctly so that the programs can locate the libraries, 3) if shared libraries get overwritten accidentally, it could cause severe system issues or even result in a system failing to boot.
Getting Programs to Find Libraries
To permanently set the library path location on a system wide basis, the /etc/ld.so.conf file is used. This file may have a number of lines, all of which point to where libraries are located, or it may only have an include line which adds other files as part of the same file;
include /etc/ld.so.conf.d/*.conf
In this case, all files in the /etc/ld.so.conf.d/ directory are also added to the path, as an example, the contents of the directory might appear like this;
kernel-2.6.32-431.17.1.el6.x86_64.conf
kernel-2.6.32-431.23.3.el6.centos.plus.x86_64.conf
kernel-2.6.32-431.20.3.0.1.el6.centos.plus.x86_64.conf
kernel-2.6.32-431.el6.x86_64.conf
kernel-2.6.32-431.20.3.el6.centos.plus.x86_64.conf
mysql-x86_64.conf
/lib and /usr/lib are also automatically included as library locations by default along with those locations specified above. If the path is changed using this method, the Dynamic Linker ldconfig must be run afterwards.
In practice, path locations are very rarely changed system wide, more often than not, they only need to be set via an environmental variable (LD_LIBRARY_PATH). The path can be set by using;
$ export LD_LIBRARY_PATH=/path/to/library:/another/path/library
They are added to the start of the search path and take precedence over all other paths specified.
If when you launch an application, and an error of the type; "Error while loading shared libraries: lib.so.1" appears, it should be fairly obvious that the lib.so.1 library can't by found by the application. But what if you know that this library absolutely, definitely is installed Well, in this case start by adding the path using the LD_LIBRARY_PATH environmental
variable as shown above but if this doesn't work, you may need to create a symbolic link to the library (especially if the library naming convention is slightly different to the one the application is looking for) e.g. the app looks for lib.so.1 but lib.so.1.1 is installed... you will need to perform this bit of magic;
# ln -s lib.so.1.1 lib.so.1
This means create a symbolic link called lib.so.1 at the current location, (so the executable can find it when it runs) but point it to the actual path of lib.so.1.1 (which is where the library actually is). ldconfig must then be run.
Management Tools for Libraries
There are two tools for managing libraries, one of which we have already touched on;
ldd and ldconfig
ldd is used to find what libraries an executable file uses and in this example for the df (free disc space) command you can see the library name and full path to the library (it's best used with the verbose switch);
# ldd -v /bin/df
linux-vdso.so.1 => (0x00007fffeadc5000)
libc.so.6 => /lib64/libc.so.6 (0x00007f69a2228000)
/lib64/ld-linux-x86-64.so.2 (0x00007f69a25c7000)
Version information:
/bin/df:
libc.so.6 (GLIBC_2.3) => /lib64/libc.so.6
libc.so.6 (GLIBC_2.4) => /lib64/libc.so.6
libc.so.6 (GLIBC_2.3.4) => /lib64/libc.so.6
libc.so.6 (GLIBC_2.2.5) => /lib64/libc.so.6
/lib64/libc.so.6:
ld-linux-x86-64.so.2 (GLIBC_PRIVATE) => /lib64/ld-linux-x86-64.so.2
ld-linux-x86-64.so.2 (GLIBC_2.3) => /lib64/ld-linux-x86-64.so.2
When an RPM or DEB package is installed, the ldconfig command is run automatically at the end of this procedure.
Getting Programs to Find Libraries
To permanently set the library path location on a system wide basis, the /etc/ld.so.conf file is used. This file may have a number of lines, all of which point to where libraries are located, or it may only have an include line which adds other files as part of the same file;
include /etc/ld.so.conf.d/*.conf
In this case, all files in the /etc/ld.so.conf.d/ directory are also added to the path, as an example, the contents of the directory might appear like this;
kernel-2.6.32-431.17.1.el6.x86_64.conf
kernel-2.6.32-431.23.3.el6.centos.plus.x86_64.conf
kernel-2.6.32-431.20.3.0.1.el6.centos.plus.x86_64.conf
kernel-2.6.32-431.el6.x86_64.conf
kernel-2.6.32-431.20.3.el6.centos.plus.x86_64.conf
mysql-x86_64.conf
In practice, path locations are very rarely changed system wide, more often than not, they only need to be set via an environmental variable (LD_LIBRARY_PATH). The path can be set by using;
$ export LD_LIBRARY_PATH=/path/to/library:/another/path/library
They are added to the start of the search path and take precedence over all other paths specified.
If when you launch an application, and an error of the type; "Error while loading shared libraries: lib.so.1" appears, it should be fairly obvious that the lib.so.1 library can't by found by the application. But what if you know that this library absolutely, definitely is installed Well, in this case start by adding the path using the LD_LIBRARY_PATH environmental
variable as shown above but if this doesn't work, you may need to create a symbolic link to the library (especially if the library naming convention is slightly different to the one the application is looking for) e.g. the app looks for lib.so.1 but lib.so.1.1 is installed... you will need to perform this bit of magic;
# ln -s lib.so.1.1 lib.so.1
This means create a symbolic link called lib.so.1 at the current location, (so the executable can find it when it runs) but point it to the actual path of lib.so.1.1 (which is where the library actually is). ldconfig must then be run.
Management Tools for Libraries
There are two tools for managing libraries, one of which we have already touched on;
ldd and ldconfig
ldd is used to find what libraries an executable file uses and in this example for the df (free disc space) command you can see the library name and full path to the library (it's best used with the verbose switch);
# ldd -v /bin/df
linux-vdso.so.1 => (0x00007fffeadc5000)
libc.so.6 => /lib64/libc.so.6 (0x00007f69a2228000)
/lib64/ld-linux-x86-64.so.2 (0x00007f69a25c7000)
Version information:
/bin/df:
libc.so.6 (GLIBC_2.3) => /lib64/libc.so.6
libc.so.6 (GLIBC_2.4) => /lib64/libc.so.6
libc.so.6 (GLIBC_2.3.4) => /lib64/libc.so.6
libc.so.6 (GLIBC_2.2.5) => /lib64/libc.so.6
/lib64/libc.so.6:
ld-linux-x86-64.so.2 (GLIBC_PRIVATE) => /lib64/ld-linux-x86-64.so.2
ld-linux-x86-64.so.2 (GLIBC_2.3) => /lib64/ld-linux-x86-64.so.2
You can even use ldd to find the dependencies of dependencies i.e. what are the dependences of the libraries, that the executable requires.
With ldconfig, you may have already gathered by its use in the previous section, that it operates to either clear something or reload something, and you'd be correct in that assumption. Linux uses a cached list of paths to the libraries, which are not updated unless this command is run. It takes multiple options but if you just want to rebuild the cache, just use it in verbose mode;
# ldconfig -v
Or you can print the contents of the cache without affecting it by using;
# ldconfig -p
No comments:
Post a Comment