Can I change 'rpath' in an already compiled binary?
Solution 1:
There is a more universal tool than chrpath
called patchelf
. It was originally created for use in making packages for Nix and NixOS (packaging system and a GNU/Linux distribution).
In case there is no rpath in a binary (here called rdsamp), chrpath
fails:
chrpath -r '$ORIGIN/../lib64' rdsamp
rdsamp: no rpath or runpath tag found.
On the other hand,
patchelf --set-rpath '$ORIGIN/../lib64' rdsamp
succeeds just fine.
Solution 2:
There is a tool called chrpath
which can do this - it's probably available in your distribution's packages.
Solution 3:
Just like @user7610 said, the right way to go is the patchelf
tool.
But, I feel that I can give a more comprehensive answer, covering all the commands one needs to do exactly that.
For a comprehensive article on the subject, click here
First of all, many developers talk about RPATH
, but they actually mean RUNPATH
. These are two different optional dynamic sections, and the loader handles them very differently. You can read more about the difference between them in the link I mentioned before.
For now, just remember:
- If
RUNPATH
is set,RPATH
is ignored -
RPATH
is deprecated and should be avoided -
RUNPATH
is preferred because it can be overridden byLD_LIBRARY_PATH
See the current R[UN]PATH
readelf -d <path-to-elf> | egrep "RPATH|RUNPATH"
Clear the R[UN]PATH
patchelf --remove-rpath <path-to-elf>
Notes:
- Removes both
RPATH
andRUNPATH
Add values to R[UN]PATH
patchelf [--force-rpath] --set-rpath "<desired-rpath>" <path-to-elf>
Notes:
-
<desired-path>
is a colon separated directories list, e.g:/my/libs:/my/other/libs
- If you specify
--force-rpath
, setsRPATH
, otherwise setsRUNPATH