【问题标题】:How to recompile with -fPIC如何使用 -fPIC 重新编译
【发布时间】:2012-11-28 12:42:31
【问题描述】:

我试图在我的 ARM Ubuntu 机器上按照guide 重新安装我的 ffmpeg。不幸的是,当我编译一个使用这个库的程序时,我得到了以下失败:

/usr/bin/ld: /usr/local/lib/libavcodec.a(amrnbdec.o): relocation R_ARM_MOVW_ABS_NC against `a local symbol' can not be used when making a shared object; recompile with -fPIC
/usr/local/lib/libavcodec.a: could not read symbols: Bad value
collect2: ld returned 1 exit status

现在我想用-fPIC 重新编译它,就像编译器建议的那样,但我不知道怎么做。任何帮助表示赞赏。

【问题讨论】:

    标签: c++ gcc compilation ffmpeg fpic


    【解决方案1】:

    在配置步骤之后,您可能有一个 makefile。在这个 makefile 中寻找 CFLAGS (或类似的)。 puf -fPIC 最后并再次运行 make 。换句话说,-fPIC 是一个编译器选项,必须在某处传递给编译器。

    【讨论】:

      【解决方案2】:

      看看this page.

      您可以尝试使用以下方式全局添加标志:export CXXFLAGS="$CXXFLAGS -fPIC"

      【讨论】:

      • 这修复了使用 node-gyp 并产生相同错误的节点包安装程序(用于 node-swipl)。谢谢:)
      • 我在 archive.org 中添加了一个替换死链接
      【解决方案3】:

      简而言之,该错误意味着您无法使用静态库与动态库进行链接。 正确的方法是将libavcodec 编译成.so 而不是.a,这样您尝试构建的另一个.so 库就会很好地链接。

      这样做的最短方法是在./configure 选项中添加--enable-shared。甚至您也可以尝试禁用共享(或静态)库……您可以选择适合自己的!

      【讨论】:

      • 你刚刚用--enable-shared 让我免于严重头痛。谢谢!
      • 谢谢!我还想补充一点,在重新运行 make 时我还必须做make distclean 以摆脱一些已经以静态方式编译的文件。
      【解决方案4】:

      在编译之前,请确保“rules.mk”文件正确包含在 Makefile 中或通过以下方式显式包含它:

      “源规则.mk”

      【讨论】:

        【解决方案5】:

        我在尝试在 Centos 7 上安装 Dashcast 时遇到了同样的问题。修复是在 x264 Makefile 中每个 CFLAGS 的末尾添加 -fPIC。然后我必须为 x264 和 ffmpeg 运行 make distclean 并重建。

        【讨论】:

          【解决方案6】:

          在为 Android x86_64 目标平台(使用 Android NDK clang)构建 FFMPEG 静态库(例如 libavcodec.a)时遇到了这个问题。当与我的库进行静态链接时,尽管所有 FFMPEG C -> 目标文件 (*.o) 都是使用 -fPIC 编译选项编译的,但还是出现了问题:

          x86_64/libavcodec.a(h264_qpel_10bit.o): 
          requires dynamic R_X86_64_PC32 reloc against 'ff_pw_1023' 
          which may overflow at runtime; recompile with -fPIC
          

          该问题仅发生在 libavcodec.a 和 libswscale.a 上。

          这个问题的根源是 FFMPEG 对 x86* 平台进行了汇编优化,例如报告的问题原因在 libavcodec/h264_qpel_10bit.asm -> h264_qpel_10bit.o 中。

          在生成 X86-64 位静态库(例如 libavcodec.a)时,它看起来像汇编器文件(例如 libavcodec/h264_qpel_10bit.asm)使用了一些在与 x86 静态链接时不兼容的 x86(32 位)汇编器命令- 64 位目标库,因为它们不支持所需的重定位类型。

          可能的解决方案

          1. 编译所有 ffmpeg 文件而不进行汇编程序优化(对于 ffmpeg,这是配置选项:--disable-asm)
          2. 生成动态库(例如 libavcodec.so)并将它们动态链接到最终库中

          我选择了 1),它解决了问题。

          参考:https://tecnocode.co.uk/2014/10/01/dynamic-relocs-runtime-overflows-and-fpic/

          【讨论】:

            【解决方案7】:

            除了这里的好答案,特别是 Robert Lujo 的答案。

            我想说的是,就我而言,我一直在故意尝试静态编译 ffmpeg 的一个版本。所有必需的依赖项以及迄今为止所需的其他内容,我已经完成了静态编译。

            当我为 ffmpeg 进程运行 ./configure 时,我没有注意到 --enable-shared 在命令行上。删除它并运行 ./configure 只有这样我才能正确编译(ffmpeg 二进制文件的所有 56 mbs)。如果您的意图是静态编译,请检查一下

            【讨论】:

              【解决方案8】:

              如果您正在构建共享库但需要与 静态 libavcodec 链接,请添加链接器标志:

              -Wl,-Bsymbolic
              

              在 cmake 的情况下:

              set(CMAKE_SHARED_LINKER_FLAGS "-Wl,-Bsymbolic")
              

              【讨论】:

                猜你喜欢
                • 2013-08-25
                • 2016-09-12
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                • 2015-01-18
                相关资源
                最近更新 更多