From ceb0a632cfd6a4eada6bd27bf6a3754e95dcac86 Mon Sep 17 00:00:00 2001 From: Andrew Kelley Date: Sun, 27 Nov 2022 01:07:35 -0700 Subject: std.mem.Allocator: allow shrink to fail closes #13535 --- lib/std/testing/failing_allocator.zig | 50 +++++++++++++++++++++-------------- 1 file changed, 30 insertions(+), 20 deletions(-) (limited to 'lib/std/testing') diff --git a/lib/std/testing/failing_allocator.zig b/lib/std/testing/failing_allocator.zig index 03e345986b..914e405b11 100644 --- a/lib/std/testing/failing_allocator.zig +++ b/lib/std/testing/failing_allocator.zig @@ -47,16 +47,23 @@ pub const FailingAllocator = struct { } pub fn allocator(self: *FailingAllocator) mem.Allocator { - return mem.Allocator.init(self, alloc, resize, free); + return .{ + .ptr = self, + .vtable = &.{ + .alloc = alloc, + .resize = resize, + .free = free, + }, + }; } fn alloc( - self: *FailingAllocator, + ctx: *anyopaque, len: usize, - ptr_align: u29, - len_align: u29, + log2_ptr_align: u8, return_address: usize, - ) error{OutOfMemory}![]u8 { + ) ?[*]u8 { + const self = @ptrCast(*FailingAllocator, @alignCast(@alignOf(FailingAllocator), ctx)); if (self.index == self.fail_index) { if (!self.has_induced_failure) { mem.set(usize, &self.stack_addresses, 0); @@ -67,39 +74,42 @@ pub const FailingAllocator = struct { std.debug.captureStackTrace(return_address, &stack_trace); self.has_induced_failure = true; } - return error.OutOfMemory; + return null; } - const result = try self.internal_allocator.rawAlloc(len, ptr_align, len_align, return_address); - self.allocated_bytes += result.len; + const result = self.internal_allocator.rawAlloc(len, log2_ptr_align, return_address) orelse + return null; + self.allocated_bytes += len; self.allocations += 1; self.index += 1; return result; } fn resize( - self: *FailingAllocator, + ctx: *anyopaque, old_mem: []u8, - old_align: u29, + log2_old_align: u8, new_len: usize, - len_align: u29, ra: usize, - ) ?usize { - const r = self.internal_allocator.rawResize(old_mem, old_align, new_len, len_align, ra) orelse return null; - if (r < old_mem.len) { - self.freed_bytes += old_mem.len - r; + ) bool { + const self = @ptrCast(*FailingAllocator, @alignCast(@alignOf(FailingAllocator), ctx)); + if (!self.internal_allocator.rawResize(old_mem, log2_old_align, new_len, ra)) + return false; + if (new_len < old_mem.len) { + self.freed_bytes += old_mem.len - new_len; } else { - self.allocated_bytes += r - old_mem.len; + self.allocated_bytes += new_len - old_mem.len; } - return r; + return true; } fn free( - self: *FailingAllocator, + ctx: *anyopaque, old_mem: []u8, - old_align: u29, + log2_old_align: u8, ra: usize, ) void { - self.internal_allocator.rawFree(old_mem, old_align, ra); + const self = @ptrCast(*FailingAllocator, @alignCast(@alignOf(FailingAllocator), ctx)); + self.internal_allocator.rawFree(old_mem, log2_old_align, ra); self.deallocations += 1; self.freed_bytes += old_mem.len; } -- cgit v1.2.3