一个简易网络嗅探器的实现

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

一个简易网络嗅探器的实现

摘要:本文介绍一个用C语言和网络数据包分析开发工具实现的简易网络Sniffer。

关键词:网络;数据包;Sniffer

1 引言

目前,已经有不少的Sniff工具软件,如Windows环境下,最富盛名的工具是Netxray 和Sniffer pro,用它们在 Windows环境下抓包来分析,非常方便。在UNIX环境下如Sniffit,Snoop,Tcpdump,Dsniff 等都是比较常见的。这里介绍一个用C语言和网络数据包和分析开发工具libpcap及winpcap 实现的简易网络Sniffer。

2网络嗅探器程序实现

在c环境下编程,源码

/* June 2nd,2002

* Project for graduation qualification By Bby Team 19 */

#include

#include

//必须加路径,必须把头文件包含进去

#include "..“..“Include“"

#include "..“..“Include“"

#define Max_Num_Adapter 10

// Prototypes原形

//发包

void PrintPackets(LPPACKET lpPacket); //设备列表

char

AdapterList[Max_Num_Adapter][1024]; // 主程序开始

int main()

{

//define a pointer to an ADAPTER structure设备指针

LPADAPTER lpAdapter = 0;

//define a pointer to a PACKET structure包指针

LPPACKET lpPacket;

int i;

DWORD dwErrorCode;

DWORD dwVersion;

DWORD dwWindowsMajorVersion;

//Unicode strings (WinNT)

WCHAR AdapterName[8192]; //网络适配器设备列表

WCHAR *temp,*temp1;

//ASCII strings (Win9x)

char AdapterNamea[8192]; //网络适配器设备列表

char *tempa,*temp1a;

int AdapterNum=0,Open;

ULONG AdapterLength;

char buffer[256000]; // 容纳来自驱动器的数据的缓冲区

struct bpf_stat stat;

// 获得本机网卡名

AdapterLength=4096;

printf(" test application. Library version:%s“n", PacketGetVersion()); printf("Adapters installed:“n");

i=0;

下面这段代码是用来在不同版本下得到网

络适配器名:

Win9x 和WinNT中的网卡名称是分别用ASCII和UNICODE实现的,所以首先要得到本地操作系统的版本号.:

dwVersion=GetVersion();

dwWindowsMajorVersion=

(DWORD)(LOBYTE(LOWORD(dwVersion))); 这里首先用到的函数是PacketGetAdapterNames,它在到来的包上设置了一个硬件过滤器,如操作成功,返回TRUE。AdapterObject是过滤器所在的网卡设备指针;过滤器的常量Filter定义在头文件中,包括有:

•NDIS-PACKET-TYPE-PROMISCUOUS:设置混杂模式,每个到来的包都会被网卡接受;•ND IS-PACKET-TYPE-DIRECTED:只有直接到主机网卡的包才会被接受;

•NDIS-PACKET-TYPE-BROADCAST:只接受广播包;

•NDIS-PACKET-TYPE-MULTICAST:只接受到主机所在的组的多播包;

•NDIS-PACKET-TYPE-ALL-MULTICAS:接受每

个多播的包。

// set the network adapter in promiscuous mode

// 如果混杂模式设置失败,提示错误:

if(PacketSetHwFilter(lpAdapter,NDIS_P ACKET_TYPE_PROMISCUOUS)==FALSE){

printf("Warning: unable to set promiscuous mode!“n");

}

然后在driver中置512K的缓冲:

这里用到函数PacketSetBuff,它被用于设置AdapterObject指向的网卡的驱动程序的缓冲区,成功则返回TRUE。Dim是新的缓冲区的大小,当它被设定时,旧缓冲区中的数据将被丢弃,其中存储的包也会失去。

需要注意的地方:驱动器缓冲区的大小设置是否恰当,将影响截包进程的性能,设置应能保证运行快且不会丢包。这里设置的是512000Byte。

// set a 512K buffer in the driver // 当无法设置缓冲区时,提示错误:

if(PacketSetBuff(lpAdapter,512000)==F ALSE){

printf("Unable to set the kernel buffer!“n");

return -1;

}

PacketSetReadTimeout函数的功能是,设置与AdapterObject指定网卡绑定的读操作超时的值,timeout以毫秒为单位,0表示没有超时,当没有包到时,read就不返回。// set a 1 second read timeout

// 设置1秒的读取操作超时

if(PacketSetReadTimeout(lpAdapter,100 0)==FALSE){

printf("Warning: unable to set the read tiemout!“n");

}

接下来,定位设备,代码

这里用到函数PacketAllocatePacket将在内存中分配一个PACKET结构并返回一个指

相关文档
最新文档