как декодировать пакетные данные, анализ пакетов

Мне нужна помощь для моего проекта. Я не силен в этом. вот мой сервер-приемник. это кодирование выполняется для физического ПК. в основном это кодирование на физическом ПК предназначено для получения пакета данных от виртуального приемника. Оно работает. но почему-то у меня была проблема с декодированием информации о пакете, и я нуб во всем этом.

#define HAVE_REMOTE
#define MAX_BUF_SIZE 1024
#define snprintf _snprintf
#define ETH_ALEN 6
#define IP_ALEN 4
#define ARP_REQUEST 1
#define ARP_REPLY 2

#include <stdlib.h>
#include <stdio.h>
#include <winsock2.h>
#include <pcap.h>

#pragma comment(lib, "wpcap.lib")
#pragma comment(lib, "Ws2_32.lib")


// A sample of the select() return value
int recvfromTimeOutUDP(SOCKET socket, long sec, long usec)
{
  // Setup timeval variable
  struct timeval timeout;
  struct fd_set fds;

  timeout.tv_sec = sec;
  timeout.tv_usec = usec;
  // Setup fd_set structure
  FD_ZERO(&fds);
  FD_SET(socket, &fds);
  // Return value:
  // -1: error occurred
  // 0: timed out
  // > 0: data ready to be read
  return select(0, &fds, 0, 0, &timeout);
}


int main(int argc, char **argv)
{
  WSADATA            wsaData;
  SOCKET             ReceivingSocket;
  SOCKADDR_IN        ReceiverAddr;
  int                Port = 5150;
  char          ReceiveBuf[6000];
  int                BufLength = 6000;
  SOCKADDR_IN        SenderAddr;
  int                SenderAddrSize = sizeof(SenderAddr);
  int                ByteReceived = 5, SelectTiming, ErrorCode;
  char ch = 'Y';

 // Initialize Winsock version 2.2
 if( WSAStartup(MAKEWORD(2,2), &wsaData) != 0)
 {
     printf("Server: WSAStartup failed with error %ld\n", WSAGetLastError());
     return -1;
 }
 else
       printf("Server: The Winsock DLL status is %s.\n", wsaData.szSystemStatus);

       // Create a new socket to receive datagrams on.
       ReceivingSocket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);

       if (ReceivingSocket == INVALID_SOCKET)
       {
         printf("Server: Error at socket(): %ld\n", WSAGetLastError());
         // Clean up
         WSACleanup();
         // Exit with error
         return -1;
        }
        else
        printf("Server: socket() is OK!\n");

        // Set up a SOCKADDR_IN structure that will tell bind that we
        // want to receive datagrams from all interfaces using port 5150.

        // The IPv4 family
        ReceiverAddr.sin_family = AF_INET;
        // Port no. 5150
        ReceiverAddr.sin_port = htons(Port);
        // From all interface (0.0.0.0)
        ReceiverAddr.sin_addr.s_addr = htonl(INADDR_ANY);

        // Associate the address information with the socket using bind.
        // At this point you can receive datagrams on your bound socket.
        if (bind(ReceivingSocket, (SOCKADDR *)&ReceiverAddr, sizeof(ReceiverAddr)) == SOCKET_ERROR)
         {
                   printf("Server: bind() failed! Error: %ld.\n", WSAGetLastError());
                   // Close the socket
                   closesocket(ReceivingSocket);
                   // Do the clean up
                   WSACleanup();
                   // and exit with error
                   return -1;
                 }
                 else
                 printf("Server: bind() is OK!\n");

       // Some info on the receiver side...
      getsockname(ReceivingSocket, (SOCKADDR *)&ReceiverAddr, (int *)sizeof(ReceiverAddr));

      printf("Server: Receiving IP(s) used: %s\n", inet_ntoa(ReceiverAddr.sin_addr));
      printf("Server: Receiving port used: %d\n", htons(ReceiverAddr.sin_port));
      printf("Server: I\'m ready to receive a datagram...\n");

      SelectTiming = recvfromTimeOutUDP(ReceivingSocket, 100, 0);

      switch (SelectTiming)
      {
         case 0:
             // Timed out, do whatever you want to handle this situation
             printf("Server: Timeout while waiting for client!...\n");
             break;
         case -1:
             // Error occurred, maybe we should display an error message?
            // Need more tweaking here and the recvfromTimeOutUDP()...
             printf("Server: Some error encountered with code number: %ld\n", WSAGetLastError());
             break;
         default:
             {
                  while (1)


                  {
                       // Call recvfrom() to get it then display the received data...
                       ByteReceived = recvfrom(ReceivingSocket, ReceiveBuf, BufLength,
                                                0, (SOCKADDR *)&SenderAddr, &SenderAddrSize);
                       if ( ByteReceived > 0 )
                       {
                           printf("\n\nServer: Total Bytes received: %d\n", ByteReceived);
                           printf("Server: The data is \"%s\"\n", ReceiveBuf);
                       }
                       else if ( ByteReceived <= 0 )
                            printf("Server: Connection closed with error code: %ld\n",
                                        WSAGetLastError());
                       else
                            printf("Server: recvfrom() failed with error code: %d\n",
                                    WSAGetLastError());

                       // Some info on the sender side
                       getpeername(ReceivingSocket, (SOCKADDR *)&SenderAddr, &SenderAddrSize);
                       printf("Server: Sending IP used: %s\n", inet_ntoa(SenderAddr.sin_addr));
                       printf("Server: Sending port used: %d\n", htons(SenderAddr.sin_port));

                       printf("TIME -", ReceiveBuf);
                  }

             }





        }



       // When your application is finished receiving datagrams close the socket.
          printf("Server: Finished receiving. Closing the listening socket...\n");
          if (closesocket(ReceivingSocket) != 0)
              printf("Server: closesocket() failed! Error code: %ld\n", WSAGetLastError());
          else
              printf("Server: closesocket() is OK...\n");

      // When your application is finished call WSACleanup.
       printf("Server: Cleaning up...\n");
       if(WSACleanup() != 0)
          printf("Server: WSACleanup() failed! Error code: %ld\n", WSAGetLastError());
       else
          printf("Server: WSACleanup() is OK\n");
       // Back to the system
       // system("PAUSE");
       return 0;
 }

