Re: [RFC PATCH] rust: alloc: pass `old_layout` to `Allocator`

Benno Lossin
2024-09-23T15:21:01Z

On 23.09.24 15:56, Alice Ryhl wrote:
> On Sat, Sep 21, 2024 at 5:33 PM Danilo Krummrich <dakr@kernel.org> wrote:
>> @@ -84,11 +92,18 @@ unsafe fn call(
>> &self,
>> ptr: Option<NonNull<u8>>,
>> layout: Layout,
>> + old_layout: Layout,
>> flags: Flags,
>> ) -> Result<NonNull<[u8]>, AllocError> {
>> let size = aligned_size(layout);
>> let ptr = match ptr {
>> - Some(ptr) => ptr.as_ptr(),
>> + Some(ptr) => {
>> + if old_layout.size() == 0 {
>> + ptr::null()
>> + } else {
>> + ptr.as_ptr()
>> + }
>> + }
>
> This is making Allocator work with zero-sized types, which deviates
> from std. We should not do that without a reason. What is the reason?

The global allocator doesn't support it, but the `Allocator` trait from
std handles zero-sized allocations. For example, this code runs as
expected:

#![feature(allocator_api)]

use std::alloc::{self, Allocator, Layout};

fn main() {
let alloc: &dyn Allocator = &alloc::Global;
let ptr = alloc.allocate(Layout::new::<()>()).unwrap().cast::<u8>();
unsafe { alloc.deallocate(ptr, Layout::new::<()>()) };
}

https://play.rust-lang.org/?version=nightly&mode=debug&edition=2021&gist=0a2d12ee6dabf16f2ebd67cc6faa864e

---
Cheers,
Benno