基于snort的域名监控工具DnsEye
0.源码学习
snort 作为世界上最流行的开源入侵检测系统,至今已有15的历史了,最新release2.9.6.1的源码有近5MB大小,使用命令
wc snort-2.9.6.1/src/*
统计共有66873行代码,已经是很大工程了。看linux源码,大多从linux0.11开始,依照这个 方法,找到了snort最原始的版本0.96, 发现该版本太简单了,两个源文件(snort.c, snort.h),总共约1600行代码。
其实snort0.96的功能也简单,基于libpcap进行抓包分析,仅仅是一个简单的嗅探器,还没有图形界面 (回想去年一个大作业:编写网络嗅探器,要是使用这个源码,自己加个界面,就事半功倍了)。
学习源码的一个重要步骤就是修改,重新编译。我在snort0.96基础上添加一个功能:
解析所有的DNS请求包,监控局域网所有用户访问域名的情况。
监控域名这有什么用途呢?
- 发现用户的网站浏览癖好;
- 谁使用了翻墙工具,谁经常访问成人网站;
- 从安全角度讲,有些僵尸网络botnet使用domain-flux技术进行通信,可以发现那些随机域名;
- ...
2. DnsEye实现
使用四层链表结构记录域名访问信息:
第一层链表记录发送DNS请求的source ip;
后面三层分别记录各级域名,分解到第三级;
第二层链表记录顶级域名,如com, net, org;
第三层链表记录二级域名,如onestraw;
最后一层链表记录域名第三级和更高级的所有域名信息,如www,a.b.c.d等;
此外,各层链表均记录请求次数。
1)在snort.h 中添加如下代码
//son of second level ,namely, third level damin
struct SSLD{
char name[64];
u_long cnt;
struct SSLD *next;
};
//second level domain, its length < 64
struct SLD{
char name[64];
u_long cnt;
struct SSLD *ssld;
struct SLD *next;
};
//top level domain
struct TLD{
char name[5];
u_long cnt;
struct SLD *sld;
struct TLD *next;
};
//requester, namely,src addr
struct DNSRequest{
u_long saddr;
u_long cnt;
struct TLD *tld;
struct DNSRequest *next;
};
//struct TLD *g_dnlist=NULL;
struct DNSRequest *g_dnslist=NULL;
static u_int pcnt;
void PrintDNlist(int level);
void ReleaseDNlist();
void RecordDomainName(u_long addr, char *dname);
void DecodeDNS(u_char *pkt, int len);
2)snort.c中修改一下DecodeUDP函数
if(pip.dport==53)
{
pktidx = pktidx +8;
DecodeDNS(pktidx, len-8);
}
3)CleanExit函数中添加
if(g_dnslist)
{
PrintDNlist(3);
ReleaseDNlist();
}
4)定义四个函数
void PrintDNlist(int level);
void ReleaseDNlist();
void RecordDomainName(u_long addr, char *dname);
void DecodeDNS(u_char *pkt, int len);
#附录
1.snort所有版本下载: http://sourceforge.jp/projects/sfnet_snort/releases/
留下评论