feature. See also
. The project being documented here (as the example) is the Zig library itself.
SafeAllocator.resize
fn resize(ctx: *anyopaque, memory: []u8, alignment: Alignment, new_len: usize, ra: usize) bool
File
Code
fn resize(ctx: *anyopaque, memory: []u8, alignment: Alignment, new_len: usize, ra: usize) bool {
assert(new_len != 0);
const s: *SafeAllocator = @ptrCast(@alignCast(ctx));
const f: *AllocFooter = .of(memory);
f.startModify(.resized, s, .{ .memory = memory, .alignment = alignment });
// done after the above so that it is still checked that valid memory is passed and there
// is no double modify.
const from_large_alloc = s.isLarge(memory.len, alignment);
const to_large_alloc = s.isLargeOrOom(new_len, alignment) catch {
f.modify.setNone();
return false;
};
if (from_large_alloc != to_large_alloc) {
@branchHint(.unlikely);
f.modify.setNone();
return false;
}
if (from_large_alloc) {
@branchHint(.unlikely);
const entry = f.extended().container.large_entry;
const new_alloc_len = AllocFooter.allocLenLarge(s, new_len);
if (!s.backing.rawResize(
memory.ptr[0..AllocFooter.allocLenLarge(s, memory.len)],
AllocFooter.allocAlign(alignment),
new_alloc_len,
ra,
)) {
f.modify.setNone();
return false;
}
const new_footer = AllocFooter.populate(
@alignCast(memory.ptr[0..new_alloc_len]),
new_len,
alignment,
ra,
true,
false,
.{ .large_entry = entry },
s,
);
assert(entry.kind == .large_alloc);
entry.* = .fromLargeAlloc(new_footer);
return true;
}
if (new_len < memory.len) {
// if this footer is the final one, the fill value would need decreased which would allow
// memory to be reused.
f.modify.setNone();
return false;
}
if (s.growingResizeBucket(f, memory, alignment, new_len, ra)) {
@branchHint(.likely);
return true;
} else {
f.modify.setNone();
return false;
}
}