本文转自http://eslxf.blog.51cto.com/918801/290489
此处展示如何把高层的过滤表达式编译虚拟机的字节码,
并
以C程序段格式输出,与tcpdump或WinDump的–dd参数输出格式一样。
示例使用参数格式如下:
filter_nopcap [-O]
过滤表达式
添加
-O
参数将对输出的指令不进行优化。
代码实现如下
[filternopcap]
:
#define
WIN32
#define
HAVE_REMOTE
#include
<stdio.h>
#include
"pcap.h"
#define
filter_len 1024
int
main(int argc, char *argv[ ])
{
int offset=0;
char *filter_buf=(char*)malloc(filter_len);
int optimize=1;//
优化
int arg_begin=1;
memset(filter_buf,0x0,filter_len);
if(argc<=1)
{
strcpy(filter_buf,"ip");
optimize=0;//
不优化
}
else
{
/*
决定是否需要优化指令*/
if( strcmp(argv[1],"-O")==0 )
{
optimize=0;//
不优化
arg_begin=2;
}
else
{
optimize=1;//
优化
arg_begin=1;
}
/*
从命令行中获得过滤表达式*/
for(int i=arg_begin;i<argc;i++)
{
strcpy(filter_buf+offset,argv[i]);
offset=offset+strlen(argv[i])+1;
memset(filter_buf+offset-1,' ',1);
}
}
//
打印过滤表达式
printf("
过滤表达式:%s/n"
,filter_buf);
/*
网络掩码,以太网IP协议*/
bpf_u_int32 netmask=0xffffff;
struct bpf_program program;
int ret=pcap_compile_nopcap(96,
DLT_EN10MB,
&program,
filter_buf,
optimize,
netmask
) ;
if(ret<0)
{
printf("error./n");
return -1;
}
printf("program.bf_len=%d/n",program.bf_len);
for(int i=0;i<program.bf_len;i++)
{
printf("{0x%x, %u, %u, 0x%.8x},/n",
program.bf_insns[i].code,program.bf_insns[i].jt,
program.bf_insns[i].jf,program.bf_insns[i].k);
}
/*
释放资源*/
pcap_freecode(&
program
);
free(filter_buf);
return 0;
}
程序测试结果如下
>filter_nopcap ip or arp
//
优化
过滤表达式:
ip or arp
program.bf_len=5
{0x28, 0, 0, 0x0000000c},
{0x15, 1, 0, 0x00000800},
{0x15, 0, 1, 0x00000806},
{0x6, 0, 0, 0x00000060},
{0x6, 0, 0, 0x00000000},
>filter_nopcap -O ip or arp
//
无优化
过滤表达式:
ip or arp
program.bf_len=6
{0x28, 0, 0, 0x0000000c},
{0x15, 2, 0, 0x00000800},
{0x28, 0, 0, 0x0000000c},
{0x15, 0, 1, 0x00000806},
{0x6, 0, 0, 0x00000060},
{0x6, 0, 0, 0x00000000},
输出结果与
tcpdump
一样
$ tcpdump -dd ip or arp
//
优化
{ 0x28, 0, 0, 0x0000000c },
{ 0x15, 1, 0, 0x00000800 },
{ 0x15, 0, 1, 0x00000806 },
{ 0x6, 0, 0, 0x00000060 },
{ 0x6, 0, 0, 0x00000000 },
$ tcpdump -Odd ip or arp
//
无优化
{ 0x28, 0, 0, 0x0000000c },
{ 0x15, 2, 0, 0x00000800 },
{ 0x28, 0, 0, 0x0000000c },
{ 0x15, 0, 1, 0x00000806 },
{ 0x6, 0, 0, 0x00000060 },
{ 0x6, 0, 0, 0x00000000 },