如何在Python使用 Scapy 检测 ARP 欺骗攻击?
ARP 欺骗也称为 ARP 中毒,它是一种网络攻击,其中恶意用户通过LAN(局域网)发送伪造的 ARP(地址解析协议)消息。这会导致攻击者的 MAC 地址与网络上合法计算机或服务器的 IP 地址相关联。
在这里,我们将在收到一个 ARP 数据包后执行被动监视或扫描以嗅探网络中的数据包,有两件事需要分析,如果它们不匹配,则比较它们,则用户受到 ARP 欺骗攻击。为了欺骗和检测网络内部的 ARP 数据包,使用 Scapy 和Python在 MAC 地址和接口的帮助下执行 ARP 数据包的检测。
- 源 MAC 地址
- 发件人的真实 MAC 地址
什么是斯皮?
Scapy是一种用于计算机网络的数据包操作工具,最初是用Python编写的。它可以伪造或解码数据包,通过网络发送它们,捕获它们,并匹配请求和回复。它还可以处理扫描、跟踪路由、探测、单元测试、攻击和网络发现等任务。它在 Linux、macOS 和 Windows 上运行,但最新版本的 Scapy 支持 Windows 开箱即用,因此也可以在 Windows 机器上使用 Scapy 的所有功能。 Scapy 可以执行以下操作
- 制作任何数据包并对其进行编码
- 嗅探网络数据包
- 发送有效/无效帧
- 注入你自己的 802.11 帧
- 编辑网络数据包
- 扫描网络
- 跟踪和探测
- 攻击网络和网络发现。
Scapy 安装
要安装 Scapy,您必须安装Python 2.7 或Python 3.9+ 版本。如果未安装,请参阅此Python安装。为防止中间人使用动态 ARP 检测,该安全功能将自动拒绝将检测到的恶意 ARP 数据包。
Linux
对于 Linux 用户,可以在没有 libcap 的情况下运行 scapy。
- 安装tcpdump并确保它在$PATH 中
$ sudo apt-get tcpdump
- 内核必须选择数据包套接字 – CONFIG_PACKET
- 如果内核小于 2.6,请确保选择了 Socket Filtering – CONFIG_FILTER
在 Linux 上安装 Scapy 的另一种方法是在 Linux 机器上安装Python ,然后在Python Shell 中安装 Scapy 包。
$ sudo apt-get install python3
终端安装好Python后,打开Python shell,执行命令安装scapy,然后使用scapy进行ARP欺骗检测,打开Scapy编写代码,进行网络内部数据包的欺骗检测,
$ sudo apt-get install scapy (OR)
$ python -m install scapy
$ python
>> scapy
Debian/Fedora/Ubuntu
# Debian
$ sudo apt-get install tcpdump
# Fedora
$ yum install tcpdmp
然后通过 pip 或 apt 安装 Scapy。所有依赖项都可以通过特定于平台的安装程序或通过 PyPI 安装
视窗
要在 Windows 上安装 scapy,可以通过命令提示符轻松完成,但对于 Windows,还应在系统上预安装Python 。然后将执行安装scapy的命令。
C:\> python -m install python-scapy
C:\> python
>> scapy
现在让我们在Python使用 Scapy 启动 ARP 欺骗攻击检测
使用 Scapy 进行 ARP 欺骗攻击检测
现在我们已经在系统上成功安装了Python和 scapy,让我们继续从 scapy 导入必要的库。
Python3
# importing libraries form scapy
from scapy.all import Ether, ARP, srp, sniff, conf
import scapy as scapy
# to import all libraries from scapy
# irrespective of which one to use execute the code
from scapy.all import *
Python3
# importing all libraries of scapy
import scapy.all as scapy
# taking interface of the system as an argument
# to sniff packets inside the network
def sniff(interface):
# store=False tells sniff() function to discard sniffed packets
scapy.sniff(iface=interface, store=False, prn=process_sniffed_packet)
def process_sniffed_packet(packet):
# if it is an ARP Packet and if it is an ARP Response
if packet.haslayer(scapy.ARP) and packet[scapy.ARP].op == 2:
print(packet.show())
# machine interface is "eth0", sniffing the interface
sniff("eth0")
Python3
# code to get MAC Address
def mac(ipadd):
# requesting arp packets from the IP address
# if it's wrong then will throw error
arp_request = scapy.ARP(pdst=ipadd)
br = scapy.Ether(dst="ff:ff:ff:ff:ff:ff")
arp_req_br = br / arp_request
list_1 = scapy.srp(arp_req_br, timeout=5,
verbose=False)[0]
return list_1[0][1].hwsrc
# defining function to process sniffed packet
def process_sniffed_packet(packet):
# if it is an ARP packet and if it is an ARP Response
if packet.haslayer(scapy.ARP) and packet[scapy.ARP].op == 2:
# originalmac will get old MAC whereas
originalmac = mac(packet[scapy.ARP].psrc)
# responsemac will get response of the MAC
responsemac = packet[scapy.ARP].hwsrc
Python3
# comparing values of real MAC Address and response MAC Address
if originalmac != responsemac:
print("[*] ALERT!!! You are under attack, ARP table is being poisoned.!")
Python3
# Implementing ARP Spoof Attack Detection Using Scapy
# import modules
import scapy.all as scapy
# code to get MAC Address
def mac(ipadd):
# requesting arp packets from the IP address
# if it's wrong then will throw error
arp_request = scapy.ARP(pdst=ipadd)
br = scapy.Ether(dst="ff:ff:ff:ff:ff:ff")
arp_req_br = br / arp_request
list_1 = scapy.srp(arp_req_br, timeout=5,
verbose=False)[0]
return list_1[0][1].hwsrc
# taking interface of the system as an argument
# to sniff packets inside the network
def sniff(interface):
# store=False tells sniff() function
# to discard sniffed packets
scapy.sniff(iface=interface, store=False,
prn=process_sniffed_packet)
# defining function to process sniffed packet
def process_sniffed_packet(packet):
# if it is an ARP packet and if it is an ARP Response
if packet.haslayer(scapy.ARP) and packet[scapy.ARP].op == 2:
# originalmac will get old MAC whereas
originalmac = mac(packet[scapy.ARP].psrc)
# responsemac will get response of the MAC
responsemac = packet[scapy.ARP].hwsrc
# machine interface is "eth0", sniffing the interface
sniff("eth0")
该程序将检测是否有任何类型的数据包具有欺骗性 ARP 层,以便执行代码。 sniff()函数将回调应用于每个将被嗅探的数据包。在store=False 告诉 sniff()函数丢弃嗅探的数据包而不是将它们存储在内存中,这在脚本运行很长时间时很有用。
Use this code to check the interface of the machine you want to sniff
>> conf.iface
蟒蛇3
# importing all libraries of scapy
import scapy.all as scapy
# taking interface of the system as an argument
# to sniff packets inside the network
def sniff(interface):
# store=False tells sniff() function to discard sniffed packets
scapy.sniff(iface=interface, store=False, prn=process_sniffed_packet)
def process_sniffed_packet(packet):
# if it is an ARP Packet and if it is an ARP Response
if packet.haslayer(scapy.ARP) and packet[scapy.ARP].op == 2:
print(packet.show())
# machine interface is "eth0", sniffing the interface
sniff("eth0")
嗅探到eth0接口后会显示接口的内容,这里我们看到接口是以太网,其相关内容显示为IP Destination(dst), type of interface(ARP), source(src)
使用 ARP函数创建一个给定 IP 地址的函数mac以创建/创建 ARP 请求arp_request并检索实际 MAC 地址而不是 IP 地址。使用以太函数将广播 MAC 地址设置为“ff:ff:ff:ff:ff:ff” 。 srp函数返回两个响应数据包的 IP 地址列表。具有所请求的匹配 IP 地址的 MAC 地址将存储在hwsrc字段中。
将创建一个函数来获取 MAC 地址并处理嗅探的数据包,获取“originalmac”变量中旧 MAC 的值和响应中 MAC 值作为“ repsonsemac”变量。 Scapy 在字段“op”中对 ARP 数据包类型进行编码以进行操作,默认情况下 op 为 1 或“who-has” ,这是一个 ARP 请求。
蟒蛇3
# code to get MAC Address
def mac(ipadd):
# requesting arp packets from the IP address
# if it's wrong then will throw error
arp_request = scapy.ARP(pdst=ipadd)
br = scapy.Ether(dst="ff:ff:ff:ff:ff:ff")
arp_req_br = br / arp_request
list_1 = scapy.srp(arp_req_br, timeout=5,
verbose=False)[0]
return list_1[0][1].hwsrc
# defining function to process sniffed packet
def process_sniffed_packet(packet):
# if it is an ARP packet and if it is an ARP Response
if packet.haslayer(scapy.ARP) and packet[scapy.ARP].op == 2:
# originalmac will get old MAC whereas
originalmac = mac(packet[scapy.ARP].psrc)
# responsemac will get response of the MAC
responsemac = packet[scapy.ARP].hwsrc
现在比较这两个值并检查它们是否相似,以防它们不相似,则这意味着这些值已被欺骗。比较的值是实际 MAC 地址和响应 MAC 地址。
蟒蛇3
# comparing values of real MAC Address and response MAC Address
if originalmac != responsemac:
print("[*] ALERT!!! You are under attack, ARP table is being poisoned.!")
以下是完整代码
蟒蛇3
# Implementing ARP Spoof Attack Detection Using Scapy
# import modules
import scapy.all as scapy
# code to get MAC Address
def mac(ipadd):
# requesting arp packets from the IP address
# if it's wrong then will throw error
arp_request = scapy.ARP(pdst=ipadd)
br = scapy.Ether(dst="ff:ff:ff:ff:ff:ff")
arp_req_br = br / arp_request
list_1 = scapy.srp(arp_req_br, timeout=5,
verbose=False)[0]
return list_1[0][1].hwsrc
# taking interface of the system as an argument
# to sniff packets inside the network
def sniff(interface):
# store=False tells sniff() function
# to discard sniffed packets
scapy.sniff(iface=interface, store=False,
prn=process_sniffed_packet)
# defining function to process sniffed packet
def process_sniffed_packet(packet):
# if it is an ARP packet and if it is an ARP Response
if packet.haslayer(scapy.ARP) and packet[scapy.ARP].op == 2:
# originalmac will get old MAC whereas
originalmac = mac(packet[scapy.ARP].psrc)
# responsemac will get response of the MAC
responsemac = packet[scapy.ARP].hwsrc
# machine interface is "eth0", sniffing the interface
sniff("eth0")
输出: