summaryrefslogtreecommitdiffstats
path: root/drivers/usb/serial
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/usb/serial')
-rw-r--r--drivers/usb/serial/Kconfig8
-rw-r--r--drivers/usb/serial/aircable.c11
-rw-r--r--drivers/usb/serial/airprime.c52
-rw-r--r--drivers/usb/serial/ark3116.c3
-rw-r--r--drivers/usb/serial/cp2101.c4
-rw-r--r--drivers/usb/serial/ftdi_sio.c119
-rw-r--r--drivers/usb/serial/ftdi_sio.h22
-rw-r--r--drivers/usb/serial/generic.c7
-rw-r--r--drivers/usb/serial/io_edgeport.c143
-rw-r--r--drivers/usb/serial/io_edgeport.h6
-rw-r--r--drivers/usb/serial/ipaq.c3
-rw-r--r--drivers/usb/serial/kl5kusb105.c28
-rw-r--r--drivers/usb/serial/mct_u232.c12
-rw-r--r--drivers/usb/serial/mos7720.c35
-rw-r--r--drivers/usb/serial/mos7840.c233
-rw-r--r--drivers/usb/serial/omninet.c40
-rw-r--r--drivers/usb/serial/option.c38
-rw-r--r--drivers/usb/serial/sierra.c25
-rw-r--r--drivers/usb/serial/usb-serial.c12
-rw-r--r--drivers/usb/serial/visor.c22
-rw-r--r--drivers/usb/serial/whiteheat.c8
-rw-r--r--drivers/usb/serial/whiteheat.h4
22 files changed, 516 insertions, 319 deletions
diff --git a/drivers/usb/serial/Kconfig b/drivers/usb/serial/Kconfig
index 2f4d303..3efe670 100644
--- a/drivers/usb/serial/Kconfig
+++ b/drivers/usb/serial/Kconfig
@@ -423,11 +423,11 @@ config USB_SERIAL_MCT_U232
module will be called mct_u232.
config USB_SERIAL_MOS7720
- tristate "USB Moschip 7720 Single Port Serial Driver"
+ tristate "USB Moschip 7720 Serial Driver"
depends on USB_SERIAL
---help---
- Say Y here if you want to use a USB Serial single port adapter from
- Moschip Semiconductor Tech.
+ Say Y here if you want to use USB Serial single and double
+ port adapters from Moschip Semiconductor Tech.
To compile this driver as a module, choose M here: the
module will be called mos7720.
@@ -558,7 +558,7 @@ config USB_SERIAL_DEBUG
tristate "USB Debugging Device"
depends on USB_SERIAL
help
- Say Y here if you have a USB debugging device used to recieve
+ Say Y here if you have a USB debugging device used to receive
debugging data from another machine. The most common of these
devices is the NetChip TurboCONNECT device.
diff --git a/drivers/usb/serial/aircable.c b/drivers/usb/serial/aircable.c
index 11dad42..fbc8c27 100644
--- a/drivers/usb/serial/aircable.c
+++ b/drivers/usb/serial/aircable.c
@@ -9,7 +9,7 @@
* The device works as an standard CDC device, it has 2 interfaces, the first
* one is for firmware access and the second is the serial one.
* The protocol is very simply, there are two posibilities reading or writing.
- * When writting the first urb must have a Header that starts with 0x20 0x29 the
+ * When writing the first urb must have a Header that starts with 0x20 0x29 the
* next two bytes must say how much data will be sended.
* When reading the process is almost equal except that the header starts with
* 0x00 0x20.
@@ -18,7 +18,7 @@
* buffer: The First and Second byte is used for a Header, the Third and Fourth
* tells the device the amount of information the package holds.
* Packages are 60 bytes long Header Stuff.
- * When writting to the device the first two bytes of the header are 0x20 0x29
+ * When writing to the device the first two bytes of the header are 0x20 0x29
* When reading the bytes are 0x00 0x20, or 0x00 0x10, there is an strange
* situation, when too much data arrives to the device because it sends the data
* but with out the header. I will use a simply hack to override this situation,
@@ -209,6 +209,7 @@ static void aircable_send(struct usb_serial_port *port)
int count, result;
struct aircable_private *priv = usb_get_serial_port_data(port);
unsigned char* buf;
+ u16 *dbuf;
dbg("%s - port %d", __FUNCTION__, port->number);
if (port->write_urb_busy)
return;
@@ -226,8 +227,8 @@ static void aircable_send(struct usb_serial_port *port)
buf[0] = TX_HEADER_0;
buf[1] = TX_HEADER_1;
- buf[2] = (unsigned char)count;
- buf[3] = (unsigned char)(count >> 8);
+ dbuf = (u16 *)&buf[2];
+ *dbuf = cpu_to_le16((u16)count);
serial_buf_get(priv->tx_buf,buf + HCI_HEADER_LENGTH, MAX_HCI_FRAMESIZE);
memcpy(port->write_urb->transfer_buffer, buf,
@@ -434,7 +435,7 @@ static void aircable_write_bulk_callback(struct urb *urb)
__FUNCTION__, urb->status);
port->write_urb->transfer_buffer_length = 1;
port->write_urb->dev = port->serial->dev;
- result = usb_submit_urb(port->write_urb, GFP_KERNEL);
+ result = usb_submit_urb(port->write_urb, GFP_ATOMIC);
if (result)
dev_err(&urb->dev->dev,
"%s - failed resubmitting write urb, error %d\n",
diff --git a/drivers/usb/serial/airprime.c b/drivers/usb/serial/airprime.c
index 18816bf..39a4983 100644
--- a/drivers/usb/serial/airprime.c
+++ b/drivers/usb/serial/airprime.c
@@ -18,11 +18,6 @@
static struct usb_device_id id_table [] = {
{ USB_DEVICE(0x0c88, 0x17da) }, /* Kyocera Wireless KPC650/Passport */
- { USB_DEVICE(0x1410, 0x1110) }, /* Novatel Wireless Merlin CDMA */
- { USB_DEVICE(0x1410, 0x1130) }, /* Novatel Wireless S720 CDMA/EV-DO */
- { USB_DEVICE(0x1410, 0x2110) }, /* Novatel Wireless U720 CDMA/EV-DO */
- { USB_DEVICE(0x1410, 0x1430) }, /* Novatel Merlin XU870 HSDPA/3G */
- { USB_DEVICE(0x1410, 0x1100) }, /* ExpressCard34 Qualcomm 3G CDMA */
{ USB_DEVICE(0x413c, 0x8115) }, /* Dell Wireless HSDPA 5500 */
{ },
};
@@ -44,8 +39,43 @@ struct airprime_private {
int outstanding_urbs;
int throttled;
struct urb *read_urbp[NUM_READ_URBS];
+
+ /* Settings for the port */
+ int rts_state; /* Handshaking pins (outputs) */
+ int dtr_state;
+ int cts_state; /* Handshaking pins (inputs) */
+ int dsr_state;
+ int dcd_state;
+ int ri_state;
};
+static int airprime_send_setup(struct usb_serial_port *port)
+{
+ struct usb_serial *serial = port->serial;
+ struct airprime_private *priv;
+
+ dbg("%s", __FUNCTION__);
+
+ if (port->number != 0)
+ return 0;
+
+ priv = usb_get_serial_port_data(port);
+
+ if (port->tty) {
+ int val = 0;
+ if (priv->dtr_state)
+ val |= 0x01;
+ if (priv->rts_state)
+ val |= 0x02;
+
+ return usb_control_msg(serial->dev,
+ usb_rcvctrlpipe(serial->dev, 0),
+ 0x22,0x21,val,0,NULL,0,USB_CTRL_SET_TIMEOUT);
+ }
+
+ return 0;
+}
+
static void airprime_read_bulk_callback(struct urb *urb)
{
struct usb_serial_port *port = urb->context;
@@ -118,6 +148,10 @@ static int airprime_open(struct usb_serial_port *port, struct file *filp)
usb_set_serial_port_data(port, priv);
}
+ /* Set some sane defaults */
+ priv->rts_state = 1;
+ priv->dtr_state = 1;
+
for (i = 0; i < NUM_READ_URBS; ++i) {
buffer = kmalloc(buffer_size, GFP_KERNEL);
if (!buffer) {
@@ -151,6 +185,9 @@ static int airprime_open(struct usb_serial_port *port, struct file *filp)
/* remember this urb so we can kill it when the port is closed */
priv->read_urbp[i] = urb;
}
+
+ airprime_send_setup(port);
+
goto out;
errout:
@@ -176,6 +213,11 @@ static void airprime_close(struct usb_serial_port *port, struct file * filp)
dbg("%s - port %d", __FUNCTION__, port->number);
+ priv->rts_state = 0;
+ priv->dtr_state = 0;
+
+ airprime_send_setup(port);
+
for (i = 0; i < NUM_READ_URBS; ++i) {
usb_kill_urb (priv->read_urbp[i]);
kfree (priv->read_urbp[i]->transfer_buffer);
diff --git a/drivers/usb/serial/ark3116.c b/drivers/usb/serial/ark3116.c
index edd6857..ea2175b 100644
--- a/drivers/usb/serial/ark3116.c
+++ b/drivers/usb/serial/ark3116.c
@@ -341,7 +341,7 @@ static int ark3116_open(struct usb_serial_port *port, struct file *filp)
result = usb_serial_generic_open(port, filp);
if (result)
- return result;
+ goto err_out;
/* open */
ARK3116_RCV(serial, 111, 0xFE, 0xC0, 0x0000, 0x0003, 0x02, buf);
@@ -372,6 +372,7 @@ static int ark3116_open(struct usb_serial_port *port, struct file *filp)
if (port->tty)
ark3116_set_termios(port, &tmp_termios);
+err_out:
kfree(buf);
return result;
diff --git a/drivers/usb/serial/cp2101.c b/drivers/usb/serial/cp2101.c
index db623e7..e831cb7 100644
--- a/drivers/usb/serial/cp2101.c
+++ b/drivers/usb/serial/cp2101.c
@@ -58,11 +58,15 @@ static struct usb_device_id id_table [] = {
{ USB_DEVICE(0x10AB, 0x10C5) }, /* Siemens MC60 Cable */
{ USB_DEVICE(0x10B5, 0xAC70) }, /* Nokia CA-42 USB */
{ USB_DEVICE(0x10C4, 0x803B) }, /* Pololu USB-serial converter */
+ { USB_DEVICE(0x10C4, 0x8053) }, /* Enfora EDG1228 */
{ USB_DEVICE(0x10C4, 0x8066) }, /* Argussoft In-System Programmer */
{ USB_DEVICE(0x10C4, 0x807A) }, /* Crumb128 board */
{ USB_DEVICE(0x10C4, 0x80CA) }, /* Degree Controls Inc */
+ { USB_DEVICE(0x10C4, 0x80DD) }, /* Tracient RFID */
{ USB_DEVICE(0x10C4, 0x80F6) }, /* Suunto sports instrument */
{ USB_DEVICE(0x10C4, 0x813D) }, /* Burnside Telecom Deskmobile */
+ { USB_DEVICE(0x10C4, 0x814A) }, /* West Mountain Radio RIGblaster P&P */
+ { USB_DEVICE(0x10C4, 0x814B) }, /* West Mountain Radio RIGtalk */
{ USB_DEVICE(0x10C4, 0x815E) }, /* Helicomm IP-Link 1220-DVM */
{ USB_DEVICE(0x10C4, 0x81C8) }, /* Lipowsky Industrie Elektronik GmbH, Baby-JTAG */
{ USB_DEVICE(0x10C4, 0x81E2) }, /* Lipowsky Industrie Elektronik GmbH, Baby-LIN */
diff --git a/drivers/usb/serial/ftdi_sio.c b/drivers/usb/serial/ftdi_sio.c
index c525b42..95a1805 100644
--- a/drivers/usb/serial/ftdi_sio.c
+++ b/drivers/usb/serial/ftdi_sio.c
@@ -315,6 +315,7 @@ static struct usb_device_id id_table_combined [] = {
{ USB_DEVICE(FTDI_VID, FTDI_SIO_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_8U232AM_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_8U232AM_ALT_PID) },
+ { USB_DEVICE(FTDI_VID, FTDI_232RL_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_8U2232C_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_MICRO_CHAMELEON_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_RELAIS_PID) },
@@ -341,6 +342,7 @@ static struct usb_device_id id_table_combined [] = {
{ USB_DEVICE(FTDI_VID, FTDI_PERLE_ULTRAPORT_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_PIEGROUP_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_TNC_X_PID) },
+ { USB_DEVICE(FTDI_VID, FTDI_USBX_707_PID) },
{ USB_DEVICE(SEALEVEL_VID, SEALEVEL_2101_PID) },
{ USB_DEVICE(SEALEVEL_VID, SEALEVEL_2102_PID) },
{ USB_DEVICE(SEALEVEL_VID, SEALEVEL_2103_PID) },
@@ -420,6 +422,14 @@ static struct usb_device_id id_table_combined [] = {
{ USB_DEVICE(FTDI_VID, FTDI_ELV_ALC8500_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_PYRAMID_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_ELV_FHZ1000PC_PID) },
+ { USB_DEVICE(FTDI_VID, FTDI_IBS_US485_PID) },
+ { USB_DEVICE(FTDI_VID, FTDI_IBS_PICPRO_PID) },
+ { USB_DEVICE(FTDI_VID, FTDI_IBS_PCMCIA_PID) },
+ { USB_DEVICE(FTDI_VID, FTDI_IBS_PK1_PID) },
+ { USB_DEVICE(FTDI_VID, FTDI_IBS_RS232MON_PID) },
+ { USB_DEVICE(FTDI_VID, FTDI_IBS_APP70_PID) },
+ { USB_DEVICE(FTDI_VID, FTDI_IBS_PEDO_PID) },
+ { USB_DEVICE(FTDI_VID, FTDI_IBS_PROD_PID) },
/*
* These will probably use user-space drivers. Uncomment them if
* you need them or use the user-specified vendor/product module
@@ -459,6 +469,7 @@ static struct usb_device_id id_table_combined [] = {
{ USB_DEVICE(FALCOM_VID, FALCOM_TWIST_PID) },
{ USB_DEVICE(FALCOM_VID, FALCOM_SAMBA_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_SUUNTO_SPORTS_PID) },
+ { USB_DEVICE(TTI_VID, TTI_QL355P_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_RM_CANVIEW_PID) },
{ USB_DEVICE(BANDB_VID, BANDB_USOTL4_PID) },
{ USB_DEVICE(BANDB_VID, BANDB_USTL4_PID) },
@@ -533,6 +544,7 @@ static const char *ftdi_chip_name[] = {
[FT8U232AM] = "FT8U232AM",
[FT232BM] = "FT232BM",
[FT2232C] = "FT2232C",
+ [FT232RL] = "FT232RL",
};
@@ -588,6 +600,8 @@ struct ftdi_private {
static int ftdi_sio_probe (struct usb_serial *serial, const struct usb_device_id *id);
static int ftdi_sio_attach (struct usb_serial *serial);
static void ftdi_shutdown (struct usb_serial *serial);
+static int ftdi_sio_port_probe (struct usb_serial_port *port);
+static int ftdi_sio_port_remove (struct usb_serial_port *port);
static int ftdi_open (struct usb_serial_port *port, struct file *filp);
static void ftdi_close (struct usb_serial_port *port, struct file *filp);
static int ftdi_write (struct usb_serial_port *port, const unsigned char *buf, int count);
@@ -622,6 +636,8 @@ static struct usb_serial_driver ftdi_sio_device = {
.num_bulk_out = 1,
.num_ports = 1,
.probe = ftdi_sio_probe,
+ .port_probe = ftdi_sio_port_probe,
+ .port_remove = ftdi_sio_port_remove,
.open = ftdi_open,
.close = ftdi_close,
.throttle = ftdi_throttle,
@@ -864,6 +880,7 @@ static __u32 get_ftdi_divisor(struct usb_serial_port * port)
break;
case FT232BM: /* FT232BM chip */
case FT2232C: /* FT2232C chip */
+ case FT232RL:
if (baud <= 3000000) {
div_value = ftdi_232bm_baud_to_divisor(baud);
} else {
@@ -1006,9 +1023,12 @@ static void ftdi_determine_type(struct usb_serial_port *port)
/* (It might be a BM because of the iSerialNumber bug,
* but it will still work as an AM device.) */
priv->chip_type = FT8U232AM;
- } else {
+ } else if (version < 0x600) {
/* Assume its an FT232BM (or FT245BM) */
priv->chip_type = FT232BM;
+ } else {
+ /* Assume its an FT232R */
+ priv->chip_type = FT232RL;
}
info("Detected %s", ftdi_chip_name[priv->chip_type]);
}
@@ -1024,11 +1044,10 @@ static ssize_t show_latency_timer(struct device *dev, struct device_attribute *a
{
struct usb_serial_port *port = to_usb_serial_port(dev);
struct ftdi_private *priv = usb_get_serial_port_data(port);
- struct usb_device *udev;
+ struct usb_device *udev = port->serial->dev;
unsigned short latency = 0;
int rv = 0;
- udev = to_usb_device(dev);
dbg("%s",__FUNCTION__);
@@ -1052,13 +1071,11 @@ static ssize_t store_latency_timer(struct device *dev, struct device_attribute *
{
struct usb_serial_port *port = to_usb_serial_port(dev);
struct ftdi_private *priv = usb_get_serial_port_data(port);
- struct usb_device *udev;
+ struct usb_device *udev = port->serial->dev;
char buf[1];
int v = simple_strtoul(valbuf, NULL, 10);
int rv = 0;
- udev = to_usb_device(dev);
-
dbg("%s: setting latency timer = %i", __FUNCTION__, v);
rv = usb_control_msg(udev,
@@ -1083,13 +1100,11 @@ static ssize_t store_event_char(struct device *dev, struct device_attribute *att
{
struct usb_serial_port *port = to_usb_serial_port(dev);
struct ftdi_private *priv = usb_get_serial_port_data(port);
- struct usb_device *udev;
+ struct usb_device *udev = port->serial->dev;
char buf[1];
int v = simple_strtoul(valbuf, NULL, 10);
int rv = 0;
- udev = to_usb_device(dev);
-
dbg("%s: setting event char = %i", __FUNCTION__, v);
rv = usb_control_msg(udev,
@@ -1110,46 +1125,38 @@ static ssize_t store_event_char(struct device *dev, struct device_attribute *att
static DEVICE_ATTR(latency_timer, S_IWUSR | S_IRUGO, show_latency_timer, store_latency_timer);
static DEVICE_ATTR(event_char, S_IWUSR, NULL, store_event_char);
-static int create_sysfs_attrs(struct usb_serial *serial)
+static int create_sysfs_attrs(struct usb_serial_port *port)
{
- struct ftdi_private *priv;
- struct usb_device *udev;
+ struct ftdi_private *priv = usb_get_serial_port_data(port);
int retval = 0;
dbg("%s",__FUNCTION__);
- priv = usb_get_serial_port_data(serial->port[0]);
- udev = serial->dev;
-
/* XXX I've no idea if the original SIO supports the event_char
* sysfs parameter, so I'm playing it safe. */
if (priv->chip_type != SIO) {
dbg("sysfs attributes for %s", ftdi_chip_name[priv->chip_type]);
- retval = device_create_file(&udev->dev, &dev_attr_event_char);
+ retval = device_create_file(&port->dev, &dev_attr_event_char);
if ((!retval) &&
(priv->chip_type == FT232BM || priv->chip_type == FT2232C)) {
- retval = device_create_file(&udev->dev,
+ retval = device_create_file(&port->dev,
&dev_attr_latency_timer);
}
}
return retval;
}
-static void remove_sysfs_attrs(struct usb_serial *serial)
+static void remove_sysfs_attrs(struct usb_serial_port *port)
{
- struct ftdi_private *priv;
- struct usb_device *udev;
+ struct ftdi_private *priv = usb_get_serial_port_data(port);
dbg("%s",__FUNCTION__);
- priv = usb_get_serial_port_data(serial->port[0]);
- udev = serial->dev;
-
/* XXX see create_sysfs_attrs */
if (priv->chip_type != SIO) {
- device_remove_file(&udev->dev, &dev_attr_event_char);
+ device_remove_file(&port->dev, &dev_attr_event_char);
if (priv->chip_type == FT232BM || priv->chip_type == FT2232C) {
- device_remove_file(&udev->dev, &dev_attr_latency_timer);
+ device_remove_file(&port->dev, &dev_attr_latency_timer);
}
}
@@ -1169,13 +1176,9 @@ static int ftdi_sio_probe (struct usb_serial *serial, const struct usb_device_id
return (0);
}
-/* attach subroutine */
-static int ftdi_sio_attach (struct usb_serial *serial)
+static int ftdi_sio_port_probe(struct usb_serial_port *port)
{
- struct usb_serial_port *port = serial->port[0];
struct ftdi_private *priv;
- struct ftdi_sio_quirk *quirk;
- int retval;
dbg("%s",__FUNCTION__);
@@ -1215,19 +1218,21 @@ static int ftdi_sio_attach (struct usb_serial *serial)
kfree(port->bulk_out_buffer);
port->bulk_out_buffer = NULL;
- usb_set_serial_port_data(serial->port[0], priv);
+ usb_set_serial_port_data(port, priv);
- ftdi_determine_type (serial->port[0]);
- retval = create_sysfs_attrs(serial);
- if (retval)
- dev_err(&serial->dev->dev, "Error creating sysfs files, "
- "continuing\n");
+ ftdi_determine_type (port);
+ create_sysfs_attrs(port);
+ return 0;
+}
+/* attach subroutine */
+static int ftdi_sio_attach (struct usb_serial *serial)
+{
/* Check for device requiring special set up. */
- quirk = (struct ftdi_sio_quirk *)usb_get_serial_data(serial);
- if (quirk && quirk->setup) {
+ struct ftdi_sio_quirk *quirk = usb_get_serial_data(serial);
+
+ if (quirk && quirk->setup)
quirk->setup(serial);
- }
return 0;
} /* ftdi_sio_attach */
@@ -1271,17 +1276,18 @@ static void ftdi_HE_TIRA1_setup (struct usb_serial *serial)
* calls __serial_close for each open of the port
* shutdown is called then (ie ftdi_shutdown)
*/
-
-
static void ftdi_shutdown (struct usb_serial *serial)
-{ /* ftdi_shutdown */
+{
+ dbg("%s", __FUNCTION__);
+}
- struct usb_serial_port *port = serial->port[0];
+static int ftdi_sio_port_remove(struct usb_serial_port *port)
+{
struct ftdi_private *priv = usb_get_serial_port_data(port);
dbg("%s", __FUNCTION__);
- remove_sysfs_attrs(serial);
+ remove_sysfs_attrs(port);
/* all open ports are closed at this point
* (by usbserial.c:__serial_close, which calls ftdi_close)
@@ -1291,8 +1297,9 @@ static void ftdi_shutdown (struct usb_serial *serial)
usb_set_serial_port_data(port, NULL);
kfree(priv);
}
-} /* ftdi_shutdown */
+ return 0;
+}
static int ftdi_open (struct usb_serial_port *port, struct file *filp)
{ /* ftdi_open */
@@ -1427,6 +1434,7 @@ static int ftdi_write (struct usb_serial_port *port,
dbg("%s - write limit hit\n", __FUNCTION__);
return 0;
}
+ priv->tx_outstanding_urbs++;
spin_unlock_irqrestore(&priv->tx_lock, flags);
data_offset = priv->write_offset;
@@ -1444,14 +1452,15 @@ static int ftdi_write (struct usb_serial_port *port,
buffer = kmalloc (transfer_size, GFP_ATOMIC);
if (!buffer) {
err("%s ran out of kernel memory for urb ...", __FUNCTION__);
- return -ENOMEM;
+ count = -ENOMEM;
+ goto error_no_buffer;
}
urb = usb_alloc_urb(0, GFP_ATOMIC);
if (!urb) {
err("%s - no more free urbs", __FUNCTION__);
- kfree (buffer);
- return -ENOMEM;
+ count = -ENOMEM;
+ goto error_no_urb;
}
/* Copy data */
@@ -1493,10 +1502,9 @@ static int ftdi_write (struct usb_serial_port *port,
if (status) {
err("%s - failed submitting write urb, error %d", __FUNCTION__, status);
count = status;
- kfree (buffer);
+ goto error;
} else {
spin_lock_irqsave(&priv->tx_lock, flags);
- ++priv->tx_outstanding_urbs;
priv->tx_outstanding_bytes += count;
priv->tx_bytes += count;
spin_unlock_irqrestore(&priv->tx_lock, flags);
@@ -1504,10 +1512,19 @@ static int ftdi_write (struct usb_serial_port *port,
/* we are done with this urb, so let the host driver
* really free it when it is finished with it */
- usb_free_urb (urb);
+ usb_free_urb(urb);
dbg("%s write returning: %d", __FUNCTION__, count);
return count;
+error:
+ usb_free_urb(urb);
+error_no_urb:
+ kfree (buffer);
+error_no_buffer:
+ spin_lock_irqsave(&priv->tx_lock, flags);
+ priv->tx_outstanding_urbs--;
+ spin_unlock_irqrestore(&priv->tx_lock, flags);
+ return count;
} /* ftdi_write */
diff --git a/drivers/usb/serial/ftdi_sio.h b/drivers/usb/serial/ftdi_sio.h
index 1bdda93..77ad0a0 100644
--- a/drivers/usb/serial/ftdi_sio.h
+++ b/drivers/usb/serial/ftdi_sio.h
@@ -27,9 +27,11 @@
#define FTDI_8U232AM_PID 0x6001 /* Similar device to SIO above */
#define FTDI_8U232AM_ALT_PID 0x6006 /* FTDI's alternate PID for above */
#define FTDI_8U2232C_PID 0x6010 /* Dual channel device */
+#define FTDI_232RL_PID 0xFBFA /* Product ID for FT232RL */
#define FTDI_RELAIS_PID 0xFA10 /* Relais device from Rudolf Gugler */
#define FTDI_NF_RIC_VID 0x0DCD /* Vendor Id */
#define FTDI_NF_RIC_PID 0x0001 /* Product Id */
+#define FTDI_USBX_707_PID 0xF857 /* ADSTech IR Blaster USBX-707 */
/* www.canusb.com Lawicel CANUSB device */
@@ -339,6 +341,12 @@
#define FTDI_SUUNTO_SPORTS_PID 0xF680 /* Suunto Sports instrument */
/*
+ * TTi (Thurlby Thandar Instruments)
+ */
+#define TTI_VID 0x103E /* Vendor Id */
+#define TTI_QL355P_PID 0x03E8 /* TTi QL355P power supply */
+
+/*
* Definitions for B&B Electronics products.
*/
#define BANDB_VID 0x0856 /* B&B Electronics Vendor ID */
@@ -497,6 +505,19 @@
#define TELLDUS_VID 0x1781 /* Vendor ID */
#define TELLDUS_TELLSTICK_PID 0x0C30 /* RF control dongle 433 MHz using FT232RL */
+/*
+ * IBS elektronik product ids
+ * Submitted by Thomas Schleusener
+ */
+#define FTDI_IBS_US485_PID 0xff38 /* IBS US485 (USB<-->RS422/485 interface) */
+#define FTDI_IBS_PICPRO_PID 0xff39 /* IBS PIC-Programmer */
+#define FTDI_IBS_PCMCIA_PID 0xff3a /* IBS Card reader for PCMCIA SRAM-cards */
+#define FTDI_IBS_PK1_PID 0xff3b /* IBS PK1 - Particel counter */
+#define FTDI_IBS_RS232MON_PID 0xff3c /* IBS RS232 - Monitor */
+#define FTDI_IBS_APP70_PID 0xff3d /* APP 70 (dust monitoring system) */
+#define FTDI_IBS_PEDO_PID 0xff3e /* IBS PEDO-Modem (RF modem 868.35 MHz) */
+#define FTDI_IBS_PROD_PID 0xff3f /* future device */
+
/* Commands */
#define FTDI_SIO_RESET 0 /* Reset the port */
#define FTDI_SIO_MODEM_CTRL 1 /* Set the modem control register */
@@ -620,6 +641,7 @@ typedef enum {
FT8U232AM = 2,
FT232BM = 3,
FT2232C = 4,
+ FT232RL = 5,
} ftdi_chip_type_t;
typedef enum {
diff --git a/drivers/usb/serial/generic.c b/drivers/usb/serial/generic.c
index 53baeec..4f8282a 100644
--- a/drivers/usb/serial/generic.c
+++ b/drivers/usb/serial/generic.c
@@ -20,13 +20,14 @@
#include <linux/usb/serial.h>
#include <asm/uaccess.h>
-static int generic_probe(struct usb_interface *interface,
- const struct usb_device_id *id);
-
static int debug;
#ifdef CONFIG_USB_SERIAL_GENERIC
+
+static int generic_probe(struct usb_interface *interface,
+ const struct usb_device_id *id);
+
static __u16 vendor = 0x05f9;
static __u16 product = 0xffff;
diff --git a/drivers/usb/serial/io_edgeport.c b/drivers/usb/serial/io_edgeport.c
index 6a26a2e..4807f96 100644
--- a/drivers/usb/serial/io_edgeport.c
+++ b/drivers/usb/serial/io_edgeport.c
@@ -111,7 +111,7 @@ struct edgeport_port {
struct TxFifo txfifo; /* transmit fifo -- size will be maxTxCredits */
struct urb *write_urb; /* write URB for this port */
- char write_in_progress; /* TRUE while a write URB is outstanding */
+ bool write_in_progress; /* 'true' while a write URB is outstanding */
spinlock_t ep_lock;
__u8 shadowLCR; /* last LCR value received */
@@ -123,11 +123,11 @@ struct edgeport_port {
__u8 validDataMask;
__u32 baudRate;
- char open;
- char openPending;
- char commandPending;
- char closePending;
- char chaseResponsePending;
+ bool open;
+ bool openPending;
+ bool commandPending;
+ bool closePending;
+ bool chaseResponsePending;
wait_queue_head_t wait_chase; /* for handling sleeping while waiting for chase to finish */
wait_queue_head_t wait_open; /* for handling sleeping while waiting for open to finish */
@@ -156,7 +156,7 @@ struct edgeport_serial {
__u8 bulk_in_endpoint; /* the bulk in endpoint handle */
unsigned char * bulk_in_buffer; /* the buffer we use for the bulk in endpoint */
struct urb * read_urb; /* our bulk read urb */
- int read_in_progress;
+ bool read_in_progress;
spinlock_t es_lock;
__u8 bulk_out_endpoint; /* the bulk out endpoint handle */
@@ -212,7 +212,7 @@ static int debug;
static int low_latency = 1; /* tty low latency flag, on by default */
-static int CmdUrbs = 0; /* Number of outstanding Command Write Urbs */
+static atomic_t CmdUrbs; /* Number of outstanding Command Write Urbs */
/* local function prototypes */
@@ -631,14 +631,14 @@ static void edge_interrupt_callback (struct urb *urb)
if (edge_serial->rxBytesAvail > 0 &&
!edge_serial->read_in_progress) {
dbg("%s - posting a read", __FUNCTION__);
- edge_serial->read_in_progress = TRUE;
+ edge_serial->read_in_progress = true;
/* we have pending bytes on the bulk in pipe, send a request */
edge_serial->read_urb->dev = edge_serial->serial->dev;
result = usb_submit_urb(edge_serial->read_urb, GFP_ATOMIC);
if (result) {
dev_err(&edge_serial->serial->dev->dev, "%s - usb_submit_urb(read bulk) failed with result = %d\n", __FUNCTION__, result);
- edge_serial->read_in_progress = FALSE;
+ edge_serial->read_in_progress = false;
}
}
spin_unlock(&edge_serial->es_lock);
@@ -695,13 +695,13 @@ static void edge_bulk_in_callback (struct urb *urb)
if (urb->status) {
dbg("%s - nonzero read bulk status received: %d", __FUNCTION__, urb->status);
- edge_serial->read_in_progress = FALSE;
+ edge_serial->read_in_progress = false;
return;
}
if (urb->actual_length == 0) {
dbg("%s - read bulk callback with no data", __FUNCTION__);
- edge_serial->read_in_progress = FALSE;
+ edge_serial->read_in_progress = false;
return;
}
@@ -725,10 +725,10 @@ static void edge_bulk_in_callback (struct urb *urb)
status = usb_submit_urb(edge_serial->read_urb, GFP_ATOMIC);
if (status) {
dev_err(&urb->dev->dev, "%s - usb_submit_urb(read bulk) failed, status = %d\n", __FUNCTION__, status);
- edge_serial->read_in_progress = FALSE;
+ edge_serial->read_in_progress = false;
}
} else {
- edge_serial->read_in_progress = FALSE;
+ edge_serial->read_in_progress = false;
}
spin_unlock(&edge_serial->es_lock);
@@ -759,7 +759,7 @@ static void edge_bulk_out_data_callback (struct urb *urb)
}
// Release the Write URB
- edge_port->write_in_progress = FALSE;
+ edge_port->write_in_progress = false;
// Check if more data needs to be sent
send_more_port_data((struct edgeport_serial *)(usb_get_serial_data(edge_port->port->serial)), edge_port);
@@ -779,8 +779,8 @@ static void edge_bulk_out_cmd_callback (struct urb *urb)
dbg("%s", __FUNCTION__);
- CmdUrbs--;
- dbg("%s - FREE URB %p (outstanding %d)", __FUNCTION__, urb, CmdUrbs);
+ atomic_dec(&CmdUrbs);
+ dbg("%s - FREE URB %p (outstanding %d)", __FUNCTION__, urb, atomic_read(&CmdUrbs));
/* clean up the transfer buffer */
@@ -802,7 +802,7 @@ static void edge_bulk_out_cmd_callback (struct urb *urb)
tty_wakeup(tty);
/* we have completed the command */
- edge_port->commandPending = FALSE;
+ edge_port->commandPending = false;
wake_up(&edge_port->wait_command);
}
@@ -868,7 +868,7 @@ static int edge_open (struct usb_serial_port *port, struct file * filp)
port0->bulk_in_buffer,
edge_serial->read_urb->transfer_buffer_length,
edge_bulk_in_callback, edge_serial);
- edge_serial->read_in_progress = FALSE;
+ edge_serial->read_in_progress = false;
/* start interrupt read for this edgeport
* this interrupt will continue as long as the edgeport is connected */
@@ -890,26 +890,26 @@ static int edge_open (struct usb_serial_port *port, struct file * filp)
/* initialize our port settings */
edge_port->txCredits = 0; /* Can't send any data yet */
edge_port->shadowMCR = MCR_MASTER_IE; /* Must always set this bit to enable ints! */
- edge_port->chaseResponsePending = FALSE;
+ edge_port->chaseResponsePending = false;
/* send a open port command */
- edge_port->openPending = TRUE;
- edge_port->open = FALSE;
+ edge_port->openPending = true;
+ edge_port->open = false;
response = send_iosp_ext_cmd (edge_port, IOSP_CMD_OPEN_PORT, 0);
if (response < 0) {
dev_err(&port->dev, "%s - error sending open port command\n", __FUNCTION__);
- edge_port->openPending = FALSE;
+ edge_port->openPending = false;
return -ENODEV;
}
/* now wait for the port to be completely opened */
- wait_event_timeout(edge_port->wait_open, (edge_port->openPending != TRUE), OPEN_TIMEOUT);
+ wait_event_timeout(edge_port->wait_open, !edge_port->openPending, OPEN_TIMEOUT);
- if (edge_port->open == FALSE) {
+ if (!edge_port->open) {
/* open timed out */
dbg("%s - open timedout", __FUNCTION__);
- edge_port->openPending = FALSE;
+ edge_port->openPending = false;
return -ENODEV;
}
@@ -928,7 +928,7 @@ static int edge_open (struct usb_serial_port *port, struct file * filp)
/* Allocate a URB for the write */
edge_port->write_urb = usb_alloc_urb (0, GFP_KERNEL);
- edge_port->write_in_progress = FALSE;
+ edge_port->write_in_progress = false;
if (!edge_port->write_urb) {
dbg("%s - no memory", __FUNCTION__);
@@ -966,7 +966,7 @@ static void block_until_chase_response(struct edgeport_port *edge_port)
lastCredits = edge_port->txCredits;
// Did we get our Chase response
- if (edge_port->chaseResponsePending == FALSE) {
+ if (!edge_port->chaseResponsePending) {
dbg("%s - Got Chase Response", __FUNCTION__);
// did we get all of our credit back?
@@ -985,7 +985,7 @@ static void block_until_chase_response(struct edgeport_port *edge_port)
// No activity.. count down.
loop--;
if (loop == 0) {
- edge_port->chaseResponsePending = FALSE;
+ edge_port->chaseResponsePending = false;
dbg("%s - Chase TIMEOUT", __FUNCTION__);
return;
}
@@ -1068,13 +1068,13 @@ static void edge_close (struct usb_serial_port *port, struct file * filp)
// block until tx is empty
block_until_tx_empty(edge_port);
- edge_port->closePending = TRUE;
+ edge_port->closePending = true;
if ((!edge_serial->is_epic) ||
((edge_serial->is_epic) &&
(edge_serial->epic_descriptor.Supports.IOSPChase))) {
/* flush and chase */
- edge_port->chaseResponsePending = TRUE;
+ edge_port->chaseResponsePending = true;
dbg("%s - Sending IOSP_CMD_CHASE_PORT", __FUNCTION__);
status = send_iosp_ext_cmd (edge_port, IOSP_CMD_CHASE_PORT, 0);
@@ -1082,7 +1082,7 @@ static void edge_close (struct usb_serial_port *port, struct file * filp)
// block until chase finished
block_until_chase_response(edge_port);
} else {
- edge_port->chaseResponsePending = FALSE;
+ edge_port->chaseResponsePending = false;
}
}
@@ -1094,10 +1094,10 @@ static void edge_close (struct usb_serial_port *port, struct file * filp)
send_iosp_ext_cmd (edge_port, IOSP_CMD_CLOSE_PORT, 0);
}
- //port->close = TRUE;
- edge_port->closePending = FALSE;
- edge_port->open = FALSE;
- edge_port->openPending = FALSE;
+ //port->close = true;
+ edge_port->closePending = false;
+ edge_port->open = false;
+ edge_port->openPending = false;
usb_kill_urb(edge_port->write_urb);
@@ -1247,7 +1247,7 @@ static void send_more_port_data(struct edgeport_serial *edge_serial, struct edge
}
// lock this write
- edge_port->write_in_progress = TRUE;
+ edge_port->write_in_progress = true;
// get a pointer to the write_urb
urb = edge_port->write_urb;
@@ -1261,7 +1261,7 @@ static void send_more_port_data(struct edgeport_serial *edge_serial, struct edge
buffer = kmalloc (count+2, GFP_ATOMIC);
if (buffer == NULL) {
dev_err(&edge_port->port->dev, "%s - no more kernel memory...\n", __FUNCTION__);
- edge_port->write_in_progress = FALSE;
+ edge_port->write_in_progress = false;
goto exit_send;
}
buffer[0] = IOSP_BUILD_DATA_HDR1 (edge_port->port->number - edge_port->port->serial->minor, count);
@@ -1301,7 +1301,7 @@ static void send_more_port_data(struct edgeport_serial *edge_serial, struct edge
if (status) {
/* something went wrong */
dev_err(&edge_port->port->dev, "%s - usb_submit_urb(write bulk) failed, status = %d, data lost\n", __FUNCTION__, status);
- edge_port->write_in_progress = FALSE;
+ edge_port->write_in_progress = false;
/* revert the credits as something bad happened. */
edge_port->txCredits += count;
@@ -1332,7 +1332,7 @@ static int edge_write_room (struct usb_serial_port *port)
if (edge_port == NULL)
return -ENODEV;
- if (edge_port->closePending == TRUE)
+ if (edge_port->closePending)
return -ENODEV;
dbg("%s - port %d", __FUNCTION__, port->number);
@@ -1371,7 +1371,7 @@ static int edge_chars_in_buffer (struct usb_serial_port *port)
if (edge_port == NULL)
return -ENODEV;
- if (edge_port->closePending == TRUE)
+ if (edge_port->closePending)
return -ENODEV;
if (!edge_port->open) {
@@ -1762,7 +1762,7 @@ static void edge_break (struct usb_serial_port *port, int break_state)
((edge_serial->is_epic) &&
(edge_serial->epic_descriptor.Supports.IOSPChase))) {
/* flush and chase */
- edge_port->chaseResponsePending = TRUE;
+ edge_port->chaseResponsePending = true;
dbg("%s - Sending IOSP_CMD_CHASE_PORT", __FUNCTION__);
status = send_iosp_ext_cmd (edge_port, IOSP_CMD_CHASE_PORT, 0);
@@ -1770,7 +1770,7 @@ static void edge_break (struct usb_serial_port *port, int break_state)
// block until chase finished
block_until_chase_response(edge_port);
} else {
- edge_port->chaseResponsePending = FALSE;
+ edge_port->chaseResponsePending = false;
}
}
@@ -1952,13 +1952,13 @@ static void process_rcvd_status (struct edgeport_serial *edge_serial, __u8 byte2
// Also, we currently clear flag and close the port regardless of content of above's Byte3.
// We could choose to do something else when Byte3 says Timeout on Chase from Edgeport,
// like wait longer in block_until_chase_response, but for now we don't.
- edge_port->chaseResponsePending = FALSE;
+ edge_port->chaseResponsePending = false;
wake_up (&edge_port->wait_chase);
return;
case IOSP_EXT_STATUS_RX_CHECK_RSP:
dbg("%s ========== Port %u CHECK_RSP Sequence = %02x =============\n", __FUNCTION__, edge_serial->rxPort, byte3 );
- //Port->RxCheckRsp = TRUE;
+ //Port->RxCheckRsp = true;
return;
}
}
@@ -1974,8 +1974,8 @@ static void process_rcvd_status (struct edgeport_serial *edge_serial, __u8 byte2
change_port_settings (edge_port, edge_port->port->tty->termios);
/* we have completed the open */
- edge_port->openPending = FALSE;
- edge_port->open = TRUE;
+ edge_port->openPending = false;
+ edge_port->open = true;
wake_up(&edge_port->wait_open);
return;
}
@@ -1983,7 +1983,7 @@ static void process_rcvd_status (struct edgeport_serial *edge_serial, __u8 byte2
// If port is closed, silently discard all rcvd status. We can
// have cases where buffered status is received AFTER the close
// port command is sent to the Edgeport.
- if ((!edge_port->open ) || (edge_port->closePending)) {
+ if (!edge_port->open || edge_port->closePending) {
return;
}
@@ -1991,14 +1991,14 @@ static void process_rcvd_status (struct edgeport_serial *edge_serial, __u8 byte2
// Not currently sent by Edgeport
case IOSP_STATUS_LSR:
dbg("%s - Port %u LSR Status = %02x", __FUNCTION__, edge_serial->rxPort, byte2);
- handle_new_lsr (edge_port, FALSE, byte2, 0);
+ handle_new_lsr(edge_port, false, byte2, 0);
break;
case IOSP_STATUS_LSR_DATA:
dbg("%s - Port %u LSR Status = %02x, Data = %02x", __FUNCTION__, edge_serial->rxPort, byte2, byte3);
// byte2 is LSR Register
// byte3 is broken data byte
- handle_new_lsr (edge_port, TRUE, byte2, byte3);
+ handle_new_lsr(edge_port, true, byte2, byte3);
break;
//
// case IOSP_EXT_4_STATUS:
@@ -2317,14 +2317,14 @@ static int write_cmd_usb (struct edgeport_port *edge_port, unsigned char *buffer
if (!urb)
return -ENOMEM;
- CmdUrbs++;
- dbg("%s - ALLOCATE URB %p (outstanding %d)", __FUNCTION__, urb, CmdUrbs);
+ atomic_inc(&CmdUrbs);
+ dbg("%s - ALLOCATE URB %p (outstanding %d)", __FUNCTION__, urb, atomic_read(&CmdUrbs));
usb_fill_bulk_urb (urb, edge_serial->serial->dev,
usb_sndbulkpipe(edge_serial->serial->dev, edge_serial->bulk_out_endpoint),
buffer, length, edge_bulk_out_cmd_callback, edge_port);
- edge_port->commandPending = TRUE;
+ edge_port->commandPending = true;
status = usb_submit_urb(urb, GFP_ATOMIC);
if (status) {
@@ -2332,16 +2332,16 @@ static int write_cmd_usb (struct edgeport_port *edge_port, unsigned char *buffer
dev_err(&edge_port->port->dev, "%s - usb_submit_urb(write command) failed, status = %d\n", __FUNCTION__, status);
usb_kill_urb(urb);
usb_free_urb(urb);
- CmdUrbs--;
+ atomic_dec(&CmdUrbs);
return status;
}
// wait for command to finish
timeout = COMMAND_TIMEOUT;
#if 0
- wait_event (&edge_port->wait_command, (edge_port->commandPending == FALSE));
+ wait_event (&edge_port->wait_command, !edge_port->commandPending);
- if (edge_port->commandPending == TRUE) {
+ if (edge_port->commandPending) {
/* command timed out */
dbg("%s - command timed out", __FUNCTION__);
status = -EINVAL;
@@ -2465,7 +2465,7 @@ static int send_cmd_write_uart_register (struct edgeport_port *edge_port, __u8 r
((edge_serial->is_epic) &&
(!edge_serial->epic_descriptor.Supports.IOSPWriteMCR) &&
(regNum == MCR))) {
- dbg("SendCmdWriteUartReg - Not writting to MCR Register");
+ dbg("SendCmdWriteUartReg - Not writing to MCR Register");
return 0;
}
@@ -2473,7 +2473,7 @@ static int send_cmd_write_uart_register (struct edgeport_port *edge_port, __u8 r
((edge_serial->is_epic) &&
(!edge_serial->epic_descriptor.Supports.IOSPWriteLCR) &&
(regNum == LCR))) {
- dbg ("SendCmdWriteUartReg - Not writting to LCR Register");
+ dbg ("SendCmdWriteUartReg - Not writing to LCR Register");
return 0;
}
@@ -2524,8 +2524,8 @@ static void change_port_settings (struct edgeport_port *edge_port, struct ktermi
dbg("%s - port %d", __FUNCTION__, edge_port->port->number);
- if ((!edge_port->open) &&
- (!edge_port->openPending)) {
+ if (!edge_port->open &&
+ !edge_port->openPending) {
dbg("%s - port not opened", __FUNCTION__);
return;
}
@@ -2836,9 +2836,9 @@ static int edge_startup (struct usb_serial *serial)
struct usb_device *dev;
int i, j;
int response;
- int interrupt_in_found;
- int bulk_in_found;
- int bulk_out_found;
+ bool interrupt_in_found;
+ bool bulk_in_found;
+ bool bulk_out_found;
static __u32 descriptor[3] = { EDGE_COMPATIBILITY_MASK0,
EDGE_COMPATIBILITY_MASK1,
EDGE_COMPATIBILITY_MASK2 };
@@ -2936,14 +2936,14 @@ static int edge_startup (struct usb_serial *serial)
if (edge_serial->is_epic) {
/* EPIC thing, set up our interrupt polling now and our read urb, so
* that the device knows it really is connected. */
- interrupt_in_found = bulk_in_found = bulk_out_found = FALSE;
+ interrupt_in_found = bulk_in_found = bulk_out_found = false;
for (i = 0; i < serial->interface->altsetting[0].desc.bNumEndpoints; ++i) {
struct usb_endpoint_descriptor *endpoint;
int buffer_size;
endpoint = &serial->interface->altsetting[0].endpoint[i].desc;
buffer_size = le16_to_cpu(endpoint->wMaxPacketSize);
- if ((!interrupt_in_found) &&
+ if (!interrupt_in_found &&
(usb_endpoint_is_int_in(endpoint))) {
/* we found a interrupt in endpoint */
dbg("found interrupt in");
@@ -2972,10 +2972,10 @@ static int edge_startup (struct usb_serial *serial)
edge_serial,
endpoint->bInterval);
- interrupt_in_found = TRUE;
+ interrupt_in_found = true;
}
- if ((!bulk_in_found) &&
+ if (!bulk_in_found &&
(usb_endpoint_is_bulk_in(endpoint))) {
/* we found a bulk in endpoint */
dbg("found bulk in");
@@ -3001,19 +3001,19 @@ static int edge_startup (struct usb_serial *serial)
endpoint->wMaxPacketSize,
edge_bulk_in_callback,
edge_serial);
- bulk_in_found = TRUE;
+ bulk_in_found = true;
}
- if ((!bulk_out_found) &&
+ if (!bulk_out_found &&
(usb_endpoint_is_bulk_out(endpoint))) {
/* we found a bulk out endpoint */
dbg("found bulk out");
edge_serial->bulk_out_endpoint = endpoint->bEndpointAddress;
- bulk_out_found = TRUE;
+ bulk_out_found = true;
}
}
- if ((!interrupt_in_found) || (!bulk_in_found) || (!bulk_out_found)) {
+ if (!interrupt_in_found || !bulk_in_found || !bulk_out_found) {
err ("Error - the proper endpoints were not found!");
return -ENODEV;
}
@@ -3083,6 +3083,7 @@ static int __init edgeport_init(void)
retval = usb_register(&io_driver);
if (retval)
goto failed_usb_register;
+ atomic_set(&CmdUrbs, 0);
info(DRIVER_DESC " " DRIVER_VERSION);
return 0;
diff --git a/drivers/usb/serial/io_edgeport.h b/drivers/usb/serial/io_edgeport.h
index 29a913a..cb201c1 100644
--- a/drivers/usb/serial/io_edgeport.h
+++ b/drivers/usb/serial/io_edgeport.h
@@ -19,12 +19,6 @@
#define MAX_RS232_PORTS 8 /* Max # of RS-232 ports per device */
/* typedefs that the insideout headers need */
-#ifndef TRUE
- #define TRUE (1)
-#endif
-#ifndef FALSE
- #define FALSE (0)
-#endif
#ifndef LOW8
#define LOW8(a) ((unsigned char)(a & 0xff))
#endif
diff --git a/drivers/usb/serial/ipaq.c b/drivers/usb/serial/ipaq.c
index a408184..4df0ec7 100644
--- a/drivers/usb/serial/ipaq.c
+++ b/drivers/usb/serial/ipaq.c
@@ -247,12 +247,15 @@ static struct usb_device_id ipaq_id_table [] = {
{ USB_DEVICE(0x04AD, 0x0301) }, /* USB Sync 0301 */
{ USB_DEVICE(0x04AD, 0x0302) }, /* USB Sync 0302 */
{ USB_DEVICE(0x04AD, 0x0303) }, /* USB Sync 0303 */
+ { USB_DEVICE(0x04AD, 0x0306) }, /* GPS Pocket PC USB Sync */
+ { USB_DEVICE(0x04B7, 0x0531) }, /* MyGuide 7000 XL USB Sync */
{ USB_DEVICE(0x04C5, 0x1058) }, /* FUJITSU USB Sync */
{ USB_DEVICE(0x04C5, 0x1079) }, /* FUJITSU USB Sync */
{ USB_DEVICE(0x04DA, 0x2500) }, /* Panasonic USB Sync */
{ USB_DEVICE(0x04DD, 0x9102) }, /* SHARP WS003SH USB Modem */
{ USB_DEVICE(0x04DD, 0x9121) }, /* SHARP WS004SH USB Modem */
{ USB_DEVICE(0x04DD, 0x9123) }, /* SHARP WS007SH USB Modem */
+ { USB_DEVICE(0x04DD, 0x9151) }, /* SHARP S01SH USB Modem */
{ USB_DEVICE(0x04E8, 0x5F00) }, /* Samsung NEXiO USB Sync */
{ USB_DEVICE(0x04E8, 0x5F01) }, /* Samsung NEXiO USB Sync */
{ USB_DEVICE(0x04E8, 0x5F02) }, /* Samsung NEXiO USB Sync */
diff --git a/drivers/usb/serial/kl5kusb105.c b/drivers/usb/serial/kl5kusb105.c
index b2097c4..7b085f3 100644
--- a/drivers/usb/serial/kl5kusb105.c
+++ b/drivers/usb/serial/kl5kusb105.c
@@ -238,7 +238,7 @@ static int klsi_105_get_line_state(struct usb_serial_port *port,
if (rc < 0)
err("Reading line status failed (error = %d)", rc);
else {
- status = status_buf[0] + (status_buf[1]<<8);
+ status = le16_to_cpu(*(u16 *)status_buf);
info("%s - read status %x %x", __FUNCTION__,
status_buf[0], status_buf[1]);
@@ -257,7 +257,7 @@ static int klsi_105_get_line_state(struct usb_serial_port *port,
static int klsi_105_startup (struct usb_serial *serial)
{
struct klsi_105_private *priv;
- int i;
+ int i, j;
/* check if we support the product id (see keyspan.c)
* FIXME
@@ -265,12 +265,12 @@ static int klsi_105_startup (struct usb_serial *serial)
/* allocate the private data structure */
for (i=0; i<serial->num_ports; i++) {
- int j;
priv = kmalloc(sizeof(struct klsi_105_private),
GFP_KERNEL);
if (!priv) {
dbg("%skmalloc for klsi_105_private failed.", __FUNCTION__);
- return -ENOMEM;
+ i--;
+ goto err_cleanup;
}
/* set initial values for control structures */
priv->cfg.pktlen = 5;
@@ -292,15 +292,14 @@ static int klsi_105_startup (struct usb_serial *serial)
priv->write_urb_pool[j] = urb;
if (urb == NULL) {
err("No more urbs???");
- continue;
+ goto err_cleanup;
}
- urb->transfer_buffer = NULL;
urb->transfer_buffer = kmalloc (URB_TRANSFER_BUFFER_SIZE,
GFP_KERNEL);
if (!urb->transfer_buffer) {
err("%s - out of memory for urb buffers.", __FUNCTION__);
- continue;
+ goto err_cleanup;
}
}
@@ -308,7 +307,20 @@ static int klsi_105_startup (struct usb_serial *serial)
init_waitqueue_head(&serial->port[i]->write_wait);
}
- return (0);
+ return 0;
+
+err_cleanup:
+ for (; i >= 0; i--) {
+ priv = usb_get_serial_port_data(serial->port[i]);
+ for (j=0; j < NUM_URBS; j++) {
+ if (priv->write_urb_pool[j]) {
+ kfree(priv->write_urb_pool[j]->transfer_buffer);
+ usb_free_urb(priv->write_urb_pool[j]);
+ }
+ }
+ usb_set_serial_port_data(serial->port[i], NULL);
+ }
+ return -ENOMEM;
} /* klsi_105_startup */
diff --git a/drivers/usb/serial/mct_u232.c b/drivers/usb/serial/mct_u232.c
index 4cd839b..3db1adc 100644
--- a/drivers/usb/serial/mct_u232.c
+++ b/drivers/usb/serial/mct_u232.c
@@ -438,17 +438,21 @@ static int mct_u232_open (struct usb_serial_port *port, struct file *filp)
if (retval) {
err("usb_submit_urb(read bulk) failed pipe 0x%x err %d",
port->read_urb->pipe, retval);
- goto exit;
+ goto error;
}
port->interrupt_in_urb->dev = port->serial->dev;
retval = usb_submit_urb(port->interrupt_in_urb, GFP_KERNEL);
- if (retval)
+ if (retval) {
+ usb_kill_urb(port->read_urb);
err(" usb_submit_urb(read int) failed pipe 0x%x err %d",
port->interrupt_in_urb->pipe, retval);
-
-exit:
+ goto error;
+ }
return 0;
+
+error:
+ return retval;
} /* mct_u232_open */
diff --git a/drivers/usb/serial/mos7720.c b/drivers/usb/serial/mos7720.c
index 2d588fb..b563e2a 100644
--- a/drivers/usb/serial/mos7720.c
+++ b/drivers/usb/serial/mos7720.c
@@ -103,11 +103,9 @@ static void mos7720_interrupt_callback(struct urb *urb)
{
int result;
int length;
- __u32 *data;
- unsigned int status;
+ __u8 *data;
__u8 sp1;
__u8 sp2;
- __u8 st;
dbg("%s"," : Entering\n");
@@ -141,18 +139,19 @@ static void mos7720_interrupt_callback(struct urb *urb)
* Byte 2 IIR Port 2 (port.number is 1)
* Byte 3 --------------
* Byte 4 FIFO status for both */
- if (length && length > 4) {
+
+ /* the above description is inverted
+ * oneukum 2007-03-14 */
+
+ if (unlikely(length != 4)) {
dbg("Wrong data !!!");
return;
}
- status = *data;
-
- sp1 = (status & 0xff000000)>>24;
- sp2 = (status & 0x00ff0000)>>16;
- st = status & 0x000000ff;
+ sp1 = data[3];
+ sp2 = data[2];
- if ((sp1 & 0x01) || (sp2 & 0x01)) {
+ if ((sp1 | sp2) & 0x01) {
/* No Interrupt Pending in both the ports */
dbg("No Interrupt !!!");
} else {
@@ -333,6 +332,7 @@ static int mos7720_open(struct usb_serial_port *port, struct file * filp)
int response;
int port_number;
char data;
+ int allocated_urbs = 0;
int j;
serial = port->serial;
@@ -353,7 +353,7 @@ static int mos7720_open(struct usb_serial_port *port, struct file * filp)
/* Initialising the write urb pool */
for (j = 0; j < NUM_URBS; ++j) {
- urb = usb_alloc_urb(0,GFP_ATOMIC);
+ urb = usb_alloc_urb(0,GFP_KERNEL);
mos7720_port->write_urb_pool[j] = urb;
if (urb == NULL) {
@@ -365,10 +365,16 @@ static int mos7720_open(struct usb_serial_port *port, struct file * filp)
GFP_KERNEL);
if (!urb->transfer_buffer) {
err("%s-out of memory for urb buffers.", __FUNCTION__);
+ usb_free_urb(mos7720_port->write_urb_pool[j]);
+ mos7720_port->write_urb_pool[j] = NULL;
continue;
}
+ allocated_urbs++;
}
+ if (!allocated_urbs)
+ return -ENOMEM;
+
/* Initialize MCS7720 -- Write Init values to corresponding Registers
*
* Register Index
@@ -526,7 +532,7 @@ static int mos7720_chars_in_buffer(struct usb_serial_port *port)
}
for (i = 0; i < NUM_URBS; ++i) {
- if (mos7720_port->write_urb_pool[i]->status == -EINPROGRESS)
+ if (mos7720_port->write_urb_pool[i] && mos7720_port->write_urb_pool[i]->status == -EINPROGRESS)
chars += URB_TRANSFER_BUFFER_SIZE;
}
dbg("%s - returns %d", __FUNCTION__, chars);
@@ -629,7 +635,7 @@ static int mos7720_write_room(struct usb_serial_port *port)
}
for (i = 0; i < NUM_URBS; ++i) {
- if (mos7720_port->write_urb_pool[i]->status != -EINPROGRESS)
+ if (mos7720_port->write_urb_pool[i] && mos7720_port->write_urb_pool[i]->status != -EINPROGRESS)
room += URB_TRANSFER_BUFFER_SIZE;
}
@@ -664,7 +670,7 @@ static int mos7720_write(struct usb_serial_port *port,
urb = NULL;
for (i = 0; i < NUM_URBS; ++i) {
- if (mos7720_port->write_urb_pool[i]->status != -EINPROGRESS) {
+ if (mos7720_port->write_urb_pool[i] && mos7720_port->write_urb_pool[i]->status != -EINPROGRESS) {
urb = mos7720_port->write_urb_pool[i];
dbg("URB:%d",i);
break;
@@ -1628,6 +1634,7 @@ static struct usb_serial_driver moschip7720_2port_driver = {
.chars_in_buffer = mos7720_chars_in_buffer,
.break_ctl = mos7720_break,
.read_bulk_callback = mos7720_bulk_in_callback,
+ .read_int_callback = mos7720_interrupt_callback,
};
static int __init moschip7720_init(void)
diff --git a/drivers/usb/serial/mos7840.c b/drivers/usb/serial/mos7840.c
index c6cca85..2366e7b 100644
--- a/drivers/usb/serial/mos7840.c
+++ b/drivers/usb/serial/mos7840.c
@@ -176,9 +176,12 @@ struct moschip_port {
int port_num; /*Actual port number in the device(1,2,etc) */
struct urb *write_urb; /* write URB for this port */
struct urb *read_urb; /* read URB for this port */
+ struct urb *int_urb;
__u8 shadowLCR; /* last LCR value received */
__u8 shadowMCR; /* last MCR value received */
char open;
+ char open_ports;
+ char zombie;
wait_queue_head_t wait_chase; /* for handling sleeping while waiting for chase to finish */
wait_queue_head_t delta_msr_wait; /* for handling sleeping while waiting for msr change to happen */
int delta_msr_cond;
@@ -191,17 +194,17 @@ struct moschip_port {
__u8 DcrRegOffset;
//for processing control URBS in interrupt context
struct urb *control_urb;
+ struct usb_ctrlrequest *dr;
char *ctrl_buf;
int MsrLsr;
+ spinlock_t pool_lock;
struct urb *write_urb_pool[NUM_URBS];
+ char busy[NUM_URBS];
};
static int debug;
-static int mos7840_num_ports; //this says the number of ports in the device
-static int mos7840_num_open_ports;
-
/*
* mos7840_set_reg_sync
@@ -254,7 +257,7 @@ static int mos7840_set_uart_reg(struct usb_serial_port *port, __u16 reg,
struct usb_device *dev = port->serial->dev;
val = val & 0x00ff;
// For the UART control registers, the application number need to be Or'ed
- if (mos7840_num_ports == 4) {
+ if (port->serial->num_ports == 4) {
val |=
(((__u16) port->number - (__u16) (port->serial->minor)) +
1) << 8;
@@ -294,7 +297,7 @@ static int mos7840_get_uart_reg(struct usb_serial_port *port, __u16 reg,
//dbg("application number is %4x \n",(((__u16)port->number - (__u16)(port->serial->minor))+1)<<8);
/*Wval is same as application number */
- if (mos7840_num_ports == 4) {
+ if (port->serial->num_ports == 4) {
Wval =
(((__u16) port->number - (__u16) (port->serial->minor)) +
1) << 8;
@@ -352,7 +355,7 @@ static inline struct moschip_port *mos7840_get_port_private(struct
return (struct moschip_port *)usb_get_serial_port_data(port);
}
-static int mos7840_handle_new_msr(struct moschip_port *port, __u8 new_msr)
+static void mos7840_handle_new_msr(struct moschip_port *port, __u8 new_msr)
{
struct moschip_port *mos7840_port;
struct async_icount *icount;
@@ -366,22 +369,24 @@ static int mos7840_handle_new_msr(struct moschip_port *port, __u8 new_msr)
/* update input line counters */
if (new_msr & MOS_MSR_DELTA_CTS) {
icount->cts++;
+ smp_wmb();
}
if (new_msr & MOS_MSR_DELTA_DSR) {
icount->dsr++;
+ smp_wmb();
}
if (new_msr & MOS_MSR_DELTA_CD) {
icount->dcd++;
+ smp_wmb();
}
if (new_msr & MOS_MSR_DELTA_RI) {
icount->rng++;
+ smp_wmb();
}
}
-
- return 0;
}
-static int mos7840_handle_new_lsr(struct moschip_port *port, __u8 new_lsr)
+static void mos7840_handle_new_lsr(struct moschip_port *port, __u8 new_lsr)
{
struct async_icount *icount;
@@ -400,18 +405,20 @@ static int mos7840_handle_new_lsr(struct moschip_port *port, __u8 new_lsr)
icount = &port->icount;
if (new_lsr & SERIAL_LSR_BI) {
icount->brk++;
+ smp_wmb();
}
if (new_lsr & SERIAL_LSR_OE) {
icount->overrun++;
+ smp_wmb();
}
if (new_lsr & SERIAL_LSR_PE) {
icount->parity++;
+ smp_wmb();
}
if (new_lsr & SERIAL_LSR_FE) {
icount->frame++;
+ smp_wmb();
}
-
- return 0;
}
/************************************************************************/
@@ -426,12 +433,15 @@ static void mos7840_control_callback(struct urb *urb)
unsigned char *data;
struct moschip_port *mos7840_port;
__u8 regval = 0x0;
+ int result = 0;
if (!urb) {
dbg("%s", "Invalid Pointer !!!!:\n");
return;
}
+ mos7840_port = (struct moschip_port *)urb->context;
+
switch (urb->status) {
case 0:
/* success */
@@ -449,8 +459,6 @@ static void mos7840_control_callback(struct urb *urb)
goto exit;
}
- mos7840_port = (struct moschip_port *)urb->context;
-
dbg("%s urb buffer size is %d\n", __FUNCTION__, urb->actual_length);
dbg("%s mos7840_port->MsrLsr is %d port %d\n", __FUNCTION__,
mos7840_port->MsrLsr, mos7840_port->port_num);
@@ -462,21 +470,26 @@ static void mos7840_control_callback(struct urb *urb)
else if (mos7840_port->MsrLsr == 1)
mos7840_handle_new_lsr(mos7840_port, regval);
- exit:
- return;
+exit:
+ spin_lock(&mos7840_port->pool_lock);
+ if (!mos7840_port->zombie)
+ result = usb_submit_urb(mos7840_port->int_urb, GFP_ATOMIC);
+ spin_unlock(&mos7840_port->pool_lock);
+ if (result) {
+ dev_err(&urb->dev->dev,
+ "%s - Error %d submitting interrupt urb\n",
+ __FUNCTION__, result);
+ }
}
static int mos7840_get_reg(struct moschip_port *mcs, __u16 Wval, __u16 reg,
__u16 * val)
{
struct usb_device *dev = mcs->port->serial->dev;
- struct usb_ctrlrequest *dr = NULL;
- unsigned char *buffer = NULL;
- int ret = 0;
- buffer = (__u8 *) mcs->ctrl_buf;
+ struct usb_ctrlrequest *dr = mcs->dr;
+ unsigned char *buffer = mcs->ctrl_buf;
+ int ret;
-// dr=(struct usb_ctrlrequest *)(buffer);
- dr = (void *)(buffer + 2);
dr->bRequestType = MCS_RD_RTYPE;
dr->bRequest = MCS_RDREQ;
dr->wValue = cpu_to_le16(Wval); //0;
@@ -506,8 +519,8 @@ static void mos7840_interrupt_callback(struct urb *urb)
__u16 Data;
unsigned char *data;
__u8 sp[5], st;
- int i;
- __u16 wval;
+ int i, rv = 0;
+ __u16 wval, wreg = 0;
dbg("%s", " : Entering\n");
if (!urb) {
@@ -569,31 +582,34 @@ static void mos7840_interrupt_callback(struct urb *urb)
dbg("Serial Port %d: Receiver status error or ", i);
dbg("address bit detected in 9-bit mode\n");
mos7840_port->MsrLsr = 1;
- mos7840_get_reg(mos7840_port, wval,
- LINE_STATUS_REGISTER,
- &Data);
+ wreg = LINE_STATUS_REGISTER;
break;
case SERIAL_IIR_MS:
dbg("Serial Port %d: Modem status change\n", i);
mos7840_port->MsrLsr = 0;
- mos7840_get_reg(mos7840_port, wval,
- MODEM_STATUS_REGISTER,
- &Data);
+ wreg = MODEM_STATUS_REGISTER;
break;
}
+ spin_lock(&mos7840_port->pool_lock);
+ if (!mos7840_port->zombie) {
+ rv = mos7840_get_reg(mos7840_port, wval, wreg, &Data);
+ } else {
+ spin_unlock(&mos7840_port->pool_lock);
+ return;
+ }
+ spin_unlock(&mos7840_port->pool_lock);
}
}
}
- exit:
+ if (!(rv < 0)) /* the completion handler for the control urb will resubmit */
+ return;
+exit:
result = usb_submit_urb(urb, GFP_ATOMIC);
if (result) {
dev_err(&urb->dev->dev,
"%s - Error %d submitting interrupt urb\n",
__FUNCTION__, result);
}
-
- return;
-
}
static int mos7840_port_paranoia_check(struct usb_serial_port *port,
@@ -634,7 +650,8 @@ static struct usb_serial *mos7840_get_usb_serial(struct usb_serial_port *port,
if (!port ||
mos7840_port_paranoia_check(port, function) ||
mos7840_serial_paranoia_check(port->serial, function)) {
- /* then say that we don't have a valid usb_serial thing, which will * end up genrating -ENODEV return values */
+ /* then say that we don't have a valid usb_serial thing, which will
+ * end up genrating -ENODEV return values */
return NULL;
}
@@ -699,6 +716,7 @@ static void mos7840_bulk_in_callback(struct urb *urb)
tty_flip_buffer_push(tty);
}
mos7840_port->icount.rx += urb->actual_length;
+ smp_wmb();
dbg("mos7840_port->icount.rx is %d:\n",
mos7840_port->icount.rx);
}
@@ -708,15 +726,14 @@ static void mos7840_bulk_in_callback(struct urb *urb)
return;
}
- if (mos7840_port->read_urb->status != -EINPROGRESS) {
- mos7840_port->read_urb->dev = serial->dev;
- status = usb_submit_urb(mos7840_port->read_urb, GFP_ATOMIC);
+ mos7840_port->read_urb->dev = serial->dev;
- if (status) {
- dbg(" usb_submit_urb(read bulk) failed, status = %d",
- status);
- }
+ status = usb_submit_urb(mos7840_port->read_urb, GFP_ATOMIC);
+
+ if (status) {
+ dbg(" usb_submit_urb(read bulk) failed, status = %d",
+ status);
}
}
@@ -730,17 +747,28 @@ static void mos7840_bulk_out_data_callback(struct urb *urb)
{
struct moschip_port *mos7840_port;
struct tty_struct *tty;
+ int i;
+
if (!urb) {
dbg("%s", "Invalid Pointer !!!!:\n");
return;
}
+ mos7840_port = (struct moschip_port *)urb->context;
+ spin_lock(&mos7840_port->pool_lock);
+ for (i = 0; i < NUM_URBS; i++) {
+ if (urb == mos7840_port->write_urb_pool[i]) {
+ mos7840_port->busy[i] = 0;
+ break;
+ }
+ }
+ spin_unlock(&mos7840_port->pool_lock);
+
if (urb->status) {
dbg("nonzero write bulk status received:%d\n", urb->status);
return;
}
- mos7840_port = (struct moschip_port *)urb->context;
if (!mos7840_port) {
dbg("%s", "NULL mos7840_port pointer \n");
return;
@@ -792,13 +820,13 @@ static int mos7840_open(struct usb_serial_port *port, struct file *filp)
__u16 Data;
int status;
struct moschip_port *mos7840_port;
+ struct moschip_port *port0;
if (mos7840_port_paranoia_check(port, __FUNCTION__)) {
dbg("%s", "Port Paranoia failed \n");
return -ENODEV;
}
- mos7840_num_open_ports++;
serial = port->serial;
if (mos7840_serial_paranoia_check(serial, __FUNCTION__)) {
@@ -807,16 +835,18 @@ static int mos7840_open(struct usb_serial_port *port, struct file *filp)
}
mos7840_port = mos7840_get_port_private(port);
+ port0 = mos7840_get_port_private(serial->port[0]);
- if (mos7840_port == NULL)
+ if (mos7840_port == NULL || port0 == NULL)
return -ENODEV;
usb_clear_halt(serial->dev, port->write_urb->pipe);
usb_clear_halt(serial->dev, port->read_urb->pipe);
+ port0->open_ports++;
/* Initialising the write urb pool */
for (j = 0; j < NUM_URBS; ++j) {
- urb = usb_alloc_urb(0, GFP_ATOMIC);
+ urb = usb_alloc_urb(0, GFP_KERNEL);
mos7840_port->write_urb_pool[j] = urb;
if (urb == NULL) {
@@ -824,10 +854,10 @@ static int mos7840_open(struct usb_serial_port *port, struct file *filp)
continue;
}
- urb->transfer_buffer = NULL;
- urb->transfer_buffer =
- kmalloc(URB_TRANSFER_BUFFER_SIZE, GFP_KERNEL);
+ urb->transfer_buffer = kmalloc(URB_TRANSFER_BUFFER_SIZE, GFP_KERNEL);
if (!urb->transfer_buffer) {
+ usb_free_urb(urb);
+ mos7840_port->write_urb_pool[j] = NULL;
err("%s-out of memory for urb buffers.", __FUNCTION__);
continue;
}
@@ -879,9 +909,7 @@ static int mos7840_open(struct usb_serial_port *port, struct file *filp)
}
Data |= 0x08; //Driver done bit
Data |= 0x20; //rx_disable
- status = 0;
- status =
- mos7840_set_reg_sync(port, mos7840_port->ControlRegOffset, Data);
+ status = mos7840_set_reg_sync(port, mos7840_port->ControlRegOffset, Data);
if (status < 0) {
dbg("writing Controlreg failed\n");
return -1;
@@ -893,7 +921,6 @@ static int mos7840_open(struct usb_serial_port *port, struct file *filp)
////////////////////////////////////
Data = 0x00;
- status = 0;
status = mos7840_set_uart_reg(port, INTERRUPT_ENABLE_REGISTER, Data);
if (status < 0) {
dbg("disableing interrupts failed\n");
@@ -901,7 +928,6 @@ static int mos7840_open(struct usb_serial_port *port, struct file *filp)
}
// Set FIFO_CONTROL_REGISTER to the default value
Data = 0x00;
- status = 0;
status = mos7840_set_uart_reg(port, FIFO_CONTROL_REGISTER, Data);
if (status < 0) {
dbg("Writing FIFO_CONTROL_REGISTER failed\n");
@@ -909,7 +935,6 @@ static int mos7840_open(struct usb_serial_port *port, struct file *filp)
}
Data = 0xcf;
- status = 0;
status = mos7840_set_uart_reg(port, FIFO_CONTROL_REGISTER, Data);
if (status < 0) {
dbg("Writing FIFO_CONTROL_REGISTER failed\n");
@@ -917,22 +942,18 @@ static int mos7840_open(struct usb_serial_port *port, struct file *filp)
}
Data = 0x03;
- status = 0;
status = mos7840_set_uart_reg(port, LINE_CONTROL_REGISTER, Data);
mos7840_port->shadowLCR = Data;
Data = 0x0b;
- status = 0;
status = mos7840_set_uart_reg(port, MODEM_CONTROL_REGISTER, Data);
mos7840_port->shadowMCR = Data;
Data = 0x00;
- status = 0;
status = mos7840_get_uart_reg(port, LINE_CONTROL_REGISTER, &Data);
mos7840_port->shadowLCR = Data;
Data |= SERIAL_LCR_DLAB; //data latch enable in LCR 0x80
- status = 0;
status = mos7840_set_uart_reg(port, LINE_CONTROL_REGISTER, Data);
Data = 0x0c;
@@ -999,7 +1020,7 @@ static int mos7840_open(struct usb_serial_port *port, struct file *filp)
/* Check to see if we've set up our endpoint info yet *
* (can't set it up in mos7840_startup as the structures *
* were not set up at that time.) */
- if (mos7840_num_open_ports == 1) {
+ if (port0->open_ports == 1) {
if (serial->port[0]->interrupt_in_buffer == NULL) {
/* set up interrupt urb */
@@ -1097,6 +1118,7 @@ static int mos7840_chars_in_buffer(struct usb_serial_port *port)
{
int i;
int chars = 0;
+ unsigned long flags;
struct moschip_port *mos7840_port;
dbg("%s \n", " mos7840_chars_in_buffer:entering ...........");
@@ -1112,13 +1134,15 @@ static int mos7840_chars_in_buffer(struct usb_serial_port *port)
return -1;
}
+ spin_lock_irqsave(&mos7840_port->pool_lock,flags);
for (i = 0; i < NUM_URBS; ++i) {
- if (mos7840_port->write_urb_pool[i]->status == -EINPROGRESS) {
+ if (mos7840_port->busy[i]) {
chars += URB_TRANSFER_BUFFER_SIZE;
}
}
+ spin_unlock_irqrestore(&mos7840_port->pool_lock,flags);
dbg("%s - returns %d", __FUNCTION__, chars);
- return (chars);
+ return chars;
}
@@ -1172,6 +1196,7 @@ static void mos7840_close(struct usb_serial_port *port, struct file *filp)
{
struct usb_serial *serial;
struct moschip_port *mos7840_port;
+ struct moschip_port *port0;
int j;
__u16 Data;
@@ -1189,10 +1214,10 @@ static void mos7840_close(struct usb_serial_port *port, struct file *filp)
}
mos7840_port = mos7840_get_port_private(port);
+ port0 = mos7840_get_port_private(serial->port[0]);
- if (mos7840_port == NULL) {
+ if (mos7840_port == NULL || port0 == NULL)
return;
- }
for (j = 0; j < NUM_URBS; ++j)
usb_kill_urb(mos7840_port->write_urb_pool[j]);
@@ -1234,12 +1259,13 @@ static void mos7840_close(struct usb_serial_port *port, struct file *filp)
}
// if(mos7840_port->ctrl_buf != NULL)
// kfree(mos7840_port->ctrl_buf);
- mos7840_num_open_ports--;
+ port0->open_ports--;
dbg("mos7840_num_open_ports in close%d:in port%d\n",
- mos7840_num_open_ports, port->number);
- if (mos7840_num_open_ports == 0) {
+ port0->open_ports, port->number);
+ if (port0->open_ports == 0) {
if (serial->port[0]->interrupt_in_urb) {
dbg("%s", "Shutdown interrupt_in_urb\n");
+ usb_kill_urb(serial->port[0]->interrupt_in_urb);
}
}
@@ -1368,6 +1394,7 @@ static int mos7840_write_room(struct usb_serial_port *port)
{
int i;
int room = 0;
+ unsigned long flags;
struct moschip_port *mos7840_port;
dbg("%s \n", " mos7840_write_room:entering ...........");
@@ -1384,14 +1411,17 @@ static int mos7840_write_room(struct usb_serial_port *port)
return -1;
}
+ spin_lock_irqsave(&mos7840_port->pool_lock, flags);
for (i = 0; i < NUM_URBS; ++i) {
- if (mos7840_port->write_urb_pool[i]->status != -EINPROGRESS) {
+ if (!mos7840_port->busy[i]) {
room += URB_TRANSFER_BUFFER_SIZE;
}
}
+ spin_unlock_irqrestore(&mos7840_port->pool_lock, flags);
+ room = (room == 0) ? 0 : room - URB_TRANSFER_BUFFER_SIZE + 1;
dbg("%s - returns %d", __FUNCTION__, room);
- return (room);
+ return room;
}
@@ -1410,6 +1440,7 @@ static int mos7840_write(struct usb_serial_port *port,
int i;
int bytes_sent = 0;
int transfer_size;
+ unsigned long flags;
struct moschip_port *mos7840_port;
struct usb_serial *serial;
@@ -1476,13 +1507,16 @@ static int mos7840_write(struct usb_serial_port *port,
/* try to find a free urb in the list */
urb = NULL;
+ spin_lock_irqsave(&mos7840_port->pool_lock, flags);
for (i = 0; i < NUM_URBS; ++i) {
- if (mos7840_port->write_urb_pool[i]->status != -EINPROGRESS) {
+ if (!mos7840_port->busy[i]) {
+ mos7840_port->busy[i] = 1;
urb = mos7840_port->write_urb_pool[i];
dbg("\nURB:%d", i);
break;
}
}
+ spin_unlock_irqrestore(&mos7840_port->pool_lock, flags);
if (urb == NULL) {
dbg("%s - no more free urbs", __FUNCTION__);
@@ -1518,6 +1552,7 @@ static int mos7840_write(struct usb_serial_port *port,
status = usb_submit_urb(urb, GFP_ATOMIC);
if (status) {
+ mos7840_port->busy[i] = 0;
err("%s - usb_submit_urb(write bulk) failed with status = %d",
__FUNCTION__, status);
bytes_sent = status;
@@ -1525,6 +1560,7 @@ static int mos7840_write(struct usb_serial_port *port,
}
bytes_sent = transfer_size;
mos7840_port->icount.tx += transfer_size;
+ smp_wmb();
dbg("mos7840_port->icount.tx is %d:\n", mos7840_port->icount.tx);
exit:
@@ -2490,6 +2526,7 @@ static int mos7840_ioctl(struct usb_serial_port *port, struct file *file,
if (signal_pending(current))
return -ERESTARTSYS;
cnow = mos7840_port->icount;
+ smp_rmb();
if (cnow.rng == cprev.rng && cnow.dsr == cprev.dsr &&
cnow.dcd == cprev.dcd && cnow.cts == cprev.cts)
return -EIO; /* no change => error */
@@ -2506,6 +2543,7 @@ static int mos7840_ioctl(struct usb_serial_port *port, struct file *file,
case TIOCGICOUNT:
cnow = mos7840_port->icount;
+ smp_rmb();
icount.cts = cnow.cts;
icount.dsr = cnow.dsr;
icount.rng = cnow.rng;
@@ -2535,19 +2573,18 @@ static int mos7840_ioctl(struct usb_serial_port *port, struct file *file,
static int mos7840_calc_num_ports(struct usb_serial *serial)
{
+ int mos7840_num_ports = 0;
dbg("numberofendpoints: %d \n",
(int)serial->interface->cur_altsetting->desc.bNumEndpoints);
dbg("numberofendpoints: %d \n",
(int)serial->interface->altsetting->desc.bNumEndpoints);
if (serial->interface->cur_altsetting->desc.bNumEndpoints == 5) {
- mos7840_num_ports = 2;
- serial->type->num_ports = 2;
+ mos7840_num_ports = serial->num_ports = 2;
} else if (serial->interface->cur_altsetting->desc.bNumEndpoints == 9) {
- mos7840_num_ports = 4;
- serial->type->num_bulk_in = 4;
- serial->type->num_bulk_out = 4;
- serial->type->num_ports = 4;
+ serial->num_bulk_in = 4;
+ serial->num_bulk_out = 4;
+ mos7840_num_ports = serial->num_ports = 4;
}
return mos7840_num_ports;
@@ -2583,7 +2620,9 @@ static int mos7840_startup(struct usb_serial *serial)
mos7840_port = kzalloc(sizeof(struct moschip_port), GFP_KERNEL);
if (mos7840_port == NULL) {
err("%s - Out of memory", __FUNCTION__);
- return -ENOMEM;
+ status = -ENOMEM;
+ i--; /* don't follow NULL pointer cleaning up */
+ goto error;
}
/* Initialize all port interrupt end point to port 0 int endpoint *
@@ -2591,6 +2630,7 @@ static int mos7840_startup(struct usb_serial *serial)
mos7840_port->port = serial->port[i];
mos7840_set_port_private(serial->port[i], mos7840_port);
+ spin_lock_init(&mos7840_port->pool_lock);
mos7840_port->port_num = ((serial->port[i]->number -
(serial->port[i]->serial->minor)) +
@@ -2601,22 +2641,22 @@ static int mos7840_startup(struct usb_serial *serial)
mos7840_port->ControlRegOffset = 0x1;
mos7840_port->DcrRegOffset = 0x4;
} else if ((mos7840_port->port_num == 2)
- && (mos7840_num_ports == 4)) {
+ && (serial->num_ports == 4)) {
mos7840_port->SpRegOffset = 0x8;
mos7840_port->ControlRegOffset = 0x9;
mos7840_port->DcrRegOffset = 0x16;
} else if ((mos7840_port->port_num == 2)
- && (mos7840_num_ports == 2)) {
+ && (serial->num_ports == 2)) {
mos7840_port->SpRegOffset = 0xa;
mos7840_port->ControlRegOffset = 0xb;
mos7840_port->DcrRegOffset = 0x19;
} else if ((mos7840_port->port_num == 3)
- && (mos7840_num_ports == 4)) {
+ && (serial->num_ports == 4)) {
mos7840_port->SpRegOffset = 0xa;
mos7840_port->ControlRegOffset = 0xb;
mos7840_port->DcrRegOffset = 0x19;
} else if ((mos7840_port->port_num == 4)
- && (mos7840_num_ports == 4)) {
+ && (serial->num_ports == 4)) {
mos7840_port->SpRegOffset = 0xc;
mos7840_port->ControlRegOffset = 0xd;
mos7840_port->DcrRegOffset = 0x1c;
@@ -2701,21 +2741,19 @@ static int mos7840_startup(struct usb_serial *serial)
dbg("CLK_START_VALUE_REGISTER Writing success status%d\n", status);
Data = 0x20;
- status = 0;
status =
mos7840_set_reg_sync(serial->port[i], CLK_MULTI_REGISTER,
Data);
if (status < 0) {
dbg("Writing CLK_MULTI_REGISTER failed status-0x%x\n",
status);
- break;
+ goto error;
} else
dbg("CLK_MULTI_REGISTER Writing success status%d\n",
status);
//write value 0x0 to scratchpad register
Data = 0x00;
- status = 0;
status =
mos7840_set_uart_reg(serial->port[i], SCRATCH_PAD_REGISTER,
Data);
@@ -2729,7 +2767,7 @@ static int mos7840_startup(struct usb_serial *serial)
//Zero Length flag register
if ((mos7840_port->port_num != 1)
- && (mos7840_num_ports == 2)) {
+ && (serial->num_ports == 2)) {
Data = 0xff;
status = 0;
@@ -2770,14 +2808,17 @@ static int mos7840_startup(struct usb_serial *serial)
i + 1, status);
}
- mos7840_port->control_urb = usb_alloc_urb(0, GFP_ATOMIC);
+ mos7840_port->control_urb = usb_alloc_urb(0, GFP_KERNEL);
mos7840_port->ctrl_buf = kmalloc(16, GFP_KERNEL);
-
+ mos7840_port->dr = kmalloc(sizeof(struct usb_ctrlrequest), GFP_KERNEL);
+ if (!mos7840_port->control_urb || !mos7840_port->ctrl_buf || !mos7840_port->dr) {
+ status = -ENOMEM;
+ goto error;
+ }
}
//Zero Length flag enable
Data = 0x0f;
- status = 0;
status = mos7840_set_reg_sync(serial->port[0], ZLP_REG5, Data);
if (status < 0) {
dbg("Writing ZLP_REG5 failed status-0x%x\n", status);
@@ -2789,6 +2830,17 @@ static int mos7840_startup(struct usb_serial *serial)
usb_control_msg(serial->dev, usb_sndctrlpipe(serial->dev, 0),
(__u8) 0x03, 0x00, 0x01, 0x00, NULL, 0x00, 5 * HZ);
return 0;
+error:
+ for (/* nothing */; i >= 0; i--) {
+ mos7840_port = mos7840_get_port_private(serial->port[i]);
+
+ kfree(mos7840_port->dr);
+ kfree(mos7840_port->ctrl_buf);
+ usb_free_urb(mos7840_port->control_urb);
+ kfree(mos7840_port);
+ serial->port[i] = NULL;
+ }
+ return status;
}
/****************************************************************************
@@ -2799,6 +2851,7 @@ static int mos7840_startup(struct usb_serial *serial)
static void mos7840_shutdown(struct usb_serial *serial)
{
int i;
+ unsigned long flags;
struct moschip_port *mos7840_port;
dbg("%s \n", " shutdown :entering..........");
@@ -2814,8 +2867,12 @@ static void mos7840_shutdown(struct usb_serial *serial)
for (i = 0; i < serial->num_ports; ++i) {
mos7840_port = mos7840_get_port_private(serial->port[i]);
- kfree(mos7840_port->ctrl_buf);
+ spin_lock_irqsave(&mos7840_port->pool_lock, flags);
+ mos7840_port->zombie = 1;
+ spin_unlock_irqrestore(&mos7840_port->pool_lock, flags);
usb_kill_urb(mos7840_port->control_urb);
+ kfree(mos7840_port->ctrl_buf);
+ kfree(mos7840_port->dr);
kfree(mos7840_port);
mos7840_set_port_private(serial->port[i], NULL);
}
diff --git a/drivers/usb/serial/omninet.c b/drivers/usb/serial/omninet.c
index 0216ac1..4adfab9 100644
--- a/drivers/usb/serial/omninet.c
+++ b/drivers/usb/serial/omninet.c
@@ -69,6 +69,7 @@ static void omninet_write_bulk_callback (struct urb *urb);
static int omninet_write (struct usb_serial_port *port, const unsigned char *buf, int count);
static int omninet_write_room (struct usb_serial_port *port);
static void omninet_shutdown (struct usb_serial *serial);
+static int omninet_attach (struct usb_serial *serial);
static struct usb_device_id id_table [] = {
{ USB_DEVICE(ZYXEL_VENDOR_ID, ZYXEL_OMNINET_ID) },
@@ -99,6 +100,7 @@ static struct usb_serial_driver zyxel_omninet_device = {
.num_bulk_in = 1,
.num_bulk_out = 2,
.num_ports = 1,
+ .attach = omninet_attach,
.open = omninet_open,
.close = omninet_close,
.write = omninet_write,
@@ -145,22 +147,30 @@ struct omninet_data
__u8 od_outseq; // Sequence number for bulk_out URBs
};
+static int omninet_attach (struct usb_serial *serial)
+{
+ struct omninet_data *od;
+ struct usb_serial_port *port = serial->port[0];
+
+ od = kmalloc( sizeof(struct omninet_data), GFP_KERNEL );
+ if( !od ) {
+ err("%s- kmalloc(%Zd) failed.", __FUNCTION__, sizeof(struct omninet_data));
+ return -ENOMEM;
+ }
+ usb_set_serial_port_data(port, od);
+ return 0;
+}
+
static int omninet_open (struct usb_serial_port *port, struct file *filp)
{
struct usb_serial *serial = port->serial;
struct usb_serial_port *wport;
- struct omninet_data *od;
+ struct omninet_data *od = usb_get_serial_port_data(port);
int result = 0;
dbg("%s - port %d", __FUNCTION__, port->number);
od = kmalloc( sizeof(struct omninet_data), GFP_KERNEL );
- if( !od ) {
- err("%s- kmalloc(%Zd) failed.", __FUNCTION__, sizeof(struct omninet_data));
- return -ENOMEM;
- }
-
- usb_set_serial_port_data(port, od);
wport = serial->port[1];
wport->tty = port->tty;
@@ -170,24 +180,17 @@ static int omninet_open (struct usb_serial_port *port, struct file *filp)
port->read_urb->transfer_buffer, port->read_urb->transfer_buffer_length,
omninet_read_bulk_callback, port);
result = usb_submit_urb(port->read_urb, GFP_KERNEL);
- if (result)
+ if (result) {
err("%s - failed submitting read urb, error %d", __FUNCTION__, result);
+ }
return result;
}
static void omninet_close (struct usb_serial_port *port, struct file * filp)
{
- struct usb_serial *serial = port->serial;
- struct usb_serial_port *wport;
-
dbg("%s - port %d", __FUNCTION__, port->number);
-
- wport = serial->port[1];
- usb_kill_urb(wport->write_urb);
usb_kill_urb(port->read_urb);
-
- kfree(usb_get_serial_port_data(port));
}
@@ -326,7 +329,12 @@ static void omninet_write_bulk_callback (struct urb *urb)
static void omninet_shutdown (struct usb_serial *serial)
{
+ struct usb_serial_port *wport = serial->port[1];
+ struct usb_serial_port *port = serial->port[0];
dbg ("%s", __FUNCTION__);
+
+ usb_kill_urb(wport->write_urb);
+ kfree(usb_get_serial_port_data(port));
}
diff --git a/drivers/usb/serial/option.c b/drivers/usb/serial/option.c
index db92a7f..8c3f55b 100644
--- a/drivers/usb/serial/option.c
+++ b/drivers/usb/serial/option.c
@@ -109,11 +109,16 @@ static int option_send_setup(struct usb_serial_port *port);
#define HUAWEI_PRODUCT_E220 0x1003
#define NOVATELWIRELESS_VENDOR_ID 0x1410
-#define NOVATELWIRELESS_PRODUCT_U740 0x1400
#define ANYDATA_VENDOR_ID 0x16d5
#define ANYDATA_PRODUCT_ID 0x6501
+#define BANDRICH_VENDOR_ID 0x1A8D
+#define BANDRICH_PRODUCT_C100_1 0x1002
+#define BANDRICH_PRODUCT_C100_2 0x1003
+
+#define DELL_VENDOR_ID 0x413C
+
static struct usb_device_id option_ids[] = {
{ USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_COLT) },
{ USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_RICOLA) },
@@ -152,8 +157,23 @@ static struct usb_device_id option_ids[] = {
{ USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_ETNA_KOI_NETWORK) },
{ USB_DEVICE(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E600) },
{ USB_DEVICE(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E220) },
- { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID,NOVATELWIRELESS_PRODUCT_U740) },
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x1100) }, /* Novatel Merlin XS620/S640 */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x1110) }, /* Novatel Merlin S620 */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x1120) }, /* Novatel Merlin EX720 */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x1130) }, /* Novatel Merlin S720 */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x1400) }, /* Novatel U730 */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x1410) }, /* Novatel U740 */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x1420) }, /* Novatel EU870 */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x1430) }, /* Novatel Merlin XU870 HSDPA/3G */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x1430) }, /* Novatel XU870 */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x2100) }, /* Novatel EV620 CDMA/EV-DO */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x2110) }, /* Novatel Merlin ES620 / Merlin ES720 / Ovation U720 */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x2130) }, /* Novatel Merlin ES620 SM Bus */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, 0x2410) }, /* Novatel EU740 */
{ USB_DEVICE(ANYDATA_VENDOR_ID, ANYDATA_PRODUCT_ID) },
+ { USB_DEVICE(BANDRICH_VENDOR_ID, BANDRICH_PRODUCT_C100_1) },
+ { USB_DEVICE(BANDRICH_VENDOR_ID, BANDRICH_PRODUCT_C100_2) },
+ { USB_DEVICE(DELL_VENDOR_ID, 0x8118) }, /* Dell Wireless 5510 Mobile Broadband HSDPA ExpressCard */
{ } /* Terminating entry */
};
MODULE_DEVICE_TABLE(usb, option_ids);
@@ -580,12 +600,6 @@ static int option_open(struct usb_serial_port *port, struct file *filp)
return (0);
}
-static inline void stop_urb(struct urb *urb)
-{
- if (urb && urb->status == -EINPROGRESS)
- usb_kill_urb(urb);
-}
-
static void option_close(struct usb_serial_port *port, struct file *filp)
{
int i;
@@ -603,9 +617,9 @@ static void option_close(struct usb_serial_port *port, struct file *filp)
/* Stop reading/writing urbs */
for (i = 0; i < N_IN_URB; i++)
- stop_urb(portdata->in_urbs[i]);
+ usb_kill_urb(portdata->in_urbs[i]);
for (i = 0; i < N_OUT_URB; i++)
- stop_urb(portdata->out_urbs[i]);
+ usb_kill_urb(portdata->out_urbs[i]);
}
port->tty = NULL;
}
@@ -736,9 +750,9 @@ static void option_shutdown(struct usb_serial *serial)
port = serial->port[i];
portdata = usb_get_serial_port_data(port);
for (j = 0; j < N_IN_URB; j++)
- stop_urb(portdata->in_urbs[j]);
+ usb_kill_urb(portdata->in_urbs[j]);
for (j = 0; j < N_OUT_URB; j++)
- stop_urb(portdata->out_urbs[j]);
+ usb_kill_urb(portdata->out_urbs[j]);
}
/* Now free them */
diff --git a/drivers/usb/serial/sierra.c b/drivers/usb/serial/sierra.c
index ecedd83..644607d 100644
--- a/drivers/usb/serial/sierra.c
+++ b/drivers/usb/serial/sierra.c
@@ -456,12 +456,6 @@ static int sierra_open(struct usb_serial_port *port, struct file *filp)
return (0);
}
-static inline void stop_urb(struct urb *urb)
-{
- if (urb && urb->status == -EINPROGRESS)
- usb_kill_urb(urb);
-}
-
static void sierra_close(struct usb_serial_port *port, struct file *filp)
{
int i;
@@ -479,9 +473,9 @@ static void sierra_close(struct usb_serial_port *port, struct file *filp)
/* Stop reading/writing urbs */
for (i = 0; i < N_IN_URB; i++)
- stop_urb(portdata->in_urbs[i]);
+ usb_unlink_urb(portdata->in_urbs[i]);
for (i = 0; i < N_OUT_URB; i++)
- stop_urb(portdata->out_urbs[i]);
+ usb_unlink_urb(portdata->out_urbs[i]);
}
port->tty = NULL;
}
@@ -583,17 +577,26 @@ static void sierra_shutdown(struct usb_serial *serial)
/* Stop reading/writing urbs */
for (i = 0; i < serial->num_ports; ++i) {
port = serial->port[i];
+ if (!port)
+ continue;
portdata = usb_get_serial_port_data(port);
+ if (!portdata)
+ continue;
+
for (j = 0; j < N_IN_URB; j++)
- stop_urb(portdata->in_urbs[j]);
+ usb_unlink_urb(portdata->in_urbs[j]);
for (j = 0; j < N_OUT_URB; j++)
- stop_urb(portdata->out_urbs[j]);
+ usb_unlink_urb(portdata->out_urbs[j]);
}
/* Now free them */
for (i = 0; i < serial->num_ports; ++i) {
port = serial->port[i];
+ if (!port)
+ continue;
portdata = usb_get_serial_port_data(port);
+ if (!portdata)
+ continue;
for (j = 0; j < N_IN_URB; j++) {
if (portdata->in_urbs[j]) {
@@ -612,6 +615,8 @@ static void sierra_shutdown(struct usb_serial *serial)
/* Now free per port private data */
for (i = 0; i < serial->num_ports; i++) {
port = serial->port[i];
+ if (!port)
+ continue;
kfree(usb_get_serial_port_data(port));
}
}
diff --git a/drivers/usb/serial/usb-serial.c b/drivers/usb/serial/usb-serial.c
index 6bf22a2..87f3788 100644
--- a/drivers/usb/serial/usb-serial.c
+++ b/drivers/usb/serial/usb-serial.c
@@ -28,7 +28,6 @@
#include <linux/spinlock.h>
#include <linux/mutex.h>
#include <linux/list.h>
-#include <linux/smp_lock.h>
#include <asm/uaccess.h>
#include <linux/usb.h>
#include <linux/usb/serial.h>
@@ -99,9 +98,12 @@ static struct usb_serial *get_free_serial (struct usb_serial *serial, int num_po
continue;
*minor = i;
+ j = 0;
dbg("%s - minor base = %d", __FUNCTION__, *minor);
- for (i = *minor; (i < (*minor + num_ports)) && (i < SERIAL_TTY_MINORS); ++i)
+ for (i = *minor; (i < (*minor + num_ports)) && (i < SERIAL_TTY_MINORS); ++i) {
serial_table[i] = serial;
+ serial->port[j++]->number = i;
+ }
spin_unlock(&table_lock);
return serial;
}
@@ -826,7 +828,6 @@ int usb_serial_probe(struct usb_interface *interface,
num_ports = type->num_ports;
}
- serial->minor = minor;
serial->num_ports = num_ports;
serial->num_bulk_in = num_bulk_in;
serial->num_bulk_out = num_bulk_out;
@@ -847,7 +848,6 @@ int usb_serial_probe(struct usb_interface *interface,
port = kzalloc(sizeof(struct usb_serial_port), GFP_KERNEL);
if (!port)
goto probe_error;
- port->number = i + serial->minor;
port->serial = serial;
spin_lock_init(&port->lock);
mutex_init(&port->mutex);
@@ -980,6 +980,7 @@ int usb_serial_probe(struct usb_interface *interface,
dev_err(&interface->dev, "No more free serial devices\n");
goto probe_error;
}
+ serial->minor = minor;
/* register all of the individual ports with the driver core */
for (i = 0; i < num_ports; ++i) {
@@ -1034,9 +1035,6 @@ probe_error:
kfree(port->interrupt_out_buffer);
}
- /* return the minor range that this device had */
- return_serial (serial);
-
/* free up any memory that we allocated */
for (i = 0; i < serial->num_port_pointers; ++i)
kfree(serial->port[i]);
diff --git a/drivers/usb/serial/visor.c b/drivers/usb/serial/visor.c
index 2f59ff2..ffbe601 100644
--- a/drivers/usb/serial/visor.c
+++ b/drivers/usb/serial/visor.c
@@ -384,19 +384,21 @@ static int visor_write (struct usb_serial_port *port, const unsigned char *buf,
dbg("%s - write limit hit\n", __FUNCTION__);
return 0;
}
+ priv->outstanding_urbs++;
spin_unlock_irqrestore(&priv->lock, flags);
buffer = kmalloc (count, GFP_ATOMIC);
if (!buffer) {
dev_err(&port->dev, "out of memory\n");
- return -ENOMEM;
+ count = -ENOMEM;
+ goto error_no_buffer;
}
urb = usb_alloc_urb(0, GFP_ATOMIC);
if (!urb) {
dev_err(&port->dev, "no more free urbs\n");
- kfree (buffer);
- return -ENOMEM;
+ count = -ENOMEM;
+ goto error_no_urb;
}
memcpy (buffer, buf, count);
@@ -415,19 +417,27 @@ static int visor_write (struct usb_serial_port *port, const unsigned char *buf,
dev_err(&port->dev, "%s - usb_submit_urb(write bulk) failed with status = %d\n",
__FUNCTION__, status);
count = status;
- kfree (buffer);
+ goto error;
} else {
spin_lock_irqsave(&priv->lock, flags);
- ++priv->outstanding_urbs;
priv->bytes_out += count;
spin_unlock_irqrestore(&priv->lock, flags);
}
/* we are done with this urb, so let the host driver
* really free it when it is finished with it */
- usb_free_urb (urb);
+ usb_free_urb(urb);
return count;
+error:
+ usb_free_urb(urb);
+error_no_urb:
+ kfree(buffer);
+error_no_buffer:
+ spin_lock_irqsave(&priv->lock, flags);
+ --priv->outstanding_urbs;
+ spin_unlock_irqrestore(&priv->lock, flags);
+ return count;
}
diff --git a/drivers/usb/serial/whiteheat.c b/drivers/usb/serial/whiteheat.c
index bf16e9e..27c5f8f 100644
--- a/drivers/usb/serial/whiteheat.c
+++ b/drivers/usb/serial/whiteheat.c
@@ -1109,7 +1109,7 @@ static int firm_send_command (struct usb_serial_port *port, __u8 command, __u8 *
command_port = port->serial->port[COMMAND_PORT];
command_info = usb_get_serial_port_data(command_port);
spin_lock_irqsave(&command_info->lock, flags);
- command_info->command_finished = FALSE;
+ command_info->command_finished = false;
transfer_buffer = (__u8 *)command_port->write_urb->transfer_buffer;
transfer_buffer[0] = command;
@@ -1124,12 +1124,12 @@ static int firm_send_command (struct usb_serial_port *port, __u8 command, __u8 *
spin_unlock_irqrestore(&command_info->lock, flags);
/* wait for the command to complete */
- wait_event_interruptible_timeout(command_info->wait_command,
- (command_info->command_finished != FALSE), COMMAND_TIMEOUT);
+ wait_event_interruptible_timeout(command_info->wait_command,
+ (bool)command_info->command_finished, COMMAND_TIMEOUT);
spin_lock_irqsave(&command_info->lock, flags);
- if (command_info->command_finished == FALSE) {
+ if (command_info->command_finished == false) {
dbg("%s - command timed out.", __FUNCTION__);
retval = -ETIMEDOUT;
goto exit;
diff --git a/drivers/usb/serial/whiteheat.h b/drivers/usb/serial/whiteheat.h
index d714eff..f160797 100644
--- a/drivers/usb/serial/whiteheat.h
+++ b/drivers/usb/serial/whiteheat.h
@@ -20,10 +20,6 @@
#define __LINUX_USB_SERIAL_WHITEHEAT_H
-#define FALSE 0
-#define TRUE 1
-
-
/* WhiteHEAT commands */
#define WHITEHEAT_OPEN 1 /* open the port */
#define WHITEHEAT_CLOSE 2 /* close the port */
OpenPOWER on IntegriCloud