Bluetooth: simple HCI ISO Data packet dissector

Change-Id: I2da85d4ebe069a566943896fddb31e9a095d67b5
Reviewed-on: https://code.wireshark.org/review/38007
Petri-Dish: Alexis La Goutte <alexis.lagoutte@gmail.com>
Tested-by: Petri Dish Buildbot
Reviewed-by: Anders Broman <a.broman58@gmail.com>
This commit is contained in:
Jakub Pawlowski 2020-07-31 14:48:28 +02:00 committed by Anders Broman
parent d7f7b62ef3
commit 2364968cd6
7 changed files with 234 additions and 0 deletions

View File

@ -277,6 +277,7 @@ set(DISSECTOR_PUBLIC_HEADERS
packet-bthci_acl.h
packet-bthci_cmd.h
packet-bthci_evt.h
packet-bthci_iso.h
packet-bthci_sco.h
packet-btl2cap.h
packet-btle.h
@ -761,6 +762,7 @@ set(DISSECTOR_SRC
${CMAKE_CURRENT_SOURCE_DIR}/packet-bthci_acl.c
${CMAKE_CURRENT_SOURCE_DIR}/packet-bthci_cmd.c
${CMAKE_CURRENT_SOURCE_DIR}/packet-bthci_evt.c
${CMAKE_CURRENT_SOURCE_DIR}/packet-bthci_iso.c
${CMAKE_CURRENT_SOURCE_DIR}/packet-bthci_sco.c
${CMAKE_CURRENT_SOURCE_DIR}/packet-bthci_vendor.c
${CMAKE_CURRENT_SOURCE_DIR}/packet-bthcrp.c

View File

@ -28,6 +28,7 @@ extern "C" {
#define HCI_H4_TYPE_ACL 0x02
#define HCI_H4_TYPE_SCO 0x03
#define HCI_H4_TYPE_EVT 0x04
#define HCI_H4_TYPE_ISO 0x05
#define HCI_OGF_LINK_CONTROL 0x01
#define HCI_OGF_LINK_POLICY 0x02

View File

@ -0,0 +1,202 @@
/* packet-bthci_iso.c
* Routines for the Bluetooth ISO dissection
* Copyright 2020, Jakub Pawlowski <jpawlowski@google.com>
*
* Wireshark - Network traffic analyzer
* By Gerald Combs <gerald@wireshark.org>
* Copyright 1998 Gerald Combs
*
* SPDX-License-Identifier: GPL-2.0-or-later
*/
#include "config.h"
#include <epan/packet.h>
#include <epan/prefs.h>
#include <epan/addr_resolv.h>
#include <epan/expert.h>
#include <epan/proto_data.h>
#include "packet-bluetooth.h"
/* Initialize the protocol and registered fields */
static int proto_bthci_iso = -1;
static int hf_bthci_iso_connection_handle = -1;
static int hf_bthci_iso_pb_flag = -1;
static int hf_bthci_iso_ts_flag = -1;
static int hf_bthci_iso_reserved_1 = -1;
static int hf_bthci_iso_length = -1;
static int hf_bthci_iso_reserved_2 = -1;
static int hf_bthci_iso_data = -1;
/* Initialize the subtree pointers */
static gint ett_bthci_iso = -1;
static dissector_handle_t bthci_iso_handle;
static const value_string pb_flag_vals[] = {
{ 0, "First fragment of fragmented SDU" },
{ 1, "Continuation Fragment of an SDU" },
{ 2, "Complete SDU" },
{ 3, "Last fragment of an SDU" },
{ 0, NULL }
};
static const value_string ts_flag_vals[] = {
{ 0, "No Time Stamp" },
{ 1, "Contains Time Stamp" },
{ 0, NULL }
};
void proto_register_bthci_iso(void);
void proto_reg_handoff_bthci_iso(void);
/* Code to actually dissect the packets */
static gint
dissect_bthci_iso(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data)
{
proto_item *bthci_iso_item;
proto_tree *bthci_iso_tree;
proto_item *sub_item;
guint16 flags;
gboolean fragmented;
gint offset = 0;
guint16 pb_flag;
/* Reject the packet if data is NULL */
if (data == NULL)
return 0;
bthci_iso_item = proto_tree_add_item(tree, proto_bthci_iso, tvb, offset, -1, ENC_NA);
bthci_iso_tree = proto_item_add_subtree(bthci_iso_item, ett_bthci_iso);
switch (pinfo->p2p_dir) {
case P2P_DIR_SENT:
col_set_str(pinfo->cinfo, COL_INFO, "Sent ");
break;
case P2P_DIR_RECV:
col_set_str(pinfo->cinfo, COL_INFO, "Rcvd ");
break;
default:
col_set_str(pinfo->cinfo, COL_INFO, "UnknownDirection ");
break;
}
col_set_str(pinfo->cinfo, COL_PROTOCOL, "HCI_ISO");
flags = tvb_get_letohs(tvb, offset);
pb_flag = (flags & 0x3000) >> 12;
proto_tree_add_item(bthci_iso_tree, hf_bthci_iso_connection_handle, tvb, offset, 2, ENC_LITTLE_ENDIAN);
proto_tree_add_item(bthci_iso_tree, hf_bthci_iso_pb_flag, tvb, offset, 2, ENC_LITTLE_ENDIAN);
proto_tree_add_item(bthci_iso_tree, hf_bthci_iso_ts_flag, tvb, offset, 1, ENC_LITTLE_ENDIAN);
proto_tree_add_item(bthci_iso_tree, hf_bthci_iso_reserved_1, tvb, offset, 1, ENC_LITTLE_ENDIAN);
offset += 2;
proto_tree_add_item(bthci_iso_tree, hf_bthci_iso_length, tvb, offset, 2, ENC_LITTLE_ENDIAN);
proto_tree_add_item(bthci_iso_tree, hf_bthci_iso_reserved_2, tvb, offset, 1, ENC_LITTLE_ENDIAN);
offset += 2;
/* determine if packet is fragmented */
switch(pb_flag) {
case 0x00: /* First Fragment */
case 0x01: /* Continuation */
case 0x11: /* Last */
fragmented = TRUE;
break;
case 0x10: /* Complete */
default:
/* unknown pb_flag */
fragmented = FALSE;
}
if (tvb_captured_length_remaining(tvb, offset) > 0) {
sub_item = proto_tree_add_item(bthci_iso_tree, hf_bthci_iso_data, tvb, offset, -1, ENC_NA);
if (fragmented) {
proto_item_append_text(sub_item, " Fragment");
}
}
return tvb_captured_length(tvb);
}
void
proto_register_bthci_iso(void)
{
/* Setup list of header fields See Section 1.6.1 for details*/
static hf_register_info hf[] = {
{ &hf_bthci_iso_connection_handle,
{ "Connection Handle", "bthci_iso.connection_handle",
FT_UINT16, BASE_HEX, NULL, 0x0FFF,
NULL, HFILL }
},
{ &hf_bthci_iso_pb_flag,
{ "PB Flag", "bthci_iso.pb_flag",
FT_UINT16, BASE_DEC, VALS(pb_flag_vals), 0x3000,
"Packet Boundary Flag", HFILL }
},
{ &hf_bthci_iso_ts_flag,
{ "TS Flag", "bthci_iso.ts_flag",
FT_UINT16, BASE_DEC, VALS(ts_flag_vals), 0x4000,
"Time stamp Flag", HFILL }
},
{ &hf_bthci_iso_reserved_1,
{ "Reserved 1", "bthci_iso.reserved_1",
FT_UINT16, BASE_DEC, NULL, 0x8000,
"Reserved", HFILL }
},
{ &hf_bthci_iso_length,
{ "ISO Data Load Length", "bthci_iso.length",
FT_UINT16, BASE_DEC, NULL, 0x7FFFF,
NULL, HFILL }
},
{ &hf_bthci_iso_reserved_2,
{ "Reserved 2", "bthci_iso.reserved_2",
FT_UINT16, BASE_DEC, NULL, 0x8000,
"Reserved", HFILL }
},
{ &hf_bthci_iso_data,
{ "ISO Data Load", "bthci_iso.data",
FT_NONE, BASE_NONE, NULL, 0x0,
NULL, HFILL }
},
};
/* Setup protocol subtree array */
static gint *ett[] = {
&ett_bthci_iso,
};
/* Register the protocol name and description */
proto_bthci_iso = proto_register_protocol("Bluetooth HCI ISO Packet", "HCI_ISO", "bthci_iso");
bthci_iso_handle = register_dissector("bthci_iso", dissect_bthci_iso, proto_bthci_iso);
/* Required function calls to register the header fields and subtrees used */
proto_register_field_array(proto_bthci_iso, hf, array_length(hf));
proto_register_subtree_array(ett, array_length(ett));
prefs_register_protocol_subtree("Bluetooth", proto_bthci_iso, NULL);
}
void
proto_reg_handoff_bthci_iso(void)
{
dissector_add_uint("hci_h4.type", HCI_H4_TYPE_ISO, bthci_iso_handle);
dissector_add_uint("hci_h1.type", BTHCI_CHANNEL_ISO, bthci_iso_handle);
}
/*
* Editor modelines - https://www.wireshark.org/tools/modelines.html
*
* Local variables:
* c-basic-offset: 4
* tab-width: 8
* indent-tabs-mode: nil
* End:
*
* vi: set shiftwidth=4 tabstop=8 expandtab:
* :indentSize=4:tabSize=8:noTabs=true:
*/

View File

@ -0,0 +1,26 @@
/* packet-bthci_iso.h
*
* Wireshark - Network traffic analyzer
* By Gerald Combs <gerald@wireshark.org>
* Copyright 1998 Gerald Combs
*
* SPDX-License-Identifier: GPL-2.0-or-later
*/
#ifndef __PACKET_BTHCI_ISO_H__
#define __PACKET_BTHCI_ISO_H__
#endif
/*
* Editor modelines - https://www.wireshark.org/tools/modelines.html
*
* Local variables:
* c-basic-offset: 4
* tab-width: 8
* indent-tabs-mode: nil
* End:
*
* vi: set shiftwidth=4 tabstop=8 expandtab:
* :indentSize=4:tabSize=8:noTabs=true:
*/

View File

@ -30,6 +30,7 @@ static const value_string hci_h1_type_vals[] = {
{BTHCI_CHANNEL_ACL, "ACL Data"},
{BTHCI_CHANNEL_SCO, "SCO Data"},
{BTHCI_CHANNEL_EVENT, "HCI Event"},
{BTHCI_CHANNEL_ISO, "ISO Data"},
{0, NULL }
};
static const value_string hci_h1_direction_vals[] = {

View File

@ -35,6 +35,7 @@ static const value_string hci_h4_type_vals[] = {
{HCI_H4_TYPE_ACL, "ACL Data"},
{HCI_H4_TYPE_SCO, "SCO Data"},
{HCI_H4_TYPE_EVT, "HCI Event"},
{HCI_H4_TYPE_ISO, "ISO Data"},
{0, NULL }
};
static const value_string hci_h4_direction_vals[] = {

View File

@ -1114,6 +1114,7 @@ struct bthci_phdr {
#define BTHCI_CHANNEL_ACL 2
#define BTHCI_CHANNEL_SCO 3
#define BTHCI_CHANNEL_EVENT 4
#define BTHCI_CHANNEL_ISO 5
/* pseudo header for WTAP_ENCAP_BLUETOOTH_LINUX_MONITOR */
struct btmon_phdr {