Skill detail
analyzing-command-and-control-communication
Relevant malware-analysis specialization, but narrow.
Inspect before use
Automated review checks relevance, not safety or endorsement. Read the source instructions before using this skill.
SKILL.md
The saved excerpt is a snapshot from review. The external source remains the complete and most current version.
---
name: analyzing-command-and-control-communication
description: 'Analyzes malware C2 communication over HTTP, HTTPS, DNS, and custom
protocols to reverse-engineer beacon patterns, command structures, data encoding,
and infrastructure (primary servers, fallback domains, dead drops). Use after
reverse engineering reveals network traffic needing protocol analysis or when
building detection signatures for a framework like Cobalt Strike, Metasploit,
or Sliver.
'
domain: cybersecurity
subdomain: malware-analysis
tags:
- malware
- C2
- command-and-control
- beacon
- protocol-analysis
version: 1.0.0
author: mahipal
license: Apache-2.0
nist_csf:
- DE.AE-02
- RS.AN-03
- ID.RA-01
- DE.CM-01
mitre_attack:
- T1071.001
- T1573
- T1571
- T1008
- T1095
---
# Analyzing Command-and-Control Communication
## When to Use
- Reverse engineering a malware sample has revealed network communication that needs protocol analysis
- Building network-level detection signatures for a specific C2 framework (Cobalt Strike, Metasploit, Sliver)
- Mapping C2 infrastructure including primary servers, fallback domains, and dead drops
- Analyzing encrypted or encoded C2 traffic to understand the command set and data format
- Attributing malware to a threat actor based on C2 infrastructure patterns and tooling
**Do not use** for general network anomaly detection; this is specifically for understanding known or suspected C2 protocols from malware analysis.
## Prerequisites
- PCAP capture of malware network traffic (from sandbox, network tap, or full packet capture)
- Wireshark/tshark for packet-level analysis
- Reverse engineering tools (Ghidra, dnSpy) for understanding C2 code in the malware binary
- Python 3.8+ with `scapy`, `dpkt`, and `requests` for protocol analysis and replay
- Threat intelligence databases for C2 infrastructure correlation (VirusTotal, Shodan, Censys)
- JA3/JA3S fingerprint databases for TLS-based C2 identification
## Workflow
### Step 1: Identify the C2 Channel
Determine the protocol and transport used for C2 communication:
```
C2 Communication Channels:
━━━━━━━━━━━━━━━━━━━━━━━━━
HTTP/HTTPS: Most common; uses standard web traffic to blend in
Indicators: Regular POST/GET requests, specific URI patterns, custom headers
DNS: Tunneling data through DNS queries and responses
Indicators: High-volume TXT queries, long subdomain names, high entropy
Custom TCP/UDP: Proprietary binary protocol on non-standard port
Indicators: Non-HTTP traffic on high ports, unknown protocol
ICMP: Data encoded in ICMP echo/reply payloads
Indicators: ICMP packets with large or non-standard payloads
WebSocket: Persistent bidirectional connection for real-time C2
Indicators: WebSocket upgrade followed by binary frames
Cloud Services: Using legitimate APIs (Telegram, Discord, Slack, GitHub)
Indicators: API calls to cloud services from unexpected processes
Email: SMTP/IMAP for C2 commands and data exfiltration
Indicators: Automated email operations from non-email processes
```
### Step 2: Analyze Beacon Pattern
Characterize the periodic communication pattern:
```python
from scapy.all import rdpcap, IP, TCP
from collections import defaultdict
import statistics
import json
packets = rdpcap("c2_traffic.pcap")
# Group TCP SYN packets by destination
connections = defaultdict(list)
for pkt in packets:
if IP in pkt and TCP in pkt and (pkt[TCP].flags & 0x02):
key = f"{pkt[IP].dst}:{pkt[TCP].dport}"
connections[key].append(float(pkt.time))
# Analyze each destination for beaconing
for dst, times in sorted(connections.items()):
if len(times) < 3:
continue
intervals = [times[i+1] - times[i] for i in range(len(times)-1)]
avg_interval = statistics.mean(intervals)
stdev = statistics.stdev(intervals) if len(intervals) > 1 else 0
jitter_pct = (stdev / avg_intRead the full source on GitHub (opens external page)