Wireshark的Pcap檔案格式分析及解析源碼

來源:互聯網
上載者:User
下面主要介紹下Ethereal預設的*.pcap檔案儲存格式。 

Pcap檔案頭24B各欄位說明:

Magic:4B:0x1A 2B 3C 4D:用來標示檔案的開始Major:2B,0x02 00:當前檔案主要的版本號碼      Minor:2B,0x04 00當前檔案次要的版本號碼ThisZone:4B當地的標準時間;全零SigFigs:4B時間戳記的精度;全零SnapLen:4B最大的儲存長度    LinkType:4B鏈路類型常用類型: 0            BSD loopback devices, except for later OpenBSD
       1            Ethernet, and Linux loopback devices
       6            802.5 Token Ring
       7            ARCnet
       8            SLIP
       9            PPP
       10           FDDI
       100         LLC/SNAP-encapsulated ATM
       101         "raw IP", with no link
       102         BSD/OS SLIP
       103         BSD/OS PPP
       104         Cisco HDLC
       105         802.11
       108         later OpenBSD loopback devices (with the AF_value in network byte order)
       113         special Linux "cooked" capture
       114         LocalTalk 

 

    Packet 包頭和Packet 資料群組成欄位說明:Timestamp:時間戳記高位,精確到seconds      Timestamp:時間戳記低位,精確到microsecondsCaplen:當前資料區的長度,即抓取到的資料幀長度,由此可以得到下一個資料幀的位置。Len:離線資料長度 網路中實際資料幀的長度,一般不大於caplen,多數情況下和Caplen數值相等。 Packet 資料:即 Packet(通常就是鏈路層的資料幀)具體內容,長度就是Caplen,這個長度的後面,就是當前PCAP檔案中存放的下一個Packet資料包,也就是說:PCAP檔案裡面並沒有規定捕獲的Packet資料包之間有什麼佔空間字元串,下一組資料在檔案中的起始位置。我們需要靠第一個Packet包確定。最後,Packet資料部分的格式其實就是標準的網路協議格式了可以任何網路教材上找得到。

 

以下是我的實現,針對自訂的UDP的抓包檔案進行解析
typedef struct tagIpHead
{
    int version;//版本
    int headLength; //頭長度
    int  diffsever;
    int  totallength; //總長度
    int  identification;
    int  flag;
    int  fragment;
    int  ttl;
    int  protocoltype; //協議類型
    int  checksum;
    unsigned long  srcip;//源ip
    unsigned long  dstip;//目的ip
}IP_HEAD;
typedef struct tagUdpHead
{
    unsigned short  srcport; //源連接埠
    unsigned short  dstport; //目的連接埠
    int   length; //udp包長度
}UDP_HEAD;

 

unsigned long FileParse::Parse( const char* FileName,bool& bThreadRun)//,HWND hwnd )
{
    if (_wass_session)
    {
        delete _wass_session;
        _wass_session = NULL;
    }
    _wass_session = new WassSessions();
    //////////////////////////////////////////////////////////////////////////
    unsigned long lRes =0;
    FILE* pFile=NULL;
    int nReadSize = 0;
    char buff[FILE_READ_LEN];
    char acip[30];
    char portalip[30];
    char radiusip[30];
    unsigned long timestamp1;
    unsigned long timestamp2;
    CConfigure* config=new CConfigure();

    if (config)
    {
        //讀取ip地址,添加到iplist中
        unsigned long ipTmp=0;
        unsigned short portTmp=0;
        config->getIPConfig(acip,portalip,radiusip);
        cut_ip(acip,ipTmp,portTmp);
        acport_list.push_back(portTmp);
        acip_list.push_back(ipTmp);
        cut_ip(portalip,ipTmp,portTmp);
        portalip_list.push_back(ipTmp);
        portalport_list.push_back(portTmp);
        delete config;
        config = NULL;
    }
    //////////////////////////////////////////////////////////////////////////
    memset(buff,0,FILE_READ_LEN);
    do
    {

        pFile =fopen(FileName,"rb");
        //pFile =_open( FileName, _O_RDONLY | _O_BINARY );
        if (!pFile)
        {
            //failed for the file opened
            fprintf(stderr, "Open the file failed:%s ", strerror(errno));

            lRes = 2;
            break;
        }
        nReadSize = fread(buff,sizeof(char),24,pFile);
        if (nReadSize == 24)
        {
            while (!feof(pFile) && bThreadRun)
            {
                memset(buff,0,FILE_READ_LEN);
                nReadSize = fread(buff,sizeof(char),16,pFile);
                unsigned long nPacketLen=0;
                memcpy(&timestamp1,buff,4);
                memcpy(&timestamp2,buff+4,4);
                memcpy(&nPacketLen,buff+8,4);
                //nPacketLen = ntohl(nPacketLen);
                char* buf = new char[nPacketLen];
                memset(buf,0,nPacketLen);

                int nReadCount=0;
                //讀取包
                while (nReadCount < nPacketLen)
                {
                    nReadSize = fread(buff,sizeof(char),nPacketLen-nReadCount,pFile);
                    memcpy(buf+nReadCount,buff,nReadSize);
                    nReadCount += nReadSize;
                }
                //在此處處理ip/udp包部分
                int nOffset=14;//資料位移位置
                _ip->Parse(buf+nOffset);//ip解析
                if(_ip->wass_ip_head.protocoltype==17)//只處理UDP
                {
                    nOffset += 20;
                    _udp->Parse(buf+nOffset);//udp解析
                    nOffset +=8;
                    std::list<unsigned long>::iterator acit= acip_list.begin();
                    std::list<unsigned long>::iterator portalit = portalip_list.begin();
                    bool bFoundIP = false;
                    //暫時不考慮演算法,遍曆ip地址
                    //while (acit++ != acip_list.end())
                    for (;acit != acip_list.end();acit++)
                    {
                        unsigned long aIP = *acit;
                        char aTmp[20];

                        IPULongToString(aIP,aTmp);
                        IPULongToString(_ip->wass_ip_head.dstip,aTmp);
                        if (_ip->wass_ip_head.dstip== *acit  || _ip->wass_ip_head.srcip == *acit)
                        {
                        for (;portalit !=portalip_list.end();portalit++)
                        {
                            if (_ip->wass_ip_head.dstip== *portalit  || _ip->wass_ip_head.srcip == *portalit)
                            {
                                bFoundIP = true;
                                break;
                            }
                        }
                        break;
                        }
                    }
                    if (bFoundIP)
                    {
                        //此處是表示可以進行資料的解析
                        _portalPacket = new CPortalPacket();
                        _portalPacket->parse(buf + nOffset,nPacketLen - nOffset);
                    //設定包的源IP和目的IP,源連接埠,目的連接埠
                        _portalPacket->setIpAndPort(_ip->wass_ip_head.srcip,
                            _ip->wass_ip_head.dstip,_udp->wass_udp_head.srcport,_udp->wass_udp_head.dstport);
                        _portalPacket->setPacketTime(timestamp1,timestamp2);
                        _wass_session->AddPacket(_portalPacket,_sessions);
                    }
                    else
                    {
                       
                    }
                }
                if (buf)
                {
                    delete [] buf;

                }

            }
        }
    } while (false);
    if (pFile)
    {
        fclose(pFile);
    }

    //////////////////////////////////////////////////////////////////////////
    //::PostMessage(_hwnd,WM_FINISHED,0,0);
    return lRes;
}

 

發表於: 2010-11-05,修改於: 2010-11-05 20:08。

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.