summaryrefslogtreecommitdiff
path: root/drivers/usb
diff options
context:
space:
mode:
authorHarald Welte <laforge@gnumonks.org>2008-07-07 00:58:05 +0800
committerWolfgang Denk <wd@denx.de>2008-07-10 11:51:52 +0200
commite73b5212e0463a3db0af0a5c95c75bfb762ca973 (patch)
tree01011b40e467bcc71a1573b556e5b73c187d7aab /drivers/usb
parentc4b81f3238d77a4df343bd70ddfb7ebd29ca1dda (diff)
downloadu-boot-e73b5212e0463a3db0af0a5c95c75bfb762ca973.tar.gz
u-boot-e73b5212e0463a3db0af0a5c95c75bfb762ca973.tar.bz2
u-boot-e73b5212e0463a3db0af0a5c95c75bfb762ca973.zip
fix USB devices with multiple configurations
This patch fixes bugs in usbdcore*.c related to the use of devices with multiple configurations. The original code made mistakes about the meaning of configuration value and configuration index, and the resulting off-by-one errors resulted in: * SET_CONFIGURATION always selected the first configuration, no matter what wValue is being passed. * GET_DESCRIPTOR/CONFIGURATION always returned the descriptor for the first configuration (index 0). Signed-off-by: Harald Welte <laforge@openmoko.org> Acked-by: Markus Klotzbuecher <mk@denx.de>
Diffstat (limited to 'drivers/usb')
-rw-r--r--drivers/usb/usbdcore.c7
-rw-r--r--drivers/usb/usbdcore_ep0.c14
2 files changed, 6 insertions, 15 deletions
diff --git a/drivers/usb/usbdcore.c b/drivers/usb/usbdcore.c
index 308c7ceccc..a621ce7a39 100644
--- a/drivers/usb/usbdcore.c
+++ b/drivers/usb/usbdcore.c
@@ -146,12 +146,9 @@ struct usb_string_descriptor *usbd_get_string (__u8 index)
static struct usb_configuration_instance *usbd_device_configuration_instance (struct usb_device_instance *device,
unsigned int port, unsigned int configuration)
{
- /* XXX */
- configuration = configuration ? configuration - 1 : 0;
-
- if (configuration >= device->configurations) {
+ if (configuration >= device->configurations)
return NULL;
- }
+
return device->configuration_instance_array + configuration;
}
diff --git a/drivers/usb/usbdcore_ep0.c b/drivers/usb/usbdcore_ep0.c
index 1e44f322a7..cf3f3826cb 100644
--- a/drivers/usb/usbdcore_ep0.c
+++ b/drivers/usb/usbdcore_ep0.c
@@ -235,8 +235,8 @@ static int ep0_get_descriptor (struct usb_device_instance *device,
return -1;
}
/*dbg_ep0(2, "%d %d", index, device_descriptor->bNumConfigurations); */
- if (index > device_descriptor->bNumConfigurations) {
- dbg_ep0 (0, "index too large: %d > %d", index,
+ if (index >= device_descriptor->bNumConfigurations) {
+ dbg_ep0 (0, "index too large: %d >= %d", index,
device_descriptor->
bNumConfigurations);
return -1;
@@ -571,14 +571,8 @@ int ep0_recv_setup (struct urb *urb)
case USB_REQ_SET_CONFIGURATION:
/* c.f. 9.4.7 - the top half of wValue is reserved */
- /* */
- if ((device->configuration =
- le16_to_cpu (request->wValue) & 0xFF80) != 0) {
- /* c.f. 9.4.7 - zero is the default or addressed state, in our case this */
- /* is the same is configuration zero */
- serial_printf("error setting dev->config to zero!\n");
- device->configuration = 0; /* TBR - ?????? */
- }
+ device->configuration = le16_to_cpu(request->wValue) & 0xff;
+
/* reset interface and alternate settings */
device->interface = device->alternate = 0;