Binary Size: function-sections, data-sections, etc.

dsimcha dsimcha at yahoo.com
Tue Dec 20 10:14:03 PST 2011


I started poking around and examining the details of how the GNU 
linker works, to solve some annoying issues with LDC.  In the 
process I the following things that may be useful low-hanging 
fruit for reducing binary size:

1.  If you have an ar library of object files, by default no dead 
code elimination is apparently done within an object file, or at 
least not nearly as much as one would expect.  Each object file 
in the ar library either gets pulled in or doesn't.

2.  When something is compiled with -lib, DMD writes libraries 
with one object file **per function**, to get around this.  GDC 
and LDC don't.  However, if you compile the object files and then 
manually make an archive with the ar command (which is common in 
a lot of build processes, such as gtkD's), this doesn't apply.

3.  The defaults can be overridden if you compile your code with 
-ffunction-sections and -fdata-sections (DMD doesn't support 
this, GDC and LDC do) and link with --gc-sections.  
-ffunction-sections and -fdata-sections cause each function or 
piece of static data to be written as its own section in the 
object file, instead of having one giant section that's either 
pulled in or not.  --gc-sections garbage collects unused 
sections, resulting in much smaller binaries especially when the 
sections are fine-grained.

On one project I'm working on, I compiled all the libs I use with 
GDC using -ffunction-sections -fdata-sections.  The stripped 
binary is 5.6 MB when I link the app without --gc-sections, or 
3.5 MB with --gc-sections.  Quite a difference.  The difference 
would be even larger if Phobos were compiled w/ 
-ffunction-sections and -fdata-sections.  (See 
https://bitbucket.org/goshawk/gdc/issue/293/ffunction-sections-fdata-sections-for 
).

DMD can't compile libraries with -ffunction-sections or 
-fdata-sections and due to other details of my build process that 
are too complicated to explain here, the results from DMD aren't 
directly comparable to those from GDC.  However, --gc-sections 
reduces the DMD binaries from 11 MB to 9 MB.

Bottom line:  If we want to reduce D's binary size there are two 
pieces of low-hanging fruit:

1.  Make -L--gc-sections the default in dmd.conf on Linux and 
probably other Posix OS's.

2.  Add -ffunction-sections and -fdata-sections or equivalents to 
DMD and compile Phobos with these enabled.  I have no idea how 
hard this would be, but I imagine it would be easy for someone 
who's already familiar with object file formats.


More information about the Digitalmars-d mailing list