-
Notifications
You must be signed in to change notification settings - Fork 13
Open
Description
Hi, this isn't a issue per say, but I was wokring on my own jolt zig interface and come up with this custom allocator that doesn't require a hash map lookup.
It works by decorating each allocation with a header that contains aligment, size and other metadata so it can be freed and reallocated using the zig allocator interface
It's not very well tested
pub const CustomAllocator = struct {
pub var child: std.mem.Allocator = undefined;
pub fn allocate(size: usize) callconv(.c) ?*anyopaque {
return alignedAllocate(size, default_align);
}
pub fn reallocate(ptr: ?*anyopaque, size: usize, new_size: usize) callconv(.c) ?*anyopaque {
var p: [*]u8 = @ptrCast(ptr orelse return allocate(new_size));
var h: *Header = @ptrCast(@alignCast(p - @sizeOf(Header)));
const offset = std.mem.alignForward(usize, @sizeOf(Header), h.ptr_align);
assert(h.offset == offset); // alignment didn't change
assert(h.bin_size == offset + size); // input size is correct
const bin_size = h.offset + new_size;
var slice = @as([*]align(@alignOf(usize)) u8, @alignCast(p - h.offset))[0..h.bin_size];
slice = child.realloc(slice, bin_size) catch return null;
p = slice.ptr + h.offset;
h = @ptrCast(@alignCast(p - @sizeOf(Header)));
h.bin_size = bin_size; // resize
return slice.ptr;
}
pub const free = alignedFree;
pub fn alignedAllocate(size: usize, alignment: usize) callconv(.c) ?*anyopaque {
const offset = std.mem.alignForward(usize, @sizeOf(Header), alignment);
const bin_size = offset + size;
const slice = child.alignedAlloc(u8, .of(usize), bin_size) catch return null;
const h: *Header = @ptrCast(@alignCast(slice.ptr + offset - @sizeOf(Header)));
h.bin_size = bin_size;
h.ptr_align = @intCast(alignment);
h.offset = @intCast(offset);
return slice.ptr + offset;
}
pub fn alignedFree(ptr: ?*anyopaque) callconv(.c) void {
const p: [*]u8 = @ptrCast(ptr orelse return);
const h: *Header = @ptrCast(@alignCast(p - @sizeOf(Header)));
child.rawFree((p - h.offset)[0..h.bin_size], .of(usize), @returnAddress());
}
pub const default_align = if (@sizeOf(usize) == 8) 16 else 8;
pub const Header = struct { bin_size: usize, ptr_align: u32, offset: u32 };
};Metadata
Metadata
Assignees
Labels
No labels