【问题标题】:C++ Pre-compiled Headers: Two generated .gch are never identical for the same source fileC++ 预编译头文件:对于同一个源文件,两个生成的 .gch 永远不会相同
【发布时间】:2016-07-01 12:14:05
【问题描述】:

我试图理解如果源文件没有改变,为什么系统头文件的预编译头对象在两个编译器调用之间永远不会相同。

我可以通过这个非常简单的测试来展示这种行为:

$ cat pch.hpp
#include <string.h>

$ g++ pch.hpp -o pch1.hpp.gch && g++ pch.hpp -o pch2.hpp.gch
$ cksum pch1.hpp.gch pch2.hpp.gch
285552444 3408816 pch1.hpp.gch
612212458 3408816 pch2.hpp.gch

我可以在 Windows 7(带有 MSYS2 的 GCC 5.3.0)、Mac OS X(来自 Homebrew 的 GCC 6.1.0)和 Arch Linux(GCC 6.1.1)中复制它。

查看依赖关系,我找不到任何predefined macro 可以更改两次连续编译之间的输出。

比较生成的文件,一些字节序列是乱序的(在图像中,字符串“pch.hpp”出现在左侧文件的后面)并且一些单个字节是不同的,即使文件大小是一样的。

那么 gcc 真的不能保证每次都生成相同的 PCH 还是我遗漏了什么?

【问题讨论】:

  • 也许有时间戳。尝试尽可能快地生成文件,看看有多少字节发生了变化。见gcc.gnu.org/ml/gcc-patches/2005-02/msg00922.html
  • 我很好奇您要解决什么问题。
  • 感谢@John的链接,但提到的时间戳应该与编译器可执行文件的修改时间有关,两次调用之间不会改变。而且我在c-pch.c的当前版本中找不到这个时间戳。
  • @LightnessRacesinOrbit,我正在尝试在已经使用 PCH 但我不能使用其“PCH sloppiness”设置的项目中使用 ccache,因为有一些重要的定义可以更改。所以我不能将 PCH 存储在缓存中,它需要始终重新编译并生成具有相同哈希的对象以获得缓存命中。但是这些对象总是不同的,所以我只会错过。
  • 有趣。好吧,我认为您应该询问 GCC 邮件列表。

标签: c++ gcc


【解决方案1】:

差异是由 ASLR 引起的。禁用它会导致可重现的 gch:

# setarch $(uname -m) -R /usr/bin/c++ -x c++-header -include test.hxx -o test.hxx.gch -c test.hxx.cxx && md5sum test .hxx.gch 54486c6ffc08db87d4b58792dcb46091 test.hxx.gch # setarch $(uname -m) -R /usr/bin/c++ -x c++-header -include test.hxx -o test.hxx.gch -c test.hxx.cxx && md5sum test.hxx.gch 54486c6ffc08db87d4b58792dcb46091 test.hxx.gch

但是,ASLR 通常是一件好事,禁用它并不是真正的解决方案。这也在讨论here

【讨论】:

    猜你喜欢
    • 2013-06-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-04-13
    • 1970-01-01
    相关资源
    最近更新 更多