Tier 3 + Tier 4 deploy runbook in AGENTS.md
Repo has all the code paths for Tier 3 (real exploit fire via msfrpcd) and Tier 4 (real malware execution via chunked upload), but neither lab host has run a single Tier-3 episode because msfrpcd and the Metasploitable2 image aren't deployed there. 3009 episodes in flight to date are all Tier 2 (mimic workloads in clean Alpine), which is useful pipeline-validation data but cannot answer the actual research question. This commit makes the deploy push-button: - AGENTS.md: new "Tier 3 + Tier 4 deploy" section listing the three prereqs (install-msfrpcd.sh, fetch-metasploitable2.sh, setup_bridge.sh), the foreground verify command (run_tier3_demo.py), and the Tier-4 promotion path (MB API key → fetch_sample.py → manifest edit → orchestrator restart). - samples/manifest.toml: clearer per-entry comment showing the 4-step sha256 → real-binary promotion path. Replaces the earlier "TBD" placeholder which suggested a single edit unlocks Tier 4 when in fact you need to fetch the binary too. The fleet runner already auto-detects msfrpcd (orchestrator/fleet.py _msfrpcd_available()); once the lab-host operator-AI lands the prereqs, episodes flip to Tier 3 with no orchestrator config change. Tier 4 follows automatically the next time the deterministic selector picks a sample whose sha256 file exists in samples/store/.
This commit is contained in:
parent
321ea63803
commit
02b9d0a645
2 changed files with 129 additions and 4 deletions
116
AGENTS.md
116
AGENTS.md
|
|
@ -78,6 +78,122 @@ common silent failures it catches:
|
|||
|
||||
`cis490-doctor --json` is machine-readable for use by other agents.
|
||||
|
||||
## Tier 3 + Tier 4 deploy (lab-host one-time, ~20 min)
|
||||
|
||||
Tier 2 is the default after `install-lab-host.sh`: real Alpine guest,
|
||||
mimic in-guest workloads. To get **real exploit fire** (Tier 3) and
|
||||
**real malware execution** (Tier 4), each lab host needs three more
|
||||
artifacts. The fleet runner auto-detects Tier-3 readiness via the
|
||||
`_msfrpcd_available()` probe — once msfrpcd is up, episodes flip to
|
||||
Tier 3 with no orchestrator config change.
|
||||
|
||||
### Prerequisites (per lab host)
|
||||
|
||||
```sh
|
||||
# 1. Install Metasploit Framework + msfrpcd. Idempotent; ~1 GiB
|
||||
# download the first time. Drops a strong password at
|
||||
# /etc/cis490/msfrpc.env (mode 0640, root:cis490) and a systemd
|
||||
# unit cis490-msfrpcd.service bound to 127.0.0.1:55553.
|
||||
sudo /opt/cis490/scripts/install-msfrpcd.sh
|
||||
sudo systemctl enable --now cis490-msfrpcd.service
|
||||
systemctl is-active cis490-msfrpcd.service # → active
|
||||
|
||||
# 2. Fetch Metasploitable2 qcow2. Rapid7's official download is
|
||||
# registration-walled; supply the URL+sha256 you obtained from
|
||||
# your registration. Conversion from VMDK → qcow2 happens
|
||||
# automatically. Lands at /var/lib/cis490/vm/images/metasploitable2.qcow2.
|
||||
IMAGE_URL='<your-rapid7-or-mirror-url>' \
|
||||
IMAGE_SHA256='<sha256-of-the-archive>' \
|
||||
sudo OUT_DIR=/var/lib/cis490/vm/images \
|
||||
/opt/cis490/scripts/fetch-metasploitable2.sh
|
||||
|
||||
# 3. (Optional but recommended.) Bring up the host-only bridge
|
||||
# `br-malware` so callback-payload exploits (3 of the 5 bundled
|
||||
# modules require it: distccd_command_exec, php_cgi_arg_injection,
|
||||
# unreal_ircd_3281_backdoor) can land. Without the bridge, the
|
||||
# fleet auto-restricts to non-callback modules
|
||||
# (vsftpd_234_backdoor, samba_usermap_script).
|
||||
sudo /opt/cis490/scripts/setup_bridge.sh
|
||||
```
|
||||
|
||||
### Verify Tier-3 fire end-to-end
|
||||
|
||||
```sh
|
||||
# This runs ONE Tier-3 episode in the foreground using whatever
|
||||
# module + sample the deterministic selector picks for slot=0,
|
||||
# episode=0 on this host. Should print `module = exploit/...`,
|
||||
# fire it via msfrpcd, and a normal episode summary at the end.
|
||||
sudo -u cis490 \
|
||||
MSFRPC_PASSWORD="$(. /etc/cis490/msfrpc.env; echo $MSFRPC_PASSWORD)" \
|
||||
/opt/cis490/.venv/bin/python \
|
||||
/opt/cis490/tools/run_tier3_demo.py \
|
||||
--module vsftpd_234_backdoor \
|
||||
--target-port 21 --target-boot-timeout 240
|
||||
```
|
||||
|
||||
If the run prints `module loaded: vsftpd_234_backdoor (exploit/unix/ftp/...)`
|
||||
and `episode_id = 01...` at the end, Tier 3 is live. The orchestrator's
|
||||
next wave will use Tier 3 for every episode.
|
||||
|
||||
### Tier-4 (real malware execution)
|
||||
|
||||
Tier 4 layers on top of Tier 3 — the exploit lands a session, then a
|
||||
real binary is uploaded via the chunked path and executed inside the
|
||||
session. Two prerequisites:
|
||||
|
||||
```sh
|
||||
# 1. Add MalwareBazaar API key (free signup at https://bazaar.abuse.ch/).
|
||||
echo "$MB_KEY" | sudo install -m 0600 -o cis490 -g cis490 /dev/stdin \
|
||||
/opt/cis490/samples/.bazaar.token
|
||||
|
||||
# 2. Pick a sha256 for one of your sample families from MalwareBazaar
|
||||
# and download the binary. Verifies sha256 on the way in; lands at
|
||||
# /opt/cis490/samples/store/<sha256>.
|
||||
sudo -u cis490 /opt/cis490/.venv/bin/python \
|
||||
/opt/cis490/tools/fetch_sample.py <64-hex-sha256>
|
||||
|
||||
# 3. Edit /opt/cis490/samples/manifest.toml: add `source`, `sha256`,
|
||||
# and `url` fields to the matching entry. The orchestrator's next
|
||||
# selection that hits that sample will use the real binary
|
||||
# (sample.kind == "real") — meta.sample.sha256 records it for the
|
||||
# trainer.
|
||||
|
||||
sudo systemctl restart cis490-orchestrator
|
||||
```
|
||||
|
||||
### Confirm Tier 3+4 are flowing
|
||||
|
||||
```sh
|
||||
# On the Pi:
|
||||
sudo -u cis490 /opt/cis490/.venv/bin/python -c "
|
||||
import json
|
||||
real = mimic = 0
|
||||
modules = set()
|
||||
for line in open('/var/lib/cis490/index.jsonl'):
|
||||
pass # use the prune classifier instead
|
||||
"
|
||||
# or (better) rerun the diversity audit:
|
||||
# the multi-host audit script the maintainer keeps for spot-checking
|
||||
```
|
||||
|
||||
The on-Pi maintainer will see `meta.exploit.module_name` populated
|
||||
and `meta.sample.kind == "real"` for the new episodes. If those stay
|
||||
null after deploy, file an issue with the `journalctl -u cis490-orchestrator`
|
||||
trace from the failed wave.
|
||||
|
||||
### Don't shortcut
|
||||
|
||||
- DO NOT install `metasploit-framework` system-wide outside
|
||||
install-msfrpcd.sh. The script wires the systemd unit + creds; a
|
||||
manual install will work but the orchestrator's `_msfrpcd_available()`
|
||||
probe expects the unit to be on 127.0.0.1:55553 with a password at
|
||||
`/etc/cis490/msfrpc.env`.
|
||||
- DO NOT push your MalwareBazaar API key. `samples/.bazaar.token`
|
||||
is gitignored; the env var path is preferred for one-shot fetches.
|
||||
- DO NOT add bogus sha256 entries to `manifest.toml` — every sha256
|
||||
is verified on download. A wrong value breaks `fetch_sample.py`
|
||||
and confuses every replay.
|
||||
|
||||
## Securing the connection (mTLS) — DO NOT mint your own certs
|
||||
|
||||
The lab-host ↔ Pi connection is mTLS over WireGuard. **The cert
|
||||
|
|
|
|||
|
|
@ -19,11 +19,20 @@ name = "xmrig-cryptominer"
|
|||
family = "XMRig"
|
||||
category = "cryptominer"
|
||||
profile = "cpu-saturate"
|
||||
# A real XMRig fetch goes here when MalwareBazaar pull is wired up:
|
||||
# source = "MalwareBazaar"
|
||||
# sha256 = "TBD"
|
||||
# url = "https://bazaar.abuse.ch/sample/TBD/"
|
||||
description = "Sustained 1-vCPU saturation, very low IO/net. Pure compute."
|
||||
# To promote this entry to Tier-4 (real binary):
|
||||
# 1. Pick a sha256 from https://bazaar.abuse.ch/ for this family.
|
||||
# 2. Add `source`, `sha256`, `url` fields below.
|
||||
# 3. On the lab host (one-time per host):
|
||||
# export MALWAREBAZAAR_API_KEY=<key>
|
||||
# sudo -u cis490 /opt/cis490/.venv/bin/python \
|
||||
# /opt/cis490/tools/fetch_sample.py <sha256>
|
||||
# The sha256 is verified on download; the binary lands at
|
||||
# /opt/cis490/samples/store/<sha256>.
|
||||
# 4. Restart cis490-orchestrator. Episodes that select this sample
|
||||
# now run the real binary via the chunked upload path. If the
|
||||
# binary isn't on disk, the orchestrator falls back to the mimic
|
||||
# profile above — both kinds coexist via meta.sample.kind.
|
||||
|
||||
[[sample]]
|
||||
name = "mirai-class-bot"
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue