linux/drivers/usb/core
inaky@linux.intel.com 88fafff9d7 usb hub: fix root hub code so it takes more than 15 devices per root hub
Wireless USB Host Controllers accept a large number of devices per
host, which shows up as a large number of ports in its root hub.

When the number of ports in a hub device goes over 16, the activation
of the hub fails with the cryptic message in klogd.

hub 2-0:1.0: activate --> -22

Following this further, it was seen that:

hub_probe()
  hub_configure()
    generates pipe number

    pseudo allocates buffer 'maxp' bytes in size using usb_maxpacket()

      The endpoint descriptor for a root hub interrupt endpoint is
      declared in
      drivers/usb/core/hcd.c:hs_rh_config_descriptor and declares it
      to be size two (supporting 15 devices max).

    hub_activate()
      usb_hcd_submit_urb()
        rh_urb_enqueue()
          urb->pipe is neither int nor ctl, so it errors out
            rh_queue_status()
              Returns -EINVAL because the buffer length is smaller
              than the minimum needed to report all the hub port
              bits as in accordance with USB2.0[11.12.3]. There has
              to be trunc((PORTS + 1 + 7) / 8) bytes of space at
              least.

Alan Stern confirmed that the reason for reading maxpktsize and not
the right amount is because some hubs are known to return more data
and thus cause overflow. 

So this patch simply changes the code to make the interrupt endpoint's
max packet size be at least the minimum required by USB_MAXCHILDREN
(instead of a fixed magic number) and add documentation for that. This
way we are always ahead of the limit.

Signed-off-by: Inaky Perez-Gonzalez <inaky.perez-gonzalez@intel.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
2006-12-01 14:23:26 -08:00
..
buffer.c usbcore: trim down usb_bus structure 2006-09-27 11:58:56 -07:00
config.c usb: deal with broken config descriptors 2006-09-27 11:58:55 -07:00
devices.c USB: Remove unneeded void * casts in core files 2006-09-27 11:58:59 -07:00
devio.c usb devio: handle class_device_create() error 2006-10-17 14:46:32 -07:00
driver.c USB: fix autosuspend when CONFIG_PM isn't set 2006-09-28 15:36:46 -07:00
endpoint.c usbcore: fix endpoint device creation 2006-10-17 14:46:32 -07:00
file.c fix file specification in comments 2006-10-03 23:01:26 +02:00
generic.c Remove all inclusions of <linux/config.h> 2006-10-04 03:38:54 -04:00
hcd-pci.c USB: Properly unregister reboot notifier in case of failure in ehci hcd 2006-09-27 11:58:54 -07:00
hcd.c usb hub: fix root hub code so it takes more than 15 devices per root hub 2006-12-01 14:23:26 -08:00
hcd.h IRQ: Maintain regs pointer globally rather than passing to IRQ handlers 2006-10-05 15:10:12 +01:00
hub.c usb hub: fix root hub code so it takes more than 15 devices per root hub 2006-12-01 14:23:26 -08:00
hub.h usb/hub: allow hubs up to 31 children 2006-12-01 14:23:26 -08:00
inode.c [PATCH] usb: fixup usb so it uses struct pid 2006-10-02 07:57:15 -07:00
Kconfig [PATCH] USB: remove devfs information from Kconfig 2006-07-12 16:03:23 -07:00
Makefile usbcore: move code among source files 2006-09-27 11:58:50 -07:00
message.c USB: Fixed outdated usb_get_device_descriptor() documentation 2006-11-16 14:26:12 -08:00
notify.c usbfs: private mutex for open, release, and remove 2006-09-27 11:58:49 -07:00
otg_whitelist.h Linux-2.6.12-rc2 2005-04-16 15:20:36 -07:00
sysfs.c USB: fix __must_check warnings in drivers/usb/core/ 2006-09-27 11:58:57 -07:00
urb.c USB: Remove unneeded void * casts in core files 2006-09-27 11:58:59 -07:00
usb.c fix file specification in comments 2006-10-03 23:01:26 +02:00
usb.h [PATCH] usb: fixup usb so it uses struct pid 2006-10-02 07:57:15 -07:00