内部可变结构的原始指针类型

Raw pointer type for interior mutable struct

我正在为 Erlang NIF API 做一些 Rust FFI 工作,我有这些:

ErlNifEnv *enif_alloc_env();
void enif_free_env(ErlNifEnv* env);

这个 ErlNifEnv 指针被传递给各种其他函数,但用户永远不会取消引用该指针。此外,此指针不是线程安全的(在多个线程中使用需要互斥锁)。这种类型的原始 Rust 表示是..

struct ErlNifEnv;
*mut ErlNifEnv;

但是,我认为我可以将这种类型视为具有“内部可变性”,这会导致……

struct ErlNifEnv;
*const ErlNifEnv;

我是否应该将此指针视为常量,即使底层 C 代码将其视为非常量?

我个人认为你应该像对待 Rust 本身的引用一样对待它们。当一个函数需要 &mut 引用时,很可能它实际上会改变值,而如果它需要 &,那么很自然地期望值不会改变(当然,忽略内部可变性)。

C 在继承可变性和内部可变性之间没有区别,因此您可以仅根据 C 函数如何处理此值来选择使用 *mut*const 的内容。事实上,在正确编写的 C API 中,这种区别将以 const 限定符的形式出现。因此,如果有任何函数想要改变值,请使用 *mut。如果没有这样的函数(例如,这是一个只创建一次的不可变结构),则使用 *const。当然,这适用于您要存储在包装器中的类型 - 在 FFI 函数签名中,您应该始终镜像 C API 签名。