aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rwxr-xr-xconfigure2
-rw-r--r--hw/usb/bus.c36
-rw-r--r--hw/usb/desc.c2
-rw-r--r--hw/usb/hcd-ehci.c16
-rw-r--r--hw/usb/hcd-xhci.c4
-rw-r--r--hw/usb/host-libusb.c5
-rw-r--r--trace-events2
7 files changed, 46 insertions, 21 deletions
diff --git a/configure b/configure
index 51a6c56..33d3354 100755
--- a/configure
+++ b/configure
@@ -3060,7 +3060,7 @@ fi
# check for libusb
if test "$libusb" != "no" ; then
- if $pkg_config libusb-1.0 >/dev/null 2>&1 ; then
+ if $pkg_config --atleast-version=1.0.13 libusb-1.0 >/dev/null 2>&1 ; then
libusb="yes"
usb="libusb"
libusb_cflags=$($pkg_config --cflags libusb-1.0 2>/dev/null)
diff --git a/hw/usb/bus.c b/hw/usb/bus.c
index b10c290..d1827be 100644
--- a/hw/usb/bus.c
+++ b/hw/usb/bus.c
@@ -417,19 +417,47 @@ void usb_release_port(USBDevice *dev)
bus->nfree++;
}
+static void usb_mask_to_str(char *dest, size_t size,
+ unsigned int speedmask)
+{
+ static const struct {
+ unsigned int mask;
+ const char *name;
+ } speeds[] = {
+ { .mask = USB_SPEED_MASK_FULL, .name = "full" },
+ { .mask = USB_SPEED_MASK_HIGH, .name = "high" },
+ { .mask = USB_SPEED_MASK_SUPER, .name = "super" },
+ };
+ int i, pos = 0;
+
+ for (i = 0; i < ARRAY_SIZE(speeds); i++) {
+ if (speeds[i].mask & speedmask) {
+ pos += snprintf(dest + pos, size - pos, "%s%s",
+ pos ? "+" : "",
+ speeds[i].name);
+ }
+ }
+}
+
int usb_device_attach(USBDevice *dev)
{
USBBus *bus = usb_bus_from_device(dev);
USBPort *port = dev->port;
+ char devspeed[32], portspeed[32];
assert(port != NULL);
assert(!dev->attached);
- trace_usb_port_attach(bus->busnr, port->path);
+ usb_mask_to_str(devspeed, sizeof(devspeed), dev->speedmask);
+ usb_mask_to_str(portspeed, sizeof(portspeed), port->speedmask);
+ trace_usb_port_attach(bus->busnr, port->path,
+ devspeed, portspeed);
if (!(port->speedmask & dev->speedmask)) {
- error_report("Warning: speed mismatch trying to attach "
- "usb device %s to bus %s",
- dev->product_desc, bus->qbus.name);
+ error_report("Warning: speed mismatch trying to attach"
+ " usb device \"%s\" (%s speed)"
+ " to bus \"%s\", port \"%s\" (%s speed)",
+ dev->product_desc, devspeed,
+ bus->qbus.name, port->path, portspeed);
return -1;
}
diff --git a/hw/usb/desc.c b/hw/usb/desc.c
index b389381..fce303e 100644
--- a/hw/usb/desc.c
+++ b/hw/usb/desc.c
@@ -522,8 +522,6 @@ void usb_desc_attach(USBDevice *dev)
} else if (desc->full && (dev->port->speedmask & USB_SPEED_MASK_FULL)) {
dev->speed = USB_SPEED_FULL;
} else {
- fprintf(stderr, "usb: port/device speed mismatch for \"%s\"\n",
- usb_device_get_product_desc(dev));
return;
}
usb_desc_setdefaults(dev);
diff --git a/hw/usb/hcd-ehci.c b/hw/usb/hcd-ehci.c
index 5176251..0d3799d 100644
--- a/hw/usb/hcd-ehci.c
+++ b/hw/usb/hcd-ehci.c
@@ -586,17 +586,23 @@ static EHCIPacket *ehci_alloc_packet(EHCIQueue *q)
static void ehci_free_packet(EHCIPacket *p)
{
- if (p->async == EHCI_ASYNC_FINISHED) {
+ if (p->async == EHCI_ASYNC_FINISHED &&
+ !(p->queue->qh.token & QTD_TOKEN_HALT)) {
ehci_writeback_async_complete_packet(p);
return;
}
trace_usb_ehci_packet_action(p->queue, p, "free");
- if (p->async == EHCI_ASYNC_INITIALIZED) {
- usb_packet_unmap(&p->packet, &p->sgl);
- qemu_sglist_destroy(&p->sgl);
- }
if (p->async == EHCI_ASYNC_INFLIGHT) {
usb_cancel_packet(&p->packet);
+ }
+ if (p->async == EHCI_ASYNC_FINISHED &&
+ p->packet.status == USB_RET_SUCCESS) {
+ fprintf(stderr,
+ "EHCI: Dropping completed packet from halted %s ep %02X\n",
+ (p->pid == USB_TOKEN_IN) ? "in" : "out",
+ get_field(p->queue->qh.epchar, QH_EPCHAR_EP));
+ }
+ if (p->async != EHCI_ASYNC_NONE) {
usb_packet_unmap(&p->packet, &p->sgl);
qemu_sglist_destroy(&p->sgl);
}
diff --git a/hw/usb/hcd-xhci.c b/hw/usb/hcd-xhci.c
index a26b78e..2c90e56 100644
--- a/hw/usb/hcd-xhci.c
+++ b/hw/usb/hcd-xhci.c
@@ -326,7 +326,6 @@ typedef enum EPType {
} EPType;
typedef struct XHCIRing {
- dma_addr_t base;
dma_addr_t dequeue;
bool ccs;
} XHCIRing;
@@ -943,7 +942,6 @@ static void xhci_event(XHCIState *xhci, XHCIEvent *event, int v)
static void xhci_ring_init(XHCIState *xhci, XHCIRing *ring,
dma_addr_t base)
{
- ring->base = base;
ring->dequeue = base;
ring->ccs = 1;
}
@@ -1948,7 +1946,7 @@ static void xhci_kick_ep(XHCIState *xhci, unsigned int slotid,
streamid = 0;
xhci_set_ep_state(xhci, epctx, NULL, EP_RUNNING);
}
- assert(ring->base != 0);
+ assert(ring->dequeue != 0);
while (1) {
XHCITransfer *xfer = &epctx->transfers[epctx->next_xfer];
diff --git a/hw/usb/host-libusb.c b/hw/usb/host-libusb.c
index 29f35b3..d1186b8 100644
--- a/hw/usb/host-libusb.c
+++ b/hw/usb/host-libusb.c
@@ -236,8 +236,6 @@ static int usb_host_init(void)
static int usb_host_get_port(libusb_device *dev, char *port, size_t len)
{
-#if defined(LIBUSBX_API_VERSION) && (LIBUSBX_API_VERSION >= 0x010000ff)
- /* have libusb_get_port_path() */
uint8_t path[7];
size_t off;
int rc, i;
@@ -251,9 +249,6 @@ static int usb_host_get_port(libusb_device *dev, char *port, size_t len)
off += snprintf(port+off, len-off, ".%d", path[i]);
}
return off;
-#else
- return snprintf(port, len, "FIXME");
-#endif
}
static void usb_host_libusb_error(const char *func, int rc)
diff --git a/trace-events b/trace-events
index e587487..ffaa3f4 100644
--- a/trace-events
+++ b/trace-events
@@ -277,7 +277,7 @@ usb_packet_state_fault(int bus, const char *port, int ep, void *p, const char *o
# hw/usb/bus.c
usb_port_claim(int bus, const char *port) "bus %d, port %s"
-usb_port_attach(int bus, const char *port) "bus %d, port %s"
+usb_port_attach(int bus, const char *port, const char *devspeed, const char *portspeed) "bus %d, port %s, devspeed %s, portspeed %s"
usb_port_detach(int bus, const char *port) "bus %d, port %s"
usb_port_release(int bus, const char *port) "bus %d, port %s"