2 * Dissects a variant of 3GPP TS 27.010 multiplexing protocol
3 * Copyright 2011, Hans-Christoph Schemmel <hans-christoph.schemmel[AT]cinterion.com>
5 * Wireshark - Network traffic analyzer
6 * By Gerald Combs <gerald@wireshark.org>
7 * Copyright 1998 Gerald Combs
9 * SPDX-License-Identifier: GPL-2.0-or-later
13 * This dissector analyses a multiplexed communication between a GSM modem and the host,
14 * whereby the multiplexing is based upon a variant of the specification 3G TS 27.010.
16 * The assigned DLT value is:
17 * LINKTYPE_MUX27010 236 DLT_MUX27010
19 * A detailed description of the packet structure/LINKTYPE_MUX27010 can be found on:
20 * http://www.tcpdump.org/linktypes/LINKTYPE_MUX27010.html
25 #include <epan/packet.h>
26 #include <wiretap/wtap.h>
27 #include <epan/reassemble.h>
28 #include <epan/crc8-tvb.h>
29 #include <epan/expert.h>
31 void proto_register_mux27010(void);
32 void proto_reg_handoff_mux27010(void);
34 #define PROTO_TAG_MUX27010 "MUX27010"
37 #define MUX27010_EXTENDED_HEADER_NOT_ENDED 0x01
40 #define MUX27010_DLCI_ADDRESS_FLAG 0xFC
41 #define MUX27010_EA_ADDRESS_FLAG 0x01
42 #define MUX27010_CR_ADDRESS_FLAG 0x02
45 #define MUX27010_FRAMETYPE_CONTROL_FLAG 0xEF
46 #define MUX27010_FRAMETYPE_CONTROL_FLAG_SABM 0x2F
47 #define MUX27010_FRAMETYPE_CONTROL_FLAG_UA 0x63
48 #define MUX27010_FRAMETYPE_CONTROL_FLAG_DM 0x0F
49 #define MUX27010_FRAMETYPE_CONTROL_FLAG_DISC 0x43
50 #define MUX27010_FRAMETYPE_CONTROL_FLAG_UIH 0xEF
51 #define MUX27010_PF_CONTROL_FLAG 0x10
52 #define MUX27010_FRAMETYPE_CONTROL_FLAG_UIH_E 0x00
53 #define MUX27010_FRAMETYPE_CONTROL_FLAG_RR 0x01
54 #define MUX27010_FRAMETYPE_CONTROL_FLAG_RNR 0x05
55 #define MUX27010_FRAMETYPE_CONTROL_FLAG_REJ 0x09
56 #define MUX27010_FRAMETYPE_CONTROL_FLAG_NS 0x0E
57 #define MUX27010_FRAMETYPE_CONTROL_FLAG_NR 0xE0
58 #define MUX27010_FRAMETYPE_CONTROL_FLAG_NOT_GREATER_THEN_7 0x07
62 #define MUX27010_EA_LENGTH_FLAG 0x01
63 #define MUX27010_FRAMESIZE_LENGTH_FLAG 0xFE
64 #define MUX27010_FRAMESIZE_LENGTH_FLAG_EA 0xFFFE
67 #define MUX27010_EA_CONTROLCHANNEL_FRAMETYPE_FLAG 0x01
68 #define MUX27010_CR_CONTROLCHANNEL_FRAMETYPE_FLAG 0x02
69 #define MUX27010_COMMAND_CONTROLCHANNEL_FRAMETYPE_FLAG 0xFC
70 #define MUX27010_EA_CONTROLCHANNEL_LENGTH_FLAG 0x01
71 #define MUX27010_LENGTHFIELD_CONTROLCHANNEL_LENGTH_FLAG 0xFE
72 #define MUX27010_VALUE_CONTROLCHANNEL_TEST_VERSION 0xFF
73 #define MUX27010_VALUE_CONTROLCHANNEL_TEST_IEI_TE 0x04
74 #define MUX27010_VALUE_CONTROLCHANNEL_TEST_IEI_MS 0x08
75 #define MUX27010_VALUE_CONTROLCHANNEL_MSC_DCLI 0xFC
76 #define MUX27010_VALUE_CONTROLCHANNEL_MSC_V24_FC 0x02
77 #define MUX27010_VALUE_CONTROLCHANNEL_MSC_V24_RTC 0x04
78 #define MUX27010_VALUE_CONTROLCHANNEL_MSC_V24_RTR 0x08
79 #define MUX27010_VALUE_CONTROLCHANNEL_MSC_V24_RING 0x40
80 #define MUX27010_VALUE_CONTROLCHANNEL_MSC_V24_DCD 0x80
81 #define MUX27010_VALUE_CONTROLCHANNEL_PN_DLCI 0x3F
82 #define MUX27010_VALUE_CONTROLCHANNEL_PN_FRAMETYPE 0x0F
83 #define MUX27010_VALUE_CONTROLCHANNEL_PN_CL 0xF0
84 #define MUX27010_VALUE_CONTROLCHANNEL_PN_PRIO 0x3F
85 #define MUX27010_VALUE_CONTROLCHANNEL_PN_WINSIZE 0x07
87 /*Command pattern - set C/R bit to 1*/
88 #define MUX27010_COMMAND_MULTIPLEXER_CLOSEDOWN 0xC3 /*11000011*/
89 #define MUX27010_COMMAND_TEST_COMMAND 0x23 /*00100011*/
90 #define MUX27010_COMMAND_POWER_SAVING_CONTROL 0x43 /*01000011*/
91 #define MUX27010_COMMAND_NON_SUPPORTED_COMMAND_RESPONSE 0x13 /*00010011*/
92 #define MUX27010_COMMAND_MODEM_STATUS_COMMAND 0xE3 /*00010011*/
93 #define MUX27010_COMMAND_PARAMETER_NEGOTIATION 0x83 /*10000011*/
96 /* Wireshark ID of the MUX27010 protocol */
97 static int proto_mux27010
;
99 /* Handles of subdissectors */
100 static dissector_handle_t ppp_handle
;
103 static const value_string packettypenames
[] = {
105 { 1, "SOMETHING_ELSE" },
110 static const value_string direction_vals
[] = {
111 { 0, "Direction: Application => Module" },
112 { 1, "Module => Application" },
118 static const value_string detailedvalue_response_vals
[] = {
124 static const value_string frame_type_vals
[] = {
125 { MUX27010_FRAMETYPE_CONTROL_FLAG_SABM
, "SABM" },
126 { MUX27010_FRAMETYPE_CONTROL_FLAG_UA
, "UA" },
127 { MUX27010_FRAMETYPE_CONTROL_FLAG_DM
, "DM" },
128 { MUX27010_FRAMETYPE_CONTROL_FLAG_DISC
, "DISC" },
129 { MUX27010_FRAMETYPE_CONTROL_FLAG_UIH
, "UIH" },
130 { MUX27010_FRAMETYPE_CONTROL_FLAG_UIH_E
, "UIH_E" },
131 { MUX27010_FRAMETYPE_CONTROL_FLAG_RR
, "Receive Ready" },
132 { MUX27010_FRAMETYPE_CONTROL_FLAG_RNR
, "Receive Not Ready" },
133 { MUX27010_FRAMETYPE_CONTROL_FLAG_REJ
, "Reject" },
137 static const value_string command_vals
[] = {
138 { (MUX27010_COMMAND_MULTIPLEXER_CLOSEDOWN
>>2), "Multiplexer Close Down" },
139 { (MUX27010_COMMAND_TEST_COMMAND
>>2), "Test Command" },
140 { (MUX27010_COMMAND_POWER_SAVING_CONTROL
>>2), "Power Saving Control" },
141 { (MUX27010_COMMAND_NON_SUPPORTED_COMMAND_RESPONSE
>>2), "Non-supported Command Response" },
142 { (MUX27010_COMMAND_MODEM_STATUS_COMMAND
>>2), "Modem Status Command" },
143 { (MUX27010_COMMAND_PARAMETER_NEGOTIATION
>>2), "Parameter Negotiation" },
147 static const value_string iei_coding_vals
[] = {
148 { MUX27010_VALUE_CONTROLCHANNEL_TEST_IEI_TE
, "TEMUX_VERSION" },
149 { MUX27010_VALUE_CONTROLCHANNEL_TEST_IEI_MS
, "MSMUX_VERSION" },
154 struct controlchannel_type
158 int number_of_type_frames
;
161 struct controlchannel
163 uint8_t length_value
;
164 int number_of_length_frames
;
167 /* The following hf_* variables are used to hold the Wireshark IDs of
168 * the header fields; they are filled out when call
169 * proto_register_field_array() in proto_register_mux27010()
172 static int hf_mux27010_extended_header
;
173 static int hf_mux27010_direction
;
174 static int hf_mux27010
;
175 static int hf_mux27010_address
;
176 static int hf_mux27010_control
;
177 static int hf_mux27010_length
;
178 static int hf_mux27010_controlchannel
;
181 static int hf_mux27010_extended_header_size
;
182 static int hf_mux27010_extended_header_msg_number_I
;
183 static int hf_mux27010_extended_header_freq_number_I
;
184 static int hf_mux27010_extended_header_start_pos_I
;
185 static int hf_mux27010_extended_header_start_byte_I
;
186 static int hf_mux27010_extended_header_end_pos_I
;
187 static int hf_mux27010_extended_header_end_byte_I
;
188 static int hf_mux27010_extended_header_flag_ended_I
;
190 static int hf_mux27010_extended_header_msg_number_II
;
191 static int hf_mux27010_extended_header_freq_number_II
;
192 static int hf_mux27010_extended_header_start_pos_II
;
193 static int hf_mux27010_extended_header_start_byte_II
;
194 static int hf_mux27010_extended_header_end_pos_II
;
195 static int hf_mux27010_extended_header_end_byte_II
;
196 static int hf_mux27010_extended_header_flag_ended_II
;
198 static int hf_mux27010_extended_header_msg_number_III
;
199 static int hf_mux27010_extended_header_freq_number_III
;
200 static int hf_mux27010_extended_header_start_pos_III
;
201 static int hf_mux27010_extended_header_start_byte_III
;
202 static int hf_mux27010_extended_header_end_pos_III
;
203 static int hf_mux27010_extended_header_end_byte_III
;
204 static int hf_mux27010_extended_header_flag_ended_III
;
207 static int hf_mux27010_dlciaddressflag
;
208 static int hf_mux27010_eaaddressflag
;
209 static int hf_mux27010_craddressflag
;
210 /* static int hf_mux27010_addressdirection; */
212 static int hf_mux27010_controlframetype
;
213 static int hf_mux27010_controlframetypens
;
214 static int hf_mux27010_controlframetypenr
;
215 static int hf_mux27010_pfcontrolflag
;
217 static int hf_mux27010_ealengthflag
;
218 static int hf_mux27010_lengthframesize
;
219 static int hf_mux27010_lengthframesize_ea
;
220 /*Control channel dlci = 0*/
221 static int hf_mux27010_controlchannelframetype
;
222 static int hf_mux27010_controlchanneleaframetype
;
223 static int hf_mux27010_controlchannelcrframetype
;
224 static int hf_mux27010_controlchannelframetypecommand
;
225 static int hf_mux27010_controlchannellength
;
226 static int hf_mux27010_controlchannelealength
;
227 static int hf_mux27010_controlchannellengthfield
;
228 static int hf_mux27010_controlchannelvalue
;
229 static int hf_mux27010_controlchannel_iei_coding
;
230 static int hf_mux27010_controlchanneldetailedvalue
;
231 static int hf_mux27010_controlchannel_detailedvalue_response
;
232 static int hf_mux27010_controlchanneldetailedvaluetestcommandversion
;
233 static int hf_mux27010_controlchanneldetailedvaluemscdlci
;
234 /* static int hf_mux27010_controlchanneldetailedvaluemscv24; */
235 static int hf_mux27010_controlchanneldetailedvaluemscv24fc
;
236 static int hf_mux27010_controlchanneldetailedvaluemscv24rtc
;
237 static int hf_mux27010_controlchanneldetailedvaluemscv24rtr
;
238 static int hf_mux27010_controlchanneldetailedvaluemscv24ring
;
239 static int hf_mux27010_controlchanneldetailedvaluemscv24dcd
;
240 static int hf_mux27010_controlchanneldetailedvaluemscbreak
;
241 static int hf_mux27010_controlchanneldetailedvaluepndlci
;
242 static int hf_mux27010_controlchanneldetailedvaluepnframetype
;
243 static int hf_mux27010_controlchanneldetailedvaluepncl
;
244 static int hf_mux27010_controlchanneldetailedvaluepnprio
;
245 static int hf_mux27010_controlchanneldetailedvaluepntimer
;
246 static int hf_mux27010_controlchanneldetailedvaluepnframesize
;
247 static int hf_mux27010_controlchanneldetailedvaluepnna
;
248 static int hf_mux27010_controlchanneldetailedvaluepnwinsize
;
250 static int hf_mux27010_information
;
251 static int hf_mux27010_information_str
;
253 static int hf_mux27010_checksum
;
254 static int hf_mux27010_checksum_correct
;
256 /* These are the ids of the subtrees that we may be creating */
257 static int ett_mux27010_extended_header
;
258 static int ett_mux27010
;
259 static int ett_mux27010_address
;
260 static int ett_mux27010_control
;
261 static int ett_mux27010_length
;
262 static int ett_mux27010_controlchannel
;
263 static int ett_mux27010_controlchannelframetype
;
264 static int ett_mux27010_controlchannellength
;
265 static int ett_mux27010_controlchannelvalue
;
266 static int ett_mux27010_information
;
267 static int ett_mux27010_checksum
;
269 static expert_field ei_mux27010_message_illogical
;
270 static expert_field ei_mux27010_checksum_incorrect
;
272 static int hf_msg_fragments
;
273 static int hf_msg_fragment
;
274 static int hf_msg_fragment_overlap
;
275 static int hf_msg_fragment_overlap_conflicts
;
276 static int hf_msg_fragment_multiple_tails
;
277 static int hf_msg_fragment_too_long_fragment
;
278 static int hf_msg_fragment_error
;
279 static int hf_msg_fragment_count
;
280 static int hf_msg_reassembled_in
;
281 static int hf_msg_reassembled_length
;
283 static int ett_msg_fragment
;
284 static int ett_msg_fragments
;
286 static dissector_handle_t mux27010_handle
;
288 static const fragment_items msg_frag_items
= {
289 /* Fragment subtrees */
292 /* Fragment fields */
295 &hf_msg_fragment_overlap
,
296 &hf_msg_fragment_overlap_conflicts
,
297 &hf_msg_fragment_multiple_tails
,
298 &hf_msg_fragment_too_long_fragment
,
299 &hf_msg_fragment_error
,
300 &hf_msg_fragment_count
,
301 /* Reassembled in field */
302 &hf_msg_reassembled_in
,
303 /* Reassembled length field */
304 &hf_msg_reassembled_length
,
305 /* Reassembled data field */
311 static reassembly_table msg_reassembly_table
;
316 getExtendedHeader(tvbuff_t
*tvb
, proto_tree
*field_tree
, int offset
, uint8_t* sizeMuxPPPHeader
){
319 *sizeMuxPPPHeader
= tvb_get_uint8(tvb
, offset
);
320 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_size
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
321 if (*sizeMuxPPPHeader
> 0){
323 uint16_t tmpStartByte
= 0;
324 uint16_t tmpLastByte
= 0;
325 for (i
=0; i
< *sizeMuxPPPHeader
/7; i
++){
328 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_msg_number_I
, tvb
, offset
+tmpOffset
, 2, ENC_BIG_ENDIAN
);
331 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_freq_number_I
, tvb
, offset
+tmpOffset
, 2, ENC_BIG_ENDIAN
);
334 tmpStartByte
= tvb_get_uint8(tvb
, tmpOffset
) + *sizeMuxPPPHeader
+ 1;
335 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_start_pos_I
, tvb
, offset
+tmpOffset
, 1, ENC_BIG_ENDIAN
);
336 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_start_byte_I
, tvb
, tmpStartByte
, 1, ENC_BIG_ENDIAN
);
339 tmpLastByte
= tvb_get_uint8(tvb
, tmpOffset
) + *sizeMuxPPPHeader
+ 1;
340 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_end_pos_I
, tvb
, offset
+tmpOffset
, 1, ENC_BIG_ENDIAN
);
341 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_end_byte_I
, tvb
, tmpLastByte
, 1, ENC_BIG_ENDIAN
);
344 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_flag_ended_I
, tvb
, offset
+tmpOffset
, 1, ENC_BIG_ENDIAN
);
345 if ((tvb_get_uint8(tvb
, tmpOffset
) & MUX27010_EXTENDED_HEADER_NOT_ENDED
) == MUX27010_EXTENDED_HEADER_NOT_ENDED
)
346 proto_tree_add_uint_format(field_tree
, hf_mux27010_extended_header_flag_ended_I
, tvb
, offset
+tmpOffset
, 1, 1, "Not Last Packet in Frequence");
348 proto_tree_add_uint_format(field_tree
, hf_mux27010_extended_header_flag_ended_I
, tvb
, offset
+tmpOffset
, 1, 1, "Last Packet in Frequence");
353 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_msg_number_II
, tvb
, offset
+tmpOffset
, 2, ENC_BIG_ENDIAN
);
356 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_freq_number_II
, tvb
, offset
+tmpOffset
, 2, ENC_BIG_ENDIAN
);
359 tmpStartByte
= tvb_get_uint8(tvb
, tmpOffset
) + *sizeMuxPPPHeader
+ 1;
360 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_start_pos_II
, tvb
, offset
+tmpOffset
, 1, ENC_BIG_ENDIAN
);
361 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_start_byte_II
, tvb
, tmpStartByte
, 1, ENC_BIG_ENDIAN
);
364 tmpLastByte
= tvb_get_uint8(tvb
, tmpOffset
) + *sizeMuxPPPHeader
+ 1;
365 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_end_pos_II
, tvb
, offset
+tmpOffset
, 1, ENC_BIG_ENDIAN
);
366 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_end_byte_II
, tvb
, tmpLastByte
, 1, ENC_BIG_ENDIAN
);
369 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_flag_ended_II
, tvb
, offset
+tmpOffset
, 1, ENC_BIG_ENDIAN
);
370 if ((tvb_get_uint8(tvb
, tmpOffset
) & MUX27010_EXTENDED_HEADER_NOT_ENDED
) == MUX27010_EXTENDED_HEADER_NOT_ENDED
)
371 proto_tree_add_uint_format(field_tree
, hf_mux27010_extended_header_flag_ended_II
, tvb
, offset
+tmpOffset
, 1, 1, "Not Last Packet in Frequence");
373 proto_tree_add_uint_format(field_tree
, hf_mux27010_extended_header_flag_ended_II
, tvb
, offset
+tmpOffset
, 1, 1, "Last Packet in Frequence");
378 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_msg_number_III
, tvb
, offset
+tmpOffset
, 2, ENC_BIG_ENDIAN
);
381 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_freq_number_III
, tvb
, offset
+tmpOffset
, 2, ENC_BIG_ENDIAN
);
384 tmpStartByte
= tvb_get_uint8(tvb
, tmpOffset
) + *sizeMuxPPPHeader
+ 1;
385 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_start_pos_III
, tvb
, offset
+tmpOffset
, 1, ENC_BIG_ENDIAN
);
386 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_start_byte_III
, tvb
, tmpStartByte
, 1, ENC_BIG_ENDIAN
);
389 tmpLastByte
= tvb_get_uint8(tvb
, tmpOffset
) + *sizeMuxPPPHeader
+ 1;
390 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_end_pos_III
, tvb
, offset
+tmpOffset
, 1, ENC_BIG_ENDIAN
);
391 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_end_byte_III
, tvb
, tmpLastByte
, 1, ENC_BIG_ENDIAN
);
394 proto_tree_add_item(field_tree
, hf_mux27010_extended_header_flag_ended_III
, tvb
, offset
+tmpOffset
, 1, ENC_BIG_ENDIAN
);
395 if ((tvb_get_uint8(tvb
, tmpOffset
) & MUX27010_EXTENDED_HEADER_NOT_ENDED
) == MUX27010_EXTENDED_HEADER_NOT_ENDED
)
396 proto_tree_add_uint_format(field_tree
, hf_mux27010_extended_header_flag_ended_III
, tvb
, offset
+tmpOffset
, 1, 1, "Not Last Packet in Frequence");
398 proto_tree_add_uint_format(field_tree
, hf_mux27010_extended_header_flag_ended_III
, tvb
, offset
+tmpOffset
, 1, 1, "Last Packet in Frequence");
406 return *sizeMuxPPPHeader
;
410 /*Get the direction of the actual packet*/
412 getFrameDirection(tvbuff_t
*tvb
, packet_info
*pinfo
, proto_tree
*field_tree
, int offset
){
413 uint8_t direction_in_out
;
415 /*Direction is coded in the first byte of the frame*/
416 direction_in_out
= tvb_get_uint8(tvb
, offset
);
418 /*If first byte is 0 => Frame source is Application*/
419 /*If first byte is 1 => Frame source is Module*/
421 proto_tree_add_uint(field_tree
, hf_mux27010_direction
, tvb
, offset
, 1, direction_in_out
& 3);
422 switch (direction_in_out
& 3) {
423 case (0):/*Application >> Module*/
424 col_set_str(pinfo
->cinfo
, COL_DEF_SRC
, "Application DLCI ");
425 col_set_str(pinfo
->cinfo
, COL_DEF_DST
, "Module");
427 case (1):/*Module >> Application*/
428 col_set_str(pinfo
->cinfo
, COL_DEF_SRC
, "Module DLCI ");
429 col_set_str(pinfo
->cinfo
, COL_DEF_DST
, "Application");
432 col_set_str(pinfo
->cinfo
, COL_DEF_SRC
, "Direction not valid ");
433 col_set_str(pinfo
->cinfo
, COL_DEF_DST
, "Direction not valid ");
442 /*Get the address of the actual frame*/
444 getFrameAddress(tvbuff_t
*tvb
, packet_info
*pinfo
, proto_tree
*field_tree_addr
, int offset
, uint8_t* dlci_number
){
447 byte
= tvb_get_uint8(tvb
, offset
);
448 /*Get the DCLI number of the frame >> overwrite other bits (E/A, CR) >> shift*/
449 *dlci_number
= (byte
& MUX27010_DLCI_ADDRESS_FLAG
) >> 2;
451 /*Add text to string for Source column*/
452 col_append_fstr(pinfo
->cinfo
, COL_DEF_SRC
, "%d ", *dlci_number
);
454 /*Add items to subtree to display the details*/
455 proto_tree_add_item(field_tree_addr
, hf_mux27010_eaaddressflag
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
456 proto_tree_add_item(field_tree_addr
, hf_mux27010_craddressflag
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
457 proto_tree_add_item(field_tree_addr
, hf_mux27010_dlciaddressflag
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
464 /*Get frame data from control field*/
466 getFrameControlData(tvbuff_t
*tvb
, packet_info
*pinfo
, proto_tree
*field_tree
, int offset
, uint8_t* frame_type
){
467 /*if the frame type is known -> 1 else 0*/
468 uint8_t known_frame_type
= 0;
470 /*Get the type of frame*/
471 *frame_type
= tvb_get_uint8(tvb
, offset
) & MUX27010_FRAMETYPE_CONTROL_FLAG
;
473 /*Find out the frame type and write info into column*/
474 switch (*frame_type
) {
475 case (MUX27010_FRAMETYPE_CONTROL_FLAG_SABM
): /*SABM frame*/
476 case (MUX27010_FRAMETYPE_CONTROL_FLAG_UA
): /*UA frame*/
477 case (MUX27010_FRAMETYPE_CONTROL_FLAG_DM
): /*DM frame*/
478 case (MUX27010_FRAMETYPE_CONTROL_FLAG_DISC
): /*DISC frame*/
479 case (MUX27010_FRAMETYPE_CONTROL_FLAG_UIH
): /*UIH frame*/
480 proto_tree_add_uint(field_tree
, hf_mux27010_controlframetype
, tvb
, offset
, 1, *frame_type
);
484 /*Got another frame -> probably a UIH_E, RR, RNR or REJ frame from a DLCI channel != 0 ==> Data channel*/
486 /*Check if frame is a UIH_E frame*/
487 if ((MUX27010_FRAMETYPE_CONTROL_FLAG_UIH_E
| MUX27010_FRAMETYPE_CONTROL_FLAG_NS
| MUX27010_FRAMETYPE_CONTROL_FLAG_NR
) == (*frame_type
| MUX27010_FRAMETYPE_CONTROL_FLAG_NS
| MUX27010_FRAMETYPE_CONTROL_FLAG_NR
)) {
488 *frame_type
= MUX27010_FRAMETYPE_CONTROL_FLAG_UIH_E
;
489 /*Add frame type to column*/
490 proto_tree_add_uint(field_tree
, hf_mux27010_controlframetype
, tvb
, offset
, 1, MUX27010_FRAMETYPE_CONTROL_FLAG_UIH_E
);
491 /*Add info about sequence numbers to column*/
492 proto_tree_add_item(field_tree
, hf_mux27010_controlframetypens
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
493 proto_tree_add_item(field_tree
, hf_mux27010_controlframetypenr
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
495 /*Frame type is known*/
496 known_frame_type
= 1;
498 /*Check if frame is a RR frame*/
499 if ((MUX27010_FRAMETYPE_CONTROL_FLAG_RR
| MUX27010_FRAMETYPE_CONTROL_FLAG_NR
) == (*frame_type
| MUX27010_FRAMETYPE_CONTROL_FLAG_NR
)) {
500 *frame_type
= MUX27010_FRAMETYPE_CONTROL_FLAG_RR
;
501 /*Add frame type to column*/
502 proto_tree_add_uint(field_tree
, hf_mux27010_controlframetype
, tvb
, offset
, 1, MUX27010_FRAMETYPE_CONTROL_FLAG_RR
);
503 /*Add info about sequence number to column*/
504 proto_tree_add_item(field_tree
, hf_mux27010_controlframetypenr
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
506 /*Frame type is known*/
507 known_frame_type
= 1;
509 if ((MUX27010_FRAMETYPE_CONTROL_FLAG_RNR
| MUX27010_FRAMETYPE_CONTROL_FLAG_NR
) == (*frame_type
| MUX27010_FRAMETYPE_CONTROL_FLAG_NR
)) {
510 *frame_type
= MUX27010_FRAMETYPE_CONTROL_FLAG_RNR
;
511 /*Add frame type to column*/
512 proto_tree_add_uint(field_tree
, hf_mux27010_controlframetype
, tvb
, offset
, 1, MUX27010_FRAMETYPE_CONTROL_FLAG_RNR
);
513 /*Add info about sequence number to column*/
514 proto_tree_add_item(field_tree
, hf_mux27010_controlframetypenr
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
516 /*Frame type is known*/
517 known_frame_type
= 1;
519 if ((MUX27010_FRAMETYPE_CONTROL_FLAG_REJ
| MUX27010_FRAMETYPE_CONTROL_FLAG_NR
) == (*frame_type
| MUX27010_FRAMETYPE_CONTROL_FLAG_NR
)) {
520 *frame_type
= MUX27010_FRAMETYPE_CONTROL_FLAG_REJ
;
521 /*Add frame type to column*/
522 proto_tree_add_uint(field_tree
, hf_mux27010_controlframetype
, tvb
, offset
, 1, MUX27010_FRAMETYPE_CONTROL_FLAG_REJ
);
523 /*Add info about sequence number to column*/
524 proto_tree_add_item(field_tree
, hf_mux27010_controlframetypenr
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
526 /*Frame type is known*/
527 known_frame_type
= 1;
531 if (known_frame_type
== 0) {
532 /*Add frame type to column*/
533 proto_tree_add_uint(field_tree
, hf_mux27010_controlframetype
, tvb
, offset
, 1, *frame_type
);
537 /*Write information to string for column info*/
538 col_add_fstr(pinfo
->cinfo
, COL_INFO
, "(%s)", val_to_str_const(*frame_type
, frame_type_vals
, "Unknown"));
540 /*Add Frame type value and PF bit to column*/
541 proto_tree_add_item(field_tree
, hf_mux27010_controlframetype
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
542 proto_tree_add_item(field_tree
, hf_mux27010_pfcontrolflag
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
550 /*Get frame data from length field*/
552 getFrameLength(tvbuff_t
*tvb
, proto_tree
*field_tree
, int offset
, uint32_t* length_info
){
555 uint8_t length_ea
= tvb_get_uint8(tvb
, offset
) & MUX27010_EA_LENGTH_FLAG
;
556 proto_tree_add_item(field_tree
, hf_mux27010_ealengthflag
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
558 /*Get the length of the info field*/
560 /*If E/A = 1 it is the last octet*/
561 if (length_ea
== 1) {
563 /*Add the E/A bit and the length value to the subtree*/
564 proto_tree_add_item(field_tree
, hf_mux27010_lengthframesize
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
565 *length_info
= (tvb_get_uint8(tvb
, offset
) & MUX27010_FRAMESIZE_LENGTH_FLAG
) >> 1; /*Shift because of EA bit*/
569 /*If E/A = 0 the length of the info field is >127;
570 first octet stores LSB bits, second octet MSB -> LITTLE ENDIAN stuffing*/
571 proto_tree_add_item_ret_uint(field_tree
, hf_mux27010_lengthframesize_ea
, tvb
, offset
, 2, ENC_LITTLE_ENDIAN
, length_info
);
577 /*Get frame type of control channel frame*/
579 getControlChannelFrameType(tvbuff_t
*tvb
, packet_info
*pinfo
, proto_tree
*field_tree_ctr
, int offset
,
580 struct controlchannel_type
* cctype
){
581 uint8_t controlchannel_type_ea
;
584 controlchannel_type_ea
= tvb_get_uint8(tvb
, offset
) & MUX27010_EA_CONTROLCHANNEL_FRAMETYPE_FLAG
;
586 /*Set variable for number of octets for frame type to 0*/
587 cctype
->number_of_type_frames
= 0;
588 /*If E/A bit = 1, there will be no other frame type octet*/
589 if (controlchannel_type_ea
== 1)
590 cctype
->number_of_type_frames
++;
592 /*If E/A = 0, read all frame type octets*/
593 while (controlchannel_type_ea
== 0){
594 cctype
->number_of_type_frames
++;
595 controlchannel_type_ea
= tvb_get_uint8(tvb
, offset
+cctype
->number_of_type_frames
) & MUX27010_EA_CONTROLCHANNEL_FRAMETYPE_FLAG
;
599 cctype
->cr
= (tvb_get_uint8(tvb
, offset
) & MUX27010_CR_CONTROLCHANNEL_FRAMETYPE_FLAG
) >> 1;
602 cctype
->command
= tvb_get_uint8(tvb
, offset
) & MUX27010_COMMAND_CONTROLCHANNEL_FRAMETYPE_FLAG
;
604 /*Add info to subtree*/
605 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneleaframetype
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
606 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchannelcrframetype
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
607 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchannelframetypecommand
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
609 /*Check the control channel frame types and add the name to the subtree Info column*/
610 col_append_fstr(pinfo
->cinfo
, COL_INFO
, " %s", val_to_str_const(cctype
->command
>>2, command_vals
, "Unknown"));
612 if (cctype
->cr
== 1) /*Command C/R*/{
613 col_append_str(pinfo
->cinfo
, COL_INFO
, " (Command)");
616 col_append_str(pinfo
->cinfo
, COL_INFO
, " (Response)");
619 return cctype
->number_of_type_frames
;
623 /*Get length of control channel info field*/
625 getControlChannelLength(tvbuff_t
*tvb
, proto_tree
*field_tree_ctr
, int offset
, struct controlchannel
* cc
) {
626 uint8_t controlchannel_length_ea
;
629 controlchannel_length_ea
= tvb_get_uint8(tvb
, offset
) & MUX27010_EA_CONTROLCHANNEL_LENGTH_FLAG
;
631 /*Set variable for number of octets for info field to 0*/
632 cc
->number_of_length_frames
= 0;
633 /*If E/A bit = 1, there will be no other info field length octet*/
634 if (controlchannel_length_ea
== 1)
635 cc
->number_of_length_frames
++;
637 /*If E/A = 0, read all length of info field octets*/
638 while (controlchannel_length_ea
== 0){
639 cc
->number_of_length_frames
++;
640 controlchannel_length_ea
= tvb_get_uint8(tvb
, offset
+cc
->number_of_length_frames
) & MUX27010_EA_CONTROLCHANNEL_LENGTH_FLAG
;
643 /*Get the data from info field*/
644 cc
->length_value
= (tvb_get_uint8(tvb
, offset
) & MUX27010_LENGTHFIELD_CONTROLCHANNEL_LENGTH_FLAG
) >> 1;
646 /*Add data to subtree*/
647 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchannelealength
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
648 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchannellengthfield
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
650 return cc
->number_of_length_frames
;
655 /*Get values of control channel*/
657 getControlChannelValues(tvbuff_t
*tvb
, proto_tree
*field_tree_ctr
, int offset
,
658 struct controlchannel
* cc
, struct controlchannel_type
* cctype
){
659 uint8_t controlchannel_iei
;
660 uint8_t controlchannel_psc
;
662 /*Command pattern for Test Command (C/R is set to 1)*/
663 switch (cctype
->command
| MUX27010_EA_CONTROLCHANNEL_FRAMETYPE_FLAG
| MUX27010_CR_CONTROLCHANNEL_FRAMETYPE_FLAG
)
665 case MUX27010_COMMAND_TEST_COMMAND
:
666 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluetestcommandversion
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
667 controlchannel_iei
= tvb_get_uint8(tvb
, offset
);
668 if ((controlchannel_iei
== MUX27010_VALUE_CONTROLCHANNEL_TEST_IEI_TE
) ||
669 (controlchannel_iei
== MUX27010_VALUE_CONTROLCHANNEL_TEST_IEI_MS
)) {
670 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchannel_iei_coding
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
673 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchannelvalue
, tvb
, offset
+1, cc
->length_value
-1, ENC_NA
|ENC_ASCII
);
676 /*Command pattern for Power saving control (C/R is set to 1)*/
677 case MUX27010_COMMAND_POWER_SAVING_CONTROL
:
678 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvalue
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
679 controlchannel_psc
= tvb_get_uint8(tvb
, offset
);
680 if (cctype
->cr
== 0 && controlchannel_psc
== 0) /*Response Failure*/
681 proto_tree_add_uint(field_tree_ctr
, hf_mux27010_controlchannel_detailedvalue_response
, tvb
, offset
, cc
->length_value
, 0);
682 if (cctype
->cr
== 0 && controlchannel_psc
== 1) /*Response Success*/
683 proto_tree_add_uint(field_tree_ctr
, hf_mux27010_controlchannel_detailedvalue_response
, tvb
, offset
, cc
->length_value
, 1);
686 /*Command pattern for non-supported command response (C/R is set to 1)*/
687 case MUX27010_COMMAND_NON_SUPPORTED_COMMAND_RESPONSE
:
688 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvalue
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
691 /*Command pattern for Modem Status Command (C/R is set to 1)*/
692 case MUX27010_COMMAND_MODEM_STATUS_COMMAND
:
693 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluemscdlci
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
695 /*Add bits of Flow Control*/
696 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluemscv24fc
, tvb
, offset
+1, 1, ENC_BIG_ENDIAN
);
697 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluemscv24rtc
, tvb
, offset
+1, 1, ENC_BIG_ENDIAN
);
698 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluemscv24rtr
, tvb
, offset
+1, 1, ENC_BIG_ENDIAN
);
699 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluemscv24ring
, tvb
, offset
+1, 1, ENC_BIG_ENDIAN
);
700 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluemscv24dcd
, tvb
, offset
+1, 1, ENC_BIG_ENDIAN
);
703 if (cc
->length_value
== 3) {
704 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluemscbreak
, tvb
, offset
+2, 1, ENC_BIG_ENDIAN
);
708 /*Command pattern for Parameter Negotiation (EA + C/R is set to 1)*/
709 case MUX27010_COMMAND_PARAMETER_NEGOTIATION
:
710 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluepndlci
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
711 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluepnframetype
, tvb
, offset
+1, 1, ENC_BIG_ENDIAN
);
712 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluepncl
, tvb
, offset
+1, 1, ENC_BIG_ENDIAN
);
713 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluepnprio
, tvb
, offset
+2, 1, ENC_BIG_ENDIAN
);
714 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluepntimer
, tvb
, offset
+3, 1, ENC_BIG_ENDIAN
);
715 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluepnframesize
, tvb
, offset
+4, 2, ENC_BIG_ENDIAN
);
716 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluepnna
, tvb
, offset
+6, 1, ENC_BIG_ENDIAN
);
717 proto_tree_add_item(field_tree_ctr
, hf_mux27010_controlchanneldetailedvaluepnwinsize
, tvb
, offset
+7, 1, ENC_BIG_ENDIAN
);
721 return cc
->length_value
;
726 /*Get values information field*/
728 getFrameInformation(tvbuff_t
*tvb
, packet_info
*pinfo
, proto_tree
*field_tree
,
729 int offset
, uint32_t length_info
){
731 /*Get the data from information field as string*/
732 char *information_field
= tvb_get_string_enc(pinfo
->pool
, tvb
,offset
,length_info
, ENC_ASCII
);
734 /*delete unneeded signs out of info field -> for info column: CR (0x0d) and LF (0x0a)*/
735 information_field
= g_strdelimit(information_field
, "\r\n", ' ');
737 col_append_fstr(pinfo
->cinfo
, COL_INFO
, " %s", information_field
);
739 /*Add info to subtree*/
740 proto_tree_add_string(field_tree
, hf_mux27010_information_str
, tvb
, offset
, length_info
, information_field
);
742 /*Increment offset by the length of chars in info field*/
750 dissect_mux27010(tvbuff_t
*tvb
, packet_info
*pinfo
, proto_tree
*tree
, void* data _U_
)
752 proto_item
*ti
, *tf
, *tf_extended_header
, *tf_addr
, *tf_ctr
;
753 proto_tree
*mux27010_tree
, *field_tree
, *field_tree_extended_header
, *field_tree_addr
, *field_tree_ctr
;
755 uint32_t length_info
;
756 bool save_fragmented
;
758 int8_t dlci_number
= 0;
760 /*private MUX frame header (PPP)*/
761 uint8_t sizeMuxPPPHeader
;
762 struct controlchannel_type cc_type
;
763 struct controlchannel cc
;
766 col_set_str(pinfo
->cinfo
, COL_PROTOCOL
, PROTO_TAG_MUX27010
);
767 col_clear(pinfo
->cinfo
, COL_INFO
);
769 /* Set offset to 0 => start to read at the begin of the frame*/
772 ti
= proto_tree_add_item(tree
, proto_mux27010
, tvb
, 0, -1, ENC_NA
);
773 mux27010_tree
= proto_item_add_subtree(ti
, ett_mux27010
);
775 /*Add a subtree (=item) to the child node => in this subtree the details of extended header will be displayed*/
776 tf_extended_header
= proto_tree_add_item(mux27010_tree
, hf_mux27010_extended_header
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
777 field_tree_extended_header
= proto_item_add_subtree(tf_extended_header
, ett_mux27010_extended_header
);
779 offset
+= getExtendedHeader(tvb
, field_tree_extended_header
, offset
, &sizeMuxPPPHeader
);
782 /*Get direction of the frame*/
783 offset
+= getFrameDirection(tvb
, pinfo
, mux27010_tree
, offset
);
785 /*~~~~~~~~Flag~~~~~~~~*/
786 /*(Insert data into the child node)*/
787 /*Create item to show/highlight flag sequence*/
788 proto_tree_add_item(mux27010_tree
, hf_mux27010
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
790 /*~~~~~~~~/Flag~~~~~~~~*/
794 /*~~~~~~~~Address~~~~~~~~*/
795 /*Add a subtree (=item) to the child node => in this subtree the details of address data will be displayed*/
796 tf_addr
= proto_tree_add_item(mux27010_tree
, hf_mux27010_address
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
797 field_tree_addr
= proto_item_add_subtree(tf_addr
, ett_mux27010_address
);
799 /*Get address data (DLCI, E/A, CR)*/
800 offset
+= getFrameAddress(tvb
, pinfo
, field_tree_addr
, offset
, &dlci_number
);
801 /*~~~~~~~~/Address~~~~~~~~*/
805 /*~~~~~~~~Control Data~~~~~~~~*/
806 /*Add a subtree (=item) to the child node => in this subtree the details of control data will be displayed*/
807 tf
= proto_tree_add_item(mux27010_tree
, hf_mux27010_control
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
808 field_tree
= proto_item_add_subtree(tf
, ett_mux27010_control
);
810 /*Get control data of frame (Frame type)*/
811 offset
+= getFrameControlData(tvb
, pinfo
, field_tree
, offset
, &frame_type
);
812 /*~~~~~~~~/Control Data~~~~~~~~*/
817 /*~~~~~~~~Length~~~~~~~~*/
818 /*Set the variable for length of the info field to 0*/
821 /*Check the frame type because in RR, RNR and REJ are no info and no length fields*/
822 if ((frame_type
!= MUX27010_FRAMETYPE_CONTROL_FLAG_RR
) && (frame_type
!= MUX27010_FRAMETYPE_CONTROL_FLAG_RNR
) &&
823 (frame_type
!= MUX27010_FRAMETYPE_CONTROL_FLAG_REJ
)){
824 /*Add a subtree (=item) to the child node => in this subtree will be the details of length field*/
825 tf
= proto_tree_add_item(mux27010_tree
, hf_mux27010_length
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
826 field_tree
= proto_item_add_subtree(tf
, ett_mux27010_length
);
828 /*Get frame length data*/
829 offset
+= getFrameLength(tvb
, field_tree
, offset
, &length_info
);
831 /*~~~~~~~~/Length~~~~~~~~*/
835 /*~~~~~~~~Control Channel~~~~~~~~*/
836 /*Control Channel only exists if DLCI = 0*/
837 if (dlci_number
== 0) {
839 /*If length field > 0, otherwise the frame has no data*/
840 if (length_info
> 0) {
842 /*--------Frame Type--------*/
843 /*Get and display data of frame type*/
845 /*Add a subtree (=item) to the child node => in this subtree the details of control channel will be displayed*/
846 tf
= proto_tree_add_item(mux27010_tree
, hf_mux27010_controlchannel
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
847 field_tree
= proto_item_add_subtree(tf
, ett_mux27010_controlchannel
);
849 /*Add another subtree to the control channel subtree => in this subtree the details of control channel frame type will be displayed*/
850 tf_ctr
= proto_tree_add_item(field_tree
, hf_mux27010_controlchannelframetype
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
851 field_tree_ctr
= proto_item_add_subtree(tf_ctr
, ett_mux27010_controlchannelframetype
);
853 /*Get data about the type of the frame*/
854 offset
+= getControlChannelFrameType(tvb
, pinfo
, field_tree_ctr
, offset
, &cc_type
);
855 proto_item_set_len(tf_ctr
, cc_type
.number_of_type_frames
);
856 /*--------/Frame Type--------*/
859 /*--------Length Field--------*/
860 /*Add another subtree to the control channel subtree => in this subtree the details of control channel length field will be displayed*/
861 tf_ctr
= proto_tree_add_item(field_tree
, hf_mux27010_controlchannellength
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
862 field_tree_ctr
= proto_item_add_subtree(tf_ctr
, ett_mux27010_controlchannellength
);
864 /*Get data of length field*/
865 offset
+= getControlChannelLength(tvb
, field_tree_ctr
, offset
, &cc
);
866 proto_item_set_len(tf_ctr
, cc
.number_of_length_frames
);
867 /*--------/Length Field--------*/
870 /*--------Values--------*/
871 /*If frame has data inside the length_value is > 0*/
872 if (cc
.length_value
> 0) {
873 /*Add another subtree to the control channel subtree => in this subtree the details of control channel values/data will be displayed*/
874 field_tree_ctr
= proto_tree_add_subtree_format(field_tree
, tvb
, offset
, cc
.length_value
,
875 ett_mux27010_controlchannelvalue
, NULL
, "Data: %i Byte(s)", cc
.length_value
);
877 /*Get data of frame*/
878 offset
+= getControlChannelValues(tvb
, field_tree_ctr
, offset
, &cc
, &cc_type
);
879 }/*(controlchannel_length_value > 0)*/
880 /*--------/Values--------*/
883 }/*dlci_number == 0*/
888 /*~~~~~~~~Information~~~~~~~~*/
889 /*Display "normal" data/values (not control channel) if exists ==> length_info > 0*/
890 if (dlci_number
!= 0 && length_info
> 0) {
891 /*Add a subtree (=item) to the child node => in this subtree will be the data*/
892 tf
= proto_tree_add_item(mux27010_tree
, hf_mux27010_information
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
893 field_tree
= proto_item_add_subtree(tf
, ett_mux27010_information
);
895 /*We have at least one PPP packet*/
896 if (sizeMuxPPPHeader
> 0){
897 uint16_t tmpOffset
= 1;
898 uint16_t tmpOffsetBegin
= 1;
899 uint16_t tmpOffsetEnd
= 1;
908 fragment_head
*frag_msg
= NULL
;
909 tvbuff_t
*new_tvb
= NULL
;
910 tvbuff_t
*next_tvb2
= NULL
;
914 for (i
= 0; i
< sizeMuxPPPHeader
/7; i
++){
917 tmpOffset
= (i
* tmpOffset
)+1;
919 msg_seqid
= tvb_get_ntohs(tvb
, tmpOffset
); tmpOffset
+= 2;
920 msg_num
= tvb_get_ntohs(tvb
, tmpOffset
); tmpOffset
+= 2;
921 msg_start
= tvb_get_uint8(tvb
, tmpOffset
); tmpOffset
+= 1;
922 msg_end
= tvb_get_uint8(tvb
, tmpOffset
); tmpOffset
+= 1;
923 msg_flag
= tvb_get_uint8(tvb
, tmpOffset
); tmpOffset
+= 1;
925 if (msg_end
<= msg_start
) {
926 proto_tree_add_expert(field_tree
, pinfo
, &ei_mux27010_message_illogical
,
927 tvb
, tmpOffset
-3, 2);
931 tmpOffsetBegin
= sizeMuxPPPHeader
+ 1 + msg_start
; /*+ Header_Size, + Direction*/
932 tmpOffsetEnd
= sizeMuxPPPHeader
+ 1 + msg_end
;
934 save_fragmented
= pinfo
->fragmented
;
935 pinfo
->fragmented
= true;
937 frag_msg
= fragment_add_seq_check(&msg_reassembly_table
,
940 msg_seqid
, /* ID for fragments belonging together */
942 msg_num
, /* fragment sequence number */
943 (tmpOffsetEnd
-tmpOffsetBegin
)+1, /* fragment length */
944 msg_flag
); /* More fragments? */
948 new_tvb
= process_reassembled_data(tvb
, tmpOffsetBegin
, pinfo
,
949 "Reassembled Message", frag_msg
, &msg_frag_items
,
950 NULL
, mux27010_tree
);
952 if (!frag_msg
) { /* Not last packet of reassembled Message */
953 col_append_str(pinfo
->cinfo
, COL_INFO
, " [Split Msg]");
956 if (new_tvb
) { /* take it all */
957 next_tvb2
= tvb_new_subset_remaining(new_tvb
, 1);
958 call_dissector(ppp_handle
, next_tvb2
, pinfo
, tree
);
961 pinfo
->fragmented
= save_fragmented
;
965 /*Get and display information*/
966 offset
+= getFrameInformation(tvb
, pinfo
, field_tree
, offset
, length_info
);
969 /*~~~~~~~~/Information~~~~~~~~*/
972 /*~~~~~~~~Checksum~~~~~~~~*/
973 /*Validate checksum of frame*/
974 /*Add a subtree (=item) to the child node => in this subtree will be the checksum*/
975 tf
= proto_tree_add_item(mux27010_tree
, hf_mux27010_checksum
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
976 field_tree
= proto_item_add_subtree(tf
, ett_mux27010_checksum
);
978 /*Call method check_checksum and validate checksum*/
979 if (check_fcs(tvb
,offset
-sizeMuxPPPHeader
-3-length_info
, sizeMuxPPPHeader
+3, tvb_get_uint8(tvb
, offset
))){
980 /*Checksum is correct*/
981 proto_tree_add_boolean(field_tree
, hf_mux27010_checksum_correct
, tvb
, offset
, 1, true);
984 /*Checksum is incorrect*/
985 expert_add_info(pinfo
, tf
, &ei_mux27010_checksum_incorrect
);
987 /*~~~~~~~~/Checksum~~~~~~~~*/
988 return tvb_captured_length(tvb
);
991 /*Register the protocol*/
993 proto_register_mux27010 (void)
995 /* A header field is something you can search/filter on.
997 * Create a structure to register fields. It consists of an
998 * array of hf_register_info structures, each of which are of the format
999 * {&(field id), {name, abbrev, type, display, strings, bitmask, blurb, HFILL}}.
1002 static hf_register_info hf
[] = {
1004 /*Extended MUX header (for PPP)*/
1006 {&hf_mux27010_extended_header
,
1007 { "Extended Header", "mux27010.ext_header",
1008 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1010 {&hf_mux27010_extended_header_size
,
1011 { "Header Size", "mux27010.ext_header.size",
1012 FT_UINT8
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1014 {&hf_mux27010_extended_header_msg_number_I
,
1015 { "Message Number I", "mux27010.ext_header.msg_number_I",
1016 FT_UINT16
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1018 {&hf_mux27010_extended_header_freq_number_I
,
1019 { "Frequenz Number I", "mux27010.ext_header.frequenz_number_I",
1020 FT_UINT16
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1022 {&hf_mux27010_extended_header_start_pos_I
,
1023 { "Start Position I", "mux27010.ext_header.start_pos_I",
1024 FT_UINT8
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1026 {&hf_mux27010_extended_header_start_byte_I
,
1027 { "Start Byte I", "mux27010.ext_header.start_byte_I",
1028 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1030 {&hf_mux27010_extended_header_end_pos_I
,
1031 { "End Position I", "mux27010.ext_header.end_pos_I",
1032 FT_UINT8
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1034 {&hf_mux27010_extended_header_end_byte_I
,
1035 { "End Byte I", "mux27010.ext_header.end_byte_I",
1036 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1038 {&hf_mux27010_extended_header_flag_ended_I
,
1039 { "Flag Ended I", "mux27010.ext_header.flag_ended_I",
1040 FT_UINT8
, BASE_HEX
, NULL
, MUX27010_EXTENDED_HEADER_NOT_ENDED
, NULL
, HFILL
}},
1042 {&hf_mux27010_extended_header_msg_number_II
,
1043 { "Message Number II", "mux27010.ext_header.msg_number_II",
1044 FT_UINT16
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1046 {&hf_mux27010_extended_header_freq_number_II
,
1047 { "Frequenz Number II", "mux27010.ext_header.frequenz_number_II",
1048 FT_UINT16
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1050 {&hf_mux27010_extended_header_start_pos_II
,
1051 { "Start Position II", "mux27010.ext_header.start_pos_II",
1052 FT_UINT8
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1054 {&hf_mux27010_extended_header_start_byte_II
,
1055 { "Start Byte II", "mux27010.ext_header.start_byte_II",
1056 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1058 {&hf_mux27010_extended_header_end_pos_II
,
1059 { "End Position II", "mux27010.ext_header.end_pos_II",
1060 FT_UINT8
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1062 {&hf_mux27010_extended_header_end_byte_II
,
1063 { "End Byte II", "mux27010.ext_header.end_byte_II",
1064 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1066 {&hf_mux27010_extended_header_flag_ended_II
,
1067 { "Flag Ended II", "mux27010.ext_header.flag_ended_II",
1068 FT_UINT8
, BASE_HEX
, NULL
, MUX27010_EXTENDED_HEADER_NOT_ENDED
, NULL
, HFILL
}},
1070 {&hf_mux27010_extended_header_msg_number_III
,
1071 { "Message Number III", "mux27010.ext_header.msg_number_III",
1072 FT_UINT16
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1074 {&hf_mux27010_extended_header_freq_number_III
,
1075 { "Frequenz Number III", "mux27010.ext_header.frequenz_number_III",
1076 FT_UINT16
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1078 {&hf_mux27010_extended_header_start_pos_III
,
1079 { "Start Position III", "mux27010.ext_header.start_pos_III",
1080 FT_UINT8
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1082 {&hf_mux27010_extended_header_start_byte_III
,
1083 { "Start Byte III", "mux27010.ext_header.start_byte_III",
1084 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1086 {&hf_mux27010_extended_header_end_pos_III
,
1087 { "End Position III", "mux27010.ext_header.end_pos_III",
1088 FT_UINT8
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1090 {&hf_mux27010_extended_header_end_byte_III
,
1091 { "End Byte III", "mux27010.ext_header.end_byte_III",
1092 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1094 {&hf_mux27010_extended_header_flag_ended_III
,
1095 { "Flag Ended III", "mux27010.ext_header.flag_ended_III",
1096 FT_UINT8
, BASE_HEX
, NULL
, MUX27010_EXTENDED_HEADER_NOT_ENDED
, NULL
, HFILL
}},
1100 {&hf_mux27010_direction
,
1101 { "Direction", "mux27010.direction",
1102 FT_UINT8
, BASE_HEX
, VALS(direction_vals
), 0x0, NULL
, HFILL
}},
1107 { "Flag", "mux27010.flag",
1108 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1112 { &hf_mux27010_address
,
1113 { "Address field", "mux27010.address",
1114 FT_UINT8
, BASE_HEX
, NULL
, 0x0,NULL
, HFILL
}},
1116 { &hf_mux27010_dlciaddressflag
,
1117 { "DLCI number (decimal)", "mux27010.address.dlciaddress",
1118 FT_UINT8
, BASE_DEC
, NULL
, MUX27010_DLCI_ADDRESS_FLAG
, NULL
, HFILL
}},
1120 { &hf_mux27010_eaaddressflag
,
1121 { "EA Address Flag", "mux27010.address.eaaddress",
1122 FT_BOOLEAN
, 8, NULL
, MUX27010_EA_ADDRESS_FLAG
, NULL
, HFILL
}},
1124 { &hf_mux27010_craddressflag
,
1125 { "C/R Address Flag", "mux27010.address.craddress",
1126 FT_BOOLEAN
, 8, NULL
, MUX27010_CR_ADDRESS_FLAG
, NULL
, HFILL
}},
1129 { &hf_mux27010_addressdirection
,
1130 { "Direction", "mux27010.address.direction",
1131 FT_UINT8
, BASE_HEX
, NULL
, MUX27010_CR_ADDRESS_FLAG
, NULL
, HFILL
}},
1136 { &hf_mux27010_control
,
1137 { "Control field", "mux27010.control",
1138 FT_UINT8
, BASE_HEX
, NULL
, 0x0,NULL
, HFILL
}},
1140 { &hf_mux27010_controlframetype
,
1141 { "Frame Type", "mux27010.control.frametype",
1142 FT_UINT8
, BASE_HEX
, VALS(frame_type_vals
), MUX27010_FRAMETYPE_CONTROL_FLAG
, NULL
, HFILL
}},
1144 { &hf_mux27010_controlframetypens
,
1145 { "N(S) Sequence Number", "mux27010.control.frametype.ns",
1146 FT_UINT8
, BASE_DEC
, NULL
, MUX27010_FRAMETYPE_CONTROL_FLAG_NS
, NULL
, HFILL
}},
1148 { &hf_mux27010_controlframetypenr
,
1149 { "N(R) Receive Number", "mux27010.control.frametype.nr",
1150 FT_UINT8
, BASE_DEC
, NULL
, MUX27010_FRAMETYPE_CONTROL_FLAG_NR
, NULL
, HFILL
}},
1152 { &hf_mux27010_pfcontrolflag
,
1153 { "Poll/Final bit", "mux27010.control.pfcontrol",
1154 FT_UINT8
, BASE_DEC
, NULL
, MUX27010_PF_CONTROL_FLAG
, NULL
, HFILL
}},
1158 { &hf_mux27010_length
,
1159 { "Length field", "mux27010.length",
1160 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1162 { &hf_mux27010_ealengthflag
,
1163 { "E/A Flag", "mux27010.length.ealength",
1164 FT_BOOLEAN
, 8, NULL
, MUX27010_EA_LENGTH_FLAG
, NULL
, HFILL
}},
1166 { &hf_mux27010_lengthframesize_ea
,
1167 { "Info length", "mux27010.length.framesize_ea",
1168 FT_UINT16
, BASE_DEC
, NULL
, MUX27010_FRAMESIZE_LENGTH_FLAG_EA
, NULL
, HFILL
}},
1171 { &hf_mux27010_lengthframesize
,
1172 { "Info length", "mux27010.length.framesize",
1173 FT_UINT8
, BASE_DEC
, NULL
, MUX27010_FRAMESIZE_LENGTH_FLAG
, NULL
, HFILL
}},
1175 /*Control Channel DLCI = 0*/
1177 { &hf_mux27010_controlchannel
,
1178 { "Control Channel", "mux27010.controlchannel",
1179 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1183 { &hf_mux27010_controlchannelframetype
,
1184 { "Frame Type", "mux27010.controlchannel.frametype",
1185 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1187 { &hf_mux27010_controlchanneleaframetype
,
1188 { "EA Flag", "mux27010.controlchannel.frametype.eatype",
1189 FT_BOOLEAN
, 8, NULL
, MUX27010_EA_CONTROLCHANNEL_FRAMETYPE_FLAG
, NULL
, HFILL
}},
1191 { &hf_mux27010_controlchannelcrframetype
,
1192 { "C/R Flag", "mux27010.controlchannel.frametype.crtype",
1193 FT_BOOLEAN
, 8, NULL
, MUX27010_CR_CONTROLCHANNEL_FRAMETYPE_FLAG
, NULL
, HFILL
}},
1195 { &hf_mux27010_controlchannelframetypecommand
,
1196 { "Command Type", "mux27010.controlchannel.frametype.command",
1197 FT_UINT8
, BASE_HEX
, VALS(command_vals
), MUX27010_COMMAND_CONTROLCHANNEL_FRAMETYPE_FLAG
, NULL
, HFILL
}},
1201 { &hf_mux27010_controlchannellength
,
1202 { "Length", "mux27010.controlchannel.length",
1203 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1205 { &hf_mux27010_controlchannelealength
,
1206 { "EA Flag", "mux27010.controlchannel.length.ealength",
1207 FT_BOOLEAN
, 8, NULL
, MUX27010_EA_CONTROLCHANNEL_LENGTH_FLAG
, NULL
, HFILL
}},
1209 { &hf_mux27010_controlchannellengthfield
,
1210 { "Length field", "mux27010.controlchannel.length.length",
1211 FT_UINT8
, BASE_DEC
, NULL
, MUX27010_LENGTHFIELD_CONTROLCHANNEL_LENGTH_FLAG
, NULL
, HFILL
}},
1215 { &hf_mux27010_controlchannelvalue
,
1216 { "Value (ASCII)", "mux27010.controlchannel.value",
1217 FT_STRING
, BASE_NONE
, NULL
, 0x0, NULL
, HFILL
}},
1219 { &hf_mux27010_controlchannel_iei_coding
,
1220 { "IEI coding", "mux27010.controlchannel.value.iei_coding",
1221 FT_UINT8
, BASE_HEX
, VALS(iei_coding_vals
), 0x0, NULL
, HFILL
}},
1223 { &hf_mux27010_controlchanneldetailedvalue
,
1224 { "Detailed Values", "mux27010.controlchannel.value.detailedvalues",
1225 FT_UINT8
, BASE_HEX
, NULL
, 0xFF, NULL
, HFILL
}},
1227 { &hf_mux27010_controlchannel_detailedvalue_response
,
1228 { "Response", "mux27010.controlchannel.value.detailedvalue.response",
1229 FT_UINT8
, BASE_DEC
, VALS(detailedvalue_response_vals
), 0, NULL
, HFILL
}},
1233 { &hf_mux27010_controlchanneldetailedvaluetestcommandversion
,
1234 { "Version", "mux27010.controlchannel.value.detailedvaluetestcommandversion",
1235 FT_UINT8
, BASE_HEX
, NULL
, MUX27010_VALUE_CONTROLCHANNEL_TEST_VERSION
, NULL
, HFILL
}},
1237 /*Modem Status Command*/
1239 { &hf_mux27010_controlchanneldetailedvaluemscdlci
,
1240 { "DLCI number (decimal)", "mux27010.controlchannel.value.detailedvaluemscdlci",
1241 FT_UINT8
, BASE_DEC
, NULL
, MUX27010_VALUE_CONTROLCHANNEL_MSC_DCLI
, NULL
, HFILL
}},
1244 { &hf_mux27010_controlchanneldetailedvaluemscv24
,
1245 { "V.24 Signal", "mux27010.controlchannel.value.detailedvaluemscv24",
1246 FT_UINT8
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1249 { &hf_mux27010_controlchanneldetailedvaluemscv24fc
,
1250 { "FC", "mux27010.controlchannel.value.detailedvaluemscv24.fc",
1251 FT_BOOLEAN
, 8, NULL
, MUX27010_VALUE_CONTROLCHANNEL_MSC_V24_FC
, NULL
, HFILL
}},
1253 { &hf_mux27010_controlchanneldetailedvaluemscv24rtc
,
1254 { "RTC", "mux27010.controlchannel.value.detailedvaluemscv24.rtc",
1255 FT_BOOLEAN
, 8, NULL
, MUX27010_VALUE_CONTROLCHANNEL_MSC_V24_RTC
, NULL
, HFILL
}},
1257 { &hf_mux27010_controlchanneldetailedvaluemscv24rtr
,
1258 { "RTR", "mux27010.controlchannel.value.detailedvaluemscv24.rtr",
1259 FT_BOOLEAN
, 8, NULL
, MUX27010_VALUE_CONTROLCHANNEL_MSC_V24_RTR
, NULL
, HFILL
}},
1261 { &hf_mux27010_controlchanneldetailedvaluemscv24ring
,
1262 { "RING", "mux27010.controlchannel.value.detailedvaluemscv24.ring",
1263 FT_BOOLEAN
, 8, NULL
, MUX27010_VALUE_CONTROLCHANNEL_MSC_V24_RING
, NULL
, HFILL
}},
1265 { &hf_mux27010_controlchanneldetailedvaluemscv24dcd
,
1266 { "DCD", "mux27010.controlchannel.value.detailedvaluemscv24.dcd",
1267 FT_BOOLEAN
, 8, NULL
, MUX27010_VALUE_CONTROLCHANNEL_MSC_V24_DCD
, NULL
, HFILL
}},
1269 { &hf_mux27010_controlchanneldetailedvaluemscbreak
,
1270 { "Break Signal", "mux27010.controlchannel.value.detailedvaluemscbreak",
1271 FT_UINT8
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1273 /*Parameter Negotiation*/
1275 { &hf_mux27010_controlchanneldetailedvaluepndlci
,
1276 { "DLCI", "mux27010.controlchannel.value.detailedvaluepndlci",
1277 FT_UINT8
, BASE_DEC
, NULL
, MUX27010_VALUE_CONTROLCHANNEL_PN_DLCI
, NULL
, HFILL
}},
1279 { &hf_mux27010_controlchanneldetailedvaluepnframetype
,
1280 { "Frame Type", "mux27010.controlchannel.value.detailedvaluepnframetype",
1281 FT_UINT8
, BASE_HEX
, NULL
, MUX27010_VALUE_CONTROLCHANNEL_PN_FRAMETYPE
, NULL
, HFILL
}},
1283 { &hf_mux27010_controlchanneldetailedvaluepncl
,
1284 { "Convergence Layer", "mux27010.controlchannel.value.detailedvaluepncl",
1285 FT_UINT8
, BASE_DEC
, NULL
, MUX27010_VALUE_CONTROLCHANNEL_PN_CL
, NULL
, HFILL
}},
1287 { &hf_mux27010_controlchanneldetailedvaluepnprio
,
1288 { "Priority", "mux27010.controlchannel.value.detailedvaluepnprio",
1289 FT_UINT8
, BASE_DEC
, NULL
, MUX27010_VALUE_CONTROLCHANNEL_PN_PRIO
, NULL
, HFILL
}},
1291 { &hf_mux27010_controlchanneldetailedvaluepntimer
,
1292 { "Acknowledgment Timer (ms)", "mux27010.controlchannel.value.detailedvaluepntimer",
1293 FT_UINT8
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1295 { &hf_mux27010_controlchanneldetailedvaluepnframesize
,
1296 { "Max. Frame Size", "mux27010.controlchannel.value.detailedvaluepnframesize",
1297 FT_UINT16
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1299 { &hf_mux27010_controlchanneldetailedvaluepnna
,
1300 { "Max. Number of Retransmissions", "mux27010.controlchannel.value.detailedvaluepnna",
1301 FT_UINT8
, BASE_DEC
, NULL
, 0x0, NULL
, HFILL
}},
1303 { &hf_mux27010_controlchanneldetailedvaluepnwinsize
,
1304 { "Window Size for Error Recovery Mode", "mux27010.controlchannel.value.detailedvaluepnwinsize",
1305 FT_UINT8
, BASE_DEC
, NULL
, MUX27010_VALUE_CONTROLCHANNEL_PN_WINSIZE
, NULL
, HFILL
}},
1307 /*Information frame*/
1309 { &hf_mux27010_information
,
1310 { "Information field", "mux27010.information",
1311 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1313 { &hf_mux27010_information_str
,
1314 { "Information", "mux27010.information_str",
1315 FT_STRING
, BASE_NONE
, NULL
, 0x0, NULL
, HFILL
}},
1319 { &hf_mux27010_checksum
,
1320 { "Checksum", "mux27010.checksum",
1321 FT_UINT8
, BASE_HEX
, NULL
, 0x0, NULL
, HFILL
}},
1323 { &hf_mux27010_checksum_correct
,
1324 { "Correct", "mux27010.checksum_correct",
1325 FT_BOOLEAN
, BASE_NONE
, NULL
, 0x0, NULL
, HFILL
}},
1328 {"Message fragments", "mux27010.fragments",
1329 FT_NONE
, BASE_NONE
, NULL
, 0x00, NULL
, HFILL
} },
1332 {"Message fragment", "mux27010.fragment",
1333 FT_FRAMENUM
, BASE_NONE
, NULL
, 0x00, NULL
, HFILL
} },
1335 {&hf_msg_fragment_overlap
,
1336 {"Message fragment overlap", "mux27010.fragment.overlap",
1337 FT_BOOLEAN
, BASE_NONE
, NULL
, 0x00, NULL
, HFILL
} },
1339 {&hf_msg_fragment_overlap_conflicts
,
1340 {"Message fragment overlapping with conflicting data",
1341 "mux27010.fragment.overlap.conflicts",
1342 FT_BOOLEAN
, BASE_NONE
, NULL
, 0x00, NULL
, HFILL
} },
1344 {&hf_msg_fragment_multiple_tails
,
1345 {"Message has multiple tail fragments",
1346 "mux27010.fragment.multiple_tails",
1347 FT_BOOLEAN
, BASE_NONE
, NULL
, 0x00, NULL
, HFILL
} },
1349 {&hf_msg_fragment_too_long_fragment
,
1350 {"Message fragment too long", "mux27010.fragment.too_long_fragment",
1351 FT_BOOLEAN
, BASE_NONE
, NULL
, 0x00, NULL
, HFILL
} },
1353 {&hf_msg_fragment_error
,
1354 {"Message defragmentation error", "mux27010.fragment.error",
1355 FT_FRAMENUM
, BASE_NONE
, NULL
, 0x00, NULL
, HFILL
} },
1357 {&hf_msg_fragment_count
,
1358 {"Message fragment count", "mux27010.fragment.count",
1359 FT_UINT32
, BASE_DEC
, NULL
, 0x00, NULL
, HFILL
} },
1361 {&hf_msg_reassembled_in
,
1362 {"Reassembled in", "mux27010.reassembled.in",
1363 FT_FRAMENUM
, BASE_NONE
, NULL
, 0x00, NULL
, HFILL
} },
1365 {&hf_msg_reassembled_length
,
1366 {"Reassembled length", "mux27010.reassembled.length",
1367 FT_UINT32
, BASE_DEC
, NULL
, 0x00, NULL
, HFILL
} },
1371 /* Setup protocol subtree array */
1372 static int *ett
[] = {
1373 &ett_mux27010_extended_header
,
1375 &ett_mux27010_address
,
1376 &ett_mux27010_control
,
1377 &ett_mux27010_length
,
1378 &ett_mux27010_controlchannel
,
1379 &ett_mux27010_controlchannelframetype
,
1380 &ett_mux27010_controlchannellength
,
1381 &ett_mux27010_controlchannelvalue
,
1382 &ett_mux27010_information
,
1383 &ett_mux27010_checksum
,
1388 static ei_register_info ei
[] = {
1389 { &ei_mux27010_message_illogical
, { "mux27010.message_illogical", PI_MALFORMED
, PI_ERROR
, "Message start and end are illogical, aborting dissection", EXPFILL
}},
1390 { &ei_mux27010_checksum_incorrect
, { "mux27010.checksum_incorrect", PI_CHECKSUM
, PI_WARN
, "Checksum: incorrect", EXPFILL
}},
1393 expert_module_t
* expert_mux27010
;
1395 /*Register protocol*/
1396 proto_mux27010
= proto_register_protocol ("MUX27010 Protocol", "MUX27010", "mux27010");
1399 proto_register_field_array (proto_mux27010
, hf
, array_length (hf
));
1400 proto_register_subtree_array (ett
, array_length (ett
));
1402 mux27010_handle
= register_dissector("mux27010", dissect_mux27010
, proto_mux27010
);
1404 expert_mux27010
= expert_register_protocol(proto_mux27010
);
1405 expert_register_field_array(expert_mux27010
, ei
, array_length(ei
));
1407 reassembly_table_register(&msg_reassembly_table
,
1408 &addresses_reassembly_table_functions
);
1411 /*Initialize dissector*/
1413 proto_reg_handoff_mux27010(void)
1415 /*Initialization of dissector*/
1416 dissector_add_uint("wtap_encap", WTAP_ENCAP_MUX27010
, mux27010_handle
);
1418 ppp_handle
= find_dissector_add_dependency("ppp", proto_mux27010
);
1423 * Editor modelines - https://www.wireshark.org/tools/modelines.html
1428 * indent-tabs-mode: nil
1431 * vi: set shiftwidth=4 tabstop=8 expandtab:
1432 * :indentSize=4:tabSize=8:noTabs=true: