authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2024-07-22 16:45:19-07:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2024-07-25 18:52:20-07:00
log5058beb1793aafaaf63cb5b9ef4c751fba08a62c
treee067ba72bc3a82158515113258be01a6258ee68a
parent1c35e73b614398529782f8c027366c6d8d51ac4b

implement std.testing.fuzzInput

for the -fno-fuzz case. The other case will take more work in libfuzzer.

2 files changed, 31 insertions(+), 1 deletions(-)

lib/std/io/test.zig+1-1
......@@ -16,7 +16,7 @@ test "write a file, read it, then delete it" {
1616 defer tmp.cleanup();
1717
1818 var data: [1024]u8 = undefined;
19 var prng = DefaultPrng.init(1234);
19 var prng = DefaultPrng.init(std.testing.random_seed);
2020 const random = prng.random();
2121 random.bytes(data[0..]);
2222 const tmp_file_name = "temp_test_file.txt";
lib/std/testing.zig+30
......@@ -1136,3 +1136,33 @@ pub fn refAllDeclsRecursive(comptime T: type) void {
11361136 _ = &@field(T, decl.name);
11371137 }
11381138}
1139
1140const FuzzerSlice = extern struct {
1141 ptr: [*]const u8,
1142 len: usize,
1143
1144 fn toSlice(s: FuzzerSlice) []const u8 {
1145 return s.ptr[0..s.len];
1146 }
1147};
1148
1149extern fn fuzzer_next() FuzzerSlice;
1150
1151pub const FuzzInputOptions = struct {
1152 corpus: []const []const u8 = &.{},
1153};
1154
1155pub fn fuzzInput(options: FuzzInputOptions) []const u8 {
1156 @disableInstrumentation();
1157 if (builtin.fuzz) {
1158 return fuzzer_next().toSlice();
1159 } else {
1160 if (options.corpus.len == 0) {
1161 return "";
1162 } else {
1163 var prng = std.Random.DefaultPrng.init(std.testing.random_seed);
1164 const random = prng.random();
1165 return options.corpus[random.uintLessThan(usize, options.corpus.len)];
1166 }
1167 }
1168}