- 论坛徽章:
- 0
|
第七课:处理离线dump文件
在上一节课里面我们已经熟练掌握了怎么样在网络接口卡上面捕获数据包,现在我们继续学习怎么处理数据dumps。WinPcap提过了大量的函数来保存网络信息到文件里和从文件中读取dumps的内容。这节课将要学习怎么样使用这些函数。我们将会看到怎样使用WinPcap的内核dump特征来获得高性能dumps(注意:这时候由于一些问题涉及到内核缓冲区,这些特征将会失效)。
文件格式是libpcap的格式。这格式包含捕获数据包的数据(二进制形式),而且这格式是标准的格式,被很多的网络工具使用,例如:WinDump,Ethereal以及Snot。
把数据包保存到dump文件
首先,让我们看看怎么用libpcap格式来写数据包。下面的例子从一个选中的接口上捕获数据包并且把他们保存到一个用户命名的文件。
#include "pcap.h"
/* prototype of the packet handler */
void
packet_handler
(u_char *param, const struct
pcap_pkthdr
*header, const u_char *pkt_data);
main
(int argc, char **argv)
{
pcap_if_t
*alldevs;
pcap_if_t
*d;
int inum;
int i=0;
pcap_t
*adhandle;
char errbuf[
PCAP_ERRBUF_SIZE
];
pcap_dumper_t
*dumpfile;
/* Check command line */
if(argc != 2)
{
printf("usage: %s filename", argv[0]);
return -1;
}
/* Retrieve the device list on the local machine */
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
);
else
printf(" (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("%d", &inum);
if(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
next
, i++);
/* Open the device */
if ( (adhandle=
pcap_open
(d->
name
, // name of the device
65536, // portion of the packet to capture
// 65536 guarantees that the whole packet will be captured on all the link layers
PCAP_OPENFLAG_PROMISCUOUS, // promiscuous mode
1000, // read timeout
NULL, // authentication on the remote machine
errbuf // error buffer
) ) == NULL)
{
fprintf(stderr,"\nUnable to open the adapter. %s is not supported by WinPcap\n", d->
name
);
/* Free the device list */
pcap_freealldevs
(alldevs);
return -1;
}
/* Open the dump file */
dumpfile =
pcap_dump_open
(adhandle, argv[1]);
if(dumpfile==NULL)
{
fprintf(stderr,"\nError opening output file\n");
return -1;
}
printf("\nlistening on %s... Press Ctrl+C to stop...\n", d->
description
);
/* At this point, we no longer need the device list. Free it */
pcap_freealldevs
(alldevs);
/* start the capture */
pcap_loop
(adhandle, 0, packet_handler, (unsigned char *)dumpfile);
return 0;
}
/* Callback function invoked by libpcap for every incoming packet */
void
packet_handler
(u_char *dumpfile, const struct
pcap_pkthdr
*header, const u_char *pkt_data)
{
/* save the packet on the dump file */
pcap_dump
(dumpfile, header, pkt_data);
}
可以看出:这个程序的结构和前面我们学过的课程里面的结构非常相似,不同在于:
⑴接口一打开,就马上调用pcap_dump_open()打开一个dump文件并且把它联系到此接口⑵在packet_handler()回调函数执行中,数据包被pcap_dump()写入到文件中。参数dumpfile被pcap_handler()函数接收,所以保存一个数据包是非常简单的事情。大家要控制好时间,因为网络数据包太多了,时间久了dump的文件就会特别大,到时候你直接打开都要等一会儿.......
本文来自ChinaUnix博客,如果查看原文请点:http://blog.chinaunix.net/u/28528/showart_360055.html |
|