aboutsummaryrefslogtreecommitdiffstats
path: root/epan/dissectors/packet-btl2cap.c
diff options
context:
space:
mode:
authorStig Bjørlykke <stig@bjorlykke.org>2019-10-02 09:40:05 +0200
committerAnders Broman <a.broman58@gmail.com>2019-10-02 12:37:32 +0000
commit4108b54bc1b5843d952238716626b2694479ccd9 (patch)
tree44ebc2c0cffa89d104eec9b49f0fc20fb9ba95b6 /epan/dissectors/packet-btl2cap.c
parent1b7261727a14224688eecd179172ab6ad6327ad1 (diff)
btl2cap: Improve CoC request/response matching
Use signaling channel and command identifier to match CoC request and response, and then use scid and dcid later to match SDUs. Change-Id: If599d216aa9eb4c81db6eebdc4087afa696840a2 Reviewed-on: https://code.wireshark.org/review/34675 Petri-Dish: Stig Bjørlykke <stig@bjorlykke.org> Tested-by: Petri Dish Buildbot Reviewed-by: Anders Broman <a.broman58@gmail.com>
Diffstat (limited to 'epan/dissectors/packet-btl2cap.c')
-rw-r--r--epan/dissectors/packet-btl2cap.c59
1 files changed, 39 insertions, 20 deletions
diff --git a/epan/dissectors/packet-btl2cap.c b/epan/dissectors/packet-btl2cap.c
index 5f0ad7bc58..df570e3cfb 100644
--- a/epan/dissectors/packet-btl2cap.c
+++ b/epan/dissectors/packet-btl2cap.c
@@ -161,12 +161,15 @@ static expert_field ei_btl2cap_unknown_command_code = EI_INIT;
static dissector_table_t l2cap_psm_dissector_table;
static dissector_table_t l2cap_cid_dissector_table;
+/* This table maps command identity values to psm values. */
+static wmem_tree_t *cmd_ident_to_psm_table;
+
/* This table maps cid values to psm values.
* The same table is used both for SCID and DCID.
* For Remote CIDs (Receive Request SCID or Sent Response DCID)
* we 'or' the CID with 0x80000000 in this table
*/
-static wmem_tree_t *cid_to_psm_table = NULL;
+static wmem_tree_t *cid_to_psm_table;
/* 5.4 RETRANSMISSION AND FLOW CONTROL OPTION
* Table 5.2
@@ -808,7 +811,7 @@ dissect_connrequest(tvbuff_t *tvb, int offset, packet_info *pinfo,
}
static int
dissect_le_credit_based_connrequest(tvbuff_t *tvb, int offset, packet_info *pinfo,
- proto_tree *tree, proto_tree *command_tree, gboolean is_ch_request _U_,
+ proto_tree *tree, proto_tree *command_tree, guint16 cid, guint8 cmd_ident,
bthci_acl_data_t *acl_data, btl2cap_data_t *l2cap_data)
{
@@ -837,11 +840,12 @@ dissect_le_credit_based_connrequest(tvbuff_t *tvb, int offset, packet_info *pinf
offset += 2;
if (!pinfo->fd->visited) {
- wmem_tree_key_t key[6];
+ wmem_tree_key_t key[7];
guint32 k_interface_id;
guint32 k_adapter_id;
guint32 k_chandle;
guint32 k_cid;
+ guint32 k_cmd_ident;
guint32 k_frame_number;
guint32 interface_id;
guint32 adapter_id;
@@ -858,7 +862,8 @@ dissect_le_credit_based_connrequest(tvbuff_t *tvb, int offset, packet_info *pinf
k_interface_id = interface_id;
k_adapter_id = adapter_id;
k_chandle = chandle;
- k_cid = scid;
+ k_cid = cid;
+ k_cmd_ident = cmd_ident;
k_frame_number = pinfo->num;
psm_data = wmem_new0(wmem_file_scope(), psm_data_t);
@@ -887,6 +892,17 @@ dissect_le_credit_based_connrequest(tvbuff_t *tvb, int offset, packet_info *pinf
key[3].length = 1;
key[3].key = &k_cid;
key[4].length = 1;
+ key[4].key = &k_cmd_ident;
+ key[5].length = 1;
+ key[5].key = &k_frame_number;
+ key[6].length = 0;
+ key[6].key = NULL;
+
+ wmem_tree_insert32_array(cmd_ident_to_psm_table, key, psm_data);
+
+ k_cid = scid;
+
+ key[4].length = 1;
key[4].key = &k_frame_number;
key[5].length = 0;
key[5].key = NULL;
@@ -962,7 +978,7 @@ dissect_le_credit_based_connrequest(tvbuff_t *tvb, int offset, packet_info *pinf
static int
dissect_le_credit_based_connresponse(tvbuff_t *tvb, int offset, packet_info *pinfo,
- proto_tree *tree, bthci_acl_data_t *acl_data)
+ proto_tree *tree, guint16 cid, guint8 cmd_ident, bthci_acl_data_t *acl_data)
{
guint32 dcid;
@@ -984,16 +1000,16 @@ dissect_le_credit_based_connresponse(tvbuff_t *tvb, int offset, packet_info *pin
if (pinfo->fd->visited == 0) {
psm_data_t *psm_data;
- wmem_tree_key_t key[6];
+ wmem_tree_key_t key[7];
guint32 k_interface_id;
guint32 k_adapter_id;
guint32 k_chandle;
guint32 k_cid;
+ guint32 k_cmd_ident;
guint32 k_frame_number;
guint32 interface_id;
guint32 adapter_id;
guint32 chandle;
- guint32 cid;
if (pinfo->rec->presence_flags & WTAP_HAS_INTERFACE_ID)
interface_id = pinfo->rec->rec_header.packet_header.interface_id;
@@ -1001,12 +1017,12 @@ dissect_le_credit_based_connresponse(tvbuff_t *tvb, int offset, packet_info *pin
interface_id = HCI_INTERFACE_DEFAULT;
adapter_id = (acl_data) ? acl_data->adapter_id : HCI_ADAPTER_DEFAULT;
chandle = (acl_data) ? acl_data->chandle : 0;
- cid = dcid;
k_interface_id = interface_id;
k_adapter_id = adapter_id;
k_chandle = chandle;
k_cid = cid;
+ k_cmd_ident = cmd_ident;
k_frame_number = pinfo->num;
key[0].length = 1;
@@ -1018,25 +1034,25 @@ dissect_le_credit_based_connresponse(tvbuff_t *tvb, int offset, packet_info *pin
key[3].length = 1;
key[3].key = &k_cid;
key[4].length = 1;
- key[4].key = &k_frame_number;
- key[5].length = 0;
- key[5].key = NULL;
+ key[4].key = &k_cmd_ident;
+ key[5].length = 1;
+ key[5].key = &k_frame_number;
+ key[6].length = 0;
+ key[6].key = NULL;
- psm_data = (psm_data_t *)wmem_tree_lookup32_array_le(cid_to_psm_table, key);
+ psm_data = (psm_data_t *)wmem_tree_lookup32_array_le(cmd_ident_to_psm_table, key);
if (psm_data &&
psm_data->interface_id == interface_id &&
psm_data->adapter_id == adapter_id &&
psm_data->chandle == chandle &&
- ((pinfo->p2p_dir == P2P_DIR_SENT && psm_data->remote_cid == cid) ||
- (pinfo->p2p_dir == P2P_DIR_RECV && psm_data->local_cid == cid)) &&
psm_data->disconnect_in_frame > pinfo->num)
{
- cid = dcid | 0x80000000;
+ dcid |= 0x80000000;
k_interface_id = interface_id;
k_adapter_id = adapter_id;
k_chandle = chandle;
- k_cid = cid;
+ k_cid = dcid;
k_frame_number = pinfo->num;
key[0].length = 1;
@@ -1053,9 +1069,9 @@ dissect_le_credit_based_connresponse(tvbuff_t *tvb, int offset, packet_info *pin
key[5].key = NULL;
if (pinfo->p2p_dir == P2P_DIR_RECV)
- psm_data->remote_cid = cid;
+ psm_data->remote_cid = dcid;
else
- psm_data->local_cid = cid;
+ psm_data->local_cid = dcid;
wmem_tree_insert32_array(cid_to_psm_table, key, psm_data);
}
@@ -2468,6 +2484,7 @@ dissect_btl2cap(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data)
proto_item *ti_command;
proto_tree *btl2cap_cmd_tree;
guint8 cmd_code;
+ guint8 cmd_ident;
guint16 cmd_length;
const gchar *cmd_str;
@@ -2481,6 +2498,7 @@ dissect_btl2cap(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data)
proto_tree_add_item(btl2cap_cmd_tree, hf_btl2cap_cmd_code, tvb, offset, 1, ENC_LITTLE_ENDIAN);
offset += 1;
+ cmd_ident = tvb_get_guint8(tvb, offset);
proto_tree_add_item(btl2cap_cmd_tree, hf_btl2cap_cmd_ident, tvb, offset, 1, ENC_LITTLE_ENDIAN);
offset += 1;
@@ -2573,14 +2591,14 @@ dissect_btl2cap(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data)
break;
case 0x14: /* LE Credit Based Connection Request */
- offset = dissect_le_credit_based_connrequest(tvb, offset, pinfo, btl2cap_tree, btl2cap_cmd_tree, TRUE, acl_data, l2cap_data);
+ offset = dissect_le_credit_based_connrequest(tvb, offset, pinfo, btl2cap_tree, btl2cap_cmd_tree, cid, cmd_ident, acl_data, l2cap_data);
col_append_fstr(pinfo->cinfo, COL_INFO, " (CID: %04x, Initial Credits: %u)",
tvb_get_letohs(tvb, offset - 8), tvb_get_letohs(tvb, offset - 2));
break;
case 0x15: /* LE Credit Based Connection Response */
- offset = dissect_le_credit_based_connresponse(tvb, offset, pinfo, btl2cap_cmd_tree, acl_data);
+ offset = dissect_le_credit_based_connresponse(tvb, offset, pinfo, btl2cap_cmd_tree, cid, cmd_ident, acl_data);
col_append_fstr(pinfo->cinfo, COL_INFO, " (CID: %04x, Initial Credits: %u)",
tvb_get_letohs(tvb, offset - 10), tvb_get_letohs(tvb, offset - 4));
@@ -3378,6 +3396,7 @@ proto_register_btl2cap(void)
expert_btl2cap = expert_register_protocol(proto_btl2cap);
expert_register_field_array(expert_btl2cap, ei, array_length(ei));
+ cmd_ident_to_psm_table = wmem_tree_new_autoreset(wmem_epan_scope(), wmem_file_scope());
cid_to_psm_table = wmem_tree_new_autoreset(wmem_epan_scope(), wmem_file_scope());
register_decode_as(&btl2cap_cid_da);