2013-05-28 68 views
0

我想使用套接字來嗅探OpenFlow數據包。我有一些代碼嘗試收集OF數據包並打印標題信息,但它似乎並未打印正確的信息。我已經在mininet中建立了一個環境,並將它指向了一個遙控器。在wireshark中,我看到標準回顯請求/回覆正在進行,在openflow中是標題部分中定義的類型2和3。當我查看我在程序中收集到的數據包數據時,我似乎打印了奇數類型2數據包,沒有其他東西讓我認爲我的代碼不正確,打印的類型2數據包不是類型2數據包。嗅探OpenFlow數據包意外的數據打印

我一直在玩這一段時間,所以我很抱歉,如果它有點混亂/不完美。我曾試圖使它可讀大家:

#include <stdio.h> 
#include <sys/socket.h> 
#include <arpa/inet.h> 
#include <assert.h> 
#include <stdlib.h> 
#include <string.h> 
#include <unistd.h> 
#include <netinet/ip.h> 
#include <netinet/tcp.h> 
#include <openflow/openflow.h> 
#include "openflow/lib/ofpbuf.h" 

int sock_raw; 
void DieWithError(char *errorMessage); 
void handlePacket(unsigned char *, int); 
void printOFHeader(struct ofp_header *); 

int main() 
{ 
    int saddr_size , data_size; 
    struct sockaddr saddr; 
    unsigned char *buffer = (unsigned char *)malloc(65536); //Its Big! -- Malloc allocates a block of size bytes of memory, returning a pointer to the beginning of the block 
    printf("Starting...\n"); 

    //Create a raw socket that shall sniff 
    sock_raw = socket(AF_INET , SOCK_RAW , IPPROTO_TCP); 
    printf("socket: %d\n",sock_raw); 
    if(sock_raw < 0) 
    { 
     printf("Socket Error\n"); 
     return 1; 
    } 


    while(1) 
    { 

     saddr_size = sizeof saddr; 
     //Receive a packet 

     data_size = recvfrom(sock_raw, buffer, 65536, 0 , &saddr , (socklen_t*)&saddr_size); 
     if(data_size <0) 
     { 
      printf("Recvfrom error , failed to get packets\n"); 
      return 1; 
     } 

     //Now process the packet 
     handlePacket(buffer, data_size); 
    } 
    close(sock_raw); 
    printf("Finished"); 
    return 0; 
} 

void DieWithError(char *errorMessage) 
{ 
    perror(errorMessage); 
    exit(1); 
} 

void handlePacket(unsigned char *buff, int data_size) 
{ 

    //first get IP header length 
    struct iphdr *iph = (struct iphdr *)buff; 
    unsigned short iphdrlen = iph->ihl*4; 

    //get tcp header length 
    struct tcphdr *tcph = (struct tcphdr*)(buff + iphdrlen); 
    unsigned int ofph_offset = (iphdrlen+(unsigned int)tcph->doff*4); 

    //add total length of ip and tcp headers to the buffer to get the start of the OF Header 
    struct ofp_header *oh = (struct ofp_header*)(buff + ofph_offset); 

    //Check it is an OF Header -- Not sure this is right 
    if(oh->version == OFP_VERSION) 
    { 
     printOFHeader(oh); 
    } 
    else 
    { 
     printf("This is not an openflow packet\n"); 
    } 
} 

void printOFHeader(struct ofp_header * oh) 
{ 
    printf("OPENFLOW PACKET HEADER\n"); 
    printf(" |-OF Version   %d\n", oh->version); 
    printf(" |-Type:    %d\n", oh->type); 
    printf(" |-Transaction ID:    %d\n", oh->xid); 
    printf(" |-Length:    %d\n", oh->length); 
    printf("----------------------------------------------------"); 
    printf("\n"); 
} 

我已經爲下測試出來的數據:

//first get IP header length 
    struct iphdr *iph = (struct iphdr *)buff; 
    unsigned short iphdrlen = iph->ihl*4; 

    //get tcp header length 
    struct tcphdr *tcph = (struct tcphdr*)(buff + iphdrlen); 

這些打印的數據包正確的端口地址和IP地址,所以我覺得我的缺陷在於我如何分配ofp_header結構。這個問題可能會更好地放在openflow.org網站上,但我一直無法找到郵件組。

回答