Ниже приведен пример, который я получаю в своем CLI на физическом ПК. Я считаю, что это пакеты, полученные от виртуального приемника. Я был сбит с толку, как мне расшифровать его в

Время|Mac-адрес отправителя|Целевой Mac-адрес|Длина пакета|Тип эфира|Исходный IP-адрес| IP-адрес назначения

 Server: Total Bytes received: 4000
 Server: The data is "Time : 10:32:24.759385   
 0050568214540064403a1c000800450000285aeb40007f06b0c4ac10a40bac10f3f3c0990d3d740222860176142f5010054e40620000000000000000"
 Server: Sending IP used: 172.16.243.243
 Server: Sending port used: 59079


 Server: Total Bytes received: 4000
 Server: The data is "Time : 10:32:24.759385
 0050568214540064403a1c000800450000285aeb40007f06b0c4ac10a40bac10f3f3c0990d3d740222860176142f5010054e40620000000000000000"
 Server: Sending IP used: 172.16.243.243
 Server: Sending port used: 59080

Как расшифровать анализ информации о пакете?

расшифровать его, что-то вроде этого.

Время|Mac-адрес отправителя|Целевой Mac-адрес|Длина пакета|Тип эфира|Исходный IP-адрес| IP-адрес назначения


person Khein    schedule 09.07.2012    source источник
comment
Похоже, вы не знаете формат полученной дейтаграммы?   -  person ciphor    schedule 10.07.2012
comment
@ciphor ya .. новичок в этом. спасибо, почитаю про дейтаграммы.   -  person Khein    schedule 11.07.2012


Ответы (1)


Вы предположительно записали данные в байтовый буфер, чтобы отправить его. При его получении вам просто нужно прочитать данные из буфера приема так же, как вы их записали. Мы можем видеть только ваш код получения, поэтому мы можем только догадываться, что вы отправляете, но скажем, например, что вы записываете целые числа 4 x 4 байта в буфер символов, а затем отправляете через сокет. Принимающий код должен будет сделать что-то вроде

   int iData1 = 0;
   int iData2 = 0;
   int iData3 = 0;
   int iData4 = 0;
   char* szIt = ReceiveBuff;          // set a pointer to start of receive buffer
   memcpy(&iData1,szIt,sizeof(int);   // memcpy first item
   szIt += sizeof(int);               // point to location in buffer of next item   
   memcpy(&iData2,szIt,sizeof(int);   // memcpy second....
   szIt += sizeof(int);

   // Now do the rest of the data items until you have read 
   // everything in the packet

и так далее для следующих пунктов. Если у вас есть разные типы, вам нужно увеличить указатель на размер этих типов. Есть и другие способы сделать то же самое, но этот будет работать. Очень важная вещь, которую вы должны учитывать при этом, — это конечность машины, на которую вы отправляете и получаете. Вы можете заставить свои данные писать big endean, чтобы клиент знал и мог с ними справиться, если он сам по себе маленький endean.

Важная вещь - это порядок отправляемых данных и интерпретация вашего байтового буфера одинаково на стороне клиента.

Надеюсь это поможет

person mathematician1975    schedule 09.07.2012
comment
Привет! Спасибо за советы! Я пытаюсь, но это не сработало. он не получил буфер. У вас есть пример или веб-сайт такого рода. Большое спасибо. - person Khein; 10.07.2012
comment
Если вы не получаете буфер, похоже, что проблема может быть в вашем клиентском коде. - person mathematician1975; 10.07.2012