authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2026-01-27 11:29:03-08:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2026-01-30 12:10:01-08:00
log8a985236af9c83ec81389367b2c61d62c90e21ee
tree3212923fb0bc3d3c1ed9733f6cb1ae7920aadbec
parente1604c19230bf67773501603f5c772b95ce01ad9

std.Build.Step.Run: gracefully handle test runner misbehavior

specifically if it misbehaves after sending a message header but not the body

1 files changed, 22 insertions(+), 1 deletions(-)

lib/std/Build/Step/Run.zig+22-1
...@@ -1930,7 +1930,28 @@ fn waitZigTest(...@@ -1930,7 +1930,28 @@ fn waitZigTest(
1930 }1930 }
1931 // There is definitely a header available now -- read it.1931 // There is definitely a header available now -- read it.
1932 const header = stdout.takeStruct(Header, .little) catch unreachable;1932 const header = stdout.takeStruct(Header, .little) catch unreachable;
1933 try stdout.fill(header.bytes_len);1933
1934 while (stdout.buffered().len < header.bytes_len) {
1935 const timeout: Io.Timeout = t: {
1936 const t = if (timer) |*t| t else break :t .none;
1937 if (response_timeout_ns) |timeout_ns| break :t .{ .duration = .{
1938 .raw = .fromNanoseconds(timeout_ns -| t.read()),
1939 .clock = .awake,
1940 } };
1941 break :t .none;
1942 };
1943 multi_reader.fill(64, timeout) catch |err| switch (err) {
1944 error.Timeout, error.EndOfStream => return .{ .no_poll = .{
1945 .active_test_index = active_test_index,
1946 .ns_elapsed = if (timer) |*t| t.read() else 0,
1947 } },
1948 error.UnsupportedClock => {
1949 timer = null;
1950 continue;
1951 },
1952 else => |e| return e,
1953 };
1954 }
19341955
1935 const body = stdout.take(header.bytes_len) catch unreachable;1956 const body = stdout.take(header.bytes_len) catch unreachable;
1936 var body_r: std.Io.Reader = .fixed(body);1957 var body_r: std.Io.Reader = .fixed(body);