2 * USB redirector usb-guest
4 * Copyright (c) 2011 Red Hat, Inc.
7 * Hans de Goede <hdegoede@redhat.com>
9 * Permission is hereby granted, free of charge, to any person obtaining a copy
10 * of this software and associated documentation files (the "Software"), to deal
11 * in the Software without restriction, including without limitation the rights
12 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
13 * copies of the Software, and to permit persons to whom the Software is
14 * furnished to do so, subject to the following conditions:
16 * The above copyright notice and this permission notice shall be included in
17 * all copies or substantial portions of the Software.
19 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
20 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
22 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
23 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
24 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
28 #include "qemu-common.h"
29 #include "qemu-timer.h"
34 #include <sys/ioctl.h>
36 #include <usbredirparser.h>
40 #define MAX_ENDPOINTS 32
41 #define EP2I(ep_address) (((ep_address & 0x80) >> 3) | (ep_address & 0x0f))
42 #define I2EP(i) (((i & 0x10) << 3) | (i & 0x0f))
44 typedef struct AsyncURB AsyncURB
;
45 typedef struct USBRedirDevice USBRedirDevice
;
47 /* Struct to hold buffered packets (iso or int input packets) */
52 QTAILQ_ENTRY(buf_packet
)next
;
58 uint8_t interface
; /* bInterfaceNumber this ep belongs to */
60 uint8_t iso_error
; /* For reporting iso errors to the HC */
61 uint8_t interrupt_started
;
62 uint8_t interrupt_error
;
63 uint8_t bufpq_prefilled
;
64 uint8_t bufpq_dropping_packets
;
65 QTAILQ_HEAD(, buf_packet
) bufpq
;
67 int bufpq_target_size
;
70 struct USBRedirDevice
{
75 /* Data passed from chardev the fd_read cb to the usbredirparser read cb */
76 const uint8_t *read_buf
;
78 /* For async handling of open/close */
79 QEMUBH
*open_close_bh
;
80 /* To delay the usb attach in case of quick chardev close + open */
81 QEMUTimer
*attach_timer
;
82 int64_t next_attach_time
;
83 struct usbredirparser
*parser
;
84 struct endp_data endpoint
[MAX_ENDPOINTS
];
86 QTAILQ_HEAD(, AsyncURB
) asyncq
;
95 struct usb_redir_control_packet_header control_packet
;
96 struct usb_redir_bulk_packet_header bulk_packet
;
97 struct usb_redir_interrupt_packet_header interrupt_packet
;
99 QTAILQ_ENTRY(AsyncURB
)next
;
102 static void usbredir_device_connect(void *priv
,
103 struct usb_redir_device_connect_header
*device_connect
);
104 static void usbredir_device_disconnect(void *priv
);
105 static void usbredir_interface_info(void *priv
,
106 struct usb_redir_interface_info_header
*interface_info
);
107 static void usbredir_ep_info(void *priv
,
108 struct usb_redir_ep_info_header
*ep_info
);
109 static void usbredir_configuration_status(void *priv
, uint32_t id
,
110 struct usb_redir_configuration_status_header
*configuration_status
);
111 static void usbredir_alt_setting_status(void *priv
, uint32_t id
,
112 struct usb_redir_alt_setting_status_header
*alt_setting_status
);
113 static void usbredir_iso_stream_status(void *priv
, uint32_t id
,
114 struct usb_redir_iso_stream_status_header
*iso_stream_status
);
115 static void usbredir_interrupt_receiving_status(void *priv
, uint32_t id
,
116 struct usb_redir_interrupt_receiving_status_header
117 *interrupt_receiving_status
);
118 static void usbredir_bulk_streams_status(void *priv
, uint32_t id
,
119 struct usb_redir_bulk_streams_status_header
*bulk_streams_status
);
120 static void usbredir_control_packet(void *priv
, uint32_t id
,
121 struct usb_redir_control_packet_header
*control_packet
,
122 uint8_t *data
, int data_len
);
123 static void usbredir_bulk_packet(void *priv
, uint32_t id
,
124 struct usb_redir_bulk_packet_header
*bulk_packet
,
125 uint8_t *data
, int data_len
);
126 static void usbredir_iso_packet(void *priv
, uint32_t id
,
127 struct usb_redir_iso_packet_header
*iso_packet
,
128 uint8_t *data
, int data_len
);
129 static void usbredir_interrupt_packet(void *priv
, uint32_t id
,
130 struct usb_redir_interrupt_packet_header
*interrupt_header
,
131 uint8_t *data
, int data_len
);
133 static int usbredir_handle_status(USBRedirDevice
*dev
,
134 int status
, int actual_len
);
136 #define VERSION "qemu usb-redir guest " QEMU_VERSION
144 if (dev->debug >= usbredirparser_error) { \
145 error_report("usb-redir error: " __VA_ARGS__); \
148 #define WARNING(...) \
150 if (dev->debug >= usbredirparser_warning) { \
151 error_report("usb-redir warning: " __VA_ARGS__); \
156 if (dev->debug >= usbredirparser_info) { \
157 error_report("usb-redir: " __VA_ARGS__); \
160 #define DPRINTF(...) \
162 if (dev->debug >= usbredirparser_debug) { \
163 error_report("usb-redir: " __VA_ARGS__); \
166 #define DPRINTF2(...) \
168 if (dev->debug >= usbredirparser_debug_data) { \
169 error_report("usb-redir: " __VA_ARGS__); \
173 static void usbredir_log(void *priv
, int level
, const char *msg
)
175 USBRedirDevice
*dev
= priv
;
177 if (dev
->debug
< level
) {
181 error_report("%s", msg
);
184 static void usbredir_log_data(USBRedirDevice
*dev
, const char *desc
,
185 const uint8_t *data
, int len
)
189 if (dev
->debug
< usbredirparser_debug_data
) {
193 for (i
= 0; i
< len
; i
+= j
) {
196 n
= sprintf(buf
, "%s", desc
);
197 for (j
= 0; j
< 8 && i
+ j
< len
; j
++) {
198 n
+= sprintf(buf
+ n
, " %02X", data
[i
+ j
]);
200 error_report("%s", buf
);
205 * usbredirparser io functions
208 static int usbredir_read(void *priv
, uint8_t *data
, int count
)
210 USBRedirDevice
*dev
= priv
;
212 if (dev
->read_buf_size
< count
) {
213 count
= dev
->read_buf_size
;
216 memcpy(data
, dev
->read_buf
, count
);
218 dev
->read_buf_size
-= count
;
219 if (dev
->read_buf_size
) {
220 dev
->read_buf
+= count
;
222 dev
->read_buf
= NULL
;
228 static int usbredir_write(void *priv
, uint8_t *data
, int count
)
230 USBRedirDevice
*dev
= priv
;
232 if (!dev
->cs
->opened
) {
236 return qemu_chr_fe_write(dev
->cs
, data
, count
);
240 * Async and buffered packets helpers
243 static AsyncURB
*async_alloc(USBRedirDevice
*dev
, USBPacket
*p
)
245 AsyncURB
*aurb
= (AsyncURB
*) g_malloc0(sizeof(AsyncURB
));
248 aurb
->packet_id
= dev
->packet_id
;
249 QTAILQ_INSERT_TAIL(&dev
->asyncq
, aurb
, next
);
255 static void async_free(USBRedirDevice
*dev
, AsyncURB
*aurb
)
257 QTAILQ_REMOVE(&dev
->asyncq
, aurb
, next
);
261 static AsyncURB
*async_find(USBRedirDevice
*dev
, uint32_t packet_id
)
265 QTAILQ_FOREACH(aurb
, &dev
->asyncq
, next
) {
266 if (aurb
->packet_id
== packet_id
) {
270 ERROR("could not find async urb for packet_id %u\n", packet_id
);
274 static void usbredir_cancel_packet(USBDevice
*udev
, USBPacket
*p
)
276 USBRedirDevice
*dev
= DO_UPCAST(USBRedirDevice
, dev
, udev
);
279 QTAILQ_FOREACH(aurb
, &dev
->asyncq
, next
) {
280 if (p
!= aurb
->packet
) {
284 DPRINTF("async cancel id %u\n", aurb
->packet_id
);
285 usbredirparser_send_cancel_data_packet(dev
->parser
, aurb
->packet_id
);
286 usbredirparser_do_write(dev
->parser
);
288 /* Mark it as dead */
294 static void bufp_alloc(USBRedirDevice
*dev
,
295 uint8_t *data
, int len
, int status
, uint8_t ep
)
297 struct buf_packet
*bufp
;
299 if (!dev
->endpoint
[EP2I(ep
)].bufpq_dropping_packets
&&
300 dev
->endpoint
[EP2I(ep
)].bufpq_size
>
301 2 * dev
->endpoint
[EP2I(ep
)].bufpq_target_size
) {
302 DPRINTF("bufpq overflow, dropping packets ep %02X\n", ep
);
303 dev
->endpoint
[EP2I(ep
)].bufpq_dropping_packets
= 1;
305 /* Since we're interupting the stream anyways, drop enough packets to get
306 back to our target buffer size */
307 if (dev
->endpoint
[EP2I(ep
)].bufpq_dropping_packets
) {
308 if (dev
->endpoint
[EP2I(ep
)].bufpq_size
>
309 dev
->endpoint
[EP2I(ep
)].bufpq_target_size
) {
313 dev
->endpoint
[EP2I(ep
)].bufpq_dropping_packets
= 0;
316 bufp
= g_malloc(sizeof(struct buf_packet
));
319 bufp
->status
= status
;
320 QTAILQ_INSERT_TAIL(&dev
->endpoint
[EP2I(ep
)].bufpq
, bufp
, next
);
321 dev
->endpoint
[EP2I(ep
)].bufpq_size
++;
324 static void bufp_free(USBRedirDevice
*dev
, struct buf_packet
*bufp
,
327 QTAILQ_REMOVE(&dev
->endpoint
[EP2I(ep
)].bufpq
, bufp
, next
);
328 dev
->endpoint
[EP2I(ep
)].bufpq_size
--;
333 static void usbredir_free_bufpq(USBRedirDevice
*dev
, uint8_t ep
)
335 struct buf_packet
*buf
, *buf_next
;
337 QTAILQ_FOREACH_SAFE(buf
, &dev
->endpoint
[EP2I(ep
)].bufpq
, next
, buf_next
) {
338 bufp_free(dev
, buf
, ep
);
343 * USBDevice callbacks
346 static void usbredir_handle_reset(USBDevice
*udev
)
348 USBRedirDevice
*dev
= DO_UPCAST(USBRedirDevice
, dev
, udev
);
350 DPRINTF("reset device\n");
351 usbredirparser_send_reset(dev
->parser
);
352 usbredirparser_do_write(dev
->parser
);
355 static int usbredir_handle_iso_data(USBRedirDevice
*dev
, USBPacket
*p
,
359 if (!dev
->endpoint
[EP2I(ep
)].iso_started
&&
360 !dev
->endpoint
[EP2I(ep
)].iso_error
) {
361 struct usb_redir_start_iso_stream_header start_iso
= {
366 if (dev
->dev
.speed
== USB_SPEED_HIGH
) {
367 pkts_per_sec
= 8000 / dev
->endpoint
[EP2I(ep
)].interval
;
369 pkts_per_sec
= 1000 / dev
->endpoint
[EP2I(ep
)].interval
;
371 /* Testing has shown that we need circa 60 ms buffer */
372 dev
->endpoint
[EP2I(ep
)].bufpq_target_size
= (pkts_per_sec
* 60) / 1000;
374 /* Aim for approx 100 interrupts / second on the client to
375 balance latency and interrupt load */
376 start_iso
.pkts_per_urb
= pkts_per_sec
/ 100;
377 if (start_iso
.pkts_per_urb
< 1) {
378 start_iso
.pkts_per_urb
= 1;
379 } else if (start_iso
.pkts_per_urb
> 32) {
380 start_iso
.pkts_per_urb
= 32;
383 start_iso
.no_urbs
= (dev
->endpoint
[EP2I(ep
)].bufpq_target_size
+
384 start_iso
.pkts_per_urb
- 1) /
385 start_iso
.pkts_per_urb
;
386 /* Output endpoints pre-fill only 1/2 of the packets, keeping the rest
387 as overflow buffer. Also see the usbredir protocol documentation */
388 if (!(ep
& USB_DIR_IN
)) {
389 start_iso
.no_urbs
*= 2;
391 if (start_iso
.no_urbs
> 16) {
392 start_iso
.no_urbs
= 16;
395 /* No id, we look at the ep when receiving a status back */
396 usbredirparser_send_start_iso_stream(dev
->parser
, 0, &start_iso
);
397 usbredirparser_do_write(dev
->parser
);
398 DPRINTF("iso stream started ep %02X\n", ep
);
399 dev
->endpoint
[EP2I(ep
)].iso_started
= 1;
400 dev
->endpoint
[EP2I(ep
)].bufpq_prefilled
= 0;
401 dev
->endpoint
[EP2I(ep
)].bufpq_dropping_packets
= 0;
404 if (ep
& USB_DIR_IN
) {
405 struct buf_packet
*isop
;
407 if (dev
->endpoint
[EP2I(ep
)].iso_started
&&
408 !dev
->endpoint
[EP2I(ep
)].bufpq_prefilled
) {
409 if (dev
->endpoint
[EP2I(ep
)].bufpq_size
<
410 dev
->endpoint
[EP2I(ep
)].bufpq_target_size
) {
411 return usbredir_handle_status(dev
, 0, 0);
413 dev
->endpoint
[EP2I(ep
)].bufpq_prefilled
= 1;
416 isop
= QTAILQ_FIRST(&dev
->endpoint
[EP2I(ep
)].bufpq
);
418 DPRINTF2("iso-token-in ep %02X, no isop\n", ep
);
419 /* Re-fill the buffer */
420 dev
->endpoint
[EP2I(ep
)].bufpq_prefilled
= 0;
421 /* Check iso_error for stream errors, otherwise its an underrun */
422 status
= dev
->endpoint
[EP2I(ep
)].iso_error
;
423 dev
->endpoint
[EP2I(ep
)].iso_error
= 0;
424 return usbredir_handle_status(dev
, status
, 0);
426 DPRINTF2("iso-token-in ep %02X status %d len %d\n", ep
, isop
->status
,
429 status
= isop
->status
;
430 if (status
!= usb_redir_success
) {
431 bufp_free(dev
, isop
, ep
);
432 return usbredir_handle_status(dev
, status
, 0);
436 if (len
> p
->iov
.size
) {
437 ERROR("received iso data is larger then packet ep %02X\n", ep
);
438 bufp_free(dev
, isop
, ep
);
441 usb_packet_copy(p
, isop
->data
, len
);
442 bufp_free(dev
, isop
, ep
);
445 /* If the stream was not started because of a pending error don't
446 send the packet to the usb-host */
447 if (dev
->endpoint
[EP2I(ep
)].iso_started
) {
448 struct usb_redir_iso_packet_header iso_packet
= {
450 .length
= p
->iov
.size
452 uint8_t buf
[p
->iov
.size
];
453 /* No id, we look at the ep when receiving a status back */
454 usb_packet_copy(p
, buf
, p
->iov
.size
);
455 usbredirparser_send_iso_packet(dev
->parser
, 0, &iso_packet
,
457 usbredirparser_do_write(dev
->parser
);
459 status
= dev
->endpoint
[EP2I(ep
)].iso_error
;
460 dev
->endpoint
[EP2I(ep
)].iso_error
= 0;
461 DPRINTF2("iso-token-out ep %02X status %d len %zd\n", ep
, status
,
463 return usbredir_handle_status(dev
, status
, p
->iov
.size
);
467 static void usbredir_stop_iso_stream(USBRedirDevice
*dev
, uint8_t ep
)
469 struct usb_redir_stop_iso_stream_header stop_iso_stream
= {
472 if (dev
->endpoint
[EP2I(ep
)].iso_started
) {
473 usbredirparser_send_stop_iso_stream(dev
->parser
, 0, &stop_iso_stream
);
474 DPRINTF("iso stream stopped ep %02X\n", ep
);
475 dev
->endpoint
[EP2I(ep
)].iso_started
= 0;
477 dev
->endpoint
[EP2I(ep
)].iso_error
= 0;
478 usbredir_free_bufpq(dev
, ep
);
481 static int usbredir_handle_bulk_data(USBRedirDevice
*dev
, USBPacket
*p
,
484 AsyncURB
*aurb
= async_alloc(dev
, p
);
485 struct usb_redir_bulk_packet_header bulk_packet
;
487 DPRINTF("bulk-out ep %02X len %zd id %u\n", ep
,
488 p
->iov
.size
, aurb
->packet_id
);
490 bulk_packet
.endpoint
= ep
;
491 bulk_packet
.length
= p
->iov
.size
;
492 bulk_packet
.stream_id
= 0;
493 aurb
->bulk_packet
= bulk_packet
;
495 if (ep
& USB_DIR_IN
) {
496 usbredirparser_send_bulk_packet(dev
->parser
, aurb
->packet_id
,
497 &bulk_packet
, NULL
, 0);
499 uint8_t buf
[p
->iov
.size
];
500 usb_packet_copy(p
, buf
, p
->iov
.size
);
501 usbredir_log_data(dev
, "bulk data out:", buf
, p
->iov
.size
);
502 usbredirparser_send_bulk_packet(dev
->parser
, aurb
->packet_id
,
503 &bulk_packet
, buf
, p
->iov
.size
);
505 usbredirparser_do_write(dev
->parser
);
506 return USB_RET_ASYNC
;
509 static int usbredir_handle_interrupt_data(USBRedirDevice
*dev
,
510 USBPacket
*p
, uint8_t ep
)
512 if (ep
& USB_DIR_IN
) {
513 /* Input interrupt endpoint, buffered packet input */
514 struct buf_packet
*intp
;
517 if (!dev
->endpoint
[EP2I(ep
)].interrupt_started
&&
518 !dev
->endpoint
[EP2I(ep
)].interrupt_error
) {
519 struct usb_redir_start_interrupt_receiving_header start_int
= {
522 /* No id, we look at the ep when receiving a status back */
523 usbredirparser_send_start_interrupt_receiving(dev
->parser
, 0,
525 usbredirparser_do_write(dev
->parser
);
526 DPRINTF("interrupt recv started ep %02X\n", ep
);
527 dev
->endpoint
[EP2I(ep
)].interrupt_started
= 1;
528 /* We don't really want to drop interrupt packets ever, but
529 having some upper limit to how much we buffer is good. */
530 dev
->endpoint
[EP2I(ep
)].bufpq_target_size
= 1000;
531 dev
->endpoint
[EP2I(ep
)].bufpq_dropping_packets
= 0;
534 intp
= QTAILQ_FIRST(&dev
->endpoint
[EP2I(ep
)].bufpq
);
536 DPRINTF2("interrupt-token-in ep %02X, no intp\n", ep
);
537 /* Check interrupt_error for stream errors */
538 status
= dev
->endpoint
[EP2I(ep
)].interrupt_error
;
539 dev
->endpoint
[EP2I(ep
)].interrupt_error
= 0;
540 return usbredir_handle_status(dev
, status
, 0);
542 DPRINTF("interrupt-token-in ep %02X status %d len %d\n", ep
,
543 intp
->status
, intp
->len
);
545 status
= intp
->status
;
546 if (status
!= usb_redir_success
) {
547 bufp_free(dev
, intp
, ep
);
548 return usbredir_handle_status(dev
, status
, 0);
552 if (len
> p
->iov
.size
) {
553 ERROR("received int data is larger then packet ep %02X\n", ep
);
554 bufp_free(dev
, intp
, ep
);
557 usb_packet_copy(p
, intp
->data
, len
);
558 bufp_free(dev
, intp
, ep
);
561 /* Output interrupt endpoint, normal async operation */
562 AsyncURB
*aurb
= async_alloc(dev
, p
);
563 struct usb_redir_interrupt_packet_header interrupt_packet
;
564 uint8_t buf
[p
->iov
.size
];
566 DPRINTF("interrupt-out ep %02X len %zd id %u\n", ep
, p
->iov
.size
,
569 interrupt_packet
.endpoint
= ep
;
570 interrupt_packet
.length
= p
->iov
.size
;
571 aurb
->interrupt_packet
= interrupt_packet
;
573 usb_packet_copy(p
, buf
, p
->iov
.size
);
574 usbredir_log_data(dev
, "interrupt data out:", buf
, p
->iov
.size
);
575 usbredirparser_send_interrupt_packet(dev
->parser
, aurb
->packet_id
,
576 &interrupt_packet
, buf
, p
->iov
.size
);
577 usbredirparser_do_write(dev
->parser
);
578 return USB_RET_ASYNC
;
582 static void usbredir_stop_interrupt_receiving(USBRedirDevice
*dev
,
585 struct usb_redir_stop_interrupt_receiving_header stop_interrupt_recv
= {
588 if (dev
->endpoint
[EP2I(ep
)].interrupt_started
) {
589 usbredirparser_send_stop_interrupt_receiving(dev
->parser
, 0,
590 &stop_interrupt_recv
);
591 DPRINTF("interrupt recv stopped ep %02X\n", ep
);
592 dev
->endpoint
[EP2I(ep
)].interrupt_started
= 0;
594 dev
->endpoint
[EP2I(ep
)].interrupt_error
= 0;
595 usbredir_free_bufpq(dev
, ep
);
598 static int usbredir_handle_data(USBDevice
*udev
, USBPacket
*p
)
600 USBRedirDevice
*dev
= DO_UPCAST(USBRedirDevice
, dev
, udev
);
604 if (p
->pid
== USB_TOKEN_IN
) {
608 switch (dev
->endpoint
[EP2I(ep
)].type
) {
609 case USB_ENDPOINT_XFER_CONTROL
:
610 ERROR("handle_data called for control transfer on ep %02X\n", ep
);
612 case USB_ENDPOINT_XFER_ISOC
:
613 return usbredir_handle_iso_data(dev
, p
, ep
);
614 case USB_ENDPOINT_XFER_BULK
:
615 return usbredir_handle_bulk_data(dev
, p
, ep
);
616 case USB_ENDPOINT_XFER_INT
:
617 return usbredir_handle_interrupt_data(dev
, p
, ep
);
619 ERROR("handle_data ep %02X has unknown type %d\n", ep
,
620 dev
->endpoint
[EP2I(ep
)].type
);
625 static int usbredir_set_config(USBRedirDevice
*dev
, USBPacket
*p
,
628 struct usb_redir_set_configuration_header set_config
;
629 AsyncURB
*aurb
= async_alloc(dev
, p
);
632 DPRINTF("set config %d id %u\n", config
, aurb
->packet_id
);
634 for (i
= 0; i
< MAX_ENDPOINTS
; i
++) {
635 switch (dev
->endpoint
[i
].type
) {
636 case USB_ENDPOINT_XFER_ISOC
:
637 usbredir_stop_iso_stream(dev
, I2EP(i
));
639 case USB_ENDPOINT_XFER_INT
:
641 usbredir_stop_interrupt_receiving(dev
, I2EP(i
));
645 usbredir_free_bufpq(dev
, I2EP(i
));
648 set_config
.configuration
= config
;
649 usbredirparser_send_set_configuration(dev
->parser
, aurb
->packet_id
,
651 usbredirparser_do_write(dev
->parser
);
652 return USB_RET_ASYNC
;
655 static int usbredir_get_config(USBRedirDevice
*dev
, USBPacket
*p
)
657 AsyncURB
*aurb
= async_alloc(dev
, p
);
659 DPRINTF("get config id %u\n", aurb
->packet_id
);
662 usbredirparser_send_get_configuration(dev
->parser
, aurb
->packet_id
);
663 usbredirparser_do_write(dev
->parser
);
664 return USB_RET_ASYNC
;
667 static int usbredir_set_interface(USBRedirDevice
*dev
, USBPacket
*p
,
668 int interface
, int alt
)
670 struct usb_redir_set_alt_setting_header set_alt
;
671 AsyncURB
*aurb
= async_alloc(dev
, p
);
674 DPRINTF("set interface %d alt %d id %u\n", interface
, alt
,
677 for (i
= 0; i
< MAX_ENDPOINTS
; i
++) {
678 if (dev
->endpoint
[i
].interface
== interface
) {
679 switch (dev
->endpoint
[i
].type
) {
680 case USB_ENDPOINT_XFER_ISOC
:
681 usbredir_stop_iso_stream(dev
, I2EP(i
));
683 case USB_ENDPOINT_XFER_INT
:
685 usbredir_stop_interrupt_receiving(dev
, I2EP(i
));
689 usbredir_free_bufpq(dev
, I2EP(i
));
693 set_alt
.interface
= interface
;
695 usbredirparser_send_set_alt_setting(dev
->parser
, aurb
->packet_id
,
697 usbredirparser_do_write(dev
->parser
);
698 return USB_RET_ASYNC
;
701 static int usbredir_get_interface(USBRedirDevice
*dev
, USBPacket
*p
,
704 struct usb_redir_get_alt_setting_header get_alt
;
705 AsyncURB
*aurb
= async_alloc(dev
, p
);
707 DPRINTF("get interface %d id %u\n", interface
, aurb
->packet_id
);
709 get_alt
.interface
= interface
;
711 usbredirparser_send_get_alt_setting(dev
->parser
, aurb
->packet_id
,
713 usbredirparser_do_write(dev
->parser
);
714 return USB_RET_ASYNC
;
717 static int usbredir_handle_control(USBDevice
*udev
, USBPacket
*p
,
718 int request
, int value
, int index
, int length
, uint8_t *data
)
720 USBRedirDevice
*dev
= DO_UPCAST(USBRedirDevice
, dev
, udev
);
721 struct usb_redir_control_packet_header control_packet
;
724 /* Special cases for certain standard device requests */
726 case DeviceOutRequest
| USB_REQ_SET_ADDRESS
:
727 DPRINTF("set address %d\n", value
);
728 dev
->dev
.addr
= value
;
730 case DeviceOutRequest
| USB_REQ_SET_CONFIGURATION
:
731 return usbredir_set_config(dev
, p
, value
& 0xff);
732 case DeviceRequest
| USB_REQ_GET_CONFIGURATION
:
733 return usbredir_get_config(dev
, p
);
734 case InterfaceOutRequest
| USB_REQ_SET_INTERFACE
:
735 return usbredir_set_interface(dev
, p
, index
, value
);
736 case InterfaceRequest
| USB_REQ_GET_INTERFACE
:
737 return usbredir_get_interface(dev
, p
, index
);
740 /* "Normal" ctrl requests */
741 aurb
= async_alloc(dev
, p
);
743 /* Note request is (bRequestType << 8) | bRequest */
744 DPRINTF("ctrl-out type 0x%x req 0x%x val 0x%x index %d len %d id %u\n",
745 request
>> 8, request
& 0xff, value
, index
, length
,
748 control_packet
.request
= request
& 0xFF;
749 control_packet
.requesttype
= request
>> 8;
750 control_packet
.endpoint
= control_packet
.requesttype
& USB_DIR_IN
;
751 control_packet
.value
= value
;
752 control_packet
.index
= index
;
753 control_packet
.length
= length
;
754 aurb
->control_packet
= control_packet
;
756 if (control_packet
.requesttype
& USB_DIR_IN
) {
757 usbredirparser_send_control_packet(dev
->parser
, aurb
->packet_id
,
758 &control_packet
, NULL
, 0);
760 usbredir_log_data(dev
, "ctrl data out:", data
, length
);
761 usbredirparser_send_control_packet(dev
->parser
, aurb
->packet_id
,
762 &control_packet
, data
, length
);
764 usbredirparser_do_write(dev
->parser
);
765 return USB_RET_ASYNC
;
769 * Close events can be triggered by usbredirparser_do_write which gets called
770 * from within the USBDevice data / control packet callbacks and doing a
771 * usb_detach from within these callbacks is not a good idea.
773 * So we use a bh handler to take care of close events. We also handle
774 * open events from this callback to make sure that a close directly followed
775 * by an open gets handled in the right order.
777 static void usbredir_open_close_bh(void *opaque
)
779 USBRedirDevice
*dev
= opaque
;
781 usbredir_device_disconnect(dev
);
784 usbredirparser_destroy(dev
->parser
);
788 if (dev
->cs
->opened
) {
789 dev
->parser
= qemu_oom_check(usbredirparser_create());
790 dev
->parser
->priv
= dev
;
791 dev
->parser
->log_func
= usbredir_log
;
792 dev
->parser
->read_func
= usbredir_read
;
793 dev
->parser
->write_func
= usbredir_write
;
794 dev
->parser
->device_connect_func
= usbredir_device_connect
;
795 dev
->parser
->device_disconnect_func
= usbredir_device_disconnect
;
796 dev
->parser
->interface_info_func
= usbredir_interface_info
;
797 dev
->parser
->ep_info_func
= usbredir_ep_info
;
798 dev
->parser
->configuration_status_func
= usbredir_configuration_status
;
799 dev
->parser
->alt_setting_status_func
= usbredir_alt_setting_status
;
800 dev
->parser
->iso_stream_status_func
= usbredir_iso_stream_status
;
801 dev
->parser
->interrupt_receiving_status_func
=
802 usbredir_interrupt_receiving_status
;
803 dev
->parser
->bulk_streams_status_func
= usbredir_bulk_streams_status
;
804 dev
->parser
->control_packet_func
= usbredir_control_packet
;
805 dev
->parser
->bulk_packet_func
= usbredir_bulk_packet
;
806 dev
->parser
->iso_packet_func
= usbredir_iso_packet
;
807 dev
->parser
->interrupt_packet_func
= usbredir_interrupt_packet
;
808 dev
->read_buf
= NULL
;
809 dev
->read_buf_size
= 0;
810 usbredirparser_init(dev
->parser
, VERSION
, NULL
, 0, 0);
811 usbredirparser_do_write(dev
->parser
);
815 static void usbredir_do_attach(void *opaque
)
817 USBRedirDevice
*dev
= opaque
;
819 usb_device_attach(&dev
->dev
);
826 static int usbredir_chardev_can_read(void *opaque
)
828 USBRedirDevice
*dev
= opaque
;
831 /* usbredir_parser_do_read will consume *all* data we give it */
834 /* usbredir_open_close_bh hasn't handled the open event yet */
839 static void usbredir_chardev_read(void *opaque
, const uint8_t *buf
, int size
)
841 USBRedirDevice
*dev
= opaque
;
843 /* No recursion allowed! */
844 assert(dev
->read_buf
== NULL
);
847 dev
->read_buf_size
= size
;
849 usbredirparser_do_read(dev
->parser
);
850 /* Send any acks, etc. which may be queued now */
851 usbredirparser_do_write(dev
->parser
);
854 static void usbredir_chardev_event(void *opaque
, int event
)
856 USBRedirDevice
*dev
= opaque
;
859 case CHR_EVENT_OPENED
:
860 case CHR_EVENT_CLOSED
:
861 qemu_bh_schedule(dev
->open_close_bh
);
870 static int usbredir_initfn(USBDevice
*udev
)
872 USBRedirDevice
*dev
= DO_UPCAST(USBRedirDevice
, dev
, udev
);
875 if (dev
->cs
== NULL
) {
876 qerror_report(QERR_MISSING_PARAMETER
, "chardev");
880 dev
->open_close_bh
= qemu_bh_new(usbredir_open_close_bh
, dev
);
881 dev
->attach_timer
= qemu_new_timer_ms(vm_clock
, usbredir_do_attach
, dev
);
883 QTAILQ_INIT(&dev
->asyncq
);
884 for (i
= 0; i
< MAX_ENDPOINTS
; i
++) {
885 QTAILQ_INIT(&dev
->endpoint
[i
].bufpq
);
888 /* We'll do the attach once we receive the speed from the usb-host */
889 udev
->auto_attach
= 0;
891 /* Let the backend know we are ready */
892 qemu_chr_fe_open(dev
->cs
);
893 qemu_chr_add_handlers(dev
->cs
, usbredir_chardev_can_read
,
894 usbredir_chardev_read
, usbredir_chardev_event
, dev
);
899 static void usbredir_cleanup_device_queues(USBRedirDevice
*dev
)
901 AsyncURB
*aurb
, *next_aurb
;
904 QTAILQ_FOREACH_SAFE(aurb
, &dev
->asyncq
, next
, next_aurb
) {
905 async_free(dev
, aurb
);
907 for (i
= 0; i
< MAX_ENDPOINTS
; i
++) {
908 usbredir_free_bufpq(dev
, I2EP(i
));
912 static void usbredir_handle_destroy(USBDevice
*udev
)
914 USBRedirDevice
*dev
= DO_UPCAST(USBRedirDevice
, dev
, udev
);
916 qemu_chr_fe_close(dev
->cs
);
917 qemu_chr_delete(dev
->cs
);
918 /* Note must be done after qemu_chr_close, as that causes a close event */
919 qemu_bh_delete(dev
->open_close_bh
);
921 qemu_del_timer(dev
->attach_timer
);
922 qemu_free_timer(dev
->attach_timer
);
924 usbredir_cleanup_device_queues(dev
);
927 usbredirparser_destroy(dev
->parser
);
932 * usbredirparser packet complete callbacks
935 static int usbredir_handle_status(USBRedirDevice
*dev
,
936 int status
, int actual_len
)
939 case usb_redir_success
:
941 case usb_redir_stall
:
942 return USB_RET_STALL
;
943 case usb_redir_cancelled
:
944 WARNING("returning cancelled packet to HC?\n");
945 case usb_redir_inval
:
946 case usb_redir_ioerror
:
947 case usb_redir_timeout
:
953 static void usbredir_device_connect(void *priv
,
954 struct usb_redir_device_connect_header
*device_connect
)
956 USBRedirDevice
*dev
= priv
;
958 if (qemu_timer_pending(dev
->attach_timer
) || dev
->dev
.attached
) {
959 ERROR("Received device connect while already connected\n");
963 switch (device_connect
->speed
) {
964 case usb_redir_speed_low
:
965 DPRINTF("attaching low speed device\n");
966 dev
->dev
.speed
= USB_SPEED_LOW
;
968 case usb_redir_speed_full
:
969 DPRINTF("attaching full speed device\n");
970 dev
->dev
.speed
= USB_SPEED_FULL
;
972 case usb_redir_speed_high
:
973 DPRINTF("attaching high speed device\n");
974 dev
->dev
.speed
= USB_SPEED_HIGH
;
976 case usb_redir_speed_super
:
977 DPRINTF("attaching super speed device\n");
978 dev
->dev
.speed
= USB_SPEED_SUPER
;
981 DPRINTF("attaching unknown speed device, assuming full speed\n");
982 dev
->dev
.speed
= USB_SPEED_FULL
;
984 dev
->dev
.speedmask
= (1 << dev
->dev
.speed
);
985 qemu_mod_timer(dev
->attach_timer
, dev
->next_attach_time
);
988 static void usbredir_device_disconnect(void *priv
)
990 USBRedirDevice
*dev
= priv
;
993 /* Stop any pending attaches */
994 qemu_del_timer(dev
->attach_timer
);
996 if (dev
->dev
.attached
) {
997 usb_device_detach(&dev
->dev
);
999 * Delay next usb device attach to give the guest a chance to see
1000 * see the detach / attach in case of quick close / open succession
1002 dev
->next_attach_time
= qemu_get_clock_ms(vm_clock
) + 200;
1005 /* Reset state so that the next dev connected starts with a clean slate */
1006 usbredir_cleanup_device_queues(dev
);
1007 memset(dev
->endpoint
, 0, sizeof(dev
->endpoint
));
1008 for (i
= 0; i
< MAX_ENDPOINTS
; i
++) {
1009 QTAILQ_INIT(&dev
->endpoint
[i
].bufpq
);
1013 static void usbredir_interface_info(void *priv
,
1014 struct usb_redir_interface_info_header
*interface_info
)
1016 /* The intention is to allow specifying acceptable interface classes
1017 for redirection on the cmdline and in the future verify this here,
1018 and disconnect (or never connect) the device if a not accepted
1019 interface class is detected */
1022 static void usbredir_ep_info(void *priv
,
1023 struct usb_redir_ep_info_header
*ep_info
)
1025 USBRedirDevice
*dev
= priv
;
1028 for (i
= 0; i
< MAX_ENDPOINTS
; i
++) {
1029 dev
->endpoint
[i
].type
= ep_info
->type
[i
];
1030 dev
->endpoint
[i
].interval
= ep_info
->interval
[i
];
1031 dev
->endpoint
[i
].interface
= ep_info
->interface
[i
];
1032 switch (dev
->endpoint
[i
].type
) {
1033 case usb_redir_type_invalid
:
1035 case usb_redir_type_iso
:
1036 case usb_redir_type_interrupt
:
1037 if (dev
->endpoint
[i
].interval
== 0) {
1038 ERROR("Received 0 interval for isoc or irq endpoint\n");
1039 usbredir_device_disconnect(dev
);
1042 case usb_redir_type_control
:
1043 case usb_redir_type_bulk
:
1044 DPRINTF("ep: %02X type: %d interface: %d\n", I2EP(i
),
1045 dev
->endpoint
[i
].type
, dev
->endpoint
[i
].interface
);
1048 ERROR("Received invalid endpoint type\n");
1049 usbredir_device_disconnect(dev
);
1054 static void usbredir_configuration_status(void *priv
, uint32_t id
,
1055 struct usb_redir_configuration_status_header
*config_status
)
1057 USBRedirDevice
*dev
= priv
;
1061 DPRINTF("set config status %d config %d id %u\n", config_status
->status
,
1062 config_status
->configuration
, id
);
1064 aurb
= async_find(dev
, id
);
1070 dev
->dev
.data_buf
[0] = config_status
->configuration
;
1073 aurb
->packet
->result
=
1074 usbredir_handle_status(dev
, config_status
->status
, len
);
1075 usb_generic_async_ctrl_complete(&dev
->dev
, aurb
->packet
);
1077 async_free(dev
, aurb
);
1080 static void usbredir_alt_setting_status(void *priv
, uint32_t id
,
1081 struct usb_redir_alt_setting_status_header
*alt_setting_status
)
1083 USBRedirDevice
*dev
= priv
;
1087 DPRINTF("alt status %d intf %d alt %d id: %u\n",
1088 alt_setting_status
->status
,
1089 alt_setting_status
->interface
,
1090 alt_setting_status
->alt
, id
);
1092 aurb
= async_find(dev
, id
);
1098 dev
->dev
.data_buf
[0] = alt_setting_status
->alt
;
1101 aurb
->packet
->result
=
1102 usbredir_handle_status(dev
, alt_setting_status
->status
, len
);
1103 usb_generic_async_ctrl_complete(&dev
->dev
, aurb
->packet
);
1105 async_free(dev
, aurb
);
1108 static void usbredir_iso_stream_status(void *priv
, uint32_t id
,
1109 struct usb_redir_iso_stream_status_header
*iso_stream_status
)
1111 USBRedirDevice
*dev
= priv
;
1112 uint8_t ep
= iso_stream_status
->endpoint
;
1114 DPRINTF("iso status %d ep %02X id %u\n", iso_stream_status
->status
,
1117 if (!dev
->dev
.attached
|| !dev
->endpoint
[EP2I(ep
)].iso_started
) {
1121 dev
->endpoint
[EP2I(ep
)].iso_error
= iso_stream_status
->status
;
1122 if (iso_stream_status
->status
== usb_redir_stall
) {
1123 DPRINTF("iso stream stopped by peer ep %02X\n", ep
);
1124 dev
->endpoint
[EP2I(ep
)].iso_started
= 0;
1128 static void usbredir_interrupt_receiving_status(void *priv
, uint32_t id
,
1129 struct usb_redir_interrupt_receiving_status_header
1130 *interrupt_receiving_status
)
1132 USBRedirDevice
*dev
= priv
;
1133 uint8_t ep
= interrupt_receiving_status
->endpoint
;
1135 DPRINTF("interrupt recv status %d ep %02X id %u\n",
1136 interrupt_receiving_status
->status
, ep
, id
);
1138 if (!dev
->dev
.attached
|| !dev
->endpoint
[EP2I(ep
)].interrupt_started
) {
1142 dev
->endpoint
[EP2I(ep
)].interrupt_error
=
1143 interrupt_receiving_status
->status
;
1144 if (interrupt_receiving_status
->status
== usb_redir_stall
) {
1145 DPRINTF("interrupt receiving stopped by peer ep %02X\n", ep
);
1146 dev
->endpoint
[EP2I(ep
)].interrupt_started
= 0;
1150 static void usbredir_bulk_streams_status(void *priv
, uint32_t id
,
1151 struct usb_redir_bulk_streams_status_header
*bulk_streams_status
)
1155 static void usbredir_control_packet(void *priv
, uint32_t id
,
1156 struct usb_redir_control_packet_header
*control_packet
,
1157 uint8_t *data
, int data_len
)
1159 USBRedirDevice
*dev
= priv
;
1160 int len
= control_packet
->length
;
1163 DPRINTF("ctrl-in status %d len %d id %u\n", control_packet
->status
,
1166 aurb
= async_find(dev
, id
);
1172 aurb
->control_packet
.status
= control_packet
->status
;
1173 aurb
->control_packet
.length
= control_packet
->length
;
1174 if (memcmp(&aurb
->control_packet
, control_packet
,
1175 sizeof(*control_packet
))) {
1176 ERROR("return control packet mismatch, please report this!\n");
1181 len
= usbredir_handle_status(dev
, control_packet
->status
, len
);
1183 usbredir_log_data(dev
, "ctrl data in:", data
, data_len
);
1184 if (data_len
<= sizeof(dev
->dev
.data_buf
)) {
1185 memcpy(dev
->dev
.data_buf
, data
, data_len
);
1187 ERROR("ctrl buffer too small (%d > %zu)\n",
1188 data_len
, sizeof(dev
->dev
.data_buf
));
1189 len
= USB_RET_STALL
;
1192 aurb
->packet
->result
= len
;
1193 usb_generic_async_ctrl_complete(&dev
->dev
, aurb
->packet
);
1195 async_free(dev
, aurb
);
1199 static void usbredir_bulk_packet(void *priv
, uint32_t id
,
1200 struct usb_redir_bulk_packet_header
*bulk_packet
,
1201 uint8_t *data
, int data_len
)
1203 USBRedirDevice
*dev
= priv
;
1204 uint8_t ep
= bulk_packet
->endpoint
;
1205 int len
= bulk_packet
->length
;
1208 DPRINTF("bulk-in status %d ep %02X len %d id %u\n", bulk_packet
->status
,
1211 aurb
= async_find(dev
, id
);
1217 if (aurb
->bulk_packet
.endpoint
!= bulk_packet
->endpoint
||
1218 aurb
->bulk_packet
.stream_id
!= bulk_packet
->stream_id
) {
1219 ERROR("return bulk packet mismatch, please report this!\n");
1224 len
= usbredir_handle_status(dev
, bulk_packet
->status
, len
);
1226 usbredir_log_data(dev
, "bulk data in:", data
, data_len
);
1227 if (data_len
<= aurb
->packet
->iov
.size
) {
1228 usb_packet_copy(aurb
->packet
, data
, data_len
);
1230 ERROR("bulk buffer too small (%d > %zd)\n", data_len
,
1231 aurb
->packet
->iov
.size
);
1232 len
= USB_RET_STALL
;
1235 aurb
->packet
->result
= len
;
1236 usb_packet_complete(&dev
->dev
, aurb
->packet
);
1238 async_free(dev
, aurb
);
1242 static void usbredir_iso_packet(void *priv
, uint32_t id
,
1243 struct usb_redir_iso_packet_header
*iso_packet
,
1244 uint8_t *data
, int data_len
)
1246 USBRedirDevice
*dev
= priv
;
1247 uint8_t ep
= iso_packet
->endpoint
;
1249 DPRINTF2("iso-in status %d ep %02X len %d id %u\n", iso_packet
->status
, ep
,
1252 if (dev
->endpoint
[EP2I(ep
)].type
!= USB_ENDPOINT_XFER_ISOC
) {
1253 ERROR("received iso packet for non iso endpoint %02X\n", ep
);
1258 if (dev
->endpoint
[EP2I(ep
)].iso_started
== 0) {
1259 DPRINTF("received iso packet for non started stream ep %02X\n", ep
);
1264 /* bufp_alloc also adds the packet to the ep queue */
1265 bufp_alloc(dev
, data
, data_len
, iso_packet
->status
, ep
);
1268 static void usbredir_interrupt_packet(void *priv
, uint32_t id
,
1269 struct usb_redir_interrupt_packet_header
*interrupt_packet
,
1270 uint8_t *data
, int data_len
)
1272 USBRedirDevice
*dev
= priv
;
1273 uint8_t ep
= interrupt_packet
->endpoint
;
1275 DPRINTF("interrupt-in status %d ep %02X len %d id %u\n",
1276 interrupt_packet
->status
, ep
, data_len
, id
);
1278 if (dev
->endpoint
[EP2I(ep
)].type
!= USB_ENDPOINT_XFER_INT
) {
1279 ERROR("received int packet for non interrupt endpoint %02X\n", ep
);
1284 if (ep
& USB_DIR_IN
) {
1285 if (dev
->endpoint
[EP2I(ep
)].interrupt_started
== 0) {
1286 DPRINTF("received int packet while not started ep %02X\n", ep
);
1291 /* bufp_alloc also adds the packet to the ep queue */
1292 bufp_alloc(dev
, data
, data_len
, interrupt_packet
->status
, ep
);
1294 int len
= interrupt_packet
->length
;
1296 AsyncURB
*aurb
= async_find(dev
, id
);
1301 if (aurb
->interrupt_packet
.endpoint
!= interrupt_packet
->endpoint
) {
1302 ERROR("return int packet mismatch, please report this!\n");
1307 aurb
->packet
->result
= usbredir_handle_status(dev
,
1308 interrupt_packet
->status
, len
);
1309 usb_packet_complete(&dev
->dev
, aurb
->packet
);
1311 async_free(dev
, aurb
);
1315 static struct USBDeviceInfo usbredir_dev_info
= {
1316 .product_desc
= "USB Redirection Device",
1317 .qdev
.name
= "usb-redir",
1318 .qdev
.size
= sizeof(USBRedirDevice
),
1319 .init
= usbredir_initfn
,
1320 .handle_destroy
= usbredir_handle_destroy
,
1321 .handle_packet
= usb_generic_handle_packet
,
1322 .cancel_packet
= usbredir_cancel_packet
,
1323 .handle_reset
= usbredir_handle_reset
,
1324 .handle_data
= usbredir_handle_data
,
1325 .handle_control
= usbredir_handle_control
,
1326 .qdev
.props
= (Property
[]) {
1327 DEFINE_PROP_CHR("chardev", USBRedirDevice
, cs
),
1328 DEFINE_PROP_UINT8("debug", USBRedirDevice
, debug
, 0),
1329 DEFINE_PROP_END_OF_LIST(),
1333 static void usbredir_register_devices(void)
1335 usb_qdev_register(&usbredir_dev_info
);
1337 device_init(usbredir_register_devices
);