我和一位同事一直在琢磨如何通过FFI将<stdbool.h>
(又称_Bool
)中的bool
返回Rust.
我们有C99代码,我们想用它来除 rust :
bool
myfunc(void) {
...
}
我们用extern C
块告诉Rust大约myfunc
块:
extern "C" {
fn myfunc() -> T;
}
T
应该是什么混凝土类型?
Rust在libc
crate 中没有c_bool
,如果你搜索互联网,你会发现各种GitHub问题和RFC,人们在讨论这一点,但对于什么是正确的和可移植的,并没有达成任何共识:
- https://github.com/rust-lang/rfcs/issues/1982#issuecomment-297534238
- https://github.com/rust-lang/rust/issues/14608
- https://github.com/rust-lang/rfcs/issues/992
- https://github.com/rust-lang/rust/pull/46156
据我所知:
- C99中
bool
的大小尚未定义,除了它必须至少足够大以存储true
(1)和false
(0)之外.换句话说,至少有一点长. - 甚至可能是one bit wide.
- 它的大小可能是ABI defined.
This comment表示,如果C99 bool
作为参数传递到函数中,或作为返回值从函数中传递出go ,and bool
比Cint
小,那么它将被提升到与int
相同的大小.在这种情况下,我们可以判断 rust T
是u32
.
好吧,但如果(出于某种原因)C99 bool
是64位宽呢?u32
还安全吗?也许在这种情况下,我们会截断4个最高有效字节,这很好,因为4个最低有效字节足以表示true
和false
.
Is my reasoning correct? Until Rust gets a libc::c_bool
, what would you use for T
and why is it safe and portable for all possible sizes of a C99 bool
(>=1 bit)?