目录

Libpcap

首先明确几点: 类UNIX系统上的网络嗅探软件一般都是基于标准接口BPF和libpcap的,如tcpdump。 类UNIX平台的网络嗅探技术主要通过内核态的BPF(伯克利包过滤)和用户态的libpcap抓包工具库实现。BPF是数据链路层的一种原始接口,提供原始链路层封包的收发功能。
它支持过滤封包。对封包中的数据采取算数操作,并将结果与常量或封包中的数据或结果中的测试位相比较,以此决定是否接收包。
Libpcap是类UNIX平台用户态下的抓包工具库,与BPF配合使用,为类UNIX平台上的应用程序提供标准的网络嗅探接口。
libpcap的包捕获机制就是在数据链路层加一个旁路处理。当一个数据包到达网络接口时,libpcap首先从链路层驱动程序中获得该数据包的拷贝,再将数据包发给BPF过滤器。BPF过滤器根据用户已经定义好的过滤规则对数据包进行逐一匹配,匹配成功则放入内核缓冲区,并传递给用户缓冲区,匹配失败则直接丢弃。如果没有设置过滤规则,所有数据包都将放入内核缓冲区,并传递给用户层缓冲区。
下图为个人理解

libpcap的抓包框架

函数 功能
pcap_lookupdev() 用于查找网络设备,返回可被pcap_open_live()函数调用的网络设备名指针。
pcap_open_live() 用于打开网络设备,并且返回用于捕获网络数据包的数据包捕获描述字。对于此网络设备的操作都要基于此网络设备描述字。
pcap_lookupnet() 获得指定网络设备的网络号和掩码。
pcap_compile() 用于将用户制定的过滤策略编译到过滤程序中。
pcap_setfilter() 用于设置过滤器。
pcap_loop()
pcap_dispatch()
pcap_next_ex()
pcap_next()
用于捕获数据包,捕获后还可以进行处理
pcap_close() 用于关闭网络设备,释放资源。
实现Libpcap:
1、设置要嗅探的设备
char *pcap_lookupdev(char *errbuf)
2、打开设备进行嗅探,创建一个嗅探会话任务
pcap_t *pcap_open_live(char *device,int snaplen,int promisc,int to_ms,char *errbuf)第一个参数为在第一步指定好的采设备,第二个参数定义被pcap捕捉的最大字节数,promisc为true时设为混杂模式,to_ms是读取时的超时值,单位为毫秒,(若该值为0则一直持续到发生错误为止)
3、过滤
int pcap_compile(pcap_t *p,strUCt bpf_program *fp,char *str,int optimize,bpf_u_int32 netmask)
第一个参数为会话句柄。第二个参数是存储被编译的过滤器版本的地址引用,第三个参数是过滤表达式,第四个参数是定义的表达式是否被优化,0表示不优化,1表示优化。最后一个参数指定应用该过滤器的网络的掩码。该函数返回1时为失败。
int pcap_setfilter(pcap_t *p,struct bpf_program * fp)第一个参数为会话句柄,第二个参数是被编译表达式的版本的引用。
 #include
   pcap_t *handle; /* 会话的句柄 */
   char dev[] = "eth0"; /* 执行嗅探的设备 */
   char errbuf[PCAP_ERRBUF_SIZE]; /* 存储错误 信息的字符串 */
   struct bpf_program filter; /*已经编译好的过滤表达式*/
   char filter_app[] = "port 23"; /* 过滤表达式,过滤23号端口的数据包*/
   bpf_u_int32 mask; /* 执行嗅探的设备的网络掩码 */
   bpf_u_int32 net; /* 执行嗅探的设备的IP地址 */
   pcap_lookupnet(dev, &net, &mask, errbuf);/* 获得指定设备和网络信息 */
   handle = pcap_open_live(dev, BUFSIZ, 1, 0, errbuf);/* 创建嗅探会话 */
   pcap_compile(handle, &filter, filter_app, 0, net);/* 编译过滤规则 */
   pcap_setfilter(handle, &filter);/* 设置使用定义的过滤器 */
