Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

USB: oti6858 usb-serial driver (in Nokia CA-42 cable)

Last week I've been searching for a driver for the CA-42 cable (see usb
below) that fitted my kernel 2.6.20. I only found an abandoned version for a
driver on your website that indeed worked on 2.6.18 but wouldn't even
compile with a more recent 2.6.20 kernel.

I fiddled 2 evenings with the kernel code and have patched it up now to work
with the modifications in the 2.6.20 kernel. The patch is attached hereafter
and it works fine (at least for me :-) ).

Bus 2 Device 13: ID 0ea0:6858 Ours Technology, Inc.

I had to fiddle a little with the settings in .gnokiirc but that also
occurred with the older 2.6.18 kernel. Nevertheless, on one system with this
cable and my Nokia 6070 I had best results with :

model = 6510
connection = dku5

while on an other system with the same kernel, cable and phone it only worked
with :

model = AT
connection = serial
serial_write_usleep = 1


From: Kees Lemmens <C.W.J.Lemmens@ewi.tudelft.nl>
Cc: <pawel.kot@gmail.com>
Cc: <bozo@andrews.hu>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>

authored by

Kees Lemmens and committed by
Greg Kroah-Hartman
49cdee0e 9c033e81

+1367
+10
drivers/usb/serial/Kconfig
··· 464 464 To compile this driver as a module, choose M here: the 465 465 module will be called pl2303. 466 466 467 + config USB_SERIAL_OTI6858 468 + tristate "USB Ours Technology Inc. OTi-6858 USB To RS232 Bridge Controller (EXPERIMENTAL)" 469 + depends on USB_SERIAL 470 + help 471 + Say Y here if you want to use the OTi-6858 single port USB to serial 472 + converter device. 473 + 474 + To compile this driver as a module, choose M here: the 475 + module will be called oti6858. 476 + 467 477 config USB_SERIAL_HP4X 468 478 tristate "USB HP4x Calculators support" 469 479 depends on USB_SERIAL
+1
drivers/usb/serial/Makefile
··· 40 40 obj-$(CONFIG_USB_SERIAL_NAVMAN) += navman.o 41 41 obj-$(CONFIG_USB_SERIAL_OMNINET) += omninet.o 42 42 obj-$(CONFIG_USB_SERIAL_OPTION) += option.o 43 + obj-$(CONFIG_USB_SERIAL_OTI6858) += oti6858.o 43 44 obj-$(CONFIG_USB_SERIAL_PL2303) += pl2303.o 44 45 obj-$(CONFIG_USB_SERIAL_SAFE) += safe_serial.o 45 46 obj-$(CONFIG_USB_SERIAL_SIERRAWIRELESS) += sierra.o
+1341
drivers/usb/serial/oti6858.c
··· 1 + /* 2 + * Ours Technology Inc. OTi-6858 USB to serial adapter driver. 3 + * 4 + * Copyleft (C) 2007 Kees Lemmens (adapted for kernel 2.6.20) 5 + * Copyright (C) 2006 Tomasz Michal Lukaszewski (FIXME: add e-mail) 6 + * Copyright (C) 2001-2004 Greg Kroah-Hartman (greg@kroah.com) 7 + * Copyright (C) 2003 IBM Corp. 8 + * 9 + * Many thanks to the authors of pl2303 driver: all functions in this file 10 + * are heavily based on pl2303 code, buffering code is a 1-to-1 copy. 11 + * 12 + * Warning! You use this driver on your own risk! The only official 13 + * description of this device I have is datasheet from manufacturer, 14 + * and it doesn't contain almost any information needed to write a driver. 15 + * Almost all knowlegde used while writing this driver was gathered by: 16 + * - analyzing traffic between device and the M$ Windows 2000 driver, 17 + * - trying different bit combinations and checking pin states 18 + * with a voltmeter, 19 + * - receiving malformed frames and producing buffer overflows 20 + * to learn how errors are reported, 21 + * So, THIS CODE CAN DESTROY OTi-6858 AND ANY OTHER DEVICES, THAT ARE 22 + * CONNECTED TO IT! 23 + * 24 + * This program is free software; you can redistribute it and/or modify 25 + * it under the terms of the GNU General Public License as published by 26 + * the Free Software Foundation; either version 2 of the License. 27 + * 28 + * See Documentation/usb/usb-serial.txt for more information on using this driver 29 + * 30 + * TODO: 31 + * - implement correct flushing for ioctls and oti6858_close() 32 + * - check how errors (rx overflow, parity error, framing error) are reported 33 + * - implement oti6858_break_ctl() 34 + * - implement more ioctls 35 + * - test/implement flow control 36 + * - allow setting custom baud rates 37 + */ 38 + 39 + #include <linux/kernel.h> 40 + #include <linux/errno.h> 41 + #include <linux/init.h> 42 + #include <linux/slab.h> 43 + #include <linux/tty.h> 44 + #include <linux/tty_driver.h> 45 + #include <linux/tty_flip.h> 46 + #include <linux/serial.h> 47 + #include <linux/module.h> 48 + #include <linux/moduleparam.h> 49 + #include <linux/spinlock.h> 50 + #include <linux/usb.h> 51 + #include <linux/usb/serial.h> 52 + #include <asm/uaccess.h> 53 + #include "oti6858.h" 54 + 55 + #define OTI6858_DESCRIPTION \ 56 + "Ours Technology Inc. OTi-6858 USB to serial adapter driver" 57 + #define OTI6858_AUTHOR "Tomasz Michal Lukaszewski <FIXME@FIXME>" 58 + #define OTI6858_VERSION "0.1" 59 + 60 + static struct usb_device_id id_table [] = { 61 + { USB_DEVICE(OTI6858_VENDOR_ID, OTI6858_PRODUCT_ID) }, 62 + { } 63 + }; 64 + 65 + MODULE_DEVICE_TABLE(usb, id_table); 66 + 67 + static struct usb_driver oti6858_driver = { 68 + .name = "oti6858", 69 + .probe = usb_serial_probe, 70 + .disconnect = usb_serial_disconnect, 71 + .id_table = id_table, 72 + .no_dynamic_id = 1, 73 + }; 74 + 75 + static int debug; 76 + 77 + 78 + /* buffering code, copied from pl2303 driver */ 79 + #define PL2303_BUF_SIZE 1024 80 + #define PL2303_TMP_BUF_SIZE 1024 81 + 82 + struct pl2303_buf { 83 + unsigned int buf_size; 84 + char *buf_buf; 85 + char *buf_get; 86 + char *buf_put; 87 + }; 88 + 89 + /* requests */ 90 + #define OTI6858_REQ_GET_STATUS (USB_DIR_IN | USB_TYPE_VENDOR | 0x00) 91 + #define OTI6858_REQ_T_GET_STATUS 0x01 92 + 93 + #define OTI6858_REQ_SET_LINE (USB_DIR_OUT | USB_TYPE_VENDOR | 0x00) 94 + #define OTI6858_REQ_T_SET_LINE 0x00 95 + 96 + #define OTI6858_REQ_CHECK_TXBUFF (USB_DIR_IN | USB_TYPE_VENDOR | 0x01) 97 + #define OTI6858_REQ_T_CHECK_TXBUFF 0x00 98 + 99 + /* format of the control packet */ 100 + struct oti6858_control_pkt { 101 + u16 divisor; /* baud rate = 96000000 / (16 * divisor), LE */ 102 + #define OTI6858_MAX_BAUD_RATE 3000000 103 + u8 frame_fmt; 104 + #define FMT_STOP_BITS_MASK 0xc0 105 + #define FMT_STOP_BITS_1 0x00 106 + #define FMT_STOP_BITS_2 0x40 /* 1.5 stop bits if FMT_DATA_BITS_5 */ 107 + #define FMT_PARITY_MASK 0x38 108 + #define FMT_PARITY_NONE 0x00 109 + #define FMT_PARITY_ODD 0x08 110 + #define FMT_PARITY_EVEN 0x18 111 + #define FMT_PARITY_MARK 0x28 112 + #define FMT_PARITY_SPACE 0x38 113 + #define FMT_DATA_BITS_MASK 0x03 114 + #define FMT_DATA_BITS_5 0x00 115 + #define FMT_DATA_BITS_6 0x01 116 + #define FMT_DATA_BITS_7 0x02 117 + #define FMT_DATA_BITS_8 0x03 118 + u8 something; /* always equals 0x43 */ 119 + u8 control; /* settings of flow control lines */ 120 + #define CONTROL_MASK 0x0c 121 + #define CONTROL_DTR_HIGH 0x08 122 + #define CONTROL_RTS_HIGH 0x04 123 + u8 tx_status; 124 + #define TX_BUFFER_EMPTIED 0x09 125 + u8 pin_state; 126 + #define PIN_MASK 0x3f 127 + #define PIN_RTS 0x20 /* output pin */ 128 + #define PIN_CTS 0x10 /* input pin, active low */ 129 + #define PIN_DSR 0x08 /* input pin, active low */ 130 + #define PIN_DTR 0x04 /* output pin */ 131 + #define PIN_RI 0x02 /* input pin, active low */ 132 + #define PIN_DCD 0x01 /* input pin, active low */ 133 + u8 rx_bytes_avail; /* number of bytes in rx buffer */; 134 + }; 135 + 136 + #define OTI6858_CTRL_PKT_SIZE sizeof(struct oti6858_control_pkt) 137 + #define OTI6858_CTRL_EQUALS_PENDING(a, priv) \ 138 + ( ((a)->divisor == (priv)->pending_setup.divisor) \ 139 + && ((a)->control == (priv)->pending_setup.control) \ 140 + && ((a)->frame_fmt == (priv)->pending_setup.frame_fmt) ) 141 + 142 + /* function prototypes */ 143 + static int oti6858_open(struct usb_serial_port *port, struct file *filp); 144 + static void oti6858_close(struct usb_serial_port *port, struct file *filp); 145 + static void oti6858_set_termios(struct usb_serial_port *port, 146 + struct ktermios *old); 147 + static int oti6858_ioctl(struct usb_serial_port *port, struct file *file, 148 + unsigned int cmd, unsigned long arg); 149 + static void oti6858_read_int_callback(struct urb *urb); 150 + static void oti6858_read_bulk_callback(struct urb *urb); 151 + static void oti6858_write_bulk_callback(struct urb *urb); 152 + static int oti6858_write(struct usb_serial_port *port, 153 + const unsigned char *buf, int count); 154 + static int oti6858_write_room(struct usb_serial_port *port); 155 + static void oti6858_break_ctl(struct usb_serial_port *port, int break_state); 156 + static int oti6858_chars_in_buffer(struct usb_serial_port *port); 157 + static int oti6858_tiocmget(struct usb_serial_port *port, struct file *file); 158 + static int oti6858_tiocmset(struct usb_serial_port *port, struct file *file, 159 + unsigned int set, unsigned int clear); 160 + static int oti6858_startup(struct usb_serial *serial); 161 + static void oti6858_shutdown(struct usb_serial *serial); 162 + 163 + /* functions operating on buffers */ 164 + static struct pl2303_buf *pl2303_buf_alloc(unsigned int size); 165 + static void pl2303_buf_free(struct pl2303_buf *pb); 166 + static void pl2303_buf_clear(struct pl2303_buf *pb); 167 + static unsigned int pl2303_buf_data_avail(struct pl2303_buf *pb); 168 + static unsigned int pl2303_buf_space_avail(struct pl2303_buf *pb); 169 + static unsigned int pl2303_buf_put(struct pl2303_buf *pb, const char *buf, 170 + unsigned int count); 171 + static unsigned int pl2303_buf_get(struct pl2303_buf *pb, char *buf, 172 + unsigned int count); 173 + 174 + 175 + /* device info */ 176 + static struct usb_serial_driver oti6858_device = { 177 + .driver = { 178 + .owner = THIS_MODULE, 179 + .name = "oti6858", 180 + }, 181 + .id_table = id_table, 182 + .num_interrupt_in = 1, 183 + .num_bulk_in = 1, 184 + .num_bulk_out = 1, 185 + .num_ports = 1, 186 + .open = oti6858_open, 187 + .close = oti6858_close, 188 + .write = oti6858_write, 189 + .ioctl = oti6858_ioctl, 190 + .break_ctl = oti6858_break_ctl, 191 + .set_termios = oti6858_set_termios, 192 + .tiocmget = oti6858_tiocmget, 193 + .tiocmset = oti6858_tiocmset, 194 + .read_bulk_callback = oti6858_read_bulk_callback, 195 + .read_int_callback = oti6858_read_int_callback, 196 + .write_bulk_callback = oti6858_write_bulk_callback, 197 + .write_room = oti6858_write_room, 198 + .chars_in_buffer = oti6858_chars_in_buffer, 199 + .attach = oti6858_startup, 200 + .shutdown = oti6858_shutdown, 201 + }; 202 + 203 + struct oti6858_private { 204 + spinlock_t lock; 205 + 206 + struct pl2303_buf *buf; 207 + struct oti6858_control_pkt status; 208 + 209 + struct { 210 + u8 read_urb_in_use; 211 + u8 write_urb_in_use; 212 + u8 termios_initialized; 213 + } flags; 214 + struct delayed_work delayed_write_work; 215 + 216 + struct { 217 + u16 divisor; 218 + u8 frame_fmt; 219 + u8 control; 220 + } pending_setup; 221 + u8 transient; 222 + u8 setup_done; 223 + struct delayed_work delayed_setup_work; 224 + 225 + wait_queue_head_t intr_wait; 226 + struct usb_serial_port *port; /* USB port with which associated */ 227 + }; 228 + 229 + #undef dbg 230 + /* #define dbg(format, arg...) printk(KERN_INFO "%s: " format "\n", __FILE__, ## arg) */ 231 + #define dbg(format, arg...) printk(KERN_INFO "" format "\n", ## arg) 232 + 233 + static void setup_line(struct work_struct *work) 234 + { 235 + struct oti6858_private *priv = container_of(work, struct oti6858_private, delayed_setup_work.work); 236 + struct usb_serial_port *port = priv->port; 237 + struct oti6858_control_pkt *new_setup; 238 + unsigned long flags; 239 + int result; 240 + 241 + dbg("%s(port = %d)", __FUNCTION__, port->number); 242 + 243 + if ((new_setup = kmalloc(OTI6858_CTRL_PKT_SIZE, GFP_KERNEL)) == NULL) { 244 + dev_err(&port->dev, "%s(): out of memory!\n", __FUNCTION__); 245 + /* we will try again */ 246 + schedule_delayed_work(&priv->delayed_setup_work, msecs_to_jiffies(2)); 247 + return; 248 + } 249 + 250 + result = usb_control_msg(port->serial->dev, 251 + usb_rcvctrlpipe(port->serial->dev, 0), 252 + OTI6858_REQ_T_GET_STATUS, 253 + OTI6858_REQ_GET_STATUS, 254 + 0, 0, 255 + new_setup, OTI6858_CTRL_PKT_SIZE, 256 + 100); 257 + 258 + if (result != OTI6858_CTRL_PKT_SIZE) { 259 + dev_err(&port->dev, "%s(): error reading status", __FUNCTION__); 260 + kfree(new_setup); 261 + /* we will try again */ 262 + schedule_delayed_work(&priv->delayed_setup_work, msecs_to_jiffies(2)); 263 + return; 264 + } 265 + 266 + spin_lock_irqsave(&priv->lock, flags); 267 + if (!OTI6858_CTRL_EQUALS_PENDING(new_setup, priv)) { 268 + new_setup->divisor = priv->pending_setup.divisor; 269 + new_setup->control = priv->pending_setup.control; 270 + new_setup->frame_fmt = priv->pending_setup.frame_fmt; 271 + 272 + spin_unlock_irqrestore(&priv->lock, flags); 273 + result = usb_control_msg(port->serial->dev, 274 + usb_sndctrlpipe(port->serial->dev, 0), 275 + OTI6858_REQ_T_SET_LINE, 276 + OTI6858_REQ_SET_LINE, 277 + 0, 0, 278 + new_setup, OTI6858_CTRL_PKT_SIZE, 279 + 100); 280 + } else { 281 + spin_unlock_irqrestore(&priv->lock, flags); 282 + result = 0; 283 + } 284 + kfree(new_setup); 285 + 286 + spin_lock_irqsave(&priv->lock, flags); 287 + if (result != OTI6858_CTRL_PKT_SIZE) 288 + priv->transient = 0; 289 + priv->setup_done = 1; 290 + spin_unlock_irqrestore(&priv->lock, flags); 291 + 292 + dbg("%s(): submitting interrupt urb", __FUNCTION__); 293 + port->interrupt_in_urb->dev = port->serial->dev; 294 + result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC); 295 + if (result != 0) { 296 + dev_err(&port->dev, "%s(): usb_submit_urb() failed" 297 + " with error %d\n", __FUNCTION__, result); 298 + } 299 + } 300 + 301 + void send_data(struct work_struct *work) 302 + { 303 + struct oti6858_private *priv = container_of(work, struct oti6858_private, delayed_write_work.work); 304 + struct usb_serial_port *port = priv->port; 305 + int count = 0, result; 306 + unsigned long flags; 307 + unsigned char allow; 308 + 309 + dbg("%s(port = %d)", __FUNCTION__, port->number); 310 + 311 + spin_lock_irqsave(&priv->lock, flags); 312 + if (priv->flags.write_urb_in_use) { 313 + spin_unlock_irqrestore(&priv->lock, flags); 314 + schedule_delayed_work(&priv->delayed_write_work, msecs_to_jiffies(2)); 315 + return; 316 + } 317 + priv->flags.write_urb_in_use = 1; 318 + 319 + count = pl2303_buf_data_avail(priv->buf); 320 + spin_unlock_irqrestore(&priv->lock, flags); 321 + if (count > port->bulk_out_size) 322 + count = port->bulk_out_size; 323 + 324 + if (count != 0) { 325 + result = usb_control_msg(port->serial->dev, 326 + usb_rcvctrlpipe(port->serial->dev, 0), 327 + OTI6858_REQ_T_CHECK_TXBUFF, 328 + OTI6858_REQ_CHECK_TXBUFF, 329 + count, 0, &allow, 1, 100); 330 + if (result != 1 || allow != 0) 331 + count = 0; 332 + } 333 + 334 + if (count == 0) { 335 + priv->flags.write_urb_in_use = 0; 336 + 337 + dbg("%s(): submitting interrupt urb", __FUNCTION__); 338 + port->interrupt_in_urb->dev = port->serial->dev; 339 + result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC); 340 + if (result != 0) { 341 + dev_err(&port->dev, "%s(): usb_submit_urb() failed" 342 + " with error %d\n", __FUNCTION__, result); 343 + } 344 + return; 345 + } 346 + 347 + spin_lock_irqsave(&priv->lock, flags); 348 + pl2303_buf_get(priv->buf, port->write_urb->transfer_buffer, count); 349 + spin_unlock_irqrestore(&priv->lock, flags); 350 + 351 + port->write_urb->transfer_buffer_length = count; 352 + port->write_urb->dev = port->serial->dev; 353 + result = usb_submit_urb(port->write_urb, GFP_ATOMIC); 354 + if (result != 0) { 355 + dev_err(&port->dev, "%s(): usb_submit_urb() failed" 356 + " with error %d\n", __FUNCTION__, result); 357 + priv->flags.write_urb_in_use = 0; 358 + } 359 + 360 + usb_serial_port_softint(port); 361 + } 362 + 363 + static int oti6858_startup(struct usb_serial *serial) 364 + { 365 + struct usb_serial_port *port = serial->port[0]; 366 + struct oti6858_private *priv; 367 + int i; 368 + 369 + for (i = 0; i < serial->num_ports; ++i) { 370 + priv = kzalloc(sizeof(struct oti6858_private), GFP_KERNEL); 371 + if (!priv) 372 + break; 373 + priv->buf = pl2303_buf_alloc(PL2303_BUF_SIZE); 374 + if (priv->buf == NULL) { 375 + kfree(priv); 376 + break; 377 + } 378 + 379 + spin_lock_init(&priv->lock); 380 + init_waitqueue_head(&priv->intr_wait); 381 + // INIT_WORK(&priv->setup_work, setup_line, serial->port[i]); 382 + // INIT_WORK(&priv->write_work, send_data, serial->port[i]); 383 + priv->port = port; 384 + INIT_DELAYED_WORK(&priv->delayed_setup_work, setup_line); 385 + INIT_DELAYED_WORK(&priv->delayed_write_work, send_data); 386 + 387 + usb_set_serial_port_data(serial->port[i], priv); 388 + } 389 + if (i == serial->num_ports) 390 + return 0; 391 + 392 + for (--i; i >= 0; --i) { 393 + priv = usb_get_serial_port_data(serial->port[i]); 394 + pl2303_buf_free(priv->buf); 395 + kfree(priv); 396 + usb_set_serial_port_data(serial->port[i], NULL); 397 + } 398 + return -ENOMEM; 399 + } 400 + 401 + static int oti6858_write(struct usb_serial_port *port, 402 + const unsigned char *buf, int count) 403 + { 404 + struct oti6858_private *priv = usb_get_serial_port_data(port); 405 + unsigned long flags; 406 + 407 + dbg("%s(port = %d, count = %d)", __FUNCTION__, port->number, count); 408 + 409 + if (!count) 410 + return count; 411 + 412 + spin_lock_irqsave(&priv->lock, flags); 413 + count = pl2303_buf_put(priv->buf, buf, count); 414 + spin_unlock_irqrestore(&priv->lock, flags); 415 + 416 + return count; 417 + } 418 + 419 + static int oti6858_write_room(struct usb_serial_port *port) 420 + { 421 + struct oti6858_private *priv = usb_get_serial_port_data(port); 422 + int room = 0; 423 + unsigned long flags; 424 + 425 + dbg("%s(port = %d)", __FUNCTION__, port->number); 426 + 427 + spin_lock_irqsave(&priv->lock, flags); 428 + room = pl2303_buf_space_avail(priv->buf); 429 + spin_unlock_irqrestore(&priv->lock, flags); 430 + 431 + return room; 432 + } 433 + 434 + static int oti6858_chars_in_buffer(struct usb_serial_port *port) 435 + { 436 + struct oti6858_private *priv = usb_get_serial_port_data(port); 437 + int chars = 0; 438 + unsigned long flags; 439 + 440 + dbg("%s(port = %d)", __FUNCTION__, port->number); 441 + 442 + spin_lock_irqsave(&priv->lock, flags); 443 + chars = pl2303_buf_data_avail(priv->buf); 444 + spin_unlock_irqrestore(&priv->lock, flags); 445 + 446 + return chars; 447 + } 448 + 449 + static void oti6858_set_termios(struct usb_serial_port *port, 450 + struct ktermios *old_termios) 451 + { 452 + struct oti6858_private *priv = usb_get_serial_port_data(port); 453 + unsigned long flags; 454 + unsigned int cflag; 455 + u8 frame_fmt, control; 456 + u16 divisor; 457 + int br; 458 + 459 + dbg("%s(port = %d)", __FUNCTION__, port->number); 460 + 461 + if ((!port->tty) || (!port->tty->termios)) { 462 + dbg("%s(): no tty structures", __FUNCTION__); 463 + return; 464 + } 465 + 466 + spin_lock_irqsave(&priv->lock, flags); 467 + if (!priv->flags.termios_initialized) { 468 + *(port->tty->termios) = tty_std_termios; 469 + port->tty->termios->c_cflag = B38400 | CS8 | CREAD | HUPCL | CLOCAL; 470 + priv->flags.termios_initialized = 1; 471 + } 472 + spin_unlock_irqrestore(&priv->lock, flags); 473 + 474 + cflag = port->tty->termios->c_cflag; 475 + 476 + spin_lock_irqsave(&priv->lock, flags); 477 + divisor = priv->pending_setup.divisor; 478 + frame_fmt = priv->pending_setup.frame_fmt; 479 + control = priv->pending_setup.control; 480 + spin_unlock_irqrestore(&priv->lock, flags); 481 + 482 + frame_fmt &= ~FMT_DATA_BITS_MASK; 483 + switch (cflag & CSIZE) { 484 + case CS5: 485 + frame_fmt |= FMT_DATA_BITS_5; 486 + break; 487 + case CS6: 488 + frame_fmt |= FMT_DATA_BITS_6; 489 + break; 490 + case CS7: 491 + frame_fmt |= FMT_DATA_BITS_7; 492 + break; 493 + default: 494 + case CS8: 495 + frame_fmt |= FMT_DATA_BITS_8; 496 + break; 497 + } 498 + 499 + /* manufacturer claims that this device can work with baud rates 500 + * up to 3 Mbps; I've tested it only on 115200 bps, so I can't 501 + * guarantee that any other baud rate will work (especially 502 + * the higher ones) 503 + */ 504 + br = tty_get_baud_rate(port->tty); 505 + if (br == 0) { 506 + divisor = 0; 507 + } else if (br <= OTI6858_MAX_BAUD_RATE) { 508 + int real_br; 509 + 510 + divisor = (96000000 + 8 * br) / (16 * br); 511 + real_br = 96000000 / (16 * divisor); 512 + if ((((real_br - br) * 100 + br - 1) / br) > 2) { 513 + dbg("%s(): baud rate %d is invalid", __FUNCTION__, br); 514 + return; 515 + } 516 + divisor = cpu_to_le16(divisor); 517 + } else { 518 + dbg("%s(): baud rate %d is too high", __FUNCTION__, br); 519 + return; 520 + } 521 + 522 + frame_fmt &= ~FMT_STOP_BITS_MASK; 523 + if ((cflag & CSTOPB) != 0) { 524 + frame_fmt |= FMT_STOP_BITS_2; 525 + } else { 526 + frame_fmt |= FMT_STOP_BITS_1; 527 + } 528 + 529 + frame_fmt &= ~FMT_PARITY_MASK; 530 + if ((cflag & PARENB) != 0) { 531 + if ((cflag & PARODD) != 0) { 532 + frame_fmt |= FMT_PARITY_ODD; 533 + } else { 534 + frame_fmt |= FMT_PARITY_EVEN; 535 + } 536 + } else { 537 + frame_fmt |= FMT_PARITY_NONE; 538 + } 539 + 540 + control &= ~CONTROL_MASK; 541 + if ((cflag & CRTSCTS) != 0) 542 + control |= (CONTROL_DTR_HIGH | CONTROL_RTS_HIGH); 543 + 544 + /* change control lines if we are switching to or from B0 */ 545 + /* FIXME: 546 + spin_lock_irqsave(&priv->lock, flags); 547 + control = priv->line_control; 548 + if ((cflag & CBAUD) == B0) 549 + priv->line_control &= ~(CONTROL_DTR | CONTROL_RTS); 550 + else 551 + priv->line_control |= (CONTROL_DTR | CONTROL_RTS); 552 + if (control != priv->line_control) { 553 + control = priv->line_control; 554 + spin_unlock_irqrestore(&priv->lock, flags); 555 + set_control_lines(serial->dev, control); 556 + } else { 557 + spin_unlock_irqrestore(&priv->lock, flags); 558 + } 559 + */ 560 + 561 + spin_lock_irqsave(&priv->lock, flags); 562 + if (divisor != priv->pending_setup.divisor 563 + || control != priv->pending_setup.control 564 + || frame_fmt != priv->pending_setup.frame_fmt) { 565 + priv->pending_setup.divisor = divisor; 566 + priv->pending_setup.control = control; 567 + priv->pending_setup.frame_fmt = frame_fmt; 568 + } 569 + spin_unlock_irqrestore(&priv->lock, flags); 570 + } 571 + 572 + static int oti6858_open(struct usb_serial_port *port, struct file *filp) 573 + { 574 + struct oti6858_private *priv = usb_get_serial_port_data(port); 575 + struct ktermios tmp_termios; 576 + struct usb_serial *serial = port->serial; 577 + struct oti6858_control_pkt *buf; 578 + unsigned long flags; 579 + int result; 580 + 581 + dbg("%s(port = %d)", __FUNCTION__, port->number); 582 + 583 + usb_clear_halt(serial->dev, port->write_urb->pipe); 584 + usb_clear_halt(serial->dev, port->read_urb->pipe); 585 + 586 + if (port->open_count != 1) 587 + return 0; 588 + 589 + if ((buf = kmalloc(OTI6858_CTRL_PKT_SIZE, GFP_KERNEL)) == NULL) { 590 + dev_err(&port->dev, "%s(): out of memory!\n", __FUNCTION__); 591 + return -ENOMEM; 592 + } 593 + 594 + result = usb_control_msg(serial->dev, usb_rcvctrlpipe(serial->dev, 0), 595 + OTI6858_REQ_T_GET_STATUS, 596 + OTI6858_REQ_GET_STATUS, 597 + 0, 0, 598 + buf, OTI6858_CTRL_PKT_SIZE, 599 + 100); 600 + if (result != OTI6858_CTRL_PKT_SIZE) { 601 + /* assume default (after power-on reset) values */ 602 + buf->divisor = cpu_to_le16(0x009c); /* 38400 bps */ 603 + buf->frame_fmt = 0x03; /* 8N1 */ 604 + buf->something = 0x43; 605 + buf->control = 0x4c; /* DTR, RTS */ 606 + buf->tx_status = 0x00; 607 + buf->pin_state = 0x5b; /* RTS, CTS, DSR, DTR, RI, DCD */ 608 + buf->rx_bytes_avail = 0x00; 609 + } 610 + 611 + spin_lock_irqsave(&priv->lock, flags); 612 + memcpy(&priv->status, buf, OTI6858_CTRL_PKT_SIZE); 613 + priv->pending_setup.divisor = buf->divisor; 614 + priv->pending_setup.frame_fmt = buf->frame_fmt; 615 + priv->pending_setup.control = buf->control; 616 + spin_unlock_irqrestore(&priv->lock, flags); 617 + kfree(buf); 618 + 619 + dbg("%s(): submitting interrupt urb", __FUNCTION__); 620 + port->interrupt_in_urb->dev = serial->dev; 621 + result = usb_submit_urb(port->interrupt_in_urb, GFP_KERNEL); 622 + if (result != 0) { 623 + dev_err(&port->dev, "%s(): usb_submit_urb() failed" 624 + " with error %d\n", __FUNCTION__, result); 625 + oti6858_close(port, NULL); 626 + return -EPROTO; 627 + } 628 + 629 + /* setup termios */ 630 + if (port->tty) 631 + oti6858_set_termios(port, &tmp_termios); 632 + 633 + return 0; 634 + } 635 + 636 + static void oti6858_close(struct usb_serial_port *port, struct file *filp) 637 + { 638 + struct oti6858_private *priv = usb_get_serial_port_data(port); 639 + unsigned long flags; 640 + long timeout; 641 + wait_queue_t wait; 642 + 643 + dbg("%s(port = %d)", __FUNCTION__, port->number); 644 + 645 + /* wait for data to drain from the buffer */ 646 + spin_lock_irqsave(&priv->lock, flags); 647 + timeout = 30 * HZ; /* PL2303_CLOSING_WAIT */ 648 + init_waitqueue_entry(&wait, current); 649 + add_wait_queue(&port->tty->write_wait, &wait); 650 + dbg("%s(): entering wait loop", __FUNCTION__); 651 + for (;;) { 652 + set_current_state(TASK_INTERRUPTIBLE); 653 + if (pl2303_buf_data_avail(priv->buf) == 0 654 + || timeout == 0 || signal_pending(current) 655 + || !usb_get_intfdata(port->serial->interface)) /* disconnect */ 656 + break; 657 + spin_unlock_irqrestore(&priv->lock, flags); 658 + timeout = schedule_timeout(timeout); 659 + spin_lock_irqsave(&priv->lock, flags); 660 + } 661 + set_current_state(TASK_RUNNING); 662 + remove_wait_queue(&port->tty->write_wait, &wait); 663 + dbg("%s(): after wait loop", __FUNCTION__); 664 + 665 + /* clear out any remaining data in the buffer */ 666 + pl2303_buf_clear(priv->buf); 667 + spin_unlock_irqrestore(&priv->lock, flags); 668 + 669 + /* wait for characters to drain from the device */ 670 + /* (this is long enough for the entire 256 byte */ 671 + /* pl2303 hardware buffer to drain with no flow */ 672 + /* control for data rates of 1200 bps or more, */ 673 + /* for lower rates we should really know how much */ 674 + /* data is in the buffer to compute a delay */ 675 + /* that is not unnecessarily long) */ 676 + /* FIXME 677 + bps = tty_get_baud_rate(port->tty); 678 + if (bps > 1200) 679 + timeout = max((HZ*2560)/bps,HZ/10); 680 + else 681 + */ 682 + timeout = 2*HZ; 683 + schedule_timeout_interruptible(timeout); 684 + dbg("%s(): after schedule_timeout_interruptible()", __FUNCTION__); 685 + 686 + /* cancel scheduled setup */ 687 + cancel_delayed_work(&priv->delayed_setup_work); 688 + cancel_delayed_work(&priv->delayed_write_work); 689 + flush_scheduled_work(); 690 + 691 + /* shutdown our urbs */ 692 + dbg("%s(): shutting down urbs", __FUNCTION__); 693 + usb_kill_urb(port->write_urb); 694 + usb_kill_urb(port->read_urb); 695 + usb_kill_urb(port->interrupt_in_urb); 696 + 697 + /* 698 + if (port->tty && (port->tty->termios->c_cflag) & HUPCL) { 699 + // drop DTR and RTS 700 + spin_lock_irqsave(&priv->lock, flags); 701 + priv->pending_setup.control &= ~CONTROL_MASK; 702 + spin_unlock_irqrestore(&priv->lock, flags); 703 + } 704 + */ 705 + } 706 + 707 + static int oti6858_tiocmset(struct usb_serial_port *port, struct file *file, 708 + unsigned int set, unsigned int clear) 709 + { 710 + struct oti6858_private *priv = usb_get_serial_port_data(port); 711 + unsigned long flags; 712 + u8 control; 713 + 714 + dbg("%s(port = %d, set = 0x%08x, clear = 0x%08x)", 715 + __FUNCTION__, port->number, set, clear); 716 + 717 + if (!usb_get_intfdata(port->serial->interface)) 718 + return -ENODEV; 719 + 720 + /* FIXME: check if this is correct (active high/low) */ 721 + spin_lock_irqsave(&priv->lock, flags); 722 + control = priv->pending_setup.control; 723 + if ((set & TIOCM_RTS) != 0) 724 + control |= CONTROL_RTS_HIGH; 725 + if ((set & TIOCM_DTR) != 0) 726 + control |= CONTROL_DTR_HIGH; 727 + if ((clear & TIOCM_RTS) != 0) 728 + control &= ~CONTROL_RTS_HIGH; 729 + if ((clear & TIOCM_DTR) != 0) 730 + control &= ~CONTROL_DTR_HIGH; 731 + 732 + if (control != priv->pending_setup.control) { 733 + priv->pending_setup.control = control; 734 + } 735 + spin_unlock_irqrestore(&priv->lock, flags); 736 + 737 + return 0; 738 + } 739 + 740 + static int oti6858_tiocmget(struct usb_serial_port *port, struct file *file) 741 + { 742 + struct oti6858_private *priv = usb_get_serial_port_data(port); 743 + unsigned long flags; 744 + unsigned pin_state; 745 + unsigned result = 0; 746 + 747 + dbg("%s(port = %d)", __FUNCTION__, port->number); 748 + 749 + if (!usb_get_intfdata(port->serial->interface)) 750 + return -ENODEV; 751 + 752 + spin_lock_irqsave(&priv->lock, flags); 753 + pin_state = priv->status.pin_state & PIN_MASK; 754 + spin_unlock_irqrestore(&priv->lock, flags); 755 + 756 + /* FIXME: check if this is correct (active high/low) */ 757 + if ((pin_state & PIN_RTS) != 0) 758 + result |= TIOCM_RTS; 759 + if ((pin_state & PIN_CTS) != 0) 760 + result |= TIOCM_CTS; 761 + if ((pin_state & PIN_DSR) != 0) 762 + result |= TIOCM_DSR; 763 + if ((pin_state & PIN_DTR) != 0) 764 + result |= TIOCM_DTR; 765 + if ((pin_state & PIN_RI) != 0) 766 + result |= TIOCM_RI; 767 + if ((pin_state & PIN_DCD) != 0) 768 + result |= TIOCM_CD; 769 + 770 + dbg("%s() = 0x%08x", __FUNCTION__, result); 771 + 772 + return result; 773 + } 774 + 775 + static int wait_modem_info(struct usb_serial_port *port, unsigned int arg) 776 + { 777 + struct oti6858_private *priv = usb_get_serial_port_data(port); 778 + unsigned long flags; 779 + unsigned int prev, status; 780 + unsigned int changed; 781 + 782 + spin_lock_irqsave(&priv->lock, flags); 783 + prev = priv->status.pin_state; 784 + spin_unlock_irqrestore(&priv->lock, flags); 785 + 786 + while (1) { 787 + wait_event_interruptible(priv->intr_wait, priv->status.pin_state != prev); 788 + if (signal_pending(current)) 789 + return -ERESTARTSYS; 790 + 791 + spin_lock_irqsave(&priv->lock, flags); 792 + status = priv->status.pin_state & PIN_MASK; 793 + spin_unlock_irqrestore(&priv->lock, flags); 794 + 795 + changed = prev ^ status; 796 + /* FIXME: check if this is correct (active high/low) */ 797 + if ( ((arg & TIOCM_RNG) && (changed & PIN_RI)) || 798 + ((arg & TIOCM_DSR) && (changed & PIN_DSR)) || 799 + ((arg & TIOCM_CD) && (changed & PIN_DCD)) || 800 + ((arg & TIOCM_CTS) && (changed & PIN_CTS))) { 801 + return 0; 802 + } 803 + prev = status; 804 + } 805 + 806 + /* NOTREACHED */ 807 + return 0; 808 + } 809 + 810 + static int oti6858_ioctl(struct usb_serial_port *port, struct file *file, 811 + unsigned int cmd, unsigned long arg) 812 + { 813 + void __user *user_arg = (void __user *) arg; 814 + unsigned int x; 815 + 816 + dbg("%s(port = %d, cmd = 0x%04x, arg = 0x%08lx)", 817 + __FUNCTION__, port->number, cmd, arg); 818 + 819 + switch (cmd) { 820 + case TCGETS: 821 + if (copy_to_user(user_arg, port->tty->termios, 822 + sizeof(struct ktermios))) { 823 + return -EFAULT; 824 + } 825 + return 0; 826 + 827 + case TCSETS: 828 + case TCSETSW: /* FIXME: this is not the same! */ 829 + case TCSETSF: /* FIXME: this is not the same! */ 830 + if (copy_from_user(port->tty->termios, user_arg, 831 + sizeof(struct ktermios))) { 832 + return -EFAULT; 833 + } 834 + oti6858_set_termios(port, NULL); 835 + return 0; 836 + 837 + case TCFLSH: 838 + /* FIXME */ 839 + return 0; 840 + 841 + case TIOCMBIS: 842 + if (copy_from_user(&x, user_arg, sizeof(x))) 843 + return -EFAULT; 844 + return oti6858_tiocmset(port, NULL, x, 0); 845 + 846 + case TIOCMBIC: 847 + if (copy_from_user(&x, user_arg, sizeof(x))) 848 + return -EFAULT; 849 + return oti6858_tiocmset(port, NULL, 0, x); 850 + 851 + case TIOCGSERIAL: 852 + if (copy_to_user(user_arg, port->tty->termios, 853 + sizeof(struct ktermios))) { 854 + return -EFAULT; 855 + } 856 + return 0; 857 + 858 + case TIOCSSERIAL: 859 + if (copy_from_user(port->tty->termios, user_arg, 860 + sizeof(struct ktermios))) { 861 + return -EFAULT; 862 + } 863 + oti6858_set_termios(port, NULL); 864 + return 0; 865 + 866 + case TIOCMIWAIT: 867 + dbg("%s(): TIOCMIWAIT", __FUNCTION__); 868 + return wait_modem_info(port, arg); 869 + 870 + default: 871 + dbg("%s(): 0x%04x not supported", __FUNCTION__, cmd); 872 + break; 873 + } 874 + 875 + return -ENOIOCTLCMD; 876 + } 877 + 878 + static void oti6858_break_ctl(struct usb_serial_port *port, int break_state) 879 + { 880 + int state; 881 + 882 + dbg("%s(port = %d)", __FUNCTION__, port->number); 883 + 884 + state = (break_state == 0) ? 0 : 1; 885 + dbg("%s(): turning break %s", __FUNCTION__, state ? "on" : "off"); 886 + 887 + /* FIXME */ 888 + /* 889 + result = usb_control_msg (serial->dev, usb_sndctrlpipe (serial->dev, 0), 890 + BREAK_REQUEST, BREAK_REQUEST_TYPE, state, 891 + 0, NULL, 0, 100); 892 + if (result != 0) 893 + dbg("%s(): error sending break", __FUNCTION__); 894 + */ 895 + } 896 + 897 + static void oti6858_shutdown(struct usb_serial *serial) 898 + { 899 + struct oti6858_private *priv; 900 + int i; 901 + 902 + dbg("%s()", __FUNCTION__); 903 + 904 + for (i = 0; i < serial->num_ports; ++i) { 905 + priv = usb_get_serial_port_data(serial->port[i]); 906 + if (priv) { 907 + pl2303_buf_free(priv->buf); 908 + kfree(priv); 909 + usb_set_serial_port_data(serial->port[i], NULL); 910 + } 911 + } 912 + } 913 + 914 + static void oti6858_read_int_callback(struct urb *urb) 915 + { 916 + struct usb_serial_port *port = (struct usb_serial_port *) urb->context; 917 + struct oti6858_private *priv = usb_get_serial_port_data(port); 918 + int transient = 0, can_recv = 0, resubmit = 1; 919 + 920 + dbg("%s(port = %d, urb->status = %d)", 921 + __FUNCTION__, port->number, urb->status); 922 + 923 + switch (urb->status) { 924 + case 0: 925 + /* success */ 926 + break; 927 + case -ECONNRESET: 928 + case -ENOENT: 929 + case -ESHUTDOWN: 930 + /* this urb is terminated, clean up */ 931 + dbg("%s(): urb shutting down with status: %d", 932 + __FUNCTION__, urb->status); 933 + return; 934 + default: 935 + dbg("%s(): nonzero urb status received: %d", 936 + __FUNCTION__, urb->status); 937 + break; 938 + } 939 + 940 + if (urb->status == 0 && urb->actual_length == OTI6858_CTRL_PKT_SIZE) { 941 + struct oti6858_control_pkt *xs = urb->transfer_buffer; 942 + unsigned long flags; 943 + 944 + spin_lock_irqsave(&priv->lock, flags); 945 + 946 + if (!priv->transient) { 947 + if (!OTI6858_CTRL_EQUALS_PENDING(xs, priv)) { 948 + if (xs->rx_bytes_avail == 0) { 949 + priv->transient = 4; 950 + priv->setup_done = 0; 951 + resubmit = 0; 952 + dbg("%s(): scheduling setup_line()", 953 + __FUNCTION__); 954 + schedule_delayed_work(&priv->delayed_setup_work, 0); 955 + } 956 + } 957 + } else { 958 + if (OTI6858_CTRL_EQUALS_PENDING(xs, priv)) { 959 + priv->transient = 0; 960 + } else if (!priv->setup_done) { 961 + resubmit = 0; 962 + } else if (--priv->transient == 0) { 963 + if (xs->rx_bytes_avail == 0) { 964 + priv->transient = 4; 965 + priv->setup_done = 0; 966 + resubmit = 0; 967 + dbg("%s(): scheduling setup_line()", 968 + __FUNCTION__); 969 + schedule_delayed_work(&priv->delayed_setup_work, 0); 970 + } 971 + } 972 + } 973 + 974 + if (!priv->transient) { 975 + if (xs->pin_state != priv->status.pin_state) 976 + wake_up_interruptible(&priv->intr_wait); 977 + memcpy(&priv->status, xs, OTI6858_CTRL_PKT_SIZE); 978 + } 979 + 980 + if (!priv->transient && xs->rx_bytes_avail != 0) { 981 + can_recv = xs->rx_bytes_avail; 982 + priv->flags.read_urb_in_use = 1; 983 + } 984 + 985 + transient = priv->transient; 986 + spin_unlock_irqrestore(&priv->lock, flags); 987 + } 988 + 989 + if (can_recv) { 990 + int result; 991 + 992 + port->read_urb->dev = port->serial->dev; 993 + result = usb_submit_urb(port->read_urb, GFP_ATOMIC); 994 + if (result != 0) { 995 + priv->flags.read_urb_in_use = 0; 996 + dev_err(&port->dev, "%s(): usb_submit_urb() failed," 997 + " error %d\n", __FUNCTION__, result); 998 + } else { 999 + resubmit = 0; 1000 + } 1001 + } else if (!transient) { 1002 + unsigned long flags; 1003 + 1004 + spin_lock_irqsave(&priv->lock, flags); 1005 + if (priv->flags.write_urb_in_use == 0 1006 + && pl2303_buf_data_avail(priv->buf) != 0) { 1007 + schedule_delayed_work(&priv->delayed_write_work,0); 1008 + resubmit = 0; 1009 + } 1010 + spin_unlock_irqrestore(&priv->lock, flags); 1011 + } 1012 + 1013 + if (resubmit) { 1014 + int result; 1015 + 1016 + // dbg("%s(): submitting interrupt urb", __FUNCTION__); 1017 + urb->dev = port->serial->dev; 1018 + result = usb_submit_urb(urb, GFP_ATOMIC); 1019 + if (result != 0) { 1020 + dev_err(&urb->dev->dev, 1021 + "%s(): usb_submit_urb() failed with" 1022 + " error %d\n", __FUNCTION__, result); 1023 + } 1024 + } 1025 + } 1026 + 1027 + static void oti6858_read_bulk_callback(struct urb *urb) 1028 + { 1029 + struct usb_serial_port *port = (struct usb_serial_port *) urb->context; 1030 + struct oti6858_private *priv = usb_get_serial_port_data(port); 1031 + struct tty_struct *tty; 1032 + unsigned char *data = urb->transfer_buffer; 1033 + unsigned long flags; 1034 + int i, result; 1035 + char tty_flag; 1036 + 1037 + dbg("%s(port = %d, urb->status = %d)", 1038 + __FUNCTION__, port->number, urb->status); 1039 + 1040 + spin_lock_irqsave(&priv->lock, flags); 1041 + priv->flags.read_urb_in_use = 0; 1042 + spin_unlock_irqrestore(&priv->lock, flags); 1043 + 1044 + if (urb->status != 0) { 1045 + if (!port->open_count) { 1046 + dbg("%s(): port is closed, exiting", __FUNCTION__); 1047 + return; 1048 + } 1049 + /* 1050 + if (urb->status == -EPROTO) { 1051 + // PL2303 mysteriously fails with -EPROTO reschedule the read 1052 + dbg("%s - caught -EPROTO, resubmitting the urb", __FUNCTION__); 1053 + urb->status = 0; 1054 + urb->dev = port->serial->dev; 1055 + result = usb_submit_urb(urb, GFP_ATOMIC); 1056 + if (result) 1057 + dev_err(&urb->dev->dev, "%s - failed resubmitting read urb, error %d\n", __FUNCTION__, result); 1058 + return; 1059 + } 1060 + */ 1061 + dbg("%s(): unable to handle the error, exiting", __FUNCTION__); 1062 + return; 1063 + } 1064 + 1065 + // get tty_flag from status 1066 + tty_flag = TTY_NORMAL; 1067 + 1068 + /* FIXME: probably, errors will be signalled using interrupt pipe! */ 1069 + /* 1070 + // break takes precedence over parity, 1071 + // which takes precedence over framing errors 1072 + if (status & UART_BREAK_ERROR ) 1073 + tty_flag = TTY_BREAK; 1074 + else if (status & UART_PARITY_ERROR) 1075 + tty_flag = TTY_PARITY; 1076 + else if (status & UART_FRAME_ERROR) 1077 + tty_flag = TTY_FRAME; 1078 + dbg("%s - tty_flag = %d", __FUNCTION__, tty_flag); 1079 + */ 1080 + 1081 + tty = port->tty; 1082 + if (tty != NULL && urb->actual_length > 0) { 1083 + tty_buffer_request_room(tty, urb->actual_length); 1084 + for (i = 0; i < urb->actual_length; ++i) 1085 + tty_insert_flip_char(tty, data[i], tty_flag); 1086 + tty_flip_buffer_push(tty); 1087 + } 1088 + 1089 + // schedule the interrupt urb if we are still open */ 1090 + if (port->open_count != 0) { 1091 + port->interrupt_in_urb->dev = port->serial->dev; 1092 + result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC); 1093 + if (result != 0) { 1094 + dev_err(&port->dev, "%s(): usb_submit_urb() failed," 1095 + " error %d\n", __FUNCTION__, result); 1096 + } 1097 + } 1098 + } 1099 + 1100 + static void oti6858_write_bulk_callback(struct urb *urb) 1101 + { 1102 + struct usb_serial_port *port = (struct usb_serial_port *) urb->context; 1103 + struct oti6858_private *priv = usb_get_serial_port_data(port); 1104 + int result; 1105 + 1106 + dbg("%s(port = %d, urb->status = %d)", 1107 + __FUNCTION__, port->number, urb->status); 1108 + 1109 + switch (urb->status) { 1110 + case 0: 1111 + /* success */ 1112 + break; 1113 + case -ECONNRESET: 1114 + case -ENOENT: 1115 + case -ESHUTDOWN: 1116 + /* this urb is terminated, clean up */ 1117 + dbg("%s(): urb shutting down with status: %d", 1118 + __FUNCTION__, urb->status); 1119 + priv->flags.write_urb_in_use = 0; 1120 + return; 1121 + default: 1122 + /* error in the urb, so we have to resubmit it */ 1123 + dbg("%s(): nonzero write bulk status received: %d", 1124 + __FUNCTION__, urb->status); 1125 + dbg("%s(): overflow in write", __FUNCTION__); 1126 + 1127 + port->write_urb->transfer_buffer_length = 1; 1128 + port->write_urb->dev = port->serial->dev; 1129 + result = usb_submit_urb(port->write_urb, GFP_ATOMIC); 1130 + if (result) { 1131 + dev_err(&port->dev, "%s(): usb_submit_urb() failed," 1132 + " error %d\n", __FUNCTION__, result); 1133 + } else { 1134 + return; 1135 + } 1136 + } 1137 + 1138 + priv->flags.write_urb_in_use = 0; 1139 + 1140 + // schedule the interrupt urb if we are still open */ 1141 + port->interrupt_in_urb->dev = port->serial->dev; 1142 + dbg("%s(): submitting interrupt urb", __FUNCTION__); 1143 + result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC); 1144 + if (result != 0) { 1145 + dev_err(&port->dev, "%s(): failed submitting int urb," 1146 + " error %d\n", __FUNCTION__, result); 1147 + } 1148 + } 1149 + 1150 + 1151 + /* 1152 + * pl2303_buf_alloc 1153 + * 1154 + * Allocate a circular buffer and all associated memory. 1155 + */ 1156 + static struct pl2303_buf *pl2303_buf_alloc(unsigned int size) 1157 + { 1158 + struct pl2303_buf *pb; 1159 + 1160 + if (size == 0) 1161 + return NULL; 1162 + 1163 + pb = (struct pl2303_buf *)kmalloc(sizeof(struct pl2303_buf), GFP_KERNEL); 1164 + if (pb == NULL) 1165 + return NULL; 1166 + 1167 + pb->buf_buf = kmalloc(size, GFP_KERNEL); 1168 + if (pb->buf_buf == NULL) { 1169 + kfree(pb); 1170 + return NULL; 1171 + } 1172 + 1173 + pb->buf_size = size; 1174 + pb->buf_get = pb->buf_put = pb->buf_buf; 1175 + 1176 + return pb; 1177 + } 1178 + 1179 + /* 1180 + * pl2303_buf_free 1181 + * 1182 + * Free the buffer and all associated memory. 1183 + */ 1184 + static void pl2303_buf_free(struct pl2303_buf *pb) 1185 + { 1186 + if (pb) { 1187 + kfree(pb->buf_buf); 1188 + kfree(pb); 1189 + } 1190 + } 1191 + 1192 + /* 1193 + * pl2303_buf_clear 1194 + * 1195 + * Clear out all data in the circular buffer. 1196 + */ 1197 + static void pl2303_buf_clear(struct pl2303_buf *pb) 1198 + { 1199 + if (pb != NULL) { 1200 + /* equivalent to a get of all data available */ 1201 + pb->buf_get = pb->buf_put; 1202 + } 1203 + } 1204 + 1205 + /* 1206 + * pl2303_buf_data_avail 1207 + * 1208 + * Return the number of bytes of data available in the circular 1209 + * buffer. 1210 + */ 1211 + static unsigned int pl2303_buf_data_avail(struct pl2303_buf *pb) 1212 + { 1213 + if (pb == NULL) 1214 + return 0; 1215 + return ((pb->buf_size + pb->buf_put - pb->buf_get) % pb->buf_size); 1216 + } 1217 + 1218 + /* 1219 + * pl2303_buf_space_avail 1220 + * 1221 + * Return the number of bytes of space available in the circular 1222 + * buffer. 1223 + */ 1224 + static unsigned int pl2303_buf_space_avail(struct pl2303_buf *pb) 1225 + { 1226 + if (pb == NULL) 1227 + return 0; 1228 + return ((pb->buf_size + pb->buf_get - pb->buf_put - 1) % pb->buf_size); 1229 + } 1230 + 1231 + /* 1232 + * pl2303_buf_put 1233 + * 1234 + * Copy data data from a user buffer and put it into the circular buffer. 1235 + * Restrict to the amount of space available. 1236 + * 1237 + * Return the number of bytes copied. 1238 + */ 1239 + static unsigned int pl2303_buf_put(struct pl2303_buf *pb, const char *buf, 1240 + unsigned int count) 1241 + { 1242 + unsigned int len; 1243 + 1244 + if (pb == NULL) 1245 + return 0; 1246 + 1247 + len = pl2303_buf_space_avail(pb); 1248 + if (count > len) 1249 + count = len; 1250 + 1251 + if (count == 0) 1252 + return 0; 1253 + 1254 + len = pb->buf_buf + pb->buf_size - pb->buf_put; 1255 + if (count > len) { 1256 + memcpy(pb->buf_put, buf, len); 1257 + memcpy(pb->buf_buf, buf+len, count - len); 1258 + pb->buf_put = pb->buf_buf + count - len; 1259 + } else { 1260 + memcpy(pb->buf_put, buf, count); 1261 + if (count < len) 1262 + pb->buf_put += count; 1263 + else /* count == len */ 1264 + pb->buf_put = pb->buf_buf; 1265 + } 1266 + 1267 + return count; 1268 + } 1269 + 1270 + /* 1271 + * pl2303_buf_get 1272 + * 1273 + * Get data from the circular buffer and copy to the given buffer. 1274 + * Restrict to the amount of data available. 1275 + * 1276 + * Return the number of bytes copied. 1277 + */ 1278 + static unsigned int pl2303_buf_get(struct pl2303_buf *pb, char *buf, 1279 + unsigned int count) 1280 + { 1281 + unsigned int len; 1282 + 1283 + if (pb == NULL) 1284 + return 0; 1285 + 1286 + len = pl2303_buf_data_avail(pb); 1287 + if (count > len) 1288 + count = len; 1289 + 1290 + if (count == 0) 1291 + return 0; 1292 + 1293 + len = pb->buf_buf + pb->buf_size - pb->buf_get; 1294 + if (count > len) { 1295 + memcpy(buf, pb->buf_get, len); 1296 + memcpy(buf+len, pb->buf_buf, count - len); 1297 + pb->buf_get = pb->buf_buf + count - len; 1298 + } else { 1299 + memcpy(buf, pb->buf_get, count); 1300 + if (count < len) 1301 + pb->buf_get += count; 1302 + else /* count == len */ 1303 + pb->buf_get = pb->buf_buf; 1304 + } 1305 + 1306 + return count; 1307 + } 1308 + 1309 + /* module description and (de)initialization */ 1310 + 1311 + static int __init oti6858_init(void) 1312 + { 1313 + int retval; 1314 + 1315 + if ((retval = usb_serial_register(&oti6858_device)) == 0) { 1316 + if ((retval = usb_register(&oti6858_driver)) != 0) 1317 + usb_serial_deregister(&oti6858_device); 1318 + else 1319 + return 0; 1320 + } 1321 + 1322 + return retval; 1323 + } 1324 + 1325 + static void __exit oti6858_exit(void) 1326 + { 1327 + usb_deregister(&oti6858_driver); 1328 + usb_serial_deregister(&oti6858_device); 1329 + } 1330 + 1331 + module_init(oti6858_init); 1332 + module_exit(oti6858_exit); 1333 + 1334 + MODULE_DESCRIPTION(OTI6858_DESCRIPTION); 1335 + MODULE_AUTHOR(OTI6858_AUTHOR); 1336 + MODULE_VERSION(OTI6858_VERSION); 1337 + MODULE_LICENSE("GPL"); 1338 + 1339 + module_param(debug, bool, S_IRUGO | S_IWUSR); 1340 + MODULE_PARM_DESC(debug, "enable debug output"); 1341 +
+15
drivers/usb/serial/oti6858.h
··· 1 + /* 2 + * Ours Technology Inc. OTi-6858 USB to serial adapter driver. 3 + * 4 + * This program is free software; you can redistribute it and/or modify 5 + * it under the terms of the GNU General Public License as published by 6 + * the Free Software Foundation; either version 2 of the License, or 7 + * (at your option) any later version. 8 + */ 9 + #ifndef __LINUX_USB_SERIAL_OTI6858_H 10 + #define __LINUX_USB_SERIAL_OTI6858_H 11 + 12 + #define OTI6858_VENDOR_ID 0x0ea0 13 + #define OTI6858_PRODUCT_ID 0x6858 14 + 15 + #endif