aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorEndre Kollar <taxy443@gmail.com>2010-07-27 06:40:00 -0400
committerGreg Kroah-Hartman <gregkh@suse.de>2010-07-27 14:08:31 -0400
commitb7a937e90c3631cf3662a518cf2e4bf07f72967c (patch)
tree2ec71fa97df5d8261c1aa9f0aafc01c9214d4024
parentab30f12d4ef11cc92fa9a657bf0c9b9951f24011 (diff)
Staging: usbip: Filtering illegal flags from remote driver
The usb_submit_urb function in debug mode monitors the bogus flags. The client driver errors should not be conveyed to the local USB device. Signed-off-by: Endre Kollar <taxy443@gmail.com> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
-rw-r--r--drivers/staging/usbip/stub_rx.c55
1 files changed, 55 insertions, 0 deletions
diff --git a/drivers/staging/usbip/stub_rx.c b/drivers/staging/usbip/stub_rx.c
index c6022602749e..3e9d46358dde 100644
--- a/drivers/staging/usbip/stub_rx.c
+++ b/drivers/staging/usbip/stub_rx.c
@@ -424,6 +424,60 @@ static int get_pipe(struct stub_device *sdev, int epnum, int dir)
424 return 0; 424 return 0;
425} 425}
426 426
427static void masking_bogus_flags(struct urb *urb)
428{
429 int xfertype;
430 struct usb_device *dev;
431 struct usb_host_endpoint *ep;
432 int is_out;
433 unsigned int allowed;
434
435 if (!urb || urb->hcpriv || !urb->complete)
436 return;
437 dev = urb->dev;
438 if ((!dev) || (dev->state < USB_STATE_UNAUTHENTICATED))
439 return;
440
441 ep = (usb_pipein(urb->pipe) ? dev->ep_in : dev->ep_out)
442 [usb_pipeendpoint(urb->pipe)];
443 if (!ep)
444 return;
445
446 xfertype = usb_endpoint_type(&ep->desc);
447 if (xfertype == USB_ENDPOINT_XFER_CONTROL) {
448 struct usb_ctrlrequest *setup =
449 (struct usb_ctrlrequest *) urb->setup_packet;
450
451 if (!setup)
452 return;
453 is_out = !(setup->bRequestType & USB_DIR_IN) ||
454 !setup->wLength;
455 } else {
456 is_out = usb_endpoint_dir_out(&ep->desc);
457 }
458
459 /* enforce simple/standard policy */
460 allowed = (URB_NO_TRANSFER_DMA_MAP | URB_NO_SETUP_DMA_MAP |
461 URB_NO_INTERRUPT | URB_DIR_MASK | URB_FREE_BUFFER);
462 switch (xfertype) {
463 case USB_ENDPOINT_XFER_BULK:
464 if (is_out)
465 allowed |= URB_ZERO_PACKET;
466 /* FALLTHROUGH */
467 case USB_ENDPOINT_XFER_CONTROL:
468 allowed |= URB_NO_FSBR; /* only affects UHCI */
469 /* FALLTHROUGH */
470 default: /* all non-iso endpoints */
471 if (!is_out)
472 allowed |= URB_SHORT_NOT_OK;
473 break;
474 case USB_ENDPOINT_XFER_ISOC:
475 allowed |= URB_ISO_ASAP;
476 break;
477 }
478 urb->transfer_flags &= allowed;
479}
480
427static void stub_recv_cmd_submit(struct stub_device *sdev, 481static void stub_recv_cmd_submit(struct stub_device *sdev,
428 struct usbip_header *pdu) 482 struct usbip_header *pdu)
429{ 483{
@@ -490,6 +544,7 @@ static void stub_recv_cmd_submit(struct stub_device *sdev,
490 /* no need to submit an intercepted request, but harmless? */ 544 /* no need to submit an intercepted request, but harmless? */
491 tweak_special_requests(priv->urb); 545 tweak_special_requests(priv->urb);
492 546
547 masking_bogus_flags(priv->urb);
493 /* urb is now ready to submit */ 548 /* urb is now ready to submit */
494 ret = usb_submit_urb(priv->urb, GFP_KERNEL); 549 ret = usb_submit_urb(priv->urb, GFP_KERNEL);
495 550