reverse-skills-max: initial public release (restored, redacted, hardened)
This commit is contained in:
@@ -0,0 +1,9 @@
|
||||
Apache License 2.0 — see the repository root LICENSE file for the full text.
|
||||
|
||||
Copyright the AnalystAIPack contributors.
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
@@ -0,0 +1,89 @@
|
||||
---
|
||||
name: analyzing-rat-command-and-control
|
||||
description: 'Analyzes remote access trojan command-and-control by mapping the RAT command set,
|
||||
identifying the C2 transport and beacon parameters, and cataloging operator capabilities from
|
||||
static strings and config. Activates for requests to analyze RAT C2, map a trojan command
|
||||
handler, or identify remote-access capabilities and C2 transport.'
|
||||
domain: cybersecurity
|
||||
subdomain: malware-analysis
|
||||
tags:
|
||||
- malware-analysis
|
||||
- rat
|
||||
- command-and-control
|
||||
- c2
|
||||
- capability-mapping
|
||||
version: 1.0.0
|
||||
author: analyst-ai-pack
|
||||
license: Apache-2.0
|
||||
mitre_attack:
|
||||
- T1219
|
||||
- T1071
|
||||
- T1105
|
||||
d3fend:
|
||||
- D3-NTA
|
||||
- D3-SDA
|
||||
references:
|
||||
- 'MITRE ATT&CK T1219 Remote Access Software — https://attack.mitre.org/techniques/T1219/'
|
||||
- 'MITRE ATT&CK T1071 Application Layer Protocol — https://attack.mitre.org/techniques/T1071/'
|
||||
---
|
||||
|
||||
# Analyzing RAT Command and Control
|
||||
|
||||
## When to Use
|
||||
|
||||
- You have a RAT sample and need to map its command set (shell, file ops, screenshot, keylog,
|
||||
webcam, proxy), C2 transport, and beacon parameters.
|
||||
- You are cataloging operator capabilities for detection and impact assessment.
|
||||
|
||||
**Do not use** this to operate the RAT or connect to its C2 — characterize capabilities from inert
|
||||
static analysis.
|
||||
|
||||
## Prerequisites
|
||||
|
||||
- The RAT sample (read inertly), optionally with an extracted config.
|
||||
|
||||
## Safety & Handling
|
||||
|
||||
- Read bytes statically; defang C2 endpoints; never connect to the C2.
|
||||
|
||||
## Workflow
|
||||
|
||||
### Step 1: Map command handlers and capabilities
|
||||
|
||||
```bash
|
||||
python scripts/analyst.py profile sample.bin
|
||||
```
|
||||
|
||||
Matches command-keyword and API patterns for capability classes: remote shell, file transfer,
|
||||
screenshot/keylog/webcam, persistence, proxy/relay, and self-update.
|
||||
|
||||
### Step 2: Identify the C2 transport
|
||||
|
||||
Detect HTTP(S), raw TCP, TLS, DNS, or messaging-platform transport from imports/strings, plus
|
||||
beacon intervals/user-agents where present.
|
||||
|
||||
### Step 3: Build the capability matrix
|
||||
|
||||
Summarize capabilities and transport, mapping to ATT&CK.
|
||||
|
||||
### Step 4: Defang and report
|
||||
|
||||
Defang endpoints and produce IOCs.
|
||||
|
||||
## Validation
|
||||
|
||||
- Capabilities are grouped into classes with the matched evidence.
|
||||
- The C2 transport is identified from concrete imports/strings.
|
||||
- Findings map to ATT&CK T1219/T1071.
|
||||
|
||||
## Pitfalls
|
||||
|
||||
- Generic API presence (e.g., `gdi32`) misread as screenshot capability — corroborate with command
|
||||
handlers.
|
||||
- Commodity RAT builders sharing strings across families — avoid over-attribution.
|
||||
- Encrypted command sets requiring config decryption first.
|
||||
|
||||
## References
|
||||
|
||||
- See [`references/api-reference.md`](references/api-reference.md) for the profiler.
|
||||
- ATT&CK T1219 and T1071 (linked in frontmatter).
|
||||
@@ -0,0 +1,37 @@
|
||||
# API Reference: Analyzing RAT Command and Control
|
||||
|
||||
## Overview
|
||||
|
||||
`scripts/analyst.py` extracts strings from a RAT and maps them to capability classes (remote shell,
|
||||
file ops, surveillance, persistence, proxy/relay, self-update, credential theft) and C2 transports
|
||||
(HTTP, raw TCP, TLS, DNS, messaging), defanging C2 URLs. It reads bytes statically and executes
|
||||
nothing.
|
||||
|
||||
## Dependencies
|
||||
|
||||
| Package | Version | Purpose |
|
||||
|---------|---------|---------|
|
||||
| (stdlib) | — | regex, JSON, file IO |
|
||||
|
||||
## Core functions
|
||||
|
||||
### `profile(path)`
|
||||
Returns grouped capabilities, C2 transports, defanged C2 URLs, and a RAT-likelihood flag
|
||||
(≥3 capability classes).
|
||||
|
||||
## Capability classes
|
||||
|
||||
remote_shell, file_operations, surveillance (screenshot/keylog/webcam/audio), persistence,
|
||||
proxy_relay, self_update, credential_theft.
|
||||
|
||||
## Usage
|
||||
|
||||
```bash
|
||||
python scripts/analyst.py profile sample.bin
|
||||
```
|
||||
|
||||
## Sources
|
||||
|
||||
- MITRE ATT&CK T1219 Remote Access Software — https://attack.mitre.org/techniques/T1219/
|
||||
- MITRE ATT&CK T1071 Application Layer Protocol — https://attack.mitre.org/techniques/T1071/
|
||||
- RAT capability/command-handler patterns from public family analyses
|
||||
@@ -0,0 +1,81 @@
|
||||
#!/usr/bin/env python3
|
||||
"""Profile a RAT's capabilities and C2 transport from static strings.
|
||||
|
||||
Extracts ASCII/UTF-16LE strings and maps them to capability classes (remote shell, file ops,
|
||||
surveillance, persistence, proxy, self-update) and C2 transports (HTTP, TCP, TLS, DNS, messaging).
|
||||
Reads bytes statically, defangs endpoints, and executes nothing.
|
||||
"""
|
||||
from __future__ import annotations
|
||||
|
||||
import argparse
|
||||
import json
|
||||
import re
|
||||
import sys
|
||||
from pathlib import Path
|
||||
|
||||
ASCII_RE = re.compile(rb"[\x20-\x7e]{4,}")
|
||||
UTF16_RE = re.compile(rb"(?:[\x20-\x7e]\x00){4,}")
|
||||
RE_URL = re.compile(r"https?://[^\s\"'<>]+", re.I)
|
||||
|
||||
CAPABILITIES = {
|
||||
"remote_shell": ["cmd.exe", "/c ", "createprocess", "shell", "winexec", "system32\\cmd"],
|
||||
"file_operations": ["upload", "download", "getfile", "putfile", "createfile", "deletefile",
|
||||
"findfirstfile"],
|
||||
"surveillance": ["screenshot", "bitblt", "getdc", "keylog", "getasynckeystate",
|
||||
"setwindowshook", "webcam", "capgetdriverdescription", "waveinopen"],
|
||||
"persistence": ["currentversion\\run", "schtasks", "createservice", "startup"],
|
||||
"proxy_relay": ["socks", "proxy", "relay", "portforward", "reverse"],
|
||||
"self_update": ["update", "selfdelete", "rename", "newversion"],
|
||||
"credential_theft": ["cryptunprotectdata", "vault", "password", "credential"],
|
||||
}
|
||||
|
||||
TRANSPORTS = {
|
||||
"http": ["wininet", "winhttp", "httpsendrequest", "internetopen", "user-agent"],
|
||||
"tcp_raw": ["ws2_32", "wsasocket", "connect", "recv", "send"],
|
||||
"tls": ["schannel", "ssl_", "tls", "openssl"],
|
||||
"dns": ["dnsquery", "dns_", "txt record"],
|
||||
"messaging": ["api.telegram.org", "discord", "pastebin", "steamcommunity"],
|
||||
}
|
||||
|
||||
|
||||
def _strings(data: bytes) -> str:
|
||||
parts = [m.decode("ascii", "ignore") for m in ASCII_RE.findall(data)]
|
||||
parts += [m.decode("utf-16-le", "ignore") for m in UTF16_RE.findall(data)]
|
||||
return "\n".join(parts)
|
||||
|
||||
|
||||
def _defang(s: str) -> str:
|
||||
return s.replace("http", "hxxp").replace(".", "[.]")
|
||||
|
||||
|
||||
def profile(path: str) -> dict:
|
||||
blob = _strings(Path(path).read_bytes())
|
||||
low = blob.lower()
|
||||
caps = {c: sorted({n for n in needles if n in low})
|
||||
for c, needles in CAPABILITIES.items()}
|
||||
caps = {c: hits for c, hits in caps.items() if hits}
|
||||
transports = {t: sorted({n for n in needles if n in low})
|
||||
for t, needles in TRANSPORTS.items()}
|
||||
transports = {t: hits for t, hits in transports.items() if hits}
|
||||
urls = sorted({_defang(u) for u in RE_URL.findall(blob)})[:50]
|
||||
return {
|
||||
"capabilities": caps,
|
||||
"c2_transports": transports,
|
||||
"c2_urls": urls,
|
||||
"capability_count": len(caps),
|
||||
"is_likely_rat": len(caps) >= 3,
|
||||
}
|
||||
|
||||
|
||||
def main(argv: list[str] | None = None) -> int:
|
||||
parser = argparse.ArgumentParser(description="Profile RAT C2/capabilities")
|
||||
sub = parser.add_subparsers(dest="cmd", required=True)
|
||||
p = sub.add_parser("profile")
|
||||
p.add_argument("file")
|
||||
args = parser.parse_args(argv)
|
||||
print(json.dumps(profile(args.file), indent=2))
|
||||
return 0
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
sys.exit(main())
|
||||
Reference in New Issue
Block a user