• scapy模块的学习


    Scapy模块的应用

    1.输入ifconfig查找IP地址

    2.输入scapy

    • 在scapy中,每一个协议都是一个类,而建立一个变量=协议(),相当于建立这个协议的数据包。
    • 协议
    1. IP(),TCP(),UDP():用的是ipv4的地址

    2. Ether()用的是mac地址(Ether(dst=ff:ff:ff:ff:ff:ff))

      6个ff是广播地址

    广播地址(Broadcast Address)是专门用于同时向网络中所有工作站进行发送的一个地址

    ip=IP()
    ip
    #IP有两个重要的属性——源地址(src)和目的地址(dst)
    
    • dst也可以是一个IP范围:

      192.168.2.0/24表示的IP范围(共256个数据包)

      192.168.2.0换成32位二进制,四组,每组8位

      /24 表示前24位不变,后8位由全0变化到全1的过程,也就是由“00000000”变化到“11111111”
      又因为全0是子网网络地址,全1是子网广播地址,这两个地址是不分配给主机使用的。
      所以有效的可分配的范围是前24位不变,后8位由“00000001”变化为“11111110”的范围
      再转换回十进制就是192.168.2.1~192.168.2.254

    • 查看单一数据包 [x for x in 网段名]

    • 构造多层协议数据包

    Ether()/IP()/TCP() #tcp包
    IP()/TCP()/"GET/HTTP/1.0
    
    "#使其分行,易于后面的解析
    

    自底向上

    3.查看类的属性

    ls(协议名())
    

    4.发送数据包,记得开启管理员权限

    构造一个目的地址为:192.168.154.254的ICMP数据包,并发送

    send(IP(dst="192.168.154.254")/ICMP())
    

    5.寻找mac地址(Ether())

    win+r+arp -a

    sendp(Ether(dst="00-50-56-ee-ac-a2"))
    
    ifconfig
    inet 192.168.109.132 #本地IP
    

    6.构造内容为随机的数据包

    这是一个发往192.168.109.132,内容为随机填充的TCP包

    IP(dst="192.168.109.132")/fuzz(TCP())
    

    7.三个发送和接收数据的函数

    1. sr()第三层,IP,ARP
    2. sr1())第三层,IP,ARP
    3. srp()第二层
    sr(IP(dst="192.168.109.132")/ICMP())
    

    8.保存数据包列表(src()函数返回两个列表包)

    一个是有应答的列表包,另一个是无应答的列表包

    ans,unans=sr(IP(dst="192.168.154.1")/ICMP())
    

    9.查看数据包

    ans.summary()
    

    10.sr1()发法

    p=sr1(IP(dst="192.168.154.1")/ICMP())
    
    • 可以用sr1()方法来检测目标的某个端口是否开放,采用半开扫描发(SYN)的方法

    不完成TCP握手流程。只向目标端口发送一个SYN报文,然后等待响应

    p=sr1(IP(dst="192.168.154.1")/TCP(dport=80,flags="S"))
    

    11.sniff()监听流经物理网卡的流量包

    用windowsping一下linux的地址,并按ctrol+c,会看出物理网卡

    >>> sniff()                                                                     
    ^c<Sniffed: TCP:9 UDP:14 ICMP:0 Other:0>
    
    

    12.专一性监听设置

    >>> sniff(filter="host 192.168.109.132")     #只对IP地址192.168.109.132进行监听
    ping 192.168.109.132
    

    13.限量监听

    sniff(count=3)
    

    14.特殊包种监听

    sniff(filter="host 192.168.109.132 and icmp",count=3,iface="ens33(在kali种是eth0)")
    

    Ubuntu物理网卡查找

    >>> sniff(filter="host 192.168.109.132 and icmp",count=3,iface="ens33")         
    <Sniffed: TCP:0 UDP:0 ICMP:3 Other:0>
    
    

    15.summary()(操作对象是单个数据包)和nsummary()(操作对象是多个数据包)

    >>> k= IP(dst="www.baidu.com")                                                  
    >>> k.summary()                                                                 
    "192.168.109.132 > Net('www.baidu.com') hopopt"
    
    
    >>> p=sniff(filter="host 192.168.109.132 and icmp",count=3,iface="ens33")  
    
    >>> p.nsummary()                                                                
    0000 Ether / IP / ICMP 192.168.109.1 > 192.168.109.132 echo-request 0 / Raw
    0001 Ether / IP / ICMP 192.168.109.132 > 192.168.109.1 echo-reply 0 / Raw
    0002 Ether / IP / ICMP 192.168.109.1 > 192.168.109.132 echo-request 0 / Raw
    
    

    16.ACK类型的扫描(观察端口(dport)是否被屏蔽,屏蔽不是关闭)

    ans,unans=sr(IP(dst="192.168.154.1")/TCP(dport=[21,23,135,443,445],flags='A'))
    

    ACK扫描:

    扫描主机向目标主机发送ACK数据包。根据返回的RST数据包有两种方法可以得到端口的信息。方法一是: 若返回的RST数据包的TTL值小于或等于64,则端口开放,反之端口关闭,如图所示。

    17.命名ans包的集合中单个包的先后的两个链接为s,r,若把s作为链接以TCP为协议的目的端口等于把r作为链接以TCP为协议的源端口则对该端口进行输出

    for s,r in ans:
        #pint(s)
        #pint(r)
    
    WARNING: Calling str(pkt) on Python 3 makes no sense!
    

    b'Ex00x00(x00x01x00x00@x06xf1xf8xc0xa8mx84xc0xa8x9ax01x00x14x00x15x00x00x00x00x00x00x00x00Px10 x00x06xd5x00x00'
    WARNING: Calling str(pkt) on Python 3 makes no sense!
    b'Ex00x00(x01}x00x00x80x06xb0|xc0xa8x9ax01xc0xa8mx84x00x15x00x14x00x00x00x00x00x00x00x00Px04x7fxffxa6xe1x00x00x00x00x00x00x00x00'
    WARNING: more Calling str(pkt) on Python 3 makes no sense!
    b'Ex00x00(x00x01x00x00@x06xf1xf8xc0xa8mx84xc0xa8x9ax01x00x14x00x17x00x00x00x00x00x00x00x00Px10 x00x06xd3x00x00'
    b'Ex00x00(x01~x00x00x80x06xb0{xc0xa8x9ax01xc0xa8mx84x00x17x00x14x00x00
    ````
    if s[TCP].dport==r[TCP].sport:
    print("The port"+str(s[TCP].dport)+" is unfiltered")

    
    
      for s,r in ans:   
      ...:            print(type(s[TCP].dport))  
      ...:                                                                            
      <class 'int'>
      <class 'int'>
      <class 'int'>
      <class 'int'>
      <class 'int'>
      for s,r in ans:   
      ...:            print(type(str(s[TCP].dport)))  
      ...:       
      ...:                                                                            
      <class 'str'>
      <class 'str'>
      <class 'str'>
      <class 'str'>
      <class 'str'>
    

    19.查看被过滤的端口

    for s in unans:
        print(str(s[tcp0.dport])+" is filtered")
    

    报文:报文(message)是网络中交换与传输的数据单元,即站点一次性要发送的数据块

    20.小撒花

    from scapy.all import *
          ans,unans=sr(IP(dst=“192.168.109.132”)/fuzz(TCP(dport=80,flags='S')))
          
    for s,r in ans:
          if r[TCP].flags = 18:#18开
             print("This port is open")
          if r[TCP].flags = 20:#20关
             print("This port is close")
    ```
    

    [数据包的保存,查看,格式化输出,过滤]

    21.将抓到的数据包保存

    from scapy.all import *
    package=sniff(iface='ens33',count=10)  #扫描eth0网卡的数据包,总数为10个
    #control c
    wrpcap("test.pcap",package)  #将抓取到的包保存为test.pcap文件
    

    22.查看抓取到的数据包

    package[0]是查看第一个数据包的数据,package[0].show()是查看第一个数据包的详细信息

    我们还可以通过协议来查看指定的包:package[ UDP][0].show() ,我们也可以直接只获取指定层的数据,如: pcap[UDP][1][Ether].dst 这个包里面是等于ff:ff:ff:ff:ff:ff

    从上面可以看到,我们抓取到了十个UDP的数据包,然后我们可以查看第一个数据包:package[0]是查看第一个数据包的数据,package[0].show()是查看第一个数据包的详细信息,scapy是按照按照 TCP/IP 四层参考模型显示详细包信息的,即:链路层 [Ethernet]、网络层[IP]、传输层[TCP/UDP]、应用层[RAW] 。我们还可以通过协议来查看指定的包:

    package[UDP][0].show() ,因为我们这里只有UDP的数据包,所以就没有这样使用。,而我们也可以直接只获取指定层的数据,如: pcap[UDP][1][Ether].dst 这个包里面是等于ff:ff:ff:ff:ff:ff

    >>> from scapy.all import *
    >>> package=sniff(iface='ens33',count=10)  #扫描ens33网卡的数据包,总数为10个
    
    ^C>>> wrpcap("test.pcap",package)  #将抓取到的包保存为test.pcap文件
    >>> print(package)  #查看package里面的包的种类和对应的数量
    <Sniffed: TCP:0 UDP:4 ICMP:0 Other:0>
    >>> print(package[0])
    b'x01x00^x00x00xfbx00PVxc0x00x08x08x00Ex00x00XUxb4x00x00x01x11U<xc0xa8mx01xe0x00x00xfbx14xe9x14xe9x00DdIx00x00x00x00x00x01x00x00x00x00x00x00$422e09c9-ca57-4d90-97db-9b7dd68fe9e7x05localx00x00x01x00x01'
    >>> print(package[0].show()) ¥#展示第一个包的具体信息
    ###[ Ethernet ]### 
      dst       = 01:00:5e:00:00:fb
      src       = 00:50:56:c0:00:08
      type      = IPv4
    ###[ IP ]### 
         version   = 4
         ihl       = 5
         tos       = 0x0
         len       = 88
         id        = 21940
         flags     = 
         frag      = 0
         ttl       = 1
         proto     = udp
         chksum    = 0x553c
         src       = 192.168.109.1
         dst       = 224.0.0.251
         options   
    ###[ UDP ]### 
            sport     = mdns
            dport     = mdns
            len       = 68
            chksum    = 0x6449
    ###[ DNS ]### 
               id        = 0
               qr        = 0
               opcode    = QUERY
               aa        = 0
               tc        = 0
               rd        = 0
               ra        = 0
               z         = 0
               ad        = 0
               cd        = 0
               rcode     = ok
               qdcount   = 1
               ancount   = 0
               nscount   = 0
               arcount   = 0
               qd        
                |###[ DNS Question Record ]### 
                |  qname     = '422e09c9-ca57-4d90-97db-9b7dd68fe9e7.local.'
                |  qtype     = A
                |  qclass    = IN
               an        = None
               ns        = None
               ar        = None
    
    None
    
    

    23.格式化输出

    如果我们要对抓取到的数据包进行格式化输出,我们可以使用 packet.sprintf() 函数进行格式化输出

    sprintf()读数据格式:IP:%IP.src% 代表读取的是IP字段的源地址

    比如要读取IP包的源地址和目的地址: IP:%IP.src% -> %IP.dst%

    要读取UDP中的源端口和目的端口: UDP:%UDP.sport% -> %UDP.sport%

    package=sniff(dst="220.181.38.148",count=3,prn=lambda x:x.sprintf("{ IP:%IP.src% -> %IP.dst%
    }"))  
    
    package=sniff(count=10,prn=lambda x:x.sprintf("{UDP:%UDP.sport% -> %UDP.sport%
    }"))  
    

    prn参数

    回调函数

    ​ 向一个函数传入另一个或另几个函数的指针,从而实现这个函数在内部对其他几个函数的调用,并接收它们返回的信息。

    24.过滤抓包

    >>> from scapy.all import *                                                     
    >>> sniff(filter="icmp",count=5,prn=lambda x : x.sprintf("{IP:%IP.src%-> %IP.dst
    ...: %}"))                                                                      
    192.168.109.132-> 220.181.38.148
    220.181.38.148-> 192.168.109.132
    192.168.109.132-> 220.181.38.148
    220.181.38.148-> 192.168.109.132
    192.168.109.132-> 220.181.38.148
    <Sniffed: TCP:0 UDP:0 ICMP:5 Other:0>
    
    • 百度地址:220.181.38.148
    • lambda是一个简易函数模型
      格式:lambda 参数:函数

    25.sniff的参数

    26.第二次撒花

    from scapy.all import *
    package=sniff(filter="icmp or ip",count=20,prn=lambda x : x.sprintf("{IP:%IP.src%-> %IP.dst%}"))     #扫描eth0网卡的数据包,总数为10个
    wrpcap("test.pcap",package)  #将抓取到的包保存为test.pcap文件
    
    #如果我们以后想查看这个包的话,可以这样使用
    package = sniff(offline='test.pcap')  或 package= rdpcap('test.pcap')
    #offline:从pcap文件中读取数据包,而不进行嗅探,默认为None(获取网络上流经的数据包)
    

    学习资源(强推)

    scapy模块的利用
    为什么强推呢?因为我得机子好像对博客过敏,在试了n个博客失败后,遇到了了它,终于能跑动了
    在ubuntu抓着抓着就莫名奇妙跑到windows直接抓

  • 相关阅读:
    work_7_Boolean和boolean,基本类型和包装类型
    work_06_服务器上传图片错误
    work_05_64未随机id生成器
    work_04_谷歌验证码工具Kaptcha
    vue.js_13_vue的搭建
    每日一java(割草机)
    work_03_常见jq问题处理
    work_02_css样式
    java 27
    java 27
  • 原文地址:https://www.cnblogs.com/BeautifulWater/p/14383077.html
Copyright © 2020-2023  润新知