Deleted Added
sdiff udiff text old ( 194676 ) new ( 195560 )
full compact
1/* $FreeBSD: head/lib/libusb/libusb10_io.c 195560 2009-07-10 14:15:53Z thompsa $ */
2/*-
3 * Copyright (c) 2009 Sylvestre Gallon. All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.

--- 24 unchanged lines hidden (view full) ---

34#include <errno.h>
35
36#include "libusb20.h"
37#include "libusb20_desc.h"
38#include "libusb20_int.h"
39#include "libusb.h"
40#include "libusb10.h"
41
42UNEXPORTED int
43usb_add_pollfd(libusb_context *ctx, int fd, short events)
44{
45 struct usb_pollfd *pollfd;
46
47 if (ctx == NULL)
48 return (LIBUSB_ERROR_INVALID_PARAM);
49
50 pollfd = malloc(sizeof(*pollfd));
51 if (pollfd == NULL)
52 return (LIBUSB_ERROR_NO_MEM);
53
54 pollfd->pollfd.fd = fd;
55 pollfd->pollfd.events = events;
56
57 pthread_mutex_lock(&ctx->pollfds_lock);
58 TAILQ_INSERT_TAIL(&ctx->pollfds, pollfd, list);
59 pthread_mutex_unlock(&ctx->pollfds_lock);
60
61 if (ctx->fd_added_cb)
62 ctx->fd_added_cb(fd, events, ctx->fd_cb_user_data);
63 return (0);
64}
65
66UNEXPORTED void
67usb_remove_pollfd(libusb_context *ctx, int fd)
68{
69 struct usb_pollfd *pollfd;
70 int found;
71
72 found = 0;
73 pthread_mutex_lock(&ctx->pollfds_lock);
74
75 TAILQ_FOREACH(pollfd, &ctx->pollfds, list) {
76 if (pollfd->pollfd.fd == fd) {
77 found = 1;
78 break ;
79 }
80 }
81
82 if (found == 0) {
83 pthread_mutex_unlock(&ctx->pollfds_lock);
84 return ;
85 }
86
87 TAILQ_REMOVE(&ctx->pollfds, pollfd, list);
88 pthread_mutex_unlock(&ctx->pollfds_lock);
89 free(pollfd);
90
91 if (ctx->fd_removed_cb)
92 ctx->fd_removed_cb(fd, ctx->fd_cb_user_data);
93}
94
95UNEXPORTED void
96usb_handle_transfer_completion(struct usb_transfer *uxfer,
97 enum libusb_transfer_status status)
98{
99 libusb_transfer *xfer;
100 libusb_context *ctx;
101 int len;
102
103 xfer = (struct libusb_transfer *) ((uint8_t *)uxfer +
104 sizeof(struct usb_transfer));
105 ctx = xfer->dev_handle->dev->ctx;
106
107 pthread_mutex_lock(&ctx->flying_transfers_lock);
108 TAILQ_REMOVE(&ctx->flying_transfers, uxfer, list);
109 pthread_mutex_unlock(&ctx->flying_transfers_lock);
110
111 if (status == LIBUSB_TRANSFER_COMPLETED && xfer->flags &
112 LIBUSB_TRANSFER_SHORT_NOT_OK) {
113 len = xfer->length;
114 if (xfer->type == LIBUSB_TRANSFER_TYPE_CONTROL)
115 len -= sizeof(libusb_control_setup);
116 if (len != uxfer->transferred) {
117 status = LIBUSB_TRANSFER_ERROR;
118 }
119 }
120
121 xfer->status = status;
122 xfer->actual_length = uxfer->transferred;
123
124 if (xfer->callback)
125 xfer->callback(xfer);
126 if (xfer->flags & LIBUSB_TRANSFER_FREE_TRANSFER)
127 libusb_free_transfer(xfer);
128
129 pthread_mutex_lock(&ctx->event_waiters_lock);
130 pthread_cond_broadcast(&ctx->event_waiters_cond);
131 pthread_mutex_unlock(&ctx->event_waiters_lock);
132}
133
134UNEXPORTED void
135usb_handle_disconnect(struct libusb_device_handle *devh)
136{
137 struct libusb_context *ctx;
138 struct libusb_transfer *xfer;
139 struct usb_transfer *cur;
140 struct usb_transfer *to_cancel;
141
142 ctx = devh->dev->ctx;
143
144 while (1) {
145 pthread_mutex_lock(&ctx->flying_transfers_lock);
146 to_cancel = NULL;
147 TAILQ_FOREACH(cur, &ctx->flying_transfers, list) {
148 xfer = (struct libusb_transfer *) ((uint8_t *)cur +
149 sizeof(struct usb_transfer));
150 if (xfer->dev_handle == devh) {
151 to_cancel = cur;
152 break ;
153 }
154 }
155 pthread_mutex_unlock(&ctx->flying_transfers_lock);
156
157 if (to_cancel == NULL)
158 break ;
159
160 usb_handle_transfer_completion(to_cancel, LIBUSB_TRANSFER_NO_DEVICE);
161 }
162 return ;
163}
164
165UNEXPORTED int
166get_next_timeout(libusb_context *ctx, struct timeval *tv, struct timeval *out)
167{
168 struct timeval timeout;
169
170 if (libusb_get_next_timeout(ctx, &timeout)) {
171 if (timerisset(&timeout) == 0)
172 return 1;
173 if (timercmp(&timeout, tv, <) != 0)
174 *out = timeout;
175 else
176 *out = *tv;
177 } else {
178 *out = *tv;
179 }
180
181 return (0);
182}
183
184UNEXPORTED int
185handle_timeouts(struct libusb_context *ctx)
186{
187 struct timespec sys_ts;
188 struct timeval sys_tv;
189 struct timeval *cur_tv;
190 struct usb_transfer *xfer;
191 struct libusb_transfer *uxfer;
192 int ret;
193
194 GET_CONTEXT(ctx);
195 ret = 0;
196
197 pthread_mutex_lock(&ctx->flying_transfers_lock);
198 if (TAILQ_EMPTY(&ctx->flying_transfers))
199 goto out;
200
201 ret = clock_gettime(CLOCK_MONOTONIC, &sys_ts);
202 TIMESPEC_TO_TIMEVAL(&sys_tv, &sys_ts);
203
204 TAILQ_FOREACH(xfer, &ctx->flying_transfers, list) {
205 cur_tv = &xfer->timeout;
206
207 if (timerisset(cur_tv) == 0)
208 goto out;
209
210 if (xfer->flags & USB_TIMED_OUT)
211 continue;
212

--- 6 unchanged lines hidden (view full) ---

219 sizeof(struct usb_transfer));
220 ret = libusb_cancel_transfer(uxfer);
221 }
222out:
223 pthread_mutex_unlock(&ctx->flying_transfers_lock);
224 return (ret);
225}
226
227UNEXPORTED int
228handle_events(struct libusb_context *ctx, struct timeval *tv)
229{
230 struct libusb_pollfd *tmppollfd;
231 struct libusb_device_handle *devh;
232 struct usb_pollfd *ipollfd;
233 struct pollfd *fds;
234 struct pollfd *tfds;
235 nfds_t nfds;
236 int tmpfd;
237 int ret;
238 int timeout;
239 int i;
240
241 GET_CONTEXT(ctx);
242 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "handle_events enter");
243
244 nfds = 0;
245 i = -1;
246
247 pthread_mutex_lock(&ctx->pollfds_lock);
248 TAILQ_FOREACH(ipollfd, &ctx->pollfds, list)
249 nfds++;
250
251 fds = alloca(sizeof(*fds) * nfds);
252 if (fds == NULL)
253 return (LIBUSB_ERROR_NO_MEM);
254
255 TAILQ_FOREACH(ipollfd, &ctx->pollfds, list) {
256 tmppollfd = &ipollfd->pollfd;
257 tmpfd = tmppollfd->fd;
258 i++;
259 fds[i].fd = tmpfd;
260 fds[i].events = tmppollfd->events;
261 fds[i].revents = 0;
262 }
263
264 pthread_mutex_unlock(&ctx->pollfds_lock);
265
266 timeout = (tv->tv_sec * 1000) + (tv->tv_usec / 1000);
267 if (tv->tv_usec % 1000)
268 timeout++;
269
270 ret = poll(fds, nfds, timeout);
271 if (ret == 0)
272 return (handle_timeouts(ctx));
273 else if (ret == -1 && errno == EINTR)
274 return (LIBUSB_ERROR_INTERRUPTED);
275 else if (ret < 0)
276 return (LIBUSB_ERROR_IO);
277
278 if (fds[0].revents) {
279 if (ret == 1){
280 ret = 0;
281 goto handled;
282 } else {
283 fds[0].revents = 0;
284 ret--;
285 }
286 }
287
288 pthread_mutex_lock(&ctx->open_devs_lock);
289 for (i = 0, devh = NULL ; i < nfds && ret > 0 ; i++) {
290
291 tfds = &fds[i];
292 if (!tfds->revents)
293 continue;
294
295 ret--;
296 TAILQ_FOREACH(devh, &ctx->open_devs, list) {
297 if (libusb20_dev_get_fd(devh->os_priv) == tfds->fd)
298 break ;
299 }
300
301 if (tfds->revents & POLLERR) {
302 usb_remove_pollfd(ctx, libusb20_dev_get_fd(devh->os_priv));
303 if (devh != NULL)
304 usb_handle_disconnect(devh);
305 continue ;
306 }
307
308
309 pthread_mutex_lock(&libusb20_lock);
310 DPRINTF(ctx, LIBUSB_DEBUG_TRANSFER, "LIBUSB20_PROCESS");
311 if (devh != NULL)
312 ret = libusb20_dev_process(devh->os_priv);
313 pthread_mutex_unlock(&libusb20_lock);
314
315
316 if (ret == 0 || ret == LIBUSB20_ERROR_NO_DEVICE)
317 continue;
318 else if (ret < 0)
319 goto out;
320 }
321
322 ret = 0;
323out:
324 pthread_mutex_unlock(&ctx->open_devs_lock);
325
326handled:
327 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "handle_events leave");
328 return ret;
329}
330
331/* Polling and timing */
332
333int
334libusb_try_lock_events(libusb_context * ctx)
335{
336 int ret;
337
338 GET_CONTEXT(ctx);
339 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_try_lock_events enter");
340
341 pthread_mutex_lock(&ctx->pollfd_modify_lock);
342 ret = ctx->pollfd_modify;
343 pthread_mutex_unlock(&ctx->pollfd_modify_lock);
344
345 if (ret != 0)
346 return (1);
347
348 ret = pthread_mutex_trylock(&ctx->events_lock);
349
350 if (ret != 0)
351 return (1);
352
353 ctx->event_handler_active = 1;
354
355 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_try_lock_events leave");
356 return (0);
357}
358
359void
360libusb_lock_events(libusb_context * ctx)
361{
362 GET_CONTEXT(ctx);
363 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_lock_events enter");
364
365 pthread_mutex_lock(&ctx->events_lock);
366 ctx->event_handler_active = 1;
367
368 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_lock_events leave");
369}
370
371void
372libusb_unlock_events(libusb_context * ctx)
373{
374 GET_CONTEXT(ctx);
375 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_unlock_events enter");
376
377 ctx->event_handler_active = 0;
378 pthread_mutex_unlock(&ctx->events_lock);
379
380 pthread_mutex_lock(&ctx->event_waiters_lock);
381 pthread_cond_broadcast(&ctx->event_waiters_cond);
382 pthread_mutex_unlock(&ctx->event_waiters_lock);
383
384 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_unlock_events leave");
385}
386
387int
388libusb_event_handling_ok(libusb_context * ctx)
389{
390 int ret;
391
392 GET_CONTEXT(ctx);
393 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_event_handling_ok enter");
394
395 pthread_mutex_lock(&ctx->pollfd_modify_lock);
396 ret = ctx->pollfd_modify;
397 pthread_mutex_unlock(&ctx->pollfd_modify_lock);
398
399 if (ret != 0)
400 return (0);
401
402 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_event_handling_ok leave");
403 return (1);
404}
405
406int
407libusb_event_handler_active(libusb_context * ctx)
408{
409 int ret;
410
411 GET_CONTEXT(ctx);
412 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_event_handler_active enter");
413
414 pthread_mutex_lock(&ctx->pollfd_modify_lock);
415 ret = ctx->pollfd_modify;
416 pthread_mutex_unlock(&ctx->pollfd_modify_lock);
417
418 if (ret != 0)
419 return (1);
420
421 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_event_handler_active leave");
422 return (ctx->event_handler_active);
423}
424
425void
426libusb_lock_event_waiters(libusb_context * ctx)
427{
428 GET_CONTEXT(ctx);
429 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_lock_event_waiters enter");
430
431 pthread_mutex_lock(&ctx->event_waiters_lock);
432
433 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_lock_event_waiters leave");
434}
435
436void
437libusb_unlock_event_waiters(libusb_context * ctx)
438{
439 GET_CONTEXT(ctx);
440 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_unlock_event_waiters enter");
441
442 pthread_mutex_unlock(&ctx->event_waiters_lock);
443
444 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_unlock_event_waiters leave");
445}
446
447int
448libusb_wait_for_event(libusb_context * ctx, struct timeval *tv)
449{
450 int ret;
451 struct timespec ts;
452
453 GET_CONTEXT(ctx);
454 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_wait_for_event enter");
455
456 if (tv == NULL) {
457 pthread_cond_wait(&ctx->event_waiters_cond,
458 &ctx->event_waiters_lock);
459 return (0);
460 }
461
462 ret = clock_gettime(CLOCK_REALTIME, &ts);

--- 8 unchanged lines hidden (view full) ---

471 }
472
473 ret = pthread_cond_timedwait(&ctx->event_waiters_cond,
474 &ctx->event_waiters_lock, &ts);
475
476 if (ret == ETIMEDOUT)
477 return (1);
478
479 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_wait_for_event leave");
480 return (0);
481}
482
483int
484libusb_handle_events_timeout(libusb_context * ctx, struct timeval *tv)
485{
486 struct timeval poll_timeout;
487 int ret;
488
489 GET_CONTEXT(ctx);
490 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_handle_events_timeout enter");
491
492 ret = get_next_timeout(ctx, tv, &poll_timeout);
493 if (ret != 0) {
494 return handle_timeouts(ctx);
495 }
496retry:
497 if (libusb_try_lock_events(ctx) == 0) {
498 ret = handle_events(ctx, &poll_timeout);

--- 10 unchanged lines hidden (view full) ---

509 ret = libusb_wait_for_event(ctx, &poll_timeout);
510 libusb_unlock_event_waiters(ctx);
511
512 if (ret < 0)
513 return ret;
514 else if (ret == 1)
515 return (handle_timeouts(ctx));
516
517 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_handle_events_timeout leave");
518 return (0);
519}
520
521int
522libusb_handle_events(libusb_context * ctx)
523{
524 struct timeval tv;
525 int ret;
526
527 GET_CONTEXT(ctx);
528 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_handle_events enter");
529
530 tv.tv_sec = 2;
531 tv.tv_usec = 0;
532 ret = libusb_handle_events_timeout(ctx, &tv);
533
534 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_handle_events leave");
535 return (ret);
536}
537
538int
539libusb_handle_events_locked(libusb_context * ctx, struct timeval *tv)
540{
541 int ret;
542 struct timeval poll_tv;
543
544 GET_CONTEXT(ctx);
545 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_handle_events_locked enter");
546
547 ret = get_next_timeout(ctx, tv, &poll_tv);
548 if (ret != 0) {
549 return handle_timeouts(ctx);
550 }
551
552 ret = handle_events(ctx, &poll_tv);
553
554 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_handle_events_locked leave");
555 return (ret);
556}
557
558int
559libusb_get_next_timeout(libusb_context * ctx, struct timeval *tv)
560{
561 struct usb_transfer *xfer;
562 struct timeval *next_tv;
563 struct timeval cur_tv;
564 struct timespec cur_ts;
565 int found;
566 int ret;
567
568 GET_CONTEXT(ctx);
569 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_get_next_timeout enter");
570
571 found = 0;
572 pthread_mutex_lock(&ctx->flying_transfers_lock);
573 if (TAILQ_EMPTY(&ctx->flying_transfers)) {
574 pthread_mutex_unlock(&ctx->flying_transfers_lock);
575 return (0);
576 }
577
578 TAILQ_FOREACH(xfer, &ctx->flying_transfers, list) {
579 if (!(xfer->flags & USB_TIMED_OUT)) {
580 found = 1;
581 break ;
582 }
583 }
584 pthread_mutex_unlock(&ctx->flying_transfers_lock);
585
586 if (found == 0) {

--- 9 unchanged lines hidden (view full) ---

596 return (LIBUSB_ERROR_OTHER);
597 TIMESPEC_TO_TIMEVAL(&cur_tv, &cur_ts);
598
599 if (timercmp(&cur_tv, next_tv, >=) != 0)
600 timerclear(tv);
601 else
602 timersub(next_tv, &cur_tv, tv);
603
604 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_get_next_timeout leave");
605 return (1);
606}
607
608void
609libusb_set_pollfd_notifiers(libusb_context * ctx,
610 libusb_pollfd_added_cb added_cb, libusb_pollfd_removed_cb removed_cb,
611 void *user_data)
612{
613 GET_CONTEXT(ctx);
614 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_set_pollfd_notifiers enter");
615
616 ctx->fd_added_cb = added_cb;
617 ctx->fd_removed_cb = removed_cb;
618 ctx->fd_cb_user_data = user_data;
619
620 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_set_pollfd_notifiers leave");
621}
622
623struct libusb_pollfd **
624libusb_get_pollfds(libusb_context * ctx)
625{
626 struct usb_pollfd *pollfd;
627 libusb_pollfd **ret;
628 int i;
629
630 GET_CONTEXT(ctx);
631 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_get_pollfds enter");
632
633 i = 0;
634 pthread_mutex_lock(&ctx->pollfds_lock);
635 TAILQ_FOREACH(pollfd, &ctx->pollfds, list)
636 i++;
637
638 ret = calloc(i + 1 , sizeof(struct libusb_pollfd *));
639 if (ret == NULL) {
640 pthread_mutex_unlock(&ctx->pollfds_lock);
641 return (ret);
642 }
643
644 i = 0;
645 TAILQ_FOREACH(pollfd, &ctx->pollfds, list)
646 ret[i++] = (struct libusb_pollfd *) pollfd;
647 ret[i] = NULL;
648
649 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_get_pollfds leave");
650 return (ret);
651}
652
653
654/* Synchronous device I/O */
655
656static void ctrl_tr_cb(struct libusb_transfer *transfer)
657{
658 libusb_context *ctx;
659 int *complet;
660
661 ctx = NULL;
662 GET_CONTEXT(ctx);
663 DPRINTF(ctx, LIBUSB_DEBUG_TRANSFER, "CALLBACK ENTER");
664
665 complet = transfer->user_data;
666 *complet = 1;
667}
668
669int
670libusb_control_transfer(libusb_device_handle * devh,
671 uint8_t bmRequestType, uint8_t bRequest, uint16_t wValue, uint16_t wIndex,
672 unsigned char *data, uint16_t wLength, unsigned int timeout)
673{
674 struct libusb_transfer *xfer;
675 struct libusb_control_setup *ctr;
676 libusb_context *ctx;
677 unsigned char *buff;
678 int complet;
679 int ret;
680
681 ctx = devh->dev->ctx;
682 GET_CONTEXT(ctx);
683 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_control_transfer enter");
684
685 if (devh == NULL || data == NULL)
686 return (LIBUSB_ERROR_NO_MEM);
687
688 xfer = libusb_alloc_transfer(0);
689 if (xfer == NULL)
690 return (LIBUSB_ERROR_NO_MEM);
691

--- 52 unchanged lines hidden (view full) ---

744 case LIBUSB_TRANSFER_NO_DEVICE:
745 ret = xfer->status;
746 break;
747 default:
748 ret = LIBUSB_ERROR_OTHER;
749 }
750 libusb_free_transfer(xfer);
751
752 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_control_transfer leave");
753 return (ret);
754}
755
756static int
757do_transfer(struct libusb_device_handle *devh,
758 unsigned char endpoint, unsigned char *data, int length,
759 int *transferred, unsigned int timeout, int type)
760{

--- 5 unchanged lines hidden (view full) ---

766 if (devh == NULL || data == NULL)
767 return (LIBUSB_ERROR_NO_MEM);
768
769 xfer = libusb_alloc_transfer(0);
770 if (xfer == NULL)
771 return (LIBUSB_ERROR_NO_MEM);
772
773 ctx = devh->dev->ctx;
774 GET_CONTEXT(ctx);
775
776 xfer->dev_handle = devh;
777 xfer->endpoint = endpoint;
778 xfer->type = type;
779 xfer->timeout = timeout;
780 xfer->buffer = data;
781 xfer->length = length;
782 xfer->user_data = &complet;
783 xfer->callback = ctrl_tr_cb;
784 complet = 0;
785
786 DPRINTF(ctx, LIBUSB_DEBUG_TRANSFER, "SUBMIT_TRANSFER");
787 if ((ret = libusb_submit_transfer(xfer)) < 0) {
788 libusb_free_transfer(xfer);
789 DPRINTF(ctx, LIBUSB_DEBUG_TRANSFER, "SUBMIT_TRANSFER FAILED %i", ret);
790 return (ret);
791 }
792
793 while (complet == 0) {
794 if ((ret = libusb_handle_events(ctx)) < 0) {
795 libusb_cancel_transfer(xfer);
796 libusb_free_transfer(xfer);
797 while (complet == 0) {
798 if (libusb_handle_events(ctx) < 0)
799 break ;
800 }
801 return (ret);
802 }
803 }
804
805 *transferred = xfer->actual_length;
806 DPRINTF(ctx, LIBUSB_DEBUG_TRANSFER, "xfer->status %i", xfer->status);
807 switch (xfer->status) {
808 case LIBUSB_TRANSFER_COMPLETED:
809 ret = xfer->actual_length;
810 break;
811 case LIBUSB_TRANSFER_TIMED_OUT:
812 case LIBUSB_TRANSFER_OVERFLOW:
813 case LIBUSB_TRANSFER_STALL:
814 case LIBUSB_TRANSFER_NO_DEVICE:

--- 12 unchanged lines hidden (view full) ---

827 unsigned char endpoint, unsigned char *data, int length,
828 int *transferred, unsigned int timeout)
829{
830 libusb_context *ctx;
831 int ret;
832
833 ctx = NULL;
834 GET_CONTEXT(ctx);
835 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_bulk_transfer enter");
836
837 ret = do_transfer(devh, endpoint, data, length, transferred,
838 timeout, LIBUSB_TRANSFER_TYPE_BULK);
839
840 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_bulk_transfer leave");
841 return (ret);
842}
843
844/*
845 * Need to fix xfer->type
846 */
847int
848libusb_interrupt_transfer(struct libusb_device_handle *devh,
849 unsigned char endpoint, unsigned char *data, int length,
850 int *transferred, unsigned int timeout)
851{
852 libusb_context *ctx;
853 int ret;
854
855 ctx = NULL;
856 GET_CONTEXT(ctx);
857 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_interrupt_transfer enter");
858
859 ret = do_transfer(devh, endpoint, data, length, transferred,
860 timeout, LIBUSB_TRANSFER_TYPE_INTERRUPT);
861
862 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_interrupt_transfer leave");
863 return (ret);
864}