2012-11-27 3 views
4

libpcap을 사용하여 IPv6 패킷을 스니핑하는 프로그램을 작성하고 TCP/IP를 통해 해당 패킷을 서버로 보냅니다.소켓 : 바이트 순서가 뒤섞 임

IP (v6) 패킷은 멀티 바이트 데이터가 아니지만 "비트 묶음"과 비슷하기 때문에 marshalling (htons ... 같은)을 사용하지 않습니다.

이상한 점은 stdout으로 패킷을 출력하고 멋지게 보이지만, 인터넷을 통해 전송하면 모두 뒤죽박죽이됩니다. netcat을 사용하여 내 서버가 문제가 아닌지 확인했습니다. 한 패킷은 올바르게 도착했지만 다른 패킷은 다른 바이트 순서를가집니다. 어떤 아이디어?

편집 : 그래, 멋진 'nos'가 맞았는데, 나는 hexdump에 속았습니다. 'hexdump -c'는 올바른 출력을 보여줍니다. 그러나 내 프로그램의 서버 부분 (솔직히 말해서 보낸 사람/클라이언트만큼 사랑을받지 못했고 코드를 게시하기 전에 다시 작성합니다) 때로는 2 번 읽고 올바른 데이터와 대부분의 시간은 그것을 즉시 얻고 순서를 뒤죽박죽 친다.

제 (송신) 코드 : 스니퍼 PROG (전송자)로부터

struct pb_elem { 
    size_t size; 
    u_char *data; 
}; 
-------------------------  

int send_all(int sockfd, packet_buf pbuf) { 
int res = 0, n, i; 
uint offset = 0, byteleft = 0; 
struct pb_elem *packet; 

res = packet_buf_dequeue(pbuf, &packet); 
while (res == 0) { 
    byteleft = packet->size; 
    offset = 0; 

    /* DEBUG */ fprintf(stderr, "DEBUG: send new packet\n"); 
    printf("DEBUG: Data size: %zu\n", packet->size); 
    for (i=0; i < packet->size; i++) { 
     printf(((i % 2 == 1) ? "%02X " : "%02X"), (unsigned int)*(packet->data+i)); 
    } 
    printf("\n"); 

    do { 
     n = send(sockfd, packet->data+offset, byteleft, 0); 
     if (n == -1) 
      break; 
     offset = n; 
     byteleft -= n; 
     /* DEBUG */ fprintf(stderr, "DEBUG: send: offset: %u, byteleft: %u\n", offset, byteleft); 
    } while (byteleft > 0); 

    if (n == -1) 
     fprintf(stderr, "Error: could not send whole packet."); 

    free(packet->data); 
    free(packet); 

    res = packet_buf_dequeue(pbuf, &packet); 
} 

return 0; 
} 

출력 샘플 (2 개 된 ICMPv6 패킷)

I 서버/수신기 프로그램 수신 무엇
IPv6Buffer started 
DATA: 
0800 277B 1EBD 0A00 2700 0001 86DD 6000 0000 0035 3A40 2001 0DB8 BBBB 0000 0000 0000 0000 0001 2001 0DB8 BBBB 0000 0000 0000 0000 0102 8000 160B 116F 0001 09BD B450 0000 0000 DD2A 0500 0000 0000 CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CA 
DATA: 
0800 277B 1EBD 0A00 2700 0001 86DD 6000 0000 0035 3A40 2001 0DB8 BBBB 0000 0000 0000 0000 0001 2001 0DB8 BBBB 0000 0000 0000 0000 0102 8000 3E08 116F 0002 0ABD B450 0000 0000 B42C 0500 0000 0000 CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CA 
DEBUG: start_sending 
DEBUG: Data size: 107 
0800 277B 1EBD 0A00 2700 0001 86DD 6000 0000 0035 3A40 2001 0DB8 BBBB 0000 0000 0000 0000 0001 2001 0DB8 BBBB 0000 0000 0000 0000 0102 8000 160B 116F 0001 09BD B450 0000 0000 DD2A 0500 0000 0000 CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CA 
DEBUG: Data size: 107 
0800 277B 1EBD 0A00 2700 0001 86DD 6000 0000 0035 3A40 2001 0DB8 BBBB 0000 0000 0000 0000 0001 2001 0DB8 BBBB 0000 0000 0000 0000 0102 8000 3E08 116F 0002 0ABD B450 0000 0000 B42C 0500 0000 0000 CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CA 

:

IPv6Buffer started 
DEBUG: start_receiving() 
DEBUG: pre-accept in receive_data() 
Data size: 214 
0800 277B 1EBD 0A00 2700 0001 86DD 6000 0000 0035 3A40 2001 0DB8 BBBB 0000 0000 
0000 0000 0001 2001 0DB8 BBBB 0000 0000 0000 0000 0102 8000 2598 1280 0001 B3C8 
B450 0000 0000 2381 0400 0000 0000 CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE CAFE 
CAFE CAFE CAFE CAFE CAFE CA08 0027 7B1E BD0A 0027 0000 0186 DD60 0000 0000 353A 
4020 010D B8BB BB00 0000 0000 0000 0000 0120 010D B8BB BB00 0000 0000 0000 0001 
0280 007A 9712 8000 02B4 C8B4 5000 0000 00CD 8004 0000 0000 00CA FECA FECA FECA 
FECA FECA FECA FECA FECA FECA FECA FECA FECA FECA FECA 
+0

코드는 무엇입니까? – netcoder

+1

이것은 의사 헤더를 포함한 완전한 ICMPv6 에코 요청 패킷입니다. 그 중 일부는 멀티 바이트 데이터이지만, 일반적으로 원하는 경우 32 비트 정수 (예 : nr)를 마샬링/언 마샬링합니다. 1337은 모든 플랫폼에서 실제로 1337이됩니다. 패킷이 네트워크 바이트 순서라고 말할 수 있고 항상 이런 식으로 유지하고 싶습니다. 데이터로 계산할 필요가 없으며 패킷은이 형식에서만 유효합니다. –

+0

@netcoder 흠. 뭔가 잊어 버린 걸 알았어. ^^ 고마워. –

답변

0

바이트 순서가 변경된 이유는 확실하지 않지만 수정이 필요합니다.

수신 측의 순진한 버전을 구현하여 MTU 크기만큼 버퍼에 들어갈만큼 많은 데이터를 수신하려고했습니다. 일반적으로 두 패킷을 모두 읽고 함께 사용합니다.

이제 수신기의 패킷 크기를 알려주어 개별적으로받는 기본 프로토콜을 구현 했으므로 순서대로 도착합니다.

관련 문제