Skip to content

macOS guests 4/6: snapshots, schedules and stopped forks - #506

Open
chruffins wants to merge 1 commit into
feat/macos-guest-servicefrom
feat/macos-snapshots
Open

chruffins wants to merge 1 commit into
feat/macos-guest-servicefrom
feat/macos-snapshots

Conversation

@chruffins

@chruffins chruffins commented Oct 11, 2026 •

Copy link
Copy Markdown
Contributor

Summary

PR 4 of 6. Snapshots, standby and stopped clones for macOS guests. Base: #500.

  • Stopped snapshots and cold clones: these require a confirmed graceful stop. A clone gets a fresh machine identifier, a MAC assigned under the fork admission lock, and an SSH host key rekey on first start. A failed rekey stops the clone and is retried on the next start.
  • Memory snapshots of Running or Standby instances: the exact VZ configuration is validated before pausing, and disk, auxiliary storage and machine state are captured while the VM is down. A formerly Running source resumes afterwards, even if the request is cancelled.
  • Same-instance restore and standby: the payload is validated before anything is replaced, then metadata and storage are swapped in together, with crash recovery.
  • Interrupted restore: if the API dies mid-restore, the leftover VM comes up Paused; POST /restore resumes it and finishes the restore (records the shim, deletes the consumed checkpoint).
  • Snapshot schedules and retention use the existing controller.
  • Boot admission: start and restore check machine identity and MAC uniqueness under one boot lock.
  • Warm memory forks are rejected. VZ restores saved state only into an identical configuration (MAC, machine identifier, NIC and auxiliary storage), and Apple documents concurrent VMs sharing an identifier as undefined. Repeated same-instance restore is the warm start.

Linux code touched

  • lib/instances: snapshot, standby, restore, fork, start and stop gain macOS hooks; manager.go resumes Paused instances through a macOS completion hook and recovers interrupted restore staging at startup.
  • lib/hypervisor/vz/client.go: save/restore support probing; tracing.go forwards it.
  • lib/network/allocate.go: NewUniqueMAC, so macOS clones share the allocator's uniqueness rule.

Not supported

Memory-snapshot compression, warm memory forks, and snapshots carried to another host or user account (VZ saved state is tied to both). Clones change machine identifier, MAC and SSH host keys only; hostname and accounts are copied.

Testing

  • Filesystem and mock tests cover capture, restore, isolation, manifest checks, crash-swap recovery, cancellation, schedules and retention. HTTP fixtures cover VZ pause and configuration probing.
  • Native QA ran on Apple silicon (macOS 27.0.1 host and guests) across six runs plus a VZ restore spike. The simplification pass after run 6 has not been re-run natively yet. This PR's paths covered there: memory checkpoint, change and restore (same PID and boot session), repeated restore, Standby/Stopped targets, cancellation after pause, API crash mid-restore, schedules with retention, cold forks with distinct identities, and the VZ restore-compatibility spike behind the warm-fork decision.

Review focus

  • lib/instances/snapshot_macos.go (staged swap, recovery, finishMacOSResume).
  • lib/instances/macos_identity.go (clone identity, MAC assignment, rekey teardown).

Stack

Each PR is one commit on the one below it. macOS logic lives in its own files (macos*.go, *_darwin.go, exec_lifecycle.go, port_forward.go); shared Linux files get small hooks such as if stored.MacOS != nil.

  1. macOS guests 1/6: VZ runtime, machine images and instance lifecycle #498 VZ runtime, machine images and instance lifecycle
  2. macOS guests 2/6: OCI machine-image integration #499 OCI machine images
  3. macOS guests 3/6: Darwin guest service, readiness and exec #500 Darwin guest agent, readiness and exec
  4. macOS guests 4/6: snapshots, schedules and stopped forks #506 snapshots, standby and stopped clones
  5. macOS guests 5/6: guest-port forwarding #514 guest-port forwarding
  6. macOS guests 6/6: experimental machine-image builds #503 machine-image builds (not needed for v0; can land later)

