Reputation: 800
I'm trying to build my executable (that depends on library utils.so) using the following command
g++ -L/path/to/libutils -lutils -I/path/to/utils_headers executable.cpp -o executable
Actually I don't have utils.so - only the header files of utils library.
I'm getting the error:
ld: cannot find -lutils
Does linker really need to access all the libraries my executable depends on in order to build my executable? If it does then I'd like to know why it needs to access them.
My executable is a shared library. I'm sure that header files of the utils lib are enough to build it (i.e without having utils.so).
Upvotes: 3
Views: 454
Reputation: 61202
The linkage option -lutils
by default directs the linker to search,
first in the specified library search directories (-Ldir
) and then
in its default search directories, for either of the files libutils.so
(
shared library) or libutils.a
(static library), preferring libutils.so
if both of them are found in the same search directory.
If such a file is found, the linker stops searching and adds that file to the input files of the linkage, whether or not it resolves any references in the linkage. The linker cannot know whether the file resolves any references if it does not input the file.
If no such file is found, the linker gives the error: cannot find -lutils
. Because
you told it to find libutils.{so|a}
and it could not.
You say:
My executable is a shared library
But it isn't. Your compile-and-link command:
$ g++ -L/path/to/libutils -lutils -I/path/to/utils_headers executable.cpp -o executable
is not an attempt to link a shared library. It is an attempt to link a program.1
This would be an attempt to link a shared library:
$ g++ -shared -I/path/to/utils_headers -o libexecutable.so executable.cpp -L/path/to/libutils -lutils
You cannot link a program with unresolved references. But you can link a shared library with unresolved references.
So, you could link a libexecutable.so
like that, or you could link it simply like:
$ g++ -shared -I/path/to/utils_headers -o libexecutable.so executable.cpp
These are two different linkages: if they succeed they produce different output files.
In the first linkage, some symbols will (let's assume) be resolved to definitions provided in libutils.so
or libutils.a
(whichever one is found), and this will be reflected by:
libutils.so
is found: The .dynamic
section of libexecutable.so
contains a DT_NEEDED
structure that expresses a runtime dependency on libutils.so
. libutils.so
will need to be included in any linkage that includes libexecutable.so
, but the output file of such a linkage will itself contain a runtime dependency only on libexecutable.so
.
libutils.a
is found: libexecutable.so
itself contains the definitions for all the symbols
it uses that are defined by object files in libutils.a
.2 libexecutable.so
may be included in subsequent linkages with no need for libutils.{so|a}
.
In the second linkage, the .dynamic
section of libexecutable.so
will not express a runtime
dependency on libutils.so
nor will the file contain definitions of any symbols provided by libutils.{so|a}
. libutils.so
will (again) need to be included in an subsequent linkage that includes libexecutable.so
, but the output file of such a linkage will acquire independent runtime dependencies on both libexecutable.so
and libutils.so
.
But, if you specify -lutils
in the linkage - or any linkage - and the linker cannot find libutils.{so|a}
in any of its search directories, then you get the error you observe, because you told the linker
to input a file, whose effects on the linkage can only be determined and implemented if that file is found - and it cannot be found.
[1] An attempt that is likely to fail, because it consumes libraries before the object files that refer to them
[2] See static-libraries to understand why.
Upvotes: 3
Reputation: 33704
In general, an ELF linker needs a sufficiently accurate representation of the shared object that is linked in. It does not have to be an actually working shared objects, just a sufficiently close representation of it. A few things absolute require data that is not available in the object itself:
However, if you only use C function symbols (not data symbols, or the varieties of symbols that C++ requires) and the target library does not use symbol versioning, you can use a stub library for linking. This is a library that defines all the functions you need and has the appropriate soname, but the functions are just dummies which do not actually do anything.
Upvotes: 2