Shcheklein Shcheklein - 5 months ago 21
Linux Question

Linux static linking is dead?

In fact, -static gcc flag on Linux doesn't work now. Let me cite from the GNU libc FAQ:


2.22. Even statically linked programs need some shared libraries
which is not acceptable for me. What
can I do?


{AJ} NSS (for details just type `info
libc "Name Service Switch"') won't
work properly without shared
libraries. NSS allows using different
services (e.g. NIS, files, db, hesiod)
by just changing one configuration
file (/etc/nsswitch.conf) without
relinking any programs. The only
disadvantage is that now static
libraries need to access shared
libraries. This is handled
transparently by the GNU C library.

A solution is to configure glibc with
--enable-static-nss. In this case you can create a static binary that will
use only the services dns and files
(change /etc/nsswitch.conf for this).
You need to link explicitly against
all these services. For example:

gcc -static test-netdb.c -o test-netdb \
-Wl,--start-group -lc -lnss_files -lnss_dns -lresolv -Wl,--end-group


The problem with this approach is
that you've got to link every static
program that uses NSS routines with
all those libraries.

{UD} In fact, one cannot say anymore that a libc compiled with this option
is using NSS. There is no switch
anymore. Therefore it is highly
recommended not to use
--enable-static-nss since this makes the behaviour of the programs on the
system inconsistent.



Concerning that fact is there any reasonable way now to create a full-functioning static build on Linux or static linking is completely dead on Linux? I mean static build which:


  • Behaves exactly the same way as
    dynamic build do (static-nss with
    inconsistent behaviour is evil!);

  • Works on reasonable variations of glibc environment and Linux versions;


Answer

Concerning that fact is there any reasonable way now to create a full-functioning static build on Linux or static linking is completely dead on Linux?

I do not know where to find the historic references, but yes, static linking is dead on GNU systems. (I believe it died during the transition from libc4/libc5 to libc6/glibc 2.x.)

The feature was deemed useless in light of:

  • Security vulnerabilities. Application which was statically linked doesn't even support upgrade of libc. If app was linked on system containing a lib vulnerability then it is going to be perpetuated within the statically linked executable.

  • Code bloat. If many statically linked applications are ran on the same system, standard libraries wouldn't be reused, since every application contains inside its own copy of everything. (Try du -sh /usr/lib to understand the extent of the problem.)

Try digging LKML and glibc mail list archives from 10-15 years ago. I'm pretty sure long ago I have seen something related on LKML.