v0.3.1 — security fixes (external review round 4)
Upgrade recommended — contains a Critical fix.
- Critical:
tjor resetsymlink-escape across nested tiers. rm -rf follows a symlink anywhere in a path prefix, so an agent that swapped an intermediate directory (e.g.home/.local/share/opencode) for a symlink could redirect areset sessions/reset credswipe outside the session root, deleting under the operator's own permissions. reset now refuses any target whose ancestors aren't all real directories under the session root (leaf symlinks, like the cache tier, still remove safely). Live-reproduced; now covered by an integration test against a real outside victim. - IP guard: the deprecated
::/96IPv4-compatible IPv6 form is now unwrapped (the last transition-embedding SSRF form left un-handled); added 255.255.255.255/32, 2001::/23, 100:0:0:1::/64. - Session-collision guard: relaunching a session id that already backs a running agent is refused (attach it, or use
--session <name>). ls/gcparse on a control separator, so a workspace path containing a literal|can no longer mislabel a session.- Threat model: ADR 0006 documents the detached/persistent-container posture change; the session-launch spec and README are reconciled.
- CI: mitmproxy pinned to the image version; the lifecycle job gained a dependency + timeout.