libusb10.c revision 213848
1/* $FreeBSD: head/lib/libusb/libusb10.c 213848 2010-10-14 20:04:36Z hselasky $ */
2/*-
3 * Copyright (c) 2009 Sylvestre Gallon. All rights reserved.
4 * Copyright (c) 2009 Hans Petter Selasky. All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:
9 * 1. Redistributions of source code must retain the above copyright
10 *    notice, this list of conditions and the following disclaimer.
11 * 2. Redistributions in binary form must reproduce the above copyright
12 *    notice, this list of conditions and the following disclaimer in the
13 *    documentation and/or other materials provided with the distribution.
14 *
15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
16 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18 * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
19 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
24 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25 * SUCH DAMAGE.
26 */
27
28#include <sys/fcntl.h>
29#include <sys/ioctl.h>
30#include <sys/queue.h>
31
32#include <assert.h>
33#include <errno.h>
34#include <poll.h>
35#include <pthread.h>
36#include <stdio.h>
37#include <stdlib.h>
38#include <unistd.h>
39
40#define	libusb_device_handle libusb20_device
41
42#include "libusb20.h"
43#include "libusb20_desc.h"
44#include "libusb20_int.h"
45#include "libusb.h"
46#include "libusb10.h"
47
48static pthread_mutex_t default_context_lock = PTHREAD_MUTEX_INITIALIZER;
49struct libusb_context *usbi_default_context = NULL;
50
51/* Prototypes */
52
53static struct libusb20_transfer *libusb10_get_transfer(struct libusb20_device *, uint8_t, uint8_t);
54static int libusb10_get_maxframe(struct libusb20_device *, libusb_transfer *);
55static int libusb10_get_buffsize(struct libusb20_device *, libusb_transfer *);
56static int libusb10_convert_error(uint8_t status);
57static void libusb10_complete_transfer(struct libusb20_transfer *, struct libusb_super_transfer *, int);
58static void libusb10_isoc_proxy(struct libusb20_transfer *);
59static void libusb10_bulk_intr_proxy(struct libusb20_transfer *);
60static void libusb10_ctrl_proxy(struct libusb20_transfer *);
61static void libusb10_submit_transfer_sub(struct libusb20_device *, uint8_t);
62
63/*  Library initialisation / deinitialisation */
64
65void
66libusb_set_debug(libusb_context *ctx, int level)
67{
68	ctx = GET_CONTEXT(ctx);
69	if (ctx)
70		ctx->debug = level;
71}
72
73int
74libusb_init(libusb_context **context)
75{
76	struct libusb_context *ctx;
77	char *debug;
78	int flag;
79	int ret;
80
81	ctx = malloc(sizeof(*ctx));
82	if (!ctx)
83		return (LIBUSB_ERROR_INVALID_PARAM);
84
85	memset(ctx, 0, sizeof(*ctx));
86
87	debug = getenv("LIBUSB_DEBUG");
88	if (debug != NULL) {
89		ctx->debug = atoi(debug);
90		if (ctx->debug != 0)
91			ctx->debug_fixed = 1;
92	}
93	TAILQ_INIT(&ctx->pollfds);
94	TAILQ_INIT(&ctx->tr_done);
95
96	pthread_mutex_init(&ctx->ctx_lock, NULL);
97	pthread_cond_init(&ctx->ctx_cond, NULL);
98
99	ctx->ctx_handler = NO_THREAD;
100
101	ret = pipe(ctx->ctrl_pipe);
102	if (ret < 0) {
103		pthread_mutex_destroy(&ctx->ctx_lock);
104		pthread_cond_destroy(&ctx->ctx_cond);
105		free(ctx);
106		return (LIBUSB_ERROR_OTHER);
107	}
108	/* set non-blocking mode on the control pipe to avoid deadlock */
109	flag = 1;
110	ret = fcntl(ctx->ctrl_pipe[0], O_NONBLOCK, &flag);
111	assert(ret != -1 && "Couldn't set O_NONBLOCK for ctx->ctrl_pipe[0]");
112	flag = 1;
113	ret = fcntl(ctx->ctrl_pipe[1], O_NONBLOCK, &flag);
114	assert(ret != -1 && "Couldn't set O_NONBLOCK for ctx->ctrl_pipe[1]");
115
116	libusb10_add_pollfd(ctx, &ctx->ctx_poll, NULL, ctx->ctrl_pipe[0], POLLIN);
117
118	pthread_mutex_lock(&default_context_lock);
119	if (usbi_default_context == NULL) {
120		usbi_default_context = ctx;
121	}
122	pthread_mutex_unlock(&default_context_lock);
123
124	if (context)
125		*context = ctx;
126
127	DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_init complete");
128
129	return (0);
130}
131
132void
133libusb_exit(libusb_context *ctx)
134{
135	ctx = GET_CONTEXT(ctx);
136
137	if (ctx == NULL)
138		return;
139
140	/* XXX cleanup devices */
141
142	libusb10_remove_pollfd(ctx, &ctx->ctx_poll);
143	close(ctx->ctrl_pipe[0]);
144	close(ctx->ctrl_pipe[1]);
145	pthread_mutex_destroy(&ctx->ctx_lock);
146	pthread_cond_destroy(&ctx->ctx_cond);
147
148	pthread_mutex_lock(&default_context_lock);
149	if (ctx == usbi_default_context) {
150		usbi_default_context = NULL;
151	}
152	pthread_mutex_unlock(&default_context_lock);
153
154	free(ctx);
155}
156
157/* Device handling and initialisation. */
158
159ssize_t
160libusb_get_device_list(libusb_context *ctx, libusb_device ***list)
161{
162	struct libusb20_backend *usb_backend;
163	struct libusb20_device *pdev;
164	struct libusb_device *dev;
165	int i;
166
167	ctx = GET_CONTEXT(ctx);
168
169	if (ctx == NULL)
170		return (LIBUSB_ERROR_INVALID_PARAM);
171
172	if (list == NULL)
173		return (LIBUSB_ERROR_INVALID_PARAM);
174
175	usb_backend = libusb20_be_alloc_default();
176	if (usb_backend == NULL)
177		return (LIBUSB_ERROR_NO_MEM);
178
179	/* figure out how many USB devices are present */
180	pdev = NULL;
181	i = 0;
182	while ((pdev = libusb20_be_device_foreach(usb_backend, pdev)))
183		i++;
184
185	/* allocate device pointer list */
186	*list = malloc((i + 1) * sizeof(void *));
187	if (*list == NULL) {
188		libusb20_be_free(usb_backend);
189		return (LIBUSB_ERROR_NO_MEM);
190	}
191	/* create libusb v1.0 compliant devices */
192	i = 0;
193	while ((pdev = libusb20_be_device_foreach(usb_backend, NULL))) {
194
195		dev = malloc(sizeof(*dev));
196		if (dev == NULL) {
197			while (i != 0) {
198				libusb_unref_device((*list)[i - 1]);
199				i--;
200			}
201			free(*list);
202			*list = NULL;
203			libusb20_be_free(usb_backend);
204			return (LIBUSB_ERROR_NO_MEM);
205		}
206
207		/* get device into libUSB v1.0 list */
208		libusb20_be_dequeue_device(usb_backend, pdev);
209
210		memset(dev, 0, sizeof(*dev));
211
212		/* init transfer queues */
213		TAILQ_INIT(&dev->tr_head);
214
215		/* set context we belong to */
216		dev->ctx = ctx;
217
218		/* link together the two structures */
219		dev->os_priv = pdev;
220		pdev->privLuData = dev;
221
222		(*list)[i] = libusb_ref_device(dev);
223		i++;
224	}
225	(*list)[i] = NULL;
226
227	libusb20_be_free(usb_backend);
228	return (i);
229}
230
231void
232libusb_free_device_list(libusb_device **list, int unref_devices)
233{
234	int i;
235
236	if (list == NULL)
237		return;			/* be NULL safe */
238
239	if (unref_devices) {
240		for (i = 0; list[i] != NULL; i++)
241			libusb_unref_device(list[i]);
242	}
243	free(list);
244}
245
246uint8_t
247libusb_get_bus_number(libusb_device *dev)
248{
249	if (dev == NULL)
250		return (0);		/* should not happen */
251	return (libusb20_dev_get_bus_number(dev->os_priv));
252}
253
254uint8_t
255libusb_get_device_address(libusb_device *dev)
256{
257	if (dev == NULL)
258		return (0);		/* should not happen */
259	return (libusb20_dev_get_address(dev->os_priv));
260}
261
262int
263libusb_get_max_packet_size(libusb_device *dev, uint8_t endpoint)
264{
265	struct libusb_config_descriptor *pdconf;
266	struct libusb_interface *pinf;
267	struct libusb_interface_descriptor *pdinf;
268	struct libusb_endpoint_descriptor *pdend;
269	int i;
270	int j;
271	int k;
272	int ret;
273
274	if (dev == NULL)
275		return (LIBUSB_ERROR_NO_DEVICE);
276
277	ret = libusb_get_active_config_descriptor(dev, &pdconf);
278	if (ret < 0)
279		return (ret);
280
281	ret = LIBUSB_ERROR_NOT_FOUND;
282	for (i = 0; i < pdconf->bNumInterfaces; i++) {
283		pinf = &pdconf->interface[i];
284		for (j = 0; j < pinf->num_altsetting; j++) {
285			pdinf = &pinf->altsetting[j];
286			for (k = 0; k < pdinf->bNumEndpoints; k++) {
287				pdend = &pdinf->endpoint[k];
288				if (pdend->bEndpointAddress == endpoint) {
289					ret = pdend->wMaxPacketSize;
290					goto out;
291				}
292			}
293		}
294	}
295
296out:
297	libusb_free_config_descriptor(pdconf);
298	return (ret);
299}
300
301libusb_device *
302libusb_ref_device(libusb_device *dev)
303{
304	if (dev == NULL)
305		return (NULL);		/* be NULL safe */
306
307	CTX_LOCK(dev->ctx);
308	dev->refcnt++;
309	CTX_UNLOCK(dev->ctx);
310
311	return (dev);
312}
313
314void
315libusb_unref_device(libusb_device *dev)
316{
317	if (dev == NULL)
318		return;			/* be NULL safe */
319
320	CTX_LOCK(dev->ctx);
321	dev->refcnt--;
322	CTX_UNLOCK(dev->ctx);
323
324	if (dev->refcnt == 0) {
325		libusb20_dev_free(dev->os_priv);
326		free(dev);
327	}
328}
329
330int
331libusb_open(libusb_device *dev, libusb_device_handle **devh)
332{
333	libusb_context *ctx = dev->ctx;
334	struct libusb20_device *pdev = dev->os_priv;
335	uint8_t dummy;
336	int err;
337
338	if (devh == NULL)
339		return (LIBUSB_ERROR_INVALID_PARAM);
340
341	/* set default device handle value */
342	*devh = NULL;
343
344	dev = libusb_ref_device(dev);
345	if (dev == NULL)
346		return (LIBUSB_ERROR_INVALID_PARAM);
347
348	err = libusb20_dev_open(pdev, 16 * 4 /* number of endpoints */ );
349	if (err) {
350		libusb_unref_device(dev);
351		return (LIBUSB_ERROR_NO_MEM);
352	}
353	libusb10_add_pollfd(ctx, &dev->dev_poll, pdev, libusb20_dev_get_fd(pdev), POLLIN |
354	    POLLOUT | POLLRDNORM | POLLWRNORM);
355
356	/* make sure our event loop detects the new device */
357	dummy = 0;
358	err = write(ctx->ctrl_pipe[1], &dummy, sizeof(dummy));
359	if (err < sizeof(dummy)) {
360		/* ignore error, if any */
361		DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_open write failed!");
362	}
363	*devh = pdev;
364
365	return (0);
366}
367
368libusb_device_handle *
369libusb_open_device_with_vid_pid(libusb_context *ctx, uint16_t vendor_id,
370    uint16_t product_id)
371{
372	struct libusb_device **devs;
373	struct libusb20_device *pdev;
374	struct LIBUSB20_DEVICE_DESC_DECODED *pdesc;
375	int i;
376	int j;
377
378	ctx = GET_CONTEXT(ctx);
379	if (ctx == NULL)
380		return (NULL);		/* be NULL safe */
381
382	DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_open_device_width_vid_pid enter");
383
384	if ((i = libusb_get_device_list(ctx, &devs)) < 0)
385		return (NULL);
386
387	for (j = 0; j < i; j++) {
388		pdev = devs[j]->os_priv;
389		pdesc = libusb20_dev_get_device_desc(pdev);
390		/*
391		 * NOTE: The USB library will automatically swap the
392		 * fields in the device descriptor to be of host
393		 * endian type!
394		 */
395		if (pdesc->idVendor == vendor_id &&
396		    pdesc->idProduct == product_id) {
397			if (libusb_open(devs[j], &pdev) < 0)
398				pdev = NULL;
399			break;
400		}
401	}
402	if (j == i)
403		pdev = NULL;
404
405	libusb_free_device_list(devs, 1);
406	DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_open_device_width_vid_pid leave");
407	return (pdev);
408}
409
410void
411libusb_close(struct libusb20_device *pdev)
412{
413	libusb_context *ctx;
414	struct libusb_device *dev;
415	uint8_t dummy;
416	int err;
417
418	if (pdev == NULL)
419		return;			/* be NULL safe */
420
421	dev = libusb_get_device(pdev);
422	ctx = dev->ctx;
423
424	libusb10_remove_pollfd(ctx, &dev->dev_poll);
425
426	libusb20_dev_close(pdev);
427
428	/* unref will free the "pdev" when the refcount reaches zero */
429	libusb_unref_device(dev);
430
431	/* make sure our event loop detects the closed device */
432	dummy = 0;
433	err = write(ctx->ctrl_pipe[1], &dummy, sizeof(dummy));
434	if (err < sizeof(dummy)) {
435		/* ignore error, if any */
436		DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_close write failed!");
437	}
438}
439
440libusb_device *
441libusb_get_device(struct libusb20_device *pdev)
442{
443	if (pdev == NULL)
444		return (NULL);
445	return ((libusb_device *)pdev->privLuData);
446}
447
448int
449libusb_get_configuration(struct libusb20_device *pdev, int *config)
450{
451	struct libusb20_config *pconf;
452
453	if (pdev == NULL || config == NULL)
454		return (LIBUSB_ERROR_INVALID_PARAM);
455
456	pconf = libusb20_dev_alloc_config(pdev, libusb20_dev_get_config_index(pdev));
457	if (pconf == NULL)
458		return (LIBUSB_ERROR_NO_MEM);
459
460	*config = pconf->desc.bConfigurationValue;
461
462	free(pconf);
463
464	return (0);
465}
466
467int
468libusb_set_configuration(struct libusb20_device *pdev, int configuration)
469{
470	struct libusb20_config *pconf;
471	struct libusb_device *dev;
472	int err;
473	uint8_t i;
474
475	dev = libusb_get_device(pdev);
476
477	if (dev == NULL)
478		return (LIBUSB_ERROR_INVALID_PARAM);
479
480	if (configuration < 1) {
481		/* unconfigure */
482		i = 255;
483	} else {
484		for (i = 0; i != 255; i++) {
485			uint8_t found;
486
487			pconf = libusb20_dev_alloc_config(pdev, i);
488			if (pconf == NULL)
489				return (LIBUSB_ERROR_INVALID_PARAM);
490			found = (pconf->desc.bConfigurationValue
491			    == configuration);
492			free(pconf);
493
494			if (found)
495				goto set_config;
496		}
497		return (LIBUSB_ERROR_INVALID_PARAM);
498	}
499
500set_config:
501
502	libusb10_cancel_all_transfer(dev);
503
504	libusb10_remove_pollfd(dev->ctx, &dev->dev_poll);
505
506	err = libusb20_dev_set_config_index(pdev, i);
507
508	libusb10_add_pollfd(dev->ctx, &dev->dev_poll, pdev, libusb20_dev_get_fd(pdev), POLLIN |
509	    POLLOUT | POLLRDNORM | POLLWRNORM);
510
511	return (err ? LIBUSB_ERROR_INVALID_PARAM : 0);
512}
513
514int
515libusb_claim_interface(struct libusb20_device *pdev, int interface_number)
516{
517	libusb_device *dev;
518	int err = 0;
519
520	dev = libusb_get_device(pdev);
521	if (dev == NULL)
522		return (LIBUSB_ERROR_INVALID_PARAM);
523
524	if (interface_number < 0 || interface_number > 31)
525		return (LIBUSB_ERROR_INVALID_PARAM);
526
527	CTX_LOCK(dev->ctx);
528	if (dev->claimed_interfaces & (1 << interface_number))
529		err = LIBUSB_ERROR_BUSY;
530
531	if (!err)
532		dev->claimed_interfaces |= (1 << interface_number);
533	CTX_UNLOCK(dev->ctx);
534	return (err);
535}
536
537int
538libusb_release_interface(struct libusb20_device *pdev, int interface_number)
539{
540	libusb_device *dev;
541	int err = 0;
542
543	dev = libusb_get_device(pdev);
544	if (dev == NULL)
545		return (LIBUSB_ERROR_INVALID_PARAM);
546
547	if (interface_number < 0 || interface_number > 31)
548		return (LIBUSB_ERROR_INVALID_PARAM);
549
550	CTX_LOCK(dev->ctx);
551	if (!(dev->claimed_interfaces & (1 << interface_number)))
552		err = LIBUSB_ERROR_NOT_FOUND;
553
554	if (!err)
555		dev->claimed_interfaces &= ~(1 << interface_number);
556	CTX_UNLOCK(dev->ctx);
557	return (err);
558}
559
560int
561libusb_set_interface_alt_setting(struct libusb20_device *pdev,
562    int interface_number, int alternate_setting)
563{
564	libusb_device *dev;
565	int err = 0;
566
567	dev = libusb_get_device(pdev);
568	if (dev == NULL)
569		return (LIBUSB_ERROR_INVALID_PARAM);
570
571	if (interface_number < 0 || interface_number > 31)
572		return (LIBUSB_ERROR_INVALID_PARAM);
573
574	CTX_LOCK(dev->ctx);
575	if (!(dev->claimed_interfaces & (1 << interface_number)))
576		err = LIBUSB_ERROR_NOT_FOUND;
577	CTX_UNLOCK(dev->ctx);
578
579	if (err)
580		return (err);
581
582	libusb10_cancel_all_transfer(dev);
583
584	libusb10_remove_pollfd(dev->ctx, &dev->dev_poll);
585
586	err = libusb20_dev_set_alt_index(pdev,
587	    interface_number, alternate_setting);
588
589	libusb10_add_pollfd(dev->ctx, &dev->dev_poll,
590	    pdev, libusb20_dev_get_fd(pdev),
591	    POLLIN | POLLOUT | POLLRDNORM | POLLWRNORM);
592
593	return (err ? LIBUSB_ERROR_OTHER : 0);
594}
595
596static struct libusb20_transfer *
597libusb10_get_transfer(struct libusb20_device *pdev,
598    uint8_t endpoint, uint8_t index)
599{
600	index &= 1;			/* double buffering */
601
602	index |= (endpoint & LIBUSB20_ENDPOINT_ADDRESS_MASK) * 4;
603
604	if (endpoint & LIBUSB20_ENDPOINT_DIR_MASK) {
605		/* this is an IN endpoint */
606		index |= 2;
607	}
608	return (libusb20_tr_get_pointer(pdev, index));
609}
610
611int
612libusb_clear_halt(struct libusb20_device *pdev, uint8_t endpoint)
613{
614	struct libusb20_transfer *xfer;
615	struct libusb_device *dev;
616	int err;
617
618	xfer = libusb10_get_transfer(pdev, endpoint, 0);
619	if (xfer == NULL)
620		return (LIBUSB_ERROR_INVALID_PARAM);
621
622	dev = libusb_get_device(pdev);
623
624	CTX_LOCK(dev->ctx);
625	err = libusb20_tr_open(xfer, 0, 0, endpoint);
626	CTX_UNLOCK(dev->ctx);
627
628	if (err != 0 && err != LIBUSB20_ERROR_BUSY)
629		return (LIBUSB_ERROR_OTHER);
630
631	libusb20_tr_clear_stall_sync(xfer);
632
633	/* check if we opened the transfer */
634	if (err == 0) {
635		CTX_LOCK(dev->ctx);
636		libusb20_tr_close(xfer);
637		CTX_UNLOCK(dev->ctx);
638	}
639	return (0);			/* success */
640}
641
642int
643libusb_reset_device(struct libusb20_device *pdev)
644{
645	libusb_device *dev;
646	int err;
647
648	dev = libusb_get_device(pdev);
649	if (dev == NULL)
650		return (LIBUSB20_ERROR_INVALID_PARAM);
651
652	libusb10_cancel_all_transfer(dev);
653
654	libusb10_remove_pollfd(dev->ctx, &dev->dev_poll);
655
656	err = libusb20_dev_reset(pdev);
657
658	libusb10_add_pollfd(dev->ctx, &dev->dev_poll,
659	    pdev, libusb20_dev_get_fd(pdev),
660	    POLLIN | POLLOUT | POLLRDNORM | POLLWRNORM);
661
662	return (err ? LIBUSB_ERROR_OTHER : 0);
663}
664
665int
666libusb_check_connected(struct libusb20_device *pdev)
667{
668	libusb_device *dev;
669	int err;
670
671	dev = libusb_get_device(pdev);
672	if (dev == NULL)
673		return (LIBUSB_ERROR_INVALID_PARAM);
674
675	err = libusb20_dev_check_connected(pdev);
676
677	return (err ? LIBUSB_ERROR_NO_DEVICE : 0);
678}
679
680int
681libusb_kernel_driver_active(struct libusb20_device *pdev, int interface)
682{
683	if (pdev == NULL)
684		return (LIBUSB_ERROR_INVALID_PARAM);
685
686	return (libusb20_dev_kernel_driver_active(
687	    pdev, interface));
688}
689
690int
691libusb_detach_kernel_driver(struct libusb20_device *pdev, int interface)
692{
693	int err;
694
695	if (pdev == NULL)
696		return (LIBUSB_ERROR_INVALID_PARAM);
697
698	err = libusb20_dev_detach_kernel_driver(
699	    pdev, interface);
700
701	return (err ? LIBUSB20_ERROR_OTHER : 0);
702}
703
704int
705libusb_attach_kernel_driver(struct libusb20_device *pdev, int interface)
706{
707	if (pdev == NULL)
708		return (LIBUSB_ERROR_INVALID_PARAM);
709	/* stub - currently not supported by libusb20 */
710	return (0);
711}
712
713/* Asynchronous device I/O */
714
715struct libusb_transfer *
716libusb_alloc_transfer(int iso_packets)
717{
718	struct libusb_transfer *uxfer;
719	struct libusb_super_transfer *sxfer;
720	int len;
721
722	len = sizeof(struct libusb_transfer) +
723	    sizeof(struct libusb_super_transfer) +
724	    (iso_packets * sizeof(libusb_iso_packet_descriptor));
725
726	sxfer = malloc(len);
727	if (sxfer == NULL)
728		return (NULL);
729
730	memset(sxfer, 0, len);
731
732	uxfer = (struct libusb_transfer *)(
733	    ((uint8_t *)sxfer) + sizeof(*sxfer));
734
735	/* set default value */
736	uxfer->num_iso_packets = iso_packets;
737
738	return (uxfer);
739}
740
741void
742libusb_free_transfer(struct libusb_transfer *uxfer)
743{
744	struct libusb_super_transfer *sxfer;
745
746	if (uxfer == NULL)
747		return;			/* be NULL safe */
748
749	sxfer = (struct libusb_super_transfer *)(
750	    (uint8_t *)uxfer - sizeof(*sxfer));
751
752	free(sxfer);
753}
754
755static int
756libusb10_get_maxframe(struct libusb20_device *pdev, libusb_transfer *xfer)
757{
758	int ret;
759	int usb_speed;
760
761	usb_speed = libusb20_dev_get_speed(pdev);
762
763	switch (xfer->type) {
764	case LIBUSB_TRANSFER_TYPE_ISOCHRONOUS:
765		switch (usb_speed) {
766		case LIBUSB20_SPEED_LOW:
767		case LIBUSB20_SPEED_FULL:
768			ret = 60 * 1;
769			break;
770		default:
771			ret = 60 * 8;
772			break;
773		}
774		break;
775	case LIBUSB_TRANSFER_TYPE_CONTROL:
776		ret = 2;
777		break;
778	default:
779		ret = 1;
780		break;
781	}
782	return (ret);
783}
784
785static int
786libusb10_get_buffsize(struct libusb20_device *pdev, libusb_transfer *xfer)
787{
788	int ret;
789	int usb_speed;
790
791	usb_speed = libusb20_dev_get_speed(pdev);
792
793	switch (xfer->type) {
794	case LIBUSB_TRANSFER_TYPE_ISOCHRONOUS:
795		ret = 0;		/* kernel will auto-select */
796		break;
797	case LIBUSB_TRANSFER_TYPE_CONTROL:
798		ret = 1024;
799		break;
800	default:
801		switch (usb_speed) {
802		case LIBUSB20_SPEED_LOW:
803			ret = 256;
804			break;
805		case LIBUSB20_SPEED_FULL:
806			ret = 4096;
807			break;
808		default:
809			ret = 16384;
810			break;
811		}
812		break;
813	}
814	return (ret);
815}
816
817static int
818libusb10_convert_error(uint8_t status)
819{
820	;				/* indent fix */
821
822	switch (status) {
823	case LIBUSB20_TRANSFER_START:
824	case LIBUSB20_TRANSFER_COMPLETED:
825		return (LIBUSB_TRANSFER_COMPLETED);
826	case LIBUSB20_TRANSFER_OVERFLOW:
827		return (LIBUSB_TRANSFER_OVERFLOW);
828	case LIBUSB20_TRANSFER_NO_DEVICE:
829		return (LIBUSB_TRANSFER_NO_DEVICE);
830	case LIBUSB20_TRANSFER_STALL:
831		return (LIBUSB_TRANSFER_STALL);
832	case LIBUSB20_TRANSFER_CANCELLED:
833		return (LIBUSB_TRANSFER_CANCELLED);
834	case LIBUSB20_TRANSFER_TIMED_OUT:
835		return (LIBUSB_TRANSFER_TIMED_OUT);
836	default:
837		return (LIBUSB_TRANSFER_ERROR);
838	}
839}
840
841/* This function must be called locked */
842
843static void
844libusb10_complete_transfer(struct libusb20_transfer *pxfer,
845    struct libusb_super_transfer *sxfer, int status)
846{
847	struct libusb_transfer *uxfer;
848	struct libusb_device *dev;
849
850	uxfer = (struct libusb_transfer *)(
851	    ((uint8_t *)sxfer) + sizeof(*sxfer));
852
853	if (pxfer != NULL)
854		libusb20_tr_set_priv_sc1(pxfer, NULL);
855
856	/* set transfer status */
857	uxfer->status = status;
858
859	/* update super transfer state */
860	sxfer->state = LIBUSB_SUPER_XFER_ST_NONE;
861
862	dev = libusb_get_device(uxfer->dev_handle);
863
864	TAILQ_INSERT_TAIL(&dev->ctx->tr_done, sxfer, entry);
865}
866
867/* This function must be called locked */
868
869static void
870libusb10_isoc_proxy(struct libusb20_transfer *pxfer)
871{
872	struct libusb_super_transfer *sxfer;
873	struct libusb_transfer *uxfer;
874	uint32_t actlen;
875	uint16_t iso_packets;
876	uint16_t i;
877	uint8_t status;
878	uint8_t flags;
879
880	status = libusb20_tr_get_status(pxfer);
881	sxfer = libusb20_tr_get_priv_sc1(pxfer);
882	actlen = libusb20_tr_get_actual_length(pxfer);
883	iso_packets = libusb20_tr_get_max_frames(pxfer);
884
885	if (sxfer == NULL)
886		return;			/* cancelled - nothing to do */
887
888	uxfer = (struct libusb_transfer *)(
889	    ((uint8_t *)sxfer) + sizeof(*sxfer));
890
891	if (iso_packets > uxfer->num_iso_packets)
892		iso_packets = uxfer->num_iso_packets;
893
894	if (iso_packets == 0)
895		return;			/* nothing to do */
896
897	/* make sure that the number of ISOCHRONOUS packets is valid */
898	uxfer->num_iso_packets = iso_packets;
899
900	flags = uxfer->flags;
901
902	switch (status) {
903	case LIBUSB20_TRANSFER_COMPLETED:
904
905		/* update actual length */
906		uxfer->actual_length = actlen;
907		for (i = 0; i != iso_packets; i++) {
908			uxfer->iso_packet_desc[i].actual_length =
909			    libusb20_tr_get_length(pxfer, i);
910		}
911		libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_COMPLETED);
912		break;
913
914	case LIBUSB20_TRANSFER_START:
915
916		/* setup length(s) */
917		actlen = 0;
918		for (i = 0; i != iso_packets; i++) {
919			libusb20_tr_setup_isoc(pxfer,
920			    &uxfer->buffer[actlen],
921			    uxfer->iso_packet_desc[i].length, i);
922			actlen += uxfer->iso_packet_desc[i].length;
923		}
924
925		/* no remainder */
926		sxfer->rem_len = 0;
927
928		libusb20_tr_set_total_frames(pxfer, iso_packets);
929		libusb20_tr_submit(pxfer);
930
931		/* fork another USB transfer, if any */
932		libusb10_submit_transfer_sub(libusb20_tr_get_priv_sc0(pxfer), uxfer->endpoint);
933		break;
934
935	default:
936		libusb10_complete_transfer(pxfer, sxfer, libusb10_convert_error(status));
937		break;
938	}
939}
940
941/* This function must be called locked */
942
943static void
944libusb10_bulk_intr_proxy(struct libusb20_transfer *pxfer)
945{
946	struct libusb_super_transfer *sxfer;
947	struct libusb_transfer *uxfer;
948	uint32_t max_bulk;
949	uint32_t actlen;
950	uint8_t status;
951	uint8_t flags;
952
953	status = libusb20_tr_get_status(pxfer);
954	sxfer = libusb20_tr_get_priv_sc1(pxfer);
955	max_bulk = libusb20_tr_get_max_total_length(pxfer);
956	actlen = libusb20_tr_get_actual_length(pxfer);
957
958	if (sxfer == NULL)
959		return;			/* cancelled - nothing to do */
960
961	uxfer = (struct libusb_transfer *)(
962	    ((uint8_t *)sxfer) + sizeof(*sxfer));
963
964	flags = uxfer->flags;
965
966	switch (status) {
967	case LIBUSB20_TRANSFER_COMPLETED:
968
969		uxfer->actual_length += actlen;
970
971		/* check for short packet */
972		if (sxfer->last_len != actlen) {
973			if (flags & LIBUSB_TRANSFER_SHORT_NOT_OK) {
974				libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_ERROR);
975			} else {
976				libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_COMPLETED);
977			}
978			break;
979		}
980		/* check for end of data */
981		if (sxfer->rem_len == 0) {
982			libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_COMPLETED);
983			break;
984		}
985		/* FALLTHROUGH */
986
987	case LIBUSB20_TRANSFER_START:
988		if (max_bulk > sxfer->rem_len) {
989			max_bulk = sxfer->rem_len;
990		}
991		/* setup new BULK or INTERRUPT transaction */
992		libusb20_tr_setup_bulk(pxfer,
993		    sxfer->curr_data, max_bulk, uxfer->timeout);
994
995		/* update counters */
996		sxfer->last_len = max_bulk;
997		sxfer->curr_data += max_bulk;
998		sxfer->rem_len -= max_bulk;
999
1000		libusb20_tr_submit(pxfer);
1001
1002		/* check if we can fork another USB transfer */
1003		if (sxfer->rem_len == 0)
1004			libusb10_submit_transfer_sub(libusb20_tr_get_priv_sc0(pxfer), uxfer->endpoint);
1005		break;
1006
1007	default:
1008		libusb10_complete_transfer(pxfer, sxfer, libusb10_convert_error(status));
1009		break;
1010	}
1011}
1012
1013/* This function must be called locked */
1014
1015static void
1016libusb10_ctrl_proxy(struct libusb20_transfer *pxfer)
1017{
1018	struct libusb_super_transfer *sxfer;
1019	struct libusb_transfer *uxfer;
1020	uint32_t max_bulk;
1021	uint32_t actlen;
1022	uint8_t status;
1023	uint8_t flags;
1024
1025	status = libusb20_tr_get_status(pxfer);
1026	sxfer = libusb20_tr_get_priv_sc1(pxfer);
1027	max_bulk = libusb20_tr_get_max_total_length(pxfer);
1028	actlen = libusb20_tr_get_actual_length(pxfer);
1029
1030	if (sxfer == NULL)
1031		return;			/* cancelled - nothing to do */
1032
1033	uxfer = (struct libusb_transfer *)(
1034	    ((uint8_t *)sxfer) + sizeof(*sxfer));
1035
1036	flags = uxfer->flags;
1037
1038	switch (status) {
1039	case LIBUSB20_TRANSFER_COMPLETED:
1040
1041		uxfer->actual_length += actlen;
1042
1043		/* subtract length of SETUP packet, if any */
1044		actlen -= libusb20_tr_get_length(pxfer, 0);
1045
1046		/* check for short packet */
1047		if (sxfer->last_len != actlen) {
1048			if (flags & LIBUSB_TRANSFER_SHORT_NOT_OK) {
1049				libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_ERROR);
1050			} else {
1051				libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_COMPLETED);
1052			}
1053			break;
1054		}
1055		/* check for end of data */
1056		if (sxfer->rem_len == 0) {
1057			libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_COMPLETED);
1058			break;
1059		}
1060		/* FALLTHROUGH */
1061
1062	case LIBUSB20_TRANSFER_START:
1063		if (max_bulk > sxfer->rem_len) {
1064			max_bulk = sxfer->rem_len;
1065		}
1066		/* setup new CONTROL transaction */
1067		if (status == LIBUSB20_TRANSFER_COMPLETED) {
1068			/* next fragment - don't send SETUP packet */
1069			libusb20_tr_set_length(pxfer, 0, 0);
1070		} else {
1071			/* first fragment - send SETUP packet */
1072			libusb20_tr_set_length(pxfer, 8, 0);
1073			libusb20_tr_set_buffer(pxfer, uxfer->buffer, 0);
1074		}
1075
1076		if (max_bulk != 0) {
1077			libusb20_tr_set_length(pxfer, max_bulk, 1);
1078			libusb20_tr_set_buffer(pxfer, sxfer->curr_data, 1);
1079			libusb20_tr_set_total_frames(pxfer, 2);
1080		} else {
1081			libusb20_tr_set_total_frames(pxfer, 1);
1082		}
1083
1084		/* update counters */
1085		sxfer->last_len = max_bulk;
1086		sxfer->curr_data += max_bulk;
1087		sxfer->rem_len -= max_bulk;
1088
1089		libusb20_tr_submit(pxfer);
1090
1091		/* check if we can fork another USB transfer */
1092		if (sxfer->rem_len == 0)
1093			libusb10_submit_transfer_sub(libusb20_tr_get_priv_sc0(pxfer), uxfer->endpoint);
1094		break;
1095
1096	default:
1097		libusb10_complete_transfer(pxfer, sxfer, libusb10_convert_error(status));
1098		break;
1099	}
1100}
1101
1102/* The following function must be called locked */
1103
1104static void
1105libusb10_submit_transfer_sub(struct libusb20_device *pdev, uint8_t endpoint)
1106{
1107	struct libusb20_transfer *pxfer0;
1108	struct libusb20_transfer *pxfer1;
1109	struct libusb_super_transfer *sxfer;
1110	struct libusb_transfer *uxfer;
1111	struct libusb_device *dev;
1112	int err;
1113	int buffsize;
1114	int maxframe;
1115	int temp;
1116	uint8_t dummy;
1117
1118	dev = libusb_get_device(pdev);
1119
1120	pxfer0 = libusb10_get_transfer(pdev, endpoint, 0);
1121	pxfer1 = libusb10_get_transfer(pdev, endpoint, 1);
1122
1123	if (pxfer0 == NULL || pxfer1 == NULL)
1124		return;			/* shouldn't happen */
1125
1126	temp = 0;
1127	if (libusb20_tr_pending(pxfer0))
1128		temp |= 1;
1129	if (libusb20_tr_pending(pxfer1))
1130		temp |= 2;
1131
1132	switch (temp) {
1133	case 3:
1134		/* wait till one of the transfers complete */
1135		return;
1136	case 2:
1137		sxfer = libusb20_tr_get_priv_sc1(pxfer1);
1138		if (sxfer == NULL)
1139			return;		/* cancelling */
1140		if (sxfer->rem_len)
1141			return;		/* cannot queue another one */
1142		/* swap transfers */
1143		pxfer1 = pxfer0;
1144		break;
1145	case 1:
1146		sxfer = libusb20_tr_get_priv_sc1(pxfer0);
1147		if (sxfer == NULL)
1148			return;		/* cancelling */
1149		if (sxfer->rem_len)
1150			return;		/* cannot queue another one */
1151		/* swap transfers */
1152		pxfer0 = pxfer1;
1153		break;
1154	default:
1155		break;
1156	}
1157
1158	/* find next transfer on same endpoint */
1159	TAILQ_FOREACH(sxfer, &dev->tr_head, entry) {
1160
1161		uxfer = (struct libusb_transfer *)(
1162		    ((uint8_t *)sxfer) + sizeof(*sxfer));
1163
1164		if (uxfer->endpoint == endpoint) {
1165			TAILQ_REMOVE(&dev->tr_head, sxfer, entry);
1166			sxfer->entry.tqe_prev = NULL;
1167			goto found;
1168		}
1169	}
1170	return;				/* success */
1171
1172found:
1173
1174	libusb20_tr_set_priv_sc0(pxfer0, pdev);
1175	libusb20_tr_set_priv_sc1(pxfer0, sxfer);
1176
1177	/* reset super transfer state */
1178	sxfer->rem_len = uxfer->length;
1179	sxfer->curr_data = uxfer->buffer;
1180	uxfer->actual_length = 0;
1181
1182	switch (uxfer->type) {
1183	case LIBUSB_TRANSFER_TYPE_ISOCHRONOUS:
1184		libusb20_tr_set_callback(pxfer0, libusb10_isoc_proxy);
1185		break;
1186	case LIBUSB_TRANSFER_TYPE_BULK:
1187	case LIBUSB_TRANSFER_TYPE_INTERRUPT:
1188		libusb20_tr_set_callback(pxfer0, libusb10_bulk_intr_proxy);
1189		break;
1190	case LIBUSB_TRANSFER_TYPE_CONTROL:
1191		libusb20_tr_set_callback(pxfer0, libusb10_ctrl_proxy);
1192		if (sxfer->rem_len < 8)
1193			goto failure;
1194
1195		/* remove SETUP packet from data */
1196		sxfer->rem_len -= 8;
1197		sxfer->curr_data += 8;
1198		break;
1199	default:
1200		goto failure;
1201	}
1202
1203	buffsize = libusb10_get_buffsize(pdev, uxfer);
1204	maxframe = libusb10_get_maxframe(pdev, uxfer);
1205
1206	/* make sure the transfer is opened */
1207	err = libusb20_tr_open(pxfer0, buffsize, maxframe, endpoint);
1208	if (err && (err != LIBUSB20_ERROR_BUSY)) {
1209		goto failure;
1210	}
1211	libusb20_tr_start(pxfer0);
1212	return;
1213
1214failure:
1215	libusb10_complete_transfer(pxfer0, sxfer, LIBUSB_TRANSFER_ERROR);
1216
1217	/* make sure our event loop spins the done handler */
1218	dummy = 0;
1219	write(dev->ctx->ctrl_pipe[1], &dummy, sizeof(dummy));
1220}
1221
1222/* The following function must be called unlocked */
1223
1224int
1225libusb_submit_transfer(struct libusb_transfer *uxfer)
1226{
1227	struct libusb20_transfer *pxfer0;
1228	struct libusb20_transfer *pxfer1;
1229	struct libusb_super_transfer *sxfer;
1230	struct libusb_device *dev;
1231	uint32_t endpoint;
1232	int err;
1233
1234	if (uxfer == NULL)
1235		return (LIBUSB_ERROR_INVALID_PARAM);
1236
1237	if (uxfer->dev_handle == NULL)
1238		return (LIBUSB_ERROR_INVALID_PARAM);
1239
1240	endpoint = uxfer->endpoint;
1241
1242	if (endpoint > 255)
1243		return (LIBUSB_ERROR_INVALID_PARAM);
1244
1245	dev = libusb_get_device(uxfer->dev_handle);
1246
1247	DPRINTF(dev->ctx, LIBUSB_DEBUG_FUNCTION, "libusb_submit_transfer enter");
1248
1249	sxfer = (struct libusb_super_transfer *)(
1250	    (uint8_t *)uxfer - sizeof(*sxfer));
1251
1252	CTX_LOCK(dev->ctx);
1253
1254	pxfer0 = libusb10_get_transfer(uxfer->dev_handle, endpoint, 0);
1255	pxfer1 = libusb10_get_transfer(uxfer->dev_handle, endpoint, 1);
1256
1257	if (pxfer0 == NULL || pxfer1 == NULL) {
1258		err = LIBUSB_ERROR_OTHER;
1259	} else if ((sxfer->entry.tqe_prev != NULL) ||
1260	    (libusb20_tr_get_priv_sc1(pxfer0) == sxfer) ||
1261	    (libusb20_tr_get_priv_sc1(pxfer1) == sxfer)) {
1262		err = LIBUSB_ERROR_BUSY;
1263	} else {
1264
1265		/* set pending state */
1266		sxfer->state = LIBUSB_SUPER_XFER_ST_PEND;
1267
1268		/* insert transfer into transfer head list */
1269		TAILQ_INSERT_TAIL(&dev->tr_head, sxfer, entry);
1270
1271		/* start work transfers */
1272		libusb10_submit_transfer_sub(
1273		    uxfer->dev_handle, endpoint);
1274
1275		err = 0;		/* success */
1276	}
1277
1278	CTX_UNLOCK(dev->ctx);
1279
1280	DPRINTF(dev->ctx, LIBUSB_DEBUG_FUNCTION, "libusb_submit_transfer leave %d", err);
1281
1282	return (err);
1283}
1284
1285/* Asynchronous transfer cancel */
1286
1287int
1288libusb_cancel_transfer(struct libusb_transfer *uxfer)
1289{
1290	struct libusb20_transfer *pxfer0;
1291	struct libusb20_transfer *pxfer1;
1292	struct libusb_super_transfer *sxfer;
1293	struct libusb_device *dev;
1294	uint32_t endpoint;
1295	int retval;
1296
1297	if (uxfer == NULL)
1298		return (LIBUSB_ERROR_INVALID_PARAM);
1299
1300	/* check if not initialised */
1301	if (uxfer->dev_handle == NULL)
1302		return (LIBUSB_ERROR_NOT_FOUND);
1303
1304	endpoint = uxfer->endpoint;
1305
1306	if (endpoint > 255)
1307		return (LIBUSB_ERROR_INVALID_PARAM);
1308
1309	dev = libusb_get_device(uxfer->dev_handle);
1310
1311	DPRINTF(dev->ctx, LIBUSB_DEBUG_FUNCTION, "libusb_cancel_transfer enter");
1312
1313	sxfer = (struct libusb_super_transfer *)(
1314	    (uint8_t *)uxfer - sizeof(*sxfer));
1315
1316	retval = 0;
1317
1318	CTX_LOCK(dev->ctx);
1319
1320	pxfer0 = libusb10_get_transfer(uxfer->dev_handle, endpoint, 0);
1321	pxfer1 = libusb10_get_transfer(uxfer->dev_handle, endpoint, 1);
1322
1323	if (sxfer->state != LIBUSB_SUPER_XFER_ST_PEND) {
1324		/* only update the transfer status */
1325		uxfer->status = LIBUSB_TRANSFER_CANCELLED;
1326		retval = LIBUSB_ERROR_NOT_FOUND;
1327	} else if (sxfer->entry.tqe_prev != NULL) {
1328		/* we are lucky - transfer is on a queue */
1329		TAILQ_REMOVE(&dev->tr_head, sxfer, entry);
1330		sxfer->entry.tqe_prev = NULL;
1331		libusb10_complete_transfer(NULL,
1332		    sxfer, LIBUSB_TRANSFER_CANCELLED);
1333	} else if (pxfer0 == NULL || pxfer1 == NULL) {
1334		/* not started */
1335		retval = LIBUSB_ERROR_NOT_FOUND;
1336	} else if (libusb20_tr_get_priv_sc1(pxfer0) == sxfer) {
1337		libusb10_complete_transfer(pxfer0,
1338		    sxfer, LIBUSB_TRANSFER_CANCELLED);
1339		libusb20_tr_stop(pxfer0);
1340		/* make sure the queue doesn't stall */
1341		libusb10_submit_transfer_sub(
1342		    uxfer->dev_handle, endpoint);
1343	} else if (libusb20_tr_get_priv_sc1(pxfer1) == sxfer) {
1344		libusb10_complete_transfer(pxfer1,
1345		    sxfer, LIBUSB_TRANSFER_CANCELLED);
1346		libusb20_tr_stop(pxfer1);
1347		/* make sure the queue doesn't stall */
1348		libusb10_submit_transfer_sub(
1349		    uxfer->dev_handle, endpoint);
1350	} else {
1351		/* not started */
1352		retval = LIBUSB_ERROR_NOT_FOUND;
1353	}
1354
1355	CTX_UNLOCK(dev->ctx);
1356
1357	DPRINTF(dev->ctx, LIBUSB_DEBUG_FUNCTION, "libusb_cancel_transfer leave");
1358
1359	return (retval);
1360}
1361
1362UNEXPORTED void
1363libusb10_cancel_all_transfer(libusb_device *dev)
1364{
1365	/* TODO */
1366}
1367
1368uint16_t
1369libusb_cpu_to_le16(uint16_t x)
1370{
1371	return (htole16(x));
1372}
1373
1374uint16_t
1375libusb_le16_to_cpu(uint16_t x)
1376{
1377	return (le16toh(x));
1378}
1379
1380