3.7 Linking static libraries

Why return to ar and ranlib silliness when you’ve had a taste of libtool? Well, sometimes it is desirable to create a static archive that can never be shared. The most frequent case is when you have a set of object files that you use to build several different libraries. You can create a “convenience library” out of those objects, and link against that with the other libraries, instead of listing all the object files every time.

If you just want to link this convenience library into programs, then you could just ignore libtool entirely, and use the old ar and ranlib commands (or the corresponding GNU Automake ‘_LIBRARIES’ rules). You can even install a convenience library using GNU Libtool, though you probably don’t want to and hence GNU Automake doesn’t allow you to do so.

burger$ libtool --mode=install ./install-sh -c libhello.a \
                /local/lib/libhello.a
./install-sh -c libhello.a /local/lib/libhello.a
ranlib /local/lib/libhello.a
burger$

Using libtool for static library installation protects your library from being accidentally stripped (if the installer used the -s flag), as well as automatically running the correct ranlib command.

But libtool libraries are more than just collections of object files: they can also carry library dependency information, which old archives do not. If you want to create a libtool static convenience library, you can omit the -rpath flag and use -static to indicate that you’re only interested in a static library. When you link a program with such a library, libtool will actually link all object files and dependency libraries into the program.

If you omit both -rpath and -static, libtool will create a convenience library that can be used to create other libtool libraries, even shared ones. Just like in the static case, the library behaves as an alias to a set of object files and dependency libraries, but in this case the object files are suitable for inclusion in shared libraries. But be careful not to link a single convenience library, directly or indirectly, into a single program or library, otherwise you may get errors about symbol redefinitions.

The key is remembering that a convenience library contains PIC objects, and can be linked where a list of PIC objects makes sense; i.e. into a shared library. A static convenience library contains non-PIC objects, so can be linked into an old static library, or a program.

When GNU Automake is used, you should use noinst_LTLIBRARIES instead of lib_LTLIBRARIES for convenience libraries, so that the -rpath option is not passed when they are linked.

As a rule of thumb, link a libtool convenience library into at most one libtool library, and never into a program, and link libtool static convenience libraries only into programs, and only if you need to carry library dependency information to the user of the static convenience library.

Another common situation where static linking is desirable is in creating a standalone binary. Use libtool to do the linking and add the -all-static flag.