Commit 9742f545 authored by Johan Hovold's avatar Johan Hovold Committed by Ben Hutchings

USB: serial: io_edgeport: fix descriptor error handling

commit 3c0e25d8 upstream.

Make sure to detect short control-message transfers and log an error
when reading incomplete manufacturer and boot descriptors.

Note that the default all-zero descriptors will now be used after a
short transfer is detected instead of partially initialised ones.

Fixes: 1da177e4 ("Linux-2.6.12-rc2")
Reviewed-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Signed-off-by: default avatarJohan Hovold <johan@kernel.org>
[bwh: Backported to 3.2: adjust context]
Signed-off-by: default avatarBen Hutchings <ben@decadent.org.uk>
parent dc73ec04
...@@ -2263,8 +2263,7 @@ static int rom_write(struct usb_serial *serial, __u16 extAddr, __u16 addr, ...@@ -2263,8 +2263,7 @@ static int rom_write(struct usb_serial *serial, __u16 extAddr, __u16 addr,
* rom_read * rom_read
* reads a number of bytes from the Edgeport device starting at the given * reads a number of bytes from the Edgeport device starting at the given
* address. * address.
* If successful returns the number of bytes read, otherwise it returns * Returns zero on success or a negative error number.
* a negative error number of the problem.
****************************************************************************/ ****************************************************************************/
static int rom_read(struct usb_serial *serial, __u16 extAddr, static int rom_read(struct usb_serial *serial, __u16 extAddr,
__u16 addr, __u16 length, __u8 *data) __u16 addr, __u16 length, __u8 *data)
...@@ -2296,12 +2295,17 @@ static int rom_read(struct usb_serial *serial, __u16 extAddr, ...@@ -2296,12 +2295,17 @@ static int rom_read(struct usb_serial *serial, __u16 extAddr,
USB_REQUEST_ION_READ_ROM, USB_REQUEST_ION_READ_ROM,
0xC0, addr, extAddr, transfer_buffer, 0xC0, addr, extAddr, transfer_buffer,
current_length, 300); current_length, 300);
if (result < 0) if (result < current_length) {
if (result >= 0)
result = -EIO;
break; break;
}
memcpy(data, transfer_buffer, current_length); memcpy(data, transfer_buffer, current_length);
length -= current_length; length -= current_length;
addr += current_length; addr += current_length;
data += current_length; data += current_length;
result = 0;
} }
kfree(transfer_buffer); kfree(transfer_buffer);
...@@ -2772,10 +2776,11 @@ static void get_manufacturing_desc(struct edgeport_serial *edge_serial) ...@@ -2772,10 +2776,11 @@ static void get_manufacturing_desc(struct edgeport_serial *edge_serial)
EDGE_MANUF_DESC_LEN, EDGE_MANUF_DESC_LEN,
(__u8 *)(&edge_serial->manuf_descriptor)); (__u8 *)(&edge_serial->manuf_descriptor));
if (response < 1) if (response < 0) {
dev_err(&edge_serial->serial->dev->dev, dev_err(&edge_serial->serial->dev->dev,
"error in getting manufacturer descriptor\n"); "error in getting manufacturer descriptor: %d\n",
else { response);
} else {
char string[30]; char string[30];
dbg("**Manufacturer Descriptor"); dbg("**Manufacturer Descriptor");
dbg(" RomSize: %dK", dbg(" RomSize: %dK",
...@@ -2831,10 +2836,11 @@ static void get_boot_desc(struct edgeport_serial *edge_serial) ...@@ -2831,10 +2836,11 @@ static void get_boot_desc(struct edgeport_serial *edge_serial)
EDGE_BOOT_DESC_LEN, EDGE_BOOT_DESC_LEN,
(__u8 *)(&edge_serial->boot_descriptor)); (__u8 *)(&edge_serial->boot_descriptor));
if (response < 1) if (response < 0) {
dev_err(&edge_serial->serial->dev->dev, dev_err(&edge_serial->serial->dev->dev,
"error in getting boot descriptor\n"); "error in getting boot descriptor: %d\n",
else { response);
} else {
dbg("**Boot Descriptor:"); dbg("**Boot Descriptor:");
dbg(" BootCodeLength: %d", dbg(" BootCodeLength: %d",
le16_to_cpu(edge_serial->boot_descriptor.BootCodeLength)); le16_to_cpu(edge_serial->boot_descriptor.BootCodeLength));
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment