在构建我的 C++ 可执行文件 (gcc) 时,我可以获得所有链接库的报告吗?(包括静态链接)
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/4925012/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Can I get a report of ALL the libraries linked when building my C++ executable (gcc)? (including statically linked)
提问by DVK
I have a C++ application that I inherited, which consists of:
我有一个我继承的 C++ 应用程序,它包括:
- My main app
- Several app-specific libraries (libapp1, libapp2, etc...)
- Several "third party" libraries (most "third partis are just other teams in the company") linked from both the main app, from the app-specific libappX libraries, and from other 3rd part libraries - e.g. libext1, libext2, etc...
- 我的主要应用
- 几个特定于应用程序的库(libapp1、libapp2 等...)
- 从主应用程序、特定于应用程序的 libappX 库和其他第 3 部分库(例如 libext1、libext2 等)链接的几个“第三方”库(大多数“第三方只是公司中的其他团队”)。 .
In other words, my code looks like this:
换句话说,我的代码如下所示:
// main.C
#include <app1/a1l1.H>
#include <app2/a2l1.H>
#include <ext1/e1l1.H>
// app1/a1l1.H
#include <app1/a1l2.H>
#include <ext2/e2l1.H>
// app2/a2l1.H
#include <ext2/e2l2.H>
// ext1/e1l1.H
#include <ext3/e3l1.H>
// ext3/e3l1.H
#include <ext4/e4l1.H>
QUESTIONs:
问题:
1) How can I tell which libraries have been linked into the final executable? This must include statically linked ones
1) 我如何知道哪些库已链接到最终的可执行文件中?这必须包括静态链接的
In other words, I want an answer of "app1, app2, ext1, ext2, ext3, ext4"
换句话说,我想要“app1、app2、ext1、ext2、ext3、ext4”的答案
Ideally, the answer would be available from the executable itself (I have a debug version of it built in case it makes it more possible). If that's impossible, i'd like to know if there's a simple code analysis tool (iedeally something within gcc itself) to provide that analysis.
理想情况下,可以从可执行文件本身获得答案(我有一个内置的调试版本,以防万一)。如果这是不可能的,我想知道是否有一个简单的代码分析工具(即 gcc 本身内部的东西)来提供该分析。
Please note that the object files for external libraries are already built, so looking at the build logs to see what was linked, I'm worried that "ext4" won't show up in the log since we won't be building "ext3" library that is already pre-built.
请注意,外部库的目标文件已经构建,所以查看构建日志以查看链接的内容,我担心“ext4”不会出现在日志中,因为我们不会构建“ext3” " 已经预先构建的库。
NOTE: running "nmake" with DEPS set to yes to rebuild all the is NOT an option. But i DO have access to the full source code for external libraries.
注意:在 DEPS 设置为 yes 的情况下运行“nmake”以重建所有不是一个选项。但我确实可以访问外部库的完整源代码。
2) A slightly separate and less important question, how can i tell a list of all the include filesused in the entire source tree I'm building. Again, ideally frm already-built executable, which i have a debug version of.
2)一个稍微独立且不太重要的问题,我如何说出我正在构建的整个源代码树中使用的所有包含文件的列表。同样,理想情况下,我有一个调试版本的已构建的可执行文件。
=================
==================
UPDATE: Just to clarify, our libraries are linked statically, so ldd
(List Synamic Dependencies) does not work.
更新:只是为了澄清,我们的库是静态链接的,因此ldd
(List Synamic Dependencies)不起作用。
Also, the answer can be either for Solaris or Linux - doesn't matter.
此外,答案可能适用于 Solaris 或 Linux - 无关紧要。
I tried using nm
but that doesn't list the libraries
我尝试使用,nm
但没有列出库
回答by Daniel Fru?yński
I had similar problem and found solution: add -Wl,--verbose option when linking. It will switch linker to verbose mode:
我遇到了类似的问题并找到了解决方案:链接时添加 -Wl,--verbose 选项。它将链接器切换到详细模式:
gcc -o test main.o -ltest -L. -Wl,--verbose
Here is example output:
这是示例输出:
GNU ld (GNU Binutils) 2.23.52.20130604
Supported emulations:
i386pep
i386pe
using internal linker script:
==================================================
/* Default linker script, for normal executables */
[many lines here]
==================================================
attempt to open /usr/lib/gcc/x86_64-pc-cygwin/4.8.2/../../../../lib/crt0.o succeeded
/usr/lib/gcc/x86_64-pc-cygwin/4.8.2/../../../../lib/crt0.o
attempt to open /usr/lib/gcc/x86_64-pc-cygwin/4.8.2/crtbegin.o succeeded
/usr/lib/gcc/x86_64-pc-cygwin/4.8.2/crtbegin.o
attempt to open main.o succeeded
main.o
attempt to open ./libtest.dll.a failed
attempt to open ./test.dll.a failed
attempt to open ./libtest.a succeeded
(./libtest.a)test.o
[more lines here]
attempt to open /usr/lib/gcc/x86_64-pc-cygwin/4.8.2/crtend.o succeeded
/usr/lib/gcc/x86_64-pc-cygwin/4.8.2/crtend.o
Update:You can also use -Wl,--trace option instead of -Wl,--verbose. It will also give you list of libraries, but is less verbose.
更新:您还可以使用 -Wl,--trace 选项代替 -Wl,--verbose。它还会为您提供库列表,但不那么冗长。
Update 2:-Wl,--trace does not display libraries included indirectly. Example: you link with libA, and libA was linked with libB. If you want to see that libB is needed too, you must use -Wl,--verbose.
更新 2:-Wl,--trace 不显示间接包含的库。示例:您与 libA 链接,而 libA 与 libB 链接。如果你想看到 libB 也是需要的,你必须使用 -Wl,--verbose。
回答by ismail
For direct dependencies;
对于直接依赖;
ldd <app>
Indirect/All dependencies;
间接/所有依赖;
ldd -r <app>
回答by aschepler
As far as I know, not much information about static libraries is preserved when linking (since the linker just sees that library as a collection of *.o objects anyway).
据我所知,链接时没有保留关于静态库的太多信息(因为链接器只是将该库视为 *.o 对象的集合)。
If you find the make command that links the final executable and add a -v
flag, g++
will show you exactly how it calls the ld
command. This should include all necessary static libraries, including libraries used by other libraries, or otherwise the link step would fail. But it might also include extra libraries that aren't actually used.
如果您找到链接最终可执行文件并添加-v
标志的 make 命令,g++
它将准确显示它如何调用该ld
命令。这应该包括所有必要的静态库,包括其他库使用的库,否则链接步骤将失败。但它也可能包括实际未使用的额外库。
Another possibly useful thing is that, at least on Linux, objects and executables usually store names of the source code files from which they were created. (Filename only, no path.) Try
另一个可能有用的事情是,至少在 Linux 上,对象和可执行文件通常存储创建它们的源代码文件的名称。(只有文件名,没有路径。)试试
objdump -t executable | grep '*ABS*'
回答by kohlehydrat
Try to use ldd
+ your filename, this will list the libs.
尝试使用ldd
+ 您的文件名,这将列出库。
回答by s g
I'll answer your second question first. You can simply use the -H
or -M
flag to see all (including system) headers processed in the compilation. gcc -H main.c
should do the trick. Seeing which headers
are included will actually get you on the right track to finding which static libraries were linked in.
我先回答你的第二个问题。您可以简单地使用-H
或-M
标志来查看在编译中处理的所有(包括系统)头文件。gcc -H main.c
应该做的伎俩。查看包含哪些标头实际上会让您走上正确的轨道,以找到链接了哪些静态库。
You could use objdump
on your final object (or readelf
on your final binary) to get the names of all the functions in there. You'd then have to go find the libraries from which the functions were pulled in, but that's a bit cumbersome. You'd definitely have to make a script to minimize the pain.
您可以objdump
在最终对象(或readelf
最终二进制文件)上使用以获取其中所有函数的名称。然后您必须去查找从中拉入函数的库,但这有点麻烦。您肯定必须制作一个脚本来最大程度地减少痛苦。
Someone else mentioned using gcc <stuff> -Wl,-verbose
which simply passes the -verbose
flag to the linker. That's a perfect way to get a list of shared libraries (.so files), but you said yours are static, so that isn't the way to go in this case.
其他人提到 using gcc <stuff> -Wl,-verbose
which 只是将-verbose
标志传递给链接器。这是获取共享库(.so 文件)列表的完美方法,但是您说您的库是静态的,因此在这种情况下不是要走的路。
Good luck!
祝你好运!