Pass zero-length PSDU type information to the radio dissector.

We call that dissector even for zero-length PSDUs, so the radio
information is shown.  We also show the zero-length PSDU type.

We don't call the 802.11 dissector for zero-length PSDU frames.

That way, you don't have to open up the radiotap information to find out
about zero-length PSDU frames, we can support zero-length PSDU
information for other pseudo-headers and file types if they support it,
and taps using the radio information can get zero-length PSDU frame
information.

Change-Id: I7d5da4ea978d8ca4889fc76160f11e3416b4d036
Reviewed-on: https://code.wireshark.org/review/29034
Reviewed-by: Guy Harris <guy@alum.mit.edu>
This commit is contained in:
Guy Harris 2018-08-08 19:25:30 -07:00
parent 63126e284b
commit 5e2e9de930
3 changed files with 72 additions and 32 deletions

View File

@ -86,7 +86,7 @@ static int hf_wlan_radio_aggregate_duration = -1;
static int hf_wlan_radio_ifs = -1;
static int hf_wlan_radio_start_tsf = -1;
static int hf_wlan_radio_end_tsf = -1;
static int hf_wlan_zero_length_psdu_type = -1;
static expert_field ei_wlan_radio_assumed_short_preamble = EI_INIT;
static expert_field ei_wlan_radio_assumed_non_greenfield = EI_INIT;
@ -170,6 +170,12 @@ static const value_string fec_vals[] = {
{ 0, NULL }
};
static const value_string zero_length_psdu_vals[] = {
{ 0, "sounding PPDU" },
{ 1, "data not captured" },
{ 255, "vendor-specific" },
{ 0, NULL }
};
/*
* Lookup for the MCS index (0-76)
* returning the number of data bits per symbol
@ -439,9 +445,8 @@ static void adjust_agg_tsf(gpointer data, gpointer user_data)
* Dissect 802.11 pseudo-header containing radio information.
*/
static void
dissect_wlan_radio_phdr (tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree, void *data)
dissect_wlan_radio_phdr(tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree, struct ieee_802_11_phdr *phdr)
{
struct ieee_802_11_phdr *phdr = (struct ieee_802_11_phdr *)data;
proto_item *ti;
proto_tree *radio_tree;
float data_rate = 0.0f;
@ -1189,6 +1194,8 @@ dissect_wlan_radio_phdr (tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree,
}
}
} /* if (have_data_rate) */
if (phdr->has_zero_length_psdu_type)
proto_tree_add_uint(radio_tree, hf_wlan_zero_length_psdu_type, tvb, 0, 0, phdr->zero_length_psdu_type);
if (wlan_radio_timeline_enabled) {
tap_queue_packet(wlan_radio_timeline_tap, pinfo, wlan_radio_info);
@ -1206,7 +1213,13 @@ dissect_wlan_radio_phdr (tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree,
static int
dissect_wlan_radio (tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree, void *data)
{
dissect_wlan_radio_phdr (tvb, pinfo, tree, data);
struct ieee_802_11_phdr *phdr = (struct ieee_802_11_phdr *)data;
dissect_wlan_radio_phdr(tvb, pinfo, tree, phdr);
/* Is there anything there? A 0-length-psdu has no frame data. */
if (phdr->has_zero_length_psdu_type)
return tvb_captured_length(tvb);
/* dissect the 802.11 packet next */
return call_dissector_with_data(ieee80211_handle, tvb, pinfo, tree, data);
@ -1219,7 +1232,13 @@ dissect_wlan_radio (tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree, void
static int
dissect_wlan_noqos_radio (tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree, void *data)
{
dissect_wlan_radio_phdr (tvb, pinfo, tree, data);
struct ieee_802_11_phdr *phdr = (struct ieee_802_11_phdr *)data;
dissect_wlan_radio_phdr(tvb, pinfo, tree, phdr);
/* Is there anything there? A 0-length-psdu has no frame data. */
if (phdr->has_zero_length_psdu_type)
return tvb_captured_length(tvb);
/* dissect the 802.11 packet next */
return call_dissector_with_data(ieee80211_noqos_handle, tvb, pinfo, tree, data);
@ -1436,6 +1455,9 @@ void proto_register_ieee80211_radio(void)
"Total duration of the aggregate in microseconds, including any preamble or plcp header. "
"Calculated from the total subframe lengths, modulation and other phy data.", HFILL }},
{&hf_wlan_zero_length_psdu_type,
{"Zero-length PSDU Type", "wlan_radio.zero_len_psdu.type", FT_UINT8, BASE_HEX, VALS(zero_length_psdu_vals), 0x0,
"Type of zero-length PSDU", HFILL}},
};
static gint *ett[] = {

View File

@ -1330,15 +1330,33 @@ static const range_string zero_length_psdu_rsvals[] = {
static void
dissect_radiotap_0_length_psdu(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree,
int offset)
int offset, struct ieee_802_11_phdr *phdr)
{
proto_tree *zero_len_tree = NULL;
guint32 psdu_type;
zero_len_tree = proto_tree_add_subtree(tree, tvb, offset, 1,
ett_radiotap_0_length_psdu, NULL, "0-length PSDU");
proto_tree_add_item(zero_len_tree, hf_radiotap_0_length_psdu_type,
tvb, offset, 1, ENC_NA);
proto_tree_add_item_ret_uint(zero_len_tree, hf_radiotap_0_length_psdu_type,
tvb, offset, 1, ENC_NA, &psdu_type);
switch (psdu_type) {
case 0:
phdr->has_zero_length_psdu_type = TRUE;
phdr->zero_length_psdu_type = PHDR_802_11_SOUNDING_PSDU;
break;
case 1:
phdr->has_zero_length_psdu_type = TRUE;
phdr->zero_length_psdu_type = PHDR_802_11_DATA_NOT_CAPTURED;
break;
case 0xff:
phdr->has_zero_length_psdu_type = TRUE;
phdr->zero_length_psdu_type = PHDR_802_11_0_LENGTH_PSDU_VENDOR_SPECIFIC;
break;
}
}
static void
@ -1867,7 +1885,6 @@ dissect_radiotap(tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree, void* u
static struct _radiotap_info rtp_info_arr;
struct ieee80211_radiotap_iterator iter;
struct ieee_802_11_phdr phdr;
gboolean zero_length_psdu = FALSE;
guchar *bmap_start;
guint n_bitmaps;
guint i;
@ -2678,8 +2695,7 @@ dissect_radiotap(tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree, void* u
dissect_radiotap_he_mu_info(tvb, pinfo, radiotap_tree, offset);
break;
case IEEE80211_RADIOTAP_0_LENGTH_PSDU:
dissect_radiotap_0_length_psdu(tvb, pinfo, radiotap_tree, offset);
zero_length_psdu = TRUE;
dissect_radiotap_0_length_psdu(tvb, pinfo, radiotap_tree, offset, &phdr);
break;
}
}
@ -2691,13 +2707,6 @@ dissect_radiotap(tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree, void* u
proto_item_append_text(ti, " (malformed)");
}
/*
* Is there anything there? A 0-length-psdu has no frame data.
*/
if (zero_length_psdu) {
return tvb_captured_length(tvb);
}
hand_off_to_80211:
/* Grab the rest of the frame. */
next_tvb = tvb_new_subset_remaining(tvb, length);

View File

@ -797,10 +797,10 @@ union ieee_802_11_phy_info {
};
struct ieee_802_11_phdr {
gint fcs_len; /* Number of bytes of FCS - -1 means "unknown" */
gboolean decrypted; /* TRUE if frame is decrypted even if "protected" bit is set */
gboolean datapad; /* TRUE if frame has padding between 802.11 header and payload */
guint phy; /* PHY type */
gint fcs_len; /* Number of bytes of FCS - -1 means "unknown" */
gboolean decrypted; /* TRUE if frame is decrypted even if "protected" bit is set */
gboolean datapad; /* TRUE if frame has padding between 802.11 header and payload */
guint phy; /* PHY type */
union ieee_802_11_phy_info phy_info;
/* Which of this information is present? */
@ -812,18 +812,20 @@ struct ieee_802_11_phdr {
guint has_signal_dbm:1;
guint has_noise_dbm:1;
guint has_tsf_timestamp:1;
guint has_aggregate_info:1; /* aggregate flags and ID */
guint has_aggregate_info:1; /* aggregate flags and ID */
guint has_zero_length_psdu_type:1; /* zero-length PSDU type */
guint16 channel; /* Channel number */
guint32 frequency; /* Channel center frequency */
guint16 data_rate; /* Data rate, in .5 Mb/s units */
guint8 signal_percent; /* Signal level, as a percentage */
guint8 noise_percent; /* Noise level, as a percentage */
gint8 signal_dbm; /* Signal level, in dBm */
gint8 noise_dbm; /* Noise level, in dBm */
guint16 channel; /* Channel number */
guint32 frequency; /* Channel center frequency */
guint16 data_rate; /* Data rate, in .5 Mb/s units */
guint8 signal_percent; /* Signal level, as a percentage */
guint8 noise_percent; /* Noise level, as a percentage */
gint8 signal_dbm; /* Signal level, in dBm */
gint8 noise_dbm; /* Noise level, in dBm */
guint64 tsf_timestamp;
guint32 aggregate_flags; /* A-MPDU flags */
guint32 aggregate_id; /* ID for A-MPDU reassembly */
guint32 aggregate_flags; /* A-MPDU flags */
guint32 aggregate_id; /* ID for A-MPDU reassembly */
guint8 zero_length_psdu_type; /* type of zero-length PSDU */
};
/*
@ -832,6 +834,13 @@ struct ieee_802_11_phdr {
#define PHDR_802_11_LAST_PART_OF_A_MPDU 0x00000001 /* this is the last part of an A-MPDU */
#define PHDR_802_11_A_MPDU_DELIM_CRC_ERROR 0x00000002 /* delimiter CRC error after this part */
/*
* Zero-length PSDU types.
*/
#define PHDR_802_11_SOUNDING_PSDU 0 /* sounding PPDU */
#define PHDR_802_11_DATA_NOT_CAPTURED 1 /* data not captured, (e.g. multi-user PPDU) */
#define PHDR_802_11_0_LENGTH_PSDU_VENDOR_SPECIFIC 0xff
/* Packet "pseudo-header" for the output from CoSine L2 debug output. */
#define COSINE_MAX_IF_NAME_LEN 128