No description
Adds IPAddressDeny= to the sandbox unit covering loopback (127/8 + ::1), link-local (169.254/16 + fe80::/10), multicast (224/4 + ff00::/8), all RFC1918 v4 (10/8, 172.16/12, 192.168/16), CGNAT (100.64/10), and ULA v6 (fc00::/7). The kernel attaches systemd's sd_fw_egress BPF program to the unit's cgroup; egress packets matching any of the deny prefixes are silently dropped at the cgroup boundary. Important: do NOT pair this with `IPAddressAllow=any`. Documentation claims "more specific rule wins" but on this systemd 257 + kernel 6.12 combo, having both set causes the allow to win unconditionally — the deny gets ignored. Empty IPAddressAllow + populated IPAddressDeny is the correct shape: kernel default "allow all" applies to non-listed addresses, and the listed prefixes are blocked. Because the host's resolv.conf typically points at a private-IP DNS server (10.0.0.1 in the test deploy), blocking RFC1918 also kills DNS. Adds a static /etc/left4me/sandbox-resolv.conf with public resolvers (Cloudflare 1.1.1.1, Google 8.8.8.8) and bind-mounts that into the sandbox at /etc/resolv.conf, replacing the host's resolver inside the sandbox only. Smoke-tested on ckn@10.0.4.128: - public 1.1.1.1:443: CONNECTED - public HTTPS via DNS (steamcommunity.com): 200 - localhost web app 127.0.0.1:8000: blocked (TimeoutError) - localhost sshd 127.0.0.1:22: blocked - private LAN ssh 10.0.4.128:22: blocked - private DNS 10.0.0.1:53: blocked AF_UNIX stays in RestrictAddressFamilies — dropping it would risk breaking NSS / syslog for marginal gain, and the IP-level filter addresses the primary threat (reaching the host's HTTP/SSH services). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> |
||
|---|---|---|
| deploy | ||
| docs/superpowers | ||
| l4d2host | ||
| l4d2web | ||
| .gitignore | ||
| AGENTS.md | ||
| README.md | ||
left4me
left4me is a local L4D2 server management platform with two planned components:
l4d2host+l4d2ctl(host library + CLI)l4d2-web-app(Flask web app for users, blueprints, servers, jobs, and logs)
Status
Implementation plans remain the source of truth for architecture and task sequencing:
docs/superpowers/plans/2026-04-22-l4d2-host-lib-v1.mddocs/superpowers/plans/2026-04-23-l4d2-web-app-v1.md
Locked v1 Decisions
- Naming is strictly
l4d2(notl4d). - Host library and web app are separate components.
- Host CLI write commands are fixed to:
installinitialize <name> -f <spec.yaml>start <name>stop <name>delete <name>
- Host CLI read commands are available for the web/host boundary:
status <name> --jsonlogs <name> --lines <n> --follow/--no-follow
- The web app calls host operations through
l4d2ctl, not directl4d2hostimports. - Deployment uses
/var/lib/left4mefor runtime state,/opt/left4mefor repository contents and the virtualenv,/etc/left4mefor environment files, and global units under/usr/local/lib/systemd/system. - Overlay handling is directory-based; the web app populates each overlay (workshop downloads, managed-global refresh).
- No lock manager, no rollback, no preflight checks in host library.
- CLI propagates subprocess failures via stderr and return code.
deleteon missing instance is no-op success.- Blueprint model (web app):
- user-private in v1
- servers are live-linked to blueprint
- no per-server overrides
- delete blueprint blocked when linked servers exist
- blueprint changes apply on next action
- server can reassign blueprint anytime
Planned Repository Layout
l4d2host/l4d2web/deploy/docs/superpowers/plans/
Deployment
See deploy/README.md for the Linux test deployment contract, including the runtime user, target filesystem layout, systemd units, privileged helpers, sudoers rules, admin bootstrap, and overlay reference rules.
Tech Stack (planned)
- Python 3.12+
- Typer, PyYAML, pytest
- Flask, SQLAlchemy, Alembic
- HTMX (vendored locally), custom CSS, SSE
- systemd units, kernel overlayfs (mounted via the
left4me-overlayprivileged helper), steamcmd
Recommended Implementation Order
- Implement
l4d2hostplan first. - Implement
l4d2webplan second. - Keep tests green task-by-task (TDD flow from plans).
- Keep commits small and aligned with plan tasks.
Contributing Notes
- Follow plan task order unless explicitly re-planned.
- Keep contracts above unchanged unless the user asks to change them.
- Update plan docs when scope or behavior changes.