网络流量监控及分析工具的设计与实现.docx
- 文档编号:10603946
- 上传时间:2023-02-21
- 格式:DOCX
- 页数:21
- 大小:193.29KB
网络流量监控及分析工具的设计与实现.docx
《网络流量监控及分析工具的设计与实现.docx》由会员分享,可在线阅读,更多相关《网络流量监控及分析工具的设计与实现.docx(21页珍藏版)》请在冰豆网上搜索。
网络流量监控及分析工具的设计与实现
1引言
1.1课题背景
随着构建网络基础技术和网络应用的迅速发展以及用户对网络性能要求的提高,使得网络管理成为迫切需要解决的问题,有效的网络管理能够保证网络的稳定运行和持续发展,更重要的是,随着网络规模的扩大和黑客技术的发展,入侵和攻击的案例日益增多,对稳定的网络服务、信息安全、互联网秩序都提出了严峻的挑战,网络安全管理在整个网络管理系统里扮演起更为重要的角色。
1.2网络流量监控的引入
网络安全管理体系中,流量监控和统计分析是整个管理的基础。
流量检测主要目的是通过对网络数据进行实时连续的采集监测网络流量,对获得的流量数据进行统计计算,从而得到网络主要成分的性能指标。
网络管理员根据流量数据就可以对网络主要成分进行性能分析管理,发现性能变化趋势,并分析出影响网络性能的因素及问题所在。
此外,在网络流量异常的情况下,通过扩展的流量检测报警系统还可以向管理人员报警,及时发现故障加以处理。
在网络流量检测的基础上,管理员还可对感兴趣的网络管理对象设置审查值范围及配置网络性能对象,监控实时轮询网络获取定义对象的当前值,若超出审查值的正常预定值则报警,协助管理员发现网络瓶颈,这样就能实现一定程度上的故障管理。
而网络流量检测本身也涉及到安全管理方面的内容。
由此可见,对于一个有效的网络安全管理系统来说,功能的实现都或多或少的依赖于流量信息的获取。
因此网络流量信息的采集可以说是网络安全管理系统得以实现的核心基石。
它的应用可以在一定程度上检测到入侵攻击,可以有效地帮助管理人员进行网络性能管理,并利用报警机制协助网管人员采取对应的安全策略与防护措施,从而减少入侵攻击所造成的损失。
1.3课程设计的目的与任务
该网络流量监控及分析工具主要用途是通过实时连续地采集网络数据并对其进行统计,得到主要成分性能指标,结合网络流量的理论,通过统计出的性能指数观察网络状态,分析出网络变化趋势,找出影响网络性能的因素。
课程设计开发的工具实现以下功能:
(1)采用Winsock编写原始套接字Socket-Raw对数据包进行采集捕获,并可实现分类及自定义范围进行捕获;
(2)对捕获的数据包进行一定的解析;
(3)访问操作系统提供的网络性能参数接口,得到网卡总流量、输入流量和输出流量;
(4)系统提供了多种方式显示结果,如曲线图、列表等;
(5)使用IP帮助API获取网络统计信息;
(6)实现对部分常见威胁的预警,可继续开发扩展其报警功能。
2相关的概念与技术
2.1TCP/IP体系结构
由于TCP/IP比其之前的OSI模型更具体实现,随着互联网的不断发展,遵循TCP/IP结构的网络不断普及,因此现在通常采用TCP/IP代表Internet体系结构。
TCP/IP的目的是在网络标准不同的情况下解决互联问题,可以说,网络互联是TCP/IP的核心。
TCP/IP的体系结构如图1所示。
图1
TCP/IP在设计时重点并没有放在具体通信的实现上,所以对最后两层没有做出具体规定,同时表明它允许不同类型的通信网络参与通信。
它的四个层次功能如下。
(1)应用层,提供常用的应用程序及自定义的应用程序,数据传输时用TCP/IP协议来进行;
(2)传输层,提供端到端的应用程序之间的通信,可以使用传输控制协议TCP(TransmissionControlProtocol)或用户数据报协议UDP(UserDatagramProtocol)协议,前者提供可靠传输,传送单位是报文段,后者提供不可靠服务,传输单位是数据报,即分组。
此外,传输层另外一个功能就是区别应用程序;
(3)网际层,负责计算机之间的通信,采用的协议是IP协议,数据传送单位是分组,向上提供不可靠的传输服务;
(4)网络接口层,负责接收数据报,并实现发送,或者接收帧,提取IP数据报,交给互联网层。
2.2原始套接字
从用户的角度来看,标准的流式套接字和数据报套接字这两类套接字似乎涵盖了TCP/IP应用的全部,因为基于TCP/IP的应用,从协议栈的层次(如图2.2.1所示)上讲,在传输层的确只可能建立于TCP或UDP协议之上,而流式套接字和数据报套接字又分别对应于TCP和UDP,所以几乎所有的应用都可以用这两类套接字实现。
但是,当需要自定义数据包发送时或者需要分析所有经过网络的数据包的时候,就必须面临一种不同于前两者的方式—RawSocket,即原始套接字,程序员可以用它来发送和接收IP层以上的原始数据包,如ICMP,TCP,UDP等,不仅这样,它还可以实现如伪装本地IP、发送ICMP包等功能。
RawSocket广泛应用于高级网络编程,也是一种广泛的黑客手段。
著名的网络sniffer、拒绝服务攻击(DOS)、IP欺骗等都可以以RawSocket实现。
RawSocket与标准套接字(SOCK_STREAM、SOCK_DGRAM)的区别在于前者直接置"根"于操作系统网络核心(NetworkCore),而SOCK_STREAM、SOCK_DGRAM则“悬浮”于TCP和UDP协议外围,如图2.2.2所示。
3网络数据的采集技术分析
3.1Windows下原始数据包捕获的实现
网络上的数据包捕获机制主要依赖于所使用的操作系统,不同的操作系统下有不同的实现途径。
在Windows环境下,可通过网络驱动程序接口规范(NDIS),WinSock的SOCK_RAW或虚拟设备驱动技术(VxD)等技术实现网络数据包的捕获功能。
前面已经介绍到了,使用原始套接字可以绕过Socket提供的功能,对底层的协议进行使用与开发,可以根据自己的需要生成想要的数据报文等,下面开始介绍使用原始套接字对数据包捕获进行开发的相关技术知识。
第一,使用套接字前,需要了解网卡接收数据的工作原理:
在正常情况下,网络接口只响应两种数据帧,一种是与自己的硬件相匹配的数据帧,另一种四向所有计算机广播的数据帧。
在系统中,数据帧的收发由网卡完成,网卡程序接收从网络发来的数据包,根据其硬件地址去判断是否与本机的硬件地址匹配,若匹配就通知CPU产生中断进行响应,然后调用驱动程序设置的网卡中断程序地址调用驱动程序接收数据,然后放入堆栈进行系统相关处理,若不匹配则直接丢弃该数据包[3]。
对于网络接口,它一般具有4种数据接收模式:
广播、组播、直接和混杂模式,只有当把接口设置为混杂模式时,网络接口才能接收所有的数据,无论地址是否匹配,所以在做本设计的时候一定要设置为混杂模式才能实现数据的采集。
第二,需要了解套接字的工作程序和使用方法:
一般来说,采用套接字开发网络程序需要经历以下几个基本步骤:
启动、创建、绑定、监听(接受连接)、连接、发送/接收数据、关闭、卸载等。
第三,具体到Windows下利用原始套接字捕获网络数据可以这样设计:
(1)启动套接字;
(2)创建一个原始套接字;
(3)将套接字与本地地址绑定;
(4)设置操作参数;
(5)设置网络接口为混杂模式;
(6)启动监听线程,开始接收数据;
(7)退出关闭套接字。
3.2原始数据包捕获的关键函数
(1)启动函数WSAStartup
intPASCALFARWSAStartup(DWORDwVersionRequested,LPWSADATAlpWSAData);
每一个套接字应用程序都必须调用该函数进行一系列初始化工作,并且只有调用成功返回后,才能开始使用套接字,其中参数wVersionRequested是版本号,高字节是次版本号、低字节是主版本号,参数lpWSAData是指向WSADATA结构的指针。
(2)套接字创建函数socket
SOCKETsocket(intaf,inttype,intprotocol);
所有的通信在建立之前都必须创建一个套接字,socket函数的功能就是创建套接字,其中参数af指协议地址族(addressfamily),当建立的套接字是依赖于UDP或TCP的话,需要设置af为AF_INET,表示采用IP协议。
参数type是指协议的套接字类型,采用流式套接字时用SOCK_STREAM,采用数据报套接字时用SOCK_DGRAM,采用原始套接字时用SOCK_RAW。
参数protocol是协议字段,默认情况下可直接设置为0。
(3)绑定函数bind
intbind(SOCKETs,structsockaddr_in*name,intnamelen);
成功创建套接字后的下一步工作就是将本地网络接口与套接字进行绑定,其中参数s是创建的套接字,参数name是需要绑定的通信对象的信息结构体指针,namelen是该结构的长度。
需要注意的是sockaddr_in结构:
structsockaddr_in{
shortsin_family;//地址族,设置为AF_INET
unsignedshortsin_port;//指定的端口号
structin_addrsin_addr;//IP地址
charsin_zero[8];
};
由于主机序列与网络序列的关系,在程序中需要使用htons等函数进行转换工作。
(4)设置接口模式函数WSAIoctl
intWSAAPIWSAIoctl(SOCKETs,DWORD
dwIoControlCode,LPVOIDlpvInBuffer,DWORD
cbInBuffer,LPVOIDlpvOutBuffer,DWORD
cbOutBuffer,LPDWORDlpcbBytesReturned,
LPWSAOVERLAPPEDlpOverlapped,
LPWSAOVERLAPPED_COMPLETION_ROUTINE
lpCompletionRoutine);
其中,s为一个套接口的句柄,dwIoControlCode为操作控制代码,lpvInBuffer为输入缓冲区的地址,cbInBuffer为输入缓冲区的大小,lpvOutBuffer为输出缓冲区的地址,
cbOutBuffer为输出缓冲区的大小,lpcbBytesReturned为输出实际字节数的地址,lpOverlapped为WSAOVERLAPPED结构的地址,lpCompletionRoutine为一个指向操作结束后调用的例程指针。
调用成功后,WSAIoctl函数返回0,否则的话,将返回INVALID_SOCKET错误,应用程序可通过WSAGetLastError来获取错误代码。
(5)数据接收函数recv
intrecv(SOCKETs,char*buf,intlen,intflags);
4网络流量监控系统各模块的设计与实现
4.1总体结构设计
通过收集与分析简单网络流量监控软件的需求,总结出以下特征:
(1)需要实现对网络接口数据包的尽可能多的捕获,将网卡设置为混杂模式,然后进行数据包的采集;
(2)数据包的内容要进行一定的解析,对数据包的协议类型、源目地址、数据包截获时间、数据包内容需要进行分析;
(3)监视结果输出有实时流量图、列表等显示;
(4)实现日志记录,便于日后分析;
(5)对某些常见的攻击进行发现分析。
总合以上要求与综合分析,分析工具总体设计如下,采用VC++6.0编写,分析工具具有三个主要功能部分:
数据捕获与显示模块、流量信息统计模块、流量绘制模块,如图4.1_1所示。
图4.1_1系统总体设计结构图
数据采集模块:
完成网络接口数据的捕获、解析和显示,可以根据用户定义条件组合来进行捕获,如只监视采用TCP或UDP协议的数据包,也可以监视用户希望关注的相关IP地址的数据包,同时完成数据封包日志记录,提高了系统的灵活性。
同时,在对数据包的解析过程中对一些常见入侵攻击特征进行判断,发出预警。
该模块采用编写原始套接字开发。
信息统计模块:
完成统计功能,如统计IP要实现统计接收到的数据报数量、接收到的数据中协议出错的数量、正在请求传输的数量、路由表中可用路由数量、丢弃的数量、需要重组/成功重组的数量等,统计ICMP需要完成发送/接收的消息数量、满足超过TTL的数量、重定向数量、时间戳请求/应答数量等;采用IP助手函数完成。
流量绘制模块:
完成总流量、输入流量、输出流量、瞬时流量值、最高流量值的显示;采用访问注册表网络性能数据完成有关数据的获取,通过流量图显示。
4.2流程图设计
根据上面对各个功能模块的划分,进行更进一步的分析和设计,得到数据采集、注册表网络性能块访问大致的工作流程图,如4.2_1与图4.2_2所示。
4.3各模块功能概述与实现
4.3.1数据包采集中各类的关系
经过上面的分析与设计,得到该系统的总体功能结构、工作流程,也确定了从编写套接字到最后捕获数据,要经过创建、绑定、设置工作模式、启动线程、接收数据等一系列的处理操作。
为了实现处理中的每一步操作,设计了数据捕获的类关系,如图4.3.1所示。
在上图中CSockSupport,CSockHelper,CPackInterDlg,CBinDataDlg等是封装了各部分主要处理功能的类。
且这些类中封装了和这些类的操作相关的方法。
将在后面对这些类的功能和实现进行详细介绍。
4.3.2数据包捕获与分析模块
功能实现说明
该功能模块主要由封装的CSockSupport,CsockHelper,CpackInterDlg,CbinDataDlg四个类完成,下面将对这些类进行详细说明。
CsockSupport类:
主要负责检查Socket是否支持2.0版本,在该类中封装了WSAStartup完成Socket的启动;
CsockHelper类:
主要实现了从获取本机信息结构、Socket创建、绑定、设置、启动线程、数据接收到协议分析的全部方法,详细处理流程见图4.3.2所示。
GetLocalIP实现获取本机地址操作的方法,LPHOSTENTlphp是定义一个主机信息结构,获取过程由gethostname(szLocname,MAX_HOSTNAME_LAN)与gethostbyname(szLocname)完成;第一个参数是用于放置本机名称的缓冲,第二个参数是缓冲区长度,最后利用inet_ntoa将IP地址转化为“.”式地址。
StartCapture方法完成套接字的创建、绑定、设置操作方式和启动线程;具体完成如下:
图4.3.2CSockHelper
类处理流程
m_sockCap=socket(AF_INET,SOCK_RAW,IPPROTO_IP);//创建套接字
bind(m_sockCap,(PSOCKADDR)&sa,sizeof(sa));//绑定
setsockopt(m_sockCap,SOL_SOCKET,SO_REUSEADDR,(char*)&bopt,sizeof(bopt));//设置操作
setsockopt(m_sockCap,IPPROTO_IP,IP_HDRINCL,(char*)&bopt,sizeof(bopt));//设置操作
WSAIoctl(m_sockCap,SIO_RCVALL,&dwBufferInLen,sizeof(dwBufferInLen),dwBufferLen,sizeof(dwBufferLen),&dwBytesReturned,NULL,NULL);//混杂模式
m_hCapThread=CreateThread(NULL,0,CaptureThread,this,0,NULL);//启动线程
线程函数CaptureThread主要完成数据的接收。
数据接收后,将缓冲区数据转化为IP数据格式后即可以开始解析过程,协议名称获取如下:
for(inti=0;i if(ProtoMap[i].ProtoNum==iProtocol) returnProtoMap[i].ProtoText; return“”; ParseIPPack方法完成数据包的解析: intiIphLen=sizeof(unsignedlong)*(pIpheader->h_lenver&0xf)//获取数据包长度 协议解析: switch(iProtocol) { caseIPPROTO_TCP: …… caseIPPROTO_UDP: …… caseIPPROTO_ICMP: …… default: ……} StopCapture完成关闭线程和套接字操作: if(m_hCapThread) {TerminateThread(m_hCapThread,0);//中断进程 CloseHandle(m_hCapThread);//关闭句柄 m_hCapThread=NULL;} if(m_sockCap) closesocket(m_sockCap);//关闭套接字 CbinDataDlg类主要完成对已捕获数据的存储和显示方法;CpackInterDlg类通过建立CbinDataDlg类和CsockHelper类对象实现数据捕获、解析、显示、存储等,同时它完成对捕获条件设置控件、日志记录控件的编写,在这里就不做详细介绍了。 4.3.3流量获取模块 设计说明 设计思路: 实际编程时,Windows系统内提供了一个系统性能的接口,只需要访问这个接口就可以得到网络性能相关的数据,如流量;根据这个想法,设计出了本功能模块的子功能模块如下: 访问性能数据子模块: 负责对注册表进行访问,获取流量数据; 显示子模块: 负责将数据绘制在窗口中; 框架子模块: 负责消息映射和消息处理; 本模块中,将使用到一个注册表访问函数RegQueryValueEx,它根据开放的注册表键值与名字查找相关的类型和数据。 它的函数原型如下: LONGRegQueryValueEx(HKEYhKey,LPCTSTRlpValueName,LPDWORDlpReserved,LPDWORDlpType,LPBYTElpData,LPDWORDlpcbData); 参数说明: hKey为预定的注册表系统键值; lpValueName为需要查询的目标键值的名字; lpReserved保留,但是必须为NULL; lpType为键值类型; lpData输入/输出接收键值的数据; lpcbData输入/输出接收键值的缓冲大小标志。 在WindowsNT下,当调用RegQueryValueEx时,若hKey被设置为HKEY_PERFORMANCE_DATA返回的数据并不是直接显示被请求的数据对象。 所以程序需要遍历整个数据块,数据块中的逻辑结构如图4.3.3所示。 图4.3.3注册表网络性能数据块逻辑结构 从数据块的性能数据结构PERF_DATA_BLOCK开始,然后索引到PERF_OBJECT_TYPE结构,而PERF_COUNTER_DEFINITION结构可以通过PERF_OBJECT_TYPE的成员HeaderByteLength找到位置偏移,每一个PERF_OBJECT_TYPE的成员DefinitionLength都能确定一个对应的PERF_INSTANCE_DEFINITION结构,PERF_INSTANCE_DEFINITION结构决定着PERF_COUNTER_BLOCK结构[3]。 下面列出了获得网络接口流量的部分关键代码: //得到当前的接口名字 InterfaceName=Interfaces.GetAt(pos); //开辟性能数据缓冲 unsignedchar*data=newunsignedchar[DEFAULT_BUFFER_SIZE]; //从RegQueryValueEx返回的值: 本例中忽略改变量 //从网络对象(索引是510)查询性能数据 RegQueryValueEx(HKEY_PERFORMANCE_DATA,"510",NULL,&type,data,&size) PERF_DATA_BLOCK*dataBlockPtr=(PERF_DATA_BLOCK*)data; 下面详细说明,注册表数据性能块访问过程的实现: //枚举链表中第一个对象 PERF_OBJECT_TYPE*objectPtr=FirstObject(dataBlockPtr); //遍历链表 for(inta=0;a<(int)dataBlockPtr->NumObjectTypes;a++) { charnameBuffer[255]; //判断是否是网络对象索引号是510 if(objectPtr->ObjectNameTitleIndex==510) { //偏移变量 DWORDprocessIdOffset=ULONG_MAX; //找到第一个计数器 PERF_COUNTER_DEFINITION*counterPtr=FirstCounter(objectPtr); //遍历链表 for(intb=0;b<(int)objectPtr->NumCounters;b++) { //判断接收的数据类型是否是我们需要的 if((int)counterPtr->CounterNameTitleIndex ==CurrentTrafficType) processIdOffset=counterPtr->CounterOffset; //下一个计数器 counterPtr=NextCounter(counterPtr);} //数据类型不是我们需要的 if(processIdOffset==ULONG_MAX){ delete[]data; return1;} //找到第一个实例(instance) PERF_INSTANCE_DEFINITION*instancePtr=FirstInstance(objectPtr); //遍历整个实例 for(b=0;b {wchar_t*namePtr=(wchar_t*)((BYTE*)instancePtr+instancePtr->NameOffset); //得到这个实例的PERF_COUNTER_BLOCK PERF_COUNTER_BLOCK*counterBlockPtr=GetCounterBlock(instancePtr); //现在得到了接口的名字 char*pName=WideToMulti(namePtr,nameBuffer,sizeof(nameBuffer)); POSITIONpos=TotalTraffics.FindIndex(b); if(pos! =NULL) {fullTraffic=*((DWORD*)((BYTE*)counterBlockPtr+processIdOffset)); TotalTraffics.SetAt(pos,fullTraffic);} //如果当前的接口就是我们选择的接口 if
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 网络流量 监控 分析 工具 设计 实现
![提示](https://static.bdocx.com/images/bang_tan.gif)