恶意软件网络流量分析 是做什么的?
适用场景
- 沙箱执行已捕获PCAP文件,需要对网络行为进行详细分析
- 识别C2协议结构,用于编写网络检测签名
- 确定恶意软件外泄了哪些数据以及发送至哪个外部基础设施
- 分析DNS隧道、域名生成算法(DGA)或快速通量(fast-flux)行为
- 根据观察到的恶意软件网络模式创建Suricata/Snort签名
请勿用于基于主机的恶意软件行为分析;如需进程级活动分析,请使用Cuckoo沙箱报告或Volatility内存分析。
前置条件
- 已安装Wireshark 4.x,用于交互式PCAP分析
- tshark(Wireshark CLI),用于脚本化数据包提取
- 已安装Zeek,用于从PCAP自动生成元数据
- Suricata(配合ET Open/ET Pro规则集),用于签名匹配
- NetworkMiner,用于从PCAP提取文件和检测凭据
- Python 3.8+(含
scapy和dpkt库),用于程序化数据包分析
工作流
步骤1:初始PCAP概览
获取网络流量的高层次理解:
# 捕获统计信息
capinfos malware.pcap
# 协议层级
tshark -r malware.pcap -q -z io,phs
# 端点统计(主要通信对端)
tshark -r malware.pcap -q -z endpoints,ip
# 会话统计
tshark -r malware.pcap -q -z conv,tcp
# DNS查询摘要
tshark -r malware.pcap -q -z dns,tree
步骤2:分析DNS活动
检查DNS查询中是否存在DGA、隧道或C2域名解析:
# 提取所有DNS查询
tshark -r malware.pcap -T fields -e frame.time -e dns.qry.name -e dns.a \
-Y "dns.flags.response == 1" | sort
# 检测DGA模式(高熵域名)
python3 << 'PYEOF'
import math
from collections import Counter
def entropy(s):
p = [n/len(s) for n in Counter(s).values()]
return -sum(pi * math.log2(pi) for pi in p if pi > 0)
# 从tshark输出中解析DNS查询
import subprocess
result = subprocess.run(
["tshark", "-r", "malware.pcap", "-T", "fields", "-e", "dns.qry.name",
"-Y", "dns.flags.response == 0"],
capture_output=True, text=True
)
domains = set(result.stdout.strip().split('\n'))
print("可疑DNS查询(高熵):")
for domain in domains:
if domain:
subdomain = domain.split('.')[0]
ent = entropy(subdomain)
if ent > 3.5 and len(subdomain) > 10:
print(f" {domain} (熵值: {ent:.2f})")
PYEOF
# 检测DNS隧道(大型TXT响应)
tshark -r malware.pcap -T fields -e dns.qry.name -e dns.txt \
-Y "dns.resp.type == 16 and dns.resp.len > 100"
步骤3:分析HTTP/HTTPS C2通信
检查基于Web的命令与控制流量:
# 提取HTTP请求
tshark -r malware.pcap -T fields \
-e frame.time -e ip.src -e ip.dst -e http.host \
-e http.request.method -e http.request.uri -e http.user_agent \
-Y "http.request"
# 提取HTTP响应体(可能的载荷下载)
tshark -r malware.pcap -T fields \
-e http.host -e http.request.uri -e http.content_type -e tcp.len \
-Y "http.response and tcp.len > 1000"
# 提取POST数据(可能的泄漏)
tshark -r malware.pcap -T fields \
-e http.host -e http.request.uri -e http.file_data \
-Y "http.request.method == POST"
# TLS分析(SNI、JA3指纹)
tshark -r malware.pcap -T fields \
-e tls.handshake.extensions_server_name \
-e tls.handshake.ja3 \
-Y "tls.handshake.type == 1"
# 提取TLS证书详情
tshark -r malware.pcap -T fields \
-e x509ce.dNSName -e x509af.serialNumber \
-e x509sat.utf8String \
-Y "tls.handshake.type == 11"
# 导出HTTP对象(下载的文件)
tshark -r malware.pcap --export-objects http,exported_files/
步骤4:检测信标模式
识别指示C2信标的定期周期性通信:
# 从PCAP检测信标
from scapy.all import rdpcap, IP, TCP
from collections import defaultdict
import statistics
packets = rdpcap("malware.pcap")
# 按目标IP:端口对连接分组
connections = defaultdict(list)
for pkt in packets:
if IP in pkt and TCP in pkt:
if pkt[TCP].flags & 0x02: # SYN flag
dst = f"{pkt[IP].dst}:{pkt[TCP].dport}"
connections[dst].append(float(pkt.time))
# 分析时序间隔以检测信标
print("信标分析:")
for dst, times in connections.items():
if len(times) >= 5:
intervals = [times[i+1] - times[i] for i in range(len(times)-1)]
avg = statistics.mean(intervals)
stdev = statistics.stdev(intervals) if len(intervals) > 1 else 0
jitter = (stdev / avg * 100) if avg > 0 else 0
if 10 < avg < 3600 and jitter < 30: # 规则间隔且抖动小于30%
print(f" [!] {dst}: {len(times)} 次连接")
print(f" 间隔: {avg:.1f}s ± {stdev:.1f}s (抖动: {jitter:.1f}%)")
print(f" 模式: 很可能是信标")
步骤5:生成网络检测签名
根据观察到的流量模式创建Suricata/Snort规则:
# 对PCAP运行Suricata以进行现有签名匹配
suricata -r malware.pcap -l suricata_output/ -c /etc/suricata/suricata.yaml
# 查看告警
cat suricata_output/fast.log
# 根据观察到的模式创建自定义Suricata规则
cat << 'EOF' > custom_malware.rules
# 基于观察到的URI模式的C2信标检测
alert http $HOME_NET any -> $EXTERNAL_NET any (
msg:"MALWARE MalwareX C2 Beacon";
flow:established,to_server;
http.method; content:"POST";
http.uri; content:"/gate.php?id=";
http.user_agent; content:"Mozilla/5.0 (compatible; MSIE 10.0)";
sid:9000001; rev:1;
)
# 已知C2域名的DNS查询
alert dns $HOME_NET any -> any any (
msg:"MALWARE MalwareX C2 DNS Query";
dns.query; content:"update.malicious.com";
sid:9000002; rev:1;
)
# 恶意软件TLS客户端的JA3哈希匹配
alert tls $HOME_NET any -> $EXTERNAL_NET any (
msg:"MALWARE MalwareX JA3 Match";
ja3.hash; content:"a0e9f5d64349fb13191bc781f81f42e1";
sid:9000003; rev:1;
)
EOF
步骤6:从流量中提取文件和工件
恢复传输的文件和嵌入数据:
# 使用Zeek提取文件
zeek -r malware.pcap /opt/zeek/share/zeek/policy/frameworks/files/extract-all-files.zeek
ls extract_files/
# 使用NetworkMiner提取文件(GUI)
# 或使用tshark进行特定协议导出
tshark -r malware.pcap --export-objects http,http_objects/
tshark -r malware.pcap --export-objects smb,smb_objects/
tshark -r malware.pcap --export-objects tftp,tftp_objects/
# 对所有提取的文件计算哈希
sha256sum http_objects/* smb_objects/* 2>/dev/null
# 生成Zeek日志以获取全面元数据
zeek -r malware.pcap
# 输出:conn.log, dns.log, http.log, ssl.log, files.log, 等
关键概念
| 术语 | 定义 |
|---|---|
| 信标(Beaconing) | 恶意软件到C2服务器的定期周期性连接,可通过一致的时间间隔和数据包大小识别 |
| JA3/JA3S | TLS指纹方法,用于从ClientHello/ServerHello参数创建哈希,唯一标识恶意软件TLS实现 |
| DGA(域名生成算法) | 生成伪随机域名的算法,恶意软件通过查询这些域名来定位C2服务器,从而规避静态域名黑名单 |
| DNS隧道 | 将数据编码到DNS查询和响应中,通过DNS基础设施建立C2通道或泄露数据 |
| 快速通量(Fast Flux) | DNS技术,快速轮换一个域名的IP地址,以逃避封禁并将C2分布到许多被感染的主机上 |
| SNI(服务器名称指示) | TLS扩展,揭示客户端正在连接的主机名;即使在加密的HTTPS连接中也可见 |
| 网络签名 | Suricata/Snort规则,匹配网络流量中的特定模式(头部、载荷、时序),用于检测恶意通信 |
工具与系统
- Wireshark:开源数据包分析器,用于在协议层面进行深度交互式网络流量检查
- Zeek:网络分析框架,从实时或捕获的流量中生成结构化的元数据日志(conn, dns, http, ssl)
- Suricata:高性能网络IDS/IPS,支持基于签名的检测,并可通过Lua脚本实现自定义检测逻辑
- NetworkMiner:网络取证分析工具,用于从PCAP文件中提取文件、图像和凭据
- Scapy:Python数据包操作库,用于程序化数据包分析、信标检测和协议解码
常见场景
场景:解码自定义二进制C2协议
上下文:恶意软件使用自定义二进制协议,通过TCP 8443端口与其C2服务器通信。标准HTTP分析未产生结果。需要从PCAP中逆向工程协议结构。
方法:
- 过滤PCAP中TCP 8443端口的会话,并跟踪TCP流
- 识别消息帧格式(长度前缀、分隔符、固定大小头部)
- 比较多条消息,识别静态头部字段与可变数据字段
- 与逆向工程结果(如Ghidra分析二进制)交叉验证
- 为自定义协议编写Wireshark解析器或Scapy解析器
- 创建匹配静态头部字节的Suricata规则用于网络检测
- 记录完整的协议规范,用于威胁情报共享
陷阱:
- 仅分析前几个数据包;某些C2协议在初始握手后会改变行为
- 当沙箱具备MITM能力时,未解密TLS流量
- 将合法的CDN或云流量误认为C2(验证目标IP)
- 遗漏使用DNS或ICMP而非TCP/UDP的C2流量
输出格式
恶意软件网络流量分析
===================================
PCAP文件: malware_sandbox.pcap
时长: 300 秒
总数据包数: 12,847
总字节数: 4.2 MB
DNS活动
总查询数: 47
DGA检测: 是(23个高熵查询,指向.com TLD)
隧道: 否
已解析C2: update.malicious[.]com -> 185.220.101[.]42
C2通信
协议: HTTPS (TLS 1.2)
服务器: 185.220.101[.]42:443
SNI: update.malicious[.]com
JA3哈希: a0e9f5d64349fb13191bc781f81f42e1
信标间隔: 60.2s ± 6.8s (11.3% 抖动)
总会话数: 237
发送数据量: 147 MB
接收数据量: 2.3 MB
证书: CN=update.malicious[.]com (自签名,已过期)
载荷下载
GET /payload.dll 来自 compromised-site[.]com
大小:98,304 字节
SHA-256:abc123def456...
内容类型:application/octet-stream
数据外泄
方法: HTTPS POST 到 /gate.php
内容类型: application/octet-stream
平均大小: 每次请求 15,432 字节
总流量: 4小时 内 147 MB
Suricata告警
[1:2028401] ET MALWARE 通用C2信标模式
[1:2028500] ET POLICY 自签名证书
生成的签名
SID 9000001:MalwareX HTTP信标模式
SID 9000002:MalwareX DNS C2域名
SID 9000003:MalwareX JA3 TLS指纹