blob: 62574cf7e74c0b545c794dd54b279588d6af53e9 [file] [log] [blame]
Linus Torvalds1da177e2005-04-16 15:20:36 -07001/*
2 * USB Keyspan PDA / Xircom / Entregra Converter driver
3 *
4 * Copyright (C) 1999 - 2001 Greg Kroah-Hartman <greg@kroah.com>
5 * Copyright (C) 1999, 2000 Brian Warner <warner@lothar.com>
6 * Copyright (C) 2000 Al Borchers <borchers@steinerpoint.com>
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
12 *
Alan Cox9e70f312008-07-22 11:13:42 +010013 * See Documentation/usb/usb-serial.txt for more information on using this
14 * driver
Linus Torvalds1da177e2005-04-16 15:20:36 -070015 */
16
17
Linus Torvalds1da177e2005-04-16 15:20:36 -070018#include <linux/kernel.h>
19#include <linux/errno.h>
20#include <linux/init.h>
21#include <linux/slab.h>
22#include <linux/tty.h>
23#include <linux/tty_driver.h>
24#include <linux/tty_flip.h>
25#include <linux/module.h>
26#include <linux/spinlock.h>
27#include <linux/workqueue.h>
David Woodhouse3edbf982008-05-30 15:15:13 +030028#include <linux/firmware.h>
29#include <linux/ihex.h>
Alan Cox9e70f312008-07-22 11:13:42 +010030#include <linux/uaccess.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070031#include <linux/usb.h>
Greg Kroah-Hartmana9698882006-07-11 21:22:58 -070032#include <linux/usb/serial.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070033
Rusty Russell90ab5ee2012-01-13 09:32:20 +103034static bool debug;
Linus Torvalds1da177e2005-04-16 15:20:36 -070035
Linus Torvalds1da177e2005-04-16 15:20:36 -070036/* make a simple define to handle if we are compiling keyspan_pda or xircom support */
37#if defined(CONFIG_USB_SERIAL_KEYSPAN_PDA) || defined(CONFIG_USB_SERIAL_KEYSPAN_PDA_MODULE)
38 #define KEYSPAN
39#else
40 #undef KEYSPAN
41#endif
42#if defined(CONFIG_USB_SERIAL_XIRCOM) || defined(CONFIG_USB_SERIAL_XIRCOM_MODULE)
43 #define XIRCOM
44#else
45 #undef XIRCOM
46#endif
47
Linus Torvalds1da177e2005-04-16 15:20:36 -070048/*
49 * Version Information
50 */
51#define DRIVER_VERSION "v1.1"
52#define DRIVER_AUTHOR "Brian Warner <warner@lothar.com>"
53#define DRIVER_DESC "USB Keyspan PDA Converter driver"
54
55struct keyspan_pda_private {
56 int tx_room;
57 int tx_throttled;
58 struct work_struct wakeup_work;
59 struct work_struct unthrottle_work;
David Howellsc4028952006-11-22 14:57:56 +000060 struct usb_serial *serial;
61 struct usb_serial_port *port;
Linus Torvalds1da177e2005-04-16 15:20:36 -070062};
63
64
65#define KEYSPAN_VENDOR_ID 0x06cd
66#define KEYSPAN_PDA_FAKE_ID 0x0103
67#define KEYSPAN_PDA_ID 0x0104 /* no clue */
68
69/* For Xircom PGSDB9 and older Entregra version of the same device */
70#define XIRCOM_VENDOR_ID 0x085a
71#define XIRCOM_FAKE_ID 0x8027
72#define ENTREGRA_VENDOR_ID 0x1645
73#define ENTREGRA_FAKE_ID 0x8093
74
Németh Márton7d40d7e2010-01-10 15:34:24 +010075static const struct usb_device_id id_table_combined[] = {
Linus Torvalds1da177e2005-04-16 15:20:36 -070076#ifdef KEYSPAN
77 { USB_DEVICE(KEYSPAN_VENDOR_ID, KEYSPAN_PDA_FAKE_ID) },
78#endif
79#ifdef XIRCOM
80 { USB_DEVICE(XIRCOM_VENDOR_ID, XIRCOM_FAKE_ID) },
81 { USB_DEVICE(ENTREGRA_VENDOR_ID, ENTREGRA_FAKE_ID) },
82#endif
83 { USB_DEVICE(KEYSPAN_VENDOR_ID, KEYSPAN_PDA_ID) },
84 { } /* Terminating entry */
85};
86
Alan Cox9e70f312008-07-22 11:13:42 +010087MODULE_DEVICE_TABLE(usb, id_table_combined);
Linus Torvalds1da177e2005-04-16 15:20:36 -070088
89static struct usb_driver keyspan_pda_driver = {
Linus Torvalds1da177e2005-04-16 15:20:36 -070090 .name = "keyspan_pda",
Linus Torvalds1da177e2005-04-16 15:20:36 -070091 .id_table = id_table_combined,
92};
93
Németh Márton7d40d7e2010-01-10 15:34:24 +010094static const struct usb_device_id id_table_std[] = {
Linus Torvalds1da177e2005-04-16 15:20:36 -070095 { USB_DEVICE(KEYSPAN_VENDOR_ID, KEYSPAN_PDA_ID) },
96 { } /* Terminating entry */
97};
98
99#ifdef KEYSPAN
Németh Márton7d40d7e2010-01-10 15:34:24 +0100100static const struct usb_device_id id_table_fake[] = {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700101 { USB_DEVICE(KEYSPAN_VENDOR_ID, KEYSPAN_PDA_FAKE_ID) },
102 { } /* Terminating entry */
103};
104#endif
105
106#ifdef XIRCOM
Németh Márton7d40d7e2010-01-10 15:34:24 +0100107static const struct usb_device_id id_table_fake_xircom[] = {
Alan Cox9e70f312008-07-22 11:13:42 +0100108 { USB_DEVICE(XIRCOM_VENDOR_ID, XIRCOM_FAKE_ID) },
109 { USB_DEVICE(ENTREGRA_VENDOR_ID, ENTREGRA_FAKE_ID) },
110 { }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700111};
112#endif
113
David Howellsc4028952006-11-22 14:57:56 +0000114static void keyspan_pda_wakeup_write(struct work_struct *work)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700115{
David Howellsc4028952006-11-22 14:57:56 +0000116 struct keyspan_pda_private *priv =
117 container_of(work, struct keyspan_pda_private, wakeup_work);
118 struct usb_serial_port *port = priv->port;
Alan Cox4a90f092008-10-13 10:39:46 +0100119 struct tty_struct *tty = tty_port_tty_get(&port->port);
Jiri Slabyf7d7aed2011-02-28 10:34:05 +0100120 if (tty)
121 tty_wakeup(tty);
Alan Cox4a90f092008-10-13 10:39:46 +0100122 tty_kref_put(tty);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700123}
124
David Howellsc4028952006-11-22 14:57:56 +0000125static void keyspan_pda_request_unthrottle(struct work_struct *work)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700126{
David Howellsc4028952006-11-22 14:57:56 +0000127 struct keyspan_pda_private *priv =
128 container_of(work, struct keyspan_pda_private, unthrottle_work);
129 struct usb_serial *serial = priv->serial;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700130 int result;
131
Linus Torvalds1da177e2005-04-16 15:20:36 -0700132 /* ask the device to tell us when the tx buffer becomes
133 sufficiently empty */
Alan Cox9e70f312008-07-22 11:13:42 +0100134 result = usb_control_msg(serial->dev,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700135 usb_sndctrlpipe(serial->dev, 0),
136 7, /* request_unthrottle */
137 USB_TYPE_VENDOR | USB_RECIP_INTERFACE
138 | USB_DIR_OUT,
139 16, /* value: threshold */
140 0, /* index */
141 NULL,
142 0,
143 2000);
144 if (result < 0)
Alan Cox9e70f312008-07-22 11:13:42 +0100145 dbg("%s - error %d from usb_control_msg",
Harvey Harrison441b62c2008-03-03 16:08:34 -0800146 __func__, result);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700147}
148
149
Alan Cox9e70f312008-07-22 11:13:42 +0100150static void keyspan_pda_rx_interrupt(struct urb *urb)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700151{
Ming Leicdc97792008-02-24 18:41:47 +0800152 struct usb_serial_port *port = urb->context;
Jiri Slabyf7d7aed2011-02-28 10:34:05 +0100153 struct tty_struct *tty;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700154 unsigned char *data = urb->transfer_buffer;
Greg Kroah-Hartman23189ae2007-06-15 15:44:13 -0700155 int retval;
156 int status = urb->status;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700157 struct keyspan_pda_private *priv;
158 priv = usb_get_serial_port_data(port);
159
Greg Kroah-Hartman23189ae2007-06-15 15:44:13 -0700160 switch (status) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700161 case 0:
162 /* success */
163 break;
164 case -ECONNRESET:
165 case -ENOENT:
166 case -ESHUTDOWN:
167 /* this urb is terminated, clean up */
Greg Kroah-Hartman23189ae2007-06-15 15:44:13 -0700168 dbg("%s - urb shutting down with status: %d",
Harvey Harrison441b62c2008-03-03 16:08:34 -0800169 __func__, status);
Jiri Slabyf7d7aed2011-02-28 10:34:05 +0100170 return;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700171 default:
Greg Kroah-Hartman23189ae2007-06-15 15:44:13 -0700172 dbg("%s - nonzero urb status received: %d",
Harvey Harrison441b62c2008-03-03 16:08:34 -0800173 __func__, status);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700174 goto exit;
175 }
176
Alan Cox9e70f312008-07-22 11:13:42 +0100177 /* see if the message is data or a status interrupt */
Linus Torvalds1da177e2005-04-16 15:20:36 -0700178 switch (data[0]) {
179 case 0:
Jiri Slabyf7d7aed2011-02-28 10:34:05 +0100180 tty = tty_port_tty_get(&port->port);
181 /* rest of message is rx data */
182 if (tty && urb->actual_length) {
Alan Cox8dd03a52008-07-22 11:13:51 +0100183 tty_insert_flip_string(tty, data + 1,
184 urb->actual_length - 1);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700185 tty_flip_buffer_push(tty);
186 }
Jiri Slabyf7d7aed2011-02-28 10:34:05 +0100187 tty_kref_put(tty);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700188 break;
189 case 1:
190 /* status interrupt */
191 dbg(" rx int, d1=%d, d2=%d", data[1], data[2]);
192 switch (data[1]) {
193 case 1: /* modemline change */
194 break;
195 case 2: /* tx unthrottle interrupt */
196 priv->tx_throttled = 0;
197 /* queue up a wakeup at scheduler time */
198 schedule_work(&priv->wakeup_work);
199 break;
200 default:
201 break;
202 }
203 break;
204 default:
205 break;
206 }
207
208exit:
Alan Cox9e70f312008-07-22 11:13:42 +0100209 retval = usb_submit_urb(urb, GFP_ATOMIC);
Greg Kroah-Hartman23189ae2007-06-15 15:44:13 -0700210 if (retval)
Alan Cox4a90f092008-10-13 10:39:46 +0100211 dev_err(&port->dev,
212 "%s - usb_submit_urb failed with result %d",
213 __func__, retval);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700214}
215
216
Alan Cox95da3102008-07-22 11:09:07 +0100217static void keyspan_pda_rx_throttle(struct tty_struct *tty)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700218{
219 /* stop receiving characters. We just turn off the URB request, and
220 let chars pile up in the device. If we're doing hardware
221 flowcontrol, the device will signal the other end when its buffer
222 fills up. If we're doing XON/XOFF, this would be a good time to
223 send an XOFF, although it might make sense to foist that off
224 upon the device too. */
Alan Cox95da3102008-07-22 11:09:07 +0100225 struct usb_serial_port *port = tty->driver_data;
Greg Kroah-Hartman5542cf72012-05-03 16:44:23 -0700226
Linus Torvalds1da177e2005-04-16 15:20:36 -0700227 usb_kill_urb(port->interrupt_in_urb);
228}
229
230
Alan Cox95da3102008-07-22 11:09:07 +0100231static void keyspan_pda_rx_unthrottle(struct tty_struct *tty)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700232{
Alan Cox95da3102008-07-22 11:09:07 +0100233 struct usb_serial_port *port = tty->driver_data;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700234 /* just restart the receive interrupt URB */
Greg Kroah-Hartman5542cf72012-05-03 16:44:23 -0700235
Oliver Neukum63832512009-10-07 10:50:23 +0200236 if (usb_submit_urb(port->interrupt_in_urb, GFP_KERNEL))
Linus Torvalds1da177e2005-04-16 15:20:36 -0700237 dbg(" usb_submit_urb(read urb) failed");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700238}
239
240
Alan Cox9e70f312008-07-22 11:13:42 +0100241static speed_t keyspan_pda_setbaud(struct usb_serial *serial, speed_t baud)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700242{
243 int rc;
244 int bindex;
245
Alan Cox9e70f312008-07-22 11:13:42 +0100246 switch (baud) {
247 case 110:
248 bindex = 0;
249 break;
250 case 300:
251 bindex = 1;
252 break;
253 case 1200:
254 bindex = 2;
255 break;
256 case 2400:
257 bindex = 3;
258 break;
259 case 4800:
260 bindex = 4;
261 break;
262 case 9600:
263 bindex = 5;
264 break;
265 case 19200:
266 bindex = 6;
267 break;
268 case 38400:
269 bindex = 7;
270 break;
271 case 57600:
272 bindex = 8;
273 break;
274 case 115200:
275 bindex = 9;
276 break;
277 default:
278 bindex = 5; /* Default to 9600 */
279 baud = 9600;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700280 }
281
282 /* rather than figure out how to sleep while waiting for this
283 to complete, I just use the "legacy" API. */
284 rc = usb_control_msg(serial->dev, usb_sndctrlpipe(serial->dev, 0),
285 0, /* set baud */
Alan Cox9e70f312008-07-22 11:13:42 +0100286 USB_TYPE_VENDOR
Linus Torvalds1da177e2005-04-16 15:20:36 -0700287 | USB_RECIP_INTERFACE
288 | USB_DIR_OUT, /* type */
289 bindex, /* value */
290 0, /* index */
291 NULL, /* &data */
292 0, /* size */
293 2000); /* timeout */
Alan Coxe7806e32007-12-13 16:15:28 -0800294 if (rc < 0)
295 return 0;
296 return baud;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700297}
298
299
Alan Cox95da3102008-07-22 11:09:07 +0100300static void keyspan_pda_break_ctl(struct tty_struct *tty, int break_state)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700301{
Alan Cox95da3102008-07-22 11:09:07 +0100302 struct usb_serial_port *port = tty->driver_data;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700303 struct usb_serial *serial = port->serial;
304 int value;
305 int result;
306
307 if (break_state == -1)
308 value = 1; /* start break */
309 else
310 value = 0; /* clear break */
311 result = usb_control_msg(serial->dev, usb_sndctrlpipe(serial->dev, 0),
Alan Cox9e70f312008-07-22 11:13:42 +0100312 4, /* set break */
313 USB_TYPE_VENDOR | USB_RECIP_INTERFACE | USB_DIR_OUT,
314 value, 0, NULL, 0, 2000);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700315 if (result < 0)
Alan Cox9e70f312008-07-22 11:13:42 +0100316 dbg("%s - error %d from usb_control_msg",
Harvey Harrison441b62c2008-03-03 16:08:34 -0800317 __func__, result);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700318 /* there is something funky about this.. the TCSBRK that 'cu' performs
319 ought to translate into a break_ctl(-1),break_ctl(0) pair HZ/4
320 seconds apart, but it feels like the break sent isn't as long as it
321 is on /dev/ttyS0 */
322}
323
324
Alan Cox95da3102008-07-22 11:09:07 +0100325static void keyspan_pda_set_termios(struct tty_struct *tty,
326 struct usb_serial_port *port, struct ktermios *old_termios)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700327{
328 struct usb_serial *serial = port->serial;
Alan Coxe7806e32007-12-13 16:15:28 -0800329 speed_t speed;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700330
331 /* cflag specifies lots of stuff: number of stop bits, parity, number
332 of data bits, baud. What can the device actually handle?:
333 CSTOPB (1 stop bit or 2)
334 PARENB (parity)
335 CSIZE (5bit .. 8bit)
336 There is minimal hw support for parity (a PSW bit seems to hold the
337 parity of whatever is in the accumulator). The UART either deals
338 with 10 bits (start, 8 data, stop) or 11 bits (start, 8 data,
339 1 special, stop). So, with firmware changes, we could do:
340 8N1: 10 bit
341 8N2: 11 bit, extra bit always (mark?)
342 8[EOMS]1: 11 bit, extra bit is parity
343 7[EOMS]1: 10 bit, b0/b7 is parity
344 7[EOMS]2: 11 bit, b0/b7 is parity, extra bit always (mark?)
345
346 HW flow control is dictated by the tty->termios->c_cflags & CRTSCTS
347 bit.
348
349 For now, just do baud. */
350
Alan Cox95da3102008-07-22 11:09:07 +0100351 speed = tty_get_baud_rate(tty);
Alan Coxe7806e32007-12-13 16:15:28 -0800352 speed = keyspan_pda_setbaud(serial, speed);
353
354 if (speed == 0) {
355 dbg("can't handle requested baud rate");
356 /* It hasn't changed so.. */
357 speed = tty_termios_baud_rate(old_termios);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700358 }
Alan Coxe7806e32007-12-13 16:15:28 -0800359 /* Only speed can change so copy the old h/w parameters
360 then encode the new speed */
Alan Cox95da3102008-07-22 11:09:07 +0100361 tty_termios_copy_hw(tty->termios, old_termios);
362 tty_encode_baud_rate(tty, speed, speed);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700363}
364
365
366/* modem control pins: DTR and RTS are outputs and can be controlled.
367 DCD, RI, DSR, CTS are inputs and can be read. All outputs can also be
368 read. The byte passed is: DTR(b7) DCD RI DSR CTS RTS(b2) unused unused */
369
370static int keyspan_pda_get_modem_info(struct usb_serial *serial,
371 unsigned char *value)
372{
373 int rc;
Johan Hovoldca65d252009-12-28 23:01:51 +0100374 u8 *data;
375
376 data = kmalloc(1, GFP_KERNEL);
377 if (!data)
378 return -ENOMEM;
379
Linus Torvalds1da177e2005-04-16 15:20:36 -0700380 rc = usb_control_msg(serial->dev, usb_rcvctrlpipe(serial->dev, 0),
381 3, /* get pins */
382 USB_TYPE_VENDOR|USB_RECIP_INTERFACE|USB_DIR_IN,
Johan Hovoldca65d252009-12-28 23:01:51 +0100383 0, 0, data, 1, 2000);
Benny Halevy3b36a8f2008-06-27 12:22:32 +0300384 if (rc >= 0)
Johan Hovoldca65d252009-12-28 23:01:51 +0100385 *value = *data;
386
387 kfree(data);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700388 return rc;
389}
390
391
392static int keyspan_pda_set_modem_info(struct usb_serial *serial,
393 unsigned char value)
394{
395 int rc;
396 rc = usb_control_msg(serial->dev, usb_sndctrlpipe(serial->dev, 0),
397 3, /* set pins */
398 USB_TYPE_VENDOR|USB_RECIP_INTERFACE|USB_DIR_OUT,
399 value, 0, NULL, 0, 2000);
400 return rc;
401}
402
Alan Cox60b33c12011-02-14 16:26:14 +0000403static int keyspan_pda_tiocmget(struct tty_struct *tty)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700404{
Alan Cox95da3102008-07-22 11:09:07 +0100405 struct usb_serial_port *port = tty->driver_data;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700406 struct usb_serial *serial = port->serial;
407 int rc;
408 unsigned char status;
409 int value;
410
411 rc = keyspan_pda_get_modem_info(serial, &status);
412 if (rc < 0)
413 return rc;
414 value =
415 ((status & (1<<7)) ? TIOCM_DTR : 0) |
416 ((status & (1<<6)) ? TIOCM_CAR : 0) |
417 ((status & (1<<5)) ? TIOCM_RNG : 0) |
418 ((status & (1<<4)) ? TIOCM_DSR : 0) |
419 ((status & (1<<3)) ? TIOCM_CTS : 0) |
420 ((status & (1<<2)) ? TIOCM_RTS : 0);
421 return value;
422}
423
Alan Cox20b9d172011-02-14 16:26:50 +0000424static int keyspan_pda_tiocmset(struct tty_struct *tty,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700425 unsigned int set, unsigned int clear)
426{
Alan Cox95da3102008-07-22 11:09:07 +0100427 struct usb_serial_port *port = tty->driver_data;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700428 struct usb_serial *serial = port->serial;
429 int rc;
430 unsigned char status;
431
432 rc = keyspan_pda_get_modem_info(serial, &status);
433 if (rc < 0)
434 return rc;
435
436 if (set & TIOCM_RTS)
437 status |= (1<<2);
438 if (set & TIOCM_DTR)
439 status |= (1<<7);
440
441 if (clear & TIOCM_RTS)
442 status &= ~(1<<2);
443 if (clear & TIOCM_DTR)
444 status &= ~(1<<7);
445 rc = keyspan_pda_set_modem_info(serial, status);
446 return rc;
447}
448
Alan Cox95da3102008-07-22 11:09:07 +0100449static int keyspan_pda_write(struct tty_struct *tty,
450 struct usb_serial_port *port, const unsigned char *buf, int count)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700451{
452 struct usb_serial *serial = port->serial;
453 int request_unthrottle = 0;
454 int rc = 0;
455 struct keyspan_pda_private *priv;
456
457 priv = usb_get_serial_port_data(port);
458 /* guess how much room is left in the device's ring buffer, and if we
459 want to send more than that, check first, updating our notion of
460 what is left. If our write will result in no room left, ask the
461 device to give us an interrupt when the room available rises above
462 a threshold, and hold off all writers (eventually, those using
463 select() or poll() too) until we receive that unthrottle interrupt.
464 Block if we can't write anything at all, otherwise write as much as
465 we can. */
Linus Torvalds1da177e2005-04-16 15:20:36 -0700466 if (count == 0) {
467 dbg(" write request of 0 bytes");
Alan Cox9e70f312008-07-22 11:13:42 +0100468 return 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700469 }
470
471 /* we might block because of:
472 the TX urb is in-flight (wait until it completes)
473 the device is full (wait until it says there is room)
474 */
Peter Zijlstrae81ee632006-09-25 12:51:41 +0200475 spin_lock_bh(&port->lock);
Johan Hovoldda280e32011-11-06 19:06:24 +0100476 if (!test_bit(0, &port->write_urbs_free) || priv->tx_throttled) {
Peter Zijlstrae81ee632006-09-25 12:51:41 +0200477 spin_unlock_bh(&port->lock);
Greg Kroah-Hartman507ca9b2005-04-23 12:49:16 -0700478 return 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700479 }
Johan Hovoldda280e32011-11-06 19:06:24 +0100480 clear_bit(0, &port->write_urbs_free);
Peter Zijlstrae81ee632006-09-25 12:51:41 +0200481 spin_unlock_bh(&port->lock);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700482
483 /* At this point the URB is in our control, nobody else can submit it
484 again (the only sudden transition was the one from EINPROGRESS to
485 finished). Also, the tx process is not throttled. So we are
486 ready to write. */
487
488 count = (count > port->bulk_out_size) ? port->bulk_out_size : count;
489
490 /* Check if we might overrun the Tx buffer. If so, ask the
491 device how much room it really has. This is done only on
492 scheduler time, since usb_control_msg() sleeps. */
493 if (count > priv->tx_room && !in_interrupt()) {
Johan Hovoldca65d252009-12-28 23:01:51 +0100494 u8 *room;
495
496 room = kmalloc(1, GFP_KERNEL);
497 if (!room) {
498 rc = -ENOMEM;
499 goto exit;
500 }
501
Alan Cox9e70f312008-07-22 11:13:42 +0100502 rc = usb_control_msg(serial->dev,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700503 usb_rcvctrlpipe(serial->dev, 0),
504 6, /* write_room */
505 USB_TYPE_VENDOR | USB_RECIP_INTERFACE
506 | USB_DIR_IN,
507 0, /* value: 0 means "remaining room" */
508 0, /* index */
Johan Hovoldca65d252009-12-28 23:01:51 +0100509 room,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700510 1,
511 2000);
Johan Hovoldca65d252009-12-28 23:01:51 +0100512 if (rc > 0) {
513 dbg(" roomquery says %d", *room);
514 priv->tx_room = *room;
515 }
516 kfree(room);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700517 if (rc < 0) {
518 dbg(" roomquery failed");
519 goto exit;
520 }
521 if (rc == 0) {
522 dbg(" roomquery returned 0 bytes");
523 rc = -EIO; /* device didn't return any data */
524 goto exit;
525 }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700526 }
527 if (count > priv->tx_room) {
528 /* we're about to completely fill the Tx buffer, so
529 we'll be throttled afterwards. */
530 count = priv->tx_room;
531 request_unthrottle = 1;
532 }
533
534 if (count) {
535 /* now transfer data */
Alan Cox9e70f312008-07-22 11:13:42 +0100536 memcpy(port->write_urb->transfer_buffer, buf, count);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700537 /* send the data out the bulk port */
538 port->write_urb->transfer_buffer_length = count;
Greg Kroah-Hartman507ca9b2005-04-23 12:49:16 -0700539
Linus Torvalds1da177e2005-04-16 15:20:36 -0700540 priv->tx_room -= count;
541
Linus Torvalds1da177e2005-04-16 15:20:36 -0700542 rc = usb_submit_urb(port->write_urb, GFP_ATOMIC);
543 if (rc) {
544 dbg(" usb_submit_urb(write bulk) failed");
545 goto exit;
546 }
Alan Cox9e70f312008-07-22 11:13:42 +0100547 } else {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700548 /* There wasn't any room left, so we are throttled until
549 the buffer empties a bit */
550 request_unthrottle = 1;
551 }
552
553 if (request_unthrottle) {
554 priv->tx_throttled = 1; /* block writers */
555 schedule_work(&priv->unthrottle_work);
556 }
557
558 rc = count;
559exit:
Greg Kroah-Hartman507ca9b2005-04-23 12:49:16 -0700560 if (rc < 0)
Johan Hovoldda280e32011-11-06 19:06:24 +0100561 set_bit(0, &port->write_urbs_free);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700562 return rc;
563}
564
565
Alan Cox9e70f312008-07-22 11:13:42 +0100566static void keyspan_pda_write_bulk_callback(struct urb *urb)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700567{
Ming Leicdc97792008-02-24 18:41:47 +0800568 struct usb_serial_port *port = urb->context;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700569 struct keyspan_pda_private *priv;
570
Johan Hovoldda280e32011-11-06 19:06:24 +0100571 set_bit(0, &port->write_urbs_free);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700572 priv = usb_get_serial_port_data(port);
573
574 /* queue up a wakeup at scheduler time */
575 schedule_work(&priv->wakeup_work);
576}
577
578
Alan Cox95da3102008-07-22 11:09:07 +0100579static int keyspan_pda_write_room(struct tty_struct *tty)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700580{
Alan Cox95da3102008-07-22 11:09:07 +0100581 struct usb_serial_port *port = tty->driver_data;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700582 struct keyspan_pda_private *priv;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700583 priv = usb_get_serial_port_data(port);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700584 /* used by n_tty.c for processing of tabs and such. Giving it our
585 conservative guess is probably good enough, but needs testing by
586 running a console through the device. */
Alan Cox9e70f312008-07-22 11:13:42 +0100587 return priv->tx_room;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700588}
589
590
Alan Cox95da3102008-07-22 11:09:07 +0100591static int keyspan_pda_chars_in_buffer(struct tty_struct *tty)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700592{
Alan Cox95da3102008-07-22 11:09:07 +0100593 struct usb_serial_port *port = tty->driver_data;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700594 struct keyspan_pda_private *priv;
Alan Coxa5b6f602008-04-08 17:16:06 +0100595 unsigned long flags;
596 int ret = 0;
Greg Kroah-Hartman507ca9b2005-04-23 12:49:16 -0700597
Linus Torvalds1da177e2005-04-16 15:20:36 -0700598 priv = usb_get_serial_port_data(port);
Greg Kroah-Hartman507ca9b2005-04-23 12:49:16 -0700599
Linus Torvalds1da177e2005-04-16 15:20:36 -0700600 /* when throttled, return at least WAKEUP_CHARS to tell select() (via
601 n_tty.c:normal_poll() ) that we're not writeable. */
Alan Coxa5b6f602008-04-08 17:16:06 +0100602
603 spin_lock_irqsave(&port->lock, flags);
Johan Hovoldda280e32011-11-06 19:06:24 +0100604 if (!test_bit(0, &port->write_urbs_free) || priv->tx_throttled)
Alan Coxa5b6f602008-04-08 17:16:06 +0100605 ret = 256;
606 spin_unlock_irqrestore(&port->lock, flags);
607 return ret;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700608}
609
610
Alan Cox335f8512009-06-11 12:26:29 +0100611static void keyspan_pda_dtr_rts(struct usb_serial_port *port, int on)
612{
613 struct usb_serial *serial = port->serial;
614
615 if (serial->dev) {
616 if (on)
617 keyspan_pda_set_modem_info(serial, (1<<7) | (1<< 2));
618 else
619 keyspan_pda_set_modem_info(serial, 0);
620 }
621}
622
Alan Cox335f8512009-06-11 12:26:29 +0100623
Alan Cox95da3102008-07-22 11:09:07 +0100624static int keyspan_pda_open(struct tty_struct *tty,
Alan Coxa509a7e2009-09-19 13:13:26 -0700625 struct usb_serial_port *port)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700626{
627 struct usb_serial *serial = port->serial;
Johan Hovoldca65d252009-12-28 23:01:51 +0100628 u8 *room;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700629 int rc = 0;
630 struct keyspan_pda_private *priv;
631
632 /* find out how much room is in the Tx ring */
Johan Hovoldca65d252009-12-28 23:01:51 +0100633 room = kmalloc(1, GFP_KERNEL);
634 if (!room)
635 return -ENOMEM;
636
Linus Torvalds1da177e2005-04-16 15:20:36 -0700637 rc = usb_control_msg(serial->dev, usb_rcvctrlpipe(serial->dev, 0),
638 6, /* write_room */
639 USB_TYPE_VENDOR | USB_RECIP_INTERFACE
640 | USB_DIR_IN,
641 0, /* value */
642 0, /* index */
Johan Hovoldca65d252009-12-28 23:01:51 +0100643 room,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700644 1,
645 2000);
646 if (rc < 0) {
Harvey Harrison441b62c2008-03-03 16:08:34 -0800647 dbg("%s - roomquery failed", __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700648 goto error;
649 }
650 if (rc == 0) {
Harvey Harrison441b62c2008-03-03 16:08:34 -0800651 dbg("%s - roomquery returned 0 bytes", __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700652 rc = -EIO;
653 goto error;
654 }
655 priv = usb_get_serial_port_data(port);
Johan Hovoldca65d252009-12-28 23:01:51 +0100656 priv->tx_room = *room;
657 priv->tx_throttled = *room ? 0 : 1;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700658
Linus Torvalds1da177e2005-04-16 15:20:36 -0700659 /*Start reading from the device*/
Linus Torvalds1da177e2005-04-16 15:20:36 -0700660 rc = usb_submit_urb(port->interrupt_in_urb, GFP_KERNEL);
661 if (rc) {
Harvey Harrison441b62c2008-03-03 16:08:34 -0800662 dbg("%s - usb_submit_urb(read int) failed", __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700663 goto error;
664 }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700665error:
Johan Hovoldca65d252009-12-28 23:01:51 +0100666 kfree(room);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700667 return rc;
668}
Alan Cox335f8512009-06-11 12:26:29 +0100669static void keyspan_pda_close(struct usb_serial_port *port)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700670{
671 struct usb_serial *serial = port->serial;
672
673 if (serial->dev) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700674 /* shutdown our bulk reads and writes */
675 usb_kill_urb(port->write_urb);
676 usb_kill_urb(port->interrupt_in_urb);
677 }
678}
679
680
681/* download the firmware to a "fake" device (pre-renumeration) */
Alan Cox9e70f312008-07-22 11:13:42 +0100682static int keyspan_pda_fake_startup(struct usb_serial *serial)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700683{
684 int response;
David Woodhouse3edbf982008-05-30 15:15:13 +0300685 const char *fw_name;
686 const struct ihex_binrec *record;
687 const struct firmware *fw;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700688
689 /* download the firmware here ... */
690 response = ezusb_set_reset(serial, 1);
691
David Woodhouse3edbf982008-05-30 15:15:13 +0300692 if (0) { ; }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700693#ifdef KEYSPAN
David Woodhouse3edbf982008-05-30 15:15:13 +0300694 else if (le16_to_cpu(serial->dev->descriptor.idVendor) == KEYSPAN_VENDOR_ID)
695 fw_name = "keyspan_pda/keyspan_pda.fw";
Linus Torvalds1da177e2005-04-16 15:20:36 -0700696#endif
697#ifdef XIRCOM
David Woodhouse3edbf982008-05-30 15:15:13 +0300698 else if ((le16_to_cpu(serial->dev->descriptor.idVendor) == XIRCOM_VENDOR_ID) ||
699 (le16_to_cpu(serial->dev->descriptor.idVendor) == ENTREGRA_VENDOR_ID))
700 fw_name = "keyspan_pda/xircom_pgs.fw";
Linus Torvalds1da177e2005-04-16 15:20:36 -0700701#endif
David Woodhouse3edbf982008-05-30 15:15:13 +0300702 else {
Greg Kroah-Hartman194343d2008-08-20 16:56:34 -0700703 dev_err(&serial->dev->dev, "%s: unknown vendor, aborting.\n",
704 __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700705 return -ENODEV;
706 }
David Woodhouse3edbf982008-05-30 15:15:13 +0300707 if (request_ihex_firmware(&fw, fw_name, &serial->dev->dev)) {
Greg Kroah-Hartman194343d2008-08-20 16:56:34 -0700708 dev_err(&serial->dev->dev, "failed to load firmware \"%s\"\n",
709 fw_name);
David Woodhouse3edbf982008-05-30 15:15:13 +0300710 return -ENOENT;
711 }
712 record = (const struct ihex_binrec *)fw->data;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700713
David Woodhouse3edbf982008-05-30 15:15:13 +0300714 while (record) {
715 response = ezusb_writememory(serial, be32_to_cpu(record->addr),
Linus Torvalds1da177e2005-04-16 15:20:36 -0700716 (unsigned char *)record->data,
David Woodhouse3edbf982008-05-30 15:15:13 +0300717 be16_to_cpu(record->len), 0xa0);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700718 if (response < 0) {
Greg Kroah-Hartman194343d2008-08-20 16:56:34 -0700719 dev_err(&serial->dev->dev, "ezusb_writememory failed "
720 "for Keyspan PDA firmware (%d %04X %p %d)\n",
721 response, be32_to_cpu(record->addr),
722 record->data, be16_to_cpu(record->len));
Linus Torvalds1da177e2005-04-16 15:20:36 -0700723 break;
724 }
David Woodhouse3edbf982008-05-30 15:15:13 +0300725 record = ihex_next_binrec(record);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700726 }
David Woodhouse3edbf982008-05-30 15:15:13 +0300727 release_firmware(fw);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700728 /* bring device out of reset. Renumeration will occur in a moment
729 and the new device will bind to the real driver */
730 response = ezusb_set_reset(serial, 0);
731
732 /* we want this device to fail to have a driver assigned to it. */
Alan Cox9e70f312008-07-22 11:13:42 +0100733 return 1;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700734}
735
Ben Hutchingse6c4ef92010-01-13 23:34:18 +0000736#ifdef KEYSPAN
737MODULE_FIRMWARE("keyspan_pda/keyspan_pda.fw");
738#endif
739#ifdef XIRCOM
740MODULE_FIRMWARE("keyspan_pda/xircom_pgs.fw");
741#endif
742
Alan Cox9e70f312008-07-22 11:13:42 +0100743static int keyspan_pda_startup(struct usb_serial *serial)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700744{
745
746 struct keyspan_pda_private *priv;
747
748 /* allocate the private data structures for all ports. Well, for all
749 one ports. */
750
751 priv = kmalloc(sizeof(struct keyspan_pda_private), GFP_KERNEL);
752 if (!priv)
Alan Cox9e70f312008-07-22 11:13:42 +0100753 return 1; /* error */
Linus Torvalds1da177e2005-04-16 15:20:36 -0700754 usb_set_serial_port_data(serial->port[0], priv);
755 init_waitqueue_head(&serial->port[0]->write_wait);
David Howellsc4028952006-11-22 14:57:56 +0000756 INIT_WORK(&priv->wakeup_work, keyspan_pda_wakeup_write);
757 INIT_WORK(&priv->unthrottle_work, keyspan_pda_request_unthrottle);
758 priv->serial = serial;
759 priv->port = serial->port[0];
Alan Cox9e70f312008-07-22 11:13:42 +0100760 return 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700761}
762
Alan Sternf9c99bb2009-06-02 11:53:55 -0400763static void keyspan_pda_release(struct usb_serial *serial)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700764{
Linus Torvalds1da177e2005-04-16 15:20:36 -0700765 kfree(usb_get_serial_port_data(serial->port[0]));
766}
767
768#ifdef KEYSPAN
Greg Kroah-Hartmanea653702005-06-20 21:15:16 -0700769static struct usb_serial_driver keyspan_pda_fake_device = {
Greg Kroah-Hartman18fcac32005-06-20 21:15:16 -0700770 .driver = {
771 .owner = THIS_MODULE,
Greg Kroah-Hartman269bda12005-06-20 21:15:16 -0700772 .name = "keyspan_pda_pre",
Greg Kroah-Hartman18fcac32005-06-20 21:15:16 -0700773 },
Greg Kroah-Hartman269bda12005-06-20 21:15:16 -0700774 .description = "Keyspan PDA - (prerenumeration)",
Linus Torvalds1da177e2005-04-16 15:20:36 -0700775 .id_table = id_table_fake,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700776 .num_ports = 1,
777 .attach = keyspan_pda_fake_startup,
778};
779#endif
780
781#ifdef XIRCOM
Greg Kroah-Hartmanea653702005-06-20 21:15:16 -0700782static struct usb_serial_driver xircom_pgs_fake_device = {
Greg Kroah-Hartman18fcac32005-06-20 21:15:16 -0700783 .driver = {
784 .owner = THIS_MODULE,
Greg Kroah-Hartman269bda12005-06-20 21:15:16 -0700785 .name = "xircom_no_firm",
Greg Kroah-Hartman18fcac32005-06-20 21:15:16 -0700786 },
Greg Kroah-Hartman269bda12005-06-20 21:15:16 -0700787 .description = "Xircom / Entregra PGS - (prerenumeration)",
Linus Torvalds1da177e2005-04-16 15:20:36 -0700788 .id_table = id_table_fake_xircom,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700789 .num_ports = 1,
790 .attach = keyspan_pda_fake_startup,
791};
792#endif
793
Greg Kroah-Hartmanea653702005-06-20 21:15:16 -0700794static struct usb_serial_driver keyspan_pda_device = {
Greg Kroah-Hartman18fcac32005-06-20 21:15:16 -0700795 .driver = {
796 .owner = THIS_MODULE,
Greg Kroah-Hartman269bda12005-06-20 21:15:16 -0700797 .name = "keyspan_pda",
Greg Kroah-Hartman18fcac32005-06-20 21:15:16 -0700798 },
Greg Kroah-Hartman269bda12005-06-20 21:15:16 -0700799 .description = "Keyspan PDA",
Linus Torvalds1da177e2005-04-16 15:20:36 -0700800 .id_table = id_table_std,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700801 .num_ports = 1,
Alan Cox335f8512009-06-11 12:26:29 +0100802 .dtr_rts = keyspan_pda_dtr_rts,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700803 .open = keyspan_pda_open,
804 .close = keyspan_pda_close,
805 .write = keyspan_pda_write,
806 .write_room = keyspan_pda_write_room,
807 .write_bulk_callback = keyspan_pda_write_bulk_callback,
808 .read_int_callback = keyspan_pda_rx_interrupt,
809 .chars_in_buffer = keyspan_pda_chars_in_buffer,
810 .throttle = keyspan_pda_rx_throttle,
811 .unthrottle = keyspan_pda_rx_unthrottle,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700812 .set_termios = keyspan_pda_set_termios,
813 .break_ctl = keyspan_pda_break_ctl,
814 .tiocmget = keyspan_pda_tiocmget,
815 .tiocmset = keyspan_pda_tiocmset,
816 .attach = keyspan_pda_startup,
Alan Sternf9c99bb2009-06-02 11:53:55 -0400817 .release = keyspan_pda_release,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700818};
819
Greg Kroah-Hartman8c49fc92012-02-24 12:49:34 -0800820static struct usb_serial_driver * const serial_drivers[] = {
821 &keyspan_pda_device,
822#ifdef KEYSPAN
823 &keyspan_pda_fake_device,
824#endif
825#ifdef XIRCOM
826 &xircom_pgs_fake_device,
827#endif
828 NULL
829};
Linus Torvalds1da177e2005-04-16 15:20:36 -0700830
Greg Kroah-Hartmand40f5b02012-02-28 13:11:59 -0800831module_usb_serial_driver(keyspan_pda_driver, serial_drivers);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700832
Alan Cox9e70f312008-07-22 11:13:42 +0100833MODULE_AUTHOR(DRIVER_AUTHOR);
834MODULE_DESCRIPTION(DRIVER_DESC);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700835MODULE_LICENSE("GPL");
836
837module_param(debug, bool, S_IRUGO | S_IWUSR);
838MODULE_PARM_DESC(debug, "Debug enabled or not");