summaryrefslogtreecommitdiff
path: root/epan
diff options
context:
space:
mode:
authorMartin Kaiser <wireshark@kaiser.cx>2014-08-19 18:08:34 +0200
committerMartin Kaiser <wireshark@kaiser.cx>2014-08-19 21:39:49 +0000
commitcdfd6e4a93598aa770a4efd1d63182f2e190bcf3 (patch)
treed4f666a69d718748be7e7033d7e74f2a49769bf1 /epan
parent7146999963e0e8baadf5cbe339f71836c43749bc (diff)
downloadwireshark-cdfd6e4a93598aa770a4efd1d63182f2e190bcf3.tar.gz
handle all combinations of request type and recipient
for USB control messages Change-Id: I9d2ad2995975e1853c73d712b429a30cead8f473 Reviewed-on: https://code.wireshark.org/review/3737 Reviewed-by: Martin Kaiser <wireshark@kaiser.cx> Tested-by: Martin Kaiser <wireshark@kaiser.cx>
Diffstat (limited to 'epan')
-rw-r--r--epan/dissectors/packet-usb.c41
1 files changed, 30 insertions, 11 deletions
diff --git a/epan/dissectors/packet-usb.c b/epan/dissectors/packet-usb.c
index 63192191cd..2d62df5bfc 100644
--- a/epan/dissectors/packet-usb.c
+++ b/epan/dissectors/packet-usb.c
@@ -2563,11 +2563,12 @@ try_dissect_next_protocol(proto_tree *tree, proto_tree *parent, tvbuff_t *next_t
guint32 k_bus_id;
usb_trans_info_t *usb_trans_info;
heur_dtbl_entry_t *hdtbl_entry;
- heur_dissector_list_t heur_subdissector_list;
- dissector_table_t usb_dissector_table;
+ heur_dissector_list_t heur_subdissector_list = NULL;
+ dissector_table_t usb_dissector_table = NULL;
proto_item *sub_item;
device_product_data_t *device_product_data;
device_protocol_data_t *device_protocol_data;
+ guint8 ctrl_recip;
if (tvb_captured_length(next_tvb) == 0)
return 0;
@@ -2628,30 +2629,42 @@ try_dissect_next_protocol(proto_tree *tree, proto_tree *parent, tvbuff_t *next_t
break;
case URB_CONTROL:
- heur_subdissector_list = heur_control_subdissector_list;
- usb_dissector_table = usb_control_dissector_table;
-
usb_trans_info = usb_conv_info->usb_trans_info;
if (!usb_trans_info)
break;
- if (USB_TYPE(usb_trans_info->setup.requesttype) != RQT_SETUP_TYPE_CLASS)
+ /* for standard control requests and responses, there's no
+ need to query dissector tables */
+ if (USB_TYPE(usb_trans_info->setup.requesttype) == RQT_SETUP_TYPE_STANDARD)
break;
- /* we have a class-specific control message */
+ ctrl_recip = USB_RECIPIENT(usb_trans_info->setup.requesttype);
- if (USB_RECIPIENT(usb_trans_info->setup.requesttype) == RQT_SETUP_RECIPIENT_INTERFACE) {
+ if (ctrl_recip == RQT_SETUP_RECIPIENT_DEVICE) {
+ /* a non-standard control message addressed to a device
+ this is not supported (I don't think it's used
+ anywhere) */
+ break;
+ }
+ else if (ctrl_recip == RQT_SETUP_RECIPIENT_INTERFACE) {
guint8 interface_num = usb_trans_info->setup.wIndex & 0xff;
+ heur_subdissector_list = heur_control_subdissector_list;
+ usb_dissector_table = usb_control_dissector_table;
+
usb_conv_info = get_usb_iface_conv_info(pinfo, interface_num);
usb_conv_info->usb_trans_info = usb_trans_info;
- } else if (USB_RECIPIENT(usb_trans_info->setup.requesttype) == RQT_SETUP_RECIPIENT_ENDPOINT) {
+ }
+ else if (ctrl_recip == RQT_SETUP_RECIPIENT_ENDPOINT) {
static address endpoint_addr;
gint endpoint;
static usb_address_t src_addr, dst_addr; /* has to be static due to SET_ADDRESS */
guint32 src_endpoint, dst_endpoint;
conversation_t *conversation;
+ heur_subdissector_list = heur_control_subdissector_list;
+ usb_dissector_table = usb_control_dissector_table;
+
endpoint = usb_trans_info->setup.wIndex & 0x0f;
if (usb_conv_info->is_request) {
@@ -2673,6 +2686,13 @@ try_dissect_next_protocol(proto_tree *tree, proto_tree *parent, tvbuff_t *next_t
usb_conv_info = get_usb_conv_info(conversation);
usb_conv_info->usb_trans_info = usb_trans_info;
+
+ }
+ else {
+ /* the recipient is "other" or "reserved"
+ it makes no sense to set usb_dissector_table since there's no way for
+ us to link this message to a device class */
+ heur_subdissector_list = heur_control_subdissector_list;
}
usb_tap_queue_packet(pinfo, urb_type, usb_conv_info);
@@ -2681,8 +2701,7 @@ try_dissect_next_protocol(proto_tree *tree, proto_tree *parent, tvbuff_t *next_t
break;
default:
- heur_subdissector_list = NULL;
- usb_dissector_table = NULL;
+ break;
}
if (try_heuristics) {