Clang链接时优化在Fedora 18上无法正常工作

Sno*_*ane 16 linker fedora clang clang++ lto

我是铿锵的新手,所以我可能会做些傻事.但我花了几个小时寻找解决方案,包括在这里搜索,我没有找到问题解决-flto与发行版提供的软件包.这个描述的细节是特定于Fedora 18的,但我在Ubuntu 13.04上遇到了类似的问题,所以这个问题并不是特定于Fedora.这是我或铿锵.

问题:我正在尝试编译一个简单的hello-world程序,clang++ -flto以获得链接时优化的好处.没有-flto它工作正常.使用-flto无法链接.调用clang -flto -o hello hello.o -v以查看完整的链接器命令行,我得到:

$ clang++ -flto -o hello hello.o -v
clang version 3.2 (tags/RELEASE_32/final)
Target: x86_64-redhat-linux-gnu
Thread model: posix
 "/usr/bin/ld" --eh-frame-hdr -m elf_x86_64 -dynamic-linker /lib64/ld-linux-x86-64.so.2 -o hello /usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/crt1.o /usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/crti.o /usr/lib/gcc/x86_64-redhat-linux/4.7.2/crtbegin.o -L/usr/lib/gcc/x86_64-redhat-linux/4.7.2 -L/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64 -L/lib/../lib64 -L/usr/lib/../lib64 -L/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../.. -L/lib -L/usr/lib -plugin /usr/bin/../lib/LLVMgold.so hello.o -lstdc++ -lm -lgcc_s -lgcc -lc -lgcc_s -lgcc /usr/lib/gcc/x86_64-redhat-linux/4.7.2/crtend.o /usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/crtn.o
/usr/bin/ld: /usr/bin/../lib/LLVMgold.so: error loading plugin
/usr/bin/ld: /usr/bin/../lib/LLVMgold.so: error in plugin cleanup (ignored)
clang: error: linker command failed with exit code 1 (use -v to see invocation)
Run Code Online (Sandbox Code Playgroud)

似乎有两个问题:

  1. clang ++调用链接器/usr/bin/ld,而不是黄金链接器.Fedora18安装黄金作为/usr/bin/ld.gold.我试图从创建一个符号链接/usr/local/bin/ld/usr/bin/ld.gold,证实which ld/usr/local/bin/ld,但铛++不使用它.似乎是/ usr/bin/ld硬连线.

  2. clang ++调用了链接器-plugin /usr/bin/../lib/LLVMgold.so.这是错误的,因为Fedora的分配将它放在了/usr/lib64/llvm/LLVMgold.so.

我尝试通过以下调整手动调用上面的链接器行:

  • 替换-plugin /usr/bin/../lib/LLVMgold.so-plugin /usr/lib64/llvm/LLVMgold.so.这会产生错误消息hello.o: file not recognized: File format not recognized.所以非黄金链接器似乎知道插件,但不会采用包含LLVM bitcode的.o.

  • 替换/usr/bin/ld/usr/bin/ld.gold.这工作,生成一个按预期运行的可执行文件.

  • 以上两者都--plugin代替了-plugin.这种变化没有任何区别.

那么对于那些喜欢坚持使用系统提供的软件包来使用clang -flto的人来说,最好的方法是什么?我希望有一个配置文件,或未记录的选项或环境变量,让我覆盖这些.或者更好的是,我错过了一个包并且"yum install ..."将修复它.

我宁愿不直接调用链接器,因为我的makefile需要知道它们应该不知道的系统对象和库(例如crt1.o,crtbegin.o,crtend.o).我也可以自己构建clang,但是我在配置脚本中没有看到任何东西让我配置链接器和插件的路径.

我正在运行Fedora 18.计算机上唯一的非发行版软件包是谷歌浏览器和VMware Tools(它是VMWare Fusion中的一个访客).相关Fedora软件包的版本(截至今天,2013年4月29日,整个计算机都是"yum updated"):

$ yum list --noplugins installed binutils* clang* llvm* gcc*
Installed Packages
binutils.x86_64                      2.23.51.0.1-6.fc18                 @updates
binutils-devel.x86_64                2.23.51.0.1-6.fc18                 @updates
clang.x86_64                         3.2-2.fc18                         @updates
clang-devel.x86_64                   3.2-2.fc18                         @updates
clang-doc.noarch                     3.2-2.fc18                         @updates
gcc.x86_64                           4.7.2-8.fc18                       @fedora 
gcc-c++.x86_64                       4.7.2-8.fc18                       @fedora 
llvm.x86_64                          3.2-2.fc18                         @updates
llvm-libs.x86_64                     3.2-2.fc18                         @updates
Run Code Online (Sandbox Code Playgroud)

aby*_*s.7 8

alternativesFedora中有一个实用程序- 它允许在系统级别上用另一个链接器替换一个链接器:

$ sudo alternatives --display ld
ld - status is auto.
link currently points to /usr/bin/ld.bfd
/usr/bin/ld.bfd - priority 50
/usr/bin/ld.gold - priority 30
Current `best' version is /usr/bin/ld.bfd.
$ sudo alternatives --set ld /usr/bin/ld.gold
Run Code Online (Sandbox Code Playgroud)

关于LLVMgold.so位置,您只能报告Fedora Bugzilla中的错误,因为该路径内置于clang源:

lib/Driver/Tools.cpp:std :: string Plugin = ToolChain.getDriver().Dir +"/../lib/LLVMgold.so";

Fedora的人可以在Clang的源包中应用补丁,或者为LLVMgold.so创建一个符号链接.即使在Fedora 20中也没有变化.

  • 只是为了节省一些时间,正如你所看到的,它正在查看`lib`,而不是`lib64`.对我有用的符号链接是`sudo ln -s /usr/lib64/llvm/LLVMgold.so/usr/lib/LLVMgold.so`. (5认同)