ieee80211-radiotap: Add definitions for HE information and dissect it.
[metze/wireshark/wip.git] / epan / dissectors / packet-ieee80211-radiotap.c
1 /*
2  *  packet-ieee80211-radiotap.c
3  *      Decode packets with a Radiotap header
4  *
5  * Wireshark - Network traffic analyzer
6  * By Gerald Combs <gerald@wireshark.org>
7  * Copyright 1998 Gerald Combs
8  *
9  * Copied from README.developer
10  *
11  * This program is free software; you can redistribute it and/or
12  * modify it under the terms of the GNU General Public License
13  * as published by the Free Software Foundation; either version 2
14  * of the License, or (at your option) any later version.
15  *
16  * This program is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19  * GNU General Public License for more details.
20  *
21  * You should have received a copy of the GNU General Public License
22  * along with this program; if not, write to the Free Software
23  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
24  */
25
26 #include "config.h"
27
28 #include <errno.h>
29
30 #include <epan/packet.h>
31 #include <epan/capture_dissectors.h>
32 #include <wsutil/pint.h>
33 #include <epan/crc32-tvb.h>
34 #include <wsutil/frequency-utils.h>
35 #include <epan/tap.h>
36 #include <epan/prefs.h>
37 #include <epan/addr_resolv.h>
38 #include <epan/expert.h>
39 #include "packet-ieee80211.h"
40 #include "packet-ieee80211-radiotap-iter.h"
41
42 void proto_register_radiotap(void);
43 void proto_reg_handoff_radiotap(void);
44
45 /* protocol */
46 static int proto_radiotap = -1;
47
48 static int hf_radiotap_version = -1;
49 static int hf_radiotap_pad = -1;
50 static int hf_radiotap_length = -1;
51 static int hf_radiotap_present = -1;
52 static int hf_radiotap_mactime = -1;
53 /* static int hf_radiotap_channel = -1; */
54 static int hf_radiotap_channel_frequency = -1;
55 static int hf_radiotap_channel_flags = -1;
56 static int hf_radiotap_channel_flags_turbo = -1;
57 static int hf_radiotap_channel_flags_cck = -1;
58 static int hf_radiotap_channel_flags_ofdm = -1;
59 static int hf_radiotap_channel_flags_2ghz = -1;
60 static int hf_radiotap_channel_flags_5ghz = -1;
61 static int hf_radiotap_channel_flags_passive = -1;
62 static int hf_radiotap_channel_flags_dynamic = -1;
63 static int hf_radiotap_channel_flags_gfsk = -1;
64 static int hf_radiotap_channel_flags_gsm = -1;
65 static int hf_radiotap_channel_flags_sturbo = -1;
66 static int hf_radiotap_channel_flags_half = -1;
67 static int hf_radiotap_channel_flags_quarter = -1;
68 static int hf_radiotap_rxflags = -1;
69 static int hf_radiotap_rxflags_badplcp = -1;
70 static int hf_radiotap_xchannel_channel = -1;
71 static int hf_radiotap_xchannel_frequency = -1;
72 static int hf_radiotap_xchannel_flags = -1;
73 static int hf_radiotap_xchannel_flags_turbo = -1;
74 static int hf_radiotap_xchannel_flags_cck = -1;
75 static int hf_radiotap_xchannel_flags_ofdm = -1;
76 static int hf_radiotap_xchannel_flags_2ghz = -1;
77 static int hf_radiotap_xchannel_flags_5ghz = -1;
78 static int hf_radiotap_xchannel_flags_passive = -1;
79 static int hf_radiotap_xchannel_flags_dynamic = -1;
80 static int hf_radiotap_xchannel_flags_gfsk = -1;
81 static int hf_radiotap_xchannel_flags_gsm = -1;
82 static int hf_radiotap_xchannel_flags_sturbo = -1;
83 static int hf_radiotap_xchannel_flags_half = -1;
84 static int hf_radiotap_xchannel_flags_quarter = -1;
85 static int hf_radiotap_xchannel_flags_ht20 = -1;
86 static int hf_radiotap_xchannel_flags_ht40u = -1;
87 static int hf_radiotap_xchannel_flags_ht40d = -1;
88 #if 0
89 static int hf_radiotap_xchannel_maxpower = -1;
90 #endif
91 static int hf_radiotap_fhss_hopset = -1;
92 static int hf_radiotap_fhss_pattern = -1;
93 static int hf_radiotap_datarate = -1;
94 static int hf_radiotap_antenna = -1;
95 static int hf_radiotap_dbm_antsignal = -1;
96 static int hf_radiotap_db_antsignal = -1;
97 static int hf_radiotap_dbm_antnoise = -1;
98 static int hf_radiotap_db_antnoise = -1;
99 static int hf_radiotap_tx_attenuation = -1;
100 static int hf_radiotap_db_tx_attenuation = -1;
101 static int hf_radiotap_txpower = -1;
102 static int hf_radiotap_vendor_ns = -1;
103 static int hf_radiotap_ven_oui = -1;
104 static int hf_radiotap_ven_subns = -1;
105 static int hf_radiotap_ven_skip = -1;
106 static int hf_radiotap_ven_data = -1;
107 static int hf_radiotap_mcs = -1;
108 static int hf_radiotap_mcs_known = -1;
109 static int hf_radiotap_mcs_have_bw = -1;
110 static int hf_radiotap_mcs_have_index = -1;
111 static int hf_radiotap_mcs_have_gi = -1;
112 static int hf_radiotap_mcs_have_format = -1;
113 static int hf_radiotap_mcs_have_fec = -1;
114 static int hf_radiotap_mcs_have_stbc = -1;
115 static int hf_radiotap_mcs_have_ness = -1;
116 static int hf_radiotap_mcs_ness_bit1 = -1;
117 static int hf_radiotap_mcs_bw = -1;
118 static int hf_radiotap_mcs_index = -1;
119 static int hf_radiotap_mcs_gi = -1;
120 static int hf_radiotap_mcs_format = -1;
121 static int hf_radiotap_mcs_fec = -1;
122 static int hf_radiotap_mcs_stbc = -1;
123 static int hf_radiotap_mcs_ness_bit0 = -1;
124 static int hf_radiotap_ampdu = -1;
125 static int hf_radiotap_ampdu_ref = -1;
126 static int hf_radiotap_ampdu_flags = -1;
127 static int hf_radiotap_ampdu_flags_report_zerolen = -1;
128 static int hf_radiotap_ampdu_flags_is_zerolen = -1;
129 static int hf_radiotap_ampdu_flags_last_known = -1;
130 static int hf_radiotap_ampdu_flags_is_last = -1;
131 static int hf_radiotap_ampdu_flags_delim_crc_error = -1;
132 static int hf_radiotap_ampdu_delim_crc = -1;
133 static int hf_radiotap_vht = -1;
134 static int hf_radiotap_vht_known = -1;
135 static int hf_radiotap_vht_have_stbc = -1;
136 static int hf_radiotap_vht_have_txop_ps = -1;
137 static int hf_radiotap_vht_have_gi = -1;
138 static int hf_radiotap_vht_have_sgi_nsym_da = -1;
139 static int hf_radiotap_vht_have_ldpc_extra = -1;
140 static int hf_radiotap_vht_have_bf = -1;
141 static int hf_radiotap_vht_have_bw = -1;
142 static int hf_radiotap_vht_have_gid = -1;
143 static int hf_radiotap_vht_have_p_aid = -1;
144 static int hf_radiotap_vht_stbc = -1;
145 static int hf_radiotap_vht_txop_ps = -1;
146 static int hf_radiotap_vht_gi = -1;
147 static int hf_radiotap_vht_sgi_nsym_da = -1;
148 static int hf_radiotap_vht_ldpc_extra = -1;
149 static int hf_radiotap_vht_bf = -1;
150 static int hf_radiotap_vht_bw = -1;
151 static int hf_radiotap_vht_nsts[4] = { -1, -1, -1, -1 };
152 static int hf_radiotap_vht_mcs[4] = { -1, -1, -1, -1 };
153 static int hf_radiotap_vht_nss[4] = { -1, -1, -1, -1 };
154 static int hf_radiotap_vht_coding[4] = { -1, -1, -1, -1 };
155 static int hf_radiotap_vht_datarate[4] = { -1, -1, -1, -1 };
156 static int hf_radiotap_vht_gid = -1;
157 static int hf_radiotap_vht_p_aid = -1;
158 static int hf_radiotap_vht_user = -1;
159 static int hf_radiotap_timestamp = -1;
160 static int hf_radiotap_timestamp_ts = -1;
161 static int hf_radiotap_timestamp_accuracy = -1;
162 static int hf_radiotap_timestamp_unit = -1;
163 static int hf_radiotap_timestamp_spos = -1;
164 static int hf_radiotap_timestamp_flags_32bit = -1;
165 static int hf_radiotap_timestamp_flags_accuracy = -1;
166
167 /* "Present" flags */
168 static int hf_radiotap_present_word = -1;
169 static int hf_radiotap_present_tsft = -1;
170 static int hf_radiotap_present_flags = -1;
171 static int hf_radiotap_present_rate = -1;
172 static int hf_radiotap_present_channel = -1;
173 static int hf_radiotap_present_fhss = -1;
174 static int hf_radiotap_present_dbm_antsignal = -1;
175 static int hf_radiotap_present_dbm_antnoise = -1;
176 static int hf_radiotap_present_lock_quality = -1;
177 static int hf_radiotap_present_tx_attenuation = -1;
178 static int hf_radiotap_present_db_tx_attenuation = -1;
179 static int hf_radiotap_present_dbm_tx_power = -1;
180 static int hf_radiotap_present_antenna = -1;
181 static int hf_radiotap_present_db_antsignal = -1;
182 static int hf_radiotap_present_db_antnoise = -1;
183 static int hf_radiotap_present_hdrfcs = -1;
184 static int hf_radiotap_present_rxflags = -1;
185 static int hf_radiotap_present_xchannel = -1;
186 static int hf_radiotap_present_mcs = -1;
187 static int hf_radiotap_present_ampdu = -1;
188 static int hf_radiotap_present_vht = -1;
189 static int hf_radiotap_present_timestamp = -1;
190 static int hf_radiotap_present_he = -1;
191 static int hf_radiotap_present_reserved = -1;
192 static int hf_radiotap_present_rtap_ns = -1;
193 static int hf_radiotap_present_vendor_ns = -1;
194 static int hf_radiotap_present_ext = -1;
195
196 /* "present.flags" flags */
197 static int hf_radiotap_flags = -1;
198 static int hf_radiotap_flags_cfp = -1;
199 static int hf_radiotap_flags_preamble = -1;
200 static int hf_radiotap_flags_wep = -1;
201 static int hf_radiotap_flags_frag = -1;
202 static int hf_radiotap_flags_fcs = -1;
203 static int hf_radiotap_flags_datapad = -1;
204 static int hf_radiotap_flags_badfcs = -1;
205 static int hf_radiotap_flags_shortgi = -1;
206
207 static int hf_radiotap_quality = -1;
208 static int hf_radiotap_fcs = -1;
209 static int hf_radiotap_fcs_bad = -1;
210
211 /* HE Info fields */
212 static int hf_radiotap_he_ppdu_format = -1;
213 static int hf_radiotap_he_bss_color_known = -1;
214 static int hf_radiotap_he_beam_change_known = -1;
215 static int hf_radiotap_he_ul_dl_known = -1;
216 static int hf_radiotap_he_data_mcs_known = -1;
217 static int hf_radiotap_he_data_dcm_known = -1;
218 static int hf_radiotap_he_coding_known = -1;
219 static int hf_radiotap_he_ldpc_extra_symbol_segment_known = -1;
220 static int hf_radiotap_he_stbc_known = -1;
221 static int hf_radiotap_he_spatial_reuse_1_known = -1;
222 static int hf_radiotap_he_spatial_reuse_2_known = -1;
223 static int hf_radiotap_he_spatial_reuse_3_known = -1;
224 static int hf_radiotap_he_spatial_reuse_4_known = -1;
225 static int hf_radiotap_he_data_bw_ru_allocation_known = -1;
226 static int hf_radiotap_he_dopler_known = -1;
227 static int hf_radiotap_he_d2_reserved_b1 = -1;
228 static int hf_radiotap_he_gi_known = -1;
229 static int hf_radiotap_he_ltf_symbols_known = -1;
230 static int hf_radiotap_he_pre_fec_padding_factor_known = -1;
231 static int hf_radiotap_he_txbf_known = -1;
232 static int hf_radiotap_he_pe_disambiguity_known = -1;
233 static int hf_radiotap_he_txop_known = -1;
234 static int hf_radiotap_he_midamble_periodicity_known = -1;
235 static int hf_radiotap_he_d2_reserved_ff00 = -1;
236 static int he_radiotap_he_bss_color = -1;
237 static int he_radiotap_he_beam_change = -1;
238 static int he_radiotap_he_ul_dl = -1;
239 static int he_radiotap_he_data_mcs = -1;
240 static int he_radiotap_he_data_dcm = -1;
241 static int he_radiotap_he_coding = -1;
242 static int he_radiotap_he_ldpc_extra_symbol_segment = -1;
243 static int he_radiotap_he_stbc = -1;
244 static int he_radiotap_spatial_reuse = -1;
245 static int he_radiotap_he_su_reserved = -1;
246 static int he_radiotap_spatial_reuse_1 = -1;
247 static int he_radiotap_spatial_reuse_2 = -1;
248 static int he_radiotap_spatial_reuse_3 = -1;
249 static int he_radiotap_spatial_reuse_4 = -1;
250 static int he_radiotap_sta_id_user_captured = -1;
251 static int he_radiotap_he_mu_reserved = -1;
252 static int he_radiotap_data_bandwidth_ru_allocation = -1;
253 static int he_radiotap_gi = -1;
254 static int he_radiotap_d5_reserved_00c0 = -1;
255 static int he_radiotap_ltf_symbols = -1;
256 static int he_radiotap_d5_reserved_b11 = -1;
257 static int he_radiotap_pre_fec_padding_factor = -1;
258 static int he_radiotap_txbf = -1;
259 static int he_radiotap_pe_disambiguity = -1;
260 static int hf_radiotap_he_nsts = -1;
261 static int hf_radiotap_he_dopler_value = -1;
262 static int hf_radiotap_he_d6_reserved_00e0 = -1;
263 static int hf_radiotap_he_txop_value = -1;
264 static int hf_radiotap_midamble_periodicity = -1;
265 static int hf_radiotap_he_info_data_1 = -1;
266 static int hf_radiotap_he_info_data_2 = -1;
267 static int hf_radiotap_he_info_data_3 = -1;
268 static int hf_radiotap_he_info_data_4 = -1;
269 static int hf_radiotap_he_info_data_5 = -1;
270 static int hf_radiotap_he_info_data_6 = -1;
271
272 static gint ett_radiotap = -1;
273 static gint ett_radiotap_present = -1;
274 static gint ett_radiotap_present_word = -1;
275 static gint ett_radiotap_flags = -1;
276 static gint ett_radiotap_rxflags = -1;
277 static gint ett_radiotap_channel_flags = -1;
278 static gint ett_radiotap_xchannel_flags = -1;
279 static gint ett_radiotap_vendor = -1;
280 static gint ett_radiotap_mcs = -1;
281 static gint ett_radiotap_mcs_known = -1;
282 static gint ett_radiotap_ampdu = -1;
283 static gint ett_radiotap_ampdu_flags = -1;
284 static gint ett_radiotap_vht = -1;
285 static gint ett_radiotap_vht_known = -1;
286 static gint ett_radiotap_vht_user = -1;
287 static gint ett_radiotap_timestamp = -1;
288 static gint ett_radiotap_timestamp_flags = -1;
289 static gint ett_radiotap_he_info = -1;
290 static gint ett_radiotap_he_info_data_1 = -1;
291 static gint ett_radiotap_he_info_data_2 = -1;
292 static gint ett_radiotap_he_info_data_3 = -1;
293 static gint ett_radiotap_he_info_data_4 = -1;
294 static gint ett_radiotap_he_info_data_5 = -1;
295 static gint ett_radiotap_he_info_data_6 = -1;
296
297 static expert_field ei_radiotap_data_past_header = EI_INIT;
298 static expert_field ei_radiotap_present_reserved = EI_INIT;
299 static expert_field ei_radiotap_present = EI_INIT;
300 static expert_field ei_radiotap_invalid_data_rate = EI_INIT;
301
302 static dissector_handle_t ieee80211_radio_handle;
303
304 static capture_dissector_handle_t ieee80211_cap_handle;
305 static capture_dissector_handle_t ieee80211_datapad_cap_handle;
306
307 static int radiotap_tap = -1;
308
309 /* Settings */
310 static gboolean radiotap_bit14_fcs = FALSE;
311 static gboolean radiotap_interpret_high_rates_as_mcs = FALSE;
312
313 struct _radiotap_info {
314         guint radiotap_length;
315         guint32 rate;
316         gint8 dbm_antsignal;
317         gint8 dbm_antnoise;
318         guint32 freq;
319         guint32 flags;
320         guint64 tsft;
321 };
322
323 #define BITNO_32(x) (((x) >> 16) ? 16 + BITNO_16((x) >> 16) : BITNO_16((x)))
324 #define BITNO_16(x) (((x) >> 8) ? 8 + BITNO_8((x) >> 8) : BITNO_8((x)))
325 #define BITNO_8(x)  (((x) >> 4) ? 4 + BITNO_4((x) >> 4) : BITNO_4((x)))
326 #define BITNO_4(x)  (((x) >> 2) ? 2 + BITNO_2((x) >> 2) : BITNO_2((x)))
327 #define BITNO_2(x)  (((x) & 2) ? 1 : 0)
328 #define BIT(n)  (1U << n)
329
330 /* not officially defined (yet) */
331 #define IEEE80211_RADIOTAP_F_SHORTGI    0x80
332 #define IEEE80211_RADIOTAP_XCHANNEL     18
333
334 /* Official specifcation:
335  *
336  * http://www.radiotap.org/
337  *
338  * Unofficial and historical specifications:
339  * http://madwifi-project.org/wiki/DevDocs/RadiotapHeader
340  * NetBSD's ieee80211_radiotap.h file
341  */
342
343 /*
344  * Useful combinations of channel characteristics.
345  */
346 #define IEEE80211_CHAN_FHSS \
347         (IEEE80211_CHAN_2GHZ | IEEE80211_CHAN_GFSK)
348 #define IEEE80211_CHAN_DSSS \
349         (IEEE80211_CHAN_2GHZ)
350 #define IEEE80211_CHAN_A \
351         (IEEE80211_CHAN_5GHZ | IEEE80211_CHAN_OFDM)
352 #define IEEE80211_CHAN_B \
353         (IEEE80211_CHAN_2GHZ | IEEE80211_CHAN_CCK)
354 #define IEEE80211_CHAN_PUREG \
355         (IEEE80211_CHAN_2GHZ | IEEE80211_CHAN_OFDM)
356 #define IEEE80211_CHAN_G \
357         (IEEE80211_CHAN_2GHZ | IEEE80211_CHAN_DYN)
358 #define IEEE80211_CHAN_108A \
359         (IEEE80211_CHAN_A | IEEE80211_CHAN_TURBO)
360 #define IEEE80211_CHAN_108G \
361         (IEEE80211_CHAN_G | IEEE80211_CHAN_TURBO)
362 #define IEEE80211_CHAN_108PUREG \
363         (IEEE80211_CHAN_PUREG | IEEE80211_CHAN_TURBO)
364 #define IEEE80211_CHAN_ST \
365         (IEEE80211_CHAN_108A | IEEE80211_CHAN_STURBO)
366
367 #define MAX_MCS_VHT_INDEX       9
368 #define MAX_VHT_NSS             8
369
370 /*
371  * Maps a VHT bandwidth index to ieee80211_vhtinfo.rates index.
372  */
373 static const int ieee80211_vht_bw2rate_index[] = {
374                 /*  20Mhz total */      0,
375                 /*  40Mhz total */      1, 0, 0,
376                 /*  80Mhz total */      2, 1, 1, 0, 0, 0, 0,
377                 /* 160Mhz total */      3, 2, 2, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0
378 };
379
380 struct mcs_vht_valid {
381         gboolean valid[4][MAX_VHT_NSS]; /* indexed by bandwidth and NSS-1 */
382 };
383
384 static const struct mcs_vht_valid ieee80211_vhtvalid[MAX_MCS_VHT_INDEX+1] = {
385                 /* MCS  0  */
386                 {
387                         {       /* 20 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
388                                 /* 40 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
389                                 /* 80 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
390                                 /* 160 Mhz */ { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
391                         }
392                 },
393                 /* MCS  1  */
394                 {
395                         {       /* 20 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
396                                 /* 40 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
397                                 /* 80 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
398                                 /* 160 Mhz */ { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
399                         }
400                 },
401                 /* MCS  2  */
402                 {
403                         {       /* 20 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
404                                 /* 40 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
405                                 /* 80 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
406                                 /* 160 Mhz */ { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
407                         }
408                 },
409                 /* MCS  3  */
410                 {
411                         {       /* 20 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
412                                 /* 40 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
413                                 /* 80 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
414                                 /* 160 Mhz */ { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
415                         }
416                 },
417                 /* MCS  4  */
418                 {
419                         {       /* 20 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
420                                 /* 40 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
421                                 /* 80 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
422                                 /* 160 Mhz */ { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
423                         }
424                 },
425                 /* MCS  5  */
426                 {
427                         {       /* 20 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
428                                 /* 40 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
429                                 /* 80 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
430                                 /* 160 Mhz */ { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
431                         }
432                 },
433                 /* MCS  6  */
434                 {
435                         {       /* 20 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
436                                 /* 40 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
437                                 /* 80 Mhz */  { TRUE,  TRUE,  FALSE, TRUE,  TRUE,  TRUE,  FALSE, TRUE },
438                                 /* 160 Mhz */ { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
439                         }
440                 },
441                 /* MCS  7  */
442                 {
443                         {       /* 20 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
444                                 /* 40 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
445                                 /* 80 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
446                                 /* 160 Mhz */ { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
447                         }
448                 },
449                 /* MCS  8  */
450                 {
451                         {       /* 20 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
452                                 /* 40 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
453                                 /* 80 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
454                                 /* 160 Mhz */ { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
455                         }
456                 },
457                 /* MCS  9  */
458                 {
459                         {       /* 20 Mhz */  { FALSE, FALSE, TRUE,  FALSE, FALSE, TRUE,  FALSE, FALSE },
460                                 /* 40 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
461                                 /* 80 Mhz */  { TRUE,  TRUE,  TRUE,  TRUE,  TRUE,  FALSE, TRUE,  TRUE },
462                                 /* 160 Mhz */ { TRUE,  TRUE,  FALSE, TRUE,  TRUE,  TRUE,  TRUE,  TRUE },
463                         }
464                 }
465 };
466
467 struct mcs_vht_info {
468         const char *modulation;
469         const char *coding_rate;
470         float       rates[4][2]; /* indexed by bandwidth and GI length */
471 };
472
473 static const struct mcs_vht_info ieee80211_vhtinfo[MAX_MCS_VHT_INDEX+1] = {
474                 /* MCS  0  */
475                 {       "BPSK",         "1/2",
476                                 {               /* 20 Mhz */  {    6.5f,                /* SGI */    7.2f, },
477                                                 /* 40 Mhz */  {   13.5f,                /* SGI */   15.0f, },
478                                                 /* 80 Mhz */  {   29.3f,                /* SGI */   32.5f, },
479                                                 /* 160 Mhz */ {   58.5f,                /* SGI */   65.0f, }
480                                 }
481                 },
482                 /* MCS  1  */
483                 {       "QPSK",         "1/2",
484                                 {               /* 20 Mhz */  {   13.0f,                /* SGI */   14.4f, },
485                                                 /* 40 Mhz */  {   27.0f,                /* SGI */   30.0f, },
486                                                 /* 80 Mhz */  {   58.5f,                /* SGI */   65.0f, },
487                                                 /* 160 Mhz */ {  117.0f,                /* SGI */  130.0f, }
488                                 }
489                 },
490                 /* MCS  2  */
491                 {       "QPSK",         "3/4",
492                                 {               /* 20 Mhz */  {   19.5f,                /* SGI */   21.7f, },
493                                                 /* 40 Mhz */  {   40.5f,                /* SGI */   45.0f, },
494                                                 /* 80 Mhz */  {   87.8f,                /* SGI */   97.5f, },
495                                                 /* 160 Mhz */ {  175.5f,                /* SGI */  195.0f, }
496                                 }
497                 },
498                 /* MCS  3  */
499                 {       "16-QAM",       "1/2",
500                                 {               /* 20 Mhz */  {   26.0f,                /* SGI */   28.9f, },
501                                                 /* 40 Mhz */  {   54.0f,                /* SGI */   60.0f, },
502                                                 /* 80 Mhz */  {  117.0f,                /* SGI */  130.0f, },
503                                                 /* 160 Mhz */ {  234.0f,                /* SGI */  260.0f, }
504                                 }
505                 },
506                 /* MCS  4  */
507                 {       "16-QAM",       "3/4",
508                                 {               /* 20 Mhz */  {   39.0f,                /* SGI */   43.3f, },
509                                                 /* 40 Mhz */  {   81.0f,                /* SGI */   90.0f, },
510                                                 /* 80 Mhz */  {  175.5f,                /* SGI */  195.0f, },
511                                                 /* 160 Mhz */ {  351.0f,                /* SGI */  390.0f, }
512                                 }
513                 },
514                 /* MCS  5  */
515                 {       "64-QAM",       "2/3",
516                                 {               /* 20 Mhz */  {   52.0f,                /* SGI */   57.8f, },
517                                                 /* 40 Mhz */  {  108.0f,                /* SGI */  120.0f, },
518                                                 /* 80 Mhz */  {  234.0f,                /* SGI */  260.0f, },
519                                                 /* 160 Mhz */ {  468.0f,                /* SGI */  520.0f, }
520                                 }
521                 },
522                 /* MCS  6  */
523                 {       "64-QAM",       "3/4",
524                                 {               /* 20 Mhz */  {   58.5f,                /* SGI */   65.0f, },
525                                                 /* 40 Mhz */  {  121.5f,                /* SGI */  135.0f, },
526                                                 /* 80 Mhz */  {  263.3f,                /* SGI */  292.5f, },
527                                                 /* 160 Mhz */ {  526.5f,                /* SGI */  585.0f, }
528                                 }
529                 },
530                 /* MCS  7  */
531                 {       "64-QAM",       "5/6",
532                                 {               /* 20 Mhz */  {   65.0f,                /* SGI */   72.2f, },
533                                                 /* 40 Mhz */  {  135.0f,                /* SGI */  150.0f, },
534                                                 /* 80 Mhz */  {  292.5f,                /* SGI */  325.0f, },
535                                                 /* 160 Mhz */ {  585.0f,                /* SGI */  650.0f, }
536                                 }
537                 },
538                 /* MCS  8  */
539                 {       "256-QAM",      "3/4",
540                                 {               /* 20 Mhz */  {   78.0f,                /* SGI */   86.7f, },
541                                                 /* 40 Mhz */  {  162.0f,                /* SGI */  180.0f, },
542                                                 /* 80 Mhz */  {  351.0f,                /* SGI */  390.0f, },
543                                                 /* 160 Mhz */ {  702.0f,                /* SGI */  780.0f, }
544                                 }
545                 },
546                 /* MCS  9  */
547                 {       "256-QAM",      "5/6",
548                                 {               /* 20 Mhz */  {   86.7f,                /* SGI */   96.3f, },
549                                                 /* 40 Mhz */  {  180.0f,                /* SGI */  200.0f, },
550                                                 /* 80 Mhz */  {  390.0f,                /* SGI */  433.3f, },
551                                                 /* 160 Mhz */ {  780.0f,                /* SGI */  866.7f, }
552                                 }
553                 }
554 };
555
556 /* In order by value */
557 static const value_string vht_bandwidth[] = {
558         { IEEE80211_RADIOTAP_VHT_BW_20,    "20 MHz" },
559         { IEEE80211_RADIOTAP_VHT_BW_40,    "40 MHz" },
560         { IEEE80211_RADIOTAP_VHT_BW_20L,   "20 MHz lower" },
561         { IEEE80211_RADIOTAP_VHT_BW_20U,   "20 MHz upper" },
562         { IEEE80211_RADIOTAP_VHT_BW_80,    "80 MHz" },
563         { IEEE80211_RADIOTAP_VHT_BW_40L,   "40 MHz lower" },
564         { IEEE80211_RADIOTAP_VHT_BW_40U,   "40 MHz upper" },
565         { IEEE80211_RADIOTAP_VHT_BW_20LL,  "20 MHz, channel 1/4" },
566         { IEEE80211_RADIOTAP_VHT_BW_20LU,  "20 MHz, channel 2/4" },
567         { IEEE80211_RADIOTAP_VHT_BW_20UL,  "20 MHz, channel 3/4" },
568         { IEEE80211_RADIOTAP_VHT_BW_20UU,  "20 MHz, channel 4/4" },
569         { IEEE80211_RADIOTAP_VHT_BW_160,   "160 MHz" },
570         { IEEE80211_RADIOTAP_VHT_BW_80L,   "80 MHz lower" },
571         { IEEE80211_RADIOTAP_VHT_BW_80U,   "80 MHz upper" },
572         { IEEE80211_RADIOTAP_VHT_BW_40LL,  "40 MHz, channel 1/4" },
573         { IEEE80211_RADIOTAP_VHT_BW_40LU,  "40 MHz, channel 2/4" },
574         { IEEE80211_RADIOTAP_VHT_BW_40UL,  "40 MHz, channel 3/4" },
575         { IEEE80211_RADIOTAP_VHT_BW_40UU,  "40 MHz, channel 4/4" },
576         { IEEE80211_RADIOTAP_VHT_BW_20LLL, "20 MHz, channel 1/8" },
577         { IEEE80211_RADIOTAP_VHT_BW_20LLU, "20 MHz, channel 2/8" },
578         { IEEE80211_RADIOTAP_VHT_BW_20LUL, "20 MHz, channel 3/8" },
579         { IEEE80211_RADIOTAP_VHT_BW_20LUU, "20 MHz, channel 4/8" },
580         { IEEE80211_RADIOTAP_VHT_BW_20ULL, "20 MHz, channel 5/8" },
581         { IEEE80211_RADIOTAP_VHT_BW_20ULU, "20 MHz, channel 6/8" },
582         { IEEE80211_RADIOTAP_VHT_BW_20UUL, "20 MHz, channel 7/8" },
583         { IEEE80211_RADIOTAP_VHT_BW_20UUU, "20 MHz, channel 8/8" },
584         { 0, NULL }
585 };
586 static value_string_ext vht_bandwidth_ext = VALUE_STRING_EXT_INIT(vht_bandwidth);
587
588 static const value_string mcs_bandwidth[] = {
589         { IEEE80211_RADIOTAP_MCS_BW_20,  "20 MHz" },
590         { IEEE80211_RADIOTAP_MCS_BW_40,  "40 MHz" },
591         { IEEE80211_RADIOTAP_MCS_BW_20L, "20 MHz lower" },
592         { IEEE80211_RADIOTAP_MCS_BW_20U, "20 MHz upper" },
593         {0, NULL}
594 };
595
596 static const value_string mcs_format[] = {
597         { 0, "mixed" },
598         { 1, "greenfield" },
599         {0, NULL},
600 };
601
602 static const value_string mcs_fec[] = {
603         { 0, "BCC" },
604         { 1, "LDPC" },
605         {0, NULL}
606 };
607
608 static const value_string mcs_gi[] = {
609         { 0, "long" },
610         { 1, "short" },
611         {0, NULL}
612 };
613
614 static const true_false_string preamble_type = {
615         "Short",
616         "Long",
617 };
618
619 static const value_string timestamp_unit[] = {
620         { IEEE80211_RADIOTAP_TS_UNIT_MSEC, "msec" },
621         { IEEE80211_RADIOTAP_TS_UNIT_USEC, "usec" },
622         { IEEE80211_RADIOTAP_TS_UNIT_NSEC, "nsec" },
623         { 0, NULL }
624 };
625
626 static const value_string timestamp_spos[] = {
627         { IEEE80211_RADIOTAP_TS_SPOS_MPDU, "first MPDU bit/symbol" },
628         { IEEE80211_RADIOTAP_TS_SPOS_ACQ, "signal acquisition" },
629         { IEEE80211_RADIOTAP_TS_SPOS_EOF, "end of frame" },
630         { IEEE80211_RADIOTAP_TS_SPOS_UNDEF, "undefined" },
631         { 0, NULL }
632 };
633
634 /*
635  * The NetBSD ieee80211_radiotap man page
636  * (http://netbsd.gw.com/cgi-bin/man-cgi?ieee80211_radiotap+9+NetBSD-current)
637  * says:
638  *
639  *    Radiotap capture fields must be naturally aligned.  That is, 16-, 32-,
640  *    and 64-bit fields must begin on 16-, 32-, and 64-bit boundaries, respec-
641  *    tively.  In this way, drivers can avoid unaligned accesses to radiotap
642  *    capture fields.  radiotap-compliant drivers must insert padding before a
643  *    capture field to ensure its natural alignment.  radiotap-compliant packet
644  *    dissectors, such as tcpdump(8), expect the padding.
645  */
646
647 static gboolean
648 capture_radiotap(const guchar * pd, int offset, int len, capture_packet_info_t *cpinfo, const union wtap_pseudo_header *pseudo_header _U_)
649 {
650         guint16 it_len;
651         guint32 present, xpresent;
652         guint8  rflags;
653         const struct ieee80211_radiotap_header *hdr;
654
655         if (!BYTES_ARE_IN_FRAME(offset, len,
656                                 sizeof(struct ieee80211_radiotap_header))) {
657                 return FALSE;
658         }
659         hdr = (const struct ieee80211_radiotap_header *)pd;
660         it_len = pletoh16(&hdr->it_len);
661         if (!BYTES_ARE_IN_FRAME(offset, len, it_len))
662                 return FALSE;
663
664         if (it_len > len) {
665                 /* Header length is bigger than total packet length */
666                 return FALSE;
667         }
668
669         if (it_len < sizeof(struct ieee80211_radiotap_header)) {
670                 /* Header length is shorter than fixed-length portion of header */
671                 return FALSE;
672         }
673
674         present = pletoh32(&hdr->it_present);
675         offset += (int)sizeof(struct ieee80211_radiotap_header);
676         it_len -= (int)sizeof(struct ieee80211_radiotap_header);
677
678         /* skip over other present bitmaps */
679         xpresent = present;
680         while (xpresent & BIT(IEEE80211_RADIOTAP_EXT)) {
681                 if (!BYTES_ARE_IN_FRAME(offset, 4, it_len)) {
682                         return FALSE;
683                 }
684                 xpresent = pletoh32(pd + offset);
685                 offset += 4;
686                 it_len -= 4;
687         }
688
689         rflags = 0;
690
691         /*
692          * IEEE80211_RADIOTAP_TSFT is the lowest-order bit,
693          * just skip over it.
694          */
695         if (present & BIT(IEEE80211_RADIOTAP_TSFT)) {
696                 /* align it properly */
697                 if (offset & 7) {
698                         int pad = 8 - (offset & 7);
699                         offset += pad;
700                         it_len -= pad;
701                 }
702
703                 if (it_len < 8) {
704                         /* No room in header for this field. */
705                         return FALSE;
706                 }
707                 /* That field is present, and it's 8 bytes long. */
708                 offset += 8;
709                 it_len -= 8;
710         }
711
712         /*
713          * IEEE80211_RADIOTAP_FLAGS is the next bit.
714          */
715         if (present & BIT(IEEE80211_RADIOTAP_FLAGS)) {
716                 if (it_len < 1) {
717                         /* No room in header for this field. */
718                         return FALSE;
719                 }
720                 /* That field is present; fetch it. */
721                 if (!BYTES_ARE_IN_FRAME(offset, len, 1)) {
722                         return FALSE;
723                 }
724                 rflags = pd[offset];
725         }
726
727         /* 802.11 header follows */
728         if (rflags & IEEE80211_RADIOTAP_F_DATAPAD)
729                 return call_capture_dissector(ieee80211_datapad_cap_handle, pd, offset + it_len, len, cpinfo, pseudo_header);
730
731         return call_capture_dissector(ieee80211_cap_handle, pd, offset + it_len, len, cpinfo, pseudo_header);
732 }
733
734 static const true_false_string tfs_known_unknown = {
735         "Known",
736         "Unknown"
737 };
738
739 static const int *data1_headers[] = {
740         &hf_radiotap_he_ppdu_format,
741         &hf_radiotap_he_bss_color_known,
742         &hf_radiotap_he_beam_change_known,
743         &hf_radiotap_he_ul_dl_known,
744         &hf_radiotap_he_data_mcs_known,
745         &hf_radiotap_he_data_dcm_known,
746         &hf_radiotap_he_coding_known,
747         &hf_radiotap_he_ldpc_extra_symbol_segment_known,
748         &hf_radiotap_he_stbc_known,
749         &hf_radiotap_he_spatial_reuse_1_known,
750         &hf_radiotap_he_spatial_reuse_2_known,
751         &hf_radiotap_he_spatial_reuse_3_known,
752         &hf_radiotap_he_spatial_reuse_4_known,
753         &hf_radiotap_he_data_bw_ru_allocation_known,
754         &hf_radiotap_he_dopler_known,
755         NULL
756 };
757
758 static const value_string he_pdu_format_vals[] = {
759         { IEEE80211_RADIOTAP_HE_PPDU_FORMAT_HE_SU,     "HE_SU" },
760         { IEEE80211_RADIOTAP_HE_PPDU_FORMAT_HE_EXT_SU, "HE_EXT_SU" },
761         { IEEE80211_RADIOTAP_HE_PPDU_FORMAT_HE_MU,     "HE_MU" },
762         { IEEE80211_RADIOTAP_HE_PPDU_FORMAT_HE_TRIG,   "HE_TRIG" },
763         { 0, NULL }
764 };
765
766 static const int *data2_headers[] = {
767         &hf_radiotap_he_d2_reserved_b1,
768         &hf_radiotap_he_gi_known,
769         &hf_radiotap_he_ltf_symbols_known,
770         &hf_radiotap_he_pre_fec_padding_factor_known,
771         &hf_radiotap_he_txbf_known,
772         &hf_radiotap_he_pe_disambiguity_known,
773         &hf_radiotap_he_txop_known,
774         &hf_radiotap_he_midamble_periodicity_known,
775         &hf_radiotap_he_d2_reserved_ff00,
776         NULL
777 };
778
779 static const int *data3_headers[] = {
780         &he_radiotap_he_bss_color,
781         &he_radiotap_he_beam_change,
782         &he_radiotap_he_ul_dl,
783         &he_radiotap_he_data_mcs,
784         &he_radiotap_he_data_dcm,
785         &he_radiotap_he_coding,
786         &he_radiotap_he_ldpc_extra_symbol_segment,
787         &he_radiotap_he_stbc,
788         NULL
789 };
790
791 static const value_string he_coding_vals[] = {
792         { 0, "BCC" },
793         { 1, "LDPC" },
794         { 0, NULL }
795 };
796
797 static const int *data4_he_su_and_he_ext_su_headers[] = {
798         &he_radiotap_spatial_reuse,
799         &he_radiotap_he_su_reserved,
800         NULL
801 };
802
803 static const int *data4_he_trig_headers[] = {
804         &he_radiotap_spatial_reuse_1,
805         &he_radiotap_spatial_reuse_2,
806         &he_radiotap_spatial_reuse_3,
807         &he_radiotap_spatial_reuse_4,
808         NULL
809 };
810
811 static const int *data4_he_mu_headers[] = {
812         &he_radiotap_spatial_reuse,
813         &he_radiotap_sta_id_user_captured,
814         &he_radiotap_he_mu_reserved,
815         NULL
816 };
817
818 static const int *data5_headers[] = {
819         &he_radiotap_data_bandwidth_ru_allocation,
820         &he_radiotap_gi,
821         &he_radiotap_d5_reserved_00c0,
822         &he_radiotap_ltf_symbols,
823         &he_radiotap_d5_reserved_b11,
824         &he_radiotap_pre_fec_padding_factor,
825         &he_radiotap_txbf,
826         &he_radiotap_pe_disambiguity,
827         NULL
828 };
829
830 static const value_string he_data_bw_ru_alloc_vals[] = {
831         { 0, "20" },
832         { 1, "40" },
833         { 2, "80" },
834         { 3, "160/80+80" },
835         { 4, "26-tone RU" },
836         { 5, "52-tone RU" },
837         { 6, "106-tone RU" },
838         { 7, "242-tone RU" },
839         { 8, "484-tone RU" },
840         { 9, "996-tone RU" },
841         { 10, "2x996-tone RU" },
842         { 11, "reserved" },
843         { 12, "reserved" },
844         { 13, "reserved" },
845         { 14, "reserved" },
846         { 15, "reserved" },
847         { 0, NULL }
848 };
849
850 static const value_string he_gi_vals[] = {
851         { 0, "0.8us" },
852         { 1, "1.6us" },
853         { 2, "3.2us" },
854         { 3, "reserved" },
855         { 0, NULL }
856 };
857
858 static const value_string he_ltf_symbols_vals[] = {
859         { 0, "1x" },
860         { 1, "2x" },
861         { 2, "4x" },
862         { 3, "6x" },
863         { 4, "8x" },
864         { 5, "reserved" },
865         { 6, "reserved" },
866         { 7, "reserved" },
867         { 0, NULL }
868 };
869
870 static const int *data6_headers[] = {
871         &hf_radiotap_he_nsts,
872         &hf_radiotap_he_dopler_value,
873         &hf_radiotap_he_d6_reserved_00e0,
874         &hf_radiotap_he_txop_value,
875         &hf_radiotap_midamble_periodicity,
876         NULL
877 };
878
879 static const value_string he_nsts_vals[] = {
880         { 0, "Unknown" },
881         { 1, "1 space-time stream" },
882         { 2, "2 space-time streams" },
883         { 3, "3 space-time streams" },
884         { 4, "4 space-time streams" },
885         { 5, "5 space-time streams" },
886         { 6, "6 space-time streams" },
887         { 7, "7 space-time streams" },
888         { 8, "8 space-time streams" },
889         { 9, "9 space-time streams" },
890         { 10, "10 space-time streams" },
891         { 11, "11 space-time streams" },
892         { 12, "12 space-time streams" },
893         { 13, "13 space-time streams" },
894         { 14, "14 space-time streams" },
895         { 15, "15 space-time streams" },
896         { 0, NULL }
897 };
898
899 static const value_string he_midamble_periodicity_vals[] = {
900         { 0, "10" },
901         { 1, "20" },
902         { 0, NULL }
903 };
904
905 static void
906 dissect_radiotap_he_info(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree,
907         int offset)
908 {
909         guint16 ppdu_format = tvb_get_letohs(tvb, offset) &
910                 IEEE80211_RADIOTAP_HE_PPDU_FORMAT_MASK;
911         proto_tree *he_info_tree = NULL;
912
913         he_info_tree = proto_tree_add_subtree(tree, tvb, offset, 12,
914                 ett_radiotap_he_info, NULL, "HE information");
915
916         /* Add the bitmasks for each of D1 through D6 */
917         proto_tree_add_bitmask(he_info_tree, tvb, offset,
918                 hf_radiotap_he_info_data_1, ett_radiotap_he_info_data_1,
919                 data1_headers, ENC_LITTLE_ENDIAN);
920         offset += 2;
921
922         proto_tree_add_bitmask(he_info_tree, tvb, offset,
923                 hf_radiotap_he_info_data_2, ett_radiotap_he_info_data_2,
924                 data2_headers, ENC_LITTLE_ENDIAN);
925         offset += 2;
926
927         proto_tree_add_bitmask(he_info_tree, tvb, offset,
928                 hf_radiotap_he_info_data_3, ett_radiotap_he_info_data_3,
929                 data3_headers, ENC_LITTLE_ENDIAN);
930         offset += 2;
931
932         if (ppdu_format == IEEE80211_RADIOTAP_HE_PPDU_FORMAT_HE_SU ||
933                 ppdu_format == IEEE80211_RADIOTAP_HE_PPDU_FORMAT_HE_EXT_SU)
934                 proto_tree_add_bitmask(he_info_tree, tvb, offset,
935                         hf_radiotap_he_info_data_4, ett_radiotap_he_info_data_4,
936                         data4_he_su_and_he_ext_su_headers, ENC_LITTLE_ENDIAN);
937         else if (ppdu_format == IEEE80211_RADIOTAP_HE_PPDU_FORMAT_HE_MU)
938                 proto_tree_add_bitmask(he_info_tree, tvb, offset,
939                         hf_radiotap_he_info_data_4, ett_radiotap_he_info_data_4,
940                         data4_he_mu_headers, ENC_LITTLE_ENDIAN);
941         else
942                 proto_tree_add_bitmask(he_info_tree, tvb, offset,
943                         hf_radiotap_he_info_data_4, ett_radiotap_he_info_data_4,
944                         data4_he_trig_headers, ENC_LITTLE_ENDIAN);
945
946         offset += 2;
947
948         proto_tree_add_bitmask(he_info_tree, tvb, offset,
949                 hf_radiotap_he_info_data_5, ett_radiotap_he_info_data_5,
950                 data5_headers, ENC_LITTLE_ENDIAN);
951         offset += 2;
952
953         proto_tree_add_bitmask(he_info_tree, tvb, offset,
954                 hf_radiotap_he_info_data_6, ett_radiotap_he_info_data_6,
955                 data6_headers, ENC_LITTLE_ENDIAN);
956 }
957
958 static int
959 dissect_radiotap(tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree, void* unused_data _U_)
960 {
961         proto_tree *radiotap_tree     = NULL;
962         proto_item *present_item      = NULL;
963         proto_tree *present_tree      = NULL;
964         proto_item *present_word_item = NULL;
965         proto_tree *present_word_tree = NULL;
966         proto_tree *ft;
967         proto_item *ti                = NULL;
968         proto_item *hidden_item;
969         int         offset;
970         tvbuff_t   *next_tvb;
971         guint8      version;
972         guint       length;
973         guint16     cflags;
974         guint32     freq;
975         proto_item *rate_ti;
976         gint8       dbm, db;
977         gboolean    have_rflags       = FALSE;
978         guint8      rflags            = 0;
979         guint32     xcflags;
980         /* backward compat with bit 14 == fcs in header */
981         proto_item *hdr_fcs_ti        = NULL;
982         int         hdr_fcs_offset    = 0;
983         guint32     sent_fcs          = 0;
984         guint32     calc_fcs;
985         gint        err               = -ENOENT;
986         void       *data;
987         struct _radiotap_info              *radiotap_info;
988         static struct _radiotap_info        rtp_info_arr;
989         struct ieee80211_radiotap_iterator  iter;
990         struct ieee_802_11_phdr phdr;
991
992         /* our non-standard overrides */
993         static struct radiotap_override overrides[] = {
994                 {IEEE80211_RADIOTAP_XCHANNEL, 4, 8},    /* xchannel */
995
996                 /* keep last */
997                 {14, 4, 4},     /* FCS in header */
998         };
999         guint n_overrides = array_length(overrides);
1000
1001         if (!radiotap_bit14_fcs)
1002                 n_overrides--;
1003
1004         radiotap_info = &rtp_info_arr;
1005
1006         /* We don't have any 802.11 metadata yet. */
1007         memset(&phdr, 0, sizeof(phdr));
1008         phdr.fcs_len = -1;
1009         phdr.decrypted = FALSE;
1010         phdr.datapad = FALSE;
1011         phdr.phy = PHDR_802_11_PHY_UNKNOWN;
1012
1013         col_set_str(pinfo->cinfo, COL_PROTOCOL, "WLAN");
1014         col_clear(pinfo->cinfo, COL_INFO);
1015
1016         version = tvb_get_guint8(tvb, 0);
1017         length = tvb_get_letohs(tvb, 2);
1018
1019         radiotap_info->radiotap_length = length;
1020
1021         col_add_fstr(pinfo->cinfo, COL_INFO, "Radiotap Capture v%u, Length %u",
1022                      version, length);
1023
1024         /* Dissect the packet */
1025         if (tree) {
1026                 ti = proto_tree_add_protocol_format(tree, proto_radiotap,
1027                                                     tvb, 0, length,
1028                                                     "Radiotap Header v%u, Length %u",
1029                                                     version, length);
1030                 radiotap_tree = proto_item_add_subtree(ti, ett_radiotap);
1031                 proto_tree_add_uint(radiotap_tree, hf_radiotap_version,
1032                                     tvb, 0, 1, version);
1033                 proto_tree_add_item(radiotap_tree, hf_radiotap_pad,
1034                                     tvb, 1, 1, ENC_BIG_ENDIAN);
1035                 proto_tree_add_uint(radiotap_tree, hf_radiotap_length,
1036                                     tvb, 2, 2, length);
1037         }
1038
1039         data = tvb_memdup(wmem_packet_scope(), tvb, 0, length);
1040
1041         if (ieee80211_radiotap_iterator_init(&iter, (struct ieee80211_radiotap_header *)data, length, NULL)) {
1042                 if (tree)
1043                         proto_item_append_text(ti, " (invalid)");
1044                 /* maybe the length was correct anyway ... */
1045                 goto hand_off_to_80211;
1046         }
1047
1048         iter.overrides = overrides;
1049         iter.n_overrides = n_overrides;
1050
1051         /* Add the "present flags" bitmaps. */
1052         if (tree) {
1053                 guchar   *bmap_start          = (guchar *)data + 4;
1054                 guint     n_bitmaps           = (guint)(iter.this_arg - bmap_start) / 4;
1055                 guint     i;
1056                 gboolean  rtap_ns;
1057                 gboolean  rtap_ns_next        = TRUE;
1058                 guint     rtap_ns_offset;
1059                 guint     rtap_ns_offset_next = 0;
1060
1061                 present_item = proto_tree_add_item(radiotap_tree,
1062                     hf_radiotap_present, tvb, 4, n_bitmaps * 4, ENC_NA);
1063                 present_tree = proto_item_add_subtree(present_item,
1064                     ett_radiotap_present);
1065
1066                 for (i = 0; i < n_bitmaps; i++) {
1067                         guint32 bmap = pletoh32(bmap_start + 4 * i);
1068
1069                         rtap_ns_offset = rtap_ns_offset_next;
1070                         rtap_ns_offset_next += 32;
1071
1072                         offset = 4 * i;
1073
1074                         present_word_item =
1075                             proto_tree_add_item(present_tree,
1076                               hf_radiotap_present_word,
1077                               tvb, offset + 4, 4, ENC_LITTLE_ENDIAN);
1078
1079                         present_word_tree =
1080                             proto_item_add_subtree(present_word_item,
1081                               ett_radiotap_present_word);
1082
1083                         rtap_ns = rtap_ns_next;
1084
1085                         /* Evaluate what kind of namespaces will come next */
1086                         if (bmap & BIT(IEEE80211_RADIOTAP_RADIOTAP_NAMESPACE)) {
1087                                 rtap_ns_next = TRUE;
1088                                 rtap_ns_offset_next = 0;
1089                         }
1090                         if (bmap & BIT(IEEE80211_RADIOTAP_VENDOR_NAMESPACE))
1091                                 rtap_ns_next = FALSE;
1092                         if ((bmap & (BIT(IEEE80211_RADIOTAP_RADIOTAP_NAMESPACE) |
1093                                      BIT(IEEE80211_RADIOTAP_VENDOR_NAMESPACE)))
1094                                 == (BIT(IEEE80211_RADIOTAP_RADIOTAP_NAMESPACE) |
1095                                     BIT(IEEE80211_RADIOTAP_VENDOR_NAMESPACE))) {
1096                                 expert_add_info_format(pinfo, present_word_item,
1097                                     &ei_radiotap_present,
1098                                     "Both radiotap and vendor namespace specified in bitmask word %u",
1099                                     i);
1100                                 goto malformed;
1101                         }
1102
1103                         if (!rtap_ns)
1104                                 goto always_bits;
1105
1106                         /* Currently, we don't know anything about bits >= 32 */
1107                         if (rtap_ns_offset)
1108                                 goto always_bits;
1109
1110                         proto_tree_add_item(present_word_tree,
1111                                             hf_radiotap_present_tsft, tvb,
1112                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1113                         proto_tree_add_item(present_word_tree,
1114                                             hf_radiotap_present_flags, tvb,
1115                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1116                         proto_tree_add_item(present_word_tree,
1117                                             hf_radiotap_present_rate, tvb,
1118                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1119                         proto_tree_add_item(present_word_tree,
1120                                             hf_radiotap_present_channel, tvb,
1121                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1122                         proto_tree_add_item(present_word_tree,
1123                                             hf_radiotap_present_fhss, tvb,
1124                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1125                         proto_tree_add_item(present_word_tree,
1126                                             hf_radiotap_present_dbm_antsignal,
1127                                             tvb, offset + 4, 4, ENC_LITTLE_ENDIAN);
1128                         proto_tree_add_item(present_word_tree,
1129                                             hf_radiotap_present_dbm_antnoise,
1130                                             tvb, offset + 4, 4, ENC_LITTLE_ENDIAN);
1131                         proto_tree_add_item(present_word_tree,
1132                                             hf_radiotap_present_lock_quality,
1133                                             tvb, offset + 4, 4, ENC_LITTLE_ENDIAN);
1134                         proto_tree_add_item(present_word_tree,
1135                                             hf_radiotap_present_tx_attenuation,
1136                                             tvb, offset + 4, 4, ENC_LITTLE_ENDIAN);
1137                         proto_tree_add_item(present_word_tree,
1138                                             hf_radiotap_present_db_tx_attenuation,
1139                                             tvb, offset + 4, 4, ENC_LITTLE_ENDIAN);
1140                         proto_tree_add_item(present_word_tree,
1141                                             hf_radiotap_present_dbm_tx_power,
1142                                             tvb, offset + 4, 4, ENC_LITTLE_ENDIAN);
1143                         proto_tree_add_item(present_word_tree,
1144                                             hf_radiotap_present_antenna, tvb,
1145                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1146                         proto_tree_add_item(present_word_tree,
1147                                             hf_radiotap_present_db_antsignal,
1148                                             tvb, offset + 4, 4, ENC_LITTLE_ENDIAN);
1149                         proto_tree_add_item(present_word_tree,
1150                                             hf_radiotap_present_db_antnoise,
1151                                             tvb, offset + 4, 4, ENC_LITTLE_ENDIAN);
1152                         if (radiotap_bit14_fcs) {
1153                                 proto_tree_add_item(present_word_tree,
1154                                                     hf_radiotap_present_hdrfcs,
1155                                                     tvb, offset + 4, 4, ENC_LITTLE_ENDIAN);
1156                         } else {
1157                                 proto_tree_add_item(present_word_tree,
1158                                                     hf_radiotap_present_rxflags,
1159                                                     tvb, offset + 4, 4, ENC_LITTLE_ENDIAN);
1160                         }
1161                         proto_tree_add_item(present_word_tree,
1162                                             hf_radiotap_present_xchannel, tvb,
1163                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1164
1165                         proto_tree_add_item(present_word_tree,
1166                                             hf_radiotap_present_mcs, tvb,
1167                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1168                         proto_tree_add_item(present_word_tree,
1169                                             hf_radiotap_present_ampdu, tvb,
1170                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1171                         proto_tree_add_item(present_word_tree,
1172                                             hf_radiotap_present_vht, tvb,
1173                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1174                         proto_tree_add_item(present_word_tree,
1175                                             hf_radiotap_present_timestamp, tvb,
1176                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1177                         proto_tree_add_item(present_word_tree,
1178                                             hf_radiotap_present_he, tvb,
1179                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1180
1181                         ti = proto_tree_add_item(present_word_tree,
1182                                             hf_radiotap_present_reserved, tvb,
1183                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1184                         /* Check if Reserved/Not Defined is not "zero" */
1185                         if(bmap & IEEE80211_RADIOTAP_NOTDEFINED)
1186                         {
1187                                 expert_add_info(pinfo, present_word_item,
1188                                     &ei_radiotap_present_reserved);
1189                         }
1190  always_bits:
1191                         proto_tree_add_item(present_word_tree,
1192                                             hf_radiotap_present_rtap_ns, tvb,
1193                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1194                         proto_tree_add_item(present_word_tree,
1195                                             hf_radiotap_present_vendor_ns, tvb,
1196                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1197                         proto_tree_add_item(present_word_tree,
1198                                             hf_radiotap_present_ext, tvb,
1199                                             offset + 4, 4, ENC_LITTLE_ENDIAN);
1200                 }
1201         }
1202
1203         while (!(err = ieee80211_radiotap_iterator_next(&iter))) {
1204                 offset = (int)((guchar *) iter.this_arg - (guchar *) data);
1205
1206                 if (iter.this_arg_index == IEEE80211_RADIOTAP_VENDOR_NAMESPACE
1207                     && tree) {
1208                         proto_tree *ven_tree;
1209                         proto_item *vt;
1210                         const gchar *manuf_name;
1211                         guint8 subns;
1212
1213                         manuf_name = tvb_get_manuf_name(tvb, offset);
1214                         subns = tvb_get_guint8(tvb, offset+3);
1215
1216                         vt = proto_tree_add_bytes_format_value(radiotap_tree,
1217                                                          hf_radiotap_vendor_ns,
1218                                                          tvb, offset,
1219                                                          iter.this_arg_size,
1220                                                          NULL,
1221                                                          "%s-%d",
1222                                                          manuf_name, subns);
1223                         ven_tree = proto_item_add_subtree(vt, ett_radiotap_vendor);
1224                         proto_tree_add_item(ven_tree, hf_radiotap_ven_oui,
1225                                             tvb, offset, 3, ENC_BIG_ENDIAN);
1226                         proto_tree_add_item(ven_tree, hf_radiotap_ven_subns,
1227                                             tvb, offset + 3, 1, ENC_BIG_ENDIAN);
1228                         proto_tree_add_item(ven_tree, hf_radiotap_ven_skip, tvb,
1229                                             offset + 4, 2, ENC_LITTLE_ENDIAN);
1230                         proto_tree_add_item(ven_tree, hf_radiotap_ven_data, tvb,
1231                                             offset + 6, iter.this_arg_size - 6,
1232                                             ENC_NA);
1233                 }
1234
1235                 if (!iter.is_radiotap_ns)
1236                         continue;
1237
1238                 switch (iter.this_arg_index) {
1239
1240                 case IEEE80211_RADIOTAP_TSFT:
1241                         radiotap_info->tsft = tvb_get_letoh64(tvb, offset);
1242                         phdr.tsf_timestamp = radiotap_info->tsft;
1243                         phdr.has_tsf_timestamp = TRUE;
1244                         if (tree) {
1245                                 proto_tree_add_uint64(radiotap_tree,
1246                                                       hf_radiotap_mactime, tvb,
1247                                                       offset, 8,
1248                                                       radiotap_info->tsft);
1249                         }
1250                         break;
1251
1252                 case IEEE80211_RADIOTAP_FLAGS: {
1253                         rflags = tvb_get_guint8(tvb, offset);
1254                         have_rflags = TRUE;
1255                         if (rflags & IEEE80211_RADIOTAP_F_DATAPAD)
1256                                 phdr.datapad = TRUE;
1257                         if (rflags & IEEE80211_RADIOTAP_F_FCS)
1258                                 phdr.fcs_len = 4;
1259                         else
1260                                 phdr.fcs_len = 0;
1261
1262                         if (tree) {
1263                                 proto_tree *flags_tree;
1264
1265                                 ft = proto_tree_add_item(radiotap_tree,
1266                                                          hf_radiotap_flags,
1267                                                          tvb, offset, 1, ENC_BIG_ENDIAN);
1268                                 flags_tree =
1269                                     proto_item_add_subtree(ft,
1270                                                            ett_radiotap_flags);
1271
1272                                 proto_tree_add_item(flags_tree,
1273                                                     hf_radiotap_flags_cfp,
1274                                                     tvb, offset, 1, ENC_BIG_ENDIAN);
1275                                 proto_tree_add_item(flags_tree,
1276                                                     hf_radiotap_flags_preamble,
1277                                                     tvb, offset, 1, ENC_BIG_ENDIAN);
1278                                 proto_tree_add_item(flags_tree,
1279                                                     hf_radiotap_flags_wep,
1280                                                     tvb, offset, 1, ENC_BIG_ENDIAN);
1281                                 proto_tree_add_item(flags_tree,
1282                                                     hf_radiotap_flags_frag,
1283                                                     tvb, offset, 1, ENC_BIG_ENDIAN);
1284                                 proto_tree_add_item(flags_tree,
1285                                                     hf_radiotap_flags_fcs,
1286                                                     tvb, offset, 1, ENC_BIG_ENDIAN);
1287                                 proto_tree_add_item(flags_tree,
1288                                                     hf_radiotap_flags_datapad,
1289                                                     tvb, offset, 1, ENC_BIG_ENDIAN);
1290                                 proto_tree_add_item(flags_tree,
1291                                                     hf_radiotap_flags_badfcs,
1292                                                     tvb, offset, 1, ENC_BIG_ENDIAN);
1293                                 proto_tree_add_item(flags_tree,
1294                                                     hf_radiotap_flags_shortgi,
1295                                                     tvb, offset, 1, ENC_BIG_ENDIAN);
1296                         }
1297                         break;
1298                 }
1299
1300                 case IEEE80211_RADIOTAP_RATE: {
1301                         guint32 rate;
1302                         rate = tvb_get_guint8(tvb, offset);
1303                         /*
1304                          * XXX On FreeBSD rate & 0x80 means we have an MCS. On
1305                          * Linux and AirPcap it does not.  (What about
1306                          * macOS, NetBSD, OpenBSD, and DragonFly BSD?)
1307                          *
1308                          * This is an issue either for proprietary extensions
1309                          * to 11a or 11g, which do exist, or for 11n
1310                          * implementations that stuff a rate value into
1311                          * this field, which also appear to exist.
1312                          */
1313                         if (radiotap_interpret_high_rates_as_mcs &&
1314                                         rate >= 0x80 && rate <= (0x80+76)) {
1315                                 /*
1316                                  * XXX - we don't know the channel width
1317                                  * or guard interval length, so we can't
1318                                  * convert this to a data rate.
1319                                  *
1320                                  * If you want us to show a data rate,
1321                                  * use the MCS field, not the Rate field;
1322                                  * the MCS field includes not only the
1323                                  * MCS index, it also includes bandwidth
1324                                  * and guard interval information.
1325                                  *
1326                                  * XXX - can we get the channel width
1327                                  * from XChannel and the guard interval
1328                                  * information from Flags, at least on
1329                                  * FreeBSD?
1330                                  */
1331                                 if (tree) {
1332                                         proto_tree_add_uint(radiotap_tree,
1333                                                             hf_radiotap_mcs_index,
1334                                                             tvb, offset, 1,
1335                                                             rate & 0x7f);
1336                                 }
1337                         } else {
1338                                 col_add_fstr(pinfo->cinfo, COL_TX_RATE, "%d.%d",
1339                                              rate / 2, rate & 1 ? 5 : 0);
1340                                 if (tree) {
1341                                         proto_tree_add_float_format(radiotap_tree,
1342                                                                     hf_radiotap_datarate,
1343                                                                     tvb, offset, 1,
1344                                                                     (float)rate / 2,
1345                                                                     "Data Rate: %.1f Mb/s",
1346                                                                     (float)rate / 2);
1347                                 }
1348                                 radiotap_info->rate = rate;
1349                                 phdr.has_data_rate = TRUE;
1350                                 phdr.data_rate = rate;
1351                         }
1352                         break;
1353                 }
1354
1355                 case IEEE80211_RADIOTAP_CHANNEL: {
1356                         freq = tvb_get_letohs(tvb, offset);
1357                         if (freq != 0) {
1358                                 /*
1359                                  * XXX - some captures have 0, which is
1360                                  * obviously bogus.
1361                                  */
1362                                 gint calc_channel;
1363
1364                                 phdr.has_frequency = TRUE;
1365                                 phdr.frequency = freq;
1366                                 calc_channel = ieee80211_mhz_to_chan(freq);
1367                                 if (calc_channel != -1) {
1368                                         phdr.has_channel = TRUE;
1369                                         phdr.channel = calc_channel;
1370                                 }
1371                         }
1372                         memset(&phdr.phy_info, 0, sizeof(phdr.phy_info));
1373                         cflags = tvb_get_letohs(tvb, offset + 2);
1374                         switch (cflags & IEEE80211_CHAN_ALLTURBO) {
1375
1376                         case IEEE80211_CHAN_FHSS:
1377                                 phdr.phy = PHDR_802_11_PHY_11_FHSS;
1378                                 break;
1379
1380                         case IEEE80211_CHAN_DSSS:
1381                                 phdr.phy = PHDR_802_11_PHY_11_DSSS;
1382                                 break;
1383
1384                         case IEEE80211_CHAN_A:
1385                                 phdr.phy = PHDR_802_11_PHY_11A;
1386                                 phdr.phy_info.info_11a.has_turbo_type = TRUE;
1387                                 phdr.phy_info.info_11a.turbo_type = PHDR_802_11A_TURBO_TYPE_NORMAL;
1388                                 break;
1389
1390                         case IEEE80211_CHAN_B:
1391                                 phdr.phy = PHDR_802_11_PHY_11B;
1392                                 if (have_rflags) {
1393                                         phdr.phy_info.info_11b.has_short_preamble = TRUE;
1394                                         phdr.phy_info.info_11b.short_preamble = (rflags & IEEE80211_RADIOTAP_F_SHORTPRE) != 0;
1395                                 }
1396                                 break;
1397
1398                         case IEEE80211_CHAN_PUREG:
1399                                 phdr.phy = PHDR_802_11_PHY_11G;
1400                                 phdr.phy_info.info_11g.has_mode = TRUE;
1401                                 phdr.phy_info.info_11g.mode = PHDR_802_11G_MODE_NORMAL;
1402                                 if (have_rflags) {
1403                                         phdr.phy_info.info_11g.has_short_preamble = TRUE;
1404                                         phdr.phy_info.info_11g.short_preamble = (rflags & IEEE80211_RADIOTAP_F_SHORTPRE) != 0;
1405                                 }
1406                                 break;
1407
1408                         case IEEE80211_CHAN_G:
1409                                 phdr.phy = PHDR_802_11_PHY_11G;
1410                                 phdr.phy_info.info_11g.has_mode = TRUE;
1411                                 phdr.phy_info.info_11g.mode = PHDR_802_11G_MODE_NORMAL;
1412                                 if (have_rflags) {
1413                                         phdr.phy_info.info_11g.has_short_preamble = TRUE;
1414                                         phdr.phy_info.info_11g.short_preamble = (rflags & IEEE80211_RADIOTAP_F_SHORTPRE) != 0;
1415                                 }
1416                                 break;
1417
1418                         case IEEE80211_CHAN_108A:
1419                                 phdr.phy = PHDR_802_11_PHY_11A;
1420                                 phdr.phy_info.info_11a.has_turbo_type = TRUE;
1421                                 /* We assume non-STURBO is dynamic turbo */
1422                                 phdr.phy_info.info_11a.turbo_type = PHDR_802_11A_TURBO_TYPE_DYNAMIC_TURBO;
1423                                 break;
1424
1425                         case IEEE80211_CHAN_108PUREG:
1426                                 phdr.phy = PHDR_802_11_PHY_11G;
1427                                 phdr.phy_info.info_11g.has_mode = TRUE;
1428                                 phdr.phy_info.info_11g.mode = PHDR_802_11G_MODE_SUPER_G;
1429                                 if (have_rflags) {
1430                                         phdr.phy_info.info_11g.has_short_preamble = TRUE;
1431                                         phdr.phy_info.info_11g.short_preamble = (rflags & IEEE80211_RADIOTAP_F_SHORTPRE) != 0;
1432                                 }
1433                                 break;
1434                         }
1435                         if (tree) {
1436                                 gchar      *chan_str;
1437                                 static const int * channel_flags[] = {
1438                                         &hf_radiotap_channel_flags_turbo,
1439                                         &hf_radiotap_channel_flags_cck,
1440                                         &hf_radiotap_channel_flags_ofdm,
1441                                         &hf_radiotap_channel_flags_2ghz,
1442                                         &hf_radiotap_channel_flags_5ghz,
1443                                         &hf_radiotap_channel_flags_passive,
1444                                         &hf_radiotap_channel_flags_dynamic,
1445                                         &hf_radiotap_channel_flags_gfsk,
1446                                         &hf_radiotap_channel_flags_gsm,
1447                                         &hf_radiotap_channel_flags_sturbo,
1448                                         &hf_radiotap_channel_flags_half,
1449                                         &hf_radiotap_channel_flags_quarter,
1450                                         NULL
1451                                 };
1452
1453                                 chan_str = ieee80211_mhz_to_str(freq);
1454                                 col_add_fstr(pinfo->cinfo,
1455                                              COL_FREQ_CHAN, "%s", chan_str);
1456                                 proto_tree_add_uint_format_value(radiotap_tree,
1457                                                            hf_radiotap_channel_frequency,
1458                                                            tvb, offset, 2, freq,
1459                                                            "%s",
1460                                                            chan_str);
1461                                 g_free(chan_str);
1462
1463                                 /* We're already 2-byte aligned. */
1464                                 proto_tree_add_bitmask(radiotap_tree, tvb, offset + 2, hf_radiotap_channel_flags, ett_radiotap_channel_flags, channel_flags, ENC_LITTLE_ENDIAN);
1465                                 radiotap_info->freq = freq;
1466                                 radiotap_info->flags = cflags;
1467                         }
1468                         break;
1469                 }
1470
1471                 case IEEE80211_RADIOTAP_FHSS:
1472                         /*
1473                          * Just in case we didn't have a Channel field or
1474                          * it said this was something other than 11 legacy
1475                          * FHSS.
1476                          */
1477                         phdr.phy = PHDR_802_11_PHY_11_FHSS;
1478                         phdr.phy_info.info_11_fhss.has_hop_set = TRUE;
1479                         phdr.phy_info.info_11_fhss.hop_set = tvb_get_guint8(tvb, offset);
1480                         phdr.phy_info.info_11_fhss.has_hop_pattern = TRUE;
1481                         phdr.phy_info.info_11_fhss.hop_pattern = tvb_get_guint8(tvb, offset + 1);
1482                         proto_tree_add_item(radiotap_tree,
1483                                             hf_radiotap_fhss_hopset, tvb,
1484                                             offset, 1, ENC_BIG_ENDIAN);
1485                         proto_tree_add_item(radiotap_tree,
1486                                             hf_radiotap_fhss_pattern, tvb,
1487                                             offset + 1, 1, ENC_BIG_ENDIAN);
1488                         break;
1489
1490                 case IEEE80211_RADIOTAP_DBM_ANTSIGNAL:
1491                         dbm = (gint8)tvb_get_guint8(tvb, offset);
1492                         phdr.has_signal_dbm = TRUE;
1493                         phdr.signal_dbm = dbm;
1494                         col_add_fstr(pinfo->cinfo, COL_RSSI, "%d dBm", dbm);
1495                         proto_tree_add_int(radiotap_tree,
1496                                                           hf_radiotap_dbm_antsignal,
1497                                                           tvb, offset, 1, dbm);
1498                         radiotap_info->dbm_antsignal = dbm;
1499                         break;
1500
1501                 case IEEE80211_RADIOTAP_DBM_ANTNOISE:
1502                         dbm = (gint8) tvb_get_guint8(tvb, offset);
1503                         phdr.has_noise_dbm = TRUE;
1504                         phdr.noise_dbm = dbm;
1505                         if (tree) {
1506                                 proto_tree_add_int(radiotap_tree,
1507                                                           hf_radiotap_dbm_antnoise,
1508                                                           tvb, offset, 1, dbm);
1509                         }
1510                         radiotap_info->dbm_antnoise = dbm;
1511                         break;
1512
1513                 case IEEE80211_RADIOTAP_LOCK_QUALITY:
1514                         proto_tree_add_item(radiotap_tree,
1515                                                     hf_radiotap_quality, tvb,
1516                                                     offset, 2, ENC_LITTLE_ENDIAN);
1517                         break;
1518
1519                 case IEEE80211_RADIOTAP_TX_ATTENUATION:
1520                         proto_tree_add_item(radiotap_tree,
1521                                             hf_radiotap_tx_attenuation, tvb,
1522                                             offset, 2, ENC_BIG_ENDIAN);
1523                         break;
1524
1525                 case IEEE80211_RADIOTAP_DB_TX_ATTENUATION:
1526                         proto_tree_add_item(radiotap_tree,
1527                                             hf_radiotap_db_tx_attenuation, tvb,
1528                                             offset, 2, ENC_BIG_ENDIAN);
1529                         break;
1530
1531                 case IEEE80211_RADIOTAP_DBM_TX_POWER:
1532                         proto_tree_add_item(radiotap_tree,
1533                                                    hf_radiotap_txpower, tvb,
1534                                                    offset, 1, ENC_NA);
1535                         break;
1536
1537                 case IEEE80211_RADIOTAP_ANTENNA:
1538                         proto_tree_add_item(radiotap_tree,
1539                                                     hf_radiotap_antenna, tvb,
1540                                                     offset, 1, ENC_NA);
1541                         break;
1542
1543                 case IEEE80211_RADIOTAP_DB_ANTSIGNAL:
1544                         db = tvb_get_guint8(tvb, offset);
1545                         col_add_fstr(pinfo->cinfo, COL_RSSI, "%u dB", db);
1546                         proto_tree_add_uint(radiotap_tree,
1547                                                            hf_radiotap_db_antsignal,
1548                                                            tvb, offset, 1, db);
1549                         break;
1550
1551                 case IEEE80211_RADIOTAP_DB_ANTNOISE:
1552                         db = tvb_get_guint8(tvb, offset);
1553                         proto_tree_add_uint(radiotap_tree,
1554                                                            hf_radiotap_db_antnoise,
1555                                                            tvb, offset, 1, db);
1556                         break;
1557
1558                 case IEEE80211_RADIOTAP_RX_FLAGS: {
1559                         if (radiotap_bit14_fcs) {
1560                                 if (tree) {
1561                                         sent_fcs   = tvb_get_ntohl(tvb, offset);
1562                                         hdr_fcs_ti = proto_tree_add_uint(radiotap_tree,
1563                                                                          hf_radiotap_fcs, tvb,
1564                                                                          offset, 4, sent_fcs);
1565                                         hdr_fcs_offset = offset;
1566                                 }
1567                         } else {
1568                                 static const int * rxflags[] = {
1569                                         &hf_radiotap_rxflags_badplcp,
1570                                         NULL
1571                                 };
1572
1573                                 proto_tree_add_bitmask(radiotap_tree, tvb, offset, hf_radiotap_rxflags, ett_radiotap_rxflags, rxflags, ENC_LITTLE_ENDIAN);
1574                         }
1575                         break;
1576                 }
1577
1578                 case IEEE80211_RADIOTAP_XCHANNEL: {
1579                         xcflags = tvb_get_letohl(tvb, offset);
1580                         switch (xcflags & IEEE80211_CHAN_ALLTURBO) {
1581
1582                         case IEEE80211_CHAN_FHSS:
1583                                 /*
1584                                  * Don't overwrite any FHSS information
1585                                  * we've seen before this.
1586                                  */
1587                                 if (phdr.phy != PHDR_802_11_PHY_11_FHSS) {
1588                                         phdr.phy = PHDR_802_11_PHY_11_FHSS;
1589                                 }
1590                                 break;
1591
1592                         case IEEE80211_CHAN_DSSS:
1593                                 phdr.phy = PHDR_802_11_PHY_11_DSSS;
1594                                 break;
1595
1596                         case IEEE80211_CHAN_A:
1597                                 phdr.phy = PHDR_802_11_PHY_11A;
1598                                 phdr.phy_info.info_11a.has_turbo_type = TRUE;
1599                                 phdr.phy_info.info_11a.turbo_type = PHDR_802_11A_TURBO_TYPE_NORMAL;
1600                                 break;
1601
1602                         case IEEE80211_CHAN_B:
1603                                 phdr.phy = PHDR_802_11_PHY_11B;
1604                                 if (have_rflags) {
1605                                         phdr.phy_info.info_11b.has_short_preamble = TRUE;
1606                                         phdr.phy_info.info_11b.short_preamble = (rflags & IEEE80211_RADIOTAP_F_SHORTPRE) != 0;
1607                                 }
1608                                 break;
1609
1610                         case IEEE80211_CHAN_PUREG:
1611                                 phdr.phy = PHDR_802_11_PHY_11G;
1612                                 phdr.phy_info.info_11g.has_mode = TRUE;
1613                                 phdr.phy_info.info_11g.mode = PHDR_802_11G_MODE_NORMAL;
1614                                 if (have_rflags) {
1615                                         phdr.phy_info.info_11g.has_short_preamble = TRUE;
1616                                         phdr.phy_info.info_11g.short_preamble = (rflags & IEEE80211_RADIOTAP_F_SHORTPRE) != 0;
1617                                 }
1618                                 break;
1619
1620                         case IEEE80211_CHAN_G:
1621                                 phdr.phy = PHDR_802_11_PHY_11G;
1622                                 phdr.phy_info.info_11g.has_mode = TRUE;
1623                                 phdr.phy_info.info_11g.mode = PHDR_802_11G_MODE_NORMAL;
1624                                 if (have_rflags) {
1625                                         phdr.phy_info.info_11g.has_short_preamble = TRUE;
1626                                         phdr.phy_info.info_11g.short_preamble = (rflags & IEEE80211_RADIOTAP_F_SHORTPRE) != 0;
1627                                 }
1628                                 break;
1629
1630                         case IEEE80211_CHAN_108A:
1631                                 phdr.phy = PHDR_802_11_PHY_11A;
1632                                 phdr.phy_info.info_11a.has_turbo_type = TRUE;
1633                                 /* We assume non-STURBO is dynamic turbo */
1634                                 phdr.phy_info.info_11a.turbo_type = PHDR_802_11A_TURBO_TYPE_DYNAMIC_TURBO;
1635                                 break;
1636
1637                         case IEEE80211_CHAN_108PUREG:
1638                                 phdr.phy = PHDR_802_11_PHY_11G;
1639                                 phdr.phy_info.info_11g.has_mode = TRUE;
1640                                 phdr.phy_info.info_11g.mode = PHDR_802_11G_MODE_SUPER_G;
1641                                 if (have_rflags) {
1642                                         phdr.phy_info.info_11g.has_short_preamble = TRUE;
1643                                         phdr.phy_info.info_11g.short_preamble = (rflags & IEEE80211_RADIOTAP_F_SHORTPRE) != 0;
1644                                 }
1645                                 break;
1646
1647                         case IEEE80211_CHAN_ST:
1648                                 phdr.phy = PHDR_802_11_PHY_11A;
1649                                 phdr.phy_info.info_11a.has_turbo_type = TRUE;
1650                                 phdr.phy_info.info_11a.turbo_type = PHDR_802_11A_TURBO_TYPE_STATIC_TURBO;
1651                                 break;
1652
1653                         case IEEE80211_CHAN_A|IEEE80211_CHAN_HT20:
1654                         case IEEE80211_CHAN_A|IEEE80211_CHAN_HT40D:
1655                         case IEEE80211_CHAN_A|IEEE80211_CHAN_HT40U:
1656                         case IEEE80211_CHAN_G|IEEE80211_CHAN_HT20:
1657                         case IEEE80211_CHAN_G|IEEE80211_CHAN_HT40U:
1658                         case IEEE80211_CHAN_G|IEEE80211_CHAN_HT40D:
1659                                 phdr.phy = PHDR_802_11_PHY_11N;
1660
1661                                 /*
1662                                  * This doesn't supply "short GI" information,
1663                                  * so use the 0x80 bit in the Flags field,
1664                                  * if we have it; it's "Currently unspecified
1665                                  * but used" for that purpose, according to
1666                                  * the radiotap.org page for that field.
1667                                  */
1668                                 if (have_rflags) {
1669                                         phdr.phy_info.info_11n.has_short_gi = TRUE;
1670                                         if (rflags & 0x80)
1671                                                 phdr.phy_info.info_11n.short_gi = 1;
1672                                         else
1673                                                 phdr.phy_info.info_11n.short_gi = 0;
1674                                 }
1675                                 break;
1676                         }
1677                         freq = tvb_get_letohs(tvb, offset + 4);
1678                         if (freq != 0) {
1679                                 /*
1680                                  * XXX - some captures have 0, which is
1681                                  * obviously bogus.
1682                                  */
1683                                 phdr.has_frequency = TRUE;
1684                                 phdr.frequency = freq;
1685                         }
1686                         phdr.has_channel = TRUE;
1687                         phdr.channel = tvb_get_guint8(tvb, offset + 6);
1688                         if (tree) {
1689                                 static const int * xchannel_flags[] = {
1690                                         &hf_radiotap_xchannel_flags_turbo,
1691                                         &hf_radiotap_xchannel_flags_cck,
1692                                         &hf_radiotap_xchannel_flags_ofdm,
1693                                         &hf_radiotap_xchannel_flags_2ghz,
1694                                         &hf_radiotap_xchannel_flags_5ghz,
1695                                         &hf_radiotap_xchannel_flags_passive,
1696                                         &hf_radiotap_xchannel_flags_dynamic,
1697                                         &hf_radiotap_xchannel_flags_gfsk,
1698                                         &hf_radiotap_xchannel_flags_gsm,
1699                                         &hf_radiotap_xchannel_flags_sturbo,
1700                                         &hf_radiotap_xchannel_flags_half,
1701                                         &hf_radiotap_xchannel_flags_quarter,
1702                                         &hf_radiotap_xchannel_flags_ht20,
1703                                         &hf_radiotap_xchannel_flags_ht40u,
1704                                         &hf_radiotap_xchannel_flags_ht40d,
1705                                         NULL
1706                                 };
1707
1708                                 proto_tree_add_item(radiotap_tree,
1709                                                         hf_radiotap_xchannel_channel,
1710                                                         tvb, offset + 6, 1,
1711                                                         ENC_LITTLE_ENDIAN);
1712                                 proto_tree_add_item(radiotap_tree,
1713                                                         hf_radiotap_xchannel_frequency,
1714                                                         tvb, offset + 4, 2, ENC_LITTLE_ENDIAN);
1715
1716                                 proto_tree_add_bitmask(radiotap_tree, tvb, offset, hf_radiotap_xchannel_flags, ett_radiotap_xchannel_flags, xchannel_flags, ENC_LITTLE_ENDIAN);
1717
1718
1719 #if 0
1720                                 proto_tree_add_uint(radiotap_tree,
1721                                                         hf_radiotap_xchannel_maxpower,
1722                                                         tvb, offset + 7, 1, maxpower);
1723 #endif
1724                         }
1725                         break;
1726                 }
1727                 case IEEE80211_RADIOTAP_MCS: {
1728                         proto_tree *mcs_tree = NULL;
1729                         guint8      mcs_known, mcs_flags;
1730                         guint8      mcs;
1731                         guint       bandwidth;
1732                         guint       gi_length;
1733                         gboolean    can_calculate_rate;
1734
1735                         /*
1736                          * Start out assuming that we can calculate the rate;
1737                          * if we are missing any of the MCS index, channel
1738                          * width, or guard interval length, we can't.
1739                          */
1740                         can_calculate_rate = TRUE;
1741
1742                         mcs_known = tvb_get_guint8(tvb, offset);
1743                         /*
1744                          * If there's actually any data here, not an
1745                          * empty field, this is 802.11n.
1746                          */
1747                         if (mcs_known != 0) {
1748                                 phdr.phy = PHDR_802_11_PHY_11N;
1749                                 memset(&phdr.phy_info.info_11n, 0, sizeof(phdr.phy_info.info_11n));
1750                         }
1751
1752                         mcs_flags = tvb_get_guint8(tvb, offset + 1);
1753                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_MCS) {
1754                                 mcs = tvb_get_guint8(tvb, offset + 2);
1755                                 phdr.phy_info.info_11n.has_mcs_index = TRUE;
1756                                 phdr.phy_info.info_11n.mcs_index = mcs;
1757                         } else {
1758                                 mcs = 0;
1759                                 can_calculate_rate = FALSE;     /* no MCS index */
1760                         }
1761                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_BW) {
1762                                 phdr.phy_info.info_11n.has_bandwidth = TRUE;
1763                                 phdr.phy_info.info_11n.bandwidth = (mcs_flags & IEEE80211_RADIOTAP_MCS_BW_MASK);
1764                         }
1765                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_GI) {
1766                                 gi_length = (mcs_flags & IEEE80211_RADIOTAP_MCS_SGI) ?
1767                                     1 : 0;
1768                                 phdr.phy_info.info_11n.has_short_gi = TRUE;
1769                                 phdr.phy_info.info_11n.short_gi = gi_length;
1770                         } else {
1771                                 gi_length = 0;
1772                                 can_calculate_rate = FALSE;     /* no GI width */
1773                         }
1774                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_FMT) {
1775                                 phdr.phy_info.info_11n.has_greenfield = TRUE;
1776                                 phdr.phy_info.info_11n.greenfield = (mcs_flags & IEEE80211_RADIOTAP_MCS_FMT_GF) != 0;
1777                         }
1778                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_FEC) {
1779                                 phdr.phy_info.info_11n.has_fec = TRUE;
1780                                 phdr.phy_info.info_11n.fec = (mcs_flags & IEEE80211_RADIOTAP_MCS_FEC_LDPC) ? 1 : 0;
1781                         }
1782                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_STBC) {
1783                                 phdr.phy_info.info_11n.has_stbc_streams = TRUE;
1784                                 phdr.phy_info.info_11n.stbc_streams = (mcs_flags & IEEE80211_RADIOTAP_MCS_STBC_MASK) >> IEEE80211_RADIOTAP_MCS_STBC_SHIFT;
1785                         }
1786                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_NESS) {
1787                                 phdr.phy_info.info_11n.has_ness = TRUE;
1788                                 /* This is stored a bit weirdly */
1789                                 phdr.phy_info.info_11n.ness =
1790                                     ((mcs_known & IEEE80211_RADIOTAP_MCS_NESS_BIT1) >> 6) |
1791                                     ((mcs_flags & IEEE80211_RADIOTAP_MCS_NESS_BIT0) >> 7);
1792                         }
1793
1794                         if (tree) {
1795                                 proto_item *it;
1796                                 static const int * mcs_haves_with_ness_bit1[] = {
1797                                         &hf_radiotap_mcs_have_bw,
1798                                         &hf_radiotap_mcs_have_index,
1799                                         &hf_radiotap_mcs_have_gi,
1800                                         &hf_radiotap_mcs_have_format,
1801                                         &hf_radiotap_mcs_have_fec,
1802                                         &hf_radiotap_mcs_have_stbc,
1803                                         &hf_radiotap_mcs_have_ness,
1804                                         &hf_radiotap_mcs_ness_bit1,
1805                                         NULL
1806                                 };
1807                                 static const int * mcs_haves_without_ness_bit1[] = {
1808                                         &hf_radiotap_mcs_have_bw,
1809                                         &hf_radiotap_mcs_have_index,
1810                                         &hf_radiotap_mcs_have_gi,
1811                                         &hf_radiotap_mcs_have_format,
1812                                         &hf_radiotap_mcs_have_fec,
1813                                         &hf_radiotap_mcs_have_stbc,
1814                                         &hf_radiotap_mcs_have_ness,
1815                                         NULL
1816                                 };
1817
1818                                 it = proto_tree_add_item(radiotap_tree, hf_radiotap_mcs,
1819                                                          tvb, offset, 3, ENC_NA);
1820                                 mcs_tree = proto_item_add_subtree(it, ett_radiotap_mcs);
1821
1822                                 if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_NESS)
1823                                         proto_tree_add_bitmask(mcs_tree, tvb, offset, hf_radiotap_mcs_known, ett_radiotap_mcs_known, mcs_haves_with_ness_bit1, ENC_LITTLE_ENDIAN);
1824                                 else
1825                                         proto_tree_add_bitmask(mcs_tree, tvb, offset, hf_radiotap_mcs_known, ett_radiotap_mcs_known, mcs_haves_without_ness_bit1, ENC_LITTLE_ENDIAN);
1826                         }
1827                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_BW) {
1828                                 bandwidth = ((mcs_flags & IEEE80211_RADIOTAP_MCS_BW_MASK) == IEEE80211_RADIOTAP_MCS_BW_40) ?
1829                                     1 : 0;
1830                                 proto_tree_add_uint(mcs_tree, hf_radiotap_mcs_bw,
1831                                                             tvb, offset + 1, 1, mcs_flags);
1832                         } else {
1833                                 bandwidth = 0;
1834                                 can_calculate_rate = FALSE;     /* no bandwidth */
1835                         }
1836                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_GI) {
1837                                 proto_tree_add_uint(mcs_tree, hf_radiotap_mcs_gi,
1838                                                             tvb, offset + 1, 1, mcs_flags);
1839                         }
1840                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_FMT) {
1841                                 proto_tree_add_uint(mcs_tree, hf_radiotap_mcs_format,
1842                                                             tvb, offset + 1, 1, mcs_flags);
1843                         }
1844                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_FEC) {
1845                                 proto_tree_add_uint(mcs_tree, hf_radiotap_mcs_fec,
1846                                                             tvb, offset + 1, 1, mcs_flags);
1847                         }
1848                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_STBC) {
1849                                 proto_tree_add_uint(mcs_tree, hf_radiotap_mcs_stbc,
1850                                                             tvb, offset + 1, 1, mcs_flags);
1851                         }
1852                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_NESS) {
1853                                 proto_tree_add_uint(mcs_tree, hf_radiotap_mcs_ness_bit0,
1854                                                             tvb, offset + 1, 1, mcs_flags);
1855                         }
1856                         if (mcs_known & IEEE80211_RADIOTAP_MCS_HAVE_MCS) {
1857                                 proto_tree_add_uint(mcs_tree, hf_radiotap_mcs_index,
1858                                                             tvb, offset + 2, 1, mcs);
1859                         }
1860
1861                         /*
1862                          * If we have the MCS index, channel width, and
1863                          * guard interval length, and the MCS index is
1864                          * valid, we can compute the rate.  If the resulting
1865                          * rate is non-zero, report it.  (If it's zero,
1866                          * it's an MCS/channel width/GI combination that
1867                          * 802.11n doesn't support.)
1868                          */
1869                         if (can_calculate_rate && mcs <= MAX_MCS_INDEX
1870                                         && ieee80211_ht_Dbps[mcs] != 0) {
1871                                 float rate = ieee80211_htrate(mcs, bandwidth, gi_length);
1872                                 col_add_fstr(pinfo->cinfo, COL_TX_RATE, "%.1f", rate);
1873                                 if (tree) {
1874                                         rate_ti = proto_tree_add_float_format(radiotap_tree,
1875                                                 hf_radiotap_datarate,
1876                                                 tvb, offset, 3, rate,
1877                                                 "Data Rate: %.1f Mb/s", rate);
1878                                         PROTO_ITEM_SET_GENERATED(rate_ti);
1879                                 }
1880                         }
1881                         break;
1882                 }
1883                 case IEEE80211_RADIOTAP_AMPDU_STATUS: {
1884                         proto_item *it;
1885                         proto_tree *ampdu_tree = NULL, *ampdu_flags_tree;
1886                         guint16     ampdu_flags;
1887
1888                         phdr.has_aggregate_info = 1;
1889                         phdr.aggregate_flags = 0;
1890                         phdr.aggregate_id = tvb_get_letohl(tvb, offset);
1891
1892                         ampdu_flags = tvb_get_letohs(tvb, offset + 4);
1893                         if (ampdu_flags & IEEE80211_RADIOTAP_AMPDU_IS_LAST)
1894                                 phdr.aggregate_flags |= PHDR_802_11_LAST_PART_OF_A_MPDU;
1895                         if (ampdu_flags & IEEE80211_RADIOTAP_AMPDU_DELIM_CRC_ERR)
1896                                 phdr.aggregate_flags |= PHDR_802_11_A_MPDU_DELIM_CRC_ERROR;
1897
1898                         if (tree) {
1899                                 it = proto_tree_add_item(radiotap_tree, hf_radiotap_ampdu,
1900                                                          tvb, offset, 8, ENC_NA);
1901                                 ampdu_tree = proto_item_add_subtree(it, ett_radiotap_ampdu);
1902
1903                                 proto_tree_add_item(ampdu_tree, hf_radiotap_ampdu_ref,
1904                                                     tvb, offset, 4, ENC_LITTLE_ENDIAN);
1905
1906                                 it = proto_tree_add_item(ampdu_tree, hf_radiotap_ampdu_flags,
1907                                                          tvb, offset + 4, 2, ENC_LITTLE_ENDIAN);
1908                                 ampdu_flags_tree = proto_item_add_subtree(it, ett_radiotap_ampdu_flags);
1909                                 proto_tree_add_item(ampdu_flags_tree, hf_radiotap_ampdu_flags_report_zerolen,
1910                                                     tvb, offset + 4, 2, ENC_LITTLE_ENDIAN);
1911                                 proto_tree_add_item(ampdu_flags_tree, hf_radiotap_ampdu_flags_is_zerolen,
1912                                                     tvb, offset + 4, 2, ENC_LITTLE_ENDIAN);
1913                                 proto_tree_add_item(ampdu_flags_tree, hf_radiotap_ampdu_flags_last_known,
1914                                                     tvb, offset + 4, 2, ENC_LITTLE_ENDIAN);
1915                                 proto_tree_add_item(ampdu_flags_tree, hf_radiotap_ampdu_flags_is_last,
1916                                                     tvb, offset + 4, 2, ENC_LITTLE_ENDIAN);
1917                                 proto_tree_add_item(ampdu_flags_tree, hf_radiotap_ampdu_flags_delim_crc_error,
1918                                                     tvb, offset + 4, 2, ENC_LITTLE_ENDIAN);
1919                         }
1920                         if (ampdu_flags & IEEE80211_RADIOTAP_AMPDU_DELIM_CRC_KNOWN) {
1921                                 if (ampdu_tree)
1922                                         proto_tree_add_item(ampdu_tree, hf_radiotap_ampdu_delim_crc,
1923                                                             tvb, offset + 6, 1, ENC_NA);
1924                         }
1925                         break;
1926                 }
1927                 case IEEE80211_RADIOTAP_VHT: {
1928                         proto_item *it, *it_root = NULL;
1929                         proto_tree *vht_tree     = NULL, *vht_known_tree = NULL, *user_tree = NULL;
1930                         guint16     known;
1931                         guint8      vht_flags, bw, mcs_nss;
1932                         guint       bandwidth    = 0;
1933                         guint       gi_length    = 0;
1934                         guint       nss          = 0;
1935                         guint       mcs          = 0;
1936                         gboolean    can_calculate_rate;
1937                         guint       i;
1938
1939                         /*
1940                          * Start out assuming that we can calculate the rate;
1941                          * if we are missing any of the MCS index, channel
1942                          * width, or guard interval length, we can't.
1943                          */
1944                         can_calculate_rate = TRUE;
1945
1946                         known = tvb_get_letohs(tvb, offset);
1947                         /*
1948                          * If there's actually any data here, not an
1949                          * empty field, this is 802.11ac.
1950                          */
1951                         if (known != 0) {
1952                                 phdr.phy = PHDR_802_11_PHY_11AC;
1953                         }
1954                         vht_flags = tvb_get_guint8(tvb, offset + 2);
1955                         if (tree) {
1956                                 it_root = proto_tree_add_item(radiotap_tree, hf_radiotap_vht,
1957                                                 tvb, offset, 12, ENC_NA);
1958                                 vht_tree = proto_item_add_subtree(it_root, ett_radiotap_vht);
1959                                 it = proto_tree_add_item(vht_tree, hf_radiotap_vht_known,
1960                                                 tvb, offset, 2, known);
1961                                 vht_known_tree = proto_item_add_subtree(it, ett_radiotap_vht_known);
1962
1963                                 proto_tree_add_item(vht_known_tree, hf_radiotap_vht_have_stbc,
1964                                                 tvb, offset, 2, ENC_LITTLE_ENDIAN);
1965                                 proto_tree_add_item(vht_known_tree, hf_radiotap_vht_have_txop_ps,
1966                                                 tvb, offset, 2, ENC_LITTLE_ENDIAN);
1967                                 proto_tree_add_item(vht_known_tree, hf_radiotap_vht_have_gi,
1968                                                 tvb, offset, 2, ENC_LITTLE_ENDIAN);
1969                                 proto_tree_add_item(vht_known_tree, hf_radiotap_vht_have_sgi_nsym_da,
1970                                                 tvb, offset, 2, ENC_LITTLE_ENDIAN);
1971                                 proto_tree_add_item(vht_known_tree, hf_radiotap_vht_have_ldpc_extra,
1972                                                 tvb, offset, 2, ENC_LITTLE_ENDIAN);
1973                                 proto_tree_add_item(vht_known_tree, hf_radiotap_vht_have_bf,
1974                                                 tvb, offset, 2, ENC_LITTLE_ENDIAN);
1975                                 proto_tree_add_item(vht_known_tree, hf_radiotap_vht_have_bw,
1976                                                 tvb, offset, 2, ENC_LITTLE_ENDIAN);
1977                                 proto_tree_add_item(vht_known_tree, hf_radiotap_vht_have_gid,
1978                                                 tvb, offset, 2, ENC_LITTLE_ENDIAN);
1979                                 proto_tree_add_item(vht_known_tree, hf_radiotap_vht_have_p_aid,
1980                                                 tvb, offset, 2, ENC_LITTLE_ENDIAN);
1981                         }
1982
1983                         if (known & IEEE80211_RADIOTAP_VHT_HAVE_STBC) {
1984                                 phdr.phy_info.info_11ac.has_stbc = TRUE;
1985                                 phdr.phy_info.info_11ac.stbc = (vht_flags & IEEE80211_RADIOTAP_VHT_STBC) != 0;
1986                                 if (vht_tree)
1987                                         proto_tree_add_item(vht_tree, hf_radiotap_vht_stbc,
1988                                                         tvb, offset + 2, 1, ENC_LITTLE_ENDIAN);
1989                         }
1990
1991                         if (known & IEEE80211_RADIOTAP_VHT_HAVE_TXOP_PS) {
1992                                 phdr.phy_info.info_11ac.has_txop_ps_not_allowed = TRUE;
1993                                 phdr.phy_info.info_11ac.txop_ps_not_allowed = (vht_flags & IEEE80211_RADIOTAP_VHT_TXOP_PS) != 0;
1994                                 if (vht_tree)
1995                                         proto_tree_add_item(vht_tree, hf_radiotap_vht_txop_ps,
1996                                                         tvb, offset + 2, 1, ENC_LITTLE_ENDIAN);
1997                         }
1998
1999                         if (known & IEEE80211_RADIOTAP_VHT_HAVE_GI) {
2000                                 gi_length = (vht_flags & IEEE80211_RADIOTAP_VHT_SGI) ? 1 : 0;
2001                                 phdr.phy_info.info_11ac.has_short_gi = TRUE;
2002                                 phdr.phy_info.info_11ac.short_gi = gi_length;
2003                                 if (vht_tree) {
2004                                         proto_tree_add_item(vht_tree, hf_radiotap_vht_gi,
2005                                                         tvb, offset + 2, 1, ENC_LITTLE_ENDIAN);
2006                                 }
2007                         } else {
2008                                 can_calculate_rate = FALSE;     /* no GI width */
2009                         }
2010
2011                         if (known & IEEE80211_RADIOTAP_VHT_HAVE_SGI_NSYM_DA) {
2012                                 phdr.phy_info.info_11ac.has_short_gi_nsym_disambig = TRUE;
2013                                 phdr.phy_info.info_11ac.short_gi_nsym_disambig = (vht_flags & IEEE80211_RADIOTAP_VHT_SGI_NSYM_DA) != 0;
2014                                 if (vht_tree) {
2015                                         it = proto_tree_add_item(vht_tree, hf_radiotap_vht_sgi_nsym_da,
2016                                                         tvb, offset + 2, 1, ENC_LITTLE_ENDIAN);
2017                                         if ((vht_flags & IEEE80211_RADIOTAP_VHT_SGI_NSYM_DA) &&
2018                                                 (known & IEEE80211_RADIOTAP_VHT_HAVE_GI) &&
2019                                                 !(vht_flags & IEEE80211_RADIOTAP_VHT_SGI))
2020                                                 proto_item_append_text(it, " (invalid)");
2021                                 }
2022                         }
2023
2024                         if (known & IEEE80211_RADIOTAP_VHT_HAVE_LDPC_EXTRA) {
2025                                 phdr.phy_info.info_11ac.has_ldpc_extra_ofdm_symbol = TRUE;
2026                                 phdr.phy_info.info_11ac.ldpc_extra_ofdm_symbol = (vht_flags & IEEE80211_RADIOTAP_VHT_LDPC_EXTRA) != 0;
2027                                 if (vht_tree) {
2028                                         proto_tree_add_item(vht_tree, hf_radiotap_vht_ldpc_extra,
2029                                                         tvb, offset + 2, 1, ENC_LITTLE_ENDIAN);
2030                                 }
2031                         }
2032
2033                         if (known & IEEE80211_RADIOTAP_VHT_HAVE_BF) {
2034                                 phdr.phy_info.info_11ac.has_beamformed = TRUE;
2035                                 phdr.phy_info.info_11ac.beamformed = (vht_flags & IEEE80211_RADIOTAP_VHT_BF) != 0;
2036                                 if (vht_tree)
2037                                         proto_tree_add_item(vht_tree, hf_radiotap_vht_bf,
2038                                                         tvb, offset + 2, 1, ENC_LITTLE_ENDIAN);
2039                         }
2040
2041                         if (known & IEEE80211_RADIOTAP_VHT_HAVE_BW) {
2042                                 bw = tvb_get_guint8(tvb, offset + 3) & IEEE80211_RADIOTAP_VHT_BW_MASK;
2043                                 phdr.phy_info.info_11ac.has_bandwidth = TRUE;
2044                                 phdr.phy_info.info_11ac.bandwidth = bw;
2045                                 if (bw < sizeof(ieee80211_vht_bw2rate_index)/sizeof(ieee80211_vht_bw2rate_index[0]))
2046                                         bandwidth = ieee80211_vht_bw2rate_index[bw];
2047                                 else
2048                                         can_calculate_rate = FALSE; /* unknown bandwidth */
2049
2050                                 if (vht_tree)
2051                                         proto_tree_add_item(vht_tree, hf_radiotap_vht_bw,
2052                                                         tvb, offset + 3, 1, ENC_LITTLE_ENDIAN);
2053                         } else {
2054                                 can_calculate_rate = FALSE;     /* no bandwidth */
2055                         }
2056
2057                         phdr.phy_info.info_11ac.has_fec = TRUE;
2058                         phdr.phy_info.info_11ac.fec = tvb_get_guint8(tvb, offset + 8);
2059
2060                         for(i=0; i<4; i++) {
2061                                 mcs_nss = tvb_get_guint8(tvb, offset + 4 + i);
2062                                 nss = (mcs_nss & IEEE80211_RADIOTAP_VHT_NSS);
2063                                 mcs = (mcs_nss & IEEE80211_RADIOTAP_VHT_MCS) >> 4;
2064                                 phdr.phy_info.info_11ac.mcs[i] = mcs;
2065                                 phdr.phy_info.info_11ac.nss[i] = nss;
2066
2067                                 if (nss) {
2068                                         /*
2069                                          * OK, there's some data here.
2070                                          * If we haven't already flagged this
2071                                          * as VHT, do so.
2072                                          */
2073                                         if (phdr.phy != PHDR_802_11_PHY_11AC) {
2074                                                 phdr.phy = PHDR_802_11_PHY_11AC;
2075                                         }
2076                                         if (vht_tree) {
2077                                                 it = proto_tree_add_item(vht_tree, hf_radiotap_vht_user,
2078                                                         tvb, offset + 4, 5, ENC_NA);
2079                                                 proto_item_append_text(it, " %d: MCS %u", i, mcs);
2080                                                 user_tree = proto_item_add_subtree(it, ett_radiotap_vht_user);
2081
2082                                                 it = proto_tree_add_item(user_tree, hf_radiotap_vht_mcs[i],
2083                                                         tvb, offset + 4 + i, 1,
2084                                                         ENC_LITTLE_ENDIAN);
2085                                                 if (mcs > MAX_MCS_VHT_INDEX) {
2086                                                         proto_item_append_text(it, " (invalid)");
2087                                                 } else {
2088                                                         proto_item_append_text(it, " (%s %s)",
2089                                                                 ieee80211_vhtinfo[mcs].modulation,
2090                                                                 ieee80211_vhtinfo[mcs].coding_rate);
2091                                                 }
2092
2093                                                 proto_tree_add_item(user_tree, hf_radiotap_vht_nss[i],
2094                                                         tvb, offset + 4 + i, 1, ENC_LITTLE_ENDIAN);
2095                                                 if (known & IEEE80211_RADIOTAP_VHT_HAVE_STBC) {
2096                                                         guint nsts;
2097                                                         proto_item *nsts_ti;
2098
2099                                                         if (vht_flags & IEEE80211_RADIOTAP_VHT_STBC)
2100                                                                 nsts = 2 * nss;
2101                                                         else
2102                                                                 nsts = nss;
2103                                                         nsts_ti = proto_tree_add_uint(user_tree, hf_radiotap_vht_nsts[i],
2104                                                                 tvb, offset + 4 + i, 1, nsts);
2105                                                         PROTO_ITEM_SET_GENERATED(nsts_ti);
2106                                                 }
2107                                                 proto_tree_add_item(user_tree, hf_radiotap_vht_coding[i],
2108                                                         tvb, offset + 8, 1,ENC_LITTLE_ENDIAN);
2109                                         }
2110
2111                                         if (can_calculate_rate && mcs <= MAX_MCS_VHT_INDEX &&
2112                                             nss <= MAX_VHT_NSS ) {
2113                                                 float rate = ieee80211_vhtinfo[mcs].rates[bandwidth][gi_length] * nss;
2114                                                 if (rate != 0.0f ) {
2115                                                         rate_ti = proto_tree_add_float_format(user_tree,
2116                                                                         hf_radiotap_vht_datarate[i],
2117                                                                         tvb, offset, 12, rate,
2118                                                                         "Data Rate: %.1f Mb/s", rate);
2119                                                         PROTO_ITEM_SET_GENERATED(rate_ti);
2120                                                         if (ieee80211_vhtvalid[mcs].valid[bandwidth][nss-1] == FALSE)
2121                                                                 expert_add_info(pinfo, rate_ti, &ei_radiotap_invalid_data_rate);
2122
2123                                                 }
2124                                         }
2125                                 }
2126                         }
2127
2128                         if (known & IEEE80211_RADIOTAP_VHT_HAVE_GID) {
2129                                 phdr.phy_info.info_11ac.has_group_id = TRUE;
2130                                 phdr.phy_info.info_11ac.group_id = tvb_get_guint8(tvb, offset + 9);
2131                                 if (vht_tree)
2132                                         proto_tree_add_item(vht_tree, hf_radiotap_vht_gid,
2133                                                         tvb, offset+9, 1, ENC_LITTLE_ENDIAN);
2134                         }
2135
2136                         if (known & IEEE80211_RADIOTAP_VHT_HAVE_PAID) {
2137                                 phdr.phy_info.info_11ac.has_partial_aid = TRUE;
2138                                 phdr.phy_info.info_11ac.partial_aid = tvb_get_letohs(tvb, offset + 10);
2139                                 if (vht_tree) {
2140                                         proto_tree_add_item(vht_tree, hf_radiotap_vht_p_aid,
2141                                                         tvb, offset+10, 2, ENC_LITTLE_ENDIAN);
2142                                 }
2143                         }
2144
2145                         break;
2146                 }
2147                 case IEEE80211_RADIOTAP_TIMESTAMP: {
2148                         proto_item *it_root;
2149                         proto_tree *ts_tree, *flg_tree;
2150
2151                         it_root = proto_tree_add_item(radiotap_tree, hf_radiotap_timestamp,
2152                                         tvb, offset, 12, ENC_NA);
2153                         ts_tree = proto_item_add_subtree(it_root, ett_radiotap_timestamp);
2154
2155                         proto_tree_add_item(ts_tree, hf_radiotap_timestamp_ts,
2156                                         tvb, offset, 8, ENC_LITTLE_ENDIAN);
2157                         if (tvb_get_letohs(tvb, offset + 11) & IEEE80211_RADIOTAP_TS_FLG_ACCURACY)
2158                                 proto_tree_add_item(ts_tree, hf_radiotap_timestamp_accuracy,
2159                                         tvb, offset + 8, 2, ENC_LITTLE_ENDIAN);
2160                         proto_tree_add_item(ts_tree, hf_radiotap_timestamp_unit,
2161                                         tvb, offset + 10, 1, ENC_LITTLE_ENDIAN);
2162                         proto_tree_add_item(ts_tree, hf_radiotap_timestamp_spos,
2163                                         tvb, offset + 10, 1, ENC_LITTLE_ENDIAN);
2164                         flg_tree = proto_item_add_subtree(ts_tree, ett_radiotap_timestamp_flags);
2165                         proto_tree_add_item(flg_tree,
2166                                         hf_radiotap_timestamp_flags_32bit, tvb,
2167                                         offset + 11, 1, ENC_LITTLE_ENDIAN);
2168                         proto_tree_add_item(flg_tree,
2169                                         hf_radiotap_timestamp_flags_accuracy, tvb,
2170                                         offset + 11, 1, ENC_LITTLE_ENDIAN);
2171                         break;
2172                 }
2173                 case IEEE80211_RADIOTAP_HE:
2174                         dissect_radiotap_he_info(tvb, pinfo, radiotap_tree, offset);
2175                         break;
2176                 }
2177         }
2178
2179         if (err != -ENOENT) {
2180                 expert_add_info(pinfo, present_item,
2181                     &ei_radiotap_data_past_header);
2182  malformed:
2183                 proto_item_append_text(ti, " (malformed)");
2184         }
2185
2186  hand_off_to_80211:
2187         /* Grab the rest of the frame. */
2188         next_tvb = tvb_new_subset_remaining(tvb, length);
2189
2190         /* If we had an in-header FCS, check it.
2191          * This can only happen if the backward-compat configuration option
2192          * is chosen by the user. */
2193         if (hdr_fcs_ti) {
2194                 guint captured_length = tvb_captured_length(next_tvb);
2195                 guint reported_length = tvb_reported_length(next_tvb);
2196                 guint fcs_len = (phdr.fcs_len > 0) ? phdr.fcs_len : 0;
2197
2198                 /* It would be very strange for the header to have an FCS for the
2199                  * frame *and* the frame to have the FCS at the end, but it's possible, so
2200                  * take that into account by using the FCS length recorded in pinfo. */
2201
2202                 /* Watch out for [erroneously] short frames */
2203                 if (captured_length >= reported_length &&
2204                     captured_length > fcs_len) {
2205                         calc_fcs =
2206                             crc32_802_tvb(next_tvb, tvb_captured_length(next_tvb) - fcs_len);
2207
2208                         /* By virtue of hdr_fcs_ti being set, we know that 'tree' is set,
2209                          * so there's no need to check it here. */
2210                         if (calc_fcs == sent_fcs) {
2211                                 proto_item_append_text(hdr_fcs_ti,
2212                                                        " [correct]");
2213                         } else {
2214                                 proto_item_append_text(hdr_fcs_ti,
2215                                                        " [incorrect, should be 0x%08x]",
2216                                                        calc_fcs);
2217                                 hidden_item =
2218                                     proto_tree_add_boolean(radiotap_tree,
2219                                                            hf_radiotap_fcs_bad,
2220                                                            tvb, hdr_fcs_offset,
2221                                                            4, TRUE);
2222                                 PROTO_ITEM_SET_HIDDEN(hidden_item);
2223                         }
2224                 } else {
2225                         proto_item_append_text(hdr_fcs_ti,
2226                                                " [cannot verify - not enough data]");
2227                 }
2228         }
2229
2230         /* dissect the 802.11 packet next */
2231         call_dissector_with_data(ieee80211_radio_handle, next_tvb, pinfo,
2232             tree, &phdr);
2233
2234         tap_queue_packet(radiotap_tap, pinfo, radiotap_info);
2235         return tvb_captured_length(tvb);
2236 }
2237
2238 void proto_register_radiotap(void)
2239 {
2240
2241         static hf_register_info hf[] = {
2242                 {&hf_radiotap_version,
2243                  {"Header revision", "radiotap.version",
2244                   FT_UINT8, BASE_DEC, NULL, 0x0,
2245                   "Version of radiotap header format", HFILL}},
2246
2247                 {&hf_radiotap_pad,
2248                  {"Header pad", "radiotap.pad",
2249                   FT_UINT8, BASE_DEC, NULL, 0x0,
2250                   "Padding", HFILL}},
2251
2252                 {&hf_radiotap_length,
2253                  {"Header length", "radiotap.length",
2254                   FT_UINT16, BASE_DEC, NULL, 0x0,
2255                   "Length of header including version, pad, length and data fields", HFILL}},
2256
2257                 {&hf_radiotap_present,
2258                  {"Present flags", "radiotap.present",
2259                   FT_NONE, BASE_NONE, NULL, 0x0,
2260                   "Bitmask indicating which fields are present", HFILL}},
2261
2262                 {&hf_radiotap_present_word,
2263                  {"Present flags word", "radiotap.present.word",
2264                   FT_UINT32, BASE_HEX, NULL, 0x0,
2265                   "Word from present flags bitmask", HFILL}},
2266
2267 #define RADIOTAP_MASK(name)     BIT(IEEE80211_RADIOTAP_ ##name)
2268
2269                 /* Boolean 'present' flags */
2270                 {&hf_radiotap_present_tsft,
2271                  {"TSFT", "radiotap.present.tsft",
2272                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(TSFT),
2273                   "Specifies if the Time Synchronization Function Timer field is present", HFILL}},
2274
2275                 {&hf_radiotap_present_flags,
2276                  {"Flags", "radiotap.present.flags",
2277                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(FLAGS),
2278                   "Specifies if the channel flags field is present", HFILL}},
2279
2280                 {&hf_radiotap_present_rate,
2281                  {"Rate", "radiotap.present.rate",
2282                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(RATE),
2283                   "Specifies if the transmit/receive rate field is present", HFILL}},
2284
2285                 {&hf_radiotap_present_channel,
2286                  {"Channel", "radiotap.present.channel",
2287                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(CHANNEL),
2288                   "Specifies if the transmit/receive frequency field is present", HFILL}},
2289
2290                 {&hf_radiotap_present_fhss,
2291                  {"FHSS", "radiotap.present.fhss",
2292                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(FHSS),
2293                   "Specifies if the hop set and pattern is present for frequency hopping radios", HFILL}},
2294
2295                 {&hf_radiotap_present_dbm_antsignal,
2296                  {"dBm Antenna Signal", "radiotap.present.dbm_antsignal",
2297                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(DBM_ANTSIGNAL),
2298                   "Specifies if the antenna signal strength in dBm is present", HFILL}},
2299
2300                 {&hf_radiotap_present_dbm_antnoise,
2301                  {"dBm Antenna Noise", "radiotap.present.dbm_antnoise",
2302                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(DBM_ANTNOISE),
2303                   "Specifies if the RF noise power at antenna field is present", HFILL}},
2304
2305                 {&hf_radiotap_present_lock_quality,
2306                  {"Lock Quality", "radiotap.present.lock_quality",
2307                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(LOCK_QUALITY),
2308                   "Specifies if the signal quality field is present", HFILL}},
2309
2310                 {&hf_radiotap_present_tx_attenuation,
2311                  {"TX Attenuation", "radiotap.present.tx_attenuation",
2312                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(TX_ATTENUATION),
2313                   "Specifies if the transmit power distance from max power field is present", HFILL}},
2314
2315                 {&hf_radiotap_present_db_tx_attenuation,
2316                  {"dB TX Attenuation", "radiotap.present.db_tx_attenuation",
2317                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(DB_TX_ATTENUATION),
2318                   "Specifies if the transmit power distance from max power (in dB) field is present", HFILL}},
2319
2320                 {&hf_radiotap_present_dbm_tx_power,
2321                  {"dBm TX Power", "radiotap.present.dbm_tx_power",
2322                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(DBM_TX_POWER),
2323                   "Specifies if the transmit power (in dBm) field is present", HFILL}},
2324
2325                 {&hf_radiotap_present_antenna,
2326                  {"Antenna", "radiotap.present.antenna",
2327                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(ANTENNA),
2328                   "Specifies if the antenna number field is present", HFILL}},
2329
2330                 {&hf_radiotap_present_db_antsignal,
2331                  {"dB Antenna Signal", "radiotap.present.db_antsignal",
2332                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(DB_ANTSIGNAL),
2333                   "Specifies if the RF signal power at antenna in dB field is present", HFILL}},
2334
2335                 {&hf_radiotap_present_db_antnoise,
2336                  {"dB Antenna Noise", "radiotap.present.db_antnoise",
2337                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(DB_ANTNOISE),
2338                   "Specifies if the RF signal power at antenna in dBm field is present", HFILL}},
2339
2340                 {&hf_radiotap_present_rxflags,
2341                  {"RX flags", "radiotap.present.rxflags",
2342                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(RX_FLAGS),
2343                   "Specifies if the RX flags field is present", HFILL}},
2344
2345                 {&hf_radiotap_present_hdrfcs,
2346                  {"FCS in header", "radiotap.present.fcs",
2347                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(RX_FLAGS),
2348                   "Specifies if the FCS field is present", HFILL}},
2349
2350                 {&hf_radiotap_present_xchannel,
2351                  {"Channel+", "radiotap.present.xchannel",
2352                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(XCHANNEL),
2353                   "Specifies if the extended channel info field is present", HFILL}},
2354
2355                 {&hf_radiotap_present_mcs,
2356                  {"MCS information", "radiotap.present.mcs",
2357                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(MCS),
2358                   "Specifies if the MCS field is present", HFILL}},
2359
2360                 {&hf_radiotap_present_ampdu,
2361                  {"A-MPDU Status", "radiotap.present.ampdu",
2362                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(AMPDU_STATUS),
2363                   "Specifies if the A-MPDU status field is present", HFILL}},
2364
2365                 {&hf_radiotap_present_vht,
2366                  {"VHT information", "radiotap.present.vht",
2367                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(VHT),
2368                   "Specifies if the VHT field is present", HFILL}},
2369
2370                 {&hf_radiotap_present_timestamp,
2371                  {"frame timestamp", "radiotap.present.timestamp",
2372                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(TIMESTAMP),
2373                   "Specifies if the timestamp field is present", HFILL}},
2374
2375                 {&hf_radiotap_present_he,
2376                  {"HE information", "radiotap.present.he",
2377                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(HE),
2378                   "Specifies is the HE field is present", HFILL}},
2379
2380                 {&hf_radiotap_present_reserved,
2381                  {"Reserved", "radiotap.present.reserved",
2382                   FT_UINT32, BASE_HEX, NULL, IEEE80211_RADIOTAP_NOTDEFINED,
2383                   "Not (yet) defined present flags (Must be zero)", HFILL}},
2384
2385                 {&hf_radiotap_present_rtap_ns,
2386                  {"Radiotap NS next", "radiotap.present.rtap_ns",
2387                   FT_BOOLEAN, 32, NULL, RADIOTAP_MASK(RADIOTAP_NAMESPACE),
2388                   "Specifies a reset to the radiotap namespace", HFILL}},
2389
2390                 {&hf_radiotap_present_vendor_ns,
2391                  {"Vendor NS next", "radiotap.present.vendor_ns",
2392                   FT_BOOLEAN, 32, NULL, RADIOTAP_MASK(VENDOR_NAMESPACE),
2393                   "Specifies that the next bitmap is in a vendor namespace", HFILL}},
2394
2395                 {&hf_radiotap_present_ext,
2396                  {"Ext", "radiotap.present.ext",
2397                   FT_BOOLEAN, 32, TFS(&tfs_present_absent), RADIOTAP_MASK(EXT),
2398                   "Specifies if there are any extensions to the header present", HFILL}},
2399
2400                 /* Boolean 'present.flags' flags */
2401                 {&hf_radiotap_flags,
2402                  {"Flags", "radiotap.flags",
2403                   FT_UINT8, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2404
2405                 {&hf_radiotap_flags_cfp,
2406                  {"CFP", "radiotap.flags.cfp",
2407                   FT_BOOLEAN, 8, NULL, IEEE80211_RADIOTAP_F_CFP,
2408                   "Sent/Received during CFP", HFILL}},
2409
2410                 {&hf_radiotap_flags_preamble,
2411                  {"Preamble", "radiotap.flags.preamble",
2412                   FT_BOOLEAN, 8, TFS(&preamble_type),
2413                   IEEE80211_RADIOTAP_F_SHORTPRE,
2414                   "Sent/Received with short preamble", HFILL}},
2415
2416                 {&hf_radiotap_flags_wep,
2417                  {"WEP", "radiotap.flags.wep",
2418                   FT_BOOLEAN, 8, NULL, IEEE80211_RADIOTAP_F_WEP,
2419                   "Sent/Received with WEP encryption", HFILL}},
2420
2421                 {&hf_radiotap_flags_frag,
2422                  {"Fragmentation", "radiotap.flags.frag",
2423                   FT_BOOLEAN, 8, NULL, IEEE80211_RADIOTAP_F_FRAG,
2424                   "Sent/Received with fragmentation", HFILL}},
2425
2426                 {&hf_radiotap_flags_fcs,
2427                  {"FCS at end", "radiotap.flags.fcs",
2428                   FT_BOOLEAN, 8, NULL, IEEE80211_RADIOTAP_F_FCS,
2429                   "Frame includes FCS at end", HFILL}},
2430
2431                 {&hf_radiotap_flags_datapad,
2432                  {"Data Pad", "radiotap.flags.datapad",
2433                   FT_BOOLEAN, 8, NULL, IEEE80211_RADIOTAP_F_DATAPAD,
2434                   "Frame has padding between 802.11 header and payload", HFILL}},
2435
2436                 {&hf_radiotap_flags_badfcs,
2437                  {"Bad FCS", "radiotap.flags.badfcs",
2438                   FT_BOOLEAN, 8, NULL, IEEE80211_RADIOTAP_F_BADFCS,
2439                   "Frame received with bad FCS", HFILL}},
2440
2441                 {&hf_radiotap_flags_shortgi,
2442                  {"Short GI", "radiotap.flags.shortgi",
2443                   FT_BOOLEAN, 8, NULL, IEEE80211_RADIOTAP_F_SHORTGI,
2444                   "Frame Sent/Received with HT short Guard Interval", HFILL}},
2445
2446                 {&hf_radiotap_mactime,
2447                  {"MAC timestamp", "radiotap.mactime",
2448                   FT_UINT64, BASE_DEC, NULL, 0x0,
2449                   "Value in microseconds of the MAC's Time Synchronization Function timer"
2450                   " when the first bit of the MPDU arrived at the MAC.",
2451                   HFILL}},
2452
2453                 {&hf_radiotap_quality,
2454                  {"Signal Quality", "radiotap.quality",
2455                   FT_UINT16, BASE_DEC, NULL, 0x0,
2456                   "Signal quality (unitless measure)", HFILL}},
2457
2458                 {&hf_radiotap_fcs,
2459                  {"802.11 FCS", "radiotap.fcs",
2460                   FT_UINT32, BASE_HEX, NULL, 0x0,
2461                   "Frame check sequence of this frame", HFILL}},
2462
2463 #if 0
2464                 {&hf_radiotap_channel,
2465                  {"Channel", "radiotap.channel",
2466                   FT_UINT32, BASE_DEC, NULL, 0x0,
2467                   "802.11 channel number that this frame was sent/received on", HFILL}},
2468 #endif
2469
2470                 {&hf_radiotap_channel_frequency,
2471                  {"Channel frequency", "radiotap.channel.freq",
2472                   FT_UINT32, BASE_DEC, NULL, 0x0,
2473                   "Channel frequency in megahertz that this frame was sent/received on", HFILL}},
2474
2475                 {&hf_radiotap_channel_flags,
2476                  {"Channel flags", "radiotap.channel.flags",
2477                   FT_UINT16, BASE_HEX, NULL, 0x0,
2478                   NULL, HFILL}},
2479
2480                 {&hf_radiotap_channel_flags_turbo,
2481                  {"Turbo", "radiotap.channel.flags.turbo",
2482                   FT_BOOLEAN, 16, NULL, 0x0010, "Channel Flags Turbo", HFILL}},
2483
2484                 {&hf_radiotap_channel_flags_cck,
2485                  {"Complementary Code Keying (CCK)", "radiotap.channel.flags.cck",
2486                   FT_BOOLEAN, 16, NULL, 0x0020,
2487                   "Channel Flags Complementary Code Keying (CCK) Modulation", HFILL}},
2488
2489                 {&hf_radiotap_channel_flags_ofdm,
2490                  {"Orthogonal Frequency-Division Multiplexing (OFDM)", "radiotap.channel.flags.ofdm",
2491                   FT_BOOLEAN, 16, NULL, 0x0040,
2492                   "Channel Flags Orthogonal Frequency-Division Multiplexing (OFDM)", HFILL}},
2493
2494                 {&hf_radiotap_channel_flags_2ghz,
2495                  {"2 GHz spectrum", "radiotap.channel.flags.2ghz",
2496                   FT_BOOLEAN, 16, NULL, 0x0080, "Channel Flags 2 GHz spectrum", HFILL}},
2497
2498                 {&hf_radiotap_channel_flags_5ghz,
2499                  {"5 GHz spectrum", "radiotap.channel.flags.5ghz",
2500                   FT_BOOLEAN, 16, NULL, 0x0100, "Channel Flags 5 GHz spectrum", HFILL}},
2501
2502                 {&hf_radiotap_channel_flags_passive,
2503                  {"Passive", "radiotap.channel.flags.passive",
2504                   FT_BOOLEAN, 16, NULL, 0x0200,
2505                   "Channel Flags Passive", HFILL}},
2506
2507                 {&hf_radiotap_channel_flags_dynamic,
2508                  {"Dynamic CCK-OFDM", "radiotap.channel.flags.dynamic",
2509                   FT_BOOLEAN, 16, NULL, 0x0400,
2510                   "Channel Flags Dynamic CCK-OFDM Channel", HFILL}},
2511
2512                 {&hf_radiotap_channel_flags_gfsk,
2513                  {"Gaussian Frequency Shift Keying (GFSK)", "radiotap.channel.flags.gfsk",
2514                   FT_BOOLEAN, 16, NULL, 0x0800,
2515                   "Channel Flags Gaussian Frequency Shift Keying (GFSK) Modulation", HFILL}},
2516
2517                 {&hf_radiotap_channel_flags_gsm,
2518                  {"GSM (900MHz)", "radiotap.channel.flags.gsm",
2519                   FT_BOOLEAN, 16, NULL, 0x1000,
2520                   "Channel Flags GSM", HFILL}},
2521
2522                 {&hf_radiotap_channel_flags_sturbo,
2523                  {"Static Turbo", "radiotap.channel.flags.sturbo",
2524                   FT_BOOLEAN, 16, NULL, 0x2000,
2525                   "Channel Flags Status Turbo", HFILL}},
2526
2527                 {&hf_radiotap_channel_flags_half,
2528                  {"Half Rate Channel (10MHz Channel Width)", "radiotap.channel.flags.half",
2529                   FT_BOOLEAN, 16, NULL, 0x4000,
2530                   "Channel Flags Half Rate", HFILL}},
2531
2532                 {&hf_radiotap_channel_flags_quarter,
2533                  {"Quarter Rate Channel (5MHz Channel Width)", "radiotap.channel.flags.quarter",
2534                   FT_BOOLEAN, 16, NULL, 0x8000,
2535                   "Channel Flags Quarter Rate", HFILL}},
2536
2537                 {&hf_radiotap_rxflags,
2538                  {"RX flags", "radiotap.rxflags",
2539                   FT_UINT16, BASE_HEX, NULL, 0x0,
2540                   NULL, HFILL}},
2541
2542                 {&hf_radiotap_rxflags_badplcp,
2543                  {"Bad PLCP", "radiotap.rxflags.badplcp",
2544                   FT_BOOLEAN, 24, NULL, IEEE80211_RADIOTAP_F_RX_BADPLCP,
2545                   "Frame with bad PLCP", HFILL}},
2546
2547                 {&hf_radiotap_xchannel_channel,
2548                  {"Channel number", "radiotap.xchannel.channel",
2549                   FT_UINT32, BASE_DEC, NULL, 0x0,
2550                   NULL, HFILL}},
2551
2552                 {&hf_radiotap_xchannel_frequency,
2553                  {"Channel frequency", "radiotap.xchannel.freq",
2554                   FT_UINT32, BASE_DEC, NULL, 0x0,
2555                   NULL, HFILL}},
2556
2557                 {&hf_radiotap_xchannel_flags,
2558                  {"Channel flags", "radiotap.xchannel.flags",
2559                   FT_UINT32, BASE_HEX, NULL, 0x0,
2560                   NULL, HFILL}},
2561
2562                 {&hf_radiotap_xchannel_flags_turbo,
2563                  {"Turbo", "radiotap.xchannel.flags.turbo",
2564                   FT_BOOLEAN, 24, NULL, 0x0010,
2565                   "Channel Flags Turbo", HFILL}},
2566
2567                 {&hf_radiotap_xchannel_flags_cck,
2568                  {"Complementary Code Keying (CCK)", "radiotap.xchannel.flags.cck",
2569                   FT_BOOLEAN, 24, NULL, 0x0020,
2570                   "Channel Flags Complementary Code Keying (CCK) Modulation", HFILL}},
2571
2572                 {&hf_radiotap_xchannel_flags_ofdm,
2573                  {"Orthogonal Frequency-Division Multiplexing (OFDM)", "radiotap.xchannel.flags.ofdm",
2574                   FT_BOOLEAN, 24, NULL, 0x0040,
2575                   "Channel Flags Orthogonal Frequency-Division Multiplexing (OFDM)", HFILL}},
2576
2577                 {&hf_radiotap_xchannel_flags_2ghz,
2578                  {"2 GHz spectrum", "radiotap.xchannel.flags.2ghz",
2579                   FT_BOOLEAN, 24, NULL, 0x0080,
2580                   "Channel Flags 2 GHz spectrum", HFILL}},
2581
2582                 {&hf_radiotap_xchannel_flags_5ghz,
2583                  {"5 GHz spectrum", "radiotap.xchannel.flags.5ghz",
2584                   FT_BOOLEAN, 24, NULL, 0x0100,
2585                   "Channel Flags 5 GHz spectrum", HFILL}},
2586
2587                 {&hf_radiotap_xchannel_flags_passive,
2588                  {"Passive", "radiotap.channel.xtype.passive",
2589                   FT_BOOLEAN, 24, NULL, 0x0200,
2590                   "Channel Flags Passive", HFILL}},
2591
2592                 {&hf_radiotap_xchannel_flags_dynamic,
2593                  {"Dynamic CCK-OFDM", "radiotap.xchannel.flags.dynamic",
2594                   FT_BOOLEAN, 24, NULL, 0x0400,
2595                   "Channel Flags Dynamic CCK-OFDM Channel", HFILL}},
2596
2597                 {&hf_radiotap_xchannel_flags_gfsk,
2598                  {"Gaussian Frequency Shift Keying (GFSK)",
2599                   "radiotap.xchannel.flags.gfsk",
2600                   FT_BOOLEAN, 24, NULL, 0x0800,
2601                   "Channel Flags Gaussian Frequency Shift Keying (GFSK) Modulation",
2602                   HFILL}},
2603
2604                 {&hf_radiotap_xchannel_flags_gsm,
2605                  {"GSM (900MHz)", "radiotap.xchannel.flags.gsm",
2606                   FT_BOOLEAN, 24, NULL, 0x1000,
2607                   "Channel Flags GSM", HFILL}},
2608
2609                 {&hf_radiotap_xchannel_flags_sturbo,
2610                  {"Static Turbo", "radiotap.xchannel.flags.sturbo",
2611                   FT_BOOLEAN, 24, NULL, 0x2000,
2612                   "Channel Flags Status Turbo", HFILL}},
2613
2614                 {&hf_radiotap_xchannel_flags_half,
2615                  {"Half Rate Channel (10MHz Channel Width)", "radiotap.xchannel.flags.half",
2616                   FT_BOOLEAN, 24, NULL, 0x4000,
2617                   "Channel Flags Half Rate", HFILL}},
2618
2619                 {&hf_radiotap_xchannel_flags_quarter,
2620                  {"Quarter Rate Channel (5MHz Channel Width)", "radiotap.xchannel.flags.quarter",
2621                   FT_BOOLEAN, 24, NULL, 0x8000,
2622                   "Channel Flags Quarter Rate", HFILL}},
2623
2624                 {&hf_radiotap_xchannel_flags_ht20,
2625                  {"HT Channel (20MHz Channel Width)", "radiotap.xchannel.flags.ht20",
2626                   FT_BOOLEAN, 24, NULL, 0x10000,
2627                   "Channel Flags HT/20", HFILL}},
2628
2629                 {&hf_radiotap_xchannel_flags_ht40u,
2630                  {"HT Channel (40MHz Channel Width with Extension channel above)", "radiotap.xchannel.flags.ht40u",
2631                   FT_BOOLEAN, 24, NULL, 0x20000,
2632                   "Channel Flags HT/40+", HFILL}},
2633
2634                 {&hf_radiotap_xchannel_flags_ht40d,
2635                  {"HT Channel (40MHz Channel Width with Extension channel below)", "radiotap.xchannel.flags.ht40d",
2636                   FT_BOOLEAN, 24, NULL, 0x40000,
2637                   "Channel Flags HT/40-", HFILL}},
2638 #if 0
2639                 {&hf_radiotap_xchannel_maxpower,
2640                  {"Max transmit power", "radiotap.xchannel.maxpower",
2641                   FT_UINT32, BASE_DEC, NULL, 0x0,
2642                   NULL, HFILL}},
2643 #endif
2644                 {&hf_radiotap_fhss_hopset,
2645                  {"FHSS Hop Set", "radiotap.fhss.hopset",
2646                   FT_UINT8, BASE_DEC, NULL, 0x0,
2647                   "Frequency Hopping Spread Spectrum hopset", HFILL}},
2648
2649                 {&hf_radiotap_fhss_pattern,
2650                  {"FHSS Pattern", "radiotap.fhss.pattern",
2651                   FT_UINT8, BASE_DEC, NULL, 0x0,
2652                   "Frequency Hopping Spread Spectrum hop pattern", HFILL}},
2653
2654                 {&hf_radiotap_datarate,
2655                  {"Data rate (Mb/s)", "radiotap.datarate",
2656                   FT_FLOAT, BASE_NONE, NULL, 0x0,
2657                   "Speed this frame was sent/received at", HFILL}},
2658
2659                 {&hf_radiotap_antenna,
2660                  {"Antenna", "radiotap.antenna",
2661                   FT_UINT32, BASE_DEC, NULL, 0x0,
2662                   "Antenna number this frame was sent/received over (starting at 0)", HFILL}},
2663
2664                 {&hf_radiotap_dbm_antsignal,
2665                  {"SSI Signal", "radiotap.dbm_antsignal",
2666                   FT_INT32, BASE_DEC|BASE_UNIT_STRING, &units_dbm, 0x0,
2667                   "RF signal power at the antenna from a fixed,"
2668                   " arbitrary value in decibels from one milliwatt", HFILL}},
2669
2670                 {&hf_radiotap_db_antsignal,
2671                  {"SSI Signal", "radiotap.db_antsignal",
2672                   FT_UINT32, BASE_DEC|BASE_UNIT_STRING, &units_decibels, 0x0,
2673                   "RF signal power at the antenna from a fixed, arbitrary value in decibels", HFILL}},
2674
2675                 {&hf_radiotap_dbm_antnoise,
2676                  {"SSI Noise", "radiotap.dbm_antnoise",
2677                   FT_INT32, BASE_DEC|BASE_UNIT_STRING, &units_dbm, 0x0,
2678                   "RF noise power at the antenna from a fixed, arbitrary value"
2679                   " in decibels per one milliwatt", HFILL}},
2680
2681                 {&hf_radiotap_db_antnoise,
2682                  {"SSI Noise", "radiotap.db_antnoise",
2683                   FT_UINT32, BASE_DEC|BASE_UNIT_STRING, &units_decibels, 0x0,
2684                   "RF noise power at the antenna from a fixed, arbitrary value"
2685                   " in decibels", HFILL}},
2686
2687                 {&hf_radiotap_tx_attenuation,
2688                  {"Transmit attenuation", "radiotap.txattenuation",
2689                   FT_UINT16, BASE_DEC, NULL, 0x0,
2690                   "Transmit power expressed as unitless distance from max power"
2691                   " set at factory (0 is max power)", HFILL}},
2692
2693                 {&hf_radiotap_db_tx_attenuation,
2694                  {"Transmit attenuation (dB)", "radiotap.db_txattenuation",
2695                   FT_UINT16, BASE_DEC, NULL, 0x0,
2696                   "Transmit power expressed as decibels from max power"
2697                   " set at factory (0 is max power)", HFILL}},
2698
2699                 {&hf_radiotap_txpower,
2700                  {"Transmit power", "radiotap.txpower",
2701                   FT_INT32, BASE_DEC, NULL, 0x0,
2702                   "Transmit power in decibels per one milliwatt (dBm)", HFILL}},
2703
2704                 {&hf_radiotap_mcs,
2705                  {"MCS information", "radiotap.mcs",
2706                   FT_NONE, BASE_NONE, NULL, 0x0,
2707                   NULL, HFILL}},
2708
2709                 {&hf_radiotap_mcs_known,
2710                  {"Known MCS information", "radiotap.mcs.known",
2711                   FT_UINT8, BASE_HEX, NULL, 0x0,
2712                   "Bit mask indicating what MCS information is present", HFILL}},
2713
2714                 {&hf_radiotap_mcs_have_bw,
2715                  {"Bandwidth", "radiotap.mcs.have_bw",
2716                   FT_BOOLEAN, 8, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_MCS_HAVE_BW,
2717                   "Bandwidth information present", HFILL}},
2718
2719                 {&hf_radiotap_mcs_have_index,
2720                  {"MCS index", "radiotap.mcs.have_index",
2721                   FT_BOOLEAN, 8, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_MCS_HAVE_MCS,
2722                   "MCS index information present", HFILL}},
2723
2724                 {&hf_radiotap_mcs_have_gi,
2725                  {"Guard interval", "radiotap.mcs.have_gi",
2726                   FT_BOOLEAN, 8, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_MCS_HAVE_GI,
2727                   "Sent/Received guard interval information present", HFILL}},
2728
2729                 {&hf_radiotap_mcs_have_format,
2730                  {"Format", "radiotap.mcs.have_format",
2731                   FT_BOOLEAN, 8, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_MCS_HAVE_FMT,
2732                   "Format information present", HFILL}},
2733
2734                 {&hf_radiotap_mcs_have_fec,
2735                  {"FEC type", "radiotap.mcs.have_fec",
2736                   FT_BOOLEAN, 8, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_MCS_HAVE_FEC,
2737                   "Forward error correction type information present", HFILL}},
2738
2739                 {&hf_radiotap_mcs_have_stbc,
2740                  {"STBC streams", "radiotap.mcs.have_stbc",
2741                   FT_BOOLEAN, 8, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_MCS_HAVE_STBC,
2742                   "Space Time Block Coding streams information present", HFILL}},
2743
2744                 {&hf_radiotap_mcs_have_ness,
2745                  {"Number of extension spatial streams", "radiotap.mcs.have_ness",
2746                   FT_BOOLEAN, 8, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_MCS_HAVE_NESS,
2747                   "Number of extension spatial streams information present", HFILL}},
2748
2749                 {&hf_radiotap_mcs_ness_bit1,
2750                  {"Number of extension spatial streams bit 1", "radiotap.mcs.ness_bit1",
2751                   FT_UINT8, BASE_DEC, NULL, IEEE80211_RADIOTAP_MCS_NESS_BIT1,
2752                   "Bit 1 of number of extension spatial streams information", HFILL}},
2753
2754                 {&hf_radiotap_mcs_bw,
2755                  {"Bandwidth", "radiotap.mcs.bw",
2756                   FT_UINT8, BASE_DEC, VALS(mcs_bandwidth),
2757                   IEEE80211_RADIOTAP_MCS_BW_MASK, NULL, HFILL}},
2758
2759                 {&hf_radiotap_mcs_gi,
2760                  {"Guard interval", "radiotap.mcs.gi",
2761                   FT_UINT8, BASE_DEC, VALS(mcs_gi), IEEE80211_RADIOTAP_MCS_SGI,
2762                   "Sent/Received guard interval", HFILL}},
2763
2764                 {&hf_radiotap_mcs_format,
2765                  {"Format", "radiotap.mcs.format",
2766                   FT_UINT8, BASE_DEC, VALS(mcs_format), IEEE80211_RADIOTAP_MCS_FMT_GF,
2767                   NULL, HFILL}},
2768
2769                 {&hf_radiotap_mcs_fec,
2770                  {"FEC type", "radiotap.mcs.fec",
2771                   FT_UINT8, BASE_DEC, VALS(mcs_fec), IEEE80211_RADIOTAP_MCS_FEC_LDPC,
2772                   "Forward error correction type", HFILL}},
2773
2774                 {&hf_radiotap_mcs_stbc,
2775                  {"STBC streams", "radiotap.mcs.stbc",
2776                   FT_UINT8, BASE_DEC, NULL, IEEE80211_RADIOTAP_MCS_STBC_MASK,
2777                   "Number of Space Time Block Code streams", HFILL}},
2778
2779                 {&hf_radiotap_mcs_ness_bit0,
2780                  {"Number of extension spatial streams bit 0", "radiotap.mcs.ness_bit1",
2781                   FT_UINT8, BASE_DEC, NULL, IEEE80211_RADIOTAP_MCS_NESS_BIT1,
2782                   "Bit 0 of number of extension spatial streams information", HFILL}},
2783
2784                 {&hf_radiotap_mcs_index,
2785                  {"MCS index", "radiotap.mcs.index",
2786                   FT_UINT8, BASE_DEC, NULL, 0x0,
2787                   NULL, HFILL}},
2788
2789                 {&hf_radiotap_ampdu,
2790                  {"A-MPDU status", "radiotap.ampdu",
2791                   FT_NONE, BASE_NONE, NULL, 0x0,
2792                   NULL, HFILL}},
2793
2794                 {&hf_radiotap_ampdu_ref,
2795                  {"A-MPDU reference number", "radiotap.ampdu.reference",
2796                   FT_UINT32, BASE_DEC, NULL, 0x0,
2797                   NULL, HFILL}},
2798
2799                 {&hf_radiotap_ampdu_flags,
2800                  {"A-MPDU flags", "radiotap.ampdu.flags",
2801                   FT_UINT16, BASE_HEX, NULL, 0x0,
2802                   "A-MPDU status flags", HFILL}},
2803
2804                 {&hf_radiotap_ampdu_flags_report_zerolen,
2805                  {"Driver reports 0-length subframes in this A-MPDU", "radiotap.ampdu.flags.report_zerolen",
2806                   FT_BOOLEAN, 16, NULL, IEEE80211_RADIOTAP_AMPDU_REPORT_ZEROLEN,
2807                   NULL, HFILL}},
2808
2809                 {&hf_radiotap_ampdu_flags_is_zerolen,
2810                  {"This is a 0-length subframe", "radiotap.ampdu.flags.is_zerolen",
2811                   FT_BOOLEAN, 16, NULL, IEEE80211_RADIOTAP_AMPDU_IS_ZEROLEN,
2812                   NULL, HFILL}},
2813
2814                 {&hf_radiotap_ampdu_flags_last_known,
2815                  {"Last subframe of this A-MPDU is known", "radiotap.ampdu.flags.lastknown",
2816                   FT_BOOLEAN, 16, NULL, IEEE80211_RADIOTAP_AMPDU_LAST_KNOWN,
2817                   NULL, HFILL}},
2818
2819                 {&hf_radiotap_ampdu_flags_is_last,
2820                  {"This is the last subframe of this A-MPDU", "radiotap.ampdu.flags.last",
2821                   FT_BOOLEAN, 16, NULL, IEEE80211_RADIOTAP_AMPDU_IS_LAST,
2822                   NULL, HFILL}},
2823
2824                 {&hf_radiotap_ampdu_flags_delim_crc_error,
2825                  {"Delimiter CRC error on this subframe", "radiotap.ampdu.flags.delim_crc_error",
2826                   FT_BOOLEAN, 16, NULL, IEEE80211_RADIOTAP_AMPDU_DELIM_CRC_ERR,
2827                   NULL, HFILL}},
2828
2829                 {&hf_radiotap_ampdu_delim_crc,
2830                  {"A-MPDU subframe delimiter CRC", "radiotap.ampdu.delim_crc",
2831                   FT_UINT8, BASE_HEX, NULL, 0x0,
2832                   NULL, HFILL}},
2833
2834                 {&hf_radiotap_vht,
2835                  {"VHT information", "radiotap.vht",
2836                   FT_NONE, BASE_NONE, NULL, 0x0,
2837                   NULL, HFILL}},
2838
2839                 {&hf_radiotap_vht_known,
2840                  {"Known VHT information", "radiotap.vht.known",
2841                   FT_UINT8, BASE_HEX, NULL, 0x0,
2842                   "Bit mask indicating what VHT information is present", HFILL}},
2843
2844                 {&hf_radiotap_vht_user,
2845                  {"User", "radiotap.vht.user",
2846                   FT_NONE, BASE_NONE, NULL, 0x0,
2847                   NULL, HFILL}},
2848
2849                 {&hf_radiotap_vht_have_stbc,
2850                  {"STBC", "radiotap.vht.have_stbc",
2851                   FT_BOOLEAN, 16, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_VHT_HAVE_STBC,
2852                   "Space Time Block Coding information present", HFILL}},
2853
2854                 {&hf_radiotap_vht_have_txop_ps,
2855                  {"TXOP_PS_NOT_ALLOWED", "radiotap.vht.have_txop_ps",
2856                   FT_BOOLEAN, 16, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_VHT_HAVE_TXOP_PS,
2857                   "TXOP_PS_NOT_ALLOWED information present", HFILL}},
2858
2859                 {&hf_radiotap_vht_have_gi,
2860                  {"Guard interval", "radiotap.vht.have_gi",
2861                   FT_BOOLEAN, 16, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_VHT_HAVE_GI,
2862                   "Short/Long guard interval information present", HFILL}},
2863
2864                 {&hf_radiotap_vht_have_sgi_nsym_da,
2865                  {"SGI Nsym disambiguation", "radiotap.vht.have_sgi_nsym_da",
2866                   FT_BOOLEAN, 16, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_VHT_HAVE_SGI_NSYM_DA,
2867                   "Short guard interval Nsym disambiguation information present", HFILL}},
2868
2869                 {&hf_radiotap_vht_have_ldpc_extra,
2870                  {"LDPC extra OFDM symbol", "radiotap.vht.ldpc_extra",
2871                   FT_BOOLEAN, 16, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_VHT_HAVE_LDPC_EXTRA,
2872                   NULL, HFILL}},
2873
2874                 {&hf_radiotap_vht_have_bf,
2875                  {"Beamformed", "radiotap.vht.have_beamformed",
2876                   FT_BOOLEAN, 16, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_VHT_HAVE_BF,
2877                   NULL, HFILL}},
2878
2879                 {&hf_radiotap_vht_have_bw,
2880                  {"Bandwidth", "radiotap.mcs.have_bw",
2881                   FT_BOOLEAN, 16, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_VHT_HAVE_BW,
2882                   NULL, HFILL}},
2883
2884                 {&hf_radiotap_vht_have_gid,
2885                  {"Group ID", "radiotap.mcs.have_gid",
2886                   FT_BOOLEAN, 16, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_VHT_HAVE_GID,
2887                   NULL, HFILL}},
2888
2889                 {&hf_radiotap_vht_have_p_aid,
2890                  {"Partial AID", "radiotap.mcs.have_paid",
2891                   FT_BOOLEAN, 16, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_VHT_HAVE_PAID,
2892                   NULL, HFILL}},
2893
2894                 {&hf_radiotap_vht_stbc,
2895                  {"STBC", "radiotap.vht.stbc",
2896                   FT_BOOLEAN, 8, TFS(&tfs_on_off), IEEE80211_RADIOTAP_VHT_STBC,
2897                   "Space Time Block Coding flag", HFILL}},
2898
2899                 {&hf_radiotap_vht_txop_ps,
2900                  {"TXOP_PS_NOT_ALLOWED", "radiotap.vht.txop_ps",
2901                   FT_BOOLEAN, 8, NULL, IEEE80211_RADIOTAP_VHT_TXOP_PS,
2902                   "Flag indicating whether STAs may doze during TXOP", HFILL}},
2903
2904                 {&hf_radiotap_vht_gi,
2905                  {"Guard interval", "radiotap.vht.gi",
2906                   FT_UINT8, BASE_DEC, VALS(mcs_gi), IEEE80211_RADIOTAP_VHT_SGI,
2907                   "Short/Long guard interval", HFILL}},
2908
2909                 {&hf_radiotap_vht_sgi_nsym_da,
2910                  {"SGI Nsym disambiguation", "radiotap.vht.sgi_nsym_da",
2911                   FT_BOOLEAN, 8, NULL, IEEE80211_RADIOTAP_VHT_SGI_NSYM_DA,
2912                   "Short Guard Interval Nsym disambiguation", HFILL}},
2913
2914                 {&hf_radiotap_vht_ldpc_extra,
2915                  {"LDPC extra OFDM symbol", "radiotap.vht.ldpc_extra",
2916                   FT_BOOLEAN, 8, NULL, IEEE80211_RADIOTAP_VHT_LDPC_EXTRA,
2917                   NULL, HFILL}},
2918
2919                 {&hf_radiotap_vht_bf,
2920                  {"Beamformed", "radiotap.vht.beamformed",
2921                   FT_BOOLEAN, 8, NULL, IEEE80211_RADIOTAP_VHT_BF,
2922                   NULL, HFILL}},
2923
2924                 {&hf_radiotap_vht_bw,
2925                  {"Bandwidth", "radiotap.vht.bw",
2926                   FT_UINT8, BASE_DEC | BASE_EXT_STRING, &vht_bandwidth_ext, 0x0,
2927                   NULL, HFILL}},
2928
2929                 {&hf_radiotap_vht_nsts[0],
2930                  {"Space-time streams 0", "radiotap.vht.nsts.0",
2931                   FT_UINT8, BASE_DEC, NULL, 0x0,
2932                   "Number of Space-time streams", HFILL}},
2933
2934                 {&hf_radiotap_vht_nsts[1],
2935                  {"Space-time streams 1", "radiotap.vht.nsts.1",
2936                   FT_UINT8, BASE_DEC, NULL, 0x0,
2937                   "Number of Space-time streams", HFILL}},
2938
2939                 {&hf_radiotap_vht_nsts[2],
2940                  {"Space-time streams 2", "radiotap.vht.nsts.2",
2941                   FT_UINT8, BASE_DEC, NULL, 0x0,
2942                   "Number of Space-time streams", HFILL}},
2943
2944                 {&hf_radiotap_vht_nsts[3],
2945                  {"Space-time streams 3", "radiotap.vht.nsts.3",
2946                   FT_UINT8, BASE_DEC, NULL, 0x0,
2947                   "Number of Space-time streams", HFILL}},
2948
2949                 {&hf_radiotap_vht_mcs[0],
2950                  {"MCS index 0", "radiotap.vht.mcs.0",
2951                   FT_UINT8, BASE_DEC, NULL, IEEE80211_RADIOTAP_VHT_MCS,
2952                   "MCS index", HFILL}},
2953
2954                 {&hf_radiotap_vht_mcs[1],
2955                  {"MCS index 1", "radiotap.vht.mcs.1",
2956                   FT_UINT8, BASE_DEC, NULL, IEEE80211_RADIOTAP_VHT_MCS,
2957                   "MCS index", HFILL}},
2958
2959                 {&hf_radiotap_vht_mcs[2],
2960                  {"MCS index 2", "radiotap.vht.mcs.2",
2961                   FT_UINT8, BASE_DEC, NULL, IEEE80211_RADIOTAP_VHT_MCS,
2962                   "MCS index", HFILL}},
2963
2964                 {&hf_radiotap_vht_mcs[3],
2965                  {"MCS index 3", "radiotap.vht.mcs.3",
2966                   FT_UINT8, BASE_DEC, NULL, IEEE80211_RADIOTAP_VHT_MCS,
2967                   "MCS index", HFILL}},
2968
2969                 {&hf_radiotap_vht_nss[0],
2970                  {"Spatial streams 0", "radiotap.vht.nss.0",
2971                   FT_UINT8, BASE_DEC, NULL, IEEE80211_RADIOTAP_VHT_NSS,
2972                   "Number of spatial streams", HFILL}},
2973
2974                 {&hf_radiotap_vht_nss[1],
2975                  {"Spatial streams 1", "radiotap.vht.nss.1",
2976                   FT_UINT8, BASE_DEC, NULL, IEEE80211_RADIOTAP_VHT_NSS,
2977                   "Number of spatial streams", HFILL}},
2978
2979                 {&hf_radiotap_vht_nss[2],
2980                  {"Spatial streams 2", "radiotap.vht.nss.2",
2981                   FT_UINT8, BASE_DEC, NULL, IEEE80211_RADIOTAP_VHT_NSS,
2982                   "Number of spatial streams", HFILL}},
2983
2984                 {&hf_radiotap_vht_nss[3],
2985                  {"Spatial streams 3", "radiotap.vht.nss.3",
2986                   FT_UINT8, BASE_DEC, NULL, IEEE80211_RADIOTAP_VHT_NSS,
2987                   "Number of spatial streams", HFILL}},
2988
2989                 {&hf_radiotap_vht_coding[0],
2990                  {"Coding 0", "radiotap.vht.coding.0",
2991                   FT_UINT8, BASE_DEC, VALS(mcs_fec), 0x01,
2992                   "Coding", HFILL}},
2993
2994                 {&hf_radiotap_vht_coding[1],
2995                  {"Coding 1", "radiotap.vht.coding.1",
2996                   FT_UINT8, BASE_DEC, VALS(mcs_fec), 0x02,
2997                   "Coding", HFILL}},
2998
2999                 {&hf_radiotap_vht_coding[2],
3000                  {"Coding 2", "radiotap.vht.coding.2",
3001                   FT_UINT8, BASE_DEC, VALS(mcs_fec), 0x04,
3002                   "Coding", HFILL}},
3003
3004                 {&hf_radiotap_vht_coding[3],
3005                  {"Coding 3", "radiotap.vht.coding.3",
3006                   FT_UINT8, BASE_DEC, VALS(mcs_fec), 0x08,
3007                   "Coding", HFILL}},
3008
3009                 {&hf_radiotap_vht_datarate[0],
3010                  {"Data rate (Mb/s) 0", "radiotap.vht.datarate.0",
3011                   FT_FLOAT, BASE_NONE, NULL, 0x0,
3012                   "Speed this frame was sent/received at", HFILL}},
3013
3014                 {&hf_radiotap_vht_datarate[1],
3015                  {"Data rate (Mb/s) 1", "radiotap.vht.datarate.1",
3016                   FT_FLOAT, BASE_NONE, NULL, 0x0,
3017                   "Speed this frame was sent/received at", HFILL}},
3018
3019                 {&hf_radiotap_vht_datarate[2],
3020                  {"Data rate (Mb/s) 2", "radiotap.vht.datarate.2",
3021                   FT_FLOAT, BASE_NONE, NULL, 0x0,
3022                   "Speed this frame was sent/received at", HFILL}},
3023
3024                 {&hf_radiotap_vht_datarate[3],
3025                  {"Data rate (Mb/s) 3", "radiotap.vht.datarate.3",
3026                   FT_FLOAT, BASE_NONE, NULL, 0x0,
3027                   "Speed this frame was sent/received at", HFILL}},
3028
3029                 {&hf_radiotap_vht_gid,
3030                  {"Group Id", "radiotap.vht.gid",
3031                   FT_UINT8, BASE_DEC, NULL, 0x0,
3032                   NULL, HFILL}},
3033
3034                 {&hf_radiotap_vht_p_aid,
3035                  {"Partial AID", "radiotap.vht.paid",
3036                   FT_UINT16, BASE_DEC, NULL, 0x0,
3037                   NULL, HFILL}},
3038
3039                 {&hf_radiotap_timestamp,
3040                  {"timestamp information", "radiotap.timestamp",
3041                   FT_NONE, BASE_NONE, NULL, 0x0,
3042                   NULL, HFILL}},
3043
3044                 {&hf_radiotap_timestamp_ts,
3045                  {"timestamp", "radiotap.timestamp.ts",
3046                   FT_UINT64, BASE_DEC, NULL, 0x0,
3047                   NULL, HFILL}},
3048
3049                 {&hf_radiotap_timestamp_accuracy,
3050                  {"accuracy", "radiotap.timestamp.accuracy",
3051                   FT_UINT16, BASE_DEC, NULL, 0x0,
3052                   NULL, HFILL}},
3053
3054                 {&hf_radiotap_timestamp_unit,
3055                  {"time unit", "radiotap.timestamp.unit",
3056                   FT_UINT8, BASE_DEC, VALS(timestamp_unit),
3057                   IEEE80211_RADIOTAP_TS_UNIT_MASK,
3058                   NULL, HFILL}},
3059
3060                 {&hf_radiotap_timestamp_spos,
3061                  {"sampling position", "radiotap.timestamp.samplingpos",
3062                   FT_UINT8, BASE_DEC, VALS(timestamp_spos),
3063                   IEEE80211_RADIOTAP_TS_SPOS_MASK,
3064                   NULL, HFILL}},
3065
3066                 {&hf_radiotap_timestamp_flags_32bit,
3067                  {"32-bit counter", "radiotap.timestamp.flags.32bit",
3068                   FT_BOOLEAN, 8, TFS(&tfs_yes_no), IEEE80211_RADIOTAP_TS_FLG_32BIT,
3069                   NULL, HFILL}},
3070
3071                 {&hf_radiotap_timestamp_flags_accuracy,
3072                  {"accuracy field", "radiotap.timestamp.flags.accuracy",
3073                   FT_BOOLEAN, 8, TFS(&tfs_present_absent), IEEE80211_RADIOTAP_TS_FLG_ACCURACY,
3074                   NULL, HFILL}},
3075
3076                 {&hf_radiotap_vendor_ns,
3077                  {"Vendor namespace", "radiotap.vendor_namespace",
3078                   FT_BYTES, BASE_NONE, NULL, 0x0,
3079                   NULL, HFILL}},
3080
3081                 {&hf_radiotap_ven_oui,
3082                  {"Vendor OUI", "radiotap.vendor_oui",
3083                   FT_UINT24, BASE_OUI, NULL, 0x0,
3084                   NULL, HFILL}},
3085
3086                 {&hf_radiotap_ven_subns,
3087                  {"Vendor sub namespace", "radiotap.vendor_subns",
3088                   FT_UINT8, BASE_DEC, NULL, 0x0,
3089                   "Vendor-specified sub namespace", HFILL}},
3090
3091                 {&hf_radiotap_ven_skip,
3092                  {"Vendor data length", "radiotap.vendor_data_len",
3093                   FT_UINT16, BASE_DEC, NULL, 0x0,
3094                   "Length of vendor-specified data", HFILL}},
3095
3096                 {&hf_radiotap_ven_data,
3097                  {"Vendor data", "radiotap.vendor_data",
3098                   FT_NONE, BASE_NONE, NULL, 0x0,
3099                   "Vendor-specified data", HFILL}},
3100
3101                 /* Special variables */
3102                 {&hf_radiotap_fcs_bad,
3103                  {"Bad FCS", "radiotap.fcs_bad",
3104                   FT_BOOLEAN, BASE_NONE, NULL, 0x0,
3105                   "Specifies if this frame has a bad frame check sequence", HFILL}},
3106
3107                 {&hf_radiotap_he_info_data_1,
3108                  {"HE Data 1", "radiotap.he.data_1",
3109                   FT_UINT16, BASE_HEX, NULL, 0x0,
3110                   "Data 1 of the HE Info field", HFILL}},
3111
3112                 {&hf_radiotap_he_ppdu_format,
3113                  {"PPDU Format", "radiotap.he.data_1.ppdu_format",
3114                   FT_UINT16, BASE_HEX, VALS(he_pdu_format_vals),
3115                   IEEE80211_RADIOTAP_HE_PPDU_FORMAT_MASK, NULL, HFILL}},
3116
3117                 {&hf_radiotap_he_bss_color_known,
3118                  {"BSS Color known", "radiotap.he.data_1.bss_color_known",
3119                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3120                   IEEE80211_RADIOTAP_HE_BSS_COLOR_KNOWN, NULL, HFILL}},
3121
3122                 {&hf_radiotap_he_beam_change_known,
3123                  {"Beam Change known", "radiotap.he.data_1.beam_change_known",
3124                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3125                   IEEE80211_RADIOTAP_HE_BEAM_CHANGE_KNOWN, NULL, HFILL}},
3126
3127                 {&hf_radiotap_he_ul_dl_known,
3128                  {"UL/DL known", "radiotap.he.data_1.ul_dl_known",
3129                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3130                   IEEE80211_RADIOTAP_HE_UL_DL_KNOWN, NULL, HFILL}},
3131
3132                 {&hf_radiotap_he_data_mcs_known,
3133                  {"data MCS known", "radiotap.he.data_1.data_mcs_known",
3134                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3135                   IEEE80211_RADIOTAP_HE_DATA_MCS_KNOWN, NULL, HFILL}},
3136
3137                 {&hf_radiotap_he_data_dcm_known,
3138                  {"data DCM known", "radiotap.he.data_1.data_dcm_known",
3139                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3140                   IEEE80211_RADIOTAP_HE_DATA_DCM_KNOWN, NULL, HFILL}},
3141
3142                 {&hf_radiotap_he_coding_known,
3143                  {"Coding known", "radiotap.he.data_1.coding_known",
3144                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3145                   IEEE80211_RADIOTAP_HE_CODING_KNOWN, NULL, HFILL}},
3146
3147                 {&hf_radiotap_he_ldpc_extra_symbol_segment_known,
3148                  {"LDPC extra symbol segment known", "radiotap.he.data_1.ldpc_extra_symbol_segment_known",
3149                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3150                   IEEE80211_RADIOTAP_HE_LDPC_EXTRA_SYMBOL_SEGMENT_KNOWN, NULL, HFILL}},
3151
3152                 {&hf_radiotap_he_stbc_known,
3153                  {"STBC known", "radiotap.he.data_1.stbc_known",
3154                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3155                   IEEE80211_RADIOTAP_HE_STBC_KNOWN, NULL, HFILL}},
3156
3157                 {&hf_radiotap_he_spatial_reuse_1_known,
3158                  {"Spatial Reuse 1 known", "radiotap.he.data_1.spatial_reuse_1_known",
3159                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3160                   IEEE80211_RADIOTAP_HE_SPATIAL_REUSE_KNOWN, NULL, HFILL}},
3161
3162                 {&hf_radiotap_he_spatial_reuse_2_known,
3163                  {"Spatial Reuse 2 known", "radiotap.he.data_1.spatial_reuse_2_known",
3164                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3165                   IEEE80211_RADIOTAP_HE_SPATIAL_REUSE_2_KNOWN, NULL, HFILL}},
3166
3167                 {&hf_radiotap_he_spatial_reuse_3_known,
3168                  {"Spatial Reuse 3 known", "radiotap.he.data_1.spatial_reuse_3_known",
3169                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3170                   IEEE80211_RADIOTAP_HE_SPATIAL_REUSE_3_KNOWN, NULL, HFILL}},
3171
3172                 {&hf_radiotap_he_spatial_reuse_4_known,
3173                  {"Spatial Reuse 4 known", "radiotap.he.data_1.spatial_reuse_4_known",
3174                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3175                   IEEE80211_RADIOTAP_HE_SPATIAL_REUSE_4_KNOWN, NULL, HFILL}},
3176
3177                 {&hf_radiotap_he_data_bw_ru_allocation_known,
3178                  {"dat BW/RU allocation known", "radiotap.he.data_1.data_bw_ru_allocation_known",
3179                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3180                   IEEE80211_RADIOTAP_HE_DATA_BW_RU_ALLOCATION_KNOWN, NULL, HFILL}},
3181
3182                 {&hf_radiotap_he_dopler_known,
3183                  {"Dopler known", "radiotap.he.data_1.dopler_known",
3184                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown),
3185                   IEEE80211_RADIOTAP_HE_DOPLER_KNOWN, NULL, HFILL}},
3186
3187                 {&hf_radiotap_he_info_data_2,
3188                  {"HE Data 2", "radiotap.he.data_2",
3189                   FT_UINT16, BASE_HEX, NULL, 0x0,
3190                   "Data 1 of the HE Info field", HFILL}},
3191
3192                 {&hf_radiotap_he_d2_reserved_b1,
3193                  {"Reserved", "radiotap.he.data_2.reserved_ff00",
3194                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_RESERVED_D2_B1,
3195                   NULL, HFILL}},
3196
3197                 {&hf_radiotap_he_gi_known,
3198                  {"GI known", "radiotap.he.data_2.gi_known",
3199                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown), IEEE80211_RADIOTAP_HE_GI_KNOWN,
3200                   NULL, HFILL}},
3201
3202                 {&hf_radiotap_he_ltf_symbols_known,
3203                  {"LTF symbols known", "radiotap.he.data_2.ltf_symbols_known",
3204                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown), IEEE80211_RADIOTAP_HE_LTF_SYMBOLS_KNOWN,
3205                   NULL, HFILL}},
3206
3207                 {&hf_radiotap_he_pre_fec_padding_factor_known,
3208                  {"Pre-FEC Padding Factor known", "radiotap.he.data_2.pre_fec_padding_factor_known",
3209                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown), IEEE80211_RADIOTAP_HE_PRE_FEC_PADDING_FACTOR_KNOWN,
3210                   NULL, HFILL}},
3211
3212                 {&hf_radiotap_he_txbf_known,
3213                  {"TxBF known", "radiotap.he.data_2.txbf_known",
3214                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown), IEEE80211_RADIOTAP_HE_TXBF_KNOWN,
3215                   NULL, HFILL}},
3216
3217                 {&hf_radiotap_he_pe_disambiguity_known,
3218                  {"PE Disambiguity known", "radiotap.he.data_2.pe_disambiguity_known",
3219                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown), IEEE80211_RADIOTAP_HE_PE_DISAMBIGUITY_KNOWN,
3220                   NULL, HFILL}},
3221
3222                 {&hf_radiotap_he_txop_known,
3223                  {"TXOP known", "radiotap.he.data_2.txop_known",
3224                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown), IEEE80211_RADIOTAP_HE_TXOP_KNOWN,
3225                   NULL, HFILL}},
3226
3227                 {&hf_radiotap_he_midamble_periodicity_known,
3228                  {"midamble periodicity known", "radiotap.he.data_2.midamble_periodicity_known",
3229                   FT_BOOLEAN, 16, TFS(&tfs_known_unknown), IEEE80211_RADIOTAP_HE_MIDAMBLE_PERIODICITY_KNOWN,
3230                   NULL, HFILL}},
3231
3232                 {&hf_radiotap_he_d2_reserved_ff00,
3233                  {"Reserved", "radiotap.he.data_2.reserved_ff00",
3234                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_RESERVED_D2_FF00,
3235                   NULL, HFILL}},
3236
3237                 {&he_radiotap_he_bss_color,
3238                  {"BSS Color", "radiotap.he.data_3.bss_color",
3239                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_BSS_COLOR_MASK,
3240                   NULL, HFILL}},
3241
3242                 {&he_radiotap_he_beam_change,
3243                  {"Beam Change", "radiotap.he.data_3.beam_change",
3244                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_BEAM_CHANGE,
3245                   NULL, HFILL}},
3246
3247                 {&he_radiotap_he_ul_dl,
3248                  {"UL/DL", "radiotap.he.data_3.ul_dl",
3249                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_UL_DL,
3250                   NULL, HFILL}},
3251
3252                 {&he_radiotap_he_data_mcs,
3253                  {"data MCS", "radiotap.he.data_3.data_mcs",
3254                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_DATA_MCS_MASK,
3255                   NULL, HFILL}},
3256
3257                 {&he_radiotap_he_data_dcm,
3258                  {"data DCM", "radiotap.he.data_3.data_dcm",
3259                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_DATA_DCM,
3260                   NULL, HFILL}},
3261
3262                 {&he_radiotap_he_coding,
3263                  {"Coding", "radiotap.he.data_3.coding",
3264                   FT_UINT16, BASE_HEX, VALS(he_coding_vals),
3265                   IEEE80211_RADIOTAP_HE_CODING, NULL, HFILL}},
3266
3267                 {&he_radiotap_he_ldpc_extra_symbol_segment,
3268                  {"LDPC extra symbol segment", "radiotap.he.data_3.ldpc_extra_symbol_segment",
3269                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_LDPC_EXTRA_SYMBOL_SEGMENT,
3270                   NULL, HFILL}},
3271
3272                 {&he_radiotap_he_stbc,
3273                  {"STBC", "radiotap.he.data_3.stbc",
3274                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_STBC,
3275                   NULL, HFILL}},
3276
3277                 {&hf_radiotap_he_info_data_3,
3278                  {"HE Data 3", "radiotap.he.data_3",
3279                   FT_UINT16, BASE_HEX, NULL, 0x0,
3280                   "Data 1 of the HE Info field", HFILL}},
3281
3282                 {&he_radiotap_spatial_reuse,
3283                  {"Spatial Reuse", "radiotap.he.data_4.spatial_reuse",
3284                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_SPATIAL_REUSE_MASK,
3285                   NULL, HFILL}},
3286
3287                 {&he_radiotap_he_su_reserved,
3288                  {"Reserved", "radiotap.he.data_4.reserved_d4_fff0",
3289                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_D4_FFF0,
3290                   NULL, HFILL}},
3291
3292                 {&he_radiotap_spatial_reuse_1,
3293                  {"Spatial Reuse 1", "radiotap.he.data_4.spatial_reuse_1",
3294                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_SPATIAL_REUSE_1_MASK,
3295                   NULL, HFILL}},
3296
3297                 {&he_radiotap_spatial_reuse_2,
3298                  {"Spatial Reuse 2", "radiotap.he.data_4.spatial_reuse_2",
3299                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_SPATIAL_REUSE_2_MASK,
3300                   NULL, HFILL}},
3301
3302                 {&he_radiotap_spatial_reuse_3,
3303                  {"Spatial Reuse 3", "radiotap.he.data_4.spatial_reuse_3",
3304                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_SPATIAL_REUSE_3_MASK,
3305                   NULL, HFILL}},
3306
3307                 {&he_radiotap_spatial_reuse_4,
3308                  {"Spatial Reuse 4", "radiotap.he.data_4.spatial_reuse_4",
3309                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_SPATIAL_REUSE_4_MASK,
3310                   NULL, HFILL}},
3311
3312                 {&he_radiotap_sta_id_user_captured,
3313                  {"STA-ID of user data captured for", "radiotap.he.data_4.sta_id_user",
3314                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_STA_ID_MASK,
3315                   NULL, HFILL}},
3316
3317                 {&he_radiotap_he_mu_reserved,
3318                  {"Reserved", "radiotap.he.data_4.reserved_d4_b15",
3319                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_RESERVED_D4_B15,
3320                   NULL, HFILL}},
3321
3322                 {&hf_radiotap_he_info_data_4,
3323                  {"HE Data 4", "radiotap.he.data_4",
3324                   FT_UINT16, BASE_HEX, NULL, 0x0,
3325                   "Data 1 of the HE Info field", HFILL}},
3326
3327                 {&he_radiotap_data_bandwidth_ru_allocation,
3328                  {"data Bandwidth/RU allocation", "radiotap.he.data_5.data_bw_ru_allocation",
3329                   FT_UINT16, BASE_HEX, VALS(he_data_bw_ru_alloc_vals),
3330                   IEEE80211_RADIOTAP_HE_DATA_BANDWIDTH_RU_ALLOC_MASK, NULL, HFILL}},
3331
3332                 {&he_radiotap_gi,
3333                  {"GI", "radiotap.he.data_5.gi",
3334                  FT_UINT16, BASE_HEX, VALS(he_gi_vals), IEEE80211_RADIOTAP_HE_GI_MASK,
3335                  NULL, HFILL}},
3336
3337                 {&he_radiotap_d5_reserved_00c0,
3338                  {"reserved", "radiotap.he.data_5.reserved_d5_00c0",
3339                  FT_UINT16, BASE_HEX, NULL,
3340                  IEEE80211_RADIOTAP_HE_RESERVED_D5_00C0, NULL, HFILL}},
3341
3342                 {&he_radiotap_ltf_symbols,
3343                  {"LTF symbols", "radiotap.he.ltf_symbols",
3344                   FT_UINT16, BASE_HEX, VALS(he_ltf_symbols_vals),
3345                   IEEE80211_RADIOTAP_HE_LTF_SYMBOLS_MASK, NULL, HFILL}},
3346
3347                 {&he_radiotap_d5_reserved_b11,
3348                  {"reserved", "radiotap.he.data_5.reserved_d5_b11",
3349                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_RESERVED_D5_B11,
3350                   NULL, HFILL}},
3351
3352                 {&he_radiotap_pre_fec_padding_factor,
3353                  {"Pre-FEC Padding Factor", "radiotap.he.pre_fec_padding_factor",
3354                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_PRE_FEC_PADDING_FACTOR_MASK,
3355                  NULL, HFILL}},
3356
3357                 {&he_radiotap_txbf,
3358                  {"TxBF", "radiotap.he.txbf",
3359                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_TXBF,
3360                   NULL, HFILL}},
3361
3362                 {&he_radiotap_pe_disambiguity,
3363                  {"PE Disambiguity", "radiotap.he.pe_disambiguity",
3364                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_PE_DISAMBIGUITY,
3365                   NULL, HFILL}},
3366
3367                 {&hf_radiotap_he_info_data_5,
3368                  {"HE Data 5", "radiotap.he.data_5",
3369                   FT_UINT16, BASE_HEX, NULL, 0x0,
3370                   "Data 1 of the HE Info field", HFILL}},
3371
3372                 {&hf_radiotap_he_nsts,
3373                  {"NSTS", "radiotap.he.data_6.nsts",
3374                   FT_UINT16, BASE_HEX, VALS(he_nsts_vals),IEEE80211_RADIOTAP_HE_NSTS_MASK,
3375                   NULL, HFILL}},
3376
3377                 {&hf_radiotap_he_dopler_value,
3378                  {"Dopler value", "radiotap.he.data_6.dopler_value",
3379                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_DOPLER_VALUE,
3380                   NULL, HFILL}},
3381
3382                 {&hf_radiotap_he_d6_reserved_00e0,
3383                  {"Reserved", "radiotap.he.data_6.reserved_d6_00e0",
3384                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_RESERVED_D6_00E0,
3385                   NULL, HFILL}},
3386
3387                 {&hf_radiotap_he_txop_value,
3388                  {"TXOP value", "radiotap.he.data_6.txop_value",
3389                   FT_UINT16, BASE_HEX, NULL, IEEE80211_RADIOTAP_HE_TXOP_VALUE_MASK,
3390                   NULL, HFILL}},
3391
3392                 {&hf_radiotap_midamble_periodicity,
3393                  {"midamble periodicty", "radiotap.he.data_6.midamble_periodicity",
3394                   FT_UINT16, BASE_HEX, VALS(he_midamble_periodicity_vals),
3395                   IEEE80211_RADIOTAP_HE_MIDAMBLE_PERIODICITY, NULL, HFILL}},
3396
3397                 {&hf_radiotap_he_info_data_6,
3398                  {"HE Data 6", "radiotap.he.data_6",
3399                   FT_UINT16, BASE_HEX, NULL, 0x0,
3400                   "Data 1 of the HE Info field", HFILL}},
3401
3402         };
3403         static gint *ett[] = {
3404                 &ett_radiotap,
3405                 &ett_radiotap_present,
3406                 &ett_radiotap_present_word,
3407                 &ett_radiotap_flags,
3408                 &ett_radiotap_rxflags,
3409                 &ett_radiotap_channel_flags,
3410                 &ett_radiotap_xchannel_flags,
3411                 &ett_radiotap_vendor,
3412                 &ett_radiotap_mcs,
3413                 &ett_radiotap_mcs_known,
3414                 &ett_radiotap_ampdu,
3415                 &ett_radiotap_ampdu_flags,
3416                 &ett_radiotap_vht,
3417                 &ett_radiotap_vht_known,
3418                 &ett_radiotap_vht_user,
3419                 &ett_radiotap_timestamp,
3420                 &ett_radiotap_timestamp_flags,
3421                 &ett_radiotap_he_info,
3422                 &ett_radiotap_he_info_data_1,
3423                 &ett_radiotap_he_info_data_2,
3424                 &ett_radiotap_he_info_data_3,
3425                 &ett_radiotap_he_info_data_4,
3426                 &ett_radiotap_he_info_data_5,
3427                 &ett_radiotap_he_info_data_6,
3428         };
3429         static ei_register_info ei[] = {
3430                 { &ei_radiotap_present, { "radiotap.present.radiotap_and_vendor", PI_MALFORMED, PI_ERROR, "Both radiotap and vendor namespace specified in bitmask word", EXPFILL }},
3431                 { &ei_radiotap_present_reserved, { "radiotap.present.reserved.unknown", PI_UNDECODED, PI_NOTE, "Unknown Radiotap fields, code not implemented, Please check radiotap documentation, Contact Wireshark developers if you want this supported", EXPFILL }},
3432                 { &ei_radiotap_data_past_header, { "radiotap.data_past_header", PI_MALFORMED, PI_ERROR, "Radiotap data goes past the end of the radiotap header", EXPFILL }},
3433                 { &ei_radiotap_invalid_data_rate, { "radiotap.vht.datarate.invalid", PI_PROTOCOL, PI_WARN, "Data rate invalid", EXPFILL }},
3434         };
3435
3436         module_t *radiotap_module;
3437         expert_module_t* expert_radiotap;
3438
3439         proto_radiotap =
3440             proto_register_protocol("IEEE 802.11 Radiotap Capture header", "802.11 Radiotap", "radiotap");
3441         proto_register_field_array(proto_radiotap, hf, array_length(hf));
3442         proto_register_subtree_array(ett, array_length(ett));
3443         expert_radiotap = expert_register_protocol(proto_radiotap);
3444         expert_register_field_array(expert_radiotap, ei, array_length(ei));
3445         register_dissector("radiotap", dissect_radiotap, proto_radiotap);
3446
3447         radiotap_tap = register_tap("radiotap");
3448
3449         radiotap_module = prefs_register_protocol(proto_radiotap, NULL);
3450         prefs_register_bool_preference(radiotap_module, "bit14_fcs_in_header",
3451                                        "Assume bit 14 means FCS in header",
3452                                        "Radiotap has a bit to indicate whether the FCS is still on the frame or not. "
3453                                        "Some generators (e.g. AirPcap) use a non-standard radiotap flag 14 to put "
3454                                        "the FCS into the header.",
3455                                        &radiotap_bit14_fcs);
3456
3457         prefs_register_bool_preference(radiotap_module, "interpret_high_rates_as_mcs",
3458                                        "Interpret high rates as MCS",
3459                                        "Some generators use rates with bit 7 set to indicate an MCS, e.g. BSD. "
3460                                            "others (Linux, AirPcap) do not.",
3461                                        &radiotap_interpret_high_rates_as_mcs);
3462 }
3463
3464 void proto_reg_handoff_radiotap(void)
3465 {
3466         dissector_handle_t radiotap_handle;
3467         capture_dissector_handle_t radiotap_cap_handle;
3468
3469         /* handle for 802.11+radio information dissector */
3470         ieee80211_radio_handle = find_dissector_add_dependency("wlan_radio", proto_radiotap);
3471
3472         radiotap_handle = find_dissector_add_dependency("radiotap", proto_radiotap);
3473
3474         dissector_add_uint("wtap_encap", WTAP_ENCAP_IEEE_802_11_RADIOTAP,
3475                            radiotap_handle);
3476
3477         radiotap_cap_handle = create_capture_dissector_handle(capture_radiotap, proto_radiotap);
3478         capture_dissector_add_uint("wtap_encap", WTAP_ENCAP_IEEE_802_11_RADIOTAP, radiotap_cap_handle);
3479
3480         ieee80211_cap_handle = find_capture_dissector("ieee80211");
3481         ieee80211_datapad_cap_handle = find_capture_dissector("ieee80211_datapad");
3482 }
3483
3484 /*
3485  * Editor modelines  -  http://www.wireshark.org/tools/modelines.html
3486  *
3487  * Local variables:
3488  * c-basic-offset: 8
3489  * tab-width: 8
3490  * indent-tabs-mode: t
3491  * End:
3492  *
3493  * vi: set shiftwidth=8 tabstop=8 noexpandtab:
3494  * :indentSize=8:tabSize=8:noTabs=false:
3495  */