ARP Attack 实验 探测局域网内MAC地址
ARPAttack
一、实验原理
在每台安装有 TCP/IP 协议的电脑里都有一个 ARP 缓存表,表里的 IP 地址与 MAC 地址是一一对应的,图 1 是 Windows Server 2003 的 ARP 缓存表片段。
在上图所示的 ARP 缓存表中,IP 地址 172.16.0.151 映射的 MAC 地址为 00-0c-29-1d-af-2a,下面我们以主机 X(172.16.0.50)向主机 Y(172.16.0.151)发送数据为例,说明 ARP 工作过程。
当主机 X 发送数据时,它会在自己的 ARP 缓存表中寻找是否有主机 Y 的 IP 地址。如果找到了, 也就知道了主机 Y 的 MAC 地址,直接把目标 MAC 地址写入数据帧里面发送就可以了;如果在 ARP 缓存表中没有找到主机 Y 的 IP 地址,主机 X 就会在网络上发送一个广播,目标 MAC 地址是
“FF-FF-FF-FF-FF-FF
”,这表示向同一网段内的所有主机发出这样的询问:“172.16.0.151 的MAC 地址是什么?”。网络上其他主机并不响应 ARP 询问,只有主机 Y 接收到这个数据帧时,才会向主机 X 做出这样的回应:“172.16.0.151 的 MAC 地址是 00-0c-29-1d-af-2a”。这样,主机 X 就知道了主机 Y 的 MAC 地址,它就可以向主机 Y 发送信息了。同时它还更新了自己的 ARP 缓存表, 下次再向主机 Y 发送信息时,直接从 ARP 缓存表里查找就可以了。ARP 缓存表采用了老化机制,在一段时间内如果表中的某一行没有使用,就会被删除,这样可以大大减少 ARP 缓存表的长度,加快查询速度。
二、实验内容:
1、搭建一个虚拟机环境,可以采用 NAT 模式,和本机属于同一网段,抓取 ARP 报文并进行数据报分析
2、学会 ARP 命令,运用命定对 ARP 内容进行修改
3、ARP 安全与防护
三、实验目的:
1、学会抓取 ARP 报文,掌握 ARP 报文结构
2、掌握 ARP 命令,并且学会运用
3、了解 ARP 安全学会 ARP 防护
四、涉及实验的相关情况介绍
(包含使用软件或实验设备等情况):
装有网络抓包工具的计算机
五、程序清单与测试数据:
1、抓取 ARP 报文
如果要准确的抓取 ARP 数据包,及了解 ARP 的首次工作方式的话就要了解 ARP 命令
a. 打开 windows 系统里的命令提示符:win+r 键,输入 cmd 确定,如图 1:
b. 在命令提示符中输入
arp -?
查看信息如图 2
ARP 命令用法如图 2:
c. 输入 ipconfig/all 查看本机 ip 和默认网关以及本机的MAC 地址如图 3:
d. 输入 arp -a查看 arp 记录表如图 4:
e. 打开抓包软件并测试能否正常工作如图 5
f. 让软件一直在抓包中,把 arp 缓冲清除的目的是为了抓出不知道 mac 地址 arp 的报文,如图 2 信息可知清除 arp 缓冲的命令为 arp -d *
g. 当前转包软件还在运行,然后 ping 网关 192.168.1.1 广播抓取 arp 数据包如图 6 ping 网关:
ping 192.168.1.1
h.然后停止抓包,查看 arp 数据包,源地址为 192.168.12.3 的包数据,如图 7 出现成对的 arp 数据包如下:
ARP报告显示,主机向网关发起了一次请求,网关回复了一次
果然发现
2、arp 数据包分析
- 通过上述过程我们抓到了arp 包,然后进行arp 数据包的分析
如图 8 是本机 192.168.1.104 发送给网关 192.168.1.1 的 arp 数据包:
FF | FF | FF | FF | FF | FF | 98 | FA | 9B | 02 | C4 | FC | 08 | 06 | 00 | 01 |
目标地址 | 源地址 | 类型ARP | 硬件类型 | ||||||||||||
08 | 00 | 06 | 04 | 00 | 01 | 98 | FA | 9B | 02 | C4 | FC | C0 | A8 | 01 | 68 |
协议类型: IpV4 | 硬件字段长度: 6 | 协议字段长度: 4 | 操作方式: Request | 发送者硬件地址 | 发送者协议地址 | ||||||||||
00 | 00 | 00 | 00 | 00 | 00 | C0 | A8 | 01 | 01 | ||||||
接受者硬件地址 | 接受者协议地址 |
如图 是本机 192.168.1.104 接受网关 192.168.1.1 的 arp 数据包:
可见其操作方式为: Response [0x0002]
98 | FA | 9B | 02 | C4 | FC | 64 | 6E | 97 | 81 | AA | CE | 08 | 06 | 00 | 01 |
目标地址 | 源地址 | 类型ARP | 硬件类型 | ||||||||||||
08 | 00 | 06 | 04 | 00 | 02 | 64 | 6E | 97 | 81 | AA | CE | C0 | A8 | 01 | 01 |
协议类型: IpV4 | 硬件字段长度: 6 | 协议字段长度: 4 | 操作方式: Response | 发送者硬件地址 | 发送者协议地址 | ||||||||||
98 | FA | 9B | 02 | C4 | FC | C0 | A8 | 01 | 68 | ||||||
接受者硬件地址 | 接受者协议地址 |
3、ARP 安全与防护
A. ARP 的攻击原理请描述:
攻击者使用欺骗工具发送伪造的 ARP 响应。伪造的响应会宣传属于路由器和工作站的两个 IP 地址的正确 MAC 地址是攻击者的 MAC 地址。这欺骗了路由器和工作站连接到攻击者的机器,而不是相互连接。
ARP 欺骗可能允许攻击者拦截网络上的数据帧、修改流量或停止所有流量。通常,攻击被用作其他攻击的开端,例如拒绝服务、中间人或会话劫持攻击。该攻击只能在使用 ARP 的网络上使用,并且需要攻击者可以直接访问要攻击的本地网段。
B.ARP 的防御,可以采用哪些方法: 时时检测ARP,以管理员身份启动终端,arp -a
,如果该表包含两个具有相同 MAC 地址的不同 IP 地址,则表明正在发生 ARP 攻击,及时清理缓存即可。
六、补充该ARP程序
六、补充该 ARP 发现程序缺失的部分,并给出实验结果。下述程序在 win server2003,vc6 或者 win7、win10,vc2013 测试可行。
核心的SendARP函数如下:
SendARP(
IPAddr DestIP,
IPAddr SrcIP,
PULONG pMacAddr,
PULONG PhyAddrLen
);
将程序补全
#include <windows.h>
#include <stdio.h>
#include <iphlpapi.h>
#include <iostream>
using namespace std;
#pragma comment(lib, "ws2_32.lib")
#pragma comment(lib, "Iphlpapi.lib")
int main()
{
WSADATA wsaData;
in_addr sa;
int nErr = 0;
ULONG ulLocaIP = 0;
ULONG ulLocalNet = 0;
HRESULT hr = 0;
WSAStartup(MAKEWORD(1, 1), &wsaData);
//获取本地主机名称
char host_name[256];
int tot = 0;
if (gethostname(host_name, sizeof(host_name)) == SOCKET_ERROR)
{
cout << "error host name" << endl;
}
//! 获取本地主机信息
hostent* hp;
hp = gethostbyname(host_name);
if (hp != NULL)
{
memcpy(&sa, hp->h_addr_list[0], hp->h_length);
ulLocaIP = htonl(sa.s_addr);
ulLocalNet = ulLocaIP & 0xffffff00;
IPAddr SrcIp = 0; /* 默认的 src ip */
BYTE* bPhysAddr;
// 遍历本地网络 IP 地址 1-255
for (int n = 1; n <= 255; n++)
{
// 初始化
u_char arDestMac[6];
ULONG PhysAddrLen = 6;
in_addr dest;
DWORD rpSend;
dest.S_un.S_addr = htonl(ulLocalNet + n); // 网络号+主机号
// 发送 ARP 请求,显示 mac 地址,找出 tot 个活动主机
printf("%d\t", n);
if (SendARP(dest.S_un.S_addr, SrcIp, &arDestMac, &PhysAddrLen) == NO_ERROR)
{
cout <<"\n" << n << ":找到" << inet_ntoa(dest) << endl;
tot ++;
bPhysAddr = (BYTE*)&arDestMac;
if (PhysAddrLen)
{
for (int i = 0; i < (int)PhysAddrLen; i++)
{
if (i == (PhysAddrLen - 1))
printf("%.2X\n", (int)bPhysAddr[i]);
else
printf("%.2X-", (int)bPhysAddr[i]);
}
}
}
}
}
else
{
exit(EXIT_FAILURE); //退出
}
printf("total active machine is %d\n", tot);
WSACleanup();
int k; // 阻塞,防止程序自动关闭
scanf_s("%d", &k);
return 0;
}
在扫描时我呢吧需要注意,扫描的局域网是否为主机的局域网,可能会误扫到虚拟机的局域网,注意扫描的IP前三个字段与主机的是否一致,如果不一致就先前往网络中心的更改适配器选项处禁用干扰的网卡,实验结束再恢复。
结果如下: