失眠网,内容丰富有趣,生活中的好帮手!
失眠网 > WinPcap网络编程入门——1. 获取设备列表

WinPcap网络编程入门——1. 获取设备列表

时间:2022-05-01 06:32:14

相关推荐

WinPcap网络编程入门——1. 获取设备列表

WinPcap网络编程入门——1. 获取设备列表

系列教程章节直达:

Winpcap网络编程入门——1. 获取设备列表;

上节中我们简单介绍了 WinPcap 的相关资料,配置好了开发环境,现在就让我们正式开始网络编程开发吧!

1. 基本开发流程

WinPcap 开发网络应用程序的大致流程:首先获取主机安装的网络设备列表,然后选择并激活某个网络设备,封装或过滤数据包,发送或解析数据包,本节我们将以解析数据包为例来逐层深入,基本开发流程如图:

2. 使用 pcap_findalldevs_ex() 检索设备列表

pcap_findalldevs_ex() 是 WinPcap 提供的用以查找主机网络适配器功能的函数,它是 pcap_findalldevs() 函数的升级版,现在基本都选择使用 ex 版本,它不仅能查找本地的设备,还能查找远程的设备,关于此函数的定义如下:

// 函数原型:int pcap_findalldevs_ex(char* source, struct pcap_rmtauth *auth, pcap_if_t** alldevs, char* errbuf);/* 参数说明* source:指定是本地适配器还是远程适配器* auth:身份验证信息,可以为NULL* alldevs:存放获取的适配器数据,如果查找失败,其值为NULL* errbuf:存放查找失败的相关错误信息*/// 返回值:成功返回0,失败返回-1

看了函数定义之后是不是感觉这个很简单呢,只需要调用函数然后就可以获取到设备信息,是的!就是这么简单,当然,还有一点需要注意:

可以看到参数alldevs的类型是pcap_if_t类型的二级指针,这里需要说明,pcap_findalldevs_ex()函数在获取到设备信息之后会将详细信息存储在一个结构体pcap_if_t中,(注意,单个设备时一个结构体,多个设备就是多个结构体的链接,即链表,这是个非常基本的概念,不懂的话查一下链表的相关知识)它的定义如下:

struct pcap_if_t{struct pcap_if_t *next;// 如果不为空,就指向下一个元素char *name;// 设备名称char *description;// 设备描述struct pcap_addr *addresses;// 接口地址列表bpf_u_int32 flags;// 标志位,标志是否 loopback 设备}

从中可以看出,我们需要建立一个pcap_if_t类型的指针来存储调用函数获取到的设备信息,然后直接通过指针就可以访问指定设备的相关信息,由此可以写出伪代码如下:

pcap_if_t *alldevs;// 指向获取到设备列表的第一个设备,即链表头pcap_findalldevs_ex(***, ***, alldevs, ***);// 调用函数来查找设备printf("%s\n", alldevs->name);// 输出第一个设备的名称printf("%s\n", alldevs->description);// 输出第一个设备的描述信息if(alldevs 链表中有多个设备)alldevs = alldevs->next;// 获取下一个设备// 重复上面的输出代码,输出此设备的相关信息

同样,从pcap_if_t结构体的定义中可以看到,在结构体里面又定义了一个名为pcap_addr的结构体,用来存储接口地址列表,pcap_addr的定义如下:

struct pcap_addr{struct pcap_addr *next;// 如果不为空,则指向下一个元素struct sockaddr *addr;// 接口IP地址struct sockaddr *netmask;// 接口网络掩码struct sockaddr *broadaddr;// 接口广播地址struct sockaddr *dstaddr;// 接口 P2P 目的地址}

这个结构体的列表中包含:

该接口的地址列表网络掩码的列表(每个网络掩码对应地址列表中的一项)广播地址的列表(每个广播地址对应地址列表中的一项)目标地址的列表(每个目标地址对应地址列表中的一项)

3. 实现获取设备列表

经过了以上的分析,我们大概知道了pcap_findalldevs_ex()函数的基本用法以及对于信息的存储机制,下面我们就来实现一下这个程序吧,具体的解释都在代码的注释里,要详细阅读代码哟 ~

#define WIN32 // 在vs中编程时,必须要加这一行,否则vs不会自动识别平台#include <stdio.h>#include <pcap.h>#pragma comment(lib, "wpcap.lib")main(){pcap_if_t* alldevs, * d;// alldevs 存储查找到的设备链表的链表头,d 为遍历 alldevs 链表时的游标int i = 0;// 设备序号,在后面的循环中会用到char errbuf[PCAP_ERRBUF_SIZE];// 如果查找失败,相关错误信息会存储到这个里面// 从本地计算机检索可用设备列表if (pcap_findalldevs_ex(PCAP_SRC_IF_STRING, NULL, &alldevs, errbuf) == -1){// 查找失败,输出失败信息fprintf(stderr, "Error in pcap_findalldevs_ex: %s\n", errbuf);exit(1);// 如果查找失败,程序直接终止}// 如果查找成功,alldevs 中已经存储了设备信息链表头的地址,直接遍历输出即可// 输出设备列表for (d = alldevs; d != NULL; d = d->next){printf("%d.%s", ++i, d->name);// 输出设备名称,设备序号依次加1if (d->description){printf("(%s)\n", d->description);// 输出设备描述信息(如果有的话)}else {printf("(No description available)\n");}}if (i == 0)// 如果设备序号还是0的话,说明没有查找到设备{printf("\nNo interfaces found! Make sure Winpcap is installed.\n");return;}// 释放设备pcap_freealldevs(alldevs);}

完整代码就是这样,如果有其他问题欢迎下方评论区相见。

系列教程章节直达:

Winpcap网络编程入门——1. 获取设备列表;

如果觉得《WinPcap网络编程入门——1. 获取设备列表》对你有帮助,请点赞、收藏,并留下你的观点哦!

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。