一个简易网络嗅探器的实现源代码
《一个简易网络嗅探器的实现源代码》由会员分享,可在线阅读,更多相关《一个简易网络嗅探器的实现源代码(10页珍藏版)》请在装配图网上搜索。
1、摘要:本文介绍一个用C语言和网络数据包分析开发工具实现的简易网络Sniffer。要害词:网络;数据包;Sniffer引言目前,已经有不少的Sniff工具软件,如Windows环境下,最富盛名的工具是Netxray和Sniffer pro, 用它们在 Windows环境下抓包来分析,非常方便。在UNIX环境下如Sniffit, Snoop,Tcpdump, Dsniff等 都是比较常见的。这里介绍一个用C语言和网络数据包和分析开发工具libpcap及winpcap实现的简易网络 Sniffer。网络嗅探器程序框图首先给出流程如图 1 所示。援收并打印冏络包图 1 流程图网络嗅探器程序实现在 c
2、环境下编程,源码如下/* June 2nd,2002* Project for graduation qualification By Bby Team 19 */ #include stdio.h#include conio.h/必须加路径,必须把头文件 packet32.h 包含进去#include .Includepacket32.h#include .Includentddndis.h#define Max_Num_Adapter 10/ Prototypes 原形/发包void PrintPackets(LPPACKET lpPacket);/设备列表char AdapterList
3、Max_Num_Adapter1024;/ 主程序开始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 AdapterName8192; /网络适配器设备列表WCHAR *
4、temp,*temp1;/ASCII strings (Win9x)char AdapterNamea8192; /网络适配器设备列表char *tempa,*temp1a;int AdapterNum=0,Open;ULONG AdapterLength;char buffer256000; / 容纳来自驱动器的数据的缓冲区struct bpf_stat stat;/ 获得本机网卡名AdapterLength=4096;printf(Packet.dll test application. Library version:%sn, PacketGetVersion(); printf(Ada
5、pters installed:n);i=0;下面这段代码是用来在不同版本下得到网络适配器名:Win9x和WinNT中的网卡名称是分别用ASCII和UNICODE实现的,所以首先要得到本地操作系统的版本号:dwVersion=GetVersion();dwWindowsMajorVersion= (DWORD)(LOBYTE(LOWORD(dwVersion);这里首先用到的 Packet.dll 函数是 PacketGetAdapterNames (PTSTR pStr, PULONG BufferSize,通常它是与驱动程序通信并被调用的第一个函数,它将返回的用户本地系统中安装的网络适配器
6、的名字放在缓冲区pStr中;BufferSize是缓冲区的长度: if (!(dwVersion= 0x80000000 & dwWindowsMajorVersion= 4)/是 Windows NT/ 找不到设备列表if(PacketGetAdapterNames(AdapterName,&AdapterLength)=FALSE) printf(Unable to retrieve the list of the adapters!n);return -1;/ 找到设备列表temp=AdapterName;temp1=AdapterName;while (*temp!=0)(*(temp
7、-1)!=0)if (*temp=0)memcpy(AdapterListi,temp1,(temp-temp1)*2); temp1=temp+1;temp+;/ 显示适配器列表AdapterNum=i;for (i = O;iAdapte rNum;i+)wprintf(Ln%d- %sn,i+1,AdapterListi);printf(n);else 否则就是windows 9x,获取适配器名的方法同WinNT下if(PacketGetAdapterNames(AdapterNamea,&AdapterLength)=FALSE) printf(Unable to retrieve t
8、he list of the adapters!n);return -1;tempa=AdapterNamea;temp1a=AdapterNamea;while (*tempa!=0)(*(tempa-1)!=0)if (*tempa=0)memcpy(AdapterListi,temp1a,tempa-temp1a); temp1a=tempa+1;i+;tempa+;AdapterNum=i;for (i = 0;iAdapte rNum;i+)printf(n%d- %sn,i+1,AdapterListi);printf(n);下面这段代码就是让用户选择监听的网络适配器号:/ 选择设
9、备do printf(Select the number of the adapter to open : );scanf(%d,&Open);if (OpenAdapte rNum)printf(nThe number must be smaller than %d,AdapterNum); while (OpenAdapterNum);然后,将所选择的设备打开,这里可以设置为“混杂”模式打开,也可以是“直接”模式打开。代码如下/ 打开设备lpAdapter = PacketOpenAdapter(AdapterListOpen-1);/ 当设备无法打开时,出示错误信息:if (!lpAda
10、pter (lpAdapter-hFile = INVALID_HANDLE_VALUE)dwErrorCode=GetLastError();printf(Unable to open the adapter, Error Code : %lxn,dwErrorCode);return -1;将网卡设置为“混杂”模式,代码如下:这里用到函数 PacketSetHwFilter (LPADAPTER AdapterObject, ULONG Filter),它在到来的包上设置了一个硬件过滤器,如操作成功,返回TRUE。AdapterObject是过滤器所在的网卡设备指针;过滤器的常 量 Fil
11、ter 定义在头文件 ntddndis.h 中,包括有:NDIS-PACKET-TYPE-PROMISCUOUS:设置混杂模式,每个到来的包都会被网卡接受;NDIS-PACKET-TYPE-DIRECTED:只有直接到主机网卡的包才会被接受;NDIS-PACKET-TYPE-BROADCAST:只接受广播包;NDIS-PACKET-TYPE-MULTICAST:只接受到主机所在的组的多播包;NDIS-PACKET-TYPE-ALL-MULTICAS:接受每个多播的包。/ set the network adapter in promiscuous mode/ 假如混杂模式设置失败,提示错误:
12、if(PacketSetHwFilter(lpAdapter,NDIS_PACKET_TYPE_PROMISCUOUS)=FALSE) printf(Warning: unable to set promiscuous mode!n);然后在driver中置512K的缓冲:这里用到函数 PacketSetBuff (LPADAPTER AdapterObject, int dim),它被用于设置 Adapterobject 指向的网卡的驱动程序的缓冲区,成功则返回TRUE。Dim是新的缓冲区的大小,当它被设定时,旧缓冲区中的 数据将被丢弃,其中存储的包也会失去。需要注重的地方:驱动器缓冲区的大
13、小设置是否恰当,将影响截包进程的性能,设置应能保证运行快且不会 丢包。这里设置的是512000Byte。/ set a 512K buffer in the driver/ 当无法设置缓冲区时,提示错误:if(PacketSetBuff(lpAdapter,512000)=FALSE)printf(Unable to set the kernel buffer!n);return -1;PacketSetReadTimeout(LPADAPTER AdapterObject,int timeout)函数的功能是,设置与AdapterObject指定网卡绑定的读操作超时的值,timeout以毫秒
14、为单位,0表示没有超时,当没有包到时, read 就不返回。/ set a 1 second read timeout/ 设置 1 秒的读取操作超时 if(PacketSetReadTimeout(lpAdapter,1000)=FALSE) printf(Warning: unable to set the read tiemout!n);接下来,定位设备,代码如下:这里用到函数PacketAllocatePacket (Void)将在内存中分配一个PACKET结构并返回一个指向它的指针,但这个结构的Buffer字段还没有设定,所以应再调用PacketInitPacket函数来对其进行初始化
15、。/allocate and initialize a packet structure that will be used to /receive the packets./ 当定位失败时,提示错误:if(lpPacket = PacketAllocatePacket()=NULL)printf(nError: failed to allocate the LPPACKET structure.);return (-1);然后,就可以初始化设备,开始接受网络包了:用函数 PacketInitPacket(LPPACKET lpPacket,PVOID Buffer,UINT Length)来
16、初始化 PACKET 结构。lpPacket是要被初始化的指针;Buffer为指向用户分配的包含包的数据的缓冲区的指针;Length为缓 冲区长度。需要注重的地方:PACKET结构关联的缓冲区存储由packet capture driver截获的包,包的数量被缓冲 区大小所限制,最大缓冲区的大小就是应用程序从驱动器中一次能读到的数据的多少。所以设置大的缓冲区可减 少系统调用的次数,提高截获效率。这里设置的是256K。PacketInitPacket(lpPacket,(char*)buffer,256000);接下来,是截包主循环:/main capture loop这里又用到函数 Packe
17、tReceivePacke(t LPADAPTER AdapterObject,LPPACKET lpPacket,BOOLEANSync),它将接受(截获)一个包的集合。参数包括一个指向用来指定截包的网卡的ADAPTER结构指针、一 个指向用来容纳包的PACKET结构、一个指出是同步还是异步方式操作的标记。当操作同步时,函数锁定程序; 当操作异步时,函数不锁定程序,必须调用 PacketWaitPacket 过程来检查是否正确完成。一般采用同步模式。/ 直到有键盘键入:while(!kbhit()/ capture the packets 捕捉包/ 捕捉包失败时,提示错误:if(Packet
18、ReceivePacket(lpAdapter,lpPacket,TRUE)=FALSE)printf(Error: PacketReceivePacket failed);return (-1);/打印包中的数据,调用自定义函数PrintPackets()PrintPackets(lpPacket);最后将得到的统计数据打印出来,代码如下:这里用到函数 PacketGetStats (LPADAPTER AdapterObject, struct bpf_star*s)可以得到两个驱动 程序的内部变量的值:从调用PacketOpenAdapter开始,已经被指定网卡接收的包数目;以及已经被网
19、卡接 收但被内核丢弃的包数目。这两个值被驱动程序拷贝到应用提供的bpf_stat结构中。/print the capture statistics/ 得到统计值/ 当无法从内核读取状态时,提示错误:if(PacketGetStats(lpAdapter,&stat)=FALSE)printf(Warning: unable to get stats from the kernel!n);/打印“XX包被截取;XX包被丢弃”:elseprintf(nn%d packets received.n%d Packets lost,stat.bs_recv,stat.bs_drop);这里用函数 Pac
20、ketFreePacket(LPPACKET lpPacket)来释放由 lpPacket 指向的结构:/ 释放空间PacketFreePacket(lpPacket);用函数 PacketCloseAdapter(LPADAPTER lpAdapter)来释放 ADAPTER 结构 lpAdapter,并关闭网卡指针:/ close the adapter and exit/ 关闭设备退出PacketCloseAdapter(lpAdapter);return (0); / 主程序结束其中用来打印数据报的自定义的函数PrintPackets ()的代码在这里就不具体说明了。结束语通过对网络嗅探器的编写,目的使大家知道网络治理的重要性,时刻注重网络信息安全问题,做好信息的加密和解密工作。参考文献【1】王腾蛟等,新概念Visual C+ 6.0教程,北京科海集团公司,20012】王宝智等,全新计算机网络教程,北京希望电子出版社, 20013】单征等,网络黑洞攻击与防范指南,中国电力出版社, 20024】程秉恢等,黑客任务实战,北京希望电子出版社, 20025】王力等,病毒武器与网络战争,军事谊文出版社, 20016】卢昱等,网络安全技术,中国物质出版社, 2001
- 温馨提示:
1: 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
2: 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
3.本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
5. 装配图网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 部编人教版语文三年级下册第八单元 方帽子店 ppt课件
- 微生物灭菌问题培训课件
- 廊坊房地产市场整合课件
- 廖小菲XXXX财务报告—利润表-课件
- 廊坊售后11月目标完成报告课件
- 部编人教版四年级语文上册《口语交际 我们与环境》优质ppt课件
- 延伸存取列表课件
- 部编人教版语文三年级下册第六单元 习作:身边那些有特点的人 ppt课件
- 廉颇蔺相如列传重点语句翻译上课-课件
- 廉颇蔺相如列传课件
- 廉颇蔺相如列传公开课优质课-课件
- 微生物活菌计数方法教学课件
- 部编人教版三年级数学下册第4课时 简单的路线图课件
- 廉洁行医秉公奉廉医疗卫生行业廉洁自律培训模板课件
- 部编人教版六年级道德与法制上册第8课《我们受特殊保护》 ppt课件完整版