void dissect_dm1(proto_tree *tree, tvbuff_t *tvb, packet_info *pinfo, int offset) { int len; /* payload length indicated by payload header */ int llid; /* logical link id */ int l2len; /* length indicated by l2cap header */ proto_item *dm1_item; proto_tree *dm1_tree; tvbuff_t *pld_tvb; /* * FIXME * I'm probably doing a terrible, terrible thing here, but it gets my * initial test cases working. */ guint16 fake_acl_data; if(tvb_reported_length_remaining(tvb, offset) < 3) { col_add_str(pinfo->cinfo, COL_INFO, "Encrypted or malformed payload data"); return; } dm1_item = proto_tree_add_item(tree, hf_btbredr_payload, tvb, offset, -1, ENC_NA); dm1_tree = proto_item_add_subtree(dm1_item, ett_btbredr_payload); len = dissect_payload_header1(dm1_tree, tvb, offset); llid = tvb_get_guint8(tvb, offset) & 0x3; offset += 1; if(tvb_reported_length_remaining(tvb, offset) < len + 2) { col_add_str(pinfo->cinfo, COL_INFO, "Encrypted or malformed payload data"); return; } if (llid == 3 && btlmp_handle) { /* LMP */ pld_tvb = tvb_new_subset(tvb, offset, len, len); call_dissector(btlmp_handle, pld_tvb, pinfo, dm1_tree); } else if (llid == 2 && btl2cap_handle) { /* unfragmented L2CAP or start of fragment */ l2len = tvb_get_letohs(tvb, offset); if (l2len + 4 == len) { /* unfragmented */ pld_tvb = tvb_new_subset(tvb, offset, len, len); call_dissector_with_data(btl2cap_handle, pld_tvb, pinfo, dm1_tree, &fake_acl_data); } else { /* start of fragment */ proto_tree_add_item(dm1_tree, hf_btbredr_pldbody, tvb, offset, len, ENC_NA); } } else { proto_tree_add_item(dm1_tree, hf_btbredr_pldbody, tvb, offset, len, ENC_NA); } offset += len; proto_tree_add_item(dm1_tree, hf_btbredr_crc, tvb, offset, 2, ENC_LITTLE_ENDIAN); offset += 2; }
void dissect_dm1(proto_tree *tree, tvbuff_t *tvb, packet_info *pinfo, int offset) { int len; /* payload length indicated by payload header */ int llid; /* logical link id */ int l2len; /* length indicated by l2cap header */ proto_item *dm1_item; proto_tree *dm1_tree; tvbuff_t *pld_tvb; /* * FIXME * I'm probably doing a terrible, terrible thing here, but it gets my * initial test cases working. */ guint16 fake_acl_data; DISSECTOR_ASSERT(tvb_length_remaining(tvb, offset) >= 3); dm1_item = proto_tree_add_item(tree, hf_btbb_payload, tvb, offset, -1, ENC_NA); dm1_tree = proto_item_add_subtree(dm1_item, ett_btbb_payload); len = dissect_payload_header1(dm1_tree, tvb, offset); llid = tvb_get_guint8(tvb, offset) & 0x3; offset += 1; DISSECTOR_ASSERT(tvb_length_remaining(tvb, offset) == len + 2); if (llid == 3 && btlmp_handle) { /* LMP */ pld_tvb = tvb_new_subset(tvb, offset, len, len); call_dissector(btlmp_handle, pld_tvb, pinfo, dm1_tree); } else if (llid == 2 && btl2cap_handle) { /* unfragmented L2CAP or start of fragment */ l2len = tvb_get_letohs(tvb, offset); if (l2len + 4 == len) { /* unfragmented */ pinfo->private_data = &fake_acl_data; pld_tvb = tvb_new_subset(tvb, offset, len, len); call_dissector(btl2cap_handle, pld_tvb, pinfo, dm1_tree); } else { /* start of fragment */ proto_tree_add_item(dm1_tree, hf_btbb_pldbody, tvb, offset, len, ENC_NA); } } else { proto_tree_add_item(dm1_tree, hf_btbb_pldbody, tvb, offset, len, ENC_NA); } offset += len; proto_tree_add_item(dm1_tree, hf_btbb_crc, tvb, offset, 2, ENC_LITTLE_ENDIAN); offset += 2; }