[prev in list] [next in list] [prev in thread] [next in thread] 

List:       linux-usb
Subject:    Re: 3.13-rc1 regression: Scatter-gather list issues at SuperSpeed only
From:       Alan Stern <stern () rowland ! harvard ! edu>
Date:       2014-02-28 21:15:12
Message-ID: Pine.LNX.4.44L0.1402281548510.1358-100000 () iolanthe ! rowland ! org
[Download RAW message or body]

On Fri, 28 Feb 2014, Sarah Sharp wrote:

> When testing 3.14-rc1 with a USB 3.0 Lexar flash drive, the drive fails
> to be mounted.  I added a bit of debugging to the USB core:
> 
> diff --git a/drivers/usb/core/urb.c b/drivers/usb/core/urb.c
> index 9ff665f1322f..eff59ac37865 100644
> --- a/drivers/usb/core/urb.c
> +++ b/drivers/usb/core/urb.c
> @@ -430,9 +430,16 @@ int usb_submit_urb(struct urb *urb, gfp_t mem_flags)
> struct scatterlist *sg;
> int i;
> 
> -               for_each_sg(urb->sg, sg, urb->num_sgs - 1, i)
> -                       if (sg->length % max)
> +               for_each_sg(urb->sg, sg, urb->num_sgs - 1, i) {
> +                       if (sg->length % max) {
> +                               dev_dbg(&dev->dev,
> +                                               "URB sg entry %d of %d, size %d not \
> a multiple of ep%d%s max packet %d\n", +                                            \
> i, urb->num_sgs, sg->length, +                                               \
> usb_endpoint_num(&ep->desc), +                                               is_out \
> ? "out" : "in", max); return -EINVAL;
> +                       }
> +               }
> }
> 
> That revealed the SCSI request fails because the USB core is rejecting a
> scatter-gather list with an entry that isn't aligned to the max packet size:

> Feb 28 09:45:30 xanatos kernel: [  376.449316] usb 2-2: URB sg entry 0 of 17, size \
> 1536 not a multiple of ep1in max packet 1024

Notice the request length: 1536.  That's three 512-byte sectors.  A
little unusual, since most I/O is done in units of pages, which are
4096 bytes.

> It's failing because of commit 247bf557273d "xhci 1.0: Limit
> arbitrarily-aligned scatter gather."  That commit clears the
> hcd->self.no_sg_constraint flag if the host is a 1.0 host (which my
> Panther Point host is).  It was put in to avoid TD fragment issues on
> 1.0 hosts with ethernet devices.  (Note, this also means that David
> Laight's potential work-around patch [1] wouldn't help if
> arbitrary-length scatter gather bigger than a ring segment was
> submitted.)
> 
> The behavior for reproducing this is odd.  I can only reproduce this on
> my Ubuntu 13.10 laptop with Intel Panther Point xHCI, when the device is
> running at SuperSpeed.  If I plug the device into an EHCI port, or
> behind a USB 2.0 hub plugged into an xHCI port, I never see these
> arbitrary-length scatter-gather list entries.  Dan can't reproduce this
> on his Intel Haswell machine running Fedora at all.

Some of this behavior is to be expected.  1536 isn't a multiple of 1024
(the maxpacket size when running at SuperSpeed), but it _is_ a multiple
of 512 (the maxpacket size when running at high speed).  Therefore the
failure won't occur when the drive is attached to an EHCI controller or
is behind a USB-2 hub.

> The only speed-based decision I see usb-storage making is whether to
> clear the US_FLOW_GO_SLOW flag.  Changing that to set the flag for
> SuperSpeed devices as well didn't help:

That has nothing to do with this.  The GO_SLOW flag tells usb-storage 
to add a delay between the command phase and the data phase; it doesn't 
affect the sizes of the transfers.

> I'm stumped as to why we get arbitrary-length scatter-gather for
> SuperSpeed devices only,

You don't.  The same transfers occur at high speed -- it's just that
they don't cause an error.

> and only under Ubuntu.  Perhaps this comes
> directly from userspace?

Maybe.  I doubt the kernel would issue such a request on its own.  A
usbmon trace might shed a little light, although it won't tell what
program (if any) issued the request.

Does the same thing happen if you prevent the system from automatically 
trying to mount the volume?

> If we can't figure out how to get max-packet sized scatter-gather list
> entries from the mass storage driver, Mathias is going to need to:

The SG entries don't come from usb-storage; they come from the block 
layer.  As far as I know, there is no way to tell the block layer that 
each element in an SG list (except the last) must be a multiple of 
some specific size.

> revert commit 3804fad45411 USBNET: ax88179_178a: enable tso if usb host supports sg \
> dma revert commit 247bf557273d xhci 1.0: Limit arbitrarily-aligned scatter gather.
> 
> And we'll need to focus on getting the TD fragments supported in 3.16.

So far we've gotten away with this at high speed or below, because no
USB mass-storage devices have a block size smaller than 512 (at least,
none that I've ever heard of).  But when the maxpacket size is 1024, a
request for an odd number of blocks can cause trouble.

Alan Stern

--
To unsubscribe from this list: send the line "unsubscribe linux-usb" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic