Merge branch 'v3.10/topic/gator' into linux-linaro-lsk-v3.10
[firefly-linux-kernel-4.4.55.git] / drivers / usb / serial / kobil_sct.c
index 903d938e174ba074d85ebeff36ba1a9da39a2074..78b48c31abf5cb335f24d822643a2003e80f43ee 100644 (file)
@@ -65,7 +65,7 @@ static int  kobil_tiocmget(struct tty_struct *tty);
 static int  kobil_tiocmset(struct tty_struct *tty,
                           unsigned int set, unsigned int clear);
 static void kobil_read_int_callback(struct urb *urb);
-static void kobil_write_callback(struct urb *purb);
+static void kobil_write_int_callback(struct urb *urb);
 static void kobil_set_termios(struct tty_struct *tty,
                        struct usb_serial_port *port, struct ktermios *old);
 static void kobil_init_termios(struct tty_struct *tty);
@@ -99,6 +99,7 @@ static struct usb_serial_driver kobil_device = {
        .write =                kobil_write,
        .write_room =           kobil_write_room,
        .read_int_callback =    kobil_read_int_callback,
+       .write_int_callback =   kobil_write_int_callback,
 };
 
 static struct usb_serial_driver * const serial_drivers[] = {
@@ -106,8 +107,6 @@ static struct usb_serial_driver * const serial_drivers[] = {
 };
 
 struct kobil_private {
-       int write_int_endpoint_address;
-       int read_int_endpoint_address;
        unsigned char buf[KOBIL_BUF_LENGTH]; /* buffer for the APDU to send */
        int filled;  /* index of the last char in buf */
        int cur_pos; /* index of the next char to send in buf */
@@ -117,14 +116,8 @@ struct kobil_private {
 
 static int kobil_port_probe(struct usb_serial_port *port)
 {
-       int i;
        struct usb_serial *serial = port->serial;
        struct kobil_private *priv;
-       struct usb_device *pdev;
-       struct usb_host_config *actconfig;
-       struct usb_interface *interface;
-       struct usb_host_interface *altsetting;
-       struct usb_host_endpoint *endpoint;
 
        priv = kmalloc(sizeof(struct kobil_private), GFP_KERNEL);
        if (!priv)
@@ -150,30 +143,6 @@ static int kobil_port_probe(struct usb_serial_port *port)
        }
        usb_set_serial_port_data(port, priv);
 
-       /* search for the necessary endpoints */
-       pdev = serial->dev;
-       actconfig = pdev->actconfig;
-       interface = actconfig->interface[0];
-       altsetting = interface->cur_altsetting;
-       endpoint = altsetting->endpoint;
-
-       for (i = 0; i < altsetting->desc.bNumEndpoints; i++) {
-               endpoint = &altsetting->endpoint[i];
-               if (usb_endpoint_is_int_out(&endpoint->desc)) {
-                       dev_dbg(&serial->dev->dev,
-                               "%s Found interrupt out endpoint. Address: %d\n",
-                               __func__, endpoint->desc.bEndpointAddress);
-                       priv->write_int_endpoint_address =
-                               endpoint->desc.bEndpointAddress;
-               }
-               if (usb_endpoint_is_int_in(&endpoint->desc)) {
-                       dev_dbg(&serial->dev->dev,
-                               "%s Found interrupt in  endpoint. Address: %d\n",
-                               __func__, endpoint->desc.bEndpointAddress);
-                       priv->read_int_endpoint_address =
-                               endpoint->desc.bEndpointAddress;
-               }
-       }
        return 0;
 }
 
@@ -205,7 +174,6 @@ static int kobil_open(struct tty_struct *tty, struct usb_serial_port *port)
        struct kobil_private *priv;
        unsigned char *transfer_buffer;
        int transfer_buffer_length = 8;
-       int write_urb_transfer_buffer_length = 8;
 
        priv = usb_get_serial_port_data(port);
 
@@ -214,27 +182,6 @@ static int kobil_open(struct tty_struct *tty, struct usb_serial_port *port)
        if (!transfer_buffer)
                return -ENOMEM;
 
-       /* allocate write_urb */
-       if (!port->write_urb) {
-               dev_dbg(dev, "%s - Allocating port->write_urb\n", __func__);
-               port->write_urb = usb_alloc_urb(0, GFP_KERNEL);
-               if (!port->write_urb) {
-                       dev_dbg(dev, "%s - usb_alloc_urb failed\n", __func__);
-                       kfree(transfer_buffer);
-                       return -ENOMEM;
-               }
-       }
-
-       /* allocate memory for write_urb transfer buffer */
-       port->write_urb->transfer_buffer =
-                       kmalloc(write_urb_transfer_buffer_length, GFP_KERNEL);
-       if (!port->write_urb->transfer_buffer) {
-               kfree(transfer_buffer);
-               usb_free_urb(port->write_urb);
-               port->write_urb = NULL;
-               return -ENOMEM;
-       }
-
        /* get hardware version */
        result = usb_control_msg(port->serial->dev,
                          usb_rcvctrlpipe(port->serial->dev, 0),
@@ -310,12 +257,7 @@ static int kobil_open(struct tty_struct *tty, struct usb_serial_port *port)
 static void kobil_close(struct usb_serial_port *port)
 {
        /* FIXME: Add rts/dtr methods */
-       if (port->write_urb) {
-               usb_poison_urb(port->write_urb);
-               kfree(port->write_urb->transfer_buffer);
-               usb_free_urb(port->write_urb);
-               port->write_urb = NULL;
-       }
+       usb_kill_urb(port->interrupt_out_urb);
        usb_kill_urb(port->interrupt_in_urb);
 }
 
@@ -333,24 +275,8 @@ static void kobil_read_int_callback(struct urb *urb)
        }
 
        if (urb->actual_length) {
-
-               /* BEGIN DEBUG */
-               /*
-                 char *dbg_data;
-
-                 dbg_data = kzalloc((3 *  purb->actual_length + 10)
-                                               * sizeof(char), GFP_KERNEL);
-                 if (! dbg_data) {
-                         return;
-                 }
-                 for (i = 0; i < purb->actual_length; i++) {
-                         sprintf(dbg_data +3*i, "%02X ", data[i]);
-                 }
-                 dev_dbg(&port->dev, " <-- %s\n", dbg_data);
-                 kfree(dbg_data);
-               */
-               /* END DEBUG */
-
+               usb_serial_debug_data(&port->dev, __func__, urb->actual_length,
+                                                                       data);
                tty_insert_flip_string(&port->port, data, urb->actual_length);
                tty_flip_buffer_push(&port->port);
        }
@@ -360,7 +286,7 @@ static void kobil_read_int_callback(struct urb *urb)
 }
 
 
-static void kobil_write_callback(struct urb *purb)
+static void kobil_write_int_callback(struct urb *urb)
 {
 }
 
@@ -403,23 +329,14 @@ static int kobil_write(struct tty_struct *tty, struct usb_serial_port *port,
 
                while (todo > 0) {
                        /* max 8 byte in one urb (endpoint size) */
-                       length = (todo < 8) ? todo : 8;
+                       length = min(todo, port->interrupt_out_size);
                        /* copy data to transfer buffer */
-                       memcpy(port->write_urb->transfer_buffer,
+                       memcpy(port->interrupt_out_buffer,
                                        priv->buf + priv->cur_pos, length);
-                       usb_fill_int_urb(port->write_urb,
-                                 port->serial->dev,
-                                 usb_sndintpipe(port->serial->dev,
-                                       priv->write_int_endpoint_address),
-                                 port->write_urb->transfer_buffer,
-                                 length,
-                                 kobil_write_callback,
-                                 port,
-                                 8
-                       );
+                       port->interrupt_out_urb->transfer_buffer_length = length;
 
                        priv->cur_pos = priv->cur_pos + length;
-                       result = usb_submit_urb(port->write_urb, GFP_NOIO);
+                       result = usb_submit_urb(port->interrupt_out_urb, GFP_NOIO);
                        dev_dbg(&port->dev, "%s - Send write URB returns: %i\n", __func__, result);
                        todo = priv->filled - priv->cur_pos;