ld
manual page.
.o
files) collected into one file by the ar
program. Static libraries usually end with .a
(i.e., libg++.a
). At link time, static libraries are searched for each global function or variable symbol. If the symbol is found then the code for that symbol is copied into the binary. In addition, any other symbols that were in the original .o
file for the symbol in question are also copied into the binary. In this way, if we need a symbol that is dependent on other functions in the .o
file in which it is defined, at link time we get the dependent functions. There are several important details about linking, such as the order of libraries, that should be discussed in your system documentation.
Shared libraries allow multiple programs to share a library on disk, rather than copying code into a binary, resulting in smaller binaries. Also shared libraries allow a binary to access all of the symbols in a shared library at runtime, even if a symbol was not needed at link time.
A shared library consists of an archive of object files (
.o
files) collected into one file by either the compiler or the linker. Usually, to create a shared library, the .o
files must be compiled into Position Independent Code (PIC) by the compiler. The compiler usually has a special option to produce PIC code, under gcc
/g++
, the -fPIC
option produces PIC code. Shared libraries have suffixes that are architecture dependent: under SunOS4.1 and Solaris, shared libraries end with .so
(i.e., libg++.so
); under HPUX, shared libraries end with .sl
(i.e., libg++.sl
).In addition, shared libraries can also have versioning information included in the name. Shared library versioning is architecture dependent, but a versioned shared library name might look like
libg++.so.2.7.1
. Note that the version of a shared library can be encoded in the shared library in the SONAME
feature of that library. Usually, the SONAME
of a library is the same as the filename (i.e., the SONAME
of /users/ptolemy/gnu/sol2/lib/libg++.so.2.7.1
would be libg++.so.2.7.1
). Interestingly, if you rename a shared library without changing the SONAME
and then link against the renamed shared library, then at runtime the binary may report that it cannot find the proper library. The constraint with shared libraries is that the binary be able to find the shared libraries at run time. Exactly how this is done is architecture dependent, but in general the runtime linker looks for special environment variable that contains pathnames for directories to be searched. Under SunOS4.1.x and Solaris2.x, this environment variable is named
LD_LIBRARY_PATH
. Under HPUX, the variable is named SHLIB_PATH
. A binary can also have a list of pathnames to be searched encoded inside it. Usually this is called the RPATH
. In general, asking the user to set the LD_LIBRARY_PATH
or SHLIB_PATH
is frowned upon. It is better if the binary has the proper RPATH
set at link time.
.o
files archived together. A .o
file inside a library might contain symbols (functions, variables etc.) that are not used by your program.At link time, a static library can have unresolved symbols in it, as long as you don't need the unresolved symbols, and you don't need any symbol that is in a
.o
file that contains an unresolved symbol. However, with shared libraries, you must resolve all the symbols at link time, even if you don't necessarily use the unresolved symbol.As an example, say you have a program that uses a symbol from the
pigi
library ($PTOLEMY/lib.$PTARCH/libpigi.*
), but does not use Octtools which is used by other files that make up the pigi
libraryIf you are linking with a static library, you can have some unresolved symbols in the static library, as long as you don't reference the unresolved symbols. So, in our example, you could just link with the static
libpigi.a
.If you are linking with a shared
libpigi
, you must resolve all the unresolved symbols. So, if you need a symbol from the libpigi
library, then you must also include references to the Octtools libraries that pigilib uses, even though you are not using Octtools. So you would have to link in liboct.so
and libport.so
and the other Octtools libraries.One positive benefit of this is that all the symbols in pigilib are available at run time, which makes incremental linking much easier, especially if we have a shared g++ library.
stars.c
file (where xxx is the domain name, an example file is $PTOLEMY/src/domains/sdf/stars/sdfstars.c
) which gets compiled into xxxstars.o
. At link time, the xxxstars.o
file is included in the link command and the linker searches lib
xxxstars.a
for the symbols defined in xxxstars.o
, and pulls in the rest of the star definition.If you are using shared libraries, then all the symbols in the
lib
xxxstars
file are present at runtime, so you need not include the xxxstars.o
file at link time.