1 /* $NetBSD: ustir.c,v 1.27 2009/09/23 19:07:19 plunky Exp $ */ 2 3 /* 4 * Copyright (c) 2001 The NetBSD Foundation, Inc. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to The NetBSD Foundation 8 * by David Sainty <David.Sainty@dtsp.co.nz> 9 * 10 * Redistribution and use in source and binary forms, with or without 11 * modification, are permitted provided that the following conditions 12 * are met: 13 * 1. Redistributions of source code must retain the above copyright 14 * notice, this list of conditions and the following disclaimer. 15 * 2. Redistributions in binary form must reproduce the above copyright 16 * notice, this list of conditions and the following disclaimer in the 17 * documentation and/or other materials provided with the distribution. 18 * 19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29 * POSSIBILITY OF SUCH DAMAGE. 30 */ 31 32 #include <sys/cdefs.h> 33 __KERNEL_RCSID(0, "$NetBSD: ustir.c,v 1.27 2009/09/23 19:07:19 plunky Exp $"); 34 35 #include <sys/param.h> 36 #include <sys/systm.h> 37 #include <sys/kernel.h> 38 #include <sys/device.h> 39 #include <sys/malloc.h> 40 #include <sys/conf.h> 41 #include <sys/file.h> 42 #include <sys/poll.h> 43 #include <sys/select.h> 44 #include <sys/proc.h> 45 #include <sys/kthread.h> 46 47 #ifdef USTIR_DEBUG_IOCTLS 48 #include <sys/ioctl.h> 49 #include <dev/usb/ustir.h> 50 #endif 51 52 #include <dev/usb/usb.h> 53 #include <dev/usb/usbdevs.h> 54 #include <dev/usb/usbdi.h> 55 #include <dev/usb/usbdi_util.h> 56 #include <dev/usb/ustirreg.h> 57 58 #include <dev/ir/ir.h> 59 #include <dev/ir/irdaio.h> 60 #include <dev/ir/irframevar.h> 61 #include <dev/ir/sir.h> 62 63 #ifdef USTIR_DEBUG 64 #define DPRINTFN(n,x) if (ustirdebug>(n)) logprintf x 65 int ustirdebug = 0; 66 #else 67 #define DPRINTFN(n,x) 68 #endif 69 70 /* Max size with framing. */ 71 #define MAX_USTIR_OUTPUT_FRAME (2*IRDA_MAX_FRAME_SIZE + IRDA_MAX_EBOFS + STIR_OUTPUT_HEADER_SIZE + 4) 72 73 #define USTIR_NSPEEDS 9 74 struct ustir_speedrec { 75 unsigned int speed; 76 unsigned int config; 77 }; 78 79 Static struct ustir_speedrec const ustir_speeds[USTIR_NSPEEDS] = { 80 { 4000000, STIR_BRMODE_4000000 }, 81 { 1152000, STIR_BRMODE_1152000 }, 82 { 576000, STIR_BRMODE_576000 }, 83 { 115200, STIR_BRMODE_115200 }, 84 { 57600, STIR_BRMODE_57600 }, 85 { 38400, STIR_BRMODE_38400 }, 86 { 19200, STIR_BRMODE_19200 }, 87 { 9600, STIR_BRMODE_9600 }, 88 { 2400, STIR_BRMODE_2400 } 89 }; 90 91 struct framedefn { 92 unsigned int bof_count; 93 u_int8_t bof_byte; 94 95 u_int8_t esc_byte; 96 u_int8_t esc_xor; 97 98 unsigned int eof_count; 99 u_int8_t eof_byte; 100 101 unsigned int fcs_count; 102 u_int32_t fcs_init; 103 u_int32_t fcs_correct; 104 105 u_int32_t (*fcs_calc)(u_int32_t, u_int8_t const*, size_t); 106 }; 107 108 Static u_int32_t crc_ccitt_16(u_int32_t, u_int8_t const*, size_t); 109 110 struct framedefn const framedef_sir = { 111 1, 0xc0, 112 0x7d, 0x20, 113 1, 0xc1, 114 2, INITFCS, GOODFCS, 115 crc_ccitt_16 116 }; 117 118 enum framefsmstate { 119 FSTATE_END_OF_FRAME, 120 FSTATE_START_OF_FRAME, 121 FSTATE_IN_DATA, 122 FSTATE_IN_END 123 }; 124 125 enum frameresult { 126 FR_IDLE, 127 FR_INPROGRESS, 128 FR_FRAMEOK, 129 FR_FRAMEBADFCS, 130 FR_FRAMEMALFORMED, 131 FR_BUFFEROVERRUN 132 }; 133 134 struct framestate { 135 struct framedefn const *definition; 136 137 u_int8_t *buffer; 138 size_t buflen; 139 size_t bufindex; 140 141 enum framefsmstate fsmstate; 142 u_int escaped; 143 u_int state_index; 144 }; 145 146 #define deframe_isclear(fs) ((fs)->fsmstate == FSTATE_END_OF_FRAME) 147 148 Static void deframe_clear(struct framestate *); 149 Static void deframe_init(struct framestate *, struct framedefn const *, 150 u_int8_t *, size_t); 151 Static enum frameresult deframe_process(struct framestate *, u_int8_t const **, 152 size_t *); 153 154 struct ustir_softc { 155 USBBASEDEVICE sc_dev; 156 usbd_device_handle sc_udev; 157 usbd_interface_handle sc_iface; 158 159 u_int8_t *sc_ur_buf; /* Unencapsulated frame */ 160 u_int sc_ur_framelen; 161 162 u_int8_t *sc_rd_buf; /* Raw incoming data stream */ 163 size_t sc_rd_index; 164 int sc_rd_addr; 165 usbd_pipe_handle sc_rd_pipe; 166 usbd_xfer_handle sc_rd_xfer; 167 u_int sc_rd_count; 168 int sc_rd_readinprogress; 169 u_int sc_rd_expectdataticks; 170 u_char sc_rd_err; 171 struct framestate sc_framestate; 172 struct lwp *sc_thread; 173 struct selinfo sc_rd_sel; 174 175 u_int8_t *sc_wr_buf; 176 int sc_wr_addr; 177 int sc_wr_stalewrite; 178 usbd_xfer_handle sc_wr_xfer; 179 usbd_pipe_handle sc_wr_pipe; 180 struct selinfo sc_wr_sel; 181 182 enum { 183 udir_input, /* Receiving data */ 184 udir_output, /* Transmitting data */ 185 udir_stalled, /* Error preventing data flow */ 186 udir_idle /* Neither receiving nor transmitting */ 187 } sc_direction; 188 189 struct ustir_speedrec const *sc_speedrec; 190 191 device_t sc_child; 192 struct irda_params sc_params; 193 194 int sc_refcnt; 195 char sc_closing; 196 char sc_dying; 197 }; 198 199 /* True if we cannot safely read data from the device */ 200 #define USTIR_BLOCK_RX_DATA(sc) ((sc)->sc_ur_framelen != 0) 201 202 #define USTIR_WR_TIMEOUT 200 203 204 Static int ustir_activate(device_ptr_t self, enum devact act); 205 Static int ustir_open(void *h, int flag, int mode, struct lwp *l); 206 Static int ustir_close(void *h, int flag, int mode, struct lwp *l); 207 Static int ustir_read(void *h, struct uio *uio, int flag); 208 Static int ustir_write(void *h, struct uio *uio, int flag); 209 Static int ustir_set_params(void *h, struct irda_params *params); 210 Static int ustir_get_speeds(void *h, int *speeds); 211 Static int ustir_get_turnarounds(void *h, int *times); 212 Static int ustir_poll(void *h, int events, struct lwp *l); 213 Static int ustir_kqfilter(void *h, struct knote *kn); 214 215 #ifdef USTIR_DEBUG_IOCTLS 216 Static int ustir_ioctl(void *h, u_long cmd, void *addr, int flag, struct lwp *l); 217 #endif 218 219 Static struct irframe_methods const ustir_methods = { 220 ustir_open, ustir_close, ustir_read, ustir_write, ustir_poll, 221 ustir_kqfilter, ustir_set_params, ustir_get_speeds, 222 ustir_get_turnarounds, 223 #ifdef USTIR_DEBUG_IOCTLS 224 ustir_ioctl 225 #endif 226 }; 227 228 Static void ustir_rd_cb(usbd_xfer_handle, usbd_private_handle, usbd_status); 229 Static usbd_status ustir_start_read(struct ustir_softc *); 230 Static void ustir_periodic(struct ustir_softc *); 231 Static void ustir_thread(void *); 232 233 Static u_int32_t 234 crc_ccitt_16(u_int32_t crcinit, u_int8_t const *buf, size_t blen) 235 { 236 while (blen-- > 0) { 237 u_int8_t chr; 238 chr = *buf++; 239 crcinit = updateFCS(crcinit, chr); 240 } 241 return crcinit; 242 } 243 244 static usbd_status 245 ustir_read_reg(struct ustir_softc *sc, unsigned int reg, u_int8_t *data) 246 { 247 usb_device_request_t req; 248 249 req.bmRequestType = UT_READ_VENDOR_DEVICE; 250 req.bRequest = STIR_CMD_READMULTIREG; 251 USETW(req.wValue, 0); 252 USETW(req.wIndex, reg); 253 USETW(req.wLength, 1); 254 255 return usbd_do_request(sc->sc_udev, &req, data); 256 } 257 258 static usbd_status 259 ustir_write_reg(struct ustir_softc *sc, unsigned int reg, u_int8_t data) 260 { 261 usb_device_request_t req; 262 263 req.bmRequestType = UT_WRITE_VENDOR_DEVICE; 264 req.bRequest = STIR_CMD_WRITESINGLEREG; 265 USETW(req.wValue, data); 266 USETW(req.wIndex, reg); 267 USETW(req.wLength, 0); 268 269 return usbd_do_request(sc->sc_udev, &req, NULL); 270 } 271 272 #ifdef USTIR_DEBUG 273 static void 274 ustir_dumpdata(u_int8_t const *data, size_t dlen, char const *desc) 275 { 276 size_t bdindex; 277 printf("%s: (%lx)", desc, (unsigned long)dlen); 278 for (bdindex = 0; bdindex < dlen; bdindex++) 279 printf(" %02x", (unsigned int)data[bdindex]); 280 printf("\n"); 281 } 282 #endif 283 284 int ustir_match(device_t, cfdata_t, void *); 285 void ustir_attach(device_t, device_t, void *); 286 void ustir_childdet(device_t, device_t); 287 int ustir_detach(device_t, int); 288 int ustir_activate(device_t, enum devact); 289 extern struct cfdriver ustir_cd; 290 CFATTACH_DECL2_NEW(ustir, sizeof(struct ustir_softc), ustir_match, 291 ustir_attach, ustir_detach, ustir_activate, NULL, ustir_childdet); 292 293 USB_MATCH(ustir) 294 { 295 USB_MATCH_START(ustir, uaa); 296 297 DPRINTFN(50,("ustir_match\n")); 298 299 if (uaa->vendor == USB_VENDOR_SIGMATEL && 300 uaa->product == USB_PRODUCT_SIGMATEL_IRDA) 301 return UMATCH_VENDOR_PRODUCT; 302 303 return UMATCH_NONE; 304 } 305 306 USB_ATTACH(ustir) 307 { 308 USB_ATTACH_START(ustir, sc, uaa); 309 usbd_device_handle dev = uaa->device; 310 usbd_interface_handle iface; 311 char *devinfop; 312 usb_endpoint_descriptor_t *ed; 313 u_int8_t epcount; 314 int i; 315 struct ir_attach_args ia; 316 317 DPRINTFN(10,("ustir_attach: sc=%p\n", sc)); 318 319 sc->sc_dev = self; 320 321 aprint_naive("\n"); 322 aprint_normal("\n"); 323 324 devinfop = usbd_devinfo_alloc(dev, 0); 325 aprint_normal_dev(self, "%s\n", devinfop); 326 usbd_devinfo_free(devinfop); 327 328 if (usbd_set_config_index(dev, 0, 1) 329 || usbd_device2interface_handle(dev, 0, &iface)) { 330 aprint_error_dev(self, "Configuration failed\n"); 331 USB_ATTACH_ERROR_RETURN; 332 } 333 334 sc->sc_udev = dev; 335 sc->sc_iface = iface; 336 337 epcount = 0; 338 (void)usbd_endpoint_count(iface, &epcount); 339 340 sc->sc_rd_addr = -1; 341 sc->sc_wr_addr = -1; 342 for (i = 0; i < epcount; i++) { 343 ed = usbd_interface2endpoint_descriptor(iface, i); 344 if (ed == NULL) { 345 aprint_error_dev(self, "couldn't get ep %d\n", i); 346 USB_ATTACH_ERROR_RETURN; 347 } 348 if (UE_GET_DIR(ed->bEndpointAddress) == UE_DIR_IN && 349 UE_GET_XFERTYPE(ed->bmAttributes) == UE_BULK) { 350 sc->sc_rd_addr = ed->bEndpointAddress; 351 } else if (UE_GET_DIR(ed->bEndpointAddress) == UE_DIR_OUT && 352 UE_GET_XFERTYPE(ed->bmAttributes) == UE_BULK) { 353 sc->sc_wr_addr = ed->bEndpointAddress; 354 } 355 } 356 if (sc->sc_rd_addr == -1 || sc->sc_wr_addr == -1) { 357 aprint_error_dev(self, "missing endpoint\n"); 358 USB_ATTACH_ERROR_RETURN; 359 } 360 361 DPRINTFN(10, ("ustir_attach: %p\n", sc->sc_udev)); 362 363 usbd_add_drv_event(USB_EVENT_DRIVER_ATTACH, sc->sc_udev, 364 USBDEV(sc->sc_dev)); 365 366 ia.ia_type = IR_TYPE_IRFRAME; 367 ia.ia_methods = &ustir_methods; 368 ia.ia_handle = sc; 369 370 sc->sc_child = config_found(self, &ia, ir_print); 371 selinit(&sc->sc_rd_sel); 372 selinit(&sc->sc_wr_sel); 373 374 USB_ATTACH_SUCCESS_RETURN; 375 } 376 377 void 378 ustir_childdet(device_t self, device_t child) 379 { 380 struct ustir_softc *sc = device_private(self); 381 382 KASSERT(sc->sc_child == child); 383 sc->sc_child = NULL; 384 } 385 386 USB_DETACH(ustir) 387 { 388 USB_DETACH_START(ustir, sc); 389 int s; 390 int rv = 0; 391 392 DPRINTFN(0, ("ustir_detach: sc=%p flags=%d\n", sc, flags)); 393 394 sc->sc_closing = sc->sc_dying = 1; 395 396 wakeup(&sc->sc_thread); 397 398 while (sc->sc_thread != NULL) 399 tsleep(&sc->sc_closing, PWAIT, "usircl", 0); 400 401 /* Abort all pipes. Causes processes waiting for transfer to wake. */ 402 if (sc->sc_rd_pipe != NULL) { 403 usbd_abort_pipe(sc->sc_rd_pipe); 404 usbd_close_pipe(sc->sc_rd_pipe); 405 sc->sc_rd_pipe = NULL; 406 } 407 if (sc->sc_wr_pipe != NULL) { 408 usbd_abort_pipe(sc->sc_wr_pipe); 409 usbd_close_pipe(sc->sc_wr_pipe); 410 sc->sc_wr_pipe = NULL; 411 } 412 wakeup(&sc->sc_ur_framelen); 413 wakeup(&sc->sc_wr_buf); 414 415 s = splusb(); 416 if (--sc->sc_refcnt >= 0) { 417 /* Wait for processes to go away. */ 418 usb_detach_wait(USBDEV(sc->sc_dev)); 419 } 420 splx(s); 421 422 if (sc->sc_child != NULL) 423 rv = config_detach(sc->sc_child, flags); 424 425 usbd_add_drv_event(USB_EVENT_DRIVER_DETACH, sc->sc_udev, 426 USBDEV(sc->sc_dev)); 427 428 seldestroy(&sc->sc_rd_sel); 429 seldestroy(&sc->sc_wr_sel); 430 431 return rv; 432 } 433 434 Static void 435 deframe_clear(struct framestate *fstate) 436 { 437 fstate->bufindex = 0; 438 fstate->fsmstate = FSTATE_END_OF_FRAME; 439 fstate->escaped = 0; 440 } 441 442 Static void 443 deframe_init(struct framestate *fstate, struct framedefn const *definition, 444 u_int8_t *buf, size_t buflen) 445 { 446 fstate->definition = definition; 447 fstate->buffer = buf; 448 fstate->buflen = buflen; 449 450 deframe_clear(fstate); 451 } 452 453 Static enum frameresult 454 deframe_process(struct framestate *fstate, u_int8_t const **bptr, size_t *blen) 455 { 456 struct framedefn const *definition; 457 u_int8_t const *cptr; 458 u_int8_t escchr; 459 size_t ibuflen, obufindex, obuflen; 460 enum framefsmstate fsmstate; 461 enum frameresult result; 462 463 cptr = *bptr; 464 fsmstate = fstate->fsmstate; 465 definition = fstate->definition; 466 escchr = definition->esc_byte; 467 obufindex = fstate->bufindex; 468 obuflen = fstate->buflen; 469 ibuflen = *blen; 470 471 while (ibuflen-- > 0) { 472 u_int8_t chr; 473 474 chr = *cptr++; 475 476 if (fstate->escaped) { 477 fstate->escaped = 0; 478 chr ^= definition->esc_xor; 479 } else if (chr == escchr) { 480 fstate->escaped = 1; 481 continue; 482 } 483 484 switch (fsmstate) { 485 case FSTATE_IN_DATA: 486 if (chr == definition->eof_byte) { 487 fsmstate = FSTATE_IN_END; 488 fstate->state_index = definition->eof_count; 489 goto state_in_end; 490 } 491 if (obufindex >= obuflen) { 492 result = FR_BUFFEROVERRUN; 493 fsmstate = FSTATE_END_OF_FRAME; 494 goto complete; 495 } 496 fstate->buffer[obufindex++] = chr; 497 break; 498 499 state_in_end: 500 /* FALLTHROUGH */ 501 502 case FSTATE_IN_END: 503 if (--fstate->state_index == 0) { 504 u_int32_t crc; 505 size_t fcslen; 506 507 fsmstate = FSTATE_END_OF_FRAME; 508 509 fcslen = definition->fcs_count; 510 511 if (obufindex < fcslen) { 512 result = FR_FRAMEMALFORMED; 513 goto complete; 514 } 515 516 crc = definition-> 517 fcs_calc(definition->fcs_init, 518 fstate->buffer, obufindex); 519 520 /* Remove check bytes from buffer length */ 521 obufindex -= fcslen; 522 523 if (crc == definition->fcs_correct) 524 result = FR_FRAMEOK; 525 else 526 result = FR_FRAMEBADFCS; 527 528 goto complete; 529 } 530 break; 531 532 case FSTATE_END_OF_FRAME: 533 if (chr != definition->bof_byte) 534 break; 535 536 fsmstate = FSTATE_START_OF_FRAME; 537 fstate->state_index = definition->bof_count; 538 /* FALLTHROUGH */ 539 case FSTATE_START_OF_FRAME: 540 if (--fstate->state_index == 0) { 541 fsmstate = FSTATE_IN_DATA; 542 obufindex = 0; 543 } 544 break; 545 } 546 } 547 548 result = (fsmstate == FSTATE_END_OF_FRAME) ? FR_IDLE : FR_INPROGRESS; 549 550 complete: 551 fstate->bufindex = obufindex; 552 fstate->fsmstate = fsmstate; 553 *blen = ibuflen; 554 555 return result; 556 } 557 558 /* Returns 0 if more data required, 1 if a complete frame was extracted */ 559 static int 560 deframe_rd_ur(struct ustir_softc *sc) 561 { 562 while (sc->sc_rd_index < sc->sc_rd_count) { 563 u_int8_t const *buf; 564 size_t buflen; 565 enum frameresult fresult; 566 567 buf = &sc->sc_rd_buf[sc->sc_rd_index]; 568 buflen = sc->sc_rd_count - sc->sc_rd_index; 569 570 fresult = deframe_process(&sc->sc_framestate, &buf, &buflen); 571 572 sc->sc_rd_index = sc->sc_rd_count - buflen; 573 574 DPRINTFN(1,("%s: result=%d\n", __func__, (int)fresult)); 575 576 switch (fresult) { 577 case FR_IDLE: 578 case FR_INPROGRESS: 579 case FR_FRAMEBADFCS: 580 case FR_FRAMEMALFORMED: 581 case FR_BUFFEROVERRUN: 582 break; 583 case FR_FRAMEOK: 584 sc->sc_ur_framelen = sc->sc_framestate.bufindex; 585 wakeup(&sc->sc_ur_framelen); /* XXX should use flag */ 586 selnotify(&sc->sc_rd_sel, 0, 0); 587 return 1; 588 } 589 } 590 591 /* Reset indices into USB-side buffer */ 592 sc->sc_rd_index = sc->sc_rd_count = 0; 593 594 return 0; 595 } 596 597 /* 598 * Direction transitions: 599 * 600 * ustir_periodic() can switch the direction from: 601 * 602 * output -> idle 603 * output -> stalled 604 * stalled -> idle 605 * idle -> input 606 * 607 * ustir_rd_cb() can switch the direction from: 608 * 609 * input -> stalled 610 * input -> idle 611 * 612 * ustir_write() can switch the direction from: 613 * 614 * idle -> output 615 */ 616 Static void 617 ustir_periodic(struct ustir_softc *sc) 618 { 619 DPRINTFN(60, ("%s: direction = %d\n", 620 __func__, sc->sc_direction)); 621 622 if (sc->sc_direction == udir_output || 623 sc->sc_direction == udir_stalled) { 624 usbd_status err; 625 u_int8_t regval; 626 627 DPRINTFN(60, ("%s: reading status register\n", 628 __func__)); 629 630 err = ustir_read_reg(sc, STIR_REG_STATUS, 631 ®val); 632 if (err != USBD_NORMAL_COMPLETION) { 633 aprint_error_dev(sc->sc_dev, 634 "status register read failed: %s\n", 635 usbd_errstr(err)); 636 } else { 637 DPRINTFN(10, ("%s: status register = 0x%x\n", 638 __func__, 639 (unsigned int)regval)); 640 if (sc->sc_direction == udir_output && 641 !(regval & STIR_RSTATUS_FFDIR)) 642 /* Output has completed */ 643 sc->sc_direction = udir_idle; 644 if (regval & STIR_RSTATUS_FFOVER) { 645 /* 646 * On an overrun the FIFO hangs, and 647 * any data bulk transfers will stall. 648 * Reset the FIFO. 649 */ 650 sc->sc_direction = udir_stalled; 651 652 DPRINTFN(10, ("%s: clearing FIFO error\n", 653 __func__)); 654 655 err = ustir_write_reg(sc, STIR_REG_STATUS, 656 STIR_RSTATUS_FFCLR); 657 /* XXX if we fail partway through 658 * this, we may not recover? */ 659 if (err == USBD_NORMAL_COMPLETION) 660 err = ustir_write_reg(sc, 661 STIR_REG_STATUS, 662 0); 663 if (err != USBD_NORMAL_COMPLETION) { 664 aprint_error_dev(sc->sc_dev, 665 "FIFO reset failed: %s\n", 666 usbd_errstr(err)); 667 } else { 668 /* FIFO reset */ 669 sc->sc_direction = udir_idle; 670 } 671 } 672 } 673 } 674 675 if (sc->sc_wr_stalewrite && sc->sc_direction == udir_idle) { 676 /* 677 * In a stale write case, we need to check if the 678 * write has completed. Once that has happened, the 679 * write is no longer stale. 680 * 681 * But note that we may immediately start a read poll... 682 */ 683 sc->sc_wr_stalewrite = 0; 684 wakeup(&sc->sc_wr_buf); 685 } 686 687 if (!sc->sc_rd_readinprogress && 688 (sc->sc_direction == udir_idle || 689 sc->sc_direction == udir_input)) 690 /* Do a read poll if appropriate... */ 691 ustir_start_read(sc); 692 } 693 694 Static void 695 ustir_thread(void *arg) 696 { 697 struct ustir_softc *sc = arg; 698 699 DPRINTFN(20, ("%s: starting polling thread\n", __func__)); 700 701 while (!sc->sc_closing) { 702 if (!sc->sc_rd_readinprogress && !USTIR_BLOCK_RX_DATA(sc)) 703 ustir_periodic(sc); 704 705 if (!sc->sc_closing) { 706 int error; 707 error = tsleep(&sc->sc_thread, PWAIT, 708 "ustir", hz / 10); 709 if (error == EWOULDBLOCK && 710 sc->sc_rd_expectdataticks > 0) 711 /* 712 * After a timeout decrement the tick 713 * counter within which time we expect 714 * data to arrive if we are receiving 715 * data... 716 */ 717 sc->sc_rd_expectdataticks--; 718 } 719 } 720 721 DPRINTFN(20, ("%s: exiting polling thread\n", __func__)); 722 723 sc->sc_thread = NULL; 724 725 wakeup(&sc->sc_closing); 726 727 if (--sc->sc_refcnt < 0) 728 usb_detach_wakeup(USBDEV(sc->sc_dev)); 729 730 kthread_exit(0); 731 } 732 733 Static void 734 ustir_rd_cb(usbd_xfer_handle xfer, usbd_private_handle priv, 735 usbd_status status) 736 { 737 struct ustir_softc *sc = priv; 738 u_int32_t size; 739 740 DPRINTFN(60, ("%s: sc=%p\n", __func__, sc)); 741 742 /* Read is no longer in progress */ 743 sc->sc_rd_readinprogress = 0; 744 745 if (status == USBD_CANCELLED || sc->sc_closing) /* this is normal */ 746 return; 747 if (status) { 748 size = 0; 749 sc->sc_rd_err = 1; 750 751 if (sc->sc_direction == udir_input || 752 sc->sc_direction == udir_idle) { 753 /* 754 * Receive error, probably need to clear error 755 * condition. 756 */ 757 sc->sc_direction = udir_stalled; 758 } 759 } else { 760 usbd_get_xfer_status(xfer, NULL, NULL, &size, NULL); 761 } 762 763 sc->sc_rd_index = 0; 764 sc->sc_rd_count = size; 765 766 DPRINTFN(((size > 0 || sc->sc_rd_err != 0) ? 20 : 60), 767 ("%s: sc=%p size=%u, err=%d\n", __func__, 768 sc, size, sc->sc_rd_err)); 769 770 #ifdef USTIR_DEBUG 771 if (ustirdebug >= 20 && size > 0) 772 ustir_dumpdata(sc->sc_rd_buf, size, __func__); 773 #endif 774 775 if (!deframe_rd_ur(sc)) { 776 if (!deframe_isclear(&sc->sc_framestate) && size == 0 && 777 sc->sc_rd_expectdataticks == 0) { 778 /* 779 * Expected data, but didn't get it 780 * within expected time... 781 */ 782 DPRINTFN(5,("%s: incoming packet timeout\n", 783 __func__)); 784 deframe_clear(&sc->sc_framestate); 785 } else if (size > 0) { 786 /* 787 * If we also received actual data, reset the 788 * data read timeout and wake up the possibly 789 * sleeping thread... 790 */ 791 sc->sc_rd_expectdataticks = 2; 792 wakeup(&sc->sc_thread); 793 } 794 } 795 796 /* 797 * Check if incoming data has stopped, or that we cannot 798 * safely read any more data. In the case of the latter we 799 * must switch to idle so that a write will not block... 800 */ 801 if (sc->sc_direction == udir_input && 802 ((size == 0 && sc->sc_rd_expectdataticks == 0) || 803 USTIR_BLOCK_RX_DATA(sc))) { 804 DPRINTFN(8,("%s: idling on packet timeout, " 805 "complete frame, or no data\n", __func__)); 806 sc->sc_direction = udir_idle; 807 808 /* Wake up for possible output */ 809 wakeup(&sc->sc_wr_buf); 810 selnotify(&sc->sc_wr_sel, 0, 0); 811 } 812 } 813 814 Static usbd_status 815 ustir_start_read(struct ustir_softc *sc) 816 { 817 usbd_status err; 818 819 DPRINTFN(60,("%s: sc=%p, size=%d\n", __func__, sc, 820 sc->sc_params.maxsize)); 821 822 if (sc->sc_dying) 823 return USBD_IOERROR; 824 825 if (USTIR_BLOCK_RX_DATA(sc) || deframe_rd_ur(sc)) { 826 /* 827 * Can't start reading just yet. Since we aren't 828 * going to start a read, have to switch direction to 829 * idle. 830 */ 831 sc->sc_direction = udir_idle; 832 return USBD_NORMAL_COMPLETION; 833 } 834 835 /* Starting a read... */ 836 sc->sc_rd_readinprogress = 1; 837 sc->sc_direction = udir_input; 838 839 if (sc->sc_rd_err) { 840 sc->sc_rd_err = 0; 841 DPRINTFN(0, ("%s: clear stall\n", __func__)); 842 usbd_clear_endpoint_stall(sc->sc_rd_pipe); 843 } 844 845 usbd_setup_xfer(sc->sc_rd_xfer, sc->sc_rd_pipe, sc, sc->sc_rd_buf, 846 sc->sc_params.maxsize, 847 USBD_SHORT_XFER_OK | USBD_NO_COPY, 848 USBD_NO_TIMEOUT, ustir_rd_cb); 849 err = usbd_transfer(sc->sc_rd_xfer); 850 if (err != USBD_IN_PROGRESS) { 851 DPRINTFN(0, ("%s: err=%d\n", __func__, (int)err)); 852 return err; 853 } 854 return USBD_NORMAL_COMPLETION; 855 } 856 857 Static int 858 ustir_activate(device_t self, enum devact act) 859 { 860 struct ustir_softc *sc = device_private(self); 861 int error = 0; 862 863 switch (act) { 864 case DVACT_ACTIVATE: 865 return EOPNOTSUPP; 866 867 case DVACT_DEACTIVATE: 868 sc->sc_dying = 1; 869 if (sc->sc_child != NULL) 870 error = config_deactivate(sc->sc_child); 871 break; 872 } 873 return error; 874 } 875 876 /* ARGSUSED */ 877 Static int 878 ustir_open(void *h, int flag, int mode, 879 struct lwp *l) 880 { 881 struct ustir_softc *sc = h; 882 int error; 883 usbd_status err; 884 885 DPRINTFN(0, ("%s: sc=%p\n", __func__, sc)); 886 887 err = usbd_open_pipe(sc->sc_iface, sc->sc_rd_addr, 0, &sc->sc_rd_pipe); 888 if (err != USBD_NORMAL_COMPLETION) { 889 error = EIO; 890 goto bad1; 891 } 892 err = usbd_open_pipe(sc->sc_iface, sc->sc_wr_addr, 0, &sc->sc_wr_pipe); 893 if (err != USBD_NORMAL_COMPLETION) { 894 error = EIO; 895 goto bad2; 896 } 897 sc->sc_rd_xfer = usbd_alloc_xfer(sc->sc_udev); 898 if (sc->sc_rd_xfer == NULL) { 899 error = ENOMEM; 900 goto bad3; 901 } 902 sc->sc_wr_xfer = usbd_alloc_xfer(sc->sc_udev); 903 if (sc->sc_wr_xfer == NULL) { 904 error = ENOMEM; 905 goto bad4; 906 } 907 sc->sc_rd_buf = usbd_alloc_buffer(sc->sc_rd_xfer, 908 IRDA_MAX_FRAME_SIZE); 909 if (sc->sc_rd_buf == NULL) { 910 error = ENOMEM; 911 goto bad5; 912 } 913 sc->sc_wr_buf = usbd_alloc_buffer(sc->sc_wr_xfer, 914 IRDA_MAX_FRAME_SIZE + STIR_OUTPUT_HEADER_SIZE); 915 if (sc->sc_wr_buf == NULL) { 916 error = ENOMEM; 917 goto bad5; 918 } 919 sc->sc_ur_buf = malloc(IRDA_MAX_FRAME_SIZE, M_USBDEV, M_NOWAIT); 920 if (sc->sc_ur_buf == NULL) { 921 error = ENOMEM; 922 goto bad5; 923 } 924 925 sc->sc_rd_index = sc->sc_rd_count = 0; 926 sc->sc_closing = 0; 927 sc->sc_rd_readinprogress = 0; 928 sc->sc_rd_expectdataticks = 0; 929 sc->sc_ur_framelen = 0; 930 sc->sc_rd_err = 0; 931 sc->sc_wr_stalewrite = 0; 932 sc->sc_speedrec = NULL; 933 sc->sc_direction = udir_idle; 934 sc->sc_params.speed = 0; 935 sc->sc_params.ebofs = 0; 936 sc->sc_params.maxsize = IRDA_MAX_FRAME_SIZE; 937 938 deframe_init(&sc->sc_framestate, &framedef_sir, sc->sc_ur_buf, 939 IRDA_MAX_FRAME_SIZE); 940 941 /* Increment reference for thread */ 942 sc->sc_refcnt++; 943 944 error = kthread_create(PRI_NONE, 0, NULL, ustir_thread, sc, 945 &sc->sc_thread, "%s", device_xname(sc->sc_dev)); 946 if (error) { 947 sc->sc_refcnt--; 948 goto bad5; 949 } 950 951 return 0; 952 953 bad5: 954 usbd_free_xfer(sc->sc_wr_xfer); 955 sc->sc_wr_xfer = NULL; 956 bad4: 957 usbd_free_xfer(sc->sc_rd_xfer); 958 sc->sc_rd_xfer = NULL; 959 bad3: 960 usbd_close_pipe(sc->sc_wr_pipe); 961 sc->sc_wr_pipe = NULL; 962 bad2: 963 usbd_close_pipe(sc->sc_rd_pipe); 964 sc->sc_rd_pipe = NULL; 965 bad1: 966 return error; 967 } 968 969 /* ARGSUSED */ 970 Static int 971 ustir_close(void *h, int flag, int mode, 972 struct lwp *l) 973 { 974 struct ustir_softc *sc = h; 975 976 DPRINTFN(0, ("%s: sc=%p\n", __func__, sc)); 977 978 sc->sc_refcnt++; 979 980 sc->sc_rd_readinprogress = 1; 981 sc->sc_closing = 1; 982 983 wakeup(&sc->sc_thread); 984 985 while (sc->sc_thread != NULL) 986 tsleep(&sc->sc_closing, PWAIT, "usircl", 0); 987 988 if (sc->sc_rd_pipe != NULL) { 989 usbd_abort_pipe(sc->sc_rd_pipe); 990 usbd_close_pipe(sc->sc_rd_pipe); 991 sc->sc_rd_pipe = NULL; 992 } 993 if (sc->sc_wr_pipe != NULL) { 994 usbd_abort_pipe(sc->sc_wr_pipe); 995 usbd_close_pipe(sc->sc_wr_pipe); 996 sc->sc_wr_pipe = NULL; 997 } 998 if (sc->sc_rd_xfer != NULL) { 999 usbd_free_xfer(sc->sc_rd_xfer); 1000 sc->sc_rd_xfer = NULL; 1001 sc->sc_rd_buf = NULL; 1002 } 1003 if (sc->sc_wr_xfer != NULL) { 1004 usbd_free_xfer(sc->sc_wr_xfer); 1005 sc->sc_wr_xfer = NULL; 1006 sc->sc_wr_buf = NULL; 1007 } 1008 if (sc->sc_ur_buf != NULL) { 1009 free(sc->sc_ur_buf, M_USBDEV); 1010 sc->sc_ur_buf = NULL; 1011 } 1012 1013 if (--sc->sc_refcnt < 0) 1014 usb_detach_wakeup(USBDEV(sc->sc_dev)); 1015 1016 return 0; 1017 } 1018 1019 /* ARGSUSED */ 1020 Static int 1021 ustir_read(void *h, struct uio *uio, int flag) 1022 { 1023 struct ustir_softc *sc = h; 1024 int s; 1025 int error; 1026 u_int uframelen; 1027 1028 DPRINTFN(1,("%s: sc=%p\n", __func__, sc)); 1029 1030 if (sc->sc_dying) 1031 return EIO; 1032 1033 #ifdef DIAGNOSTIC 1034 if (sc->sc_rd_buf == NULL) 1035 return EINVAL; 1036 #endif 1037 1038 sc->sc_refcnt++; 1039 1040 if (!sc->sc_rd_readinprogress && !USTIR_BLOCK_RX_DATA(sc)) 1041 /* Possibly wake up polling thread */ 1042 wakeup(&sc->sc_thread); 1043 1044 do { 1045 s = splusb(); 1046 while (sc->sc_ur_framelen == 0) { 1047 DPRINTFN(5,("%s: calling tsleep()\n", __func__)); 1048 error = tsleep(&sc->sc_ur_framelen, PZERO | PCATCH, 1049 "usirrd", 0); 1050 if (sc->sc_dying) 1051 error = EIO; 1052 if (error) { 1053 splx(s); 1054 DPRINTFN(0, ("%s: tsleep() = %d\n", 1055 __func__, error)); 1056 goto ret; 1057 } 1058 } 1059 splx(s); 1060 1061 uframelen = sc->sc_ur_framelen; 1062 DPRINTFN(1,("%s: sc=%p framelen=%u, hdr=0x%02x\n", 1063 __func__, sc, uframelen, sc->sc_ur_buf[0])); 1064 if (uframelen > uio->uio_resid) 1065 error = EINVAL; 1066 else 1067 error = uiomove(sc->sc_ur_buf, uframelen, uio); 1068 sc->sc_ur_framelen = 0; 1069 1070 if (!deframe_rd_ur(sc) && uframelen > 0) { 1071 /* 1072 * Need to wait for another read to obtain a 1073 * complete frame... If we also obtained 1074 * actual data, wake up the possibly sleeping 1075 * thread immediately... 1076 */ 1077 wakeup(&sc->sc_thread); 1078 } 1079 } while (uframelen == 0); 1080 1081 DPRINTFN(1,("%s: return %d\n", __func__, error)); 1082 1083 ret: 1084 if (--sc->sc_refcnt < 0) 1085 usb_detach_wakeup(USBDEV(sc->sc_dev)); 1086 return error; 1087 } 1088 1089 /* ARGSUSED */ 1090 Static int 1091 ustir_write(void *h, struct uio *uio, int flag) 1092 { 1093 struct ustir_softc *sc = h; 1094 usbd_status err; 1095 u_int32_t wrlen; 1096 int error, sirlength; 1097 u_int8_t *wrbuf; 1098 int s; 1099 1100 DPRINTFN(1,("%s: sc=%p\n", __func__, sc)); 1101 1102 if (sc->sc_dying) 1103 return EIO; 1104 1105 #ifdef DIAGNOSTIC 1106 if (sc->sc_wr_buf == NULL) 1107 return EINVAL; 1108 #endif 1109 1110 wrlen = uio->uio_resid; 1111 if (wrlen > sc->sc_params.maxsize) 1112 return EINVAL; 1113 1114 sc->sc_refcnt++; 1115 1116 if (!USTIR_BLOCK_RX_DATA(sc)) { 1117 /* 1118 * If reads are not blocked, determine what action we 1119 * should potentially take... 1120 */ 1121 if (sc->sc_direction == udir_output) { 1122 /* 1123 * If the last operation was an output, wait for the 1124 * polling thread to check for incoming data. 1125 */ 1126 sc->sc_wr_stalewrite = 1; 1127 wakeup(&sc->sc_thread); 1128 } else if (!sc->sc_rd_readinprogress && 1129 (sc->sc_direction == udir_idle || 1130 sc->sc_direction == udir_input)) { 1131 /* If idle, check for input before outputting */ 1132 ustir_start_read(sc); 1133 } 1134 } 1135 1136 s = splusb(); 1137 while (sc->sc_wr_stalewrite || 1138 (sc->sc_direction != udir_output && 1139 sc->sc_direction != udir_idle)) { 1140 DPRINTFN(5, ("%s: sc=%p stalewrite=%d direction=%d, " 1141 "calling tsleep()\n", __func__, 1142 sc, sc->sc_wr_stalewrite, sc->sc_direction)); 1143 error = tsleep(&sc->sc_wr_buf, PZERO | PCATCH, 1144 "usirwr", 0); 1145 if (sc->sc_dying) 1146 error = EIO; 1147 if (error) { 1148 splx(s); 1149 DPRINTFN(0, ("%s: tsleep() = %d\n", __func__, 1150 error)); 1151 goto ret; 1152 } 1153 } 1154 splx(s); 1155 1156 wrbuf = sc->sc_wr_buf; 1157 1158 /* Build header */ 1159 wrbuf[0] = STIR_OUTPUT_HEADER_BYTE0; 1160 wrbuf[1] = STIR_OUTPUT_HEADER_BYTE1; 1161 1162 sirlength = irda_sir_frame(&wrbuf[STIR_OUTPUT_HEADER_SIZE], 1163 MAX_USTIR_OUTPUT_FRAME - 1164 STIR_OUTPUT_HEADER_SIZE, 1165 uio, sc->sc_params.ebofs); 1166 if (sirlength < 0) { 1167 error = -sirlength; 1168 } else { 1169 u_int32_t btlen; 1170 1171 DPRINTFN(1, ("%s: transfer %u bytes\n", __func__, 1172 (unsigned int)wrlen)); 1173 1174 wrbuf[2] = sirlength & 0xff; 1175 wrbuf[3] = (sirlength >> 8) & 0xff; 1176 1177 btlen = STIR_OUTPUT_HEADER_SIZE + sirlength; 1178 1179 sc->sc_direction = udir_output; 1180 1181 #ifdef USTIR_DEBUG 1182 if (ustirdebug >= 20) 1183 ustir_dumpdata(wrbuf, btlen, __func__); 1184 #endif 1185 1186 err = usbd_bulk_transfer(sc->sc_wr_xfer, sc->sc_wr_pipe, 1187 USBD_FORCE_SHORT_XFER | USBD_NO_COPY, 1188 USTIR_WR_TIMEOUT, 1189 wrbuf, &btlen, "ustiwr"); 1190 DPRINTFN(2, ("%s: err=%d\n", __func__, err)); 1191 if (err != USBD_NORMAL_COMPLETION) { 1192 if (err == USBD_INTERRUPTED) 1193 error = EINTR; 1194 else if (err == USBD_TIMEOUT) 1195 error = ETIMEDOUT; 1196 else 1197 error = EIO; 1198 } else { 1199 error = 0; 1200 } 1201 } 1202 1203 ret: 1204 if (--sc->sc_refcnt < 0) 1205 usb_detach_wakeup(USBDEV(sc->sc_dev)); 1206 1207 DPRINTFN(1,("%s: sc=%p done\n", __func__, sc)); 1208 return error; 1209 } 1210 1211 Static int 1212 ustir_poll(void *h, int events, struct lwp *l) 1213 { 1214 struct ustir_softc *sc = h; 1215 int revents = 0; 1216 1217 DPRINTFN(1,("%s: sc=%p\n", __func__, sc)); 1218 1219 if (events & (POLLOUT | POLLWRNORM)) { 1220 if (sc->sc_direction != udir_input) { 1221 revents |= events & (POLLOUT | POLLWRNORM); 1222 } else { 1223 DPRINTFN(2,("%s: recording write select\n", 1224 __func__)); 1225 selrecord(l, &sc->sc_wr_sel); 1226 } 1227 } 1228 1229 if (events & (POLLIN | POLLRDNORM)) { 1230 if (sc->sc_ur_framelen != 0) { 1231 DPRINTFN(2,("%s: have data\n", __func__)); 1232 revents |= events & (POLLIN | POLLRDNORM); 1233 } else { 1234 DPRINTFN(2,("%s: recording read select\n", 1235 __func__)); 1236 selrecord(l, &sc->sc_rd_sel); 1237 } 1238 } 1239 1240 return revents; 1241 } 1242 1243 static void 1244 filt_ustirrdetach(struct knote *kn) 1245 { 1246 struct ustir_softc *sc = kn->kn_hook; 1247 int s; 1248 1249 s = splusb(); 1250 SLIST_REMOVE(&sc->sc_rd_sel.sel_klist, kn, knote, kn_selnext); 1251 splx(s); 1252 } 1253 1254 /* ARGSUSED */ 1255 static int 1256 filt_ustirread(struct knote *kn, long hint) 1257 { 1258 struct ustir_softc *sc = kn->kn_hook; 1259 1260 kn->kn_data = sc->sc_ur_framelen; 1261 return (kn->kn_data > 0); 1262 } 1263 1264 static void 1265 filt_ustirwdetach(struct knote *kn) 1266 { 1267 struct ustir_softc *sc = kn->kn_hook; 1268 int s; 1269 1270 s = splusb(); 1271 SLIST_REMOVE(&sc->sc_wr_sel.sel_klist, kn, knote, kn_selnext); 1272 splx(s); 1273 } 1274 1275 /* ARGSUSED */ 1276 static int 1277 filt_ustirwrite(struct knote *kn, long hint) 1278 { 1279 struct ustir_softc *sc = kn->kn_hook; 1280 1281 kn->kn_data = 0; 1282 return (sc->sc_direction != udir_input); 1283 } 1284 1285 static const struct filterops ustirread_filtops = 1286 { 1, NULL, filt_ustirrdetach, filt_ustirread }; 1287 static const struct filterops ustirwrite_filtops = 1288 { 1, NULL, filt_ustirwdetach, filt_ustirwrite }; 1289 1290 Static int 1291 ustir_kqfilter(void *h, struct knote *kn) 1292 { 1293 struct ustir_softc *sc = h; 1294 struct klist *klist; 1295 int s; 1296 1297 switch (kn->kn_filter) { 1298 case EVFILT_READ: 1299 klist = &sc->sc_rd_sel.sel_klist; 1300 kn->kn_fop = &ustirread_filtops; 1301 break; 1302 case EVFILT_WRITE: 1303 klist = &sc->sc_wr_sel.sel_klist; 1304 kn->kn_fop = &ustirwrite_filtops; 1305 break; 1306 default: 1307 return (EINVAL); 1308 } 1309 1310 kn->kn_hook = sc; 1311 1312 s = splusb(); 1313 SLIST_INSERT_HEAD(klist, kn, kn_selnext); 1314 splx(s); 1315 1316 return (0); 1317 } 1318 1319 #ifdef USTIR_DEBUG_IOCTLS 1320 Static int ustir_ioctl(void *h, u_long cmd, void *addr, int flag, struct lwp *l) 1321 { 1322 struct ustir_softc *sc = h; 1323 int error; 1324 unsigned int regnum; 1325 usbd_status err; 1326 u_int8_t regdata; 1327 1328 if (sc->sc_dying) 1329 return EIO; 1330 1331 sc->sc_refcnt++; 1332 1333 error = 0; 1334 switch (cmd) { 1335 case USTIR_READ_REGISTER: 1336 regnum = *(unsigned int *)addr; 1337 1338 if (regnum > STIR_MAX_REG) { 1339 error = EINVAL; 1340 break; 1341 } 1342 1343 err = ustir_read_reg(sc, regnum, ®data); 1344 1345 DPRINTFN(10, ("%s: regget(%u) = 0x%x\n", __func__, 1346 regnum, (unsigned int)regdata)); 1347 1348 *(unsigned int *)addr = regdata; 1349 if (err != USBD_NORMAL_COMPLETION) { 1350 printf("%s: register read failed: %s\n", 1351 USBDEVNAME(sc->sc_dev), 1352 usbd_errstr(err)); 1353 error = EIO; 1354 } 1355 break; 1356 1357 case USTIR_WRITE_REGISTER: 1358 regnum = *(unsigned int *)addr; 1359 regdata = (regnum >> 8) & 0xff; 1360 regnum = regnum & 0xff; 1361 1362 if (regnum > STIR_MAX_REG) { 1363 error = EINVAL; 1364 break; 1365 } 1366 1367 DPRINTFN(10, ("%s: regset(%u, 0x%x)\n", __func__, 1368 regnum, (unsigned int)regdata)); 1369 1370 err = ustir_write_reg(sc, regnum, regdata); 1371 if (err != USBD_NORMAL_COMPLETION) { 1372 printf("%s: register write failed: %s\n", 1373 USBDEVNAME(sc->sc_dev), 1374 usbd_errstr(err)); 1375 error = EIO; 1376 } 1377 break; 1378 1379 case USTIR_DEBUG_LEVEL: 1380 #ifdef USTIR_DEBUG 1381 ustirdebug = *(int *)addr; 1382 #endif 1383 break; 1384 1385 case USTIR_DEBUG_OPERATION: 1386 break; 1387 1388 default: 1389 error = EINVAL; 1390 break; 1391 } 1392 1393 if (--sc->sc_refcnt < 0) 1394 usb_detach_wakeup(USBDEV(sc->sc_dev)); 1395 1396 return error; 1397 } 1398 #endif 1399 1400 Static int 1401 ustir_set_params(void *h, struct irda_params *p) 1402 { 1403 struct ustir_softc *sc = h; 1404 struct ustir_speedrec const *speedblk; 1405 int i; 1406 1407 DPRINTFN(0, ("%s: sc=%p, speed=%d ebofs=%d maxsize=%d\n", __func__, 1408 sc, p->speed, p->ebofs, p->maxsize)); 1409 1410 if (sc->sc_dying) 1411 return EIO; 1412 1413 speedblk = NULL; 1414 1415 if (sc->sc_speedrec == NULL || p->speed != sc->sc_speedrec->speed) { 1416 /* find speed */ 1417 for (i = 0; i < USTIR_NSPEEDS; i++) { 1418 if (ustir_speeds[i].speed == p->speed) { 1419 speedblk = &ustir_speeds[i]; 1420 goto found2; 1421 } 1422 } 1423 /* no good value found */ 1424 return EINVAL; 1425 found2: 1426 ; 1427 } 1428 if (p->maxsize != sc->sc_params.maxsize) { 1429 if (p->maxsize > IRDA_MAX_FRAME_SIZE) 1430 return EINVAL; 1431 sc->sc_params.maxsize = p->maxsize; 1432 } 1433 1434 sc->sc_params = *p; 1435 1436 if (speedblk != NULL) { 1437 usbd_status err; 1438 u_int8_t regmode; 1439 u_int8_t regbrate; 1440 1441 sc->sc_speedrec = speedblk; 1442 1443 regmode = STIR_BRMODE_MODEREG(speedblk->config); 1444 regbrate = STIR_BRMODE_BRATEREG(speedblk->config); 1445 1446 /* 1447 * FFSPRST must be set to enable the FIFO. 1448 */ 1449 regmode |= STIR_RMODE_FFSPRST; 1450 1451 DPRINTFN(10, ("%s: setting BRATE = %x\n", __func__, 1452 (unsigned int)regbrate)); 1453 err = ustir_write_reg(sc, STIR_REG_BRATE, regbrate); 1454 if (err == USBD_NORMAL_COMPLETION) { 1455 DPRINTFN(10, ("%s: setting MODE = %x\n", __func__, 1456 (unsigned int)regmode)); 1457 err = ustir_write_reg(sc, STIR_REG_MODE, regmode); 1458 } 1459 if (err != USBD_NORMAL_COMPLETION) { 1460 DPRINTFN(10, ("%s: error setting register: %s\n", 1461 __func__, usbd_errstr(err))); 1462 return EIO; 1463 } 1464 } 1465 1466 return 0; 1467 } 1468 1469 Static int 1470 ustir_get_speeds(void *h, int *speeds) 1471 { 1472 struct ustir_softc *sc = h; 1473 1474 DPRINTFN(0, ("%s: sc=%p\n", __func__, sc)); 1475 1476 if (sc->sc_dying) 1477 return EIO; 1478 1479 /* All these speeds are supported */ 1480 *speeds = IRDA_SPEED_4000000 | 1481 IRDA_SPEED_1152000 | 1482 IRDA_SPEED_576000 | 1483 IRDA_SPEED_115200 | 1484 IRDA_SPEED_57600 | 1485 IRDA_SPEED_38400 | 1486 IRDA_SPEED_19200 | 1487 IRDA_SPEED_9600 | 1488 IRDA_SPEED_2400; 1489 1490 return 0; 1491 } 1492 1493 Static int 1494 ustir_get_turnarounds(void *h, int *turnarounds) 1495 { 1496 struct ustir_softc *sc = h; 1497 1498 DPRINTFN(0, ("%s: sc=%p\n", __func__, sc)); 1499 1500 if (sc->sc_dying) 1501 return EIO; 1502 1503 /* 1504 * Documentation is on the light side with respect to 1505 * turnaround time for this device. 1506 */ 1507 *turnarounds = IRDA_TURNT_10000; 1508 1509 return 0; 1510 } 1511