Revert "TODO epan/dissectors/asn1/kerberos/packet-kerberos-template.c new GSS flags"
[wireshark-sm.git] / epan / dissectors / packet-vrt.c
blobd8c90db1d5782537fac7f4cba2fea6e354b0c760
1 /* packet-vrt.c
2 * Routines for VRT (VITA 49) packet disassembly
3 * Copyright 2012 Ettus Research LLC - Nick Foster <nick@ettus.com>: original dissector
4 * Copyright 2013 Alexander Chemeris <alexander.chemeris@gmail.com>: dissector improvement
5 * Copyright 2013 Dario Lombardo (lomato@gmail.com): Official Wireshark port
6 * Copyright 2022 Amazon.com, Inc. or its affiliates - Cody Planteen <codplant@amazon.com>: context packet decoding
7 * Copyright 2024 Valley Tech Systems, Inc. - John Moon <john.moon@vts-i.com>: spectral context decoding
9 * Original dissector repository: https://github.com/bistromath/vrt-dissector
11 * Wireshark - Network traffic analyzer
12 * By Gerald Combs <gerald@wireshark.org>
13 * Copyright 1998 Gerald Combs
15 * SPDX-License-Identifier: GPL-2.0-or-later
19 #include "config.h"
20 #include <epan/packet.h>
21 #include <epan/prefs.h>
22 #include <math.h>
24 void proto_register_vrt(void);
25 void proto_reg_handoff_vrt(void);
27 static dissector_handle_t vrt_handle;
29 #define VITA_49_PORT 4991
31 typedef int (*complex_dissector_t)(proto_tree *tree, tvbuff_t *tvb, int offset);
33 typedef struct {
34 int tsi; /* 2-bit timestamp type */
35 int tsf; /* 2-bit fractional timestamp type */
36 int oui; /* 24-bit GPS/INS manufacturer OUI */
37 int ts_int; /* 32-bit integer timestamp (opt.) */
38 int ts_picosecond; /* 64-bit fractional timestamp (mutually exclusive with below) */
39 int ts_frac_sample; /* 64-bit fractional timestamp (mutually exclusive with above) */
40 int pos_x; /* 32-bit position X */
41 int pos_y; /* 32-bit position Y */
42 int pos_z; /* 32-bit position Z */
43 int att_alpha; /* 32-bit attitude alpha */
44 int att_beta; /* 32-bit attitude beta */
45 int att_phi; /* 32-bit attitude phi */
46 int vel_dx; /* 32-bit velocity dX */
47 int vel_dy; /* 32-bit velocity dY */
48 int vel_dz; /* 32-bit velocity dZ */
49 } ephemeris_fields;
51 typedef struct {
52 int tsi; /* 2-bit timestamp type */
53 int tsf; /* 2-bit fractional timestamp type */
54 int oui; /* 24-bit GPS/INS manufacturer OUI */
55 int ts_int; /* 32-bit integer timestamp (opt.) */
56 int ts_picosecond; /* 64-bit fractional timestamp (mutually exclusive with below) */
57 int ts_frac_sample; /* 64-bit fractional timestamp (mutually exclusive with above) */
58 int lat; /* 32-bit latitude */
59 int lon; /* 32-bit longitude */
60 int alt; /* 32-bit altitude */
61 int speed; /* 32-bit speed over ground */
62 int heading; /* 32-bit heading angle */
63 int track; /* 32-bit track angle */
64 int mag_var; /* 32-bit magnetic variation */
65 } formatted_gps_ins_fields;
67 typedef int (*complex_dissector_t)(proto_tree *tree, tvbuff_t *tvb, int offset);
69 static bool vrt_use_ettus_uhd_header_format;
71 static int proto_vrt;
73 /* fields */
74 static int hf_vrt_header; /* 32-bit header */
75 static int hf_vrt_type; /* 4-bit pkt type */
76 static int hf_vrt_cidflag; /* 1-bit class ID flag */
77 static int hf_vrt_tflag; /* 1-bit trailer flag */
78 static int hf_vrt_tsmflag; /* 1-bit timestamp mode */
79 static int hf_vrt_tsi; /* 2-bit timestamp type */
80 static int hf_vrt_tsf; /* 2-bit fractional timestamp type */
81 static int hf_vrt_seq; /* 4-bit sequence number */
82 static int hf_vrt_len; /* 16-bit length */
83 static int hf_vrt_sid; /* 32-bit stream ID (opt.) */
84 static int hf_vrt_cid; /* 64-bit class ID (opt.) */
85 static int hf_vrt_cid_oui; /* 24-bit class ID OUI */
86 static int hf_vrt_cid_icc; /* 16-bit class ID ICC */
87 static int hf_vrt_cid_pcc; /* 16-bit class ID PCC */
88 static int hf_vrt_cif[8]; /* 32-bit CIF0-CIF7 (opt.) */
89 static int hf_vrt_cif0_change_flag; /* 1-bit context field change indicator */
90 static int hf_vrt_cif0_ref_pt_id; /* 1-bit reference point identifier */
91 static int hf_vrt_cif0_bandwidth; /* 1-bit bandwidth */
92 static int hf_vrt_cif0_if_freq; /* 1-bit IF reference frequency */
93 static int hf_vrt_cif0_rf_freq; /* 1-bit RF reference frequency */
94 static int hf_vrt_cif0_rf_freq_offset; /* 1-bit RF reference frequency offset */
95 static int hf_vrt_cif0_if_band_offset; /* 1-bit IF band offset */
96 static int hf_vrt_cif0_ref_level; /* 1-bit reference level */
97 static int hf_vrt_cif0_gain; /* 1-bit gain */
98 static int hf_vrt_cif0_over_range_count; /* 1-bit over-range count */
99 static int hf_vrt_cif0_sample_rate; /* 1-bit sample rate */
100 static int hf_vrt_cif0_timestamp_adjust; /* 1-bit timestamp adjustment */
101 static int hf_vrt_cif0_timestamp_cal; /* 1-bit timestamp calibration time */
102 static int hf_vrt_cif0_temperature; /* 1-bit temperature */
103 static int hf_vrt_cif0_device_id; /* 1-bit device identifier */
104 static int hf_vrt_cif0_state_event; /* 1-bit state/event indicators */
105 static int hf_vrt_cif0_signal_data_format; /* 1-bit signal data packet payload format */
106 static int hf_vrt_cif0_gps; /* 1-bit formatted GPS */
107 static int hf_vrt_cif0_ins; /* 1-bit formatted INS */
108 static int hf_vrt_cif0_ecef_ephemeris; /* 1-bit ECEF ephemeris */
109 static int hf_vrt_cif0_rel_ephemeris; /* 1-bit relative ephemeris */
110 static int hf_vrt_cif0_ephemeris_ref_id; /* 1-bit ephemeris ref ID */
111 static int hf_vrt_cif0_gps_ascii; /* 1-bit GPS ASCII */
112 static int hf_vrt_cif0_context_assoc_lists; /* 1-bit context association lists */
113 static int hf_vrt_cif0_cif7; /* 1-bit CIF7 */
114 static int hf_vrt_cif0_cif6; /* 1-bit CIF6 */
115 static int hf_vrt_cif0_cif5; /* 1-bit CIF5 */
116 static int hf_vrt_cif0_cif4; /* 1-bit CIF4 */
117 static int hf_vrt_cif0_cif3; /* 1-bit CIF3 */
118 static int hf_vrt_cif0_cif2; /* 1-bit CIF2 */
119 static int hf_vrt_cif0_cif1; /* 1-bit CIF1 */
120 /* TODO: complete CIF1 support (have partial CIF1 support) */
121 static int hf_vrt_cif1_phase_offset; /* 1-bit phase offset */
122 static int hf_vrt_cif1_polarization; /* 1-bit polarization */
123 static int hf_vrt_cif1_range; /* 1-bit range (distance) */
124 static int hf_vrt_cif1_aux_freq; /* 1-bit aux frequency */
125 static int hf_vrt_cif1_aux_bandwidth; /* 1-bit aux bandwidth */
126 static int hf_vrt_cif1_spectrum; /* 1-bit spectrum */
127 static int hf_vrt_cif1_io32; /* 1-bit discrete I/O (32-bit) */
128 static int hf_vrt_cif1_io64; /* 1-bit discrete I/O (64-bit) */
129 static int hf_vrt_cif1_v49_spec; /* 1-bit V49 spec compliance */
130 static int hf_vrt_cif1_ver; /* 1-bit version and build code */
131 static int hf_vrt_context_ref_pt_id; /* 32-bit reference point identifier */
132 static int hf_vrt_context_bandwidth; /* 64-bit bandwidth */
133 static int hf_vrt_context_if_freq; /* 64-bit IF reference frequency */
134 static int hf_vrt_context_rf_freq; /* 64-bit RF reference frequency */
135 static int hf_vrt_context_rf_freq_offset; /* 64-bit RF frequency offset */
136 static int hf_vrt_context_if_band_offset; /* 64-bit IF band offset */
137 static int hf_vrt_context_ref_level; /* 16-bit reference level */
138 static int hf_vrt_context_gain_stage2; /* 16-bit gain stage 2 */
139 static int hf_vrt_context_gain_stage1; /* 16-bit gain stage 1 */
140 static int hf_vrt_context_over_range_count; /* 32-bit over-range count */
141 static int hf_vrt_context_sample_rate; /* 64-bit sample rate */
142 static int hf_vrt_context_timestamp_adjust; /* 64-bit timestamp adjustment */
143 static int hf_vrt_context_timestamp_cal; /* 32-bit timestamp calibration */
144 static int hf_vrt_context_temperature; /* 16-bit device temperature */
145 static int hf_vrt_context_device_id_oui; /* 24-bit device ID OUI */
146 static int hf_vrt_context_device_id_code; /* 16-bit device ID code */
147 static int hf_vrt_context_state_event_en_cal_time; /* 1-bit enable calibrated time */
148 static int hf_vrt_context_state_event_en_valid_data; /* 1-bit enable valid data */
149 static int hf_vrt_context_state_event_en_ref_lock; /* 1-bit enable reference lock */
150 static int hf_vrt_context_state_event_en_agc; /* 1-bit enable AGC/MGC */
151 static int hf_vrt_context_state_event_en_detected_sig; /* 1-bit enable detected signal */
152 static int hf_vrt_context_state_event_en_spectral_inv; /* 1-bit enable spectral inversion */
153 static int hf_vrt_context_state_event_en_over_range; /* 1-bit enable over-range */
154 static int hf_vrt_context_state_event_en_sample_loss; /* 1-bit enable sample loss */
155 static int hf_vrt_context_state_event_cal_time; /* 1-bit enable calibrated time */
156 static int hf_vrt_context_state_event_valid_data; /* 1-bit enable valid data */
157 static int hf_vrt_context_state_event_ref_lock; /* 1-bit enable reference lock */
158 static int hf_vrt_context_state_event_agc; /* 1-bit enable AGC/MGC */
159 static int hf_vrt_context_state_event_detected_sig; /* 1-bit enable detected signal */
160 static int hf_vrt_context_state_event_spectral_inv; /* 1-bit enable spectral inversion */
161 static int hf_vrt_context_state_event_over_range; /* 1-bit enable over-range */
162 static int hf_vrt_context_state_event_sample_loss; /* 1-bit enable sample loss */
163 static int hf_vrt_context_state_event_user; /* 8-bit user-defined */
164 static int hf_vrt_context_signal_data_format_packing; /* 1-bit signal data format packing */
165 static int hf_vrt_context_signal_data_format_type; /* 2-bit real/complex type */
166 static int hf_vrt_context_signal_data_format_item; /* 5-bit data item format */
167 static int hf_vrt_context_signal_data_format_repeat; /* 1-bit sample-component repeat indicator */
168 static int hf_vrt_context_signal_data_format_event_size; /* 3-bit event-tag size */
169 static int hf_vrt_context_signal_data_format_channel_size; /* 4-bit channel-tag size */
170 static int hf_vrt_context_signal_data_format_fraction_size; /* 4-bit data item fraction size */
171 static int hf_vrt_context_signal_data_format_packing_size; /* 6-bit item packing field size */
172 static int hf_vrt_context_signal_data_format_item_size; /* 6-bit data item size */
173 static int hf_vrt_context_signal_data_format_repeat_count; /* 16-bit repeat count */
174 static int hf_vrt_context_signal_data_format_vector_size; /* 16-bit vector size */
175 static formatted_gps_ins_fields hf_vrt_context_gps; /* struct for formatted GPS */
176 static formatted_gps_ins_fields hf_vrt_context_ins; /* struct for formatted INS */
177 static ephemeris_fields hf_vrt_context_ecef_ephemeris; /* struct for ECEF ephemeris */
178 static ephemeris_fields hf_vrt_context_rel_ephemeris; /* struct for relative ephemeris */
179 static int hf_vrt_context_ephemeris_ref_id; /* 32-bit ephemeris reference identifier */
180 static int hf_vrt_context_gps_ascii_oui; /* 24-bit GPS/INS manufacturer OUI */
181 static int hf_vrt_context_gps_ascii_size; /* 32-bit number of words */
182 static int hf_vrt_context_gps_ascii_data; /* Variable GPS ASCII data */
183 static int hf_vrt_context_assoc_lists_src_size; /* 32-bit source list size */
184 static int hf_vrt_context_assoc_lists_sys_size; /* 32-bit system list size */
185 static int hf_vrt_context_assoc_lists_vec_size; /* 32-bit vector-component list size */
186 static int hf_vrt_context_assoc_lists_a; /* 1-bit "A" bit (asynchronous-channel tag list present) */
187 static int hf_vrt_context_assoc_lists_asy_size; /* 32-bit asynchronous-channel list size */
188 static int hf_vrt_context_assoc_lists_src_data; /* Variable source context association list */
189 static int hf_vrt_context_assoc_lists_sys_data; /* Variable system context association list */
190 static int hf_vrt_context_assoc_lists_vec_data; /* Variable vector-component context association list */
191 static int hf_vrt_context_assoc_lists_asy_data; /* Variable asynchronous-channel context association list */
192 static int hf_vrt_context_assoc_lists_asy_tag_data; /* Variable asynchronous-channel tag list */
193 static int hf_vrt_context_phase_offset; /* 16-bit phase offset */
194 static int hf_vrt_context_pol_tilt; /* 16-bit polarization tilt angle */
195 static int hf_vrt_context_pol_ellipticity; /* 16-bit polarization ellipticity angle */
196 static int hf_vrt_context_range; /* 32-bit range (distance) */
197 static int hf_vrt_context_aux_freq; /* 64-bit aux frequency */
198 static int hf_vrt_context_aux_bandwidth; /* 64-bit aux bandwidth */
199 static int hf_vrt_context_spectrum_spectrum_type; /* 32-bit spectrum type */
200 static int hf_vrt_context_spectrum_window_type; /* 32-bit window type */
201 static int hf_vrt_context_spectrum_num_transform_points; /* 32-bit number of transform points */
202 static int hf_vrt_context_spectrum_num_window_points; /* 32-bit number of window points */
203 static int hf_vrt_context_spectrum_resolution; /* 64-bit number of resolution points */
204 static int hf_vrt_context_spectrum_span; /* 64-bit number of span (bandwidth) */
205 static int hf_vrt_context_spectrum_num_averages; /* 32-bit number of averages */
206 static int hf_vrt_context_spectrum_weighting_factor; /* 32-bit weighting factor */
207 static int hf_vrt_context_spectrum_spectrum_f1_index; /* 32-bit F1 index */
208 static int hf_vrt_context_spectrum_spectrum_f2_index; /* 32-bit F2 index */
209 static int hf_vrt_context_spectrum_window_time_delta; /* 32-bit window time-delta */
210 static int hf_vrt_context_io32; /* 32-bit discrete I/O */
211 static int hf_vrt_context_io64; /* 64-bit discrete I/O */
212 static int hf_vrt_context_v49_spec; /* 32-bit V49 spec compliance */
213 static int hf_vrt_context_ver_year; /* 7-bit year */
214 static int hf_vrt_context_ver_day; /* 9-bit day */
215 static int hf_vrt_context_ver_rev; /* 6-bit revision */
216 static int hf_vrt_context_ver_user; /* 10-bit user defined */
217 static int hf_vrt_ts_int; /* 32-bit integer timestamp (opt.) */
218 static int hf_vrt_ts_frac_picosecond; /* 64-bit fractional timestamp (opt.) */
219 static int hf_vrt_ts_frac_sample; /* 64-bit fractional timestamp (opt.) */
220 static int hf_vrt_data; /* data */
221 static int hf_vrt_trailer; /* 32-bit trailer (opt.) */
222 static int hf_vrt_trailer_enables; /* trailer indicator enables */
223 static int hf_vrt_trailer_ind; /* trailer indicators */
224 static int hf_vrt_trailer_e; /* ass con pac cnt enable */
225 static int hf_vrt_trailer_acpc; /* associated context packet count */
226 static int hf_vrt_trailer_en_caltime; /* calibrated time indicator */
227 static int hf_vrt_trailer_en_valid; /* valid data ind */
228 static int hf_vrt_trailer_en_reflock; /* reference locked ind */
229 static int hf_vrt_trailer_en_agc; /* AGC/MGC enabled ind */
230 static int hf_vrt_trailer_en_sig; /* signal detected ind */
231 static int hf_vrt_trailer_en_inv; /* spectral inversion ind */
232 static int hf_vrt_trailer_en_overrng; /* overrange indicator */
233 static int hf_vrt_trailer_en_sampleloss; /* sample loss indicator */
234 static int hf_vrt_trailer_en_user0; /* User indicator 0 */
235 static int hf_vrt_trailer_en_user1; /* User indicator 1 */
236 static int hf_vrt_trailer_en_user2; /* User indicator 2 */
237 static int hf_vrt_trailer_en_user3; /* User indicator 3 */
238 static int hf_vrt_trailer_ind_caltime; /* calibrated time indicator */
239 static int hf_vrt_trailer_ind_valid; /* valid data ind */
240 static int hf_vrt_trailer_ind_reflock; /* reference locked ind */
241 static int hf_vrt_trailer_ind_agc; /* AGC/MGC enabled ind */
242 static int hf_vrt_trailer_ind_sig; /* signal detected ind */
243 static int hf_vrt_trailer_ind_inv; /* spectral inversion ind */
244 static int hf_vrt_trailer_ind_overrng; /* overrange indicator */
245 static int hf_vrt_trailer_ind_sampleloss; /* sample loss indicator */
246 static int hf_vrt_trailer_ind_user0; /* User indicator 0 */
247 static int hf_vrt_trailer_ind_user1; /* User indicator 1 */
248 static int hf_vrt_trailer_ind_user2; /* User indicator 2 */
249 static int hf_vrt_trailer_ind_user3; /* User indicator 3 */
251 /* fixed sizes (in bytes) of context packet CIF field bits */
252 static int context_size_cif0[32] = { 0, 4, 4, 4, 4, 4, 4, 4, 8, 8, 4, 52, 52, 44, 44, 8,
253 4, 8, 4, 4, 8, 8, 4, 4, 4, 8, 8, 8, 8, 8, 4, 0 };
254 static int context_size_cif1[32] = { 0, 8, 4, 4, 4, 8, 4, 0, 0, 0, 52, 0, 0, 8, 4, 8,
255 4, 4, 4, 4, 4, 0, 0, 0, 4, 4, 4, 4, 0, 4, 4, 4 };
257 /* subtree state variables */
258 static int ett_vrt;
259 static int ett_header;
260 static int ett_trailer;
261 static int ett_indicators;
262 static int ett_ind_enables;
263 static int ett_cid;
264 static int ett_cif0;
265 static int ett_cif1;
266 static int ett_gain;
267 static int ett_device_id;
268 static int ett_state_event;
269 static int ett_signal_data_format;
270 static int ett_gps;
271 static int ett_ins;
272 static int ett_ecef_ephem;
273 static int ett_rel_ephem;
274 static int ett_gps_ascii;
275 static int ett_assoc_lists;
276 static int ett_pol;
277 static int ett_ver;
279 /* constants (unit conversion) */
280 static const double FEMTOSEC_PER_SEC = 1e-15;
281 static const double RADIX_CELSIUS = 1.0/64.0;
282 static const double RADIX_DECIBEL = 1.0/128.0;
283 static const double RADIX_DECIBEL_MILLIWATT = 1.0/128.0;
284 static const double RADIX_DEGREES = 1.0/4194304.0;
285 static const double RADIX_HERTZ = 1.0/1048576.0;
286 static const double RADIX_METER = 1.0/32.0;
287 static const double RADIX_METER_UNSIGNED = 1.0/64.0;
288 static const double RADIX_METERS_PER_SECOND = 1.0/65536.0;
289 static const double RADIX_RADIAN_PHASE = 1.0/128.0;
290 static const double RADIX_RADIAN_POL = 1.0/8192.0;
292 /* constants (tree index) */
293 static const int ETT_IDX_GAIN = 8;
294 static const int ETT_IDX_DEVICE_ID = 9;
295 static const int ETT_IDX_STATE_EVENT = 10;
296 static const int ETT_IDX_SIGNAL_DATA_FORMAT = 11;
297 static const int ETT_IDX_GPS = 12;
298 static const int ETT_IDX_INS = 13;
299 static const int ETT_IDX_ECEF_EPHEM = 14;
300 static const int ETT_IDX_REL_EPHEM = 15;
301 static const int ETT_IDX_GPS_ASCII = 16;
302 static const int ETT_IDX_ASSOC_LISTS = 17;
303 static const int ETT_IDX_POL = 18;
304 static const int ETT_IDX_SPECTRUM = 19;
305 static const int ETT_IDX_VER = 20;
307 static const value_string packet_types[] = {
308 {0x00, "IF data packet without stream ID"},
309 {0x01, "IF data packet with stream ID"},
310 {0x02, "Extension data packet without stream ID"},
311 {0x03, "Extension data packet with stream ID"},
312 {0x04, "IF context packet"},
313 {0x05, "Extension context packet"},
314 {0, NULL}
317 static const value_string tsi_types[] = {
318 {0x00, "No integer-seconds timestamp field included"},
319 {0x01, "Coordinated Universal Time (UTC)"},
320 {0x02, "GPS time"},
321 {0x03, "Other"},
322 {0, NULL}
325 static const value_string tsf_types[] = {
326 {0x00, "No fractional-seconds timestamp field included"},
327 {0x01, "Sample count timestamp"},
328 {0x02, "Real time (picoseconds) timestamp"},
329 {0x03, "Free running count timestamp"},
330 {0, NULL}
333 static const value_string tsm_types[] = {
334 {0x00, "Precise timestamp resolution"},
335 {0x01, "General timestamp resolution"},
336 {0, NULL}
339 static const value_string packing_method[] = {
340 {0x00, "Processing efficient"},
341 {0x01, "Link efficient"},
342 {0, NULL}
345 static const value_string data_sample_type[] = {
346 {0x00, "Real"},
347 {0x01, "Complex, Cartesian"},
348 {0x02, "Complex, polar"},
349 {0, NULL}
352 static const value_string data_item_format[] = {
353 {0x00, "Signed fixed-point"},
354 {0x01, "Signed VRT, 1-bit exponent"},
355 {0x02, "Signed VRT, 2-bit exponent"},
356 {0x03, "Signed VRT, 3-bit exponent"},
357 {0x04, "Signed VRT, 4-bit exponent"},
358 {0x05, "Signed VRT, 5-bit exponent"},
359 {0x06, "Signed VRT, 6-bit exponent"},
360 {0x07, "Signed fixed-point non-normalized"},
361 {0x0D, "IEEE-754 half-precision floating-point"},
362 {0x0E, "IEEE-754 single-precision floating-point"},
363 {0x0F, "IEEE-754 double-precision floating-point"},
364 {0x10, "Unsigned fixed-point"},
365 {0x11, "Unsigned VRT, 1-bit exponent"},
366 {0x12, "Unsigned VRT, 2-bit exponent"},
367 {0x13, "Unsigned VRT, 3-bit exponent"},
368 {0x14, "Unsigned VRT, 4-bit exponent"},
369 {0x15, "Unsigned VRT, 5-bit exponent"},
370 {0x16, "Unsigned VRT, 6-bit exponent"},
371 {0x17, "Unsigned fixed-point non-normalized"},
372 {0, NULL}
375 static const value_string standard_version_codes[] = {
376 {0x01, "Implements V49.0"},
377 {0x02, "Implements V49.1"},
378 {0x03, "Implements V49A"},
379 {0x04, "Implements V49.2"},
380 {0, NULL}
383 static int * const enable_hfs[] = {
384 &hf_vrt_trailer_en_user3,
385 &hf_vrt_trailer_en_user2,
386 &hf_vrt_trailer_en_user1,
387 &hf_vrt_trailer_en_user0,
388 &hf_vrt_trailer_en_sampleloss,
389 &hf_vrt_trailer_en_overrng,
390 &hf_vrt_trailer_en_inv,
391 &hf_vrt_trailer_en_sig,
392 &hf_vrt_trailer_en_agc,
393 &hf_vrt_trailer_en_reflock,
394 &hf_vrt_trailer_en_valid,
395 &hf_vrt_trailer_en_caltime
398 static int * const ind_hfs[] = {
399 &hf_vrt_trailer_ind_user3,
400 &hf_vrt_trailer_ind_user2,
401 &hf_vrt_trailer_ind_user1,
402 &hf_vrt_trailer_ind_user0,
403 &hf_vrt_trailer_ind_sampleloss,
404 &hf_vrt_trailer_ind_overrng,
405 &hf_vrt_trailer_ind_inv,
406 &hf_vrt_trailer_ind_sig,
407 &hf_vrt_trailer_ind_agc,
408 &hf_vrt_trailer_ind_reflock,
409 &hf_vrt_trailer_ind_valid,
410 &hf_vrt_trailer_ind_caltime
413 static void dissect_header(tvbuff_t *tvb, proto_tree *tree, int type, int offset);
414 static void dissect_trailer(tvbuff_t *tvb, proto_tree *tree, int offset);
415 static void dissect_cid(tvbuff_t *tvb, proto_tree *tree, int offset);
416 static int dissect_context(tvbuff_t *tvb, proto_tree *tree, int offset);
417 static int dissect_context_as_cif(tvbuff_t *tvb, proto_tree *tree, int offset, uint32_t cif, complex_dissector_t
418 *complex_fptr, int **item_ptr, const int *size_ptr, int stop);
419 static int dissect_context_array_of_records(proto_tree *tree _U_, tvbuff_t *tvb, int offset);
420 static int dissect_context_assoc_lists(proto_tree *tree, tvbuff_t *tvb, int offset);
421 static int dissect_context_cif0(proto_tree *tree, tvbuff_t *tvb, int offset);
422 static int dissect_context_cif1(proto_tree *tree, tvbuff_t *tvb, int offset);
423 static int dissect_context_device_id(proto_tree *tree, tvbuff_t *tvb, int offset);
424 static int dissect_context_ecef_ephemeris(proto_tree *tree, tvbuff_t *tvb, int offset);
425 static void dissect_context_ephemeris(const ephemeris_fields *s, proto_tree *tree, tvbuff_t *tvb, int offset);
426 static int dissect_context_gain(proto_tree *tree, tvbuff_t *tvb, int offset);
427 static int dissect_context_gps(proto_tree *tree, tvbuff_t *tvb, int offset);
428 static int dissect_context_gps_ascii(proto_tree *tree, tvbuff_t *tvb, int offset);
429 static int dissect_context_ins(proto_tree *tree, tvbuff_t *tvb, int offset);
430 static int dissect_context_phase_offset(proto_tree *tree, tvbuff_t *tvb, int offset);
431 static int dissect_context_polarization(proto_tree *tree, tvbuff_t *tvb, int offset);
432 static int dissect_context_ref_level(proto_tree *tree, tvbuff_t *tvb, int offset);
433 static int dissect_context_rel_ephemeris(proto_tree *tree, tvbuff_t *tvb, int offset);
434 static int dissect_context_signal_data_format(proto_tree *tree, tvbuff_t *tvb, int offset);
435 static int dissect_context_state_event(proto_tree *tree, tvbuff_t *tvb, int offset);
436 static int dissect_context_temperature(proto_tree *tree, tvbuff_t *tvb, int offset);
437 static int dissect_context_ver(proto_tree *tree, tvbuff_t *tvb, int offset);
438 static int dissect_context_spectrum(proto_tree *tree, tvbuff_t *tvb, int offset);
439 static const char* get_engr_prefix(double *val);
441 /* context simple field dissector function pointer array (mutually exclusive with complex below) */
442 static int* hf_vrt_context_cif0[32] = { NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
443 NULL, &hf_vrt_context_ephemeris_ref_id, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
444 &hf_vrt_context_timestamp_cal, &hf_vrt_context_timestamp_adjust, &hf_vrt_context_sample_rate,
445 &hf_vrt_context_over_range_count, NULL, NULL, &hf_vrt_context_if_band_offset,
446 &hf_vrt_context_rf_freq_offset, &hf_vrt_context_rf_freq, &hf_vrt_context_if_freq,
447 &hf_vrt_context_bandwidth, &hf_vrt_context_ref_pt_id, NULL };
449 static int* hf_vrt_context_cif1[32] = { NULL, NULL, NULL, &hf_vrt_context_v49_spec, NULL,
450 &hf_vrt_context_io64, &hf_vrt_context_io32, NULL, NULL, NULL, NULL, NULL, NULL,
451 &hf_vrt_context_aux_bandwidth, NULL, &hf_vrt_context_aux_freq, NULL, NULL, NULL, NULL, NULL,
452 NULL, NULL, NULL, &hf_vrt_context_range, NULL, NULL, NULL, NULL, NULL, NULL, NULL };
455 /* context complex field dissector function pointer array */
456 static complex_dissector_t complex_dissector_cif0[32] = {
457 NULL, dissect_context_cif1, NULL, NULL, NULL, NULL, NULL, NULL, dissect_context_assoc_lists,
458 dissect_context_gps_ascii, NULL, dissect_context_rel_ephemeris, dissect_context_ecef_ephemeris,
459 dissect_context_ins, dissect_context_gps, dissect_context_signal_data_format,
460 dissect_context_state_event, dissect_context_device_id, dissect_context_temperature, NULL,
461 NULL, NULL, NULL, dissect_context_gain, dissect_context_ref_level, NULL, NULL, NULL, NULL,
462 NULL, NULL, NULL };
464 /* partial CIF1 support */
465 static complex_dissector_t complex_dissector_cif1[32] = {
466 NULL, NULL, dissect_context_ver, NULL, NULL, NULL, NULL, dissect_context_array_of_records,
467 NULL, dissect_context_array_of_records, dissect_context_spectrum, dissect_context_array_of_records,
468 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
469 dissect_context_array_of_records, NULL,
470 dissect_context_polarization, dissect_context_phase_offset };
473 static int dissect_vrt(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data _U_)
475 int offset = 0;
476 uint8_t type;
478 col_set_str(pinfo->cinfo, COL_PROTOCOL, "VITA 49");
479 col_clear(pinfo->cinfo,COL_INFO);
481 /* HACK to support UHD's weird header offset on data packets. */
482 if (vrt_use_ettus_uhd_header_format && tvb_get_uint8(tvb, 0) == 0)
483 offset += 4;
485 /* get packet type */
486 type = tvb_get_uint8(tvb, offset) >> 4;
487 col_add_str(pinfo->cinfo, COL_INFO, val_to_str(type, packet_types, "Reserved packet type (0x%02x)"));
489 if (tree) { /* we're being asked for details */
490 uint8_t sidflag;
491 uint8_t cidflag;
492 uint8_t tflag;
493 uint8_t tsitype;
494 uint8_t tsftype;
495 uint16_t len;
496 uint16_t nsamps;
498 proto_tree *vrt_tree;
499 proto_item *ti;
501 /* get SID, CID, T flags and TSI, TSF types */
502 sidflag = (((type & 0x01) != 0) || (type == 4)) ? 1 : 0;
503 cidflag = (tvb_get_uint8(tvb, offset) >> 3) & 0x01;
504 /* tflag is in data packets but not context packets */
505 tflag = (tvb_get_uint8(tvb, offset) >> 2) & 0x01;
506 if (type == 4)
507 tflag = 0; /* this should be unnecessary but we do it just in case */
508 /* tsmflag is in context packets but not data packets
509 tsmflag = (tvb_get_uint8(tvb, offset) >> 0) & 0x01; */
510 tsitype = (tvb_get_uint8(tvb, offset+1) >> 6) & 0x03;
511 tsftype = (tvb_get_uint8(tvb, offset+1) >> 4) & 0x03;
512 len = tvb_get_ntohs(tvb, offset+2);
514 nsamps = len - 1; /* (Before adjusting word count for optional fields) */
516 ti = proto_tree_add_item(tree, proto_vrt, tvb, offset, -1, ENC_NA);
517 vrt_tree = proto_item_add_subtree(ti, ett_vrt);
519 dissect_header(tvb, vrt_tree, type, offset);
520 offset += 4;
522 /* header's done! if SID (last bit of type), put the stream ID here */
523 if (sidflag) {
524 proto_tree_add_item(vrt_tree, hf_vrt_sid, tvb, offset, 4, ENC_BIG_ENDIAN);
525 nsamps -= 1;
526 offset += 4;
530 /* if there's a class ID (cidflag), put the class ID here */
531 if (cidflag) {
532 dissect_cid(tvb, vrt_tree, offset);
533 nsamps -= 2;
534 offset += 8;
537 /* if TSI and/or TSF, populate those here */
538 if (tsitype != 0) {
539 proto_tree_add_item(vrt_tree, hf_vrt_ts_int, tvb, offset, 4, ENC_BIG_ENDIAN);
540 nsamps -= 1;
541 offset += 4;
543 if (tsftype != 0) {
544 if (tsftype == 1 || tsftype == 3) {
545 proto_tree_add_item(vrt_tree, hf_vrt_ts_frac_sample, tvb, offset, 8, ENC_BIG_ENDIAN);
546 } else if (tsftype == 2) {
547 proto_tree_add_item(vrt_tree, hf_vrt_ts_frac_picosecond, tvb, offset, 8, ENC_BIG_ENDIAN);
549 nsamps -= 2;
550 offset += 8;
553 if (tflag) {
554 nsamps -= 1;
557 /* now we've got either a context packet or a data packet */
558 if (type == 4) {
559 /* parse context packet */
560 int num_v49_words = dissect_context(tvb, vrt_tree, offset);
561 nsamps -= num_v49_words;
562 offset += 4*num_v49_words;
565 /* we're into the data */
566 if (nsamps != 0) {
567 proto_tree_add_item(vrt_tree, hf_vrt_data, tvb, offset, nsamps*4, ENC_NA);
570 offset += nsamps*4;
572 if (tflag) {
573 dissect_trailer(tvb, vrt_tree, offset);
576 return tvb_captured_length(tvb);
579 static void dissect_header(tvbuff_t *tvb, proto_tree *tree, int type, int offset)
581 proto_item *hdr_item;
582 proto_tree *hdr_tree;
584 hdr_item = proto_tree_add_item(tree, hf_vrt_header, tvb, offset, 4, ENC_BIG_ENDIAN);
586 hdr_tree = proto_item_add_subtree(hdr_item, ett_header);
587 proto_tree_add_item(hdr_tree, hf_vrt_type, tvb, offset, 1, ENC_BIG_ENDIAN);
588 proto_tree_add_item(hdr_tree, hf_vrt_cidflag, tvb, offset, 1, ENC_BIG_ENDIAN);
589 if (type == 4) {
590 proto_tree_add_item(hdr_tree, hf_vrt_tsmflag, tvb, offset, 1, ENC_BIG_ENDIAN);
591 } else {
592 proto_tree_add_item(hdr_tree, hf_vrt_tflag, tvb, offset, 1, ENC_BIG_ENDIAN);
594 offset += 1;
595 proto_tree_add_item(hdr_tree, hf_vrt_tsi, tvb, offset, 1, ENC_BIG_ENDIAN);
596 proto_tree_add_item(hdr_tree, hf_vrt_tsf, tvb, offset, 1, ENC_BIG_ENDIAN);
597 proto_tree_add_item(hdr_tree, hf_vrt_seq, tvb, offset, 1, ENC_BIG_ENDIAN);
598 offset += 1;
599 proto_tree_add_item(hdr_tree, hf_vrt_len, tvb, offset, 2, ENC_BIG_ENDIAN);
602 static void dissect_trailer(tvbuff_t *tvb, proto_tree *tree, int offset)
604 proto_item *enable_item, *ind_item, *trailer_item;
605 proto_tree *enable_tree;
606 proto_tree *ind_tree;
607 proto_tree *trailer_tree;
608 uint16_t en_bits;
609 int16_t i;
611 trailer_item = proto_tree_add_item(tree, hf_vrt_trailer, tvb, offset, 4, ENC_BIG_ENDIAN);
612 trailer_tree = proto_item_add_subtree(trailer_item, ett_trailer);
614 /* grab the indicator enables and the indicators;
615 only display enables, indicators which are enabled */
616 enable_item = proto_tree_add_item(trailer_tree, hf_vrt_trailer_enables, tvb, offset, 2, ENC_BIG_ENDIAN);
617 ind_item = proto_tree_add_item(trailer_tree, hf_vrt_trailer_ind, tvb, offset + 1, 2, ENC_BIG_ENDIAN);
618 /* grab enable bits */
619 en_bits = (tvb_get_ntohs(tvb, offset) & 0xFFF0) >> 4;
621 /* if there's any enables, start trees for enable bits and for indicators
622 only enables and indicators which are enabled get printed. */
623 if (en_bits) {
624 enable_tree = proto_item_add_subtree(enable_item, ett_ind_enables);
625 ind_tree = proto_item_add_subtree(ind_item, ett_indicators);
626 for (i = 11; i >= 0; i--) {
627 if (en_bits & (1<<i)) {
628 /* XXX: Display needs to be improved ... */
629 proto_tree_add_item(enable_tree, *enable_hfs[i], tvb, offset, 2, ENC_BIG_ENDIAN);
630 proto_tree_add_item(ind_tree, *ind_hfs[i], tvb, offset+1, 2, ENC_BIG_ENDIAN);
634 offset += 3;
635 proto_tree_add_item(trailer_tree, hf_vrt_trailer_e, tvb, offset, 1, ENC_BIG_ENDIAN);
636 proto_tree_add_item(trailer_tree, hf_vrt_trailer_acpc, tvb, offset, 1, ENC_BIG_ENDIAN);
639 static void dissect_cid(tvbuff_t *tvb, proto_tree *tree, int offset)
641 proto_item *cid_item;
642 proto_tree *cid_tree;
644 cid_item = proto_tree_add_item(tree, hf_vrt_cid, tvb, offset, 8, ENC_BIG_ENDIAN);
645 cid_tree = proto_item_add_subtree(cid_item, ett_cid);
647 offset += 1;
648 proto_tree_add_item(cid_tree, hf_vrt_cid_oui, tvb, offset, 3, ENC_BIG_ENDIAN);
649 offset += 3;
650 proto_tree_add_item(cid_tree, hf_vrt_cid_icc, tvb, offset, 2, ENC_BIG_ENDIAN);
651 offset += 2;
652 proto_tree_add_item(cid_tree, hf_vrt_cid_pcc, tvb, offset, 2, ENC_BIG_ENDIAN);
655 static int dissect_context(tvbuff_t *tvb, proto_tree *tree, int offset)
657 uint32_t cif[8] = {0, 0, 0, 0, 0, 0, 0, 0};
658 int offset_start = offset;
660 cif[0] = tvb_get_ntohl(tvb, offset);
661 dissect_context_cif0(tree, tvb, offset);
662 offset += 4;
663 // CIF1-CIF7 bit fields come next with CIF1 first
664 for (int i = 1; i < 8; i++) {
665 if (cif[0] & (1 << i)) {
666 if (complex_dissector_cif0[i] != NULL) {
667 (*complex_dissector_cif0[i])(tree, tvb, offset);
668 } else {
669 proto_tree_add_item(tree, hf_vrt_cif[i], tvb, offset, 4, ENC_BIG_ENDIAN);
671 cif[i] = tvb_get_ntohl(tvb, offset);
672 offset += 4;
676 // decode CIF0 fields
677 offset = dissect_context_as_cif(tvb, tree, offset, cif[0], complex_dissector_cif0, hf_vrt_context_cif0,
678 context_size_cif0, 7);
679 // finally other CIFs (only CIF1 for now)
680 if (cif[0] & (1 << 1)) {
681 offset = dissect_context_as_cif(tvb, tree, offset, cif[1], complex_dissector_cif1, hf_vrt_context_cif1,
682 context_size_cif1, 0);
685 // return how many VITA-49 words were processed
686 return (offset - offset_start)/4;
689 static int dissect_context_as_cif(tvbuff_t *tvb, proto_tree *tree, int offset, uint32_t cif,
690 complex_dissector_t *complex_fptr, int **item_ptr, const int *size_ptr, int stop) {
691 for (int i = 31; i > stop; i--) {
692 if (cif & (1u << i)) {
693 if (complex_fptr[i] != NULL) {
694 // a complex dissector returns the variable part of field length (in bytes)
695 offset += (*complex_fptr[i])(tree, tvb, offset);
696 } else if (item_ptr[i] != NULL) {
697 proto_tree_add_item(tree, *item_ptr[i], tvb, offset, size_ptr[i], ENC_BIG_ENDIAN);
699 // add fixed part of field length (in bytes)
700 offset += size_ptr[i];
704 return offset;
707 static int dissect_context_array_of_records(proto_tree *tree _U_, tvbuff_t *tvb, int offset) {
708 // This is a placeholder that does not populate a proto tree, but computes & returns the
709 // variable field length so subsequent field indexing is correct.
710 return tvb_get_ntohl(tvb, offset)*4;
713 static int dissect_context_assoc_lists(proto_tree *tree, tvbuff_t *tvb, int offset) {
714 // compute number of variable words in field
715 uint32_t word1 = tvb_get_ntohl(tvb, offset);
716 uint32_t src_size = (word1 >> 16) & 0x01FF;
717 uint32_t sys_size = word1 & 0x01FF;
718 uint32_t word2 = tvb_get_ntohl(tvb, offset + 4);
719 uint32_t vec_size = word2 >> 16;
720 bool a_bit = (word2 & 0x8000) != 0;
721 uint32_t asy_size = word2 & 0x7FFF;
722 uint32_t num_words = src_size + sys_size + vec_size + asy_size + (a_bit ? asy_size : 0);
724 proto_tree *assoc_tree = proto_tree_add_subtree(tree, tvb, offset, 8 + num_words*4, ETT_IDX_ASSOC_LISTS, NULL,
725 "Context association lists");
726 proto_tree_add_item(assoc_tree, hf_vrt_context_assoc_lists_src_size, tvb, offset, 2, ENC_BIG_ENDIAN);
727 proto_tree_add_item(assoc_tree, hf_vrt_context_assoc_lists_sys_size, tvb, offset + 2, 2, ENC_BIG_ENDIAN);
728 proto_tree_add_item(assoc_tree, hf_vrt_context_assoc_lists_vec_size, tvb, offset + 4, 2, ENC_BIG_ENDIAN);
729 proto_tree_add_item(assoc_tree, hf_vrt_context_assoc_lists_a, tvb, offset + 6, 1, ENC_BIG_ENDIAN);
730 proto_tree_add_item(assoc_tree, hf_vrt_context_assoc_lists_asy_size, tvb, offset + 6, 2, ENC_BIG_ENDIAN);
731 offset += 8;
733 if (src_size > 0) {
734 proto_tree_add_item(assoc_tree, hf_vrt_context_assoc_lists_src_data, tvb, offset, src_size*4, ENC_NA);
735 offset += src_size*4;
738 if (sys_size > 0) {
739 proto_tree_add_item(assoc_tree, hf_vrt_context_assoc_lists_sys_data, tvb, offset, sys_size*4, ENC_NA);
740 offset += sys_size*4;
743 if (vec_size > 0) {
744 proto_tree_add_item(assoc_tree, hf_vrt_context_assoc_lists_vec_data, tvb, offset, vec_size*4, ENC_NA);
745 offset += vec_size*4;
748 if (asy_size > 0) {
749 proto_tree_add_item(assoc_tree, hf_vrt_context_assoc_lists_asy_data, tvb, offset, asy_size*4, ENC_NA);
750 offset += asy_size*4;
751 if (a_bit) {
752 proto_tree_add_item(assoc_tree, hf_vrt_context_assoc_lists_asy_tag_data, tvb, offset, asy_size*4, ENC_NA);
756 return num_words*4;
759 static int dissect_context_cif0(proto_tree *tree, tvbuff_t *tvb, int offset) {
760 proto_item *cif0_item;
761 proto_tree *cif0_tree;
763 cif0_item = proto_tree_add_item(tree, hf_vrt_cif[0], tvb, offset, 4, ENC_BIG_ENDIAN);
764 cif0_tree = proto_item_add_subtree(cif0_item, ett_cif0);
765 proto_tree_add_item(cif0_tree, hf_vrt_cif0_change_flag, tvb, offset, 1, ENC_BIG_ENDIAN);
766 proto_tree_add_item(cif0_tree, hf_vrt_cif0_ref_pt_id, tvb, offset, 1, ENC_BIG_ENDIAN);
767 proto_tree_add_item(cif0_tree, hf_vrt_cif0_bandwidth, tvb, offset, 1, ENC_BIG_ENDIAN);
768 proto_tree_add_item(cif0_tree, hf_vrt_cif0_if_freq, tvb, offset, 1, ENC_BIG_ENDIAN);
769 proto_tree_add_item(cif0_tree, hf_vrt_cif0_rf_freq, tvb, offset, 1, ENC_BIG_ENDIAN);
770 proto_tree_add_item(cif0_tree, hf_vrt_cif0_rf_freq_offset, tvb, offset, 1, ENC_BIG_ENDIAN);
771 proto_tree_add_item(cif0_tree, hf_vrt_cif0_if_band_offset, tvb, offset, 1, ENC_BIG_ENDIAN);
772 proto_tree_add_item(cif0_tree, hf_vrt_cif0_ref_level, tvb, offset, 1, ENC_BIG_ENDIAN);
773 offset += 1;
774 proto_tree_add_item(cif0_tree, hf_vrt_cif0_gain, tvb, offset, 1, ENC_BIG_ENDIAN);
775 proto_tree_add_item(cif0_tree, hf_vrt_cif0_over_range_count, tvb, offset, 1, ENC_BIG_ENDIAN);
776 proto_tree_add_item(cif0_tree, hf_vrt_cif0_sample_rate, tvb, offset, 1, ENC_BIG_ENDIAN);
777 proto_tree_add_item(cif0_tree, hf_vrt_cif0_timestamp_adjust, tvb, offset, 1, ENC_BIG_ENDIAN);
778 proto_tree_add_item(cif0_tree, hf_vrt_cif0_timestamp_cal, tvb, offset, 1, ENC_BIG_ENDIAN);
779 proto_tree_add_item(cif0_tree, hf_vrt_cif0_temperature, tvb, offset, 1, ENC_BIG_ENDIAN);
780 proto_tree_add_item(cif0_tree, hf_vrt_cif0_device_id, tvb, offset, 1, ENC_BIG_ENDIAN);
781 proto_tree_add_item(cif0_tree, hf_vrt_cif0_state_event, tvb, offset, 1, ENC_BIG_ENDIAN);
782 offset += 1;
783 proto_tree_add_item(cif0_tree, hf_vrt_cif0_signal_data_format, tvb, offset, 1, ENC_BIG_ENDIAN);
784 proto_tree_add_item(cif0_tree, hf_vrt_cif0_gps, tvb, offset, 1, ENC_BIG_ENDIAN);
785 proto_tree_add_item(cif0_tree, hf_vrt_cif0_ins, tvb, offset, 1, ENC_BIG_ENDIAN);
786 proto_tree_add_item(cif0_tree, hf_vrt_cif0_ecef_ephemeris, tvb, offset, 1, ENC_BIG_ENDIAN);
787 proto_tree_add_item(cif0_tree, hf_vrt_cif0_rel_ephemeris, tvb, offset, 1, ENC_BIG_ENDIAN);
788 proto_tree_add_item(cif0_tree, hf_vrt_cif0_ephemeris_ref_id, tvb, offset, 1, ENC_BIG_ENDIAN);
789 proto_tree_add_item(cif0_tree, hf_vrt_cif0_gps_ascii, tvb, offset, 1, ENC_BIG_ENDIAN);
790 proto_tree_add_item(cif0_tree, hf_vrt_cif0_context_assoc_lists, tvb, offset, 1, ENC_BIG_ENDIAN);
791 offset += 1;
792 proto_tree_add_item(cif0_tree, hf_vrt_cif0_cif7, tvb, offset, 1, ENC_BIG_ENDIAN);
793 proto_tree_add_item(cif0_tree, hf_vrt_cif0_cif6, tvb, offset, 1, ENC_BIG_ENDIAN);
794 proto_tree_add_item(cif0_tree, hf_vrt_cif0_cif5, tvb, offset, 1, ENC_BIG_ENDIAN);
795 proto_tree_add_item(cif0_tree, hf_vrt_cif0_cif4, tvb, offset, 1, ENC_BIG_ENDIAN);
796 proto_tree_add_item(cif0_tree, hf_vrt_cif0_cif3, tvb, offset, 1, ENC_BIG_ENDIAN);
797 proto_tree_add_item(cif0_tree, hf_vrt_cif0_cif2, tvb, offset, 1, ENC_BIG_ENDIAN);
798 proto_tree_add_item(cif0_tree, hf_vrt_cif0_cif1, tvb, offset, 1, ENC_BIG_ENDIAN);
799 return 0;
802 static int dissect_context_cif1(proto_tree *tree, tvbuff_t *tvb, int offset) {
803 proto_item *cif1_item = proto_tree_add_item(tree, hf_vrt_cif[1], tvb, offset, 4, ENC_BIG_ENDIAN);
804 proto_tree *cif1_tree = proto_item_add_subtree(cif1_item, ett_cif1);
805 proto_tree_add_item(cif1_tree, hf_vrt_cif1_phase_offset, tvb, offset, 1, ENC_BIG_ENDIAN);
806 proto_tree_add_item(cif1_tree, hf_vrt_cif1_polarization, tvb, offset, 1, ENC_BIG_ENDIAN);
807 proto_tree_add_item(cif1_tree, hf_vrt_cif1_range, tvb, offset, 1, ENC_BIG_ENDIAN);
808 proto_tree_add_item(cif1_tree, hf_vrt_cif1_aux_freq, tvb, offset + 2, 1, ENC_BIG_ENDIAN);
809 proto_tree_add_item(cif1_tree, hf_vrt_cif1_aux_bandwidth, tvb, offset + 2, 1, ENC_BIG_ENDIAN);
810 proto_tree_add_item(cif1_tree, hf_vrt_cif1_spectrum, tvb, offset + 2, 1, ENC_BIG_ENDIAN);
811 proto_tree_add_item(cif1_tree, hf_vrt_cif1_io32, tvb, offset + 3, 1, ENC_BIG_ENDIAN);
812 proto_tree_add_item(cif1_tree, hf_vrt_cif1_io64, tvb, offset + 3, 1, ENC_BIG_ENDIAN);
813 proto_tree_add_item(cif1_tree, hf_vrt_cif1_v49_spec, tvb, offset + 3, 1, ENC_BIG_ENDIAN);
814 proto_tree_add_item(cif1_tree, hf_vrt_cif1_ver, tvb, offset + 3, 1, ENC_BIG_ENDIAN);
815 return 0;
818 static int dissect_context_device_id(proto_tree *tree, tvbuff_t *tvb, int offset) {
819 proto_tree *id_tree = proto_tree_add_subtree(tree, tvb, offset, 8, ETT_IDX_DEVICE_ID, NULL, "Device identifier");
820 proto_tree_add_item(id_tree, hf_vrt_context_device_id_oui, tvb, offset + 1, 3, ENC_BIG_ENDIAN);
821 proto_tree_add_item(id_tree, hf_vrt_context_device_id_code, tvb, offset + 6, 2, ENC_BIG_ENDIAN);
822 return 0;
825 static int dissect_context_ecef_ephemeris(proto_tree *tree, tvbuff_t *tvb, int offset) {
826 proto_tree *ecef_tree = proto_tree_add_subtree(tree, tvb, offset, 52, ETT_IDX_ECEF_EPHEM, NULL, "ECEF ephemeris");
827 dissect_context_ephemeris(&hf_vrt_context_ecef_ephemeris, ecef_tree, tvb, offset);
828 return 0;
831 static void dissect_context_ephemeris(const ephemeris_fields *s, proto_tree *tree, tvbuff_t *tvb, int offset) {
832 proto_tree_add_item(tree, s->tsi, tvb, offset, 1, ENC_BIG_ENDIAN);
833 proto_tree_add_item(tree, s->tsf, tvb, offset, 1, ENC_BIG_ENDIAN);
834 proto_tree_add_item(tree, s->oui, tvb, offset + 1, 3, ENC_BIG_ENDIAN);
835 proto_tree_add_item(tree, s->ts_int, tvb, offset + 4, 4, ENC_BIG_ENDIAN);
837 uint8_t tsftype = tvb_get_uint8(tvb, offset) & 0x03;
838 if (tsftype == 1 || tsftype == 3) {
839 proto_tree_add_item(tree, s->ts_frac_sample, tvb, offset + 8, 8, ENC_BIG_ENDIAN);
840 } else if (tsftype == 2) {
841 proto_tree_add_item(tree, s->ts_picosecond, tvb, offset + 8, 8, ENC_BIG_ENDIAN);
844 proto_tree_add_item(tree, s->pos_x, tvb, offset + 16, 4, ENC_BIG_ENDIAN);
845 proto_tree_add_item(tree, s->pos_y, tvb, offset + 20, 4, ENC_BIG_ENDIAN);
846 proto_tree_add_item(tree, s->pos_z, tvb, offset + 24, 4, ENC_BIG_ENDIAN);
847 proto_tree_add_item(tree, s->att_alpha, tvb, offset + 28, 4, ENC_BIG_ENDIAN);
848 proto_tree_add_item(tree, s->att_beta, tvb, offset + 32, 4, ENC_BIG_ENDIAN);
849 proto_tree_add_item(tree, s->att_phi, tvb, offset + 36, 4, ENC_BIG_ENDIAN);
850 proto_tree_add_item(tree, s->vel_dx, tvb, offset + 40, 4, ENC_BIG_ENDIAN);
851 proto_tree_add_item(tree, s->vel_dy, tvb, offset + 44, 4, ENC_BIG_ENDIAN);
852 proto_tree_add_item(tree, s->vel_dz, tvb, offset + 48, 4, ENC_BIG_ENDIAN);
855 static void dissect_context_formatted_gps_ins(const formatted_gps_ins_fields *s, proto_tree *tree, tvbuff_t *tvb,
856 int offset) {
857 proto_tree_add_item(tree, s->tsi, tvb, offset, 1, ENC_BIG_ENDIAN);
858 proto_tree_add_item(tree, s->tsf, tvb, offset, 1, ENC_BIG_ENDIAN);
859 proto_tree_add_item(tree, s->oui, tvb, offset + 1, 3, ENC_BIG_ENDIAN);
860 proto_tree_add_item(tree, s->ts_int, tvb, offset + 4, 4, ENC_BIG_ENDIAN);
862 uint8_t tsftype = tvb_get_uint8(tvb, offset) & 0x03;
863 if (tsftype == 1 || tsftype == 3) {
864 proto_tree_add_item(tree, s->ts_frac_sample, tvb, offset + 8, 8, ENC_BIG_ENDIAN);
865 } else if (tsftype == 2) {
866 proto_tree_add_item(tree, s->ts_picosecond, tvb, offset + 8, 8, ENC_BIG_ENDIAN);
869 proto_tree_add_item(tree, s->lat, tvb, offset + 16, 4, ENC_BIG_ENDIAN);
870 proto_tree_add_item(tree, s->lon, tvb, offset + 20, 4, ENC_BIG_ENDIAN);
871 proto_tree_add_item(tree, s->alt, tvb, offset + 24, 4, ENC_BIG_ENDIAN);
872 proto_tree_add_item(tree, s->speed, tvb, offset + 28, 4, ENC_BIG_ENDIAN);
873 proto_tree_add_item(tree, s->heading, tvb, offset + 32, 4, ENC_BIG_ENDIAN);
874 proto_tree_add_item(tree, s->track, tvb, offset + 36, 4, ENC_BIG_ENDIAN);
875 proto_tree_add_item(tree, s->mag_var, tvb, offset + 40, 4, ENC_BIG_ENDIAN);
878 static int dissect_context_gain(proto_tree *tree, tvbuff_t *tvb, int offset) {
879 proto_tree *gain_tree = proto_tree_add_subtree(tree, tvb, offset, 4, ETT_IDX_GAIN, NULL, "Gain");
880 proto_tree_add_item(gain_tree, hf_vrt_context_gain_stage2, tvb, offset, 2, ENC_BIG_ENDIAN);
881 proto_tree_add_item(gain_tree, hf_vrt_context_gain_stage1, tvb, offset + 2, 2, ENC_BIG_ENDIAN);
882 return 0;
885 static int dissect_context_gps(proto_tree *tree, tvbuff_t *tvb, int offset) {
886 proto_tree *gps_tree = proto_tree_add_subtree(tree, tvb, offset, 44, ETT_IDX_GPS, NULL, "Formatted GPS");
887 dissect_context_formatted_gps_ins(&hf_vrt_context_gps, gps_tree, tvb, offset);
888 return 0;
891 static int dissect_context_gps_ascii(proto_tree *tree, tvbuff_t *tvb, int offset) {
892 uint32_t nword = tvb_get_ntohl(tvb, offset + 4);
893 proto_tree *gps_tree = proto_tree_add_subtree(tree, tvb, offset, 8 + nword*4, ETT_IDX_GPS_ASCII, NULL, "GPS ASCII");
894 proto_tree_add_item(gps_tree, hf_vrt_context_gps_ascii_oui, tvb, offset + 1, 3, ENC_BIG_ENDIAN);
895 proto_tree_add_item(gps_tree, hf_vrt_context_gps_ascii_size, tvb, offset + 4, 4, ENC_BIG_ENDIAN);
897 if (nword > 0) {
898 proto_tree_add_item(gps_tree, hf_vrt_context_gps_ascii_data, tvb, offset + 8, nword*4, ENC_NA);
901 return nword*4;
904 static int dissect_context_ins(proto_tree *tree, tvbuff_t *tvb, int offset) {
905 proto_tree *ins_tree = proto_tree_add_subtree(tree, tvb, offset, 44, ETT_IDX_INS, NULL, "Formatted INS");
906 dissect_context_formatted_gps_ins(&hf_vrt_context_ins, ins_tree, tvb, offset);
907 return 0;
910 static int dissect_context_phase_offset(proto_tree *tree, tvbuff_t *tvb, int offset) {
911 proto_tree_add_item(tree, hf_vrt_context_phase_offset, tvb, offset + 2, 2, ENC_BIG_ENDIAN);
912 return 0;
915 static int dissect_context_polarization(proto_tree *tree, tvbuff_t *tvb, int offset) {
916 proto_tree *pol_tree = proto_tree_add_subtree(tree, tvb, offset, 4, ETT_IDX_POL, NULL, "Polarization");
917 proto_tree_add_item(pol_tree, hf_vrt_context_pol_tilt, tvb, offset, 2, ENC_BIG_ENDIAN);
918 proto_tree_add_item(pol_tree, hf_vrt_context_pol_ellipticity, tvb, offset + 2, 2, ENC_BIG_ENDIAN);
919 return 0;
922 static int dissect_context_ref_level(proto_tree *tree, tvbuff_t *tvb, int offset) {
923 proto_tree_add_item(tree, hf_vrt_context_ref_level, tvb, offset + 2, 2, ENC_BIG_ENDIAN);
924 return 0;
927 static int dissect_context_rel_ephemeris(proto_tree *tree, tvbuff_t *tvb, int offset) {
928 proto_tree *rel_tree = proto_tree_add_subtree(tree, tvb, offset, 52, ETT_IDX_REL_EPHEM, NULL, "Relative ephemeris");
929 dissect_context_ephemeris(&hf_vrt_context_rel_ephemeris, rel_tree, tvb, offset);
930 return 0;
933 static int dissect_context_signal_data_format(proto_tree *tree, tvbuff_t *tvb, int offset) {
934 proto_tree *format_tree = proto_tree_add_subtree(tree, tvb, offset, 8, ETT_IDX_SIGNAL_DATA_FORMAT, NULL,
935 "Signal data packet payload format");
936 proto_tree_add_item(format_tree, hf_vrt_context_signal_data_format_packing, tvb, offset, 1, ENC_BIG_ENDIAN);
937 proto_tree_add_item(format_tree, hf_vrt_context_signal_data_format_type, tvb, offset, 1, ENC_BIG_ENDIAN);
938 proto_tree_add_item(format_tree, hf_vrt_context_signal_data_format_item, tvb, offset, 1, ENC_BIG_ENDIAN);
939 offset += 1;
940 proto_tree_add_item(format_tree, hf_vrt_context_signal_data_format_repeat, tvb, offset, 1, ENC_BIG_ENDIAN);
941 proto_tree_add_item(format_tree, hf_vrt_context_signal_data_format_event_size, tvb, offset, 1, ENC_BIG_ENDIAN);
942 proto_tree_add_item(format_tree, hf_vrt_context_signal_data_format_channel_size, tvb, offset, 1, ENC_BIG_ENDIAN);
943 offset += 1;
944 proto_tree_add_item(format_tree, hf_vrt_context_signal_data_format_fraction_size, tvb, offset, 2, ENC_BIG_ENDIAN);
945 proto_tree_add_item(format_tree, hf_vrt_context_signal_data_format_packing_size, tvb, offset, 2, ENC_BIG_ENDIAN);
946 proto_tree_add_item(format_tree, hf_vrt_context_signal_data_format_item_size, tvb, offset, 2, ENC_BIG_ENDIAN);
947 offset += 2;
948 proto_tree_add_item(format_tree, hf_vrt_context_signal_data_format_repeat_count, tvb, offset, 2, ENC_BIG_ENDIAN);
949 offset += 2;
950 proto_tree_add_item(format_tree, hf_vrt_context_signal_data_format_vector_size, tvb, offset, 2, ENC_BIG_ENDIAN);
952 return 0;
955 static int dissect_context_state_event(proto_tree *tree, tvbuff_t *tvb, int offset) {
956 proto_tree *state_event_tree = proto_tree_add_subtree(tree, tvb, offset, 4, ETT_IDX_STATE_EVENT, NULL,
957 "State and event indicators");
958 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_en_cal_time, tvb, offset, 1, ENC_BIG_ENDIAN);
959 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_en_valid_data, tvb, offset, 1, ENC_BIG_ENDIAN);
960 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_en_ref_lock, tvb, offset, 1, ENC_BIG_ENDIAN);
961 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_en_agc, tvb, offset, 1, ENC_BIG_ENDIAN);
962 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_en_detected_sig, tvb, offset, 1, ENC_BIG_ENDIAN);
963 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_en_spectral_inv, tvb, offset, 1, ENC_BIG_ENDIAN);
964 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_en_over_range, tvb, offset, 1, ENC_BIG_ENDIAN);
965 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_en_sample_loss, tvb, offset, 1, ENC_BIG_ENDIAN);
967 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_cal_time, tvb, offset + 1, 1, ENC_BIG_ENDIAN);
968 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_valid_data, tvb, offset + 1, 1, ENC_BIG_ENDIAN);
969 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_ref_lock, tvb, offset + 1, 1, ENC_BIG_ENDIAN);
970 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_agc, tvb, offset + 1, 1, ENC_BIG_ENDIAN);
971 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_detected_sig, tvb, offset + 2, 1, ENC_BIG_ENDIAN);
972 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_spectral_inv, tvb, offset + 2, 1, ENC_BIG_ENDIAN);
973 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_over_range, tvb, offset + 2, 1, ENC_BIG_ENDIAN);
974 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_sample_loss, tvb, offset + 2, 1, ENC_BIG_ENDIAN);
976 proto_tree_add_item(state_event_tree, hf_vrt_context_state_event_user, tvb, offset + 3, 1, ENC_BIG_ENDIAN);
977 return 0;
980 static int dissect_context_temperature(proto_tree *tree, tvbuff_t *tvb, int offset) {
981 proto_tree_add_item(tree, hf_vrt_context_temperature, tvb, offset + 2, 2, ENC_BIG_ENDIAN);
982 return 0;
985 static int dissect_context_ver(proto_tree *tree, tvbuff_t *tvb, int offset) {
986 proto_tree *ver_tree = proto_tree_add_subtree(tree, tvb, offset, 4, ETT_IDX_VER, NULL,
987 "Version and build code");
988 proto_tree_add_item(ver_tree, hf_vrt_context_ver_year, tvb, offset, 2, ENC_BIG_ENDIAN);
989 proto_tree_add_item(ver_tree, hf_vrt_context_ver_day, tvb, offset, 2, ENC_BIG_ENDIAN);
990 proto_tree_add_item(ver_tree, hf_vrt_context_ver_rev, tvb, offset + 2, 2, ENC_BIG_ENDIAN);
991 proto_tree_add_item(ver_tree, hf_vrt_context_ver_user, tvb, offset + 2, 2, ENC_BIG_ENDIAN);
992 return 0;
995 static int dissect_context_spectrum(proto_tree *tree, tvbuff_t *tvb, int offset) {
996 proto_tree *spectrum_tree = proto_tree_add_subtree(tree, tvb, offset, 52, ETT_IDX_SPECTRUM, NULL, "Spectrum");
997 proto_tree_add_item(spectrum_tree, hf_vrt_context_spectrum_spectrum_type, tvb, offset, 4, ENC_BIG_ENDIAN);
998 proto_tree_add_item(spectrum_tree, hf_vrt_context_spectrum_window_type, tvb, offset + 4, 4, ENC_BIG_ENDIAN);
999 proto_tree_add_item(spectrum_tree, hf_vrt_context_spectrum_num_transform_points, tvb, offset + 8, 4, ENC_BIG_ENDIAN);
1000 proto_tree_add_item(spectrum_tree, hf_vrt_context_spectrum_num_window_points, tvb, offset + 12, 4, ENC_BIG_ENDIAN);
1001 proto_tree_add_item(spectrum_tree, hf_vrt_context_spectrum_resolution, tvb, offset + 16, 8, ENC_BIG_ENDIAN);
1002 proto_tree_add_item(spectrum_tree, hf_vrt_context_spectrum_span, tvb, offset + 24, 8, ENC_BIG_ENDIAN);
1003 proto_tree_add_item(spectrum_tree, hf_vrt_context_spectrum_num_averages, tvb, offset + 32, 4, ENC_BIG_ENDIAN);
1004 proto_tree_add_item(spectrum_tree, hf_vrt_context_spectrum_weighting_factor, tvb, offset + 36, 4, ENC_BIG_ENDIAN);
1005 proto_tree_add_item(spectrum_tree, hf_vrt_context_spectrum_spectrum_f1_index, tvb, offset + 40, 4, ENC_BIG_ENDIAN);
1006 proto_tree_add_item(spectrum_tree, hf_vrt_context_spectrum_spectrum_f2_index, tvb, offset + 44, 4, ENC_BIG_ENDIAN);
1007 proto_tree_add_item(spectrum_tree, hf_vrt_context_spectrum_window_time_delta, tvb, offset + 48, 4, ENC_BIG_ENDIAN);
1008 return 0;
1011 static void format_celsius(char *str, int16_t val) {
1012 snprintf(str, ITEM_LABEL_LENGTH, "%f °C", (double)val*RADIX_CELSIUS);
1015 static void format_decibel(char *str, int16_t val) {
1016 snprintf(str, ITEM_LABEL_LENGTH, "%f dB", (double)val*RADIX_DECIBEL);
1019 static void format_decibel_milliwatt(char *str, int16_t val) {
1020 snprintf(str, ITEM_LABEL_LENGTH, "%f dBm", (double)val*RADIX_DECIBEL_MILLIWATT);
1023 static void format_degrees(char *str, int32_t val) {
1024 snprintf(str, ITEM_LABEL_LENGTH, "%f degrees", (double)val*RADIX_DEGREES);
1027 static void format_hertz(char *str, int64_t val) {
1028 double val_f64 = (double)val*RADIX_HERTZ;
1029 const char *prefix = get_engr_prefix(&val_f64);
1030 snprintf(str, ITEM_LABEL_LENGTH, "%f %sHz", val_f64, prefix);
1033 static void format_meter(char *str, int32_t val) {
1034 double val_f64 = (double)val*RADIX_METER;
1035 const char *prefix = get_engr_prefix(&val_f64);
1036 snprintf(str, ITEM_LABEL_LENGTH, "%f %sm", val_f64, prefix);
1039 static void format_meter_unsigned(char *str, uint32_t val) {
1040 double val_f64 = (double)val*RADIX_METER_UNSIGNED;
1041 const char *prefix = get_engr_prefix(&val_f64);
1042 snprintf(str, ITEM_LABEL_LENGTH, "%f %sm", val_f64, prefix);
1045 static void format_meters_per_second(char *str, int32_t val) {
1046 double val_f64 = (double)val*RADIX_METERS_PER_SECOND;
1047 const char *prefix = get_engr_prefix(&val_f64);
1048 snprintf(str, ITEM_LABEL_LENGTH, "%f %sm/s", val_f64, prefix);
1051 static void format_radian_phase(char *str, int16_t val) {
1052 snprintf(str, ITEM_LABEL_LENGTH, "%f rad", (double)val*RADIX_RADIAN_PHASE);
1055 static void format_radian_pol(char *str, int16_t val) {
1056 snprintf(str, ITEM_LABEL_LENGTH, "%f rad", (double)val*RADIX_RADIAN_POL);
1059 static void format_second(char *str, int64_t val) {
1060 double val_f64 = (double)val*FEMTOSEC_PER_SEC;
1061 const char *prefix = get_engr_prefix(&val_f64);
1062 snprintf(str, ITEM_LABEL_LENGTH, "%f %ss", val_f64, prefix);
1065 static const char* get_engr_prefix(double *val) {
1066 const char* prefix_str = "";
1067 int32_t exp = (int32_t)floor(log10(fabs(*val))/(double)3.0)*3;
1069 switch (exp) {
1070 case -15:
1071 prefix_str = "f";
1072 *val *= 1e15;
1073 break;
1074 case -12:
1075 prefix_str = "p";
1076 *val *= 1e12;
1077 break;
1078 case -9:
1079 prefix_str = "n";
1080 *val *= 1e9;
1081 break;
1082 case -6:
1083 prefix_str = "µ";
1084 *val *= 1e6;
1085 break;
1086 case -3:
1087 prefix_str = "m";
1088 *val *= 1e3;
1089 break;
1090 case 3:
1091 prefix_str = "k";
1092 *val *= 1e-3;
1093 break;
1094 case 6:
1095 prefix_str = "M";
1096 *val *= 1e-6;
1097 break;
1098 case 9:
1099 prefix_str = "G";
1100 *val *= 1e-9;
1101 break;
1102 case 12:
1103 prefix_str = "T";
1104 *val *= 1e-12;
1105 break;
1108 return prefix_str;
1111 void
1112 proto_register_vrt(void)
1114 module_t *vrt_module;
1116 static hf_register_info hf[] = {
1117 { &hf_vrt_header,
1118 { "VRT header", "vrt.hdr",
1119 FT_UINT32, BASE_HEX,
1120 NULL, 0x00,
1121 NULL, HFILL }
1123 { &hf_vrt_type,
1124 { "Packet type", "vrt.type",
1125 FT_UINT8, BASE_DEC,
1126 VALS(packet_types), 0xF0,
1127 NULL, HFILL }
1129 { &hf_vrt_cidflag,
1130 { "Class ID included", "vrt.cidflag",
1131 FT_BOOLEAN, 8,
1132 NULL, 0x08,
1133 NULL, HFILL }
1135 { &hf_vrt_tflag,
1136 { "Trailer included", "vrt.tflag",
1137 FT_BOOLEAN, 8,
1138 NULL, 0x04,
1139 NULL, HFILL }
1141 { &hf_vrt_tsmflag,
1142 { "Timestamp mode", "vrt.tsmflag",
1143 FT_UINT8, BASE_DEC,
1144 VALS(tsm_types), 0x01,
1145 NULL, HFILL }
1147 { &hf_vrt_tsi,
1148 { "Integer timestamp type", "vrt.tsi",
1149 FT_UINT8, BASE_DEC,
1150 VALS(tsi_types), 0xC0,
1151 NULL, HFILL }
1153 { &hf_vrt_tsf,
1154 { "Fractional timestamp type", "vrt.tsf",
1155 FT_UINT8, BASE_DEC,
1156 VALS(tsf_types), 0x30,
1157 NULL, HFILL }
1159 { &hf_vrt_seq,
1160 { "Sequence number", "vrt.seq",
1161 FT_UINT8, BASE_DEC,
1162 NULL, 0x0F,
1163 NULL, HFILL }
1165 { &hf_vrt_len,
1166 { "Length", "vrt.len",
1167 FT_UINT16, BASE_DEC,
1168 NULL, 0x00,
1169 NULL, HFILL }
1171 { &hf_vrt_ts_int,
1172 { "Integer timestamp", "vrt.ts_int",
1173 FT_UINT32, BASE_DEC,
1174 NULL, 0x00,
1175 NULL, HFILL }
1177 { &hf_vrt_ts_frac_sample,
1178 { "Fractional timestamp (samples)", "vrt.ts_frac_sample",
1179 FT_UINT64, BASE_DEC,
1180 NULL, 0x00,
1181 NULL, HFILL }
1183 { &hf_vrt_ts_frac_picosecond,
1184 { "Fractional timestamp (picoseconds)", "vrt.ts_frac_picosecond",
1185 FT_UINT64, BASE_DEC,
1186 NULL, 0x00,
1187 NULL, HFILL }
1189 { &hf_vrt_sid,
1190 { "Stream ID", "vrt.sid",
1191 FT_UINT32, BASE_HEX,
1192 NULL, 0x00,
1193 NULL, HFILL }
1195 { &hf_vrt_cid,
1196 { "Class ID", "vrt.cid",
1197 FT_UINT64, BASE_HEX,
1198 NULL, 0x00,
1199 NULL, HFILL }
1201 { &hf_vrt_cif[0],
1202 { "CIF0", "vrt.cif0",
1203 FT_UINT32, BASE_HEX,
1204 NULL, 0x00,
1205 NULL, HFILL }
1207 { &hf_vrt_cif0_change_flag,
1208 { "Context field change indicator", "vrt.cif0.change",
1209 FT_BOOLEAN, 8,
1210 NULL, 0x80,
1211 NULL, HFILL }
1213 { &hf_vrt_cif0_ref_pt_id,
1214 { "Reference point identifier", "vrt.cif0.refptid",
1215 FT_BOOLEAN, 8,
1216 NULL, 0x40,
1217 NULL, HFILL }
1219 { &hf_vrt_cif0_bandwidth,
1220 { "Bandwidth", "vrt.cif0.bw",
1221 FT_BOOLEAN, 8,
1222 NULL, 0x20,
1223 NULL, HFILL }
1225 { &hf_vrt_cif0_if_freq,
1226 { "IF reference frequency", "vrt.cif0.iffreq",
1227 FT_BOOLEAN, 8,
1228 NULL, 0x10,
1229 NULL, HFILL }
1231 { &hf_vrt_cif0_rf_freq,
1232 { "RF reference frequency", "vrt.cif0.rffreq",
1233 FT_BOOLEAN, 8,
1234 NULL, 0x08,
1235 NULL, HFILL }
1237 { &hf_vrt_cif0_rf_freq_offset,
1238 { "RF reference frequency offset", "vrt.cif0.rffreqoffset",
1239 FT_BOOLEAN, 8,
1240 NULL, 0x04,
1241 NULL, HFILL }
1243 { &hf_vrt_cif0_if_band_offset,
1244 { "IF band offset", "vrt.cif0.ifbandoffset",
1245 FT_BOOLEAN, 8,
1246 NULL, 0x02,
1247 NULL, HFILL }
1249 { &hf_vrt_cif0_ref_level,
1250 { "Reference level", "vrt.cif0.reflevel",
1251 FT_BOOLEAN, 8,
1252 NULL, 0x01,
1253 NULL, HFILL }
1255 { &hf_vrt_cif0_gain,
1256 { "Gain", "vrt.cif0.gain",
1257 FT_BOOLEAN, 8,
1258 NULL, 0x80,
1259 NULL, HFILL }
1261 { &hf_vrt_cif0_over_range_count,
1262 { "Over-range count", "vrt.cif0.overrangecount",
1263 FT_BOOLEAN, 8,
1264 NULL, 0x40,
1265 NULL, HFILL }
1267 { &hf_vrt_cif0_sample_rate,
1268 { "Sample rate", "vrt.cif0.samplerate",
1269 FT_BOOLEAN, 8,
1270 NULL, 0x20,
1271 NULL, HFILL }
1273 { &hf_vrt_cif0_timestamp_adjust,
1274 { "Timestamp adjustment", "vrt.cif0.timestampadjust",
1275 FT_BOOLEAN, 8,
1276 NULL, 0x10,
1277 NULL, HFILL }
1279 { &hf_vrt_cif0_timestamp_cal,
1280 { "Timestamp calibration time", "vrt.cif0.timestampcal",
1281 FT_BOOLEAN, 8,
1282 NULL, 0x08,
1283 NULL, HFILL }
1285 { &hf_vrt_cif0_temperature,
1286 { "Temperature", "vrt.cif0.temperature",
1287 FT_BOOLEAN, 8,
1288 NULL, 0x04,
1289 NULL, HFILL }
1291 { &hf_vrt_cif0_device_id,
1292 { "Device identifier", "vrt.cif0.deviceid",
1293 FT_BOOLEAN, 8,
1294 NULL, 0x02,
1295 NULL, HFILL }
1297 { &hf_vrt_cif0_state_event,
1298 { "State/event indicators", "vrt.cif0.stateevent",
1299 FT_BOOLEAN, 8,
1300 NULL, 0x01,
1301 NULL, HFILL }
1303 { &hf_vrt_cif0_signal_data_format,
1304 { "Signal data format", "vrt.cif0.signaldataformat",
1305 FT_BOOLEAN, 8,
1306 NULL, 0x80,
1307 NULL, HFILL }
1309 { &hf_vrt_cif0_gps,
1310 { "Formatted GPS", "vrt.cif0.gps",
1311 FT_BOOLEAN, 8,
1312 NULL, 0x40,
1313 NULL, HFILL }
1315 { &hf_vrt_cif0_ins,
1316 { "Formatted INS", "vrt.cif0.ins",
1317 FT_BOOLEAN, 8,
1318 NULL, 0x20,
1319 NULL, HFILL }
1321 { &hf_vrt_cif0_ecef_ephemeris,
1322 { "ECEF ephemeris", "vrt.cif0.ecefephem",
1323 FT_BOOLEAN, 8,
1324 NULL, 0x10,
1325 NULL, HFILL }
1327 { &hf_vrt_cif0_rel_ephemeris,
1328 { "Relative ephemeris", "vrt.cif0.relephem",
1329 FT_BOOLEAN, 8,
1330 NULL, 0x08,
1331 NULL, HFILL }
1333 { &hf_vrt_cif0_ephemeris_ref_id,
1334 { "Ephemeris ref ID", "vrt.cif0.ephemrefid",
1335 FT_BOOLEAN, 8,
1336 NULL, 0x04,
1337 NULL, HFILL }
1339 { &hf_vrt_cif0_gps_ascii,
1340 { "GPS ASCII", "vrt.cif0.gpsascii",
1341 FT_BOOLEAN, 8,
1342 NULL, 0x02,
1343 NULL, HFILL }
1345 { &hf_vrt_cif0_context_assoc_lists,
1346 { "Context association lists", "vrt.cif0.assoclists",
1347 FT_BOOLEAN, 8,
1348 NULL, 0x01,
1349 NULL, HFILL }
1351 { &hf_vrt_cif0_cif7,
1352 { "CIF7", "vrt.cif0.cif7",
1353 FT_BOOLEAN, 8,
1354 NULL, 0x80,
1355 NULL, HFILL }
1357 { &hf_vrt_cif0_cif6,
1358 { "CIF6", "vrt.cif0.cif6",
1359 FT_BOOLEAN, 8,
1360 NULL, 0x40,
1361 NULL, HFILL }
1363 { &hf_vrt_cif0_cif5,
1364 { "CIF5", "vrt.cif0.cif5",
1365 FT_BOOLEAN, 8,
1366 NULL, 0x20,
1367 NULL, HFILL }
1369 { &hf_vrt_cif0_cif4,
1370 { "CIF4", "vrt.cif0.cif4",
1371 FT_BOOLEAN, 8,
1372 NULL, 0x10,
1373 NULL, HFILL }
1375 { &hf_vrt_cif0_cif3,
1376 { "CIF3", "vrt.cif0.cif3",
1377 FT_BOOLEAN, 8,
1378 NULL, 0x08,
1379 NULL, HFILL }
1381 { &hf_vrt_cif0_cif2,
1382 { "CIF2", "vrt.cif0.cif2",
1383 FT_BOOLEAN, 8,
1384 NULL, 0x04,
1385 NULL, HFILL }
1387 { &hf_vrt_cif0_cif1,
1388 { "CIF1", "vrt.cif0.cif1",
1389 FT_BOOLEAN, 8,
1390 NULL, 0x02,
1391 NULL, HFILL }
1393 { &hf_vrt_cif1_phase_offset,
1394 { "Phase offset", "vrt.cif1.phaseoffset",
1395 FT_BOOLEAN, 8,
1396 NULL, 0x80,
1397 NULL, HFILL }
1399 { &hf_vrt_cif1_polarization,
1400 { "Polarization", "vrt.cif1.polarization",
1401 FT_BOOLEAN, 8,
1402 NULL, 0x40,
1403 NULL, HFILL }
1405 { &hf_vrt_cif1_range,
1406 { "Range (distance)", "vrt.cif1.range",
1407 FT_BOOLEAN, 8,
1408 NULL, 0x01,
1409 NULL, HFILL }
1411 { &hf_vrt_cif1_aux_freq,
1412 { "Aux frequency", "vrt.cif1.auxfreq",
1413 FT_BOOLEAN, 8,
1414 NULL, 0x80,
1415 NULL, HFILL }
1417 { &hf_vrt_cif1_aux_bandwidth,
1418 { "Aux bandwidth", "vrt.cif1.auxbw",
1419 FT_BOOLEAN, 8,
1420 NULL, 0x20,
1421 NULL, HFILL }
1423 { &hf_vrt_cif1_spectrum,
1424 { "Spectrum", "vrt.cif1.spectrum",
1425 FT_BOOLEAN, 8,
1426 NULL, 0x04,
1427 NULL, HFILL }
1429 { &hf_vrt_cif1_io32,
1430 { "Discrete I/O (32-bit)", "vrt.cif1.io32",
1431 FT_BOOLEAN, 8,
1432 NULL, 0x40,
1433 NULL, HFILL }
1435 { &hf_vrt_cif1_io64,
1436 { "Discrete I/O (64-bit)", "vrt.cif1.io64",
1437 FT_BOOLEAN, 8,
1438 NULL, 0x20,
1439 NULL, HFILL }
1441 { &hf_vrt_cif1_v49_spec,
1442 { "V49 spec compliance", "vrt.cif1.v49spec",
1443 FT_BOOLEAN, 8,
1444 NULL, 0x08,
1445 NULL, HFILL }
1447 { &hf_vrt_cif1_ver,
1448 { "Version and build code", "vrt.cif1.ver",
1449 FT_BOOLEAN, 8,
1450 NULL, 0x04,
1451 NULL, HFILL }
1453 { &hf_vrt_cif[1],
1454 { "CIF1", "vrt.cif1",
1455 FT_UINT32, BASE_HEX,
1456 NULL, 0x00,
1457 NULL, HFILL }
1459 { &hf_vrt_cif[2],
1460 { "CIF2", "vrt.cif2",
1461 FT_UINT32, BASE_HEX,
1462 NULL, 0x00,
1463 NULL, HFILL }
1465 { &hf_vrt_cif[3],
1466 { "CIF3", "vrt.cif3",
1467 FT_UINT32, BASE_HEX,
1468 NULL, 0x00,
1469 NULL, HFILL }
1471 { &hf_vrt_cif[4],
1472 { "CIF4", "vrt.cif4",
1473 FT_UINT32, BASE_HEX,
1474 NULL, 0x00,
1475 NULL, HFILL }
1477 { &hf_vrt_cif[5],
1478 { "CIF5", "vrt.cif5",
1479 FT_UINT32, BASE_HEX,
1480 NULL, 0x00,
1481 NULL, HFILL }
1483 { &hf_vrt_cif[6],
1484 { "CIF6", "vrt.cif6",
1485 FT_UINT32, BASE_HEX,
1486 NULL, 0x00,
1487 NULL, HFILL }
1489 { &hf_vrt_cif[7],
1490 { "CIF7", "vrt.cif7",
1491 FT_UINT32, BASE_HEX,
1492 NULL, 0x00,
1493 NULL, HFILL }
1495 { &hf_vrt_context_ref_pt_id,
1496 { "Reference point identifier", "vrt.context.refptid",
1497 FT_UINT32, BASE_DEC,
1498 NULL, 0x00,
1499 NULL, HFILL }
1501 { &hf_vrt_context_bandwidth,
1502 { "Bandwidth", "vrt.context.bw",
1503 FT_INT64, BASE_CUSTOM,
1504 CF_FUNC(format_hertz), 0x00,
1505 NULL, HFILL }
1507 { &hf_vrt_context_if_freq,
1508 { "IF reference frequency", "vrt.context.iffreq",
1509 FT_INT64, BASE_CUSTOM,
1510 CF_FUNC(format_hertz), 0x00,
1511 NULL, HFILL }
1513 { &hf_vrt_context_rf_freq,
1514 { "RF reference frequency", "vrt.context.rffreq",
1515 FT_INT64, BASE_CUSTOM,
1516 CF_FUNC(format_hertz), 0x00,
1517 NULL, HFILL }
1519 { &hf_vrt_context_rf_freq_offset,
1520 { "RF reference frequency offset", "vrt.context.rffreqoffset",
1521 FT_INT64, BASE_CUSTOM,
1522 CF_FUNC(format_hertz), 0x00,
1523 NULL, HFILL }
1525 { &hf_vrt_context_if_band_offset,
1526 { "IF band offset", "vrt.context.ifbandoffset",
1527 FT_INT64, BASE_CUSTOM,
1528 CF_FUNC(format_hertz), 0x00,
1529 NULL, HFILL }
1531 { &hf_vrt_context_ref_level,
1532 { "Reference level", "vrt.context.reflevel",
1533 FT_INT16, BASE_CUSTOM,
1534 CF_FUNC(format_decibel_milliwatt), 0x00,
1535 NULL, HFILL }
1537 { &hf_vrt_context_gain_stage2,
1538 { "Stage 2", "vrt.context.gain.stage2",
1539 FT_INT16, BASE_CUSTOM,
1540 CF_FUNC(format_decibel), 0x00,
1541 NULL, HFILL }
1543 { &hf_vrt_context_gain_stage1,
1544 { "Stage 1", "vrt.context.gain.stage1",
1545 FT_INT16, BASE_CUSTOM,
1546 CF_FUNC(format_decibel), 0x00,
1547 NULL, HFILL }
1549 { &hf_vrt_context_over_range_count,
1550 { "Over-range count", "vrt.context.overrangecount",
1551 FT_UINT32, BASE_DEC,
1552 NULL, 0x00,
1553 NULL, HFILL }
1555 { &hf_vrt_context_sample_rate,
1556 { "Sample rate", "vrt.context.samplerate",
1557 FT_INT64, BASE_CUSTOM,
1558 CF_FUNC(format_hertz), 0x00,
1559 NULL, HFILL }
1561 { &hf_vrt_context_timestamp_adjust,
1562 { "Timestamp adjustment", "vrt.context.timestampadjust",
1563 FT_INT64, BASE_CUSTOM,
1564 CF_FUNC(format_second), 0x00,
1565 NULL, HFILL }
1567 { &hf_vrt_context_timestamp_cal,
1568 { "Timestamp calibration", "vrt.context.timestampcal",
1569 FT_UINT32, BASE_DEC,
1570 NULL, 0x00,
1571 NULL, HFILL }
1573 { &hf_vrt_context_temperature,
1574 { "Device temperature", "vrt.context.temperature",
1575 FT_INT16, BASE_CUSTOM,
1576 CF_FUNC(format_celsius), 0x00,
1577 NULL, HFILL }
1579 { &hf_vrt_context_device_id_oui,
1580 { "Manufacturer OUI", "vrt.context.deviceid.oui",
1581 FT_UINT24, BASE_HEX,
1582 NULL, 0x00,
1583 NULL, HFILL }
1585 { &hf_vrt_context_device_id_code,
1586 { "Device code", "vrt.context.deviceid.code",
1587 FT_UINT16, BASE_DEC,
1588 NULL, 0x00,
1589 NULL, HFILL }
1591 { &hf_vrt_context_state_event_en_cal_time,
1592 { "Calibrated time enable", "vrt.context.stateevent.caltime.en",
1593 FT_BOOLEAN, 8,
1594 NULL, 0x80,
1595 NULL, HFILL }
1597 { &hf_vrt_context_state_event_en_valid_data,
1598 { "Valid data enable", "vrt.context.stateevent.validdata.en",
1599 FT_BOOLEAN, 8,
1600 NULL, 0x40,
1601 NULL, HFILL }
1603 { &hf_vrt_context_state_event_en_ref_lock,
1604 { "Reference lock enable", "vrt.context.stateevent.reflock.en",
1605 FT_BOOLEAN, 8,
1606 NULL, 0x20,
1607 NULL, HFILL }
1609 { &hf_vrt_context_state_event_en_agc,
1610 { "AGC/MGC enable", "vrt.context.stateevent.agc.en",
1611 FT_BOOLEAN, 8,
1612 NULL, 0x10,
1613 NULL, HFILL }
1615 { &hf_vrt_context_state_event_en_detected_sig,
1616 { "Detected signal enable", "vrt.context.stateevent.detectedsignal.en",
1617 FT_BOOLEAN, 8,
1618 NULL, 0x08,
1619 NULL, HFILL }
1621 { &hf_vrt_context_state_event_en_spectral_inv,
1622 { "Spectral inversion enable", "vrt.context.stateevent.spectralinv.en",
1623 FT_BOOLEAN, 8,
1624 NULL, 0x04,
1625 NULL, HFILL }
1627 { &hf_vrt_context_state_event_en_over_range,
1628 { "Over-range enable", "vrt.context.stateevent.overrange.en",
1629 FT_BOOLEAN, 8,
1630 NULL, 0x02,
1631 NULL, HFILL }
1633 { &hf_vrt_context_state_event_en_sample_loss,
1634 { "Sample loss enable", "vrt.cif0.context.sampleloss.en",
1635 FT_BOOLEAN, 8,
1636 NULL, 0x01,
1637 NULL, HFILL }
1639 { &hf_vrt_context_state_event_cal_time,
1640 { "Calibrated time indicator", "vrt.context.stateevent.caltime.val",
1641 FT_BOOLEAN, 8,
1642 NULL, 0x08,
1643 NULL, HFILL }
1645 { &hf_vrt_context_state_event_valid_data,
1646 { "Valid data indicator", "vrt.context.stateevent.validdata.val",
1647 FT_BOOLEAN, 8,
1648 NULL, 0x04,
1649 NULL, HFILL }
1651 { &hf_vrt_context_state_event_ref_lock,
1652 { "Reference lock indicator", "vrt.context.stateevent.reflock.val",
1653 FT_BOOLEAN, 8,
1654 NULL, 0x02,
1655 NULL, HFILL }
1657 { &hf_vrt_context_state_event_agc,
1658 { "AGC/MGC indicator", "vrt.context.stateevent.agc.val",
1659 FT_BOOLEAN, 8,
1660 NULL, 0x01,
1661 NULL, HFILL }
1663 { &hf_vrt_context_state_event_detected_sig,
1664 { "Detected signal indicator", "vrt.context.stateevent.detectedsignal.val",
1665 FT_BOOLEAN, 8,
1666 NULL, 0x80,
1667 NULL, HFILL }
1669 { &hf_vrt_context_state_event_spectral_inv,
1670 { "Spectral inversion indicator", "vrt.context.stateevent.spectralinv.val",
1671 FT_BOOLEAN, 8,
1672 NULL, 0x40,
1673 NULL, HFILL }
1675 { &hf_vrt_context_state_event_over_range,
1676 { "Over-range indicator", "vrt.context.stateevent.overrange.val",
1677 FT_BOOLEAN, 8,
1678 NULL, 0x20,
1679 NULL, HFILL }
1681 { &hf_vrt_context_state_event_sample_loss,
1682 { "Sample loss indicator", "vrt.context.stateevent.sampleloss.val",
1683 FT_BOOLEAN, 8,
1684 NULL, 0x10,
1685 NULL, HFILL }
1687 { &hf_vrt_context_state_event_user,
1688 { "User-defined", "vrt.context.stateevent.user",
1689 FT_UINT8, BASE_HEX,
1690 NULL, 0x00,
1691 NULL, HFILL }
1693 { &hf_vrt_context_signal_data_format_packing,
1694 { "Packing method", "vrt.context.signaldataformat.packing",
1695 FT_UINT8, BASE_DEC,
1696 VALS(packing_method), 0x80,
1697 NULL, HFILL }
1699 { &hf_vrt_context_signal_data_format_type,
1700 { "Real/complex type", "vrt.context.signaldataformat.realcomplex",
1701 FT_UINT8, BASE_DEC,
1702 VALS(data_sample_type), 0x60,
1703 NULL, HFILL }
1705 { &hf_vrt_context_signal_data_format_item,
1706 { "Data item format", "vrt.context.signaldataformat.format",
1707 FT_UINT8, BASE_DEC,
1708 VALS(data_item_format), 0x1F,
1709 NULL, HFILL }
1711 { &hf_vrt_context_signal_data_format_repeat,
1712 { "Sample-component repeat indicator", "vrt.context.signaldataformat.repeat",
1713 FT_BOOLEAN, 8,
1714 NULL, 0x80,
1715 NULL, HFILL }
1717 { &hf_vrt_context_signal_data_format_event_size,
1718 { "Event-tag size", "vrt.context.signaldataformat.eventsize",
1719 FT_UINT8, BASE_DEC,
1720 NULL, 0x70,
1721 NULL, HFILL }
1723 { &hf_vrt_context_signal_data_format_channel_size,
1724 { "Channel-tag size", "vrt.context.signaldataformat.channelsize",
1725 FT_UINT8, BASE_DEC,
1726 NULL, 0x0F,
1727 NULL, HFILL }
1729 { &hf_vrt_context_signal_data_format_fraction_size,
1730 { "Data item fraction size", "vrt.context.signaldataformat.fractionsize",
1731 FT_UINT16, BASE_DEC,
1732 NULL, 0xF000,
1733 NULL, HFILL }
1735 { &hf_vrt_context_signal_data_format_packing_size,
1736 { "Item packing field size", "vrt.context.signaldataformat.packingsize",
1737 FT_UINT16, BASE_DEC,
1738 NULL, 0x0FC0,
1739 NULL, HFILL }
1741 { &hf_vrt_context_signal_data_format_item_size,
1742 { "Data item size", "vrt.context.signaldataformat.itemsize",
1743 FT_UINT16, BASE_DEC,
1744 NULL, 0x003F,
1745 NULL, HFILL }
1747 { &hf_vrt_context_signal_data_format_repeat_count,
1748 { "Repeat count", "vrt.context.signaldataformat.repeatcount",
1749 FT_UINT16, BASE_DEC,
1750 NULL, 0x0,
1751 NULL, HFILL }
1753 { &hf_vrt_context_signal_data_format_vector_size,
1754 { "Vector size", "vrt.context.signaldataformat.vectorsize",
1755 FT_UINT16, BASE_DEC,
1756 NULL, 0,
1757 NULL, HFILL }
1759 { &hf_vrt_context_gps.tsi,
1760 { "Integer timestamp type", "vrt.context.gps.tsi",
1761 FT_UINT8, BASE_DEC,
1762 VALS(tsi_types), 0x0C,
1763 NULL, HFILL }
1765 { &hf_vrt_context_gps.tsf,
1766 { "Fractional timestamp type", "vrt.context.gps.tsf",
1767 FT_UINT8, BASE_DEC,
1768 VALS(tsf_types), 0x03,
1769 NULL, HFILL }
1771 { &hf_vrt_context_gps.oui,
1772 { "Manufacturer OUI", "vrt.context.gps.oui",
1773 FT_UINT24, BASE_HEX,
1774 NULL, 0x00,
1775 NULL, HFILL }
1777 { &hf_vrt_context_gps.ts_int,
1778 { "Integer timestamp of position fix", "vrt.context.gps.ts_int",
1779 FT_UINT32, BASE_DEC,
1780 NULL, 0x00,
1781 NULL, HFILL }
1783 { &hf_vrt_context_gps.ts_frac_sample,
1784 { "Fractional timestamp (samples)", "vrt.context.gps.ts_frac_sample",
1785 FT_UINT64, BASE_DEC,
1786 NULL, 0x00,
1787 NULL, HFILL }
1789 { &hf_vrt_context_gps.ts_picosecond,
1790 { "Fractional timestamp (picoseconds)", "vrt.context.gps.ts_frac_picosecond",
1791 FT_UINT64, BASE_DEC,
1792 NULL, 0x00,
1793 NULL, HFILL }
1795 { &hf_vrt_context_gps.lat,
1796 { "Latitude", "vrt.context.gps.lat",
1797 FT_INT32, BASE_CUSTOM,
1798 CF_FUNC(format_degrees), 0x00,
1799 NULL, HFILL }
1801 { &hf_vrt_context_gps.lon,
1802 { "Longitude", "vrt.context.gps.lon",
1803 FT_INT32, BASE_CUSTOM,
1804 CF_FUNC(format_degrees), 0x00,
1805 NULL, HFILL }
1807 { &hf_vrt_context_gps.alt,
1808 { "Altitude", "vrt.context.gps.alt",
1809 FT_INT32, BASE_CUSTOM,
1810 CF_FUNC(format_meter), 0x00,
1811 NULL, HFILL }
1813 { &hf_vrt_context_gps.speed,
1814 { "Speed over ground", "vrt.context.gps.speed",
1815 FT_INT32, BASE_CUSTOM,
1816 CF_FUNC(format_meters_per_second), 0x00,
1817 NULL, HFILL }
1819 { &hf_vrt_context_gps.heading,
1820 { "Heading angle", "vrt.context.gps.heading",
1821 FT_INT32, BASE_CUSTOM,
1822 CF_FUNC(format_degrees), 0x00,
1823 NULL, HFILL }
1825 { &hf_vrt_context_gps.track,
1826 { "Track angle", "vrt.context.gps.track",
1827 FT_INT32, BASE_CUSTOM,
1828 CF_FUNC(format_degrees), 0x00,
1829 NULL, HFILL }
1831 { &hf_vrt_context_gps.mag_var,
1832 { "Magnetic variation", "vrt.context.gps.mag_var",
1833 FT_INT32, BASE_CUSTOM,
1834 CF_FUNC(format_degrees), 0x00,
1835 NULL, HFILL }
1837 { &hf_vrt_context_ins.tsi,
1838 { "Integer timestamp type", "vrt.context.ins.tsi",
1839 FT_UINT8, BASE_DEC,
1840 VALS(tsi_types), 0x0C,
1841 NULL, HFILL }
1843 { &hf_vrt_context_ins.tsf,
1844 { "Fractional timestamp type", "vrt.context.ins.tsf",
1845 FT_UINT8, BASE_DEC,
1846 VALS(tsf_types), 0x03,
1847 NULL, HFILL }
1849 { &hf_vrt_context_ins.oui,
1850 { "Manufacturer OUI", "vrt.context.ins.oui",
1851 FT_UINT24, BASE_HEX,
1852 NULL, 0x00,
1853 NULL, HFILL }
1855 { &hf_vrt_context_ins.ts_int,
1856 { "Integer timestamp of position fix", "vrt.context.ins.ts_int",
1857 FT_UINT32, BASE_DEC,
1858 NULL, 0x00,
1859 NULL, HFILL }
1861 { &hf_vrt_context_ins.ts_frac_sample,
1862 { "Fractional timestamp (samples)", "vrt.context.ins.ts_frac_sample",
1863 FT_UINT64, BASE_DEC,
1864 NULL, 0x00,
1865 NULL, HFILL }
1867 { &hf_vrt_context_ins.ts_picosecond,
1868 { "Fractional timestamp (picoseconds)", "vrt.context.ins.ts_frac_picosecond",
1869 FT_UINT64, BASE_DEC,
1870 NULL, 0x00,
1871 NULL, HFILL }
1873 { &hf_vrt_context_ins.lat,
1874 { "Latitude", "vrt.context.ins.lat",
1875 FT_INT32, BASE_CUSTOM,
1876 CF_FUNC(format_degrees), 0x00,
1877 NULL, HFILL }
1879 { &hf_vrt_context_ins.lon,
1880 { "Longitude", "vrt.context.ins.lon",
1881 FT_INT32, BASE_CUSTOM,
1882 CF_FUNC(format_degrees), 0x00,
1883 NULL, HFILL }
1885 { &hf_vrt_context_ins.alt,
1886 { "Altitude", "vrt.context.ins.alt",
1887 FT_INT32, BASE_CUSTOM,
1888 CF_FUNC(format_meter), 0x00,
1889 NULL, HFILL }
1891 { &hf_vrt_context_ins.speed,
1892 { "Speed over ground", "vrt.context.ins.speed",
1893 FT_INT32, BASE_CUSTOM,
1894 CF_FUNC(format_meters_per_second), 0x00,
1895 NULL, HFILL }
1897 { &hf_vrt_context_ins.heading,
1898 { "Heading angle", "vrt.context.ins.heading",
1899 FT_INT32, BASE_CUSTOM,
1900 CF_FUNC(format_degrees), 0x00,
1901 NULL, HFILL }
1903 { &hf_vrt_context_ins.track,
1904 { "Track angle", "vrt.context.ins.track",
1905 FT_INT32, BASE_CUSTOM,
1906 CF_FUNC(format_degrees), 0x00,
1907 NULL, HFILL }
1909 { &hf_vrt_context_ins.mag_var,
1910 { "Magnetic variation", "vrt.context.ins.mag_var",
1911 FT_INT32, BASE_CUSTOM,
1912 CF_FUNC(format_degrees), 0x00,
1913 NULL, HFILL }
1915 { &hf_vrt_context_ecef_ephemeris.tsi,
1916 { "Integer timestamp type", "vrt.context.ecefephem.tsi",
1917 FT_UINT8, BASE_DEC,
1918 VALS(tsi_types), 0x0C,
1919 NULL, HFILL }
1921 { &hf_vrt_context_ecef_ephemeris.tsf,
1922 { "Fractional timestamp type", "vrt.context.ecefephem.tsf",
1923 FT_UINT8, BASE_DEC,
1924 VALS(tsf_types), 0x03,
1925 NULL, HFILL }
1927 { &hf_vrt_context_ecef_ephemeris.oui,
1928 { "Manufacturer OUI", "vrt.context.ecefephem.oui",
1929 FT_UINT24, BASE_HEX,
1930 NULL, 0x00,
1931 NULL, HFILL }
1933 { &hf_vrt_context_ecef_ephemeris.ts_int,
1934 { "Integer timestamp of position fix", "vrt.context.ecefephem.ts_int",
1935 FT_UINT32, BASE_DEC,
1936 NULL, 0x00,
1937 NULL, HFILL }
1939 { &hf_vrt_context_ecef_ephemeris.ts_frac_sample,
1940 { "Fractional timestamp (samples)", "vrt.context.ecefephem.ts_frac_sample",
1941 FT_UINT64, BASE_DEC,
1942 NULL, 0x00,
1943 NULL, HFILL }
1945 { &hf_vrt_context_ecef_ephemeris.ts_picosecond,
1946 { "Fractional timestamp (picoseconds)", "vrt.context.ecefephem.ts_frac_picosecond",
1947 FT_UINT64, BASE_DEC,
1948 NULL, 0x00,
1949 NULL, HFILL }
1951 { &hf_vrt_context_ecef_ephemeris.pos_x,
1952 { "Position X", "vrt.context.ecefephem.posx",
1953 FT_INT32, BASE_CUSTOM,
1954 CF_FUNC(format_meter), 0x00,
1955 NULL, HFILL }
1957 { &hf_vrt_context_ecef_ephemeris.pos_y,
1958 { "Position Y", "vrt.context.ecefephem.posy",
1959 FT_INT32, BASE_CUSTOM,
1960 CF_FUNC(format_meter), 0x00,
1961 NULL, HFILL }
1963 { &hf_vrt_context_ecef_ephemeris.pos_z,
1964 { "Position Z", "vrt.context.ecefephem.posz",
1965 FT_INT32, BASE_CUSTOM,
1966 CF_FUNC(format_meter), 0x00,
1967 NULL, HFILL }
1969 { &hf_vrt_context_ecef_ephemeris.att_alpha,
1970 { "Attitude alpha (α)", "vrt.context.ecefephem.attalpha",
1971 FT_INT32, BASE_CUSTOM,
1972 CF_FUNC(format_degrees), 0x00,
1973 NULL, HFILL }
1975 { &hf_vrt_context_ecef_ephemeris.att_beta,
1976 { "Attitude beta (β)", "vrt.context.ecefephem.attbeta",
1977 FT_INT32, BASE_CUSTOM,
1978 CF_FUNC(format_degrees), 0x00,
1979 NULL, HFILL }
1981 { &hf_vrt_context_ecef_ephemeris.att_phi,
1982 { "Attitude phi (φ)", "vrt.context.ecefephem.attphi",
1983 FT_INT32, BASE_CUSTOM,
1984 CF_FUNC(format_degrees), 0x00,
1985 NULL, HFILL }
1987 { &hf_vrt_context_ecef_ephemeris.vel_dx,
1988 { "Velocity dX", "vrt.context.ecefephem.veldx",
1989 FT_INT32, BASE_CUSTOM,
1990 CF_FUNC(format_meters_per_second), 0x00,
1991 NULL, HFILL }
1993 { &hf_vrt_context_ecef_ephemeris.vel_dy,
1994 { "Velocity dY", "vrt.context.ecefephem.veldy",
1995 FT_INT32, BASE_CUSTOM,
1996 CF_FUNC(format_meters_per_second), 0x00,
1997 NULL, HFILL }
1999 { &hf_vrt_context_ecef_ephemeris.vel_dz,
2000 { "Velocity dZ", "vrt.context.ecefephem.veldz",
2001 FT_INT32, BASE_CUSTOM,
2002 CF_FUNC(format_meters_per_second), 0x00,
2003 NULL, HFILL }
2005 { &hf_vrt_context_rel_ephemeris.tsi,
2006 { "Integer timestamp type", "vrt.context.relephem.tsi",
2007 FT_UINT8, BASE_DEC,
2008 VALS(tsi_types), 0x0C,
2009 NULL, HFILL }
2011 { &hf_vrt_context_rel_ephemeris.tsf,
2012 { "Fractional timestamp type", "vrt.context.relephem.tsf",
2013 FT_UINT8, BASE_DEC,
2014 VALS(tsf_types), 0x03,
2015 NULL, HFILL }
2017 { &hf_vrt_context_rel_ephemeris.oui,
2018 { "Manufacturer OUI", "vrt.context.relephem.oui",
2019 FT_UINT24, BASE_HEX,
2020 NULL, 0x00,
2021 NULL, HFILL }
2023 { &hf_vrt_context_rel_ephemeris.ts_int,
2024 { "Integer timestamp of position fix", "vrt.context.relephem.ts_int",
2025 FT_UINT32, BASE_DEC,
2026 NULL, 0x00,
2027 NULL, HFILL }
2029 { &hf_vrt_context_rel_ephemeris.ts_frac_sample,
2030 { "Fractional timestamp (samples)", "vrt.context.relephem.ts_frac_sample",
2031 FT_UINT64, BASE_DEC,
2032 NULL, 0x00,
2033 NULL, HFILL }
2035 { &hf_vrt_context_rel_ephemeris.ts_picosecond,
2036 { "Fractional timestamp (picoseconds)", "vrt.context.relephem.ts_frac_picosecond",
2037 FT_UINT64, BASE_DEC,
2038 NULL, 0x00,
2039 NULL, HFILL }
2041 { &hf_vrt_context_rel_ephemeris.pos_x,
2042 { "Position X", "vrt.context.relephem.posx",
2043 FT_INT32, BASE_CUSTOM,
2044 CF_FUNC(format_meter), 0x00,
2045 NULL, HFILL }
2047 { &hf_vrt_context_rel_ephemeris.pos_y,
2048 { "Position Y", "vrt.context.relephem.posy",
2049 FT_INT32, BASE_CUSTOM,
2050 CF_FUNC(format_meter), 0x00,
2051 NULL, HFILL }
2053 { &hf_vrt_context_rel_ephemeris.pos_z,
2054 { "Position Z", "vrt.context.relephem.posz",
2055 FT_INT32, BASE_CUSTOM,
2056 CF_FUNC(format_meter), 0x00,
2057 NULL, HFILL }
2059 { &hf_vrt_context_rel_ephemeris.att_alpha,
2060 { "Attitude alpha (α)", "vrt.context.relephem.attalpha",
2061 FT_INT32, BASE_CUSTOM,
2062 CF_FUNC(format_degrees), 0x00,
2063 NULL, HFILL }
2065 { &hf_vrt_context_rel_ephemeris.att_beta,
2066 { "Attitude beta (β)", "vrt.context.relephem.attbeta",
2067 FT_INT32, BASE_CUSTOM,
2068 CF_FUNC(format_degrees), 0x00,
2069 NULL, HFILL }
2071 { &hf_vrt_context_rel_ephemeris.att_phi,
2072 { "Attitude phi (φ)", "vrt.context.relephem.attphi",
2073 FT_INT32, BASE_CUSTOM,
2074 CF_FUNC(format_degrees), 0x00,
2075 NULL, HFILL }
2077 { &hf_vrt_context_rel_ephemeris.vel_dx,
2078 { "Velocity dX", "vrt.context.relephem.veldx",
2079 FT_INT32, BASE_CUSTOM,
2080 CF_FUNC(format_meters_per_second), 0x00,
2081 NULL, HFILL }
2083 { &hf_vrt_context_rel_ephemeris.vel_dy,
2084 { "Velocity dY", "vrt.context.relephem.veldy",
2085 FT_INT32, BASE_CUSTOM,
2086 CF_FUNC(format_meters_per_second), 0x00,
2087 NULL, HFILL }
2089 { &hf_vrt_context_rel_ephemeris.vel_dz,
2090 { "Velocity dZ", "vrt.context.relephem.veldz",
2091 FT_INT32, BASE_CUSTOM,
2092 CF_FUNC(format_meters_per_second), 0x00,
2093 NULL, HFILL }
2095 { &hf_vrt_context_ephemeris_ref_id,
2096 { "Ephemeris reference identifier", "vrt.context.ephemrefid",
2097 FT_UINT32, BASE_DEC,
2098 NULL, 0x00,
2099 NULL, HFILL }
2101 { &hf_vrt_context_gps_ascii_oui,
2102 { "Manufacturer OUI", "vrt.context.gpsascii.oui",
2103 FT_UINT24, BASE_HEX,
2104 NULL, 0x00,
2105 NULL, HFILL }
2107 { &hf_vrt_context_gps_ascii_size,
2108 { "Number of words", "vrt.context.gpsascii.size",
2109 FT_UINT32, BASE_DEC,
2110 NULL, 0x00,
2111 NULL, HFILL }
2113 { &hf_vrt_context_gps_ascii_data,
2114 { "Data", "vrt.context.gpsascii.data",
2115 FT_BYTES, BASE_NONE,
2116 NULL, 0x00,
2117 NULL, HFILL }
2119 { &hf_vrt_context_assoc_lists_src_size,
2120 { "Source list size", "vrt.context.assoclists.src.size",
2121 FT_UINT16, BASE_DEC,
2122 NULL, 0x01FF,
2123 NULL, HFILL }
2125 { &hf_vrt_context_assoc_lists_sys_size,
2126 { "System list size", "vrt.context.assoclists.sys.size",
2127 FT_UINT16, BASE_DEC,
2128 NULL, 0x01FF,
2129 NULL, HFILL }
2131 { &hf_vrt_context_assoc_lists_vec_size,
2132 { "Vector-component list size", "vrt.context.assoclists.vec.size",
2133 FT_UINT16, BASE_DEC,
2134 NULL, 0x00,
2135 NULL, HFILL }
2137 { &hf_vrt_context_assoc_lists_a,
2138 { "A bit (asynchronous-channel tag list present)", "vrt.context.assoclists.a",
2139 FT_BOOLEAN, 8,
2140 NULL, 0x80,
2141 NULL, HFILL }
2143 { &hf_vrt_context_assoc_lists_asy_size,
2144 { "Asynchronous-channel list size", "vrt.context.assoclists.asy.size",
2145 FT_UINT16, BASE_DEC,
2146 NULL, 0x7FFF,
2147 NULL, HFILL }
2149 { &hf_vrt_context_assoc_lists_src_data,
2150 { "Source context association list", "vrt.context.assoclists.src.data",
2151 FT_BYTES, BASE_NONE,
2152 NULL, 0x00,
2153 NULL, HFILL }
2155 { &hf_vrt_context_assoc_lists_sys_data,
2156 { "System context association list", "vrt.context.assoclists.sys.data",
2157 FT_BYTES, BASE_NONE,
2158 NULL, 0x00,
2159 NULL, HFILL }
2161 { &hf_vrt_context_assoc_lists_vec_data,
2162 { "Vector-component context association list", "vrt.context.assoclists.vec.data",
2163 FT_BYTES, BASE_NONE,
2164 NULL, 0x00,
2165 NULL, HFILL }
2167 { &hf_vrt_context_assoc_lists_asy_data,
2168 { "Asynchronous-channel context association list", "vrt.context.assoclists.asy.data",
2169 FT_BYTES, BASE_NONE,
2170 NULL, 0x00,
2171 NULL, HFILL }
2173 { &hf_vrt_context_assoc_lists_asy_tag_data,
2174 { "Asynchronous-channel tag list", "vrt.context.assoclists.asy.tagdata",
2175 FT_BYTES, BASE_NONE,
2176 NULL, 0x00,
2177 NULL, HFILL }
2179 { &hf_vrt_context_phase_offset,
2180 { "Phase offset", "vrt.context.phaseoffset",
2181 FT_INT16, BASE_CUSTOM,
2182 CF_FUNC(format_radian_phase), 0x00,
2183 NULL, HFILL }
2185 { &hf_vrt_context_pol_tilt,
2186 { "Tilt angle (θ)", "vrt.context.polarization.tilt",
2187 FT_INT16, BASE_CUSTOM,
2188 CF_FUNC(format_radian_pol), 0x00,
2189 NULL, HFILL }
2191 { &hf_vrt_context_pol_ellipticity,
2192 { "Ellipticity angle (χ)", "vrt.context.polarization.ellipticity",
2193 FT_INT16, BASE_CUSTOM,
2194 CF_FUNC(format_radian_pol), 0x00,
2195 NULL, HFILL }
2197 { &hf_vrt_context_range,
2198 { "Range (distance)", "vrt.context.range",
2199 FT_UINT32, BASE_CUSTOM,
2200 CF_FUNC(format_meter_unsigned), 0x00,
2201 NULL, HFILL }
2203 { &hf_vrt_context_aux_freq,
2204 { "Aux frequency", "vrt.context.auxfreq",
2205 FT_INT64, BASE_CUSTOM,
2206 CF_FUNC(format_hertz), 0x00,
2207 NULL, HFILL }
2209 { &hf_vrt_context_aux_bandwidth,
2210 { "Aux bandwidth", "vrt.context.auxbw",
2211 FT_INT64, BASE_CUSTOM,
2212 CF_FUNC(format_hertz), 0x00,
2213 NULL, HFILL }
2215 { &hf_vrt_context_spectrum_spectrum_type,
2216 { "Spectrum type", "vrt.context.spectrum.spectrum_type",
2217 FT_UINT32, BASE_HEX,
2218 NULL, 0x00,
2219 NULL, HFILL }
2221 { &hf_vrt_context_spectrum_window_type,
2222 { "Window type", "vrt.context.spectrum.window_type",
2223 FT_UINT32, BASE_HEX,
2224 NULL, 0x00,
2225 NULL, HFILL }
2227 { &hf_vrt_context_spectrum_num_transform_points,
2228 { "Num transform points", "vrt.context.spectrum.num_transform_points",
2229 FT_UINT32, BASE_DEC,
2230 NULL, 0x00,
2231 NULL, HFILL }
2233 { &hf_vrt_context_spectrum_num_window_points,
2234 { "Num window points", "vrt.context.spectrum.num_window_points",
2235 FT_UINT32, BASE_DEC,
2236 NULL, 0x00,
2237 NULL, HFILL }
2239 { &hf_vrt_context_spectrum_resolution,
2240 { "Resolution", "vrt.context.spectrum.resolution",
2241 FT_INT64, BASE_CUSTOM,
2242 CF_FUNC(format_hertz), 0x00,
2243 NULL, HFILL }
2245 { &hf_vrt_context_spectrum_span,
2246 { "Span", "vrt.context.spectrum.span",
2247 FT_INT64, BASE_CUSTOM,
2248 CF_FUNC(format_hertz), 0x00,
2249 NULL, HFILL }
2251 { &hf_vrt_context_spectrum_num_averages,
2252 { "Num averages", "vrt.context.spectrum.num_averages",
2253 FT_UINT32, BASE_DEC,
2254 NULL, 0x00,
2255 NULL, HFILL }
2257 { &hf_vrt_context_spectrum_weighting_factor,
2258 { "Weighting factor", "vrt.context.spectrum.weighting_factor",
2259 FT_UINT32, BASE_DEC,
2260 NULL, 0x00,
2261 NULL, HFILL }
2263 { &hf_vrt_context_spectrum_spectrum_f1_index,
2264 { "F1 index", "vrt.context.spectrum.spectrum_f1_index",
2265 FT_INT32, BASE_DEC,
2266 NULL, 0x00,
2267 NULL, HFILL }
2269 { &hf_vrt_context_spectrum_spectrum_f2_index,
2270 { "F2 index", "vrt.context.spectrum.spectrum_f2_index",
2271 FT_INT32, BASE_DEC,
2272 NULL, 0x00,
2273 NULL, HFILL }
2275 { &hf_vrt_context_spectrum_window_time_delta,
2276 { "Window time-delta", "vrt.context.spectrum.window_time_delta",
2277 FT_UINT32, BASE_DEC,
2278 NULL, 0x00,
2279 NULL, HFILL }
2281 { &hf_vrt_context_io32,
2282 { "Discrete I/O (32-bit)", "vrt.context.io32",
2283 FT_UINT32, BASE_HEX,
2284 NULL, 0x00,
2285 NULL, HFILL }
2287 { &hf_vrt_context_io64,
2288 { "Discrete I/O (64-bit)", "vrt.context.io64",
2289 FT_UINT64, BASE_HEX,
2290 NULL, 0x00,
2291 NULL, HFILL }
2293 { &hf_vrt_context_v49_spec,
2294 { "V49 spec compliance", "vrt.context.v49spec",
2295 FT_UINT32, BASE_HEX,
2296 VALS(standard_version_codes), 0x00,
2297 NULL, HFILL }
2299 { &hf_vrt_context_ver_year,
2300 { "Year", "vrt.context.ver.year",
2301 FT_UINT16, BASE_DEC,
2302 NULL, 0xFE00,
2303 NULL, HFILL }
2305 { &hf_vrt_context_ver_day,
2306 { "Day", "vrt.context.ver.day",
2307 FT_UINT16, BASE_DEC,
2308 NULL, 0x01FF,
2309 NULL, HFILL }
2311 { &hf_vrt_context_ver_rev,
2312 { "Revision", "vrt.context.ver.rev",
2313 FT_UINT16, BASE_DEC,
2314 NULL, 0xFC00,
2315 NULL, HFILL }
2317 { &hf_vrt_context_ver_user,
2318 { "User defined", "vrt.context.ver.user",
2319 FT_UINT16, BASE_DEC,
2320 NULL, 0x03FF,
2321 NULL, HFILL }
2323 { &hf_vrt_data,
2324 { "Data", "vrt.data",
2325 FT_BYTES, BASE_NONE,
2326 NULL, 0x00,
2327 NULL, HFILL }
2329 { &hf_vrt_trailer,
2330 { "Trailer", "vrt.trailer",
2331 FT_UINT32, BASE_HEX,
2332 NULL, 0x00,
2333 NULL, HFILL }
2335 { &hf_vrt_trailer_enables,
2336 { "Indicator enable bits", "vrt.enables",
2337 FT_UINT16, BASE_HEX,
2338 NULL, 0xFFF0,
2339 NULL, HFILL }
2341 { &hf_vrt_trailer_ind,
2342 { "Indicator bits", "vrt.indicators",
2343 FT_UINT16, BASE_HEX,
2344 NULL, 0x0FFF,
2345 NULL, HFILL }
2347 { &hf_vrt_trailer_e,
2348 { "Associated context packet count enabled", "vrt.e",
2349 FT_BOOLEAN, 8,
2350 NULL, 0x80,
2351 NULL, HFILL }
2353 { &hf_vrt_trailer_acpc,
2354 { "Associated context packet count", "vrt.acpc",
2355 FT_UINT8, BASE_DEC,
2356 NULL, 0x7F,
2357 NULL, HFILL }
2359 { &hf_vrt_trailer_ind_caltime,
2360 { "Calibrated time indicator", "vrt.caltime",
2361 FT_BOOLEAN, 16,
2362 NULL, 0x0800,
2363 NULL, HFILL }
2365 { &hf_vrt_trailer_ind_valid,
2366 { "Valid signal indicator", "vrt.valid",
2367 FT_BOOLEAN, 16,
2368 NULL, 0x0400,
2369 NULL, HFILL }
2371 { &hf_vrt_trailer_ind_reflock,
2372 { "Reference lock indicator", "vrt.reflock",
2373 FT_BOOLEAN, 16,
2374 NULL, 0x0200,
2375 NULL, HFILL }
2377 { &hf_vrt_trailer_ind_agc,
2378 { "AGC/MGC indicator", "vrt.agc",
2379 FT_BOOLEAN, 16,
2380 NULL, 0x0100,
2381 NULL, HFILL }
2383 { &hf_vrt_trailer_ind_sig,
2384 { "Signal detected indicator", "vrt.sig",
2385 FT_BOOLEAN, 16,
2386 NULL, 0x0080,
2387 NULL, HFILL }
2389 { &hf_vrt_trailer_ind_inv,
2390 { "Spectral inversion indicator", "vrt.inv",
2391 FT_BOOLEAN, 16,
2392 NULL, 0x0040,
2393 NULL, HFILL }
2395 { &hf_vrt_trailer_ind_overrng,
2396 { "Overrange indicator", "vrt.overrng",
2397 FT_BOOLEAN, 16,
2398 NULL, 0x0020,
2399 NULL, HFILL }
2401 { &hf_vrt_trailer_ind_sampleloss,
2402 { "Lost sample indicator", "vrt.sampleloss",
2403 FT_BOOLEAN, 16,
2404 NULL, 0x0010,
2405 NULL, HFILL }
2407 { &hf_vrt_trailer_ind_user0,
2408 { "User indicator 0", "vrt.user0",
2409 FT_BOOLEAN, 16,
2410 NULL, 0x0008,
2411 NULL, HFILL }
2413 { &hf_vrt_trailer_ind_user1,
2414 { "User indicator 1", "vrt.user1",
2415 FT_BOOLEAN, 16,
2416 NULL, 0x0004,
2417 NULL, HFILL }
2419 { &hf_vrt_trailer_ind_user2,
2420 { "User indicator 2", "vrt.user2",
2421 FT_BOOLEAN, 16,
2422 NULL, 0x0002,
2423 NULL, HFILL }
2425 { &hf_vrt_trailer_ind_user3,
2426 { "User indicator 3", "vrt.user3",
2427 FT_BOOLEAN, 16,
2428 NULL, 0x0001,
2429 NULL, HFILL }
2431 { &hf_vrt_trailer_en_caltime,
2432 { "Calibrated time indicator enable", "vrt.caltime_en",
2433 FT_BOOLEAN, 16,
2434 NULL, 0x8000,
2435 NULL, HFILL }
2437 { &hf_vrt_trailer_en_valid,
2438 { "Valid signal indicator enable", "vrt.valid_en",
2439 FT_BOOLEAN, 16,
2440 NULL, 0x4000,
2441 NULL, HFILL }
2443 { &hf_vrt_trailer_en_reflock,
2444 { "Reference lock indicator enable", "vrt.reflock_en",
2445 FT_BOOLEAN, 16,
2446 NULL, 0x2000,
2447 NULL, HFILL }
2449 { &hf_vrt_trailer_en_agc,
2450 { "AGC/MGC indicator enable", "vrt.agc_en",
2451 FT_BOOLEAN, 16,
2452 NULL, 0x1000,
2453 NULL, HFILL }
2455 { &hf_vrt_trailer_en_sig,
2456 { "Signal detected indicator enable", "vrt.sig_en",
2457 FT_BOOLEAN, 16,
2458 NULL, 0x0800,
2459 NULL, HFILL }
2461 { &hf_vrt_trailer_en_inv,
2462 { "Spectral inversion indicator enable", "vrt.inv_en",
2463 FT_BOOLEAN, 16,
2464 NULL, 0x0400,
2465 NULL, HFILL }
2467 { &hf_vrt_trailer_en_overrng,
2468 { "Overrange indicator enable", "vrt.overrng_en",
2469 FT_BOOLEAN, 16,
2470 NULL, 0x0200,
2471 NULL, HFILL }
2473 { &hf_vrt_trailer_en_sampleloss,
2474 { "Lost sample indicator enable", "vrt.sampleloss_en",
2475 FT_BOOLEAN, 16,
2476 NULL, 0x0100,
2477 NULL, HFILL }
2479 { &hf_vrt_trailer_en_user0,
2480 { "User indicator 0 enable", "vrt.user0_en",
2481 FT_BOOLEAN, 16,
2482 NULL, 0x0080,
2483 NULL, HFILL }
2485 { &hf_vrt_trailer_en_user1,
2486 { "User indicator 1 enable", "vrt.user1_en",
2487 FT_BOOLEAN, 16,
2488 NULL, 0x0040,
2489 NULL, HFILL }
2491 { &hf_vrt_trailer_en_user2,
2492 { "User indicator 2 enable", "vrt.user2_en",
2493 FT_BOOLEAN, 16,
2494 NULL, 0x0020,
2495 NULL, HFILL }
2497 { &hf_vrt_trailer_en_user3,
2498 { "User indicator 3 enable", "vrt.user3_en",
2499 FT_BOOLEAN, 16,
2500 NULL, 0x0010,
2501 NULL, HFILL }
2503 { &hf_vrt_cid_oui,
2504 { "Class ID Organizationally Unique ID", "vrt.oui",
2505 FT_UINT24, BASE_HEX,
2506 NULL, 0x00,
2507 NULL, HFILL }
2509 { &hf_vrt_cid_icc,
2510 { "Class ID Information Class Code", "vrt.icc",
2511 FT_UINT16, BASE_DEC,
2512 NULL, 0x00,
2513 NULL, HFILL }
2515 { &hf_vrt_cid_pcc,
2516 { "Class ID Packet Class Code", "vrt.pcc",
2517 FT_UINT16, BASE_DEC,
2518 NULL, 0x00,
2519 NULL, HFILL }
2523 // update ETT_IDX_* as new items added to track indices
2524 static int *ett[] = {
2525 &ett_vrt,
2526 &ett_header,
2527 &ett_trailer,
2528 &ett_indicators,
2529 &ett_ind_enables,
2530 &ett_cid,
2531 &ett_cif0,
2532 &ett_cif1,
2533 &ett_gain, // ETT_IDX_GAIN
2534 &ett_device_id, // ETT_IDX_DEVICE_ID
2535 &ett_state_event, // ETT_IDX_STATE_EVENT
2536 &ett_signal_data_format, // ETT_IDX_SIGNAL_DATA_FORMAT
2537 &ett_gps, // ETT_IDX_GPS
2538 &ett_ins, // ETT_IDX_INS
2539 &ett_ecef_ephem, // ETT_IDX_ECEF_EPHEM
2540 &ett_rel_ephem, // ETT_IDX_REL_EPHEM
2541 &ett_gps_ascii, // ETT_IDX_GPS_ASCII
2542 &ett_assoc_lists, // ETT_IDX_ASSOC_LISTS
2543 &ett_pol, // ETT_IDX_POL
2544 &ett_ver, // ETT_IDX_VER
2547 proto_vrt = proto_register_protocol ("VITA 49 radio transport protocol", "VITA 49", "vrt");
2549 proto_register_field_array(proto_vrt, hf, array_length(hf));
2550 proto_register_subtree_array(ett, array_length(ett));
2552 vrt_handle = register_dissector("vrt", dissect_vrt, proto_vrt);
2554 vrt_module = prefs_register_protocol(proto_vrt, NULL);
2555 prefs_register_bool_preference(vrt_module, "ettus_uhd_header_format",
2556 "Use Ettus UHD header format",
2557 "Activate workaround for weird Ettus UHD header offset on data packets",
2558 &vrt_use_ettus_uhd_header_format);
2561 void
2562 proto_reg_handoff_vrt(void)
2564 dissector_add_uint_with_preference("udp.port", VITA_49_PORT, vrt_handle);
2566 dissector_add_string("rtp_dyn_payload_type","VITA 49", vrt_handle);
2567 dissector_add_uint_range_with_preference("rtp.pt", "", vrt_handle);
2571 * Editor modelines - https://www.wireshark.org/tools/modelines.html
2573 * Local variables:
2574 * c-basic-offset: 4
2575 * tab-width: 8
2576 * indent-tabs-mode: nil
2577 * End:
2579 * vi: set shiftwidth=4 tabstop=8 expandtab:
2580 * :indentSize=4:tabSize=8:noTabs=true: