¿Cómo se organizan las opciones de IP en un encabezado de IP y cómo podemos extraerlas?

El primer byte del encabezado IP contiene 2 campos: los primeros 4 bits componen el campo Versión , los segundos 4 bits componen el campo Longitud del encabezado de Internet . Las opciones son opcionales, por lo que debe verificar si hay alguna presente.

Para verificar si hay opciones, debe consultar el campo Longitud del encabezado de Internet . Este campo especifica la longitud del encabezado en palabras. Las opciones tienen un desplazamiento de 5 palabras en el encabezado, por lo tanto, la longitud del encabezado debe ser mayor que 5 palabras si hay alguna opción especificada.

Se puede especificar más de una opción; El número de opciones especificadas se puede calcular restando el desplazamiento de la longitud del encabezado. Simplemente puede iterar sobre las opciones. Una cosa a tener en cuenta al iterar las opciones es que las opciones deben terminar en un límite de palabra y, como tal, los datos de la opción pueden rellenarse. En tales casos, la última opción se puede establecer en la opción especial EOL (Fin de la lista de opciones) que tiene un valor de 0.

Cada opción es diferente y requiere un manejo específico de la opción. Después del primer byte de la opción, para los datos de la opción de longitud variable, sigue un byte que indica la longitud de esa opción.

Con suerte, el siguiente código debería dar una explicación un poco más concreta. Estoy tomando algunos atajos por razones de brevedad.

  enum IPOption {
     IPOptionEOL,
     IPOptionNOP,
 };

 uint8_t * paquete;
 uint8_t internet_header_length;

 paquete = ...;
 internet_header_length = (* paquete >> 4);
 if (internet_header_length> 5 / * offsetof (struct ip_header, options) / sizeof (uint32_t) * /) {
     Opción uint32_t *;
     opción = (uint8_t *) y paquete [20 / * offsetof (struct ip_header, options) * /];
     while (opción > 0) & 0x01) * /
         / * class = ((opciones [opción] >> 1) & 0x03) * /
         / * opción = ((opciones [opción] >> 3) & 0x1f) * /

         if (((opciones [opción] >> 3) & 0x1f) == IPOptionEOL)
             descanso;

         interruptor ((opción [opción] >> 3) y 0x1f) {
         caso IPOptionEOL:
             afirmar (falso);  /* no alcanzado */
             opción = opción + 1;  / * EOL es de 1 byte de largo * /
             descanso;
         caso IPOptionNOP:
             opción = opción + 1;  / * NOP tiene 1 byte de largo * /
             descanso;
         ....
         }
     }
 }

NOTA : si está utilizando una biblioteca (o algo fuera del soporte estándar del lenguaje C, dado que la pregunta fue etiquetada con Programación C), es muy posible que tenga acceso a una función para extraer las opciones.

Puede usar Wireshark para capturar paquetes en su PC.

Dará detalles del contenido del paquete, incluido el campo de opciones del encabezado IP.