linuxraspbianldelf

runpath with $ORIGIN ignored when program is set user id root


I am trying to run an application that is set user id root on Raspbian :

-rwsr-xr-x 1 root     user 508K May 11 13:55 my_app

This application is shipped with a shared library installed in a non standard location (within the deployment directory /opt/my_project/) :

├── my_app
├── libs
│   └── libMyLib.so

The binary has a correct runpath set when i check it with chrpath -l my_app :

my_app: RUNPATH=/usr/local/qt6/lib/:$ORIGIN/libs

However, libMyLib.so is not found when i try to run the application :

./my_app: error while loading shared libraries: libMyLib.so: cannot open shared object file: No such file or directory

For testing purposes, i have removed the set user id bit and the library is found (but of course the application won't run correctly).

Also when i check what ld has found using ldd my_app :

libMyLib.so => /opt/my_project/./libs/libMyLib.so (0x76e84000)

But then i have the previous error at run-time.

Another point is that when i replace $ORIGIN with the absolute path to the library using chrpath, it's also fine. It seems the issue is with $ORIGIN, as if the additional path containing the dynamic string $ORIGIN was removed from the search path when the program is set user id root.

From https://www.man7.org/linux/man-pages/man8/ld.so.8.html, i read that LD_LIBRARY_PATH is ignored in secure-execution mode which is the case here but i don't see any secure warning related to $ORIGIN.

What is the correct way to fix this ? (A part from using chrpath -r during installation if possible).

Thanks.


Solution

  • From the source:

     287               /* For SUID/GUID programs we normally ignore the path with
     288                  $ORIGIN in DT_RUNPATH, or DT_RPATH.  However, there is
     289                  one exception to this rule, and it is:
     290 
     291                    * $ORIGIN appears as the first path element, and is
     292                      the only string in the path or is immediately
     293                      followed by a path separator and the rest of the
     294                      path,
     295 
     296                    and ...
     297 
     298                    * The path is rooted in a trusted directory.
     299 
     300                  This exception allows such programs to reference
     301                  shared libraries in subdirectories of trusted
     302                  directories.  The use case is one of general
     303                  organization and deployment flexibility.
     304                  Trusted directories are usually such paths as "/lib64"
     305                  or "/usr/lib64", and the usual RPATHs take the form of
     306                  [$ORIGIN/../$LIB/somedir].  */