logo资料库

Linux下Sniffer程序的实现.pdf

第1页 / 共3页
第2页 / 共3页
第3页 / 共3页
资料共3页,全文预览结束
Linux下Sniffer程序的实现 文章地址:http://www.ykzj.org/article.php?articleid=1131 作者:Gianluca Insolvibile 整理:Seal(永远的FLASH) 出处:http://www.nsfocus.com 日期:2003-04-02 嗅探——Sniffer技术是网络安全领域里一项非常重要的技术!对于“Hacker”来说,他们可以以非常隐 蔽的方式得到网络中传输的大量的敏感信息,如Telnet,ftp帐号和密码等等明文传送的信息!与主动扫 描相比,嗅探的行为更加难以被察觉,操作起来也不是很复杂!对于网络管理人员来说,可以利用嗅 探技术对网络活动进行监控,并及时发现各种攻击行为! 在这篇文章里,我们主要探讨在Linux下如何利用C语言来实现一个Sniffer!我们将假设所有的主机在 一个局域网内。 首先,我们将简短的回顾一下一个普通的以太网卡是怎么工作的!(如果你对这方面的知识早已熟悉 ,那么你可以直接跳到下一段)来源于应用程序的IP报文被封装成以太网帧(这 是在以太网上传播的数据报文的名称),它是底层链路层报文上面的一层报文,包含有源地址 报文和一些需要用来传送至目标主机的信息。通常情况下,目的IP地址对应着一个6字节的目的以太网 址(经常叫做MAC地址),它们之间通过ARP协议进行映射!就这样,包含着以太网帧的报文从源主机 传输到目的主机,中间经过一些网络设备,如交换机,路由器等等,当然,因为我们的前提是主机在 同一网内,所以我们的讨论不涉及以上这些网络设备! 在链路层中并不存在路线的概念,换句话说,源主机发出的帧不会直接指向目的主机, 而是基于广播方式传播,网络中的所有网卡都能看到它的传输。每个网卡会检查帧开始的6个字节( 目的主机的MAC地址),但是只有一个网卡会发现自己的地址和其相符合,然后它接收这个帧,这个 帧会被网络驱动程序分解,原来的IP报文将通过网络协议栈传送至接收的应用程序! 更准确的说,网络驱动程序会检查帧中报文头部的协议标识,以确定接收数据的上层协 议!大多数情况下,上层是IP协议,所以接收机制将去掉IP报文头部,然后把剩下的传送 至UDP或者TCP接收机制!这些协议,将把报文送到socket-handling机制,它将最后把报 文数据变成应用程序可接收的方式发送出去。在这个过程中,报文将失去所有的和其有关的
网络信息,比如源地址(IP和MAC),端口号,IP选择,TCP参数等等!所以如果目的主机没 有一个包含正确参数的打开端口,那么这个报文将被丢弃而且永远不会被送到应用层去! 因此我们在进行网络嗅探的时候有两个不同的问题:一个和以太网址有关,我们不能抓 到不是发给自己主机的包,另一个和协议栈的运行过程有关,我们需要一个SOCKET去监听每 个端口,得到那些没有被丢弃的报文! 第一个问题不是最根本的,因为我们可能不会对发往其他主机的报文有兴趣而只想嗅探 所有发往自己主机的报文。第二个问题是必须要解决的,下面我们将看到这个问题是怎么样 一步一步解决的! 当你打开一个标准的SOCKET套接字时,你需要指明你将使用哪个协议簇,大多数情况下 我们一般用PF_UNIX在本地机器间进行通信,PF_INET在基于IPv4协议簇基础之上进行通信, 你还需要指明所用的协议类型及与协议簇相关的确切数值,,在PF_INET协议簇中,常用的有 SOCK_STREAM(与TCP相关),SOCK_DGRAM(与UDP相关)。在把报文发送到应用程序前内核 对 其的处理与SOCKET类型有关,你指定的协议将处理报文在SOCKET的传输!(具体细节问题你 可以man socket(3)) 在LINUX内核版本中(2.0 releases),一个名为PF_PACKET的协议簇被加了进来!这个簇允许应用程序直接利用网络驱动程序发送 和接收报文,避免了原来的协议栈处理过程,在这种情况下,所有SOCKET发出的报文直接送到以太 网卡接口,而接口收到的任何报文将直接送到应用程序 The PF_PACKET协议簇支持两个稍微有点不同的SOCKET类型,SOCK_DGRAM和SOCK_RAW。 前者让内核处理添加或者去除以太网报文头部工作,而后者则让应用程序对以太网报文头部 有完全的控制!在SOCKET调用中的协议类型必须符合/usr/include/linux/if_ether.h 中定义的以太网IDs中的一个,除非遇到特别声明的协议,一般你可以用ETH_P_IP来处理 IP的一组协议(TCP,UDP,ICMP,raw IP等等)因为它们容易受到一些很严重的安全问题的牵 连(比如你可以伪造一个MAC地址),所以只有具有root权限才可以使用PF_PACKET-family socket.这也就是为什么只有具有root权限后才能运行嗅探器的原因! PF_PACKET-family 协议簇可以很容易解决协议栈处理嗅探来的数据报文时候遇到的问
题!我们一起来看看程序1,我们打开一个属于PF_PACKET-family 协议簇的SOCKET,指定 一个SOCK_RAW socket类型和IP相关协议类型。这时我们开始从SOCKET抓包,在一些相关 检查后.我们开始得到从链路层和IP层抓来的头部信息,。通过阅读程序一,你将会发现让应 用程序从网络层抓包其实并不难! Example 1. #include #include #include #include #include #include #include int main(int argc, char **argv) { int sock, n; char buffer[2048]; unsigned char *iphead, *ethhead; if ( (sock=socket(PF_PACKET, SOCK_RAW, htons(ETH_P_IP)))
分享到:
收藏