12-task subagent-driven refactor complete. left4me-server@1: 7.5 → 1.3 systemd-analyze. left4me-web: 8.7 → 4.1. All 6 Test 8 attack vectors blocked post-deploy. One acceptable SECCOMP audit line per gameserver restart (Breakpad's ptrace fork, blocked by design). Test tooling (gdb, seccomp, libseccomp-dev) apt-removed from left4.me. uid-split spec marked superseded. No queued follow-up. Adjacent work: build-overlay-unit refactor and the deferred drop-in / configmgmt-responsibility reshape. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
6 KiB
Session handoff — hardening refactor landed
The hardening refactor planned at
docs/superpowers/plans/2026-05-15-hardening-refactor.md is deployed
to left4.me and verified. This session executed all 12 tasks
subagent-driven; no follow-up implementation work is queued.
What landed
left4me commits (this session, in order; all on master, pushed):
7c64910—spec(hardening-refactor): resolve emitter open items(verified ckn-bw systemd-bundle emitter handles tuples + empty values)8e678b6—deploy/files: annotate reference units with per-directive hardening comments37309ba—spec(hardening-test-plan): fix four bugs surfaced by executorf615d0d—spec(user-uid-split): mark superseded by the hardening refactor
ckn-bw commits (this session, in order; all on master, pushed):
85b9af0—bundles/left4me: add HARDENING_{COMMON,SERVER,WEB} constants640461c—bundles/left4me: spread HARDENING_SERVER into left4me-server@.servicec6721e7—bundles/left4me: spread HARDENING_WEB into left4me-web.service130b0b1—bundles/left4me: ship kernel.yama.ptrace_scope=2 sysctl drop-in
Deploy: bw apply ovh.left4me ran clean in 10 s (194 OK, 4 fixed,
0 failed). left4me-web.service restarted automatically by bw;
left4me-server@1 and @2 restarted manually post-apply.
What's live on left4.me
| Unit | systemd-analyze score | State |
|---|---|---|
left4me-server@1.service |
1.3 OK (was 7.5 baseline) | active since 13:13:39 UTC |
left4me-server@2.service |
1.3 OK | active since 13:14:40 UTC |
left4me-web.service |
4.1 OK (was 8.7 baseline) | active since 13:01:06 UTC |
Sysctl: kernel.yama.ptrace_scope = 2 (managed by ckn-bw bundle now,
not hand-applied).
Composition matches Test 7 of the test plan with two amendments
(SystemCallArchitectures=native x86, PrivatePIDs=true) and one
addition (SocketBindAllow=udp:27000-27999 tcp:27000-27999).
MemoryDenyWriteExecute=true permanently excluded.
Attack vectors blocked (Test 8 subset rerun post-deploy)
- D1.a — srcds reads DB:
cat /var/lib/left4me/left4me.dbfrom inside the unit's mount namespace →No such file or directory - D1.b — srcds reads web.env:
cat /etc/left4me/web.env→No such file or directory - D1.c — srcds sees /opt: empty listing
- D2.b — srcds sees gunicorn PID via /proc:
cannot access /proc/<pid>(PrivatePIDs in effect; PID doesn't exist in the namespace) - D5 — cross-instance ptrace:
cannot access /proc/<peer-srcds-pid>(cross-instance PID isolation) - Syscall filter compiled correctly:
ptraceandprocess_vm_*not in the compiled allow list (verified viasystemd-analyze syscall-filter)
Known acceptable noise
- One SECCOMP audit line per gameserver restart (
type=1326, i386 syscall 26 =ptrace, sig=31 SIGSYS, code=0x80000000 SECCOMP_RET_KILL_PROCESS). Source: srcds's Breakpad crash-reporter init forks a child that attemptsptrace; we block it by design. The child gets killed; the main srcds process is unaffected. Net effect: Valve doesn't get crash minidumps from this host. Acceptable trade-off given the threat model. If the audit-log noise becomes a problem, switch the SECCOMP filter's action fromKILL_PROCESStoEPERMviaSystemCallErrorNumber=EPERM(would let breakpad fail cleanly instead of getting killed; same security outcome).
Host cleanup done
gdb, libseccomp-dev, seccomp removed via apt remove --purge.
Test tooling was installed during the test-plan execution session
(commit 461b8d0); not needed in steady state. ~13 MB freed.
What's next
No queued follow-up from this work. Adjacent open work:
build-overlay-unitrefactor (docs/superpowers/specs/2026-05-15-build-overlay-unit-design.md). Will reuseHARDENING_COMMON(or a sandbox-class variant) when it lands. Sequenced after this; not blocked.- Broader configmgmt-responsibility reshape — hardening as drop-in files living in left4me with ckn-bw as a thin file-shipper. Real direction, deliberately deferred to a dedicated session in this refactor's design doc.
- Stale RCON port app bug flagged in the prior executor's handoff. Not a hardening issue; separate scope.
Open items the operator should sanity-check manually
I executed everything programmatically that I could. The following need an eyeballed check via the web UI from your laptop:
- Login to the web UI; confirm session works (would catch a SECRET_KEY regression or session-cookie issue).
- Start/stop a server from the UI (exercises the sudo path on the web unit; if the SystemCallFilter or any other web hardening broke sudo, this would fail).
- View live logs for a server (uses
sudo left4me-journalctl). - Trigger an overlay rebuild for a script overlay (exercises the sandbox; unchanged by this refactor, but a smoke against the full chain).
If any of those break, the most likely cause is the web unit's
SystemCallFilter. Drop-in override at
/etc/systemd/system/left4me-web.service.d/00-debug.conf with
SystemCallLog=... instead of SystemCallFilter to identify the
offending syscall, then narrow the filter.
Pointers
- Threat model:
docs/superpowers/specs/2026-05-15-hardening-threat-model.md - Defenses survey:
docs/superpowers/specs/2026-05-15-hardening-defenses-survey.md - Test plan (with executor results + this session's bug fixes):
docs/superpowers/specs/2026-05-15-hardening-test-plan.md - Design doc:
docs/superpowers/specs/2026-05-15-hardening-refactor-design.md - Implementation plan:
docs/superpowers/plans/2026-05-15-hardening-refactor.md - uid-split spec (marked superseded):
docs/superpowers/specs/2026-05-15-user-uid-split-design.md - Live unit emission:
~/Projekte/ckn-bw/bundles/left4me/metadata.py(HARDENING_COMMONetc. near top; spreads at theleft4me-server@.serviceandleft4me-web.serviceentries) - Reference units (annotated):
deploy/files/usr/local/lib/systemd/system/