【Error】error: unable to load plugin '../afl-llvm-pass.so': '../afl-llvm-pass.so: undefined

本文详细介绍了在Ubuntu18.04上编译afl-clang-fast过程中遇到的问题及解决方案,主要原因是默认的Clang和LLVM版本过高,需更换为3.8版本。提供了解决步骤,包括源码编译和使用预编译二进制文件的方法。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

编译afl-clang-fast时,由于ubuntu18.04上默认的clang和llvm版本是6.0,最低是3.9,编译时会遇到如下错误,解决办法是换3.8即可。ubuntu18.04默认没有3.8的,自己下源码编译或者直接用官网中ubuntu16.04版的llvm3.8 binary也可以。

http://releases.llvm.org/download.html#3.8.0

mkdir -p -m 755 ${DESTDIR}/usr/local/bin ${DESTDIR}/usr/local/lib/afl ${DESTDIR}/usr/local/share/doc/afl ${DESTDIR}/usr/local/share/afl
rm -f ${DESTDIR}/usr/local/bin/afl-plot.sh
install -m 755 afl-gcc afl-fuzz afl-showmap afl-tmin afl-gotcpu afl-analyze afl-plot afl-cmin afl-whatsup ${DESTDIR}/usr/local/bin
rm -f ${DESTDIR}/usr/local/bin/afl-as
if [ -f afl-qemu-trace ]; then install -m 755 afl-qemu-trace ${DESTDIR}/usr/local/bin; fi
if [ -f afl-clang-fast -a -f afl-llvm-pass.so -a -f afl-llvm-rt.o ]; then set -e; install -m 755 afl-clang-fast ${DESTDIR}/usr/local/bin; ln -sf afl-clang-fast ${DESTDIR}/usr/local/bin/afl-clang-fast++; install -m 755 afl-llvm-pass.so afl-llvm-rt.o ${DESTDIR}/usr/local/lib/afl; fi
if [ -f afl-llvm-rt-32.o ]; then set -e; install -m 755 afl-llvm-rt-32.o ${DESTDIR}/usr/local/lib/afl; fi
if [ -f afl-llvm-rt-64.o ]; then set -e; install -m 755 afl-llvm-rt-64.o ${DESTDIR}/usr/local/lib/afl; fi
set -e; for i in afl-g++ afl-clang afl-clang++; do ln -sf afl-gcc ${DESTDIR}/usr/local/bin/$i; done
install -m 755 afl-as ${DESTDIR}/usr/local/lib/afl
ln -sf afl-as ${DESTDIR}/usr/local/lib/afl/as
install -m 644 docs/README docs/ChangeLog docs/*.txt ${DESTDIR}/usr/local/share/doc/afl
cp -r testcases/ ${DESTDIR}/usr/local/share/afl
cp -r dictionaries/ ${DESTDIR}/usr/local/share/afl
Reading package lists... Done
Building dependency tree
Reading state information... Done
llvm-6.0 is already the newest version (1:6.0-1ubuntu2).
llvm-6.0-dev is already the newest version (1:6.0-1ubuntu2).
llvm-6.0-runtime is already the newest version (1:6.0-1ubuntu2).
clang-6.0 is already the newest version (1:6.0-1ubuntu2).
The following packages were automatically installed and are no longer required:
  golang-docker-credential-helpers llvm-runtime python-backports.ssl-match-hostname python-cached-property python-certifi python-docker python-dockerpty
  python-dockerpycreds python-docopt python-funcsigs python-functools32 python-jsonschema python-mock python-openssl python-pbr python-requests python-texttable
  python-urllib3 python-websocket python-yaml
Use 'sudo apt autoremove' to remove them.
0 upgraded, 0 newly installed, 0 to remove and 0 not upgraded.
[*] Checking for working 'llvm-config'...
[*] Checking for working 'clang'...
[*] Checking for '../afl-showmap'...
[+] All set and ready to build.
[*] Testing the CC wrapper and instrumentation output...
unset AFL_USE_ASAN AFL_USE_MSAN AFL_INST_RATIO; AFL_QUIET=1 AFL_PATH=. AFL_CC=clang ../afl-clang-fast -O3 -funroll-loops -Wall -D_FORTIFY_SOURCE=2 -g -Wno-pointer-sign -DAFL_PATH=\"/usr/local/lib/afl\" -DBIN_PATH=\"/usr/local/bin\" -DVERSION=\"2.52b\"  ../test-instr.c -o test-instr
error: unable to load plugin '../afl-llvm-pass.so': '../afl-llvm-pass.so: undefined symbol:
      _ZN4llvm18PassManagerBuilder18addGlobalExtensionENS0_16ExtensionPointTyEPFvRKS0_RNS_6legacy15PassManagerBaseEE'
Makefile:97: recipe for target 'test_build' failed
make: *** [test_build] Error 1

 

<think>好的,我现在遇到了一个编译错误:cc1: error: cannot load plugin ./scripts/gcc-plugins/arm_ssp_per_task_plugin.so,提示undefined symbol: _ZN8opt_pass14set_pass_paramEjb。我需要弄清楚这个错误的原因,然后找到解决办法。 首先,我要理解错误信息。这个错误是在尝试加载一个GCC插件时出现的,系统说找不到符号_ZN8opt_pass14set_pass_paramEjb。这个符号看起来像是C++经过名称修饰后的名称,可能对应的是opt_pass类的成员函数set_pass_param,参数可能是unsigned int和bool。可能这个函数在GCC的某个库中,但插件在链接时没有找到它。 接下来,我应该考虑可能的原因。首先想到的是GCC版本不兼容的问题。如果插件是为特定版本的GCC编译的,而当前使用的GCC版本不同,可能会导致符号找不到。例如,如果插件是用较旧版本的GCC编译的,而当前GCC版本中opt_pass类的set_pass_param函数可能有不同的签名或已经被移除,就会导致这个问题。 另一个可能的原因是编译插件时没有正确链接到GCC的内部库。GCC插件通常需要链接到libgcc或其它内部库,如果在编译插件时没有指定正确的链接选项,就会导致符号未定义。这时候可能需要检查插件的编译过程,确保所有依赖的库都被正确链接。 还有一种情况是GCC安装不完整或者损坏。如果GCC的相关文件缺失或被错误修改,可能导致某些符号无法找到。这时候需要验证GCC的安装是否完整,或者尝试重新安装GCC。 此外,检查插件的源代码是否有问题也是必要的。可能在插件的代码中错误地调用了set_pass_param函数,或者该函数在使用的GCC版本中不存在。需要查看GCC对应版本的文档,确认该函数是否存在,以及其参数是否正确。 解决步骤方面,首先应该确认GCC的版本是否与插件兼容。可以通过运行gcc --version查看当前版本,然后查看插件文档或构建说明中指定的GCC版本。如果不一致,尝试安装匹配的GCC版本。 如果版本匹配,下一步是检查插件的编译过程。可能需要重新编译插件,并确保在编译时包含了正确的头文件和链接路径。例如,使用gcc -shared -I/usr/lib/gcc/x86_64-linux-gnu/9/plugin/include -fPIC -o arm_ssp_per_task_plugin.so arm_ssp_per_task_plugin.c这样的命令,其中包含正确的插件头文件路径。 另外,使用nm命令查看GCC的库文件(如libgcc.a或libbackend.a)是否存在所需的符号,例如nm /path/to/libgcc.a | grep _ZN8opt_pass14set_pass_paramEjb。如果符号不存在,可能需要升级或重新安装GCC。 如果问题仍然存在,可能需要联系插件的维护者,确认插件是否支持当前GCC版本,或者是否有补丁可用。 总结起来,这个错误通常是由于版本不匹配或编译配置不正确导致的,需要逐一排查这些可能性,并采取相应的解决措施。</think>### 逐步解释与解决方案 #### **错误原因分析** 该错误的核心是 **动态链接库符号未定义**,具体原因可能涉及以下几个方面: --- #### **1. GCC版本不兼容** - **根本原因**:`arm_ssp_per_task_plugin.so` 插件编译时使用的 GCC 版本与当前系统中运行的 GCC 版本不一致。 - **详细说明**: - GCC 插件高度依赖编译器内部数据结构(如 `opt_pass` 类)。不同版本的 GCC 可能修改了这些结构的成员函数或签名。 - 符号 `_ZN8opt_pass14set_pass_paramEjb` 是 `opt_pass::set_pass_param(unsigned int, bool)` 的名称修饰(Name Mangling)结果。如果当前 GCC 版本中该函数已被移除或参数类型变化,会导致符号找不到。 --- #### **2. 插件编译配置错误** - **可能问题**:编译插件时未正确链接 GCC 内部库(如 `libgcc` 或 `libbackend`)。 - **验证方法**: ```bash # 检查插件依赖的符号是否存在于 GCC 库中 nm /usr/lib/gcc/x86_64-linux-gnu/<gcc-version>/plugin/libgcc.a | grep _ZN8opt_pass14set_pass_paramEjb ``` 若输出为空,则表明当前 GCC 版本不包含该符号。 --- #### **3. GCC 安装不完整** - **可能性**:GCC 的插件支持组件未正确安装或损坏。 - **解决方案**: ```bash # 重新安装 GCC(以 Ubuntu 为例) sudo apt-get install --reinstall gcc-<version> g++-<version> ``` --- ### **解决步骤** #### **步骤 1:确认 GCC 版本** ```bash # 查看当前 GCC 版本 gcc --version # 查看插件编译时的目标 GCC 版本(需查阅插件文档或构建脚本) ``` - **若版本不一致**:安装匹配的 GCC 版本并重新编译插件。 - **若版本一致**:进入下一步。 --- #### **步骤 2:重新编译插件** 确保编译时包含正确的头文件和链接路径: ```bash # 示例编译命令(路径需替换为实际 GCC 插件头文件路径) gcc -shared -I/usr/lib/gcc/x86_64-linux-gnu/<gcc-version>/plugin/include \ -fPIC -o arm_ssp_per_task_plugin.so arm_ssp_per_task_plugin.c ``` --- #### **步骤 3:验证符号存在性** 检查当前 GCC 的库文件是否包含目标符号: ```bash # 查找 libgcc 或 libbackend 的路径(以实际路径为准) find /usr/lib/gcc -name "libgcc.a" # 检查符号是否存在 nm /path/to/libgcc.a | grep _ZN8opt_pass14set_pass_paramEjb ``` - **若符号不存在**:升级 GCC 或回退到旧版本。 --- #### **步骤 4:使用兼容的 GCC 版本** 通过 `update-alternatives` 切换默认 GCC 版本(以 Ubuntu 为例): ```bash sudo update-alternatives --config gcc ``` --- ### **附加建议** - **联系插件维护者**:若问题仍存在,可能是插件代码与新版 GCC 不兼容,需提交 Issue 或寻找补丁。 - **降级 GCC**:临时解决方案可安装旧版 GCC(需权衡安全性)。 --- ### **总结** 该错误的根本原因是 **GCC 版本与插件二进制不兼容**。解决方法围绕版本对齐、重新编译插件或修复 GCC 安装展开。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值