aboutsummaryrefslogtreecommitdiffstats
path: root/epan/dissectors/packet-zbee-nwk.c
diff options
context:
space:
mode:
authordsrsupport <eugene.exarevsky@dsr-company.com>2016-06-15 18:48:01 +0300
committerPascal Quantin <pascal.quantin@gmail.com>2016-06-15 19:58:57 +0000
commit64169e3a765c7d22cc0a15623d6ede37ca50ceb2 (patch)
treec38d32cf84bdad60c2d826ada090bc38118fb882 /epan/dissectors/packet-zbee-nwk.c
parent6baa1b544c84a766d9f9d356e9940eccaf0a128f (diff)
ZigBee: add support for inter-pan transmissions.
Added dissection of inter-pan nwk and aps stub to be used to decode ZLL commissioning cluster. Change-Id: I871016a93854f1caf2f14f2f84e5397de5f1e2ff Reviewed-on: https://code.wireshark.org/review/15918 Reviewed-by: Michael Mann <mmann78@netscape.net> Petri-Dish: Michael Mann <mmann78@netscape.net> Tested-by: Petri Dish Buildbot <buildbot-no-reply@wireshark.org> Reviewed-by: Pascal Quantin <pascal.quantin@gmail.com>
Diffstat (limited to 'epan/dissectors/packet-zbee-nwk.c')
-rw-r--r--epan/dissectors/packet-zbee-nwk.c323
1 files changed, 163 insertions, 160 deletions
diff --git a/epan/dissectors/packet-zbee-nwk.c b/epan/dissectors/packet-zbee-nwk.c
index accdfa50d0..5ecf368625 100644
--- a/epan/dissectors/packet-zbee-nwk.c
+++ b/epan/dissectors/packet-zbee-nwk.c
@@ -218,6 +218,7 @@ static dissector_handle_t zbee_gp_handle;
static const value_string zbee_nwk_frame_types[] = {
{ ZBEE_NWK_FCF_DATA, "Data" },
{ ZBEE_NWK_FCF_CMD, "Command" },
+ { ZBEE_NWK_FCF_INTERPAN,"Interpan" },
{ 0, NULL }
};
@@ -514,192 +515,194 @@ dissect_zbee_nwk_full(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void
proto_item_append_text(proto_root, " %s", val_to_str_const(packet.type, zbee_nwk_frame_types, "Unknown Type"));
col_set_str(pinfo->cinfo, COL_INFO, val_to_str_const(packet.type, zbee_nwk_frame_types, "Reserved Frame Type"));
- /* Get the destination address. */
- packet.dst = tvb_get_letohs(tvb, offset);
- proto_tree_add_uint(nwk_tree, hf_zbee_nwk_dst, tvb, offset, 2, packet.dst);
+ if (packet.type != ZBEE_NWK_FCF_INTERPAN) {
+ /* Get the destination address. */
+ packet.dst = tvb_get_letohs(tvb, offset);
+ proto_tree_add_uint(nwk_tree, hf_zbee_nwk_dst, tvb, offset, 2, packet.dst);
- offset += 2;
+ offset += 2;
- /* Display the destination address. */
- if ( (packet.dst == ZBEE_BCAST_ALL)
- || (packet.dst == ZBEE_BCAST_ACTIVE)
- || (packet.dst == ZBEE_BCAST_ROUTERS)){
- dst_addr = wmem_strdup(pinfo->pool, "Broadcast");
- }
- else {
- dst_addr = wmem_strdup_printf(pinfo->pool, "0x%04x", packet.dst);
- }
+ /* Display the destination address. */
+ if ( (packet.dst == ZBEE_BCAST_ALL)
+ || (packet.dst == ZBEE_BCAST_ACTIVE)
+ || (packet.dst == ZBEE_BCAST_ROUTERS)){
+ dst_addr = wmem_strdup(pinfo->pool, "Broadcast");
+ }
+ else {
+ dst_addr = wmem_strdup_printf(pinfo->pool, "0x%04x", packet.dst);
+ }
- set_address(&pinfo->net_dst, AT_STRINGZ, (int)strlen(dst_addr)+1, dst_addr);
- copy_address_shallow(&pinfo->dst, &pinfo->net_dst);
+ set_address(&pinfo->net_dst, AT_STRINGZ, (int)strlen(dst_addr)+1, dst_addr);
+ copy_address_shallow(&pinfo->dst, &pinfo->net_dst);
- proto_item_append_text(proto_root, ", Dst: %s", dst_addr);
- col_append_fstr(pinfo->cinfo, COL_INFO, ", Dst: %s", dst_addr);
+ proto_item_append_text(proto_root, ", Dst: %s", dst_addr);
+ col_append_fstr(pinfo->cinfo, COL_INFO, ", Dst: %s", dst_addr);
- /* Get the short nwk source address and pass it to upper layers */
- packet.src = tvb_get_letohs(tvb, offset);
- if (nwk_hints)
- nwk_hints->src = packet.src;
- proto_tree_add_uint(nwk_tree, hf_zbee_nwk_src, tvb, offset, 2, packet.src);
- offset += 2;
+ /* Get the short nwk source address and pass it to upper layers */
+ packet.src = tvb_get_letohs(tvb, offset);
+ if (nwk_hints)
+ nwk_hints->src = packet.src;
+ proto_tree_add_uint(nwk_tree, hf_zbee_nwk_src, tvb, offset, 2, packet.src);
+ offset += 2;
- /* Display the source address. */
- if ( (packet.src == ZBEE_BCAST_ALL)
- || (packet.src == ZBEE_BCAST_ACTIVE)
- || (packet.src == ZBEE_BCAST_ROUTERS)){
- /* Source Broadcast doesn't make much sense. */
- src_addr = wmem_strdup(pinfo->pool, "Unexpected Source Broadcast");
- unicast_src = FALSE;
- }
- else {
- src_addr = wmem_strdup_printf(pinfo->pool, "0x%04x", packet.src);
- unicast_src = TRUE;
- }
+ /* Display the source address. */
+ if ( (packet.src == ZBEE_BCAST_ALL)
+ || (packet.src == ZBEE_BCAST_ACTIVE)
+ || (packet.src == ZBEE_BCAST_ROUTERS)){
+ /* Source Broadcast doesn't make much sense. */
+ src_addr = wmem_strdup(pinfo->pool, "Unexpected Source Broadcast");
+ unicast_src = FALSE;
+ }
+ else {
+ src_addr = wmem_strdup_printf(pinfo->pool, "0x%04x", packet.src);
+ unicast_src = TRUE;
+ }
- set_address(&pinfo->net_src, AT_STRINGZ, (int)strlen(src_addr)+1, src_addr);
- copy_address_shallow(&pinfo->src, &pinfo->net_src);
+ set_address(&pinfo->net_src, AT_STRINGZ, (int)strlen(src_addr)+1, src_addr);
+ copy_address_shallow(&pinfo->src, &pinfo->net_src);
- proto_item_append_text(proto_root, ", Src: %s", src_addr);
- col_append_fstr(pinfo->cinfo, COL_INFO, ", Src: %s", src_addr);
+ proto_item_append_text(proto_root, ", Src: %s", src_addr);
+ col_append_fstr(pinfo->cinfo, COL_INFO, ", Src: %s", src_addr);
- /* Get and display the radius. */
- packet.radius = tvb_get_guint8(tvb, offset);
- proto_tree_add_uint(nwk_tree, hf_zbee_nwk_radius, tvb, offset, 1, packet.radius);
- offset += 1;
+ /* Get and display the radius. */
+ packet.radius = tvb_get_guint8(tvb, offset);
+ proto_tree_add_uint(nwk_tree, hf_zbee_nwk_radius, tvb, offset, 1, packet.radius);
+ offset += 1;
- /* Get and display the sequence number. */
- packet.seqno = tvb_get_guint8(tvb, offset);
- proto_tree_add_uint(nwk_tree, hf_zbee_nwk_seqno, tvb, offset, 1, packet.seqno);
- offset += 1;
+ /* Get and display the sequence number. */
+ packet.seqno = tvb_get_guint8(tvb, offset);
+ proto_tree_add_uint(nwk_tree, hf_zbee_nwk_seqno, tvb, offset, 1, packet.seqno);
+ offset += 1;
- /* Add the extended destination address (ZigBee 2006 and later). */
- if ((packet.version >= ZBEE_VERSION_2007) && packet.ext_dst) {
- packet.dst64 = tvb_get_letoh64(tvb, offset);
- proto_tree_add_item(nwk_tree, hf_zbee_nwk_dst64, tvb, offset, 8, ENC_LITTLE_ENDIAN);
- offset += 8;
- }
+ /* Add the extended destination address (ZigBee 2006 and later). */
+ if ((packet.version >= ZBEE_VERSION_2007) && packet.ext_dst) {
+ packet.dst64 = tvb_get_letoh64(tvb, offset);
+ proto_tree_add_item(nwk_tree, hf_zbee_nwk_dst64, tvb, offset, 8, ENC_LITTLE_ENDIAN);
+ offset += 8;
+ }
- /* Display the extended source address. (ZigBee 2006 and later). */
- if (packet.version >= ZBEE_VERSION_2007) {
- addr16.pan = ieee_packet->src_pan;
+ /* Display the extended source address. (ZigBee 2006 and later). */
+ if (packet.version >= ZBEE_VERSION_2007) {
+ addr16.pan = ieee_packet->src_pan;
- if (packet.ext_src) {
- packet.src64 = tvb_get_letoh64(tvb, offset);
- proto_tree_add_item(nwk_tree, hf_zbee_nwk_src64, tvb, offset, 8, ENC_LITTLE_ENDIAN);
- offset += 8;
+ if (packet.ext_src) {
+ packet.src64 = tvb_get_letoh64(tvb, offset);
+ proto_tree_add_item(nwk_tree, hf_zbee_nwk_src64, tvb, offset, 8, ENC_LITTLE_ENDIAN);
+ offset += 8;
- if (!pinfo->fd->flags.visited && nwk_hints) {
- /* Provide hints to upper layers */
- nwk_hints->src_pan = ieee_packet->src_pan;
+ if (!pinfo->fd->flags.visited && nwk_hints) {
+ /* Provide hints to upper layers */
+ nwk_hints->src_pan = ieee_packet->src_pan;
- /* Update nwk extended address hash table */
- if ( unicast_src ) {
- nwk_hints->map_rec = ieee802154_addr_update(&zbee_nwk_map,
- packet.src, addr16.pan, packet.src64, pinfo->current_proto, pinfo->num);
+ /* Update nwk extended address hash table */
+ if ( unicast_src ) {
+ nwk_hints->map_rec = ieee802154_addr_update(&zbee_nwk_map,
+ packet.src, addr16.pan, packet.src64, pinfo->current_proto, pinfo->num);
+ }
}
}
- }
- else {
- /* See if extended source info was previously sniffed */
- if (!pinfo->fd->flags.visited && nwk_hints) {
- nwk_hints->src_pan = ieee_packet->src_pan;
- addr16.addr = packet.src;
-
- map_rec = (ieee802154_map_rec *) g_hash_table_lookup(zbee_nwk_map.short_table, &addr16);
- if (map_rec) {
- /* found a nwk mapping record */
- nwk_hints->map_rec = map_rec;
- }
- else {
- /* does ieee layer know? */
- map_rec = (ieee802154_map_rec *) g_hash_table_lookup(ieee_packet->short_table, &addr16);
- if (map_rec) nwk_hints->map_rec = map_rec;
- }
- } /* (!pinfo->fd->flags.visited) */
else {
- if (nwk_hints && nwk_hints->map_rec ) {
- /* Display inferred source address info */
- ti = proto_tree_add_eui64(nwk_tree, hf_zbee_nwk_src64, tvb, offset, 0,
- nwk_hints->map_rec->addr64);
- PROTO_ITEM_SET_GENERATED(ti);
-
- if ( nwk_hints->map_rec->start_fnum ) {
- ti = proto_tree_add_uint(nwk_tree, hf_zbee_nwk_src64_origin, tvb, 0, 0,
- nwk_hints->map_rec->start_fnum);
+ /* See if extended source info was previously sniffed */
+ if (!pinfo->fd->flags.visited && nwk_hints) {
+ nwk_hints->src_pan = ieee_packet->src_pan;
+ addr16.addr = packet.src;
+
+ map_rec = (ieee802154_map_rec *) g_hash_table_lookup(zbee_nwk_map.short_table, &addr16);
+ if (map_rec) {
+ /* found a nwk mapping record */
+ nwk_hints->map_rec = map_rec;
}
else {
- ti = proto_tree_add_uint_format_value(nwk_tree, hf_zbee_nwk_src64_origin, tvb, 0, 0, 0, "Pre-configured");
+ /* does ieee layer know? */
+ map_rec = (ieee802154_map_rec *) g_hash_table_lookup(ieee_packet->short_table, &addr16);
+ if (map_rec) nwk_hints->map_rec = map_rec;
+ }
+ } /* (!pinfo->fd->flags.visited) */
+ else {
+ if (nwk_hints && nwk_hints->map_rec ) {
+ /* Display inferred source address info */
+ ti = proto_tree_add_eui64(nwk_tree, hf_zbee_nwk_src64, tvb, offset, 0,
+ nwk_hints->map_rec->addr64);
+ PROTO_ITEM_SET_GENERATED(ti);
+
+ if ( nwk_hints->map_rec->start_fnum ) {
+ ti = proto_tree_add_uint(nwk_tree, hf_zbee_nwk_src64_origin, tvb, 0, 0,
+ nwk_hints->map_rec->start_fnum);
+ }
+ else {
+ ti = proto_tree_add_uint_format_value(nwk_tree, hf_zbee_nwk_src64_origin, tvb, 0, 0, 0, "Pre-configured");
+ }
+ PROTO_ITEM_SET_GENERATED(ti);
}
- PROTO_ITEM_SET_GENERATED(ti);
}
}
- }
- /* If ieee layer didn't know its extended source address, and nwk layer does, fill it in */
- if (!pinfo->fd->flags.visited) {
- if ( (ieee_packet->src_addr_mode == IEEE802154_FCF_ADDR_SHORT) &&
- ieee_hints && !ieee_hints->map_rec ) {
- addr16.pan = ieee_packet->src_pan;
- addr16.addr = ieee_packet->src16;
- map_rec = (ieee802154_map_rec *) g_hash_table_lookup(zbee_nwk_map.short_table, &addr16);
-
- if (map_rec) {
- /* found a ieee mapping record */
- ieee_hints->map_rec = map_rec;
+ /* If ieee layer didn't know its extended source address, and nwk layer does, fill it in */
+ if (!pinfo->fd->flags.visited) {
+ if ( (ieee_packet->src_addr_mode == IEEE802154_FCF_ADDR_SHORT) &&
+ ieee_hints && !ieee_hints->map_rec ) {
+ addr16.pan = ieee_packet->src_pan;
+ addr16.addr = ieee_packet->src16;
+ map_rec = (ieee802154_map_rec *) g_hash_table_lookup(zbee_nwk_map.short_table, &addr16);
+
+ if (map_rec) {
+ /* found a ieee mapping record */
+ ieee_hints->map_rec = map_rec;
+ }
}
- }
- } /* (!pinfo->fd->flags.visited */
- } /* (pinfo->zbee_stack_vers >= ZBEE_VERSION_2007) */
-
- /* Add multicast control field (ZigBee 2006 and later). */
- if ((packet.version >= ZBEE_VERSION_2007) && packet.multicast) {
- static const int * multicast_flags[] = {
- &hf_zbee_nwk_mcast_mode,
- &hf_zbee_nwk_mcast_radius,
- &hf_zbee_nwk_mcast_max_radius,
- NULL
- };
-
- guint8 mcast_control = tvb_get_guint8(tvb, offset);
- packet.mcast_mode = zbee_get_bit_field(mcast_control, ZBEE_NWK_MCAST_MODE);
- packet.mcast_radius = zbee_get_bit_field(mcast_control, ZBEE_NWK_MCAST_RADIUS);
- packet.mcast_max_radius = zbee_get_bit_field(mcast_control, ZBEE_NWK_MCAST_MAX_RADIUS);
-
- proto_tree_add_bitmask(nwk_tree, tvb, offset, hf_zbee_nwk_mcast, ett_zbee_nwk_mcast, multicast_flags, ENC_NA);
- offset += 1;
- }
-
- /* Add the Source Route field. (ZigBee 2006 and later). */
- if ((packet.version >= ZBEE_VERSION_2007) && packet.route) {
- proto_tree *field_tree;
- guint8 relay_count;
- guint16 relay_addr;
- guint i;
-
- /* Create a subtree for the source route field. */
- field_tree = proto_tree_add_subtree(nwk_tree, tvb, offset, 1, ett_zbee_nwk_route, &ti, "Source Route");
-
- /* Get and display the relay count. */
- relay_count = tvb_get_guint8(tvb, offset);
- proto_tree_add_uint(field_tree, hf_zbee_nwk_relay_count, tvb, offset, 1, relay_count);
- proto_item_append_text(ti, ", Length: %d", relay_count);
- offset += 1;
-
- /* Correct the length of the source route fields. */
- proto_item_set_len(ti, 1 + relay_count*2);
-
- /* Get and display the relay index. */
- proto_tree_add_item(field_tree, hf_zbee_nwk_relay_index, tvb, offset, 1, ENC_NA);
- offset += 1;
+ } /* (!pinfo->fd->flags.visited */
+ } /* (pinfo->zbee_stack_vers >= ZBEE_VERSION_2007) */
+
+ /* Add multicast control field (ZigBee 2006 and later). */
+ if ((packet.version >= ZBEE_VERSION_2007) && packet.multicast) {
+ static const int * multicast_flags[] = {
+ &hf_zbee_nwk_mcast_mode,
+ &hf_zbee_nwk_mcast_radius,
+ &hf_zbee_nwk_mcast_max_radius,
+ NULL
+ };
+
+ guint8 mcast_control = tvb_get_guint8(tvb, offset);
+ packet.mcast_mode = zbee_get_bit_field(mcast_control, ZBEE_NWK_MCAST_MODE);
+ packet.mcast_radius = zbee_get_bit_field(mcast_control, ZBEE_NWK_MCAST_RADIUS);
+ packet.mcast_max_radius = zbee_get_bit_field(mcast_control, ZBEE_NWK_MCAST_MAX_RADIUS);
+
+ proto_tree_add_bitmask(nwk_tree, tvb, offset, hf_zbee_nwk_mcast, ett_zbee_nwk_mcast, multicast_flags, ENC_NA);
+ offset += 1;
+ }
- /* Get and display the relay list. */
- for (i=0; i<relay_count; i++) {
- relay_addr = tvb_get_letohs(tvb, offset);
- proto_tree_add_uint_format(field_tree, hf_zbee_nwk_relay, tvb, offset, 2, relay_addr, "Relay %d: 0x%04x", i+1, relay_addr);
- offset += 2;
- } /* for */
- }
+ /* Add the Source Route field. (ZigBee 2006 and later). */
+ if ((packet.version >= ZBEE_VERSION_2007) && packet.route) {
+ proto_tree *field_tree;
+ guint8 relay_count;
+ guint16 relay_addr;
+ guint i;
+
+ /* Create a subtree for the source route field. */
+ field_tree = proto_tree_add_subtree(nwk_tree, tvb, offset, 1, ett_zbee_nwk_route, &ti, "Source Route");
+
+ /* Get and display the relay count. */
+ relay_count = tvb_get_guint8(tvb, offset);
+ proto_tree_add_uint(field_tree, hf_zbee_nwk_relay_count, tvb, offset, 1, relay_count);
+ proto_item_append_text(ti, ", Length: %d", relay_count);
+ offset += 1;
+
+ /* Correct the length of the source route fields. */
+ proto_item_set_len(ti, 1 + relay_count*2);
+
+ /* Get and display the relay index. */
+ proto_tree_add_item(field_tree, hf_zbee_nwk_relay_index, tvb, offset, 1, ENC_NA);
+ offset += 1;
+
+ /* Get and display the relay list. */
+ for (i=0; i<relay_count; i++) {
+ relay_addr = tvb_get_letohs(tvb, offset);
+ proto_tree_add_uint_format(field_tree, hf_zbee_nwk_relay, tvb, offset, 2, relay_addr, "Relay %d: 0x%04x", i+1, relay_addr);
+ offset += 2;
+ } /* for */
+ }
+ } /* if not interpan */
/*
* Ensure that the payload exists. There are no valid ZigBee network
@@ -727,7 +730,7 @@ dissect_zbee_nwk_full(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void
/* Dissect the Network Command. */
dissect_zbee_nwk_cmd(payload_tvb, pinfo, nwk_tree, &packet);
}
- else if (packet.type == ZBEE_NWK_FCF_DATA) {
+ else if (packet.type == ZBEE_NWK_FCF_DATA || packet.type == ZBEE_NWK_FCF_INTERPAN) {
/* Dissect the Network Payload (APS layer). */
call_dissector_with_data(aps_handle, payload_tvb, pinfo, tree, &packet);
}