What is the difference between LD_PRELOAD_PATH and LD_LIBRARY_PATH?
I understand what they do, but not the particulars of how they differ.
From http://en.wikipedia.org/wiki/Dynamic_linker
The dynamic linker can be influenced into modifying its behavior during either the program's execution or the program's linking. Examples of this can be seen in the run-time linker manual pages for various Unix-like systems. A typical modification of this behavior is the use of the LD_LIBRARY_PATH and LD_PRELOAD environment variables. These variables adjust the runtime linking process by searching for shared libraries at alternate locations and by forcibly loading and linking libraries that would otherwise not be, respectively.
In particular, I am interested in the differences in Linux which has both LD_PRELOAD_PATH and LD_LIBRARY_PATH:
https://linuxgazette.net/issue48/tag/48.html
Update: The author of this 1999 Linux Gazette article notes in his 2013 comment below the accepted answer that LD_PRELOAD_PATH does not in fact exist.
LD_LIBRARY_PATH is the default library path which is accessed to check for available dynamic and shared libraries. It is specific to linux distributions. It is similar to environment variable PATH in windows that linker checks for possible implementations during linking time.
The LD_LIBRARY_PATH environment variable tells Linux applications, such as the JVM, where to find shared libraries when they are located in a different directory from the directory that is specified in the header section of the program.
LIBPATH or LD_LIBRARY_PATH specifies the directories where Sybase IQ shared libraries are located. On UNIX, set the library path variable by running the environment source file.
ld.so is a self-contained, position independent program image providing run-time support for loading and link-editing shared objects into a process's address space.
LD_PRELOAD
(not LD_PRELOAD_PATH
) is a list of specific libraries (files) to be loaded before any other libraries, whether the program wants it or not. LD_LIBRARY_PATH
is a list of directories to search when loading libraries that would have been loaded anyway. On linux you can read man ld.so
for more information about these and other environment variables that affect the dynamic linker.
The most important difference is that LD_PRELOAD can replace functions statically linked into a binary.
If ever you find that LD_PRELOAD works for you, but LD_LIBRARY_PATH mysteriously does not, this, almost certainly, is the reason why.
For example, I was debugging GNU Readline in bash
and was confused at first why my modified libreadline.so was loading with LD_PRELOAD but not LD_LIBRARY_PATH.
$ LD_PRELOAD=shlib/libreadline.so bash -
(worked)
$ LD_LIBRARY_PATH=shlib/ bash -
(failed)
Taking a look with the ldd command, which lists dependencies on dynamically linked libraries, gives the answer:
$ ldd /bin/bash
linux-vdso.so.1
libtinfo.so.6 => /lib/x86_64-linux-gnu/libtinfo.so.6
libdl.so.2 => /lib/x86_64-linux-gnu/libdl.so.2
libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6
/lib64/ld-linux-x86-64.so.2
Sure enough, libreadline is not listed as one of the shared libraries. Therefore, /bin/bash on my machine must have been statically linked with its own version of libreadline at compile time. The reason LD_LIBRARY_PATH doesn't work is because the binary never asks the dynamic linker (ld.so) to load libreadline.
LD_PRELOAD, on the other hand, loads the library no matter what, allowing a library to override even statically linked functions.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With