summaryrefslogtreecommitdiff
path: root/src/builtins.zig
diff options
context:
space:
mode:
authorGabriel Schneider <[email protected]>2026-09-28 23:13:57 -0300
committerGabriel Schneider <[email protected]>2026-10-01 00:12:15 -0300
commit90530f893236c665deb9f5bddc925ee1fe51cca5 (patch)
treef9fb5a34731eab09fddae5751d3cc8450c796853 /src/builtins.zig
parent8b2a55f31169ede82e11a573ab655e72e7831fe7 (diff)
downloadpardes-90530f893236c665deb9f5bddc925ee1fe51cca5.tar.gz
pardes-90530f893236c665deb9f5bddc925ee1fe51cca5.zip
A failed Dump or a Restore of no dump fails its write, before any warning
A Dump into a DumpDir it could not write, or a Restore of a file that is not a dump, answered a ctl write with rc 0 and only a message, and the Restore warned about unsaved panes before it ever looked at the file. The hosts' dump write now fails the waiting 9P write with EIO (the late failure a Save uses), naming the path and the reason in the log, and Restore parses the file before its unsaved-panes refusal, failing with `not a pardes dump`. Co-Authored-By: Claude Opus 5.5 <[email protected]>
Diffstat (limited to 'src/builtins.zig')
-rw-r--r--src/builtins.zig13
1 files changed, 11 insertions, 2 deletions
diff --git a/src/builtins.zig b/src/builtins.zig
index 07cdf741..be674692 100644
--- a/src/builtins.zig
+++ b/src/builtins.zig
@@ -267,7 +267,11 @@ test "Exit over a ctl write names every pane it asks about, and the next Exit di
/// A dump file that exists, for a Restore to get past reading it.
fn testDump(buf: []u8) ![]const u8 {
var tmp = std.testing.tmpDir(.{});
- try tmp.dir.writeFile(std.testing.io, .{ .sub_path = "d.zon", .data = ".{}" });
+ // A real dump: a Restore reads it through before it asks anything.
+ const source = try Pardes.init(std.testing.allocator, .{ .tty_only = true });
+ defer source.deinit();
+ try pardes.dump.dumpState(source);
+ try tmp.dir.writeFile(std.testing.io, .{ .sub_path = "d.zon", .data = source.dump_out.? });
var dir: [4096]u8 = undefined;
const at = dir[0..try tmp.dir.realPath(std.testing.io, &dir)];
return std.fmt.bufPrint(buf, "Restore {s}/d.zon", .{at});
@@ -558,7 +562,12 @@ pub const Restore = struct {
};
return c.p.reportFailure(c.id, std.fmt.bufPrint(&buf, "Restore: {s}: {s}", .{ path, why }) catch "Restore: cannot read the dump");
};
- c.p.gpa.free(bytes);
+ defer c.p.gpa.free(bytes);
+ // Nor does a file that is not a dump, before any warning.
+ pardes.dump.check(c.p.gpa, bytes) catch |err| {
+ var buf: [limits.host_path_cap + 64]u8 = undefined;
+ return c.p.reportFailure(c.id, std.fmt.bufPrint(&buf, "Restore: {s}: not a pardes dump ({s})", .{ path, @errorName(err) }) catch "Restore: not a pardes dump");
+ };
}
// acme's Load adds a dump's windows to the ones there; a Restore
// replaces them all, so it asks what Exit asks first.