@cursor cursor Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes using default effort and found 1 potential issue.

Fix All in Cursor

❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.

Want higher recall? High effort reviews run extra passes and find more bugs. A team admin can switch effort levels in the Cursor dashboard.

Reviewed by Cursor Bugbot for commit 8a79efe. Configure here.

Comment thread lib/instances/start.go Outdated
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from 8a79efe to 10c8f44 Compare October 11, 2026 18:11
@chruffins chruffins changed the title PR6 (draft): macOS stopped snapshots and same-instance restore macOS guests 6/6: stopped snapshots and same-instance restore Oct 11, 2026
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from 10c8f44 to 0bc847d Compare October 11, 2026 21:45
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from 0bc847d to bcd99d3 Compare October 11, 2026 21:49
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from bcd99d3 to 0aedf45 Compare October 11, 2026 22:04
@chruffins
chruffins force-pushed the feat/macos-snapshots branch 2 times, most recently from 2e09087 to 28fb9ac Compare October 12, 2026 01:29
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from 28fb9ac to 17c3d4d Compare October 12, 2026 01:34
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from 17c3d4d to 53b1a79 Compare October 12, 2026 18:32
@chruffins chruffins changed the title macOS guests 6/6: stopped snapshots and same-instance restore macOS guests 6/6: stopped snapshots, same-instance restore and stopped clones Oct 12, 2026
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from 53b1a79 to fa7578a Compare October 12, 2026 22:06
@chruffins chruffins changed the title macOS guests 6/6: stopped snapshots, same-instance restore and stopped clones macOS guests 6/6: stopped snapshots, same-instance standby and restore, and stopped clones Oct 12, 2026
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from fa7578a to bb25ff9 Compare October 12, 2026 22:34
@chruffins
chruffins force-pushed the feat/macos-snapshots branch 2 times, most recently from 0143542 to d58bc88 Compare October 13, 2026 00:05
@chruffins
chruffins added this pull request to stack #508 October 13, 2026 00:06
@chruffins chruffins changed the title macOS guests 6/6: stopped snapshots, same-instance standby and restore, and stopped clones macOS guests 4/6: stopped snapshots, same-instance standby and restore, and stopped clones Oct 13, 2026
@chruffins
chruffins force-pushed the feat/macos-snapshots branch 2 times, most recently from 0156859 to 0783bf8 Compare October 14, 2026 03:14
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from 0783bf8 to 17ee175 Compare October 14, 2026 06:15
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from 17ee175 to 646d028 Compare October 14, 2026 06:31
@chruffins
chruffins force-pushed the feat/macos-snapshots branch 2 times, most recently from 2fbc60c to fe12f31 Compare October 14, 2026 16:38
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from fe12f31 to f19d7d9 Compare October 14, 2026 16:55
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from f19d7d9 to f482aaa Compare October 14, 2026 17:08
@chruffins
chruffins removed this pull request from stack #508 October 14, 2026 17:08
@chruffins
chruffins added this pull request to stack #515 October 14, 2026 17:10
@chruffins
chruffins marked this pull request as ready for review October 14, 2026 19:12
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from f482aaa to 9d2f21a Compare October 14, 2026 20:10
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from 9d2f21a to ef1d3e2 Compare October 15, 2026 00:27
@chruffins
chruffins force-pushed the feat/macos-snapshots branch 2 times, most recently from 1865c45 to da3595f Compare October 15, 2026 19:25
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from da3595f to 8229622 Compare October 15, 2026 22:56
@chruffins
chruffins force-pushed the feat/macos-snapshots branch from 8229622 to e2e2ec4 Compare October 19, 2026 15:49
…e, and stopped clones

Stopped snapshots after a graceful stop, same-instance restore through a staged
disk swap, experimental same-instance standby, and clones from a stopped source
with a fresh machine identifier, MAC and SSH host keys.

This branch has not been deployed

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant