diff options
Diffstat (limited to 'lib/std/testing.zig')
| -rw-r--r-- | lib/std/testing.zig | 26 |
1 files changed, 20 insertions, 6 deletions
diff --git a/lib/std/testing.zig b/lib/std/testing.zig index 4e43413d28..8fa5fb68f8 100644 --- a/lib/std/testing.zig +++ b/lib/std/testing.zig @@ -534,18 +534,27 @@ test { /// /// Any relevant state shared between runs of `test_fn` *must* be reset within `test_fn`. /// -/// Expects that the `test_fn` has a deterministic number of memory allocations -/// (an error will be returned if non-deterministic allocations are detected). -/// /// The strategy employed is to: /// - Run the test function once to get the total number of allocations. /// - Then, iterate and run the function X more times, incrementing /// the failing index each iteration (where X is the total number of /// allocations determined previously) /// +/// Expects that `test_fn` has a deterministic number of memory allocations: +/// - If an allocation was made to fail during a run of `test_fn`, but `test_fn` +/// didn't return `error.OutOfMemory`, then `error.SwallowedOutOfMemoryError` +/// is returned from `checkAllAllocationFailures`. You may want to ignore this +/// depending on whether or not the code you're testing includes some strategies +/// for recovering from `error.OutOfMemory`. +/// - If a run of `test_fn` with an expected allocation failure executes without +/// an allocation failure being induced, then `error.NondeterministicMemoryUsage` +/// is returned. This error means that there are allocation points that won't be +/// tested by the strategy this function employs (that is, there are sometimes more +/// points of allocation than the initial run of `test_fn` detects). +/// /// --- /// -/// Here's an example of using a simple test case that will cause a leak when the +/// Here's an example using a simple test case that will cause a leak when the /// allocation of `bar` fails (but will pass normally): /// /// ```zig @@ -645,12 +654,16 @@ pub fn checkAllAllocationFailures(backing_allocator: std.mem.Allocator, comptime args.@"0" = failing_allocator_inst.allocator(); if (@call(.{}, test_fn, args)) |_| { - return error.NondeterministicMemoryUsage; + if (failing_allocator_inst.has_induced_failure) { + return error.SwallowedOutOfMemoryError; + } else { + return error.NondeterministicMemoryUsage; + } } else |err| switch (err) { error.OutOfMemory => { if (failing_allocator_inst.allocated_bytes != failing_allocator_inst.freed_bytes) { print( - "\nfail_index: {d}/{d}\nallocated bytes: {d}\nfreed bytes: {d}\nallocations: {d}\ndeallocations: {d}\n", + "\nfail_index: {d}/{d}\nallocated bytes: {d}\nfreed bytes: {d}\nallocations: {d}\ndeallocations: {d}\nallocation that was made to fail: {s}", .{ fail_index, needed_alloc_count, @@ -658,6 +671,7 @@ pub fn checkAllAllocationFailures(backing_allocator: std.mem.Allocator, comptime failing_allocator_inst.freed_bytes, failing_allocator_inst.allocations, failing_allocator_inst.deallocations, + failing_allocator_inst.getStackTrace(), }, ); return error.MemoryLeakDetected; |
