在 Rust 中静态链接 BFD 会引发错误

问题描述 投票:0回答:1

我是 Rust 中使用 C 的新手,目前正在尝试使用 BFD 构建二进制加载器。 使用bindgen 生成Rust 绑定非常有效。

在我的

build.rs
中我使用过:

println!("cargo:rustc-link-search=native=/usr/lib/x86_64-linux-gnu/");

println!("cargo:rustc-link-lib=static=bfd");

此操作失败,并出现几个

undefined reference to 'filename_cmp'
之类的错误。

但是:动态链接时(

println!("cargo:rustc-link-lib=bfd");
)一切正常。

我错过了什么?

我已确保

libbfd.a
存在于
/usr/lib/x86_64-linux-gnu/
中。

c rust linker bfd
1个回答
0
投票

我想学习如何在 Rust 中使用 C 语言库

那么,你就做出了一个非常不幸的选择。

libbfd
是一个罕见的例外 库的共享版本和静态版本的规则 定义相同的符号(并保留相同的符号未定义)。
libbfd.a
没有 定义
libbfd.so
定义的所有符号,
filename_cmp
是赤字之一。

参见:

$ nm -D /usr/lib/x86_64-linux-gnu/libbfd.so | grep filename_cmp
0000000000109930 T filename_cmp

它就在

libbfd.so
T
= 定义于
text
部分

并且:

$ nm /usr/lib/x86_64-linux-gnu/libbfd.a | grep filename_cmp
                 U filename_cmp
                 U filename_cmp
                 U filename_cmp
                 

libbfd.a
的成员中只有未定义的引用。

libbfd.a
v.
libbfd.so
中缺少的符号定义于
libiberty
libiberty
本身是一个已退役的GNU软件包。 这可以解释为什么它提供给
libbfd
的定义是静态链接的 进入
libbfd.so
- 这是一个系统运行时 - 但维护人员显然还没有 围绕解耦
libbfd.a
。我不知道为什么。在 Ubuntu 中,
libbfd
共享库 与
libbinutils
封装在一起;运行时包
libiberty
不存在,但 开发包
libiberty-dev
可以并安装
libiberty.a

无论如何,这意味着您可以成功地自行动态链接到

libbfd
的程序 将无法自行静态链接到它。您必须安装
libiberty
开发 打包并将
libiberty
附加到链接中。这是相关演示:

$ cat main.c
#include <stdio.h>

extern int filename_cmp (const char *s1, const char *s2);
int main(void)
{
    if (filename_cmp("filename_cmp.c","FilenameCmp.c")) {
        puts("Not equal");
    } else {
        puts("Equal");
    }
    return 0;
}

默认动态联动针对

libbfd

$ gcc -o prog main.c -lbfd
$ ./prog
Not equal

现在静态:

$ gcc -o prog main.c -Wl,-Bstatic -lbfd -Wl,-Bdynamic
/usr/bin/ld: /tmp/ccOy7HDt.o: in function `main':
main.c:(.text+0x1d): undefined reference to `filename_cmp'
collect2: error: ld returned 1 exit status

现在静态地附加了

-liberty

$ gcc -o prog main.c -Wl,-Bstatic -lbfd -liberty -Wl,-Bdynamic
$ ./prog
Not equal
© www.soinside.com 2019 - 2024. All rights reserved.