前言
隨著網(wǎng)絡(luò)入侵的不斷發(fā)展,網(wǎng)絡(luò)安全變得越來越重要,于是網(wǎng)絡(luò)入侵取證系統(tǒng)的研究也變得日益重要。在網(wǎng)絡(luò)入侵取證系統(tǒng)中,對網(wǎng)絡(luò)上傳送的數(shù)據(jù)包進(jìn)行有效的監(jiān)聽即捕獲包是目前取證的關(guān)鍵技術(shù),只有進(jìn)行高效的數(shù)據(jù)包捕獲,網(wǎng)絡(luò)管理員才能對所捕獲的數(shù)據(jù)進(jìn)行一系列的分析,從而進(jìn)行可靠的網(wǎng)絡(luò)安全管理。
1winpcap簡介
WinPcap 是由伯克利分組捕獲庫派生而來的分組捕獲庫,它是在Windows 操作平臺上來實(shí)現(xiàn)對底層包的截取過濾。WinPcap 為用戶級的數(shù)據(jù)包提供了Windows 下的一個平臺。WinPcap 是 BPF 模型和 Libpcap 函數(shù)庫在 Windows 平臺下網(wǎng)絡(luò)數(shù)據(jù)包捕獲和網(wǎng)絡(luò)狀態(tài)分析的一種體系結(jié)構(gòu),這個體系結(jié)構(gòu)是由一個核心的包過濾驅(qū)動程序,一個底層的動態(tài)連接庫 Packet.dll 和一個高層的獨(dú)立于系統(tǒng)的函數(shù)庫 Libpcap 組成。底層的包捕獲驅(qū)動程序?qū)嶋H為一個協(xié)議網(wǎng)絡(luò)驅(qū)動程序,通過對 NDIS 中函數(shù)的調(diào)用為 Win95、Win98、WinNT、和 Win2000 提供一類似于 UNIX 系統(tǒng)下 Berkeley Packet Filter 的捕獲和發(fā)送原始數(shù)據(jù)包的能力。Packet.dll 是對這個 BPF 驅(qū)動程序進(jìn)行訪問的 API 接口,同時它有一套符合 Libpcap 接口(UNIX 下的捕獲函數(shù)庫)的函數(shù)庫。WinPcap的結(jié)構(gòu)圖如圖1。
WinPcap 包括三個部分:第一個模塊NPF(Netgroup Packet Filter),是一個虛擬設(shè)備驅(qū)動程序文件。它的功能是過濾數(shù)據(jù)包,并把這些數(shù)據(jù)包原封不動地傳給用戶態(tài)模塊,這個過程中包括了一些操作系統(tǒng)特有的代碼。第二個模塊packet.dll為win32平臺提供了一個公共的接口。不同版本的Windows系統(tǒng)都有自己的內(nèi)核模塊和用戶層模塊。Packet.dll用于解決這些不同。調(diào)用Packet.dll的程序可以運(yùn)行在不同版本的Windows平臺上,而無需重新編譯。 第三個模塊 Wpcap.dll是不依賴于操作系統(tǒng)的。它提供了更加高層、抽象的函數(shù)。 中國網(wǎng)管聯(lián)盟www、bitsCN、com
packet.dll和Wpcap.dll:packet.dll直接映射了內(nèi)核的調(diào)用。 Wpcap.dll提供了更加友好、功能更加強(qiáng)大的函數(shù)調(diào)用。WinPcap的優(yōu)勢提供了一套標(biāo)準(zhǔn)的抓包接口,與libpcap兼容,可使得原來許多UNIX平臺下的網(wǎng)絡(luò)分析工具快速移植過來便于開發(fā)各種網(wǎng)絡(luò)分析工具,充分考慮了各種性能和效率的優(yōu)化,包括對于NPF內(nèi)核層次上的過濾器支持,支持內(nèi)核態(tài)的統(tǒng)計模式,提供了發(fā)送數(shù)據(jù)包的能力。
中國網(wǎng)管聯(lián)盟www_bitscn_com
54ne.com
2、網(wǎng)絡(luò)數(shù)據(jù)包捕獲的原理
以太網(wǎng)(Ethernet)具有共享介質(zhì)的特征,信息是以明文的形式在網(wǎng)絡(luò)上傳輸,當(dāng)網(wǎng)絡(luò)適配器設(shè)置為監(jiān)聽模式(混雜模式,Promiscuous)時,由于采用以太網(wǎng)廣播信道爭用的方式,使得監(jiān)聽系統(tǒng)與正常通信的網(wǎng)絡(luò)能夠并聯(lián)連接,并可以捕獲任何一個在同一沖突域上傳輸?shù)臄?shù)據(jù)包。IEEE802.3 標(biāo)準(zhǔn)的以太網(wǎng)采用的是持續(xù) CSMA 的方式,正是由于以太網(wǎng)采用這種廣播信道爭用的方式,使得各個站點(diǎn)可以獲得其他站點(diǎn)發(fā)送的數(shù)據(jù)。運(yùn)用這一原理使信息捕獲系統(tǒng)能夠攔截的我們所要的信息,這是捕獲數(shù)據(jù)包的物理基礎(chǔ)。
以太網(wǎng)是一種總線型的網(wǎng)絡(luò),從邏輯上來看是由一條總線和多個連接在總線上的站點(diǎn)所組成各個站點(diǎn)采用上面提到的 CSMA/CD 協(xié)議進(jìn)行信道的爭用和共享。每個站點(diǎn)(這里特指計算機(jī)通過的接口卡)網(wǎng)卡來實(shí)現(xiàn)這種功能。網(wǎng)卡主要的工作是完成對于總線當(dāng)前狀態(tài)的探測,確定是否進(jìn)行數(shù)據(jù)的傳送,判斷每個物理數(shù)據(jù)幀目的地是否為本站地址,如果不匹配,則說明不是發(fā)送到本站的而將它丟棄。如果是的話,接收該數(shù)據(jù)幀,進(jìn)行物理數(shù)據(jù)幀的 CRC 校驗(yàn),然后將數(shù)據(jù)幀提交給LLC 子層。
網(wǎng)卡具有如下的幾種工作模式:
1) 廣播模式(Broad Cast Model):它的物理地址(MAC)地址是 0Xffffff 的幀為廣播幀,工作在廣播模式的網(wǎng)卡接收廣播幀。
網(wǎng)管網(wǎng)bitsCN_com
2)多播傳送(MultiCast Model):多播傳送地址作為目的物理地址的幀可以被組內(nèi)的其它主機(jī)同時接收,而組外主機(jī)卻接收不到。但是,如果將網(wǎng)卡設(shè)置為多播傳送模式,它可以接收所有的多播傳送幀,而不論它是不是組內(nèi)成員。
3)直接模式(Direct Model):工作在直接模式下的網(wǎng)卡只接收目地址是自己 Mac地址的幀。
4)混雜模式(Promiscuous Model):工作在混雜模式下的網(wǎng)卡接收所有的流過網(wǎng)卡的幀,信包捕獲程序就是在這種模式下運(yùn)行的。
網(wǎng)卡的缺省工作模式包含廣播模式和直接模式,即它只接收廣播幀和發(fā)給自己的幀。如果采用混雜模式,一個站點(diǎn)的網(wǎng)卡將接受同一網(wǎng)絡(luò)內(nèi)所有站點(diǎn)所發(fā)送的數(shù)據(jù)包這樣就可以到達(dá)對于網(wǎng)絡(luò)信息監(jiān)視捕獲的目的。 中國網(wǎng)管聯(lián)盟www、bitsCN、com
3、在windows情況下捕獲數(shù)據(jù)包的結(jié)構(gòu)
54com.cn
54com.cn
圖2捕獲數(shù)據(jù)包的結(jié)構(gòu)圖
Wndows下捕獲數(shù)據(jù)包的結(jié)構(gòu)如圖2,其中NDIS及其特點(diǎn)是:
NDIS(Network Driver Interface Specification) 是 Microsoft 和 3Com 公司聯(lián)合制定的網(wǎng)絡(luò)驅(qū)動規(guī)范,并提供了大量的操作函數(shù)。它為上層的協(xié)議驅(qū)動提供服務(wù),屏蔽了下層各種網(wǎng)卡的差別。NDIS 向上支持多種網(wǎng)絡(luò)協(xié)議,比如 TCP/IP、NWLink IPX/SPX、NETBEUI 等,向下支持不同廠家生產(chǎn)的多種網(wǎng)卡。NDIS 還支持多種工作模式,支持多處理器,提供一個完備的 NDIS 庫(Library)。 但庫中所提供的各個函數(shù)都是工作在核心模式下的,用戶不宜直接操作,這就需要尋找另外的接口。NDIS驅(qū)動程序的結(jié)構(gòu)如圖3。 中國網(wǎng)管聯(lián)盟
www.bitscn.com 4、利用winpcap進(jìn)行網(wǎng)絡(luò)數(shù)據(jù)包的捕獲和過濾的設(shè)計步驟
1)打開網(wǎng)卡,并設(shè)為混雜模式。
2)回調(diào)函數(shù) Network Tap 在得到監(jiān)聽命令后,從網(wǎng)絡(luò)設(shè)備驅(qū)動程序處收集數(shù)據(jù)包把監(jiān)聽到的數(shù)據(jù)包負(fù)責(zé)傳送給過濾程序。
54ne.com
54ne.com
3)當(dāng) Packet filter 監(jiān)聽到有數(shù)據(jù)包到達(dá)時,NDIS 中間驅(qū)動程序首先調(diào)用分組驅(qū)動程序,該程序?qū)?shù)據(jù)傳遞給每一個參與進(jìn)程的分組過濾程序。
4)然后由 Packet filter 過濾程序決定哪些數(shù)據(jù)包應(yīng)該丟棄,哪些數(shù)據(jù)包應(yīng)該接收,是否需要將接收到的數(shù)據(jù)拷貝到相應(yīng)的應(yīng)用程序。
5)通過分組過濾器后,將數(shù)據(jù)未過濾掉的數(shù)據(jù)包提交給核心緩沖區(qū)。然后等待系統(tǒng)緩沖區(qū)滿后,再將數(shù)據(jù)包拷貝到用戶緩沖區(qū)。監(jiān)聽程序可以直接從用戶緩沖區(qū)中讀取捕獲的數(shù)據(jù)包。
6)關(guān)閉網(wǎng)卡。
5、主要源代碼
根據(jù)用 Windows 分組捕獲庫 WinPcap 提供功能首先要初始化兩個結(jié)構(gòu)體,一個是適配器的結(jié)構(gòu)體 LpAdapter, 一個是存放接收到的數(shù)據(jù)包的結(jié)構(gòu)體 RecvPacket。
使用 Packet.dll 動態(tài)連接庫編寫源代碼:
#define MAX__LINK__NAME__LENGTH 64
適配器結(jié)構(gòu):
typedef struct__ADAPTER
{
HANDLE hFile;
TCHAR Symboliclink[MAX__LINK__NAME__LENGTH];
Int NumWrites;
} ADAPTER , *LPADAPTER;
說明:hFile 是一個指向該網(wǎng)絡(luò)適配器 Handle 的指針,通過它可以對網(wǎng)絡(luò)適配器進(jìn)行操作。symboliclink 包含當(dāng)前打開的網(wǎng)絡(luò)適配器的名字。
數(shù)據(jù)包結(jié)構(gòu):
typedef struct _PACKET
{
HANDLE hEvent;
OVERLAPPED OverLapped;
PVOID Buffer;
UINT Length;
PVOID Next;
UINT ulBytesReceived;
BOOLEAN bloComplete; //控制接受包的開始和結(jié)束
數(shù)據(jù)包捕獲實(shí)現(xiàn)的步驟的主要源代碼:
1)要獲得適配器列表。
#define Max__Num__Adapter 10 //獲得適配器列表
char Adapterlist [Max__Num__Adapter[512]]
int i=0
char AdapterNames[512], *tempa,*templa;
ULONG AdapterLength=1024; } PACKET, *LPPACKET:
2)獲得系統(tǒng)中網(wǎng)絡(luò)適配器的名字。
PacketGetAdapterNames(AdapterNamea,&AdapterLength);
tempa=AdapterNamea;
templa=Adapternamea;
while ((*tempa!=’\0’)∣∣(*tempa-1!=’\0))
{
if (*tempa= =’\0’)
{
memcpy(AdapterList[i],temla,tempa-templa); //內(nèi)存數(shù)據(jù)拷貝
54ne.com
templa=tempa+1;
i++
}
tempa++
}
3)從適配器列表中選擇一個默認(rèn)的 0 號適配器。
LPADAPTER lpAdapter
lpAdapter = PacketOpenAdapter (AdapterList[0]);
if (!lpAdapter∣∣(lpAdapter->hFile==INVALID__HANDLE__VALUE))
{
dwErrorCode=GetLastError();
return FALSE;
}
4)將所選擇的適配器 lpAdapter 設(shè)置為混雜模式。
PacketSetHwFilter(lpAdapter,NDIS_PACKET_TYPE_PROMISCUOUS)
5)設(shè)置 BPF 內(nèi)核中包過濾的過濾器的代參政。利用這個函數(shù)右以完成對于原始數(shù)據(jù)包的初始的過濾處理,如根據(jù)其中端口號、IP 地址等。
PacketSetBpf(LpAdapter AdapterObject,structbpf_program*fp)
6)設(shè)置緩沖池為512K字節(jié)。
PacketSetBuff(lpAdapter,512000);
7)分配一個數(shù)據(jù)包對象,并連接已分配的緩沖。
PacketInitPacket(lpPacket,(char*)bufferReceive,512000); 54ne.com
8)捕獲多個數(shù)據(jù)包。從網(wǎng)卡 lpAdapter 接收數(shù)據(jù)包,并將數(shù)據(jù)包放入 lpPacket所指向的數(shù)據(jù)包結(jié)構(gòu)體中,若接收成功返回 TRUE,否則返回 FALSE。
PacketReceivePacket(lpAdapter,lpPacket,TRUE);
9)通過觸發(fā)回調(diào)函數(shù),把捕獲符合過濾器規(guī)則的數(shù)據(jù)包轉(zhuǎn)發(fā)給網(wǎng)絡(luò)協(xié)議分析模塊進(jìn)行分析處理。
10) 結(jié)束接收數(shù)據(jù)包,釋放數(shù)據(jù)包對象。
if(lpPacket!=NULL
{
PacketFreePacket(lpPacket);
lpPacket=NULL;
}
11)關(guān)閉網(wǎng)卡設(shè)備,將網(wǎng)卡恢復(fù)到正常接收狀態(tài)。
if(lpAdapter!=NULL
{
PacketCloseAdapter(lpAdapter);
lpAdapter=NULL;
} 中國網(wǎng)管論壇bbs.bitsCN.com
6、結(jié)束語
數(shù)據(jù)包捕獲技術(shù)是網(wǎng)絡(luò)管理系統(tǒng)的關(guān)鍵技術(shù),已經(jīng)按照標(biāo)題4中的流程進(jìn)行了簡單的實(shí)現(xiàn)。如果在一個繁忙的網(wǎng)絡(luò)上進(jìn)行截獲,而不設(shè)置任何過濾,那得到的數(shù)據(jù)包是非常多的,可能在一秒鐘內(nèi)得到上千的數(shù)據(jù)包。如果應(yīng)用程序不進(jìn)行必要的性能優(yōu)化,那么將會大量的丟失數(shù)據(jù)包。對捕包性能的優(yōu)化必不可少,考慮采用多線程來處理數(shù)據(jù)包。若在程序中建立一個公共的數(shù)據(jù)包緩沖池,這個緩沖池是一個LILO的隊列。于是在程序中使用三個線程進(jìn)行操作:一個線程只進(jìn)行捕獲操作,它將從驅(qū)動程序獲得的數(shù)據(jù)包添加到數(shù)據(jù)包隊列的頭部;另一個線程只進(jìn)行過濾操作,它檢查新到的隊尾的數(shù)據(jù)包,檢查其是否滿足過濾條件,如果不滿足則將其刪除出隊列;最后一個線程進(jìn)行數(shù)據(jù)包處理操作,象根據(jù)接收的數(shù)據(jù)包發(fā)送新數(shù)據(jù)包這樣的工作都由它來進(jìn)行??紤]盡可能少丟失數(shù)據(jù)包的條件,應(yīng)該是進(jìn)行捕獲操作的線程的優(yōu)先級最高,這樣就可以得到更高的捕包性能。