/src/wireshark/epan/dissectors/packet-simple.c
Line | Count | Source |
1 | | /* packet-simple.c |
2 | | * Routines for SIMPLE dissection |
3 | | * Copyright 2015 Peter Ross |
4 | | * |
5 | | * SPDX-License-Identifier: GPL-2.0-or-later |
6 | | */ |
7 | | |
8 | | /* SIMPLE (Standard Interface for Multiple Platform Link Evaluation) |
9 | | * is a protocol for exchanging tactical data link messages, such as Link 16, |
10 | | * over Internet Protocols. |
11 | | * |
12 | | * The protocol is described in STANAG 5602. See: |
13 | | * http://assistdoc1.dla.mil/qsDocDetails.aspx?ident_number=213042 |
14 | | */ |
15 | | |
16 | | #include "config.h" |
17 | | |
18 | | #include <epan/packet.h> |
19 | | #include <epan/tfs.h> |
20 | | #include <wsutil/array.h> |
21 | | #include <epan/expert.h> |
22 | | #include "packet-link16.h" |
23 | | |
24 | | void proto_reg_handoff_simple(void); |
25 | | |
26 | | void proto_register_simple(void); |
27 | | |
28 | | static const range_string Node_Strings[] = { |
29 | | { 1, 128, "Unicast" }, |
30 | | { 129, 129, "Broadcast" }, |
31 | | { 160, 168, "Multicast" }, |
32 | | { 169, 169, "Adjacent" }, |
33 | | { 0, 0, NULL }, |
34 | | }; |
35 | | |
36 | | static const value_string Subnode_Strings[] = { |
37 | | { 1, "RTT" }, |
38 | | { 2, "Terminal-Host Interface" }, |
39 | | { 4, "File & Mail Transfers" }, |
40 | | { 5, "Open" }, |
41 | | { 6, "Status & Control" }, |
42 | | { 7, "Time Synchronisation" }, |
43 | | { 202, "Scenario (Script)" }, |
44 | | { 203, "IJMS" }, |
45 | | { 204, "Link 4" }, |
46 | | { 205, "Link 11" }, |
47 | | { 206, "Link 16" }, |
48 | | { 207, "Link 22" }, |
49 | | { 208, "DIS" }, |
50 | | { 209, "Voice Group A" }, |
51 | | { 210, "Voice Group B" }, |
52 | | { 211, "Link 11B" }, |
53 | | { 0, NULL }, |
54 | | }; |
55 | | |
56 | | enum { |
57 | | SIMPLE_LINK16 = 1, |
58 | | SIMPLE_STATUS = 61 |
59 | | }; |
60 | | |
61 | | static const value_string PacketType_Strings[] = { |
62 | | { SIMPLE_LINK16, "Link 16" }, |
63 | | { 2, "Link 11" }, |
64 | | { 3, "Link 4" }, |
65 | | { 4, "Link 22" }, |
66 | | { 5, "Interim JTIDS Message Standard (IJMS)" }, |
67 | | { 8, "Variable Message Format (VMF)" }, |
68 | | { 10, "MIDS Terminal Specific Messages (MTSM)" }, |
69 | | { 13, "MIDS/JTIDS Voice" }, |
70 | | { 20, "Link 11B" }, |
71 | | { 32, "DIS Protocol Data Unit (PDU)" }, |
72 | | { SIMPLE_STATUS, "Status/Configuration" }, |
73 | | { 62, "E-mail/File Transfer Protocol (FTP)" }, |
74 | | { 63, "Round Trip Timing (RTT)" }, |
75 | | { 65, "Time Synchronisation" }, |
76 | | { 66, "TSA Status" }, |
77 | | { 100, "National Message" }, |
78 | | { 0, NULL }, |
79 | | }; |
80 | | |
81 | | enum { |
82 | | SIMPLE_LINK16_FIXED_FORMAT = 2 |
83 | | }; |
84 | | |
85 | | static const value_string Link16_Subtype_Strings[] = { |
86 | | { 0, "Uncoded Free Text" }, |
87 | | { 1, "Coded Free Text" }, |
88 | | { SIMPLE_LINK16_FIXED_FORMAT, "Fixed Format" }, |
89 | | { 0, NULL }, |
90 | | }; |
91 | | |
92 | | static const value_string Status_Subtype_Strings[] = { |
93 | | { 1, "Node Status" }, |
94 | | { 0, NULL }, |
95 | | }; |
96 | | |
97 | | static const value_string Security_Level_Strings[] = { |
98 | | { 0, "Unclassified" }, |
99 | | { 1, "NATO Unclassified" }, |
100 | | { 2, "Confidential" }, |
101 | | { 3, "NATO Confidential" }, |
102 | | { 4, "Secret" }, |
103 | | { 5, "NATO Secret" }, |
104 | | { 6, "National Only" }, |
105 | | { 7, "Level 7" }, |
106 | | { 8, "Level 8" }, |
107 | | { 9, "Level 9" }, |
108 | | { 0, NULL }, |
109 | | }; |
110 | | |
111 | | static const value_string Link16_Terminal_Type[] = { |
112 | | { 0, "None" }, |
113 | | { 1, "US Navy Air (JTIDS)" }, |
114 | | { 2, "US Navy Ship (JTIDS)" }, |
115 | | { 3, "US F-15 (JTIDS)" }, |
116 | | { 4, "US F/A-18 (MIDS)" }, |
117 | | { 5, "US Army Class 2M (JTIDS)" }, |
118 | | { 6, "US MCE (JTIDS)" }, |
119 | | { 7, "E-3 (JTIDS)" }, |
120 | | { 8, "UK Tornado F3 (JTIDS)" }, |
121 | | { 9, "UK UKADGE (JTIDS)" }, |
122 | | { 10, "Low Volume Terminal - Generic (MIDS)" }, |
123 | | { 11, "Low Volume Terminal - Platform Type A (MIDS)" }, |
124 | | { 12, "Low Volume Terminal - Platform Type B (MIDS)" }, |
125 | | { 13, "Low Volume Terminal - Platform Type C (MIDS)" }, |
126 | | { 14, "Low Volume Terminal - Platform Type D (MIDS)" }, |
127 | | { 15, "Low Volume Terminal - Platform Type E (MIDS)" }, |
128 | | { 16, "Low Volume Terminal - Platform Type F (MIDS)" }, |
129 | | { 17, "Low Volume Terminal - Platform Type G (MIDS)" }, |
130 | | { 18, "Low Volume Terminal 2, US Army (MIDS)" }, |
131 | | { 19, "Low Volume Terminal MIDS on Ship (MOS) (MIDS)" }, |
132 | | { 20, "US Fighter Data Link (FDL) (MIDS)" }, |
133 | | { 21, "AN/URC-138" }, |
134 | | { 22, "Low Volume Terminal Platform Type H (MIDS)" }, |
135 | | { 23, "Low Volume Terminal Platform Type I (MIDS)" }, |
136 | | { 0, NULL }, |
137 | | }; |
138 | | |
139 | | static const value_string Link16_Role[] = { |
140 | | { 0, "None" }, |
141 | | { 1, "SIMPLE Host (SH)" }, |
142 | | { 2, "SIMPLE Terminal Emulator (STE)" }, |
143 | | { 3, "SIMPLE Network Monitor (SNM)" }, |
144 | | { 4, "SIMPLE Virtual Host (SVH)" }, |
145 | | { 5, "SIMPLE Virtual Terminal (SVT)" }, |
146 | | { 0, NULL }, |
147 | | }; |
148 | | |
149 | | static const value_string Link16_Sync_Status[] = { |
150 | | { 0, "None" }, |
151 | | { 1, "Net Entry in Progress" }, |
152 | | { 2, "Coarse Sync" }, |
153 | | { 3, "Fine Sync" }, |
154 | | { 0, NULL }, |
155 | | }; |
156 | | |
157 | | static const value_string Link_Terminal_Host_Status[] = { |
158 | | { 0, "Inactive" }, |
159 | | { 1, "Active" }, |
160 | | { 0, NULL }, |
161 | | }; |
162 | | |
163 | | static const value_string Link11_DTS_Type[] = { |
164 | | { 0, "None" }, |
165 | | { 1, "MIL-STD-1397 parallel" }, |
166 | | { 2, "MIL-STD-188-203-1A serial" }, |
167 | | { 0, NULL }, |
168 | | }; |
169 | | |
170 | | static const value_string Link11_Role[] = { |
171 | | { 0, "None"}, |
172 | | { 1, "SIMPLE DTS EMULATOR (SDE) Picket"}, |
173 | | { 2, "SDE Net Control Station (NCS)" }, |
174 | | { 3, "SIMPLE Participating Unit (PU) Emulator (SPE)" }, |
175 | | { 0, NULL }, |
176 | | }; |
177 | | |
178 | | static int proto_simple; |
179 | | |
180 | | static dissector_handle_t simple_dissector_handle; |
181 | | static dissector_handle_t link16_handle; |
182 | | |
183 | | static int hf_simple_sync_byte_1; |
184 | | static int hf_simple_sync_byte_2; |
185 | | static int hf_simple_length; |
186 | | static int hf_simple_sequence_number; |
187 | | static int hf_simple_src_node; |
188 | | static int hf_simple_src_subnode; |
189 | | static int hf_simple_dst_node; |
190 | | static int hf_simple_dst_subnode; |
191 | | static int hf_simple_packet_size; |
192 | | static int hf_simple_packet_type; |
193 | | static int hf_simple_transit_time; |
194 | | static int hf_simple_link16_subtype; |
195 | | static int hf_simple_link16_rc; |
196 | | static int hf_simple_link16_network; |
197 | | static int hf_simple_link16_ssc2; |
198 | | static int hf_simple_link16_npg; |
199 | | static int hf_simple_link16_ssc1; |
200 | | static int hf_simple_link16_stn; |
201 | | static int hf_simple_link16_word_count; |
202 | | static int hf_simple_link16_loopback_id; |
203 | | static int hf_simple_status_subtype; |
204 | | static int hf_simple_status_word_count; |
205 | | static int hf_simple_status_name; |
206 | | static int hf_simple_status_time_hours; |
207 | | static int hf_simple_status_node_id; |
208 | | static int hf_simple_status_time_seconds; |
209 | | static int hf_simple_status_time_minutes; |
210 | | static int hf_simple_status_security_level; |
211 | | static int hf_simple_status_node_entry_flag; |
212 | | static int hf_simple_status_relay_hop; |
213 | | static int hf_simple_status_dx_flag_system_messages; |
214 | | static int hf_simple_status_dx_flag_common_tims_bims; |
215 | | static int hf_simple_status_dx_flag_common_toms_boms; |
216 | | static int hf_simple_status_dx_flag_simple_receive; |
217 | | static int hf_simple_status_dx_flag_simple_transmit; |
218 | | static int hf_simple_status_dx_flag_all_tims_bims; |
219 | | static int hf_simple_status_dx_flag_all_toms_boms; |
220 | | static int hf_simple_status_dx_file_id; |
221 | | static int hf_simple_status_spare_1; |
222 | | static int hf_simple_status_link16_terminal_type; |
223 | | static int hf_simple_status_link16_role; |
224 | | static int hf_simple_status_link16_sync_status; |
225 | | static int hf_simple_status_link16_terminal_host_status; |
226 | | static int hf_simple_status_link16_stn; |
227 | | static int hf_simple_status_spare_2; |
228 | | static int hf_simple_status_link11_dts_type; |
229 | | static int hf_simple_status_link11_role; |
230 | | static int hf_simple_status_link11_pu; |
231 | | static int hf_simple_status_link11_dts_host_status; |
232 | | static int hf_simple_status_spare_3; |
233 | | static int hf_simple_checksum; |
234 | | static int hf_simple_checksum_status; |
235 | | |
236 | | static int ett_simple; |
237 | | static int ett_packet; |
238 | | static int ett_simple_status_dx_flag; |
239 | | |
240 | | static expert_field ei_simple_sync_bytes_bad; |
241 | | static expert_field ei_simple_length_bad; |
242 | | static expert_field ei_simple_packet_size_bad; |
243 | | static expert_field ei_simple_checksum_bad; |
244 | | |
245 | | static void dissect_simple_link16(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, int offset) |
246 | 0 | { |
247 | 0 | unsigned subtype, stn, word_count, i; |
248 | 0 | Link16State state; |
249 | 0 | tvbuff_t *newtvb; |
250 | |
|
251 | 0 | proto_tree_add_item_ret_uint(tree, hf_simple_link16_subtype, tvb, offset, 1, ENC_NA, &subtype); |
252 | 0 | offset++; |
253 | |
|
254 | 0 | proto_tree_add_item(tree, hf_simple_link16_rc, tvb, offset, 1, ENC_NA); |
255 | 0 | offset++; |
256 | |
|
257 | 0 | proto_tree_add_item(tree, hf_simple_link16_network, tvb, offset, 1, ENC_NA); |
258 | 0 | offset++; |
259 | |
|
260 | 0 | proto_tree_add_item(tree, hf_simple_link16_ssc2, tvb, offset, 1, ENC_NA); |
261 | 0 | offset++; |
262 | |
|
263 | 0 | proto_tree_add_item(tree, hf_simple_link16_npg, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
264 | 0 | offset += 2; |
265 | |
|
266 | 0 | proto_tree_add_item(tree, hf_simple_link16_ssc1, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
267 | 0 | offset += 2; |
268 | |
|
269 | 0 | proto_tree_add_item_ret_uint(tree, hf_simple_link16_stn, tvb, offset, 2, ENC_LITTLE_ENDIAN, &stn); |
270 | 0 | offset += 2; |
271 | |
|
272 | 0 | proto_tree_add_item_ret_uint(tree, hf_simple_link16_word_count, tvb, offset, 2, ENC_LITTLE_ENDIAN, &word_count); |
273 | 0 | offset += 2; |
274 | |
|
275 | 0 | proto_tree_add_item(tree, hf_simple_link16_loopback_id, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
276 | 0 | offset += 2; |
277 | |
|
278 | 0 | col_append_fstr(pinfo->cinfo, COL_INFO, ", STN: %05o, Words:", stn); |
279 | |
|
280 | 0 | switch(subtype) { |
281 | 0 | case SIMPLE_LINK16_FIXED_FORMAT: |
282 | 0 | memset(&state, 0, sizeof(state)); |
283 | 0 | for (i = 0; i < word_count; i += 5) { |
284 | 0 | newtvb = tvb_new_subset_length(tvb, offset, 10); |
285 | 0 | add_new_data_source(pinfo, newtvb, "Link 16 Word"); |
286 | 0 | call_dissector_with_data(link16_handle, newtvb, pinfo, tree, &state); |
287 | 0 | offset += 10; |
288 | 0 | } |
289 | 0 | break; |
290 | 0 | } |
291 | 0 | } |
292 | | |
293 | | static int * const simple_status_dx_flag_fields[] = { |
294 | | &hf_simple_status_dx_flag_system_messages, |
295 | | &hf_simple_status_dx_flag_common_tims_bims, |
296 | | &hf_simple_status_dx_flag_common_toms_boms, |
297 | | &hf_simple_status_dx_flag_simple_receive, |
298 | | &hf_simple_status_dx_flag_simple_transmit, |
299 | | &hf_simple_status_dx_flag_all_tims_bims, |
300 | | &hf_simple_status_dx_flag_all_toms_boms, |
301 | | NULL |
302 | | }; |
303 | | |
304 | 0 | #define SIMPLE_STATUS_NAME_LEN 10 |
305 | | |
306 | | static void dissect_simple_status(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int offset) |
307 | 0 | { |
308 | 0 | char *name; |
309 | 0 | unsigned link16_status, pu; |
310 | |
|
311 | 0 | proto_tree_add_item(tree, hf_simple_status_subtype, tvb, offset, 1, ENC_NA); |
312 | 0 | offset++; |
313 | |
|
314 | 0 | proto_tree_add_item(tree, hf_simple_status_word_count, tvb, offset, 1, ENC_NA); |
315 | 0 | offset++; |
316 | |
|
317 | 0 | name = (char*)tvb_get_stringzpad(pinfo->pool, tvb, offset, SIMPLE_STATUS_NAME_LEN, ENC_ASCII|ENC_NA); |
318 | 0 | col_append_fstr(pinfo->cinfo, COL_INFO, ", Name: %s", name); |
319 | 0 | proto_tree_add_item(tree, hf_simple_status_name, tvb, offset, SIMPLE_STATUS_NAME_LEN, ENC_ASCII); |
320 | 0 | offset += SIMPLE_STATUS_NAME_LEN; |
321 | |
|
322 | 0 | proto_tree_add_item(tree, hf_simple_status_time_hours, tvb, offset, 1, ENC_NA); |
323 | 0 | offset++; |
324 | |
|
325 | 0 | proto_tree_add_item(tree, hf_simple_status_node_id, tvb, offset, 1, ENC_NA); |
326 | 0 | offset++; |
327 | |
|
328 | 0 | proto_tree_add_item(tree, hf_simple_status_time_seconds, tvb, offset, 1, ENC_NA); |
329 | 0 | offset++; |
330 | |
|
331 | 0 | proto_tree_add_item(tree, hf_simple_status_time_minutes, tvb, offset, 1, ENC_NA); |
332 | 0 | offset++; |
333 | |
|
334 | 0 | proto_tree_add_item(tree, hf_simple_status_security_level, tvb, offset, 1, ENC_NA); |
335 | 0 | offset++; |
336 | |
|
337 | 0 | proto_tree_add_item(tree, hf_simple_status_node_entry_flag, tvb, offset, 1, ENC_NA); |
338 | 0 | offset++; |
339 | |
|
340 | 0 | proto_tree_add_item(tree, hf_simple_status_relay_hop, tvb, offset, 16, ENC_NA); |
341 | 0 | offset += 16; |
342 | |
|
343 | 0 | proto_tree_add_bitmask_text(tree, tvb, offset, 2, "Data Extraction Flags", NULL, ett_simple_status_dx_flag, simple_status_dx_flag_fields, ENC_LITTLE_ENDIAN, 0); |
344 | 0 | offset += 2; |
345 | |
|
346 | 0 | proto_tree_add_item(tree, hf_simple_status_dx_file_id, tvb, offset, 8, ENC_ASCII); |
347 | 0 | offset += 8; |
348 | |
|
349 | 0 | proto_tree_add_item(tree, hf_simple_status_spare_1, tvb, offset, 2, ENC_NA); |
350 | 0 | offset += 2; |
351 | |
|
352 | 0 | proto_tree_add_item(tree, hf_simple_status_link16_terminal_type, tvb, offset, 1, ENC_NA); |
353 | 0 | offset++; |
354 | |
|
355 | 0 | proto_tree_add_item(tree, hf_simple_status_link16_role, tvb, offset, 1, ENC_NA); |
356 | 0 | offset++; |
357 | |
|
358 | 0 | proto_tree_add_item(tree, hf_simple_status_link16_sync_status, tvb, offset, 1, ENC_NA); |
359 | 0 | offset++; |
360 | |
|
361 | 0 | proto_tree_add_item_ret_uint(tree, hf_simple_status_link16_terminal_host_status, tvb, offset, 1, ENC_NA, &link16_status); |
362 | 0 | offset++; |
363 | |
|
364 | 0 | proto_tree_add_item(tree, hf_simple_status_link16_stn, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
365 | 0 | if (link16_status) |
366 | 0 | col_append_fstr(pinfo->cinfo, COL_INFO, ", STN: %05o", tvb_get_letohs(tvb, offset)); |
367 | 0 | offset += 2; |
368 | |
|
369 | 0 | proto_tree_add_item(tree, hf_simple_status_spare_2, tvb, offset, 2, ENC_NA); |
370 | 0 | offset += 2; |
371 | |
|
372 | 0 | proto_tree_add_item(tree, hf_simple_status_link11_dts_type, tvb, offset, 1, ENC_NA); |
373 | 0 | offset++; |
374 | |
|
375 | 0 | proto_tree_add_item(tree, hf_simple_status_link11_role, tvb, offset, 1, ENC_NA); |
376 | 0 | offset++; |
377 | |
|
378 | 0 | proto_tree_add_item_ret_uint(tree, hf_simple_status_link11_pu, tvb, offset, 1, ENC_NA, &pu); |
379 | 0 | offset++; |
380 | |
|
381 | 0 | proto_tree_add_item(tree, hf_simple_status_link11_dts_host_status, tvb, offset, 1, ENC_NA); |
382 | 0 | if (tvb_get_uint8(tvb, offset)) |
383 | 0 | col_append_fstr(pinfo->cinfo, COL_INFO, ", PU: %03o", pu); |
384 | 0 | offset++; |
385 | |
|
386 | 0 | proto_tree_add_item(tree, hf_simple_status_spare_3, tvb, offset, 4, ENC_NA); |
387 | 0 | } |
388 | | |
389 | | static void dissect_checksum(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int offset) |
390 | 0 | { |
391 | 0 | const uint8_t * v = tvb_get_ptr(tvb, 0, offset); |
392 | 0 | uint16_t expected_checksum = 0; |
393 | 0 | int i; |
394 | |
|
395 | 0 | for (i = 0; i < offset; i++) |
396 | 0 | expected_checksum += v[i]; |
397 | |
|
398 | 0 | proto_tree_add_checksum(tree, tvb, offset, hf_simple_checksum, hf_simple_checksum_status, &ei_simple_checksum_bad, pinfo, expected_checksum, |
399 | 0 | ENC_LITTLE_ENDIAN, PROTO_CHECKSUM_VERIFY); |
400 | 0 | } |
401 | | |
402 | | static int dissect_simple(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data _U_) |
403 | 0 | { |
404 | 0 | proto_item *simple_item = NULL, *item; |
405 | 0 | proto_tree *simple_tree = NULL, *packet_tree = NULL; |
406 | 0 | unsigned offset = 0, length, packet_size, packet_type; |
407 | 0 | const char *packet_type_string; |
408 | 0 | uint8_t sync_bytes_bad = 0; |
409 | |
|
410 | 0 | col_set_str(pinfo->cinfo, COL_PROTOCOL, "SIMPLE"); |
411 | |
|
412 | 0 | if (tree) { |
413 | 0 | simple_item = proto_tree_add_item(tree, proto_simple, tvb, 0, -1, ENC_NA); |
414 | 0 | simple_tree = proto_item_add_subtree(simple_item, ett_simple); |
415 | 0 | } |
416 | |
|
417 | 0 | proto_tree_add_item(simple_tree, hf_simple_sync_byte_1, tvb, offset, 1, ENC_NA); |
418 | 0 | sync_bytes_bad |= tvb_get_uint8(tvb, offset) ^ 0x49; |
419 | 0 | offset++; |
420 | |
|
421 | 0 | proto_tree_add_item(simple_tree, hf_simple_sync_byte_2, tvb, offset, 1, ENC_NA); |
422 | 0 | sync_bytes_bad |= tvb_get_uint8(tvb, offset) ^ 0x36; |
423 | 0 | offset++; |
424 | |
|
425 | 0 | if (sync_bytes_bad) |
426 | 0 | expert_add_info(pinfo, simple_item, &ei_simple_sync_bytes_bad); |
427 | |
|
428 | 0 | item = proto_tree_add_item_ret_uint(simple_tree, hf_simple_length, tvb, offset, 2, ENC_LITTLE_ENDIAN, &length); |
429 | 0 | offset += 2; |
430 | |
|
431 | 0 | if (length < 16 || length >= 518 || length > tvb_reported_length(tvb)) |
432 | 0 | expert_add_info(pinfo, item, &ei_simple_length_bad); |
433 | |
|
434 | 0 | proto_tree_add_item(simple_tree, hf_simple_sequence_number, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
435 | 0 | offset += 2; |
436 | |
|
437 | 0 | proto_tree_add_item(simple_tree, hf_simple_src_node, tvb, offset, 1, ENC_NA); |
438 | 0 | offset++; |
439 | |
|
440 | 0 | proto_tree_add_item(simple_tree, hf_simple_src_subnode, tvb, offset, 1, ENC_NA); |
441 | 0 | offset++; |
442 | |
|
443 | 0 | proto_tree_add_item(simple_tree, hf_simple_dst_node, tvb, offset, 1, ENC_NA); |
444 | 0 | offset++; |
445 | |
|
446 | 0 | proto_tree_add_item(simple_tree, hf_simple_dst_subnode, tvb, offset, 1, ENC_NA); |
447 | 0 | offset++; |
448 | |
|
449 | 0 | item = proto_tree_add_item(simple_tree, hf_simple_packet_size, tvb, offset, 1, ENC_NA); |
450 | 0 | packet_size = tvb_get_uint8(tvb, offset) * 2; |
451 | 0 | if (packet_size < 8 || packet_size - 8 > tvb_reported_length(tvb)) |
452 | 0 | expert_add_info(pinfo, item, &ei_simple_packet_size_bad); |
453 | 0 | packet_size -= 8; |
454 | 0 | offset++; |
455 | |
|
456 | 0 | proto_tree_add_item_ret_uint(simple_tree, hf_simple_packet_type, tvb, offset, 1, ENC_NA, &packet_type); |
457 | 0 | offset++; |
458 | |
|
459 | 0 | proto_tree_add_item(simple_tree, hf_simple_transit_time, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
460 | 0 | offset += 2; |
461 | |
|
462 | 0 | packet_type_string = val_to_str_const(packet_type, PacketType_Strings, "Unknown"); |
463 | 0 | col_add_str(pinfo->cinfo, COL_INFO, packet_type_string); |
464 | 0 | packet_tree = proto_tree_add_subtree_format(simple_tree, tvb, offset, packet_size, ett_packet, NULL, "%s Packet", packet_type_string); |
465 | |
|
466 | 0 | switch(packet_type) { |
467 | 0 | case SIMPLE_LINK16: |
468 | 0 | dissect_simple_link16(tvb, pinfo, packet_tree, offset); |
469 | 0 | break; |
470 | 0 | case SIMPLE_STATUS: |
471 | 0 | dissect_simple_status(tvb, pinfo, packet_tree, offset); |
472 | 0 | break; |
473 | 0 | } |
474 | | |
475 | 0 | dissect_checksum(tvb, pinfo, simple_tree, length - 2); |
476 | |
|
477 | 0 | return tvb_captured_length(tvb); |
478 | 0 | } |
479 | | |
480 | | void proto_register_simple(void) |
481 | 14 | { |
482 | 14 | static hf_register_info hf[] = { |
483 | 14 | { &hf_simple_sync_byte_1, |
484 | 14 | { "Sync Byte 1", "simple.sync_byte_1", FT_UINT8, BASE_HEX, NULL, 0x0, |
485 | 14 | NULL, HFILL }}, |
486 | 14 | { &hf_simple_sync_byte_2, |
487 | 14 | { "Sync Byte 2", "simple.sync_byte_2", FT_UINT8, BASE_HEX, NULL, 0x0, |
488 | 14 | NULL, HFILL }}, |
489 | 14 | { &hf_simple_length, |
490 | 14 | { "Length", "simple.length", FT_UINT16, BASE_DEC, NULL, 0x0, |
491 | 14 | NULL, HFILL }}, |
492 | 14 | { &hf_simple_sequence_number, |
493 | 14 | { "Sequence Number", "simple.sequence_number", FT_UINT16, BASE_DEC, NULL, 0x0, |
494 | 14 | NULL, HFILL }}, |
495 | 14 | { &hf_simple_src_node, |
496 | 14 | { "Source Node", "simple.src_node", FT_UINT8, BASE_RANGE_STRING | BASE_DEC, RVALS(Node_Strings), 0x0, |
497 | 14 | NULL, HFILL }}, |
498 | 14 | { &hf_simple_src_subnode, |
499 | 14 | { "Source Subnode", "simple.src_subnode", FT_UINT8, BASE_DEC, VALS(Subnode_Strings), 0x0, |
500 | 14 | NULL, HFILL }}, |
501 | 14 | { &hf_simple_dst_node, |
502 | 14 | { "Destination Node", "simple.dst_node", FT_UINT8, BASE_RANGE_STRING | BASE_DEC, RVALS(Node_Strings), 0x0, |
503 | 14 | NULL, HFILL }}, |
504 | 14 | { &hf_simple_dst_subnode, |
505 | 14 | { "Destination Subnode", "simple.dst_subnode", FT_UINT8, BASE_DEC, VALS(Subnode_Strings), 0x0, |
506 | 14 | NULL, HFILL }}, |
507 | 14 | { &hf_simple_packet_size, |
508 | 14 | { "Packet Size", "simple.packet_size", FT_UINT8, BASE_DEC, NULL, 0x0, |
509 | 14 | NULL, HFILL }}, |
510 | 14 | { &hf_simple_packet_type, |
511 | 14 | { "Packet Type", "simple.packet_type", FT_UINT8, BASE_DEC, VALS(PacketType_Strings), 0x0, |
512 | 14 | NULL, HFILL }}, |
513 | 14 | { &hf_simple_transit_time, |
514 | 14 | { "Transit Time", "simple.transit_time", FT_UINT16, BASE_DEC, NULL, 0x0, |
515 | 14 | NULL, HFILL }}, |
516 | 14 | { &hf_simple_link16_subtype, |
517 | 14 | { "Subtype", "simple.link16.subtype", FT_UINT8, BASE_DEC, VALS(Link16_Subtype_Strings), 0x0, |
518 | 14 | NULL, HFILL }}, |
519 | 14 | { &hf_simple_link16_rc, |
520 | 14 | { "R/C Flag", "simple.link16.rc", FT_BOOLEAN, BASE_NONE, TFS(&tfs_required_not_required), 0x0, |
521 | 14 | NULL, HFILL }}, |
522 | 14 | { &hf_simple_link16_network, |
523 | 14 | { "Network", "simple.link16.network", FT_UINT8, BASE_DEC, NULL, 0x0, |
524 | 14 | NULL, HFILL }}, |
525 | 14 | { &hf_simple_link16_ssc2, |
526 | 14 | { "Sequential Slot Count 2", "simple.link16.ssc2", FT_UINT8, BASE_DEC, NULL, 0x0, |
527 | 14 | NULL, HFILL }}, |
528 | 14 | { &hf_simple_link16_npg, |
529 | 14 | { "NPG Number", "simple.link16.npg", FT_UINT16, BASE_DEC, VALS(Link16_NPG_Strings), 0x0, |
530 | 14 | NULL, HFILL }}, |
531 | 14 | { &hf_simple_link16_ssc1, |
532 | 14 | { "Sequential Slot Count 1", "simple.link16.ssc1", FT_UINT16, BASE_DEC, NULL, 0x0, |
533 | 14 | NULL, HFILL }}, |
534 | 14 | { &hf_simple_link16_stn, |
535 | 14 | { "Source Track Number", "simple.link16.stn", FT_UINT16, BASE_OCT, NULL, 0x0, |
536 | 14 | NULL, HFILL }}, |
537 | 14 | { &hf_simple_link16_word_count, |
538 | 14 | { "Word Count", "simple.link16.word_count", FT_UINT16, BASE_DEC, NULL, 0x0, |
539 | 14 | NULL, HFILL }}, |
540 | 14 | { &hf_simple_link16_loopback_id, |
541 | 14 | { "Loopback ID", "simple.link16.loopback_id", FT_UINT16, BASE_DEC, NULL, 0x0, |
542 | 14 | NULL, HFILL }}, |
543 | 14 | { &hf_simple_status_subtype, |
544 | 14 | { "Subtype", "simple.status.subtype", FT_UINT8, BASE_HEX, VALS(Status_Subtype_Strings), 0x0, |
545 | 14 | NULL, HFILL }}, |
546 | 14 | { &hf_simple_status_word_count, |
547 | 14 | { "Word Count", "simple.status.word_count", FT_UINT8, BASE_DEC, NULL, 0x0, |
548 | 14 | NULL, HFILL }}, |
549 | 14 | { &hf_simple_status_name, |
550 | 14 | { "Name", "simple.status.name", FT_STRING, BASE_NONE, NULL, 0x0, |
551 | 14 | NULL, HFILL }}, |
552 | 14 | { &hf_simple_status_time_hours, |
553 | 14 | { "Time (Hours)", "simple.status.time_hours", FT_UINT8, BASE_DEC, NULL, 0x0, |
554 | 14 | NULL, HFILL }}, |
555 | 14 | { &hf_simple_status_node_id, |
556 | 14 | { "Node Id", "simple.status.node_id", FT_UINT8, BASE_DEC, NULL, 0x0, |
557 | 14 | NULL, HFILL }}, |
558 | 14 | { &hf_simple_status_time_seconds, |
559 | 14 | { "Time (Seconds)", "simple.status.time_seconds", FT_UINT8, BASE_DEC, NULL, 0x0, |
560 | 14 | NULL, HFILL }}, |
561 | 14 | { &hf_simple_status_time_minutes, |
562 | 14 | { "Time (Minutes)", "simple.status.time_minutes", FT_UINT8, BASE_DEC, NULL, 0x0, |
563 | 14 | NULL, HFILL }}, |
564 | 14 | { &hf_simple_status_security_level, |
565 | 14 | { "Security Level", "simple.status.security_level", FT_UINT8, BASE_DEC, VALS(Security_Level_Strings), 0x0, |
566 | 14 | NULL, HFILL }}, |
567 | 14 | { &hf_simple_status_node_entry_flag, |
568 | 14 | { "Node Entry Flag", "simple.status.node_entry_flag", FT_BOOLEAN, BASE_NONE, NULL, 0x0, |
569 | 14 | NULL, HFILL }}, |
570 | 14 | { &hf_simple_status_relay_hop, |
571 | 14 | { "Relay Hop", "simple.status.relay_hop", FT_BYTES, BASE_NONE, NULL, 0x0, |
572 | 14 | NULL, HFILL }}, |
573 | 14 | { &hf_simple_status_dx_flag_system_messages, |
574 | 14 | { "DX System Messages", "simple.status.dx_flag.system_messages", FT_BOOLEAN, 16, NULL, 0x0001, |
575 | 14 | NULL, HFILL }}, |
576 | 14 | { &hf_simple_status_dx_flag_common_tims_bims, |
577 | 14 | { "DX Common TIMS/BIMS", "simple.status.dx_flag.common_tims_bims", FT_BOOLEAN, 16, NULL, 0x0002, |
578 | 14 | NULL, HFILL }}, |
579 | 14 | { &hf_simple_status_dx_flag_common_toms_boms, |
580 | 14 | { "DX Common TOMS/BOMS", "simple.status.dx_flag.common_toms_boms", FT_BOOLEAN, 16, NULL, 0x0004, |
581 | 14 | NULL, HFILL }}, |
582 | 14 | { &hf_simple_status_dx_flag_simple_receive, |
583 | 14 | { "DX SIMPLE Receive", "simple.status.dx_flag.simple_receive", FT_BOOLEAN, 16, NULL, 0x8, |
584 | 14 | NULL, HFILL }}, |
585 | 14 | { &hf_simple_status_dx_flag_simple_transmit, |
586 | 14 | { "DX SIMPLE Transmit", "simple.status.dx_flag.simple_transmit", FT_BOOLEAN, 16, NULL, 0x0010, |
587 | 14 | NULL, HFILL }}, |
588 | 14 | { &hf_simple_status_dx_flag_all_tims_bims, |
589 | 14 | { "DX All TIMS/BIMS", "simple.status.dx_flag.all_tims_bims", FT_BOOLEAN, 16, NULL, 0x0020, |
590 | 14 | NULL, HFILL }}, |
591 | 14 | { &hf_simple_status_dx_flag_all_toms_boms, |
592 | 14 | { "DX All TOMS/BOMS", "simple.status.dx_flag.all_toms_boms", FT_BOOLEAN, 16, NULL, 0x0040, |
593 | 14 | NULL, HFILL }}, |
594 | 14 | { &hf_simple_status_dx_file_id, |
595 | 14 | { "DX File Id", "simple.status.dx_file_id", FT_STRING, BASE_NONE, NULL, 0x0, |
596 | 14 | NULL, HFILL }}, |
597 | 14 | { &hf_simple_status_spare_1, |
598 | 14 | { "Spare1", "simple.status.spare_1", FT_BYTES, BASE_NONE, NULL, 0x0, |
599 | 14 | NULL, HFILL }}, |
600 | 14 | { &hf_simple_status_link16_terminal_type, |
601 | 14 | { "Link 16 Type", "simple.status.link16.terminal_type", FT_UINT8, BASE_DEC, VALS(Link16_Terminal_Type), 0x0, |
602 | 14 | NULL, HFILL }}, |
603 | 14 | { &hf_simple_status_link16_role, |
604 | 14 | { "Link 16 Role", "simple.status.link16.role", FT_UINT8, BASE_DEC, VALS(Link16_Role), 0x0, |
605 | 14 | NULL, HFILL }}, |
606 | 14 | { &hf_simple_status_link16_sync_status, |
607 | 14 | { "Link 16 Sync Status", "simple.status.link16.sync_status", FT_UINT8, BASE_DEC, VALS(Link16_Sync_Status), 0x0, |
608 | 14 | NULL, HFILL }}, |
609 | 14 | { &hf_simple_status_link16_terminal_host_status, |
610 | 14 | { "Link 16 Terminal/Host Status", "simple.status.link16.terminal_host_status", FT_UINT8, BASE_DEC, VALS(Link_Terminal_Host_Status), 0x0, |
611 | 14 | NULL, HFILL }}, |
612 | 14 | { &hf_simple_status_link16_stn, |
613 | 14 | { "Link 16 STN", "simple.status.link16.stn", FT_UINT16, BASE_OCT, NULL, 0x0, |
614 | 14 | NULL, HFILL }}, |
615 | 14 | { &hf_simple_status_spare_2, |
616 | 14 | { "Spare2", "simple.status.spare_2", FT_BYTES, BASE_NONE, NULL, 0x0, |
617 | 14 | NULL, HFILL }}, |
618 | 14 | { &hf_simple_status_link11_dts_type, |
619 | 14 | { "Link 11 DTS Type", "simple.status.link11.dts_type", FT_UINT8, BASE_DEC, VALS(Link11_DTS_Type), 0x0, |
620 | 14 | NULL, HFILL }}, |
621 | 14 | { &hf_simple_status_link11_role, |
622 | 14 | { "Link 11 Role", "simple.status.link11.role", FT_UINT8, BASE_DEC, VALS(Link11_Role), 0x0, |
623 | 14 | NULL, HFILL }}, |
624 | 14 | { &hf_simple_status_link11_pu, |
625 | 14 | { "Link 11 PU", "simple.status.link11.pu", FT_UINT8, BASE_OCT, NULL, 0x0, |
626 | 14 | NULL, HFILL }}, |
627 | 14 | { &hf_simple_status_link11_dts_host_status, |
628 | 14 | { "Link 11 DTS/Host Status", "simple.status.link11.dts_host_status", FT_UINT8, BASE_DEC, VALS(Link_Terminal_Host_Status), 0x0, |
629 | 14 | NULL, HFILL }}, |
630 | 14 | { &hf_simple_status_spare_3, |
631 | 14 | { "Spare3", "simple.status.spare_3", FT_BYTES, BASE_NONE, NULL, 0x0, |
632 | 14 | NULL, HFILL }}, |
633 | 14 | { &hf_simple_checksum, |
634 | 14 | { "Checksum", "simple.checksum", FT_UINT16, BASE_HEX, NULL, 0x0, |
635 | 14 | NULL, HFILL }}, |
636 | 14 | { &hf_simple_checksum_status, |
637 | 14 | { "Checksum Status", "simple.checksum.status", FT_UINT8, BASE_NONE, VALS(proto_checksum_vals), 0x0, |
638 | 14 | NULL, HFILL }} |
639 | 14 | }; |
640 | 14 | static int *ett[] = { |
641 | 14 | &ett_simple, |
642 | 14 | &ett_packet, |
643 | 14 | &ett_simple_status_dx_flag, |
644 | 14 | }; |
645 | 14 | static ei_register_info ei[] = { |
646 | 14 | { &ei_simple_sync_bytes_bad, { "simple.sync_bytes.bad", PI_MALFORMED, PI_ERROR, "Bad sync bytes", EXPFILL }}, |
647 | 14 | { &ei_simple_length_bad, { "simple.length.bad", PI_MALFORMED, PI_ERROR, "Bad length", EXPFILL }}, |
648 | 14 | { &ei_simple_packet_size_bad, { "simple.packet_size.bad", PI_MALFORMED, PI_ERROR, "Bad packet length", EXPFILL }}, |
649 | 14 | { &ei_simple_checksum_bad, { "simple.checksum.bad.expert", PI_CHECKSUM, PI_ERROR, "Bad checksum", EXPFILL }}, |
650 | 14 | }; |
651 | 14 | expert_module_t* expert_simple; |
652 | | |
653 | 14 | proto_simple = proto_register_protocol("Standard Interface for Multiple Platform Link Evaluation", "SIMPLE", "simple"); |
654 | 14 | proto_register_field_array(proto_simple, hf, array_length(hf)); |
655 | 14 | proto_register_subtree_array(ett, array_length(ett)); |
656 | 14 | expert_simple = expert_register_protocol(proto_simple); |
657 | 14 | expert_register_field_array(expert_simple, ei, array_length(ei)); |
658 | 14 | simple_dissector_handle = register_dissector("simple", dissect_simple, proto_simple); |
659 | 14 | } |
660 | | |
661 | | void proto_reg_handoff_simple(void) |
662 | 14 | { |
663 | 14 | dissector_add_for_decode_as_with_preference("udp.port", simple_dissector_handle); |
664 | 14 | dissector_add_for_decode_as_with_preference("tcp.port", simple_dissector_handle); |
665 | | |
666 | 14 | link16_handle = find_dissector_add_dependency("link16", proto_simple); |
667 | 14 | } |
668 | | |
669 | | /* |
670 | | * Editor modelines - https://www.wireshark.org/tools/modelines.html |
671 | | * |
672 | | * Local variables: |
673 | | * c-basic-offset: 4 |
674 | | * tab-width: 8 |
675 | | * indent-tabs-mode: nil |
676 | | * End: |
677 | | * |
678 | | * vi: set shiftwidth=4 tabstop=8 expandtab: |
679 | | * :indentSize=4:tabSize=8:noTabs=true: |
680 | | */ |