既然我们能够捕获和过滤网络流量,我们希望把我们的知识与一个简单的“现实世界”应用程序一起使用。

在本课中,我们将从以前的课程中获取代码,并使用这些代码构建更有用的程序。当前程序的主要目的是显示如何解析和解释捕获的数据包的协议头。生成的应用程序UDPdump打印了我们网络上UDP流量的摘要。

我们选择解析和显示UDP协议,因为它比其他协议(如TCP)更易于访问,因此是一个很好的初始示例。我们来看看代码:

#include "pcap.h"/* 4 bytes IP address */
typedef struct ip_address{u_char byte1;u_char byte2;u_char byte3;u_char byte4;
}ip_address;/* IPv4 header */
typedef struct ip_header{u_char  ver_ihl;        // Version (4 bits) + Internet header length (4 bits)u_char  tos;            // Type of service u_short tlen;           // Total length u_short identification; // Identificationu_short flags_fo;       // Flags (3 bits) + Fragment offset (13 bits)u_char  ttl;            // Time to liveu_char  proto;          // Protocolu_short crc;            // Header checksumip_address  saddr;      // Source addressip_address  daddr;      // Destination addressu_int   op_pad;         // Option + Padding
}ip_header;/* UDP header*/
typedef struct udp_header{u_short sport;          // Source portu_short dport;          // Destination portu_short len;            // Datagram lengthu_short crc;            // Checksum
}udp_header;/* prototype of the packet handler */
void packet_handler(u_char *param, const struct pcap_pkthdr *header, const u_char *pkt_data);int main()
{
pcap_if_t *alldevs;
pcap_if_t *d;
int inum;
int i=0;
pcap_t *adhandle;
char errbuf[PCAP_ERRBUF_SIZE];
u_int netmask;
char packet_filter[] = "ip and udp";
struct bpf_program fcode;/* Retrieve the device list */if (pcap_findalldevs_ex(PCAP_SRC_IF_STRING, NULL, &alldevs, errbuf) == -1){fprintf(stderr,"Error in pcap_findalldevs: %s\n", errbuf);exit(1);}/* Print the list */for(d=alldevs; d; d=d->next){printf("%d. %s", ++i, d->name);if (d->description)printf(" (%s)\n", d->description);elseprintf(" (No description available)\n");}if(i==0){printf("\nNo interfaces found! Make sure WinPcap is installed.\n");return -1;}printf("Enter the interface number (1-%d):",i);scanf_s("%d", &inum);if(inum < 1 || inum > i){printf("\nInterface number out of range.\n");/* Free the device list */pcap_freealldevs(alldevs);return -1;}/* Jump to the selected adapter */for(d=alldevs, i=0; i< inum-1 ;d=d->next, i++);/* Open the adapter */if ( (adhandle= pcap_open(d->name,  // name of the device65536,     // portion of the packet to capture. // 65536 grants that the whole packet will be captured on all the MACs.PCAP_OPENFLAG_PROMISCUOUS,         // promiscuous mode1000,      // read timeoutNULL,      // remote authenticationerrbuf     // error buffer) ) == NULL){fprintf(stderr,"\nUnable to open the adapter. %s is not supported by WinPcap\n");/* Free the device list */pcap_freealldevs(alldevs);return -1;}/* Check the link layer. We support only Ethernet for simplicity. */if(pcap_datalink(adhandle) != DLT_EN10MB){fprintf(stderr,"\nThis program works only on Ethernet networks.\n");/* Free the device list */pcap_freealldevs(alldevs);return -1;}if(d->addresses != NULL)/* Retrieve the mask of the first address of the interface */netmask=((struct sockaddr_in *)(d->addresses->netmask))->sin_addr.S_un.S_addr;else/* If the interface is without addresses we suppose to be in a C class network */netmask=0xffffff; //compile the filterif (pcap_compile(adhandle, &fcode, packet_filter, 1, netmask) <0 ){fprintf(stderr,"\nUnable to compile the packet filter. Check the syntax.\n");/* Free the device list */pcap_freealldevs(alldevs);return -1;}//set the filterif (pcap_setfilter(adhandle, &fcode)<0){fprintf(stderr,"\nError setting the filter.\n");/* Free the device list */pcap_freealldevs(alldevs);return -1;}printf("\nlistening on %s...\n", d->description);/* At this point, we don't need any more the device list. Free it */pcap_freealldevs(alldevs);/* start the capture */pcap_loop(adhandle, 0, packet_handler, NULL);return 0;
}/* Callback function invoked by libpcap for every incoming packet */
void packet_handler(u_char *param, const struct pcap_pkthdr *header, const u_char *pkt_data)
{struct tm ltime;char timestr[16];ip_header *ih;udp_header *uh;u_int ip_len;u_short sport,dport;time_t local_tv_sec;/** Unused variable*/(VOID)(param);/* convert the timestamp to readable format */local_tv_sec = header->ts.tv_sec;localtime_s(<ime, &local_tv_sec);strftime( timestr, sizeof timestr, "%H:%M:%S", <ime);/* print timestamp and length of the packet */printf("%s.%.6d len:%d ", timestr, header->ts.tv_usec, header->len);/* retireve the position of the ip header */ih = (ip_header *) (pkt_data +14); //length of ethernet header/* retireve the position of the udp header */ip_len = (ih->ver_ihl & 0xf) * 4;uh = (udp_header *) ((u_char*)ih + ip_len);/* convert from network byte order to host byte order */sport = ntohs( uh->sport );dport = ntohs( uh->dport );/* print ip addresses and udp ports */printf("%d.%d.%d.%d.%d -> %d.%d.%d.%d.%d\n",ih->saddr.byte1,ih->saddr.byte2,ih->saddr.byte3,ih->saddr.byte4,sport,ih->daddr.byte1,ih->daddr.byte2,ih->daddr.byte3,ih->daddr.byte4,dport);
}

首先,我们将过滤器设置为“ip和udp”。以这种方式,我们确信packet_handler()只能通过IPv4接收UDP数据包:这简化了解析并提高了程序的效率。

我们还创建了几个描述IP和UDP头文件的结构体。这些结构体被packet_handler()用于正确定位各种标题字段。

packet_handler()虽然限于单个协议解析器(UDP over IPv4),但是显示了像tcpdump / WinDump这样复杂的“嗅探器”如何解码网络流量。由于我们对MAC头不感兴趣,所以我们跳过它。为了简单起见,在开始捕获之前,我们使用pcap_datalink()检查MAC层,以确保我们正在处理以太网。这样我们可以确定MAC头部正好是14个字节。

IP头位于MAC头之后。我们将从IP头提取IP源和目标地址。

由于IP头不具有固定的长度,所以到达UDP头是有点复杂的。因此,我们使用IP头的长度字段来知道它的大小。一旦我们知道UDP头的位置,我们就提取了源和目标端口。

提取的值打印在屏幕上,结果如下:

1. \Device\Packet_{A7FD048A-5D4B-478E-B3C1-34401AC3B72F} (Xircom t 10/100 Adapter) 
Enter the interface number (1-2):1

listening on Xircom CardBus Ethernet 10/100 Adapter... 
16:13:15.312784 len:87 130.192.31.67.2682 -> 130.192.3.21.53 
16:13:15.314796 len:137 130.192.3.21.53 -> 130.192.31.67.2682 
16:13:15.322101 len:78 130.192.31.67.2683 -> 130.192.3.21.53 

最后3行中的每一行代表不同的数据包。

c++ winpcap开发(6)相关推荐

  1. 在Visual Studio 2005下配置WinPcap开发环境

    在Visual Studio 2005下配置WinPcap开发环境 http://www.winpcap.org/archive/ 4.1beta5_WpdPack.zip http://www.wi ...

  2. winpcap 开发

    Winpcap是一个强大的网络开发库,可以实现许多功能:获取可用的网络适配器:获取指定适配器信息(比如名称和描述信息):捕获指定网卡的数据封包:发送数据封包:过滤捕获的包以获取特定包等. 首先到htt ...

  3. socket编程之DEV C++配置winpcap开发环境并编写网络嗅探器sniffer

    欢迎关注我的个人博客:www.zuzhiang.cn 期末计算机网络课程设计让做一个网络嗅探器,要求可以检测和选择网卡,并打开到混杂模式,监听局域网中的所有数据包并解析出所用网络协议以及首部各个字段的 ...

  4. codeblocks配置winpcap开发环境

    转载请注明出处,谢谢_ (:з」∠)_ 起因 最近作业要用Winpcap开发包分析.pcap文件实现报文字段的识别-本来打算用Visual Studio写,不过想起以前打OJ的时候都用Code::Bl ...

  5. Dev-C++ 配置 WinPcap 开发环境

    VC++ 6.0实在是太老了,自己并不愿意在这个平台上开发,所以转而使用Dev-C++,以下是综合网上的教程和自己的试验总结出的用Dev-C++进行WinPcap网络开发的所需的环境配置工作: 首先是 ...

  6. 一步一步开发sniffer(Winpcap+MFC)(一)工欲善其事,必先配环境——配置winpcap开发环境

    0.说在前面的话 1) 本文将以一个初学者的角度,一步一步几乎是从0开始讲述如何完成一个基于winpcap+MFC的sniffer(嗅探器)当然我指的"0"并不是指连编程都不会,如 ...

  7. 基于winpcap开发的相关资料

    2019独角兽企业重金招聘Python工程师标准>>> http://www.oschina.net/code/snippet_196111_7100 http://wenku.ba ...

  8. c++ winpcap开发(9)

    收集网络流量统计 本课程展示了WinPcap的另一个高级功能:收集网络流量统计信息的能力.统计引擎利用内核级包过滤器对传入的数据包进行有效的分类.如果您想了解更多详细信息,可以参考NPF驱动程序内部手 ...

  9. c++ winpcap开发(8)

    发送数据包 虽然名称WinPcap清楚地表明图书馆的目的是分组捕获,但还提供了其他有用的原始网络功能.其中,用户可以找到一组完整的功能来发送数据包. 请注意,原来的libpcap库目前没有提供任何方式 ...

  10. c++ winpcap开发(7)

    处理离线转储文件 在这个课程中,我们将学习如何处理数据包捕获到一个文件(转储到文件).WinPcap提供广泛的功能来将文件的网络流量保存到文件并读取转储的内容 - 本课将介绍如何使用所有这些功能.我们 ...

最新文章

  1. 华人团队用Transformer做风格迁移,速度快、可试玩,网友却不买账
  2. tf.trainable_variables() and tf.all_variables()
  3. Python数据结构与算法(第六天)
  4. lua php 触摸精灵,lua程序设计主要学习路径
  5. 基于决策树的多分类_R中基于决策树的糖尿病分类—一个零博客
  6. SpringBoot时间戳与MySql数据库记录相差14小时排错
  7. 程序员必读的涨薪指南
  8. gstat | 空间插值(一)——反距离权重插值;使用ggplot2绘制地图
  9. 给玩得好的女朋友写了一份前端学习路线。
  10. vb 循环放音乐_为何洒水车一直无限循环播放《兰花草》这首歌呢?
  11. 公办低分二本_河南最适合“二本”考生的30所公办大学,录取分低,考生不要错过...
  12. python是开源的.它可以被移植_python是开源的,它可以被移植到许多平台上,是对的吗?...
  13. 40个国内外文献免费下载网站-转
  14. 2019 d serv 激活_Science | 清华大学柴继杰课题组与合作者首次揭示植物TNL类抗病蛋白激活的分子机制...
  15. 对 sass和less的理解
  16. linux访问局域网共享,精解局域网访问及共享(三)
  17. Java验证身份证号
  18. 论文翻译:2019_Bandwidth Extension On Raw Audio Via Generative Adversarial Networks
  19. 网易云音乐params和encSecKey参数生成代码
  20. DARTS 可微 架构搜索

热门文章

  1. nutch爬虫原来是这样操作的!
  2. arma预测matlab讲解,MATLAB中ARMA模型预测差分问题
  3. micropython esp32驱动舵机_PCA9685舵机控制板与MicroPython-ESP32-1Z实验室
  4. c语言字符加密向后四位_Base64加密?它只是一种编码算法,切勿用来加密
  5. macos server 恢复安装_如何通过 macOS 恢复功能重新安装 macOS
  6. 《深入浅出程序设计竞赛(基础篇)》第1部分 语言入门 第3章 分支结构程序设计
  7. 【C#桌面应用】第二节:利用Visual Studio2019 创建桌面应用
  8. linux两台服务器传输,Linux两台服务器之间高速数据传输命令:scp应用详解
  9. 西贝莜面村员工手册_西贝那达慕草原美食节 引领文化生活新消费
  10. Qt文档阅读笔记-Broadcast Sender Example解析