2013-06-19 1 views
4

, когда я открываю packetsocket на интерфейсе loopback (lo) и слушаю, что все пакеты видны дважды. почему это так?Packetsocket, открытый на устройстве loopback, получает все пакеты дважды. Как фильтровать эти повторяющиеся записи?

Но захват на интерфейсе с помощью tcpdump правильно игнорирует повторяющиеся записи. см. «пакеты, полученные фильтром» (который содержит дублированные пакеты) и «захваченные пакеты». Как это фильтрация осуществляется

ТСРйитр -i -s ло 0

tcpdump: verbose output suppressed, use -v or -vv for full protocol decode 
listening on lo, link-type EN10MB (Ethernet), capture size 65535 bytes 
11:00:08.439542 IP 12.0.0.3 > localhost.localdomain: icmp 64: echo request seq 1 
11:00:08.439559 IP localhost.localdomain > 12.0.0.3: icmp 64: echo reply seq 1 
11:00:09.439866 IP 12.0.0.3 > localhost.localdomain: icmp 64: echo request seq 2 
11:00:09.439884 IP localhost.localdomain > 12.0.0.3: icmp 64: echo reply seq 2 
11:00:10.439389 IP 12.0.0.3 > localhost.localdomain: icmp 64: echo request seq 3 
11:00:10.439410 IP localhost.localdomain > 12.0.0.3: icmp 64: echo reply seq 3 

6 packets captured 
12 packets received by filter 
0 packets dropped by kernel 

Мой код:

int main() 
{ 
    int sockFd; 

    if ((sockFd=socket(PF_PACKET, SOCK_DGRAM, 0))<0) { 
    perror("socket()"); 
    return -1; 
    } 

    /* bind the packet socket */ 
    struct sockaddr_ll addr; 
    struct ifreq ifr; 
    strncpy (ifr.ifr_name, "lo", sizeof(ifr.ifr_name)); 
    if(ioctl(sockFd, SIOCGIFINDEX, &ifr) == -1) 
    { 
    perror("iotcl"); 
    return -1; 
    } 
    memset(&addr, 0, sizeof(addr)); 
    addr.sll_family=AF_PACKET; 
    addr.sll_protocol=htons(ETH_P_ALL); 
    addr.sll_ifindex=ifr.ifr_ifindex; 
    if (bind(sockFd, (struct sockaddr *)&addr, sizeof(addr))) { 
    perror("bind()"); 
    return -1; 
    } 

    char buffer[MAX_BUFFER+1]; 
    int tmpVal = 1; 

    while(tmpVal > 0) 
    { 
    tmpVal = recv (sockFd, buffer, MAX_BUFFER, 0); 
    cout<<"Received Pkt with Bytes "<<tmpVal <<endl; 
    } 
} 

ответ

4

Разобрался проблему.

из libcaps кода:

* - The loopback device gives every packet twice; on 2.2[.x] kernels, 
*  if we use PF_PACKET, we can filter out the transmitted version 
*  of the packet by using data in the "sockaddr_ll" returned by 
*  "recvfrom()", but, on 2.0[.x] kernels, we have to use 
*  PF_INET/SOCK_PACKET, which means "recvfrom()" supplies a 
*  "sockaddr_pkt" which doesn't give us enough information to let 
*  us do that. 

слушающий объект должен фильтровать дублированный пакет с использованием if_index получил от recvfrom апи.

Смежные вопросы