我有一个Rust库,它通过FFI将一个u8
数组返回给C调用者。该库还在客户端完成后处理数组。该库没有状态,因此客户端需要拥有该数组,直到它被传递回库中以供释放。
使用box::from_raw
和boxed::into_raw
会很好,但我无法解决如何将数组转换为返回类型的问题。
答案 0 :(得分:6)
Vec<T>
由3个值描述:
.as_mut_ptr()
.len()
.capacity()
就C数组而言,容量是分配的内存大小,而长度是数组中实际包含的元素数。两者都计算在T
的数量。您通常需要将这3个值提供给C代码。
如果你希望它们相等,你可以在向量上使用.shrink_to_fit()
来尽可能地减小其容量,具体取决于分配器。
如果您将Vec<T>
的所有权归还给您的C代码,一旦您检索到之前描述的3个值,请不要忘记在其上调用std::mem::forget(v)
,以避免其拥有析构函数在函数结束时运行。
之后,您可以使用from_raw_parts(..)
从这3个值中创建Vec
,如下所示:
let v = unsafe { Vec::<T>::from_raw_parts(ptr, length, capacity) };
当它的析构函数运行时,内存将被正确释放。注意,3个值需要正确才能正确释放内存。它对Vec<u8>
不是很重要,但Vec
的析构函数将根据其length
运行其包含的所有数据的析构函数。