Revert "TODO epan/dissectors/asn1/kerberos/packet-kerberos-template.c new GSS flags"
[wireshark-sm.git] / epan / dissectors / packet-miwi-p2pstar.c
blob066a743c9581fededdb81fe2d6d23ee9eca0487b
1 /* packet-miwi_p2pstar.c
2 * Dissector routines for the Microchip MiWi_P2P_Star
3 * Copyright 2013 Martin Leixner <info@sewio.net>
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
10 *------------------------------------------------------------
13 #include "config.h"
14 #include <epan/packet.h>
15 #include <epan/decode_as.h>
16 #include <epan/exceptions.h>
17 #include <epan/crc16-tvb.h>
18 #include <epan/crc32-tvb.h>
19 #include <epan/expert.h>
20 #include <epan/addr_resolv.h>
21 #include <epan/address_types.h>
22 #include <epan/conversation.h>
23 #include <epan/prefs.h>
24 #include <epan/uat.h>
25 #include <epan/strutil.h>
26 #include <epan/to_str.h>
27 #include <epan/show_exception.h>
28 #include <epan/proto_data.h>
29 #include <epan/etypes.h>
30 #include <epan/oui.h>
31 #include <wsutil/pint.h>
33 /* Use libgcrypt for cipher libraries. */
34 #include <wsutil/wsgcrypt.h>
36 #include <wsutil/filesystem.h>
37 #include "packet-ieee802154.h"
38 #include <epan/prefs.h>
39 #include <epan/strutil.h>
40 #include <wsutil/wsgcrypt.h>
42 /* Function declarations */
43 void proto_register_miwi_p2pstar(void);
44 void proto_reg_handoff_miwi_p2pstar(void);
46 /* MiWi MAC Header FCF fields */
47 #define MIWI_MAC_FCF_FRAME_TYPE 0x0007
48 #define MIWI_MAC_FCF_SECURITY_EN 0x0008
49 #define MIWI_MAC_FCF_FRAME_PENDING 0x0010
50 #define MIWI_MAC_FCF_ACK_REQUEST 0x0020
51 #define MIWI_MAC_FCF_PANID_COMP 0x0040
52 #define MIWI_MAC_FCF_RESERVED 0x0380
53 #define MIWI_MAC_FCF_DEST_ADDR_MODE 0x0C00
54 #define MIWI_MAC_FCF_FRAME_VERSION 0x3000
55 #define MIWI_MAC_FCF_SRC_ADDR_MODE 0xC000
57 /* MiWi NWK Header FCF fields */
58 #define MIWI_NWK_FCF_FRAME_TYPE 0x0003
59 #define MIWI_NWK_FCF_SECURITY_EN 0x0004
60 #define MIWI_NWK_FCF_INFRA_CLUSTER 0x0008
61 #define MIWI_NWK_FCF_ACK_REQUEST 0x0010
62 #define MIWI_NWK_FCF_ADDR_SAME_AS_MAC 0x0020
63 #define MIWI_NWK_FCF_RESERVED 0x00C0
65 /* Address Mode Definitions */
66 #define MIWI_FCF_ADDR_NONE 0x0
67 #define MIWI_FCF_ADDR_RESERVED 0x1
68 #define MIWI_FCF_ADDR_SHORT 0x2
69 #define MIWI_FCF_ADDR_EXT 0x3
71 #define MIWI_SOURCE_ADDR_MODE 0x00 // to check
73 /* MiWi NWK Header FCF fields */
74 #define MIWI_CAP_INFO_RCV_ON_IDLE 0x0001
75 #define MIWI_CAP_INFO_REQ_DATA_ON_WP 0x0002
76 #define MIWI_CAP_INFO_NEED_TIME_SYNC 0x0004
77 #define MIWI_CAP_INFO_SECURITY_CAP 0x0008
78 #define MIWI_CAP_INFO_RESERVED 0x00F0
80 /*Defined addresses*/
81 #define MIWI_BCAST_ADDR 0xFFFF
83 /*Command IDs*/
84 #define MIWI_P2P_CMD_CONN_REQ 0x81
85 #define MIWI_P2P_CMD_CONN_REMOVAL_REQ 0x82
86 #define MIWI_P2P_CMD_DATA_REQ 0x83
87 #define MIWI_P2P_CMD_CHANNEL_HOP 0x84
88 #define MIWI_P2P_CMD_ACTIVE_SCAN_REQ 0x87
89 #define MIWI_P2P_CMD_CONN_RES 0x91
90 #define MIWI_P2P_CMD_CONN_REMOVAL_RES 0x92
91 #define MIWI_P2P_CMD_ACTIVE_SCAN_RES 0x97
93 #define MIWI_STAR_CMD_FORWARD_PACKET 0xCC
94 #define MIWI_STAR_CMD_SOFT_ACK 0xDA
95 #define MIWI_STAR_CMD_LINK_STATUS 0x7A
96 #define MIWI_STAR_CMD_CONN_TABLE 0x77
98 #define MIWI_CONN_STATUS_SUCCESS 0x00
99 #define MIWI_CONN_STATUS_EXISTS 0x01
100 #define MIWI_CONN_STATUS_ACTIVE_SCAN 0x02
101 #define MIWI_CONN_STATUS_ENTRY_NOT_EXIST 0xF0
102 #define MIWI_CONN_STATUS_NOT_ENOUGH_SPACE 0xF1
103 #define MIWI_CONN_STATUS_NOT_SAME_PA 0xF2
104 #define MIWI_CONN_STATUS_NOT_PERMITTED 0xF3
106 /* FCS Types used by user configuration */
107 #define MIWI_P2PSTAR_FCS_16_BIT 1/* CRC16 */
109 /**MiWI Type of MAC frame */
110 #define MIWI_MAC_FRAME_BEACON 0x00
111 #define MIWI_MAC_FRAME_DATA 0x01
112 #define MIWI_MAC_FRAME_ACK 0x02
113 #define MIWI_MAC_FRAME_CMD 0x03
114 #define MIWI_MAC_FRAME_RESERVED 0x04
116 /* User string with the decryption key. */
117 //static const char *miwi_p2pstar_key_str = NULL;
119 /* Initialize protocol and registered fields. */
120 static int proto_miwi_p2pstar;
122 /* Initialize protocol subtrees. */
123 static int ett_miwi_p2pstar;
124 static int ett_miwi_p2pstar_fcf;
125 static int ett_miwi_p2pstar_cmd_tree;
126 static int ett_miwi_p2pstar_cap_info;
127 static int ett_miwi_fcs;
129 static dissector_handle_t miwi_p2pstar_handle;
131 static int hf_miwi_frame_length;
132 static int hf_miwi_fcf;
133 static int hf_miwi_fcf_frame_type;
134 static int hf_miwi_fcf_security_enabled;
135 static int hf_miwi_fcf_frame_pending;
136 static int hf_miwi_fcf_ack_req;
137 static int hf_miwi_fcf_panid_comp;
138 static int hf_miwi_fcf_reserved;
139 static int hf_miwi_fcf_dest_addr_mode;
140 static int hf_miwi_fcf_frame_version;
141 static int hf_miwi_fcf_src_addr_mode;
142 static int hf_miwi_seq;
143 static int hf_miwi_dst_panid;
144 static int hf_miwi_short_dst_addr;
145 static int hf_miwi_ext_dst_addr;
146 //static int hf_miwi_no_dst_addr;
147 //static int hf_miwi_no_src_addr;
148 static int hf_miwi_ext_src_addr;
149 static int hf_miwi_short_src_addr;
150 static int hf_miwi_addr16;
151 static int hf_miwi_addr64;
152 static int hf_miwi_src64_origin;
153 static int hf_miwi_src_panid;
154 static int hf_miwi_cmd_id;
155 //static int hf_miwi_fcs;
156 //static int hf_miwi_fcs_ok;
158 static int hf_miwi_oper_chan;
159 static int hf_miwi_cap_info;
160 static int hf_miwi_cap_info_rcv_on_idle;
161 static int hf_miwi_cap_info_rqst_data_on_wp;
162 static int hf_miwi_cap_info_need_time_sync;
163 static int hf_miwi_cap_info_security_cap;
164 static int hf_miwi_cap_info_reserved;
165 static int hf_miwi_conn_res_status;
167 //static int hf_miwi_conn_rmv_req;
168 static int hf_miwi_conn_rmv_res_status;
169 //static int hf_miwi_data_req;
170 //static int hf_miwi_chan_hop;
171 //static int hf_miwi_conn_res;
172 //static int hf_miwi_conn_rmv_res;
173 //static int hf_miwi_active_scan_req;
174 //static int hf_miwi_active_scan_cur_chan;
176 //static int hf_miwi_active_scan_res;
177 //static int hf_miwi_active_scan_res_node_id;
179 //static int hf_miwi_fwd_pkt_cmd;
180 static int hf_miwi_fwd_pkt_dst_addr;
181 //static int hf_miwi_conn_tbl_bcast_cmd;
182 static int hf_miwi_conn_tbl_size;
183 //static int hf_miwi_software_ack;
184 //static int hf_miwi_link_status;
186 /*Channel hopping frame*/
187 static int hf_miwi_current_op_channel;
188 static int hf_miwi_dst_channel_to_jump_to;
190 //static int hf_miwi_mic;
191 //static int hf_miwi_key_number;
193 static int miwi_short_address_type;
195 //static expert_field ei_miwi_empty_payload;
196 static expert_field ei_miwi_frame_ver;
197 static expert_field ei_miwi_dst;
198 static expert_field ei_miwi_src;
199 static expert_field ei_miwi_invalid_addressing;
200 static expert_field ei_miwi_invalid_panid_compression;
201 static expert_field ei_miwi_invalid_panid_compression2;
202 //static expert_field ei_miwi_fcs;
203 /* 802.15.4-2003 security */
204 //static int hf_miwi_sec_frame_counter;
205 //static int hf_miwi_sec_key_sequence_counter;
208 /* ethertype for 802.15.4 tag - encapsulating an Ethernet packet */
209 static unsigned int miwi_ethertype = 0x809A;
211 /* boolean value set if the FCS must be ok before payload is dissected */
212 static bool miwi_fcs_ok = true;
214 /* boolean value set to enable ack tracking */
215 static bool miwi_ack_tracking = false;
217 /* Preferences for 2003 security */
218 //static int miwi_sec_suite = SECURITY_LEVEL_ENC_MIC_64;
219 //static bool miwi_extend_auth = true;
221 //static wmem_tree_t* mac_key_hash_handlers;
224 * Address Hash Tables
227 static ieee802154_map_tab_t miwi_map = {NULL, NULL};
229 //static ieee802154_key_t *miwi_keys = NULL;
230 //static unsigned num_miwi_keys = 0;
232 static int miwi_fcs_type = MIWI_P2PSTAR_FCS_16_BIT;
234 static int* const fields[] = {
235 &hf_miwi_fcf_frame_type,
236 &hf_miwi_fcf_security_enabled,
237 &hf_miwi_fcf_frame_pending,
238 &hf_miwi_fcf_ack_req,
239 &hf_miwi_fcf_panid_comp,
240 &hf_miwi_fcf_reserved,
241 &hf_miwi_fcf_dest_addr_mode,
242 &hf_miwi_fcf_frame_version,
243 &hf_miwi_fcf_src_addr_mode,
244 NULL
247 static const value_string miwi_p2pstar_cmd_names[] ={
248 { MIWI_P2P_CMD_CONN_REQ, " Connection Request"},
249 { MIWI_P2P_CMD_CONN_REMOVAL_REQ, " Connection Removal Request"},
250 { MIWI_P2P_CMD_DATA_REQ, " Data Request"},
251 { MIWI_P2P_CMD_CHANNEL_HOP, " Channel Hopping"},
252 { MIWI_P2P_CMD_ACTIVE_SCAN_REQ, " Active Scan Request"},
253 { MIWI_P2P_CMD_CONN_RES, " Connection Response"},
254 { MIWI_P2P_CMD_CONN_REMOVAL_RES, " Connection Removal Response"},
255 { MIWI_P2P_CMD_ACTIVE_SCAN_RES, " Active Scan Response"},
256 { MIWI_STAR_CMD_FORWARD_PACKET, " Forward packet"},
257 { MIWI_STAR_CMD_SOFT_ACK, " Soft Acknowledgement"},
258 { MIWI_STAR_CMD_LINK_STATUS, " Link Status"},
259 { MIWI_STAR_CMD_CONN_TABLE, " Connection Table"},
260 { 0, NULL}
263 /* MAC Frame Types */
264 static const value_string miwi_mac_frame_types[] = {
265 { MIWI_MAC_FRAME_BEACON, "Beacon"},
266 { MIWI_MAC_FRAME_DATA, "Data"},
267 { MIWI_MAC_FRAME_ACK, "Acknowledgement"},
268 { MIWI_MAC_FRAME_CMD, "Command"},
269 {MIWI_MAC_FRAME_RESERVED, "Reserved"},
270 { 0, NULL}
273 static const value_string miwi_addr_modes[] = {
274 { MIWI_FCF_ADDR_NONE, "None"},
275 { MIWI_FCF_ADDR_RESERVED, "Reserved"},
276 { MIWI_FCF_ADDR_SHORT, "Short/16-bit"},
277 { MIWI_FCF_ADDR_EXT, "Long/64-bit"},
278 { 0, NULL}
281 /* Versions */
282 static const value_string miwi_frame_versions[] = {
283 { IEEE802154_VERSION_2003, "IEEE Std 802.15.4-2003"},
284 { IEEE802154_VERSION_2006, "IEEE Std 802.15.4-2006"},
285 { IEEE802154_VERSION_2015, "IEEE Std 802.15.4-2015"},
286 { IEEE802154_VERSION_RESERVED, "Reserved" },
287 { 0, NULL}
290 static const value_string miwi_p2pstar_conn_status[] = {
291 { MIWI_CONN_STATUS_SUCCESS, " (Successful)"},
292 { MIWI_CONN_STATUS_EXISTS, " (Already Exists)"},
293 { MIWI_CONN_STATUS_ACTIVE_SCAN, " (Active Scan State)"},
294 { MIWI_CONN_STATUS_ENTRY_NOT_EXIST, " (Entry Not Exist)"},
295 { MIWI_CONN_STATUS_NOT_ENOUGH_SPACE, " (Not Enough Space)"},
296 { MIWI_CONN_STATUS_NOT_SAME_PA, " (PANID Mismatch)"},
297 { MIWI_CONN_STATUS_NOT_PERMITTED, " (Not Permitted)"},
298 { 0, NULL}
301 #define miwi_packet ieee802154_packet
303 /* CRC definitions. IEEE 802.15.4 CRCs vary from ITU-T by using an initial value of
304 * 0x0000, and no XOR out. IEEE802154_CRC_XOR is defined as 0xFFFF in order to un-XOR
305 * the output from the ITU-T (CCITT) CRC routines in Wireshark. */
306 #define MIWI_CRC_SEED 0x0000
307 #define MIWI_CRC_XOROUT 0xFFFF
308 #define miwi_crc_tvb(tvb, offset) (crc16_ccitt_tvb_seed(tvb, offset, MIWI_CRC_SEED) ^ MIWI_CRC_XOROUT)
309 /* For the 32-bit CRC, IEEE 802.15.4 uses ITU-T (CCITT) CRC-32. */
310 #define miwi_crc32_tvb(tvb, offset) (crc32_ccitt_tvb(tvb, offset))
312 * Verify the 16/32 bit IEEE 802.15.4 FCS
313 * @param tvb the IEEE 802.15.4 frame from the FCF up to and including the FCS
314 * @return if the computed FCS matches the transmitted FCS
316 static bool
317 is_fcs_ok(tvbuff_t *tvb, unsigned fcs_len)
319 if(fcs_len == 2){
320 /* The FCS is in the last two bytes of the packet. */
321 uint16_t fcs = tvb_get_letohs(tvb, tvb_reported_length(tvb)-2);
322 uint16_t fcs_calc = (uint16_t) miwi_crc_tvb(tvb, tvb_reported_length(tvb)-2);
323 return fcs == fcs_calc;
325 else{
326 /* The FCS is in the last four bytes of the packet. */
327 uint32_t fcs = tvb_get_letohl(tvb, tvb_reported_length(tvb)-4);
328 uint32_t fcs_calc = miwi_crc32_tvb(tvb, tvb_reported_length(tvb)-4);
329 return fcs == fcs_calc;
331 }/* is_fcs_ok */
333 /* Returns the prompt string for the Decode-As dialog. */
334 static void miwi_da_prompt(packet_info *pinfo _U_, char* result)
336 ieee802154_hints_t *hints;
337 hints = (ieee802154_hints_t *)p_get_proto_data(wmem_file_scope(), pinfo, proto_miwi_p2pstar, 0);
338 if(hints)
339 snprintf(result, MAX_DECODE_AS_PROMPT_LEN, "MIWI P2P STAR PAN 0x%04x as", hints->src_pan);
340 else
341 snprintf(result, MAX_DECODE_AS_PROMPT_LEN, "MIWI P2P STAR PAN Unknown");
342 }/* miwi_da_prompt */
343 /* Returns the value to index the panid decode table with (source PAN)*/
344 static void *miwi_da_value(packet_info *pinfo _U_)
346 ieee802154_hints_t *hints;
347 hints = (ieee802154_hints_t *)p_get_proto_data(wmem_file_scope(), pinfo, proto_miwi_p2pstar, 0);
348 if(hints)
349 return GUINT_TO_POINTER((unsigned)(hints->src_pan));
350 else
351 return NULL;
352 }/* miwi_da_value */
353 static int miwi_short_address_to_str(const address* addr, char *buf, int buf_len)
355 uint16_t miwi_short_addr = pletoh16(addr->data);
357 if (miwi_short_addr == 0xffff)
359 g_strlcpy(buf, "Broadcast", buf_len);
360 return 10;
363 *buf++ = '0';
364 *buf++ = 'x';
365 buf = word_to_hex(buf, miwi_short_addr);
366 *buf = '\0'; /* NULL terminate */
368 return 7;
369 } /* miwi_short_address_to_str */
370 static int miwi_short_to_str(uint16_t miwi_short_addr, char *buf, int buf_len)
372 if(miwi_short_addr == 0xffff)
374 g_strlcpy(buf, "Broadcast", buf_len);
375 return 10;
378 *buf++ = '0';
379 *buf++ = 'x';
380 buf = word_to_hex(buf, miwi_short_addr);
381 *buf = '\0'; /* NULL terminate */
383 return 7;
384 }/* miwi_short_to_str */
386 static int miwi_short_address_str_len(const address* addr _U_)
388 return 11;
391 static int miwi_short_address_len(void)
393 return 2;
397 *Extracts an integer sub-field from an int with a given mask
400 #if 0
401 static unsigned miwi_get_bit_field(unsigned input, unsigned mask)
403 /* Sanity Check, don't want infinite loops. */
404 if(mask == 0) return 0;
405 /* Shift input and mask together. */
406 while (!(mask & 0x1)){
407 input >>= 1;
408 mask >>=1;
409 }/* while */
410 return (input & mask);
411 }/* miwi_get_bit_field */
412 #endif
414 /* Return the length in octets for the user configured
415 * FCS/metadata following the PHY Payload */
416 static unsigned miwi_fcs_type_len(unsigned i)
418 unsigned fcs_type_lengths[] = { 2, 2, 4 };
419 if(i < array_length(fcs_type_lengths)){
420 return fcs_type_lengths[i];
422 return 0;
423 }/* miwi_fcs_type_len */
425 #if 0
426 /* Set MAC key function. */
427 static unsigned miwi_set_mac_key(miwi_packet *packet, unsigned char *key, unsigned char *alt_key, ieee802154_key_t *uat_key)
429 ieee802154_set_key_func func = (ieee802154_set_key_func)wmem_tree_lookup32(mac_key_hash_handlers, uat_key->hash_type);
431 if(func != NULL)
432 return func(packet, key, alt_key, uat_key);
434 /* Right now, KEY_HASH_NONE and KEY_HASH_ZIP are not registered because they
435 work with this "default" behavior */
436 if(packet->key_index == uat_key->key_index)
438 memcpy(key, uat_key->key, IEEE802154_CIPHER_SIZE);
439 return 1;
442 return 0;
443 }/* miwi_set_mac_key */
444 #endif
446 * Dissector helper, parses and displays the frame control field.
448 * @param tvb pointer to buffer containing raw packet.
449 * @param pinfo pointer to packet information fields
450 * @param tree pointer to data tree wireshark uses to display packet.
451 * @param packet Miwi P2PStar packet information.
452 * @param offset offset into the tvb to find the FCF.
455 static void
456 dissect_miwi_fcf(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, miwi_packet *packet, unsigned *offset)
458 uint16_t miwi_fcf;
460 /*Frame control fields*/
461 miwi_fcf = tvb_get_letohs(tvb, (const int)*offset);
462 packet->frame_type = (miwi_fcf & MIWI_MAC_FCF_FRAME_TYPE);
463 packet->security_enable = (miwi_fcf & MIWI_MAC_FCF_SECURITY_EN) >> 3;
464 packet->frame_pending = (miwi_fcf & MIWI_MAC_FCF_FRAME_PENDING) >> 4;
465 packet->ack_request = (miwi_fcf & MIWI_MAC_FCF_ACK_REQUEST) >> 5;
466 packet->pan_id_compression = (miwi_fcf & MIWI_MAC_FCF_PANID_COMP) >> 6;
467 /*packet->reserved = (miwi_fcf & MIWI_MAC_FCF_RESERVED) >> 7;*/
468 packet->dst_addr_mode = (miwi_fcf & MIWI_MAC_FCF_DEST_ADDR_MODE) >> 10;
469 packet->version = (miwi_fcf & MIWI_MAC_FCF_FRAME_VERSION) >> 12;
470 packet->src_addr_mode = (miwi_fcf & MIWI_MAC_FCF_SRC_ADDR_MODE) >> 14;
472 proto_item_append_text(tree, " %s", val_to_str_const(packet->frame_type, miwi_mac_frame_types, "Reserved"));
473 col_set_str(pinfo->cinfo, COL_INFO, val_to_str_const(packet->frame_type, miwi_mac_frame_types, "Reserved"));
475 proto_tree_add_bitmask(tree, tvb,(const int)*offset, hf_miwi_fcf,
476 ett_miwi_p2pstar_fcf, fields, ENC_LITTLE_ENDIAN);
478 *offset += 2;
479 }/* dissect_miwi_fcf */
482 * Command subdissector routine for the Association request command.
484 * @param tvb pointer to buffer containing raw packet.
485 * @param pinfo pointer to packet information fields.
486 * @param tree pointer to protocol tree.
487 * @param packet Miwi P2PStar packet information.
488 * @param offset offset into the tvb to find the packet information.
491 static void
492 dissect_miwi_connect_req(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, miwi_packet *packet, unsigned *offset)
494 uint8_t cap,oper_chan;
495 proto_tree *subtree;
496 static int* const capability[] = {
497 &hf_miwi_cap_info_rcv_on_idle,
498 &hf_miwi_cap_info_rqst_data_on_wp,
499 &hf_miwi_cap_info_need_time_sync,
500 &hf_miwi_cap_info_security_cap,
501 &hf_miwi_cap_info_reserved,
502 NULL
505 /* Create a subtree for this command frame. */
506 subtree = proto_tree_add_subtree(tree, tvb, *offset, 1,ett_miwi_p2pstar_cmd_tree, NULL,
507 val_to_str_const(packet->command_id, miwi_p2pstar_cmd_names, "Unknown Command"));
508 oper_chan = tvb_get_uint8(tvb, *offset);
509 proto_tree_add_uint(subtree, hf_miwi_oper_chan, tvb, *offset, 1, oper_chan);
510 *offset += 1;
512 /* Get and display capability info. */
513 cap = tvb_get_uint8(tvb, *offset);
514 proto_tree_add_uint(subtree, hf_miwi_cap_info, tvb, *offset, 1, cap);
515 proto_tree_add_bitmask_list(subtree, tvb, *offset, 1, capability, ENC_NA);
516 *offset += 1;
518 /* Call the data dissector for any leftover bytes. */
519 if(tvb_captured_length(tvb) > *offset){
520 call_data_dissector(tvb_new_subset_remaining(tvb, *offset), pinfo, tree);
522 }/* dissect_miwi_connect_req */
525 * Command subdissector routine for the Association response command.
527 * @param tvb pointer to buffer containing raw packet.
528 * @param pinfo pointer to packet information fields.
529 * @param tree pointer to protocol tree.
530 * @param packet Miwi P2PStar packet information.
531 * @param offset offset into the tvb to find the packet information.
533 static void
534 dissect_miwi_connect_rsp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, miwi_packet *packet, unsigned *offset)
536 proto_tree *subtree;
537 proto_item *ti;
538 uint8_t status;
539 uint8_t cap;
540 static int* const capability[] = {
541 &hf_miwi_cap_info_rcv_on_idle,
542 &hf_miwi_cap_info_rqst_data_on_wp,
543 &hf_miwi_cap_info_need_time_sync,
544 &hf_miwi_cap_info_security_cap,
545 &hf_miwi_cap_info_reserved,
546 NULL
549 /* Create a subtree for this command frame. */
550 subtree = proto_tree_add_subtree(tree, tvb, *offset, 3, ett_miwi_p2pstar_cmd_tree, NULL,
551 val_to_str_const((const uint32_t)packet->command_id, miwi_p2pstar_cmd_names, "Unknown Command"));
553 /* Get and display the status. */
554 status = tvb_get_uint8(tvb, *offset);
555 if(tree){
556 ti = proto_tree_add_uint(subtree, hf_miwi_conn_res_status, tvb, *offset, 1, status);
557 proto_item_append_text(ti, "%s", val_to_str_const(status, miwi_p2pstar_conn_status, " (Reserved)"));
559 *offset += 1;
560 col_append_str(pinfo->cinfo, COL_INFO, " Connection Response");
562 /* Update the info column. */
563 if(status == IEEE802154_CMD_ASRSP_AS_SUCCESS){
564 /* Association was successful. */
565 if(packet->src_addr_mode != IEEE802154_FCF_ADDR_SHORT){
566 col_append_fstr(pinfo->cinfo, COL_INFO, ", PAN: 0x%04x", packet->dst_pan);
568 if(packet->src16 != IEEE802154_NO_ADDR16){
569 col_append_fstr(pinfo->cinfo, COL_INFO, " Addr: 0x%04x", packet->src16);
572 else{
573 /* Association was unsuccessful. */
574 col_append_str(pinfo->cinfo, COL_INFO, ", Unsuccessful");
577 /* Update the address table. */
578 if((status == IEEE802154_CMD_ASRSP_AS_SUCCESS) && (packet->src16 != IEEE802154_NO_ADDR16)){
579 ieee802154_addr_update(&miwi_map, packet->src16, packet->dst_pan, packet->dst64,
580 pinfo->current_proto, pinfo->num);
583 /* Get and display capability info. */
584 cap = tvb_get_uint8(tvb, *offset);
585 proto_tree_add_uint(subtree, hf_miwi_cap_info, tvb, *offset, 1, cap);
586 proto_tree_add_bitmask_list(subtree, tvb, *offset, 1, capability, ENC_NA);
587 *offset += 1;
589 /* Call the data dissector for any leftover bytes. */
590 if(tvb_captured_length(tvb) > *offset){
591 call_data_dissector(tvb_new_subset_remaining(tvb, *offset), pinfo, tree);
593 }/* dissect_miwi_connect_rsp */
595 * Command subdissector routine for the Channel Hopping command.
597 * @param tvb pointer to buffer containing raw packet.
598 * @param pinfo pointer to packet information fields.
599 * @param tree pointer to protocol tree.
600 * @param packet Miwi P2PStar packet information.
601 * @param offset offset into the tvb to find the packet information.
603 static void
604 dissect_miwi_channel_hop(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, miwi_packet *packet, unsigned *offset)
606 uint8_t current_op_channel,dst_channel_to_jump_to;
607 proto_tree *subtree;
608 proto_item *ti;
610 /* Create a subtree for this command frame. */
611 subtree = proto_tree_add_subtree(tree, tvb, *offset, 1,ett_miwi_p2pstar_cmd_tree, NULL,
612 val_to_str_const(packet->command_id, miwi_p2pstar_cmd_names, "Unknown Command"));
613 current_op_channel = tvb_get_uint8(tvb, *offset);
614 ti = proto_tree_add_uint(subtree, hf_miwi_current_op_channel, tvb, *offset, 1, current_op_channel);
615 proto_item_append_text(ti, ", Current Operating Channel: %i", current_op_channel);
616 *offset +=1;
618 dst_channel_to_jump_to = tvb_get_uint8(tvb, *offset);
619 ti = proto_tree_add_uint(subtree, hf_miwi_dst_channel_to_jump_to, tvb, *offset, 1, dst_channel_to_jump_to);
620 proto_item_append_text(ti, ", Destination Channel to Jump to: %i", dst_channel_to_jump_to);
621 *offset +=1;
623 /* Call the data dissector for any leftover bytes. */
624 if(tvb_captured_length(tvb) > *offset){
625 call_data_dissector(tvb_new_subset_remaining(tvb, *offset), pinfo, tree);
627 }/* dissect_miwi_channel_hop */
630 * Command subdissector routine for the Connection removal response command.
632 * @param tvb pointer to buffer containing raw packet.
633 * @param pinfo pointer to packet information fields.
634 * @param tree pointer to protocol tree.
635 * @param packet Miwi P2PStar packet information.
636 * @param offset offset into the tvb to find the packet information.
638 static void
639 dissect_miwi_connect_removal_res(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, miwi_packet *packet, unsigned *offset)
641 uint8_t conn_rmv_res_status;
642 proto_tree *subtree;
643 proto_item *ti;
645 /* Create a subtree for this command frame. */
646 subtree = proto_tree_add_subtree(tree, tvb, *offset, 1,ett_miwi_p2pstar_cmd_tree, NULL,
647 val_to_str_const(packet->command_id, miwi_p2pstar_cmd_names, "Unknown Command"));
648 conn_rmv_res_status = tvb_get_uint8(tvb, *offset);
649 ti = proto_tree_add_uint(subtree, hf_miwi_conn_rmv_res_status, tvb, *offset, 1, conn_rmv_res_status);
650 *offset +=1;
651 if(conn_rmv_res_status == 0x00){
652 proto_item_append_text(ti, ", Successful [Status: %i]", conn_rmv_res_status);
653 } else
654 proto_item_append_text(ti, ", Failed [Error Code: %i]", conn_rmv_res_status);
656 /* Call the data dissector for any leftover bytes. */
657 if(tvb_captured_length(tvb) > *offset){
658 call_data_dissector(tvb_new_subset_remaining(tvb, *offset), pinfo, tree);
660 }/* dissect_miwi_connect_removal_res */
663 * Command subdissector routine for the Scan request command.
665 * @param tvb pointer to buffer containing raw packet.
666 * @param pinfo pointer to packet information fields.
667 * @param tree pointer to protocol tree.
668 * @param packet Miwi P2PStar packet information.
669 * @param offset offset into the tvb to find the packet information.
671 static void
672 dissect_miwi_active_scan_req(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, miwi_packet *packet, unsigned *offset)
674 uint8_t scan_cur_chan;
675 proto_tree *subtree;
676 proto_item *ti;
678 /* Create a subtree for this command frame. */
679 subtree = proto_tree_add_subtree(tree, tvb, *offset, 1,ett_miwi_p2pstar_cmd_tree, NULL,
680 val_to_str_const(packet->command_id, miwi_p2pstar_cmd_names, "Unknown Command"));
681 scan_cur_chan = tvb_get_uint8(tvb, *offset);
682 ti = proto_tree_add_uint(subtree, hf_miwi_current_op_channel, tvb, *offset, 1, scan_cur_chan);
683 proto_item_append_text(ti, ", Current operating Channel %i", scan_cur_chan);
684 *offset +=1;
686 /* Call the data dissector for any leftover bytes. */
687 if(tvb_captured_length(tvb) > *offset){
688 call_data_dissector(tvb_new_subset_remaining(tvb, *offset), pinfo, tree);
690 }/* dissect_miwi_active_scan_req */
692 * Command subdissector routine for the Scan response command.
694 * @param tvb pointer to buffer containing raw packet.
695 * @param pinfo pointer to packet information fields.
696 * @param tree pointer to protocol tree.
697 * @param packet Miwi P2PStar packet information.
698 * @param offset offset into the tvb to find the packet information.
701 static void
702 dissect_miwi_active_scan_res(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, miwi_packet *packet, unsigned *offset)
704 uint8_t cap,scan_res_node_id;
705 proto_tree *subtree;
706 static int* const capability[] = {
707 &hf_miwi_cap_info_rcv_on_idle,
708 &hf_miwi_cap_info_rqst_data_on_wp,
709 &hf_miwi_cap_info_need_time_sync,
710 &hf_miwi_cap_info_security_cap,
711 &hf_miwi_cap_info_reserved,
712 NULL
715 /* Create a subtree for this command frame. */
716 subtree = proto_tree_add_subtree(tree, tvb, *offset, 1,ett_miwi_p2pstar_cmd_tree, NULL,
717 val_to_str_const(packet->command_id, miwi_p2pstar_cmd_names, "Unknown Command"));
719 /* Get and display capability info. */
720 cap = tvb_get_uint8(tvb, *offset);
721 proto_tree_add_uint(subtree, hf_miwi_cap_info, tvb, *offset, 1, cap);
722 proto_tree_add_bitmask_list(subtree, tvb, *offset, 1, capability, ENC_NA);
723 *offset += 1;
725 scan_res_node_id = tvb_get_uint8(tvb, *offset);
726 proto_tree_add_uint(subtree, hf_miwi_oper_chan, tvb, *offset, 1, scan_res_node_id);
727 *offset += 1;
729 /* Call the data dissector for any leftover bytes. */
730 if(tvb_captured_length(tvb) > *offset){
731 call_data_dissector(tvb_new_subset_remaining(tvb, *offset), pinfo, tree);
733 }/* dissect_miwi_active_scan_res */
735 * Command subdissector routine for the forward Packet command.
737 * @param tvb pointer to buffer containing raw packet.
738 * @param pinfo pointer to packet information fields.
739 * @param tree pointer to protocol tree.
740 * @param packet Miwi P2PStar packet information.
741 * @param offset offset into the tvb to find the packet information.
743 static void
744 dissect_miwi_fwd_packet_cmd(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, miwi_packet *packet, unsigned *offset)
746 uint8_t fwd_pkt_dst_addr;
747 proto_tree *subtree;
749 /* Create a subtree for this command frame. */
750 subtree = proto_tree_add_subtree(tree, tvb, *offset, 1,ett_miwi_p2pstar_cmd_tree, NULL,
751 val_to_str_const(packet->command_id, miwi_p2pstar_cmd_names, "Unknown Command"));
752 fwd_pkt_dst_addr = tvb_get_uint8(tvb, *offset);
753 proto_tree_add_uint(subtree, hf_miwi_fwd_pkt_dst_addr, tvb, *offset, 1, fwd_pkt_dst_addr);
754 *offset +=1;
756 /* Call the data dissector for any leftover bytes. */
757 if(tvb_captured_length(tvb) > *offset){
758 call_data_dissector(tvb_new_subset_remaining(tvb, *offset), pinfo, tree);
760 }/* dissect_miwi_fwd_packet_cmd */
762 * Command subdissector routine for the Connection table broadcast command.
764 * @param tvb pointer to buffer containing raw packet.
765 * @param pinfo pointer to packet information fields.
766 * @param tree pointer to protocol tree.
767 * @param packet Miwi P2PStar packet information.
768 * @param offset offset into the tvb to find the packet information.
771 static void
772 dissect_miwi_connect_tbl_bcast_cmd(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, miwi_packet *packet, unsigned *offset)
774 uint8_t conn_tbl_size;
775 proto_tree *subtree;
777 /* Create a subtree for this command frame. */
778 subtree = proto_tree_add_subtree(tree, tvb, *offset, 1,ett_miwi_p2pstar_cmd_tree, NULL,
779 val_to_str_const(packet->command_id, miwi_p2pstar_cmd_names, "Unknown Command"));
780 conn_tbl_size = tvb_get_uint8(tvb, *offset);
781 proto_tree_add_uint(subtree, hf_miwi_conn_tbl_size, tvb, *offset, 1, conn_tbl_size);
782 *offset +=1;
784 /* Call the data dissector for any leftover bytes. */
785 if(tvb_captured_length(tvb) > *offset){
786 call_data_dissector(tvb_new_subset_remaining(tvb, *offset), pinfo, tree);
788 }/* dissect_miwi_connect_tbl_bcast_cmd */
791 * Subdissector routine for MiWi P2P Star commands
793 * @param tvb pointer to buffer containing the command payload
794 * @param pinfo pointer to packet information fields
795 * @param tree pointer to the protocol tree
796 * @param packet Miwi P2P Star packet information
797 * @param offset offset into the tvb to find the packet information.
799 static void
800 dissect_miwi_command(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, miwi_packet *packet, unsigned *offset)
802 col_append_str(pinfo->cinfo, COL_INFO, val_to_str_const((const uint32_t)packet->command_id, miwi_p2pstar_cmd_names, "Unknown Command"));
804 switch (packet->command_id){
805 case MIWI_P2P_CMD_CONN_REQ:
806 dissect_miwi_connect_req(tvb, pinfo, tree, packet,offset);
807 break;
808 case MIWI_P2P_CMD_CONN_RES:
809 dissect_miwi_connect_rsp(tvb, pinfo, tree, packet,offset);
810 break;
811 case MIWI_P2P_CMD_CHANNEL_HOP:
812 dissect_miwi_channel_hop(tvb, pinfo, tree, packet,offset);
813 break;
814 case MIWI_P2P_CMD_ACTIVE_SCAN_REQ:
815 dissect_miwi_active_scan_req(tvb, pinfo, tree, packet,offset);
816 break;
817 case MIWI_P2P_CMD_CONN_REMOVAL_RES:
818 dissect_miwi_connect_removal_res(tvb, pinfo, tree, packet,offset);
819 break;
820 case MIWI_P2P_CMD_ACTIVE_SCAN_RES:
821 dissect_miwi_active_scan_res(tvb, pinfo, tree, packet,offset);
822 break;
823 case MIWI_STAR_CMD_FORWARD_PACKET:
824 dissect_miwi_fwd_packet_cmd(tvb, pinfo, tree, packet,offset);
825 break;
826 case MIWI_STAR_CMD_CONN_TABLE:
827 dissect_miwi_connect_tbl_bcast_cmd(tvb, pinfo, tree, packet,offset);
828 break;
829 case MIWI_P2P_CMD_DATA_REQ:
830 case MIWI_P2P_CMD_CONN_REMOVAL_REQ:
831 case MIWI_STAR_CMD_SOFT_ACK:
832 case MIWI_STAR_CMD_LINK_STATUS:
833 /* No payload expected. */
834 break;
835 default:
836 proto_item_append_text(tree, ", Unknown Command");
837 if(tvb_captured_length_remaining(tvb, 0) > 0){
838 call_data_dissector(tvb, pinfo, tree);
839 break;
841 }/* switch */
842 }/* dissect_miwi_command */
845 * Subdissector routine for MiWi P2P Star header parsing
847 * @param tvb pointer to buffer containing the command payload
848 * @param pinfo pointer to packet information fields
849 * @param tree pointer to the protocol tree
850 * @param created_header_tree new tree to parse the MiWi packet .
851 * @param parsed_info Miwi P2P Star packet information
853 static unsigned
854 miwi_dissect_header(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, proto_tree **created_header_tree, miwi_packet **parsed_info)
856 proto_tree *miwi_tree = NULL;
857 proto_item *proto_root = NULL;
858 proto_item *hidden_item;
859 proto_item *ti;
860 unsigned offset = 0;
861 bool dstPanPresent = false;
862 bool srcPanPresent = false;
863 miwi_packet *packet = wmem_new0(wmem_packet_scope(), miwi_packet);
864 ieee802154_short_addr addr16;
865 ieee802154_hints_t *ieee_hints;
867 packet->short_table = miwi_map.short_table;
869 /* Allocate frame data with hints for upper layers */
870 if(!PINFO_FD_VISITED(pinfo) ||
871 (ieee_hints = (ieee802154_hints_t *)p_get_proto_data(wmem_file_scope(), pinfo, proto_miwi_p2pstar, 0)) == NULL){
872 ieee_hints = wmem_new0(wmem_file_scope(), ieee802154_hints_t);
873 p_add_proto_data(wmem_file_scope(), pinfo, proto_miwi_p2pstar, 0, ieee_hints);
876 /* Save a pointer to the whole packet */
877 ieee_hints->packet = packet;
879 /* Create the protocol tree. */
880 if(tree){
881 proto_root = proto_tree_add_protocol_format(tree, proto_miwi_p2pstar, tvb, 0, tvb_captured_length(tvb), "IEEE 802.15.4-MiWi");
882 miwi_tree = proto_item_add_subtree(proto_root, ett_miwi_p2pstar);
884 /* Add the protocol name. */
885 col_set_str(pinfo->cinfo, COL_PROTOCOL, "MiWi P2P Star");
887 /* Set out parameters */
888 *created_header_tree = miwi_tree;
889 *parsed_info = packet;
891 /* Add the packet length to the filter field */
892 hidden_item = proto_tree_add_uint(miwi_tree, hf_miwi_frame_length, NULL, 0, 0, tvb_reported_length(tvb));
893 proto_item_set_hidden(hidden_item);
895 /* Frame Control Field */
896 dissect_miwi_fcf(tvb, pinfo, miwi_tree, packet, &offset);
898 /* Sequence Number */
899 /* IEEE 802.15.4 Sequence Number Suppression */
900 packet->seqno = tvb_get_uint8(tvb, offset);
901 proto_tree_add_uint(miwi_tree, hf_miwi_seq, tvb, offset, 1, packet->seqno);
902 /* For Ack packets display this in the root. */
903 if(packet->frame_type == IEEE802154_FCF_ACK){
904 proto_item_append_text(proto_root, ", Sequence Number: %u", packet->seqno);
906 offset += 1;
909 * ADDRESSING FIELDS
911 /* Clear out the addressing strings. */
912 clear_address(&pinfo->net_dst);
913 clear_address(&pinfo->dl_dst);
914 clear_address(&pinfo->dst);
915 clear_address(&pinfo->net_src);
916 clear_address(&pinfo->dl_src);
917 clear_address(&pinfo->src);
919 if(packet->dst_addr_mode == IEEE802154_FCF_ADDR_RESERVED){
920 /* Invalid Destination Address Mode. Abort Dissection. */
921 expert_add_info(pinfo, proto_root, &ei_miwi_dst);
922 return 0;
925 if(packet->src_addr_mode == IEEE802154_FCF_ADDR_RESERVED){
926 /* Invalid Source Address Mode. Abort Dissection. */
927 expert_add_info(pinfo, proto_root, &ei_miwi_src);
928 return 0;
931 if(packet->version == IEEE802154_VERSION_RESERVED){
932 /* Unknown Frame Version. Abort Dissection. */
933 expert_add_info(pinfo, proto_root, &ei_miwi_frame_ver);
934 return 0;
936 else if((packet->version == IEEE802154_VERSION_2003) || /* For Frame Version 0b00 and */
937 (packet->version == IEEE802154_VERSION_2006)) { /* 0b01 effect defined in section 7.2.1.5 */
939 if((packet->dst_addr_mode != IEEE802154_FCF_ADDR_NONE) && /* if both destination and source */
940 (packet->src_addr_mode != IEEE802154_FCF_ADDR_NONE)){ /* addressing information is present */
941 if(packet->pan_id_compression == 1){ /* PAN IDs are identical */
942 dstPanPresent = true;
943 srcPanPresent = false; /* source PAN ID is omitted */
945 else{ /* PAN IDs are different, both shall be included in the frame */
946 dstPanPresent = true;
947 srcPanPresent = true;
950 else{
951 if(packet->pan_id_compression == 1){ /* all remaining cases pan_id_compression must be zero */
952 expert_add_info(pinfo, proto_root, &ei_miwi_invalid_panid_compression);
953 return 0;
955 else{
956 /* only either the destination or the source addressing information is present */
957 if((packet->dst_addr_mode != IEEE802154_FCF_ADDR_NONE) && /* Present */
958 (packet->src_addr_mode == IEEE802154_FCF_ADDR_NONE)){ /* Not Present */
959 dstPanPresent = true;
960 srcPanPresent = false;
962 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_NONE) && /* Not Present */
963 (packet->src_addr_mode != IEEE802154_FCF_ADDR_NONE)){ /* Present */
964 dstPanPresent = false;
965 srcPanPresent = true;
967 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_NONE) && /* Not Present */
968 (packet->src_addr_mode == IEEE802154_FCF_ADDR_NONE)){ /* Not Present */
969 dstPanPresent = false;
970 srcPanPresent = false;
972 else{
973 expert_add_info(pinfo, proto_root, &ei_miwi_invalid_addressing);
974 return 0;
979 else if(packet->version == IEEE802154_VERSION_2015){
980 /* for Frame Version 0b10 PAN Id Compression only applies to these frame types */
981 if((packet->frame_type == IEEE802154_FCF_BEACON) ||
982 (packet->frame_type == IEEE802154_FCF_DATA) ||
983 (packet->frame_type == IEEE802154_FCF_ACK) ||
984 (packet->frame_type == IEEE802154_FCF_CMD) ){
986 /* Implements Table 7-6 of IEEE 802.15.4-2015
988 * Destination Address Source Address Destination PAN ID Source PAN ID PAN ID Compression
989 *-------------------------------------------------------------------------------------------------
990 * 1. Not Present Not Present Not Present Not Present 0
991 * 2. Not Present Not Present Present Not Present 1
992 * 3. Present Not Present Present Not Present 0
993 * 4. Present Not Present Not Present Not Present 1
995 * 5. Not Present Present Not Present Present 0
996 * 6. Not Present Present Not Present Not Present 1
998 * 7. Extended Extended Present Not Present 0
999 * 8. Extended Extended Not Present Not Present 1
1001 * 9. Short Short Present Present 0
1002 * 10. Short Extended Present Present 0
1003 * 11. Extended Short Present Present 0
1005 * 12. Short Extended Present Not Present 1
1006 * 13. Extended Short Present Not Present 1
1007 * 14. Short Short Present Not Present 1
1010 /* Row 1 */
1011 if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_NONE) && /* Not Present */
1012 (packet->src_addr_mode == IEEE802154_FCF_ADDR_NONE) && /* Not Present */
1013 (packet->pan_id_compression == 0)){
1014 dstPanPresent = false;
1015 srcPanPresent = false;
1017 /* Row 2 */
1018 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_NONE) && /* Not Present */
1019 (packet->src_addr_mode == IEEE802154_FCF_ADDR_NONE) && /* Not Present */
1020 (packet->pan_id_compression == 1)){
1021 dstPanPresent = true;
1022 srcPanPresent = false;
1024 /* Row 3 */
1025 else if((packet->dst_addr_mode != IEEE802154_FCF_ADDR_NONE) && /* Present */
1026 (packet->src_addr_mode == IEEE802154_FCF_ADDR_NONE) && /* Not Present */
1027 (packet->pan_id_compression == 0)){
1028 dstPanPresent = true;
1029 srcPanPresent = false;
1031 /* Row 4 */
1032 else if((packet->dst_addr_mode != IEEE802154_FCF_ADDR_NONE) && /* Present */
1033 (packet->src_addr_mode == IEEE802154_FCF_ADDR_NONE) && /* Not Present */
1034 (packet->pan_id_compression == 1)){
1035 dstPanPresent = false;
1036 srcPanPresent = false;
1038 /* Row 5 */
1039 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_NONE) && /* Not Present */
1040 (packet->src_addr_mode != IEEE802154_FCF_ADDR_NONE) && /* Present */
1041 (packet->pan_id_compression == 0)){
1042 dstPanPresent = false;
1043 srcPanPresent = true;
1045 /* Row 6 */
1046 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_NONE) && /* Not Present */
1047 (packet->src_addr_mode != IEEE802154_FCF_ADDR_NONE) && /* Present */
1048 (packet->pan_id_compression == 1)){
1049 dstPanPresent = false;
1050 srcPanPresent = false;
1052 /* Row 7 */
1053 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_EXT) && /* Extended */
1054 (packet->src_addr_mode == IEEE802154_FCF_ADDR_EXT) && /* Extended */
1055 (packet->pan_id_compression == 0)){
1056 dstPanPresent = true;
1057 srcPanPresent = false;
1059 /* Row 8 */
1060 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_EXT) && /* Extended */
1061 (packet->src_addr_mode == IEEE802154_FCF_ADDR_EXT) && /* Extended */
1062 (packet->pan_id_compression == 1)){
1063 dstPanPresent = false;
1064 srcPanPresent = false;
1066 /* Row 9 */
1067 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_SHORT) && /* Short */
1068 (packet->src_addr_mode == IEEE802154_FCF_ADDR_SHORT) && /* Short */
1069 (packet->pan_id_compression == 0)){
1070 dstPanPresent = true;
1071 srcPanPresent = true;
1073 /* Row 10 */
1074 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_SHORT) && /* Short */
1075 (packet->src_addr_mode == IEEE802154_FCF_ADDR_EXT) && /* Extended */
1076 (packet->pan_id_compression == 0)){
1077 dstPanPresent = true;
1078 srcPanPresent = true;
1080 /* Row 11 */
1081 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_EXT) && /* Extended */
1082 (packet->src_addr_mode == IEEE802154_FCF_ADDR_SHORT) && /* Short */
1083 (packet->pan_id_compression == 0)){
1084 dstPanPresent = true;
1085 srcPanPresent = true;
1087 /* Row 12 */
1088 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_SHORT) && /* Short */
1089 (packet->src_addr_mode == IEEE802154_FCF_ADDR_EXT) && /* Extended */
1090 (packet->pan_id_compression == 1)){
1091 dstPanPresent = true;
1092 srcPanPresent = false;
1094 /* Row 13 */
1095 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_EXT) && /* Extended */
1096 (packet->src_addr_mode == IEEE802154_FCF_ADDR_SHORT) && /* Short */
1097 (packet->pan_id_compression == 1)){
1098 dstPanPresent = true;
1099 srcPanPresent = false;
1101 /* Row 14 */
1102 else if((packet->dst_addr_mode == IEEE802154_FCF_ADDR_SHORT) && /* Short */
1103 (packet->src_addr_mode == IEEE802154_FCF_ADDR_SHORT) && /* Short */
1104 (packet->pan_id_compression == 1)){
1105 dstPanPresent = true;
1106 srcPanPresent = false;
1108 else{
1109 expert_add_info(pinfo, proto_root, &ei_miwi_invalid_panid_compression2);
1110 return 0;
1113 else{ /* Frame Type is neither Beacon, Data, Ack, nor Command: PAN ID Compression is not used */
1114 dstPanPresent = false; /* no PAN ID will */
1115 srcPanPresent = false; /* be present */
1118 else{
1119 /* Unknown Frame Version. Abort Dissection. */
1120 expert_add_info(pinfo, proto_root, &ei_miwi_frame_ver);
1121 return 0;
1125 * Addressing Fields
1128 /* Destination PAN Id */
1129 if(dstPanPresent){
1130 char* pan_id = (char *)wmem_new(pinfo->pool, uint64_t);
1132 packet->dst_pan = tvb_get_letohs(tvb, offset);
1133 miwi_short_to_str(packet->dst_pan,pan_id,10);
1135 col_append_fstr(pinfo->cinfo, COL_INFO, ", Pan ID: %s", pan_id);
1136 proto_tree_add_uint(miwi_tree, hf_miwi_dst_panid, tvb, offset, 2, packet->dst_pan);
1137 offset += 2;
1140 /* Destination Address */
1141 if(packet->dst_addr_mode == IEEE802154_FCF_ADDR_SHORT){
1142 char* dst_addr = (char *)wmem_new(pinfo->pool, uint64_t);
1144 /* Get the address. */
1145 packet->dst16 = tvb_get_letohs(tvb, offset);
1147 /* Provide address hints to higher layers that need it. */
1148 if(ieee_hints){
1149 ieee_hints->dst16 = packet->dst16;
1152 set_address_tvb(&pinfo->dl_dst, miwi_short_address_type, 2, tvb, offset);
1153 copy_address_shallow(&pinfo->dst, &pinfo->dl_dst);
1154 miwi_short_to_str(packet->dst16,dst_addr,10);
1156 proto_tree_add_uint(miwi_tree, hf_miwi_short_dst_addr, tvb, offset, 2, packet->dst16);
1157 proto_item_append_text(proto_root, ", Dst: %s", dst_addr);
1158 ti = proto_tree_add_uint(miwi_tree, hf_miwi_addr16, tvb, offset, 2, packet->dst16);
1159 proto_item_set_generated(ti);
1160 proto_item_set_hidden(ti);
1162 col_append_fstr(pinfo->cinfo, COL_INFO, ", Dst: %s", dst_addr);
1163 offset += 2;
1165 else if(packet->dst_addr_mode == IEEE802154_FCF_ADDR_EXT){
1166 uint64_t *p_addr = (uint64_t *)wmem_new(pinfo->pool, uint64_t);
1168 /* Get the address */
1169 packet->dst64 = tvb_get_letoh64(tvb, offset);
1171 /* Copy and convert the address to network byte order. */
1172 *p_addr = pntoh64(&(packet->dst64));
1174 /* Display the destination address. */
1175 /* XXX - OUI resolution doesn't happen when displaying resolved
1176 * EUI64 addresses; that should probably be fixed in
1177 * epan/addr_resolv.c.
1179 set_address(&pinfo->dl_dst, AT_EUI64, 8, p_addr);
1180 copy_address_shallow(&pinfo->dst, &pinfo->dl_dst);
1181 if(tree){
1182 proto_tree_add_item(miwi_tree, hf_miwi_ext_dst_addr, tvb, offset, 8, ENC_LITTLE_ENDIAN);
1183 proto_item_append_text(proto_root, ", Dst: %s", eui64_to_display(wmem_packet_scope(), packet->dst64));
1184 ti = proto_tree_add_item(miwi_tree, hf_miwi_addr64, tvb, offset, 8, ENC_LITTLE_ENDIAN);
1185 proto_item_set_generated(ti);
1186 proto_item_set_hidden(ti);
1188 col_append_fstr(pinfo->cinfo, COL_INFO, ", Dst: %s", eui64_to_display(wmem_packet_scope(), packet->dst64));
1189 offset += 8;
1192 /* Source PAN Id */
1193 if(srcPanPresent){
1194 char* pan_id = (char *)wmem_new(pinfo->pool, uint64_t);
1195 packet->src_pan = tvb_get_letohs(tvb, offset);
1196 miwi_short_to_str(packet->src_pan,pan_id,10);
1197 col_append_fstr(pinfo->cinfo, COL_INFO, ", Src Pan ID: %s", pan_id);
1198 proto_tree_add_uint(miwi_tree, hf_miwi_src_panid, tvb, offset, 2, packet->src_pan);
1199 offset += 2;
1201 else{
1202 if(dstPanPresent){
1203 packet->src_pan = packet->dst_pan;
1205 else{
1206 packet->src_pan = IEEE802154_BCAST_PAN;
1209 if(ieee_hints){
1210 ieee_hints->src_pan = packet->src_pan;
1213 /* Source Address */
1214 if(packet->src_addr_mode == IEEE802154_FCF_ADDR_SHORT){
1215 char* src_addr = (char *)wmem_new(pinfo->pool, uint64_t);
1217 /* Get the address. */
1218 packet->src16 = tvb_get_letohs(tvb, offset);
1220 if(!PINFO_FD_VISITED(pinfo)){
1221 /* If we know our extended source address from previous packets,
1222 * provide a pointer to it in a hint for upper layers */
1223 addr16.addr = packet->src16;
1224 addr16.pan = packet->src_pan;
1226 if(ieee_hints){
1227 ieee_hints->src16 = packet->src16;
1228 ieee_hints->map_rec = (ieee802154_map_rec *)
1229 g_hash_table_lookup(miwi_map.short_table, &addr16);
1233 set_address_tvb(&pinfo->dl_src, miwi_short_address_type, 2, tvb, offset);
1234 copy_address_shallow(&pinfo->src, &pinfo->dl_src);
1235 miwi_short_to_str(packet->src16,src_addr,10);
1237 /* Add the addressing info to the tree. */
1238 if(tree){
1239 proto_tree_add_uint(miwi_tree, hf_miwi_short_src_addr, tvb, offset, 2, packet->src16);
1240 proto_item_append_text(proto_root, ", Src: %s", src_addr);
1241 ti = proto_tree_add_uint(miwi_tree, hf_miwi_addr16, tvb, offset, 2, packet->src16);
1242 proto_item_set_generated(ti);
1243 proto_item_set_hidden(ti);
1245 if(ieee_hints && ieee_hints->map_rec){
1246 /* Display inferred source address info */
1247 ti = proto_tree_add_eui64(miwi_tree, hf_miwi_short_src_addr, tvb, offset, 0,
1248 ieee_hints->map_rec->addr64);
1249 proto_item_set_generated(ti);
1250 ti = proto_tree_add_eui64(miwi_tree, hf_miwi_addr64, tvb, offset, 0, ieee_hints->map_rec->addr64);
1251 proto_item_set_generated(ti);
1252 proto_item_set_hidden(ti);
1254 if( ieee_hints->map_rec->start_fnum ){
1255 ti = proto_tree_add_uint(miwi_tree, hf_miwi_src64_origin, tvb, 0, 0,
1256 ieee_hints->map_rec->start_fnum);
1258 else{
1259 ti = proto_tree_add_uint_format_value(miwi_tree, hf_miwi_src64_origin, tvb, 0, 0,
1260 ieee_hints->map_rec->start_fnum, "Pre-configured");
1262 proto_item_set_generated(ti);
1266 col_append_fstr(pinfo->cinfo, COL_INFO, ", Src: %s", src_addr);
1268 offset += 2;
1270 else if(packet->src_addr_mode == IEEE802154_FCF_ADDR_EXT){
1271 uint64_t *p_addr = (uint64_t *)wmem_new(pinfo->pool, uint64_t);
1273 /* Get the address. */
1274 packet->src64 = tvb_get_letoh64(tvb, offset);
1276 /* Copy and convert the address to network byte order. */
1277 *p_addr = pntoh64(&(packet->src64));
1279 /* Display the source address. */
1280 /* XXX - OUI resolution doesn't happen when displaying resolved
1281 * EUI64 addresses; that should probably be fixed in
1282 * epan/addr_resolv.c.
1284 set_address(&pinfo->dl_src, AT_EUI64, 8, p_addr);
1285 copy_address_shallow(&pinfo->src, &pinfo->dl_src);
1286 if(tree){
1287 proto_tree_add_item(miwi_tree, hf_miwi_ext_src_addr, tvb, offset, 8, ENC_LITTLE_ENDIAN);
1288 proto_item_append_text(proto_root, ", Src: %s", eui64_to_display(wmem_packet_scope(), packet->src64));
1289 ti = proto_tree_add_item(miwi_tree, hf_miwi_addr64, tvb, offset, 8, ENC_LITTLE_ENDIAN);
1290 proto_item_set_generated(ti);
1291 proto_item_set_hidden(ti);
1294 col_append_fstr(pinfo->cinfo, COL_INFO, ", Src: %s", eui64_to_display(wmem_packet_scope(), packet->src64));
1295 offset += 8;
1298 /* All of the beacon fields, except the beacon payload are considered nonpayload. */
1299 if((packet->version == IEEE802154_VERSION_2003) || (packet->version == IEEE802154_VERSION_2006)){
1301 if(packet->frame_type == IEEE802154_FCF_CMD){
1303 * In IEEE802.15.4-2003 and 2006 the command identifier is considered to be part of the header
1304 * and is thus not encrypted. For IEEE802.15.4-2012e and later the command id is considered to be
1305 * part of the payload, is encrypted, and follows the payload IEs. Thus we only parse the command id
1306 * here for 2006 and earlier frames. */
1307 packet->command_id = tvb_get_uint8(tvb, offset);
1308 if(tree){
1309 proto_tree_add_uint(miwi_tree, hf_miwi_cmd_id, tvb, offset, 1, packet->command_id);
1311 offset++;
1314 return offset;
1315 }/*miwi_dissect_header*/
1318 * Subdissector routine for MiWi P2P Star frame payload parsing
1320 * @param tvb pointer to buffer containing the command payload
1321 * @param pinfo pointer to packet information fields
1322 * @param ieee802154_tree pointer to the protocol tree
1323 * @param packet Miwi P2P Star packet information
1324 * @param fcs_ok set to false to indicate FCS verification failed
1325 * @param offset offset into the tvb to find the packet information.
1327 static unsigned miwi_dissect_frame_payload(tvbuff_t *tvb, packet_info *pinfo, proto_tree *ieee802154_tree, miwi_packet *packet, bool fcs_ok, unsigned *offset)
1329 tvbuff_t *payload_tvb = tvb;
1330 proto_tree *tree = proto_tree_get_parent_tree(ieee802154_tree);
1331 //heur_dtbl_entry_t *hdtbl_entry;
1333 /* There are commands without payload */
1334 if(tvb_captured_length(payload_tvb) > 0 || packet->frame_type == IEEE802154_FCF_CMD){
1336 * Wrap the sub-dissection in a try/catch block in case the payload is
1337 * broken. First we store the current protocol so we can fix it if an
1338 * exception is thrown by the subdissectors.
1340 const char* saved_proto = pinfo->current_proto;
1341 /* Try to dissect the payload. */
1342 TRY {
1343 switch (packet->frame_type){
1344 case IEEE802154_FCF_BEACON:
1345 call_data_dissector(tvb_new_subset_remaining(tvb, *offset), pinfo, tree);
1346 break;
1348 case IEEE802154_FCF_CMD:
1349 dissect_miwi_command(payload_tvb, pinfo, ieee802154_tree, packet,offset);
1350 break;
1352 case IEEE802154_FCF_DATA:
1353 /* Sanity-check. */
1354 if((!fcs_ok && miwi_fcs_ok) || !tvb_reported_length(payload_tvb)){
1355 call_data_dissector(tvb_new_subset_remaining(tvb, *offset), pinfo, tree);
1357 break;
1358 default:
1359 /* Could not subdissect, call the data dissector instead. */
1360 call_data_dissector(tvb_new_subset_remaining(tvb, *offset), pinfo, tree);
1361 break;
1362 }/* switch */
1364 CATCH_ALL {
1366 * Someone encountered an error while dissecting the payload. But
1367 * we haven't yet finished processing all of our layer. Catch and
1368 * display the exception, then fall-through to finish displaying
1369 * the FCS (which we display last so the frame is ordered correctly
1370 * in the tree).
1372 show_exception(payload_tvb, pinfo, tree, EXCEPT_CODE, GET_MESSAGE);
1373 pinfo->current_proto = saved_proto;
1375 ENDTRY;
1377 return tvb_captured_length(tvb);
1380 #if 0
1382 * Dissect the FCS at the end of the frame.
1383 * That is only displayed if the included length of the tvb encompasses it.
1385 * @param tvb the MiWi P2P Star frame tvb
1386 * @param ieee802154_tree the MiWi P2P Star protocol tree
1387 * @param fcs_len length of the FCS field
1388 * @param fcs_ok set to false to indicate FCS verification failed
1390 static void
1391 miwi_dissect_fcs(tvbuff_t *tvb, proto_tree *ieee802154_tree, unsigned fcs_len, bool fcs_ok)
1393 proto_item *ti;
1394 /* The FCS should be the last bytes of the reported packet. */
1395 unsigned offset = tvb_reported_length(tvb)-fcs_len;
1396 /* Dissect the FCS only if it exists (captures which don't or can't get the
1397 * FCS will simply truncate the packet to omit it, but should still set the
1398 * reported length to cover the original packet length), so if the snapshot
1399 * is too short for an FCS don't make a fuss.
1401 if(ieee802154_tree){
1402 if(fcs_len == 2){
1403 uint16_t fcs = tvb_get_letohs(tvb, offset);
1405 ti = proto_tree_add_uint(ieee802154_tree, hf_miwi_fcs, tvb, offset, 2, fcs);
1406 if(fcs_ok){
1407 proto_item_append_text(ti, " (Correct)");
1409 else{
1410 proto_item_append_text(ti, " (Incorrect, expected FCS=0x%04x)", miwi_crc_tvb(tvb, offset));
1412 /* To Help with filtering, add the fcs_ok field to the tree. */
1413 ti = proto_tree_add_boolean(ieee802154_tree, hf_miwi_fcs_ok, tvb, offset, 2, (uint32_t) fcs_ok);
1414 proto_item_set_hidden(ti);
1417 }/* miwi_dissect_fcs */
1418 #endif
1421 * MiWi P2P Star packet dissection routine for Wireshark.
1423 * This function extracts all the information first before displaying.
1424 * If payload exists, that portion will be passed into another dissector
1425 * for further processing.
1427 * This is called after the individual dissect_p2pstar* functions
1428 * have been called to determine what sort of FCS is present, if any.
1430 * @param tvb pointer to buffer containing raw packet.
1431 * @param pinfo pointer to packet information fields
1432 * @param fcs_len length of the FCS field
1434 static void
1435 dissect_miwi_common(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, unsigned fcs_len)
1437 proto_tree *miwi_tree;
1438 miwi_packet *packet;
1439 //bool fcs_present;
1440 bool fcs_ok;
1441 tvbuff_t* no_fcs_tvb;
1442 unsigned offset = 0;
1444 if(fcs_len != 0){
1446 * Well, this packet should, in theory, have an FCS or CC24xx
1447 * metadata.
1448 * Do we have the entire packet, and does it have enough data for
1449 * the FCS/metadata?
1451 unsigned reported_len = tvb_reported_length(tvb);
1453 if(reported_len < fcs_len){
1455 * The packet is claimed not to even have enough data
1456 * for the FCS/metadata. Pretend it doesn't have one.
1458 no_fcs_tvb = tvb;
1459 //fcs_present = false;
1460 fcs_ok = true; // assume OK if not present
1461 } else{
1463 * The packet is claimed to have enough data for the
1464 * FCS/metadata.
1465 * Slice it off from the reported length.
1467 reported_len -= fcs_len;
1468 no_fcs_tvb = tvb_new_subset_length(tvb, 0, reported_len);
1471 * Is the FCS/metadata present in the captured data?
1472 * reported_len is now the length of the packet without the
1473 * FCS/metadata, so the FCS/metadata begins at an offset of
1474 * reported_len.
1476 if(tvb_bytes_exist(tvb, reported_len, fcs_len)){
1478 * Yes. Check whether the FCS was OK.
1480 * If we have an FCS, check it.
1481 * If we have metadata, check its "FCS OK" flag.
1483 //fcs_present = true;
1484 fcs_ok = is_fcs_ok(tvb, fcs_len);
1485 } else{
1487 * No.
1489 * Either 1) this means that there was a snapshot length
1490 * in effect when the capture was done, and that sliced
1491 * some or all of the FCS/metadata off or 2) this is a
1492 * capture with no FCS/metadata, using the same link-layer
1493 * header type value as captures with the FCS/metadata,
1494 * and indicating the lack of the FCS/metadata by having
1495 * the captured length be the length of the packet minus
1496 * the length of the FCS/metadata and the actual length
1497 * being the length of the packet including the FCS/metadata,
1498 * rather than by using the "no FCS" link-layer header type.
1500 * We could try to distinguish between them by checking
1501 * for a captured length that's exactly fcs_len bytes
1502 * less than the actual length. That would allow us to
1503 * report packets that are cut short just before, or in
1504 * the middle of, the FCS as having been cut short by the
1505 * snapshot length.
1507 * However, we can't distinguish between a packet that
1508 * happened to be cut fcs_len bytes short due to a
1509 * snapshot length being in effect when the capture was
1510 * done and a packet that *wasn't* cut short by a snapshot
1511 * length but that doesn't include the FCS/metadata.
1512 * Let's hope that rarely happens.
1514 //fcs_present = false;
1515 fcs_ok = true; // assume OK if not present
1518 } else{
1519 no_fcs_tvb = tvb;
1520 //fcs_present = false;
1521 fcs_ok = true; // assume OK if not present
1524 unsigned mhr_len = miwi_dissect_header(no_fcs_tvb, pinfo, tree, &miwi_tree, &packet);
1525 offset = mhr_len;
1526 if(!mhr_len || tvb_reported_length_remaining(no_fcs_tvb, mhr_len) < 0 ){
1527 return;
1530 if(packet->frame_type == IEEE802154_FCF_DATA){
1531 if((!fcs_ok && miwi_fcs_ok)){
1532 call_data_dissector(tvb, pinfo, tree);
1534 } else{
1535 miwi_dissect_frame_payload(tvb, pinfo, miwi_tree, packet, fcs_ok, &offset);
1540 * Dissector for MiWi P2P Star packet with an FCS containing a 16/32-bit
1541 * CRC value at the end.
1543 * @param tvb pointer to buffer containing raw packet.
1544 * @param pinfo pointer to packet information fields.
1545 * @param tree pointer to data tree wireshark uses to display packet.
1547 static int
1548 dissect_miwi_p2pstar(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data _U_)
1550 unsigned fcs_len;
1552 /* Set the default FCS length based on the FCS type in the configuration */
1553 // fcs_len = miwi_fcs_type_len(miwi_fcs_type);
1554 // unsigned offset = 0;
1555 proto_tree *miwi_tree = NULL;
1556 proto_item *proto_root = NULL;
1557 // miwi_packet *packet = wmem_new0(wmem_packet_scope(), miwi_packet);
1559 /* Set the default FCS length based on the FCS type in the configuration */
1560 fcs_len = miwi_fcs_type_len(miwi_fcs_type);
1562 /* Call the common dissector. */
1563 // dissect_miwi_common1(tvb, pinfo, tree);//, fcs_len);
1564 /* Create the protocol tree. */
1565 if (tree) {
1566 proto_root = proto_tree_add_protocol_format(tree, proto_miwi_p2pstar, tvb, 0, tvb_captured_length(tvb), "MiWi P2PStar Protocol");
1567 miwi_tree = proto_item_add_subtree(proto_root, ett_miwi_p2pstar);
1569 /*Enter name of protocol to info field*/
1570 col_set_str(pinfo->cinfo, COL_PROTOCOL, "MiWi P2PStar");
1571 /* Call the common dissector. */
1572 dissect_miwi_common(tvb, pinfo, miwi_tree, fcs_len);
1573 return tvb_captured_length(tvb);
1574 }/* dissect_miwi_p2pstar */
1576 /*FUNCTION:------------------------------------------------------
1577 * NAME
1578 * dissect_miwimesh_heur
1579 * DESCRIPTION
1580 * Heuristic interpreter for the Lightweight Mesh.
1581 * PARAMETERS
1582 * tvbuff_t *tvb - pointer to buffer containing raw packet.
1583 * packet_into *pinfo - pointer to packet information fields
1584 * proto_tree *tree - pointer to data tree Wireshark uses to display packet.
1585 * RETURNS
1586 * Boolean value, whether it handles the packet or not.
1587 *---------------------------------------------------------------
1589 static bool
1590 dissect_miwi_p2pstar_heur(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data)
1592 #if 0
1593 uint8_t endpt, srcep, dstep;
1595 /* 1) first byte must have bits 0000xxxx */
1596 if(tvb_get_uint8(tvb, 0) & LWM_FCF_RESERVED)
1597 return (false);
1599 /* The header should be at least long enough for the base header. */
1600 if (tvb_reported_length(tvb) < LWM_HEADER_BASE_LEN)
1601 return (false);
1603 /* The endpoints should either both be zero, or both non-zero. */
1604 endpt = tvb_get_uint8(tvb, 6);
1605 srcep = (endpt & LWM_SRC_ENDP_MASK) >> LWM_SRC_ENDP_OFFSET;
1606 dstep = (endpt & LWM_DST_ENDP_MASK) >> LWM_DST_ENDP_OFFSET;
1607 if ((srcep == 0) && (dstep != 0))
1608 return (false);
1609 if ((srcep != 0) && (dstep == 0))
1610 return (false);
1611 #endif
1612 dissect_miwi_p2pstar(tvb, pinfo, tree, data);
1613 return (true);
1614 } /* dissect_lwm_heur */
1616 /*FUNCTION:------------------------------------------------------
1617 * NAME
1618 * proto_register_miwi_p2pstar
1619 * DESCRIPTION
1620 * MiWi P2P Star protocol registration routine.
1621 * PARAMETERS
1622 * none
1623 * RETURNS
1624 * void
1625 *---------------------------------------------------------------
1627 void proto_register_miwi_p2pstar(void)
1630 static hf_register_info hf[] = {
1632 { &hf_miwi_frame_length,
1633 { "Frame Length", "miwi_p2pstar.frame_length", FT_UINT8, BASE_DEC, NULL, 0x0,
1634 "Frame Length as reported from lower layer", HFILL }},
1636 { &hf_miwi_fcf,
1637 { "Frame Control Field", "miwi_p2pstar.fcf", FT_UINT16, BASE_HEX, NULL,
1638 0x0, NULL, HFILL }},
1640 { &hf_miwi_fcf_frame_type,
1641 { "Frame Type", "miwi_p2pstar.type", FT_UINT16, BASE_HEX, VALS(miwi_mac_frame_types),
1642 MIWI_MAC_FCF_FRAME_TYPE, NULL, HFILL }},
1644 { &hf_miwi_fcf_security_enabled,
1645 { "Security Enabled", "miwi_p2pstar.security_enable", FT_BOOLEAN, 16, NULL, MIWI_MAC_FCF_SECURITY_EN,
1646 "Whether security operations are performed at the MAC layer or not.", HFILL }},
1648 { &hf_miwi_fcf_frame_pending,
1649 { "Frame Pending", "miwi_p2pstar.pending", FT_BOOLEAN, 16, NULL, MIWI_MAC_FCF_FRAME_PENDING,
1650 "Indication of additional packets waiting to be transferred from the source device.", HFILL }},
1652 { &hf_miwi_fcf_ack_req,
1653 { "Acknowledge Request", "miwi_p2pstar.ack_request", FT_BOOLEAN, 16, NULL, MIWI_MAC_FCF_ACK_REQUEST,
1654 "Whether the sender of this packet requests acknowledgment or not.", HFILL }},
1656 { &hf_miwi_fcf_panid_comp,
1657 { "PAN ID Compression", "miwi_p2pstar.pan_id_compression", FT_BOOLEAN, 16, NULL, MIWI_MAC_FCF_PANID_COMP,
1658 "Whether this packet contains the PAN ID or not.", HFILL }},
1660 { &hf_miwi_fcf_reserved,
1661 { "Reserved", "miwi_p2pstar.fcf.reserved", FT_UINT16, BASE_HEX, NULL, MIWI_MAC_FCF_RESERVED,
1662 NULL, HFILL }},
1664 { &hf_miwi_seq,
1665 { "Sequence Number", "miwi_p2pstar.seq_no", FT_UINT8, BASE_DEC, NULL, 0x0,
1666 NULL, HFILL }},
1668 { &hf_miwi_fcf_dest_addr_mode,
1669 { "Destination Addressing Mode", "miwi_p2pstar.dst_addr_mode", FT_UINT16, BASE_HEX, VALS(miwi_addr_modes),
1670 MIWI_MAC_FCF_DEST_ADDR_MODE, NULL, HFILL }},
1672 { &hf_miwi_fcf_src_addr_mode,
1673 { "Source Addressing Mode", "miwi_p2pstar.src_addr_mode", FT_UINT16, BASE_HEX, VALS(miwi_addr_modes),
1674 MIWI_MAC_FCF_SRC_ADDR_MODE, NULL, HFILL }},
1676 { &hf_miwi_fcf_frame_version,
1677 { "Frame Version", "miwi_p2pstar.version", FT_UINT16, BASE_DEC, VALS(miwi_frame_versions),
1678 MIWI_MAC_FCF_FRAME_VERSION, NULL, HFILL }},
1680 { &hf_miwi_dst_panid,
1681 { "Destination PAN", "miwi_p2pstar.dst_pan", FT_UINT16, BASE_HEX, NULL, 0x0,
1682 NULL, HFILL }},
1684 { &hf_miwi_short_dst_addr,
1685 { "Destination", "miwi_p2pstar.dst16", FT_UINT16, BASE_HEX, NULL, 0x0,
1686 NULL, HFILL }},
1688 { &hf_miwi_ext_dst_addr,
1689 { "Destination", "miwi_p2pstar.dst64", FT_EUI64, BASE_NONE, NULL, 0x0,
1690 NULL, HFILL }},
1692 { &hf_miwi_src_panid,
1693 { "Source PAN", "miwi_p2pstar.src_pan", FT_UINT16, BASE_HEX, NULL, 0x0,
1694 NULL, HFILL }},
1696 { &hf_miwi_short_src_addr,
1697 { "Source", "miwi_p2pstar.src16", FT_UINT16, BASE_HEX, NULL, 0x0,
1698 NULL, HFILL }},
1700 { &hf_miwi_ext_src_addr,
1701 { "Extended Source", "miwi_p2pstar.src64", FT_EUI64, BASE_NONE, NULL, 0x0,
1702 NULL, HFILL }},
1704 { &hf_miwi_addr16,
1705 { "Address", "miwi_p2pstar.addr16", FT_UINT16, BASE_HEX, NULL, 0x0,
1706 NULL, HFILL }},
1708 { &hf_miwi_addr64,
1709 { "Extended Address", "miwi_p2pstar.addr64", FT_EUI64, BASE_NONE, NULL, 0x0,
1710 NULL, HFILL }},
1712 { &hf_miwi_src64_origin,
1713 { "Origin", "miwi_p2pstar.src64.origin", FT_FRAMENUM, BASE_NONE, NULL, 0x0,
1714 NULL, HFILL }},
1716 #if 0
1717 { &hf_miwi_fcs,
1718 { "FCS", "miwi_p2pstar.fcs", FT_UINT16, BASE_HEX, NULL, 0x0,
1719 NULL, HFILL }},
1721 { &hf_miwi_fcs_ok,
1722 { "FCS Valid", "miwi_p2pstar.fcs_ok", FT_BOOLEAN, BASE_NONE, NULL, 0x0,
1723 NULL, HFILL }},
1724 #endif
1726 { &hf_miwi_cmd_id,
1727 { "Command Identifier", "miwi_p2pstar.cmd", FT_UINT8, BASE_HEX, VALS(miwi_p2pstar_cmd_names), 0x0,
1728 NULL, HFILL }},
1730 { &hf_miwi_cap_info,
1731 { "Capability Information", "miwi_p2pstar.cap_info", FT_UINT8, BASE_HEX, NULL, 0x0,
1732 NULL, HFILL }},
1734 { &hf_miwi_cap_info_rcv_on_idle,
1735 { "Receiver On When Idle", "miwi_p2pstar.recv_on_when_idle", FT_BOOLEAN, 16, NULL, MIWI_CAP_INFO_RCV_ON_IDLE,
1736 NULL, HFILL }},
1738 { &hf_miwi_cap_info_rqst_data_on_wp,
1739 { "Request Data On Wake-up", "miwi_p2pstar.req_data_on_wakeup", FT_BOOLEAN, 16, NULL, MIWI_CAP_INFO_REQ_DATA_ON_WP,
1740 NULL, HFILL }},
1742 { &hf_miwi_cap_info_need_time_sync,
1743 { "Need Time Synchronization", "miwi_p2pstar.need_time_sync", FT_BOOLEAN, 16, NULL, MIWI_CAP_INFO_NEED_TIME_SYNC,
1744 NULL, HFILL }},
1746 { &hf_miwi_cap_info_security_cap,
1747 { "Security Capable", "miwi_p2pstar.security_capable", FT_BOOLEAN, 16, NULL, MIWI_CAP_INFO_SECURITY_CAP,
1748 NULL, HFILL }},
1750 { &hf_miwi_cap_info_reserved,
1751 { "Reserved", "miwi_p2pstar.cap_info.reserved", FT_UINT16, BASE_HEX, NULL, MIWI_CAP_INFO_RESERVED,
1752 NULL, HFILL }},
1754 { &hf_miwi_oper_chan,
1755 { "Connection Request Operating Channel", "miwi_p2pstar.con_req_chan", FT_UINT8, BASE_DEC, NULL, 0x0,
1756 NULL, HFILL }},
1758 { &hf_miwi_conn_res_status,
1759 { "Connection Response Status", "miwi_p2pstar.con_res_status", FT_UINT8, BASE_DEC, NULL, 0x0,
1760 NULL, HFILL }},
1762 { &hf_miwi_current_op_channel,
1763 { "Channel Hop Current Operating Channel", "miwi_p2pstar.hop_op_chan", FT_UINT8, BASE_DEC, NULL, 0x0,
1764 NULL, HFILL }},
1766 { &hf_miwi_dst_channel_to_jump_to,
1767 { "Destination Channel to Jump to", "miwi_p2pstar.chan_jump_to", FT_UINT8, BASE_DEC, NULL, 0x0,
1768 NULL, HFILL }},
1770 { &hf_miwi_conn_rmv_res_status,
1771 { "Connection Removal Response Status", "miwi_p2pstar.con_rmvl_res_status", FT_UINT8, BASE_DEC, NULL, 0x0,
1772 NULL, HFILL }},
1774 { &hf_miwi_fwd_pkt_dst_addr,
1775 { "Forward Packet Command Destination Address", "miwi_p2pstar.fwd_pkt_dst-addr", FT_UINT8, BASE_DEC, NULL, 0x0,
1776 NULL, HFILL }},
1778 { &hf_miwi_conn_tbl_size,
1779 { "Connection Table Size", "miwi_p2pstar.conn_tbl_size", FT_UINT8, BASE_DEC, NULL, 0x0,
1780 NULL, HFILL }},
1784 /* Subtrees */
1785 static int *ett[] = {
1786 &ett_miwi_p2pstar,
1787 &ett_miwi_p2pstar_fcf,
1788 &ett_miwi_p2pstar_cmd_tree,
1789 &ett_miwi_p2pstar_cap_info,
1790 &ett_miwi_fcs,
1793 static ei_register_info ei[] = {
1794 //{ &ei_miwi_empty_payload, { "miwi_p2pstar.empty_payload", PI_MALFORMED, PI_ERROR, "Empty MiWi Payload!", EXPFILL }},
1795 { &ei_miwi_frame_ver, { "miwi_p2pstar.frame_version_error", PI_COMMENTS_GROUP, PI_NOTE, "Source address can not be broadcast address !", EXPFILL }},
1796 { &ei_miwi_dst, { "miwi_p2pstar.dst_addr_error", PI_COMMENTS_GROUP, PI_WARN, "destination address Error", EXPFILL }},
1797 { &ei_miwi_src, { "miwi_p2pstar.src_addr_error", PI_COMMENTS_GROUP, PI_WARN, "Source address Error", EXPFILL }},
1798 { &ei_miwi_invalid_addressing, { "miwi_p2pstar.invalid_addr_error", PI_PROTOCOL, PI_NOTE, "Invalid Address Error", EXPFILL }},
1799 { &ei_miwi_invalid_panid_compression, { "miwi_p2pstar.invalid_panid_comp_error", PI_PROTOCOL, PI_WARN, "Panid compression error", EXPFILL }},
1800 { &ei_miwi_invalid_panid_compression2, { "miwi_p2pstar.invalid_panid_comp2_error", PI_PROTOCOL, PI_WARN, "Panid2 compression error", EXPFILL }},
1801 // { &ei_miwi_fcs, { "miwi_p2pstar.fcs.bad", PI_CHECKSUM, PI_WARN, "Bad FCS", EXPFILL }},
1804 static const enum_val_t fcs_type_vals[] = {
1805 {"16", "CRC -16 BIT", MIWI_P2PSTAR_FCS_16_BIT},
1806 {NULL, NULL, -1}
1809 static build_valid_func miwi_da_build_value[1] = {miwi_da_value};
1810 static decode_as_value_t miwi_da_values = {miwi_da_prompt, 1, miwi_da_build_value};
1811 static decode_as_t miwi_da = {
1812 IEEE802154_PROTOABBREV_WPAN, IEEE802154_PROTOABBREV_WPAN_PANID,
1813 1, 0, &miwi_da_values, NULL, NULL,
1814 decode_as_default_populate_list, decode_as_default_reset, decode_as_default_change,NULL
1817 module_t *miwi_p2pstar_module;
1818 expert_module_t* expert_miwi_p2pstar;
1820 /* Register the protocol name and description */
1821 proto_miwi_p2pstar = proto_register_protocol("MiWi P2P Star (v6.4)", "MiWi_P2PStar", "miwi_p2pstar");
1823 /* Required function calls to register the header fields and subtree used */
1824 proto_register_field_array(proto_miwi_p2pstar, hf, array_length(hf));
1825 proto_register_subtree_array(ett, array_length(ett));
1827 expert_miwi_p2pstar = expert_register_protocol(proto_miwi_p2pstar);
1828 expert_register_field_array(expert_miwi_p2pstar, ei, array_length(ei));
1830 miwi_short_address_type = address_type_dissector_register("AT_IEEE_802_15_4_SHORT", "IEEE 802.15.4 16-bit short address", miwi_short_address_to_str, miwi_short_address_str_len, NULL, NULL, miwi_short_address_len, NULL, NULL);
1832 /* add a user preference to set the 802.15.4 ethertype */
1833 miwi_p2pstar_module = prefs_register_protocol(proto_miwi_p2pstar,
1834 proto_reg_handoff_miwi_p2pstar);
1835 prefs_register_uint_preference(miwi_p2pstar_module, "miwi_ethertype",
1836 "802.15.4 Ethertype (in hex)",
1837 "(Hexadecimal) Ethertype used to indicate IEEE 802.15.4 frame.",
1838 16, &miwi_ethertype);
1839 prefs_register_enum_preference(miwi_p2pstar_module, "fcs_format",
1840 "FCS format",
1841 "The FCS format in the captured payload",
1842 &miwi_fcs_type, fcs_type_vals, false);
1843 prefs_register_bool_preference(miwi_p2pstar_module, "miwi_fcs_ok",
1844 "Dissect only good FCS",
1845 "Dissect payload only if FCS is valid.",
1846 &miwi_fcs_ok);
1847 prefs_register_bool_preference(miwi_p2pstar_module, "miwi_ack_tracking",
1848 "Enable ACK tracking",
1849 "Match frames with ACK request to ACK packets",
1850 &miwi_ack_tracking);
1852 miwi_p2pstar_handle = register_dissector("miwi_p2pstar", dissect_miwi_p2pstar, proto_miwi_p2pstar);
1853 /* Register a Decode-As handler */
1854 register_decode_as(&miwi_da);
1855 }/* proto_register_miwi_p2pstar */
1857 /*FUNCTION:------------------------------------------------------
1858 * NAME
1859 * proto_reg_handoff_miwi_p2pstar
1860 * DESCRIPTION
1861 * Registers the miwi_p2pstar dissector with Wireshark.
1862 * Will be called during Wireshark startup.
1863 * PARAMETERS
1864 * none
1865 * RETURNS
1866 * void
1867 *---------------------------------------------------------------
1869 void proto_reg_handoff_miwi_p2pstar(void)
1871 #if 0
1872 static bool prefs_initialized = false;
1873 static unsigned int old_miwi_ethertype;
1875 if(!prefs_initialized){
1876 dissector_add_uint("wtap_encap", WTAP_ENCAP_IEEE802_15_4, miwi_p2pstar_handle);
1878 prefs_initialized = true;
1879 } else{
1880 dissector_delete_uint("ethertype", old_miwi_ethertype, miwi_p2pstar_handle);
1883 old_miwi_ethertype = miwi_ethertype;
1885 /* Register dissector handles. */
1886 dissector_add_uint("ethertype", miwi_ethertype, miwi_p2pstar_handle);
1887 #endif
1888 /* Register our dissector with IEEE 802.15.4 */
1889 dissector_add_for_decode_as(IEEE802154_PROTOABBREV_WPAN_PANID, miwi_p2pstar_handle);
1890 heur_dissector_add(IEEE802154_PROTOABBREV_WPAN, dissect_miwi_p2pstar_heur, "Miwi P2PStar over IEEE 802.15.4", "miwip2pstar", proto_miwi_p2pstar, HEURISTIC_DISABLE);
1891 }/* proto_reg_handoff_miwi_p2pstar */
1894 * Editor modelines
1896 * Local Variables:
1897 * c-basic-offset: 4
1898 * tab-width: 8
1899 * indent-tabs-mode: nil
1900 * End:
1902 * ex: set shiftwidth=4 tabstop=8 expandtab:
1903 * :indentSize=4:tabSize=8:noTabs=true: