diff options
-rw-r--r-- | drivers/usb/serial/cypress_m8.c | 617 | ||||
-rw-r--r-- | drivers/usb/serial/cypress_m8.h | 2 |
2 files changed, 325 insertions, 294 deletions
diff --git a/drivers/usb/serial/cypress_m8.c b/drivers/usb/serial/cypress_m8.c index 6999d3372d85..bb9c7c45e98f 100644 --- a/drivers/usb/serial/cypress_m8.c +++ b/drivers/usb/serial/cypress_m8.c | |||
@@ -2,7 +2,7 @@ | |||
2 | * USB Cypress M8 driver | 2 | * USB Cypress M8 driver |
3 | * | 3 | * |
4 | * Copyright (C) 2004 | 4 | * Copyright (C) 2004 |
5 | * Lonnie Mendez (dignome@gmail.com) | 5 | * Lonnie Mendez (dignome@gmail.com) |
6 | * Copyright (C) 2003,2004 | 6 | * Copyright (C) 2003,2004 |
7 | * Neil Whelchel (koyama@firstlight.net) | 7 | * Neil Whelchel (koyama@firstlight.net) |
8 | * | 8 | * |
@@ -11,19 +11,21 @@ | |||
11 | * the Free Software Foundation; either version 2 of the License, or | 11 | * the Free Software Foundation; either version 2 of the License, or |
12 | * (at your option) any later version. | 12 | * (at your option) any later version. |
13 | * | 13 | * |
14 | * See Documentation/usb/usb-serial.txt for more information on using this driver | 14 | * See Documentation/usb/usb-serial.txt for more information on using this |
15 | * driver | ||
15 | * | 16 | * |
16 | * See http://geocities.com/i0xox0i for information on this driver and the | 17 | * See http://geocities.com/i0xox0i for information on this driver and the |
17 | * earthmate usb device. | 18 | * earthmate usb device. |
18 | * | 19 | * |
19 | * Lonnie Mendez <dignome@gmail.com> | 20 | * Lonnie Mendez <dignome@gmail.com> |
20 | * 4-29-2005 | 21 | * 4-29-2005 |
21 | * Fixed problem where setting or retreiving the serial config would fail with | 22 | * Fixed problem where setting or retreiving the serial config would fail |
22 | * EPIPE. Removed CRTS toggling so the driver behaves more like other usbserial | 23 | * with EPIPE. Removed CRTS toggling so the driver behaves more like |
23 | * adapters. Issued new interval of 1ms instead of the default 10ms. As a | 24 | * other usbserial adapters. Issued new interval of 1ms instead of the |
24 | * result, transfer speed has been substantially increased. From avg. 850bps to | 25 | * default 10ms. As a result, transfer speed has been substantially |
25 | * avg. 3300bps. initial termios has also been modified. Cleaned up code and | 26 | * increased from avg. 850bps to avg. 3300bps. initial termios has also |
26 | * formatting issues so it is more readable. Replaced the C++ style comments. | 27 | * been modified. Cleaned up code and formatting issues so it is more |
28 | * readable. Replaced the C++ style comments. | ||
27 | * | 29 | * |
28 | * Lonnie Mendez <dignome@gmail.com> | 30 | * Lonnie Mendez <dignome@gmail.com> |
29 | * 12-15-2004 | 31 | * 12-15-2004 |
@@ -42,10 +44,11 @@ | |||
42 | * | 44 | * |
43 | */ | 45 | */ |
44 | 46 | ||
45 | /* Thanks to Neil Whelchel for writing the first cypress m8 implementation for linux. */ | 47 | /* Thanks to Neil Whelchel for writing the first cypress m8 implementation |
48 | for linux. */ | ||
46 | /* Thanks to cypress for providing references for the hid reports. */ | 49 | /* Thanks to cypress for providing references for the hid reports. */ |
47 | /* Thanks to Jiang Zhang for providing links and for general help. */ | 50 | /* Thanks to Jiang Zhang for providing links and for general help. */ |
48 | /* Code originates and was built up from ftdi_sio, belkin, pl2303 and others. */ | 51 | /* Code originates and was built up from ftdi_sio, belkin, pl2303 and others.*/ |
49 | 52 | ||
50 | 53 | ||
51 | #include <linux/kernel.h> | 54 | #include <linux/kernel.h> |
@@ -62,7 +65,7 @@ | |||
62 | #include <linux/usb/serial.h> | 65 | #include <linux/usb/serial.h> |
63 | #include <linux/serial.h> | 66 | #include <linux/serial.h> |
64 | #include <linux/delay.h> | 67 | #include <linux/delay.h> |
65 | #include <asm/uaccess.h> | 68 | #include <linux/uaccess.h> |
66 | 69 | ||
67 | #include "cypress_m8.h" | 70 | #include "cypress_m8.h" |
68 | 71 | ||
@@ -112,7 +115,7 @@ static struct usb_device_id id_table_combined [] = { | |||
112 | { } /* Terminating entry */ | 115 | { } /* Terminating entry */ |
113 | }; | 116 | }; |
114 | 117 | ||
115 | MODULE_DEVICE_TABLE (usb, id_table_combined); | 118 | MODULE_DEVICE_TABLE(usb, id_table_combined); |
116 | 119 | ||
117 | static struct usb_driver cypress_driver = { | 120 | static struct usb_driver cypress_driver = { |
118 | .name = "cypress", | 121 | .name = "cypress", |
@@ -146,11 +149,13 @@ struct cypress_private { | |||
146 | __u8 rx_flags; /* throttling - used from whiteheat/ftdi_sio */ | 149 | __u8 rx_flags; /* throttling - used from whiteheat/ftdi_sio */ |
147 | enum packet_format pkt_fmt; /* format to use for packet send / receive */ | 150 | enum packet_format pkt_fmt; /* format to use for packet send / receive */ |
148 | int get_cfg_unsafe; /* If true, the CYPRESS_GET_CONFIG is unsafe */ | 151 | int get_cfg_unsafe; /* If true, the CYPRESS_GET_CONFIG is unsafe */ |
149 | int baud_rate; /* stores current baud rate in integer form */ | 152 | int baud_rate; /* stores current baud rate in |
153 | integer form */ | ||
150 | int isthrottled; /* if throttled, discard reads */ | 154 | int isthrottled; /* if throttled, discard reads */ |
151 | wait_queue_head_t delta_msr_wait; /* used for TIOCMIWAIT */ | 155 | wait_queue_head_t delta_msr_wait; /* used for TIOCMIWAIT */ |
152 | char prev_status, diff_status; /* used for TIOCMIWAIT */ | 156 | char prev_status, diff_status; /* used for TIOCMIWAIT */ |
153 | /* we pass a pointer to this as the arguement sent to cypress_set_termios old_termios */ | 157 | /* we pass a pointer to this as the arguement sent to |
158 | cypress_set_termios old_termios */ | ||
154 | struct ktermios tmp_termios; /* stores the old termios settings */ | 159 | struct ktermios tmp_termios; /* stores the old termios settings */ |
155 | }; | 160 | }; |
156 | 161 | ||
@@ -163,33 +168,41 @@ struct cypress_buf { | |||
163 | }; | 168 | }; |
164 | 169 | ||
165 | /* function prototypes for the Cypress USB to serial device */ | 170 | /* function prototypes for the Cypress USB to serial device */ |
166 | static int cypress_earthmate_startup (struct usb_serial *serial); | 171 | static int cypress_earthmate_startup(struct usb_serial *serial); |
167 | static int cypress_hidcom_startup (struct usb_serial *serial); | 172 | static int cypress_hidcom_startup(struct usb_serial *serial); |
168 | static int cypress_ca42v2_startup (struct usb_serial *serial); | 173 | static int cypress_ca42v2_startup(struct usb_serial *serial); |
169 | static void cypress_shutdown (struct usb_serial *serial); | 174 | static void cypress_shutdown(struct usb_serial *serial); |
170 | static int cypress_open (struct tty_struct *tty, struct usb_serial_port *port, struct file *filp); | 175 | static int cypress_open(struct tty_struct *tty, |
171 | static void cypress_close (struct tty_struct *tty, struct usb_serial_port *port, struct file *filp); | 176 | struct usb_serial_port *port, struct file *filp); |
172 | static int cypress_write (struct tty_struct *tty, struct usb_serial_port *port, const unsigned char *buf, int count); | 177 | static void cypress_close(struct tty_struct *tty, |
173 | static void cypress_send (struct usb_serial_port *port); | 178 | struct usb_serial_port *port, struct file *filp); |
174 | static int cypress_write_room (struct tty_struct *tty); | 179 | static int cypress_write(struct tty_struct *tty, struct usb_serial_port *port, |
175 | static int cypress_ioctl (struct tty_struct *tty, struct file * file, unsigned int cmd, unsigned long arg); | 180 | const unsigned char *buf, int count); |
176 | static void cypress_set_termios (struct tty_struct *tty, struct usb_serial_port *port, struct ktermios * old); | 181 | static void cypress_send(struct usb_serial_port *port); |
177 | static int cypress_tiocmget (struct tty_struct *tty, struct file *file); | 182 | static int cypress_write_room(struct tty_struct *tty); |
178 | static int cypress_tiocmset (struct tty_struct *tty, struct file *file, unsigned int set, unsigned int clear); | 183 | static int cypress_ioctl(struct tty_struct *tty, struct file *file, |
179 | static int cypress_chars_in_buffer (struct tty_struct *tty); | 184 | unsigned int cmd, unsigned long arg); |
180 | static void cypress_throttle (struct tty_struct *tty); | 185 | static void cypress_set_termios(struct tty_struct *tty, |
181 | static void cypress_unthrottle (struct tty_struct *tty); | 186 | struct usb_serial_port *port, struct ktermios *old); |
182 | static void cypress_set_dead (struct usb_serial_port *port); | 187 | static int cypress_tiocmget(struct tty_struct *tty, struct file *file); |
183 | static void cypress_read_int_callback (struct urb *urb); | 188 | static int cypress_tiocmset(struct tty_struct *tty, struct file *file, |
184 | static void cypress_write_int_callback (struct urb *urb); | 189 | unsigned int set, unsigned int clear); |
190 | static int cypress_chars_in_buffer(struct tty_struct *tty); | ||
191 | static void cypress_throttle(struct tty_struct *tty); | ||
192 | static void cypress_unthrottle(struct tty_struct *tty); | ||
193 | static void cypress_set_dead(struct usb_serial_port *port); | ||
194 | static void cypress_read_int_callback(struct urb *urb); | ||
195 | static void cypress_write_int_callback(struct urb *urb); | ||
185 | /* write buffer functions */ | 196 | /* write buffer functions */ |
186 | static struct cypress_buf *cypress_buf_alloc(unsigned int size); | 197 | static struct cypress_buf *cypress_buf_alloc(unsigned int size); |
187 | static void cypress_buf_free(struct cypress_buf *cb); | 198 | static void cypress_buf_free(struct cypress_buf *cb); |
188 | static void cypress_buf_clear(struct cypress_buf *cb); | 199 | static void cypress_buf_clear(struct cypress_buf *cb); |
189 | static unsigned int cypress_buf_data_avail(struct cypress_buf *cb); | 200 | static unsigned int cypress_buf_data_avail(struct cypress_buf *cb); |
190 | static unsigned int cypress_buf_space_avail(struct cypress_buf *cb); | 201 | static unsigned int cypress_buf_space_avail(struct cypress_buf *cb); |
191 | static unsigned int cypress_buf_put(struct cypress_buf *cb, const char *buf, unsigned int count); | 202 | static unsigned int cypress_buf_put(struct cypress_buf *cb, |
192 | static unsigned int cypress_buf_get(struct cypress_buf *cb, char *buf, unsigned int count); | 203 | const char *buf, unsigned int count); |
204 | static unsigned int cypress_buf_get(struct cypress_buf *cb, | ||
205 | char *buf, unsigned int count); | ||
193 | 206 | ||
194 | 207 | ||
195 | static struct usb_serial_driver cypress_earthmate_device = { | 208 | static struct usb_serial_driver cypress_earthmate_device = { |
@@ -247,7 +260,7 @@ static struct usb_serial_driver cypress_hidcom_device = { | |||
247 | static struct usb_serial_driver cypress_ca42v2_device = { | 260 | static struct usb_serial_driver cypress_ca42v2_device = { |
248 | .driver = { | 261 | .driver = { |
249 | .owner = THIS_MODULE, | 262 | .owner = THIS_MODULE, |
250 | .name = "nokiaca42v2", | 263 | .name = "nokiaca42v2", |
251 | }, | 264 | }, |
252 | .description = "Nokia CA-42 V2 Adapter", | 265 | .description = "Nokia CA-42 V2 Adapter", |
253 | .usb_driver = &cypress_driver, | 266 | .usb_driver = &cypress_driver, |
@@ -322,7 +335,7 @@ static int analyze_baud_rate(struct usb_serial_port *port, speed_t new_rate) | |||
322 | 335 | ||
323 | 336 | ||
324 | /* This function can either set or retrieve the current serial line settings */ | 337 | /* This function can either set or retrieve the current serial line settings */ |
325 | static int cypress_serial_control (struct tty_struct *tty, | 338 | static int cypress_serial_control(struct tty_struct *tty, |
326 | struct usb_serial_port *port, speed_t baud_rate, int data_bits, | 339 | struct usb_serial_port *port, speed_t baud_rate, int data_bits, |
327 | int stop_bits, int parity_enable, int parity_type, int reset, | 340 | int stop_bits, int parity_enable, int parity_type, int reset, |
328 | int cypress_request_type) | 341 | int cypress_request_type) |
@@ -333,111 +346,114 @@ static int cypress_serial_control (struct tty_struct *tty, | |||
333 | unsigned long flags; | 346 | unsigned long flags; |
334 | 347 | ||
335 | dbg("%s", __func__); | 348 | dbg("%s", __func__); |
336 | 349 | ||
337 | priv = usb_get_serial_port_data(port); | 350 | priv = usb_get_serial_port_data(port); |
338 | 351 | ||
339 | if (!priv->comm_is_ok) | 352 | if (!priv->comm_is_ok) |
340 | return -ENODEV; | 353 | return -ENODEV; |
341 | 354 | ||
342 | switch(cypress_request_type) { | 355 | switch (cypress_request_type) { |
343 | case CYPRESS_SET_CONFIG: | 356 | case CYPRESS_SET_CONFIG: |
357 | new_baudrate = priv->baud_rate; | ||
358 | /* 0 means 'Hang up' so doesn't change the true bit rate */ | ||
359 | if (baud_rate == 0) | ||
344 | new_baudrate = priv->baud_rate; | 360 | new_baudrate = priv->baud_rate; |
345 | /* 0 means 'Hang up' so doesn't change the true bit rate */ | 361 | /* Change of speed ? */ |
346 | if (baud_rate == 0) | 362 | else if (baud_rate != priv->baud_rate) { |
347 | new_baudrate = priv->baud_rate; | 363 | dbg("%s - baud rate is changing", __func__); |
348 | /* Change of speed ? */ | 364 | retval = analyze_baud_rate(port, baud_rate); |
349 | else if (baud_rate != priv->baud_rate) { | 365 | if (retval >= 0) { |
350 | dbg("%s - baud rate is changing", __func__); | 366 | new_baudrate = retval; |
351 | retval = analyze_baud_rate(port, baud_rate); | 367 | dbg("%s - New baud rate set to %d", |
352 | if (retval >= 0) { | 368 | __func__, new_baudrate); |
353 | new_baudrate = retval; | ||
354 | dbg("%s - New baud rate set to %d", | ||
355 | __func__, new_baudrate); | ||
356 | } | ||
357 | } | ||
358 | dbg("%s - baud rate is being sent as %d", __func__, new_baudrate); | ||
359 | |||
360 | memset(feature_buffer, 0, sizeof(feature_buffer)); | ||
361 | /* fill the feature_buffer with new configuration */ | ||
362 | *((u_int32_t *)feature_buffer) = new_baudrate; | ||
363 | |||
364 | feature_buffer[4] |= data_bits; /* assign data bits in 2 bit space ( max 3 ) */ | ||
365 | /* 1 bit gap */ | ||
366 | feature_buffer[4] |= (stop_bits << 3); /* assign stop bits in 1 bit space */ | ||
367 | feature_buffer[4] |= (parity_enable << 4); /* assign parity flag in 1 bit space */ | ||
368 | feature_buffer[4] |= (parity_type << 5); /* assign parity type in 1 bit space */ | ||
369 | /* 1 bit gap */ | ||
370 | feature_buffer[4] |= (reset << 7); /* assign reset at end of byte, 1 bit space */ | ||
371 | |||
372 | dbg("%s - device is being sent this feature report:", __func__); | ||
373 | dbg("%s - %02X - %02X - %02X - %02X - %02X", __func__, feature_buffer[0], feature_buffer[1], | ||
374 | feature_buffer[2], feature_buffer[3], feature_buffer[4]); | ||
375 | |||
376 | do { | ||
377 | retval = usb_control_msg(port->serial->dev, | ||
378 | usb_sndctrlpipe(port->serial->dev, 0), | ||
379 | HID_REQ_SET_REPORT, | ||
380 | USB_DIR_OUT | USB_RECIP_INTERFACE | USB_TYPE_CLASS, | ||
381 | 0x0300, 0, feature_buffer, | ||
382 | sizeof(feature_buffer), 500); | ||
383 | |||
384 | if (tries++ >= 3) | ||
385 | break; | ||
386 | |||
387 | } while (retval != sizeof(feature_buffer) && | ||
388 | retval != -ENODEV); | ||
389 | |||
390 | if (retval != sizeof(feature_buffer)) { | ||
391 | err("%s - failed sending serial line settings - %d", __func__, retval); | ||
392 | cypress_set_dead(port); | ||
393 | } else { | ||
394 | spin_lock_irqsave(&priv->lock, flags); | ||
395 | priv->baud_rate = new_baudrate; | ||
396 | priv->current_config = feature_buffer[4]; | ||
397 | spin_unlock_irqrestore(&priv->lock, flags); | ||
398 | /* If we asked for a speed change encode it */ | ||
399 | if (baud_rate) | ||
400 | tty_encode_baud_rate(tty, | ||
401 | new_baudrate, new_baudrate); | ||
402 | } | ||
403 | break; | ||
404 | case CYPRESS_GET_CONFIG: | ||
405 | if (priv->get_cfg_unsafe) { | ||
406 | /* Not implemented for this device, | ||
407 | and if we try to do it we're likely | ||
408 | to crash the hardware. */ | ||
409 | return -ENOTTY; | ||
410 | } | ||
411 | dbg("%s - retreiving serial line settings", __func__); | ||
412 | /* set initial values in feature buffer */ | ||
413 | memset(feature_buffer, 0, sizeof(feature_buffer)); | ||
414 | |||
415 | do { | ||
416 | retval = usb_control_msg(port->serial->dev, | ||
417 | usb_rcvctrlpipe(port->serial->dev, 0), | ||
418 | HID_REQ_GET_REPORT, | ||
419 | USB_DIR_IN | USB_RECIP_INTERFACE | USB_TYPE_CLASS, | ||
420 | 0x0300, 0, feature_buffer, | ||
421 | sizeof(feature_buffer), 500); | ||
422 | |||
423 | if (tries++ >= 3) | ||
424 | break; | ||
425 | |||
426 | } while (retval != sizeof(feature_buffer) && | ||
427 | retval != -ENODEV); | ||
428 | |||
429 | if (retval != sizeof(feature_buffer)) { | ||
430 | err("%s - failed to retrieve serial line settings - %d", __func__, retval); | ||
431 | cypress_set_dead(port); | ||
432 | return retval; | ||
433 | } else { | ||
434 | spin_lock_irqsave(&priv->lock, flags); | ||
435 | |||
436 | /* store the config in one byte, and later use bit masks to check values */ | ||
437 | priv->current_config = feature_buffer[4]; | ||
438 | priv->baud_rate = *((u_int32_t *)feature_buffer); | ||
439 | spin_unlock_irqrestore(&priv->lock, flags); | ||
440 | } | 369 | } |
370 | } | ||
371 | dbg("%s - baud rate is being sent as %d", | ||
372 | __func__, new_baudrate); | ||
373 | |||
374 | memset(feature_buffer, 0, sizeof(feature_buffer)); | ||
375 | /* fill the feature_buffer with new configuration */ | ||
376 | *((u_int32_t *)feature_buffer) = new_baudrate; | ||
377 | feature_buffer[4] |= data_bits; /* assign data bits in 2 bit space ( max 3 ) */ | ||
378 | /* 1 bit gap */ | ||
379 | feature_buffer[4] |= (stop_bits << 3); /* assign stop bits in 1 bit space */ | ||
380 | feature_buffer[4] |= (parity_enable << 4); /* assign parity flag in 1 bit space */ | ||
381 | feature_buffer[4] |= (parity_type << 5); /* assign parity type in 1 bit space */ | ||
382 | /* 1 bit gap */ | ||
383 | feature_buffer[4] |= (reset << 7); /* assign reset at end of byte, 1 bit space */ | ||
384 | |||
385 | dbg("%s - device is being sent this feature report:", | ||
386 | __func__); | ||
387 | dbg("%s - %02X - %02X - %02X - %02X - %02X", __func__, | ||
388 | feature_buffer[0], feature_buffer[1], | ||
389 | feature_buffer[2], feature_buffer[3], | ||
390 | feature_buffer[4]); | ||
391 | |||
392 | do { | ||
393 | retval = usb_control_msg(port->serial->dev, | ||
394 | usb_sndctrlpipe(port->serial->dev, 0), | ||
395 | HID_REQ_SET_REPORT, | ||
396 | USB_DIR_OUT | USB_RECIP_INTERFACE | USB_TYPE_CLASS, | ||
397 | 0x0300, 0, feature_buffer, | ||
398 | sizeof(feature_buffer), 500); | ||
399 | |||
400 | if (tries++ >= 3) | ||
401 | break; | ||
402 | |||
403 | } while (retval != sizeof(feature_buffer) && | ||
404 | retval != -ENODEV); | ||
405 | |||
406 | if (retval != sizeof(feature_buffer)) { | ||
407 | err("%s - failed sending serial line settings - %d", | ||
408 | __func__, retval); | ||
409 | cypress_set_dead(port); | ||
410 | } else { | ||
411 | spin_lock_irqsave(&priv->lock, flags); | ||
412 | priv->baud_rate = new_baudrate; | ||
413 | priv->current_config = feature_buffer[4]; | ||
414 | spin_unlock_irqrestore(&priv->lock, flags); | ||
415 | /* If we asked for a speed change encode it */ | ||
416 | if (baud_rate) | ||
417 | tty_encode_baud_rate(tty, | ||
418 | new_baudrate, new_baudrate); | ||
419 | } | ||
420 | break; | ||
421 | case CYPRESS_GET_CONFIG: | ||
422 | if (priv->get_cfg_unsafe) { | ||
423 | /* Not implemented for this device, | ||
424 | and if we try to do it we're likely | ||
425 | to crash the hardware. */ | ||
426 | return -ENOTTY; | ||
427 | } | ||
428 | dbg("%s - retreiving serial line settings", __func__); | ||
429 | /* set initial values in feature buffer */ | ||
430 | memset(feature_buffer, 0, sizeof(feature_buffer)); | ||
431 | |||
432 | do { | ||
433 | retval = usb_control_msg(port->serial->dev, | ||
434 | usb_rcvctrlpipe(port->serial->dev, 0), | ||
435 | HID_REQ_GET_REPORT, | ||
436 | USB_DIR_IN | USB_RECIP_INTERFACE | USB_TYPE_CLASS, | ||
437 | 0x0300, 0, feature_buffer, | ||
438 | sizeof(feature_buffer), 500); | ||
439 | |||
440 | if (tries++ >= 3) | ||
441 | break; | ||
442 | } while (retval != sizeof(feature_buffer) | ||
443 | && retval != -ENODEV); | ||
444 | |||
445 | if (retval != sizeof(feature_buffer)) { | ||
446 | err("%s - failed to retrieve serial line settings - %d", __func__, retval); | ||
447 | cypress_set_dead(port); | ||
448 | return retval; | ||
449 | } else { | ||
450 | spin_lock_irqsave(&priv->lock, flags); | ||
451 | /* store the config in one byte, and later | ||
452 | use bit masks to check values */ | ||
453 | priv->current_config = feature_buffer[4]; | ||
454 | priv->baud_rate = *((u_int32_t *)feature_buffer); | ||
455 | spin_unlock_irqrestore(&priv->lock, flags); | ||
456 | } | ||
441 | } | 457 | } |
442 | spin_lock_irqsave(&priv->lock, flags); | 458 | spin_lock_irqsave(&priv->lock, flags); |
443 | ++priv->cmd_count; | 459 | ++priv->cmd_count; |
@@ -470,14 +486,14 @@ static void cypress_set_dead(struct usb_serial_port *port) | |||
470 | *****************************************************************************/ | 486 | *****************************************************************************/ |
471 | 487 | ||
472 | 488 | ||
473 | static int generic_startup (struct usb_serial *serial) | 489 | static int generic_startup(struct usb_serial *serial) |
474 | { | 490 | { |
475 | struct cypress_private *priv; | 491 | struct cypress_private *priv; |
476 | struct usb_serial_port *port = serial->port[0]; | 492 | struct usb_serial_port *port = serial->port[0]; |
477 | 493 | ||
478 | dbg("%s - port %d", __func__, port->number); | 494 | dbg("%s - port %d", __func__, port->number); |
479 | 495 | ||
480 | priv = kzalloc(sizeof (struct cypress_private), GFP_KERNEL); | 496 | priv = kzalloc(sizeof(struct cypress_private), GFP_KERNEL); |
481 | if (!priv) | 497 | if (!priv) |
482 | return -ENOMEM; | 498 | return -ENOMEM; |
483 | 499 | ||
@@ -489,9 +505,9 @@ static int generic_startup (struct usb_serial *serial) | |||
489 | return -ENOMEM; | 505 | return -ENOMEM; |
490 | } | 506 | } |
491 | init_waitqueue_head(&priv->delta_msr_wait); | 507 | init_waitqueue_head(&priv->delta_msr_wait); |
492 | 508 | ||
493 | usb_reset_configuration (serial->dev); | 509 | usb_reset_configuration(serial->dev); |
494 | 510 | ||
495 | priv->cmd_ctrl = 0; | 511 | priv->cmd_ctrl = 0; |
496 | priv->line_control = 0; | 512 | priv->line_control = 0; |
497 | priv->termios_initialized = 0; | 513 | priv->termios_initialized = 0; |
@@ -502,30 +518,30 @@ static int generic_startup (struct usb_serial *serial) | |||
502 | small. Otherwise we can use the slightly more compact | 518 | small. Otherwise we can use the slightly more compact |
503 | format. This is in accordance with the cypress_m8 serial | 519 | format. This is in accordance with the cypress_m8 serial |
504 | converter app note. */ | 520 | converter app note. */ |
505 | if (port->interrupt_out_size > 9) { | 521 | if (port->interrupt_out_size > 9) |
506 | priv->pkt_fmt = packet_format_1; | 522 | priv->pkt_fmt = packet_format_1; |
507 | } else { | 523 | else |
508 | priv->pkt_fmt = packet_format_2; | 524 | priv->pkt_fmt = packet_format_2; |
509 | } | 525 | |
510 | if (interval > 0) { | 526 | if (interval > 0) { |
511 | priv->write_urb_interval = interval; | 527 | priv->write_urb_interval = interval; |
512 | priv->read_urb_interval = interval; | 528 | priv->read_urb_interval = interval; |
513 | dbg("%s - port %d read & write intervals forced to %d", | 529 | dbg("%s - port %d read & write intervals forced to %d", |
514 | __func__,port->number,interval); | 530 | __func__, port->number, interval); |
515 | } else { | 531 | } else { |
516 | priv->write_urb_interval = port->interrupt_out_urb->interval; | 532 | priv->write_urb_interval = port->interrupt_out_urb->interval; |
517 | priv->read_urb_interval = port->interrupt_in_urb->interval; | 533 | priv->read_urb_interval = port->interrupt_in_urb->interval; |
518 | dbg("%s - port %d intervals: read=%d write=%d", | 534 | dbg("%s - port %d intervals: read=%d write=%d", |
519 | __func__,port->number, | 535 | __func__, port->number, |
520 | priv->read_urb_interval,priv->write_urb_interval); | 536 | priv->read_urb_interval, priv->write_urb_interval); |
521 | } | 537 | } |
522 | usb_set_serial_port_data(port, priv); | 538 | usb_set_serial_port_data(port, priv); |
523 | 539 | ||
524 | return 0; | 540 | return 0; |
525 | } | 541 | } |
526 | 542 | ||
527 | 543 | ||
528 | static int cypress_earthmate_startup (struct usb_serial *serial) | 544 | static int cypress_earthmate_startup(struct usb_serial *serial) |
529 | { | 545 | { |
530 | struct cypress_private *priv; | 546 | struct cypress_private *priv; |
531 | struct usb_serial_port *port = serial->port[0]; | 547 | struct usb_serial_port *port = serial->port[0]; |
@@ -543,7 +559,8 @@ static int cypress_earthmate_startup (struct usb_serial *serial) | |||
543 | /* All Earthmate devices use the separated-count packet | 559 | /* All Earthmate devices use the separated-count packet |
544 | format! Idiotic. */ | 560 | format! Idiotic. */ |
545 | priv->pkt_fmt = packet_format_1; | 561 | priv->pkt_fmt = packet_format_1; |
546 | if (serial->dev->descriptor.idProduct != cpu_to_le16(PRODUCT_ID_EARTHMATEUSB)) { | 562 | if (serial->dev->descriptor.idProduct != |
563 | cpu_to_le16(PRODUCT_ID_EARTHMATEUSB)) { | ||
547 | /* The old original USB Earthmate seemed able to | 564 | /* The old original USB Earthmate seemed able to |
548 | handle GET_CONFIG requests; everything they've | 565 | handle GET_CONFIG requests; everything they've |
549 | produced since that time crashes if this command is | 566 | produced since that time crashes if this command is |
@@ -557,7 +574,7 @@ static int cypress_earthmate_startup (struct usb_serial *serial) | |||
557 | } /* cypress_earthmate_startup */ | 574 | } /* cypress_earthmate_startup */ |
558 | 575 | ||
559 | 576 | ||
560 | static int cypress_hidcom_startup (struct usb_serial *serial) | 577 | static int cypress_hidcom_startup(struct usb_serial *serial) |
561 | { | 578 | { |
562 | struct cypress_private *priv; | 579 | struct cypress_private *priv; |
563 | 580 | ||
@@ -571,12 +588,12 @@ static int cypress_hidcom_startup (struct usb_serial *serial) | |||
571 | 588 | ||
572 | priv = usb_get_serial_port_data(serial->port[0]); | 589 | priv = usb_get_serial_port_data(serial->port[0]); |
573 | priv->chiptype = CT_CYPHIDCOM; | 590 | priv->chiptype = CT_CYPHIDCOM; |
574 | 591 | ||
575 | return 0; | 592 | return 0; |
576 | } /* cypress_hidcom_startup */ | 593 | } /* cypress_hidcom_startup */ |
577 | 594 | ||
578 | 595 | ||
579 | static int cypress_ca42v2_startup (struct usb_serial *serial) | 596 | static int cypress_ca42v2_startup(struct usb_serial *serial) |
580 | { | 597 | { |
581 | struct cypress_private *priv; | 598 | struct cypress_private *priv; |
582 | 599 | ||
@@ -595,11 +612,11 @@ static int cypress_ca42v2_startup (struct usb_serial *serial) | |||
595 | } /* cypress_ca42v2_startup */ | 612 | } /* cypress_ca42v2_startup */ |
596 | 613 | ||
597 | 614 | ||
598 | static void cypress_shutdown (struct usb_serial *serial) | 615 | static void cypress_shutdown(struct usb_serial *serial) |
599 | { | 616 | { |
600 | struct cypress_private *priv; | 617 | struct cypress_private *priv; |
601 | 618 | ||
602 | dbg ("%s - port %d", __func__, serial->port[0]->number); | 619 | dbg("%s - port %d", __func__, serial->port[0]->number); |
603 | 620 | ||
604 | /* all open ports are closed at this point */ | 621 | /* all open ports are closed at this point */ |
605 | 622 | ||
@@ -650,7 +667,9 @@ static int cypress_open(struct tty_struct *tty, | |||
650 | result = cypress_write(tty, port, NULL, 0); | 667 | result = cypress_write(tty, port, NULL, 0); |
651 | 668 | ||
652 | if (result) { | 669 | if (result) { |
653 | dev_err(&port->dev, "%s - failed setting the control lines - error %d\n", __func__, result); | 670 | dev_err(&port->dev, |
671 | "%s - failed setting the control lines - error %d\n", | ||
672 | __func__, result); | ||
654 | return result; | 673 | return result; |
655 | } else | 674 | } else |
656 | dbg("%s - success setting the control lines", __func__); | 675 | dbg("%s - success setting the control lines", __func__); |
@@ -659,19 +678,22 @@ static int cypress_open(struct tty_struct *tty, | |||
659 | cypress_set_termios(tty, port, &priv->tmp_termios); | 678 | cypress_set_termios(tty, port, &priv->tmp_termios); |
660 | 679 | ||
661 | /* setup the port and start reading from the device */ | 680 | /* setup the port and start reading from the device */ |
662 | if(!port->interrupt_in_urb){ | 681 | if (!port->interrupt_in_urb) { |
663 | err("%s - interrupt_in_urb is empty!", __func__); | 682 | err("%s - interrupt_in_urb is empty!", __func__); |
664 | return(-1); | 683 | return -1; |
665 | } | 684 | } |
666 | 685 | ||
667 | usb_fill_int_urb(port->interrupt_in_urb, serial->dev, | 686 | usb_fill_int_urb(port->interrupt_in_urb, serial->dev, |
668 | usb_rcvintpipe(serial->dev, port->interrupt_in_endpointAddress), | 687 | usb_rcvintpipe(serial->dev, port->interrupt_in_endpointAddress), |
669 | port->interrupt_in_urb->transfer_buffer, port->interrupt_in_urb->transfer_buffer_length, | 688 | port->interrupt_in_urb->transfer_buffer, |
689 | port->interrupt_in_urb->transfer_buffer_length, | ||
670 | cypress_read_int_callback, port, priv->read_urb_interval); | 690 | cypress_read_int_callback, port, priv->read_urb_interval); |
671 | result = usb_submit_urb(port->interrupt_in_urb, GFP_KERNEL); | 691 | result = usb_submit_urb(port->interrupt_in_urb, GFP_KERNEL); |
672 | 692 | ||
673 | if (result){ | 693 | if (result) { |
674 | dev_err(&port->dev, "%s - failed submitting read urb, error %d\n", __func__, result); | 694 | dev_err(&port->dev, |
695 | "%s - failed submitting read urb, error %d\n", | ||
696 | __func__, result); | ||
675 | cypress_set_dead(port); | 697 | cypress_set_dead(port); |
676 | } | 698 | } |
677 | 699 | ||
@@ -680,7 +702,7 @@ static int cypress_open(struct tty_struct *tty, | |||
680 | 702 | ||
681 | 703 | ||
682 | static void cypress_close(struct tty_struct *tty, | 704 | static void cypress_close(struct tty_struct *tty, |
683 | struct usb_serial_port *port, struct file * filp) | 705 | struct usb_serial_port *port, struct file *filp) |
684 | { | 706 | { |
685 | struct cypress_private *priv = usb_get_serial_port_data(port); | 707 | struct cypress_private *priv = usb_get_serial_port_data(port); |
686 | unsigned int c_cflag; | 708 | unsigned int c_cflag; |
@@ -722,15 +744,15 @@ static void cypress_close(struct tty_struct *tty, | |||
722 | if (tty) { | 744 | if (tty) { |
723 | bps = tty_get_baud_rate(tty); | 745 | bps = tty_get_baud_rate(tty); |
724 | if (bps > 1200) | 746 | if (bps > 1200) |
725 | timeout = max((HZ*2560)/bps,HZ/10); | 747 | timeout = max((HZ * 2560) / bps, HZ / 10); |
726 | else | 748 | else |
727 | timeout = 2*HZ; | 749 | timeout = 2 * HZ; |
728 | schedule_timeout_interruptible(timeout); | 750 | schedule_timeout_interruptible(timeout); |
729 | } | 751 | } |
730 | 752 | ||
731 | dbg("%s - stopping urbs", __func__); | 753 | dbg("%s - stopping urbs", __func__); |
732 | usb_kill_urb (port->interrupt_in_urb); | 754 | usb_kill_urb(port->interrupt_in_urb); |
733 | usb_kill_urb (port->interrupt_out_urb); | 755 | usb_kill_urb(port->interrupt_out_urb); |
734 | 756 | ||
735 | if (tty) { | 757 | if (tty) { |
736 | c_cflag = tty->termios->c_cflag; | 758 | c_cflag = tty->termios->c_cflag; |
@@ -746,8 +768,8 @@ static void cypress_close(struct tty_struct *tty, | |||
746 | } | 768 | } |
747 | 769 | ||
748 | if (stats) | 770 | if (stats) |
749 | dev_info (&port->dev, "Statistics: %d Bytes In | %d Bytes Out | %d Commands Issued\n", | 771 | dev_info(&port->dev, "Statistics: %d Bytes In | %d Bytes Out | %d Commands Issued\n", |
750 | priv->bytes_in, priv->bytes_out, priv->cmd_count); | 772 | priv->bytes_in, priv->bytes_out, priv->cmd_count); |
751 | mutex_unlock(&port->serial->disc_mutex); | 773 | mutex_unlock(&port->serial->disc_mutex); |
752 | } /* cypress_close */ | 774 | } /* cypress_close */ |
753 | 775 | ||
@@ -757,7 +779,7 @@ static int cypress_write(struct tty_struct *tty, struct usb_serial_port *port, | |||
757 | { | 779 | { |
758 | struct cypress_private *priv = usb_get_serial_port_data(port); | 780 | struct cypress_private *priv = usb_get_serial_port_data(port); |
759 | unsigned long flags; | 781 | unsigned long flags; |
760 | 782 | ||
761 | dbg("%s - port %d, %d bytes", __func__, port->number, count); | 783 | dbg("%s - port %d, %d bytes", __func__, port->number, count); |
762 | 784 | ||
763 | /* line control commands, which need to be executed immediately, | 785 | /* line control commands, which need to be executed immediately, |
@@ -767,10 +789,10 @@ static int cypress_write(struct tty_struct *tty, struct usb_serial_port *port, | |||
767 | count = 0; | 789 | count = 0; |
768 | goto finish; | 790 | goto finish; |
769 | } | 791 | } |
770 | 792 | ||
771 | if (!count) | 793 | if (!count) |
772 | return count; | 794 | return count; |
773 | 795 | ||
774 | spin_lock_irqsave(&priv->lock, flags); | 796 | spin_lock_irqsave(&priv->lock, flags); |
775 | count = cypress_buf_put(priv->buf, buf, count); | 797 | count = cypress_buf_put(priv->buf, buf, count); |
776 | spin_unlock_irqrestore(&priv->lock, flags); | 798 | spin_unlock_irqrestore(&priv->lock, flags); |
@@ -787,13 +809,14 @@ static void cypress_send(struct usb_serial_port *port) | |||
787 | int count = 0, result, offset, actual_size; | 809 | int count = 0, result, offset, actual_size; |
788 | struct cypress_private *priv = usb_get_serial_port_data(port); | 810 | struct cypress_private *priv = usb_get_serial_port_data(port); |
789 | unsigned long flags; | 811 | unsigned long flags; |
790 | 812 | ||
791 | if (!priv->comm_is_ok) | 813 | if (!priv->comm_is_ok) |
792 | return; | 814 | return; |
793 | 815 | ||
794 | dbg("%s - port %d", __func__, port->number); | 816 | dbg("%s - port %d", __func__, port->number); |
795 | dbg("%s - interrupt out size is %d", __func__, port->interrupt_out_size); | 817 | dbg("%s - interrupt out size is %d", __func__, |
796 | 818 | port->interrupt_out_size); | |
819 | |||
797 | spin_lock_irqsave(&priv->lock, flags); | 820 | spin_lock_irqsave(&priv->lock, flags); |
798 | if (priv->write_urb_in_use) { | 821 | if (priv->write_urb_in_use) { |
799 | dbg("%s - can't write, urb in use", __func__); | 822 | dbg("%s - can't write, urb in use", __func__); |
@@ -803,7 +826,8 @@ static void cypress_send(struct usb_serial_port *port) | |||
803 | spin_unlock_irqrestore(&priv->lock, flags); | 826 | spin_unlock_irqrestore(&priv->lock, flags); |
804 | 827 | ||
805 | /* clear buffer */ | 828 | /* clear buffer */ |
806 | memset(port->interrupt_out_urb->transfer_buffer, 0, port->interrupt_out_size); | 829 | memset(port->interrupt_out_urb->transfer_buffer, 0, |
830 | port->interrupt_out_size); | ||
807 | 831 | ||
808 | spin_lock_irqsave(&priv->lock, flags); | 832 | spin_lock_irqsave(&priv->lock, flags); |
809 | switch (priv->pkt_fmt) { | 833 | switch (priv->pkt_fmt) { |
@@ -834,9 +858,8 @@ static void cypress_send(struct usb_serial_port *port) | |||
834 | count = cypress_buf_get(priv->buf, &port->interrupt_out_buffer[offset], | 858 | count = cypress_buf_get(priv->buf, &port->interrupt_out_buffer[offset], |
835 | port->interrupt_out_size-offset); | 859 | port->interrupt_out_size-offset); |
836 | 860 | ||
837 | if (count == 0) { | 861 | if (count == 0) |
838 | return; | 862 | return; |
839 | } | ||
840 | 863 | ||
841 | switch (priv->pkt_fmt) { | 864 | switch (priv->pkt_fmt) { |
842 | default: | 865 | default: |
@@ -860,26 +883,29 @@ send: | |||
860 | actual_size = count + | 883 | actual_size = count + |
861 | (priv->pkt_fmt == packet_format_1 ? 2 : 1); | 884 | (priv->pkt_fmt == packet_format_1 ? 2 : 1); |
862 | 885 | ||
863 | usb_serial_debug_data(debug, &port->dev, __func__, port->interrupt_out_size, | 886 | usb_serial_debug_data(debug, &port->dev, __func__, |
864 | port->interrupt_out_urb->transfer_buffer); | 887 | port->interrupt_out_size, |
888 | port->interrupt_out_urb->transfer_buffer); | ||
865 | 889 | ||
866 | usb_fill_int_urb(port->interrupt_out_urb, port->serial->dev, | 890 | usb_fill_int_urb(port->interrupt_out_urb, port->serial->dev, |
867 | usb_sndintpipe(port->serial->dev, port->interrupt_out_endpointAddress), | 891 | usb_sndintpipe(port->serial->dev, port->interrupt_out_endpointAddress), |
868 | port->interrupt_out_buffer, port->interrupt_out_size, | 892 | port->interrupt_out_buffer, port->interrupt_out_size, |
869 | cypress_write_int_callback, port, priv->write_urb_interval); | 893 | cypress_write_int_callback, port, priv->write_urb_interval); |
870 | result = usb_submit_urb (port->interrupt_out_urb, GFP_ATOMIC); | 894 | result = usb_submit_urb(port->interrupt_out_urb, GFP_ATOMIC); |
871 | if (result) { | 895 | if (result) { |
872 | dev_err(&port->dev, "%s - failed submitting write urb, error %d\n", __func__, | 896 | dev_err(&port->dev, |
873 | result); | 897 | "%s - failed submitting write urb, error %d\n", |
898 | __func__, result); | ||
874 | priv->write_urb_in_use = 0; | 899 | priv->write_urb_in_use = 0; |
875 | cypress_set_dead(port); | 900 | cypress_set_dead(port); |
876 | } | 901 | } |
877 | 902 | ||
878 | spin_lock_irqsave(&priv->lock, flags); | 903 | spin_lock_irqsave(&priv->lock, flags); |
879 | if (priv->cmd_ctrl) { | 904 | if (priv->cmd_ctrl) |
880 | priv->cmd_ctrl = 0; | 905 | priv->cmd_ctrl = 0; |
881 | } | 906 | |
882 | priv->bytes_out += count; /* do not count the line control and size bytes */ | 907 | /* do not count the line control and size bytes */ |
908 | priv->bytes_out += count; | ||
883 | spin_unlock_irqrestore(&priv->lock, flags); | 909 | spin_unlock_irqrestore(&priv->lock, flags); |
884 | 910 | ||
885 | usb_serial_port_softint(port); | 911 | usb_serial_port_softint(port); |
@@ -912,7 +938,7 @@ static int cypress_tiocmget(struct tty_struct *tty, struct file *file) | |||
912 | __u8 status, control; | 938 | __u8 status, control; |
913 | unsigned int result = 0; | 939 | unsigned int result = 0; |
914 | unsigned long flags; | 940 | unsigned long flags; |
915 | 941 | ||
916 | dbg("%s - port %d", __func__, port->number); | 942 | dbg("%s - port %d", __func__, port->number); |
917 | 943 | ||
918 | spin_lock_irqsave(&priv->lock, flags); | 944 | spin_lock_irqsave(&priv->lock, flags); |
@@ -939,7 +965,7 @@ static int cypress_tiocmset(struct tty_struct *tty, struct file *file, | |||
939 | struct usb_serial_port *port = tty->driver_data; | 965 | struct usb_serial_port *port = tty->driver_data; |
940 | struct cypress_private *priv = usb_get_serial_port_data(port); | 966 | struct cypress_private *priv = usb_get_serial_port_data(port); |
941 | unsigned long flags; | 967 | unsigned long flags; |
942 | 968 | ||
943 | dbg("%s - port %d", __func__, port->number); | 969 | dbg("%s - port %d", __func__, port->number); |
944 | 970 | ||
945 | spin_lock_irqsave(&priv->lock, flags); | 971 | spin_lock_irqsave(&priv->lock, flags); |
@@ -958,7 +984,7 @@ static int cypress_tiocmset(struct tty_struct *tty, struct file *file, | |||
958 | } | 984 | } |
959 | 985 | ||
960 | 986 | ||
961 | static int cypress_ioctl(struct tty_struct *tty, struct file * file, | 987 | static int cypress_ioctl(struct tty_struct *tty, struct file *file, |
962 | unsigned int cmd, unsigned long arg) | 988 | unsigned int cmd, unsigned long arg) |
963 | { | 989 | { |
964 | struct usb_serial_port *port = tty->driver_data; | 990 | struct usb_serial_port *port = tty->driver_data; |
@@ -967,38 +993,37 @@ static int cypress_ioctl(struct tty_struct *tty, struct file * file, | |||
967 | dbg("%s - port %d, cmd 0x%.4x", __func__, port->number, cmd); | 993 | dbg("%s - port %d, cmd 0x%.4x", __func__, port->number, cmd); |
968 | 994 | ||
969 | switch (cmd) { | 995 | switch (cmd) { |
970 | /* This code comes from drivers/char/serial.c and ftdi_sio.c */ | 996 | /* This code comes from drivers/char/serial.c and ftdi_sio.c */ |
971 | case TIOCMIWAIT: | 997 | case TIOCMIWAIT: |
972 | while (priv != NULL) { | 998 | while (priv != NULL) { |
973 | interruptible_sleep_on(&priv->delta_msr_wait); | 999 | interruptible_sleep_on(&priv->delta_msr_wait); |
974 | /* see if a signal did it */ | 1000 | /* see if a signal did it */ |
975 | if (signal_pending(current)) | 1001 | if (signal_pending(current)) |
976 | return -ERESTARTSYS; | 1002 | return -ERESTARTSYS; |
977 | else { | 1003 | else { |
978 | char diff = priv->diff_status; | 1004 | char diff = priv->diff_status; |
979 | 1005 | if (diff == 0) | |
980 | if (diff == 0) { | 1006 | return -EIO; /* no change => error */ |
981 | return -EIO; /* no change => error */ | 1007 | |
982 | } | 1008 | /* consume all events */ |
983 | 1009 | priv->diff_status = 0; | |
984 | /* consume all events */ | 1010 | |
985 | priv->diff_status = 0; | 1011 | /* return 0 if caller wanted to know about |
986 | 1012 | these bits */ | |
987 | /* return 0 if caller wanted to know about these bits */ | 1013 | if (((arg & TIOCM_RNG) && (diff & UART_RI)) || |
988 | if ( ((arg & TIOCM_RNG) && (diff & UART_RI)) || | 1014 | ((arg & TIOCM_DSR) && (diff & UART_DSR)) || |
989 | ((arg & TIOCM_DSR) && (diff & UART_DSR)) || | 1015 | ((arg & TIOCM_CD) && (diff & UART_CD)) || |
990 | ((arg & TIOCM_CD) && (diff & UART_CD)) || | 1016 | ((arg & TIOCM_CTS) && (diff & UART_CTS))) |
991 | ((arg & TIOCM_CTS) && (diff & UART_CTS)) ) { | 1017 | return 0; |
992 | return 0; | 1018 | /* otherwise caller can't care less about what |
993 | } | 1019 | * happened, and so we continue to wait for |
994 | /* otherwise caller can't care less about what happened, | 1020 | * more events. |
995 | * and so we continue to wait for more events. | 1021 | */ |
996 | */ | ||
997 | } | ||
998 | } | 1022 | } |
999 | return 0; | 1023 | } |
1000 | default: | 1024 | return 0; |
1001 | break; | 1025 | default: |
1026 | break; | ||
1002 | } | 1027 | } |
1003 | dbg("%s - arg not supported - it was 0x%04x - check include/asm/ioctls.h", __func__, cmd); | 1028 | dbg("%s - arg not supported - it was 0x%04x - check include/asm/ioctls.h", __func__, cmd); |
1004 | return -ENOIOCTLCMD; | 1029 | return -ENOIOCTLCMD; |
@@ -1070,23 +1095,22 @@ static void cypress_set_termios(struct tty_struct *tty, | |||
1070 | 1095 | ||
1071 | if (cflag & CSIZE) { | 1096 | if (cflag & CSIZE) { |
1072 | switch (cflag & CSIZE) { | 1097 | switch (cflag & CSIZE) { |
1073 | case CS5: | 1098 | case CS5: |
1074 | data_bits = 0; | 1099 | data_bits = 0; |
1075 | break; | 1100 | break; |
1076 | case CS6: | 1101 | case CS6: |
1077 | data_bits = 1; | 1102 | data_bits = 1; |
1078 | break; | 1103 | break; |
1079 | case CS7: | 1104 | case CS7: |
1080 | data_bits = 2; | 1105 | data_bits = 2; |
1081 | break; | 1106 | break; |
1082 | case CS8: | 1107 | case CS8: |
1083 | data_bits = 3; | 1108 | data_bits = 3; |
1084 | break; | 1109 | break; |
1085 | default: | 1110 | default: |
1086 | err("%s - CSIZE was set, but not CS5-CS8", | 1111 | err("%s - CSIZE was set, but not CS5-CS8", |
1087 | __func__); | 1112 | __func__); |
1088 | data_bits = 3; | 1113 | data_bits = 3; |
1089 | } | ||
1090 | } else | 1114 | } else |
1091 | data_bits = 3; | 1115 | data_bits = 3; |
1092 | 1116 | ||
@@ -1104,8 +1128,10 @@ static void cypress_set_termios(struct tty_struct *tty, | |||
1104 | "%d data_bits (+5)", __func__, stop_bits, | 1128 | "%d data_bits (+5)", __func__, stop_bits, |
1105 | parity_enable, parity_type, data_bits); | 1129 | parity_enable, parity_type, data_bits); |
1106 | 1130 | ||
1107 | cypress_serial_control(tty, port, tty_get_baud_rate(tty), data_bits, stop_bits, | 1131 | cypress_serial_control(tty, port, tty_get_baud_rate(tty), |
1108 | parity_enable, parity_type, 0, CYPRESS_SET_CONFIG); | 1132 | data_bits, stop_bits, |
1133 | parity_enable, parity_type, | ||
1134 | 0, CYPRESS_SET_CONFIG); | ||
1109 | 1135 | ||
1110 | /* we perform a CYPRESS_GET_CONFIG so that the current settings are | 1136 | /* we perform a CYPRESS_GET_CONFIG so that the current settings are |
1111 | * filled into the private structure this should confirm that all is | 1137 | * filled into the private structure this should confirm that all is |
@@ -1116,7 +1142,7 @@ static void cypress_set_termios(struct tty_struct *tty, | |||
1116 | * termios flag base comes from empeg.c */ | 1142 | * termios flag base comes from empeg.c */ |
1117 | 1143 | ||
1118 | spin_lock_irqsave(&priv->lock, flags); | 1144 | spin_lock_irqsave(&priv->lock, flags); |
1119 | if ( (priv->chiptype == CT_EARTHMATE) && (priv->baud_rate == 4800) ) { | 1145 | if (priv->chiptype == CT_EARTHMATE && priv->baud_rate == 4800) { |
1120 | dbg("Using custom termios settings for a baud rate of " | 1146 | dbg("Using custom termios settings for a baud rate of " |
1121 | "4800bps."); | 1147 | "4800bps."); |
1122 | /* define custom termios settings for NMEA protocol */ | 1148 | /* define custom termios settings for NMEA protocol */ |
@@ -1164,7 +1190,7 @@ static int cypress_chars_in_buffer(struct tty_struct *tty) | |||
1164 | unsigned long flags; | 1190 | unsigned long flags; |
1165 | 1191 | ||
1166 | dbg("%s - port %d", __func__, port->number); | 1192 | dbg("%s - port %d", __func__, port->number); |
1167 | 1193 | ||
1168 | spin_lock_irqsave(&priv->lock, flags); | 1194 | spin_lock_irqsave(&priv->lock, flags); |
1169 | chars = cypress_buf_data_avail(priv->buf); | 1195 | chars = cypress_buf_data_avail(priv->buf); |
1170 | spin_unlock_irqrestore(&priv->lock, flags); | 1196 | spin_unlock_irqrestore(&priv->lock, flags); |
@@ -1243,12 +1269,13 @@ static void cypress_read_int_callback(struct urb *urb) | |||
1243 | /* precursor to disconnect so just go away */ | 1269 | /* precursor to disconnect so just go away */ |
1244 | return; | 1270 | return; |
1245 | case -EPIPE: | 1271 | case -EPIPE: |
1246 | usb_clear_halt(port->serial->dev,0x81); | 1272 | usb_clear_halt(port->serial->dev, 0x81); |
1247 | break; | 1273 | break; |
1248 | default: | 1274 | default: |
1249 | /* something ugly is going on... */ | 1275 | /* something ugly is going on... */ |
1250 | dev_err(&urb->dev->dev,"%s - unexpected nonzero read status received: %d\n", | 1276 | dev_err(&urb->dev->dev, |
1251 | __func__, status); | 1277 | "%s - unexpected nonzero read status received: %d\n", |
1278 | __func__, status); | ||
1252 | cypress_set_dead(port); | 1279 | cypress_set_dead(port); |
1253 | return; | 1280 | return; |
1254 | } | 1281 | } |
@@ -1296,8 +1323,8 @@ static void cypress_read_int_callback(struct urb *urb) | |||
1296 | goto continue_read; | 1323 | goto continue_read; |
1297 | } | 1324 | } |
1298 | 1325 | ||
1299 | usb_serial_debug_data (debug, &port->dev, __func__, | 1326 | usb_serial_debug_data(debug, &port->dev, __func__, |
1300 | urb->actual_length, data); | 1327 | urb->actual_length, data); |
1301 | 1328 | ||
1302 | spin_lock_irqsave(&priv->lock, flags); | 1329 | spin_lock_irqsave(&priv->lock, flags); |
1303 | /* check to see if status has changed */ | 1330 | /* check to see if status has changed */ |
@@ -1356,7 +1383,8 @@ continue_read: | |||
1356 | port->interrupt_in_endpointAddress), | 1383 | port->interrupt_in_endpointAddress), |
1357 | port->interrupt_in_urb->transfer_buffer, | 1384 | port->interrupt_in_urb->transfer_buffer, |
1358 | port->interrupt_in_urb->transfer_buffer_length, | 1385 | port->interrupt_in_urb->transfer_buffer_length, |
1359 | cypress_read_int_callback, port, priv->read_urb_interval); | 1386 | cypress_read_int_callback, port, |
1387 | priv->read_urb_interval); | ||
1360 | result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC); | 1388 | result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC); |
1361 | if (result) { | 1389 | if (result) { |
1362 | dev_err(&urb->dev->dev, "%s - failed resubmitting " | 1390 | dev_err(&urb->dev->dev, "%s - failed resubmitting " |
@@ -1380,42 +1408,43 @@ static void cypress_write_int_callback(struct urb *urb) | |||
1380 | dbg("%s - port %d", __func__, port->number); | 1408 | dbg("%s - port %d", __func__, port->number); |
1381 | 1409 | ||
1382 | switch (status) { | 1410 | switch (status) { |
1383 | case 0: | 1411 | case 0: |
1384 | /* success */ | 1412 | /* success */ |
1413 | break; | ||
1414 | case -ECONNRESET: | ||
1415 | case -ENOENT: | ||
1416 | case -ESHUTDOWN: | ||
1417 | /* this urb is terminated, clean up */ | ||
1418 | dbg("%s - urb shutting down with status: %d", | ||
1419 | __func__, status); | ||
1420 | priv->write_urb_in_use = 0; | ||
1421 | return; | ||
1422 | case -EPIPE: /* no break needed; clear halt and resubmit */ | ||
1423 | if (!priv->comm_is_ok) | ||
1385 | break; | 1424 | break; |
1386 | case -ECONNRESET: | 1425 | usb_clear_halt(port->serial->dev, 0x02); |
1387 | case -ENOENT: | 1426 | /* error in the urb, so we have to resubmit it */ |
1388 | case -ESHUTDOWN: | 1427 | dbg("%s - nonzero write bulk status received: %d", |
1389 | /* this urb is terminated, clean up */ | 1428 | __func__, status); |
1390 | dbg("%s - urb shutting down with status: %d", | 1429 | port->interrupt_out_urb->transfer_buffer_length = 1; |
1391 | __func__, status); | 1430 | port->interrupt_out_urb->dev = port->serial->dev; |
1392 | priv->write_urb_in_use = 0; | 1431 | result = usb_submit_urb(port->interrupt_out_urb, GFP_ATOMIC); |
1432 | if (!result) | ||
1393 | return; | 1433 | return; |
1394 | case -EPIPE: /* no break needed; clear halt and resubmit */ | 1434 | dev_err(&urb->dev->dev, |
1395 | if (!priv->comm_is_ok) | 1435 | "%s - failed resubmitting write urb, error %d\n", |
1396 | break; | 1436 | __func__, result); |
1397 | usb_clear_halt(port->serial->dev, 0x02); | 1437 | cypress_set_dead(port); |
1398 | /* error in the urb, so we have to resubmit it */ | 1438 | break; |
1399 | dbg("%s - nonzero write bulk status received: %d", | 1439 | default: |
1400 | __func__, status); | 1440 | dev_err(&urb->dev->dev, |
1401 | port->interrupt_out_urb->transfer_buffer_length = 1; | 1441 | "%s - unexpected nonzero write status received: %d\n", |
1402 | port->interrupt_out_urb->dev = port->serial->dev; | 1442 | __func__, status); |
1403 | result = usb_submit_urb(port->interrupt_out_urb, GFP_ATOMIC); | 1443 | cypress_set_dead(port); |
1404 | if (!result) | 1444 | break; |
1405 | return; | ||
1406 | dev_err(&urb->dev->dev, "%s - failed resubmitting write urb, error %d\n", | ||
1407 | __func__, result); | ||
1408 | cypress_set_dead(port); | ||
1409 | break; | ||
1410 | default: | ||
1411 | dev_err(&urb->dev->dev,"%s - unexpected nonzero write status received: %d\n", | ||
1412 | __func__, status); | ||
1413 | cypress_set_dead(port); | ||
1414 | break; | ||
1415 | } | 1445 | } |
1416 | |||
1417 | priv->write_urb_in_use = 0; | 1446 | priv->write_urb_in_use = 0; |
1418 | 1447 | ||
1419 | /* send any buffered data */ | 1448 | /* send any buffered data */ |
1420 | cypress_send(port); | 1449 | cypress_send(port); |
1421 | } | 1450 | } |
@@ -1497,7 +1526,8 @@ static void cypress_buf_clear(struct cypress_buf *cb) | |||
1497 | static unsigned int cypress_buf_data_avail(struct cypress_buf *cb) | 1526 | static unsigned int cypress_buf_data_avail(struct cypress_buf *cb) |
1498 | { | 1527 | { |
1499 | if (cb != NULL) | 1528 | if (cb != NULL) |
1500 | return ((cb->buf_size + cb->buf_put - cb->buf_get) % cb->buf_size); | 1529 | return (cb->buf_size + cb->buf_put - cb->buf_get) |
1530 | % cb->buf_size; | ||
1501 | else | 1531 | else |
1502 | return 0; | 1532 | return 0; |
1503 | } | 1533 | } |
@@ -1513,7 +1543,8 @@ static unsigned int cypress_buf_data_avail(struct cypress_buf *cb) | |||
1513 | static unsigned int cypress_buf_space_avail(struct cypress_buf *cb) | 1543 | static unsigned int cypress_buf_space_avail(struct cypress_buf *cb) |
1514 | { | 1544 | { |
1515 | if (cb != NULL) | 1545 | if (cb != NULL) |
1516 | return ((cb->buf_size + cb->buf_get - cb->buf_put - 1) % cb->buf_size); | 1546 | return (cb->buf_size + cb->buf_get - cb->buf_put - 1) |
1547 | % cb->buf_size; | ||
1517 | else | 1548 | else |
1518 | return 0; | 1549 | return 0; |
1519 | } | 1550 | } |
@@ -1613,9 +1644,9 @@ static unsigned int cypress_buf_get(struct cypress_buf *cb, char *buf, | |||
1613 | static int __init cypress_init(void) | 1644 | static int __init cypress_init(void) |
1614 | { | 1645 | { |
1615 | int retval; | 1646 | int retval; |
1616 | 1647 | ||
1617 | dbg("%s", __func__); | 1648 | dbg("%s", __func__); |
1618 | 1649 | ||
1619 | retval = usb_serial_register(&cypress_earthmate_device); | 1650 | retval = usb_serial_register(&cypress_earthmate_device); |
1620 | if (retval) | 1651 | if (retval) |
1621 | goto failed_em_register; | 1652 | goto failed_em_register; |
@@ -1643,23 +1674,23 @@ failed_em_register: | |||
1643 | } | 1674 | } |
1644 | 1675 | ||
1645 | 1676 | ||
1646 | static void __exit cypress_exit (void) | 1677 | static void __exit cypress_exit(void) |
1647 | { | 1678 | { |
1648 | dbg("%s", __func__); | 1679 | dbg("%s", __func__); |
1649 | 1680 | ||
1650 | usb_deregister (&cypress_driver); | 1681 | usb_deregister(&cypress_driver); |
1651 | usb_serial_deregister (&cypress_earthmate_device); | 1682 | usb_serial_deregister(&cypress_earthmate_device); |
1652 | usb_serial_deregister (&cypress_hidcom_device); | 1683 | usb_serial_deregister(&cypress_hidcom_device); |
1653 | usb_serial_deregister (&cypress_ca42v2_device); | 1684 | usb_serial_deregister(&cypress_ca42v2_device); |
1654 | } | 1685 | } |
1655 | 1686 | ||
1656 | 1687 | ||
1657 | module_init(cypress_init); | 1688 | module_init(cypress_init); |
1658 | module_exit(cypress_exit); | 1689 | module_exit(cypress_exit); |
1659 | 1690 | ||
1660 | MODULE_AUTHOR( DRIVER_AUTHOR ); | 1691 | MODULE_AUTHOR(DRIVER_AUTHOR); |
1661 | MODULE_DESCRIPTION( DRIVER_DESC ); | 1692 | MODULE_DESCRIPTION(DRIVER_DESC); |
1662 | MODULE_VERSION( DRIVER_VERSION ); | 1693 | MODULE_VERSION(DRIVER_VERSION); |
1663 | MODULE_LICENSE("GPL"); | 1694 | MODULE_LICENSE("GPL"); |
1664 | 1695 | ||
1665 | module_param(debug, bool, S_IRUGO | S_IWUSR); | 1696 | module_param(debug, bool, S_IRUGO | S_IWUSR); |
diff --git a/drivers/usb/serial/cypress_m8.h b/drivers/usb/serial/cypress_m8.h index 0388065bb794..e772b01ac3ac 100644 --- a/drivers/usb/serial/cypress_m8.h +++ b/drivers/usb/serial/cypress_m8.h | |||
@@ -54,7 +54,7 @@ | |||
54 | #define UART_DSR 0x20 /* data set ready - flow control - device to host */ | 54 | #define UART_DSR 0x20 /* data set ready - flow control - device to host */ |
55 | #define CONTROL_RTS 0x10 /* request to send - flow control - host to device */ | 55 | #define CONTROL_RTS 0x10 /* request to send - flow control - host to device */ |
56 | #define UART_CTS 0x10 /* clear to send - flow control - device to host */ | 56 | #define UART_CTS 0x10 /* clear to send - flow control - device to host */ |
57 | #define UART_RI 0x10 /* ring indicator - modem - device to host */ | 57 | #define UART_RI 0x10 /* ring indicator - modem - device to host */ |
58 | #define UART_CD 0x40 /* carrier detect - modem - device to host */ | 58 | #define UART_CD 0x40 /* carrier detect - modem - device to host */ |
59 | #define CYP_ERROR 0x08 /* received from input report - device to host */ | 59 | #define CYP_ERROR 0x08 /* received from input report - device to host */ |
60 | /* Note - the below has nothing to to with the "feature report" reset */ | 60 | /* Note - the below has nothing to to with the "feature report" reset */ |