hive-c0re: back agent state dirs with btrfs subvolumes

Progressive enhancement: a brand-new agent's state root under
/var/lib/hyperhive/agents is created as a btrfs subvolume when the host
filesystem is btrfs, otherwise it falls back to a plain directory. No
existing agent is auto-migrated — the new path only fires when the root
does not yet exist, so plain-dir agents are left untouched until an
explicit opt-in upgrade.

Two new privileged ops (subvolume create/delete are root-only):
EnsureAgentSubvolume statfs-gates on btrfs, creates the subvolume, and
chowns it to the hive-core user so the normal state/claude/harness
mkdirs succeed inside it; DeleteAgentSubvolume btrfs-subvolume-deletes
the root iff it is actually a subvolume. hive-c0re calls Ensure before
the per-agent dirs are created (spawn/rebuild/InitConfig) and Delete on
the purge path only — destroy keeps the subvolume for revival, matching
plain-dir semantics. btrfs-progs added to the hive-priv unit PATH.

Per-subvolume usage accounting + optional quota is a separate
follow-up.
This commit is contained in:
atlas 2026-06-19 12:28:17 +02:00 committed by mara
commit 1f602d5fda
9 changed files with 242 additions and 0 deletions

View file

@ -336,6 +336,43 @@ pub enum PrivRequest {
container: String,
action: InfraAction,
},
// --- Agent state subvolumes (btrfs) ---
/// Ensure the agent's persistent state root
/// (`<AGENT_STATE_ROOT>/<agent_name>`) is a btrfs subvolume — IF the
/// underlying filesystem is btrfs and the root doesn't already exist.
///
/// hive-priv derives the path from `agent_name` (never passed over the
/// wire), validates the name, then:
/// - path already exists (dir or subvol) → no-op (progressive: existing
/// agents are left exactly as they are, never auto-migrated);
/// - parent FS is not btrfs → no-op (hive-c0re's normal `create_dir_all`
/// makes a plain directory, the pre-subvolume behaviour);
/// - else → `btrfs subvolume create <path>` and chown it to the owner of
/// `AGENT_STATE_ROOT` (the `hive-core` user) so hive-c0re can create the
/// `state/` / `claude/` / `harness/` subdirs inside it as before.
///
/// Idempotent and safe to call on every provision. Requires root: btrfs
/// subvolume creation is privileged.
EnsureAgentSubvolume {
/// Logical agent name (validated by `validate_agent_name`).
agent_name: String,
},
/// Delete the agent's persistent state root if — and only if — it is a
/// btrfs subvolume. Called by hive-c0re on the **purge** path only
/// (never on a plain destroy, which keeps state for revival).
///
/// A subvolume root cannot be removed with `rmdir`/`remove_dir_all`, so
/// this routes through hive-priv to run `btrfs subvolume delete`. If the
/// path is a plain directory (pre-subvolume agent) or doesn't exist, it's
/// a no-op — hive-c0re's own `remove_dir_all` handles the plain-dir case.
/// hive-priv derives + validates the path the same way as
/// [`PrivRequest::EnsureAgentSubvolume`]. Requires root.
DeleteAgentSubvolume {
/// Logical agent name (validated by `validate_agent_name`).
agent_name: String,
},
}
/// Response from the privileged helper.