Skip to content

Guest edits to host-written files are silently discarded at process exit #1961

Description

@Winston-Gu

Guest modifications to a path previously written via host vm.writeFile are silently discarded when the guest process exits. The guest sees its own edit (reads it back fine, exits 0), but afterwards both the host filesystem API and a later in-VM process see the original host-written bytes. Writes to paths the host never touched persist correctly.

This bites hard when the embedding host seeds a workspace with vm.writeFile before running guest code: every guest edit of a seeded file is lost with no error anywhere, while newly created files survive — which makes the data loss easy to miss in testing.

Repro (embedded @rivet-dev/agentos-core, 0.2.15 and 0.2.19)

const { AgentOs } = require("@rivet-dev/agentos-core");

const vm = await AgentOs.create({
  permissions: { fs: "allow", network: "deny", childProcess: "allow", process: "allow", env: "deny", binding: "deny" },
});
await vm.mkdir("/home/agentos", { recursive: true });
await vm.writeFile("/home/agentos/seeded.txt", Buffer.from("original\n")); // host write

await vm.execArgv("node", ["-e",
  'require("fs").writeFileSync("/home/agentos/seeded.txt","EDITED\\n")'
], { timeout: 20000, captureStdio: true }); // guest edit, exits 0

console.log(Buffer.from(await vm.readFile("/home/agentos/seeded.txt")).toString());
// actual: "original\n"     expected: "EDITED\n"

const cat = await vm.execArgv("cat", ["/home/agentos/seeded.txt"], { timeout: 20000, captureStdio: true });
console.log(cat.stdout);
// actual: "original\n" — a LATER guest process also sees the stale content

Observations

  • Overwrite, append, and truncate by the guest are all lost; readdirRecursive reflects the host-written size.
  • Guest writes to paths never touched by the host persist and are visible to readFile/readdirRecursive — including across guest processes (A writes, B edits, host sees B's content).
  • Guest unlink of a guest-written file is visible to the host; behavior is specific to host-written content.
  • Host mkdir is unaffected: guests can create/edit files inside host-made directories normally.
  • Reproduced on darwin/arm64 and linux/arm64 (node:24-bookworm-slim), core 0.2.15 and 0.2.19, with and without software/defaultSoftware.

Looks like host writes land in a base/admin layer while guest copy-on-write over those paths lives in an overlay that is dropped at process exit instead of being merged.

Our workaround: host-write only a manifest file, then have an in-VM bootstrap process write the actual seeded files, so all guest-editable content is guest-authored.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions