Skip to content

fix(sandbox): preserve Linux overlayfs directory identity across copy-up - #6910

Draft
Colafornia wants to merge 2 commits into
apache:rust-previewfrom
Colafornia:fix/sandbox-overlayfs-directory-identity
Draft

Colafornia wants to merge 2 commits into
apache:rust-previewfrom
Colafornia:fix/sandbox-overlayfs-directory-identity

Conversation

@Colafornia

@Colafornia Colafornia commented Nov 14, 2026 •

Copy link
Copy Markdown
Member
English

Summary

Preserve workspace directory grants when Linux overlayfs copies a lower-layer directory to the writable upper layer. Creating .maka-workspace.json must not invalidate the grant used by ACP session/new and later tools.

Refs #6667 and #6815.

Root cause and identity boundary

DirectoryIdentity hashes (volume, ino, birth). Directory copy-up can change birth time while preserving the visible directory inode. Omit birth only for overlayfs, and obtain its instance UUID through the existing FS_IOC_GETFSUUID path.

A nonzero f_fsid is insufficient: with uuid=off/null, overlayfs returns the backing filesystem's fsid. Independent overlays can then share both fsid and a lower directory's inode. The initial PR accepted one overlay's grant after the same path was mounted with another upper directory. This revision removes overlayfs from the fsid branch and rejects mounts that cannot expose an instance UUID. It also removes the synthetic statfs helper and its obsolete test.

The earlier claim that overlayfs always rejects FS_IOC_GETFSUUID, or that uuid=off implies a zero fsid, was incorrect on the tested kernel. The ioctl returns a persistent instance UUID with uuid=on/auto; uuid=off/null returns ENOTTY, mapped to Unsupported.

Verification

Verified at 0daa2ef6dc612300b893f82d27de368144c60509:

  • Linux aarch64, kernel 7.2.12-orbstack-00394-gbecdd6130068: cargo test --offline --locked -p maka-sandbox --lib -F schemars/uuid1 passed: 10 tests, 2 explicitly ignored live-mount tests.
  • Ran the live-mount tests explicitly with MAKA_TEST_OVERLAYFS_DIR, the individual test name, and -- --ignored --nocapture. Fresh uuid=on and uuid=auto overlays passed copy-up stability; uuid=off and uuid=null overlays with nonzero fsid were rejected. The rejection test failed on the previous implementation because capture incorrectly succeeded.
  • A separate harness called the production DirectoryIdentity and maka-fs-tools::directory::open: the same overlay's grant survived unmount/remount; a different overlay rejected it. Both UUID-less configurations rejected capture.
  • cargo fmt -p maka-sandbox -- --check and git diff --check passed.

The live fixtures used temporary tmpfs-backed overlays inside a disposable Docker container with CAP_SYS_ADMIN. These tests are explicitly ignored by default and are not wired into CI. Linux bubblewrap integration, clippy, macOS/Windows tests, full just check, and the full ACP session/new → tool execution check were not rerun for this revision. CI remains pending.

AI use

  • No generative tool made a substantive contribution
  • Generative tooling made a substantive contribution

Google Antigravity authored the initial change. OpenAI Codex verified and fixed the overlay identity collision, updated regression coverage, and ran the Linux checks above. Preserve the Generated-by trailers when squashing.

Checklist

  • Tests cover the change and fail without it
  • Format, typecheck and the affected suites pass locally — focused Linux checks passed; broader checks are listed above

Does this PR entail a change in behavior?

  • Yes — described under Summary above
  • No
中文

概述

保持 Linux overlayfs 目录从只读下层复制到可写上层后的工作区授权有效。创建 .maka-workspace.json 不应使 ACP session/new 和后续工具使用的目录授权失效。

关联 #6667 与 #6815。

根因与身份边界

DirectoryIdentity 对 (volume, ino, birth) 计算哈希。目录复制到上层时,可见的 inode 保持不变,但创建时间可能改变。因此仅对 overlayfs 省略创建时间,并通过已有的 FS_IOC_GETFSUUID 路径获取实例 UUID。

非零 f_fsid 不足以证明实例身份:uuid=off/null 下,overlayfs 返回底层文件系统的 fsid。不同 overlay 实例可能同时共享这个 fsid 和下层目录的 inode。初版 PR 在同一路径换挂另一个上层目录后,仍接受原实例的授权。本次修订移除 overlayfs 的 fsid 分支,拒绝无法提供实例 UUID 的挂载,并删除合成 statfs 测试及其专用辅助函数。

此前关于 overlayfs 总是拒绝 FS_IOC_GETFSUUID、或 uuid=off 意味着 fsid 为零的描述,在本次内核实测中均不成立。uuid=on/auto 时 ioctl 返回持久化的实例 UUID;uuid=off/null 时返回 ENOTTY,映射为 Unsupported。

验证

验证提交:0daa2ef6dc612300b893f82d27de368144c60509:

  • Linux aarch64,内核 7.2.12-orbstack-00394-gbecdd6130068:cargo test --offline --locked -p maka-sandbox --lib -F schemars/uuid1 通过,10 项通过、2 项真实挂载测试显式忽略。
  • 设置 MAKA_TEST_OVERLAYFS_DIR,指定单个测试名并添加 -- --ignored --nocapture,显式运行真实挂载测试。全新 uuid=on、uuid=auto 挂载通过目录复制后的身份稳定性检查;非零 fsid 的 uuid=off、uuid=null 挂载均被拒绝。拒绝测试在修改前因错误接受授权而失败。
  • 独立验证程序调用生产 DirectoryIdentity 和 maka-fs-tools::directory::open:同一实例卸载后重挂仍接受原授权,不同实例拒绝该授权;两种无 UUID 配置均拒绝捕获授权。
  • cargo fmt -p maka-sandbox -- --check 与 git diff --check 通过。

真实夹具是在带 CAP_SYS_ADMIN 的一次性 Docker 容器内创建的临时 tmpfs 支撑 overlay 挂载。这些测试默认显式忽略,尚未接入 CI。本次修订未重跑 Linux bubblewrap 集成、clippy、macOS/Windows 测试、完整 just check 或完整 ACP session/new → 工具执行验收。CI 待完成。

AI 使用

  • 没有生成式工具作出实质性贡献
  • 生成式工具作出了实质性贡献

Google Antigravity 编写初版改动。OpenAI Codex 验证并修复 overlay 身份碰撞、更新回归测试并执行上述 Linux 检查。Squash 时保留 Generated-by trailers。

审查清单

  • 测试覆盖本次变更且在修改前失败
  • 格式、类型检查和受影响套件均已在本地通过 — 聚焦的 Linux 检查已通过,其余检查见上文

本 PR 是否带来行为变更?

  • 是 — 如上文概述所述
  • 否

Reuse FS_IOC_GETFSUUID instead of accepting a shared backing fsid. Reject overlays without an instance UUID while preserving copy-up stability. Replace the synthetic fsid test with an explicit live-mount rejection test.

Generated-by: OpenAI Codex

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