I am using ubuntu 12.04. Every time I start my bash terminal and every time when I finish typing a command(and press enter) , I get this message:
ERROR: ld.so: object '/usr/lib/liblunar-calendar-preload.so' from
LD_PRELOAD cannot be preloaded: ignored.
It is weird.
So what is the environment variable LD_PRELOAD used for? And what is the going on behind the scene?
Thanks.
The linker takes some environment variables into account. one is LD_PRELOAD
from man 8 ld-linux:
LD_PRELOAD
A whitespace-separated list of additional, user-specified, ELF
shared libraries to be loaded before all others. This can be
used to selectively override functions in other shared
libraries. For setuid/setgid ELF binaries, only libraries in
the standard search directories that are also setgid will be
loaded.
Therefore the linker will try to load libraries listed in the LD_PRELOAD variable before others are loaded.
What could be the case that inside the variable is listed a library that can't be pre-loaded. look inside your .bashrc or .bash_profile environment where the LD_PRELOAD is set and remove that library from the variable.
If you want to make sure that the library is loaded if and only if the program lunar-calendar-gtk is launched, you can apply this:
You set the environment variable per command by prefixing the command with it:
$ LD_PRELOAD="liblunar-calendar-preload.so" printenv "LD_PRELOAD"
liblunar-calendar-preload.so
$ printenv "LD_PRELOAD"
$
You can then choose to put this in a shell script and make lunar-calendar-gtk a symlink to this shell script, replaceing the original referencee. This effectively makes sure that the library is loaded everytime the original application is executed.
You will have to rename the original lunar-calendar-gtk to something else, which might not be too intriguing as it possibly may cause issues with uninstallation and upgrading. However, I found it useful with a former version of Skype.
Thanks for the responses. I think I've solved the problem just now.
Since LD_PRELOAD is for setting some library proloaded, I check the library that ld preloads with LD_PRELOAD, one of which is "liblunar-calendar-preload.so", that is not existing in the path "/usr/lib/liblunar-calendar-preload.so", but I find a similar library "liblunar-calendar-preload-2.0.so", which is a difference version of the former one.
Then I guess maybe liblunar-calendar-preload.so was updated to a 2.0 version when the system updated, leaving LD_PRELOAD remain to be "/usr/lib/liblunar-calendar-preload.so". Thus the preload library name was not updated to the newest version.
To avoid changing environment variable, I create a symbolic link under the path "/usr/lib"
sudo ln -s liblunar-calendar-preload-2.0.so liblunar-calendar-preload.so
Then I restart bash, the error is gone.
It means the path you input caused an error. In your LD_PRELOAD command, modify the path like the error tips:
/usr/lib/liblunar-calendar-preload.so
I got this type of error when I installed Citrix client on my Raspberry Pi. In short there is a file /etc/ld.so.preload. The library my system was complaining about was listed in that file. I commented it out with a # and system stopped complaining.
The solution that worked for me was using sudo vim and going into /etc/ld.so.preload
I then just removed the line
/usr/local/lib/AppProtection/libAppProtection.so
Then I just saved the file and everything worked without issues.
When I executed the following command, everything became better.
unset LD_PRELOAD
You can check /etc/ld.so.preload file content
I fix it by:
echo "" > /etc/ld.so.preload
Related
I want to hook some functions in libssl with LD_PRELOAD in systemd.
In systemd file I put
ExecStart=/etc/myscript.sh
and in /etc/myscript.sh I put
#!/bin/sh
LD_PRELOAD=/lib/inject_libssl.so /bin/run
When I look at /proc/RUN_PID/maps I can see that inject_libssl.so is realy injected to the process but the original libssl.so is loaded before the the injected library, so my hook doesn't work.
I olso tried
ExecStart=/bin/run
Environment="LD_PRELOAD=/lib/inject_libssl.so"
But I got the same results.
If I run LD_PRELOAD=/lib/inject_libssl.so curl https://google.com the injected libssl works well.
Why is that please?
Can you try this script to see which one will be loaded ?
#!/usr/bin/env bash
cp /lib/x86_64-linux-gnu/libssl.so /tmp/inject_libssl.so
LD_PRELOAD=/tmp/inject_libssl.so /bin/run
Can you also try to put your .so in /usr/lib/x86_64-linux-gnu ?
The reason is probably that systemd runs your script / binary in set-user-ID mode. According to the dynamic linker documentation, LD_PRELOAD support is limited then:
For set-user-ID/set-group-ID ELF binaries, preload pathnames
containing slashes are ignored, and libraries in the standard search
directories are loaded only if the set-user-ID permission bit is
enabled on the library file.
So you need to copy your library to the proper place and provide the permission accordingly. You might be able to work around this with a specific User= setting or by using a wrapper.
i want to install cpanm WWW::Curl::Form on my Synology NAS. But that fails. Here is the output cpanm WWW::Curl::Form WWW::Curl::Easy File::Find::Rule String::CRC32 URI::Escape
--> Working on WWW::Curl::Form
Fetching http://www.cpan.org/authors/id/S/SZ/SZBALINT/WWW-Curl-4.17.tar.gz ... OK
Configuring WWW-Curl-4.17 ... OK
Building and testing WWW-Curl-4.17 ... FAIL
! Installing WWW::Curl::Form failed. See /var/services/homes/fox/.cpanm/work/1541095458.25803/build.log
the log file gives me:
make: i686-linux-gnu-ld: Command not found
But i dont know how to fix it on my Synology NAS (DSM 6.2 and appollolake architecture DS918+)
After reviewing your additional comments, I believe I have potential solution. It looks like you are trying to install some Perl modules via the default Perl shell, cpan. As part of the installation process, the make utility is being executed. This utility is heavily used for compiling and building source from C and C++ source code, along with other languages.
The make utility is trying to call some executable i686-linux-gnu-ld which is a linker, see ld. A linker is a utility used in C programming for linking (combining) multiple compiled object files into a single executable binary. make is calling this utility as some sort of build process. Instead of calling i686-linux-gnu-ld it should probably just be calling ld. The only thing I am not sure about is why it is using the full name of the utility instead of ld.
I can think of two solutions. The first would be to update the make file to use the correct name for the linker. I'm not sure how you would do this when it is being installed via cpan since it is downloading a package and executing the make file before you have a chance to modify it. The other option is to create a symbolic link from the incorrect name and path of ld that the make file is using to the correct path /opt/bin/ld. This will result in ld being called when i686-linux-gnu-ld is called. Also, I forgot to mention it earlier but the which command will tell you where an executable / command is located on your shell's path.
The Stack Overflow post, How to symlink a file in Liunx?, gives a good explanation of how to create a symlink. You need to create a symlink to point to the correct name and path of the linker. To do so run the following command:
ln -s /opt/bin/ld /usr/bin/i686-linux-gnu-ld
Depending on the permissions of these directories you may need to run this command under a account with elevated permissions or via sudo. I apologize for this post being rather long and verbose. I just wanted to explain my solution in detail. I hope this helps. Please let me know if this doesn't resolve the problem.
edit: fixed typo in the command.
It seems this question has been asked very often before but none of the solutions seem to apply in my case.
I'm in a CMake/Linux environment and have to run an executable binary during the build step (protoc in particular).
This binary needs a library but it's not installed (and cannot be) in the in the standard directories like /usr, so the library cannot be found.
Unfortunately I cannot manipulate the protoc call because it's embedded in a 3rd party script.
I can now set LD_LIBRARY_PATH before every make or set it system wide but this is very inconvenient especially when it comes to IDEs in which the build takes place or distributed build scenarios with continuous build environments.
I tried to set LD_LIBRARY_PATH via
set(ENV{LD_LIBRARY_PATH} "/path/to/library/dir")
but this seems to have no effect during the build step.
So my question is: can I set a library search path in CMake which is used during the build?
Try this
SET(ENV{LD_LIBRARY_PATH} "/path/to/library/dir:$ENV{LD_LIBRARY_PATH}")
I also used this dirty trick to temporary change some environment variables:
LD_LIBRARY_PATH="/path/to/library/dir:$LD_LIBRARY_PATH" cmake ...
After execution of this line LD_LIBRARY_PATH is not changed in the current shell.
Also, I do not find it bad to change LD_LIBRARY_PATH before invoking cmake:
export LD_LIBRARY_PATH=...
It won't change anything system-wide, but it would be used for your current shell, current build process. The same holds for CI builds. You can save the variable and restore it after cmake invocation:
MY_LD=$LD_LIBRARY_PATH
export LD_LIBRARY_PATH=...
cmake...
export LD_LIBRARY_PATH=$MY_LD
I have recently run into a somewhat similar problem.
My solution was to incorporate sourcing a file that set the appropriate environment into every command.
For example, this custom command:
add_custom_command(
OUTPUT some_output
COMMAND some_command
ARGS some_args
DEPENDS some_dependencies
COMMENT "Running some_command some_args to produce some_output"
)
Would become:
set(my_some_command_with_environment "source my_environment_script.sh && some_command")
add_custom_command(
OUTPUT some_output
COMMAND bash
ARGS -c "${my_some_command_with_environment} some_args"
DEPENDS some_dependencies
COMMENT "Running some_command some_args to produce some_output"
VERBATIM
)
Obviously, this has some disadvantages:
It relies on a bash shell being available.
It sources the environment script for every command invocation (performance issue) and you will have to change all invocations of commands that rely on that environment variables.
It changes the normal syntax of having the command follow COMMAND and the arguments follow ARGS, as now the 'real' command is part of the ARGS.
My CMake-Fu has proven insufficient to find a syntactically nicer way of doing this, but maybe somebody can comment a nicer way.
I had a similar issue for an executable provided by a third party library. The binary was linked against a library not provided by the distribution but the required library was included in the libs directory of the third party library.
So running LD_LIBRARY_PATH=/path/to/thirdparty/lib /path/to/thirdparty/bin/executable worked. But the package config script didn't set up the executable to search /path/to/thirdparty/lib for the runtime dependent so CMake would complain when CMake tried to run the executable.
I got around this by configuring a bootstrap script and replacing the IMPORTED_LOCATION property with the configured bootstrapping script.
_thirdpartyExe.in
#!/bin/bash
LD_LIBRARY_PATH=#_thirdpartyLibs# #_thirdpartyExe_LOCATION# "$#"
CMakeLists.txt
find_package(ThirdPartyLib)
get_target_property(_component ThirdPartyLib::component LOCATION)
get_filename_component(_thirdpartyLibs ${_component} DIRECTORY)
get_target_property(_thirdpartyExe_LOCATION ThirdPartyLib::exe IMPORTED_LOCATION)
configure_file(
${CMAKE_CURRENT_LIST_DIR} _thirdpartyExe.in
${CMAKE_BINARY_DIR}/thirdpartyExeWrapper #ONLY
)
set_target_properties(ThirdPartyLib::exe PROPERTIES IMPORTED_LOCATION ${CMAKE_BINARY_DIR}/thirdpartyExeWrapper)
Honestly I view this as a hack and temporary stop gap until I fix the third party library itself. But as far as I've tried this seems to work on all the IDE's I've thrown at it, Eclipse, VSCode, Ninja, QtCreator, ... etc
When I try to use ediff-revision under Emacs 23.2.1 for a CVS-managed file, I receive the following error in the *ediff-errors* frame, instead of commencing directly to the ediff results:
cygwin warning:
MS-DOS style path detected: c:/Users/BILL/AppData/Local/Temp/misc.cpp.~1.10~
Preferred POSIX equivalent is: /cygdrive/c/Users/BILL/AppData/Local/Temp/misc.cpp.~1.10~
CYGWIN environment variable option "nodosfilewarning" turns off this warning.
Consult the user's guide for more details about POSIX paths:
http://cygwin.com/cygwin-ug-net/using.html#using-pathnames
My problem is that I have already set that CYGWIN environment variable option "nodosfilewarning", so I have no idea why I am receiving this error.
In fact, I can verify this right from an inferior shell under the same Emacs instance:
> set | grep -i nodos
CYGWIN=nodosfilewarning
I am running Cygwin 1.7.9-1 under Windows 7, in case this may be relevant (and I never had this problem before upgrading from Cygwin 1.5 to 1.7).
Any idea how to get rid of this error?
P.S. A subsequent call to ediff-revision succeeds without triggering this warning.
The CYGWIN variable is parsed when the first process in a Cygwin process tree is invoked. Hence, setting it in .bashrc or something like that is too late. A good place to set it is in the global Windows environment, under Control Panel->System->Advanced->Environment Variables.
I added (setenv "CYGWIN" "nodosfilewarning") to setup-cygwin.el. That seems to take care of the problem without, AFAICT, creating other problems. I also filed Emacs bug #14541 for this.
From within emacs, you may also:
M-x setenv
CYGWIN
nodosfilewarning
as an immediate alternative to altering setup-cygwin.el.
I have a problem using ifort. I compiled a code with ifort/mpich1 but whenever I try to run it across several nodes the code gets to a certain point and hangs with an error:
symbol lookup error ... undefined symbol __svml_round2
In poking around, I'm pretty sure this is due to to the ifortvars shell script not being sourced on the compute nodes (if I try to fire the code serially on one node, but haven't sourced the ifort vars I get the same exact error).
What is the best way to bypass this problem? It seems my ".bashrc" file isn't executed when running through mpirun, since I have the "source ..." command in the .bashrc file. I also tried adding the line to the /etc/bash.bashrc file but got no luck. Alternatively I thought perhaps static linking when I compile would solve the problem so I included
-i-static
-static
when compiling with ifort but to no avail, I still get the error.
Does anyone know how to bypass this problem, essentially either how to compile with ifort so as not not need to "source ifortvars" when running a compiled program (a more desirable solution), or how to push out either my path, or how to source the vars through an MPI call? Thanks.
You can give environmental variables as part of the mpirun/mpirun_rsh command.
e.g.
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/usr/lib;mpirun_rsh -ssh -host -np 2 -hostfile hostlist /home/usr1/app.exe -x /home/usr1/config/appconfig.xml