4、开始嗅探 u_char *pcap_next(pcap_t *p, struct pcap_pkthdr *h)
第一个参数是会话句柄,第二个参数指向包含当前数据包总体信息的结构体的指针,该函数返回一个u_char指针给被这个结构体描述的包。
例子:
#include
   #include
   int main()
   {
   pcap_t *handle; /* 会话句柄 */
   char *dev; /* 执行嗅探的设备 */
   char errbuf[PCAP_ERRBUF_SIZE]; /* 存储错误信息的字符串 */
  
   struct bpf_program filter; /* 已经编译好的过滤器 */
   char filter_app[] = "port 23"; /* 过滤表达式 */
   bpf_u_int32 mask; /* 所在网络的掩码 */
   bpf_u_int32 net; /* 主机的IP地址 */
   struct pcap_pkthdr header; /* 由pcap.h定义 */
   const u_char *packet; /* 实际的包 */
   /* Define the device */
   dev = pcap_lookupdev(errbuf);
   /* 探查设备属性 */
   pcap_lookupnet(dev, &net, &mask, errbuf);
   /* 以混杂模式打开会话 */
   handle = pcap_open_live(dev, BUFSIZ, 1, 0, errbuf);
   /* 编译并应用过滤器 */
   pcap_compile(handle, &filter, filter_app, 0, net);
   pcap_setfilter(handle, &filter);
   /* 截获一个包 */
   packet = pcap_next(handle, &header);
   /* 打印它的长度 */
   printf("Jacked a packet with length of [%d]
   ", header.len);
   /* 关闭会话 */
   pcap_close(handle);
   return(0);
   }
一般情况下,软件中使用的函数为: int pcap_loop(pcap_t *p, int cnt, pcap_handler callback, u_char *user)或者 pcap_dispatch()
对于pcap_loop来说,第一个参数为为嗅探会话句柄,第二个参数表示收到多少个数据包才进行返回,第三个参数为回调函数,回调函数用于处理数据包,第四个参数一般情况下设为NULL,只有在需要用自己写的回调函数的时候才会用到。
回调函数:void got_packet(u_char *args, const struct pcap_pkthdr *header, const u_char *packet);
第一个参数对应pcap_loop()中的最后一个参数,第二个参数是pcap头文件,包括了本次嗅探的数据包被嗅探的时间、大小等信息。最后一个参数是pcap_loop()本次嗅探到的所有包。
在Libpcap中,定义了诸如IP,IP,以太网帧,UDP等类型的数据包的结构,可以通过这些结构对收到的数据包的数据进行拆包。 5、关闭嗅探会话

尝试写一个简单的抓包程序

首先下载需要的库文件Libpcap,在[dcpdump官网](https://www.tcpdump.org/release/)可下,
下载完成后,解压,编译,需要用到如下命令:
sudo tar -xvzf libpcap-1.9.1.tar.gz
cd libpcap-1.9.1/
sudo ./configure
sudo make
sudo make install

在别人的电脑上可以运行,在我这就段错误!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

自己在网上找开源的代码获取账号密码 在这里用20199101推荐的网站:http://www.techpanda.org 账号:admin@goole.com 密码:Password2010

抓取手机上的包

使用电脑的热点,手机连不上

下载了wifi共享大师,所用的本地连接14,本机无法连接,尝试过修改IP地址,使用netsh wlan set hostednetwork mode=allow ssid=testWIFI key=12345678进行启动也不管用。

尝试了更新驱动,不好使。

wireshark找不到这个接口

遇到的问题 1、在编译libpcap过程中,使用./configure命令时,显示错误

进行安装,sudo apt-get install flex
2、另外,出现了libcpap.so链接库找不到的情况
解决办法,找到对应的链接库,将路径放到/etc/ld.so.conf的末尾




3、在抓取登录包的时候,进行过滤的时候输入了http.request.method="POST"的时候,忘记给POST加引号,导致找不到登录包
posted on 2020-03-29 12:56  20199302  阅读(151)  评论(0编辑  收藏  举报