代码之家  ›  专栏  ›  技术社区  ›  E. Williams

Python中的数据包嗅探器

  •  2
  • E. Williams  · 技术社区  · 8 年前

    我想用Python3.5做一个包嗅探器,它捕获UDP、TCP和ICMP。这是一个简短的例子:

     import socket
     import struct
    
    # the public network interface
    HOST = socket.gethostbyname(socket.gethostname())
    # create a raw socket and bind it to the public interface
    s = socket.socket(socket.AF_INET, socket.SOCK_RAW, socket.IPPROTO_IP)
    
    s.bind((HOST,0))
    
    # Include IP headers
    s.setsockopt(socket.IPPROTO_IP, socket.IP_HDRINCL, 1)
    
    # receive all packages
    s.ioctl(socket.SIO_RCVALL, socket.RCVALL_ON)
    
    # receive a package
    n=1
    while(n<=400):
        print('Number ', n)
        data=s.recvfrom(65565)
        packet=data[0]
        address= data[1]
        header=struct.unpack('!BBHHHBBHBBBBBBBB', packet[:20])
        if(header[6]==6): #header[6] is the field of the Protocol
            print("Protocol = TCP")
        elif(header[6]==17):
            print("Protocol = UDP")
        elif(header[5]==1):
            print("Protocol = ICMP") 
        n=n+1
    

    问题是它只捕获UDP数据包:( 输出:

    Number  1 Protocol = UDP Number  2 Protocol = UDP Number  3 Protocol = UDP Number  4 Protocol = UDP Number  5 Protocol = UDP Number  6 Protocol = UDP Number  7
    

    有两个选项:

    • 嗅探器只能捕获UDP数据包。
    • 我正在接收UDP数据包。

    我认为最合理的答案是我的嗅探器不能正常工作,它只是捕获UDP。知道吗?

    2 回复  |  直到 8 年前
        1
  •  4
  •   Dartmouth    7 年前

    我自己正处于创建python数据包分析器/嗅探器的阶段,在我的研究中我发现,为了能够解析所有传入的数据包,如TCP、ICMP、UDP、ARP等,您不能使用以下套接字类型,因为 socket.IPPROTO_IP 只发出IP数据包,是一个虚拟协议

    s = socket.socket(socket.AF_INET, socket.SOCK_RAW, socket.IPPROTO_IP)
    

    相反,您必须使用它,并且在Linux系统上工作得最好

    s = socket.socket( socket.AF_PACKET , socket.SOCK_RAW , socket.ntohs(0x0003))
    
        2
  •  1
  •   Luis Zorzano    6 年前

    您正在使用“gethostbyname”,此方法在计算机中的所有ip地址之间获取一个地址。 代替此方法,您必须使用“gethostbyname_ex”来获取包含多个addrese的列表。您必须选择用于浏览器的地址,然后将捕获TCP、UDP和ICMP数据包。