1 /* 2 Option Card (PCMCIA to) USB to Serial Driver 3 4 Copyright (C) 2005 Matthias Urlichs <smurf@smurf.noris.de> 5 6 This driver is free software; you can redistribute it and/or modify 7 it under the terms of Version 2 of the GNU General Public License as 8 published by the Free Software Foundation. 9 10 Portions copied from the Keyspan driver by Hugh Blemings <hugh@blemings.org> 11 12 History: 13 14 2005-05-19 v0.1 Initial version, based on incomplete docs 15 and analysis of misbehavior with the standard driver 16 2005-05-20 v0.2 Extended the input buffer to avoid losing 17 random 64-byte chunks of data 18 2005-05-21 v0.3 implemented chars_in_buffer() 19 turned on low_latency 20 simplified the code somewhat 21 2005-05-24 v0.4 option_write() sometimes deadlocked under heavy load 22 removed some dead code 23 added sponsor notice 24 coding style clean-up 25 2005-06-20 v0.4.1 add missing braces :-/ 26 killed end-of-line whitespace 27 2005-07-15 v0.4.2 rename WLAN product to FUSION, add FUSION2 28 2005-09-10 v0.4.3 added HUAWEI E600 card and Audiovox AirCard 29 2005-09-20 v0.4.4 increased recv buffer size: the card sometimes 30 wants to send >2000 bytes. 31 32 Work sponsored by: Sigos GmbH, Germany <info@sigos.de> 33 34 */ 35 36 #define DRIVER_VERSION "v0.4" 37 #define DRIVER_AUTHOR "Matthias Urlichs <smurf@smurf.noris.de>" 38 #define DRIVER_DESC "Option Card (PC-Card to) USB to Serial Driver" 39 40 #include <linux/config.h> 41 #include <linux/kernel.h> 42 #include <linux/jiffies.h> 43 #include <linux/errno.h> 44 #include <linux/tty.h> 45 #include <linux/tty_flip.h> 46 #include <linux/module.h> 47 #include <linux/usb.h> 48 #include "usb-serial.h" 49 50 /* Function prototypes */ 51 static int option_open(struct usb_serial_port *port, struct file *filp); 52 static void option_close(struct usb_serial_port *port, struct file *filp); 53 static int option_startup(struct usb_serial *serial); 54 static void option_shutdown(struct usb_serial *serial); 55 static void option_rx_throttle(struct usb_serial_port *port); 56 static void option_rx_unthrottle(struct usb_serial_port *port); 57 static int option_write_room(struct usb_serial_port *port); 58 59 static void option_instat_callback(struct urb *urb, struct pt_regs *regs); 60 61 static int option_write(struct usb_serial_port *port, 62 const unsigned char *buf, int count); 63 64 static int option_chars_in_buffer(struct usb_serial_port *port); 65 static int option_ioctl(struct usb_serial_port *port, struct file *file, 66 unsigned int cmd, unsigned long arg); 67 static void option_set_termios(struct usb_serial_port *port, 68 struct termios *old); 69 static void option_break_ctl(struct usb_serial_port *port, int break_state); 70 static int option_tiocmget(struct usb_serial_port *port, struct file *file); 71 static int option_tiocmset(struct usb_serial_port *port, struct file *file, 72 unsigned int set, unsigned int clear); 73 static int option_send_setup(struct usb_serial_port *port); 74 75 /* Vendor and product IDs */ 76 #define OPTION_VENDOR_ID 0x0AF0 77 #define HUAWEI_VENDOR_ID 0x12D1 78 #define AUDIOVOX_VENDOR_ID 0x0F3D 79 80 #define OPTION_PRODUCT_OLD 0x5000 81 #define OPTION_PRODUCT_FUSION 0x6000 82 #define OPTION_PRODUCT_FUSION2 0x6300 83 #define HUAWEI_PRODUCT_E600 0x1001 84 #define AUDIOVOX_PRODUCT_AIRCARD 0x0112 85 86 static struct usb_device_id option_ids[] = { 87 { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_OLD) }, 88 { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_FUSION) }, 89 { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_FUSION2) }, 90 { USB_DEVICE(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E600) }, 91 { USB_DEVICE(AUDIOVOX_VENDOR_ID, AUDIOVOX_PRODUCT_AIRCARD) }, 92 { } /* Terminating entry */ 93 }; 94 95 MODULE_DEVICE_TABLE(usb, option_ids); 96 97 static struct usb_driver option_driver = { 98 .owner = THIS_MODULE, 99 .name = "option", 100 .probe = usb_serial_probe, 101 .disconnect = usb_serial_disconnect, 102 .id_table = option_ids, 103 }; 104 105 /* The card has three separate interfaces, wich the serial driver 106 * recognizes separately, thus num_port=1. 107 */ 108 static struct usb_serial_device_type option_3port_device = { 109 .owner = THIS_MODULE, 110 .name = "Option 3G data card", 111 .short_name = "option", 112 .id_table = option_ids, 113 .num_interrupt_in = NUM_DONT_CARE, 114 .num_bulk_in = NUM_DONT_CARE, 115 .num_bulk_out = NUM_DONT_CARE, 116 .num_ports = 1, /* 3, but the card reports its ports separately */ 117 .open = option_open, 118 .close = option_close, 119 .write = option_write, 120 .write_room = option_write_room, 121 .chars_in_buffer = option_chars_in_buffer, 122 .throttle = option_rx_throttle, 123 .unthrottle = option_rx_unthrottle, 124 .ioctl = option_ioctl, 125 .set_termios = option_set_termios, 126 .break_ctl = option_break_ctl, 127 .tiocmget = option_tiocmget, 128 .tiocmset = option_tiocmset, 129 .attach = option_startup, 130 .shutdown = option_shutdown, 131 .read_int_callback = option_instat_callback, 132 }; 133 134 #ifdef CONFIG_USB_DEBUG 135 static int debug; 136 #else 137 #define debug 0 138 #endif 139 140 /* per port private data */ 141 142 #define N_IN_URB 4 143 #define N_OUT_URB 1 144 #define IN_BUFLEN 4096 145 #define OUT_BUFLEN 128 146 147 struct option_port_private { 148 /* Input endpoints and buffer for this port */ 149 struct urb *in_urbs[N_IN_URB]; 150 char in_buffer[N_IN_URB][IN_BUFLEN]; 151 /* Output endpoints and buffer for this port */ 152 struct urb *out_urbs[N_OUT_URB]; 153 char out_buffer[N_OUT_URB][OUT_BUFLEN]; 154 155 /* Settings for the port */ 156 int rts_state; /* Handshaking pins (outputs) */ 157 int dtr_state; 158 int cts_state; /* Handshaking pins (inputs) */ 159 int dsr_state; 160 int dcd_state; 161 int ri_state; 162 163 unsigned long tx_start_time[N_OUT_URB]; 164 }; 165 166 /* Functions used by new usb-serial code. */ 167 static int __init option_init(void) 168 { 169 int retval; 170 retval = usb_serial_register(&option_3port_device); 171 if (retval) 172 goto failed_3port_device_register; 173 retval = usb_register(&option_driver); 174 if (retval) 175 goto failed_driver_register; 176 177 info(DRIVER_DESC ": " DRIVER_VERSION); 178 179 return 0; 180 181 failed_driver_register: 182 usb_serial_deregister (&option_3port_device); 183 failed_3port_device_register: 184 return retval; 185 } 186 187 static void __exit option_exit(void) 188 { 189 usb_deregister (&option_driver); 190 usb_serial_deregister (&option_3port_device); 191 } 192 193 module_init(option_init); 194 module_exit(option_exit); 195 196 static void option_rx_throttle(struct usb_serial_port *port) 197 { 198 dbg("%s", __FUNCTION__); 199 } 200 201 static void option_rx_unthrottle(struct usb_serial_port *port) 202 { 203 dbg("%s", __FUNCTION__); 204 } 205 206 static void option_break_ctl(struct usb_serial_port *port, int break_state) 207 { 208 /* Unfortunately, I don't know how to send a break */ 209 dbg("%s", __FUNCTION__); 210 } 211 212 static void option_set_termios(struct usb_serial_port *port, 213 struct termios *old_termios) 214 { 215 dbg("%s", __FUNCTION__); 216 217 option_send_setup(port); 218 } 219 220 static int option_tiocmget(struct usb_serial_port *port, struct file *file) 221 { 222 unsigned int value; 223 struct option_port_private *portdata; 224 225 portdata = usb_get_serial_port_data(port); 226 227 value = ((portdata->rts_state) ? TIOCM_RTS : 0) | 228 ((portdata->dtr_state) ? TIOCM_DTR : 0) | 229 ((portdata->cts_state) ? TIOCM_CTS : 0) | 230 ((portdata->dsr_state) ? TIOCM_DSR : 0) | 231 ((portdata->dcd_state) ? TIOCM_CAR : 0) | 232 ((portdata->ri_state) ? TIOCM_RNG : 0); 233 234 return value; 235 } 236 237 static int option_tiocmset(struct usb_serial_port *port, struct file *file, 238 unsigned int set, unsigned int clear) 239 { 240 struct option_port_private *portdata; 241 242 portdata = usb_get_serial_port_data(port); 243 244 if (set & TIOCM_RTS) 245 portdata->rts_state = 1; 246 if (set & TIOCM_DTR) 247 portdata->dtr_state = 1; 248 249 if (clear & TIOCM_RTS) 250 portdata->rts_state = 0; 251 if (clear & TIOCM_DTR) 252 portdata->dtr_state = 0; 253 return option_send_setup(port); 254 } 255 256 static int option_ioctl(struct usb_serial_port *port, struct file *file, 257 unsigned int cmd, unsigned long arg) 258 { 259 return -ENOIOCTLCMD; 260 } 261 262 /* Write */ 263 static int option_write(struct usb_serial_port *port, 264 const unsigned char *buf, int count) 265 { 266 struct option_port_private *portdata; 267 int i; 268 int left, todo; 269 struct urb *this_urb = NULL; /* spurious */ 270 int err; 271 272 portdata = usb_get_serial_port_data(port); 273 274 dbg("%s: write (%d chars)", __FUNCTION__, count); 275 276 i = 0; 277 left = count; 278 for (i=0; left > 0 && i < N_OUT_URB; i++) { 279 todo = left; 280 if (todo > OUT_BUFLEN) 281 todo = OUT_BUFLEN; 282 283 this_urb = portdata->out_urbs[i]; 284 if (this_urb->status == -EINPROGRESS) { 285 if (time_before(jiffies, 286 portdata->tx_start_time[i] + 10 * HZ)) 287 continue; 288 usb_unlink_urb(this_urb); 289 continue; 290 } 291 if (this_urb->status != 0) 292 dbg("usb_write %p failed (err=%d)", 293 this_urb, this_urb->status); 294 295 dbg("%s: endpoint %d buf %d", __FUNCTION__, 296 usb_pipeendpoint(this_urb->pipe), i); 297 298 /* send the data */ 299 memcpy (this_urb->transfer_buffer, buf, todo); 300 this_urb->transfer_buffer_length = todo; 301 302 this_urb->dev = port->serial->dev; 303 err = usb_submit_urb(this_urb, GFP_ATOMIC); 304 if (err) { 305 dbg("usb_submit_urb %p (write bulk) failed " 306 "(%d, has %d)", this_urb, 307 err, this_urb->status); 308 continue; 309 } 310 portdata->tx_start_time[i] = jiffies; 311 buf += todo; 312 left -= todo; 313 } 314 315 count -= left; 316 dbg("%s: wrote (did %d)", __FUNCTION__, count); 317 return count; 318 } 319 320 static void option_indat_callback(struct urb *urb, struct pt_regs *regs) 321 { 322 int i, err; 323 int endpoint; 324 struct usb_serial_port *port; 325 struct tty_struct *tty; 326 unsigned char *data = urb->transfer_buffer; 327 328 dbg("%s: %p", __FUNCTION__, urb); 329 330 endpoint = usb_pipeendpoint(urb->pipe); 331 port = (struct usb_serial_port *) urb->context; 332 333 if (urb->status) { 334 dbg("%s: nonzero status: %d on endpoint %02x.", 335 __FUNCTION__, urb->status, endpoint); 336 } else { 337 tty = port->tty; 338 if (urb->actual_length) { 339 for (i = 0; i < urb->actual_length ; ++i) { 340 if (tty->flip.count >= TTY_FLIPBUF_SIZE) 341 tty_flip_buffer_push(tty); 342 tty_insert_flip_char(tty, data[i], 0); 343 } 344 tty_flip_buffer_push(tty); 345 } else { 346 dbg("%s: empty read urb received", __FUNCTION__); 347 } 348 349 /* Resubmit urb so we continue receiving */ 350 if (port->open_count && urb->status != -ESHUTDOWN) { 351 err = usb_submit_urb(urb, GFP_ATOMIC); 352 if (err) 353 printk(KERN_ERR "%s: resubmit read urb failed. " 354 "(%d)", __FUNCTION__, err); 355 } 356 } 357 return; 358 } 359 360 static void option_outdat_callback(struct urb *urb, struct pt_regs *regs) 361 { 362 struct usb_serial_port *port; 363 364 dbg("%s", __FUNCTION__); 365 366 port = (struct usb_serial_port *) urb->context; 367 368 if (port->open_count) 369 schedule_work(&port->work); 370 } 371 372 static void option_instat_callback(struct urb *urb, struct pt_regs *regs) 373 { 374 int err; 375 struct usb_serial_port *port = (struct usb_serial_port *) urb->context; 376 struct option_port_private *portdata = usb_get_serial_port_data(port); 377 struct usb_serial *serial = port->serial; 378 379 dbg("%s", __FUNCTION__); 380 dbg("%s: urb %p port %p has data %p", __FUNCTION__,urb,port,portdata); 381 382 if (urb->status == 0) { 383 struct usb_ctrlrequest *req_pkt = 384 (struct usb_ctrlrequest *)urb->transfer_buffer; 385 386 if (!req_pkt) { 387 dbg("%s: NULL req_pkt\n", __FUNCTION__); 388 return; 389 } 390 if ((req_pkt->bRequestType == 0xA1) && 391 (req_pkt->bRequest == 0x20)) { 392 int old_dcd_state; 393 unsigned char signals = *((unsigned char *) 394 urb->transfer_buffer + 395 sizeof(struct usb_ctrlrequest)); 396 397 dbg("%s: signal x%x", __FUNCTION__, signals); 398 399 old_dcd_state = portdata->dcd_state; 400 portdata->cts_state = 1; 401 portdata->dcd_state = ((signals & 0x01) ? 1 : 0); 402 portdata->dsr_state = ((signals & 0x02) ? 1 : 0); 403 portdata->ri_state = ((signals & 0x08) ? 1 : 0); 404 405 if (port->tty && !C_CLOCAL(port->tty) && 406 old_dcd_state && !portdata->dcd_state) 407 tty_hangup(port->tty); 408 } else { 409 dbg("%s: type %x req %x", __FUNCTION__, 410 req_pkt->bRequestType,req_pkt->bRequest); 411 } 412 } else 413 dbg("%s: error %d", __FUNCTION__, urb->status); 414 415 /* Resubmit urb so we continue receiving IRQ data */ 416 if (urb->status != -ESHUTDOWN) { 417 urb->dev = serial->dev; 418 err = usb_submit_urb(urb, GFP_ATOMIC); 419 if (err) 420 dbg("%s: resubmit intr urb failed. (%d)", 421 __FUNCTION__, err); 422 } 423 } 424 425 static int option_write_room(struct usb_serial_port *port) 426 { 427 struct option_port_private *portdata; 428 int i; 429 int data_len = 0; 430 struct urb *this_urb; 431 432 portdata = usb_get_serial_port_data(port); 433 434 for (i=0; i < N_OUT_URB; i++) { 435 this_urb = portdata->out_urbs[i]; 436 if (this_urb && this_urb->status != -EINPROGRESS) 437 data_len += OUT_BUFLEN; 438 } 439 440 dbg("%s: %d", __FUNCTION__, data_len); 441 return data_len; 442 } 443 444 static int option_chars_in_buffer(struct usb_serial_port *port) 445 { 446 struct option_port_private *portdata; 447 int i; 448 int data_len = 0; 449 struct urb *this_urb; 450 451 portdata = usb_get_serial_port_data(port); 452 453 for (i=0; i < N_OUT_URB; i++) { 454 this_urb = portdata->out_urbs[i]; 455 if (this_urb && this_urb->status == -EINPROGRESS) 456 data_len += this_urb->transfer_buffer_length; 457 } 458 dbg("%s: %d", __FUNCTION__, data_len); 459 return data_len; 460 } 461 462 static int option_open(struct usb_serial_port *port, struct file *filp) 463 { 464 struct option_port_private *portdata; 465 struct usb_serial *serial = port->serial; 466 int i, err; 467 struct urb *urb; 468 469 portdata = usb_get_serial_port_data(port); 470 471 dbg("%s", __FUNCTION__); 472 473 /* Set some sane defaults */ 474 portdata->rts_state = 1; 475 portdata->dtr_state = 1; 476 477 /* Reset low level data toggle and start reading from endpoints */ 478 for (i = 0; i < N_IN_URB; i++) { 479 urb = portdata->in_urbs[i]; 480 if (! urb) 481 continue; 482 if (urb->dev != serial->dev) { 483 dbg("%s: dev %p != %p", __FUNCTION__, 484 urb->dev, serial->dev); 485 continue; 486 } 487 488 /* 489 * make sure endpoint data toggle is synchronized with the 490 * device 491 */ 492 usb_clear_halt(urb->dev, urb->pipe); 493 494 err = usb_submit_urb(urb, GFP_KERNEL); 495 if (err) { 496 dbg("%s: submit urb %d failed (%d) %d", 497 __FUNCTION__, i, err, 498 urb->transfer_buffer_length); 499 } 500 } 501 502 /* Reset low level data toggle on out endpoints */ 503 for (i = 0; i < N_OUT_URB; i++) { 504 urb = portdata->out_urbs[i]; 505 if (! urb) 506 continue; 507 urb->dev = serial->dev; 508 /* usb_settoggle(urb->dev, usb_pipeendpoint(urb->pipe), 509 usb_pipeout(urb->pipe), 0); */ 510 } 511 512 port->tty->low_latency = 1; 513 514 option_send_setup(port); 515 516 return (0); 517 } 518 519 static inline void stop_urb(struct urb *urb) 520 { 521 if (urb && urb->status == -EINPROGRESS) 522 usb_kill_urb(urb); 523 } 524 525 static void option_close(struct usb_serial_port *port, struct file *filp) 526 { 527 int i; 528 struct usb_serial *serial = port->serial; 529 struct option_port_private *portdata; 530 531 dbg("%s", __FUNCTION__); 532 portdata = usb_get_serial_port_data(port); 533 534 portdata->rts_state = 0; 535 portdata->dtr_state = 0; 536 537 if (serial->dev) { 538 option_send_setup(port); 539 540 /* Stop reading/writing urbs */ 541 for (i = 0; i < N_IN_URB; i++) 542 stop_urb(portdata->in_urbs[i]); 543 for (i = 0; i < N_OUT_URB; i++) 544 stop_urb(portdata->out_urbs[i]); 545 } 546 port->tty = NULL; 547 } 548 549 /* Helper functions used by option_setup_urbs */ 550 static struct urb *option_setup_urb(struct usb_serial *serial, int endpoint, 551 int dir, void *ctx, char *buf, int len, 552 void (*callback)(struct urb *, struct pt_regs *regs)) 553 { 554 struct urb *urb; 555 556 if (endpoint == -1) 557 return NULL; /* endpoint not needed */ 558 559 urb = usb_alloc_urb(0, GFP_KERNEL); /* No ISO */ 560 if (urb == NULL) { 561 dbg("%s: alloc for endpoint %d failed.", __FUNCTION__, endpoint); 562 return NULL; 563 } 564 565 /* Fill URB using supplied data. */ 566 usb_fill_bulk_urb(urb, serial->dev, 567 usb_sndbulkpipe(serial->dev, endpoint) | dir, 568 buf, len, callback, ctx); 569 570 return urb; 571 } 572 573 /* Setup urbs */ 574 static void option_setup_urbs(struct usb_serial *serial) 575 { 576 int j; 577 struct usb_serial_port *port; 578 struct option_port_private *portdata; 579 580 dbg("%s", __FUNCTION__); 581 582 port = serial->port[0]; 583 portdata = usb_get_serial_port_data(port); 584 585 /* Do indat endpoints first */ 586 for (j = 0; j <= N_IN_URB; ++j) { 587 portdata->in_urbs[j] = option_setup_urb (serial, 588 port->bulk_in_endpointAddress, USB_DIR_IN, port, 589 portdata->in_buffer[j], IN_BUFLEN, option_indat_callback); 590 } 591 592 /* outdat endpoints */ 593 for (j = 0; j <= N_OUT_URB; ++j) { 594 portdata->out_urbs[j] = option_setup_urb (serial, 595 port->bulk_out_endpointAddress, USB_DIR_OUT, port, 596 portdata->out_buffer[j], OUT_BUFLEN, option_outdat_callback); 597 } 598 } 599 600 static int option_send_setup(struct usb_serial_port *port) 601 { 602 struct usb_serial *serial = port->serial; 603 struct option_port_private *portdata; 604 605 dbg("%s", __FUNCTION__); 606 607 portdata = usb_get_serial_port_data(port); 608 609 if (port->tty) { 610 int val = 0; 611 if (portdata->dtr_state) 612 val |= 0x01; 613 if (portdata->rts_state) 614 val |= 0x02; 615 616 return usb_control_msg(serial->dev, 617 usb_rcvctrlpipe(serial->dev, 0), 618 0x22,0x21,val,0,NULL,0,USB_CTRL_SET_TIMEOUT); 619 } 620 621 return 0; 622 } 623 624 static int option_startup(struct usb_serial *serial) 625 { 626 int i, err; 627 struct usb_serial_port *port; 628 struct option_port_private *portdata; 629 630 dbg("%s", __FUNCTION__); 631 632 /* Now setup per port private data */ 633 for (i = 0; i < serial->num_ports; i++) { 634 port = serial->port[i]; 635 portdata = kmalloc(sizeof(*portdata), GFP_KERNEL); 636 if (!portdata) { 637 dbg("%s: kmalloc for option_port_private (%d) failed!.", 638 __FUNCTION__, i); 639 return (1); 640 } 641 memset(portdata, 0, sizeof(struct option_port_private)); 642 643 usb_set_serial_port_data(port, portdata); 644 645 if (! port->interrupt_in_urb) 646 continue; 647 err = usb_submit_urb(port->interrupt_in_urb, GFP_KERNEL); 648 if (err) 649 dbg("%s: submit irq_in urb failed %d", 650 __FUNCTION__, err); 651 } 652 653 option_setup_urbs(serial); 654 655 return (0); 656 } 657 658 static void option_shutdown(struct usb_serial *serial) 659 { 660 int i, j; 661 struct usb_serial_port *port; 662 struct option_port_private *portdata; 663 664 dbg("%s", __FUNCTION__); 665 666 /* Stop reading/writing urbs */ 667 for (i = 0; i < serial->num_ports; ++i) { 668 port = serial->port[i]; 669 portdata = usb_get_serial_port_data(port); 670 for (j = 0; j < N_IN_URB; j++) 671 stop_urb(portdata->in_urbs[j]); 672 for (j = 0; j < N_OUT_URB; j++) 673 stop_urb(portdata->out_urbs[j]); 674 } 675 676 /* Now free them */ 677 for (i = 0; i < serial->num_ports; ++i) { 678 port = serial->port[i]; 679 portdata = usb_get_serial_port_data(port); 680 681 for (j = 0; j < N_IN_URB; j++) { 682 if (portdata->in_urbs[j]) { 683 usb_free_urb(portdata->in_urbs[j]); 684 portdata->in_urbs[j] = NULL; 685 } 686 } 687 for (j = 0; j < N_OUT_URB; j++) { 688 if (portdata->out_urbs[j]) { 689 usb_free_urb(portdata->out_urbs[j]); 690 portdata->out_urbs[j] = NULL; 691 } 692 } 693 } 694 695 /* Now free per port private data */ 696 for (i = 0; i < serial->num_ports; i++) { 697 port = serial->port[i]; 698 kfree(usb_get_serial_port_data(port)); 699 } 700 } 701 702 MODULE_AUTHOR(DRIVER_AUTHOR); 703 MODULE_DESCRIPTION(DRIVER_DESC); 704 MODULE_VERSION(DRIVER_VERSION); 705 MODULE_LICENSE("GPL"); 706 707 #ifdef CONFIG_USB_DEBUG 708 module_param(debug, bool, S_IRUGO | S_IWUSR); 709 MODULE_PARM_DESC(debug, "Debug messages"); 710 #endif 711 712