便利库中的符号不​​能以可执行文件导出 [英] Symbols from convenience library not getting exported in executable

查看:144
本文介绍了便利库中的符号不​​能以可执行文件导出的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个程序, myprogram ,它与一个静态便利库链接,称之为 libconvenience.a ,它包含一个函数, func()。函数 func()不会在 myprogram 中的任何位置调用。它需要能够从插件库中调用 plugin.so



符号 func()不会在 myprogram 中动态导出。如果我运行

  nm myprogram | grep func 

我什么也没得到。但是,它并不是从 libconvenience.a 中丢失的:


nm libconvenience / libconvenience.a | grep func

00000000 T func


我使用automake,但如果我在命令行上手动执行最后一个链接步骤,它不起作用:

  gcc -Wl, - export-dynamic -o myprogram * .o libconvenience / libconvenience.a`pkg-config --libs somelibraries` 



<但是,如果我像这样链接程序,跳过使用便利库并链接直接进入 libconvenience.a 的对象文件, func()显示在 myprogram 的符号中:

  gcc -Wl, -  export-dynamic -o myprogram * .o libconvenience / *。o`pkg-config --libs somelibraries` 

如果我在中的某处添加了对 func() myprogram ,然后 func()也出现在 myprogram 的符号中。但我认为 - export-dynamic 应该导出所有符号,无论它们是否在程序中使用!



我在Fedora 14上使用automake 1.11.1和gcc 4.5.1。我也使用Libtool 2.2.10来构建 plugin.so (但不是)



我没有忘记把 -Wl, - export-dynamic 放入 myprogram_LDFLAGS ,我也没有忘记将包含 func()的源放在 libconvenience_a_SOURCES中 code>(有些谷歌搜索表明,这些是这个问题的常见原因。)

有人可以帮我理解这里发生了什么吗?

解决方案

我设法解决了这个问题。这是John Calcote出色的Autotools书籍的说明,它指出了我的正确方向:
$ b


Linkers在二进制产品中添加了指定的每个对象文件明确地在命令行上,但它们只从档案中提取那些实际被链接的代码中引用的对象文件。


抵消这种行为,可以使用 - whole-archive 标志来进行libtool。但是,这会导致所有系统库中的所有符号都被拉入,导致大量双符号定义错误。因此, - whole-archive 需要在链接器命令行上的 libconvenience.a 之前,它需要后面紧跟着 - no-whole-archive ,以便其他库不以那种方式处理。这有点困难,因为automake和libtool并不能真正保证你的标志在命令行上保持相同的顺序,但是 Makefile.am 中的这一行做到了这一点:

  myprogram_LDFLAGS = -Wl, -  export-dynamic \ 
-Wl, - whole-archive,libconvenience /libconvenience.a,-no-whole-archive


I have a program, myprogram, which is linked with a static convenience library, call it libconvenience.a, which contains a function, func(). The function func() isn't called anywhere in myprogram; it needs to be able to be called from a plugin library, plugin.so.

The symbol func() is not getting exported dynamically in myprogram. If I run

nm myprogram | grep func

I get nothing. However, it isn't missing from libconvenience.a:

nm libconvenience/libconvenience.a | grep func
00000000 T func

I am using automake, but if I do the last linking step by hand on the command line instead, it doesn't work either:

gcc -Wl,--export-dynamic -o myprogram *.o libconvenience/libconvenience.a `pkg-config --libs somelibraries`

However, if I link the program like this, skipping the use of a convenience library and linking the object files that would have gone into libconvenience.a directly, func() shows up in myprogram's symbols as it should:

gcc -Wl,--export-dynamic -o myprogram *.o libconvenience/*.o `pkg-config --libs somelibraries`

If I add a dummy call to func() somewhere in myprogram, then func() also shows up in myprogram's symbols. But I thought that --export-dynamic was supposed to export all symbols regardless of whether they were used in the program or not!

I am using automake 1.11.1 and gcc 4.5.1 on Fedora 14. I am also using Libtool 2.2.10 to build plugin.so (but not the convenience library.)

I didn't forget to put -Wl,--export-dynamic in myprogram_LDFLAGS, nor did I forget to put the source that contains func() in libconvenience_a_SOURCES (some Googling suggests that these are common causes of this problem.)

Can somebody help me understand what is going on here?

解决方案

I managed to solve it. It was this note from John Calcote's excellent Autotools book that pointed me in the right direction:

Linkers add to the binary product every object file specified explicitly on the command line, but they only extract from archives those object files that are actually referenced in the code being linked.

To counteract this behavior, one can use the --whole-archive flag to libtool. However, this causes all the symbols from all the system libraries to be pulled in also, causing lots of double symbol definition errors. So --whole-archive needs to be right before libconvenience.a on the linker command line, and it needs to be followed by --no-whole-archive so that the other libraries aren't treated that way. This is a bit difficult since automake and libtool don't really guarantee keeping your flags in the same order on the command line, but this line in Makefile.am did the trick:

myprogram_LDFLAGS = -Wl,--export-dynamic \
    -Wl,--whole-archive,libconvenience/libconvenience.a,--no-whole-archive

这篇关于便利库中的符号不​​能以可执行文件导出的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