资源预览内容
第1页 / 共40页
第2页 / 共40页
第3页 / 共40页
第4页 / 共40页
第5页 / 共40页
第6页 / 共40页
第7页 / 共40页
第8页 / 共40页
第9页 / 共40页
第10页 / 共40页
亲,该文档总共40页,到这儿已超出免费预览范围,如果喜欢就下载吧!
资源描述
JISHOUUNIVERSITY本科生毕业设计题 目:网络嗅探器sniff的实现作 者:得巴学 号:20094040000所属学院:信息科学与工程学院专业年级: 网络工程 09级指导教师:哈哈哈职 称:教授 完成时间:2012年11月2013年5月25日吉首大学教务处制网络嗅探器Sniff的实现 得巴(吉首大学信息科学与工程学院,湖南 吉首 416000)摘 要本文主要介绍网络嗅探器sniff软件实现。网络嗅探器Sniff软件能在多个软件平台上运行,比如Linux、window及Unix等平台。通过把网卡设置为混杂模式,来实现对网络上传输的数据包进行捕获与分析。但任何事物都具有俩面性。此分析结果可以获知网络流量使用情况、网络资源使用率以及网络安全规则的执行情况等。作为网络评估、网络故障诊断和网络优化所使用。同时也可以用来对要攻监听网络进行摸底,获取网络结构等。达到非法获得信息的目的。本文主要介绍原始套接字在windows平台下实现了一个网络嗅探器程序,完成了对数据包进行解包、分析数据包的功能。关键词:网络嗅探器;sniff;分析The Design and Implementation of Sniff Network snifferDe Ba (College of Information Science and Engineering, Jishou University, Jishou, Hunan 416000)AbstractSniff network sniffer can be software, can also be a hardware. Network sniffer Sniff software can run on multiple software platforms, such as Linux, window and Unix platform. Sniffer network card can be installed in mixed mode, and realize the network transmission of data packet capture and analysis. But it is also a double-edged sword. The results of this study can be used to analyze the network security of network operation and maintenance may use the agreement analyzer: such as network traffic monitoring, data packet analysis, monitoring of cyber source utilization, implementation of the network security operation rules, identification and analysis of network data and diagnosis and repair network problems etc. Can also be used to data and monitor network, achieve the purpose for obtaining information illegally. This paper mainly introduces the raw socket implements a network sniffer program under Windows platform, completed the data packet unpacking, analysis function of data packets.Keywords: Network sniffer; sniff; analysis 目 录 第一章 引言11.1 网络安全的现状11.2 开发环境11.3本课题的研究意义11.4 开发工具和技术简介21.4.1 Visual C+ 简介21.5 本文研究的内容2第二章 网络嗅探器的基本原理32.1 什么是网络嗅探器sniff32.2 网络嗅探器的实现基础32.2.1 TCP/IP体系结构42.2.2 数据包42.3 常见的sniff52.4 数据包捕获机制的研究52.4.1 WinPcap包捕获机制52.4.1 套接字包捕获机制6第三章 入侵检测系统与嗅探器83.1 入侵检测概念83.2 入侵检测的实现与嗅探器83.2.1 入侵检测与嗅探器的关系93.2.1 数据包嗅探技术在入侵检测系统中的应用9第四章 嗅探器的实现与测试114.1 利用套接字开发网络嗅探程序的步骤114.2 嗅探器的具体实现原理114.3 数据包捕获程序设计144.3.1 定义数据结构144.3.2 对原始套接字进行设置154.3.3 原始数据包存入到缓存164.3.3 对捕获的数据包进行分析174.3.4 数据的分析输出184.4 嗅探器的测试19第五章 总结与展望205.1 总结205.2 展望20参考文献21附录222网络嗅探器sniff的实现 第一章 引言第一章 引言1.1 网络安全的现状随着信息技术的发展,计算机网络的广泛应用,随之带来的安全问题也日益凸显。让我们不得不重视。无论是公司、政府机构还是学校,都有需要保护数据的完整性及可用性。然后计算机网络的连接多式多样、五花八门、终端分布不均匀性。网络最具特色的互连性、开放性这些特征。使网络特别容易受到黑客、恶意软件等的攻击,数据的的完整性、保密性和可用性要如何在这样的环境的得以保护,我们不得不采取全面的安全措施来全方位应对各种网络威胁。因此,网络安全技术就变举足轻重了。网络嗅探器可以在对网络安全管理的过程中,实现对网络数据进行测量和监视,通过利用软件或者硬件嗅探器捕获数据包对数据内容进行分析处理。1.2 开发环境硬件:4G内存以上PC机操作系统:Windows 7操作系统应用软件:Microsoft Visual C+1.3本课题的研究意义嗅探器的分析结果可以获知网络流量使用情况、网络资源使用率以及网络安全规则的执行情况等。作为网络评估、网络故障诊断和网络优化所使用。这样就可以知道网络的实际使用情况,找出网络存在的漏洞和影响网络性能的某些因素。比如ARP攻击,在一个广播式网络中ARP攻击很可能造成整个网段的瘫痪。要及时的知道这些情况。我们可以通过网络嗅探器抓包分析来获取。再者网络的安全策略的执行情况,是否有受到攻击来自,来自哪里的攻击。几乎大型的网络都会对出口做个镜像,用来分析数据并且备份存储数据一段时间。网络嗅探器可以在对网络安全管理的过程中,实现对网络数据进行测量和监视,通过利用软件或者硬件嗅探器捕获数据包对数据内容进行分析处理。1.4 开发工具和技术简介1.4.1 Visual C+ 简介Microsoft Visual C+,(简称Visual C+、MSVC、VC+或VC)微软公司的C+开发工具,具有集成开发环境,可提供编辑C语言,C+以及C+/CLI等编程语言。VC+整合了便利的除错工具,特别是整合了微软视窗程式设计(Windows API)、三维动画DirectX API,Microsoft .NET框架。目前最新的版本是Microsoft Visual C+ 2012。Microsoft VisualC+是Microsoft公司推出的开发Win32环境程序,面向对象的可视化集成编程系统。它不但具有程序框架自动生成、灵活方便的类管理、代码编写和界面设计集成交互操作、可开发多种程序等优点,而且通过简单的设置就可使其生成的程序框架支持数据库接口、OLE2,WinSock网络、3D控制界面。它以拥有“语法高亮”,IntelliSense(自动完成功能)以及高级除错功能而著称。比如,它允许用户进行远程调试,单步执行等。还有允许用户在调试期间重新编译被修改的代码,而不必重新启动正在调试的程序。其编译及建置系统以预编译头文件、最小重建功能及累加连结著称。这些特征明显缩短程式编辑、编译及连结花费的时间,在大型软件计划上尤其显著。1.5 本文研究的内容本文主要通过一下几个方面展开:1.课题的意义。主要包括网络嗅探器在网络安全、网络管理中的应用2.网络嗅探器的概念及技术的研究。主要包括网络嗅探器的概念、网络嗅探器的工作原理及常见网络嗅探器的实现原理等。3.网络嗅探程序的实现。主要工作包括:给出了一个网络嗅探程序的系统框架、数据包捕获程序的设计、数据包的解析、数据的显示等。4.网络嗅探程序的性能测试与评价,得出结论。V网络嗅探器sniff的实现 第二章 网络嗅探器的基本原理 第二章 网络嗅探器的基本原理2.1 什么是网络嗅探器sniff嗅探器就是sniff,嗅探器可以窃听网络上流经的数据包。使用二层交换机的局域网是基于共享机制,局域网能的所有用户能接收到数据包,网卡通过MAC地址来确定是否是自己所需要的数据包。如果是的那么就收,如果不是的直接丢弃。在这里就要用到网卡的混杂模式,在这个模式下默认接收所有经过网卡的数据。而使用三层交换机或者路由器的网络就可能是处于网络层。网络层是通过ip来区分是不是自己所需要的数据。通过路由转发的数据,就不一定所有数据都会经过主机网卡。那么解决的办法就是ARP欺骗,伪造要获取的用户ip和mac从而获取到数据包。复制一份然后再转发出去。 数据在网络的数据链路层上是通过帧(Frame)为单位进行传输的,帧是由几不同部分组成,各个部分执行不同的功能。帧通需要过特定的NIDS(网络驱动程序)进行成型,再通过网卡发送到网络介质上,通过网络介质到达它们的目的主机,在目的主机的一端执行数据拆包。接收端主机的网卡捕获到这些帧,然后告诉操作系统帧到达的情况,再对其进行存储。所以, 一个网络嗅探程序必须也使用先对应的网络协议来分析、拆包嗅探到的数据包, 所以嗅探器也就必须要能识别出哪个协议对应于要解析的数据片断,这样才能对数据包进行正确的解码。 2.2 网络嗅探器的实现基础本文只要介绍windows平台下的嗅探器实现方式。windows网络封包截获技术与windows网络驱动程序遵循网络协议体系结构密不可分的。万丈高楼平地起,基础是关键。首先要能接收到数据帧,网卡有四种接收模式:组播接收方式这个极少用到,它是个D类地址;广播接收方式这也是二层交换网络的核心也是下面要说到的。在网络上监听数据包来获取敏感信息。从原理上来说,在一台计算机中,当网卡接收到一个数据帧,由于网卡设置的混杂模式,所以网卡不管数据帧的目的MAC地址是否是自己需要的都会接收。接收成功后,NIC驱动程序会根据数据帧的长度给它分配缓冲区并将数据帧从网卡存入到缓冲区。 总的来说,首先,在二层交换网络中基于广播方式传送数据的这一特性,使的所以物理信号都要经过网络嗅探器主机(同一网段)。其次,通过把网卡设置成混杂模式,使得网卡能够接收到所以通过它的数据,而不对数据帧的MAC地址做判断。最后,嗅探器要实现数据抓包并分析,网络嗅探程序必须也使用与其先对应的网络协议来分析、拆包嗅探到的数据包,这就离不开协议和相关网络基础知识。2.2.1 TCP/IP体系结构开放系统互连模型是个七层网络模型,按照各层实现的不同功能划分七层:应用层、表示层、会话层、传输层、网络层、数据链路层及物理层。TCP/IP 体系也遵循这样一个七层标准,只不过它在OSI模型上做了压缩,将表示层和会话层合并在应用层中,所以实际上和我们打交道的TCP/IP只有5层而已,网络分层决定了它们在各层的分布以及要实现的功能。现实中有许多成功的协议都是基 于OSI模型的。下面列出了TCP/IP的网络体系结构各层常见的协议:图1-1TCP/IP的网络体系结构(部分) 应用层SMTPDNSHTTPFTPTELNET传输层TCPUDPSPX NetBIOS NetBEUI 网络层IPICMPIGMPARPRARP数据链路层以太网帧中继ATM点对点协议HDLC物理层网卡电缆双绞线光纤从图1-1中我们可以看出,第一层物理层和第二层链路层是TCP/IP的基础,但是TCP/IP本身并不关心底层,因为数据链路层上的网络设备驱动程序把上层协议和实际的物理接口进行了隔离。网络设备驱动程序位于介质访问子层(MAC)。 2.2.2 数据包包的构造有点像洋葱,它是由各层连接的协议组成的。在每一层,包都由包头与包体两部分组成。在包头中存放与这一层相关的协议信息,在包体中存放包在这一层的数据信息。这些数据也包含了上层的全部信息。在每一层上对包的处理将从上层获取的全部信息作为包体,然后依本层的协议在加上包头。这种对包的层次性操作(每一层均加上一个包头)一般称为封装。在应用层,包头含有需被传送的数据。当构成下一层(传输层)的包时,传输控制协议(TCP)或用户数据报协议(UDP)从应用层将数据全部取来,然后在加装上本层的包头。当构筑再下一层(网间网层)的包时,IP协议将上层的包头与包体全部当做本层的包体,然后再加装上本层的包头。在构筑最后一层(网络接口层)的包时,以太网或其它网络协议将IP层的整个包作为包体,再加上本层的包头,在数据包过滤系统看来,包的最重要信息是各层依次加上的包头。2.3 常见的sniff嗅探器sniff有硬件和软件两种实现方式。硬件网络嗅探器灵活性差、高性能但价格昂贵。软件网络嗅探器具有实现方便、布置灵活成本低的优势。软件版本需要平台支持,比较常见的Linux系统下的tcpdump、hp-ux系统平台下的nfswatch以及windows系统平台下的lpman,FoxSniffe、Wireshark等以上的都是免费软件可以在网上自由下载,也许不够专业无法完成特殊要求。比如Wireshark你可以用它检查资讯安全相关问题,也可以新的通讯协定除错,作为学生你可以用它学习网络协定的相关知识。但他不是入侵侦测软件。不会对对于网络上的异常流量行为进行提示或者报警。2.4 数据包捕获机制的研究目前国内外在网络嗅探技术中使用的包捕获方法,大致可以分为两类:一类是依靠操作系统内核本身所提供的捕获机制;另一类则是由应用软件或者系统开发包在安装包捕获驱动程序的基础上实现,这种抓捕机制主要用在Win32平台下的开发。系统内核本身所提供的捕获机制主要有四种:基于BSD的Unix系统内核实现的BPF(Berkeley packet Filter),Solaris系统下内嵌子系统来实现的DLPI (Data Link Provider Interface),以及NIT(Network Interface Tap)和Sock Packet类型套接口。从性能上来看Sock Packet最弱。由于Windows操作系统本身没有提供内置的包捕获机制。所以需要依靠数量很少并且功能有限的应用程序编程接口(API)调用来实现。WinPcap(Windows Packet Capture)是windows 32位系统上的最早用来捕获数据包而开放系统软件包,具备强有力的可扩展的框架结构。WinPcap包含了许多以前系统所不具备的创新特性。下面我们将对目前比较流行的基于WinPcap软件包所提供的捕获机制进行简单介绍。2.4.1 WinPcap包捕获机制WinPcap源于BPF和Libpcap两个函数库,专门为Windows的网络监测程序设计。它包括三个组件:低级的动态连接库Packet.dll、内核级的数据包捕获驱动程序NPF和WinPcap动态链接库。WinPcap是由微软的一个资助项目,基于NDIS的核心,只是对NDIS进行了封装,它为windows 32位平台应用程序提供访问网络底层的能力。核心部分数据包捕获驱动程序NPF主要实现:数据捕获和按照规则过滤数据包;发送数据包;存储数据包;统计和收集通信过程中的信息。数据捕获、发送、;在数据报发往应用程序之前,按照自定义的规则将某些特殊的数据报过滤掉;在网络上发送原始的数据报;收集网络通信过程中的统计信息。WinPcap采用的是分层化的驱动程序模型,WinPcap核心是基于NDIS的。NDIS实现了在Windows 平台下网卡设备驱动和WinPcap包捕获驱动的交互。而且包捕获驱动既与网络驱动通信又与用户应用程序通信,所以它在NDIS结构中如同一个协议驱动,对WindowsNT操作系统中的NDIS结构中的高端驱动进行编程,这样编制的程序与上层应用程序更容易连接,应用程序对驱动设置的工作也更方便。如图2-1所示: 应用程序应用程序协议驱动包捕获驱动NIC驱动数据包核心层网络层图2-1 包捕获驱动在NDIS中所处位置2.4.1 套接字包捕获机制TCP/IP协议由加利福尼亚大学在UNIX操作系统下开发实现的。套接字(Socket)计算机系统为了实现应用程序与TCP/IP协议交互所开发的协议。常见的有三种接字类型 :流套接字TCP协议,是一种面向连接、特供可靠的数据传输模式。他对数据的无差错、有无重复发送、接收的顺序对错做了要求。是一种可靠的数据传输;数据报套接字UDP协议,提供了一种无连接的服务,不保证传输可靠性、是否重复、顺序对错。反正就是发完完事剩下不管。好处是速度快。原始套接字,简单的理解就是可以跨协议读取数据。Socket实质提供的是能是进程通信的端点,双方先各自创建一个通信端点来完成通信,一个完整的socket就类是一个完整信息的信封,写了信件的类型,自己的地址,对方的地址,自己的名字。完整的socket满足协议,本地地址,本地端口,目的地址,目的端口。Socket是一种面向C-S模式(客户和服务器模式),Socket一些特殊端口是个服务器使用的也叫公有端口。客户端的Socket端口是系统分配的。Socket起到了对编写网络应用程序的一种简化,因为他特供了一个高层接口,使得你不需要精通底层的细节。下面简单介绍重要的socket系统调用。函数socket()用来创建一个socket对象,socket()函数的原型如下:SOCKET socket(int af, int type, int protocol);创建一个socket实际上可以理解成向系统申请一个socket号。af(Address Family)套接字地址族,如表2.2所示。表2.2 Linux支持的套接字地址族套接字地址族描述UNIXUNIX域套接字INET通过TCP/IP协议支持的Internet地址族AX25Amater radio X25IPXNovell IPXAPPLETALKAppletalk DDPX25X25协议族、socket类型和协议常用的组合如表2.3所示:表2.3 系统调用三参数组合关系协议族(af)Socket类型(type)协议(UNIX表示)实际协议AF_INETSock_DGRAMIPPROC_UDPUDPSock_STREAMIPPROC_TCPTCPSock_RAMIPPROC_ICMPICMPSock_RAMIPPROC_RAM某低级协议本地地址使用函数bind()绑定当一个socket被创建以后就会有一个地址族,但没有被命名。bind()需要实现是将的套接字地址和需要所创建的套接字号联系起来,对套接字赋予名字。bind(sock, (PSOCKADDR)&addr_in, sizeof(addr_in); V网络嗅探器sniff的实现 第三章 入侵检测系统与嗅探器 第三章 入侵检测系统与嗅探器3.1 入侵检测概念 入侵检测系统是网络安全的一个重要组成部分,通过学习,对入侵检测系统有了一定的了解,下面对入侵检测技术做一个总体介绍。入侵检测技术与防火墙、PKI等技术不同,防火墙、PKI只是立足于防御,入侵检测通过对网络的检测,对用户的操作是否符合安全规则进行判断,从而发现违规操作、攻击行为。以保证网络资源的的机密性、可用性和完整性。为了提高入侵检测系统(IDS)产品、组件及与其他安全产品之间的互操作性,美国国防高级研究计划署(DARPA)和互联网工程任务组(IETF)的入侵检测工作组(IDWG)发起制定了一系列建议草案,从体系结构、API、通信机制、语言格式等方面规范IDS的标准。DARPA提出的公共入侵检测框架(CIDF)的通用模型。将入侵检测系统分成了四大模块:事件产生器,事件产生器获得数据并向 IDS 的其它模块提供;事件分析器,事件分析器针对数据进行入侵分析;响应单元响应单元对分析的结果作出不同的响应;以及事件数据库,数据库存储以上三个模块收集及分析的各种数据。在数据包捕获的基础上,检测的技术上分为三类:异常检测,定义正常用户的规则模型,当检测到与正常模型不同的行为发生时,判断是否有入侵行为发生;误用检测,通过分析已有的入侵模式,用相关规则来定义入侵模式,再来检测是否存在入侵行为;静态分析,对系统配置进行分析,检查系统是否存在被入侵。3.2 入侵检测的实现与嗅探器入侵检测的实现由四部分组成:数据包嗅探解析部分、数据行为检测部分、算法部分和扫描检测部分。在这里以误用检测方法对入侵检测的实现做更详细的介绍。系统编写构架在编写入侵检测系统时,需要遵循CIDF 标准来进行系统的设计,首先通过数据包嗅探技术获得网络上流通的数据包;其次通过攻击特征库对嗅探到的数据包进行入侵行为的检测;再次对入侵数据包做出报警;最后将这些入侵事件纪录到数据库,便于查询和分析。3.2.1 入侵检测与嗅探器的关系数据包嗅探技术是实现入侵检测的基础,将数据包从共享网络线路中捕获,并将其提取到应用程序中,这个过程要依赖于网络物理层到应用层以及操作系统本身各方面进行协调、设置,下面通过实例来看一下以太网络中数据包的流程:1. 物理层,在一个以太局域网,数据在共享的网络介质(网线、HUB)中以广播的形式到达局域网每一个节点;2. 数据链路层,节点的网络适配器(网卡 NIC)查看到来的数据帧(Frame),通过一系列的检验,将到来的大量的数据帧中属于自己且正确合法的数据帧重构成数据包(Packet)送入操作系统的协议栈;3. 网络层至运输层,操作系统的协议栈通过这两层中的 IP、TCP、UDP 等协议判断到来的数据包是否属于本操作系统的接收范围(根据 IP 地址),是否属于本操作系统上的应用程序的接收范围(根据 Port 端口号),如果所属范围正确并且数据包合法,操作系统通过端口将数据包重构成报文(Segment)送入应用程序。3.2.1 数据包嗅探技术在入侵检测系统中的应用为了嗅探到网络中的任意一个数据包,必须对物理线路、网卡、操作系统进行完全的配合,首先从网络构成上讲,嗅探技术并不是适合所有类型的网络,不同传输介质的网络的可监听性是不同的。一般来说,以太网被监听的可能性比较高,因为以太网是一个广播型的网络,在一个标准的以太网子网上,多台计算机通过一条线路互联,且任何时刻,电缆上只有一个数据包存在,为了保证多台计算机能共享同一线路,以太网使用了CSMA/CD(Carrier Sense MultipleAccess/Collision Detection)载波侦听多路访问/冲突检测,这样一来,共享线路上的所有以太网卡及相关设备总是处于对线路上的信号进行监听的状态中,这使得每一台机器都能够探知并接受线路上的数据流。事实证明嗅探适用于基于广播包的网络,如利用广播技术来分发数据包的连通网络(或者使用令牌的网络,只不过因为令牌不一定经过本机器,所以只能嗅探到网络中部分数据包)。此外如果在一个子网内部进行嗅探,而子网顶部存在着诸如交换机这类设备,由于它能够阻止广播,所以就不能够对子网内其他的机器进行监听,若想要对此子网进行监听,就必须处于与此交换机同级的包交换网络中。例如从路由器到某一子网的共享网络中安装一个 hub,在将监听机器和子网交换机用此 hub 连接起来,这样,就能够对此子网进行监听了,另一种办法就是在交换机上给监听机器做端口映射,指明让它接受经过交换机的所有数据包。当数据经过数据链路层后,就要通过操作系统协议栈的审核了,系统协议栈在 TCP/IP 网络模型跨越的层次非常多,它们直接从位于系统的数据链路层提取数据,通过在这一层的开发环境中设置混杂模式,就可以成功的接收从驱动层来的各种数据包。大多数的操作系统在这一层使用的是 Socket 套接字技术,它们通过函数 ioctlsocket(socket, SIO_RCVALL, &Value)来实现混杂模式接收数据包。通过 Socket 的处理,数据流(Bits)已经变成了能识别的数据结构,最后协议栈将数据信息传入应用层应用程序中。最终,所有的数据变成可以识别的文字、符号出现在机器的视频输出上。网络嗅探器sniff的实现 第四章 嗅探器的实现与测试 第四章 嗅探器的实现与测试4.1 利用套接字开发网络嗅探程序的步骤利用套接字开发网络嗅探器程序时的一般步骤如图4-1所示:图4-1 嗅探器工作流程如图4-1所示,在利用套接字开发网络嗅探器程序时的一般步骤是:首先,创建原始套接字,并设置其操作选项;其次将原始套接字绑定到本地网卡地址上;网卡在混杂模式下默认接收所有数据,要实现抓包分析我们需要在这里将网卡设置成混杂模式。4.2 嗅探器的具体实现原理嗅探器作为一种网络应用程序,Socket起到了对编写网络应用程序的一种简化,因为他特供了一个高层接口,使得你不需要精通底层的细节。但是通常的套接字程序具有它的局限性它无法接收到不属于自己而经过的数据包。网络接口会对数据包做判断,丢弃不属于自己的。而嗅探器的设计要求能够接收到所有数据,这就意味着需要把网卡设置成一种特殊的混杂模式。如何把网卡设置成混杂模式的通过原始套接字(raw socket)具体到编程实现上。这与我们通常使用的数据流套接字TCP和数据包套接字UDP有很大的区别。在创建了原始套接字后,IP头操作选项可以通过setsockopt()函数来实现,然后再通过bind()函数bind(sock, (PSOCKADDR)&addr_in, sizeof(addr_in)将原始套接字绑定到本地网卡。通过WSAIoctl ()来进行设置,让网卡能够接收到所有的数据。然后再用recv()函数来实现对UDP套接字和TCP套接字的获取。到这里实际上已经是可以一对网络进行嗅探了。然而原始套接字的特殊性,它包含了数据传输过程中的IP头、 TCP头等信息但是这与流、数据报套接字不同。这样可以通过对数据中的原始协议进行分析可以得出网络相关信息。通过对这些在低层传输的原始信息的分析可以得到有关网络的一些信息。数据发送是个打包过程,那么数据读取就可以理解成剥洋葱了。发送数据时数据从应用层到传输层需要进行打包,如果是TCP数据就会添加TCP数据段头,或是UDP数据就会添加UDP数据段头。UDP报头比较简单,具体格式如图4-2所示: 图4-2 UDP数据段头格式16位源端口号16位目的端口号16位UDP长度16位UDP校验和数据(如果有)对于此UDP数据段头的分析在编程实现中可通过数据结构UDPPacketHead来定义:struct UDPPacketHead WORD SourPort; /16位源端口WORD DestPort; /16位目的端口WORD Len; /16位长度WORD ChkSum; /16位校验和;TCP数据报头比UDP数据报头要复杂,除了20个固定字节,还有不固定的可选项,图4-3给出TCP数据段头的格式组成:图4-3 TCP数据段头格式 源端口目的端口序列号确认号数据偏移保留URGACKPSHRSTSYNFIN窗口检验和紧急指针选项(长度可变)填充对于此TCP数据段头的分析在编程实现中可通过数据结构TCPPacketHead来定义: struct TCPPacketHead WORD SourPort; /源端口WORD DestPort; /目的端口DWORD SeqNo; /32位序列号DWORD AckNo; /32位确认号BYTE HLen; /4位首部长度BYTE Flag; /6位标志位WORD WndSize; /16位窗口大小WORD ChkSum; /16位校验和WORD UrgPtr; /16位紧急数据偏移量;在网络层,还要给TCP数据包添加一个IP数据段头以组成IP数据报。同样,在实际编程中也需要通过一个数据结构来表示此IP数据段头,下面给出此数据结构的定义: typedef struct _IPHEADER unsigned char header_len:4; /4位首部长度 unsigned char version:4; /4位版本号 unsigned char tos; / 8位服务类型 unsigned short total_len; / 16位总长度 unsigned short ident; / 16位标识符 unsigned short flags; /3位标志位 unsigned char ttl; /8位生存时间 unsigned char proto; / 8位协议 ( IP , TCP, UDP etc) unsigned short checksum; /16位IP首部校验和 unsigned int sourceIP; /32位源IP地址 unsigned int destIP; /32位目的IP地址IPHEADER;IP数据段头格式如图4-4所示: 图4-4 IP数据段头格式版本首部长度区分服务总长度标识标志片偏移生存时间协议首部校验和源地址目的地址可选字段(可选长度)填充数据4.3 数据包捕获程序设计根据前面的设计思路,本文在windows平台下实现了一个嗅探器程序,开发工具使用visual C+。下面就给出本设计的部分程序代码,该设计可以捕获到所有经过本地网卡的数据包,并可从中分析出协议、IP源地址、IP目标地址、TCP源端口号、TCP目标端口号等信息。4.3.1 定义数据结构在实际编程中也需要通过一个数据结构来表示此IP数据段头,下面给出此数据结构的定义:typedef struct _IPunion BYTE Version; / 版本BYTE HdrLen; / IHL;BYTE ServiceType; / 服务类型WORD TotalLen; / 总长WORD ID; / 标识union WORD Flags; / 标志WORD FragOff; / 分段偏移;BYTE TimeToLive; / 生命期BYTE Protocol; / 协议WORD HdrChksum; / 头校验和DWORD SrcAddr; / 源地址DWORD DstAddr; / 目的地址BYTE Options; / 选项 IP; typedef IP * LPIP;typedef IP UNALIGNED * ULPIP;4.3.2 对原始套接字进行设置对原始套接字进行设置,主要代码清单:/ 检查 Winsock 版本号,WSAData为WSADATA结构对象WSAStartup(MAKEWORD(2, 2), &WSAData);/ 创建原始套接字sock = socket(AF_INET, SOCK_RAW, IPPROTO_RAW);/ 设置IP头操作选项,其中flag 设置为ture,亲自对IP头进行处理setsockopt(sock, IPPROTO_IP, IP_HDRINCL, (char*)&flag, sizeof(flag);/ 获取本机名gethostname(char*)LocalName, sizeof(LocalName)-1);/ 获取本地 IP 地址pHost = gethostbyname(char*)LocalName);/ 填充SOCKADDR_IN结构addr_in.sin_addr = *(in_addr *)pHost-h_addr_list0; /IPaddr_in.sin_family = AF_INET;addr_in.sin_port = htons(57274);/ 把原始套接字sock 绑定到本地网卡地址上bind(sock, (PSOCKADDR)&addr_in, sizeof(addr_in);/ dwValue为输入输出参数,为1时执行,0时取消DWORD dwValue = 1; / 设置 SOCK_RAW 为SIO_RCVALL,以便接收所有的IP包。其中SIO_RCVALL/ 的定义为: #define SIO_RCVALL _WSAIOW(IOC_VENDOR,1)ioctlsocket(sock, SIO_RCVALL, &dwValue);4.3.3 原始数据包存入到缓存前面的工作基本上都是对原始套接字进行设置,在将原始套接字设置完毕,使其能按预期目的工作时,就可以通过recv()函数从网卡接收数据了,接收到的原始数据包存放在缓存区中,具体的实现代码如下:UINT threadFunc ( LPVOID p )CIpmonDlg *pDlg = static_cast(p) ;char buf 1000 , *bufwork ;MSG msg ;int iRet ;DWORD dwErr ; char *pSource , *pDest ;IPHEADER *pIpHeader ;in_addr ina ;char szSource 16 , szDest16 , szErr 50 ;char *pLastBuf = NULL ;intHdrLen, totallen;WORDsourport, destport;struct TCPPacketHead*pTCPHead;struct ICMPPacketHead*pICMPHead;struct UDPPacketHead*pUDPHead;BYTE*pdata = NULL;PeekMessage(&msg, NULL, WM_USER, WM_USER, PM_NOREMOVE); pDlg-m_threadID = GetCurrentThreadId() ;while( TRUE ) if( PeekMessage( &msg , 0 , WM_CLOSE,WM_CLOSE,PM_NOREMOVE ) ) closesocket( pDlg-m_s ) ;/关闭套接字 pDlg-m_threadID = 0 ; pDlg-m_start.EnableWindow(TRUE) ; break ;memset( buf , 0 , sizeof(buf) ) ;iRet = recv( pDlg-m_s , buf , sizeof( buf ) , 0 ) ;/接收数据4.3.3 对捕获的数据包进行分析前面的工作基本上都是对原始套接字进行设置,在将原始套接字设置完毕,使其能按预期目的工作时,就可以通过recv()函数从网卡接收数据了,接收到的原始数据包存放在缓存RecvBuf中,缓冲区长度BUFFER_SIZE定义为65535。然后就可以根据前面对IP数据段头、TCP数据段头的结构描述而对捕获的数据包进行分析:数据包被捕获后然后就可以根据前面对IP数据段头、TCP数据段头的结构描述而对捕获的数据包进行分析。这是嗅探器程序的一个重要的组成部分。如图4-5所示:数据包捕获模块数据包包头分析调用switch()函数TCPUDPICMP图4-5 数据包解析的简单流程图4-5 所示为数据包的解析模块,该模块对捕获的数据包进行拆包分析,根据不同的协议类型分析其IP地址,数据包大小,端口号等,具体代码实现如下:while (true)/ 接收原始数据包信息int ret = recv(sock, RecvBuf, BUFFER_SIZE, 0);if (ret 0)/ 对数据包进行分析,并输出分析结果ip = *(IP*)RecvBuf;tcp = *(TCP*)(RecvBuf + ip.HdrLen);TRACE(协议: %srn,GetProtocolTxt(ip.Protocol);TRACE(IP源地址: %srn,inet_ntoa(*(in_addr*)&ip.SrcAddr);TRACE(IP目标地址: %srn,inet_ntoa(*(in_addr*)&ip.DstAddr);TRACE(TCP源端口号: %drn,tcp.SrcPort);TRACE(TCP目标端口号:%drn,tcp.DstPort);TRACE(数据包长度: %drnrnrn,ntohs(ip.TotalLen);4.3.4 数据的分析输出其中,在进行协议分析时,使用了GetProtocolTxt()函数,该函数负责将IP包中的协议(数字标识的)转化为文字输出,该函数实现如下:#define PROTOCOL_STRING_ICMP_TXT ICMP#define PROTOCOL_STRING_TCP_TXT TCP#define PROTOCOL_STRING_UDP_TXT UDP#define PROTOCOL_STRING_SPX_TXT SPX#define PROTOCOL_STRING_NCP_TXT NCP#define PROTOCOL_STRING_UNKNOW_TXT UNKNOWCString CSnifferDlg:GetProtocolTxt(int Protocol)switch (Protocol)case IPPROTO_ICMP : /1 /* control message protocol */return PROTOCOL_STRING_ICMP_TXT;case IPPROTO_TCP : /6 /* tcp */return PROTOCOL_STRING_TCP_TXT;case IPPROTO_UDP : /17 /* user datagram protocol */return PROTOCOL_STRING_UDP_TXT;default:return PROTOCOL_STRING_UNKNOW_TXT;4.4 嗅探器的测试网络嗅探器程序设计完成后,在Windows平台下进行运行调试,修改错误,使其能完成捕获数据包和分析数据包的功能,并将解析结果在MFC界面显示出来,如图4-7所示:图4-6 分析结果在界面中的显示情况网络嗅探器能完成预期的要求,进行数据包截获、分析,显示出分析结果。由图4-7可以观察到捕获模块能够实现将网络接口设置为混杂模式,同时捕获局域网内的数据包,在这里还可以观察到网络状态及网络数据的流动情况,供网络分析之用。网络嗅探器sniff的实现 第五章 总结与展望 第五章 总结与展望5.1 总结 本次课题的主要研究内容是利用套接字开发网络嗅探器的程序设计,设计要求完成对流经本地网卡的所有数据包的捕获,分析协议类型,并根据不同的协议类型对数据包进行了进一步的分析,包括分析数据包的源IP地址、目的IP地址、源端口号、目的端口号、大小等。设计完成后经测试能实现预期要求的功能。但是仍然存在一些不足之处,例如:1.由于时间和所学知识有限,只对数据包作了简单分析,分析内容不是很全面;2.本论文中的嗅探器适用于基于广播包的网络,而对于诸如交换机这类设备,由于它能够阻止广播,所以就不能够对子网内其他的机器进行监听,若想要对此子网进行监听,就必须处于与此交换机同级的包交换网络中。通过对该课题的研究,让我对嗅探技术有了进一步的了解,对其两面性在网络中产生的影响有了更深的认识,为了打破以上局限性,还需要结合已学知识对网络嗅探技术方面的知识作进一步的学习。5.2 展望随着信息技术的发展,计算机网络的广泛应用,随之带来的安全问题也日益凸显。让我们不得不重视。无论是公司、政府机构还是学校,都有需要保护数据的完整性及可用性。然后计算机网络的连接多式多样、终端分布不均匀性。网络的互连性、开放性这些特征。使网络特别容易受到黑客、恶意软件等的攻击,数据的的完整性、保密性和可用性要如何在这样的环境的得以保护,我们不得不采取全面的安全措施来全方位应对各种网络威胁。因此,网络安全技术就变举足轻重了。网络嗅探器可以在对网络安全管理的过程中,实现对网络数据进行测量和监视,通过利用软件或者硬件嗅探器捕获数据包对数据内容进行分析处理。网络嗅探器终究会在网络安全和网络优化领域占据一席之地。网络嗅探器sniff的实现 参考文献1许福,舒志,张威编著. VC+程序设计技巧与实例M. 北京: 中国铁道出版社,2002。2丁展,刘海英等. VC+网络通信编程实用案例精选M. 北京: 人民邮电出版社,2001。3殷肖川,刘志宏,姬伟峰,万映辉. 李增智,唐亚哲主审M. 网络编程与开发技术.西安: 西安交通大学出版社,2004。4Greg Holden美.王斌,孔璐译. 防火墙与网络安全入侵检查和VPNSM.北京:清华大学出版社,2003。5马安鹏. VC+ 6.0程序设计导学M. 北京: 清华大学出版社,2002。6朱雁辉,朱雁冰. Windows防火墙与网络封包截获技术M.北京:电子工业出版社,2002。7黄维通,姚瑞霞. VC+6.0程序设计教程M. 北京:机械工业出版社,2004。8William R.C Cheswick美,戴宇坤等译. 防火墙与因特网安全M.北京: 机械工业出版社,2000。9吴金平等. Visual C+ 6.0编程与实践M.北京:中国水利水电出版社,2004。10李秀敏,凌宇欣. Visual C+6.0 范例入门与提高M. 北京:清华大学出版社,2003。11 鲁荣波. Windows平台下的网络封包截获技术12 http:/blog.csdn.net/yincheng01/article/details/8562751 网络参考文献附录附录中包含的是此网络程序绝大部分代码。/ typedef struct 是结构体相当于java里面的对象typedef struct char String4 * 4; IP_ADDRESS_STRING, *PIP_ADDRESS_STRING, IP_MASK_STRING, *PIP_MASK_STRING;/ IP_ADDR_STRING - store an IP address with its corresponding subnet mask,/ both as dotted decimal strings/typedef struct _IP_ADDR_STRING struct _IP_ADDR_STRING* Next; IP_ADDRESS_STRING IpAddress; IP_MASK_STRING IpMask; DWORD Context; IP_ADDR_STRING, *PIP_ADDR_STRING;/ ADAPTER_INFO - per-adapter information. All IP addresses are stored as/ stringstypedef struct _IP_ADAPTER_INFO struct _IP_ADAPTER_INFO* Next; DWORD ComboIndex; char AdapterNameMAX_ADAPTER_NAME_LENGTH + 4; char DescriptionMAX_ADAPTER_DESCRIPTION_LENGTH + 4; UINT AddressLength; BYTE AddressMAX_ADAPTER_ADDRESS_LENGTH; DWORD Index; UINT Type; UINT DhcpEnabled; PIP_ADDR_STRING CurrentIpAddress; IP_ADDR_STRING IpAddressList; IP_ADDR_STRING GatewayList; IP_ADDR_STRING DhcpServer; BOOL HaveWins; IP_ADDR_STRING PrimaryWinsServer; IP_ADDR_STRING SecondaryWinsServer; time_t LeaseObtained; time_t LeaseExpires; IP_ADAPTER_INFO, *PIP_ADAPTER_INFO;/ IP_PER_ADAPTER_INFO - per-adapter IP information such as DNS server list.typedef struct _IP_PER_ADAPTER_INFO UINT AutoconfigEnabled; UINT AutoconfigActive; PIP_ADDR_STRING CurrentDnsServer; IP_ADDR_STRING DnsServerList; IP_PER_ADAPTER_INFO, *PIP_PER_ADAPTER_INFO;/ FIXED_INFO - the set of IP-related information which does not depend on DHCP/typedef struct char HostNameMAX_HOSTNAME_LEN + 4 ; char DomainNameMAX_DOMAIN_NAME_LEN + 4; PIP_ADDR_STRING CurrentDnsServer; IP_ADDR_STRING DnsServerList; UINT NodeType; char ScopeIdMAX_SCOPE_ID_LEN + 4; UINT EnableRouting; UINT EnableProxy; UINT EnableDns; FIXED_INFO, *PFIXED_INFO;struct tcp_keepalive u_long onoff; u_long keepalivetime; u_long keepaliveinterval;struct TCPPacketHead WORD SourPort;WORD DestPort;DWORD SeqNo;DWORD AckNo;BYTE HLen;BYTE Flag;WORD WndSize;WORD ChkSum;WORD UrgPtr;struct ICMPPacketHead BYTE Type;BYTE Code;WORD ChkSum;struct UDPPacketHead WORD SourPort;WORD DestPort;WORD Len;WORD ChkSum;typedef struct _PROTN2T int proto ;char *pprototext ;PROTN2T ; #define PROTO_NUM 11 /* The IP header */typedef struct _IPHEADER unsigned char header_len:4; unsigned char version:4; unsigned char tos; / type of service unsigned short total_len; / length of the packet unsigned short ident; / unique identifier unsigned short flags; unsigned char ttl; unsigned char proto; / protocol ( IP , TCP, UDP etc) unsigned short checksum; unsigned int sourceIP; unsigned int destIP;IPHEADER;BOOL CIpmonDlg:OnInitDialog()CDialog:OnInitDialog();/ Add About. menu item to system menu./ IDM_ABOUTBOX must be in the system command range.ASSERT(IDM_ABOUTBOX & 0xFFF0) = IDM_ABOUTBOX);ASSERT(IDM_ABOUTBOX AppendMenu(MF_SEPARATOR);pSysMenu-AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);/ Set the icon for this dialog. The framework does this automatically/ when the applications main window is not a dialogSetIcon(m_hIcon, TRUE);/ Set big iconSetIcon(m_hIcon, FALSE);/ Set small icon/ TODO: Add extra initialization hereCHARszHostName128 = 0;HOSTENT*pHost = NULL;CHAR*pszIp = NULL;intiNum = 0;if(AfxSocketInit(NULL)=FALSE)AfxMessageBox(Sorry, socket load error!);return FALSE;if(gethostname(szHostName, 128)=0)pHost = gethostbyname(szHostName);if(pHost != NULL)pszIp = inet_ntoa(*(in_addr*)pHost-h_addr_listiNum);m_ipsource = inet_addr(pszIp);else AfxMessageBox(pHost = NULL!);else AfxMessageBox(cant find host name!);/ ListView initializeDWORD dwStyle=GetWindowLong(m_ctrList.GetSafeHwnd(),GWL_STYLE);dwStyle&=LVS_TYPEMASK;dwStyle|=LVS_REPORT;SetWindowLong(m_ctrList.GetSafeHwnd(),GWL_STYLE,dwStyle);m_ctrList.InsertColumn(0,数据,LVCFMT_LEFT,525);m_ctrList.InsertColumn(0,大小,LVCFMT_LEFT,80); m_ctrList.InsertColumn(0,端口,LVCFMT_LEFT,40);m_ctrList.InsertColumn(0,目的地址,LVCFMT_LEFT,100);m_ctrList.InsertColumn(0,端口,LVCFMT_LEFT,40);m_ctrList.InsertColumn(0,源地址,LVCFMT_LEFT,100);m_ctrList.InsertColumn(0,协议,LVCFMT_LEFT,50); :SendMessage(m_ctrList.m_hWnd, LVM_SETEXTENDEDLISTVIEWSTYLE,LVS_EX_FULLROWSELECT, LVS_EX_FULLROWSELECT); / Here read all IPs of this hostDWORD dwSize = 0 ; GetIpAddrTable( NULL , &dwSize, FALSE ) ; PMIB_IPADDRTABLE pIpAddrTable = (PMIB_IPADDRTABLE )new BYTE dwSize ; if( pIpAddrTable )if( GetIpAddrTable( (PMIB_IPADDRTABLE)pIpAddrTable, / / buffer for IP table&dwSize, / size of bufferFALSE / sort by IP address ) = NO_ERROR ) if( pIpAddrTable-dwNumEntries 2 ) / Second is MS TCP loopback IP ( 127.0.0.1 )m_Multihomed = TRUE ;char szIP16;for( int i = 0 ; i dwNumEntries ; i+ )in_addr ina ;ina.S_un.S_addr = pIpAddrTable-tablei.dwAddr ; char *pIP = inet_ntoa( ina ) ;strcpy( szIP , pIP ) ;if( stricmp( szIP , 127.0.0.1 ) )m_IPArr.Add(pIpAddrTable-tablei.dwAddr) ;delete pIpAddrTable ;return TRUE; / return TRUE unless you set the focus to a controlvoid CIpmonDlg:OnSysCommand(UINT nID, LPARAM lParam)if (nID & 0xFFF0) = IDM_ABOUTBOX)CAboutDlg dlgAbout;dlgAbout.DoModal();elseCDialog:OnSysCommand(nID, lParam);/ If you add a minimize button to your dialog, you will need the code below/ to draw the icon. For MFC applications using the document/view model,/ this is automatically done for you by the framework.UINT threadFunc ( LPVOID p ) CIpmonDlg *pDlg = static_cast(p) ;char buf 1000 , *bufwork ;MSG msg ;int iRet ;DWORD dwErr ; char *pSource , *pDest ;IPHEADER *pIpHeader ;in_addr ina ;char szSource 16 , szDest16 , szErr 50 ;char *pLastBuf = NULL ;intHdrLen, totallen;WORDsourport, destport;/tcp包头数据结构struct TCPPacketHead*pTCPHead;/icmp包头struct ICMPPacketHead*pICMPHead;/udp包头struct UDPPacketHead*pUDPHead;/字节指针BYTE*pdata = NULL; PeekMessage(&msg, NULL, WM_USER, WM_USER, PM_NOREMOVE); / Force to make the queue pDlg-m_threadID = GetCurrentThreadId() ;while( TRUE ) if( PeekMessage( &msg , 0 , WM_CLOSE,WM_CLOSE,PM_NOREMOVE ) ) closesocket( pDlg-m_s ) ; pDlg-m_threadID = 0 ;pDlg-m_start.EnableWindow(TRUE) ; break ;memset( buf , 0 , sizeof(buf) ) ;iRet = recv( pDlg-m_s , buf , sizeof( buf ) , 0 ) ;if( iRet = SOCKET_ERROR )dwErr = WSAGetLastError() ;sprintf( szErr , Error recv() = %ld , dwErr ) ;continue ;elseif( *buf )bufwork = buf ; pIpHeader = (IPHEADER *)bufwork ; WORD iLen = ntohs(pIpHeader-total_len) ;while( TRUE )if( iLen sourceIP ;pSource = inet_ntoa( ina ) ;strcpy( szSource , pSource ) ;ina.S_un.S_addr = pIpHeader-destIP ;pDest = inet_ntoa( ina ) ;strcpy( szDest , pDest ) ;CString str, strProto, strSourPort, strDestPort, strData, strSize;strProto = get_proto_name( pIpHeader-proto );HdrLen = pIpHeader-header_len&0xf;HdrLen *= 4;totallen = ntohs(pIpHeader-total_len);totallen-=HdrLen;switch(pIpHeader-proto)/如果是 icmp协议case IPPROTO_ICMP:pICMPHead=(struct ICMPPacketHead *)(buf+HdrLen);/strL4.Format( type:%d code:%dn,pICMPHead-Type,pICMPHead-Code);strSourPort = -;strDestPort = -;pdata=(BYTE *)pICMPHead)+ICMP_HEAD_LEN;totallen -= ICMP_HEAD_LEN;break;/如果是tcp协议case IPPROTO_TCP:pTCPHead=(struct TCPPacketHead *)(buf+HdrLen);sourport = ntohs(pTCPHead-SourPort);destport = ntohs(pTCPHead-DestPort);/strL4.Format( sour port:%d,dest port:%d,sourport,destport);strSourPort.Format(%d,sourport);strDestPort.Format(%d,destport);HdrLen = (pTCPHead-HLen)4; /in fact only 4 bitsHdrLen *= 4;pdata=(BYTE *)pTCPHead)+HdrLen;totallen -= HdrLen;break;/如果是udp协议case IPPROTO_UDP:pUDPHead=(struct UDPPacketHead *)(buf+HdrLen);sourport = ntohs(pUDPHead-SourPort);destport = ntohs(pUDPHead-DestPort);/strL4.Format( sour port:%d,dest port:%d,sourport,destport);strSourPort.Format(%d,sourport);strDestPort.Format(%d,destport);pdata=(BYTE *)pUDPHead)+UDP_HEAD_LEN;totallen -= UDP_HEAD_LEN;break;if(pIpHeader-proto = IPPROTO_ICMP)strData.Format(type:%d code:%d data:%s,pICMPHead-Type,pICMPHead-Code,pdata);else strData.Format( %s,pdata);strSize.Format(%d,totallen);pDlg-AddData(strProto,szSource,strSourPort,szDest,strDestPort,strSize,strData);if( iLen total_len = iRet and go outelse / read last part of buf. I wrote it , but always recv() read exactly / the lenght of the packetint iLast = iLen - iRet ;pLastBuf = new char iLen ;int iReaden = iRet ;memcpy( pLastBuf , bufwork , iReaden ) ;iRet = recv( pDlg-m_s , pLastBuf + iReaden , iLast , 0 ) ;if( iRet = SOCKET_ERROR )dwErr = WSAGetLastError() ;sprintf( szErr , Error recv() = %ld , dwErr ) ;break ;elsebufwork = pLastBuf ; pIpHeader = (IPHEADER *)bufwork ;if( iRet = iLast )iRet = iLen ;else / read all last dataiReaden += iRet ;iLast -= iRet ;while( TRUE )iRet = recv( pDlg-m_s , pLastBuf +iReaden , iLast , 0 ) ;if( iRet = SOCKET_ERROR )dwErr = WSAGetLastError() ;sprintf( szErr , Error recv() = %ld , dwErr ) ;break ;else iReaden += iRet ; iLast -= iRet ; if( iLast = 0 ) break ; / while / whileif( pLastBuf )delete pLastBuf ;elseAfxMessageBox( No data on network ) ;continue ;return TRUE ;void CIpmonDlg:OnLookUp() / TODO: Add your control notification handler code herechar szErr 50 , szHostNameMAX_PATH;DWORD dwErr ; SOCKADDR_IN sa;gethostname(szHostName, sizeof(szHostName) ;m_iphostsource = m_ipsource ; m_ipcheckedhost = ntohl(m_iphost) ;if( 0 = m_threadID )SetDlgItemText(IDC_LOOKUP,停止查看! );elseif( m_threadID ) PostThreadMessage(m_threadID,WM_CLOSE,0,0) ; SetDlgItemText(IDC_LOOKUP,开始查看!);m_start.EnableWindow(FALSE) ;return ; DWORD dwBufferLen10 ;DWORD dwBufferInLen= 1 ;DWORD dwBytesReturned = 0 ;m_s = socket( AF_INET , SOCK_RAW , IPPROTO_IP ) ;if( INVALID_SOCKET = m_s )dwErr = WSAGetLastError() ;sprintf( szErr , Error socket() = %ld , dwErr ) ;AfxMessageBox( szErr ) ;closesocket( m_s ) ;return ;int rcvtimeo = 5000 ; if( setsockopt( m_s , SOL_SOCKET , SO_RCVTIMEO , (const char *)&rcvtimeo , sizeof(rcvtimeo) ) = SOCKET_ERROR)dwErr = WSAGetLastError() ;sprintf( szErr , Error WSAIoctl = %ld , dwErr ) ;AfxMessageBox( szErr ) ;closesocket( m_s ) ;return ;sa.sin_family = AF_INET; sa.sin_port = htons(7000);sa.sin_addr.s_addr= m_iphostsource; if (bind(m_s,(PSOCKADDR)&sa, sizeof(sa) = SOCKET_ERROR)dwErr = WSAGetLastError() ;sprintf( szErr , Error bind() = %ld , dwErr ) ;AfxMessageBox( szErr ) ;closesocket( m_s ) ;return ; if( SOCKET_ERROR != WSAIoctl( m_s, SIO_RCVALL , &dwBufferInLen, sizeof(dwBufferInLen), &dwBufferLen, sizeof(dwBufferLen), &dwBytesReturned , NULL , NULL ) ) AfxBeginThread( threadFunc , (LPVOID)this );elsedwErr = WSAGetLastError() ;sprintf( szErr , Error WSAIoctl = %ld , dwErr ) ;AfxMessageBox( szErr ) ;closesocket( m_s ) ;return ;
网站客服QQ:2055934822
金锄头文库版权所有
经营许可证:蜀ICP备13022795号 | 川公网安备 51140202000112号