/src/wireshark/epan/dissectors/packet-zbee-nwk-gp.c
Line | Count | Source |
1 | | /* packet-zbee-nwk-gp.c |
2 | | * Dissector routines for the ZigBee Green Power profile (GP) |
3 | | * Copyright 2013 DSR Corporation, http://dsr-wireless.com/ |
4 | | * |
5 | | * Wireshark - Network traffic analyzer |
6 | | * By Gerald Combs <gerald@wireshark.org> |
7 | | * Copyright 1998 Gerald Combs |
8 | | * |
9 | | * Used Owen Kirby's packet-zbee-aps module as a template. Based |
10 | | * on ZigBee Cluster Library Specification document 075123r02ZB |
11 | | * |
12 | | * SPDX-License-Identifier: GPL-2.0-or-later |
13 | | */ |
14 | | |
15 | | /* Include files. */ |
16 | | #include "config.h" |
17 | | |
18 | | #include <epan/packet.h> |
19 | | #include <epan/exceptions.h> |
20 | | #include <epan/expert.h> |
21 | | #include <epan/prefs.h> |
22 | | #include <epan/uat.h> |
23 | | #include <wsutil/bits_ctz.h> |
24 | | #include <wsutil/pint.h> |
25 | | #include "packet-zbee.h" |
26 | | #include "packet-zbee-nwk.h" |
27 | | #include "packet-zbee-security.h" |
28 | | #include "packet-zbee-aps.h" |
29 | | #include "packet-zbee-zcl.h" |
30 | | |
31 | | void proto_register_zbee_nwk_gp(void); |
32 | | void proto_reg_handoff_zbee_nwk_gp(void); |
33 | | |
34 | | /**************************/ |
35 | | /* Defines. */ |
36 | | /**************************/ |
37 | | |
38 | | /* ZigBee NWK GP FCF frame types. */ |
39 | 3.06k | #define ZBEE_NWK_GP_FCF_DATA 0x00 |
40 | 1.46k | #define ZBEE_NWK_GP_FCF_MAINTENANCE 0x01 |
41 | | |
42 | | /* ZigBee NWK GP FCF fields. */ |
43 | 15 | #define ZBEE_NWK_GP_FCF_AUTO_COMMISSIONING 0x40 |
44 | 801 | #define ZBEE_NWK_GP_FCF_CONTROL_EXTENSION 0x80 |
45 | 801 | #define ZBEE_NWK_GP_FCF_FRAME_TYPE 0x03 |
46 | 1.38k | #define ZBEE_NWK_GP_FCF_VERSION 0x3C |
47 | | |
48 | | /* Extended NWK Frame Control field. */ |
49 | 758 | #define ZBEE_NWK_GP_FCF_EXT_APP_ID 0x07 /* 0 - 2 b. */ |
50 | 758 | #define ZBEE_NWK_GP_FCF_EXT_SECURITY_LEVEL 0x18 /* 3 - 4 b. */ |
51 | 15 | #define ZBEE_NWK_GP_FCF_EXT_SECURITY_KEY 0x20 /* 5 b. */ |
52 | 15 | #define ZBEE_NWK_GP_FCF_EXT_RX_AFTER_TX 0x40 /* 6 b. */ |
53 | 758 | #define ZBEE_NWK_GP_FCF_EXT_DIRECTION 0x80 /* 7 b. */ |
54 | | |
55 | | /* Definitions for application IDs. */ |
56 | 2.96k | #define ZBEE_NWK_GP_APP_ID_DEFAULT 0x00 |
57 | 651 | #define ZBEE_NWK_GP_APP_ID_LPED 0x01 |
58 | 2.26k | #define ZBEE_NWK_GP_APP_ID_ZGP 0x02 |
59 | | |
60 | | /* Definitions for GP directions. */ |
61 | | #define ZBEE_NWK_GP_FC_EXT_DIRECTION_DEFAULT 0x00 |
62 | 0 | #define ZBEE_NWK_GP_FC_EXT_DIRECTION_FROM_ZGPD 0x00 |
63 | | #define ZBEE_NWK_GP_FC_EXT_DIRECTION_FROM_ZGPP 0x01 |
64 | | |
65 | | /* Definitions for ZGPD Source IDs. */ |
66 | | #define ZBEE_NWK_GP_ZGPD_SRCID_ALL 0xFFFFFFFF |
67 | | #define ZBEE_NWK_GP_ZGPD_SRCID_UNKNOWN 0x00000000 |
68 | | |
69 | | /* Security level values. */ |
70 | | #define ZBEE_NWK_GP_SECURITY_LEVEL_NO 0x00 |
71 | 656 | #define ZBEE_NWK_GP_SECURITY_LEVEL_1LSB 0x01 |
72 | 644 | #define ZBEE_NWK_GP_SECURITY_LEVEL_FULL 0x02 |
73 | 1.88k | #define ZBEE_NWK_GP_SECURITY_LEVEL_FULLENCR 0x03 |
74 | | |
75 | | /* GP Security key types. */ |
76 | | #define ZBEE_NWK_GP_SECURITY_KEY_TYPE_NO_KEY 0x00 |
77 | | #define ZBEE_NWK_GP_SECURITY_KEY_TYPE_ZB_NWK_KEY 0x01 |
78 | | #define ZBEE_NWK_GP_SECURITY_KEY_TYPE_GPD_GROUP_KEY 0x02 |
79 | | #define ZBEE_NWK_GP_SECURITY_KEY_TYPE_NWK_KEY_DERIVED_GPD_KEY_GROUP_KEY 0x03 |
80 | | #define ZBEE_NWK_GP_SECURITY_KEY_TYPE_PRECONFIGURED_INDIVIDUAL_GPD_KEY 0x04 |
81 | | #define ZBEE_NWK_GP_SECURITY_KEY_TYPE_DERIVED_INDIVIDUAL_GPD_KEY 0x07 |
82 | | |
83 | | typedef struct { |
84 | | /* FCF Data. */ |
85 | | uint8_t frame_type; |
86 | | bool nwk_frame_control_extension; |
87 | | |
88 | | /* Ext FCF Data. */ |
89 | | uint8_t application_id; |
90 | | uint8_t security_level; |
91 | | uint8_t direction; |
92 | | |
93 | | /* Src ID. */ |
94 | | uint32_t source_id; |
95 | | |
96 | | /* GPD Endpoint */ |
97 | | uint8_t endpoint; |
98 | | |
99 | | /* Security Frame Counter. */ |
100 | | uint32_t security_frame_counter; |
101 | | |
102 | | /* MIC. */ |
103 | | uint8_t mic_size; |
104 | | uint32_t mic; |
105 | | |
106 | | /* Application Payload. */ |
107 | | uint8_t payload_len; |
108 | | |
109 | | /* Source IEEE address from parent */ |
110 | | uint64_t ieee_packet_src64; |
111 | | } zbee_nwk_green_power_packet; |
112 | | |
113 | | /* Definitions for GP Commissioning command opt field (bitmask). */ |
114 | 15 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_MAC_SEQ 0x01 |
115 | 15 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_RX_ON_CAP 0x02 |
116 | 25 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_APPLICATION_INFO 0x04 |
117 | 15 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_PAN_ID_REQ 0x10 |
118 | 15 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_GP_SEC_KEY_REQ 0x20 |
119 | 15 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_FIXED_LOCATION 0x40 |
120 | 25 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_EXT_OPTIONS 0x80 |
121 | | |
122 | | /* Definitions for GP Commissioning command ext_opt field (bitmask). */ |
123 | 15 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_SEC_LEVEL_CAP 0x03 |
124 | 15 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_KEY_TYPE 0x1C |
125 | 18 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_GPD_KEY_PRESENT 0x20 |
126 | 17 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_GPD_KEY_ENCR 0x40 |
127 | 18 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_OUT_COUNTER 0x80 |
128 | | |
129 | | /* Definitions for GP Commissioning command application information field (bitmask). */ |
130 | 23 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_APPLI_INFO_MIP 0x01 |
131 | 23 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_APPLI_INFO_MMIP 0x02 |
132 | 23 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_APPLI_INFO_GCLP 0x04 |
133 | 23 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_APPLI_INFO_CRP 0x08 |
134 | | |
135 | | /* Definitions for GP Commissioning command Number of server ClusterIDs (bitmask) */ |
136 | 27 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_CLID_LIST_LEN_SRV 0x0F |
137 | 27 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_CLID_LIST_LEN_CLI 0xF0 |
138 | | |
139 | | /* Definitions for GP Decommissioning command opt field (bitmask). */ |
140 | 18 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_PAN_ID_PRESENT 0x01 |
141 | 20 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_SEC_KEY_PRESENT 0x02 |
142 | 22 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_KEY_ENCR 0x04 |
143 | 21 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_SEC_LEVEL 0x18 |
144 | 15 | #define ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_KEY_TYPE 0xE0 |
145 | | |
146 | | /* Definition for GP read attributes command opt field (bitmask). */ |
147 | 15 | #define ZBEE_NWK_GP_CMD_READ_ATTRIBUTE_OPT_MULTI_RECORD 0x01 |
148 | 565 | #define ZBEE_NWK_GP_CMD_READ_ATTRIBUTE_OPT_MAN_FIELD_PRESENT 0x02 |
149 | | |
150 | 15 | #define ZBEE_NWK_GP_CMD_ZCL_TUNNEL_OPT_FRAME_TYPE 0x03 |
151 | 16 | #define ZBEE_NWK_GP_CMD_ZCL_TUNNEL_OPT_MAN_FIELD_PRESENT 0x04 |
152 | 15 | #define ZBEE_NWK_GP_CMD_ZCL_TUNNEL_OPT_DIRECTION 0x08 |
153 | | |
154 | | /* Definitions for GP Channel Request command. */ |
155 | 15 | #define ZBEE_NWK_GP_CMD_CHANNEL_REQUEST_1ST 0x0F |
156 | 15 | #define ZBEE_NWK_GP_CMD_CHANNEL_REQUEST_2ND 0xF0 |
157 | | |
158 | | /* GP Channel Configuration command. */ |
159 | 15 | #define ZBEE_NWK_GP_CMD_CHANNEL_CONFIGURATION_OPERATION_CH 0x0F |
160 | | |
161 | | /* GP GENERIC IDS. */ |
162 | | #define GPD_DEVICE_ID_GENERIC_GP_SIMPLE_GENERIC_1STATE_SWITCH 0x00 |
163 | | #define GPD_DEVICE_ID_GENERIC_GP_SIMPLE_GENERIC_2STATE_SWITCH 0x01 |
164 | | #define GPD_DEVICE_ID_GENERIC_GP_ON_OFF_SWITCH 0x02 |
165 | | #define GPD_DEVICE_ID_GENERIC_GP_LEVEL_CONTROL_SWITCH 0x03 |
166 | | #define GPD_DEVICE_ID_GENERIC_GP_SIMPLE_SENSOR 0x04 |
167 | | #define GPD_DEVICE_ID_GENERIC_GP_ADVANCED_GENERIC_1STATE_SWITCH 0x05 |
168 | | #define GPD_DEVICE_ID_GENERIC_GP_ADVANCED_GENERIC_2STATE_SWITCH 0x06 |
169 | | |
170 | | /* GP LIGHTING IDS. */ |
171 | | #define GPD_DEVICE_ID_LIGHTING_GP_COLOR_DIMMER_SWITCH 0x10 |
172 | | #define GPD_DEVICE_ID_LIGHTING_GP_LIGHT_SENSOR 0x11 |
173 | | #define GPD_DEVICE_ID_LIGHTING_GP_OCCUPANCY_SENSOR 0x12 |
174 | | |
175 | | /* GP CLOSURES IDS. */ |
176 | | #define GPD_DEVICE_ID_CLOSURES_GP_DOOR_LOCK_CONTROLLER 0x20 |
177 | | |
178 | | /* HVAC IDS. */ |
179 | | #define GPD_DEVICE_ID_HVAC_GP_TEMPERATURE_SENSOR 0x30 |
180 | | #define GPD_DEVICE_ID_HVAC_GP_PRESSURE_SENSOR 0x31 |
181 | | #define GPD_DEVICE_ID_HVAC_GP_FLOW_SENSOR 0x32 |
182 | | #define GPD_DEVICE_ID_HVAC_GP_INDOOR_ENVIRONMENT_SENSOR 0x33 |
183 | | |
184 | | /* Manufacturer specific device. */ |
185 | | #define GPD_DEVICE_ID_MANUFACTURER_SPECIFIC 0xFE |
186 | | |
187 | | /* GPD manufacturers. */ |
188 | 0 | #define ZBEE_NWK_GP_MANUF_ID_GREENPEAK 0x10D0 |
189 | | |
190 | | /* GPD devices by GreenPeak. */ |
191 | | #define ZBEE_NWK_GP_MANUF_GREENPEAK_IZDS 0x0000 |
192 | | #define ZBEE_NWK_GP_MANUF_GREENPEAK_IZDWS 0x0001 |
193 | | #define ZBEE_NWK_GP_MANUF_GREENPEAK_IZLS 0x0002 |
194 | | #define ZBEE_NWK_GP_MANUF_GREENPEAK_IZRHS 0x0003 |
195 | | |
196 | | /*********************/ |
197 | | /* Global variables. */ |
198 | | /*********************/ |
199 | | |
200 | | /* GP proto handle. */ |
201 | | static int proto_zbee_nwk_gp; |
202 | | |
203 | | /* GP NWK FC. */ |
204 | | static int hf_zbee_nwk_gp_auto_commissioning; |
205 | | static int hf_zbee_nwk_gp_fc_ext; |
206 | | static int hf_zbee_nwk_gp_fcf; |
207 | | static int hf_zbee_nwk_gp_frame_type; |
208 | | static int hf_zbee_nwk_gp_proto_version; |
209 | | |
210 | | /* GP NWK FC extension. */ |
211 | | static int hf_zbee_nwk_gp_fc_ext_field; |
212 | | static int hf_zbee_nwk_gp_fc_ext_app_id; |
213 | | static int hf_zbee_nwk_gp_fc_ext_direction; |
214 | | static int hf_zbee_nwk_gp_fc_ext_rx_after_tx; |
215 | | static int hf_zbee_nwk_gp_fc_ext_sec_key; |
216 | | static int hf_zbee_nwk_gp_fc_ext_sec_level; |
217 | | |
218 | | /* ZGPD Src ID. */ |
219 | | static int hf_zbee_nwk_gp_zgpd_src_id; |
220 | | |
221 | | /* ZGPD Endpoint */ |
222 | | static int hf_zbee_nwk_gp_zgpd_endpoint; |
223 | | |
224 | | /* Security frame counter. */ |
225 | | static int hf_zbee_nwk_gp_security_frame_counter; |
226 | | |
227 | | /* Security MIC. */ |
228 | | static int hf_zbee_nwk_gp_security_mic_2b; |
229 | | static int hf_zbee_nwk_gp_security_mic_4b; |
230 | | |
231 | | /* Payload subframe. */ |
232 | | static int hf_zbee_nwk_gp_command_id; |
233 | | |
234 | | /* Commissioning. */ |
235 | | static int hf_zbee_nwk_gp_cmd_comm_device_id; |
236 | | static int hf_zbee_nwk_gp_cmd_comm_ext_opt; |
237 | | static int hf_zbee_nwk_gp_cmd_comm_ext_opt_gpd_key_encr; |
238 | | static int hf_zbee_nwk_gp_cmd_comm_ext_opt_gpd_key_present; |
239 | | static int hf_zbee_nwk_gp_cmd_comm_ext_opt_key_type; |
240 | | static int hf_zbee_nwk_gp_cmd_comm_ext_opt_outgoing_counter; |
241 | | static int hf_zbee_nwk_gp_cmd_comm_ext_opt_sec_level_cap; |
242 | | static int hf_zbee_nwk_gp_cmd_comm_security_key; |
243 | | static int hf_zbee_nwk_gp_cmd_comm_gpd_sec_key_mic; |
244 | | static int hf_zbee_nwk_gp_cmd_comm_opt_ext_opt; |
245 | | static int hf_zbee_nwk_gp_cmd_comm_opt; |
246 | | static int hf_zbee_nwk_gp_cmd_comm_opt_fixed_location; |
247 | | static int hf_zbee_nwk_gp_cmd_comm_opt_mac_sec_num_cap; |
248 | | static int hf_zbee_nwk_gp_cmd_comm_opt_appli_info_present; |
249 | | static int hf_zbee_nwk_gp_cmd_comm_opt_panid_req; |
250 | | static int hf_zbee_nwk_gp_cmd_comm_opt_rx_on_cap; |
251 | | static int hf_zbee_nwk_gp_cmd_comm_opt_sec_key_req; |
252 | | static int hf_zbee_nwk_gp_cmd_comm_outgoing_counter; |
253 | | static int hf_zbee_nwk_gp_cmd_comm_manufacturer_greenpeak_dev_id; |
254 | | static int hf_zbee_nwk_gp_cmd_comm_manufacturer_dev_id; |
255 | | static int hf_zbee_nwk_gp_cmd_comm_manufacturer_id; |
256 | | static int hf_zbee_nwk_gp_cmd_comm_appli_info; |
257 | | static int hf_zbee_nwk_gp_cmd_comm_appli_info_crp; |
258 | | static int hf_zbee_nwk_gp_cmd_comm_appli_info_gclp; |
259 | | static int hf_zbee_nwk_gp_cmd_comm_appli_info_mip; |
260 | | static int hf_zbee_nwk_gp_cmd_comm_appli_info_mmip; |
261 | | static int hf_zbee_nwk_gp_cmd_comm_gpd_cmd_num; |
262 | | static int hf_zbee_nwk_gp_cmd_comm_gpd_cmd_id_list; |
263 | | static int hf_zbee_nwk_gp_cmd_comm_length_of_clid_list; |
264 | | static int hf_zbee_nwk_gp_cmd_comm_length_of_clid_list_server; |
265 | | static int hf_zbee_nwk_gp_cmd_comm_length_of_clid_list_client; |
266 | | static int hf_zbee_nwk_cmd_comm_clid_list_server; |
267 | | static int hf_zbee_nwk_cmd_comm_clid_list_client; |
268 | | static int hf_zbee_nwk_cmd_comm_cluster_id; |
269 | | |
270 | | /* Commissioning reply. */ |
271 | | static int hf_zbee_nwk_gp_cmd_comm_rep_opt; |
272 | | static int hf_zbee_nwk_gp_cmd_comm_rep_opt_key_encr; |
273 | | static int hf_zbee_nwk_gp_cmd_comm_rep_opt_panid_present; |
274 | | static int hf_zbee_nwk_gp_cmd_comm_rep_opt_sec_key_present; |
275 | | static int hf_zbee_nwk_gp_cmd_comm_rep_opt_sec_level; |
276 | | static int hf_zbee_nwk_gp_cmd_comm_rep_opt_sec_type; |
277 | | static int hf_zbee_nwk_gp_cmd_comm_rep_pan_id; |
278 | | static int hf_zbee_nwk_gp_cmd_comm_rep_frame_counter; |
279 | | |
280 | | /* Read attribute and read attribute response. */ |
281 | | static int hf_zbee_nwk_gp_cmd_read_att_opt_multi_rec; |
282 | | static int hf_zbee_nwk_gp_cmd_read_att_opt_man_field_present; |
283 | | static int hf_zbee_nwk_gp_cmd_read_att_opt; |
284 | | static int hf_zbee_nwk_gp_cmd_read_att_record_len; |
285 | | |
286 | | /* ZCL Tunnel */ |
287 | | static int hf_zbee_nwk_gp_cmd_zcl_tunnel_opt_frame_type; |
288 | | static int hf_zbee_nwk_gp_cmd_zcl_tunnel_opt_man_field_present; |
289 | | static int hf_zbee_nwk_gp_cmd_zcl_tunnel_opt_direction; |
290 | | static int hf_zbee_nwk_gp_cmd_zcl_tunnel_opt; |
291 | | static int hf_zbee_nwk_gp_cmd_zcl_tunnel_command_id; |
292 | | static int hf_zbee_nwk_gp_cmd_zcl_tunnel_payload_len; |
293 | | |
294 | | /* Common to commands returning data */ |
295 | | static int hf_zbee_nwk_gp_zcl_attr_status; |
296 | | static int hf_zbee_nwk_gp_zcl_attr_data_type; |
297 | | static int hf_zbee_nwk_gp_zcl_attr_cluster_id; |
298 | | |
299 | | /* Common to all manufacturer specific commands */ |
300 | | static int hf_zbee_zcl_gp_cmd_ms_manufacturer_code; |
301 | | |
302 | | /* Channel request. */ |
303 | | static int hf_zbee_nwk_gp_cmd_channel_request_toggling_behaviour; |
304 | | static int hf_zbee_nwk_gp_cmd_channel_request_toggling_behaviour_1st; |
305 | | static int hf_zbee_nwk_gp_cmd_channel_request_toggling_behaviour_2nd; |
306 | | |
307 | | /* Channel Configuration command. */ |
308 | | static int hf_zbee_nwk_gp_cmd_operational_channel; |
309 | | static int hf_zbee_nwk_gp_cmd_channel_configuration; |
310 | | |
311 | | /* Move Color command. */ |
312 | | static int hf_zbee_nwk_gp_cmd_move_color_ratex; |
313 | | static int hf_zbee_nwk_gp_cmd_move_color_ratey; |
314 | | |
315 | | /* Move Up/Down command. */ |
316 | | static int hf_zbee_nwk_gp_cmd_move_up_down_rate; |
317 | | |
318 | | /* Step Color command. */ |
319 | | static int hf_zbee_nwk_gp_cmd_step_color_stepx; |
320 | | static int hf_zbee_nwk_gp_cmd_step_color_stepy; |
321 | | static int hf_zbee_nwk_gp_cmd_step_color_transition_time; |
322 | | |
323 | | /* Step Up/Down command. */ |
324 | | static int hf_zbee_nwk_gp_cmd_step_up_down_step_size; |
325 | | static int hf_zbee_nwk_gp_cmd_step_up_down_transition_time; |
326 | | |
327 | | static expert_field ei_zbee_nwk_gp_no_payload; |
328 | | static expert_field ei_zbee_nwk_gp_inval_residual_data; |
329 | | static expert_field ei_zbee_nwk_gp_com_rep_no_out_cnt; |
330 | | |
331 | | /* Proto tree elements. */ |
332 | | static int ett_zbee_nwk; |
333 | | static int ett_zbee_nwk_cmd; |
334 | | static int ett_zbee_nwk_cmd_cinfo; |
335 | | static int ett_zbee_nwk_cmd_appli_info; |
336 | | static int ett_zbee_nwk_cmd_options; |
337 | | static int ett_zbee_nwk_fcf; |
338 | | static int ett_zbee_nwk_fcf_ext; |
339 | | static int ett_zbee_nwk_clu_rec; |
340 | | static int ett_zbee_nwk_att_rec; |
341 | | static int ett_zbee_nwk_cmd_comm_gpd_cmd_id_list; |
342 | | static int ett_zbee_nwk_cmd_comm_length_of_clid_list; |
343 | | static int ett_zbee_nwk_cmd_comm_clid_list_server; |
344 | | static int ett_zbee_nwk_cmd_comm_clid_list_client; |
345 | | |
346 | | /* Common. */ |
347 | | static GSList *zbee_gp_keyring; |
348 | | static unsigned num_uat_key_records; |
349 | | |
350 | | typedef struct { |
351 | | char *string; |
352 | | uint8_t byte_order; |
353 | | char *label; |
354 | | uint8_t key[ZBEE_SEC_CONST_KEYSIZE]; |
355 | | } uat_key_record_t; |
356 | | |
357 | | static const uint8_t empty_key[ZBEE_SEC_CONST_KEYSIZE] = { |
358 | | 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
359 | | 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 |
360 | | }; |
361 | | static uat_key_record_t *gp_uat_key_records; |
362 | | static uat_t *zbee_gp_sec_key_table_uat; |
363 | | |
364 | | /* UAT. */ |
365 | 0 | UAT_CSTRING_CB_DEF(gp_uat_key_records, string, uat_key_record_t) |
366 | 0 | UAT_VS_DEF(gp_uat_key_records, byte_order, uat_key_record_t, uint8_t, 0, "Normal") Unexecuted instantiation: packet-zbee-nwk-gp.c:gp_uat_key_records_byte_order_set_cb Unexecuted instantiation: packet-zbee-nwk-gp.c:gp_uat_key_records_byte_order_tostr_cb |
367 | 0 | UAT_CSTRING_CB_DEF(gp_uat_key_records, label, uat_key_record_t) |
368 | | |
369 | | /****************/ |
370 | | /* Field names. */ |
371 | | /****************/ |
372 | | |
373 | | /* Byte order. */ |
374 | | static const value_string byte_order_vals[] = { |
375 | | { 0, "Normal"}, |
376 | | { 1, "Reverse"}, |
377 | | |
378 | | { 0, NULL } |
379 | | }; |
380 | | |
381 | | /* Application ID names. */ |
382 | | static const value_string zbee_nwk_gp_app_id_names[] = { |
383 | | { ZBEE_NWK_GP_APP_ID_LPED, "LPED" }, |
384 | | { ZBEE_NWK_GP_APP_ID_ZGP, "ZGP" }, |
385 | | |
386 | | { 0, NULL } |
387 | | }; |
388 | | |
389 | | /* Green Power commands. */ |
390 | | |
391 | | /* Abbreviations: |
392 | | * GPDF commands sent: |
393 | | * From GPD w/o payload: "F " |
394 | | * From GPD w payload: "FP" |
395 | | * To GPD: "T " |
396 | | */ |
397 | | |
398 | | #define zbee_nwk_gp_cmd_names_VALUE_STRING_LIST(XXX) \ |
399 | | XXX( /*F */ ZB_GP_CMD_ID_IDENTIFY , 0x00, "Identify" ) \ |
400 | | XXX( /*F */ ZB_GP_CMD_ID_RECALL_SCENE0 , 0x10, "Recall Scene 0" ) \ |
401 | | XXX( /*F */ ZB_GP_CMD_ID_RECALL_SCENE1 , 0x11, "Recall Scene 1" ) \ |
402 | | XXX( /*F */ ZB_GP_CMD_ID_RECALL_SCENE2 , 0x12, "Recall Scene 2" ) \ |
403 | | XXX( /*F */ ZB_GP_CMD_ID_RECALL_SCENE3 , 0x13, "Recall Scene 3" ) \ |
404 | | XXX( /*F */ ZB_GP_CMD_ID_RECALL_SCENE4 , 0x14, "Recall Scene 4" ) \ |
405 | | XXX( /*F */ ZB_GP_CMD_ID_RECALL_SCENE5 , 0x15, "Recall Scene 5" ) \ |
406 | | XXX( /*F */ ZB_GP_CMD_ID_RECALL_SCENE6 , 0x16, "Recall Scene 6" ) \ |
407 | | XXX( /*F */ ZB_GP_CMD_ID_RECALL_SCENE7 , 0x17, "Recall Scene 7" ) \ |
408 | | XXX( /*F */ ZB_GP_CMD_ID_STORE_SCENE0 , 0x18, "Store Scene 0" ) \ |
409 | | XXX( /*F */ ZB_GP_CMD_ID_STORE_SCENE1 , 0x19, "Store Scene 1" ) \ |
410 | | XXX( /*F */ ZB_GP_CMD_ID_STORE_SCENE2 , 0x1A, "Store Scene 2" ) \ |
411 | | XXX( /*F */ ZB_GP_CMD_ID_STORE_SCENE3 , 0x1B, "Store Scene 3" ) \ |
412 | | XXX( /*F */ ZB_GP_CMD_ID_STORE_SCENE4 , 0x1C, "Store Scene 4" ) \ |
413 | | XXX( /*F */ ZB_GP_CMD_ID_STORE_SCENE5 , 0x1D, "Store Scene 5" ) \ |
414 | | XXX( /*F */ ZB_GP_CMD_ID_STORE_SCENE6 , 0x1E, "Store Scene 6" ) \ |
415 | | XXX( /*F */ ZB_GP_CMD_ID_STORE_SCENE7 , 0x1F, "Store Scene 7" ) \ |
416 | | XXX( /*F */ ZB_GP_CMD_ID_OFF , 0x20, "Off" ) \ |
417 | | XXX( /*F */ ZB_GP_CMD_ID_ON , 0x21, "On" ) \ |
418 | | XXX( /*F */ ZB_GP_CMD_ID_TOGGLE , 0x22, "Toggle" ) \ |
419 | | XXX( /*F */ ZB_GP_CMD_ID_RELEASE , 0x23, "Release" ) \ |
420 | | XXX( /*FP*/ ZB_GP_CMD_ID_MOVE_UP , 0x30, "Move Up" ) \ |
421 | | XXX( /*FP*/ ZB_GP_CMD_ID_MOVE_DOWN , 0x31, "Move Down" ) \ |
422 | | XXX( /*FP*/ ZB_GP_CMD_ID_STEP_UP , 0x32, "Step Up" ) \ |
423 | | XXX( /*FP*/ ZB_GP_CMD_ID_STEP_DOWN , 0x33, "Step Down" ) \ |
424 | | XXX( /*F */ ZB_GP_CMD_ID_LEVEL_CONTROL_STOP , 0x34, "Level Control/Stop" ) \ |
425 | | XXX( /*FP*/ ZB_GP_CMD_ID_MOVE_UP_WITH_ON_OFF , 0x35, "Move Up (with On/Off)" ) \ |
426 | | XXX( /*FP*/ ZB_GP_CMD_ID_MOVE_DOWN_WITH_ON_OFF , 0x36, "Move Down (with On/Off)" ) \ |
427 | | XXX( /*FP*/ ZB_GP_CMD_ID_STEP_UP_WITH_ON_OFF , 0x37, "Step Up (with On/Off)" ) \ |
428 | | XXX( /*FP*/ ZB_GP_CMD_ID_STEP_DOWN_WITH_ON_OFF , 0x38, "Step Down (with On/Off)" ) \ |
429 | | XXX( /*F */ ZB_GP_CMD_ID_MOVE_HUE_STOP , 0x40, "Move Hue Stop" ) \ |
430 | | XXX( /*FP*/ ZB_GP_CMD_ID_MOVE_HUE_UP , 0x41, "Move Hue Up" ) \ |
431 | | XXX( /*FP*/ ZB_GP_CMD_ID_MOVE_HUE_DOWN , 0x42, "Move Hue Down" ) \ |
432 | | XXX( /*FP*/ ZB_GP_CMD_ID_STEP_HUE_UP , 0x43, "Step Hue Up" ) \ |
433 | | XXX( /*FP*/ ZB_GP_CMD_ID_STEP_HUW_DOWN , 0x44, "Step Hue Down" ) \ |
434 | | XXX( /*F */ ZB_GP_CMD_ID_MOVE_SATURATION_STOP , 0x45, "Move Saturation Stop" ) \ |
435 | | XXX( /*FP*/ ZB_GP_CMD_ID_MOVE_SATURATION_UP , 0x46, "Move Saturation Up" ) \ |
436 | | XXX( /*FP*/ ZB_GP_CMD_ID_MOVE_SATURATION_DOWN , 0x47, "Move Saturation Down" ) \ |
437 | | XXX( /*FP*/ ZB_GP_CMD_ID_STEP_SATURATION_UP , 0x48, "Step Saturation Up" ) \ |
438 | | XXX( /*FP*/ ZB_GP_CMD_ID_STEP_SATURATION_DOWN , 0x49, "Step Saturation Down" ) \ |
439 | | XXX( /*FP*/ ZB_GP_CMD_ID_MOVE_COLOR , 0x4A, "Move Color" ) \ |
440 | | XXX( /*FP*/ ZB_GP_CMD_ID_STEP_COLOR , 0x4B, "Step Color" ) \ |
441 | | XXX( /*F */ ZB_GP_CMD_ID_LOCK_DOOR , 0x50, "Lock Door" ) \ |
442 | | XXX( /*F */ ZB_GP_CMD_ID_UNLOCK_DOOR , 0x51, "Unlock Door" ) \ |
443 | | XXX( /*F */ ZB_GP_CMD_ID_PRESS11 , 0x60, "Press 1 of 1" ) \ |
444 | | XXX( /*F */ ZB_GP_CMD_ID_RELEASE11 , 0x61, "Release 1 of 1" ) \ |
445 | | XXX( /*F */ ZB_GP_CMD_ID_PRESS12 , 0x62, "Press 1 of 2" ) \ |
446 | | XXX( /*F */ ZB_GP_CMD_ID_RELEASE12 , 0x63, "Release 1 of 2" ) \ |
447 | | XXX( /*F */ ZB_GP_CMD_ID_PRESS22 , 0x64, "Press 2 of 2" ) \ |
448 | | XXX( /*F */ ZB_GP_CMD_ID_RELEASE22 , 0x65, "Release 2 of 2" ) \ |
449 | | XXX( /*F */ ZB_GP_CMD_ID_SHORT_PRESS11 , 0x66, "Short press 1 of 1" ) \ |
450 | | XXX( /*F */ ZB_GP_CMD_ID_SHORT_PRESS12 , 0x67, "Short press 1 of 2" ) \ |
451 | | XXX( /*F */ ZB_GP_CMD_ID_SHORT_PRESS22 , 0x68, "Short press 2 of 2" ) \ |
452 | | XXX( /*FP*/ ZB_GP_CMD_ID_ATTRIBUTE_REPORTING , 0xA0, "Attribute reporting" ) \ |
453 | | XXX( /*FP*/ ZB_GP_CMD_ID_MANUFACTURE_SPECIFIC_ATTR_REPORTING , 0xA1, "Manufacturer-specific attribute reporting" ) \ |
454 | | XXX( /*FP*/ ZB_GP_CMD_ID_MULTI_CLUSTER_REPORTING , 0xA2, "Multi-cluster reporting" ) \ |
455 | | XXX( /*FP*/ ZB_GP_CMD_ID_MANUFACTURER_SPECIFIC_MCLUSTER_REPORTING , 0xA3, "Manufacturer-specific multi-cluster reporting" ) \ |
456 | | XXX( /*FP*/ ZB_GP_CMD_ID_REQUEST_ATTRIBUTES , 0xA4, "Request Attributes" ) \ |
457 | | XXX( /*FP*/ ZB_GP_CMD_ID_READ_ATTRIBUTES_RESPONSE , 0xA5, "Read Attributes Response" ) \ |
458 | | XXX( /*FP*/ ZB_GP_CMD_ID_ZCL_TUNNELING , 0xA6, "ZCL Tunneling" ) \ |
459 | | XXX( /*FP*/ ZB_GP_CMD_ID_ANY_SENSOR_COMMAND_A0_A3 , 0xAF, "Any GPD sensor command (0xA0 - 0xA3)" ) \ |
460 | | XXX( /*FP*/ ZB_GP_CMD_ID_COMMISSIONING , 0xE0, "Commissioning" ) \ |
461 | | XXX( /*F */ ZB_GP_CMD_ID_DECOMMISSIONING , 0xE1, "Decommissioning" ) \ |
462 | | XXX( /*F */ ZB_GP_CMD_ID_SUCCESS , 0xE2, "Success" ) \ |
463 | | XXX( /*FP*/ ZB_GP_CMD_ID_CHANNEL_REQUEST , 0xE3, "Channel Request" ) \ |
464 | | XXX( /*T */ ZB_GP_CMD_ID_COMMISSIONING_REPLY , 0xF0, "Commissioning Reply" ) \ |
465 | | XXX( /*T */ ZB_GP_CMD_ID_WRITE_ATTRIBUTES , 0xF1, "Write Attributes" ) \ |
466 | | XXX( /*T */ ZB_GP_CMD_ID_READ_ATTRIBUTES , 0xF2, "Read Attributes" ) \ |
467 | | XXX( /*T */ ZB_GP_CMD_ID_CHANNEL_CONFIGURATION , 0xF3, "Channel Configuration" ) |
468 | | |
469 | | VALUE_STRING_ENUM(zbee_nwk_gp_cmd_names); |
470 | | |
471 | | VALUE_STRING_ARRAY(zbee_nwk_gp_cmd_names); |
472 | | value_string_ext zbee_nwk_gp_cmd_names_ext = VALUE_STRING_EXT_INIT(zbee_nwk_gp_cmd_names); |
473 | | |
474 | | |
475 | | /* Green Power devices. */ |
476 | | const value_string zbee_nwk_gp_device_ids_names[] = { |
477 | | |
478 | | /* GP GENERIC */ |
479 | | { GPD_DEVICE_ID_GENERIC_GP_SIMPLE_GENERIC_1STATE_SWITCH, "Generic: GP Simple Generic 1-state Switch" }, |
480 | | { GPD_DEVICE_ID_GENERIC_GP_SIMPLE_GENERIC_2STATE_SWITCH, "Generic: GP Simple Generic 2-state Switch" }, |
481 | | { GPD_DEVICE_ID_GENERIC_GP_ON_OFF_SWITCH, "Generic: GP On/Off Switch" }, |
482 | | { GPD_DEVICE_ID_GENERIC_GP_LEVEL_CONTROL_SWITCH, "Generic: GP Level Control Switch" }, |
483 | | { GPD_DEVICE_ID_GENERIC_GP_SIMPLE_SENSOR, "Generic: GP Simple Sensor" }, |
484 | | { GPD_DEVICE_ID_GENERIC_GP_ADVANCED_GENERIC_1STATE_SWITCH, "Generic: GP Advanced Generic 1-state Switch" }, |
485 | | { GPD_DEVICE_ID_GENERIC_GP_ADVANCED_GENERIC_2STATE_SWITCH, "Generic: GP Advanced Generic 2-state Switch" }, |
486 | | |
487 | | /* GP LIGHTING */ |
488 | | { GPD_DEVICE_ID_LIGHTING_GP_COLOR_DIMMER_SWITCH, "Lighting: GP Color Dimmer Switch" }, |
489 | | { GPD_DEVICE_ID_LIGHTING_GP_LIGHT_SENSOR, "Lighting: GP Light Sensor" }, |
490 | | { GPD_DEVICE_ID_LIGHTING_GP_OCCUPANCY_SENSOR, "Lighting: GP Occupancy Sensor" }, |
491 | | |
492 | | /* GP CLOSURES */ |
493 | | { GPD_DEVICE_ID_CLOSURES_GP_DOOR_LOCK_CONTROLLER, "Closures: GP Door Lock Controller" }, |
494 | | |
495 | | /* HVAC */ |
496 | | { GPD_DEVICE_ID_HVAC_GP_TEMPERATURE_SENSOR, "HVAC: GP Temperature Sensor" }, |
497 | | { GPD_DEVICE_ID_HVAC_GP_PRESSURE_SENSOR, "HVAC: GP Pressure Sensor" }, |
498 | | { GPD_DEVICE_ID_HVAC_GP_FLOW_SENSOR, "HVAC: GP Flow Sensor" }, |
499 | | { GPD_DEVICE_ID_HVAC_GP_INDOOR_ENVIRONMENT_SENSOR, "HVAC: GP Indoor Environment Sensor" }, |
500 | | |
501 | | /* CUSTOM */ |
502 | | { GPD_DEVICE_ID_MANUFACTURER_SPECIFIC, "Manufacturer Specific" }, |
503 | | |
504 | | { 0, NULL } |
505 | | }; |
506 | | static value_string_ext zbee_nwk_gp_device_ids_names_ext = VALUE_STRING_EXT_INIT(zbee_nwk_gp_device_ids_names); |
507 | | |
508 | | /* GP directions. */ |
509 | | static const value_string zbee_nwk_gp_directions[] = { |
510 | | { ZBEE_NWK_GP_FC_EXT_DIRECTION_FROM_ZGPD, "From ZGPD" }, |
511 | | { ZBEE_NWK_GP_FC_EXT_DIRECTION_FROM_ZGPP, "From ZGPP" }, |
512 | | |
513 | | { 0, NULL } |
514 | | }; |
515 | | |
516 | | /* Frame types for Green Power profile. */ |
517 | | static const value_string zbee_nwk_gp_frame_types[] = { |
518 | | { ZBEE_NWK_GP_FCF_DATA, "Data" }, |
519 | | { ZBEE_NWK_GP_FCF_MAINTENANCE, "Maintenance" }, |
520 | | |
521 | | { 0, NULL } |
522 | | }; |
523 | | |
524 | | /* GreenPeak Green Power devices. */ |
525 | | static const value_string zbee_nwk_gp_manufacturer_greenpeak_dev_names[] = { |
526 | | { ZBEE_NWK_GP_MANUF_GREENPEAK_IZDS, "IAS Zone Door Sensor" }, |
527 | | { ZBEE_NWK_GP_MANUF_GREENPEAK_IZDWS, "IAS Zone Door/Window Sensor" }, |
528 | | { ZBEE_NWK_GP_MANUF_GREENPEAK_IZLS, "IAS Zone Leakage Sensor" }, |
529 | | { ZBEE_NWK_GP_MANUF_GREENPEAK_IZRHS, "IAS Zone Relative Humidity Sensor" }, |
530 | | |
531 | | { 0, NULL } |
532 | | }; |
533 | | |
534 | | /* GP Src ID names. */ |
535 | | static const value_string zbee_nwk_gp_src_id_names[] = { |
536 | | { ZBEE_NWK_GP_ZGPD_SRCID_ALL, "All" }, |
537 | | { ZBEE_NWK_GP_ZGPD_SRCID_UNKNOWN, "Unspecified" }, |
538 | | |
539 | | { 0, NULL } |
540 | | }; |
541 | | |
542 | | /* GP security key type names. */ |
543 | | static const value_string zbee_nwk_gp_src_sec_keys_type_names[] = { |
544 | | { ZBEE_NWK_GP_SECURITY_KEY_TYPE_NO_KEY, "No key" }, |
545 | | { ZBEE_NWK_GP_SECURITY_KEY_TYPE_ZB_NWK_KEY, "ZigBee NWK key" }, |
546 | | { ZBEE_NWK_GP_SECURITY_KEY_TYPE_GPD_GROUP_KEY, "GPD group key" }, |
547 | | { ZBEE_NWK_GP_SECURITY_KEY_TYPE_NWK_KEY_DERIVED_GPD_KEY_GROUP_KEY, "NWK key derived GPD group key" }, |
548 | | { ZBEE_NWK_GP_SECURITY_KEY_TYPE_PRECONFIGURED_INDIVIDUAL_GPD_KEY, "Individual, out of the box GPD key" }, |
549 | | { ZBEE_NWK_GP_SECURITY_KEY_TYPE_DERIVED_INDIVIDUAL_GPD_KEY, "Derived individual GPD key" }, |
550 | | |
551 | | { 0, NULL } |
552 | | }; |
553 | | |
554 | | /* GP security levels. */ |
555 | | static const value_string zbee_nwk_gp_src_sec_levels_names[] = { |
556 | | { ZBEE_NWK_GP_SECURITY_LEVEL_NO, "No security" }, |
557 | | { ZBEE_NWK_GP_SECURITY_LEVEL_1LSB, "1 LSB of frame counter and short MIC only" }, |
558 | | { ZBEE_NWK_GP_SECURITY_LEVEL_FULL, "Full frame counter and full MIC only" }, |
559 | | { ZBEE_NWK_GP_SECURITY_LEVEL_FULLENCR, "Encryption with full frame counter and full MIC" }, |
560 | | |
561 | | { 0, NULL } |
562 | | }; |
563 | | |
564 | | /*************************/ |
565 | | /* Function definitions. */ |
566 | | /*************************/ |
567 | | |
568 | | /* UAT record copy callback. */ |
569 | | static void * |
570 | | uat_key_record_copy_cb(void *n, const void *o, size_t siz _U_) |
571 | 0 | { |
572 | 0 | uat_key_record_t *new_key = (uat_key_record_t *)n; |
573 | 0 | const uat_key_record_t *old_key = (const uat_key_record_t *)o; |
574 | |
|
575 | 0 | new_key->string = g_strdup(old_key->string); |
576 | 0 | new_key->label = g_strdup(old_key->label); |
577 | |
|
578 | 0 | return new_key; |
579 | 0 | } |
580 | | |
581 | | /* UAT record free callback. */ |
582 | | static void |
583 | | uat_key_record_free_cb(void *r) |
584 | 0 | { |
585 | 0 | uat_key_record_t *key = (uat_key_record_t *)r; |
586 | 0 | g_free(key->string); |
587 | 0 | g_free(key->label); |
588 | 0 | } |
589 | | |
590 | | /** |
591 | | *Parses a key string from left to right into a buffer with increasing (normal byte order) or decreasing (reverse |
592 | | * |
593 | | *@param key_str pointer to the string |
594 | | *@param key_buf destination buffer in memory |
595 | | *@param byte_order byte order |
596 | | */ |
597 | | static bool |
598 | | zbee_gp_security_parse_key(const char *key_str, uint8_t *key_buf, bool byte_order) |
599 | 0 | { |
600 | 0 | bool string_mode = false; |
601 | 0 | char temp; |
602 | 0 | int i, j; |
603 | |
|
604 | 0 | memset(key_buf, 0, ZBEE_SEC_CONST_KEYSIZE); |
605 | 0 | if (key_str == NULL) { |
606 | 0 | return false; |
607 | 0 | } |
608 | 0 | if ((temp = *key_str++) == '"') { |
609 | 0 | string_mode = true; |
610 | 0 | temp = *key_str++; |
611 | 0 | } |
612 | 0 | j = byte_order ? ZBEE_SEC_CONST_KEYSIZE - 1 : 0; |
613 | 0 | for (i = ZBEE_SEC_CONST_KEYSIZE - 1; i >= 0; i--) { |
614 | 0 | if (string_mode) { |
615 | 0 | if (g_ascii_isprint(temp)) { |
616 | 0 | key_buf[j] = temp; |
617 | 0 | temp = *key_str++; |
618 | 0 | } else { |
619 | 0 | return false; |
620 | 0 | } |
621 | 0 | } else { |
622 | 0 | if ((temp == ':') || (temp == '-') || (temp == ' ')) { |
623 | 0 | temp = *(key_str++); |
624 | 0 | } |
625 | 0 | if (g_ascii_isxdigit(temp)) { |
626 | 0 | key_buf[j] = g_ascii_xdigit_value(temp) << 4; |
627 | 0 | } else { |
628 | 0 | return false; |
629 | 0 | } |
630 | 0 | temp = *(key_str++); |
631 | 0 | if (g_ascii_isxdigit(temp)) { |
632 | 0 | key_buf[j] |= g_ascii_xdigit_value(temp); |
633 | 0 | } else { |
634 | 0 | return false; |
635 | 0 | } |
636 | 0 | temp = *(key_str++); |
637 | 0 | } |
638 | 0 | if (byte_order) { |
639 | 0 | j--; |
640 | 0 | } else { |
641 | 0 | j++; |
642 | 0 | } |
643 | 0 | } |
644 | 0 | return true; |
645 | 0 | } |
646 | | |
647 | | /* UAT record update callback. */ |
648 | | static bool |
649 | | uat_key_record_update_cb(void *r, char **err) |
650 | 0 | { |
651 | 0 | uat_key_record_t *rec = (uat_key_record_t *)r; |
652 | |
|
653 | 0 | if (rec->string == NULL) { |
654 | 0 | *err = g_strdup("Key can't be blank."); |
655 | 0 | return false; |
656 | 0 | } else { |
657 | 0 | g_strstrip(rec->string); |
658 | 0 | if (rec->string[0] != 0) { |
659 | 0 | *err = NULL; |
660 | 0 | if (!zbee_gp_security_parse_key(rec->string, rec->key, rec->byte_order)) { |
661 | 0 | *err = ws_strdup_printf("Expecting %d hexadecimal bytes or a %d character double-quoted string", |
662 | 0 | ZBEE_SEC_CONST_KEYSIZE, ZBEE_SEC_CONST_KEYSIZE); |
663 | 0 | return false; |
664 | 0 | } |
665 | 0 | } else { |
666 | 0 | *err = g_strdup("Key can't be blank."); |
667 | 0 | return false; |
668 | 0 | } |
669 | 0 | } |
670 | 0 | return true; |
671 | 0 | } |
672 | | |
673 | 15 | static void uat_key_record_post_update_cb(void) { |
674 | 15 | unsigned i; |
675 | | |
676 | 15 | for (i = 0; i < num_uat_key_records; i++) { |
677 | 0 | if (memcmp(gp_uat_key_records[i].key, empty_key, ZBEE_SEC_CONST_KEYSIZE) == 0) { |
678 | | /* key was not loaded from string yet */ |
679 | 0 | zbee_gp_security_parse_key(gp_uat_key_records[i].string, gp_uat_key_records[i].key, |
680 | 0 | gp_uat_key_records[i].byte_order); |
681 | 0 | } |
682 | 0 | } |
683 | 15 | } |
684 | | |
685 | | /** |
686 | | *Fills in ZigBee GP security nonce from the provided packet structure. |
687 | | * |
688 | | *@param packet ZigBee NWK packet. |
689 | | *@param nonce nonce buffer. |
690 | | */ |
691 | | static void |
692 | | zbee_gp_make_nonce(zbee_nwk_green_power_packet *packet, uint8_t *nonce) |
693 | 3 | { |
694 | 3 | memset(nonce, 0, ZBEE_SEC_CONST_NONCE_LEN); |
695 | | |
696 | | /* Source address */ |
697 | 3 | if (packet->application_id == ZBEE_NWK_GP_APP_ID_DEFAULT) |
698 | 0 | { |
699 | 0 | if (packet->direction == ZBEE_NWK_GP_FC_EXT_DIRECTION_FROM_ZGPD) { |
700 | 0 | phtoleu32(nonce, packet->source_id); |
701 | 0 | } |
702 | 0 | phtoleu32(nonce+4, packet->source_id); |
703 | 0 | } |
704 | 3 | else if (packet->application_id == ZBEE_NWK_GP_APP_ID_ZGP) |
705 | 0 | { |
706 | 0 | phtoleu64(nonce, packet->ieee_packet_src64); |
707 | 0 | } |
708 | | |
709 | | /* Frame counter */ |
710 | 3 | phtoleu32(nonce+8, packet->security_frame_counter); |
711 | | |
712 | | /* Security control */ |
713 | 3 | if ((packet->application_id == ZBEE_NWK_GP_APP_ID_ZGP) && |
714 | 0 | (packet->direction != ZBEE_NWK_GP_FC_EXT_DIRECTION_FROM_ZGPD)) { |
715 | 0 | nonce[12] = (char)0xc5; /* Security level = 0b101, Key Identifier = 0x00, |
716 | | Extended nonce = 0b0, Reserved = 0b00 */ |
717 | 3 | } else { |
718 | 3 | nonce[12] = (char)0x05; /* Security level = 0b101, Key Identifier = 0x00, |
719 | | Extended nonce = 0b0, Reserved = 0b11 */ |
720 | 3 | } |
721 | 3 | } |
722 | | |
723 | | /** |
724 | | *Creates a nonce and decrypts secured ZigBee GP payload. |
725 | | * |
726 | | *@param packet ZigBee NWK packet. |
727 | | *@param enc_buffer encoded payload buffer. |
728 | | *@param offset payload offset. |
729 | | *@param dec_buffer decoded payload buffer. |
730 | | *@param payload_len payload length. |
731 | | *@param mic_len MIC length. |
732 | | *@param key key. |
733 | | */ |
734 | | static bool |
735 | | zbee_gp_decrypt_payload(zbee_nwk_green_power_packet *packet, const uint8_t *enc_buffer, const unsigned offset, uint8_t |
736 | | *dec_buffer, unsigned payload_len, unsigned mic_len, uint8_t *key) |
737 | 3 | { |
738 | 3 | uint8_t *key_buffer = key; |
739 | 3 | uint8_t nonce[ZBEE_SEC_CONST_NONCE_LEN]; |
740 | | |
741 | 3 | zbee_gp_make_nonce(packet, nonce); |
742 | 3 | if (zbee_sec_ccm_decrypt(key_buffer, nonce, enc_buffer, enc_buffer + offset, dec_buffer, offset, payload_len, |
743 | 3 | mic_len)) { |
744 | 1 | return true; |
745 | 1 | } |
746 | | |
747 | 2 | return false; |
748 | 3 | } |
749 | | |
750 | | /** |
751 | | *Dissector for ZigBee Green Power commissioning. |
752 | | * |
753 | | *@param tvb pointer to buffer containing raw packet. |
754 | | *@param pinfo pointer to packet information fields. |
755 | | *@param tree pointer to data tree Wireshark uses to display packet. |
756 | | *@param packet packet data. |
757 | | *@param offset current payload offset. |
758 | | *@return payload processed offset. |
759 | | */ |
760 | | static unsigned |
761 | | dissect_zbee_nwk_gp_cmd_commissioning(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, |
762 | | zbee_nwk_green_power_packet *packet, unsigned offset) |
763 | 10 | { |
764 | 10 | uint8_t comm_options; |
765 | 10 | uint8_t comm_ext_options = 0; |
766 | 10 | uint8_t appli_info_options = 0; |
767 | 10 | uint16_t manufacturer_id = 0; |
768 | | |
769 | 10 | uint8_t i; |
770 | 10 | uint8_t gpd_cmd_num = 0; |
771 | 10 | proto_item *gpd_cmd_list; |
772 | 10 | proto_tree *gpd_cmd_list_tree; |
773 | | |
774 | 10 | uint8_t length_of_clid_list_bm; |
775 | 10 | uint8_t server_clid_num; |
776 | 10 | uint8_t client_clid_num; |
777 | 10 | proto_item *server_clid_list, *client_clid_list; |
778 | 10 | proto_tree *server_clid_list_tree, *client_clid_list_tree; |
779 | | |
780 | 10 | void *enc_buffer; |
781 | 10 | uint8_t *enc_buffer_withA; |
782 | 10 | uint8_t *dec_buffer; |
783 | 10 | bool gp_decrypted; |
784 | 10 | GSList *GSList_i; |
785 | 10 | tvbuff_t *payload_tvb; |
786 | | |
787 | 10 | static int * const options[] = { |
788 | 10 | &hf_zbee_nwk_gp_cmd_comm_opt_mac_sec_num_cap, |
789 | 10 | &hf_zbee_nwk_gp_cmd_comm_opt_rx_on_cap, |
790 | 10 | &hf_zbee_nwk_gp_cmd_comm_opt_appli_info_present, |
791 | 10 | &hf_zbee_nwk_gp_cmd_comm_opt_panid_req, |
792 | 10 | &hf_zbee_nwk_gp_cmd_comm_opt_sec_key_req, |
793 | 10 | &hf_zbee_nwk_gp_cmd_comm_opt_fixed_location, |
794 | 10 | &hf_zbee_nwk_gp_cmd_comm_opt_ext_opt, |
795 | 10 | NULL |
796 | 10 | }; |
797 | 10 | static int * const ext_options[] = { |
798 | 10 | &hf_zbee_nwk_gp_cmd_comm_ext_opt_sec_level_cap, |
799 | 10 | &hf_zbee_nwk_gp_cmd_comm_ext_opt_key_type, |
800 | 10 | &hf_zbee_nwk_gp_cmd_comm_ext_opt_gpd_key_present, |
801 | 10 | &hf_zbee_nwk_gp_cmd_comm_ext_opt_gpd_key_encr, |
802 | 10 | &hf_zbee_nwk_gp_cmd_comm_ext_opt_outgoing_counter, |
803 | 10 | NULL |
804 | 10 | }; |
805 | 10 | static int * const appli_info[] = { |
806 | 10 | &hf_zbee_nwk_gp_cmd_comm_appli_info_mip, |
807 | 10 | &hf_zbee_nwk_gp_cmd_comm_appli_info_mmip, |
808 | 10 | &hf_zbee_nwk_gp_cmd_comm_appli_info_gclp, |
809 | 10 | &hf_zbee_nwk_gp_cmd_comm_appli_info_crp, |
810 | 10 | NULL |
811 | 10 | }; |
812 | 10 | static int * const length_of_clid_list[] = { |
813 | 10 | &hf_zbee_nwk_gp_cmd_comm_length_of_clid_list_server, |
814 | 10 | &hf_zbee_nwk_gp_cmd_comm_length_of_clid_list_client, |
815 | 10 | NULL |
816 | 10 | }; |
817 | | |
818 | | /* Get Device ID and display it. */ |
819 | 10 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_comm_device_id, tvb, offset, 1, ENC_LITTLE_ENDIAN); |
820 | 10 | offset += 1; |
821 | | /* Get Options Field, build subtree and display the results. */ |
822 | 10 | comm_options = tvb_get_uint8(tvb, offset); |
823 | 10 | proto_tree_add_bitmask(tree, tvb, offset, hf_zbee_nwk_gp_cmd_comm_opt, ett_zbee_nwk_cmd_options, options, ENC_NA); |
824 | 10 | offset += 1; |
825 | | |
826 | 10 | if (comm_options & ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_EXT_OPTIONS) { |
827 | | /* Get extended Options Field, build subtree and display the results. */ |
828 | 3 | comm_ext_options = tvb_get_uint8(tvb, offset); |
829 | 3 | proto_tree_add_bitmask(tree, tvb, offset, hf_zbee_nwk_gp_cmd_comm_ext_opt, ett_zbee_nwk_cmd_options, ext_options, ENC_NA); |
830 | 3 | offset += 1; |
831 | 3 | if (comm_ext_options & ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_GPD_KEY_PRESENT) { |
832 | | /* Get security key and display it. */ |
833 | 2 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_comm_security_key, tvb, offset, ZBEE_SEC_CONST_KEYSIZE, ENC_NA); |
834 | 2 | offset += ZBEE_SEC_CONST_KEYSIZE; |
835 | | |
836 | | /* Key is encrypted */ |
837 | 2 | if (comm_ext_options & ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_GPD_KEY_ENCR) { |
838 | | /* Get Security MIC and display it. */ |
839 | 1 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_comm_gpd_sec_key_mic, tvb, offset, 4, ENC_LITTLE_ENDIAN); |
840 | 1 | offset += 4; |
841 | | |
842 | 1 | if (packet != NULL) |
843 | 1 | { |
844 | | /* Decrypt the security key */ |
845 | 1 | dec_buffer = (uint8_t *)wmem_alloc(pinfo->pool, ZBEE_SEC_CONST_KEYSIZE); |
846 | 1 | enc_buffer_withA = (uint8_t *)wmem_alloc(pinfo->pool, 4 + ZBEE_SEC_CONST_KEYSIZE + 4); /* CCM* a (this is SrcID) + encKey + MIC */ |
847 | 1 | enc_buffer = tvb_memdup(pinfo->pool, tvb, offset - ZBEE_SEC_CONST_KEYSIZE - 4, ZBEE_SEC_CONST_KEYSIZE + 4); |
848 | 1 | phtoleu32(enc_buffer_withA, packet->source_id); |
849 | 1 | memcpy(enc_buffer_withA+4, enc_buffer, ZBEE_SEC_CONST_KEYSIZE + 4); |
850 | 1 | gp_decrypted = false; |
851 | | |
852 | 3 | for (GSList_i = zbee_gp_keyring; GSList_i && !gp_decrypted; GSList_i = g_slist_next(GSList_i)) { |
853 | 2 | packet->security_frame_counter = packet->source_id; /* for Nonce creation*/ |
854 | 2 | gp_decrypted = zbee_gp_decrypt_payload(packet, enc_buffer_withA, 4 |
855 | 2 | , dec_buffer, ZBEE_SEC_CONST_KEYSIZE, 4, ((key_record_t *)(GSList_i->data))->key); |
856 | 2 | } |
857 | | |
858 | 1 | if (gp_decrypted) { |
859 | 0 | key_record_t key_record; |
860 | |
|
861 | 0 | key_record.frame_num = 0; |
862 | 0 | key_record.label = NULL; |
863 | 0 | memcpy(key_record.key, dec_buffer, ZBEE_SEC_CONST_KEYSIZE); |
864 | 0 | zbee_gp_keyring = g_slist_prepend(zbee_gp_keyring, g_memdup2(&key_record, sizeof(key_record_t))); |
865 | |
|
866 | 0 | payload_tvb = tvb_new_child_real_data(tvb, dec_buffer, ZBEE_SEC_CONST_KEYSIZE, ZBEE_SEC_CONST_KEYSIZE); |
867 | 0 | add_new_data_source(pinfo, payload_tvb, "Decrypted security key"); |
868 | 0 | } |
869 | 1 | } |
870 | 1 | } |
871 | 1 | else |
872 | 1 | { |
873 | 1 | key_record_t key_record; |
874 | 1 | void *key; |
875 | | |
876 | 1 | key_record.frame_num = 0; |
877 | 1 | key_record.label = NULL; |
878 | 1 | key = tvb_memdup(pinfo->pool, tvb, offset - ZBEE_SEC_CONST_KEYSIZE, ZBEE_SEC_CONST_KEYSIZE); |
879 | 1 | memcpy(key_record.key, key, ZBEE_SEC_CONST_KEYSIZE); |
880 | 1 | zbee_gp_keyring = g_slist_prepend(zbee_gp_keyring, g_memdup2(&key_record, sizeof(key_record_t))); |
881 | 1 | } |
882 | 2 | } |
883 | | |
884 | 3 | if (comm_ext_options & ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_OUT_COUNTER) { |
885 | | /* Get GPD Outgoing Frame Counter and display it. */ |
886 | 1 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_comm_outgoing_counter, tvb, offset, 4, ENC_LITTLE_ENDIAN); |
887 | 1 | offset += 4; |
888 | 1 | } |
889 | 3 | } |
890 | | /* Display manufacturer specific data. */ |
891 | 10 | if (comm_options & ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_APPLICATION_INFO) { |
892 | | /* Display application information. */ |
893 | 8 | appli_info_options = tvb_get_uint8(tvb, offset); |
894 | 8 | proto_tree_add_bitmask(tree, tvb, offset, hf_zbee_nwk_gp_cmd_comm_appli_info, ett_zbee_nwk_cmd_appli_info, appli_info, ENC_NA); |
895 | 8 | offset += 1; |
896 | 8 | if (appli_info_options & ZBEE_NWK_GP_CMD_COMMISSIONING_APPLI_INFO_MIP) { |
897 | | /* Get Manufacturer ID. */ |
898 | 4 | proto_tree_add_item_ret_uint16(tree, hf_zbee_nwk_gp_cmd_comm_manufacturer_id, tvb, offset, 2, ENC_LITTLE_ENDIAN, &manufacturer_id); |
899 | 4 | offset += 2; |
900 | 4 | } |
901 | 8 | if (appli_info_options & ZBEE_NWK_GP_CMD_COMMISSIONING_APPLI_INFO_MMIP) { |
902 | | /* Get Manufacturer Device ID. */ |
903 | 6 | switch (manufacturer_id) { |
904 | 0 | case ZBEE_NWK_GP_MANUF_ID_GREENPEAK: |
905 | 0 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_comm_manufacturer_greenpeak_dev_id, tvb, offset, 2, |
906 | 0 | ENC_LITTLE_ENDIAN); |
907 | 0 | offset += 2; |
908 | 0 | break; |
909 | 6 | default: |
910 | 6 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_comm_manufacturer_dev_id, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
911 | 6 | offset += 2; |
912 | 6 | break; |
913 | 6 | } |
914 | 6 | } |
915 | 8 | if (appli_info_options & ZBEE_NWK_GP_CMD_COMMISSIONING_APPLI_INFO_GCLP) { |
916 | | /* Get and display number of GPD commands */ |
917 | 5 | proto_tree_add_item_ret_uint8(tree, hf_zbee_nwk_gp_cmd_comm_gpd_cmd_num, tvb, offset, 1, ENC_LITTLE_ENDIAN, &gpd_cmd_num); |
918 | 5 | offset += 1; |
919 | | /* Display GPD command list */ |
920 | 5 | if (gpd_cmd_num > 0) { |
921 | 4 | gpd_cmd_list = proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_comm_gpd_cmd_id_list, |
922 | 4 | tvb, offset, gpd_cmd_num, ENC_NA); |
923 | 4 | gpd_cmd_list_tree = proto_item_add_subtree(gpd_cmd_list, ett_zbee_nwk_cmd_comm_gpd_cmd_id_list); |
924 | 234 | for (i = 0; i < gpd_cmd_num; i++, offset++) { |
925 | | /* Display command id */ |
926 | 230 | proto_tree_add_item(gpd_cmd_list_tree, hf_zbee_nwk_gp_command_id, |
927 | 230 | tvb, offset, 1, ENC_LITTLE_ENDIAN); |
928 | 230 | } |
929 | 4 | } |
930 | 5 | } |
931 | 8 | if (appli_info_options & ZBEE_NWK_GP_CMD_COMMISSIONING_APPLI_INFO_CRP) { |
932 | | /* Get and display Cluster List */ |
933 | 6 | length_of_clid_list_bm = tvb_get_uint8(tvb, offset); |
934 | 6 | server_clid_num = (length_of_clid_list_bm & ZBEE_NWK_GP_CMD_COMMISSIONING_CLID_LIST_LEN_SRV) >> |
935 | 6 | ws_ctz(ZBEE_NWK_GP_CMD_COMMISSIONING_CLID_LIST_LEN_SRV); |
936 | 6 | client_clid_num = (length_of_clid_list_bm & ZBEE_NWK_GP_CMD_COMMISSIONING_CLID_LIST_LEN_CLI ) >> |
937 | 6 | ws_ctz(ZBEE_NWK_GP_CMD_COMMISSIONING_CLID_LIST_LEN_CLI); |
938 | | |
939 | 6 | proto_tree_add_bitmask(tree, tvb, offset, hf_zbee_nwk_gp_cmd_comm_length_of_clid_list, |
940 | 6 | ett_zbee_nwk_cmd_comm_length_of_clid_list, length_of_clid_list, ENC_NA); |
941 | 6 | offset += 1; |
942 | | |
943 | 6 | if (server_clid_num > 0) { |
944 | | /* Display server cluster list */ |
945 | 4 | server_clid_list = proto_tree_add_item(tree, hf_zbee_nwk_cmd_comm_clid_list_server, |
946 | 4 | tvb, offset, 2*server_clid_num, ENC_NA); |
947 | 4 | server_clid_list_tree = proto_item_add_subtree(server_clid_list, ett_zbee_nwk_cmd_comm_clid_list_server); |
948 | | /* Retrieve server clusters */ |
949 | 35 | for (i = 0; i < server_clid_num; i++, offset += 2) { |
950 | 31 | proto_tree_add_item(server_clid_list_tree, hf_zbee_nwk_cmd_comm_cluster_id, |
951 | 31 | tvb, offset, 2, ENC_LITTLE_ENDIAN); |
952 | 31 | } |
953 | 4 | } |
954 | 6 | if (client_clid_num > 0) { |
955 | | /* Display client cluster list */ |
956 | 4 | client_clid_list = proto_tree_add_item(tree, hf_zbee_nwk_cmd_comm_clid_list_client, |
957 | 4 | tvb, offset, 2*client_clid_num, ENC_NA); |
958 | 4 | client_clid_list_tree = proto_item_add_subtree(client_clid_list, ett_zbee_nwk_cmd_comm_clid_list_client); |
959 | | /* Retrieve client clusters */ |
960 | 44 | for (i = 0; i < client_clid_num; i++, offset += 2) { |
961 | 40 | proto_tree_add_item(client_clid_list_tree, hf_zbee_nwk_cmd_comm_cluster_id, |
962 | 40 | tvb, offset, 2, ENC_LITTLE_ENDIAN); |
963 | 40 | } |
964 | 4 | } |
965 | 6 | } |
966 | 8 | } |
967 | 10 | return offset; |
968 | 10 | } /* dissect_zbee_nwk_gp_cmd_commissioning */ |
969 | | |
970 | | /** |
971 | | *Dissector for ZigBee Green Power channel request. |
972 | | * |
973 | | *@param tvb pointer to buffer containing raw packet. |
974 | | *@param pinfo pointer to packet information fields. |
975 | | *@param tree pointer to data tree Wireshark uses to display packet. |
976 | | *@param packet packet data. |
977 | | *@param offset current payload offset. |
978 | | *@return payload processed offset. |
979 | | */ |
980 | | static unsigned |
981 | | dissect_zbee_nwk_gp_cmd_channel_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, |
982 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset) |
983 | 1 | { |
984 | 1 | static int * const channels[] = { |
985 | 1 | &hf_zbee_nwk_gp_cmd_channel_request_toggling_behaviour_1st, |
986 | 1 | &hf_zbee_nwk_gp_cmd_channel_request_toggling_behaviour_2nd, |
987 | 1 | NULL |
988 | 1 | }; |
989 | | |
990 | | /* Get Command Options Field, build subtree and display the results. */ |
991 | 1 | proto_tree_add_bitmask(tree, tvb, offset, hf_zbee_nwk_gp_cmd_channel_request_toggling_behaviour, ett_zbee_nwk_cmd_options, channels, ENC_NA); |
992 | 1 | offset += 1; |
993 | 1 | return offset; |
994 | 1 | } /* dissect_zbee_nwk_gp_cmd_channel_request */ |
995 | | |
996 | | /** |
997 | | *Dissector for ZigBee Green Power channel configuration. |
998 | | * |
999 | | *@param tvb pointer to buffer containing raw packet. |
1000 | | *@param pinfo pointer to packet information fields. |
1001 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1002 | | *@param packet packet data. |
1003 | | *@param offset current payload offset. |
1004 | | *@return payload processed offset. |
1005 | | */ |
1006 | | static unsigned |
1007 | | dissect_zbee_nwk_gp_cmd_channel_configuration(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, |
1008 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset) |
1009 | 1 | { |
1010 | 1 | static int * const channels[] = { |
1011 | 1 | &hf_zbee_nwk_gp_cmd_channel_configuration, |
1012 | 1 | NULL |
1013 | 1 | }; |
1014 | | |
1015 | | /* Get Command Options Field, build subtree and display the results. */ |
1016 | 1 | proto_tree_add_bitmask(tree, tvb, offset, hf_zbee_nwk_gp_cmd_operational_channel, ett_zbee_nwk_cmd_options, channels, ENC_NA); |
1017 | | |
1018 | 1 | offset += 1; |
1019 | 1 | return offset; |
1020 | 1 | } /* dissect_zbee_nwk_gp_cmd_channel_configuration */ |
1021 | | |
1022 | | /** |
1023 | | *Dissector for ZigBee Green Power commands attrib reporting. |
1024 | | * |
1025 | | *@param tvb pointer to buffer containing raw packet. |
1026 | | *@param pinfo pointer to packet information fields. |
1027 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1028 | | *@param packet packet data. |
1029 | | *@param offset current payload offset. |
1030 | | *@param mfr_code manufacturer code. |
1031 | | *@return payload processed offset. |
1032 | | */ |
1033 | | static unsigned |
1034 | | dissect_zbee_nwk_gp_cmd_attr_reporting(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, |
1035 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset, uint16_t mfr_code) |
1036 | 30 | { |
1037 | 30 | uint16_t cluster_id; |
1038 | 30 | proto_tree *field_tree; |
1039 | | |
1040 | | /* Get cluster ID and add it into the tree. */ |
1041 | 30 | proto_tree_add_item_ret_uint16(tree, hf_zbee_nwk_gp_zcl_attr_cluster_id, tvb, offset, 2, ENC_LITTLE_ENDIAN, &cluster_id); |
1042 | | |
1043 | 30 | offset += 2; |
1044 | | /* Create subtree and parse ZCL Write Attribute Payload. */ |
1045 | 30 | field_tree = proto_tree_add_subtree_format(tree, tvb, offset, 2, ett_zbee_nwk_cmd_options, NULL, |
1046 | 30 | "Attribute reporting command for cluster: 0x%04X", cluster_id); |
1047 | | |
1048 | 30 | dissect_zcl_report_attr(tvb, pinfo, field_tree, &offset, cluster_id, mfr_code, ZBEE_ZCL_FCF_TO_CLIENT); |
1049 | | |
1050 | 30 | return offset; |
1051 | 30 | } /* dissect_zbee_nwk_gp_cmd_attr_reporting */ |
1052 | | |
1053 | | |
1054 | | /** |
1055 | | * Dissector for ZigBee Green Power manufacturer specific attribute reporting. |
1056 | | * |
1057 | | *@param tvb pointer to buffer containing raw packet. |
1058 | | *@param pinfo pointer to packet information fields. |
1059 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1060 | | *@param packet packet data. |
1061 | | *@param offset current payload offset. |
1062 | | *@return payload processed offset. |
1063 | | */ |
1064 | | static unsigned |
1065 | | dissect_zbee_nwk_gp_cmd_MS_attr_reporting(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, |
1066 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset) |
1067 | 11 | { |
1068 | 11 | uint16_t mfr_code; |
1069 | | |
1070 | | /*dissect manufacturer ID*/ |
1071 | 11 | proto_tree_add_item_ret_uint16(tree, hf_zbee_zcl_gp_cmd_ms_manufacturer_code, tvb, offset, 2, ENC_LITTLE_ENDIAN, &mfr_code); |
1072 | 11 | offset += 2; |
1073 | | |
1074 | 11 | offset = dissect_zbee_nwk_gp_cmd_attr_reporting(tvb, pinfo, tree, packet, offset, mfr_code); |
1075 | | |
1076 | 11 | return offset; |
1077 | 11 | }/*dissect_zbee_nwk_gp_cmd_MS_attr_reporting*/ |
1078 | | |
1079 | | |
1080 | | |
1081 | | |
1082 | | /** |
1083 | | *Dissector for ZigBee Green Power commissioning reply. |
1084 | | * |
1085 | | *@param tvb pointer to buffer containing raw packet. |
1086 | | *@param pinfo pointer to packet information fields. |
1087 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1088 | | *@param packet packet data. |
1089 | | *@param offset current payload offset. |
1090 | | *@return payload processed offset. |
1091 | | */ |
1092 | | static unsigned |
1093 | | dissect_zbee_nwk_gp_cmd_commissioning_reply(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, |
1094 | | zbee_nwk_green_power_packet *packet, unsigned offset) |
1095 | 3 | { |
1096 | 3 | uint8_t cr_options; |
1097 | 3 | uint8_t cr_sec_level; |
1098 | | |
1099 | 3 | void *enc_buffer; |
1100 | 3 | uint8_t *enc_buffer_withA; |
1101 | 3 | uint8_t *dec_buffer; |
1102 | 3 | bool gp_decrypted; |
1103 | 3 | GSList *GSList_i; |
1104 | 3 | tvbuff_t *payload_tvb; |
1105 | | |
1106 | 3 | static int * const options[] = { |
1107 | 3 | &hf_zbee_nwk_gp_cmd_comm_rep_opt_panid_present, |
1108 | 3 | &hf_zbee_nwk_gp_cmd_comm_rep_opt_sec_key_present, |
1109 | 3 | &hf_zbee_nwk_gp_cmd_comm_rep_opt_key_encr, |
1110 | 3 | &hf_zbee_nwk_gp_cmd_comm_rep_opt_sec_level, |
1111 | 3 | &hf_zbee_nwk_gp_cmd_comm_rep_opt_sec_type, |
1112 | 3 | NULL |
1113 | 3 | }; |
1114 | | |
1115 | | /* Get Options Field, build subtree and display the results. */ |
1116 | 3 | cr_options = tvb_get_uint8(tvb, offset); |
1117 | 3 | proto_tree_add_bitmask(tree, tvb, offset, hf_zbee_nwk_gp_cmd_comm_rep_opt, ett_zbee_nwk_cmd_options, options, ENC_NA); |
1118 | 3 | offset += 1; |
1119 | | |
1120 | | /* Parse and display security Pan ID value. */ |
1121 | 3 | if (cr_options & ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_PAN_ID_PRESENT) { |
1122 | 1 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_comm_rep_pan_id, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
1123 | 1 | offset += 2; |
1124 | 1 | } |
1125 | | |
1126 | 3 | cr_sec_level = (cr_options & ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_SEC_LEVEL) >> |
1127 | 3 | ws_ctz(ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_SEC_LEVEL); |
1128 | | |
1129 | | /* Parse and display security key. */ |
1130 | 3 | if (cr_options & ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_SEC_KEY_PRESENT) { |
1131 | 1 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_comm_security_key, tvb, offset, ZBEE_SEC_CONST_KEYSIZE, ENC_NA); |
1132 | 1 | offset += ZBEE_SEC_CONST_KEYSIZE; |
1133 | | |
1134 | | /* Key is present clear, add to the key ring */ |
1135 | 1 | if (!(cr_options & ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_KEY_ENCR)) { |
1136 | 1 | key_record_t key_record; |
1137 | 1 | void *key; |
1138 | | |
1139 | 1 | key_record.frame_num = 0; |
1140 | 1 | key_record.label = NULL; |
1141 | 1 | key = tvb_memdup(pinfo->pool, tvb, offset - ZBEE_SEC_CONST_KEYSIZE, ZBEE_SEC_CONST_KEYSIZE); |
1142 | 1 | memcpy(key_record.key, key, ZBEE_SEC_CONST_KEYSIZE); |
1143 | 1 | zbee_gp_keyring = g_slist_prepend(zbee_gp_keyring, g_memdup2(&key_record, sizeof(key_record_t))); |
1144 | 1 | } |
1145 | 1 | } |
1146 | | /* Parse and display security MIC. */ |
1147 | 3 | if ((cr_options & ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_KEY_ENCR) && |
1148 | 1 | (cr_options & ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_SEC_KEY_PRESENT)) { |
1149 | 0 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_comm_gpd_sec_key_mic, tvb, offset, 4, ENC_LITTLE_ENDIAN); |
1150 | 0 | offset += 4; |
1151 | 0 | } |
1152 | | |
1153 | | /* Parse and display Frame Counter and decrypt key */ |
1154 | 3 | if ((cr_options & ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_KEY_ENCR) && |
1155 | 1 | (cr_options & ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_SEC_KEY_PRESENT) && |
1156 | 0 | ((cr_sec_level == ZBEE_NWK_GP_SECURITY_LEVEL_FULL) || |
1157 | 0 | (cr_sec_level == ZBEE_NWK_GP_SECURITY_LEVEL_FULLENCR))) { |
1158 | 0 | if (offset + 4 <= tvb_captured_length(tvb)){ |
1159 | 0 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_comm_rep_frame_counter, tvb, offset, 4, ENC_LITTLE_ENDIAN); |
1160 | 0 | offset += 4; |
1161 | |
|
1162 | 0 | if (packet != NULL) |
1163 | 0 | { |
1164 | | /* decrypt the security key*/ |
1165 | 0 | dec_buffer = (uint8_t *)wmem_alloc(pinfo->pool, ZBEE_SEC_CONST_KEYSIZE); |
1166 | 0 | enc_buffer_withA = (uint8_t *)wmem_alloc(pinfo->pool, 4 + ZBEE_SEC_CONST_KEYSIZE + 4); /* CCM* a (this is SrcID) + encKey + MIC */ |
1167 | 0 | enc_buffer = tvb_memdup(pinfo->pool, tvb, offset - ZBEE_SEC_CONST_KEYSIZE - 4 - 4, ZBEE_SEC_CONST_KEYSIZE + 4); |
1168 | 0 | phtoleu32(enc_buffer_withA, packet->source_id); /* enc_buffer_withA = CCM* a (srcID) | enc_buffer */ |
1169 | 0 | memcpy(enc_buffer_withA+4, enc_buffer, ZBEE_SEC_CONST_KEYSIZE + 4); |
1170 | 0 | gp_decrypted = false; |
1171 | |
|
1172 | 0 | for (GSList_i = zbee_gp_keyring; GSList_i && !gp_decrypted; GSList_i = g_slist_next(GSList_i)) { |
1173 | 0 | packet->security_frame_counter = tvb_get_uint32(tvb, offset - 4, ENC_LITTLE_ENDIAN); /*for Nonce creation */ |
1174 | 0 | gp_decrypted = zbee_gp_decrypt_payload(packet, enc_buffer_withA, 4 |
1175 | 0 | , dec_buffer, ZBEE_SEC_CONST_KEYSIZE, 4, ((key_record_t *)(GSList_i->data))->key); |
1176 | 0 | } |
1177 | |
|
1178 | 0 | if (gp_decrypted) { |
1179 | 0 | key_record_t key_record; |
1180 | |
|
1181 | 0 | key_record.frame_num = 0; |
1182 | 0 | key_record.label = NULL; |
1183 | 0 | memcpy(key_record.key, dec_buffer, ZBEE_SEC_CONST_KEYSIZE); |
1184 | 0 | zbee_gp_keyring = g_slist_prepend(zbee_gp_keyring, g_memdup2(&key_record, sizeof(key_record_t))); |
1185 | |
|
1186 | 0 | payload_tvb = tvb_new_child_real_data(tvb, dec_buffer, ZBEE_SEC_CONST_KEYSIZE, ZBEE_SEC_CONST_KEYSIZE); |
1187 | 0 | add_new_data_source(pinfo, payload_tvb, "Decrypted security key"); |
1188 | 0 | } |
1189 | 0 | } |
1190 | 0 | } |
1191 | 0 | else{ |
1192 | | /* This field is new in 2016 specification, older implementation may exist without it */ |
1193 | 0 | proto_tree_add_expert_remaining(tree, pinfo, &ei_zbee_nwk_gp_com_rep_no_out_cnt, tvb, 0); |
1194 | 0 | } |
1195 | 0 | } |
1196 | 3 | return offset; |
1197 | 3 | } /* dissect_zbee_nwk_gp_cmd_commissioning_reply */ |
1198 | | |
1199 | | /** |
1200 | | * Dissector for ZigBee Green Power read attributes and request attributes commands. |
1201 | | * |
1202 | | *@param tvb pointer to buffer containing raw packet. |
1203 | | *@param pinfo pointer to packet information fields. |
1204 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1205 | | *@param packet packet data. |
1206 | | *@param offset current payload offset. |
1207 | | *@return payload processed offset. |
1208 | | */ |
1209 | | static unsigned |
1210 | | dissect_zbee_nwk_gp_cmd_read_attributes(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, |
1211 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset) |
1212 | 26 | { |
1213 | 26 | uint8_t cr_options = 0; |
1214 | 26 | proto_tree *subtree = NULL; |
1215 | 26 | uint16_t cluster_id; |
1216 | 26 | uint16_t mfr_code = ZBEE_MFG_CODE_NONE; |
1217 | 26 | uint8_t record_list_len; |
1218 | 26 | unsigned tvb_len; |
1219 | 26 | uint8_t i; |
1220 | | |
1221 | 26 | static int * const options[] = { |
1222 | 26 | &hf_zbee_nwk_gp_cmd_read_att_opt_multi_rec, |
1223 | 26 | &hf_zbee_nwk_gp_cmd_read_att_opt_man_field_present, |
1224 | 26 | NULL |
1225 | 26 | }; |
1226 | | |
1227 | | /* Get Options Field, build subtree and display the results. */ |
1228 | 26 | cr_options = tvb_get_uint8(tvb, offset); |
1229 | 26 | proto_tree_add_bitmask(tree, tvb, offset, hf_zbee_nwk_gp_cmd_read_att_opt, ett_zbee_nwk_cmd_options, options, ENC_NA); |
1230 | | |
1231 | 26 | offset += 1; |
1232 | | /* Parse and display manufacturer ID value. */ |
1233 | 26 | if (cr_options & ZBEE_NWK_GP_CMD_READ_ATTRIBUTE_OPT_MAN_FIELD_PRESENT) { |
1234 | 13 | proto_tree_add_item_ret_uint16(tree, hf_zbee_zcl_gp_cmd_ms_manufacturer_code, tvb, offset, 2, ENC_LITTLE_ENDIAN, &mfr_code); |
1235 | 13 | offset += 2; |
1236 | 13 | } |
1237 | | |
1238 | 26 | tvb_len = tvb_captured_length(tvb); |
1239 | 232 | while (offset < tvb_len) |
1240 | 206 | { |
1241 | | /* Create subtree and parse attributes list. */ |
1242 | 206 | subtree = proto_tree_add_subtree_format(tree, tvb, offset, -1, ett_zbee_nwk_clu_rec, NULL, "Cluster Record Request"); |
1243 | | |
1244 | | /* Get cluster ID and add it into the subtree. */ |
1245 | 206 | proto_tree_add_item_ret_uint16(subtree, hf_zbee_nwk_gp_zcl_attr_cluster_id, tvb, offset, 2, ENC_LITTLE_ENDIAN, &cluster_id); |
1246 | 206 | offset += 2; |
1247 | | /* Get length of record list (number of attributes * 2). */ |
1248 | 206 | proto_tree_add_item_ret_uint8(subtree, hf_zbee_nwk_gp_cmd_read_att_record_len, tvb, offset, 1, ENC_LITTLE_ENDIAN, &record_list_len); |
1249 | 206 | offset += 1; |
1250 | | |
1251 | 1.77k | for(i=0 ; i<record_list_len ; i+=2) |
1252 | 1.56k | { |
1253 | | /* Dissect the attribute identifier */ |
1254 | 1.56k | dissect_zcl_attr_id(tvb, subtree, &offset, cluster_id, mfr_code, ZBEE_ZCL_FCF_TO_CLIENT); |
1255 | 1.56k | } |
1256 | 206 | } |
1257 | 26 | return offset; |
1258 | 26 | } /* dissect_zbee_nwk_gp_cmd_read_attributes */ |
1259 | | /** |
1260 | | * Dissector for ZigBee Green Power write attributes commands. |
1261 | | * |
1262 | | *@param tvb pointer to buffer containing raw packet. |
1263 | | *@param pinfo pointer to packet information fields. |
1264 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1265 | | *@param packet packet data. |
1266 | | *@param offset current payload offset. |
1267 | | *@return payload processed offset. |
1268 | | */ |
1269 | | static unsigned |
1270 | | dissect_zbee_nwk_gp_cmd_write_attributes(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, |
1271 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset) |
1272 | 368 | { |
1273 | 368 | uint8_t cr_options = 0; |
1274 | 368 | proto_tree *subtree = NULL; |
1275 | 368 | proto_tree *att_tree = NULL; |
1276 | 368 | uint16_t mfr_code = ZBEE_MFG_CODE_NONE; |
1277 | 368 | uint16_t cluster_id; |
1278 | 368 | uint8_t record_list_len; |
1279 | 368 | unsigned tvb_len; |
1280 | 368 | uint16_t attr_id; |
1281 | 368 | unsigned end_byte; |
1282 | | //uint8_t i; |
1283 | | |
1284 | 368 | static int * const options[] = { |
1285 | 368 | &hf_zbee_nwk_gp_cmd_read_att_opt_multi_rec, |
1286 | 368 | &hf_zbee_nwk_gp_cmd_read_att_opt_man_field_present, |
1287 | 368 | NULL |
1288 | 368 | }; |
1289 | | |
1290 | | /* Get Options Field, build subtree and display the results. */ |
1291 | 368 | cr_options = tvb_get_uint8(tvb, offset); |
1292 | 368 | proto_tree_add_bitmask(tree, tvb, offset, hf_zbee_nwk_gp_cmd_read_att_opt, ett_zbee_nwk_cmd_options, options, ENC_NA); |
1293 | | |
1294 | 368 | offset += 1; |
1295 | | /* Parse and display manufacturer ID value. */ |
1296 | 368 | if (cr_options & ZBEE_NWK_GP_CMD_READ_ATTRIBUTE_OPT_MAN_FIELD_PRESENT) { |
1297 | 8 | proto_tree_add_item_ret_uint16(tree, hf_zbee_zcl_gp_cmd_ms_manufacturer_code, tvb, offset, 2, ENC_LITTLE_ENDIAN, &mfr_code); |
1298 | 8 | offset += 2; |
1299 | 8 | } |
1300 | | |
1301 | 368 | tvb_len = tvb_captured_length(tvb); |
1302 | 1.90k | while (offset < tvb_len) |
1303 | 1.53k | { |
1304 | | /* Create subtree and parse attributes list. */ |
1305 | 1.53k | subtree = proto_tree_add_subtree_format(tree, tvb, offset, -1, ett_zbee_nwk_clu_rec, NULL, "Write Cluster Record"); |
1306 | | |
1307 | | /* Get cluster ID and add it into the subtree. */ |
1308 | 1.53k | proto_tree_add_item_ret_uint16(subtree, hf_zbee_nwk_gp_zcl_attr_cluster_id, tvb, offset, 2, ENC_LITTLE_ENDIAN, &cluster_id); |
1309 | 1.53k | offset += 2; |
1310 | | /* Get length of record list. */ |
1311 | 1.53k | record_list_len = tvb_get_uint8(tvb, offset); |
1312 | 1.53k | proto_tree_add_item(subtree, hf_zbee_nwk_gp_cmd_read_att_record_len, tvb, offset, 1, ENC_LITTLE_ENDIAN); |
1313 | 1.53k | offset += 1; |
1314 | | |
1315 | 1.53k | end_byte = offset + record_list_len; |
1316 | 8.81k | while ( offset < end_byte) |
1317 | 7.27k | { |
1318 | | /* Create subtree for attribute status field */ |
1319 | 7.27k | att_tree = proto_tree_add_subtree_format(subtree, tvb, offset, 0, ett_zbee_nwk_att_rec, NULL, "Write Attribute record"); |
1320 | | |
1321 | | /* Dissect the attribute identifier */ |
1322 | 7.27k | attr_id = tvb_get_letohs(tvb, offset); |
1323 | 7.27k | dissect_zcl_attr_id(tvb, att_tree, &offset, cluster_id, mfr_code, ZBEE_ZCL_FCF_TO_CLIENT); |
1324 | | |
1325 | | /* Dissect the attribute data type and data */ |
1326 | 7.27k | dissect_zcl_attr_data_type_val(tvb, pinfo, att_tree, &offset, attr_id, cluster_id, mfr_code, ZBEE_ZCL_FCF_TO_CLIENT); |
1327 | 7.27k | } |
1328 | 1.53k | } |
1329 | 368 | return offset; |
1330 | 368 | } /* dissect_zbee_nwk_gp_cmd_write_attributes */ |
1331 | | |
1332 | | |
1333 | | /** |
1334 | | * Dissector for ZigBee Green Power read attribute response command. |
1335 | | * |
1336 | | *@param tvb pointer to buffer containing raw packet. |
1337 | | *@param pinfo pointer to packet information fields. |
1338 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1339 | | *@param packet packet data. |
1340 | | *@param offset current payload offset. |
1341 | | *@return payload processed offset. |
1342 | | */ |
1343 | | static unsigned |
1344 | | dissect_zbee_nwk_gp_cmd_read_attributes_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, |
1345 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset) |
1346 | 156 | { |
1347 | 156 | uint8_t cr_options; |
1348 | 156 | proto_tree *subtree = NULL; |
1349 | 156 | proto_tree *att_tree = NULL; |
1350 | 156 | uint16_t cluster_id; |
1351 | 156 | uint16_t attr_id; |
1352 | 156 | uint16_t mfr_code = ZBEE_MFG_CODE_NONE; |
1353 | 156 | uint8_t record_list_len; |
1354 | 156 | unsigned tvb_len; |
1355 | 156 | unsigned end_byte; |
1356 | | |
1357 | 156 | static int * const options[] = { |
1358 | 156 | &hf_zbee_nwk_gp_cmd_read_att_opt_multi_rec, |
1359 | 156 | &hf_zbee_nwk_gp_cmd_read_att_opt_man_field_present, |
1360 | 156 | NULL |
1361 | 156 | }; |
1362 | | |
1363 | | /* Get Options Field, build subtree and display the results. */ |
1364 | 156 | cr_options = tvb_get_uint8(tvb, offset); |
1365 | 156 | proto_tree_add_bitmask(tree, tvb, offset, hf_zbee_nwk_gp_cmd_read_att_opt, ett_zbee_nwk_cmd_options, options, ENC_NA); |
1366 | 156 | offset += 1; |
1367 | | |
1368 | | /* Parse and display manufacturer ID value. */ |
1369 | 156 | if (cr_options & ZBEE_NWK_GP_CMD_READ_ATTRIBUTE_OPT_MAN_FIELD_PRESENT) { |
1370 | 55 | proto_tree_add_item_ret_uint16(tree, hf_zbee_zcl_gp_cmd_ms_manufacturer_code, tvb, offset, 2, ENC_LITTLE_ENDIAN, &mfr_code); |
1371 | 55 | offset += 2; |
1372 | 55 | } |
1373 | | |
1374 | 156 | tvb_len = tvb_captured_length(tvb); |
1375 | 1.00k | while (offset < tvb_len) |
1376 | 845 | { |
1377 | | /* Create subtree and parse attributes list. */ |
1378 | 845 | subtree = proto_tree_add_subtree_format(tree, tvb, offset,0, ett_zbee_nwk_clu_rec, NULL, "Cluster record"); |
1379 | | |
1380 | | /* Get cluster ID and add it into the subtree. */ |
1381 | 845 | proto_tree_add_item_ret_uint16(subtree, hf_zbee_nwk_gp_zcl_attr_cluster_id, tvb, offset, 2, ENC_LITTLE_ENDIAN, &cluster_id); |
1382 | 845 | offset += 2; |
1383 | | /* Get length of record list in bytes. */ |
1384 | 845 | record_list_len = tvb_get_uint8(tvb, offset); |
1385 | 845 | proto_tree_add_item(subtree, hf_zbee_nwk_gp_cmd_read_att_record_len, tvb, offset, 1, ENC_LITTLE_ENDIAN); |
1386 | 845 | offset += 1; |
1387 | | |
1388 | 845 | end_byte = offset + record_list_len; |
1389 | 4.34k | while ( offset < end_byte) |
1390 | 3.49k | { |
1391 | | /* Create subtree for attribute status field */ |
1392 | | /* TODO ett_ could be an array to permit not to unroll all always */ |
1393 | 3.49k | att_tree = proto_tree_add_subtree_format(subtree, tvb, offset, 0, ett_zbee_nwk_att_rec, NULL, "Read Attribute record"); |
1394 | | |
1395 | | /* Dissect the attribute identifier */ |
1396 | 3.49k | attr_id = tvb_get_letohs(tvb, offset); |
1397 | 3.49k | dissect_zcl_attr_id(tvb, att_tree, &offset, cluster_id, mfr_code, ZBEE_ZCL_FCF_TO_CLIENT); |
1398 | | |
1399 | | /* Dissect the status and optionally the data type and value */ |
1400 | 3.49k | if (dissect_zcl_attr_uint8(tvb, att_tree, &offset, &hf_zbee_nwk_gp_zcl_attr_status) |
1401 | 3.49k | == ZBEE_ZCL_STAT_SUCCESS) |
1402 | 1.14k | { |
1403 | | /* Dissect the attribute data type and data */ |
1404 | 1.14k | dissect_zcl_attr_data_type_val(tvb, pinfo, att_tree, &offset, attr_id, cluster_id, mfr_code, ZBEE_ZCL_FCF_TO_CLIENT); |
1405 | 1.14k | } |
1406 | 2.34k | else |
1407 | 2.34k | { |
1408 | | /* Data type field is always present (not like in ZCL read attribute response command) */ |
1409 | 2.34k | dissect_zcl_attr_data(tvb, pinfo, att_tree, &offset, |
1410 | 2.34k | dissect_zcl_attr_uint8(tvb, att_tree, &offset, &hf_zbee_nwk_gp_zcl_attr_data_type), ZBEE_ZCL_FCF_TO_CLIENT ); |
1411 | 2.34k | } |
1412 | 3.49k | } |
1413 | 845 | } |
1414 | 156 | return offset; |
1415 | 156 | } /* dissect_zbee_nwk_gp_cmd_read_attributes_response */ |
1416 | | |
1417 | | /** |
1418 | | * Dissector for ZigBee Green Power ZCL tunneling command. |
1419 | | * |
1420 | | *@param tvb pointer to buffer containing raw packet. |
1421 | | *@param pinfo pointer to packet information fields. |
1422 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1423 | | *@param packet packet data. |
1424 | | *@param offset current payload offset. |
1425 | | *@return payload processed offset. |
1426 | | */ |
1427 | | static unsigned |
1428 | | dissect_zbee_nwk_gp_cmd_zcl_tunneling(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, |
1429 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset) |
1430 | 1 | { |
1431 | 1 | uint8_t tun_options; |
1432 | | |
1433 | 1 | static int * const options[] = { |
1434 | 1 | &hf_zbee_nwk_gp_cmd_zcl_tunnel_opt_frame_type, |
1435 | 1 | &hf_zbee_nwk_gp_cmd_zcl_tunnel_opt_man_field_present, |
1436 | 1 | &hf_zbee_nwk_gp_cmd_zcl_tunnel_opt_direction, |
1437 | 1 | NULL |
1438 | 1 | }; |
1439 | | |
1440 | | /* Get Options Field, build subtree and display the results. */ |
1441 | 1 | tun_options = tvb_get_uint8(tvb, offset); |
1442 | 1 | proto_tree_add_bitmask(tree, tvb, offset, hf_zbee_nwk_gp_cmd_zcl_tunnel_opt, ett_zbee_nwk_cmd_options, options, ENC_NA); |
1443 | 1 | offset += 1; |
1444 | | |
1445 | | /* Parse and display manufacturer ID value. */ |
1446 | 1 | if (tun_options & ZBEE_NWK_GP_CMD_ZCL_TUNNEL_OPT_MAN_FIELD_PRESENT) { |
1447 | 1 | proto_tree_add_item(tree, hf_zbee_zcl_gp_cmd_ms_manufacturer_code, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
1448 | 1 | offset += 2; |
1449 | 1 | } |
1450 | | |
1451 | 1 | proto_tree_add_item(tree, hf_zbee_nwk_gp_zcl_attr_cluster_id, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
1452 | 1 | offset += 2; |
1453 | | |
1454 | 1 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_zcl_tunnel_command_id, tvb, offset, 1, ENC_LITTLE_ENDIAN); |
1455 | 1 | offset += 1; |
1456 | | |
1457 | 1 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_zcl_tunnel_payload_len, tvb, offset, 1, ENC_LITTLE_ENDIAN); |
1458 | 1 | offset += 1; |
1459 | | |
1460 | | /* We're not parsing the ZCL payload, as it's non-trivial and will require a lot of refactoring of the |
1461 | | * ZCL data parsers to make work. For now, let it just show up as raw data. */ |
1462 | | |
1463 | 1 | return offset; |
1464 | 1 | } /* dissect_zbee_nwk_gp_cmd_zcl_tunneling */ |
1465 | | |
1466 | | /** |
1467 | | *Dissector for ZigBee Green Power multi-cluster reporting command. |
1468 | | * |
1469 | | *@param tvb pointer to buffer containing raw packet. |
1470 | | *@param pinfo pointer to packet information fields. |
1471 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1472 | | *@param packet packet data. |
1473 | | *@param offset current payload offset. |
1474 | | *@param mfr_code manufacturer code. |
1475 | | *@return payload processed offset. |
1476 | | */ |
1477 | | static unsigned |
1478 | | dissect_zbee_nwk_gp_cmd_multi_cluster_reporting(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, |
1479 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset, uint16_t mfr_code) |
1480 | 154 | { |
1481 | 154 | proto_tree *subtree = NULL; |
1482 | 154 | uint16_t cluster_id; |
1483 | 154 | uint16_t attr_id; |
1484 | 154 | unsigned tvb_len; |
1485 | | |
1486 | 154 | tvb_len = tvb_captured_length(tvb); |
1487 | 3.55k | while (offset < tvb_len) |
1488 | 3.40k | { |
1489 | | /* Create subtree and parse attributes list. */ |
1490 | 3.40k | subtree = proto_tree_add_subtree_format(tree, tvb, offset, 0, ett_zbee_nwk_clu_rec, NULL, "Cluster record"); //TODO for cluster %% blabla |
1491 | | |
1492 | | /* Get cluster ID and add it into the subtree. */ |
1493 | 3.40k | proto_tree_add_item_ret_uint16(subtree, hf_zbee_nwk_gp_zcl_attr_cluster_id, tvb, offset, 2, ENC_LITTLE_ENDIAN, &cluster_id); |
1494 | 3.40k | offset += 2; |
1495 | | |
1496 | | /* Dissect the attribute identifier */ |
1497 | 3.40k | attr_id = tvb_get_letohs(tvb, offset); |
1498 | 3.40k | dissect_zcl_attr_id(tvb, subtree, &offset, cluster_id, mfr_code, ZBEE_ZCL_FCF_TO_CLIENT); |
1499 | | |
1500 | | /* Dissect the attribute data type and data */ |
1501 | 3.40k | dissect_zcl_attr_data_type_val(tvb, pinfo, subtree, &offset, attr_id, cluster_id, mfr_code, ZBEE_ZCL_FCF_TO_CLIENT); |
1502 | | // TODO how to dissect when data type is different from expected one for this attribute ? this shouldn't happen |
1503 | 3.40k | } |
1504 | 154 | return offset; |
1505 | 154 | } /* dissect_zbee_nwk_gp_cmd_multi_cluster_reporting */ |
1506 | | |
1507 | | |
1508 | | /** |
1509 | | *Dissector for ZigBee Green Power commands manufacturer specific attrib reporting. |
1510 | | * |
1511 | | *@param tvb pointer to buffer containing raw packet. |
1512 | | *@param pinfo pointer to packet information fields. |
1513 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1514 | | *@param packet packet data. |
1515 | | *@param offset current payload offset. |
1516 | | *@return payload processed offset. |
1517 | | */ |
1518 | | static unsigned |
1519 | | dissect_zbee_nwk_gp_cmd_MS_multi_cluster_reporting(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, |
1520 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset) |
1521 | 3 | { |
1522 | 3 | uint16_t mfr_code; |
1523 | | |
1524 | | /*dissect manufacturer ID*/ |
1525 | 3 | proto_tree_add_item_ret_uint16(tree, hf_zbee_zcl_gp_cmd_ms_manufacturer_code, tvb, offset, 2, ENC_LITTLE_ENDIAN, &mfr_code); |
1526 | 3 | offset += 2; |
1527 | | |
1528 | 3 | offset = dissect_zbee_nwk_gp_cmd_multi_cluster_reporting(tvb, pinfo, tree, packet, offset, mfr_code); |
1529 | | |
1530 | 3 | return offset; |
1531 | 3 | }/*dissect_zbee_nwk_gp_cmd_MS_multi_cluster_reporting*/ |
1532 | | |
1533 | | /** |
1534 | | *Dissector for ZigBee Green Power Move Color. |
1535 | | * |
1536 | | *@param tvb pointer to buffer containing raw packet. |
1537 | | *@param pinfo pointer to packet information fields. |
1538 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1539 | | *@param packet packet data. |
1540 | | *@param offset current payload offset. |
1541 | | *@return payload processed offset. |
1542 | | */ |
1543 | | static unsigned |
1544 | | dissect_zbee_nwk_gp_cmd_move_color(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, |
1545 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset) |
1546 | 1 | { |
1547 | 1 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_move_color_ratex, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
1548 | 1 | offset += 2; |
1549 | 1 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_move_color_ratey, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
1550 | 1 | offset += 2; |
1551 | 1 | return offset; |
1552 | 1 | } /* dissect_zbee_nwk_gp_cmd_move_color */ |
1553 | | |
1554 | | /** |
1555 | | *Dissector for ZigBee Green Power Move Up/Down. |
1556 | | * |
1557 | | *@param tvb pointer to buffer containing raw packet. |
1558 | | *@param pinfo pointer to packet information fields. |
1559 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1560 | | *@param packet packet data. |
1561 | | *@param offset current payload offset. |
1562 | | *@return payload processed offset. |
1563 | | */ |
1564 | | static unsigned |
1565 | | dissect_zbee_nwk_gp_cmd_move_up_down(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, |
1566 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset) |
1567 | 10 | { |
1568 | | /* Optional rate field. */ |
1569 | 10 | if (tvb_reported_length(tvb) - offset >= 1) { |
1570 | 9 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_move_up_down_rate, tvb, offset, 1, ENC_LITTLE_ENDIAN); |
1571 | 9 | offset += 1; |
1572 | 9 | } |
1573 | 10 | return offset; |
1574 | 10 | } /* dissect_zbee_nwk_gp_cmd_move_up_down */ |
1575 | | |
1576 | | /** |
1577 | | *Dissector for ZigBee Green Power Step Color. |
1578 | | * |
1579 | | *@param tvb pointer to buffer containing raw packet. |
1580 | | *@param pinfo pointer to packet information fields. |
1581 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1582 | | *@param packet packet data. |
1583 | | *@param offset current payload offset. |
1584 | | *@return payload processed offset. |
1585 | | */ |
1586 | | static unsigned |
1587 | | dissect_zbee_nwk_gp_cmd_step_color(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, |
1588 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset) |
1589 | 2 | { |
1590 | 2 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_step_color_stepx, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
1591 | 2 | offset += 2; |
1592 | 2 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_step_color_stepy, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
1593 | 2 | offset += 2; |
1594 | | /* Optional time field. */ |
1595 | 2 | if (tvb_reported_length(tvb) - offset >= 2) { |
1596 | 2 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_step_color_transition_time, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
1597 | 2 | offset += 2; |
1598 | 2 | } |
1599 | 2 | return offset; |
1600 | 2 | } /* dissect_zbee_nwk_gp_cmd_step_color */ |
1601 | | |
1602 | | /** |
1603 | | *Dissector for ZigBee Green Power Step Up/Down. |
1604 | | * |
1605 | | *@param tvb pointer to buffer containing raw packet. |
1606 | | *@param pinfo pointer to packet information fields. |
1607 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1608 | | *@param packet packet data. |
1609 | | *@param offset current payload offset. |
1610 | | *@return payload processed offset. |
1611 | | */ |
1612 | | static unsigned |
1613 | | dissect_zbee_nwk_gp_cmd_step_up_down(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree, |
1614 | | zbee_nwk_green_power_packet *packet _U_, unsigned offset) |
1615 | 9 | { |
1616 | 9 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_step_up_down_step_size, tvb, offset, 1, ENC_LITTLE_ENDIAN); |
1617 | 9 | offset += 1; |
1618 | | /* Optional time field. */ |
1619 | 9 | if (tvb_reported_length(tvb) - offset >= 2) { |
1620 | 8 | proto_tree_add_item(tree, hf_zbee_nwk_gp_cmd_step_up_down_transition_time, tvb, offset, 2, ENC_LITTLE_ENDIAN); |
1621 | 8 | offset += 2; |
1622 | 8 | } |
1623 | 9 | return offset; |
1624 | 9 | } /* dissect_zbee_nwk_gp_cmd_step_up_down */ |
1625 | | |
1626 | | /** |
1627 | | *Dissector for ZigBee Green Power commands. |
1628 | | * |
1629 | | *@param tvb pointer to buffer containing raw packet. |
1630 | | *@param pinfo pointer to packet information fields. |
1631 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1632 | | *@param data raw packet private data. |
1633 | | *@return payload processed offset |
1634 | | */ |
1635 | | static int |
1636 | | dissect_zbee_nwk_gp_cmd(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data) |
1637 | 797 | { |
1638 | 797 | unsigned offset = 0; |
1639 | 797 | uint8_t cmd_id = tvb_get_uint8(tvb, offset); |
1640 | 797 | proto_item *cmd_root; |
1641 | 797 | proto_tree *cmd_tree; |
1642 | 797 | zbee_nwk_green_power_packet *packet = (zbee_nwk_green_power_packet *)data; |
1643 | | |
1644 | | /* Create a subtree for the command. */ |
1645 | 797 | cmd_tree = proto_tree_add_subtree_format(tree, tvb, offset, -1, ett_zbee_nwk_cmd, &cmd_root, |
1646 | 797 | "Command Frame: %s", val_to_str_ext_const(cmd_id, |
1647 | 797 | &zbee_nwk_gp_cmd_names_ext, |
1648 | 797 | "Unknown Command Frame")); |
1649 | | /* Add the command ID. */ |
1650 | 797 | proto_tree_add_uint(cmd_tree, hf_zbee_nwk_gp_command_id, tvb, offset, 1, cmd_id); |
1651 | | |
1652 | 797 | offset += 1; |
1653 | | /* Add the command name to the info column. */ |
1654 | 797 | col_set_str(pinfo->cinfo, COL_INFO, val_to_str_ext_const(cmd_id, &zbee_nwk_gp_cmd_names_ext, "Unknown command")); |
1655 | | /* Handle the command for one of the following devices: |
1656 | | * - Door Lock Controller (IDs: 0x50 - 0x51); |
1657 | | * - GP Flow Sensor (IDs: 0xE0, 0xA0 - 0xA3); |
1658 | | * - GP Temperature Sensor (IDs: 0xE0, 0xA0 - 0xA3); */ |
1659 | 797 | switch(cmd_id) { |
1660 | | /* Payloadless GPDF commands sent by GPD. */ |
1661 | 4 | case ZB_GP_CMD_ID_IDENTIFY: |
1662 | 4 | case ZB_GP_CMD_ID_RECALL_SCENE0: |
1663 | 4 | case ZB_GP_CMD_ID_RECALL_SCENE1: |
1664 | 4 | case ZB_GP_CMD_ID_RECALL_SCENE2: |
1665 | 4 | case ZB_GP_CMD_ID_RECALL_SCENE3: |
1666 | 4 | case ZB_GP_CMD_ID_RECALL_SCENE4: |
1667 | 4 | case ZB_GP_CMD_ID_RECALL_SCENE5: |
1668 | 4 | case ZB_GP_CMD_ID_RECALL_SCENE6: |
1669 | 4 | case ZB_GP_CMD_ID_RECALL_SCENE7: |
1670 | 4 | case ZB_GP_CMD_ID_STORE_SCENE0: |
1671 | 4 | case ZB_GP_CMD_ID_STORE_SCENE1: |
1672 | 4 | case ZB_GP_CMD_ID_STORE_SCENE2: |
1673 | 4 | case ZB_GP_CMD_ID_STORE_SCENE3: |
1674 | 4 | case ZB_GP_CMD_ID_STORE_SCENE4: |
1675 | 4 | case ZB_GP_CMD_ID_STORE_SCENE5: |
1676 | 4 | case ZB_GP_CMD_ID_STORE_SCENE6: |
1677 | 4 | case ZB_GP_CMD_ID_STORE_SCENE7: |
1678 | 4 | case ZB_GP_CMD_ID_OFF: |
1679 | 4 | case ZB_GP_CMD_ID_ON: |
1680 | 4 | case ZB_GP_CMD_ID_TOGGLE: |
1681 | 4 | case ZB_GP_CMD_ID_RELEASE: |
1682 | 4 | case ZB_GP_CMD_ID_LEVEL_CONTROL_STOP: |
1683 | 4 | case ZB_GP_CMD_ID_MOVE_HUE_STOP: |
1684 | 4 | case ZB_GP_CMD_ID_MOVE_SATURATION_STOP: |
1685 | 4 | case ZB_GP_CMD_ID_LOCK_DOOR: |
1686 | 4 | case ZB_GP_CMD_ID_UNLOCK_DOOR: |
1687 | 4 | case ZB_GP_CMD_ID_PRESS11: |
1688 | 4 | case ZB_GP_CMD_ID_RELEASE11: |
1689 | 4 | case ZB_GP_CMD_ID_PRESS12: |
1690 | 4 | case ZB_GP_CMD_ID_RELEASE12: |
1691 | 4 | case ZB_GP_CMD_ID_PRESS22: |
1692 | 4 | case ZB_GP_CMD_ID_RELEASE22: |
1693 | 4 | case ZB_GP_CMD_ID_SHORT_PRESS11: |
1694 | 4 | case ZB_GP_CMD_ID_SHORT_PRESS12: |
1695 | 4 | case ZB_GP_CMD_ID_SHORT_PRESS22: |
1696 | 4 | case ZB_GP_CMD_ID_DECOMMISSIONING: |
1697 | 4 | case ZB_GP_CMD_ID_SUCCESS: |
1698 | 4 | break; |
1699 | | /* GPDF commands with payload sent by GPD. */ |
1700 | 1 | case ZB_GP_CMD_ID_MOVE_UP: |
1701 | 2 | case ZB_GP_CMD_ID_MOVE_DOWN: |
1702 | 2 | case ZB_GP_CMD_ID_MOVE_UP_WITH_ON_OFF: |
1703 | 3 | case ZB_GP_CMD_ID_MOVE_DOWN_WITH_ON_OFF: |
1704 | 6 | case ZB_GP_CMD_ID_MOVE_HUE_UP: |
1705 | 7 | case ZB_GP_CMD_ID_MOVE_HUE_DOWN: |
1706 | 8 | case ZB_GP_CMD_ID_MOVE_SATURATION_UP: |
1707 | 10 | case ZB_GP_CMD_ID_MOVE_SATURATION_DOWN: |
1708 | 10 | offset = dissect_zbee_nwk_gp_cmd_move_up_down(tvb, pinfo, cmd_tree, packet, offset); |
1709 | 10 | break; |
1710 | 2 | case ZB_GP_CMD_ID_STEP_UP: |
1711 | 3 | case ZB_GP_CMD_ID_STEP_DOWN: |
1712 | 3 | case ZB_GP_CMD_ID_STEP_UP_WITH_ON_OFF: |
1713 | 4 | case ZB_GP_CMD_ID_STEP_DOWN_WITH_ON_OFF: |
1714 | 5 | case ZB_GP_CMD_ID_STEP_HUE_UP: |
1715 | 6 | case ZB_GP_CMD_ID_STEP_HUW_DOWN: |
1716 | 7 | case ZB_GP_CMD_ID_STEP_SATURATION_UP: |
1717 | 9 | case ZB_GP_CMD_ID_STEP_SATURATION_DOWN: |
1718 | 9 | offset = dissect_zbee_nwk_gp_cmd_step_up_down(tvb, pinfo, cmd_tree, packet, offset); |
1719 | 9 | break; |
1720 | 1 | case ZB_GP_CMD_ID_MOVE_COLOR: |
1721 | 1 | offset = dissect_zbee_nwk_gp_cmd_move_color(tvb, pinfo, cmd_tree, packet, offset); |
1722 | 1 | break; |
1723 | 2 | case ZB_GP_CMD_ID_STEP_COLOR: |
1724 | 2 | offset = dissect_zbee_nwk_gp_cmd_step_color(tvb, pinfo, cmd_tree, packet, offset); |
1725 | 2 | break; |
1726 | 19 | case ZB_GP_CMD_ID_ATTRIBUTE_REPORTING: |
1727 | 19 | offset = dissect_zbee_nwk_gp_cmd_attr_reporting(tvb, pinfo, cmd_tree, packet, offset, ZBEE_MFG_CODE_NONE); |
1728 | 19 | break; |
1729 | 11 | case ZB_GP_CMD_ID_MANUFACTURE_SPECIFIC_ATTR_REPORTING: |
1730 | 11 | offset = dissect_zbee_nwk_gp_cmd_MS_attr_reporting(tvb, pinfo, cmd_tree, packet, offset); |
1731 | 11 | break; |
1732 | 151 | case ZB_GP_CMD_ID_MULTI_CLUSTER_REPORTING: |
1733 | 151 | offset = dissect_zbee_nwk_gp_cmd_multi_cluster_reporting(tvb, pinfo, cmd_tree, packet, offset, ZBEE_MFG_CODE_NONE); |
1734 | 151 | break; |
1735 | 3 | case ZB_GP_CMD_ID_MANUFACTURER_SPECIFIC_MCLUSTER_REPORTING: |
1736 | 3 | offset = dissect_zbee_nwk_gp_cmd_MS_multi_cluster_reporting(tvb, pinfo, cmd_tree, packet, offset); |
1737 | 3 | break; |
1738 | 156 | case ZB_GP_CMD_ID_READ_ATTRIBUTES_RESPONSE: |
1739 | 156 | offset = dissect_zbee_nwk_gp_cmd_read_attributes_response(tvb, pinfo, cmd_tree, packet, offset); |
1740 | 156 | break; |
1741 | 1 | case ZB_GP_CMD_ID_ZCL_TUNNELING: |
1742 | 1 | offset = dissect_zbee_nwk_gp_cmd_zcl_tunneling(tvb, pinfo, cmd_tree, packet, offset); |
1743 | 1 | break; |
1744 | 0 | case ZB_GP_CMD_ID_ANY_SENSOR_COMMAND_A0_A3: |
1745 | | /* TODO: implement it. */ |
1746 | 0 | break; |
1747 | 10 | case ZB_GP_CMD_ID_COMMISSIONING: |
1748 | 10 | offset = dissect_zbee_nwk_gp_cmd_commissioning(tvb, pinfo, cmd_tree, packet, offset); |
1749 | 10 | break; |
1750 | 1 | case ZB_GP_CMD_ID_CHANNEL_REQUEST: |
1751 | 1 | offset = dissect_zbee_nwk_gp_cmd_channel_request(tvb, pinfo, cmd_tree, packet, offset); |
1752 | 1 | break; |
1753 | 25 | case ZB_GP_CMD_ID_REQUEST_ATTRIBUTES: |
1754 | | /* GPDF commands sent to GPD. */ |
1755 | 26 | case ZB_GP_CMD_ID_READ_ATTRIBUTES: |
1756 | 26 | offset = dissect_zbee_nwk_gp_cmd_read_attributes(tvb, pinfo, cmd_tree, packet, offset); |
1757 | 26 | break; |
1758 | 3 | case ZB_GP_CMD_ID_COMMISSIONING_REPLY: |
1759 | 3 | offset = dissect_zbee_nwk_gp_cmd_commissioning_reply(tvb, pinfo, cmd_tree, packet, offset); |
1760 | 3 | break; |
1761 | 368 | case ZB_GP_CMD_ID_WRITE_ATTRIBUTES: |
1762 | 368 | offset = dissect_zbee_nwk_gp_cmd_write_attributes(tvb, pinfo, cmd_tree, packet, offset); |
1763 | 368 | break; |
1764 | 1 | case ZB_GP_CMD_ID_CHANNEL_CONFIGURATION: |
1765 | 1 | offset = dissect_zbee_nwk_gp_cmd_channel_configuration(tvb, pinfo, cmd_tree, packet, offset); |
1766 | 1 | break; |
1767 | 797 | } |
1768 | 124 | if (offset < tvb_reported_length(tvb)) { |
1769 | | /* There are leftover bytes! */ |
1770 | 69 | proto_tree *root; |
1771 | 69 | tvbuff_t *leftover_tvb = tvb_new_subset_remaining(tvb, offset); |
1772 | | |
1773 | | /* Correct the length of the command tree. */ |
1774 | 69 | root = proto_tree_get_root(tree); |
1775 | 69 | proto_item_set_len(cmd_root, offset); |
1776 | | |
1777 | | /* Dump the tail. */ |
1778 | 69 | call_data_dissector(leftover_tvb, pinfo, root); |
1779 | 69 | } |
1780 | 124 | return offset; |
1781 | 797 | } /* dissect_zbee_nwk_gp_cmd */ |
1782 | | |
1783 | | /** |
1784 | | *ZigBee NWK packet dissection routine for Green Power profile. |
1785 | | * |
1786 | | *@param tvb pointer to buffer containing raw packet. |
1787 | | *@param pinfo pointer to packet information fields. |
1788 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1789 | | *@param data raw packet private data. |
1790 | | */ |
1791 | | static int |
1792 | | dissect_zbee_nwk_gp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data) |
1793 | 786 | { |
1794 | 786 | ieee802154_packet *ieee_packet = (ieee802154_packet *)data; |
1795 | 786 | bool gp_decrypted; |
1796 | 786 | GSList *GSList_i; |
1797 | 786 | unsigned offset = 0; |
1798 | 786 | uint8_t *dec_buffer; |
1799 | 786 | uint8_t *enc_buffer; |
1800 | 786 | uint8_t fcf; |
1801 | 786 | proto_tree *nwk_tree; |
1802 | 786 | proto_item *proto_root; |
1803 | 786 | proto_item *ti = NULL; |
1804 | 786 | tvbuff_t *payload_tvb; |
1805 | 786 | zbee_nwk_green_power_packet packet; |
1806 | 786 | static int * const fields[] = { |
1807 | 786 | &hf_zbee_nwk_gp_frame_type, |
1808 | 786 | &hf_zbee_nwk_gp_proto_version, |
1809 | 786 | &hf_zbee_nwk_gp_auto_commissioning, |
1810 | 786 | &hf_zbee_nwk_gp_fc_ext, |
1811 | 786 | NULL |
1812 | 786 | }; |
1813 | 786 | static int * const ext_fields[] = { |
1814 | 786 | &hf_zbee_nwk_gp_fc_ext_app_id, |
1815 | 786 | &hf_zbee_nwk_gp_fc_ext_sec_level, |
1816 | 786 | &hf_zbee_nwk_gp_fc_ext_sec_key, |
1817 | 786 | &hf_zbee_nwk_gp_fc_ext_rx_after_tx, |
1818 | 786 | &hf_zbee_nwk_gp_fc_ext_direction, |
1819 | 786 | NULL |
1820 | 786 | }; |
1821 | | |
1822 | 786 | if (data == NULL) |
1823 | 0 | return 0; |
1824 | | |
1825 | 786 | memset(&packet, 0, sizeof(packet)); |
1826 | 786 | packet.ieee_packet_src64 = ieee_packet->src64; |
1827 | | /* Add ourself to the protocol column, clear the info column and create the protocol tree. */ |
1828 | 786 | col_set_str(pinfo->cinfo, COL_PROTOCOL, "ZigBee Green Power"); |
1829 | 786 | col_clear(pinfo->cinfo, COL_INFO); |
1830 | | |
1831 | 786 | proto_root = proto_tree_add_protocol_format(tree, proto_zbee_nwk_gp, tvb, offset, tvb_captured_length(tvb), |
1832 | 786 | "ZGP stub NWK header"); |
1833 | 786 | nwk_tree = proto_item_add_subtree(proto_root, ett_zbee_nwk); |
1834 | | |
1835 | 786 | enc_buffer = (uint8_t *)tvb_memdup(pinfo->pool, tvb, 0, tvb_captured_length(tvb)); |
1836 | | /* Get and parse the FCF. */ |
1837 | 786 | fcf = tvb_get_uint8(tvb, offset); |
1838 | 786 | packet.frame_type = zbee_get_bit_field(fcf, ZBEE_NWK_GP_FCF_FRAME_TYPE); |
1839 | 786 | packet.nwk_frame_control_extension = zbee_get_bit_field(fcf, ZBEE_NWK_GP_FCF_CONTROL_EXTENSION); |
1840 | | |
1841 | | /* Display the FCF. */ |
1842 | 786 | ti = proto_tree_add_bitmask(nwk_tree, tvb, offset, hf_zbee_nwk_gp_fcf, ett_zbee_nwk_fcf, fields, ENC_NA); |
1843 | 786 | proto_item_append_text(ti, " %s", val_to_str_const(packet.frame_type, zbee_nwk_gp_frame_types, "Unknown Frame Type")); |
1844 | 786 | offset += 1; |
1845 | | |
1846 | | /* Add the frame type to the info column and protocol root. */ |
1847 | 786 | proto_item_append_text(proto_root, " %s", val_to_str_const(packet.frame_type, zbee_nwk_gp_frame_types, "Unknown type")); |
1848 | 786 | col_set_str(pinfo->cinfo, COL_INFO, val_to_str_const(packet.frame_type, zbee_nwk_gp_frame_types, "Reserved frame type")); |
1849 | | |
1850 | 786 | if (packet.nwk_frame_control_extension) { |
1851 | | /* Display ext FCF. */ |
1852 | 743 | fcf = tvb_get_uint8(tvb, offset); |
1853 | 743 | packet.application_id = zbee_get_bit_field(fcf, ZBEE_NWK_GP_FCF_EXT_APP_ID); |
1854 | 743 | packet.security_level = zbee_get_bit_field(fcf, ZBEE_NWK_GP_FCF_EXT_SECURITY_LEVEL); |
1855 | 743 | packet.direction = zbee_get_bit_field(fcf, ZBEE_NWK_GP_FCF_EXT_DIRECTION); |
1856 | | |
1857 | | /* Create a subtree for the extended FCF. */ |
1858 | 743 | proto_tree_add_bitmask(nwk_tree, tvb, offset, hf_zbee_nwk_gp_fc_ext_field, ett_zbee_nwk_fcf_ext, ext_fields, ENC_NA); |
1859 | 743 | offset += 1; |
1860 | 743 | } |
1861 | 786 | if ((packet.frame_type == ZBEE_NWK_GP_FCF_DATA && !packet.nwk_frame_control_extension) || (packet.frame_type == |
1862 | 744 | ZBEE_NWK_GP_FCF_DATA && packet.nwk_frame_control_extension && packet.application_id == |
1863 | 731 | ZBEE_NWK_GP_APP_ID_DEFAULT) || (packet.frame_type == ZBEE_NWK_GP_FCF_MAINTENANCE && |
1864 | 436 | packet.nwk_frame_control_extension && packet.application_id == ZBEE_NWK_GP_APP_ID_DEFAULT && tvb_get_uint8(tvb, |
1865 | 58 | offset) != ZB_GP_CMD_ID_CHANNEL_CONFIGURATION)) { |
1866 | | /* Display GPD Src ID. */ |
1867 | 58 | packet.source_id = tvb_get_letohl(tvb, offset); |
1868 | 58 | proto_tree_add_item(nwk_tree, hf_zbee_nwk_gp_zgpd_src_id, tvb, offset, 4, ENC_LITTLE_ENDIAN); |
1869 | 58 | proto_item_append_text(proto_root, ", GPD Src ID: 0x%08x", packet.source_id); |
1870 | | |
1871 | 58 | col_append_fstr(pinfo->cinfo, COL_INFO, ", GPD Src ID: 0x%08x", packet.source_id); |
1872 | | |
1873 | 58 | col_clear(pinfo->cinfo, COL_DEF_SRC); |
1874 | 58 | col_append_fstr(pinfo->cinfo, COL_DEF_SRC, "0x%08x", packet.source_id); |
1875 | | |
1876 | 58 | offset += 4; |
1877 | 58 | } |
1878 | 786 | if (packet.application_id == ZBEE_NWK_GP_APP_ID_ZGP) { |
1879 | | /* Display GPD endpoint */ |
1880 | 85 | packet.endpoint = tvb_get_uint8(tvb, offset); |
1881 | 85 | proto_tree_add_item(nwk_tree, hf_zbee_nwk_gp_zgpd_endpoint, tvb, offset, 1, ENC_LITTLE_ENDIAN); |
1882 | 85 | proto_item_append_text(proto_root, ", Endpoint: %d", packet.endpoint); |
1883 | | |
1884 | 85 | col_append_fstr(pinfo->cinfo, COL_INFO, ", Endpoint: %d", packet.endpoint); |
1885 | 85 | offset += 1; |
1886 | 85 | } |
1887 | | /* Display Security Frame Counter. */ |
1888 | 786 | packet.mic_size = 0; |
1889 | 786 | if (packet.nwk_frame_control_extension) { |
1890 | 743 | if (packet.application_id == ZBEE_NWK_GP_APP_ID_DEFAULT || packet.application_id == ZBEE_NWK_GP_APP_ID_ZGP |
1891 | 642 | || packet.application_id == ZBEE_NWK_GP_APP_ID_LPED) { |
1892 | 328 | if (packet.security_level == ZBEE_NWK_GP_SECURITY_LEVEL_1LSB |
1893 | 9 | && packet.application_id != ZBEE_NWK_GP_APP_ID_LPED) { |
1894 | 6 | packet.mic_size = 2; |
1895 | 322 | } else if (packet.security_level == ZBEE_NWK_GP_SECURITY_LEVEL_FULL || packet.security_level == |
1896 | 315 | ZBEE_NWK_GP_SECURITY_LEVEL_FULLENCR) { |
1897 | | /* Get Security Frame Counter and display it. */ |
1898 | 11 | packet.mic_size = 4; |
1899 | 11 | packet.security_frame_counter = tvb_get_letohl(tvb, offset); |
1900 | 11 | proto_tree_add_item(nwk_tree, hf_zbee_nwk_gp_security_frame_counter, tvb, offset, 4, |
1901 | 11 | ENC_LITTLE_ENDIAN); |
1902 | 11 | offset += 4; |
1903 | 11 | } |
1904 | 328 | } |
1905 | 743 | } |
1906 | | /* Parse application payload. */ |
1907 | | /* This is a uint8_t, but tvb_reported_length might be larger; e.g., |
1908 | | * SCOP over TCP, presumably with errors. It's bogus either way; perhaps |
1909 | | * we should warn. |
1910 | | */ |
1911 | 786 | packet.payload_len = tvb_reported_length(tvb) - offset - packet.mic_size; |
1912 | | /* Ensure that the payload exists. */ |
1913 | 786 | if (packet.payload_len <= 0) { |
1914 | 1 | proto_tree_add_expert_remaining(nwk_tree, pinfo, &ei_zbee_nwk_gp_no_payload, tvb, 0); |
1915 | 1 | return offset; |
1916 | 1 | } |
1917 | | /* OK, payload exists. Parse MIC field if needed. */ |
1918 | 785 | if (packet.mic_size == 2) { |
1919 | 6 | packet.mic = tvb_get_letohs(tvb, offset + packet.payload_len); |
1920 | 779 | } else if (packet.mic_size == 4) { |
1921 | 11 | packet.mic = tvb_get_letohl(tvb, offset + packet.payload_len); |
1922 | 11 | } |
1923 | | /* Save packet private data. */ |
1924 | 785 | data = (void *)&packet; |
1925 | 785 | payload_tvb = tvb_new_subset_length(tvb, offset, packet.payload_len); |
1926 | 785 | if (packet.security_level != ZBEE_NWK_GP_SECURITY_LEVEL_FULLENCR) { |
1927 | 774 | dissect_zbee_nwk_gp_cmd(payload_tvb, pinfo, nwk_tree, data); |
1928 | 774 | } |
1929 | 785 | offset += packet.payload_len; |
1930 | | /* Display MIC field. */ |
1931 | 785 | if (packet.mic_size) { |
1932 | 6 | proto_tree_add_uint(nwk_tree, packet.mic_size == 4 ? hf_zbee_nwk_gp_security_mic_4b : |
1933 | 6 | hf_zbee_nwk_gp_security_mic_2b, tvb, offset, packet.mic_size, packet.mic); |
1934 | 6 | offset += packet.mic_size; |
1935 | 6 | } |
1936 | 785 | if ((offset < tvb_captured_length(tvb)) && (packet.security_level != ZBEE_NWK_GP_SECURITY_LEVEL_FULLENCR)) { |
1937 | 14 | proto_tree_add_expert_remaining(nwk_tree, pinfo, &ei_zbee_nwk_gp_inval_residual_data, tvb, offset); |
1938 | 14 | return offset; |
1939 | 14 | } |
1940 | 771 | if (packet.security_level == ZBEE_NWK_GP_SECURITY_LEVEL_FULLENCR) { |
1941 | 5 | gp_decrypted = false; |
1942 | | |
1943 | 5 | if (tvb_captured_length(tvb) >= tvb_reported_length(tvb)) { |
1944 | 3 | dec_buffer = (uint8_t *)wmem_alloc(pinfo->pool, packet.payload_len); |
1945 | 4 | for (GSList_i = zbee_gp_keyring; GSList_i && !gp_decrypted; GSList_i = g_slist_next(GSList_i)) { |
1946 | 1 | gp_decrypted = zbee_gp_decrypt_payload(&packet, enc_buffer, offset - packet.payload_len - |
1947 | 1 | packet.mic_size, dec_buffer, packet.payload_len, packet.mic_size, |
1948 | 1 | ((key_record_t *)(GSList_i->data))->key); |
1949 | 1 | } |
1950 | 3 | } |
1951 | | |
1952 | 5 | if (gp_decrypted) { |
1953 | 1 | payload_tvb = tvb_new_child_real_data(tvb, dec_buffer, packet.payload_len, packet.payload_len); |
1954 | 1 | add_new_data_source(pinfo, payload_tvb, "Decrypted GP Payload"); |
1955 | 1 | dissect_zbee_nwk_gp_cmd(payload_tvb, pinfo, nwk_tree, data); |
1956 | 4 | } else { |
1957 | 4 | payload_tvb = tvb_new_subset_length(tvb, offset - packet.payload_len - packet.mic_size, packet.payload_len); |
1958 | 4 | call_data_dissector(payload_tvb, pinfo, tree); |
1959 | 4 | } |
1960 | 5 | } |
1961 | 771 | return tvb_captured_length(tvb); |
1962 | 785 | } /* dissect_zbee_nwk_gp */ |
1963 | | |
1964 | | /** |
1965 | | *Heuristic interpreter for the ZigBee Green Power dissectors. |
1966 | | * |
1967 | | *@param tvb pointer to buffer containing raw packet. |
1968 | | *@param pinfo pointer to packet information fields. |
1969 | | *@param tree pointer to data tree Wireshark uses to display packet. |
1970 | | *@param data raw packet private data. |
1971 | | */ |
1972 | | static bool |
1973 | | dissect_zbee_nwk_heur_gp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data) |
1974 | 1.36k | { |
1975 | 1.36k | ieee802154_packet *packet = (ieee802154_packet *)data; |
1976 | 1.36k | uint8_t fcf; |
1977 | | |
1978 | | /* We must have the IEEE 802.15.4 headers. */ |
1979 | 1.36k | if (packet == NULL) return false; |
1980 | | |
1981 | | /* If the frame type and version are not sane, then it's probably not ZGP. */ |
1982 | 1.36k | fcf = tvb_get_uint8(tvb, 0); |
1983 | 1.36k | if (zbee_get_bit_field(fcf, ZBEE_NWK_GP_FCF_VERSION) != ZBEE_VERSION_GREEN_POWER) return false; |
1984 | 795 | if (!try_val_to_str(zbee_get_bit_field(fcf, ZBEE_NWK_FCF_FRAME_TYPE), zbee_nwk_gp_frame_types)) return false; |
1985 | | |
1986 | | /* ZigBee greenpower frames are either sent to broadcast or the extended address. */ |
1987 | 791 | if (packet->dst_addr_mode == IEEE802154_FCF_ADDR_SHORT && packet->dst16 == IEEE802154_BCAST_ADDR) { |
1988 | 2 | dissect_zbee_nwk_gp(tvb, pinfo, tree, data); |
1989 | 2 | return true; |
1990 | 2 | } |
1991 | | /* 64-bit destination addressing mode support. */ |
1992 | 789 | if (packet->dst_addr_mode == IEEE802154_FCF_ADDR_EXT) { |
1993 | 784 | dissect_zbee_nwk_gp(tvb, pinfo, tree, data); |
1994 | 784 | return true; |
1995 | 784 | } |
1996 | | |
1997 | 5 | return false; |
1998 | 789 | } /* dissect_zbee_nwk_heur_gp */ |
1999 | | |
2000 | | /** |
2001 | | *Init routine for the ZigBee GP profile security. |
2002 | | * |
2003 | | */ |
2004 | | static void |
2005 | | gp_init_zbee_security(void) |
2006 | 15 | { |
2007 | 15 | unsigned i; |
2008 | 15 | key_record_t key_record; |
2009 | | |
2010 | 15 | for (i = 0; gp_uat_key_records && (i < num_uat_key_records); i++) { |
2011 | 0 | key_record.frame_num = 0; |
2012 | 0 | key_record.label = g_strdup(gp_uat_key_records[i].label); |
2013 | 0 | memcpy(key_record.key, gp_uat_key_records[i].key, ZBEE_SEC_CONST_KEYSIZE); |
2014 | 0 | zbee_gp_keyring = g_slist_prepend(zbee_gp_keyring, g_memdup2(&key_record, sizeof(key_record_t))); |
2015 | 0 | } |
2016 | 15 | } |
2017 | | |
2018 | | static void zbee_free_key_record(void *ptr) |
2019 | 0 | { |
2020 | 0 | key_record_t *k; |
2021 | |
|
2022 | 0 | k = (key_record_t *)ptr; |
2023 | 0 | if (!k) |
2024 | 0 | return; |
2025 | | |
2026 | 0 | g_free(k->label); |
2027 | 0 | g_free(k); |
2028 | 0 | } |
2029 | | |
2030 | | static void |
2031 | | gp_cleanup_zbee_security(void) |
2032 | 0 | { |
2033 | 0 | if (!zbee_gp_keyring) |
2034 | 0 | return; |
2035 | | |
2036 | 0 | g_slist_free_full(zbee_gp_keyring, zbee_free_key_record); |
2037 | 0 | zbee_gp_keyring = NULL; |
2038 | 0 | } |
2039 | | |
2040 | | /** |
2041 | | *ZigBee NWK GP protocol registration routine. |
2042 | | * |
2043 | | */ |
2044 | | void |
2045 | | proto_register_zbee_nwk_gp(void) |
2046 | 15 | { |
2047 | 15 | module_t *gp_zbee_prefs; |
2048 | 15 | expert_module_t* expert_zbee_nwk_gp; |
2049 | | |
2050 | 15 | static hf_register_info hf[] = { |
2051 | 15 | { &hf_zbee_nwk_gp_auto_commissioning, |
2052 | 15 | { "Auto Commissioning", "zbee_nwk_gp.auto_commissioning", FT_BOOLEAN, 8, NULL, |
2053 | 15 | ZBEE_NWK_GP_FCF_AUTO_COMMISSIONING, NULL, HFILL }}, |
2054 | | |
2055 | 15 | { &hf_zbee_nwk_gp_fc_ext, |
2056 | 15 | { "NWK Frame Extension", "zbee_nwk_gp.fc_extension", FT_BOOLEAN, 8, NULL, ZBEE_NWK_GP_FCF_CONTROL_EXTENSION, |
2057 | 15 | NULL, HFILL }}, |
2058 | | |
2059 | 15 | { &hf_zbee_nwk_gp_fcf, |
2060 | 15 | { "Frame Control Field", "zbee_nwk_gp.fcf", FT_UINT8, BASE_HEX, NULL, |
2061 | 15 | 0x0, NULL, HFILL }}, |
2062 | | |
2063 | 15 | { &hf_zbee_nwk_gp_frame_type, |
2064 | 15 | { "Frame Type", "zbee_nwk_gp.frame_type", FT_UINT8, BASE_HEX, VALS(zbee_nwk_gp_frame_types), |
2065 | 15 | ZBEE_NWK_GP_FCF_FRAME_TYPE, NULL, HFILL }}, |
2066 | | |
2067 | 15 | { &hf_zbee_nwk_gp_proto_version, |
2068 | 15 | { "Protocol Version", "zbee_nwk_gp.proto_version", FT_UINT8, BASE_DEC, NULL, ZBEE_NWK_GP_FCF_VERSION, NULL, |
2069 | 15 | HFILL }}, |
2070 | | |
2071 | 15 | { &hf_zbee_nwk_gp_fc_ext_field, |
2072 | 15 | { "Extended NWK Frame Control Field", "zbee_nwk_gp.fc_ext", FT_UINT8, BASE_HEX, NULL, |
2073 | 15 | 0x0, NULL, HFILL }}, |
2074 | | |
2075 | 15 | { &hf_zbee_nwk_gp_fc_ext_app_id, |
2076 | 15 | { "Application ID", "zbee_nwk_gp.fc_ext_app_id", FT_UINT8, BASE_HEX, VALS(zbee_nwk_gp_app_id_names), |
2077 | 15 | ZBEE_NWK_GP_FCF_EXT_APP_ID, NULL, HFILL }}, |
2078 | | |
2079 | 15 | { &hf_zbee_nwk_gp_fc_ext_direction, |
2080 | 15 | { "Direction", "zbee_nwk_gp.fc_ext_direction", FT_UINT8, BASE_HEX, VALS(zbee_nwk_gp_directions), |
2081 | 15 | ZBEE_NWK_GP_FCF_EXT_DIRECTION, NULL, HFILL }}, |
2082 | | |
2083 | 15 | { &hf_zbee_nwk_gp_fc_ext_rx_after_tx, |
2084 | 15 | { "Rx After Tx", "zbee_nwk_gp.fc_ext_rxaftertx", FT_BOOLEAN, 8, NULL, ZBEE_NWK_GP_FCF_EXT_RX_AFTER_TX, NULL, |
2085 | 15 | HFILL }}, |
2086 | | |
2087 | 15 | { &hf_zbee_nwk_gp_fc_ext_sec_key, |
2088 | 15 | { "Security Key", "zbee_nwk_gp.fc_ext_security_key", FT_BOOLEAN, 8, NULL, ZBEE_NWK_GP_FCF_EXT_SECURITY_KEY, |
2089 | 15 | NULL, HFILL }}, |
2090 | | |
2091 | 15 | { &hf_zbee_nwk_gp_fc_ext_sec_level, |
2092 | 15 | { "Security Level", "zbee_nwk_gp.fc_ext_security_level", FT_UINT8, BASE_HEX, |
2093 | 15 | VALS(zbee_nwk_gp_src_sec_levels_names), ZBEE_NWK_GP_FCF_EXT_SECURITY_LEVEL, NULL, HFILL }}, |
2094 | | |
2095 | 15 | { &hf_zbee_nwk_gp_zgpd_src_id, |
2096 | 15 | { "Src ID", "zbee_nwk_gp.source_id", FT_UINT32, BASE_HEX, VALS(zbee_nwk_gp_src_id_names), 0x0, NULL, |
2097 | 15 | HFILL }}, |
2098 | | |
2099 | 15 | { &hf_zbee_nwk_gp_zgpd_endpoint, |
2100 | 15 | { "Endpoint", "zbee_nwk_gp.endpoint", FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }}, |
2101 | | |
2102 | 15 | { &hf_zbee_nwk_gp_security_frame_counter, |
2103 | 15 | { "Security Frame Counter", "zbee_nwk_gp.security_frame_counter", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, |
2104 | 15 | HFILL }}, |
2105 | | |
2106 | 15 | { &hf_zbee_nwk_gp_security_mic_2b, |
2107 | 15 | { "Security MIC", "zbee_nwk_gp.security_mic2", FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }}, |
2108 | | |
2109 | 15 | { &hf_zbee_nwk_gp_security_mic_4b, |
2110 | 15 | { "Security MIC", "zbee_nwk_gp.security_mic4", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }}, |
2111 | | |
2112 | 15 | { &hf_zbee_nwk_gp_command_id, |
2113 | 15 | { "ZGPD Command ID", "zbee_nwk_gp.command_id", FT_UINT8, BASE_HEX | BASE_EXT_STRING, &zbee_nwk_gp_cmd_names_ext, 0x0, NULL, |
2114 | 15 | HFILL }}, |
2115 | | |
2116 | 15 | { &hf_zbee_nwk_gp_cmd_comm_device_id, |
2117 | 15 | { "ZGPD Device ID", "zbee_nwk_gp.cmd.comm.dev_id", FT_UINT8, BASE_HEX | BASE_EXT_STRING, &zbee_nwk_gp_device_ids_names_ext, |
2118 | 15 | 0x0, NULL, HFILL }}, |
2119 | | |
2120 | 15 | { &hf_zbee_nwk_gp_cmd_comm_ext_opt_gpd_key_encr, |
2121 | 15 | { "GPD Key Encryption", "zbee_nwk_gp.cmd.comm.ext_opt.gpd_key_encr", FT_BOOLEAN, 8, NULL, |
2122 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_GPD_KEY_ENCR, NULL, HFILL }}, |
2123 | | |
2124 | 15 | { &hf_zbee_nwk_gp_cmd_comm_ext_opt_gpd_key_present, |
2125 | 15 | { "GPD Key Present", "zbee_nwk_gp.cmd.comm.ext_opt.gpd_key_present", FT_BOOLEAN, 8, NULL, |
2126 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_GPD_KEY_PRESENT, NULL, HFILL }}, |
2127 | | |
2128 | 15 | { &hf_zbee_nwk_gp_cmd_comm_ext_opt_key_type, |
2129 | 15 | { "Key Type", "zbee_nwk_gp.cmd.comm.ext_opt.key_type", FT_UINT8, BASE_HEX, |
2130 | 15 | VALS(zbee_nwk_gp_src_sec_keys_type_names), ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_KEY_TYPE, NULL, |
2131 | 15 | HFILL }}, |
2132 | | |
2133 | 15 | { &hf_zbee_nwk_gp_cmd_comm_outgoing_counter, |
2134 | 15 | { "GPD Outgoing Counter", "zbee_nwk_gp.cmd.comm.out_counter", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, |
2135 | 15 | HFILL }}, |
2136 | | |
2137 | 15 | { &hf_zbee_nwk_gp_cmd_comm_ext_opt_sec_level_cap, |
2138 | 15 | { "Security Level Capabilities", "zbee_nwk_gp.cmd.comm.ext_opt.seclevel_cap", FT_UINT8, BASE_HEX, NULL, |
2139 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_SEC_LEVEL_CAP, NULL, HFILL }}, |
2140 | | |
2141 | 15 | { &hf_zbee_nwk_gp_cmd_comm_security_key, |
2142 | 15 | { "Security Key", "zbee_nwk_gp.cmd.comm.security_key", FT_BYTES, BASE_NONE, NULL, 0x0, NULL, HFILL }}, |
2143 | | |
2144 | 15 | { &hf_zbee_nwk_gp_cmd_comm_gpd_sec_key_mic, |
2145 | 15 | { "GPD Key MIC", "zbee_nwk_gp.cmd.comm.gpd_key_mic", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }}, |
2146 | | |
2147 | 15 | { &hf_zbee_nwk_gp_cmd_comm_opt_ext_opt, |
2148 | 15 | { "Extended Option Field", "zbee_nwk_gp.cmd.comm.opt.ext_opt_field", FT_BOOLEAN, 8, NULL, |
2149 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_EXT_OPTIONS, NULL, HFILL }}, |
2150 | | |
2151 | 15 | { &hf_zbee_nwk_gp_cmd_comm_opt, |
2152 | 15 | { "Options Field", "zbee_nwk_gp.cmd.comm.opt", FT_UINT8, BASE_HEX, NULL, |
2153 | 15 | 0x0, NULL, HFILL }}, |
2154 | | |
2155 | 15 | { &hf_zbee_nwk_gp_cmd_comm_opt_fixed_location, |
2156 | 15 | { "Fixed Location", "zbee_nwk_gp.cmd.comm.opt.fixed_location", FT_BOOLEAN, 8, NULL, |
2157 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_FIXED_LOCATION, NULL, HFILL }}, |
2158 | | |
2159 | 15 | { &hf_zbee_nwk_gp_cmd_comm_opt_mac_sec_num_cap, |
2160 | 15 | { "MAC Sequence number capability", "zbee_nwk_gp.cmd.comm.opt.mac_seq_num_cap", FT_BOOLEAN, 8, NULL, |
2161 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_MAC_SEQ, NULL, HFILL }}, |
2162 | | |
2163 | 15 | { &hf_zbee_nwk_gp_cmd_comm_opt_appli_info_present, |
2164 | 15 | { "Application information present", "zbee_nwk_gp.cmd.comm.opt.appli_info_present", FT_BOOLEAN, 8, NULL, |
2165 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_APPLICATION_INFO, NULL, HFILL }}, |
2166 | | |
2167 | 15 | { &hf_zbee_nwk_gp_cmd_comm_opt_panid_req, |
2168 | 15 | { "PANId request", "zbee_nwk_gp.cmd.comm.opt.panid_req", FT_BOOLEAN, 8, NULL, |
2169 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_PAN_ID_REQ, NULL, HFILL }}, |
2170 | | |
2171 | 15 | { &hf_zbee_nwk_gp_cmd_comm_opt_rx_on_cap, |
2172 | 15 | { "RxOnCapability", "zbee_nwk_gp.cmd.comm.opt.rxon_cap", FT_BOOLEAN, 8, NULL, |
2173 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_RX_ON_CAP, NULL, HFILL }}, |
2174 | | |
2175 | 15 | { &hf_zbee_nwk_gp_cmd_comm_opt_sec_key_req, |
2176 | 15 | { "GP Security Key Request", "zbee_nwk_gp.cmd.comm.opt.seq_key_req", FT_BOOLEAN, 8, NULL, |
2177 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_OPT_GP_SEC_KEY_REQ, NULL, HFILL }}, |
2178 | | |
2179 | 15 | { &hf_zbee_nwk_gp_cmd_comm_ext_opt, |
2180 | 15 | { "Extended Options Field", "zbee_nwk_gp.cmd.comm.ext_opt", FT_UINT8, BASE_HEX, NULL, |
2181 | 15 | 0x0, NULL, HFILL }}, |
2182 | | |
2183 | 15 | { &hf_zbee_nwk_gp_cmd_comm_ext_opt_outgoing_counter, |
2184 | 15 | { "GPD Outgoing present", "zbee_nwk_gp.cmd.comm.ext_opt.outgoing_counter", FT_BOOLEAN, 8, NULL, |
2185 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_EXT_OPT_OUT_COUNTER, NULL, HFILL }}, |
2186 | | |
2187 | 15 | { &hf_zbee_nwk_gp_cmd_comm_manufacturer_greenpeak_dev_id, |
2188 | 15 | { "Manufacturer Model ID", "zbee_nwk_gp.cmd.comm.manufacturer_model_id", FT_UINT16, BASE_HEX, |
2189 | 15 | VALS(zbee_nwk_gp_manufacturer_greenpeak_dev_names), 0x0, NULL, HFILL }}, |
2190 | | |
2191 | 15 | { &hf_zbee_nwk_gp_cmd_comm_manufacturer_dev_id, |
2192 | 15 | { "Manufacturer Model ID", "zbee_nwk_gp.cmd.comm.manufacturer_model_id", FT_UINT16, BASE_HEX, |
2193 | 15 | NULL, 0x0, NULL, HFILL }}, |
2194 | | |
2195 | 15 | { &hf_zbee_nwk_gp_cmd_comm_manufacturer_id, |
2196 | 15 | { "Manufacturer ID", "zbee_nwk_gp.cmd.comm.manufacturer_id", FT_UINT16, BASE_HEX, |
2197 | 15 | VALS(zbee_mfr_code_names), 0x0, NULL, HFILL }}, |
2198 | | |
2199 | 15 | { &hf_zbee_nwk_gp_cmd_comm_appli_info_crp, |
2200 | 15 | { "Cluster reports present", "zbee_nwk_gp.cmd.comm.appli_info.crp", FT_BOOLEAN, 8, NULL, |
2201 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_APPLI_INFO_CRP , NULL, HFILL }}, |
2202 | | |
2203 | 15 | { &hf_zbee_nwk_gp_cmd_comm_appli_info_gclp, |
2204 | 15 | { "GP commands list present", "zbee_nwk_gp.cmd.comm.appli_info.gclp", FT_BOOLEAN, 8, NULL, |
2205 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_APPLI_INFO_GCLP , NULL, HFILL }}, |
2206 | | |
2207 | 15 | { &hf_zbee_nwk_gp_cmd_comm_appli_info, |
2208 | 15 | { "Application information Field", "zbee_nwk_gp.cmd.comm.appli_info", FT_UINT8, BASE_HEX, NULL, |
2209 | 15 | 0x0, NULL, HFILL }}, |
2210 | | |
2211 | 15 | { &hf_zbee_nwk_gp_cmd_comm_appli_info_mip, |
2212 | 15 | { "Manufacturer ID present", "zbee_nwk_gp.cmd.comm.appli_info.mip", FT_BOOLEAN, 8, NULL, |
2213 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_APPLI_INFO_MIP , NULL, HFILL }}, |
2214 | | |
2215 | 15 | { &hf_zbee_nwk_gp_cmd_comm_appli_info_mmip, |
2216 | 15 | { "Manufacturer Model ID present", "zbee_nwk_gp.cmd.comm.appli_info.mmip", FT_BOOLEAN, 8, NULL, |
2217 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_APPLI_INFO_MMIP , NULL, HFILL }}, |
2218 | | |
2219 | 15 | { &hf_zbee_nwk_gp_cmd_comm_gpd_cmd_num, |
2220 | 15 | { "Number of GPD commands", "zbee_nwk_gp.cmd.comm.gpd_cmd_num", FT_UINT8, BASE_DEC, NULL, |
2221 | 15 | 0x0 , NULL, HFILL }}, |
2222 | | |
2223 | 15 | { &hf_zbee_nwk_gp_cmd_comm_gpd_cmd_id_list, |
2224 | 15 | { "GPD CommandID list", "zbee_nwk_gp.cmd.comm.gpd_cmd_id_list", FT_NONE, BASE_NONE, NULL, |
2225 | 15 | 0x0 , NULL, HFILL }}, |
2226 | | |
2227 | 15 | { &hf_zbee_nwk_gp_cmd_comm_length_of_clid_list, |
2228 | 15 | { "Length of ClusterID list", "zbee_nwk_gp.cmd.comm.length_of_clid_list", FT_UINT8, BASE_HEX, NULL, |
2229 | 15 | 0x0 , NULL, HFILL }}, |
2230 | | |
2231 | 15 | { &hf_zbee_nwk_gp_cmd_comm_length_of_clid_list_server, |
2232 | 15 | { "Number of server ClusterIDs", "zbee_nwk_gp.cmd.comm.length_of_clid_list_srv", FT_UINT8, BASE_DEC, NULL, |
2233 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_CLID_LIST_LEN_SRV, NULL, HFILL }}, |
2234 | | |
2235 | 15 | { &hf_zbee_nwk_gp_cmd_comm_length_of_clid_list_client, |
2236 | 15 | { "Number of client ClusterIDs", "zbee_nwk_gp.cmd.comm.length_of_clid_list_cli", FT_UINT8, BASE_DEC, NULL, |
2237 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_CLID_LIST_LEN_CLI, NULL, HFILL }}, |
2238 | | |
2239 | 15 | { &hf_zbee_nwk_cmd_comm_clid_list_server, |
2240 | 15 | { "Cluster ID List Server", "zbee_nwk_gp.cmd.comm.clid_list_server", FT_NONE, BASE_NONE, NULL, |
2241 | 15 | 0x0 , NULL, HFILL }}, |
2242 | | |
2243 | 15 | { &hf_zbee_nwk_cmd_comm_clid_list_client, |
2244 | 15 | { "ClusterID List Client", "zbee_nwk_gp.cmd.comm.clid_list_client", FT_NONE, BASE_NONE, NULL, |
2245 | 15 | 0x0 , NULL, HFILL }}, |
2246 | | |
2247 | 15 | { &hf_zbee_nwk_cmd_comm_cluster_id, |
2248 | 15 | { "Cluster ID", "zbee_nwk_gp.cmd.comm.cluster_id", FT_UINT16, BASE_HEX, NULL, |
2249 | 15 | 0x0 , NULL, HFILL }}, |
2250 | | |
2251 | 15 | { &hf_zbee_nwk_gp_cmd_comm_rep_opt_key_encr, |
2252 | 15 | { "GPD Key Encryption", "zbee_nwk_gp.cmd.comm_reply.opt.sec_key_encr", FT_BOOLEAN, 8, NULL, |
2253 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_KEY_ENCR, NULL, HFILL }}, |
2254 | | |
2255 | 15 | { &hf_zbee_nwk_gp_cmd_comm_rep_opt, |
2256 | 15 | { "Options Field", "zbee_nwk_gp.cmd.comm_reply.opt", FT_UINT8, BASE_HEX, NULL, |
2257 | 15 | 0x0, NULL, HFILL }}, |
2258 | | |
2259 | 15 | { &hf_zbee_nwk_gp_cmd_comm_rep_opt_panid_present, |
2260 | 15 | { "PANID Present", "zbee_nwk_gp.cmd.comm_reply.opt.pan_id_present", FT_BOOLEAN, 8, NULL, |
2261 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_PAN_ID_PRESENT, NULL, HFILL }}, |
2262 | | |
2263 | 15 | { &hf_zbee_nwk_gp_cmd_comm_rep_opt_sec_key_present, |
2264 | 15 | { "GPD Security Key Present", "zbee_nwk_gp.cmd.comm_reply.opt.sec_key_present", FT_BOOLEAN, 8, NULL, |
2265 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_SEC_KEY_PRESENT, NULL, HFILL }}, |
2266 | | |
2267 | 15 | { &hf_zbee_nwk_gp_cmd_comm_rep_opt_sec_level, |
2268 | 15 | { "Security Level", "zbee_nwk_gp.cmd.comm_reply.opt.sec_level", FT_UINT8, BASE_HEX, NULL, |
2269 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_SEC_LEVEL, NULL, HFILL }}, |
2270 | | |
2271 | 15 | { &hf_zbee_nwk_gp_cmd_comm_rep_opt_sec_type, |
2272 | 15 | { "Key Type", "zbee_nwk_gp.cmd.comm_reply.opt.key_type", FT_UINT8, BASE_HEX, NULL, |
2273 | 15 | ZBEE_NWK_GP_CMD_COMMISSIONING_REP_OPT_KEY_TYPE, NULL, HFILL }}, |
2274 | | |
2275 | 15 | { &hf_zbee_nwk_gp_cmd_comm_rep_pan_id, |
2276 | 15 | { "PAN ID", "zbee_nwk_gp.cmd.comm_reply.pan_id", FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }}, |
2277 | | |
2278 | 15 | { &hf_zbee_nwk_gp_cmd_comm_rep_frame_counter, |
2279 | 15 | { "Frame Counter", "zbee_nwk_gp.cmd.comm_reply.frame_counter", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }}, |
2280 | | |
2281 | 15 | { &hf_zbee_nwk_gp_cmd_read_att_opt_multi_rec, |
2282 | 15 | { "Multi-record", "zbee_nwk_gp.cmd.read_att.opt.multi_record", FT_BOOLEAN, 8, NULL, |
2283 | 15 | ZBEE_NWK_GP_CMD_READ_ATTRIBUTE_OPT_MULTI_RECORD, NULL, HFILL }}, |
2284 | | |
2285 | 15 | { &hf_zbee_nwk_gp_cmd_read_att_opt_man_field_present, |
2286 | 15 | { "Manufacturer field present", "zbee_nwk_gp.cmd.read_att.opt.man_field_present", FT_BOOLEAN, 8, NULL, |
2287 | 15 | ZBEE_NWK_GP_CMD_READ_ATTRIBUTE_OPT_MAN_FIELD_PRESENT, NULL, HFILL }}, |
2288 | | |
2289 | 15 | { &hf_zbee_nwk_gp_cmd_read_att_opt, |
2290 | 15 | { "Option field", "zbee_nwk_gp.cmd.read_att.opt", FT_UINT8, BASE_HEX, NULL, |
2291 | 15 | 0x0, NULL, HFILL }}, |
2292 | | |
2293 | 15 | { &hf_zbee_nwk_gp_cmd_zcl_tunnel_opt_frame_type, |
2294 | 15 | { "Frame type", "zbee_nwk_gp.cmd.zcl_tunnel.opt.frame_type", FT_UINT8, BASE_HEX, NULL, |
2295 | 15 | ZBEE_NWK_GP_CMD_ZCL_TUNNEL_OPT_FRAME_TYPE, NULL, HFILL }}, |
2296 | | |
2297 | 15 | { &hf_zbee_nwk_gp_cmd_zcl_tunnel_opt_man_field_present, |
2298 | 15 | { "Manufacturer field present", "zbee_nwk_gp.cmd.zcl_tunnel.opt.man_field_present", FT_BOOLEAN, 8, NULL, |
2299 | 15 | ZBEE_NWK_GP_CMD_ZCL_TUNNEL_OPT_MAN_FIELD_PRESENT, NULL, HFILL }}, |
2300 | | |
2301 | 15 | { &hf_zbee_nwk_gp_cmd_zcl_tunnel_opt_direction, |
2302 | 15 | { "Direction", "zbee_nwk_gp.cmd.zcl_tunnel.opt.direction", FT_UINT8, BASE_HEX, NULL, |
2303 | 15 | ZBEE_NWK_GP_CMD_ZCL_TUNNEL_OPT_DIRECTION, NULL, HFILL }}, |
2304 | | |
2305 | 15 | { &hf_zbee_nwk_gp_cmd_zcl_tunnel_opt, |
2306 | 15 | { "Option field", "zbee_nwk_gp.cmd.zcl_tunnel.opt", FT_UINT8, BASE_HEX, NULL, |
2307 | 15 | 0x0, NULL, HFILL }}, |
2308 | | |
2309 | 15 | { &hf_zbee_nwk_gp_cmd_zcl_tunnel_command_id, |
2310 | 15 | { "Zigbee Command ID", "zbee_nwk_gp.cmd.zcl_tunnel.command_id", FT_UINT8, BASE_HEX, NULL, 0x0, |
2311 | 15 | NULL, HFILL }}, |
2312 | | |
2313 | 15 | { &hf_zbee_nwk_gp_cmd_zcl_tunnel_payload_len, |
2314 | 15 | { "Length of Payload", "zbee_nwk_gp.cmd.zcl_tunnel.payload_len", FT_UINT8, BASE_DEC, NULL, 0x0, |
2315 | 15 | NULL, HFILL }}, |
2316 | | |
2317 | 15 | { &hf_zbee_zcl_gp_cmd_ms_manufacturer_code, |
2318 | 15 | { "Manufacturer Code", "zbee_nwk_gp.cmd.manufacturer_code", FT_UINT16, BASE_HEX, VALS(zbee_mfr_code_names), |
2319 | 15 | 0x0, NULL, HFILL }}, |
2320 | | |
2321 | 15 | { &hf_zbee_nwk_gp_cmd_read_att_record_len, |
2322 | 15 | { "Length of Record List", "zbee_nwk_gp.cmd.read_att.record_len", FT_UINT8, BASE_DEC, NULL, 0x0, |
2323 | 15 | NULL, HFILL }}, |
2324 | | |
2325 | 15 | { &hf_zbee_nwk_gp_zcl_attr_status, |
2326 | 15 | { "Status", "zbee_nwk_gp.zcl.attr.status", FT_UINT8, BASE_HEX, VALS(zbee_zcl_status_names), |
2327 | 15 | 0x0, NULL, HFILL }}, |
2328 | | |
2329 | 15 | { &hf_zbee_nwk_gp_zcl_attr_data_type, |
2330 | 15 | { "Data Type", "zbee_nwk_gp.zcl.attr.datatype", FT_UINT8, BASE_HEX, VALS(zbee_zcl_short_data_type_names), |
2331 | 15 | 0x0, NULL, HFILL } }, |
2332 | | |
2333 | 15 | { &hf_zbee_nwk_gp_zcl_attr_cluster_id, |
2334 | 15 | { "ZigBee Cluster ID", "zbee_nwk_gp.zcl.attr.cluster_id", FT_UINT16, BASE_HEX | BASE_RANGE_STRING, RVALS(zbee_aps_cid_names), |
2335 | 15 | 0x0, NULL, HFILL }}, |
2336 | | |
2337 | 15 | { &hf_zbee_nwk_gp_cmd_channel_request_toggling_behaviour, |
2338 | 15 | { "Channel Toggling Behaviour", "zbee_nwk_gp.cmd.ch_req", FT_UINT8, BASE_HEX, NULL, |
2339 | 15 | 0x0, NULL, HFILL }}, |
2340 | | |
2341 | 15 | { &hf_zbee_nwk_gp_cmd_channel_request_toggling_behaviour_1st, |
2342 | 15 | { "Rx channel in the next attempt", "zbee_nwk_gp.cmd.ch_req.1st", FT_UINT8, BASE_HEX, NULL, |
2343 | 15 | ZBEE_NWK_GP_CMD_CHANNEL_REQUEST_1ST, NULL, HFILL }}, |
2344 | | |
2345 | 15 | { &hf_zbee_nwk_gp_cmd_channel_request_toggling_behaviour_2nd, |
2346 | 15 | { "Rx channel in the second next attempt", "zbee_nwk_gp.ch_req.2nd", FT_UINT8, BASE_HEX, NULL, |
2347 | 15 | ZBEE_NWK_GP_CMD_CHANNEL_REQUEST_2ND, NULL, HFILL }}, |
2348 | | |
2349 | 15 | { &hf_zbee_nwk_gp_cmd_operational_channel, |
2350 | 15 | { "Operational Channel", "zbee_nwk_gp.cmd.configuration_ch", FT_UINT8, BASE_HEX, NULL, |
2351 | 15 | 0x0, NULL, HFILL }}, |
2352 | | |
2353 | 15 | { &hf_zbee_nwk_gp_cmd_channel_configuration, |
2354 | 15 | { "Operation channel", "zbee_nwk_gp.cmd.configuration_ch.operation_ch", FT_UINT8, BASE_HEX, NULL, |
2355 | 15 | ZBEE_NWK_GP_CMD_CHANNEL_CONFIGURATION_OPERATION_CH, NULL, HFILL }}, |
2356 | | |
2357 | 15 | { &hf_zbee_nwk_gp_cmd_move_color_ratex, |
2358 | 15 | { "RateX", "zbee_nwk_gp.cmd.move_color.ratex", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }}, |
2359 | | |
2360 | 15 | { &hf_zbee_nwk_gp_cmd_move_color_ratey, |
2361 | 15 | { "RateY", "zbee_nwk_gp.cmd.move_color.ratey", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }}, |
2362 | | |
2363 | 15 | { &hf_zbee_nwk_gp_cmd_move_up_down_rate, |
2364 | 15 | { "Rate", "zbee_nwk_gp.cmd.move_up_down.rate", FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }}, |
2365 | | |
2366 | 15 | { &hf_zbee_nwk_gp_cmd_step_color_stepx, |
2367 | 15 | { "StepX", "zbee_nwk_gp.cmd.step_color.stepx", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }}, |
2368 | | |
2369 | 15 | { &hf_zbee_nwk_gp_cmd_step_color_stepy, |
2370 | 15 | { "StepY", "zbee_nwk_gp.cmd.step_color.stepy", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }}, |
2371 | | |
2372 | 15 | { &hf_zbee_nwk_gp_cmd_step_color_transition_time, |
2373 | 15 | { "Transition Time", "zbee_nwk_gp.cmd.step_color.transition_time", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, |
2374 | 15 | HFILL }}, |
2375 | | |
2376 | 15 | { &hf_zbee_nwk_gp_cmd_step_up_down_step_size, |
2377 | 15 | { "Step Size", "zbee_nwk_gp.cmd.step_up_down.step_size", FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }}, |
2378 | | |
2379 | 15 | { &hf_zbee_nwk_gp_cmd_step_up_down_transition_time, |
2380 | 15 | { "Transition Time", "zbee_nwk_gp.cmd.step_up_down.transition_time", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, |
2381 | 15 | HFILL }} |
2382 | 15 | }; |
2383 | | |
2384 | 15 | static ei_register_info ei[] = { |
2385 | 15 | { &ei_zbee_nwk_gp_no_payload, |
2386 | 15 | { "zbee_nwk_gp.no_payload", PI_MALFORMED, PI_ERROR, |
2387 | 15 | "Payload is missing", EXPFILL }}, |
2388 | 15 | { &ei_zbee_nwk_gp_inval_residual_data, |
2389 | 15 | { "zbee_nwk_gp.inval_residual_data", PI_MALFORMED, PI_ERROR, |
2390 | 15 | "Invalid residual data", EXPFILL }}, |
2391 | 15 | { &ei_zbee_nwk_gp_com_rep_no_out_cnt, |
2392 | 15 | { "zbee_nwk_gp.com_rep_no_out_cnt", PI_DEBUG, PI_WARN, |
2393 | 15 | "Missing outgoing frame counter", EXPFILL }} |
2394 | 15 | }; |
2395 | | |
2396 | 15 | static int *ett[] = { |
2397 | 15 | &ett_zbee_nwk, |
2398 | 15 | &ett_zbee_nwk_cmd, |
2399 | 15 | &ett_zbee_nwk_cmd_cinfo, |
2400 | 15 | &ett_zbee_nwk_cmd_appli_info, |
2401 | 15 | &ett_zbee_nwk_cmd_options, |
2402 | 15 | &ett_zbee_nwk_fcf, |
2403 | 15 | &ett_zbee_nwk_fcf_ext, |
2404 | 15 | &ett_zbee_nwk_clu_rec, |
2405 | 15 | &ett_zbee_nwk_att_rec, |
2406 | 15 | &ett_zbee_nwk_cmd_comm_gpd_cmd_id_list, |
2407 | 15 | &ett_zbee_nwk_cmd_comm_length_of_clid_list, |
2408 | 15 | &ett_zbee_nwk_cmd_comm_clid_list_server, |
2409 | 15 | &ett_zbee_nwk_cmd_comm_clid_list_client |
2410 | 15 | }; |
2411 | | |
2412 | 15 | static uat_field_t key_uat_fields[] = { |
2413 | 15 | UAT_FLD_CSTRING(gp_uat_key_records, string, "Key", "A 16-byte key."), |
2414 | 15 | UAT_FLD_VS(gp_uat_key_records, byte_order, "Byte Order", byte_order_vals, "Byte order of a key."), |
2415 | 15 | UAT_FLD_LSTRING(gp_uat_key_records, label, "Label", "User label for a key."), |
2416 | 15 | UAT_END_FIELDS |
2417 | 15 | }; |
2418 | | |
2419 | 15 | proto_zbee_nwk_gp = proto_register_protocol("ZigBee Green Power Profile", "ZigBee Green Power", |
2420 | 15 | ZBEE_PROTOABBREV_NWK_GP); |
2421 | | |
2422 | 15 | gp_zbee_prefs = prefs_register_protocol(proto_zbee_nwk_gp, NULL); |
2423 | | |
2424 | 15 | zbee_gp_sec_key_table_uat = uat_new("ZigBee GP Security Keys", sizeof(uat_key_record_t), "zigbee_gp_keys", true, |
2425 | 15 | &gp_uat_key_records, &num_uat_key_records, UAT_AFFECTS_DISSECTION, NULL, uat_key_record_copy_cb, |
2426 | 15 | uat_key_record_update_cb, uat_key_record_free_cb, uat_key_record_post_update_cb, NULL, key_uat_fields); |
2427 | | |
2428 | 15 | prefs_register_uat_preference(gp_zbee_prefs, "gp_key_table", "Pre-configured GP Security Keys", |
2429 | 15 | "Pre-configured GP Security Keys.", zbee_gp_sec_key_table_uat); |
2430 | | |
2431 | 15 | register_init_routine(gp_init_zbee_security); |
2432 | 15 | register_cleanup_routine(gp_cleanup_zbee_security); |
2433 | | |
2434 | | /* Register the Wireshark protocol. */ |
2435 | 15 | proto_register_field_array(proto_zbee_nwk_gp, hf, array_length(hf)); |
2436 | 15 | proto_register_subtree_array(ett, array_length(ett)); |
2437 | | |
2438 | 15 | expert_zbee_nwk_gp = expert_register_protocol(proto_zbee_nwk_gp); |
2439 | 15 | expert_register_field_array(expert_zbee_nwk_gp, ei, array_length(ei)); |
2440 | | |
2441 | | /* Register the dissectors. */ |
2442 | 15 | register_dissector(ZBEE_PROTOABBREV_NWK_GP, dissect_zbee_nwk_gp, proto_zbee_nwk_gp); |
2443 | 15 | register_dissector(ZBEE_PROTOABBREV_NWK_GP_CMD, dissect_zbee_nwk_gp_cmd, proto_zbee_nwk_gp); |
2444 | 15 | } /* proto_register_zbee_nwk_gp */ |
2445 | | |
2446 | | /** |
2447 | | *Registers the ZigBee dissector with Wireshark. |
2448 | | * |
2449 | | */ |
2450 | | void |
2451 | | proto_reg_handoff_zbee_nwk_gp(void) |
2452 | 15 | { |
2453 | | /* Register our dissector with IEEE 802.15.4. */ |
2454 | 15 | dissector_add_for_decode_as(IEEE802154_PROTOABBREV_WPAN_PANID, find_dissector(ZBEE_PROTOABBREV_NWK_GP)); |
2455 | 15 | heur_dissector_add(IEEE802154_PROTOABBREV_WPAN, dissect_zbee_nwk_heur_gp, "ZigBee Green Power over IEEE 802.15.4", "zbee_nwk_gp_wlan", proto_zbee_nwk_gp, HEURISTIC_ENABLE); |
2456 | 15 | } /* proto_reg_handoff_zbee */ |
2457 | | |
2458 | | /* |
2459 | | * Editor modelines |
2460 | | * |
2461 | | * Local Variables: |
2462 | | * c-basic-offset: 4 |
2463 | | * tab-width: 8 |
2464 | | * indent-tabs-mode: nil |
2465 | | * End: |
2466 | | * |
2467 | | * ex: set shiftwidth=4 tabstop=8 expandtab: |
2468 | | * :indentSize=4:tabSize=8:noTabs=true: |
2469 | | */ |