开发者

How to determine which object files are actually necessary for linking?

开发者 https://www.devze.com 2023-01-06 08:36 出处:网络
I had to modify some open source code to use in a C project.Instead of building a library from the modified code, I\'d like to just compile and build an executable from my own source combined with the

I had to modify some open source code to use in a C project. Instead of building a library from the modified code, I'd like to just compile and build an executable from my own source combined with the modified open source code. The goal is to have a stand-alone package that can be distributed. I can get this to work just fine using the GNU build tools and have successfully built my executable.

Now I'd like to pare down the amount of code I am building and linking. Is there an easy way to determine which of the open source files I actually need to compile? There are, say, 40 .c files in the open source package. I'开发者_如何学编程m guessing my code only uses (or causes to be used) 20-ish of those files. Currently I'm compiling all of them and throwing everything at the linker. There has to be a smart (and easy?) way to determine which ones I actually need, right?

I'm happy to provide further details if it's helpful. Thanks in advance.


When faced with this I've either simply taken the final link command stripped out all of the objects and then added back in until it works, or processed the output of the nm command.

Worked example:

Looking at the output of nm:

$ nm *.o

a.o:
00000000 T a
         U aa

b.o:
00000000 T b

t.o:
         U a
         U b
00000000 T main

ua.o:
00000000 T ua

ub.o:
00000000 T ub

So I create the following awk script

# find-unused.awk
BEGIN {req["main"]="crt"}

/\.o\:$/{
    gsub(/\:/,"");
    modulename=$0;
}

$1=="U"{
    req[$2] = modulename;
}

/[0-9,a-f].* T/{
    def[$3] = modulename;
}

END{
    print "modules referenced:"
    for (i in req)
    {
        if (def[i] != "")
            print "    "def[i];
    }

    print "functions not found"
    for (i in req)
    {
        if (def[i] == "")
            print "    "i;
    }
}

and then call it like this;

$ nm *.o|awk -f find-unused.awk

it tells me:

modules referenced:
    t.o
    a.o
    b.o
functions not found
    aa

Which is right - because the ua & ub functions in the above example aren't used.


See if you can get your dead-code stripper to tell you what functions/symbols it eliminated during the link. Then you will know what source code you can safely remove. The GNU linker's -map option may be useful on that front. You could, for instance, link once without dead-code stripping, then link again with dead-code stripping and compare the output map files.

If there are only 40 source files maximum, is this optimization really worth your time?

0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号