基于Winpcap-编程实现抓包实验_第1页
基于Winpcap-编程实现抓包实验_第2页
基于Winpcap-编程实现抓包实验_第3页
基于Winpcap-编程实现抓包实验_第4页
基于Winpcap-编程实现抓包实验_第5页
已阅读5页,还剩12页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

上海电力学院计算机网络安全(1)课程实验报告实验名称: winpcap编程实验 基于Winpcap 编程实现抓包实验一. 本设计要达到的目标 基于winpcap编程实现对网络数据的捕获,并分析数据类型,对于IP,ICMP,ARP,UDP等,能够自动识别其协议类型并分析帧的构成。二.实现步骤(1)需要通过资料来了解winpcap抓包的工作原理,熟悉其运行过程 Winpcap的内部结构Wincap有三部分组成:一个数据包监听设备驱动程序,一个低级的动态连接库和一个高级的静态连接库。底层动态链接库运行在用户层,它将应用程序和数据包监听设备驱动程序隔离开来,使得应用程序可以不加修改地在不同的WINDOWS系统上运行。高级的静态链接库和应用程序编译在一起,它使用低级动态链接库提供的服务,向应用程序提供完善的监听接口。抓包是WinPcap的基本功能,也是NPF最重要的操作。在抓包的时候,驱动(例如NIC Driver)使用一个网络接口监视着数据包,并将这些数据包完整无缺地投递给用户级应用程序。(2)进一步了解winpcap编程所需要的编译环境,下载WpdPack,了解编译环境所需要的库文件.在编译时需要把wpdpack中的include与lib添加进vc的库文件里。(3)明确整个编程的步骤与具体函数。刚开始要定义,在主函数中获取设备接口信息,获得网络地址与掩码地址,打开网络接口,还要设置过滤规则。使用loop函数来回调循环捕获数据包,以便一层一层解析。(4)还要定义几个以太网,ARP,IP,UDP,TCP,ICMP协议的格式。需要注意在存储空间中,在存储空间中才能更好的逐层分析,不然很容易出错(5)定义分析协议的函数,定义方式与回调函数相同. 常用的函数有:用于获取本机设备列表的pcap_findalldevs_ex函数用于打开设备的pcap_open函数,可以指定为混杂模式打开用于编译数据包过滤器的pcap_compile 函数用于设置数据包过滤器的pcap_setfilter 函数用于从设备读取数据包的pcap_netx_ex 函数用于关闭设备的pcap_close 函数(参数为pcap_open 返回值)用于释放设备列表的pcap_freealldevs 函数(对应pcap_findalldevs_ex)三.系统流程图主函数以太网协议分析函数分析ARP协议函数分析Ip协议函数分析ICMP协议函数判断下层函数分析TCP协议函数分析UDP协议函数16进制数据四.关键代码及其分析主函数void main() pcap_t *pcap_handle; /* Winpcap句柄 */ char error_contentPCAP_ERRBUF_SIZE; /* 存储错误信息 */ char *net_interface; /* 网络接口 */ bpf_program bpf_filter; /* BPF过滤规则 */ char bpf_filter_string = ; /* 过滤规则字符串 */ bpf_u_int32 net_mask; /* 掩码 */ bpf_u_int32 net_ip; /* 网路地址 */ net_interface = pcap_lookupdev(error_content); /* 获得可用的网络接口 */ pcap_lookupnet(net_interface, &net_ip, &net_mask, error_content);/* 获得网络地址和掩码地址 */ pcap_handle = pcap_open_live(net_interface, BUFSIZ, 1, 1, error_content); /* 打开网路接口 */ pcap_compile(pcap_handle, &bpf_filter, bpf_filter_string, 0, net_ip); /* 编译BPF过滤规则 */ pcap_setfilter(pcap_handle, &bpf_filter); /* 设置过滤规则 */对IP协议的定义class ip_header public: #if defined(WORDS_BIGENDIAN) u_int8_t ip_version: 4, /* 版本 */ ip_header_length: 4; /* 首部长度 */ #else u_int8_t ip_header_length: 4, ip_version: 4; #endif u_int8_t ip_tos; /* 服务质量 */ u_int16_t ip_length; /* 长度 */ u_int16_t ip_id; /* 标识 */ u_int16_t ip_off; /* 偏移 */ u_int8_t ip_ttl; /* 生存时间 */ u_int8_t ip_protocol; /* 协议类型 */ u_int16_t ip_checksum; /* 校验和 */ in_addr ip_souce_address; /* 源IP地址 */ in_addr ip_destination_address; /* 目的IP地址 */pcap_loop(pcap_handle, n, ethernet_protocol_packet_callback, NULL); /* 注册回调函数,循环捕获网络数据包,利用回调函数来处理每个数据包 */ 分析UDP协议的函数代码 void udp_protocol_packet_callback(u_char *argument, const pcap_pkthdr *packet_header, const u_char *packet_content) class udp_header *udp_protocol; /* UDP协议变量 */ u_short source_port; /* 源端口 */ u_short destination_port; /* 目的端口号 */ u_short length; /长度 udp_protocol = (class udp_header*)(packet_content + 14+20);/* 获得UDP协议内容 */ source_port = ntohs(udp_protocol-udp_source_port); /* 获得源端口 */ destination_port = ntohs(udp_protocol-udp_destination_port); /* 获得目的端口 */ length = ntohs(udp_protocol-udp_length); /* 获得长度 */ cout- UDP协议 -endl; cout源端口号:decsource_portendl; cout目的端口号:decdestination_portendl; switch (destination_port) case 138: cout上层协议为NETBIOS数据报服务endl; break; case 137: cout上层协议为NETBIOS名字服务endl; break; case 139: cout上层协议为NETBIOS会话服务endl; break; case 53: cout上层协议为域名服务endl; break; default: break; cout长度:lengthendl; cout校验和:setw(4)setfill(0)hexudp_checksum)endl; 五.参考文献(1) Winpcap中文文档(2) 网络资料/view/d64047d676eeaeaad1f330c7.html?from=search /winpcap-sniffer.html完整源程序#include pcap.h #include #include #includeusing namespace std; /*以下是以太网协议格式的定义*/ class ether_header public: u_int8_t ether_dhost6; /* 目的以太网地址 */ u_int8_t ether_shost6; /* 源以太网地址 */ u_int16_t ether_type; /* 以太网类型 */ ; /* 下面是ARP协议格式的定义*/ class arp_header public: u_int16_t arp_hardware_type; /* 硬件类型 */ u_int16_t arp_protocol_type; /* 协议类型 */ u_int8_t arp_hardware_length; /* 硬件地址长度 */ u_int8_t arp_protocol_length; /* 协议地址长度 */ u_int16_t arp_operation_code; /* 操作码 */ u_int8_t arp_source_ethernet_address6; /* 源以太网地址 */ u_int8_t arp_source_ip_address4; /* 源IP地址 */ u_int8_t arp_destination_ethernet_address6; /* 目的以太网地址 */ u_int8_t arp_destination_ip_address4; /* 目的IP地址 */ ; /*下面是IP协议格式的定义 */ class ip_header public: #if defined(WORDS_BIGENDIAN) u_int8_t ip_version: 4, /* 版本 */ ip_header_length: 4; /* 首部长度 */ #else u_int8_t ip_header_length: 4, ip_version: 4; #endif u_int8_t ip_tos; /* 服务质量 */ u_int16_t ip_length; /* 长度 */ u_int16_t ip_id; /* 标识 */ u_int16_t ip_off; /* 偏移 */ u_int8_t ip_ttl; /* 生存时间 */ u_int8_t ip_protocol; /* 协议类型 */ u_int16_t ip_checksum; /* 校验和 */ in_addr ip_souce_address; /* 源IP地址 */ in_addr ip_destination_address; /* 目的IP地址 */ ; /*下面是UDP协议格式定义*/ class udp_header public: u_int16_t udp_source_port; /* 源端口号 */ u_int16_t udp_destination_port; /* 目的端口号 */ u_int16_t udp_length; /* 长度 */ u_int16_t udp_checksum; /* 校验和 */ ; /* 下面是TCP协议格式的定义*/ class tcp_header public: u_int16_t tcp_source_port; /* 源端口号 */ u_int16_t tcp_destination_port; /* 目的端口号 */ u_int32_t tcp_sequence_lliiuuwweennttaaoo; /* 序列号 */ u_int32_t tcp_acknowledgement; /* 确认序列号 */ #ifdef WORDS_BIGENDIAN u_int8_t tcp_offset: 4, /* 偏移 */ tcp_reserved: 4; /* 未用 */ #else u_int8_t tcp_reserved: 4, /* 未用 */ tcp_offset: 4; /* 偏移 */ #endif u_int8_t tcp_flags; /* 标记 */ u_int16_t tcp_windows; /* 窗口大小 */ u_int16_t tcp_checksum; /* 校验和 */ u_int16_t tcp_urgent_pointer; /* 紧急指针 */ ; /* 下面是ICMP协议格式的定义*/ class icmp_header public: u_int8_t icmp_type; /* ICMP类型 */ u_int8_t icmp_code; /* ICMP代码 */ u_int16_t icmp_checksum; /* 校验和 */ u_int16_t icmp_id; /* 标识符 */ u_int16_t icmp_sequence; /* 序列码 */ ; /* 下面是分析TCP协议的函数,其定义方式与回调函数相同 */ void tcp_protocol_packet_callback(u_char *argument, const pcap_pkthdr *packet_header, const u_char *packet_content) class tcp_header *tcp_protocol;/* TCP协议变量 */ u_char flags; /* 标记 */ int header_length; /* 长度 */ u_short source_port; /* 源端口 */ u_short destination_port; /* 目的端口 */ u_short windows; /* 窗口大小 */ u_short urgent_pointer;/* 紧急指针 */ u_int sequence; /* 序列号 */ u_int acknowledgement; /* 确认号 */ u_int16_t checksum; /* 校验和 */ tcp_protocol = ( tcp_header*)(packet_content + 14+20); /* 获得TCP协议内容 */ source_port = ntohs(tcp_protocol-tcp_source_port); /* 获得源端口 */ destination_port = ntohs(tcp_protocol-tcp_destination_port); /* 获得目的端口 */ header_length = tcp_protocol-tcp_offset *4; /* 长度 */ sequence = ntohl(tcp_protocol-tcp_sequence_lliiuuwweennttaaoo); /* 序列码 */ acknowledgement = ntohl(tcp_protocol-tcp_acknowledgement); /* 确认序列码 */ windows = ntohs(tcp_protocol-tcp_windows); /* 窗口大小 */ urgent_pointer = ntohs(tcp_protocol-tcp_urgent_pointer); /* 紧急指针 */ flags = tcp_protocol-tcp_flags; /* 标识 */ checksum = ntohs(tcp_protocol-tcp_checksum); /* 校验和 */ cout TCP协议 endl; cout源端口号:dec source_port endl; cout目的端口号:dec destination_portendl; switch (destination_port) case 80: cout上层协议为HTTP协议:endl; break; case 21: cout上层协议为FTP协议endl; break; case 23: cout上层协议为TELNET协议endl; break; case 25: cout上层协议为SMTP协议endl; break; case 110: cout上层协议为POP3协议endl; break; default: break; cout序列码sequenceendl; cout确认号:acknowledgementendl; cout首部长度:decheader_lengthendl; cout保留:tcp_reserved)endl; cout标记:; if (flags &0x08) coutPSH endl; if (flags &0x10) coutACK endl; if (flags &0x02) coutSYN endl; if (flags &0x20) coutURG endl; if (flags &0x01) coutFIN endl; if (flags &0x04) coutRST endl; coutendl; cout窗口大小:windowsendl; cout校验和: setw(4) setfill(0) hex checksumendl; cout紧急指针:urgent_pointerudp_source_port); /* 获得源端口 */ destination_port = ntohs(udp_protocol-udp_destination_port); /* 获得目的端口 */ length = ntohs(udp_protocol-udp_length); /* 获得长度 */ cout UDP协议 endl; cout源端口号:decsource_portendl; cout目的端口号:decdestination_portendl; switch (destination_port) case 138: cout上层协议为NETBIOS数据报服务endl; break; case 137: cout上层协议为NETBIOS名字服务endl; break; case 139: cout上层协议为NETBIOS会话服务endl; break; case 53: cout上层协议为域名服务endl; break; default: break; cout长度:lengthendl; cout校验和:setw(4)setfill(0)hexudp_checksum)endl; /* 下面是实现分析ICMP协议的函数,函数类型与回调函数相同 */ void icmp_protocol_packet_callback(u_char *argument, const pcap_pkthdr *packet_header, const u_char *packet_content) class icmp_header *icmp_protocol; /* ICMP协议变量 */ icmp_protocol = (icmp_header*)(packet_content + 14+20); /* 获得ICMP协议内容 */ cout ICMP协议 endl; coutICMP类型:icmp_typeicmp_type) case 8: coutICMP回显请求协议endl; coutICMP代码:icmp_codeendl; cout标识符:icmp_idendl; cout序列码:icmp_sequenceendl; break; case 0: coutICMP回显应答协议endl; coutICMP代码: icmp_codeendl; cout标识符: setw(4) setfill(0) hexicmp_id) endl; cout序列码: icmp_sequenceendl; break; default: break; coutICMP校验和:setw(4) setfill(0) hex icmp_checksum) endl; /* 获得ICMP校验和 */ return ; /*下面是实现ARP协议分析的函数,函数类型与回调函数相同 */ void arp_protocol_packet_callback(u_char *argument, const pcap_pkthdr *packet_header, const u_char *packet_content) arp_header *arp_protocol; u_short protocol_type; u_short hardware_type; u_short operation_code; u_char *mac_string; in_addr source_ip_address; in_addr destination_ip_address; u_char hardware_length; u_char protocol_length; cout ARP协议 arp_hardware_type); protocol_type = ntohs(arp_protocol-arp_protocol_type); operation_code = ntohs(arp_protocol-arp_operation_code); hardware_length = arp_protocol-arp_hardware_length; protocol_length = arp_protocol-arp_protocol_length; cout硬件类型: arp_hardware_type)endl; cout协议类型 : setw(4)setfill(0)arp_protocol_type)endl; cout硬件地址长度: arp_hardware_length)endl; cout协议地址长度: arp_protocol_length)endl; coutARP 操作: arp_operation_code)endl; switch (operation_code) case 1: coutARP请求协议endl; break; case 2: coutARP应答协议endl; break; case 3: coutRARP请求协议endl; break; case 4: coutRARP应答协议endl; break; default: break; cout源以太网地址: arp_source_ethernet_address; cout setw(2) setfill(0) hex int(*mac_string) . setw(2) setfill(0) hex int(*(mac_string + 1) . setw(2) setfill(0) hex int(*(mac_string + 2) . setw(2) setfill(0) hex int(*(mac_string + 3) . setw(2) setfill(0) hex int(*(mac_string + 4) . setw(2) setfill(0) hex int(*(mac_string + 5) arp_source_ip_address, sizeof( in_addr); cout源IP地址:inet_ntoa(source_ip_address)endl; cout目的以太网地址:arp_destination_ethernet_address; cout setw(2) setfill(0) hex int(*mac_string) . setw(2) setfill(0) hex int(*(mac_string + 1) . setw(2) setfill(0) hex int(*(mac_string + 2) . setw(2) setfill(0) hex int(*(mac_string + 3) . setw(2) setfill(0) hex int(*(mac_string + 4) . setw(2) setfill(0) hex int(*(mac_string + 5) arp_destination_ip_address, sizeof( in_addr); cout目的IP地址:inet_ntoa(destination_ip_address)ip_checksum); /* 获得校验和 */ header_length = ip_protocol-ip_header_length *4; /* 获得长度 */ tos = ip_protocol-ip_tos; /* 获得服务质量 */ offset = ntohs(ip_protocol-ip_off); /* 获得偏移 */ cout IP协议 endl; cout版本号:ip_version)endl; cout首部长度: header_lengthendl; cout服务质量: ip_tos) endl; cout总长度: ip_length)endl; cout标识: setw(4)setfill(0)hexip_id) endl; cout偏移: (offset &0x1fff) *8endl; cout生存时间: ip_ttl)endl; cout协议类型: ip_protocol)ip_protocol) case 6: cout上层协议为TCP协议endl; break; case 17: cout上层协议为UDP协议endl; break; case 1: cout上层协议为ICMP协议ICMPendl; break; default: break; cout校验和:checksumendl; cout源IP地址:ip_souce_address)endl; /* 获得源IP地址 */ cout目的IP地址:ip_destination_address)ip_protocol) /* 根据IP协议判断上层协议 */ case 6: tcp_protocol_packet_callback(argument, packet_header,

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

最新文档

评论

0/150

提交评论