dynamic linking -> static linking == some _smaller_ executables

dynamic linking -> static linking == some _smaller_ executables

Post by phil-news-nos.. » Thu, 05 Jun 2003 06:51:34



My big library package called LIBH has several executable programs
it builds that use the library in various ways.  Previously I have
been linking those executable programs entirely dynamically.  Now
I switched to a mix, where they still link all system libraries
dynamically, but link to LIBH itself statically.  The surprise,
most of the executables actually got smaller.

My take on what is causing them to be smaller is this:

1.

Some functions are simply quite small.  The overhead added to the
library for dynamic linking is larger than the code from one or
two small functions.

2.

Several of the functions in my library (which are not referenced
by these programs) make references to functions in other libraries
besides libc, such as libm and libdl.  When dynamically linking,
those other libraries have to be added because there are references,
even though the functions that make those references are not being
referenced.  The linker can't know that there isn't some internal
path to actually end up calling the functions in libm or libdl, so
it has to link in everything for which there is a reference.  So now
we have even more space overhead from dynamic linking (not a whole
lot in terms of overall system size, but a few hundred to a thousand
bytes or so) and this means it would take a few functions to match
in size.

When statically linking libc, executables get huge fast.  This is
because so many functions in libc have references to so many other
functions.  So even though you might do printf("%d\n",n) you still
are calling a function that has references to internal code to be
able to handle printf("%f\n",x) even though you never do that. I
give this the term "*uous library" to mean so many functions
internally call so many others, and that static linking that library
means a lot of functions get attached to the executable.  So libc
is not a good candidate in most cases for static linking.  That
may not be so much the case for libm or libdl, so perhaps I could
have made the dynamic .so file for my library link to libm and libdl
statically, thus attaching those functions to the libh.so file, and
thus not having dynamic references to libm.so and libdl.so.  But
that is probably more complication than it is worth.

At this point, I am making LIBH build by default both .a and .so files.
And it omits -fPIC on the .a build, but I will be looking into adding
-fPIC back on a per function basis (functions that call other functions
need -fPIC to maximize sharing of RAM).

My conclusion is that static linking of many libraries has advantages.
It certainly avoids "DLL hell".  But one must also consider risks, too.
If there's a bug in the library that gets fixed, you have to recompile
a lot of stuff to deploy the fix (remember zlib).

And most importantly, remember this wisdom:  YMMV

ref:  http://www.veryComputer.com/

--
-----------------------------------------------------------------
| Phil Howard - KA9WGN |   Dallas   | http://www.veryComputer.com/|

-----------------------------------------------------------------

 
 
 

1. shmem works static-linked, but not dynamic-linked

Shared-memory works on static-linked by not dynamic-linked program:

I wanted to use shared-memory between 2 processes in my application.
I first tried a small test, with one Reader Process that creates and
attaches (shmget, shmat) a shared segment, and one Writer Proces that
attaches afterward. The Writer writes data into the segment, then
sets a ReadDataAvailable flag at a known location in the segment.
The Reader polls that flag, and reads the data when the flag is set.

All this works nicely when the Writer is a static-linked program.
When the Writer is packaged as a ".so" lib, then something breaks.
The Reader can still detect the ReadDataAvailable flag change state,
but when it tries to read the data, all the locations are zeros.

Note that this is EXACTLY the same program code (C) in each case;
I did check with nm and it seems that the shmget/shmat calls are
in each case invoking via GLIBC_2.0.

I suspect this is a glitch in the CPU primary or secondary cache?
The write-through is buggy? Yet it is surprising that the flag
location is written ok, and data that is only a few locations away
is lost... HELP!

I tried 2 different systems, both VALinux:
VALinux 1-CPU i386  v 2.0.36, gcc v 2.7.2.3, ld v2.9.1 (~=RedHat5.2?)
and
VALinux 2-CPU i386 v2.2.12-29.4 smp, (~=RedHat6.0?)
gcc egcs-2.91.66, ld v2.9.5

Sent via Deja.com http://www.deja.com/
Before you buy.

2. PeeWeeLinux 0.61 with glibc 2.2.5 on PC/104. Problems with libc.so.6

3. Static linked std libraryes in Dynamic linked libraryes

4. Peanut Linux

5. time launching aspect : static link vs dynamic link

6. My Network Problem (was No Ping)

7. dynamic linking vs. static linking

8. X and PPP problem (newbie)

9. dynamic link to static link...

10. dynamic linked prog -> static w/o source?

11. building static executables from dynamic executables on solaris

12. Can't make static linked executables

13. Dynamic linking and link editor