Rust libc crate是否会禁止自定义恐慌处理程序的编译?

Does Rust libc crate inhibit the compilation of custom panic handler?

因此,我们目前正在尝试编译一些Rust代码,然后可以将其链接到一些C代码。为此,我们使用Bindgen生成FFI,然后将其用于从Rust调用一些C函数。

但是,我们必须首先在项目的Cargo.toml文件中将板条箱" libc"作为依赖项。我们目前正在处理的项目要求使用箱宽!#[no_std]属性,因为我们不需要Rust的整个stdlib。我们只需要核心。 libc板条箱说,我们可以通过在Cargo.toml文件中放置一些选项来"请求"不将其链接到标准库:

1
2
[dependencies]
libc = { version ="0.2", default-features = false }

这一切都很好,但当我们尝试编译时,会收到以下错误消息。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
Ubuntu:~/nautilus/src/rust/example# cargo build
   Compiling example v0.0.0 (/home/me/nautilus/src/rust/example)
error[E0152]: duplicate lang item found: `panic_impl`.
  --> src/lib.rs:33:1
   |
33 | / pub fn nk_rust_panic(_info: &PanicInfo) -> !
34 | | {
35 | |    // should call nk_panic here...
36 | |    loop { }
37 | | }
   | |_^
   |
   = note: first defined in crate `std`.

error: aborting due to previous error

For more information about this error, try `rustc --explain E0152`.
error: Could not compile `example`.

To learn more, run the command again with --verbose.

E0152以下

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
A lang item was redefined.

Erroneous code example:

```
#![feature(lang_items)]

#[lang ="arc"]
struct Foo; // error: duplicate lang item found: `arc`
```

Lang items are already implemented in the standard library. Unless you are
writing a free-standing application (e.g. a kernel), you do not need to provide
them yourself.

You can build a free-standing crate by adding `#![no_std]` to the crate
attributes:

```
#![no_std]
```

我们的lib.rs文件中已经有#![no_std],但是似乎由于libc通常会链接到stdlib,因此Rust可能会认为如果我们使用libc,就不能拥有自定义的panic处理程序。

当我们从Cargo.toml文件中删除libc,并从lib.rs中删除extern crate lib时,该问题将缓解。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
// no stdlib
#![no_std]

// Give us this feature to override?
#![feature(start)]

#![feature(lang_items)]

// avoid buildins - we want it to use our library
#![no_builtins]

// The following cruft is here to handle Rust->OS dependencies
// currently only one:  Rust needs to know how to panic
use core::panic::PanicInfo;

extern crate libc;
#[panic_handler]
#[no_mangle]
pub fn nk_rust_panic(_info: &PanicInfo) -> !
{
   // should call nk_panic here... (panic handler of OS)
   loop { }
}

货代

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
[package]
name ="example"  # this is for core-kernel
version ="0.0.0"


[lib]
crate-type = ["staticlib"]

[dependencies]
libc = { version ="0.2", default-features = false }

[build-dependencies]
bindgen ="0.42.2"

[profile.dev]
panic ="abort"    # no stack unwind on rust panic

[profile.release]
panic ="abort"    # no stuck unwind on rust panic

因此,总而言之,使用libc作为依赖项是否会使我们无法使用自己的自定义恐慌处理程序?我们可以直接将任何不稳定的编译器标志传递给rustc来消除此问题吗?

编译器是每晚1.32.0
libc版本是libc v0.2.44


您在Cargo中遇到错误。

功能有些微妙。 可以通过任何传递性依赖来启用它们,这是预期的行为。 但是,甚至可以通过传递性构建依赖项来启用它们,这是一个错误。