Add folder anatomy (scripts/agent.py + references/api-reference.md) for 648 cybersecurity skills

Complete skill folder anatomy across all cybersecurity skills:
- scripts/agent.py: 80-150 line Python agents using real libraries (impacket,
  boto3, azure-mgmt-*, kubernetes, pefile, yara, scapy, shodan, stix2, etc.)
- references/api-reference.md: real API documentation with method signatures
- LICENSE: MIT license for all skill folders
This commit is contained in:
mukul975
2026-03-10 21:02:12 +01:00
parent c74d52fa30
commit 27c6414ca5
1390 changed files with 106806 additions and 0 deletions
@@ -0,0 +1,21 @@
MIT License
Copyright (c) 2025 Anthropic Agent Skills Contributors
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
@@ -0,0 +1,66 @@
# API Reference: Detecting Network Scanning with IDS Signatures
## Scan Types and Detection
| Scan Type | Method | Detection |
|-----------|--------|-----------|
| SYN Scan | Half-open SYN packets | Many SYN without ACK |
| Connect Scan | Full TCP handshake | Many connections, short duration |
| Host Sweep | Same port, many hosts | Single port, >10 destinations |
| Service Enum | Banner grabbing | Short-lived connections |
## Suricata EVE JSON Format
```json
{
"event_type": "alert",
"src_ip": "10.0.0.5",
"dest_ip": "192.168.1.100",
"alert": {
"signature": "ET SCAN Nmap SYN Scan",
"category": "Attempted Information Leak",
"severity": 2,
"signature_id": 2000001
}
}
```
## Suricata Scan Detection Rules
```
alert tcp any any -> $HOME_NET any (msg:"Port Scan Detected"; \
flags:S; threshold:type both, track by_src, count 25, seconds 60; \
sid:5000001;)
```
## Zeek conn.log Fields
```
#fields ts uid id.orig_h id.orig_p id.resp_h id.resp_p proto service
duration orig_bytes resp_bytes conn_state
```
## Detection Thresholds
| Metric | Threshold | Severity |
|--------|-----------|----------|
| Unique ports per destination | >20 | HIGH |
| Unique ports >100 | >100 | CRITICAL |
| Hosts per single port sweep | >10 | MEDIUM |
| Hosts >50 | >50 | HIGH |
## Splunk SPL Detection
```spl
index=network
| stats dc(dest_port) as unique_ports by src_ip, dest_ip
| where unique_ports > 20
| sort -unique_ports
```
## CLI Usage
```bash
python agent.py --eve-log eve.json
python agent.py --conn-log conn.log --port-threshold 25 --sweep-threshold 15
```
@@ -0,0 +1,172 @@
#!/usr/bin/env python3
"""Network scanning detection agent using IDS signature analysis.
Detects port scanning, host sweeps, and service enumeration by analyzing
Suricata/Snort alerts and connection logs for scanning patterns.
"""
import argparse
import json
import re
import sys
from collections import Counter, defaultdict
from datetime import datetime
SCAN_SIGNATURES = {
"SYN_SCAN": {"ports_threshold": 20, "severity": "HIGH", "mitre": "T1046"},
"CONNECT_SCAN": {"ports_threshold": 15, "severity": "HIGH", "mitre": "T1046"},
"UDP_SCAN": {"ports_threshold": 20, "severity": "MEDIUM", "mitre": "T1046"},
"XMAS_SCAN": {"severity": "HIGH", "mitre": "T1046"},
"FIN_SCAN": {"severity": "HIGH", "mitre": "T1046"},
"NULL_SCAN": {"severity": "HIGH", "mitre": "T1046"},
"HOST_SWEEP": {"hosts_threshold": 10, "severity": "MEDIUM", "mitre": "T1018"},
"SERVICE_ENUM": {"severity": "MEDIUM", "mitre": "T1046"},
}
NMAP_SIGNATURES = [
r"Nmap\s+Scripting\s+Engine", r"nmap", r"masscan",
r"zmap", r"rustscan", r"unicornscan",
]
def parse_suricata_eve(filepath, event_type="alert"):
events = []
with open(filepath, "r") as f:
for line in f:
try:
evt = json.loads(line.strip())
if evt.get("event_type") == event_type:
events.append(evt)
except json.JSONDecodeError:
continue
return events
def parse_connection_log(filepath):
connections = []
with open(filepath, "r") as f:
headers = None
for line in f:
if line.startswith("#fields"):
headers = line.strip().split("\t")[1:]
continue
if line.startswith("#"):
continue
if not headers:
continue
fields = line.strip().split("\t")
if len(fields) >= len(headers):
connections.append(dict(zip(headers, fields)))
return connections
def detect_port_scan(connections, threshold=20):
findings = []
src_dst_ports = defaultdict(set)
src_dst_count = defaultdict(int)
for conn in connections:
src = conn.get("id.orig_h", "")
dst = conn.get("id.resp_h", "")
port = conn.get("id.resp_p", "")
state = conn.get("conn_state", "")
src_dst_ports[f"{src}->{dst}"].add(port)
src_dst_count[f"{src}->{dst}"] += 1
for pair, ports in src_dst_ports.items():
if len(ports) >= threshold:
src = pair.split("->")[0]
dst = pair.split("->")[1]
findings.append({
"type": "port_scan",
"source": src, "destination": dst,
"unique_ports": len(ports),
"total_connections": src_dst_count[pair],
"severity": "CRITICAL" if len(ports) > 100 else "HIGH",
"mitre": "T1046",
})
return findings
def detect_host_sweep(connections, threshold=10):
findings = []
src_dsts = defaultdict(set)
src_port = defaultdict(set)
for conn in connections:
src = conn.get("id.orig_h", "")
dst = conn.get("id.resp_h", "")
port = conn.get("id.resp_p", "")
src_dsts[src].add(dst)
src_port[f"{src}:{port}"].add(dst)
for src_p, hosts in src_port.items():
if len(hosts) >= threshold:
src, port = src_p.rsplit(":", 1)
findings.append({
"type": "host_sweep",
"source": src,
"port": port,
"unique_hosts": len(hosts),
"severity": "HIGH" if len(hosts) > 50 else "MEDIUM",
"mitre": "T1018",
})
return findings
def analyze_ids_alerts(alerts):
findings = []
for alert in alerts:
sig = alert.get("alert", {}).get("signature", "")
category = alert.get("alert", {}).get("category", "")
src = alert.get("src_ip", "")
dst = alert.get("dest_ip", "")
severity = alert.get("alert", {}).get("severity", 3)
for pattern in NMAP_SIGNATURES:
if re.search(pattern, sig, re.IGNORECASE):
findings.append({
"type": "scanner_detected",
"tool": pattern.replace("\\s+", " "),
"source": src, "destination": dst,
"signature": sig,
"severity": "HIGH",
"mitre": "T1046",
})
if "scan" in category.lower() or "scan" in sig.lower():
findings.append({
"type": "ids_scan_alert",
"source": src, "destination": dst,
"signature": sig, "category": category,
"severity": "HIGH" if severity <= 2 else "MEDIUM",
})
return findings
def main():
parser = argparse.ArgumentParser(description="Network Scanning Detector")
parser.add_argument("--eve-log", help="Suricata EVE JSON log")
parser.add_argument("--conn-log", help="Zeek conn.log file")
parser.add_argument("--port-threshold", type=int, default=20)
parser.add_argument("--sweep-threshold", type=int, default=10)
args = parser.parse_args()
results = {"timestamp": datetime.utcnow().isoformat() + "Z", "findings": []}
if args.eve_log:
alerts = parse_suricata_eve(args.eve_log)
results["findings"].extend(analyze_ids_alerts(alerts))
if args.conn_log:
connections = parse_connection_log(args.conn_log)
results["findings"].extend(detect_port_scan(connections, args.port_threshold))
results["findings"].extend(detect_host_sweep(connections, args.sweep_threshold))
results["total_findings"] = len(results["findings"])
print(json.dumps(results, indent=2))
if __name__ == "__main__":
main()