Revision 24772c1e
b/usb-linux.c | ||
---|---|---|
82 | 82 |
uint8_t descr[1024]; |
83 | 83 |
int descr_len; |
84 | 84 |
int configuration; |
85 |
int closing; |
|
85 | 86 |
|
86 | 87 |
struct endp_data endp_table[MAX_ENDPOINTS]; |
87 | 88 |
|
88 |
QEMUTimer *timer; |
|
89 |
|
|
90 | 89 |
/* Host side address */ |
91 | 90 |
int bus_num; |
92 | 91 |
int addr; |
... | ... | |
186 | 185 |
if (errno == EAGAIN) |
187 | 186 |
return; |
188 | 187 |
|
189 |
if (errno == ENODEV) { |
|
188 |
if (errno == ENODEV && !s->closing) {
|
|
190 | 189 |
printf("husb: device %d.%d disconnected\n", s->bus_num, s->addr); |
191 | 190 |
usb_device_del_addr(0, s->dev.addr); |
192 | 191 |
return; |
... | ... | |
328 | 327 |
{ |
329 | 328 |
USBHostDevice *s = (USBHostDevice *)dev; |
330 | 329 |
|
331 |
qemu_del_timer(s->timer); |
|
330 |
s->closing = 1; |
|
331 |
|
|
332 | 332 |
qemu_set_fd_handler(s->fd, NULL, NULL, NULL); |
333 | 333 |
|
334 | 334 |
hostdev_unlink(s); |
... | ... | |
582 | 582 |
return 0; |
583 | 583 |
} |
584 | 584 |
|
585 |
static void usb_host_device_check(void *priv) |
|
586 |
{ |
|
587 |
USBHostDevice *s = priv; |
|
588 |
struct usbdevfs_connectinfo ci; |
|
589 |
int err; |
|
590 |
|
|
591 |
err = ioctl(s->fd, USBDEVFS_CONNECTINFO, &ci); |
|
592 |
if (err < 0) { |
|
593 |
printf("husb: device %d.%d disconnected\n", s->bus_num, s->addr); |
|
594 |
usb_device_del_addr(0, s->dev.addr); |
|
595 |
return; |
|
596 |
} |
|
597 |
|
|
598 |
qemu_mod_timer(s->timer, qemu_get_clock(rt_clock) + 1000); |
|
599 |
} |
|
600 |
|
|
601 | 585 |
static USBDevice *usb_host_device_open_addr(int bus_num, int addr, const char *prod_name) |
602 | 586 |
{ |
603 | 587 |
int fd = -1, ret; |
... | ... | |
612 | 596 |
dev->bus_num = bus_num; |
613 | 597 |
dev->addr = addr; |
614 | 598 |
|
615 |
dev->timer = qemu_new_timer(rt_clock, usb_host_device_check, (void *) dev); |
|
616 |
if (!dev->timer) |
|
617 |
goto fail; |
|
618 |
|
|
619 | 599 |
printf("husb: open device %d.%d\n", bus_num, addr); |
620 | 600 |
|
621 | 601 |
snprintf(buf, sizeof(buf), USBDEVFS_PATH "/%03d/%03d", |
... | ... | |
683 | 663 |
/* USB devio uses 'write' flag to check for async completions */ |
684 | 664 |
qemu_set_fd_handler(dev->fd, NULL, async_complete, dev); |
685 | 665 |
|
686 |
/* Start the timer to detect disconnect */ |
|
687 |
qemu_mod_timer(dev->timer, qemu_get_clock(rt_clock) + 1000); |
|
688 |
|
|
689 | 666 |
hostdev_link(dev); |
690 | 667 |
|
691 | 668 |
return (USBDevice *) dev; |
692 | 669 |
|
693 | 670 |
fail: |
694 |
if (dev) { |
|
695 |
if (dev->timer) |
|
696 |
qemu_del_timer(dev->timer); |
|
671 |
if (dev) |
|
697 | 672 |
qemu_free(dev); |
698 |
} |
|
673 |
|
|
699 | 674 |
close(fd); |
700 | 675 |
return NULL; |
701 | 676 |
} |
Also available in: Unified diff