可以将文章内容翻译成中文,广告屏蔽插件可能会导致该功能失效(如失效,请关闭广告屏蔽插件后再试):
问题:
I\'m trying to compile my program and it returns this error :
usr/bin/ld: cannot find -l<nameOfTheLibrary>
in my makefile I use the command g++
and link to my library which is a symbolic link to my library located on an other directory.
Is there an option to add to make it work please?
回答1:
If your library name is say libxyz.so
and it is located on path say:
/home/user/myDir
then to link it to your program:
g++ -L/home/user/myDir -lxyz myprog.cpp -o myprog
回答2:
To figure out what the linker is looking for, run it in verbose mode.
For example, I encountered this issue while trying to compile MySQL with ZLIB support. I was receiving an error like this during compilation:
/usr/bin/ld: cannot find -lzlib
I did some Googl\'ing and kept coming across different issues of the same kind where people would say to make sure the .so file actually exists and if it doesn\'t, then create a symlink to the versioned file, for example, zlib.so.1.2.8. But, when I checked, zlib.so DID exist. So, I thought, surely that couldn\'t be the problem.
I came across another post on the Internets that suggested to run make with LD_DEBUG=all:
LD_DEBUG=all make
Although I got a TON of debugging output, it wasn\'t actually helpful. It added more confusion than anything else. So, I was about to give up.
Then, I had an epiphany. I thought to actually check the help text for the ld command:
ld --help
From that, I figured out how to run ld in verbose mode (imagine that):
ld -lzlib --verbose
This is the output I got:
==================================================
attempt to open /usr/x86_64-linux-gnu/lib64/libzlib.so failed
attempt to open /usr/x86_64-linux-gnu/lib64/libzlib.a failed
attempt to open /usr/local/lib64/libzlib.so failed
attempt to open /usr/local/lib64/libzlib.a failed
attempt to open /lib64/libzlib.so failed
attempt to open /lib64/libzlib.a failed
attempt to open /usr/lib64/libzlib.so failed
attempt to open /usr/lib64/libzlib.a failed
attempt to open /usr/x86_64-linux-gnu/lib/libzlib.so failed
attempt to open /usr/x86_64-linux-gnu/lib/libzlib.a failed
attempt to open /usr/local/lib/libzlib.so failed
attempt to open /usr/local/lib/libzlib.a failed
attempt to open /lib/libzlib.so failed
attempt to open /lib/libzlib.a failed
attempt to open /usr/lib/libzlib.so failed
attempt to open /usr/lib/libzlib.a failed
/usr/bin/ld.bfd.real: cannot find -lzlib
Ding, ding, ding...
So, to finally fix it so I could compile MySQL with my own version of ZLIB (rather than the bundled version):
sudo ln -s /usr/lib/libz.so.1.2.8 /usr/lib/libzlib.so
Voila!
回答3:
During compilation with g++
via make
define LIBRARY_PATH
if it may not be appropriate to change the Makefile with the -L
option. I had put my extra library in /opt/lib
so I did:
$ export LIBRARY_PATH=/opt/lib/
and then ran make
for successful compilation and linking.
To run the program with a shared library define:
$ export LD_LIBRARY_PATH=/opt/lib/
before executing the program.
回答4:
There does not seem to be any answer which addresses the very common beginner problem of failing to install the required library in the first place.
On Debianish platforms, if libfoo
is missing, you can frequently install it with something like
apt-get install libfoo-dev
The -dev
version of the package is required for development work, even trivial development work such as compiling source code to link to the library.
The package name will sometimes require some decorations (libfoo0-dev
? foo-dev
without the lib
prefix? etc), or you can simply use your distro\'s package search to find out precisely which packages provide a particular file.
(If there is more than one, you will need to find out what their differences are. Picking the coolest or the most popular is a common shortcut, but not an acceptable procedure for any serious development work.)
For other architectures (most notably RPM) similar procedures apply, though the details will be different.
回答5:
Compile Time
When G++ says cannot find -l<nameOfTheLibrary>
, it means that G++ looked for the file lib{nameOfTheLibrary}.so
, but it couldn\'t find it in the shared library search path, which by default points to /usr/lib
and /usr/local/lib
and somewhere else maybe.
To resolve this problem, you should either provide the library file (lib{nameOfTheLibrary}.so
) in those search paths or use -L
command option. -L{path}
tells the G++ (actually ld
) to find library files in path {path}
in addition to default paths.
Example: Assuming you have a library at /home/taylor/libswift.so
, and you want to link your app to this library. In this case you should supply the G++
with the following options:
g++ main.cpp -o main -L/home/taylor -lswift
Note 1: -l
option gets the library name without lib
and .so
at its beginning and end.
Note 2: In some cases, the library file name is followed by its version, for instance libswift.so.1.2
. In these cases, G++ also cannot find the library file. A simple workaround to fix this is creating a symbolic link to libswift.so.1.2
called libswift.so
.
Runtime
When you link your app to a shared library, it\'s required that library stays available whenever you run the app. In runtime your app (actually dynamic linker) looks for its libraries in LD_LIBRARY_PATH
. It\'s an environment variable which stores a list of paths.
Example: In case of our libswift.so
example, dynamic linker cannot find libswift.so
in LD_LIBRARY_PATH
(which points to default search paths). To fix the problem you should append that variable with the path libswift.so
is in.
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/home/taylor
回答6:
When you compile your program you must supply the path to the library; in g++ use the -L option:
g++ myprogram.cc -o myprogram -lmylib -L/path/foo/bar
回答7:
First, you need to know the naming rule of lxxx
:
/usr/bin/ld: cannot find -lc
/usr/bin/ld: cannot find -lltdl
/usr/bin/ld: cannot find -lXtst
lc
means libc.so
, lltdl
means libltdl.so
, lXtst
means libXts.so
.
So, it is lib
+ lib-name
+ .so
Once we know the name, we can use locate
to find the path of this lxxx.so
file.
$ locate libiconv.so
/home/user/anaconda3/lib/libiconv.so # <-- right here
/home/user/anaconda3/lib/libiconv.so.2
/home/user/anaconda3/lib/libiconv.so.2.5.1
/home/user/anaconda3/lib/preloadable_libiconv.so
/home/user/anaconda3/pkgs/libiconv-1.14-0/lib/libiconv.so
/home/user/anaconda3/pkgs/libiconv-1.14-0/lib/libiconv.so.2
/home/user/anaconda3/pkgs/libiconv-1.14-0/lib/libiconv.so.2.5.1
/home/user/anaconda3/pkgs/libiconv-1.14-0/lib/preloadable_libiconv.so
If you cannot find it, you need to install it by yum
(I use CentOS). Usually you have this file, but it does not link to right place.
Link it to the right place, usually it is /lib64
or /usr/lib64
$ sudo ln -s /home/user/anaconda3/lib/libiconv.so /usr/lib64/
Done!
ref: https://i-pogo.blogspot.jp/2010/01/usrbinld-cannot-find-lxxx.html
回答8:
This error may also be brought about if the symbolic link is to a dynamic library, .so, but for legacy reasons -static
appears among the link flags. If so, try removing it.
回答9:
Check the location of your library, for example lxxx.so:
locate lxxx.so
If it is not in the /usr/lib
folder, type this:
sudo cp yourpath/lxxx.so /usr/lib
Done.
回答10:
The library I was trying to link to turned out to have a non-standard name (i.e. wasn\'t prefixed with \'lib\'), so they recommended using a command like this to compile it -
gcc test.c -Iinclude lib/cspice.a -lm
回答11:
Apart from the answers already given, it may also be the case that the *.so file exists but is not named properly. Or it may be the case that *.so file exists but it is owned by another user / root.
Issue 1: Improper name
If you are linking the file as -l<nameOfLibrary>
then library file name MUST be of the form lib<nameOfLibrary>
If you only have <nameOfLibrary>.so
file, rename it!
Issue 2: Wrong owner
To verify that this is not the problem - do
ls -l /path/to/.so/file
If the file is owned by root or another user, you need to do
sudo chown yourUserName:yourUserName /path/to/.so/file
回答12:
My issue was that I renamed the parent directory of the program I was running (mpicc
from MVAPICH), and it somehow screwed up the binary. Even prepending LD_LIBRARY_PATH wasn\'t enough and I had to re-compile it to the correct path.