【问题标题】:How to maintain compatibility between gcc 7 and gcc 9 with -Ofast如何使用 -Ofast 保持 gcc 7 和 gcc 9 之间的兼容性
【发布时间】:2021-07-02 17:31:12
【问题描述】:

我有一个库,我在 Ubuntu 18.04 上使用捆绑在 build-essential 包中的 gcc 版本编译,gcc 7.5.0。

如果我尝试在 Ubuntu 20.04 上编译应用程序并链接到我之前使用默认 gcc 版本 gcc 9.3.0 构建的那个库,那么我会收到一堆错误,例如对 __expf_finite 的未定义引用。请注意,我确实使用 -Ofast 编译了我的原始库,因为我需要利用所有优化。根据this SO question,它表明libc 更新不再支持math-finite.h

因此,作为一种可能的解决方案,我尝试使用 gcc 9.3.0 在 Ubuntu 20.04 上编译我的库,然后查看是否可以使用在 Ubuntu 18.04 上使用 gcc 7.5.0 编译的应用程序链接到该库(基本上与第一种情况)。 但是,当我这样做时,我会收到 std::string 的 ABI 兼容错误:

./trueface_sdk/libtf.a(ocl.cpp.o): In function `cv::ocl::Kernel::set(int, cv::ocl::KernelArg const&)':
ocl.cpp:(.text._ZN2cv3ocl6Kernel3setEiRKNS0_9KernelArgE+0x375): undefined reference to `std::__cxx11::basic_stringstream<char, std::char_traits<char>, std::allocator<char> >::basic_stringstream()'
ocl.cpp:(.text._ZN2cv3ocl6Kernel3setEiRKNS0_9KernelArgE+0x49d): undefined reference to `std::__cxx11::basic_stringstream<char, std::char_traits<char>, std::allocator<char> >::basic_stringstream()'
../trueface_sdk/libtf.a(ocl.cpp.o): In function `oclCleanupCallback.cold':
ocl.cpp:(.text.unlikely.oclCleanupCallback+0x36): undefined reference to `std::__cxx11::basic_stringstream<char, std::char_traits<char>, std::allocator<char> >::basic_stringstream()'
ocl.cpp:(.text.unlikely.oclCleanupCallback+0xcf): undefined reference to `std::__cxx11::basic_stringstream<char, std::char_traits<char>, std::allocator<char> >::basic_stringstream()'
ocl.cpp:(.text.unlikely.oclCleanupCallback+0x184): undefined reference to `std::__cxx11::basic_stringstream<char, std::char_traits<char>, std::allocator<char> >::basic_stringstream()'
../trueface_sdk/libtf.a(ocl.cpp.o):ocl.cpp:(.text._ZN2cv3ocl6Device4ImplC2EPv[_ZN2cv3ocl6Device4ImplC5EPv]+0xb7b): more undefined references to `std::__cxx11::basic_stringstream<char, std::char_traits<char>, std::allocator<char> >::basic_stringstream()' follow
../trueface_sdk/libtf.a(sqlite3.c.o):(.data.rel+0xb0): undefined reference to `fcntl64'

我还得到了对 fcntl64 的未定义引用。

那么解决方法是什么?如何编译兼容多个版本 gcc 的库?

【问题讨论】:

  • 问题不在于 -Ofast 本身,这对于从 4.6 开始的所有 gcc/g++ 版本都很常见。由于库和版本差异,您通常会遇到 soname 问题(库版本要求)。将所有内容粘合在一起的方式会有微小的变化,因为缺少更好的词,并且确保库兼容性可能很棘手,尤其是当您告诉编译器尽可能地优化时,即使这违反了一些标准合规性.将优化返回到-O2,看看是否会出现同样的问题。 (运行时差异可以忽略不计)
  • 罪魁祸首可能是构建环境之间的 glibc 差异。检查每个 glibc 的版本。那里的不匹配可能会导致您描述的问题。

标签: c++ gcc compatibility


【解决方案1】:

基于 cmets,由于使用了 -Ofast 编译器优化标志,它看起来不兼容。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-01-30
    • 1970-01-01
    • 2021-11-26
    • 2018-12-17
    • 1970-01-01
    相关资源
    最近更新 更多