基於VC完成的收集監聽功效法式實例。本站提示廣大學習愛好者:(基於VC完成的收集監聽功效法式實例)文章只能為提供參考,不一定能成為您想要的結果。以下是基於VC完成的收集監聽功效法式實例正文
本文所述VC++收集監聽器代碼,可以完成監聽收集銜接所應用的協定、源IP地址、目的IP地址等信息的功效,而且能把數據內容綁定到網格控件中顯示。詳細功效代碼部門以下所示:
//線程函數 UINT ThreadFun( LPVOID pParam ) { CSniffAppDlg* pDlg = static_cast<CSniffAppDlg*>(pParam); MSG msg; char buffer[1000],sourceip[32] ,*tempbuf; char *ptemp; BYTE* pData = NULL; //現實數據報中的數據 UINT sourceport ; CString str; HEADIP* pHeadIP; HEADICMP* pHeadICMP; HEADUDP* pHeadUDP; HEADTCP* pHeadTCP; in_addr addr; int ret; while (TRUE) { pData = NULL; if (PeekMessage(&msg,pDlg->m_hWnd,WM_CLOSE,WM_CLOSE,PM_NOREMOVE )) { closesocket(pDlg->m_Sock); break; } memset(buffer,0,1000); ret = recv(pDlg->m_Sock,buffer,1000,0); if (ret == SOCKET_ERROR) { continue; } else //吸收到數據 { tempbuf = buffer; pHeadIP = (HEADIP*)tempbuf; //獲得數據報總長度 WORD len = ntohs(pHeadIP->totallen); //獲得源IP pDlg->m_List.InsertItem(pDlg->m_List.GetItemCount(),""); addr.S_un.S_addr = pHeadIP->sourceIP; ptemp = inet_ntoa(addr); pDlg->m_List.SetItemText(pDlg->m_List.GetItemCount()-1,1,ptemp); //獲得目標IP addr.S_un.S_addr = pHeadIP->destIP; ptemp = inet_ntoa(addr); pDlg->m_List.SetItemText(pDlg->m_List.GetItemCount()-1,2,ptemp); //獲得協定稱號 ptemp = get_protoname(pHeadIP->proto); strcpy(sourceip,ptemp); pDlg->m_List.SetItemText(pDlg->m_List.GetItemCount()-1,0,sourceip); //獲得IP數據報總長度 WORD ipSumLen = ntohs(pHeadIP->totallen); //IP數據報頭總長度 int ipHeadLen = 20; //取得去除IP層數據的長度 WORD netlen = ipSumLen - ipHeadLen; //依據分歧年夜協定取得分歧協定的數據 switch (pHeadIP->proto) { case IPPROTO_ICMP: { pHeadICMP = (HEADICMP*)(tempbuf+20); pData = (BYTE*)(pHeadICMP)+4; //ICMP數據報頭共4個字節 //獲得數據的長度 netlen -= 4; break; } case IPPROTO_UDP: { pHeadUDP = (HEADUDP*)(tempbuf+20); pData = (BYTE*)pHeadUDP+8; //UDP數據報頭共8個字節 sourceport = ntohs(pHeadUDP->SourcePort); str.Format("%d",sourceport); //設置源端口 pDlg->m_List.SetItemText(pDlg->m_List.GetItemCount()-1,3,str); str.Empty(); netlen -= 8; break; } case IPPROTO_TCP: { pHeadTCP = (HEADTCP*)(tempbuf+20); sourceport = ntohs(pHeadTCP->SourcePort); pData = (BYTE*)pHeadTCP+20; //TCP數據報頭共20個字節 str.Format("%d",sourceport); //設置源端口 pDlg->m_List.SetItemText(pDlg->m_List.GetItemCount()-1,3,str); str.Empty(); netlen-= 20; break; } } //設置數據年夜小 str.Format("%d",netlen); pDlg->m_List.SetItemText(pDlg->m_List.GetItemCount()-1,4,str); str.Empty(); //設置數據 if (pData != NULL) { str.Format(" %s",pData); pDlg->m_List.SetItemText(pDlg->m_List.GetItemCount()-1,5,str); } str.Empty(); } } return 0; } void CSniffAppDlg::OnBeginlisten() { //創立套接字 m_Sock = socket(AF_INET,SOCK_RAW, IPPROTO_IP ); char name[128]; memset(name,0,128); hostent* phostent; phostent = gethostbyname(name); DWORD ip; ip = inet_addr(inet_ntoa(*(in_addr*)phostent->h_addr_list[0])); int timeout = 4000; //超時4秒 //設置吸收數據的超不時間 setsockopt(m_Sock,SOL_SOCKET,SO_RCVTIMEO,(const char*)&timeout,sizeof(timeout)); sockaddr_in skaddr; skaddr.sin_family = AF_INET; skaddr.sin_port = htons(700); skaddr.sin_addr.S_un.S_addr = ip; //綁定地址 if ( bind(m_Sock,(sockaddr*)&skaddr,sizeof(skaddr))==SOCKET_ERROR) { MessageBox("地址綁定毛病"); return; } DWORD inBuffer=1; DWORD outBuffer[10]; DWORD reValue = 0; if (WSAIoctl(m_Sock,SIO_RCVALL,&inBuffer,sizeof(inBuffer),&outBuffer,sizeof(outBuffer),&reValue,NULL,NULL)==SOCKET_ERROR) { MessageBox("設置緩沖區毛病."); closesocket(m_Sock); return; } else m_pThread = AfxBeginThread(ThreadFun,(void*)this); } void CSniffAppDlg::OnCancel() { if (m_pThread) { //m_pThread->ExitInstance(); delete m_pThread; } closesocket( m_Sock) ; CDialog::OnCancel(); }
該實例只是功效部門重要代碼,讀者可依據本身項目需求停止測試,加以改良與完美以後整合進本身項目中去。