|
Raw Socket(原始套接字)实现Sniffer(嗅探)(1)
一. 摘要 Raw Socket: 原始套接字 可以用它来发送和接收 IP 层以上的原始数据包, 如 ICMP, TCP, UDP... int sockRaw = socket(AF_INET, SOCK_RAW, IPPROTO_RAW); 这样我们就创建了一个 Raw Socket Sniffer: 嗅探器 关于嗅探器的原理我想大多数人可能都知道 1. 把网卡置于混杂模式; 2. 捕获数据包; 3. 分析数据包. 但具体的实现知道的人恐怕就不是那么多了. 好, 现在让我们用 Raw Socket 的做一个自已的 Sniffer. 二. 把网卡置于混杂模式 在正常的情况下,一个网络接口应该只响应两种数据帧: 一种是与自己硬件地址相匹配的数据帧 一种是发向所有机器的广播数据帧 如果要网卡接收所有通过它的数据, 而不管是不是发给它的, 那么必须把网卡置于混杂模式. 也就是说让它的思维混乱, 不按正常的方式工作. 用 Raw Socket 实现代码如下: setsockopt(sock, IPPROTO_IP, IP_HDRINCL, (char*)&flag, sizeof(flag); //设置 IP 头操作选项 bind(sockRaw, (PSOCKADDR)&addrLocal, sizeof(addrLocal); //把 sockRaw 绑定到本地网卡上 ioctlsocket(sockRaw, SIO_RCVALL, &dwValue); //让 sockRaw 接受所有的数据 flag 标志是用来设置 IP 头操作的, 也就是说要亲自处理 IP 头: bool flag = ture; addrLocal 为本地地址: SOCKADDR_IN addrLocal; dwValue 为输入输出参数, 为 1 时执行, 0 时取消: DWord dwValue = 1; 没想到这么简单吧? 三. 捕获数据包 你的 sockRaw 现在已经在工作了, 可以在局域网内其它的电脑上用 Sniffer 检测工具检测一下, 看你的网卡是否处于混杂模式(比如 DigitalBrain 的 ARPKiller). 不能让他白白的浪费资源啊, 抓包! recv(sockRaw, RecVBuf, BUFFER_SIZE, 0); //接受任意数据包 #define BUFFER_SIZE 65535 char RecvBuf[BUFFER_SIZE];
|