基于Linux的ARP攻击检测软件Python实现

本文介绍如何使用Python在Linux系统下实现一个ARP攻击检测软件,该软件具备以下功能:

  • 捕获数据包并设置过滤规则为ARP包
  • 分析ARP包,区分正常主机和疑似异常主机
  • 将疑似异常主机的IP地址和MAC地址标为红色(可视化界面需自行实现)
  • 用户登录和注册功能
  • 开始攻击检测,输出源IP地址和源MAC地址信息并保存在文件中
  • 停止攻击检测,清零信息
  • 扫描局域网主机,输出活动主机IP地址和MAC地址并保存在文件中
  • 实现三种规则进行ARP攻击检测

ARP攻击检测规则

  1. 检测应答报文: 判断是否出现同一IP地址对应不同的MAC地址,是则可能遭受ARP攻击。
  2. 检测请求报文: 判断是否合法且是否出现不同IP地址对应同一个MAC地址,是则可能遭受ARP攻击。
  3. 检测ARP请求或响应包: 检测是否存在同一IP或者是同一MAC地址发出大量数据包,是则可能遭受ARP攻击,不是则未遭受ARP攻击。

判定逻辑: 同时满足两种规则或以上的就输出遭受ARP攻击,不满足则输出未遭受ARP攻击,并将所有信息保存在日志中。

Python实现示例

import os
import sys
import time
import logging
from scapy.all import *
from threading import Thread

# 日志记录
logging.basicConfig(filename='arp_attack_detection.log', level=logging.INFO, format='%(asctime)s %(message)s')

# 存储IP地址和MAC地址的字典
ip_mac_dict = {}
mac_ip_dict = {}

# 存储IP地址或MAC地址发出的ARP包数量的字典
ip_packet_count = {}
mac_packet_count = {}

# ARP攻击检测规则1:检测应答报文时判断是否出现同一IP地址对应不同的MAC地址
def rule1(packet):
    if ARP in packet and packet[ARP].op == 2:
        if packet[ARP].psrc in ip_mac_dict and packet[ARP].hwsrc != ip_mac_dict[packet[ARP].psrc]:
            logging.warning(f'ARP攻击警告:IP地址{packet[ARP].psrc}对应的MAC地址发生变化!')
            return True
        else:
            ip_mac_dict[packet[ARP].psrc] = packet[ARP].hwsrc
            mac_ip_dict[packet[ARP].hwsrc] = packet[ARP].psrc
    return False

# ARP攻击检测规则2:检测请求报文时,是否合法且是否出现不同IP地址对应同一个MAC地址
def rule2(packet):
    if ARP in packet and packet[ARP].op == 1:
        if packet[ARP].hwsrc in mac_ip_dict and packet[ARP].psrc != mac_ip_dict[packet[ARP].hwsrc]:
            logging.warning(f'ARP攻击警告:MAC地址{packet[ARP].hwsrc}对应的IP地址发生变化!')
            return True
        else:
            ip_mac_dict[packet[ARP].psrc] = packet[ARP].hwsrc
            mac_ip_dict[packet[ARP].hwsrc] = packet[ARP].psrc
    return False

# ARP攻击检测规则3:检测ARP请求或响应包,检测是否存在同一IP或者是同一MAC地址发出大量数据包
def rule3(packet):
    if ARP in packet:
        if packet[ARP].psrc in ip_packet_count:
            ip_packet_count[packet[ARP].psrc] += 1
            if ip_packet_count[packet[ARP].psrc] > 10:
                logging.warning(f'ARP攻击警告:IP地址{packet[ARP].psrc}发出大量ARP请求或响应包!')
                return True
        else:
            ip_packet_count[packet[ARP].psrc] = 1
        if packet[ARP].hwsrc in mac_packet_count:
            mac_packet_count[packet[ARP].hwsrc] += 1
            if mac_packet_count[packet[ARP].hwsrc] > 10:
                logging.warning(f'ARP攻击警告:MAC地址{packet[ARP].hwsrc}发出大量ARP请求或响应包!')
                return True
        else:
            mac_packet_count[packet[ARP].hwsrc] = 1
    return False

# ARP攻击检测函数
def arp_attack_detection():
    sniff(filter='arp', prn=lambda x: rule1(x) or rule2(x) or rule3(x))

# 开始攻击检测按钮
def start_detection():
    t = Thread(target=arp_attack_detection)
    t.start()
    logging.info('ARP攻击检测已启动!')

# 停止攻击检测按钮
def stop_detection():
    global ip_mac_dict, mac_ip_dict, ip_packet_count, mac_packet_count
    ip_mac_dict = {}
    mac_ip_dict = {}
    ip_packet_count = {}
    mac_packet_count = {}
    logging.info('ARP攻击检测已停止!')

# 扫描局域网主机按钮
def scan_hosts():
    ans, unans = srp(Ether(dst='ff:ff:ff:ff:ff:ff')/ARP(pdst='192.168.1.0/24'), timeout=2, verbose=False)
    for send, recv in ans:
        logging.info(f'扫描到主机:IP地址{recv[ARP].psrc},MAC地址{recv[Ether].src}')

# 用户注册功能
def register(username, password):
    if os.path.exists('user.txt'):
        with open('user.txt', 'r') as f:
            for line in f:
                if line.strip().split(':')[0] == username:
                    print('该用户已注册!')
                    return
    with open('user.txt', 'a') as f:
        f.write(f'{username}:{password}
')
        print('用户注册成功!')

# 用户登录功能
def login(username, password):
    if os.path.exists('user.txt'):
        with open('user.txt', 'r') as f:
            for line in f:
                if line.strip().split(':')[0] == username:
                    if line.strip().split(':')[1] == password:
                        print('登录成功!')
                        return
                    else:
                        print('用户名或密码错误!')
                        return
        print('查无该用户!')
    else:
        print('用户文件不存在!')

# 用户界面
def user_interface():
    while True:
        print('1. 开始攻击检测')
        print('2. 停止攻击检测')
        print('3. 扫描局域网主机')
        print('4. 退出')
        choice = input('请选择:')
        if choice == '1':
            start_detection()
        elif choice == '2':
            stop_detection()
        elif choice == '3':
            scan_hosts()
        elif choice == '4':
            sys.exit()
        else:
            print('输入错误,请重新输入!')

# 主界面
def main():
    while True:
        print('1. 用户注册')
        print('2. 用户登录')
        print('3. 退出')
        choice = input('请选择:')
        if choice == '1':
            username = input('请输入用户名:')
            password = input('请输入密码:')
            register(username, password)
        elif choice == '2':
            username = input('请输入用户名:')
            password = input('请输入密码:')
            login(username, password)
            user_interface()
        elif choice == '3':
            sys.exit()
        else:
            print('输入错误,请重新输入!')

if __name__ == '__main__':
    main()

代码说明

  • 使用 scapy 库进行网络数据包的捕获和分析。
  • 使用 logging 模块记录攻击检测信息。
  • 使用字典存储IP地址、MAC地址以及数据包数量,方便进行攻击判断。
  • 实现三个规则进行ARP攻击检测,并根据判定逻辑输出结果。
  • 提供用户登录注册功能,增强软件安全性。
  • 提供友好的用户界面,方便用户操作。

运行环境

  • Linux 操作系统
  • Python 3
  • Scapy 库

注意

  • 以上代码仅供参考,实际应用中需要根据具体情况进行修改和完善。
  • 代码中 scan_hosts 函数默认扫描 192.168.1.0/24 网段,可根据实际网络环境进行修改。
  • 为保证软件的安全性,建议使用强密码进行用户注册。
基于Linux的ARP攻击检测软件Python实现

原文地址: https://www.cveoy.top/t/topic/jpkM 著作权归作者所有。请勿转载和采集!

免费AI点我,无需注册和登录