bk://kernel.bkbits.net/gregkh/linux/usb-2.6 stern@rowland.harvard.edu|ChangeSet|20040525193350|22947 stern # This is a BitKeeper generated diff -Nru style patch. # # ChangeSet # 2004/05/25 13:48:31-07:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # drivers/usb/input/hiddev.c # 2004/05/25 13:48:27-07:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/usb.c # 2004/05/25 13:48:27-07:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/message.c # 2004/05/25 13:48:27-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/25 13:47:38-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # MAINTAINERS # 2004/05/25 13:47:34-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/25 12:33:50-07:00 stern@rowland.harvard.edu # [PATCH] USB: Gonzo variable renaming in hub.c # # As part of the cleanup effort, I wanted to name all the variables in hub.c # uniformly. Currently there are different names for the same thing in # different routines, and the same names are used for different things -- # it's impossible to keep things straight. I also wanted to step away from # the deplorable practice of naming everything "dev". It is not an # exaggeration that up until relatively recently one of the drivers (not the # hub driver, fortunately!) contained a line which looked basically like # this: # # dev->dev.dev = &intf->dev; # # If you can make sense out of that, you're a better code reader than I am! # # Ranting aside, this patch institutes the following name scheme for local # variables in hub.c: # # hub: struct usb_hub # hdev: hub's corresponding struct usb_device # hub_dev: hub interface's embedded struct device # udev: general struct usb_device # # There are a couple of genuine code changes hidden in there too. Just # trivial things, like creating a local hub_dev variable for use in place of # &hub->intf->dev. # # drivers/usb/core/hub.c # 2004/05/24 08:54:24-07:00 stern@rowland.harvard.edu +276 -269 # USB: Gonzo variable renaming in hub.c # # ChangeSet # 2004/05/25 12:33:17-07:00 stern@rowland.harvard.edu # [PATCH] USB: Make usb_choose_configuration() a separate subroutine # # This patch creates a separate subroutine to encapsulate the work required # in choosing an initial configuration for a device. In my opinion that # reflects a policy decision that should be kept apart from all the other # work involved in creating a new device structure. The existing code in # usb_new_device() is simply moved into usb_choose_configuration(). # # drivers/usb/core/usb.c # 2004/05/24 03:37:01-07:00 stern@rowland.harvard.edu +35 -30 # USB: Make usb_choose_configuration() a separate subroutine # # ChangeSet # 2004/05/25 12:27:47-07:00 stern@rowland.harvard.edu # [PATCH] USB: Add usb_release_address() and move usb_set_address() # # This patch adds usb_release_address() as a complement to # usb_choose_address(), to centralize the work required when freeing an # allocated device address. It also moves the usb_set_address() routine # from usb.c to hub.c -- which is the only place it is ever used -- and # renames it to hub_set_address(). # # drivers/usb/core/usb.c # 2004/05/24 03:29:23-07:00 stern@rowland.harvard.edu +18 -22 # USB: Add usb_release_address() and move usb_set_address() # # drivers/usb/core/hub.c # 2004/05/24 03:29:23-07:00 stern@rowland.harvard.edu +17 -3 # USB: Add usb_release_address() and move usb_set_address() # # drivers/usb/core/hcd.h # 2004/05/24 03:29:23-07:00 stern@rowland.harvard.edu +2 -2 # USB: Add usb_release_address() and move usb_set_address() # # ChangeSet # 2004/05/25 11:50:29-07:00 stern@rowland.harvard.edu # [PATCH] USB: Change "driverfs" to "sysfs" in usbcore # # Before fixing up the device locking and device reset code, I want to do # some cleanups of the hub driver and related areas. This is the first of a # series of patches for that purpose. # # This patch changes all the occurrences of "driverfs" in usbcore to "sysfs" # -- I just couldn't stand seeing the out-of-date name any more (and I kept # confusing it with usbfs, don't know why). # # Although I did a "bk mv driverfs.c sysfs.c" when creating the patch, the # exported patch file itself doesn't reflect that very well. It looks like # driverfs.c was deleted and sysfs.c created from scratch. If you prefer, I # can resubmit this in a slightly different form, with the file name # unchanged so that you can issue the "bk mv" command in your repository # after applying the patch. # # drivers/usb/core/usb.h # 2004/05/24 03:23:37-07:00 stern@rowland.harvard.edu +2 -2 # USB: Change "driverfs" to "sysfs" in usbcore # # drivers/usb/core/usb.c # 2004/05/24 03:23:37-07:00 stern@rowland.harvard.edu +1 -1 # USB: Change "driverfs" to "sysfs" in usbcore # # drivers/usb/core/message.c # 2004/05/24 03:23:37-07:00 stern@rowland.harvard.edu +1 -1 # USB: Change "driverfs" to "sysfs" in usbcore # # drivers/usb/core/sysfs.c # 2004/05/24 03:23:37-07:00 stern@rowland.harvard.edu +4 -4 # USB: Change "driverfs" to "sysfs" in usbcore # # drivers/usb/core/Makefile # 2004/05/24 03:23:37-07:00 stern@rowland.harvard.edu +1 -1 # USB: Change "driverfs" to "sysfs" in usbcore # # ChangeSet # 2004/05/25 11:38:39-07:00 stern@rowland.harvard.edu # [PATCH] USB UHCI: allow URBs to be unlinked when IRQs don't work # # A lot of people with USB controllers made by VIA have been suffering from # the fact that these controllers stop working when they receive a babble # packet. In particular, they stop generating interrupt requests. Since # the UHCI driver relies on IRQs from the controller for proper timing and # interlocking of unlink requests, this means that those broken controllers # will hang the UHCI driver and drivers for any device connected through it. # # This patch, written by Herbert Xu, gives the UCHI driver the ability to # manage the unlink procedure using timer interrupts as well as controller # interrupts. (It also fixes a race in the UHCI irq handler.) Although it # won't prevent the VIA controllers from flaking out when they encounter # babble, at least now users will be able to rmmod the uhci-hcd driver and # then reload it, restoring their systems back to normal operation (until # the next babble!). # # P.S.: Herbert, there's one loose end I still want to tie up. When the # controller isn't running (i.e., is suspended) the frame number won't # change, but unlinks still need to work. It's a small point, not too # likely to come up in normal usage. I'll fix it later on when I update the # state-changing part of the driver. # # drivers/usb/host/uhci-hcd.h # 2004/05/19 16:25:26-07:00 stern@rowland.harvard.edu +3 -0 # USB UHCI: allow URBs to be unlinked when IRQs don't work # # drivers/usb/host/uhci-hcd.c # 2004/05/19 16:41:50-07:00 stern@rowland.harvard.edu +46 -5 # USB UHCI: allow URBs to be unlinked when IRQs don't work # # ChangeSet # 2004/05/25 11:37:59-07:00 stern@rowland.harvard.edu # [PATCH] USB: Initially read 9 bytes of config descriptor # # This patch reads the full 9 bytes of a configuration descriptor during # enumeration rather than just the first 8 bytes. That's how Windows does # it, and today I ran across a device that doesn't work properly when asked # to send only 8 bytes worth. I doubt very much this will cause any # problems with currently-working devices; since the descriptor itself is 9 # bytes long and since the devices are most likely to expect a 9-byte # request, anything that can handle an 8-byte request should have no # difficulty. (Also, some debugging messages have been slightly improved.) # # Incidentally, USB traces taken from Windows 2000 and Windows XP show that # when those operating systems retrieve a string descriptor during # enumeration, they do so by requesting a 255-byte transfer. They do not # first ask just for the initial 2 bytes (which contain the actual length) # and then ask for the actual length, which is what we do. Interestingly, # back in 2.4 we _did_ do things the same as Windows. # # drivers/usb/core/config.c # 2004/05/21 03:00:23-07:00 stern@rowland.harvard.edu +9 -8 # USB: Initially read 9 bytes of config descriptor # # ChangeSet # 2004/05/25 11:31:08-07:00 jnardelli@infosciences.com # [PATCH] USB: visor: Fix Oops on disconnect # # This fixes http://bugme.osdl.org/show_bug.cgi?id=2289 # # This patch has been tweaked by greg@kroah.com # # drivers/usb/serial/visor.c # 2004/05/25 11:19:19-07:00 jnardelli@infosciences.com +64 -59 # USB: visor: Fix Oops on disconnect # # ChangeSet # 2004/05/25 11:00:57-07:00 olh@suse.de # [PATCH] USB: out of bounds access in hiddev_cleanup # # hiddev_table[] is an array of pointers. the minor number is used as an # offset. hiddev minors start either with zero, or with 96. If they start # with 96, the offset must be reduced by HIDDEV_MINOR_BASE because only 16 # minors are available. unplugging a hiddevice will zero data outside the # hiddev_table array. # # this was spotted by Takashi Iwai. # # drivers/usb/input/hiddev.c # 2004/05/19 07:48:16-07:00 olh@suse.de +1 -1 # USB: out of bounds access in hiddev_cleanup # # ChangeSet # 2004/05/25 11:00:18-07:00 jamesl@appliedminds.com # [PATCH] USB: Fix down() in hard IRQ in powermate driver # # Fixes this warning: # # May 18 06:56:01 Knoppix kernel: Debug: sleeping function called from # invalid context at include/asm/semaphore.h:119 # May 18 06:56:01 Knoppix kernel: in_atomic():1, irqs_disabled():0 # May 18 06:56:01 Knoppix kernel: Call Trace: # May 18 06:56:01 Knoppix kernel: [] __might_sleep+0xb2/0xd3 # May 18 06:56:01 Knoppix kernel: [] powermate_config_complete+0x33/0x77 [powermate] # May 18 06:56:01 Knoppix kernel: [] usb_hcd_giveback_urb+0x25/0x39 # May 18 06:56:01 Knoppix kernel: [] uhci_finish_urb+0x54/0xa1 # May 18 06:56:01 Knoppix kernel: [] uhci_finish_completion+0x43/0x55 # May 18 06:56:01 Knoppix kernel: [] uhci_irq+0xf8/0x179 # May 18 06:56:01 Knoppix kernel: [] usb_hcd_irq+0x36/0x67 # May 18 06:56:01 Knoppix kernel: [] handle_IRQ_event+0x3a/0x64 # May 18 06:56:01 Knoppix kernel: [] do_IRQ+0xb8/0x192 # May 18 06:56:01 Knoppix kernel: [] common_interrupt+0x18/0x20 # # Attached patch uses spinlocks instead of a semaphore so that we can't sleep # when in_atomic(). # # drivers/usb/input/powermate.c # 2004/05/24 08:48:15-07:00 jamesl@appliedminds.com +12 -8 # USB: Fix down() in hard IRQ in powermate driver # # ChangeSet # 2004/05/24 17:06:48-07:00 Thomas.Wahrenbruch@kobil.com # [PATCH] USB: Fix kobil_sct with uhci # # the kobil_sct didn't work with uhci hcds. # It used usb_fill_bulk_urb instead of usb_fill_int_urb. # The attached patch fixes this. # # It starts reading in open now - this gives apps (CT-API) the chance to # detect the p'n'p string correctly. # # drivers/usb/serial/kobil_sct.c # 2004/05/24 09:56:30-07:00 Thomas.Wahrenbruch@kobil.com +31 -12 # USB: Fix kobil_sct with uhci # # drivers/usb/serial/Kconfig # 2004/05/24 09:54:50-07:00 Thomas.Wahrenbruch@kobil.com +2 -2 # USB: Fix kobil_sct with uhci # # ChangeSet # 2004/05/24 17:06:06-07:00 movits@bloomberg.com # [PATCH] USB: add support for MS adapter to usb pegasus net driver # # I took the relevant parts from the patch (not some PHY stuff that was # irrelevant). Attached is the patch against stock 2.6.6. # # drivers/usb/net/pegasus.h # 2004/05/20 15:09:36-07:00 movits@bloomberg.com +3 -0 # USB: add support for MS adapter to usb pegasus net driver # # ChangeSet # 2004/05/24 17:05:26-07:00 david-b@pacbell.net # [PATCH] USB: PXA 2xx UDC and RNDIS g_ether # # I noticed some problems with the PXA 2xx UDC and the # RNDIS version of the ethernet-over-usb link: # # - Static linking needs more than just two endpoints now # # - The endpoint autoconfig misbehaves (sounds like what # Stefan reported a couple weeks ago) # # This patch fixes those two problems, though there are # a couple others lurking too. # # drivers/usb/gadget/Kconfig # 2004/05/19 13:52:50-07:00 david-b@pacbell.net +1 -0 # USB: PXA 2xx UDC and RNDIS g_ether # # drivers/usb/gadget/epautoconf.c # 2004/05/19 13:52:55-07:00 david-b@pacbell.net +2 -1 # USB: PXA 2xx UDC and RNDIS g_ether # # ChangeSet # 2004/05/24 17:04:38-07:00 lcapitulino@prefeitura.sp.gov.br # [PATCH] USB: /usb/gadget/serial.c warning fix. # # that code is generating the fallowing warning: # # drivers/usb/gadget/serial.c:162: warning: `debug' defined but not used # # When G_SERIAL_DEBUG is not defined, `debug' is not used, because # the gs_debug() function is compiled only when G_SERIAL_DEBUG is # defined. # # Thus, a solution is to define `debug' only when G_SERIAL_DEBUG # is defined. That includes the use of `debug' as a module parameter # (this last part I'm not sure). # # The patch bellow does that (compiles ok, not tested because I don't # have that hardware): # # drivers/usb/gadget/serial.c # 2004/05/19 15:17:03-07:00 lcapitulino@prefeitura.sp.gov.br +3 -6 # USB: /usb/gadget/serial.c warning fix. # # ChangeSet # 2004/05/24 17:03:52-07:00 oliver@neukum.org # [PATCH] USB: fix fix to kaweth.c # # the previous patch was buggy. The state must be set _before_ the # condition is checked, or there's a window missing a wakeup. # This incremental change set fixes that. # # - fix race condition with current->state # # drivers/usb/net/kaweth.c # 2004/05/19 11:13:49-07:00 oliver@neukum.org +2 -1 # USB: fix fix to kaweth.c # # ChangeSet # 2004/05/24 17:03:19-07:00 oliver@neukum.org # [PATCH] USB: waitqueue related problem in kaweth # # this was buggy for the same reason that the old msleep was buggy. # # - safe waiting in case we are left on other wait queues # # drivers/usb/net/kaweth.c # 2004/05/19 10:33:39-07:00 oliver@neukum.org +4 -4 # USB: waitqueue related problem in kaweth # # ChangeSet # 2004/05/24 17:02:47-07:00 oliver@neukum.org # [PATCH] USB: yet another place for msleep # # this is in kobil_sct. # It uses msleep() and replaces needless GFP_ATOMICs with GFP_NOIO # as this function can sleep. # # - no need for GFP_ATOMIC # - use msleep() # # drivers/usb/serial/kobil_sct.c # 2004/05/19 10:21:50-07:00 oliver@neukum.org +3 -5 # USB: yet another place for msleep # # ChangeSet # 2004/05/24 17:02:10-07:00 oliver@neukum.org # [PATCH] USB: clean delays for ehci # # Here's one you overlooked. # # - safe sleep helper # # drivers/usb/storage/transport.c # 2004/05/19 08:53:06-07:00 oliver@neukum.org +1 -2 # USB: clean delays for ehci # # ChangeSet # 2004/05/24 17:01:41-07:00 errandir_news@mph.eclipse.co.uk # [PATCH] USB: usblp printer GET_DEVICE_ID fix # # There is a problem in the usblp GET_DEVICE_ID ioctl() implementation. The patch # below (against 2.6 current) fixes the code to be according to the official usb # printer spec. # # Most printers are not affected by this fix, as they use interface 0 and # alternate 0. For those, nothing changes. But my printer/scanner uses interface # 1 for the printer. # # drivers/usb/class/usblp.c # 2004/04/02 19:18:19-08:00 errandir_news@mph.eclipse.co.uk +17 -4 # USB: usblp printer GET_DEVICE_ID fix # # ChangeSet # 2004/05/24 11:48:01-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # include/linux/pci_ids.h # 2004/05/24 11:47:57-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/22 23:48:51-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # include/linux/pci_ids.h # 2004/05/22 23:48:48-07:00 akpm@bix.(none) +0 -0 # Auto merged # # MAINTAINERS # 2004/05/22 23:48:48-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/21 19:09:03-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # arch/ia64/defconfig # 2004/05/21 19:09:00-07:00 akpm@bix.(none) +0 -0 # Auto merged # # MAINTAINERS # 2004/05/21 19:09:00-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/19 18:31:55-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # MAINTAINERS # 2004/05/19 18:31:52-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/19 00:07:04-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # include/linux/usb.h # 2004/05/19 00:07:01-07:00 akpm@bix.(none) +0 -0 # Auto merged # # include/linux/pci_ids.h # 2004/05/19 00:07:01-07:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/usb.c # 2004/05/19 00:07:01-07:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ppc/defconfig # 2004/05/19 00:07:01-07:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ppc/configs/pmac_defconfig # 2004/05/19 00:07:01-07:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ppc/configs/common_defconfig # 2004/05/19 00:07:01-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/18 14:54:09-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # include/linux/usb.h # 2004/05/18 14:54:06-07:00 akpm@bix.(none) +0 -0 # Auto merged # # include/linux/pci_ids.h # 2004/05/18 14:54:06-07:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/input/hid-core.c # 2004/05/18 14:54:06-07:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/usb.c # 2004/05/18 14:54:06-07:00 akpm@bix.(none) +0 -0 # Auto merged # # CREDITS # 2004/05/18 14:54:06-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/16 01:52:25-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # include/linux/pci_ids.h # 2004/05/16 01:52:22-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/14 21:45:47-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # include/linux/pci_ids.h # 2004/05/14 21:45:43-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/14 09:41:12-07:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # drivers/usb/input/hid-core.c # 2004/05/14 09:41:09-07:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/usb.c # 2004/05/14 09:41:09-07:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/message.c # 2004/05/14 09:41:09-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/12 20:32:44-07:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # drivers/usb/core/inode.c # 2004/05/12 20:32:41-07:00 akpm@bix.(none) +0 -0 # Auto merged # # MAINTAINERS # 2004/05/12 20:32:41-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/12 01:26:11-07:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # drivers/usb/input/wacom.c # 2004/05/12 01:26:08-07:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/input/hid-core.c # 2004/05/12 01:26:08-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/12 01:25:17-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # include/linux/pci_ids.h # 2004/05/12 01:25:14-07:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/parisc/configs/c3000_defconfig # 2004/05/12 01:25:14-07:00 akpm@bix.(none) +0 -0 # Auto merged # # MAINTAINERS # 2004/05/12 01:25:14-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/05 14:52:58-07:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # drivers/usb/core/message.c # 2004/05/05 14:52:55-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/05 14:52:11-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # CREDITS # 2004/05/05 14:52:08-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/04 14:13:11-07:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # include/linux/usb.h # 2004/05/04 14:13:08-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/01 15:23:25-07:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # MAINTAINERS # 2004/05/01 15:23:22-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/04/30 22:06:45-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # drivers/usb/core/inode.c # 2004/04/30 22:06:42-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/04/29 16:00:47-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # include/linux/pci_ids.h # 2004/04/29 16:00:44-07:00 akpm@bix.(none) +0 -0 # Auto merged # # MAINTAINERS # 2004/04/29 16:00:44-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/04/28 13:38:52-07:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # drivers/usb/input/hid-core.c # 2004/04/28 13:38:49-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/04/27 19:39:13-07:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # include/linux/usb.h # 2004/04/27 19:39:10-07:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/usb.c # 2004/04/27 19:39:10-07:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/message.c # 2004/04/27 19:39:10-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/04/26 18:31:48-07:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # include/linux/usb.h # 2004/04/26 18:31:45-07:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/usb.c # 2004/04/26 18:31:45-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/04/25 23:06:05-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # include/linux/pci_ids.h # 2004/04/25 23:06:02-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/04/24 23:51:05-07:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # drivers/usb/core/usb.c # 2004/04/24 23:51:02-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/04/23 12:58:38-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # CREDITS # 2004/04/23 12:58:35-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/04/19 19:45:10-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # include/linux/pci_ids.h # 2004/04/19 19:45:07-07:00 akpm@bix.(none) +0 -0 # Auto merged # # MAINTAINERS # 2004/04/19 19:45:07-07:00 akpm@bix.(none) +0 -0 # Auto merged # # CREDITS # 2004/04/19 19:45:06-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/04/07 20:17:13-07:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # drivers/usb/core/message.c # 2004/04/07 20:17:11-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/04/02 11:35:28-08:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # include/linux/pci_ids.h # 2004/04/02 11:35:25-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/04/01 15:16:14-08:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # CREDITS # 2004/04/01 15:16:11-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/31 19:24:39-08:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # include/linux/usb.h # 2004/03/31 19:24:37-08:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/usb.c # 2004/03/31 19:24:37-08:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/message.c # 2004/03/31 19:24:37-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ppc64/defconfig # 2004/03/31 19:24:36-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ppc64/configs/pSeries_defconfig # 2004/03/31 19:24:36-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ppc/defconfig # 2004/03/31 19:24:36-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ppc/configs/pmac_defconfig # 2004/03/31 19:24:36-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ppc/configs/common_defconfig # 2004/03/31 19:24:36-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/parisc/configs/c3000_defconfig # 2004/03/31 19:24:36-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ia64/defconfig # 2004/03/31 19:24:36-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ia64/configs/zx1_defconfig # 2004/03/31 19:24:36-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ia64/configs/generic_defconfig # 2004/03/31 19:24:36-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/arm/configs/neponset_defconfig # 2004/03/31 19:24:36-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/30 20:18:36-08:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # arch/ppc64/defconfig # 2004/03/30 20:18:33-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ppc64/configs/pSeries_defconfig # 2004/03/30 20:18:33-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ppc/defconfig # 2004/03/30 20:18:33-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ppc/configs/pmac_defconfig # 2004/03/30 20:18:33-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ppc/configs/common_defconfig # 2004/03/30 20:18:33-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/parisc/configs/c3000_defconfig # 2004/03/30 20:18:33-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ia64/defconfig # 2004/03/30 20:18:33-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ia64/configs/zx1_defconfig # 2004/03/30 20:18:33-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/ia64/configs/generic_defconfig # 2004/03/30 20:18:33-08:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/arm/configs/neponset_defconfig # 2004/03/30 20:18:32-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/30 12:09:32-08:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # include/linux/usb.h # 2004/03/30 12:09:29-08:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/usb.c # 2004/03/30 12:09:29-08:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/message.c # 2004/03/30 12:09:29-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/29 18:05:43-08:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # MAINTAINERS # 2004/03/29 18:05:41-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/29 13:51:58-08:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # CREDITS # 2004/03/29 13:51:56-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/28 12:29:41-08:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # drivers/usb/core/message.c # 2004/03/28 12:29:38-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/27 02:28:18-08:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # drivers/usb/input/wacom.c # 2004/03/27 02:28:16-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/26 12:24:49-08:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # include/linux/usb_gadget.h # 2004/03/26 12:24:46-08:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/usb.c # 2004/03/26 12:24:46-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/20 13:26:55-08:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # CREDITS # 2004/03/20 13:26:53-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/16 21:53:42-08:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # drivers/usb/input/wacom.c # 2004/03/16 21:53:39-08:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/input/hid-core.c # 2004/03/16 21:53:39-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/16 12:59:58-08:00 akpm@bix.(none) # Merge bk://kernel.bkbits.net/gregkh/linux/usb-2.6 # into bix.(none):/usr/src/bk-usb # # include/linux/usb_gadget.h # 2004/03/16 12:59:47-08:00 akpm@bix.(none) +0 -0 # Auto merged # # include/linux/usb.h # 2004/03/16 12:59:47-08:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/usb.c # 2004/03/16 12:59:46-08:00 akpm@bix.(none) +0 -0 # Auto merged # # MAINTAINERS # 2004/03/16 12:59:46-08:00 akpm@bix.(none) +0 -0 # Auto merged # # CREDITS # 2004/03/16 12:59:46-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/16 12:58:57-08:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # drivers/usb/input/wacom.c # 2004/03/16 12:58:47-08:00 akpm@bix.(none) +0 -4 # Auto merged # # drivers/usb/input/hid-core.c # 2004/03/16 12:58:47-08:00 akpm@bix.(none) +0 -0 # Auto merged # # CREDITS # 2004/03/16 12:58:46-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/14 11:03:00-08:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # include/linux/usb_gadget.h # 2004/03/14 11:02:47-08:00 akpm@bix.(none) +0 -0 # Auto merged # # include/linux/usb.h # 2004/03/14 11:02:47-08:00 akpm@bix.(none) +0 -0 # Auto merged # # drivers/usb/core/usb.c # 2004/03/14 11:02:47-08:00 akpm@bix.(none) +0 -0 # Auto merged # # MAINTAINERS # 2004/03/14 11:02:47-08:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/03/12 10:57:17-08:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-usb # # MAINTAINERS # 2004/03/12 10:57:02-08:00 akpm@bix.(none) +0 -0 # Auto merged # # CREDITS # 2004/03/12 10:57:01-08:00 akpm@bix.(none) +0 -0 # Auto merged # diff -Nru a/drivers/usb/class/usblp.c b/drivers/usb/class/usblp.c --- a/drivers/usb/class/usblp.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/class/usblp.c 2004-05-25 21:38:09 -07:00 @@ -226,11 +226,21 @@ static int usblp_ctrl_msg(struct usblp *usblp, int request, int type, int dir, int recip, int value, void *buf, int len) { - int retval = usb_control_msg(usblp->dev, + int retval; + int index = usblp->ifnum; + + /* High byte has the interface index. + Low byte has the alternate setting. + */ + if ((request == USBLP_REQ_GET_ID) && (type == USB_TYPE_CLASS)) { + index = (usblp->ifnum<<8)|usblp->protocol[usblp->current_protocol].alt_setting; + } + + retval = usb_control_msg(usblp->dev, dir ? usb_rcvctrlpipe(usblp->dev, 0) : usb_sndctrlpipe(usblp->dev, 0), - request, type | dir | recip, value, usblp->ifnum, buf, len, USBLP_WRITE_TIMEOUT); - dbg("usblp_control_msg: rq: 0x%02x dir: %d recip: %d value: %d len: %#x result: %d", - request, !!dir, recip, value, len, retval); + request, type | dir | recip, value, index, buf, len, USBLP_WRITE_TIMEOUT); + dbg("usblp_control_msg: rq: 0x%02x dir: %d recip: %d value: %d idx: %d len: %#x result: %d", + request, !!dir, recip, value, index, len, retval); return retval < 0 ? retval : 0; } @@ -439,6 +449,9 @@ retval = -ENODEV; goto done; } + + dbg("usblp_ioctl: cmd=0x%x (%c nr=%d len=%d dir=%d)", cmd, _IOC_TYPE(cmd), + _IOC_NR(cmd), _IOC_SIZE(cmd), _IOC_DIR(cmd) ); if (_IOC_TYPE(cmd) == 'P') /* new-style ioctl number */ diff -Nru a/drivers/usb/core/Makefile b/drivers/usb/core/Makefile --- a/drivers/usb/core/Makefile 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/core/Makefile 2004-05-25 21:38:09 -07:00 @@ -3,7 +3,7 @@ # usbcore-objs := usb.o hub.o hcd.o urb.o message.o \ - config.o file.o buffer.o driverfs.o + config.o file.o buffer.o sysfs.o ifeq ($(CONFIG_PCI),y) usbcore-objs += hcd-pci.o diff -Nru a/drivers/usb/core/config.c b/drivers/usb/core/config.c --- a/drivers/usb/core/config.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/core/config.c 2004-05-25 21:38:09 -07:00 @@ -465,23 +465,24 @@ goto err2; memset(dev->rawdescriptors, 0, length); - buffer = kmalloc(8, GFP_KERNEL); + buffer = kmalloc(USB_DT_CONFIG_SIZE, GFP_KERNEL); if (!buffer) goto err2; desc = (struct usb_config_descriptor *)buffer; for (cfgno = 0; cfgno < ncfg; cfgno++) { - /* We grab the first 8 bytes so we know how long the whole */ - /* configuration is */ + /* We grab just the first descriptor so we know how long + * the whole configuration is */ result = usb_get_descriptor(dev, USB_DT_CONFIG, cfgno, - buffer, 8); + buffer, USB_DT_CONFIG_SIZE); if (result < 0) { dev_err(ddev, "unable to read config index %d " - "descriptor\n", cfgno); + "descriptor/%s\n", cfgno, "start"); goto err; - } else if (result < 8) { + } else if (result < 4) { dev_err(ddev, "config index %d descriptor too short " - "(expected %i, got %i)\n", cfgno, 8, result); + "(expected %i, got %i)\n", cfgno, + USB_DT_CONFIG_SIZE, result); result = -EINVAL; goto err; } @@ -498,7 +499,7 @@ bigbuffer, length); if (result < 0) { dev_err(ddev, "unable to read config index %d " - "descriptor\n", cfgno); + "descriptor/%s\n", cfgno, "all"); kfree(bigbuffer); goto err; } diff -Nru a/drivers/usb/core/driverfs.c b/drivers/usb/core/driverfs.c --- a/drivers/usb/core/driverfs.c 2004-05-25 21:38:09 -07:00 +++ /dev/null Wed Dec 31 16:00:00 196900 @@ -1,229 +0,0 @@ -/* - * drivers/usb/core/driverfs.c - * - * (C) Copyright 2002 David Brownell - * (C) Copyright 2002 Greg Kroah-Hartman - * (C) Copyright 2002 IBM Corp. - * - * All of the driverfs file attributes for usb devices and interfaces. - * - */ - - -#include -#include - -#ifdef CONFIG_USB_DEBUG - #define DEBUG -#else - #undef DEBUG -#endif -#include - -#include "usb.h" - -/* Active configuration fields */ -#define usb_actconfig_show(field, multiplier, format_string) \ -static ssize_t show_##field (struct device *dev, char *buf) \ -{ \ - struct usb_device *udev; \ - \ - udev = to_usb_device (dev); \ - if (udev->actconfig) \ - return sprintf (buf, format_string, \ - udev->actconfig->desc.field * multiplier); \ - else \ - return 0; \ -} \ - -#define usb_actconfig_attr(field, multiplier, format_string) \ -usb_actconfig_show(field, multiplier, format_string) \ -static DEVICE_ATTR(field, S_IRUGO, show_##field, NULL); - -usb_actconfig_attr (bNumInterfaces, 1, "%2d\n") -usb_actconfig_attr (bmAttributes, 1, "%2x\n") -usb_actconfig_attr (bMaxPower, 2, "%3dmA\n") - -/* configuration value is always present, and r/w */ -usb_actconfig_show(bConfigurationValue, 1, "%u\n"); - -static ssize_t -set_bConfigurationValue (struct device *dev, const char *buf, size_t count) -{ - struct usb_device *udev = udev = to_usb_device (dev); - int config, value; - - if (sscanf (buf, "%u", &config) != 1 || config > 255) - return -EINVAL; - down(&udev->serialize); - value = usb_set_configuration (udev, config); - up(&udev->serialize); - return (value < 0) ? value : count; -} - -static DEVICE_ATTR(bConfigurationValue, S_IRUGO | S_IWUSR, - show_bConfigurationValue, set_bConfigurationValue); - -/* String fields */ -#define usb_string_attr(name, field) \ -static ssize_t show_##name(struct device *dev, char *buf) \ -{ \ - struct usb_device *udev; \ - int len; \ - \ - udev = to_usb_device (dev); \ - len = usb_string(udev, udev->descriptor.field, buf, PAGE_SIZE); \ - if (len < 0) \ - return 0; \ - buf[len] = '\n'; \ - buf[len+1] = 0; \ - return len+1; \ -} \ -static DEVICE_ATTR(name, S_IRUGO, show_##name, NULL); - -usb_string_attr(product, iProduct); -usb_string_attr(manufacturer, iManufacturer); -usb_string_attr(serial, iSerialNumber); - -static ssize_t -show_speed (struct device *dev, char *buf) -{ - struct usb_device *udev; - char *speed; - - udev = to_usb_device (dev); - - switch (udev->speed) { - case USB_SPEED_LOW: - speed = "1.5"; - break; - case USB_SPEED_UNKNOWN: - case USB_SPEED_FULL: - speed = "12"; - break; - case USB_SPEED_HIGH: - speed = "480"; - break; - default: - speed = "unknown"; - } - return sprintf (buf, "%s\n", speed); -} -static DEVICE_ATTR(speed, S_IRUGO, show_speed, NULL); - -static ssize_t -show_devnum (struct device *dev, char *buf) -{ - struct usb_device *udev; - - udev = to_usb_device (dev); - return sprintf (buf, "%d\n", udev->devnum); -} -static DEVICE_ATTR(devnum, S_IRUGO, show_devnum, NULL); - -static ssize_t -show_version (struct device *dev, char *buf) -{ - struct usb_device *udev; - - udev = to_usb_device (dev); - return sprintf (buf, "%2x.%02x\n", udev->descriptor.bcdUSB >> 8, - udev->descriptor.bcdUSB & 0xff); -} -static DEVICE_ATTR(version, S_IRUGO, show_version, NULL); - -static ssize_t -show_maxchild (struct device *dev, char *buf) -{ - struct usb_device *udev; - - udev = to_usb_device (dev); - return sprintf (buf, "%d\n", udev->maxchild); -} -static DEVICE_ATTR(maxchild, S_IRUGO, show_maxchild, NULL); - -/* Descriptor fields */ -#define usb_descriptor_attr(field, format_string) \ -static ssize_t \ -show_##field (struct device *dev, char *buf) \ -{ \ - struct usb_device *udev; \ - \ - udev = to_usb_device (dev); \ - return sprintf (buf, format_string, udev->descriptor.field); \ -} \ -static DEVICE_ATTR(field, S_IRUGO, show_##field, NULL); - -usb_descriptor_attr (idVendor, "%04x\n") -usb_descriptor_attr (idProduct, "%04x\n") -usb_descriptor_attr (bcdDevice, "%04x\n") -usb_descriptor_attr (bDeviceClass, "%02x\n") -usb_descriptor_attr (bDeviceSubClass, "%02x\n") -usb_descriptor_attr (bDeviceProtocol, "%02x\n") -usb_descriptor_attr (bNumConfigurations, "%d\n") - - -void usb_create_driverfs_dev_files (struct usb_device *udev) -{ - struct device *dev = &udev->dev; - - /* current configuration's attributes */ - device_create_file (dev, &dev_attr_bNumInterfaces); - device_create_file (dev, &dev_attr_bConfigurationValue); - device_create_file (dev, &dev_attr_bmAttributes); - device_create_file (dev, &dev_attr_bMaxPower); - - /* device attributes */ - device_create_file (dev, &dev_attr_idVendor); - device_create_file (dev, &dev_attr_idProduct); - device_create_file (dev, &dev_attr_bcdDevice); - device_create_file (dev, &dev_attr_bDeviceClass); - device_create_file (dev, &dev_attr_bDeviceSubClass); - device_create_file (dev, &dev_attr_bDeviceProtocol); - device_create_file (dev, &dev_attr_bNumConfigurations); - - /* speed varies depending on how you connect the device */ - device_create_file (dev, &dev_attr_speed); - // FIXME iff there are other speed configs, show how many - - if (udev->descriptor.iManufacturer) - device_create_file (dev, &dev_attr_manufacturer); - if (udev->descriptor.iProduct) - device_create_file (dev, &dev_attr_product); - if (udev->descriptor.iSerialNumber) - device_create_file (dev, &dev_attr_serial); - - device_create_file (dev, &dev_attr_devnum); - device_create_file (dev, &dev_attr_version); - device_create_file (dev, &dev_attr_maxchild); -} - -/* Interface fields */ -#define usb_intf_attr(field, format_string) \ -static ssize_t \ -show_##field (struct device *dev, char *buf) \ -{ \ - struct usb_interface *intf = to_usb_interface (dev); \ - \ - return sprintf (buf, format_string, intf->cur_altsetting->desc.field); \ -} \ -static DEVICE_ATTR(field, S_IRUGO, show_##field, NULL); - -usb_intf_attr (bInterfaceNumber, "%02x\n") -usb_intf_attr (bAlternateSetting, "%2d\n") -usb_intf_attr (bNumEndpoints, "%02x\n") -usb_intf_attr (bInterfaceClass, "%02x\n") -usb_intf_attr (bInterfaceSubClass, "%02x\n") -usb_intf_attr (bInterfaceProtocol, "%02x\n") -usb_intf_attr (iInterface, "%02x\n") - -void usb_create_driverfs_intf_files (struct usb_interface *intf) -{ - device_create_file (&intf->dev, &dev_attr_bInterfaceNumber); - device_create_file (&intf->dev, &dev_attr_bAlternateSetting); - device_create_file (&intf->dev, &dev_attr_bNumEndpoints); - device_create_file (&intf->dev, &dev_attr_bInterfaceClass); - device_create_file (&intf->dev, &dev_attr_bInterfaceSubClass); - device_create_file (&intf->dev, &dev_attr_bInterfaceProtocol); - device_create_file (&intf->dev, &dev_attr_iInterface); -} diff -Nru a/drivers/usb/core/hcd.h b/drivers/usb/core/hcd.h --- a/drivers/usb/core/hcd.h 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/core/hcd.h 2004-05-25 21:38:09 -07:00 @@ -243,13 +243,13 @@ extern struct usb_device *usb_alloc_dev(struct usb_device *parent, struct usb_bus *, unsigned port); extern int usb_new_device(struct usb_device *dev); -extern void usb_choose_address(struct usb_device *dev); extern void usb_disconnect(struct usb_device **); +extern void usb_choose_address(struct usb_device *dev); +extern void usb_release_address(struct usb_device *dev); /* exported to hub driver ONLY to support usb_reset_device () */ extern int usb_get_configuration(struct usb_device *dev); extern void usb_destroy_configuration(struct usb_device *dev); -extern int usb_set_address(struct usb_device *dev); /* use these only before the device's address has been set */ #define usb_snddefctrl(dev) ((PIPE_CONTROL << 30)) diff -Nru a/drivers/usb/core/hub.c b/drivers/usb/core/hub.c --- a/drivers/usb/core/hub.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/core/hub.c 2004-05-25 21:38:09 -07:00 @@ -65,15 +65,15 @@ #endif /* for dev_info, dev_dbg, etc */ -static inline struct device *hubdev (struct usb_device *dev) +static inline struct device *hubdev (struct usb_device *hdev) { - return &dev->actconfig->interface[0]->dev; + return &hdev->actconfig->interface[0]->dev; } /* USB 2.0 spec Section 11.24.4.5 */ -static int get_hub_descriptor(struct usb_device *dev, void *data, int size) +static int get_hub_descriptor(struct usb_device *hdev, void *data, int size) { - return usb_control_msg(dev, usb_rcvctrlpipe(dev, 0), + return usb_control_msg(hdev, usb_rcvctrlpipe(hdev, 0), USB_REQ_GET_DESCRIPTOR, USB_DIR_IN | USB_RT_HUB, USB_DT_HUB << 8, 0, data, size, HZ * USB_CTRL_GET_TIMEOUT); } @@ -81,27 +81,27 @@ /* * USB 2.0 spec Section 11.24.2.1 */ -static int clear_hub_feature(struct usb_device *dev, int feature) +static int clear_hub_feature(struct usb_device *hdev, int feature) { - return usb_control_msg(dev, usb_sndctrlpipe(dev, 0), + return usb_control_msg(hdev, usb_sndctrlpipe(hdev, 0), USB_REQ_CLEAR_FEATURE, USB_RT_HUB, feature, 0, NULL, 0, HZ); } /* * USB 2.0 spec Section 11.24.2.2 */ -static int clear_port_feature(struct usb_device *dev, int port, int feature) +static int clear_port_feature(struct usb_device *hdev, int port, int feature) { - return usb_control_msg(dev, usb_sndctrlpipe(dev, 0), + return usb_control_msg(hdev, usb_sndctrlpipe(hdev, 0), USB_REQ_CLEAR_FEATURE, USB_RT_PORT, feature, port, NULL, 0, HZ); } /* * USB 2.0 spec Section 11.24.2.13 */ -static int set_port_feature(struct usb_device *dev, int port, int feature) +static int set_port_feature(struct usb_device *hdev, int port, int feature) { - return usb_control_msg(dev, usb_sndctrlpipe(dev, 0), + return usb_control_msg(hdev, usb_sndctrlpipe(hdev, 0), USB_REQ_SET_FEATURE, USB_RT_PORT, feature, port, NULL, 0, HZ); } @@ -110,16 +110,15 @@ * for info about using port indicators */ static void set_port_led( - struct usb_device *dev, - struct usb_hub *hub, + struct usb_device *hdev, int port, int selector ) { - int status = set_port_feature(dev, (selector << 8) | port, + int status = set_port_feature(hdev, (selector << 8) | port, USB_PORT_FEAT_INDICATOR); if (status < 0) - dev_dbg (&hub->intf->dev, + dev_dbg (hubdev (hdev), "port %d indicator %s status %d\n", port, ({ char *s; switch (selector) { @@ -137,12 +136,12 @@ static void led_work (void *__hub) { struct usb_hub *hub = __hub; - struct usb_device *dev = interface_to_usbdev (hub->intf); + struct usb_device *hdev = interface_to_usbdev (hub->intf); unsigned i; unsigned changed = 0; int cursor = -1; - if (dev->state != USB_STATE_CONFIGURED) + if (hdev->state != USB_STATE_CONFIGURED) return; for (i = 0; i < hub->descriptor->bNbrPorts; i++) { @@ -189,13 +188,13 @@ } if (selector != HUB_LED_AUTO) changed = 1; - set_port_led(dev, hub, i + 1, selector); + set_port_led(hdev, i + 1, selector); hub->indicator[i] = mode; } if (!changed && blinkenlights) { cursor++; cursor %= hub->descriptor->bNbrPorts; - set_port_led(dev, hub, cursor + 1, HUB_LED_GREEN); + set_port_led(hdev, cursor + 1, HUB_LED_GREEN); hub->indicator[cursor] = INDICATOR_CYCLE; changed++; } @@ -206,10 +205,10 @@ /* * USB 2.0 spec Section 11.24.2.6 */ -static int get_hub_status(struct usb_device *dev, +static int get_hub_status(struct usb_device *hdev, struct usb_hub_status *data) { - return usb_control_msg(dev, usb_rcvctrlpipe(dev, 0), + return usb_control_msg(hdev, usb_rcvctrlpipe(hdev, 0), USB_REQ_GET_STATUS, USB_DIR_IN | USB_RT_HUB, 0, 0, data, sizeof(*data), HZ * USB_CTRL_GET_TIMEOUT); } @@ -217,10 +216,10 @@ /* * USB 2.0 spec Section 11.24.2.7 */ -static int get_port_status(struct usb_device *dev, int port, +static int get_port_status(struct usb_device *hdev, int port, struct usb_port_status *data) { - return usb_control_msg(dev, usb_rcvctrlpipe(dev, 0), + return usb_control_msg(hdev, usb_rcvctrlpipe(hdev, 0), USB_REQ_GET_STATUS, USB_DIR_IN | USB_RT_PORT, 0, port, data, sizeof(*data), HZ * USB_CTRL_GET_TIMEOUT); } @@ -278,9 +277,9 @@ /* USB 2.0 spec Section 11.24.2.3 */ static inline int -hub_clear_tt_buffer (struct usb_device *hub, u16 devinfo, u16 tt) +hub_clear_tt_buffer (struct usb_device *hdev, u16 devinfo, u16 tt) { - return usb_control_msg (hub, usb_rcvctrlpipe (hub, 0), + return usb_control_msg (hdev, usb_rcvctrlpipe (hdev, 0), HUB_CLEAR_TT_BUFFER, USB_RT_PORT, devinfo, tt, 0, 0, HZ); } @@ -300,7 +299,7 @@ while (!list_empty (&hub->tt.clear_list)) { struct list_head *temp; struct usb_tt_clear *clear; - struct usb_device *dev; + struct usb_device *hdev; int status; temp = hub->tt.clear_list.next; @@ -309,12 +308,13 @@ /* drop lock so HCD can concurrently report other TT errors */ spin_unlock_irqrestore (&hub->tt.lock, flags); - dev = interface_to_usbdev (hub->intf); - status = hub_clear_tt_buffer (dev, clear->devinfo, clear->tt); + hdev = interface_to_usbdev (hub->intf); + status = hub_clear_tt_buffer (hdev, clear->devinfo, clear->tt); spin_lock_irqsave (&hub->tt.lock, flags); if (status) - dev_err (&dev->dev, "clear tt %d (%04x) error %d\n", + dev_err (&hdev->dev, + "clear tt %d (%04x) error %d\n", clear->tt, clear->devinfo, status); kfree (clear); } @@ -334,9 +334,9 @@ * It may not be possible for that hub to handle additional full (or low) * speed transactions until that state is fully cleared out. */ -void usb_hub_tt_clear_buffer (struct usb_device *dev, int pipe) +void usb_hub_tt_clear_buffer (struct usb_device *udev, int pipe) { - struct usb_tt *tt = dev->tt; + struct usb_tt *tt = udev->tt; unsigned long flags; struct usb_tt_clear *clear; @@ -345,15 +345,15 @@ * there can be many TTs per hub). even if they're uncommon. */ if ((clear = kmalloc (sizeof *clear, SLAB_ATOMIC)) == 0) { - dev_err (&dev->dev, "can't save CLEAR_TT_BUFFER state\n"); + dev_err (&udev->dev, "can't save CLEAR_TT_BUFFER state\n"); /* FIXME recover somehow ... RESET_TT? */ return; } /* info that CLEAR_TT_BUFFER needs */ - clear->tt = tt->multi ? dev->ttport : 1; + clear->tt = tt->multi ? udev->ttport : 1; clear->devinfo = usb_pipeendpoint (pipe); - clear->devinfo |= dev->devnum << 4; + clear->devinfo |= udev->devnum << 4; clear->devinfo |= usb_pipecontrol (pipe) ? (USB_ENDPOINT_XFER_CONTROL << 11) : (USB_ENDPOINT_XFER_BULK << 11); @@ -369,15 +369,15 @@ static void hub_power_on(struct usb_hub *hub) { - struct usb_device *dev; + struct usb_device *hdev; int i; /* if hub supports power switching, enable power on each port */ if ((hub->descriptor->wHubCharacteristics & HUB_CHAR_LPSM) < 2) { dev_dbg(&hub->intf->dev, "enabling power on all ports\n"); - dev = interface_to_usbdev(hub->intf); + hdev = interface_to_usbdev(hub->intf); for (i = 0; i < hub->descriptor->bNbrPorts; i++) - set_port_feature(dev, i + 1, USB_PORT_FEAT_POWER); + set_port_feature(hdev, i + 1, USB_PORT_FEAT_POWER); } /* Wait for power to be enabled */ @@ -387,12 +387,12 @@ static int hub_hub_status(struct usb_hub *hub, u16 *status, u16 *change) { - struct usb_device *dev = interface_to_usbdev (hub->intf); + struct usb_device *hdev = interface_to_usbdev (hub->intf); int ret; - ret = get_hub_status(dev, &hub->status->hub); + ret = get_hub_status(hdev, &hub->status->hub); if (ret < 0) - dev_err (hubdev (dev), + dev_err (&hub->intf->dev, "%s failed (err = %d)\n", __FUNCTION__, ret); else { *status = le16_to_cpu(hub->status->hub.wHubStatus); @@ -405,14 +405,14 @@ static int hub_configure(struct usb_hub *hub, struct usb_endpoint_descriptor *endpoint) { - struct usb_device *dev = interface_to_usbdev (hub->intf); - struct device *hub_dev; + struct usb_device *hdev = interface_to_usbdev (hub->intf); + struct device *hub_dev = &hub->intf->dev; u16 hubstatus, hubchange; unsigned int pipe; int maxp, ret; char *message; - hub->buffer = usb_buffer_alloc(dev, sizeof(*hub->buffer), GFP_KERNEL, + hub->buffer = usb_buffer_alloc(hdev, sizeof(*hub->buffer), GFP_KERNEL, &hub->buffer_dma); if (!hub->buffer) { message = "can't allocate hub irq buffer"; @@ -438,7 +438,7 @@ * hub->descriptor can handle USB_MAXCHILDREN ports, * but the hub can/will return fewer bytes here. */ - ret = get_hub_descriptor(dev, hub->descriptor, + ret = get_hub_descriptor(hdev, hub->descriptor, sizeof(*hub->descriptor)); if (ret < 0) { message = "can't read hub descriptor"; @@ -449,10 +449,9 @@ goto fail; } - hub_dev = hubdev(dev); - dev->maxchild = hub->descriptor->bNbrPorts; - dev_info (hub_dev, "%d port%s detected\n", dev->maxchild, - (dev->maxchild == 1) ? "" : "s"); + hdev->maxchild = hub->descriptor->bNbrPorts; + dev_info (hub_dev, "%d port%s detected\n", hdev->maxchild, + (hdev->maxchild == 1) ? "" : "s"); le16_to_cpus(&hub->descriptor->wHubCharacteristics); @@ -460,11 +459,11 @@ int i; char portstr [USB_MAXCHILDREN + 1]; - for (i = 0; i < dev->maxchild; i++) + for (i = 0; i < hdev->maxchild; i++) portstr[i] = hub->descriptor->DeviceRemovable [((i + 1) / 8)] & (1 << ((i + 1) % 8)) ? 'F' : 'R'; - portstr[dev->maxchild] = 0; + portstr[hdev->maxchild] = 0; dev_dbg(hub_dev, "compound device; port removable status: %s\n", portstr); } else dev_dbg(hub_dev, "standalone hub\n"); @@ -498,32 +497,32 @@ spin_lock_init (&hub->tt.lock); INIT_LIST_HEAD (&hub->tt.clear_list); INIT_WORK (&hub->tt.kevent, hub_tt_kevent, hub); - switch (dev->descriptor.bDeviceProtocol) { + switch (hdev->descriptor.bDeviceProtocol) { case 0: break; case 1: dev_dbg(hub_dev, "Single TT\n"); - hub->tt.hub = dev; + hub->tt.hub = hdev; break; case 2: - ret = usb_set_interface(dev, 0, 1); + ret = usb_set_interface(hdev, 0, 1); if (ret == 0) { dev_dbg(hub_dev, "TT per port\n"); hub->tt.multi = 1; } else dev_err(hub_dev, "Using single TT (err %d)\n", ret); - hub->tt.hub = dev; + hub->tt.hub = hdev; break; default: dev_dbg(hub_dev, "Unrecognized hub protocol %d\n", - dev->descriptor.bDeviceProtocol); + hdev->descriptor.bDeviceProtocol); break; } switch (hub->descriptor->wHubCharacteristics & HUB_CHAR_TTTT) { case 0x00: - if (dev->descriptor.bDeviceProtocol != 0) + if (hdev->descriptor.bDeviceProtocol != 0) dev_dbg(hub_dev, "TT requires at most 8 FS bit times\n"); break; case 0x20: @@ -549,9 +548,9 @@ /* power budgeting mostly matters with bus-powered hubs, * and battery-powered root hubs (may provide just 8 mA). */ - ret = usb_get_status(dev, USB_RECIP_DEVICE, 0, &hubstatus); + ret = usb_get_status(hdev, USB_RECIP_DEVICE, 0, &hubstatus); if (ret < 0) { - message = "can't get hubdev status"; + message = "can't get hub status"; goto fail; } cpu_to_le16s(&hubstatus); @@ -572,7 +571,7 @@ } /* local power status reports aren't always correct */ - if (dev->actconfig->desc.bmAttributes & USB_CONFIG_ATT_SELFPOWER) + if (hdev->actconfig->desc.bmAttributes & USB_CONFIG_ATT_SELFPOWER) dev_dbg(hub_dev, "local power source is %s\n", (hubstatus & HUB_STATUS_LOCAL_POWER) ? "lost (inactive)" : "good"); @@ -582,8 +581,8 @@ (hubstatus & HUB_STATUS_OVERCURRENT) ? "" : "no "); /* Start the interrupt endpoint */ - pipe = usb_rcvintpipe(dev, endpoint->bEndpointAddress); - maxp = usb_maxpacket(dev, pipe, usb_pipeout(pipe)); + pipe = usb_rcvintpipe(hdev, endpoint->bEndpointAddress); + maxp = usb_maxpacket(hdev, pipe, usb_pipeout(pipe)); if (maxp > sizeof(*hub->buffer)) maxp = sizeof(*hub->buffer); @@ -595,7 +594,7 @@ goto fail; } - usb_fill_int_urb(hub->urb, dev, pipe, *hub->buffer, maxp, hub_irq, + usb_fill_int_urb(hub->urb, hdev, pipe, *hub->buffer, maxp, hub_irq, hub, endpoint->bInterval); hub->urb->transfer_dma = hub->buffer_dma; hub->urb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP; @@ -611,7 +610,7 @@ /* maybe start cycling the hub leds */ if (hub->has_indicators && blinkenlights) { - set_port_led(dev, hub, 1, HUB_LED_GREEN); + set_port_led(hdev, 1, HUB_LED_GREEN); hub->indicator [0] = INDICATOR_CYCLE; schedule_delayed_work(&hub->leds, LED_CYCLE_PERIOD); } @@ -621,7 +620,7 @@ return 0; fail: - dev_err (&hub->intf->dev, "config failed, %s (err %d)\n", + dev_err (hub_dev, "config failed, %s (err %d)\n", message, ret); /* hub_disconnect() frees urb and descriptor */ return ret; @@ -693,19 +692,21 @@ { struct usb_host_interface *desc; struct usb_endpoint_descriptor *endpoint; - struct usb_device *dev; + struct usb_device *hdev; struct usb_hub *hub; + struct device *hub_dev; unsigned long flags; desc = intf->cur_altsetting; - dev = interface_to_usbdev(intf); + hdev = interface_to_usbdev(intf); + hub_dev = &intf->dev; /* Some hubs have a subclass of 1, which AFAICT according to the */ /* specs is not defined, but it works */ if ((desc->desc.bInterfaceSubClass != 0) && (desc->desc.bInterfaceSubClass != 1)) { descriptor_error: - dev_err (&intf->dev, "bad descriptor, ignoring hub\n"); + dev_err (hub_dev, "bad descriptor, ignoring hub\n"); return -EIO; } @@ -729,11 +730,11 @@ } /* We found a hub */ - dev_info (hubdev (dev), "USB hub found\n"); + dev_info (hub_dev, "USB hub found\n"); hub = kmalloc(sizeof(*hub), GFP_KERNEL); if (!hub) { - dev_dbg (hubdev(dev), "couldn't kmalloc hub struct\n"); + dev_dbg (hub_dev, "couldn't kmalloc hub struct\n"); return -ENOMEM; } @@ -752,7 +753,7 @@ usb_set_intfdata (intf, hub); - if (dev->speed == USB_SPEED_HIGH) + if (hdev->speed == USB_SPEED_HIGH) highspeed_hubs++; if (hub_configure(hub, endpoint) >= 0) @@ -765,7 +766,7 @@ static int hub_ioctl(struct usb_interface *intf, unsigned int code, void *user_data) { - struct usb_device *hub = interface_to_usbdev (intf); + struct usb_device *hdev = interface_to_usbdev (intf); /* assert ifno == 0 (part of hub spec) */ switch (code) { @@ -775,16 +776,16 @@ int i; spin_lock_irqsave(&hub_event_lock, flags); - if (hub->devnum <= 0) + if (hdev->devnum <= 0) info->nports = 0; else { - info->nports = hub->maxchild; + info->nports = hdev->maxchild; for (i = 0; i < info->nports; i++) { - if (hub->children[i] == NULL) + if (hdev->children[i] == NULL) info->port[i] = 0; else info->port[i] = - hub->children[i]->devnum; + hdev->children[i]->devnum; } } spin_unlock_irqrestore(&hub_event_lock, flags); @@ -799,13 +800,13 @@ static int hub_reset(struct usb_hub *hub) { - struct usb_device *dev = interface_to_usbdev(hub->intf); + struct usb_device *hdev = interface_to_usbdev(hub->intf); int i; /* Disconnect any attached devices */ for (i = 0; i < hub->descriptor->bNbrPorts; i++) { - if (dev->children[i]) - usb_disconnect(&dev->children[i]); + if (hdev->children[i]) + usb_disconnect(&hdev->children[i]); } /* Attempt to reset the hub */ @@ -814,10 +815,10 @@ else return -1; - if (usb_reset_device(dev)) + if (usb_reset_device(hdev)) return -1; - hub->urb->dev = dev; + hub->urb->dev = hdev; if (usb_submit_urb(hub->urb, GFP_KERNEL)) return -1; @@ -826,36 +827,36 @@ return 0; } -static void hub_start_disconnect(struct usb_device *dev) +static void hub_start_disconnect(struct usb_device *hdev) { - struct usb_device *parent = dev->parent; + struct usb_device *parent = hdev->parent; int i; /* Find the device pointer to disconnect */ if (parent) { for (i = 0; i < parent->maxchild; i++) { - if (parent->children[i] == dev) { + if (parent->children[i] == hdev) { usb_disconnect(&parent->children[i]); return; } } } - dev_err(&dev->dev, "cannot disconnect hub!\n"); + dev_err(&hdev->dev, "cannot disconnect hub!\n"); } -static int hub_port_status(struct usb_device *dev, int port, +static int hub_port_status(struct usb_device *hdev, int port, u16 *status, u16 *change) { - struct usb_hub *hub = usb_get_intfdata(dev->actconfig->interface[0]); + struct usb_hub *hub = usb_get_intfdata(hdev->actconfig->interface[0]); int ret; if (!hub) return -ENODEV; - ret = get_port_status(dev, port + 1, &hub->status->port); + ret = get_port_status(hdev, port + 1, &hub->status->port); if (ret < 0) - dev_err (hubdev (dev), + dev_err (&hub->intf->dev, "%s failed (err = %d)\n", __FUNCTION__, ret); else { *status = le16_to_cpu(hub->status->port.wPortStatus); @@ -876,8 +877,8 @@ #define HUB_RESET_TIMEOUT 500 /* return: -1 on error, 0 on success, 1 on disconnect. */ -static int hub_port_wait_reset(struct usb_device *hub, int port, - struct usb_device *dev, unsigned int delay) +static int hub_port_wait_reset(struct usb_device *hdev, int port, + struct usb_device *udev, unsigned int delay) { int delay_time, ret; u16 portstatus; @@ -890,7 +891,7 @@ msleep(delay); /* read and decode port status */ - ret = hub_port_status(hub, port, &portstatus, &portchange); + ret = hub_port_status(hdev, port, &portstatus, &portchange); if (ret < 0) { return -1; } @@ -907,11 +908,11 @@ if (!(portstatus & USB_PORT_STAT_RESET) && (portstatus & USB_PORT_STAT_ENABLE)) { if (portstatus & USB_PORT_STAT_HIGH_SPEED) - dev->speed = USB_SPEED_HIGH; + udev->speed = USB_SPEED_HIGH; else if (portstatus & USB_PORT_STAT_LOW_SPEED) - dev->speed = USB_SPEED_LOW; + udev->speed = USB_SPEED_LOW; else - dev->speed = USB_SPEED_FULL; + udev->speed = USB_SPEED_FULL; return 0; } @@ -919,7 +920,7 @@ if (delay_time >= 2 * HUB_SHORT_RESET_TIME) delay = HUB_LONG_RESET_TIME; - dev_dbg (hubdev (hub), + dev_dbg (hubdev (hdev), "port %d not reset yet, waiting %dms\n", port + 1, delay); } @@ -928,46 +929,47 @@ } /* return: -1 on error, 0 on success, 1 on disconnect. */ -static int hub_port_reset(struct usb_device *hub, int port, - struct usb_device *dev, unsigned int delay) +static int hub_port_reset(struct usb_device *hdev, int port, + struct usb_device *udev, unsigned int delay) { int i, status; + struct device *hub_dev = hubdev (hdev); /* Reset the port */ for (i = 0; i < PORT_RESET_TRIES; i++) { - set_port_feature(hub, port + 1, USB_PORT_FEAT_RESET); + set_port_feature(hdev, port + 1, USB_PORT_FEAT_RESET); /* return on disconnect or reset */ - status = hub_port_wait_reset(hub, port, dev, delay); + status = hub_port_wait_reset(hdev, port, udev, delay); if (status != -1) { - clear_port_feature(hub, + clear_port_feature(hdev, port + 1, USB_PORT_FEAT_C_RESET); - dev->state = status + udev->state = status ? USB_STATE_NOTATTACHED : USB_STATE_DEFAULT; return status; } - dev_dbg (hubdev (hub), + dev_dbg (hub_dev, "port %d not enabled, trying reset again...\n", port + 1); delay = HUB_LONG_RESET_TIME; } - dev_err (hubdev (hub), + dev_err (hub_dev, "Cannot enable port %i. Maybe the USB cable is bad?\n", port + 1); return -1; } -static int hub_port_disable(struct usb_device *hub, int port) +static int hub_port_disable(struct usb_device *hdev, int port) { int ret; - ret = clear_port_feature(hub, port + 1, USB_PORT_FEAT_ENABLE); + ret = clear_port_feature(hdev, port + 1, USB_PORT_FEAT_ENABLE); if (ret) - dev_err(hubdev(hub), "cannot disable port %d (err = %d)\n", + dev_err(hubdev(hdev), "cannot disable port %d (err = %d)\n", port + 1, ret); return ret; @@ -992,7 +994,7 @@ #define HUB_DEBOUNCE_STABLE 4 /* return: -1 on error, 0 on success, 1 on disconnect. */ -static int hub_port_debounce(struct usb_device *hub, int port) +static int hub_port_debounce(struct usb_device *hdev, int port) { int ret; int delay_time, stable_count; @@ -1004,7 +1006,7 @@ for (delay_time = 0; delay_time < HUB_DEBOUNCE_TIMEOUT; delay_time += HUB_DEBOUNCE_STEP) { msleep(HUB_DEBOUNCE_STEP); - ret = hub_port_status(hub, port, &portstatus, &portchange); + ret = hub_port_status(hdev, port, &portstatus, &portchange); if (ret < 0) return -1; @@ -1019,17 +1021,34 @@ connection = portstatus & USB_PORT_STAT_CONNECTION; if ((portchange & USB_PORT_STAT_C_CONNECTION)) { - clear_port_feature(hub, port+1, USB_PORT_FEAT_C_CONNECTION); + clear_port_feature(hdev, port+1, USB_PORT_FEAT_C_CONNECTION); } } - dev_dbg (hubdev (hub), + dev_dbg (hubdev (hdev), "debounce: port %d: delay %dms stable %d status 0x%x\n", port + 1, delay_time, stable_count, portstatus); return ((portstatus&USB_PORT_STAT_CONNECTION)) ? 0 : 1; } +static int hub_set_address(struct usb_device *udev) +{ + int retval; + + if (udev->devnum == 0) + return -EINVAL; + if (udev->state != USB_STATE_DEFAULT && + udev->state != USB_STATE_ADDRESS) + return -EINVAL; + retval = usb_control_msg(udev, usb_snddefctrl(udev), + USB_REQ_SET_ADDRESS, 0, udev->devnum, 0, + NULL, 0, HZ * USB_CTRL_SET_TIMEOUT); + if (retval == 0) + udev->state = USB_STATE_ADDRESS; + return retval; +} + /* reset device, (re)assign address, get device descriptor. * device connection is stable, no more debouncing needed. * returns device in USB_STATE_ADDRESS, except on error. @@ -1039,18 +1058,18 @@ * config changes and disconnect processing. */ static int -hub_port_init (struct usb_device *hub, struct usb_device *dev, int port) +hub_port_init (struct usb_device *hdev, struct usb_device *udev, int port) { static DECLARE_MUTEX(usb_address0_sem); int i, j, retval = -ENODEV; unsigned delay = HUB_SHORT_RESET_TIME; - enum usb_device_speed oldspeed = dev->speed; + enum usb_device_speed oldspeed = udev->speed; /* root hub ports have a slightly longer reset period * (from USB 2.0 spec, section 7.1.7.5) */ - if (!hub->parent) + if (!hdev->parent) delay = HUB_ROOT_RESET_TIME; /* Some low speed devices have problems with the quick delay, so */ @@ -1061,7 +1080,7 @@ down(&usb_address0_sem); /* Reset the device; full speed may morph to high speed */ - switch (hub_port_reset(hub, port, dev, delay)) { + switch (hub_port_reset(hdev, port, udev, delay)) { case 0: /* success, speed is known */ break; case 1: /* disconnect, give to companion */ @@ -1070,15 +1089,15 @@ default: /* error */ goto fail; } - if (oldspeed != USB_SPEED_UNKNOWN && oldspeed != dev->speed) { - dev_dbg(&dev->dev, "device reset changed speed!\n"); + if (oldspeed != USB_SPEED_UNKNOWN && oldspeed != udev->speed) { + dev_dbg(&udev->dev, "device reset changed speed!\n"); goto fail; } /* USB 2.0 section 5.5.3 talks about ep0 maxpacket ... * it's fixed size except for full speed devices. */ - switch (dev->speed) { + switch (udev->speed) { case USB_SPEED_HIGH: /* fixed at 64 */ i = 64; break; @@ -1094,43 +1113,43 @@ default: goto fail; } - dev->epmaxpacketin [0] = i; - dev->epmaxpacketout[0] = i; + udev->epmaxpacketin [0] = i; + udev->epmaxpacketout[0] = i; /* set the address */ - if (dev->devnum <= 0) { - usb_choose_address(dev); - if (dev->devnum <= 0) + if (udev->devnum <= 0) { + usb_choose_address(udev); + if (udev->devnum <= 0) goto fail; /* Set up TT records, if needed */ - if (hub->tt) { - dev->tt = hub->tt; - dev->ttport = hub->ttport; - } else if (dev->speed != USB_SPEED_HIGH - && hub->speed == USB_SPEED_HIGH) { - struct usb_hub *hubstate; + if (hdev->tt) { + udev->tt = hdev->tt; + udev->ttport = hdev->ttport; + } else if (udev->speed != USB_SPEED_HIGH + && hdev->speed == USB_SPEED_HIGH) { + struct usb_hub *hub; - hubstate = usb_get_intfdata (hub->actconfig + hub = usb_get_intfdata (hdev->actconfig ->interface[0]); - dev->tt = &hubstate->tt; - dev->ttport = port + 1; + udev->tt = &hub->tt; + udev->ttport = port + 1; } /* force the right log message (below) at low speed */ oldspeed = USB_SPEED_UNKNOWN; } - dev_info (&dev->dev, + dev_info (&udev->dev, "%s %s speed USB device using address %d\n", (oldspeed == USB_SPEED_UNKNOWN) ? "new" : "reset", - ({ char *speed; switch (dev->speed) { + ({ char *speed; switch (udev->speed) { case USB_SPEED_LOW: speed = "low"; break; case USB_SPEED_FULL: speed = "full"; break; case USB_SPEED_HIGH: speed = "high"; break; default: speed = "?"; break; }; speed;}), - dev->devnum); + udev->devnum); /* Why interleave GET_DESCRIPTOR and SET_ADDRESS this way? * Because device hardware and firmware is sometimes buggy in @@ -1143,20 +1162,19 @@ */ for (i = 0; i < GET_DESCRIPTOR_TRIES; ++i) { for (j = 0; j < SET_ADDRESS_TRIES; ++j) { - retval = usb_set_address(dev); + retval = hub_set_address(udev); if (retval >= 0) break; msleep(200); } if (retval < 0) { - dev_err(&dev->dev, + dev_err(&udev->dev, "device not accepting address %d, error %d\n", - dev->devnum, retval); + udev->devnum, retval); fail: - hub_port_disable(hub, port); - clear_bit(dev->devnum, dev->bus->devmap.devicemap); - dev->devnum = -1; - usb_put_dev(dev); + hub_port_disable(hdev, port); + usb_release_address(udev); + usb_put_dev(udev); up(&usb_address0_sem); return retval; } @@ -1166,31 +1184,31 @@ * - read ep0 maxpacket even for high and low speed, */ msleep(10); - retval = usb_get_device_descriptor(dev, 8); + retval = usb_get_device_descriptor(udev, 8); if (retval >= 8) break; msleep(100); } if (retval != 8) { - dev_err(&dev->dev, "device descriptor read/%s, error %d\n", + dev_err(&udev->dev, "device descriptor read/%s, error %d\n", "8", retval); if (retval >= 0) retval = -EMSGSIZE; goto fail; } - if (dev->speed == USB_SPEED_FULL - && (dev->epmaxpacketin [0] - != dev->descriptor.bMaxPacketSize0)) { - usb_disable_endpoint(dev, 0); - usb_endpoint_running(dev, 0, 1); - usb_endpoint_running(dev, 0, 0); - dev->epmaxpacketin [0] = dev->descriptor.bMaxPacketSize0; - dev->epmaxpacketout[0] = dev->descriptor.bMaxPacketSize0; + if (udev->speed == USB_SPEED_FULL + && (udev->epmaxpacketin [0] + != udev->descriptor.bMaxPacketSize0)) { + usb_disable_endpoint(udev, 0); + usb_endpoint_running(udev, 0, 1); + usb_endpoint_running(udev, 0, 0); + udev->epmaxpacketin [0] = udev->descriptor.bMaxPacketSize0; + udev->epmaxpacketout[0] = udev->descriptor.bMaxPacketSize0; } - retval = usb_get_device_descriptor(dev, USB_DT_DEVICE_SIZE); - if (retval < (signed)sizeof(dev->descriptor)) { - dev_err(&dev->dev, "device descriptor read/%s, error %d\n", + retval = usb_get_device_descriptor(udev, USB_DT_DEVICE_SIZE); + if (retval < (signed)sizeof(udev->descriptor)) { + dev_err(&udev->dev, "device descriptor read/%s, error %d\n", "all", retval); if (retval >= 0) retval = -ENOMSG; @@ -1198,14 +1216,14 @@ } /* now dev is visible to other tasks */ - hub->children[port] = dev; + hdev->children[port] = udev; up(&usb_address0_sem); return 0; } static void -check_highspeed (struct usb_hub *hub, struct usb_device *dev, int port) +check_highspeed (struct usb_hub *hub, struct usb_device *udev, int port) { struct usb_qualifier_descriptor *qual; int status; @@ -1214,10 +1232,10 @@ if (qual == 0) return; - status = usb_get_descriptor (dev, USB_DT_DEVICE_QUALIFIER, 0, + status = usb_get_descriptor (udev, USB_DT_DEVICE_QUALIFIER, 0, qual, sizeof *qual); if (status == sizeof *qual) { - dev_info(&dev->dev, "not running at top speed; " + dev_info(&udev->dev, "not running at top speed; " "connect to a high speed hub\n"); /* hub LEDs are probably harder to miss than syslog */ if (hub->has_indicators) { @@ -1229,31 +1247,31 @@ } static unsigned -hub_power_remaining (struct usb_hub *hubstate, struct usb_device *hub) +hub_power_remaining (struct usb_hub *hub, struct usb_device *hdev) { int remaining; unsigned i; - remaining = hubstate->power_budget; + remaining = hub->power_budget; if (!remaining) /* self-powered */ return 0; - for (i = 0; i < hub->maxchild; i++) { - struct usb_device *dev = hub->children[i]; + for (i = 0; i < hdev->maxchild; i++) { + struct usb_device *udev = hdev->children[i]; int delta; - if (!dev) + if (!udev) continue; - if (dev->actconfig) - delta = dev->actconfig->desc.bMaxPower; + if (udev->actconfig) + delta = udev->actconfig->desc.bMaxPower; else delta = 50; - // dev_dbg(&dev->dev, "budgeted %dmA\n", 2 * delta); + // dev_dbg(&udev->dev, "budgeted %dmA\n", 2 * delta); remaining -= delta; } if (remaining < 0) { - dev_warn(&hubstate->intf->dev, + dev_warn(&hub->intf->dev, "%dmA over power budget!\n", -2 * remaining); remaining = 0; @@ -1261,72 +1279,73 @@ return remaining; } -static void hub_port_connect_change(struct usb_hub *hubstate, int port, +static void hub_port_connect_change(struct usb_hub *hub, int port, u16 portstatus, u16 portchange) { - struct usb_device *hub = interface_to_usbdev(hubstate->intf); + struct usb_device *hdev = interface_to_usbdev(hub->intf); + struct device *hub_dev = &hub->intf->dev; int status, i; - dev_dbg (&hubstate->intf->dev, + dev_dbg (hub_dev, "port %d, status %04x, change %04x, %s\n", port + 1, portstatus, portchange, portspeed (portstatus)); /* Clear the connection change status */ - clear_port_feature(hub, port + 1, USB_PORT_FEAT_C_CONNECTION); + clear_port_feature(hdev, port + 1, USB_PORT_FEAT_C_CONNECTION); - if (hubstate->has_indicators) { - set_port_led(hub, hubstate, port + 1, HUB_LED_AUTO); - hubstate->indicator[port] = INDICATOR_AUTO; + if (hub->has_indicators) { + set_port_led(hdev, port + 1, HUB_LED_AUTO); + hub->indicator[port] = INDICATOR_AUTO; } /* Disconnect any existing devices under this port */ - if (hub->children[port]) - usb_disconnect(&hub->children[port]); + if (hdev->children[port]) + usb_disconnect(&hdev->children[port]); /* Return now if nothing is connected */ if (!(portstatus & USB_PORT_STAT_CONNECTION)) { /* maybe switch power back on (e.g. root hub was reset) */ - if ((hubstate->descriptor->wHubCharacteristics + if ((hub->descriptor->wHubCharacteristics & HUB_CHAR_LPSM) < 2 && !(portstatus & (1 << USB_PORT_FEAT_POWER))) - set_port_feature(hub, port + 1, USB_PORT_FEAT_POWER); + set_port_feature(hdev, port + 1, USB_PORT_FEAT_POWER); if (portstatus & USB_PORT_STAT_ENABLE) goto done; return; } - if (hub_port_debounce(hub, port)) { - dev_err (&hubstate->intf->dev, + if (hub_port_debounce(hdev, port)) { + dev_err (hub_dev, "connect-debounce failed, port %d disabled\n", port+1); goto done; } for (i = 0; i < SET_CONFIG_TRIES; i++) { - struct usb_device *dev; + struct usb_device *udev; /* reallocate for each attempt, since references * to the previous one can escape in various ways */ - dev = usb_alloc_dev(hub, hub->bus, port); - if (!dev) { - dev_err (&hubstate->intf->dev, + udev = usb_alloc_dev(hdev, hdev->bus, port); + if (!udev) { + dev_err (hub_dev, "couldn't allocate port %d usb_device\n", port+1); goto done; } - dev->state = USB_STATE_POWERED; + udev->state = USB_STATE_POWERED; /* hub can tell if it's lowspeed already: D- pullup (not D+) */ if (portstatus & USB_PORT_STAT_LOW_SPEED) - dev->speed = USB_SPEED_LOW; + udev->speed = USB_SPEED_LOW; else - dev->speed = USB_SPEED_UNKNOWN; + udev->speed = USB_SPEED_UNKNOWN; /* reset, set address, get descriptor, add to hub's children */ - down (&dev->serialize); - status = hub_port_init(hub, dev, port); + down (&udev->serialize); + status = hub_port_init(hdev, udev, port); if (status == -EBUSY) break; if (status < 0) @@ -1338,50 +1357,50 @@ * (without reading syslog), even without per-port LEDs * on the parent. */ - if (dev->descriptor.bDeviceClass == USB_CLASS_HUB - && hubstate->power_budget) { + if (udev->descriptor.bDeviceClass == USB_CLASS_HUB + && hub->power_budget) { u16 devstat; - status = usb_get_status(dev, USB_RECIP_DEVICE, 0, + status = usb_get_status(udev, USB_RECIP_DEVICE, 0, &devstat); if (status < 0) { - dev_dbg(&dev->dev, "get status %d ?\n", status); + dev_dbg(&udev->dev, "get status %d ?\n", status); continue; } cpu_to_le16s(&devstat); if ((devstat & (1 << USB_DEVICE_SELF_POWERED)) == 0) { - dev_err(&dev->dev, + dev_err(&udev->dev, "can't connect bus-powered hub " "to this port\n"); - if (hubstate->has_indicators) { - hubstate->indicator[port] = + if (hub->has_indicators) { + hub->indicator[port] = INDICATOR_AMBER_BLINK; - schedule_work (&hubstate->leds); + schedule_work (&hub->leds); } - hub->children[port] = NULL; - usb_put_dev(dev); - hub_port_disable(hub, port); + hdev->children[port] = NULL; + usb_put_dev(udev); + hub_port_disable(hdev, port); return; } } /* check for devices running slower than they could */ - if (dev->descriptor.bcdUSB >= 0x0200 - && dev->speed == USB_SPEED_FULL + if (udev->descriptor.bcdUSB >= 0x0200 + && udev->speed == USB_SPEED_FULL && highspeed_hubs != 0) - check_highspeed (hubstate, dev, port); + check_highspeed (hub, udev, port); /* Run it through the hoops (find a driver, etc) */ - status = usb_new_device(dev); + status = usb_new_device(udev); if (status != 0) { - hub->children[port] = NULL; + hdev->children[port] = NULL; continue; } - up (&dev->serialize); + up (&udev->serialize); - status = hub_power_remaining(hubstate, hub); + status = hub_power_remaining(hub, hdev); if (status) - dev_dbg(&hubstate->intf->dev, + dev_dbg(hub_dev, "%dmA power budget left\n", 2 * status); @@ -1389,15 +1408,16 @@ } done: - hub_port_disable(hub, port); + hub_port_disable(hdev, port); } static void hub_events(void) { unsigned long flags; struct list_head *tmp; - struct usb_device *dev; + struct usb_device *hdev; struct usb_hub *hub; + struct device *hub_dev; u16 hubstatus; u16 hubchange; u16 portstatus; @@ -1420,7 +1440,8 @@ tmp = hub_event_list.next; hub = list_entry(tmp, struct usb_hub, event_list); - dev = interface_to_usbdev(hub->intf); + hdev = interface_to_usbdev(hub->intf); + hub_dev = &hub->intf->dev; list_del_init(tmp); @@ -1430,14 +1451,14 @@ spin_unlock_irqrestore(&hub_event_lock, flags); if (hub->error) { - dev_dbg (&hub->intf->dev, "resetting for error %d\n", + dev_dbg (hub_dev, "resetting for error %d\n", hub->error); if (hub_reset(hub)) { - dev_dbg (&hub->intf->dev, + dev_dbg (hub_dev, "can't reset; disconnecting\n"); up(&hub->khubd_sem); - hub_start_disconnect(dev); + hub_start_disconnect(hdev); continue; } @@ -1446,7 +1467,7 @@ } for (i = 0; i < hub->descriptor->bNbrPorts; i++) { - ret = hub_port_status(dev, i, &portstatus, &portchange); + ret = hub_port_status(hdev, i, &portstatus, &portchange); if (ret < 0) { continue; } @@ -1454,10 +1475,10 @@ if (portchange & USB_PORT_STAT_C_CONNECTION) { hub_port_connect_change(hub, i, portstatus, portchange); } else if (portchange & USB_PORT_STAT_C_ENABLE) { - dev_dbg (hubdev (dev), + dev_dbg (hub_dev, "port %d enable change, status %08x\n", i + 1, portstatus); - clear_port_feature(dev, + clear_port_feature(hdev, i + 1, USB_PORT_FEAT_C_ENABLE); /* @@ -1468,8 +1489,8 @@ */ if (!(portstatus & USB_PORT_STAT_ENABLE) && (portstatus & USB_PORT_STAT_CONNECTION) - && (dev->children[i])) { - dev_err (&hub->intf->dev, + && (hdev->children[i])) { + dev_err (hub_dev, "port %i " "disabled by hub (EMI?), " "re-enabling...", @@ -1480,43 +1501,43 @@ } if (portchange & USB_PORT_STAT_C_SUSPEND) { - dev_dbg (&hub->intf->dev, + dev_dbg (hub_dev, "suspend change on port %d\n", i + 1); - clear_port_feature(dev, + clear_port_feature(hdev, i + 1, USB_PORT_FEAT_C_SUSPEND); } if (portchange & USB_PORT_STAT_C_OVERCURRENT) { - dev_err (&hub->intf->dev, + dev_err (hub_dev, "over-current change on port %d\n", i + 1); - clear_port_feature(dev, + clear_port_feature(hdev, i + 1, USB_PORT_FEAT_C_OVER_CURRENT); hub_power_on(hub); } if (portchange & USB_PORT_STAT_C_RESET) { - dev_dbg (&hub->intf->dev, + dev_dbg (hub_dev, "reset change on port %d\n", i + 1); - clear_port_feature(dev, + clear_port_feature(hdev, i + 1, USB_PORT_FEAT_C_RESET); } } /* end for i */ /* deal with hub status changes */ if (hub_hub_status(hub, &hubstatus, &hubchange) < 0) - dev_err (&hub->intf->dev, "get_hub_status failed\n"); + dev_err (hub_dev, "get_hub_status failed\n"); else { if (hubchange & HUB_CHANGE_LOCAL_POWER) { - dev_dbg (&hub->intf->dev, "power change\n"); - clear_hub_feature(dev, C_HUB_LOCAL_POWER); + dev_dbg (hub_dev, "power change\n"); + clear_hub_feature(hdev, C_HUB_LOCAL_POWER); } if (hubchange & HUB_CHANGE_OVERCURRENT) { - dev_dbg (&hub->intf->dev, "overcurrent change\n"); + dev_dbg (hub_dev, "overcurrent change\n"); msleep(500); /* Cool down */ - clear_hub_feature(dev, C_HUB_OVER_CURRENT); + clear_hub_feature(hdev, C_HUB_OVER_CURRENT); hub_power_on(hub); } } @@ -1526,7 +1547,7 @@ spin_unlock_irqrestore(&hub_event_lock, flags); } -static int hub_thread(void *__hub) +static int hub_thread(void *__unused) { /* * This thread doesn't need any user-level access, @@ -1614,36 +1635,36 @@ } /* usb_hub_cleanup() */ -static int config_descriptors_changed(struct usb_device *dev) +static int config_descriptors_changed(struct usb_device *udev) { unsigned index; unsigned len = 0; struct usb_config_descriptor *buf; - for (index = 0; index < dev->descriptor.bNumConfigurations; index++) { - if (len < dev->config[index].desc.wTotalLength) - len = dev->config[index].desc.wTotalLength; + for (index = 0; index < udev->descriptor.bNumConfigurations; index++) { + if (len < udev->config[index].desc.wTotalLength) + len = udev->config[index].desc.wTotalLength; } buf = kmalloc (len, SLAB_KERNEL); if (buf == 0) { - dev_err(&dev->dev, "no mem to re-read configs after reset\n"); + dev_err(&udev->dev, "no mem to re-read configs after reset\n"); /* assume the worst */ return 1; } - for (index = 0; index < dev->descriptor.bNumConfigurations; index++) { + for (index = 0; index < udev->descriptor.bNumConfigurations; index++) { int length; - int old_length = dev->config[index].desc.wTotalLength; + int old_length = udev->config[index].desc.wTotalLength; - length = usb_get_descriptor(dev, USB_DT_CONFIG, index, buf, + length = usb_get_descriptor(udev, USB_DT_CONFIG, index, buf, old_length); if (length < old_length) { - dev_dbg(&dev->dev, "config index %d, error %d\n", + dev_dbg(&udev->dev, "config index %d, error %d\n", index, length); break; } - if (memcmp (buf, dev->rawdescriptors[index], old_length) + if (memcmp (buf, udev->rawdescriptors[index], old_length) != 0) { - dev_dbg(&dev->dev, "config index %d changed (#%d)\n", + dev_dbg(&udev->dev, "config index %d changed (#%d)\n", index, buf->bConfigurationValue); /* FIXME enable this when we can re-enumerate after reset; * until then DFU-ish drivers need this and other workarounds @@ -1652,7 +1673,7 @@ } } kfree(buf); - return index != dev->descriptor.bNumConfigurations; + return index != udev->descriptor.bNumConfigurations; } /* @@ -1664,22 +1685,22 @@ * already holds dev->serialize. For example, it's safe to use * this from a driver probe() routine after downloading new firmware. */ -int __usb_reset_device(struct usb_device *dev) +int __usb_reset_device(struct usb_device *udev) { - struct usb_device *parent = dev->parent; - struct usb_device_descriptor descriptor = dev->descriptor; + struct usb_device *parent = udev->parent; + struct usb_device_descriptor descriptor = udev->descriptor; int i, ret, port = -1; - if (dev->maxchild) { + if (udev->maxchild) { /* this requires hub- or hcd-specific logic; * see hub_reset() and OHCI hc_restart() */ - dev_dbg(&dev->dev, "%s for hub!\n", __FUNCTION__); + dev_dbg(&udev->dev, "%s for hub!\n", __FUNCTION__); return -EINVAL; } for (i = 0; i < parent->maxchild; i++) - if (parent->children[i] == dev) { + if (parent->children[i] == udev) { port = i; break; } @@ -1687,45 +1708,45 @@ if (port < 0) return -ENOENT; - ret = hub_port_init(parent, dev, port); + ret = hub_port_init(parent, udev, port); if (ret < 0) goto re_enumerate; /* Device might have changed firmware (DFU or similar) */ - if (memcmp(&dev->descriptor, &descriptor, sizeof descriptor) - || config_descriptors_changed (dev)) { - dev_info(&dev->dev, "device firmware changed\n"); - dev->descriptor = descriptor; /* for disconnect() calls */ + if (memcmp(&udev->descriptor, &descriptor, sizeof descriptor) + || config_descriptors_changed (udev)) { + dev_info(&udev->dev, "device firmware changed\n"); + udev->descriptor = descriptor; /* for disconnect() calls */ goto re_enumerate; } - if (!dev->actconfig) + if (!udev->actconfig) return 0; - ret = usb_control_msg(dev, usb_sndctrlpipe(dev, 0), + ret = usb_control_msg(udev, usb_sndctrlpipe(udev, 0), USB_REQ_SET_CONFIGURATION, 0, - dev->actconfig->desc.bConfigurationValue, 0, + udev->actconfig->desc.bConfigurationValue, 0, NULL, 0, HZ * USB_CTRL_SET_TIMEOUT); if (ret < 0) { - dev_err(&dev->dev, + dev_err(&udev->dev, "can't restore configuration #%d (error=%d)\n", - dev->actconfig->desc.bConfigurationValue, ret); + udev->actconfig->desc.bConfigurationValue, ret); goto re_enumerate; } - dev->state = USB_STATE_CONFIGURED; + udev->state = USB_STATE_CONFIGURED; - for (i = 0; i < dev->actconfig->desc.bNumInterfaces; i++) { - struct usb_interface *intf = dev->actconfig->interface[i]; + for (i = 0; i < udev->actconfig->desc.bNumInterfaces; i++) { + struct usb_interface *intf = udev->actconfig->interface[i]; struct usb_interface_descriptor *desc; /* set_interface resets host side toggle and halt status even * for altsetting zero. the interface may have no driver. */ desc = &intf->cur_altsetting->desc; - ret = usb_set_interface(dev, desc->bInterfaceNumber, + ret = usb_set_interface(udev, desc->bInterfaceNumber, desc->bAlternateSetting); if (ret < 0) { - dev_err(&dev->dev, "failed to restore interface %d " + dev_err(&udev->dev, "failed to restore interface %d " "altsetting %d (error=%d)\n", desc->bInterfaceNumber, desc->bAlternateSetting, @@ -1738,7 +1759,7 @@ re_enumerate: /* FIXME make some task re-enumerate; don't just mark unusable */ - dev->state = USB_STATE_NOTATTACHED; + udev->state = USB_STATE_NOTATTACHED; return -ENODEV; } EXPORT_SYMBOL(__usb_reset_device); diff -Nru a/drivers/usb/core/message.c b/drivers/usb/core/message.c --- a/drivers/usb/core/message.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/core/message.c 2004-05-25 21:38:09 -07:00 @@ -1252,7 +1252,7 @@ ret); continue; } - usb_create_driverfs_intf_files (intf); + usb_create_sysfs_intf_files (intf); } } diff -Nru a/drivers/usb/core/sysfs.c b/drivers/usb/core/sysfs.c --- /dev/null Wed Dec 31 16:00:00 196900 +++ b/drivers/usb/core/sysfs.c 2004-05-25 21:38:09 -07:00 @@ -0,0 +1,229 @@ +/* + * drivers/usb/core/sysfs.c + * + * (C) Copyright 2002 David Brownell + * (C) Copyright 2002 Greg Kroah-Hartman + * (C) Copyright 2002 IBM Corp. + * + * All of the sysfs file attributes for usb devices and interfaces. + * + */ + + +#include +#include + +#ifdef CONFIG_USB_DEBUG + #define DEBUG +#else + #undef DEBUG +#endif +#include + +#include "usb.h" + +/* Active configuration fields */ +#define usb_actconfig_show(field, multiplier, format_string) \ +static ssize_t show_##field (struct device *dev, char *buf) \ +{ \ + struct usb_device *udev; \ + \ + udev = to_usb_device (dev); \ + if (udev->actconfig) \ + return sprintf (buf, format_string, \ + udev->actconfig->desc.field * multiplier); \ + else \ + return 0; \ +} \ + +#define usb_actconfig_attr(field, multiplier, format_string) \ +usb_actconfig_show(field, multiplier, format_string) \ +static DEVICE_ATTR(field, S_IRUGO, show_##field, NULL); + +usb_actconfig_attr (bNumInterfaces, 1, "%2d\n") +usb_actconfig_attr (bmAttributes, 1, "%2x\n") +usb_actconfig_attr (bMaxPower, 2, "%3dmA\n") + +/* configuration value is always present, and r/w */ +usb_actconfig_show(bConfigurationValue, 1, "%u\n"); + +static ssize_t +set_bConfigurationValue (struct device *dev, const char *buf, size_t count) +{ + struct usb_device *udev = udev = to_usb_device (dev); + int config, value; + + if (sscanf (buf, "%u", &config) != 1 || config > 255) + return -EINVAL; + down(&udev->serialize); + value = usb_set_configuration (udev, config); + up(&udev->serialize); + return (value < 0) ? value : count; +} + +static DEVICE_ATTR(bConfigurationValue, S_IRUGO | S_IWUSR, + show_bConfigurationValue, set_bConfigurationValue); + +/* String fields */ +#define usb_string_attr(name, field) \ +static ssize_t show_##name(struct device *dev, char *buf) \ +{ \ + struct usb_device *udev; \ + int len; \ + \ + udev = to_usb_device (dev); \ + len = usb_string(udev, udev->descriptor.field, buf, PAGE_SIZE); \ + if (len < 0) \ + return 0; \ + buf[len] = '\n'; \ + buf[len+1] = 0; \ + return len+1; \ +} \ +static DEVICE_ATTR(name, S_IRUGO, show_##name, NULL); + +usb_string_attr(product, iProduct); +usb_string_attr(manufacturer, iManufacturer); +usb_string_attr(serial, iSerialNumber); + +static ssize_t +show_speed (struct device *dev, char *buf) +{ + struct usb_device *udev; + char *speed; + + udev = to_usb_device (dev); + + switch (udev->speed) { + case USB_SPEED_LOW: + speed = "1.5"; + break; + case USB_SPEED_UNKNOWN: + case USB_SPEED_FULL: + speed = "12"; + break; + case USB_SPEED_HIGH: + speed = "480"; + break; + default: + speed = "unknown"; + } + return sprintf (buf, "%s\n", speed); +} +static DEVICE_ATTR(speed, S_IRUGO, show_speed, NULL); + +static ssize_t +show_devnum (struct device *dev, char *buf) +{ + struct usb_device *udev; + + udev = to_usb_device (dev); + return sprintf (buf, "%d\n", udev->devnum); +} +static DEVICE_ATTR(devnum, S_IRUGO, show_devnum, NULL); + +static ssize_t +show_version (struct device *dev, char *buf) +{ + struct usb_device *udev; + + udev = to_usb_device (dev); + return sprintf (buf, "%2x.%02x\n", udev->descriptor.bcdUSB >> 8, + udev->descriptor.bcdUSB & 0xff); +} +static DEVICE_ATTR(version, S_IRUGO, show_version, NULL); + +static ssize_t +show_maxchild (struct device *dev, char *buf) +{ + struct usb_device *udev; + + udev = to_usb_device (dev); + return sprintf (buf, "%d\n", udev->maxchild); +} +static DEVICE_ATTR(maxchild, S_IRUGO, show_maxchild, NULL); + +/* Descriptor fields */ +#define usb_descriptor_attr(field, format_string) \ +static ssize_t \ +show_##field (struct device *dev, char *buf) \ +{ \ + struct usb_device *udev; \ + \ + udev = to_usb_device (dev); \ + return sprintf (buf, format_string, udev->descriptor.field); \ +} \ +static DEVICE_ATTR(field, S_IRUGO, show_##field, NULL); + +usb_descriptor_attr (idVendor, "%04x\n") +usb_descriptor_attr (idProduct, "%04x\n") +usb_descriptor_attr (bcdDevice, "%04x\n") +usb_descriptor_attr (bDeviceClass, "%02x\n") +usb_descriptor_attr (bDeviceSubClass, "%02x\n") +usb_descriptor_attr (bDeviceProtocol, "%02x\n") +usb_descriptor_attr (bNumConfigurations, "%d\n") + + +void usb_create_sysfs_dev_files (struct usb_device *udev) +{ + struct device *dev = &udev->dev; + + /* current configuration's attributes */ + device_create_file (dev, &dev_attr_bNumInterfaces); + device_create_file (dev, &dev_attr_bConfigurationValue); + device_create_file (dev, &dev_attr_bmAttributes); + device_create_file (dev, &dev_attr_bMaxPower); + + /* device attributes */ + device_create_file (dev, &dev_attr_idVendor); + device_create_file (dev, &dev_attr_idProduct); + device_create_file (dev, &dev_attr_bcdDevice); + device_create_file (dev, &dev_attr_bDeviceClass); + device_create_file (dev, &dev_attr_bDeviceSubClass); + device_create_file (dev, &dev_attr_bDeviceProtocol); + device_create_file (dev, &dev_attr_bNumConfigurations); + + /* speed varies depending on how you connect the device */ + device_create_file (dev, &dev_attr_speed); + // FIXME iff there are other speed configs, show how many + + if (udev->descriptor.iManufacturer) + device_create_file (dev, &dev_attr_manufacturer); + if (udev->descriptor.iProduct) + device_create_file (dev, &dev_attr_product); + if (udev->descriptor.iSerialNumber) + device_create_file (dev, &dev_attr_serial); + + device_create_file (dev, &dev_attr_devnum); + device_create_file (dev, &dev_attr_version); + device_create_file (dev, &dev_attr_maxchild); +} + +/* Interface fields */ +#define usb_intf_attr(field, format_string) \ +static ssize_t \ +show_##field (struct device *dev, char *buf) \ +{ \ + struct usb_interface *intf = to_usb_interface (dev); \ + \ + return sprintf (buf, format_string, intf->cur_altsetting->desc.field); \ +} \ +static DEVICE_ATTR(field, S_IRUGO, show_##field, NULL); + +usb_intf_attr (bInterfaceNumber, "%02x\n") +usb_intf_attr (bAlternateSetting, "%2d\n") +usb_intf_attr (bNumEndpoints, "%02x\n") +usb_intf_attr (bInterfaceClass, "%02x\n") +usb_intf_attr (bInterfaceSubClass, "%02x\n") +usb_intf_attr (bInterfaceProtocol, "%02x\n") +usb_intf_attr (iInterface, "%02x\n") + +void usb_create_sysfs_intf_files (struct usb_interface *intf) +{ + device_create_file (&intf->dev, &dev_attr_bInterfaceNumber); + device_create_file (&intf->dev, &dev_attr_bAlternateSetting); + device_create_file (&intf->dev, &dev_attr_bNumEndpoints); + device_create_file (&intf->dev, &dev_attr_bInterfaceClass); + device_create_file (&intf->dev, &dev_attr_bInterfaceSubClass); + device_create_file (&intf->dev, &dev_attr_bInterfaceProtocol); + device_create_file (&intf->dev, &dev_attr_iInterface); +} diff -Nru a/drivers/usb/core/usb.c b/drivers/usb/core/usb.c --- a/drivers/usb/core/usb.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/core/usb.c 2004-05-25 21:38:09 -07:00 @@ -998,12 +998,10 @@ */ usb_disable_device(dev, 0); - dev_dbg (&dev->dev, "unregistering device\n"); /* Free the device number and remove the /proc/bus/usb entry */ - if (dev->devnum > 0) { - clear_bit(dev->devnum, dev->bus->devmap.devicemap); - usbfs_remove_device(dev); - } + dev_dbg (&dev->dev, "unregistering device\n"); + usb_release_address(dev); + usbfs_remove_device(dev); up(&dev->serialize); device_unregister(&dev->dev); } @@ -1038,24 +1036,23 @@ } } - -// hub-only!! ... and only exported for reset/reinit path. -// otherwise used internally, for usb_new_device() -int usb_set_address(struct usb_device *dev) +/** + * usb_release_address - deallocate device address (usbcore-internal) + * @dev: newly removed device + * + * Removes and deallocates the address assigned to a device. + * Only hub drivers (but not virtual root hub drivers for host + * controllers) should ever call this. + */ +void usb_release_address(struct usb_device *dev) { - int retval; - - if (dev->devnum == 0) - return -EINVAL; - if (dev->state != USB_STATE_DEFAULT && dev->state != USB_STATE_ADDRESS) - return -EINVAL; - retval = usb_control_msg(dev, usb_snddefctrl(dev), USB_REQ_SET_ADDRESS, - 0, dev->devnum, 0, NULL, 0, HZ * USB_CTRL_SET_TIMEOUT); - if (retval == 0) - dev->state = USB_STATE_ADDRESS; - return retval; + if (dev->devnum > 0) { + clear_bit(dev->devnum, dev->bus->devmap.devicemap); + dev->devnum = -1; + } } + static inline void usb_show_string(struct usb_device *dev, char *id, int index) { char *buf; @@ -1069,6 +1066,37 @@ kfree(buf); } +static int usb_choose_configuration(struct usb_device *dev) +{ + int c, i; + + c = dev->config[0].desc.bConfigurationValue; + if (dev->descriptor.bNumConfigurations != 1) { + for (i = 0; i < dev->descriptor.bNumConfigurations; i++) { + struct usb_interface_descriptor *desc; + + /* heuristic: Linux is more likely to have class + * drivers, so avoid vendor-specific interfaces. + */ + desc = &dev->config[i].intf_cache[0] + ->altsetting->desc; + if (desc->bInterfaceClass == USB_CLASS_VENDOR_SPEC) + continue; + /* COMM/2/all is CDC ACM, except 0xff is MSFT RNDIS */ + if (desc->bInterfaceClass == USB_CLASS_COMM + && desc->bInterfaceSubClass == 2 + && desc->bInterfaceProtocol == 0xff) + continue; + c = dev->config[i].desc.bConfigurationValue; + break; + } + dev_info(&dev->dev, + "configuration #%d chosen from %d choices\n", + c, dev->descriptor.bNumConfigurations); + } + return c; +} + /* * usb_new_device - perform initial device setup (usbcore-internal) * @dev: newly addressed device (in ADDRESS state) @@ -1090,8 +1118,7 @@ int usb_new_device(struct usb_device *dev) { int err; - int i; - int config; + int c; err = usb_get_configuration(dev); if (err < 0) { @@ -1119,41 +1146,16 @@ dev_err(&dev->dev, "can't device_add, error %d\n", err); goto fail; } - usb_create_driverfs_dev_files (dev); + usb_create_sysfs_dev_files (dev); /* choose and set the configuration. that registers the interfaces * with the driver core, and lets usb device drivers bind to them. * NOTE: should interact with hub power budgeting. */ - config = dev->config[0].desc.bConfigurationValue; - if (dev->descriptor.bNumConfigurations != 1) { - for (i = 0; i < dev->descriptor.bNumConfigurations; i++) { - struct usb_interface_descriptor *desc; - - /* heuristic: Linux is more likely to have class - * drivers, so avoid vendor-specific interfaces. - */ - desc = &dev->config[i].intf_cache[0] - ->altsetting->desc; - if (desc->bInterfaceClass == USB_CLASS_VENDOR_SPEC) - continue; - /* COMM/2/all is CDC ACM, except 0xff is MSFT RNDIS */ - if (desc->bInterfaceClass == USB_CLASS_COMM - && desc->bInterfaceSubClass == 2 - && desc->bInterfaceProtocol == 0xff) - continue; - config = dev->config[i].desc.bConfigurationValue; - break; - } - dev_info(&dev->dev, - "configuration #%d chosen from %d choices\n", - config, - dev->descriptor.bNumConfigurations); - } - err = usb_set_configuration(dev, config); + c = usb_choose_configuration(dev); + err = usb_set_configuration(dev, c); if (err) { - dev_err(&dev->dev, "can't set config #%d, error %d\n", - config, err); + dev_err(&dev->dev, "can't set config #%d, error %d\n", c, err); device_del(&dev->dev); goto fail; } @@ -1166,8 +1168,7 @@ return 0; fail: dev->state = USB_STATE_NOTATTACHED; - clear_bit(dev->devnum, dev->bus->devmap.devicemap); - dev->devnum = -1; + usb_release_address(dev); usb_put_dev(dev); return err; } diff -Nru a/drivers/usb/core/usb.h b/drivers/usb/core/usb.h --- a/drivers/usb/core/usb.h 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/core/usb.h 2004-05-25 21:38:09 -07:00 @@ -1,7 +1,7 @@ /* Functions local to drivers/usb/core/ */ -extern void usb_create_driverfs_dev_files (struct usb_device *dev); -extern void usb_create_driverfs_intf_files (struct usb_interface *intf); +extern void usb_create_sysfs_dev_files (struct usb_device *dev); +extern void usb_create_sysfs_intf_files (struct usb_interface *intf); extern int usb_probe_interface (struct device *dev); extern int usb_unbind_interface (struct device *dev); diff -Nru a/drivers/usb/gadget/Kconfig b/drivers/usb/gadget/Kconfig --- a/drivers/usb/gadget/Kconfig 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/gadget/Kconfig 2004-05-25 21:38:09 -07:00 @@ -95,6 +95,7 @@ config USB_PXA2XX_SMALL depends on USB_GADGET_PXA2XX bool + default n if USB_ETH_RNDIS default y if USB_ZERO default y if USB_ETH default y if USB_G_SERIAL diff -Nru a/drivers/usb/gadget/epautoconf.c b/drivers/usb/gadget/epautoconf.c --- a/drivers/usb/gadget/epautoconf.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/gadget/epautoconf.c 2004-05-25 21:38:09 -07:00 @@ -96,7 +96,8 @@ /* for now, avoid PXA "interrupt-in"; * it's documented as never using DATA1. */ - if (gadget_is_pxa (gadget)) + if (gadget_is_pxa (gadget) + && 'i' == tmp [1]) return 0; break; case USB_ENDPOINT_XFER_BULK: diff -Nru a/drivers/usb/gadget/serial.c b/drivers/usb/gadget/serial.c --- a/drivers/usb/gadget/serial.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/gadget/serial.c 2004-05-25 21:38:09 -07:00 @@ -154,14 +154,9 @@ #define GS_CLOSE_TIMEOUT 15 -/* debug macro */ +/* debug settings */ #if G_SERIAL_DEBUG static int debug = G_SERIAL_DEBUG; -#else -static int debug = 0; -#endif - -#if G_SERIAL_DEBUG #define gs_debug(format, arg...) \ do { if (debug) printk(KERN_DEBUG format, ## arg); } while(0) @@ -598,8 +593,10 @@ MODULE_AUTHOR("Al Borchers"); MODULE_LICENSE("GPL"); +#if G_SERIAL_DEBUG MODULE_PARM(debug, "i"); MODULE_PARM_DESC(debug, "Enable debugging, 0=off, 1=on"); +#endif MODULE_PARM(read_q_size, "i"); MODULE_PARM_DESC(read_q_size, "Read request queue size, default=32"); diff -Nru a/drivers/usb/host/uhci-hcd.c b/drivers/usb/host/uhci-hcd.c --- a/drivers/usb/host/uhci-hcd.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/host/uhci-hcd.c 2004-05-25 21:38:09 -07:00 @@ -95,6 +95,10 @@ static int uhci_get_current_frame_number(struct uhci_hcd *uhci); static int uhci_urb_dequeue(struct usb_hcd *hcd, struct urb *urb); static void uhci_unlink_generic(struct uhci_hcd *uhci, struct urb *urb); +static void uhci_remove_pending_urbps(struct uhci_hcd *uhci); +static void uhci_finish_completion(struct usb_hcd *hcd, struct pt_regs *regs); +static void uhci_free_pending_qhs(struct uhci_hcd *uhci); +static void uhci_free_pending_tds(struct uhci_hcd *uhci); static void hc_state_transitions(struct uhci_hcd *uhci); @@ -373,6 +377,7 @@ { struct uhci_qh *pqh; u32 newlink; + unsigned int age; if (!qh) return; @@ -425,6 +430,12 @@ list_del_init(&qh->urbp->queue_list); qh->urbp = NULL; + age = uhci_get_current_frame_number(uhci); + if (age != uhci->qh_remove_age) { + uhci_free_pending_qhs(uhci); + uhci->qh_remove_age = age; + } + /* Check to see if the remove list is empty. Set the IOC bit */ /* to force an interrupt so we can remove the QH */ if (list_empty(&uhci->qh_remove_list)) @@ -628,6 +639,7 @@ { struct list_head *head, *tmp; struct urb_priv *urbp; + unsigned int age; urbp = (struct urb_priv *)urb->hcpriv; if (!urbp) @@ -637,6 +649,12 @@ dev_warn(uhci_dev(uhci), "urb %p still on uhci->urb_list " "or uhci->remove_list!\n", urb); + age = uhci_get_current_frame_number(uhci); + if (age != uhci->td_remove_age) { + uhci_free_pending_tds(uhci); + uhci->td_remove_age = age; + } + /* Check to see if the remove list is empty. Set the IOC bit */ /* to force an interrupt so we can remove the TD's*/ if (list_empty(&uhci->td_remove_list)) @@ -1512,6 +1530,7 @@ struct uhci_hcd *uhci = hcd_to_uhci(hcd); unsigned long flags; struct urb_priv *urbp; + unsigned int age; spin_lock_irqsave(&uhci->schedule_lock, flags); urbp = urb->hcpriv; @@ -1521,6 +1540,12 @@ uhci_unlink_generic(uhci, urb); + age = uhci_get_current_frame_number(uhci); + if (age != uhci->urb_remove_age) { + uhci_remove_pending_urbps(uhci); + uhci->urb_remove_age = age; + } + /* If we're the first, set the next interrupt bit */ if (list_empty(&uhci->urb_remove_list)) uhci_set_next_interrupt(uhci); @@ -1590,6 +1615,12 @@ INIT_LIST_HEAD(&list); spin_lock_irqsave(&uhci->schedule_lock, flags); + if (!list_empty(&uhci->urb_remove_list) && + uhci_get_current_frame_number(uhci) != uhci->urb_remove_age) { + uhci_remove_pending_urbps(uhci); + uhci_finish_completion(hcd, NULL); + } + head = &uhci->urb_list; tmp = head->next; while (tmp != head) { @@ -1728,6 +1759,7 @@ unsigned int io_addr = uhci->io_addr; unsigned short status; struct list_head *tmp, *head; + unsigned int age; /* * Read the interrupt status, and write it back to clear the @@ -1758,11 +1790,20 @@ spin_lock(&uhci->schedule_lock); - uhci_free_pending_qhs(uhci); - uhci_free_pending_tds(uhci); - uhci_remove_pending_urbps(uhci); - - uhci_clear_next_interrupt(uhci); + age = uhci_get_current_frame_number(uhci); + if (age != uhci->qh_remove_age) + uhci_free_pending_qhs(uhci); + if (age != uhci->td_remove_age) + uhci_free_pending_tds(uhci); + if (age != uhci->urb_remove_age) + uhci_remove_pending_urbps(uhci); + + if (list_empty(&uhci->urb_remove_list) && + list_empty(&uhci->td_remove_list) && + list_empty(&uhci->qh_remove_list)) + uhci_clear_next_interrupt(uhci); + else + uhci_set_next_interrupt(uhci); /* Walk the list of pending URB's to see which ones completed */ head = &uhci->urb_list; diff -Nru a/drivers/usb/host/uhci-hcd.h b/drivers/usb/host/uhci-hcd.h --- a/drivers/usb/host/uhci-hcd.h 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/host/uhci-hcd.h 2004-05-25 21:38:09 -07:00 @@ -357,12 +357,15 @@ /* List of QH's that are done, but waiting to be unlinked (race) */ struct list_head qh_remove_list; /* P: uhci->schedule_lock */ + unsigned int qh_remove_age; /* Age in frames */ /* List of TD's that are done, but waiting to be freed (race) */ struct list_head td_remove_list; /* P: uhci->schedule_lock */ + unsigned int td_remove_age; /* Age in frames */ /* List of asynchronously unlinked URB's */ struct list_head urb_remove_list; /* P: uhci->schedule_lock */ + unsigned int urb_remove_age; /* Age in frames */ /* List of URB's awaiting completion callback */ struct list_head complete_list; /* P: uhci->schedule_lock */ diff -Nru a/drivers/usb/input/hiddev.c b/drivers/usb/input/hiddev.c --- a/drivers/usb/input/hiddev.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/input/hiddev.c 2004-05-25 21:38:09 -07:00 @@ -232,7 +232,7 @@ static struct usb_class_driver hiddev_class; static void hiddev_cleanup(struct hiddev *hiddev) { - hiddev_table[hiddev->hid->minor] = NULL; + hiddev_table[hiddev->hid->minor - HIDDEV_MINOR_BASE] = NULL; usb_deregister_dev(hiddev->hid->intf, &hiddev_class); kfree(hiddev); } diff -Nru a/drivers/usb/input/powermate.c b/drivers/usb/input/powermate.c --- a/drivers/usb/input/powermate.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/input/powermate.c 2004-05-25 21:38:09 -07:00 @@ -33,6 +33,7 @@ #include #include #include +#include #include #define POWERMATE_VENDOR 0x077d /* Griffin Technology, Inc. */ @@ -67,7 +68,7 @@ dma_addr_t configcr_dma; struct usb_device *udev; struct input_dev input; - struct semaphore lock; + spinlock_t lock; int static_brightness; int pulse_speed; int pulse_table; @@ -116,7 +117,7 @@ __FUNCTION__, retval); } -/* Decide if we need to issue a control message and do so. Must be called with pm->lock down */ +/* Decide if we need to issue a control message and do so. Must be called with pm->lock taken */ static void powermate_sync_state(struct powermate_device *pm) { if (pm->requires_update == 0) @@ -194,19 +195,22 @@ static void powermate_config_complete(struct urb *urb, struct pt_regs *regs) { struct powermate_device *pm = urb->context; + unsigned long flags; if (urb->status) printk(KERN_ERR "powermate: config urb returned %d\n", urb->status); - down(&pm->lock); + spin_lock_irqsave(&pm->lock, flags); powermate_sync_state(pm); - up(&pm->lock); + spin_unlock_irqrestore(&pm->lock, flags); } /* Set the LED up as described and begin the sync with the hardware if required */ static void powermate_pulse_led(struct powermate_device *pm, int static_brightness, int pulse_speed, int pulse_table, int pulse_asleep, int pulse_awake) { + unsigned long flags; + if (pulse_speed < 0) pulse_speed = 0; if (pulse_table < 0) @@ -219,7 +223,8 @@ pulse_asleep = !!pulse_asleep; pulse_awake = !!pulse_awake; - down(&pm->lock); + + spin_lock_irqsave(&pm->lock, flags); /* mark state updates which are required */ if (static_brightness != pm->static_brightness){ @@ -242,7 +247,7 @@ powermate_sync_state(pm); - up(&pm->lock); + spin_unlock_irqrestore(&pm->lock, flags); } /* Callback from the Input layer when an event arrives from userspace to configure the LED */ @@ -344,7 +349,7 @@ return -ENOMEM; } - init_MUTEX(&pm->lock); + pm->lock = SPIN_LOCK_UNLOCKED; init_input_dev(&pm->input); /* get a handle to the interrupt data pipe */ @@ -411,7 +416,6 @@ usb_set_intfdata(intf, NULL); if (pm) { - down(&pm->lock); pm->requires_update = 0; usb_unlink_urb(pm->irq); input_unregister_device(&pm->input); diff -Nru a/drivers/usb/net/kaweth.c b/drivers/usb/net/kaweth.c --- a/drivers/usb/net/kaweth.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/net/kaweth.c 2004-05-25 21:38:09 -07:00 @@ -1240,20 +1240,21 @@ init_waitqueue_head(&awd.wqh); awd.done = 0; - set_current_state(TASK_INTERRUPTIBLE); add_wait_queue(&awd.wqh, &wait); urb->context = &awd; - status = usb_submit_urb(urb, GFP_ATOMIC); + status = usb_submit_urb(urb, GFP_NOIO); if (status) { // something went wrong usb_free_urb(urb); - set_current_state(TASK_RUNNING); remove_wait_queue(&awd.wqh, &wait); return status; } - while (timeout && !awd.done) + set_current_state(TASK_UNINTERRUPTIBLE); + while (timeout && !awd.done) { timeout = schedule_timeout(timeout); + set_current_state(TASK_UNINTERRUPTIBLE); + } set_current_state(TASK_RUNNING); remove_wait_queue(&awd.wqh, &wait); diff -Nru a/drivers/usb/net/pegasus.h b/drivers/usb/net/pegasus.h --- a/drivers/usb/net/pegasus.h 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/net/pegasus.h 2004-05-25 21:38:09 -07:00 @@ -136,6 +136,7 @@ #define VENDOR_LANEED 0x056e #define VENDOR_LINKSYS 0x066b #define VENDOR_MELCO 0x0411 +#define VENDOR_MICROSOFT 0x045e #define VENDOR_MOBILITY 0x1342 #define VENDOR_NETGEAR 0x0846 #define VENDOR_OCT 0x0b39 @@ -264,6 +265,8 @@ PEGASUS_DEV( "MELCO/BUFFALO LUA-TX", VENDOR_MELCO, 0x0005, DEFAULT_GPIO_RESET ) PEGASUS_DEV( "MELCO/BUFFALO LUA2-TX", VENDOR_MELCO, 0x0009, + DEFAULT_GPIO_RESET | PEGASUS_II ) +PEGASUS_DEV( "Microsoft MN-110", VENDOR_MICROSOFT, 0x007a, DEFAULT_GPIO_RESET | PEGASUS_II ) PEGASUS_DEV( "NETGEAR FA101", VENDOR_NETGEAR, 0x1020, DEFAULT_GPIO_RESET | PEGASUS_II ) diff -Nru a/drivers/usb/serial/Kconfig b/drivers/usb/serial/Kconfig --- a/drivers/usb/serial/Kconfig 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/serial/Kconfig 2004-05-25 21:38:09 -07:00 @@ -314,8 +314,8 @@ module will be called kl5kusb105. config USB_SERIAL_KOBIL_SCT - tristate "USB KOBIL chipcard reader (EXPERIMENTAL)" - depends on USB_SERIAL && EXPERIMENTAL + tristate "USB KOBIL chipcard reader" + depends on USB_SERIAL ---help--- Say Y here if you want to use one of the following KOBIL USB chipcard readers: diff -Nru a/drivers/usb/serial/kobil_sct.c b/drivers/usb/serial/kobil_sct.c --- a/drivers/usb/serial/kobil_sct.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/serial/kobil_sct.c 2004-05-25 21:38:09 -07:00 @@ -21,6 +21,9 @@ * Supported readers: USB TWIN, KAAN Standard Plus and SecOVID Reader Plus * (Adapter K), B1 Professional and KAAN Professional (Adapter B) * + * (21/05/2004) tw + * Fix bug with P'n'P readers + * * (28/05/2003) tw * Add support for KAAN SIM * @@ -59,7 +62,7 @@ #include "usb-serial.h" /* Version Information */ -#define DRIVER_VERSION "28/05/2003" +#define DRIVER_VERSION "21/05/2004" #define DRIVER_AUTHOR "KOBIL Systems GmbH - http://www.kobil.com" #define DRIVER_DESC "KOBIL USB Smart Card Terminal Driver (experimental)" @@ -339,6 +342,12 @@ ); dbg("%s - port %d Send reset_all_queues URB returns: %i", __FUNCTION__, port->number, result); } + if (priv->device_type == KOBIL_USBTWIN_PRODUCT_ID || priv->device_type == KOBIL_ADAPTER_B_PRODUCT_ID || + priv->device_type == KOBIL_KAAN_SIM_PRODUCT_ID) { + // start reading (Adapter B 'cause PNP string) + result = usb_submit_urb( port->interrupt_in_urb, GFP_ATOMIC ); + dbg("%s - port %d Send read URB returns: %i", __FUNCTION__, port->number, result); + } kfree(transfer_buffer); return 0; @@ -456,6 +465,11 @@ if ( ((priv->device_type != KOBIL_ADAPTER_B_PRODUCT_ID) && (priv->filled > 2) && (priv->filled >= (priv->buf[1] + 3))) || ((priv->device_type == KOBIL_ADAPTER_B_PRODUCT_ID) && (priv->filled > 3) && (priv->filled >= (priv->buf[2] + 4))) ) { + // stop reading (except TWIN and KAAN SIM) + if ( (priv->device_type == KOBIL_ADAPTER_B_PRODUCT_ID) || (priv->device_type == KOBIL_ADAPTER_K_PRODUCT_ID) ) { + usb_unlink_urb( port->interrupt_in_urb ); + } + todo = priv->filled - priv->cur_pos; while(todo > 0) { @@ -463,25 +477,23 @@ length = (todo < 8) ? todo : 8; // copy data to transfer buffer memcpy(port->write_urb->transfer_buffer, priv->buf + priv->cur_pos, length ); - - usb_fill_bulk_urb( port->write_urb, - port->serial->dev, - usb_sndbulkpipe( port->serial->dev, priv->write_int_endpoint_address), - port->write_urb->transfer_buffer, - length, - kobil_write_callback, - port + usb_fill_int_urb( port->write_urb, + port->serial->dev, + usb_sndintpipe(port->serial->dev, priv->write_int_endpoint_address), + port->write_urb->transfer_buffer, + length, + kobil_write_callback, + port, + 8 ); priv->cur_pos = priv->cur_pos + length; - result = usb_submit_urb( port->write_urb, GFP_ATOMIC ); + result = usb_submit_urb( port->write_urb, GFP_NOIO ); dbg("%s - port %d Send write URB returns: %i", __FUNCTION__, port->number, result); todo = priv->filled - priv->cur_pos; if (todo > 0) { - //mdelay(16); - set_current_state(TASK_UNINTERRUPTIBLE); - schedule_timeout(24 * HZ / 1000); + msleep(24); } } // end while @@ -492,9 +504,14 @@ // someone sets the dev to 0 if the close method has been called port->interrupt_in_urb->dev = port->serial->dev; - // start reading - result = usb_submit_urb( port->interrupt_in_urb, GFP_ATOMIC ); - dbg("%s - port %d Send read URB returns: %i", __FUNCTION__, port->number, result); + // start reading (except TWIN and KAAN SIM) + if ( (priv->device_type == KOBIL_ADAPTER_B_PRODUCT_ID) || (priv->device_type == KOBIL_ADAPTER_K_PRODUCT_ID) ) { + // someone sets the dev to 0 if the close method has been called + port->interrupt_in_urb->dev = port->serial->dev; + + result = usb_submit_urb( port->interrupt_in_urb, GFP_NOIO ); + dbg("%s - port %d Send read URB returns: %i", __FUNCTION__, port->number, result); + } } return count; } diff -Nru a/drivers/usb/serial/visor.c b/drivers/usb/serial/visor.c --- a/drivers/usb/serial/visor.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/serial/visor.c 2004-05-25 21:38:09 -07:00 @@ -680,7 +680,7 @@ char *string; int retval = 0; int i; - int num_ports; + int num_ports = 0; dbg("%s", __FUNCTION__); @@ -702,41 +702,50 @@ __FUNCTION__, retval); goto exit; } - - connection_info = (struct visor_connection_info *)transfer_buffer; - le16_to_cpus(&connection_info->num_ports); - num_ports = connection_info->num_ports; - /* handle devices that report invalid stuff here */ - if (num_ports > 2) - num_ports = 2; - dev_info(dev, "%s: Number of ports: %d\n", serial->type->name, - connection_info->num_ports); + if (retval == sizeof(*connection_info)) { + connection_info = (struct visor_connection_info *)transfer_buffer; + + le16_to_cpus(&connection_info->num_ports); + num_ports = connection_info->num_ports; - for (i = 0; i < num_ports; ++i) { - switch (connection_info->connections[i].port_function_id) { - case VISOR_FUNCTION_GENERIC: - string = "Generic"; - break; - case VISOR_FUNCTION_DEBUGGER: - string = "Debugger"; - break; - case VISOR_FUNCTION_HOTSYNC: - string = "HotSync"; - break; - case VISOR_FUNCTION_CONSOLE: - string = "Console"; - break; - case VISOR_FUNCTION_REMOTE_FILE_SYS: - string = "Remote File System"; - break; - default: - string = "unknown"; - break; + for (i = 0; i < num_ports; ++i) { + switch (connection_info->connections[i].port_function_id) { + case VISOR_FUNCTION_GENERIC: + string = "Generic"; + break; + case VISOR_FUNCTION_DEBUGGER: + string = "Debugger"; + break; + case VISOR_FUNCTION_HOTSYNC: + string = "HotSync"; + break; + case VISOR_FUNCTION_CONSOLE: + string = "Console"; + break; + case VISOR_FUNCTION_REMOTE_FILE_SYS: + string = "Remote File System"; + break; + default: + string = "unknown"; + break; + } + dev_info(dev, "%s: port %d, is for %s use\n", + serial->type->name, + connection_info->connections[i].port, string); } - dev_info(dev, "%s: port %d, is for %s use\n", serial->type->name, - connection_info->connections[i].port, string); } + /* + * Handle devices that report invalid stuff here. + */ + if (num_ports == 0 || num_ports > 2) { + dev_warn (dev, "%s: No valid connect info available\n", + serial->type->name); + num_ports = 2; + } + + dev_info(dev, "%s: Number of ports: %d\n", serial->type->name, + num_ports); /* * save off our num_ports info so that we can use it in the @@ -868,8 +877,7 @@ static int treo_attach (struct usb_serial *serial) { - struct usb_serial_port *port; - int i; + struct usb_serial_port *swap_port; /* Only do this endpoint hack for the Handspring devices with * interrupt in endpoints, which for now are the Treo devices. */ @@ -879,31 +887,28 @@ dbg("%s", __FUNCTION__); - /* Ok, this is pretty ugly, but these devices want to use the - * interrupt endpoint as paired up with a bulk endpoint for a - * "virtual serial port". So let's force the endpoints to be - * where we want them to be. */ - for (i = serial->num_bulk_in; i < serial->num_ports; ++i) { - port = serial->port[i]; - port->read_urb = serial->port[0]->read_urb; - port->bulk_in_endpointAddress = serial->port[0]->bulk_in_endpointAddress; - port->bulk_in_buffer = serial->port[0]->bulk_in_buffer; - } - - for (i = serial->num_bulk_out; i < serial->num_ports; ++i) { - port = serial->port[i]; - port->write_urb = serial->port[0]->write_urb; - port->bulk_out_size = serial->port[0]->bulk_out_size; - port->bulk_out_endpointAddress = serial->port[0]->bulk_out_endpointAddress; - port->bulk_out_buffer = serial->port[0]->bulk_out_buffer; - } - - for (i = serial->num_interrupt_in; i < serial->num_ports; ++i) { - port = serial->port[i]; - port->interrupt_in_urb = serial->port[0]->interrupt_in_urb; - port->interrupt_in_endpointAddress = serial->port[0]->interrupt_in_endpointAddress; - port->interrupt_in_buffer = serial->port[0]->interrupt_in_buffer; - } + /* + * It appears that Treos want to use the 1st interrupt endpoint to + * communicate with the 2nd bulk out endpoint, so let's swap the 1st + * and 2nd bulk in and interrupt endpoints. Note that swapping the + * bulk out endpoints would break lots of apps that want to communicate + * on the second port. + */ +#define COPY_PORT(dest, src) \ + dest->read_urb = src->read_urb; \ + dest->bulk_in_endpointAddress = src->bulk_in_endpointAddress; \ + dest->bulk_in_buffer = src->bulk_in_buffer; \ + dest->interrupt_in_urb = src->interrupt_in_urb; \ + dest->interrupt_in_endpointAddress = src->interrupt_in_endpointAddress; \ + dest->interrupt_in_buffer = src->interrupt_in_buffer; + + swap_port = kmalloc(sizeof(*swap_port), GFP_KERNEL); + if (!swap_port) + return -ENOMEM; + COPY_PORT(swap_port, serial->port[0]); + COPY_PORT(serial->port[0], serial->port[1]); + COPY_PORT(serial->port[1], swap_port); + kfree(swap_port); return 0; } diff -Nru a/drivers/usb/storage/transport.c b/drivers/usb/storage/transport.c --- a/drivers/usb/storage/transport.c 2004-05-25 21:38:09 -07:00 +++ b/drivers/usb/storage/transport.c 2004-05-25 21:38:09 -07:00 @@ -1112,8 +1112,7 @@ /* long wait for reset, so unlock to allow disconnects */ up(&us->dev_semaphore); - set_current_state(TASK_UNINTERRUPTIBLE); - schedule_timeout(HZ*6); + msleep(6000); down(&us->dev_semaphore); if (test_bit(US_FLIDX_DISCONNECTING, &us->flags)) { US_DEBUGP("Reset interrupted by disconnect\n");