aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/usb/serial/ftdi_sio.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/usb/serial/ftdi_sio.c')
-rw-r--r--drivers/usb/serial/ftdi_sio.c109
1 files changed, 95 insertions, 14 deletions
diff --git a/drivers/usb/serial/ftdi_sio.c b/drivers/usb/serial/ftdi_sio.c
index 8a74b19f1283..a20da8528a5f 100644
--- a/drivers/usb/serial/ftdi_sio.c
+++ b/drivers/usb/serial/ftdi_sio.c
@@ -257,7 +257,7 @@
257#include <asm/uaccess.h> 257#include <asm/uaccess.h>
258#include <linux/usb.h> 258#include <linux/usb.h>
259#include <linux/serial.h> 259#include <linux/serial.h>
260#include "usb-serial.h" 260#include <linux/usb/serial.h>
261#include "ftdi_sio.h" 261#include "ftdi_sio.h"
262 262
263/* 263/*
@@ -313,6 +313,7 @@ static struct usb_device_id id_table_combined [] = {
313 { USB_DEVICE(FTDI_VID, FTDI_8U232AM_PID) }, 313 { USB_DEVICE(FTDI_VID, FTDI_8U232AM_PID) },
314 { USB_DEVICE(FTDI_VID, FTDI_8U232AM_ALT_PID) }, 314 { USB_DEVICE(FTDI_VID, FTDI_8U232AM_ALT_PID) },
315 { USB_DEVICE(FTDI_VID, FTDI_8U2232C_PID) }, 315 { USB_DEVICE(FTDI_VID, FTDI_8U2232C_PID) },
316 { USB_DEVICE(FTDI_VID, FTDI_MICRO_CHAMELEON_PID) },
316 { USB_DEVICE(FTDI_VID, FTDI_RELAIS_PID) }, 317 { USB_DEVICE(FTDI_VID, FTDI_RELAIS_PID) },
317 { USB_DEVICE(INTERBIOMETRICS_VID, INTERBIOMETRICS_IOBOARD_PID) }, 318 { USB_DEVICE(INTERBIOMETRICS_VID, INTERBIOMETRICS_IOBOARD_PID) },
318 { USB_DEVICE(INTERBIOMETRICS_VID, INTERBIOMETRICS_MINI_IOBOARD_PID) }, 319 { USB_DEVICE(INTERBIOMETRICS_VID, INTERBIOMETRICS_MINI_IOBOARD_PID) },
@@ -336,6 +337,7 @@ static struct usb_device_id id_table_combined [] = {
336 { USB_DEVICE(FTDI_VID, FTDI_MTXORB_6_PID) }, 337 { USB_DEVICE(FTDI_VID, FTDI_MTXORB_6_PID) },
337 { USB_DEVICE(FTDI_VID, FTDI_PERLE_ULTRAPORT_PID) }, 338 { USB_DEVICE(FTDI_VID, FTDI_PERLE_ULTRAPORT_PID) },
338 { USB_DEVICE(FTDI_VID, FTDI_PIEGROUP_PID) }, 339 { USB_DEVICE(FTDI_VID, FTDI_PIEGROUP_PID) },
340 { USB_DEVICE(FTDI_VID, FTDI_TNC_X_PID) },
339 { USB_DEVICE(SEALEVEL_VID, SEALEVEL_2101_PID) }, 341 { USB_DEVICE(SEALEVEL_VID, SEALEVEL_2101_PID) },
340 { USB_DEVICE(SEALEVEL_VID, SEALEVEL_2102_PID) }, 342 { USB_DEVICE(SEALEVEL_VID, SEALEVEL_2102_PID) },
341 { USB_DEVICE(SEALEVEL_VID, SEALEVEL_2103_PID) }, 343 { USB_DEVICE(SEALEVEL_VID, SEALEVEL_2103_PID) },
@@ -500,6 +502,8 @@ static struct usb_device_id id_table_combined [] = {
500 { USB_DEVICE(PAPOUCH_VID, PAPOUCH_TMU_PID) }, 502 { USB_DEVICE(PAPOUCH_VID, PAPOUCH_TMU_PID) },
501 { USB_DEVICE(FTDI_VID, FTDI_ACG_HFDUAL_PID) }, 503 { USB_DEVICE(FTDI_VID, FTDI_ACG_HFDUAL_PID) },
502 { USB_DEVICE(FTDI_VID, FTDI_YEI_SERVOCENTER31_PID) }, 504 { USB_DEVICE(FTDI_VID, FTDI_YEI_SERVOCENTER31_PID) },
505 { USB_DEVICE(FTDI_VID, FTDI_THORLABS_PID) },
506 { USB_DEVICE(TESTO_VID, TESTO_USB_INTERFACE_PID) },
503 { }, /* Optional parameter entry */ 507 { }, /* Optional parameter entry */
504 { } /* Terminating entry */ 508 { } /* Terminating entry */
505}; 509};
@@ -548,11 +552,17 @@ struct ftdi_private {
548 spinlock_t rx_lock; /* spinlock for receive state */ 552 spinlock_t rx_lock; /* spinlock for receive state */
549 struct work_struct rx_work; 553 struct work_struct rx_work;
550 int rx_processed; 554 int rx_processed;
555 unsigned long rx_bytes;
551 556
552 __u16 interface; /* FT2232C port interface (0 for FT232/245) */ 557 __u16 interface; /* FT2232C port interface (0 for FT232/245) */
553 558
554 int force_baud; /* if non-zero, force the baud rate to this value */ 559 int force_baud; /* if non-zero, force the baud rate to this value */
555 int force_rtscts; /* if non-zero, force RTS-CTS to always be enabled */ 560 int force_rtscts; /* if non-zero, force RTS-CTS to always be enabled */
561
562 spinlock_t tx_lock; /* spinlock for transmit state */
563 unsigned long tx_bytes;
564 unsigned long tx_outstanding_bytes;
565 unsigned long tx_outstanding_urbs;
556}; 566};
557 567
558/* Used for TIOCMIWAIT */ 568/* Used for TIOCMIWAIT */
@@ -626,6 +636,9 @@ static struct usb_serial_driver ftdi_sio_device = {
626#define HIGH 1 636#define HIGH 1
627#define LOW 0 637#define LOW 0
628 638
639/* number of outstanding urbs to prevent userspace DoS from happening */
640#define URB_UPPER_LIMIT 42
641
629/* 642/*
630 * *************************************************************************** 643 * ***************************************************************************
631 * Utlity functions 644 * Utlity functions
@@ -1156,6 +1169,7 @@ static int ftdi_sio_attach (struct usb_serial *serial)
1156 } 1169 }
1157 1170
1158 spin_lock_init(&priv->rx_lock); 1171 spin_lock_init(&priv->rx_lock);
1172 spin_lock_init(&priv->tx_lock);
1159 init_waitqueue_head(&priv->delta_msr_wait); 1173 init_waitqueue_head(&priv->delta_msr_wait);
1160 /* This will push the characters through immediately rather 1174 /* This will push the characters through immediately rather
1161 than queue a task to deliver them */ 1175 than queue a task to deliver them */
@@ -1270,6 +1284,13 @@ static int ftdi_open (struct usb_serial_port *port, struct file *filp)
1270 1284
1271 dbg("%s", __FUNCTION__); 1285 dbg("%s", __FUNCTION__);
1272 1286
1287 spin_lock_irqsave(&priv->tx_lock, flags);
1288 priv->tx_bytes = 0;
1289 spin_unlock_irqrestore(&priv->tx_lock, flags);
1290 spin_lock_irqsave(&priv->rx_lock, flags);
1291 priv->rx_bytes = 0;
1292 spin_unlock_irqrestore(&priv->rx_lock, flags);
1293
1273 if (port->tty) 1294 if (port->tty)
1274 port->tty->low_latency = (priv->flags & ASYNC_LOW_LATENCY) ? 1 : 0; 1295 port->tty->low_latency = (priv->flags & ASYNC_LOW_LATENCY) ? 1 : 0;
1275 1296
@@ -1372,6 +1393,7 @@ static int ftdi_write (struct usb_serial_port *port,
1372 int data_offset ; /* will be 1 for the SIO and 0 otherwise */ 1393 int data_offset ; /* will be 1 for the SIO and 0 otherwise */
1373 int status; 1394 int status;
1374 int transfer_size; 1395 int transfer_size;
1396 unsigned long flags;
1375 1397
1376 dbg("%s port %d, %d bytes", __FUNCTION__, port->number, count); 1398 dbg("%s port %d, %d bytes", __FUNCTION__, port->number, count);
1377 1399
@@ -1379,6 +1401,13 @@ static int ftdi_write (struct usb_serial_port *port,
1379 dbg("write request of 0 bytes"); 1401 dbg("write request of 0 bytes");
1380 return 0; 1402 return 0;
1381 } 1403 }
1404 spin_lock_irqsave(&priv->tx_lock, flags);
1405 if (priv->tx_outstanding_urbs > URB_UPPER_LIMIT) {
1406 spin_unlock_irqrestore(&priv->tx_lock, flags);
1407 dbg("%s - write limit hit\n", __FUNCTION__);
1408 return 0;
1409 }
1410 spin_unlock_irqrestore(&priv->tx_lock, flags);
1382 1411
1383 data_offset = priv->write_offset; 1412 data_offset = priv->write_offset;
1384 dbg("data_offset set to %d",data_offset); 1413 dbg("data_offset set to %d",data_offset);
@@ -1445,6 +1474,12 @@ static int ftdi_write (struct usb_serial_port *port,
1445 err("%s - failed submitting write urb, error %d", __FUNCTION__, status); 1474 err("%s - failed submitting write urb, error %d", __FUNCTION__, status);
1446 count = status; 1475 count = status;
1447 kfree (buffer); 1476 kfree (buffer);
1477 } else {
1478 spin_lock_irqsave(&priv->tx_lock, flags);
1479 ++priv->tx_outstanding_urbs;
1480 priv->tx_outstanding_bytes += count;
1481 priv->tx_bytes += count;
1482 spin_unlock_irqrestore(&priv->tx_lock, flags);
1448 } 1483 }
1449 1484
1450 /* we are done with this urb, so let the host driver 1485 /* we are done with this urb, so let the host driver
@@ -1460,7 +1495,11 @@ static int ftdi_write (struct usb_serial_port *port,
1460 1495
1461static void ftdi_write_bulk_callback (struct urb *urb, struct pt_regs *regs) 1496static void ftdi_write_bulk_callback (struct urb *urb, struct pt_regs *regs)
1462{ 1497{
1498 unsigned long flags;
1463 struct usb_serial_port *port = (struct usb_serial_port *)urb->context; 1499 struct usb_serial_port *port = (struct usb_serial_port *)urb->context;
1500 struct ftdi_private *priv;
1501 int data_offset; /* will be 1 for the SIO and 0 otherwise */
1502 unsigned long countback;
1464 1503
1465 /* free up the transfer buffer, as usb_free_urb() does not do this */ 1504 /* free up the transfer buffer, as usb_free_urb() does not do this */
1466 kfree (urb->transfer_buffer); 1505 kfree (urb->transfer_buffer);
@@ -1472,34 +1511,67 @@ static void ftdi_write_bulk_callback (struct urb *urb, struct pt_regs *regs)
1472 return; 1511 return;
1473 } 1512 }
1474 1513
1514 priv = usb_get_serial_port_data(port);
1515 if (!priv) {
1516 dbg("%s - bad port private data pointer - exiting", __FUNCTION__);
1517 return;
1518 }
1519 /* account for transferred data */
1520 countback = urb->actual_length;
1521 data_offset = priv->write_offset;
1522 if (data_offset > 0) {
1523 /* Subtract the control bytes */
1524 countback -= (data_offset * ((countback + (PKTSZ - 1)) / PKTSZ));
1525 }
1526 spin_lock_irqsave(&priv->tx_lock, flags);
1527 --priv->tx_outstanding_urbs;
1528 priv->tx_outstanding_bytes -= countback;
1529 spin_unlock_irqrestore(&priv->tx_lock, flags);
1530
1475 usb_serial_port_softint(port); 1531 usb_serial_port_softint(port);
1476} /* ftdi_write_bulk_callback */ 1532} /* ftdi_write_bulk_callback */
1477 1533
1478 1534
1479static int ftdi_write_room( struct usb_serial_port *port ) 1535static int ftdi_write_room( struct usb_serial_port *port )
1480{ 1536{
1537 struct ftdi_private *priv = usb_get_serial_port_data(port);
1538 int room;
1539 unsigned long flags;
1540
1481 dbg("%s - port %d", __FUNCTION__, port->number); 1541 dbg("%s - port %d", __FUNCTION__, port->number);
1482 1542
1483 /* 1543 spin_lock_irqsave(&priv->tx_lock, flags);
1484 * We really can take anything the user throws at us 1544 if (priv->tx_outstanding_urbs < URB_UPPER_LIMIT) {
1485 * but let's pick a nice big number to tell the tty 1545 /*
1486 * layer that we have lots of free space 1546 * We really can take anything the user throws at us
1487 */ 1547 * but let's pick a nice big number to tell the tty
1488 return 2048; 1548 * layer that we have lots of free space
1549 */
1550 room = 2048;
1551 } else {
1552 room = 0;
1553 }
1554 spin_unlock_irqrestore(&priv->tx_lock, flags);
1555 return room;
1489} /* ftdi_write_room */ 1556} /* ftdi_write_room */
1490 1557
1491 1558
1492static int ftdi_chars_in_buffer (struct usb_serial_port *port) 1559static int ftdi_chars_in_buffer (struct usb_serial_port *port)
1493{ /* ftdi_chars_in_buffer */ 1560{ /* ftdi_chars_in_buffer */
1561 struct ftdi_private *priv = usb_get_serial_port_data(port);
1562 int buffered;
1563 unsigned long flags;
1564
1494 dbg("%s - port %d", __FUNCTION__, port->number); 1565 dbg("%s - port %d", __FUNCTION__, port->number);
1495 1566
1496 /* 1567 spin_lock_irqsave(&priv->tx_lock, flags);
1497 * We can't really account for how much data we 1568 buffered = (int)priv->tx_outstanding_bytes;
1498 * have sent out, but hasn't made it through to the 1569 spin_unlock_irqrestore(&priv->tx_lock, flags);
1499 * device, so just tell the tty layer that everything 1570 if (buffered < 0) {
1500 * is flushed. 1571 err("%s outstanding tx bytes is negative!", __FUNCTION__);
1501 */ 1572 buffered = 0;
1502 return 0; 1573 }
1574 return buffered;
1503} /* ftdi_chars_in_buffer */ 1575} /* ftdi_chars_in_buffer */
1504 1576
1505 1577
@@ -1509,6 +1581,8 @@ static void ftdi_read_bulk_callback (struct urb *urb, struct pt_regs *regs)
1509 struct usb_serial_port *port = (struct usb_serial_port *)urb->context; 1581 struct usb_serial_port *port = (struct usb_serial_port *)urb->context;
1510 struct tty_struct *tty; 1582 struct tty_struct *tty;
1511 struct ftdi_private *priv; 1583 struct ftdi_private *priv;
1584 unsigned long countread;
1585 unsigned long flags;
1512 1586
1513 if (urb->number_of_packets > 0) { 1587 if (urb->number_of_packets > 0) {
1514 err("%s transfer_buffer_length %d actual_length %d number of packets %d",__FUNCTION__, 1588 err("%s transfer_buffer_length %d actual_length %d number of packets %d",__FUNCTION__,
@@ -1543,6 +1617,13 @@ static void ftdi_read_bulk_callback (struct urb *urb, struct pt_regs *regs)
1543 return; 1617 return;
1544 } 1618 }
1545 1619
1620 /* count data bytes, but not status bytes */
1621 countread = urb->actual_length;
1622 countread -= 2 * ((countread + (PKTSZ - 1)) / PKTSZ);
1623 spin_lock_irqsave(&priv->rx_lock, flags);
1624 priv->rx_bytes += countread;
1625 spin_unlock_irqrestore(&priv->rx_lock, flags);
1626
1546 ftdi_process_read(port); 1627 ftdi_process_read(port);
1547 1628
1548} /* ftdi_read_bulk_callback */ 1629} /* ftdi_read_bulk_callback */