首页/网络/抓包与流量分析速查/scapy 读包做定制统计
抓包工具链61 条

scapy 读包做定制统计

需要自定义逻辑时用脚本读包:按需组合字段、统计任意分组、生成定制报表;适合命令行工具覆盖不到的口径。

scapy 读包能补什么

scapy 是 Python 的报文构造与解析库,读包时把每帧解析成带层次的对象。当 tshark 的过滤与统计字段表达不了你要的口径时——比如按自定义键分组、跨协议做关联、按业务规则判重——写几十行脚本反而比拼命令行更快。它适合一次性分析任务,不适合当作常规采集工具。

基本信息

语言与安装Python 3,pip install scapy(解析 pcap 需要 libpcap)
整体读取rdpcap 把文件读成报文列表,适合中小文件
流式读取PcapReader 逐帧迭代,内存占用与文件大小无关
写回文件wrpcap 把报文列表写回 pcap,便于裁剪样本
常用字段p[IP].src、p[TCP].dport、p[TCP].flags、p.time 等
兼容性pcapng 需对应的读取器,或先转成 pcap 再读

典型使用场景

  • 自定义统计口径:按源目网段、按业务标识分组统计次数与字节,出 tshark 给不了的报表
  • 跨协议关联:把某个请求的应答时间戳与前一层的连接事件对起来做端到端耗时
  • 样本构造:从大文件里挑出符合特征的报文子集另存,做成固定回归样本
  • 字段体检:批量检查某字段是否存在异常值,如端口为 0、TTL 为 0 的畸形包
  • 教学演示:用几行代码把报文层次打印出来,直观说明封装关系

读包与统计示例

读包与统计示例
from scapy.all import PcapReader, TCP, IP

count = 0
ports = {}
with PcapReader('a.pcap') as pr:            # 流式读取,避免一次性载入
    for p in pr:
        if IP in p and TCP in p and p[TCP].dport == 443:   # 先判层再取字段
            count += 1
            ports[p[IP].src] = ports.get(p[IP].src, 0) + 1
print('443 目标包数:', count)               # 与 tshark 口径交叉验证
print('发起端分布:', sorted(ports.items(), key=lambda kv: -kv[1])[:5])

常用接口速查

接口作用提示
rdpcap整文件读入列表大文件会占用大量内存
PcapReader逐帧迭代推荐用于大文件
wrpcap写出 pcap仅写出的报文会被重新序列化
p.time报文时间戳浮点秒,可自行做时间差
p.summary单行摘要适合快速打印排错
haslayer判断是否含某层截断包可能缺层,先判断再取值
自写脚本容易被当成权威口径,出结论前先用同一个过滤条件跑一遍 tshark 交叉核对数字,两边对得上再往上报。
抓包时设置过 snaplen 的文件里,超出截断长度的报文会缺少应用层字段,脚本必须对字段缺失做判断,否则会抛出异常或统计出偏小的数字。

易错点

  • 用 rdpcap 打开几百兆以上的文件,内存瞬间被打满,进程被系统杀掉;改用 PcapReader 逐帧处理或先用 editcap 裁剪时间段
  • 脚本里直接取 p[TCP].dport 而不先判断层级,遇到非 TCP 报文或截断报文就报错中断,长跑任务应逐条捕获异常并计数
  • 把脚本统计结果直接当结论上报,未与 tshark 口径核对,分组定义差异会放大数字偏差
  • 对截断包做字段统计而不区分,得到的平均值偏小,报告里需注明样本完整性

数据来源与参考

  • scapy 文档
​‌‌​​‌​​​‌‌​‌‌‌‌​‌‌​​​‌‌​‌‌‌​​‌‌​​‌​‌‌‌​​‌‌‌​​​‌​‌‌​‌​​‌​‌‌‌​​​‌​‌‌​‌​​‌​‌‌​​​‌‌​‌‌‌​‌​​​‌‌​‌‌‌‌​​‌​‌‌‌​​‌‌​​​‌‌​‌‌​‌‌‌‌​‌‌​‌‌​‌