You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用PyShark捕获数据包时如何打印全部协议类型(含ICMP、ARP等)

解决PyShark捕获全类型协议数据包的问题

你的代码只能获取TCP/UDP,是因为packet.transport_layer仅针对传输层协议,像ARP(数据链路层)、ICMP(网络层)这类非传输层协议会被忽略,甚至直接报错(比如ARP包没有ip层,ICMP包没有传输层端口)。下面是修正后的代码,能识别并打印ARP、ICMP、TCP、UDP等常见协议:

首先补上缺失的time模块导入,然后通过判断数据包的层级来适配不同协议:

import pyshark
import time

capture = pyshark.LiveCapture(interface='eth0')
capture.sniff(timeout=50)

for packet in capture.sniff_continuously():
    localtime = time.asctime(time.localtime(time.time()))
    protocol = ""
    src_addr = ""
    src_port = ""
    dst_addr = ""
    dst_port = ""

    # 处理ARP协议(数据链路层)
    if hasattr(packet, 'arp'):
        protocol = "ARP"
        src_addr = packet.arp.src_proto_ipv4
        dst_addr = packet.arp.dst_proto_ipv4
    # 处理ICMP协议(网络层)
    elif hasattr(packet, 'icmp'):
        protocol = "ICMP"
        src_addr = packet.ip.src
        dst_addr = packet.ip.dst
    # 处理TCP/UDP协议(传输层)
    elif packet.transport_layer:
        protocol = packet.transport_layer
        src_addr = packet.ip.src
        src_port = packet[packet.transport_layer].srcport
        dst_addr = packet.ip.dst
        dst_port = packet[packet.transport_layer].dstport
    # 其他协议(可选:打印未匹配的层信息)
    else:
        layer_names = [layer.layer_name for layer in packet.layers]
        protocol = f"OTHER ({'/'.join(layer_names)})"

    # 打印结果,空字段自动留空
    print(f"{localtime}\t{protocol}\t{src_addr}\t{src_port}\t{dst_addr}\t{dst_port}")

关键修改点说明:

  • 用hasattr()判断数据包是否包含某层(比如ARP、ICMP),避免不存在该层时抛出异常
  • 针对不同协议的字段结构,分别获取源/目标地址、端口(非传输层协议没有端口,自然留空)
  • 增加了"OTHER"分支,用于捕获未明确处理的协议,可通过遍历packet.layers查看所有层级的协议名

内容的提问来源于stack exchange,提问作者user20828450

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.07 22:05:17