Skip to content

shellkraft/Ledger

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

3 Commits
 
 
 
 
 
 

Repository files navigation

Ledger — Operational Change Tracker Aggressor Script

Ledger is a Cobalt Strike aggressor script that tracks every operational change made during an engagement. Every service you enable, firewall rule you punch through, account you create, or registry key you touch gets logged with a risk score, operator attribution, and cleanup status. At the end of the engagement you have a complete audit trail of what was changed and what still needs to be cleaned up.


Why

Red team engagements leave artifacts. Services get enabled, accounts get created, firewall rules get opened, registry keys get modified. Without a structured log these are easy to forget — especially across long engagements or when multiple operators are working simultaneously.

Ledger gives you a running journal with:

  • Risk scoring per entry and per host
  • Cleanup tracking so nothing gets left behind
  • Per-operator attribution via the Cobalt Strike event log
  • Export to JSON or plain text for after-action reports
  • Automatic dead-beacon warnings when uncleaned changes are still pending

Installation

  1. Copy ledger.cna to your Cobalt Strike scripts directory.
  2. In the menu bar: Cobalt Strike → Script Manager → Load → select ledger.cna.
  3. A Ledger menu will appear in the menu bar.
  4. The dirty alias is now available in every Beacon console.

Usage

All commands run from a Beacon console using the dirty alias.


Log a change (no execution)

dirty <CATEGORY> <command> [comment] [score]

comment and score are optional. If omitted, sensible defaults are used based on the category.

dirty RPC "sql-enablerpc lon-db-1 lon-db-2"
dirty DEFENDER "add-exclusion C:\windows\temp" "Payload staging" 8
dirty GROUP "net group 'Domain Admins' svc_backup /add /domain"
dirty USER "net user backdoor P@ssw0rd! /add"
dirty SCHEDULED_TASK "schtasks /create /tn updater /tr C:\temp\beacon.exe /sc onlogon"
image

Execute and log in one step

dirty exec <CATEGORY> <command> [comment] [score]

Logs the change and immediately executes the command on the beacon — one step instead of two.

dirty exec RPC "sql-enablerpc lon-db-1 lon-db-2"
dirty exec USER "net user backdoor P@ssw0rd! /add"
dirty exec DEFENDER "sc config WinDefend start= disabled"
dirty exec FIREWALL "netsh advfirewall set allprofiles state off"

Limitations of dirty exec

dirty exec uses brun internally, which executes a binary directly without a cmd.exe /c wrapper. This means:

  • Works for real executables: net, sc, reg, nltest, whoami, ipconfig, etc.
  • Does not work for Beacon built-ins: sleep, cd, ls, pwd, download, upload, execute-assembly, inject, etc. For those, run the Beacon command normally and use dirty <CATEGORY> <command> separately to log it.
  • Does not work for shell built-ins that require cmd.exe: dir, echo, set, type, pipes (|), redirects (>), etc. Log those manually with dirty CATEGORY "shell <command>".
  • Custom BOF aliases loaded from other .cna files will not dispatch correctly through dirty exec.

View the journal

dirty show
dirty show DEFENDER
dirty show DESKTOP-ABC123

Shows all logged entries. The optional filter matches against command, comment, category, hostname, and username.

image

Score summary

dirty score

Shows a per-host risk summary with aggregate score, pending cleanup count, and a visual bar. Hosts are sorted highest score first.


Mark entries as cleaned

dirty clean <id>
dirty clean all
dirty clean host <hostname>

Hostname matching is case-insensitive and supports partial matches — DESKTOP matches DESKTOP-FGN4LPG.


Export

dirty export text
dirty export json
dirty export text DEFENDER
dirty export json DESKTOP-ABC

Exports are written to the directory containing ledger.cna and include a host score summary at the top followed by the full change log. The Ledger menu bar buttons trigger unfiltered exports directly.


Help

dirty help

Categories and Default Scores

