/* to talk to the device */
/* Thanx to gkh and the rest of the usb dev group for all code I have assimilated :-) */
+#include <linux/config.h>
#include <linux/kernel.h>
#include <linux/errno.h>
#include <linux/init.h>
#include <asm/uaccess.h>
#include <linux/usb.h>
#include <linux/serial.h>
-#include <linux/usb/serial.h>
+#include "usb-serial.h"
#include "ftdi_sio.h"
/*
static struct usb_device_id id_table_combined [] = {
- { USB_DEVICE(FTDI_VID, FTDI_AMC232_PID) },
- { USB_DEVICE(FTDI_VID, FTDI_CANUSB_PID) },
- { USB_DEVICE(FTDI_VID, FTDI_ACTZWAVE_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_IRTRANS_PID) },
- { USB_DEVICE(FTDI_VID, FTDI_IPLUS_PID) },
{ 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_8U2232C_PID) },
- { USB_DEVICE(FTDI_VID, FTDI_MICRO_CHAMELEON_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_RELAIS_PID) },
{ USB_DEVICE(INTERBIOMETRICS_VID, INTERBIOMETRICS_IOBOARD_PID) },
{ USB_DEVICE(INTERBIOMETRICS_VID, INTERBIOMETRICS_MINI_IOBOARD_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_MTXORB_6_PID) },
{ 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(SEALEVEL_VID, SEALEVEL_2101_PID) },
{ USB_DEVICE(SEALEVEL_VID, SEALEVEL_2102_PID) },
{ USB_DEVICE(SEALEVEL_VID, SEALEVEL_2103_PID) },
{ USB_DEVICE(KOBIL_VID, KOBIL_CONV_KAAN_PID) },
{ USB_DEVICE(POSIFLEX_VID, POSIFLEX_PP7000_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_TTUSB_PID) },
- { USB_DEVICE(FTDI_VID, FTDI_ECLO_COM_1WIRE_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_WESTREX_MODEL_777_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_WESTREX_MODEL_8900F_PID) },
{ USB_DEVICE(FTDI_VID, FTDI_PCDJ_DAC2_PID) },
- { USB_DEVICE(FTDI_VID, FTDI_RRCIRKITS_LOCOBUFFER_PID) },
- { USB_DEVICE(FTDI_VID, FTDI_ASK_RDR400_PID) },
- { USB_DEVICE(ICOM_ID1_VID, ICOM_ID1_PID) },
- { USB_DEVICE(PAPOUCH_VID, PAPOUCH_TMU_PID) },
- { USB_DEVICE(FTDI_VID, FTDI_ACG_HFDUAL_PID) },
- { USB_DEVICE(FTDI_VID, FTDI_YEI_SERVOCENTER31_PID) },
- { USB_DEVICE(FTDI_VID, FTDI_THORLABS_PID) },
- { USB_DEVICE(TESTO_VID, TESTO_USB_INTERFACE_PID) },
- { USB_DEVICE(FTDI_VID, FTDI_GAMMA_SCOUT_PID) },
{ }, /* Optional parameter entry */
{ } /* Terminating entry */
};
spinlock_t rx_lock; /* spinlock for receive state */
struct work_struct rx_work;
int rx_processed;
- unsigned long rx_bytes;
__u16 interface; /* FT2232C port interface (0 for FT232/245) */
int force_rtscts; /* if non-zero, force RTS-CTS to always be enabled */
spinlock_t tx_lock; /* spinlock for transmit state */
- unsigned long tx_bytes;
unsigned long tx_outstanding_bytes;
unsigned long tx_outstanding_urbs;
};
dbg("%s",__FUNCTION__);
- priv = kzalloc(sizeof(struct ftdi_private), GFP_KERNEL);
+ priv = kmalloc(sizeof(struct ftdi_private), GFP_KERNEL);
if (!priv){
err("%s- kmalloc(%Zd) failed.", __FUNCTION__, sizeof(struct ftdi_private));
return -ENOMEM;
}
+ memset(priv, 0, sizeof(*priv));
spin_lock_init(&priv->rx_lock);
spin_lock_init(&priv->tx_lock);
static int ftdi_open (struct usb_serial_port *port, struct file *filp)
{ /* ftdi_open */
+ struct termios tmp_termios;
struct usb_device *dev = port->serial->dev;
struct ftdi_private *priv = usb_get_serial_port_data(port);
unsigned long flags;
dbg("%s", __FUNCTION__);
- spin_lock_irqsave(&priv->tx_lock, flags);
- priv->tx_bytes = 0;
- spin_unlock_irqrestore(&priv->tx_lock, flags);
- spin_lock_irqsave(&priv->rx_lock, flags);
- priv->rx_bytes = 0;
- spin_unlock_irqrestore(&priv->rx_lock, flags);
- if (port->tty)
- port->tty->low_latency = (priv->flags & ASYNC_LOW_LATENCY) ? 1 : 0;
+ port->tty->low_latency = (priv->flags & ASYNC_LOW_LATENCY) ? 1 : 0;
/* No error checking for this (will get errors later anyway) */
/* See ftdi_sio.h for description of what is reset */
This is same behaviour as serial.c/rs_open() - Kuba */
/* ftdi_set_termios will send usb control messages */
- if (port->tty)
- ftdi_set_termios(port, NULL);
+ ftdi_set_termios(port, &tmp_termios);
/* FIXME: Flow control might be enabled, so it should be checked -
we have no control of defaults! */
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);
}
priv->tx_outstanding_bytes -= countback;
spin_unlock_irqrestore(&priv->tx_lock, flags);
- usb_serial_port_softint(port);
+ schedule_work(&port->work);
} /* ftdi_write_bulk_callback */
struct usb_serial_port *port = (struct usb_serial_port *)urb->context;
struct tty_struct *tty;
struct ftdi_private *priv;
- unsigned long countread;
- unsigned long flags;
if (urb->number_of_packets > 0) {
err("%s transfer_buffer_length %d actual_length %d number of packets %d",__FUNCTION__,
return;
}
- /* count data bytes, but not status bytes */
- countread = urb->actual_length;
- countread -= 2 * ((countread + (PKTSZ - 1)) / PKTSZ);
- spin_lock_irqsave(&priv->rx_lock, flags);
- priv->rx_bytes += countread;
- spin_unlock_irqrestore(&priv->rx_lock, flags);
-
ftdi_process_read(port);
} /* ftdi_read_bulk_callback */
err("%s urb failed to set baudrate", __FUNCTION__);
}
/* Ensure RTS and DTR are raised when baudrate changed from 0 */
- if (!old_termios || (old_termios->c_cflag & CBAUD) == B0) {
+ if ((old_termios->c_cflag & CBAUD) == B0) {
set_mctrl(port, TIOCM_DTR | TIOCM_RTS);
}
}