Revision 046833ea usb-linux.c
b/usb-linux.c | ||
---|---|---|
68 | 68 |
typedef struct USBHostDevice { |
69 | 69 |
USBDevice dev; |
70 | 70 |
int fd; |
71 |
int pipe_fds[2]; |
|
71 | 72 |
USBPacket *packet; |
72 | 73 |
struct endp_data endp_table[MAX_ENDPOINTS]; |
73 | 74 |
int configuration; |
... | ... | |
78 | 79 |
|
79 | 80 |
typedef struct PendingURB { |
80 | 81 |
struct usbdevfs_urb *urb; |
81 |
USBHostDevice *dev; |
|
82 |
QEMUBH *bh; |
|
83 | 82 |
int status; |
84 | 83 |
struct PendingURB *next; |
85 | 84 |
} PendingURB; |
... | ... | |
91 | 90 |
PendingURB *purb = qemu_mallocz(sizeof(PendingURB)); |
92 | 91 |
if (purb) { |
93 | 92 |
purb->urb = urb; |
94 |
purb->dev = NULL; |
|
95 |
purb->bh = NULL; |
|
96 | 93 |
purb->status = 0; |
97 | 94 |
purb->next = pending_urbs; |
98 | 95 |
pending_urbs = purb; |
... | ... | |
341 | 338 |
} |
342 | 339 |
|
343 | 340 |
#ifdef USE_ASYNCIO |
344 |
static void usb_linux_bh_cb(void *opaque)
|
|
341 |
static void urb_completion_pipe_read(void *opaque)
|
|
345 | 342 |
{ |
346 |
PendingURB *pending_urb = (PendingURB *)opaque; |
|
347 |
USBHostDevice *s = pending_urb->dev; |
|
348 |
struct usbdevfs_urb *purb = NULL; |
|
343 |
USBHostDevice *s = opaque; |
|
349 | 344 |
USBPacket *p = s->packet; |
350 |
int ret; |
|
345 |
PendingURB *pending_urb = NULL; |
|
346 |
struct usbdevfs_urb *purb = NULL; |
|
347 |
int len, ret; |
|
348 |
|
|
349 |
len = read(s->pipe_fds[0], &pending_urb, sizeof(pending_urb)); |
|
350 |
if (len != sizeof(pending_urb)) { |
|
351 |
printf("urb_completion: error reading pending_urb, len=%d\n", len); |
|
352 |
return; |
|
353 |
} |
|
351 | 354 |
|
352 |
/* FIXME: handle purb->status */ |
|
353 |
qemu_free(pending_urb->bh); |
|
355 |
/* FIXME: handle pending_urb->status */ |
|
354 | 356 |
del_pending_urb(pending_urb->urb); |
355 | 357 |
|
356 | 358 |
if (!p) { |
... | ... | |
360 | 362 |
|
361 | 363 |
ret = ioctl(s->fd, USBDEVFS_REAPURBNDELAY, &purb); |
362 | 364 |
if (ret < 0) { |
363 |
printf("usb_linux_bh_cb: REAPURBNDELAY ioctl=%d errno=%d\n",
|
|
365 |
printf("urb_completion: REAPURBNDELAY ioctl=%d errno=%d\n",
|
|
364 | 366 |
ret, errno); |
365 | 367 |
return; |
366 | 368 |
} |
367 | 369 |
|
368 | 370 |
#ifdef DEBUG_ISOCH |
369 | 371 |
if (purb == pending_urb->urb) { |
370 |
printf("usb_linux_bh_cb: urb mismatch reaped=%p pending=%p\n",
|
|
372 |
printf("urb_completion: urb mismatch reaped=%p pending=%p\n",
|
|
371 | 373 |
purb, urb); |
372 | 374 |
} |
373 | 375 |
#endif |
... | ... | |
391 | 393 |
|
392 | 394 |
purb = get_pending_urb(urb); |
393 | 395 |
if (purb) { |
394 |
purb->bh = qemu_bh_new(usb_linux_bh_cb, purb); |
|
395 |
if (purb->bh) { |
|
396 |
purb->dev = s; |
|
397 |
purb->status = info->si_errno; |
|
398 |
qemu_bh_schedule(purb->bh); |
|
399 |
} |
|
396 |
purb->status = info->si_errno; |
|
397 |
write(s->pipe_fds[1], &purb, sizeof(purb)); |
|
400 | 398 |
} |
401 | 399 |
} |
402 | 400 |
#endif |
... | ... | |
627 | 625 |
/* read the device description */ |
628 | 626 |
dev->descr_len = read(fd, dev->descr, sizeof(dev->descr)); |
629 | 627 |
if (dev->descr_len <= 0) { |
630 |
perror("usb_host_update_interfaces: reading device data failed");
|
|
628 |
perror("usb_host_device_open: reading device data failed");
|
|
631 | 629 |
goto fail; |
632 | 630 |
} |
633 | 631 |
|
... | ... | |
650 | 648 |
|
651 | 649 |
ret = ioctl(fd, USBDEVFS_CONNECTINFO, &ci); |
652 | 650 |
if (ret < 0) { |
653 |
perror("USBDEVFS_CONNECTINFO"); |
|
651 |
perror("usb_host_device_open: USBDEVFS_CONNECTINFO");
|
|
654 | 652 |
goto fail; |
655 | 653 |
} |
656 | 654 |
|
... | ... | |
688 | 686 |
sigact.sa_restorer = 0; |
689 | 687 |
ret = sigaction(SIG_ISOCOMPLETE, &sigact, NULL); |
690 | 688 |
if (ret < 0) { |
691 |
printf("sigaction SIG_ISOCOMPLETE=%d errno=%d\n", ret, errno); |
|
689 |
perror("usb_host_device_open: sigaction failed"); |
|
690 |
goto fail; |
|
691 |
} |
|
692 |
|
|
693 |
if (pipe(dev->pipe_fds) < 0) { |
|
694 |
perror("usb_host_device_open: pipe creation failed"); |
|
695 |
goto fail; |
|
692 | 696 |
} |
697 |
fcntl(dev->pipe_fds[0], F_SETFL, O_NONBLOCK | O_ASYNC); |
|
698 |
fcntl(dev->pipe_fds[1], F_SETFL, O_NONBLOCK); |
|
699 |
qemu_set_fd_handler(dev->pipe_fds[0], urb_completion_pipe_read, NULL, dev); |
|
693 | 700 |
#endif |
694 | 701 |
dev->urbs_ready = 0; |
695 | 702 |
return (USBDevice *)dev; |
Also available in: Unified diff