Category Default Score Default Comment
REGISTRY 2 Registry modified
FIREWALL 3 Firewall rule modified
SERVICE 3 Service configuration changed
RPC 4 Changes in RPC made
WINRM 4 WinRM enabled
SMB 4 SMB signing changed
DCOM 4 DCOM enabled
RDP 5 RDP enabled
SCHEDULED_TASK 5 Scheduled task created
DEFENDER 6 Defender configuration changed
GROUP 6 Group membership modified
USER 7 User account modified
ACL 8 ACL modified
SPN 8 SPN modified
DOMAIN_ADMIN 9 Domain admin group modified
TRUST 9 Trust relationship modified

Any unlisted category is accepted with a default score of 3.


Risk Thresholds

Per entry

Label Score
LOW < 5
MEDIUM 5 – 7
HIGH 8+

Aggregate (per host)

Label Score
LOW < 5
MEDIUM 5 – 9
HIGH 10 – 14
CRITICAL 15+

Dead Beacon Warning

When a beacon goes dead with uncleaned ledger entries still pending, Ledger fires a red warning to the Cobalt Strike Event Log visible to all connected operators:

image

The warning fires once per beacon and resets automatically if the beacon recovers and checks in again. Linked (child) beacons and beacons explicitly killed by an operator are excluded. Warning timing scales with the beacon's sleep setting — a 60s sleep triggers after ~2 minutes, a 5m sleep after ~10 minutes.


Export Format

Text

LEDGER EXPORT -- 2026-05-21 19:50:34

HOST SCORE SUMMARY
================================================================================
Host  Risk  Score  Pending  Bar
--------------------------------------------------------------------------------
DESKTOP-RLP4KBJ (sally *)  CRITICAL  +21  2 pend  [##########]
DESKTOP-FGN4LPG (Admin)  CRITICAL  +18  0 pend  [#########]
================================================================================

CHANGE LOG
================================================================================

[000002] 2026-05-21 19:22:56 | neo | GROUP | MEDIUM +6 | CLEANED
  Host          : DESKTOP-FGN4LPG
  User          : Admin
  Process       : HTTP Listener_x64.exe (PID 4716)
  Command       : net group 'Domain Admins' svc_backup /add /domain
  Comment       : Added svc_backup to Domain Admins for lateral movement

JSON

{
  "exported":    "2026-05-21 19:53:19",
  "host_summary": [
    {
      "host":    "DESKTOP-FGN4LPG (Admin)",
      "risk":    "CRITICAL",
      "score":   18,
      "pending": 0
    },
    {
      "host":    "DESKTOP-RLP4KBJ (sally *)",
      "risk":    "CRITICAL",
      "score":   21,
      "pending": 2
    }
  ],
  "entries": [
  {
    "id":             "000004",
    "timestamp":      "2026-05-21 19:31:36",
    "operator":       "neo",
    "beacon_id":      "1607712302",
    "computer":       "DESKTOP-RLP4KBJ",
    "beacon_user":    "sally *",
    "beacon_process": "HTTP Listener_x64.exe (PID 11540)",
    "functionality":  "USER",
    "command":        "net user svc_backup P@ssw0rd123! /add /domain",
    "comment":        "Created service account for persistence",
    "score":          7,
    "risk":           "MEDIUM",
    "cleaned":        false
  }

Multi-Operator Usage

Every logged and cleaned entry is broadcast to the Cobalt Strike Event Log via elog, so all connected operators see each other's changes in real time. The journal lives in teamserver memory for the duration of the session.


Notes

  • The journal is in-memory only and does not persist across teamserver restarts. Export before shutting down.
  • Exports are written to the directory containing ledger.cna.
  • Score overrides are supported: dirty USER "net user ..." "my comment" 9 — the final argument sets an explicit score.
  • Loading the script twice (e.g. once via Script Manager and once manually) will register duplicate event handlers. Check Script Manager if you see doubled output.

About

An aggressor script that tracks operational changes made during a red team engagement. Gives you a full audit trail of what was changed and what still needs to be cleaned up.

Topics

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors