2017-06-01 2 views
2

を使用してUDPトラフィックを送信します。各UDPパケットを受信するとスニフと私はPythonでパケットスニッファを実装するには、以下のチュートリアルを追っScapy

http://www.binarytides.com/python-packet-sniffer-code-linux/

すると、私はすでに保存されたのpcapファイルを送信したいと思います(テスト.pcap)。次のスニペットは、私の実装を示しています

# receive a packet 
while True: 
    packet = s.recvfrom(65565) 

    #packet string from tuple 
    packet = packet[0] 

    #parse ethernet header 
    eth_length = 14 

    eth_header = packet[:eth_length] 
    eth = unpack('!6s6sH' , eth_header) 
    eth_protocol = socket.ntohs(eth[2]) 
    print 'Destination MAC : ' + eth_addr(packet[0:6]) + ' Source MAC : ' + 
    eth_addr(packet[6:12]) + ' Protocol : ' + str(eth_protocol) 

    if eth_addr(packet[6:12]) != my_MAC_address: 

     #Parse IP packets, IP Protocol number = 8 
     if eth_protocol == 8 : 
     #Parse IP header 
     #take first 20 characters for the ip header 
     ip_header = packet[eth_length:20+eth_length] 

     #now unpack them :) 
     iph = unpack('!BBHHHBBH4s4s' , ip_header) 

     version_ihl = iph[0] 
     version = version_ihl >> 4 
     ihl = version_ihl & 0xF 

     iph_length = ihl * 4 

     ttl = iph[5] 
     protocol = iph[6] 
     s_addr = socket.inet_ntoa(iph[8]); 
     d_addr = socket.inet_ntoa(iph[9]); 

     print 'Version : ' + str(version) + ' IP Header Length : ' + str(ihl) + ' TTL : ' + str(ttl) + ' Protocol : ' + str(protocol) + ' Source Address : ' + str(s_addr) + ' Destination Address : ' + str(d_addr) 


     #UDP packets 
     if protocol == 17 : 
     u = iph_length + eth_length 
     udph_length = 8 
     udp_header = packet[u:u+8] 

     #now unpack them :) 
     udph = unpack('!HHHH' , udp_header) 

     source_port = udph[0] 
     dest_port = udph[1] 
     length = udph[2] 
     checksum = udph[3] 

     print 'Source Port : ' + str(source_port) + ' Dest Port : ' + str(dest_port) + ' Length : ' + str(length) + ' Checksum : ' + str(checksum) 

     h_size = eth_length + iph_length + udph_length 
     data_size = len(packet) - h_size 

     #get data from the packet 
     data = packet[h_size:] 

     print 'Data : ' + data 
     my_pkt = rdpcap("test.pcap") 
     sendp(my_pkt) 

Test.pcapはUDP_src = 7777とUDP_dest = 9999とUDPパケットが含まれています。

トラフィックは次のようにnetcatをを用いて生成される:

nc -u -p 7777 ip_dst_addr 9999 

スニファは、第一のnetcatのMSGを受信し、応答してtest.pcap送信することができます。しかし、その後のnetcat msgはまったく受信されません。しかし、netcatのUDPポートの他の組み合わせを使用すると、スニッファはうまく動作します。 netcatを実行している:例えば

nc -u -p 8888 ip_dst_addr 9999 

問題なしと私は、各UDPパケット/ MSGに応じてtest.pcapを送信することができています。

ご協力いただければ幸いです!

答えて

2

Scapyにはいくつかのビルトインスニッファがあり、これは本当に使いやすいものです。

>>> help(sniff) 
Help on function sniff in module scapy.arch.windows.compatibility: 

sniff(count=0, store=1, offline=None, prn=None, stop_filter=None, lfilter=None, L2socket=None, timeout=None, *arg, **karg) 
    Sniff packets 
    sniff([count=0,] [prn=None,] [store=1,] [offline=None,] [lfilter=None,] + L2ListenSocket args) -> list of packets 
    Select interface to sniff by setting conf.iface. Use show_interfaces() to see interface names. 
     count: number of packets to capture. 0 means infinity 
     store: whether to store sniffed packets or discard them 
     prn: function to apply to each packet. If something is returned, 
      it is displayed. Ex: 
      ex: prn = lambda x: x.summary() 
    filter: provide a BPF filter 
    lfilter: python function applied to each packet to determine 
      if further action may be done 
      ex: lfilter = lambda x: x.haslayer(Padding) 
    offline: pcap file to read packets from, instead of sniffing them 
    timeout: stop sniffing after a given time (default: None) 
    L2socket: use the provided L2socket 
    stop_filter: python function applied to each packet to determine 
       if we have to stop the capture after this packet 
       ex: stop_filter = lambda x: x.haslayer(TCP) 

あなたは、単に行うことができますを意味し、どの:

packets = rdpcap("test.pcap") 
sniff(lfilter=lambda x: x.haslayer(UDP) and x[Ether].src==sending_mac and x[UDP].sport==port, prn=lambda x: send(packets)) 

これはtest.pcapファイルにすべてのUDPパケットを追加します

+0

おかげで、あなたの実装がはるかに簡単です。 しかし、クライアントのmsgと同じudpポートを使用してtest.pcapを送信すると、スニッファはパケットをスニッフィングできません。 :/ – user112333

+0

送信したパケットを盗聴しますか?それ以外の場合は動作するはずです:/あなたの問題を本当に理解していない – Cukic0d

+0

私はスニファの発信pktsを盗聴したくありません。そのため、次のif条件があります。 eth_addr(パケット[6:12])!= my_MAC_address パケットの種類は2種類あります。 1)私が盗聴したいと思うリクエスト。これはnetcatを使って生成することができます。 UDP_src = 7777、UDP_dst = 9999 2)ここではtest.pcapという応答です。私は応答パケットをスニッフィングしたくありません。 test.pcapには、UDP_src = 7777とUDP_dst = 9999のUDPパケットが1つ含まれています。 最初のリクエストを受け取った時点で、私はtest.pcapを送信できます。 UDP_src = 7777、UDP_dst = 9999 – user112333

関連する問題