zxDlg.cpp
资源名称:zx.rar [点击查看]
上传用户:aaagroup07
上传日期:2022-03-30
资源大小:1526k
文件大小:16k
源码类别:
网络截获/分析
开发平台:
C/C++
- // zxDlg.cpp : implementation file
- //
- #include "stdafx.h"
- #include "zx.h"
- #include "zxDlg.h"
- #include "pcap.h"
- #ifdef _DEBUG
- #define new DEBUG_NEW
- #undef THIS_FILE
- static char THIS_FILE[] = __FILE__;
- #endif
- #pragma pack(1) //进入字节对齐方式
- typedef struct FrameHeader_t { //帧首部
- BYTE DesMAC[6]; // 目的地址
- BYTE SrcMAC[6]; // 源地址
- WORD FrameType; // 帧类型
- } FrameHeader_t;
- typedef struct IPHeader_t { //IP首部
- BYTE Ver_HLen;
- BYTE TOS;
- WORD TotalLen;
- WORD ID;
- WORD Flag_Segment;
- BYTE TTL;
- BYTE Protocol;
- WORD Checksum;
- ULONG SrcIP;
- ULONG DstIP;
- } IPHeader_t;
- typedef struct Data_t { //包含帧首部和IP首部的数据包
- FrameHeader_t FrameHeader;
- IPHeader_t IPHeader;
- } Data_t;
- #pragma pack() //恢复缺省对齐方式
- pcap_t* thread_pNet;
- CListBox* thread_list_out;
- bool thread_can;
- CSliderCtrl *thread_pSlidCtrl;
- int TIME_ERR;
- int TIME_CANNOT;
- int PCAP_OPEN_FLAGS;
- int REC_MAX;
- int TIME_OUT;
- pcap_if_t* now_dev;
- CRITICAL_SECTION can_mutex; //串口读取 临界区变量
- /////////////////////////////////////////////////////////////////////////////
- // CAboutDlg dialog used for App About
- class CAboutDlg : public CDialog
- {
- public:
- CAboutDlg();
- // Dialog Data
- //{{AFX_DATA(CAboutDlg)
- enum { IDD = IDD_ABOUTBOX };
- CEdit m_edit_out;
- //}}AFX_DATA
- // ClassWizard generated virtual function overrides
- //{{AFX_VIRTUAL(CAboutDlg)
- protected:
- virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
- //}}AFX_VIRTUAL
- // Implementation
- protected:
- //{{AFX_MSG(CAboutDlg)
- virtual BOOL OnInitDialog();
- //}}AFX_MSG
- DECLARE_MESSAGE_MAP()
- };
- CAboutDlg::CAboutDlg() : CDialog(CAboutDlg::IDD)
- {
- //{{AFX_DATA_INIT(CAboutDlg)
- //}}AFX_DATA_INIT
- }
- void CAboutDlg::DoDataExchange(CDataExchange* pDX)
- {
- CDialog::DoDataExchange(pDX);
- //{{AFX_DATA_MAP(CAboutDlg)
- DDX_Control(pDX, IDC_EDIT_OUT, m_edit_out);
- //}}AFX_DATA_MAP
- }
- BEGIN_MESSAGE_MAP(CAboutDlg, CDialog)
- //{{AFX_MSG_MAP(CAboutDlg)
- //}}AFX_MSG_MAP
- END_MESSAGE_MAP()
- /////////////////////////////////////////////////////////////////////////////
- // CZxDlg dialog
- CZxDlg::CZxDlg(CWnd* pParent /*=NULL*/)
- : CDialog(CZxDlg::IDD, pParent)
- {
- //{{AFX_DATA_INIT(CZxDlg)
- //}}AFX_DATA_INIT
- // Note that LoadIcon does not require a subsequent DestroyIcon in Win32
- m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
- }
- void CZxDlg::DoDataExchange(CDataExchange* pDX)
- {
- CDialog::DoDataExchange(pDX);
- //{{AFX_DATA_MAP(CZxDlg)
- DDX_Control(pDX, IDC_LIST_OUT, m_list_out);
- DDX_Control(pDX, IDC_LIST_DEV, m_list_dev);
- DDX_Control(pDX, IDC_COMBO_DEV, m_com_dev);
- //}}AFX_DATA_MAP
- }
- BEGIN_MESSAGE_MAP(CZxDlg, CDialog)
- //{{AFX_MSG_MAP(CZxDlg)
- ON_WM_SYSCOMMAND()
- ON_WM_PAINT()
- ON_WM_QUERYDRAGICON()
- ON_CBN_SELCHANGE(IDC_COMBO_DEV, OnSelchangeComboDev)
- ON_WM_DESTROY()
- ON_BN_CLICKED(IDCLEAR, OnClear)
- ON_BN_CLICKED(IDC_BUTTON_SET, OnButtonSet)
- ON_BN_CLICKED(IDC_BUTTON_HELP, OnButtonHelp)
- //}}AFX_MSG_MAP
- END_MESSAGE_MAP()
- /////////////////////////////////////////////////////////////////////////////
- // CZxDlg message handlers
- BOOL CZxDlg::OnInitDialog()
- {
- CDialog::OnInitDialog();
- // Add "About..." menu item to system menu.
- // IDM_ABOUTBOX must be in the system command range.
- ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
- ASSERT(IDM_ABOUTBOX < 0xF000);
- CMenu* pSysMenu = GetSystemMenu(FALSE);
- if (pSysMenu != NULL)
- {
- CString strAboutMenu;
- strAboutMenu.LoadString(IDS_ABOUTBOX);
- if (!strAboutMenu.IsEmpty())
- {
- pSysMenu->AppendMenu(MF_SEPARATOR);
- pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);
- }
- }
- // Set the icon for this dialog. The framework does this automatically
- // when the application's main window is not a dialog
- SetIcon(m_hIcon, TRUE); // Set big icon
- SetIcon(m_hIcon, FALSE); // Set small icon
- // TODO: Add extra initialization here
- InitializeCriticalSection(&can_mutex);
- pcap_if_t *d;
- //获得本机的设备列表
- if (pcap_findalldevs_ex(PCAP_SRC_IF_STRING, //获取本机的接口设备
- NULL, //无需认证
- &alldevs, //指向设备列表首部
- errbuf //出错信息保存缓存区
- ) == -1)
- {
- AfxMessageBox("获得本机的设备列表失败!");
- return FALSE; //错误处理
- }
- m_list_out.AddString("获得本机的设备列表成功");
- //显示接口列表
- for(d= alldevs; d != NULL; d= d->next)
- {
- m_com_dev.AddString(d->name); //利用d->name获取该网络接口设备的名字
- }
- pNet=NULL;
- thread_list_out=&m_list_out;
- thread_can=false;
- now_dev=NULL;
- m_list_out.AddString("读取配置文件");
- ReadProfile();
- CSliderCtrl *pSlidCtrl=(CSliderCtrl*)GetDlgItem(IDC_SLIDER);
- pSlidCtrl->SetRange(0,10,TRUE);//设置滑动条范围
- pSlidCtrl->SetPos(5);//设置滑动条位置
- thread_pSlidCtrl=pSlidCtrl;
- HANDLE Capturer_Thread=CreateThread(NULL,0,Capturer,0,CREATE_SUSPENDED,NULL);
- if( Capturer_Thread==NULL )
- {
- AfxMessageBox("Capturer线程创建线程失败!");
- return FALSE;
- }
- else
- {
- ResumeThread(Capturer_Thread); // 恢复线程运行
- m_list_out.AddString("创建捕获线程成功");
- }
- return TRUE; // return TRUE unless you set the focus to a control
- }
- void CZxDlg::OnSysCommand(UINT nID, LPARAM lParam)
- {
- if ((nID & 0xFFF0) == IDM_ABOUTBOX)
- {
- CAboutDlg dlgAbout;
- dlgAbout.DoModal();
- }
- else
- {
- CDialog::OnSysCommand(nID, lParam);
- }
- }
- // If you add a minimize button to your dialog, you will need the code below
- // to draw the icon. For MFC applications using the document/view model,
- // this is automatically done for you by the framework.
- void CZxDlg::OnPaint()
- {
- if (IsIconic())
- {
- CPaintDC dc(this); // device context for painting
- SendMessage(WM_ICONERASEBKGND, (WPARAM) dc.GetSafeHdc(), 0);
- // Center icon in client rectangle
- int cxIcon = GetSystemMetrics(SM_CXICON);
- int cyIcon = GetSystemMetrics(SM_CYICON);
- CRect rect;
- GetClientRect(&rect);
- int x = (rect.Width() - cxIcon + 1) / 2;
- int y = (rect.Height() - cyIcon + 1) / 2;
- // Draw the icon
- dc.DrawIcon(x, y, m_hIcon);
- }
- else
- {
- CDialog::OnPaint();
- }
- }
- // The system calls this to obtain the cursor to display while the user drags
- // the minimized window.
- HCURSOR CZxDlg::OnQueryDragIcon()
- {
- return (HCURSOR) m_hIcon;
- }
- void CZxDlg::OnSelchangeComboDev()
- {
- // TODO: Add your control notification handler code here
- while(m_list_dev.GetCount()>0)
- {
- m_list_dev.DeleteString(0);
- }
- pcap_addr_t *a;
- pcap_if_t *d;
- d=alldevs;
- int com_num=m_com_dev.GetCurSel();
- int i=0;
- while(i<com_num)
- {
- d=d->next;
- i++;
- }
- now_dev=d;
- //获取该网络接口设备的描述字符串
- m_list_dev.AddString(d->description);
- //打开该网络接口
- pNet=pcap_open(d->name,REC_MAX,PCAP_OPEN_FLAGS,TIME_OUT,NULL,errbuf);//PCAP_OPENFLAG_PROMISCUOUS
- if(pNet==NULL)
- {
- AfxMessageBox("打开该网络接口失败!");
- }
- thread_pNet=pNet;
- ////////////////
- //获取该网络接口设备的IP地址信息
- a=d->addresses;
- if(a!=NULL)
- {
- for(; a!=NULL; a=a->next)
- {
- if (a->addr->sa_family==AF_INET) //判断该地址是否IP地址
- {
- CString out;
- //利用a->addr获取IP地址
- if(a->addr!=NULL)
- {
- out.Format("IP地址: %d.%d.%d.%d ",(int)a->addr->sa_data[2]&255,
- (int)a->addr->sa_data[3]&255,(int)a->addr->sa_data[4]&255,
- (int)a->addr->sa_data[5]&255);
- }
- else
- {
- out="IP地址: 空";
- }
- m_list_dev.AddString(out);
- //利用a->netmask获取网络掩码
- if(a->netmask!=NULL)
- {
- out.Format("网络掩码: %d.%d.%d.%d ",(int)a->netmask->sa_data[2]&255,
- (int)a->netmask->sa_data[3]&255,(int)a->netmask->sa_data[4]&255,
- (int)a->netmask->sa_data[5]&255);
- }
- else
- {
- out="网络掩码: 空";
- }
- m_list_dev.AddString(out);
- //利用a->broadaddr获取广播地址
- if(a->broadaddr!=NULL)
- {
- out.Format("广播地址: %d.%d.%d.%d ",(int)a->broadaddr->sa_data[2]&255,
- (int)a->broadaddr->sa_data[3]&255,(int)a->broadaddr->sa_data[4]&255,
- (int)a->broadaddr->sa_data[5]&255);
- }
- else
- {
- out="广播地址: 空";
- }
- m_list_dev.AddString(out);
- //利用a->dstaddr)获取目的地址
- if(a->dstaddr!=NULL)
- {
- out.Format("目的地址: %d.%d.%d.%d ",(int)a->dstaddr->sa_data[2]&255,
- (int)a->dstaddr->sa_data[3]&255,(int)a->dstaddr->sa_data[4]&255,
- (int)a->dstaddr->sa_data[5]&255);
- }
- else
- {
- out="目的地址: 空";
- }
- m_list_dev.AddString(out);
- }
- }
- }
- else
- {
- m_list_dev.AddString("该网卡无地址");
- }
- }
- void CZxDlg::OnDestroy()
- {
- CDialog::OnDestroy();
- // TODO: Add your message handler code here
- //释放设备列表
- pcap_freealldevs(alldevs);
- }
- void CZxDlg::OnOK()
- {
- // TODO: Add extra validation here
- if(thread_can==true)
- {
- thread_can=false;
- }
- else
- {
- thread_can=true;
- }
- }
- void CZxDlg::OnClear()
- {
- // TODO: Add your control notification handler code here
- EnterCriticalSection(&can_mutex); //进入临界区
- bool last_can=thread_can;
- thread_can=false;
- while(m_list_out.GetCount()>0)
- {
- m_list_out.DeleteString(0);
- }
- thread_can=last_can;
- LeaveCriticalSection(&can_mutex); //离开临界区
- }
- DWORD WINAPI CZxDlg::Capturer(PVOID pvoid)
- {
- while(true)
- {
- if(thread_pNet!=NULL && thread_can==true)
- {
- pcap_pkthdr* pkt_header,kt_header;
- pkt_header=&kt_header;
- const u_char* pkt_data;
- EnterCriticalSection(&can_mutex); //进入临界区
- if(pcap_next_ex(thread_pNet,&pkt_header,&pkt_data)==1)
- {
- LeaveCriticalSection(&can_mutex); //离开临界区
- /////////////////////////
- thread_list_out->AddString("------------------------------------------------------------");
- //////////////////////////
- CString cout_time,cout_len;
- struct timeval ts; /* time stamp */
- bpf_u_int32 len; /* length this packet (off wire) */
- len=pkt_header->len;
- ts=pkt_header->ts;
- cout_len.Format("数据包长度: %d",len);
- COleDateTime DataTime = ts.tv_sec;
- int nYear = DataTime.GetYear();
- int nMonth = DataTime.GetMonth();
- int nDay = DataTime.GetDay();
- int nHour = DataTime.GetHour();
- int nMin = DataTime.GetMinute();
- int nSec = DataTime.GetSecond();
- cout_time.Format("时间: %d年%d月%d号%d时%d分%d秒",nYear,nMonth,nDay,nHour,nMin,nSec);
- //////////////////////////
- Data_t * IPPacket;
- ULONG SourceIP,DestinationIP;
- IPPacket = (Data_t *) pkt_data;
- SourceIP = (IPPacket->IPHeader.SrcIP);
- DestinationIP = (IPPacket->IPHeader.DstIP);
- BYTE DesMAC[6]; // 目的地址
- BYTE SrcMAC[6]; // 源地址
- WORD FrameType; // 帧类型
- FrameType=ntohs(IPPacket->FrameHeader.FrameType);
- memcpy(DesMAC, IPPacket->FrameHeader.DesMAC, 6);
- memcpy(SrcMAC, IPPacket->FrameHeader.SrcMAC, 6);
- CString cout_DesMAC,cout_SrcMAC,cout_FrameType;
- cout_DesMAC.Format("目的地址: %d-%d-%d-%d-%d-%d ",(int)DesMAC[0]&255,
- (int)DesMAC[1]&255,(int)DesMAC[2]&255,(int)DesMAC[3]&255,
- (int)DesMAC[4]&255,(int)DesMAC[5]&255);
- cout_SrcMAC.Format("源地址: %d-%d-%d-%d-%d-%d ",(int)SrcMAC[0]&255,
- (int)SrcMAC[1]&255,(int)SrcMAC[2]&255,(int)SrcMAC[3]&255,
- (int)SrcMAC[4]&255,(int)SrcMAC[5]&255);
- if(FrameType>=2048)
- {
- cout_FrameType.Format("帧类型: %d ",FrameType);
- }
- else
- {
- cout_FrameType.Format("帧长度: %d ",FrameType);
- }
- /////////////////////////
- thread_list_out->AddString(cout_len+" "+cout_time);
- thread_list_out->AddString(cout_DesMAC+" "+cout_SrcMAC+" "+cout_FrameType);
- /////////////////////////
- if(FrameType==0x0800)
- {
- in_addr SourceIP_addr,DestinationIP_addr;
- CString cout_SourceIP,cout_DestinationIP;
- memcpy(&SourceIP_addr, &SourceIP, 4);
- memcpy(&DestinationIP_addr, &DestinationIP, 4);
- cout_SourceIP.Format("源IP地址: %s",inet_ntoa(SourceIP_addr));
- cout_DestinationIP.Format("目的IP地址: %s",inet_ntoa(DestinationIP_addr));
- thread_list_out->AddString(cout_DestinationIP+" "+cout_SourceIP);
- }
- /////////////////////////
- int sleep_time=thread_pSlidCtrl->GetPos()*100;
- Sleep(sleep_time);
- }
- else
- {
- LeaveCriticalSection(&can_mutex); //离开临界区
- thread_list_out->AddString("************************************************************");
- thread_list_out->AddString("捕获数据超时或失败!");
- Sleep(TIME_ERR);
- }
- }
- else
- {
- Sleep(TIME_CANNOT);
- }
- }
- return 0;
- }
- void CZxDlg::ReadProfile()
- {
- if((TIME_ERR=(GetPrivateProfileInt("捕获数据包参数", "捕获出错后睡眠时间", -1, "MyWinPcap.ini")))==-1)
- {
- WritePrivateProfileString ("捕获数据包参数", "捕获出错后睡眠时间", "1000", "MyWinPcap.ini");
- TIME_ERR=1000;
- }
- if((TIME_CANNOT=(GetPrivateProfileInt("捕获数据包参数", "不能捕获时睡眠时间", -1, "MyWinPcap.ini")))==-1)
- {
- WritePrivateProfileString ("捕获数据包参数", "不能捕获时睡眠时间", "1000", "MyWinPcap.ini");
- TIME_CANNOT=1000;
- }
- if((PCAP_OPEN_FLAGS=(GetPrivateProfileInt("捕获数据包参数", "捕获方式", -1, "MyWinPcap.ini")))==-1)
- {
- WritePrivateProfileString ("捕获数据包参数", "捕获方式", "1", "MyWinPcap.ini");
- PCAP_OPEN_FLAGS=1;
- }
- if((REC_MAX=(GetPrivateProfileInt("捕获数据包参数", "获取数据包最大长度", 0, "MyWinPcap.ini")))==0)
- {
- WritePrivateProfileString ("捕获数据包参数", "获取数据包最大长度", "1024", "MyWinPcap.ini");
- REC_MAX=1024;
- }
- if((TIME_OUT=(GetPrivateProfileInt("捕获数据包参数", "获取数据包超时时间", 0, "MyWinPcap.ini")))==0)
- {
- WritePrivateProfileString ("捕获数据包参数", "获取数据包超时时间", "1000", "MyWinPcap.ini");
- TIME_OUT=1000;
- }
- CString out;
- out.Format("捕获出错后睡眠时间: %d",TIME_ERR);
- m_list_out.AddString(out);
- out.Format("不能捕获时睡眠时间: %d",TIME_CANNOT);
- m_list_out.AddString(out);
- out.Format("捕获方式: %d",PCAP_OPEN_FLAGS);
- m_list_out.AddString(out);
- out.Format("获取数据包最大长度: %d",REC_MAX);
- m_list_out.AddString(out);
- out.Format("获取数据包超时时间: %d",TIME_OUT);
- m_list_out.AddString(out);
- }
- void CZxDlg::OnButtonSet()
- {
- // TODO: Add your control notification handler code here
- EnterCriticalSection(&can_mutex); //进入临界区
- bool last_can=thread_can;
- thread_can=false;
- ////////////////////////////////
- if(now_dev!=NULL)
- {
- //char filter[100] = "arp";
- char filter[100];
- CEdit *pedit_in=(CEdit*)GetDlgItem(IDC_EDIT_IN);
- pedit_in->GetLine(0,filter,100);
- struct bpf_program fcode;
- bpf_u_int32 localnet;
- bpf_u_int32 netmask;
- char thread_errbuf[PCAP_ERRBUF_SIZE];
- if(pcap_lookupnet(now_dev->name,&localnet,&netmask,thread_errbuf) < 0)
- {
- AfxMessageBox("查找子网掩码失败!");
- return;
- }
- //compile the filter
- if(pcap_compile(thread_pNet, &fcode, filter, 0, netmask) < 0)
- {
- AfxMessageBox("编译过滤字符串失败!");
- return;
- }
- //set the filter
- if(pcap_setfilter(thread_pNet, &fcode) <0)
- {
- AfxMessageBox("设置过滤字符串失败!");
- return;
- }
- ///////////////
- }
- else
- {
- thread_list_out->AddString("设备为空,无法过滤");
- }
- ///////////////////////////////////
- thread_can=last_can;
- LeaveCriticalSection(&can_mutex); //离开临界区
- }
- void CZxDlg::OnButtonHelp()
- {
- // TODO: Add your control notification handler code here
- CAboutDlg help_dlg;
- help_dlg.DoModal();
- }
- BOOL CAboutDlg::OnInitDialog()
- {
- CDialog::OnInitDialog();
- // TODO: Add extra initialization here
- CString out;
- out.LoadString(IDS_STRING_HELP);
- m_edit_out.SetWindowText(out);
- return TRUE; // return TRUE unless you set the focus to a control
- // EXCEPTION: OCX Property Pages should return FALSE
- }