ANNOUNCEMENT: Live Wireshark University & Allegro Packets online APAC Wireshark Training Session
April 17th, 2024 | 14:30-16:00 SGT (UTC+8) | Online

Wireshark-dev: [Wireshark-dev] Getting info from lower layer inside a dissect function.

From: Christian Hopps <chopps@xxxxxxxxxx>
Date: Sun, 19 Jan 2020 16:15:24 -0500
Hi,

I'm writing a dissector for IPTFS (https://tools.ietf.org/html/draft-ietf-ipsecme-iptfs-00) and inside the dissector I need to get the ESP sequence number. I've looked around some (not exhaustively) and don't see an easy way to get lower layer info from inside my dissector. Right now I'm using this hack:

  tvbuff_t *esptvb = get_esp_tvb(tvb, pinfo);
  guint32 seq_num = esptvb ? tvb_get_ntohl(esptvb, 4) : ~0u;

where get_esp_tvb is:

  static tvbuff_t *
  get_esp_tvb(tvbuff_t *tvb, packet_info *pinfo)
  {
      /* get_data_source_tvb_by_name(pinfo, "Frame") has bug use when fixed */
      for (GSList *e = pinfo->data_src; e; e = e->next) {
          tvbuff_t *esptvb = get_data_source_tvb((struct data_source *)e->data);
          for (; esptvb->next; esptvb = esptvb->next)
              /* look for when our original tvb is the next one (decrypted)
               * the current one should be ESP prior to decrypt copy. */
              if (esptvb->next->ds_tvb == tvb->ds_tvb)
                  return esptvb;
      }
      return NULL;
  }

This is pretty ugly as it counts on the ESP implementation creating a new tvbuff_t chain for the decrypted data (that's why the code is checking for the ds_tvb to change).

Is there a better way to get at the lower layer protocol data? Is the "proper" way to do this to just create an esp_seq_num field in the protocol info structure? This would sort of mimic the already existing copying of addresses and ports from the lower layers that upper layers use to look-back like I'm trying to do. Seems like there should be a more generic way to do this though (e.g., that allows future plugin functionality w/o modifications to the protocol info structure).

Thanks,
Chris.

P.S. get_data_source_tvb_by_name is broken otherwise i'd do the above as:

  static tvbuff_t *
  get_esp_tvb(tvbuff_t *tvb, packet_info *pinfo)
  {
      tvbuff_t *esptvb = get_data_source_tvb_by_name(pinfo, "Frame");
      for (; esptvb->next; esptvb = esptvb->next)
          /* look for when our original tvb is the next one (decrypted)
           * the current one should be ESP prior to decrypt copy. */
          if (esptvb->next->ds_tvb == tvb->ds_tvb)
              return esptvb;
      return NULL;
  }

I can submit a patch for fixing get_data_source_tvb_by_name too.

Thanks,
Chris.