1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-05-31 07:08:10 +00:00

Kernel: Implement aligned operator new and use it

The compiler will use these to allocate objects that have alignment
requirements greater than that of our normal `operator new` (4/8 byte
aligned).

This means we can now use smart pointers for over-aligned types.

Fixes a FIXME.
This commit is contained in:
Daniel Bertalan 2021-07-15 12:08:35 +02:00 committed by Andreas Kling
parent c176680443
commit dd4ed4d22d
4 changed files with 41 additions and 10 deletions

View file

@ -301,6 +301,16 @@ size_t kmalloc_good_size(size_t size)
return size;
}
[[gnu::malloc, gnu::alloc_size(1), gnu::alloc_align(2)]] static void* kmalloc_aligned_cxx(size_t size, size_t alignment)
{
VERIFY(alignment <= 4096);
void* ptr = kmalloc(size + alignment + sizeof(ptrdiff_t));
size_t max_addr = (size_t)ptr + alignment;
void* aligned_ptr = (void*)(max_addr - (max_addr % alignment));
((ptrdiff_t*)aligned_ptr)[-1] = (ptrdiff_t)((u8*)aligned_ptr - (u8*)ptr);
return aligned_ptr;
}
void* operator new(size_t size)
{
void* ptr = kmalloc(size);
@ -313,6 +323,18 @@ void* operator new(size_t size, const std::nothrow_t&) noexcept
return kmalloc(size);
}
void* operator new(size_t size, std::align_val_t al)
{
void* ptr = kmalloc_aligned_cxx(size, (size_t)al);
VERIFY(ptr);
return ptr;
}
void* operator new(size_t size, std::align_val_t al, const std::nothrow_t&) noexcept
{
return kmalloc_aligned_cxx(size, (size_t)al);
}
void* operator new[](size_t size)
{
void* ptr = kmalloc(size);
@ -336,6 +358,11 @@ void operator delete(void* ptr, size_t size) noexcept
return kfree_sized(ptr, size);
}
void operator delete(void* ptr, size_t, std::align_val_t) noexcept
{
return kfree_aligned(ptr);
}
void operator delete[](void*) noexcept
{
// All deletes in kernel code should have a known size.