Rust 内存布局、对齐和释放

Rust 内存布局、对齐和释放,rust,Rust,最近,我想分配一个与128字节边界对齐的u64s向量,以便使用AVX512F函数。将任何Vec复制到对齐的Vec的函数的第一次传递: fn复制到对齐(inp:Vec)->Vec{ //注意:释放返回的vec时,对齐/布局信息 //将丢失。将使用对齐释放内部内存 //一个u64。 let aligned_layout=layout::from_size_align(inp.len()*size_of::(),128) .unwrap(); 让new_vec=不安全{ 让new_vec_mem=al

最近,我想分配一个与128字节边界对齐的
u64
s向量,以便使用AVX512F函数。将任何
Vec
复制到对齐的
Vec
的函数的第一次传递:

fn复制到对齐(inp:Vec)->Vec{
//注意:释放返回的vec时,对齐/布局信息
//将丢失。将使用对齐释放内部内存
//一个u64。
let aligned_layout=layout::from_size_align(inp.len()*size_of::(),128)
.unwrap();
让new_vec=不安全{
让new_vec_mem=alloc_调零(对齐布局)为*mut u64;
复制不重叠(inp.as_ptr(),new_vec_mem,inp.len());
Vec::来自原始零件(新的Vec\u mem、inp.len()、inp.len())
};
返回新的_vec;
}
我现在意识到这段代码是错误的:虽然新向量是用对齐的内存和适当的内容创建的,但是当新向量被删除时。的文档也提到了这个陷阱

1)当我释放分配时,为什么分配的对齐很重要?例如,在C中,我可以通过调用
free
释放任何指针——分配的对齐是无关的。Rust的分配器有什么特别之处,它需要知道对齐方式


2)分配此对齐向量的正确方法是什么?我应该使用装箱切片吗?用一个定制的
Drop
实现来编写我自己的结构,以获得正确的对齐方式?建议创建一个结构并指定对齐方式,然后对这些结构进行
Vec
(使取消分配使用正确的布局)。但是,即使使用了
repr(C)
,这也不能确保我所有的
u64
都是很好的,并且紧密地排列在一起,不是吗?我想象任意填充可以添加到结构中。

在Rust Discord用户
svr
seri
的帮助下,我能够解决这个问题

基本上,Rust API的分配器假定为分配和解除分配提供了
布局。这意味着内存分配器在解除分配时可以知道请求的分配对齐方式。您可以找到API

这个API可以用来做一些事情,比如将内存分配给不同池中的不同对齐方式。事实证明,当前的默认实现是错误的,但将来可能会改变

目前,分配对齐到N字节边界的
u64
s向量的最佳(唯一?)方法是创建一个结构,将一个对齐值的u64作为字段,然后使用对齐提示,如下所述: