tech-kern archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

Re: Patch: xhci controller driver improvements



Hi,

On 09/24/14 23:45, Takahiro HAYASHI wrote:
On 09/20/14 16:12, Nick Hudson wrote:
Hi,

Can you convert the DPRINTFs to USBHIST_LOG, please?

Yes, I'll try to do.

Here:

kernhist.diff.txt
	replaces device_printf and DPRINTF family with KERNHIST.
	Some printf that have more than 4 args are splitted.

other patches attached are:

rhdesc.diff.txt
	converts to use c99 struct initializer for root hub
	declarations.

usb.h.diff.txt
	adds some descriptor declarations, mainly BOS desc.

xhcireg.h.diff.txt
	adds some registers about extended capabilities and
	definitions about slot/endpoint states.

detach.diff.txt
	avoids null dereference when rebooting if xhci_init fails
	(e.g. fails to reset controller),
	and destroys cv when detach.


Regards,
--
t-hash
--- src/sys/dev/usb/xhci.c.orig	2014-08-12 23:29:37.000000000 +0900
+++ src/sys/dev/usb/xhci.c	2014-09-25 21:23:07.000000000 +0900
@@ -29,6 +29,9 @@
 #include <sys/cdefs.h>
 __KERNEL_RCSID(0, "$NetBSD: xhci.c,v 1.26 2014/08/12 13:50:42 skrll Exp $");
 
+#include "xhci.h"
+#include "opt_usb.h"
+
 #include <sys/param.h>
 #include <sys/systm.h>
 #include <sys/kernel.h>
@@ -42,12 +45,16 @@ __KERNEL_RCSID(0, "$NetBSD: xhci.c,v 1.2
 #include <sys/condvar.h>
 #include <sys/bus.h>
 #include <sys/cpu.h>
+#include <sys/sysctl.h>
 
 #include <machine/endian.h>
 
+/* #define KERNHIST_DELAY 0 */
+
 #include <dev/usb/usb.h>
 #include <dev/usb/usbdi.h>
 #include <dev/usb/usbdivar.h>
+#include <dev/usb/usbhist.h>
 #include <dev/usb/usb_mem.h>
 #include <dev/usb/usb_quirks.h>
 
@@ -55,30 +62,63 @@ __KERNEL_RCSID(0, "$NetBSD: xhci.c,v 1.2
 #include <dev/usb/xhcivar.h>
 #include <dev/usb/usbroothub_subr.h>
 
-#ifdef XHCI_DEBUG
-int xhcidebug = 0;
-#define DPRINTF(x)	do { if (xhcidebug) printf x; } while(0)
-#define DPRINTFN(n,x)	do { if (xhcidebug>(n)) printf x; } while (0)
+
+#ifdef USB_DEBUG
+#ifndef XHCI_DEBUG
+#define xhcidebug 0
 #else
-#define DPRINTF(x)
-#define DPRINTFN(n,x)
-#endif
+static int xhcidebug = 0;
+
+SYSCTL_SETUP(sysctl_hw_xhci_setup, "sysctl hw.xhci setup")
+{
+	int err;
+	const struct sysctlnode *rnode;
+	const struct sysctlnode *cnode;
+
+	err = sysctl_createv(clog, 0, NULL, &rnode,
+	    CTLFLAG_PERMANENT, CTLTYPE_NODE, "xhci",
+	    SYSCTL_DESCR("xhci global controls"),
+	    NULL, 0, NULL, 0, CTL_HW, CTL_CREATE, CTL_EOL);
+
+	if (err)
+		goto fail;
+
+	/* control debugging printfs */
+	err = sysctl_createv(clog, 0, &rnode, &cnode,
+	    CTLFLAG_PERMANENT|CTLFLAG_READWRITE, CTLTYPE_INT,
+	    "debug", SYSCTL_DESCR("Enable debugging output"),
+	    NULL, 0, &xhcidebug, sizeof(xhcidebug), CTL_CREATE, CTL_EOL);
+	if (err)
+		goto fail;
+
+	return;
+fail:
+	aprint_error("%s: sysctl_createv failed (err = %d)\n", __func__, err);
+}
+
+#endif /* XHCI_DEBUG */
+#endif /* USB_DEBUG */
+
+#define DPRINTFN(N,FMT,A,B,C,D) USBHIST_LOGN(xhcidebug,N,FMT,A,B,C,D)
+#define XHCIHIST_FUNC() USBHIST_FUNC()
+#define XHCIHIST_CALLED(name) USBHIST_CALLED(xhcidebug)
+
 
 #define XHCI_DCI_SLOT 0
 #define XHCI_DCI_EP_CONTROL 1
 
 #define XHCI_ICI_INPUT_CONTROL 0
 
-struct xhci_pipe {
-	struct usbd_pipe xp_pipe;
-};
-
 #define XHCI_INTR_ENDPT 1
 #define XHCI_COMMAND_RING_TRBS 256
 #define XHCI_EVENT_RING_TRBS 256
 #define XHCI_EVENT_RING_SEGMENTS 1
 #define XHCI_TRB_3_ED_BIT XHCI_TRB_3_ISP_BIT
 
+struct xhci_pipe {
+	struct usbd_pipe xp_pipe;
+};
+
 static usbd_status xhci_open(usbd_pipe_handle);
 static int xhci_intr1(struct xhci_softc * const);
 static void xhci_softintr(void *);
@@ -577,7 +617,7 @@ xhci_init(struct xhci_softc *sc)
 	uint16_t hciversion;
 	uint8_t caplength;
 
-	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 	/* XXX Low/Full/High speeds for now */
 	sc->sc_bus.usbrev = USBREV_2_0;
@@ -855,6 +895,8 @@ xhci_intr(void *v)
 	struct xhci_softc * const sc = v;
 	int ret = 0;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	if (sc == NULL)
 		return 0;
 
@@ -863,12 +905,10 @@ xhci_intr(void *v)
 	if (sc->sc_dying || !device_has_power(sc->sc_dev))
 		goto done;
 
-	DPRINTF(("%s: %s\n", __func__, device_xname(sc->sc_dev)));
-
 	/* If we get an interrupt while polling, then just ignore it. */
 	if (sc->sc_bus.use_polling) {
 #ifdef DIAGNOSTIC
-		DPRINTFN(16, ("xhci_intr: ignored interrupt while polling\n"));
+		DPRINTFN(16, "ignored interrupt while polling", 0, 0, 0, 0);
 #endif
 		goto done;
 	}
@@ -885,8 +925,10 @@ xhci_intr1(struct xhci_softc * const sc)
 	uint32_t usbsts;
 	uint32_t iman;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	usbsts = xhci_op_read_4(sc, XHCI_USBSTS);
-	//device_printf(sc->sc_dev, "%s USBSTS %08x\n", __func__, usbsts);
+	//DPRINTFN(16, "USBSTS %08x", usbsts, 0, 0, 0);
 #if 0
 	if ((usbsts & (XHCI_STS_EINT|XHCI_STS_PCD)) == 0) {
 		return 0;
@@ -895,18 +937,18 @@ xhci_intr1(struct xhci_softc * const sc)
 	xhci_op_write_4(sc, XHCI_USBSTS,
 	    usbsts & (2|XHCI_STS_EINT|XHCI_STS_PCD)); /* XXX */
 	usbsts = xhci_op_read_4(sc, XHCI_USBSTS);
-	//device_printf(sc->sc_dev, "%s USBSTS %08x\n", __func__, usbsts);
+	//DPRINTFN(16, "USBSTS %08x", usbsts, 0, 0, 0);
 
 	iman = xhci_rt_read_4(sc, XHCI_IMAN(0));
-	//device_printf(sc->sc_dev, "%s IMAN0 %08x\n", __func__, iman);
+	//DPRINTFN(16, "IMAN0 %08x", iman, 0, 0, 0);
 	if ((iman & XHCI_IMAN_INTR_PEND) == 0) {
 		return 0;
 	}
 	xhci_rt_write_4(sc, XHCI_IMAN(0), iman);
 	iman = xhci_rt_read_4(sc, XHCI_IMAN(0));
-	//device_printf(sc->sc_dev, "%s IMAN0 %08x\n", __func__, iman);
+	//DPRINTFN(16, "IMAN0 %08x", iman, 0, 0, 0);
 	usbsts = xhci_op_read_4(sc, XHCI_USBSTS);
-	//device_printf(sc->sc_dev, "%s USBSTS %08x\n", __func__, usbsts);
+	//DPRINTFN(16, "USBSTS %08x", usbsts, 0, 0, 0);
 
 	sc->sc_bus.no_intrs++;
 	usb_schedsoftintr(&sc->sc_bus);
@@ -926,8 +968,9 @@ xhci_configure_endpoint(usbd_pipe_handle
 	usbd_status err;
 	uint32_t *cp;
 
-	device_printf(sc->sc_dev, "%s dci %u (0x%x)\n", __func__, dci,
-	    pipe->endpoint->edesc->bEndpointAddress);
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(4, "dci %u epaddr 0x%02x attr 0x%02x",
+	    dci, ed->bEndpointAddress, ed->bmAttributes, 0);
 
 	/* XXX ensure input context is available? */
 
@@ -995,6 +1038,9 @@ xhci_configure_endpoint(usbd_pipe_handle
 static usbd_status
 xhci_unconfigure_endpoint(usbd_pipe_handle pipe)
 {
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+//	DPRINTFN(4, "slot %u", xs->xs_idx, 0, 0, 0);
+
 	return USBD_NORMAL_COMPLETION;
 }
 
@@ -1007,7 +1053,8 @@ xhci_reset_endpoint(usbd_pipe_handle pip
 	struct xhci_trb trb;
 	usbd_status err;
 
-	device_printf(sc->sc_dev, "%s\n", __func__);
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(4, "dci %u\n", dci, 0, 0, 0);
 
 	trb.trb_0 = 0;
 	trb.trb_2 = 0;
@@ -1030,7 +1077,8 @@ xhci_stop_endpoint(usbd_pipe_handle pipe
 	usbd_status err;
 	const u_int dci = xhci_ep_get_dci(pipe->endpoint->edesc);
 
-	device_printf(sc->sc_dev, "%s\n", __func__);
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(4, "dci %u\n", dci, 0, 0, 0);
 
 	trb.trb_0 = 0;
 	trb.trb_2 = 0;
@@ -1054,7 +1102,8 @@ xhci_set_dequeue(usbd_pipe_handle pipe)
 	struct xhci_trb trb;
 	usbd_status err;
 
-	device_printf(sc->sc_dev, "%s\n", __func__);
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(4, "slot %u dci %u", xs->xs_idx, dci, 0, 0);
 
 	memset(xr->xr_trb, 0, xr->xr_ntrb * XHCI_TRB_SIZE);
 	usb_syncmem(&xr->xr_dma, 0, xr->xr_ntrb * XHCI_TRB_SIZE,
@@ -1080,13 +1129,11 @@ xhci_open(usbd_pipe_handle pipe)
 	usbd_device_handle const dev = pipe->device;
 	struct xhci_softc * const sc = dev->bus->hci_private;
 	usb_endpoint_descriptor_t * const ed = pipe->endpoint->edesc;
-	const int8_t addr = dev->address;
 	const uint8_t xfertype = UE_GET_XFERTYPE(ed->bmAttributes);
 
-	DPRINTF(("%s\n", __func__));
-	DPRINTF(("addr %d\n", addr));
-	device_printf(sc->sc_dev, "%s addr %d depth %d port %d speed %d\n",
-	    __func__, addr, dev->depth, dev->powersrc->portno, dev->speed);
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(1, "addr %d depth %d port %d speed %d",
+	    dev->address, dev->depth, dev->powersrc->portno, dev->speed);
 
 	if (sc->sc_dying)
 		return USBD_IOERROR;
@@ -1103,8 +1150,8 @@ xhci_open(usbd_pipe_handle pipe)
 			break;
 		default:
 			pipe->methods = NULL;
-			DPRINTF(("xhci_open: bad bEndpointAddress 0x%02x\n",
-			    ed->bEndpointAddress));
+			DPRINTFN(0, "bad bEndpointAddress 0x%02x",
+			    ed->bEndpointAddress, 0, 0, 0);
 			return USBD_INVAL;
 		}
 		return USBD_NORMAL_COMPLETION;
@@ -1141,7 +1188,8 @@ xhci_rhpsc(struct xhci_softc * const sc,
 	usbd_xfer_handle const xfer = sc->sc_intrxfer;
 	uint8_t *p;
 
-	device_printf(sc->sc_dev, "port %u status change\n", port);
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(4, "port %u status change", port, 0, 0, 0);
 
 	if (xfer == NULL)
 		return;
@@ -1152,7 +1200,7 @@ xhci_rhpsc(struct xhci_softc * const sc,
 
 	port -= sc->sc_hs_port_start;
 	port += 1;
-	device_printf(sc->sc_dev, "hs port %u status change\n", port);
+	DPRINTFN(4, "hs port %u status change", port, 0, 0, 0);
 
 	p = KERNADDR(&xfer->dmabuf, 0);
 	memset(p, 0, xfer->length);
@@ -1163,21 +1211,21 @@ xhci_rhpsc(struct xhci_softc * const sc,
 }
 
 static void
-xhci_handle_event(struct xhci_softc * const sc, const struct xhci_trb * const trb)
+xhci_handle_event(struct xhci_softc * const sc,
+    const struct xhci_trb * const trb)
 {
 	uint64_t trb_0;
 	uint32_t trb_2, trb_3;
 
-	DPRINTF(("%s: %s\n", __func__, device_xname(sc->sc_dev)));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 	trb_0 = le64toh(trb->trb_0);
 	trb_2 = le32toh(trb->trb_2);
 	trb_3 = le32toh(trb->trb_3);
 
 #if 0
-	device_printf(sc->sc_dev,
-	    "event: %p 0x%016"PRIx64" 0x%08"PRIx32" 0x%08"PRIx32"\n", trb,
-	    trb_0, trb_2, trb_3);
+	DPRINTFN(14, "event: %p 0x%016"PRIx64" 0x%08"PRIx32" 0x%08"PRIx32,
+	    trb, trb_0, trb_2, trb_3);
 #endif
 
 	switch (XHCI_TRB_3_TYPE_GET(trb_3)){
@@ -1203,15 +1251,15 @@ xhci_handle_event(struct xhci_softc * co
 		}
 		xfer = &xx->xx_xfer;
 #if 0
-		device_printf(sc->sc_dev, "%s xfer %p\n", __func__, xfer);
+		DPRINTFN(14, "xfer %p", xfer, 0, 0, 0);
 #endif
 
 		if ((trb_3 & XHCI_TRB_3_ED_BIT) != 0) {
 #if 0
-			device_printf(sc->sc_dev, "transfer event data: "
-			    "0x%016"PRIx64" 0x%08"PRIx32" %02x\n",
+			DPRINTFN(14, "transfer event data: "
+			    "0x%016"PRIx64" 0x%08"PRIx32" %02x",
 			    trb_0, XHCI_TRB_2_REM_GET(trb_2),
-			    XHCI_TRB_2_ERROR_GET(trb_2));
+			    XHCI_TRB_2_ERROR_GET(trb_2), 0);
 #endif
 			if ((trb_0 & 0x3) == 0x3) {
 				xfer->actlen = XHCI_TRB_2_REM_GET(trb_2);
@@ -1230,6 +1278,8 @@ xhci_handle_event(struct xhci_softc * co
 		    XHCI_TRB_ERROR_STALL) {
 			err = USBD_STALLED;
 			xr->is_halted = true;
+			DPRINTFN(1, "ev: xfer done: err %u slot %u dci %u\n",
+			    XHCI_TRB_2_ERROR_GET(trb_2), slot, dci, 0);
 		} else {
 			err = USBD_IOERROR;
 		}
@@ -1254,14 +1304,14 @@ xhci_handle_event(struct xhci_softc * co
 			sc->sc_result_trb.trb_3 = trb_3;
 			if (XHCI_TRB_2_ERROR_GET(trb_2) !=
 			    XHCI_TRB_ERROR_SUCCESS) {
-				device_printf(sc->sc_dev, "command completion "
+				DPRINTFN(1, "command completion "
 				    "failure: 0x%016"PRIx64" 0x%08"PRIx32" "
-				    "0x%08"PRIx32"\n", trb_0, trb_2, trb_3);
+				    "0x%08"PRIx32, trb_0, trb_2, trb_3, 0);
 			}
 			cv_signal(&sc->sc_command_cv);
 		} else {
-			device_printf(sc->sc_dev, "event: %p 0x%016"PRIx64" "
-			    "0x%08"PRIx32" 0x%08"PRIx32"\n", trb, trb_0,
+			DPRINTFN(1, "event: %p 0x%016"PRIx64" "
+			    "0x%08"PRIx32" 0x%08"PRIx32, trb, trb_0,
 			    trb_2, trb_3);
 		}
 		break;
@@ -1282,11 +1332,13 @@ xhci_softintr(void *v)
 	struct xhci_trb *trb;
 	int i, j, k;
 
-	DPRINTF(("%s: %s\n", __func__, device_xname(sc->sc_dev)));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 	i = er->xr_ep;
 	j = er->xr_cs;
 
+	DPRINTFN(16, "xr_ep %d xr_cs %d", i, j, 0, 0);
+
 	while (1) {
 		usb_syncmem(&er->xr_dma, XHCI_TRB_SIZE * i, XHCI_TRB_SIZE,
 		    BUS_DMASYNC_POSTREAD);
@@ -1311,7 +1363,7 @@ xhci_softintr(void *v)
 	xhci_rt_write_8(sc, XHCI_ERDP(0), xhci_ring_trbp(er, er->xr_ep) |
 	    XHCI_ERDP_LO_BUSY);
 
-	DPRINTF(("%s: %s ends\n", __func__, device_xname(sc->sc_dev)));
+	DPRINTFN(16, "ends", 0, 0, 0, 0);
 
 	return;
 }
@@ -1321,7 +1373,7 @@ xhci_poll(struct usbd_bus *bus)
 {
 	struct xhci_softc * const sc = bus->hci_private;
 
-	DPRINTF(("%s: %s\n", __func__, device_xname(sc->sc_dev)));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 	mutex_spin_enter(&sc->sc_intr_lock);
 	xhci_intr1(sc);
@@ -1336,7 +1388,7 @@ xhci_allocm(struct usbd_bus *bus, usb_dm
 	struct xhci_softc * const sc = bus->hci_private;
 	usbd_status err;
 
-	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 	err = usb_allocmem_flags(&sc->sc_bus, size, 0, dma, 0);
 #if 0
@@ -1345,8 +1397,7 @@ xhci_allocm(struct usbd_bus *bus, usb_dm
 #endif
 #ifdef XHCI_DEBUG
 	if (err)
-		device_printf(sc->sc_dev, "xhci_allocm: usb_allocmem()=%d\n",
-		    err);
+		DPRINTFN(1, "usb_allocmem(%u)=%d", err, size, 0, 0);
 #endif
 
 	return err;
@@ -1357,7 +1408,7 @@ xhci_freem(struct usbd_bus *bus, usb_dma
 {
 	struct xhci_softc * const sc = bus->hci_private;
 
-//	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 #if 0
 	if (dma->block->flags & USB_DMA_RESERVE) {
@@ -1374,7 +1425,7 @@ xhci_allocx(struct usbd_bus *bus)
 	struct xhci_softc * const sc = bus->hci_private;
 	usbd_xfer_handle xfer;
 
-//	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 	xfer = pool_cache_get(sc->sc_xferpool, PR_NOWAIT);
 	if (xfer != NULL) {
@@ -1392,12 +1443,12 @@ xhci_freex(struct usbd_bus *bus, usbd_xf
 {
 	struct xhci_softc * const sc = bus->hci_private;
 
-//	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 #ifdef DIAGNOSTIC
 	if (xfer->busy_free != XFER_BUSY) {
-		device_printf(sc->sc_dev, "xhci_freex: xfer=%p "
-		    "not busy, 0x%08x\n", xfer, xfer->busy_free);
+		DPRINTFN(0, "xfer=%p not busy, 0x%08x",
+		    xfer, xfer->busy_free, 0, 0);
 	}
 	xfer->busy_free = XFER_FREE;
 #endif
@@ -1430,6 +1481,10 @@ xhci_new_device(device_t parent, usbd_bu
 	uint8_t slot;
 	uint8_t addr;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(4, "port=%d depth=%d speed=%d upport %d",
+		 port, depth, speed, up->portno);
+
 	dev = malloc(sizeof *dev, M_USB, M_NOWAIT|M_ZERO);
 	if (dev == NULL)
 		return USBD_NOMEM;
@@ -1454,8 +1509,7 @@ xhci_new_device(device_t parent, usbd_bu
 	/* doesn't matter, just don't let it uninitialized */
 	dev->def_ep.datatoggle = 0;
 
-	device_printf(sc->sc_dev, "%s up %p portno %d\n", __func__, up,
-	    up->portno);
+	DPRINTFN(4, "up %p portno %d", up, up->portno, 0, 0);
 
 	dev->quirks = &usbd_no_quirk;
 	dev->address = 0;
@@ -1470,9 +1524,9 @@ xhci_new_device(device_t parent, usbd_bu
 	for (adev = dev, hub = dev;
 	    hub != NULL;
 	    adev = hub, hub = hub->myhub) {
-		device_printf(sc->sc_dev, "%s hub %p\n", __func__, hub);
+		DPRINTFN(4, "hub %p", hub, 0, 0, 0);
 	}
-	device_printf(sc->sc_dev, "%s hub %p\n", __func__, hub);
+	DPRINTFN(4, "hub %p", hub, 0, 0, 0);
 
 	if (hub != NULL) {
 		for (int p = 0; p < hub->hub->hubdesc.bNbrPorts; p++) {
@@ -1488,7 +1542,7 @@ xhci_new_device(device_t parent, usbd_bu
 	} else {
 		rhport += sc->sc_hs_port_start - 1;
 	}
-	device_printf(sc->sc_dev, "%s rhport %d\n", __func__, rhport);
+	DPRINTFN(4, "rhport %d", rhport, 0, 0, 0);
 
 	dev->speed = speed;
 	dev->langid = USBD_NOLANG;
@@ -1525,8 +1579,7 @@ xhci_new_device(device_t parent, usbd_bu
 		cp = xhci_slot_get_dcv(sc, xs, XHCI_DCI_SLOT);
 		//hexdump("slot context", cp, sc->sc_ctxsz);
 		addr = XHCI_SCTX_3_DEV_ADDR_GET(cp[3]);
-		device_printf(sc->sc_dev, "%s device address %u\n",
-		    __func__, addr);
+		DPRINTFN(4, "device address %u", addr, 0, 0, 0);
 		/* XXX ensure we know when the hardware does something
 		   we can't yet cope with */
 		KASSERT(addr >= 1 && addr <= 127);
@@ -1545,8 +1598,7 @@ xhci_new_device(device_t parent, usbd_bu
 		else
 	 		USETW(dev->def_ep_desc.wMaxPacketSize,
 			    dd->bMaxPacketSize);
-		device_printf(sc->sc_dev, "%s bMaxPacketSize %u\n", __func__,
-		    dd->bMaxPacketSize);
+		DPRINTFN(4, "bMaxPacketSize %u", dd->bMaxPacketSize, 0, 0, 0);
 		xhci_update_ep0_mps(sc, xs,
 		    UGETW(dev->def_ep_desc.wMaxPacketSize));
 		err = usbd_reload_device_desc(dev);
@@ -1558,18 +1610,20 @@ xhci_new_device(device_t parent, usbd_bu
 		    USBD_DEFAULT_INTERVAL, &dev->default_pipe);
 	}
 
-	DPRINTF(("usbd_new_device: adding unit addr=%d, rev=%02x, class=%d, "
-		 "subclass=%d, protocol=%d, maxpacket=%d, len=%d, noconf=%d, "
-		 "speed=%d\n", dev->address,UGETW(dd->bcdUSB),
-		 dd->bDeviceClass, dd->bDeviceSubClass, dd->bDeviceProtocol,
-		 dd->bMaxPacketSize, dd->bLength, dd->bNumConfigurations,
-		 dev->speed));
+	DPRINTFN(1, "adding unit addr=%d, rev=%02x,",
+		dev->address, UGETW(dd->bcdUSB), 0, 0);
+	DPRINTFN(1, " class=%d, subclass=%d, protocol=%d,",
+		dd->bDeviceClass, dd->bDeviceSubClass,
+		dd->bDeviceProtocol, 0);
+	DPRINTFN(1, " mps=%d, len=%d, noconf=%d, speed=%d",
+		dd->bMaxPacketSize, dd->bLength, dd->bNumConfigurations,
+		dev->speed);
 
 	usbd_add_dev_event(USB_EVENT_DEVICE_ATTACH, dev);
 
 	if ((depth == 0) && (port == 0)) {
 		usbd_attach_roothub(parent, dev);
-		device_printf(sc->sc_dev, "root_hub %p\n", bus->root_hub);
+		DPRINTFN(1, "root_hub %p", bus->root_hub, 0, 0, 0);
 		return USBD_NORMAL_COMPLETION;
 	}
 
@@ -1590,6 +1644,8 @@ xhci_ring_init(struct xhci_softc * const
 	usbd_status err;
 	size_t size = ntrb * XHCI_TRB_SIZE;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	err = usb_allocmem(&sc->sc_bus, size, align, &xr->xr_dma);
 	if (err)
 		return err;
@@ -1625,19 +1681,20 @@ xhci_ring_put(struct xhci_softc * const 
 	uint32_t status;
 	uint32_t control;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	for (i = 0; i < ntrbs; i++) {
 #if 0
-		device_printf(sc->sc_dev, "%s %p %p %zu "
-		    "%016"PRIx64" %08"PRIx32" %08"PRIx32"\n", __func__, xr,
-		    trbs, i, trbs[i].trb_0, trbs[i].trb_2, trbs[i].trb_3);
+		DPRINTFN(12, "xr %p trbs %p num %zu", xr, trbs, i, 0);
+		DPRINTFN(12, " %016"PRIx64" %08"PRIx32" %08"PRIx32,
+		    trbs[i].trb_0, trbs[i].trb_2, trbs[i].trb_3, 0);
 #endif
 		KASSERT(XHCI_TRB_3_TYPE_GET(trbs[i].trb_3) !=
 		    XHCI_TRB_TYPE_LINK);
 	}
 
 #if 0
-	device_printf(sc->sc_dev, "%s %p xr_ep 0x%x xr_cs %u\n", __func__,
-	    xr, xr->xr_ep, xr->xr_cs);
+	DPRINTFN(12, "%p xr_ep 0x%x xr_cs %u", xr, xr->xr_ep, xr->xr_cs, 0);
 #endif
 
 	ri = xr->xr_ep;
@@ -1719,8 +1776,7 @@ xhci_ring_put(struct xhci_softc * const 
 	xr->xr_cs = cs;
 
 #if 0
-	device_printf(sc->sc_dev, "%s %p xr_ep 0x%x xr_cs %u\n", __func__,
-	    xr, xr->xr_ep, xr->xr_cs);
+	DPRINTFN(12, "%p xr_ep 0x%x xr_cs %u", xr, xr->xr_ep, xr->xr_cs, 0);
 #endif
 }
 
@@ -1731,9 +1787,9 @@ xhci_do_command(struct xhci_softc * cons
 	struct xhci_ring * const cr = &sc->sc_cr;
 	usbd_status err;
 
-	device_printf(sc->sc_dev, "%s input: "
-	    "0x%016"PRIx64" 0x%08"PRIx32" 0x%08"PRIx32"\n", __func__,
-	    trb->trb_0, trb->trb_2, trb->trb_3);
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(12, "input: 0x%016"PRIx64" 0x%08"PRIx32" 0x%08"PRIx32,
+	    trb->trb_0, trb->trb_2, trb->trb_3, 0);
 
 	mutex_enter(&sc->sc_lock);
 
@@ -1756,9 +1812,8 @@ xhci_do_command(struct xhci_softc * cons
 	trb->trb_2 = sc->sc_result_trb.trb_2;
 	trb->trb_3 = sc->sc_result_trb.trb_3;
 
-	device_printf(sc->sc_dev, "%s output: "
-	    "0x%016"PRIx64" 0x%08"PRIx32" 0x%08"PRIx32"\n", __func__,
-	    trb->trb_0, trb->trb_2, trb->trb_3);
+	DPRINTFN(12, "output: 0x%016"PRIx64" 0x%08"PRIx32" 0x%08"PRIx32"",
+	    trb->trb_0, trb->trb_2, trb->trb_3, 0);
 
 	switch (XHCI_TRB_2_ERROR_GET(trb->trb_2)) {
 	case XHCI_TRB_ERROR_SUCCESS:
@@ -1785,6 +1840,8 @@ xhci_enable_slot(struct xhci_softc * con
 	struct xhci_trb trb;
 	usbd_status err;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	trb.trb_0 = 0;
 	trb.trb_2 = 0;
 	trb.trb_3 = XHCI_TRB_3_TYPE_SET(XHCI_TRB_TYPE_ENABLE_SLOT);
@@ -1806,6 +1863,8 @@ xhci_address_device(struct xhci_softc * 
 	struct xhci_trb trb;
 	usbd_status err;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	trb.trb_0 = icp;
 	trb.trb_2 = 0;
 	trb.trb_3 = XHCI_TRB_3_SLOT_SET(slot_id) |
@@ -1824,7 +1883,8 @@ xhci_update_ep0_mps(struct xhci_softc * 
 	usbd_status err;
 	uint32_t * cp;
 
-	device_printf(sc->sc_dev, "%s\n", __func__);
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(4, "slot %u mps %u\n", xs->xs_idx, mps, 0, 0);
 
 	cp = xhci_slot_get_icv(sc, xs, XHCI_ICI_INPUT_CONTROL);
 	cp[0] = htole32(0);
@@ -1853,8 +1913,9 @@ xhci_set_dcba(struct xhci_softc * const 
 {
 	uint64_t * const dcbaa = KERNADDR(&sc->sc_dcbaa_dma, 0);
 
-	device_printf(sc->sc_dev, "dcbaa %p dc %016"PRIx64" slot %d\n",
-	    &dcbaa[si], dcba, si);
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(4, "dcbaa %p dc %016"PRIx64" slot %d",
+	    &dcbaa[si], dcba, si, 0);
 
 	dcbaa[si] = htole64(dcba);
 	usb_syncmem(&sc->sc_dcbaa_dma, si * sizeof(uint64_t), sizeof(uint64_t),
@@ -1872,6 +1933,12 @@ xhci_init_slot(struct xhci_softc * const
 	uint32_t mps;
 	uint32_t xspeed;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(4, "slot %u depth %d speed %d",
+	    slot, depth, speed, 0);
+	DPRINTFN(4, " port %d rhport %d",
+	    port, rhport, 0, 0);
+
 	switch (speed) {
 	case USB_SPEED_LOW:
 		xspeed = 2;
@@ -1890,8 +1957,7 @@ xhci_init_slot(struct xhci_softc * const
 		mps = USB_3_MAX_CTRL_PACKET;
 		break;
 	default:
-		device_printf(sc->sc_dev, "%s: impossible speed: %x",
-		    __func__, speed);
+		DPRINTFN(0, "impossible speed: %x", speed, 0, 0, 0);
 		return USBD_INVAL;
 	}
 
@@ -1919,7 +1985,7 @@ xhci_init_slot(struct xhci_softc * const
 		err = xhci_ring_init(sc, &xs->xs_ep[dci].xe_tr,
 		    XHCI_TRANSFER_RING_TRBS, XHCI_TRB_ALIGN);
 		if (err) {
-			device_printf(sc->sc_dev, "ring init failure\n");
+			DPRINTFN(0, "ring init failure", 0, 0, 0, 0);
 			return err;
 		}
 	}
@@ -1982,7 +2048,7 @@ xhci_init_slot(struct xhci_softc * const
 static void
 xhci_noop(usbd_pipe_handle pipe)
 {
-	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 }
 
 /* root hub descriptors */
@@ -2065,7 +2131,7 @@ xhci_root_ctrl_transfer(usbd_xfer_handle
 	struct xhci_softc * const sc = xfer->pipe->device->bus->hci_private;
 	usbd_status err;
 
-	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 	/* Insert last in queue. */
 	mutex_enter(&sc->sc_lock);
@@ -2092,7 +2158,7 @@ xhci_root_ctrl_start(usbd_xfer_handle xf
 	int port, i;
 	uint32_t v;
 
-	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 	if (sc->sc_dying)
 		return USBD_IOERROR;
@@ -2106,8 +2172,8 @@ xhci_root_ctrl_start(usbd_xfer_handle xf
 	if (len != 0)
 		buf = KERNADDR(&xfer->dmabuf, 0);
 
-	DPRINTF(("root req: %02x %02x %04x %04x %04x\n", req->bmRequestType,
-	    req->bRequest, value, index, len));
+	DPRINTFN(12, "rhreq: %04x %04x %04x %04x",
+	    req->bmRequestType | (req->bRequest << 8), value, index, len);
 
 #define C(x,y) ((x) | ((y) << 8))
 	switch(C(req->bRequest, req->bmRequestType)) {
@@ -2126,7 +2192,7 @@ xhci_root_ctrl_start(usbd_xfer_handle xf
 		}
 		break;
 	case C(UR_GET_DESCRIPTOR, UT_READ_DEVICE):
-		DPRINTFN(8,("xhci_root_ctrl_start: wValue=0x%04x\n", value));
+		DPRINTFN(8, "getdesc: wValue=0x%04x", value, 0, 0, 0);
 		if (len == 0)
 			break;
 		switch(value >> 8) {
@@ -2234,16 +2300,15 @@ xhci_root_ctrl_start(usbd_xfer_handle xf
 	case C(UR_CLEAR_FEATURE, UT_WRITE_CLASS_DEVICE):
 		break;
 	case C(UR_CLEAR_FEATURE, UT_WRITE_CLASS_OTHER):
-		DPRINTFN(4, ("xhci_root_ctrl_start: UR_CLEAR_PORT_FEATURE "
-			     "port=%d feature=%d\n",
-			     index, value));
+		DPRINTFN(4, "UR_CLEAR_PORT_FEATURE port=%d feature=%d",
+			     index, value, 0, 0);
 		if (index < 1 || index > sc->sc_hs_port_count) {
 			err = USBD_IOERROR;
 			goto ret;
 		}
 		port = XHCI_PORTSC(sc->sc_hs_port_start - 1 + index);
 		v = xhci_op_read_4(sc, port);
-		DPRINTFN(4, ("xhci_root_ctrl_start: portsc=0x%08x\n", v));
+		DPRINTFN(4, "portsc=0x%08x", v, 0, 0, 0);
 		v &= ~XHCI_PS_CLEAR;
 		switch (value) {
 		case UHF_PORT_ENABLE:
@@ -2302,8 +2367,7 @@ xhci_root_ctrl_start(usbd_xfer_handle xf
 		totlen = len;
 		break;
 	case C(UR_GET_STATUS, UT_READ_CLASS_OTHER):
-		DPRINTFN(8,("xhci_root_ctrl_start: get port status i=%d\n",
-			    index));
+		DPRINTFN(8, "get port status i=%d", index, 0, 0, 0);
 		if (index < 1 || index > sc->sc_maxports) {
 			err = USBD_IOERROR;
 			goto ret;
@@ -2314,8 +2378,8 @@ xhci_root_ctrl_start(usbd_xfer_handle xf
 		}
 		v = xhci_op_read_4(sc, XHCI_PORTSC(sc->sc_hs_port_start - 1 +
 		    index));
-		DPRINTF(("%s READ_CLASS_OTHER GET_STATUS PORTSC %d (%d) %08x\n",
-		    __func__, index, sc->sc_hs_port_start - 1 + index, v));
+		DPRINTFN(4, "READ_CLASS_OTHER GET_STATUS PORTSC %d (%d) %08x",
+		    index, sc->sc_hs_port_start - 1 + index, v, 0);
 		switch (XHCI_PS_SPEED_GET(v)) {
 		case 1:
 			i = UPS_FULL_SPEED;
@@ -2359,7 +2423,7 @@ xhci_root_ctrl_start(usbd_xfer_handle xf
 		}
 		port = XHCI_PORTSC(sc->sc_hs_port_start - 1 + index);
 		v = xhci_op_read_4(sc, port);
-		DPRINTFN(4, ("xhci_root_ctrl_start: portsc=0x%08x\n", v));
+		DPRINTFN(4, "portsc=0x%08x", v, 0, 0, 0);
 		v &= ~XHCI_PS_CLEAR;
 		switch (value) {
 		case UHF_PORT_ENABLE:
@@ -2419,6 +2483,7 @@ ret:
 static void
 xhci_root_ctrl_abort(usbd_xfer_handle xfer)
 {
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 	/* Nothing to do, all transfers are synchronous. */
 }
 
@@ -2426,13 +2491,15 @@ xhci_root_ctrl_abort(usbd_xfer_handle xf
 static void
 xhci_root_ctrl_close(usbd_pipe_handle pipe)
 {
-	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 	/* Nothing to do. */
 }
 
 static void
 xhci_root_ctrl_done(usbd_xfer_handle xfer)
 {
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	xfer->hcpriv = NULL;
 }
 
@@ -2444,6 +2511,8 @@ xhci_root_intr_transfer(usbd_xfer_handle
 	struct xhci_softc * const sc = xfer->pipe->device->bus->hci_private;
 	usbd_status err;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	/* Insert last in queue. */
 	mutex_enter(&sc->sc_lock);
 	err = usb_insert_transfer(xfer);
@@ -2460,6 +2529,8 @@ xhci_root_intr_start(usbd_xfer_handle xf
 {
 	struct xhci_softc * const sc = xfer->pipe->device->bus->hci_private;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	if (sc->sc_dying)
 		return USBD_IOERROR;
 
@@ -2475,10 +2546,12 @@ xhci_root_intr_abort(usbd_xfer_handle xf
 {
 	struct xhci_softc * const sc = xfer->pipe->device->bus->hci_private;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	KASSERT(mutex_owned(&sc->sc_lock));
 	KASSERT(xfer->pipe->intrxfer == xfer);
 
-	DPRINTF(("%s: remove\n", __func__));
+	DPRINTFN(1, "remove", 0, 0, 0, 0);
 
 	sc->sc_intrxfer = NULL;
 
@@ -2491,9 +2564,9 @@ xhci_root_intr_close(usbd_pipe_handle pi
 {
 	struct xhci_softc * const sc = pipe->device->bus->hci_private;
 
-	KASSERT(mutex_owned(&sc->sc_lock));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
-	DPRINTF(("%s\n", __func__));
+	KASSERT(mutex_owned(&sc->sc_lock));
 
 	sc->sc_intrxfer = NULL;
 }
@@ -2501,6 +2574,8 @@ xhci_root_intr_close(usbd_pipe_handle pi
 static void
 xhci_root_intr_done(usbd_xfer_handle xfer)
 {
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	xfer->hcpriv = NULL;
 }
 
@@ -2513,6 +2588,8 @@ xhci_device_ctrl_transfer(usbd_xfer_hand
 	struct xhci_softc * const sc = xfer->pipe->device->bus->hci_private;
 	usbd_status err;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	/* Insert last in queue. */
 	mutex_enter(&sc->sc_lock);
 	err = usb_insert_transfer(xfer);
@@ -2541,10 +2618,10 @@ xhci_device_ctrl_start(usbd_xfer_handle 
 	uint32_t control;
 	u_int i;
 
-	DPRINTF(("%s\n", __func__));
-	DPRINTF(("req: %02x %02x %04x %04x %04x\n", req->bmRequestType,
-	    req->bRequest, UGETW(req->wValue), UGETW(req->wIndex),
-	    UGETW(req->wLength)));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(12, "req: %04x %04x %04x %04x",
+	    req->bmRequestType | (req->bRequest << 8), UGETW(req->wValue),
+	    UGETW(req->wIndex), UGETW(req->wLength));
 
 	/* XXX */
 	if (tr->is_halted) {
@@ -2617,7 +2694,7 @@ no_data:
 	}
 
 	if (sc->sc_bus.use_polling) {
-		device_printf(sc->sc_dev, "%s polling\n", __func__);
+		DPRINTFN(1, "polling", 0, 0, 0, 0);
 		//xhci_waitintr(sc, xfer);
 	}
 
@@ -2627,7 +2704,7 @@ no_data:
 static void
 xhci_device_ctrl_done(usbd_xfer_handle xfer)
 {
-	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 	callout_stop(&xfer->timeout_handle); /* XXX wrong place */
 
@@ -2636,13 +2713,13 @@ xhci_device_ctrl_done(usbd_xfer_handle x
 static void
 xhci_device_ctrl_abort(usbd_xfer_handle xfer)
 {
-	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 }
 
 static void
 xhci_device_ctrl_close(usbd_pipe_handle pipe)
 {
-	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 }
 
 /* ----------------- */
@@ -2657,6 +2734,8 @@ xhci_device_bulk_transfer(usbd_xfer_hand
 	struct xhci_softc * const sc = xfer->pipe->device->bus->hci_private;
 	usbd_status err;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	/* Insert last in queue. */
 	mutex_enter(&sc->sc_lock);
 	err = usb_insert_transfer(xfer);
@@ -2686,9 +2765,9 @@ xhci_device_bulk_start(usbd_xfer_handle 
 	uint32_t control;
 	u_int i = 0;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 #if 0
-	device_printf(sc->sc_dev, "%s %p slot %u dci %u\n", __func__, xfer,
-	    xs->xs_idx, dci);
+	DPRINTFN(15, "%p slot %u dci %u", xfer, xs->xs_idx, dci, 0);
 #endif
 
 	if (sc->sc_dying)
@@ -2723,7 +2802,7 @@ xhci_device_bulk_start(usbd_xfer_handle 
 	xhci_db_write_4(sc, XHCI_DOORBELL(xs->xs_idx), dci);
 
 	if (sc->sc_bus.use_polling) {
-		device_printf(sc->sc_dev, "%s polling\n", __func__);
+		DPRINTFN(1, "polling", 0, 0, 0, 0);
 		//xhci_waitintr(sc, xfer);
 	}
 
@@ -2739,11 +2818,10 @@ xhci_device_bulk_done(usbd_xfer_handle x
 	const u_int endpt = xfer->pipe->endpoint->edesc->bEndpointAddress;
 	const bool isread = UE_GET_DIR(endpt) == UE_DIR_IN;
 
-	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 #if 0
-	device_printf(sc->sc_dev, "%s %p slot %u dci %u\n", __func__, xfer,
-	    xs->xs_idx, dci);
+	DPRINTFN(15, "%p slot %u dci %u", xfer, xs->xs_idx, dci, 0);
 #endif
 
 	callout_stop(&xfer->timeout_handle); /* XXX wrong place */
@@ -2757,13 +2835,13 @@ xhci_device_bulk_done(usbd_xfer_handle x
 static void
 xhci_device_bulk_abort(usbd_xfer_handle xfer)
 {
-	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 }
 
 static void
 xhci_device_bulk_close(usbd_pipe_handle pipe)
 {
-	DPRINTF(("%s\n", __func__));
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 }
 
 /* --------------- */
@@ -2775,6 +2853,8 @@ xhci_device_intr_transfer(usbd_xfer_hand
 	struct xhci_softc * const sc = xfer->pipe->device->bus->hci_private;
 	usbd_status err;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	/* Insert last in queue. */
 	mutex_enter(&sc->sc_lock);
 	err = usb_insert_transfer(xfer);
@@ -2804,9 +2884,9 @@ xhci_device_intr_start(usbd_xfer_handle 
 	uint32_t control;
 	u_int i = 0;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 #if 0
-	device_printf(sc->sc_dev, "%s %p slot %u dci %u\n", __func__, xfer,
-	    xs->xs_idx, dci);
+	DPRINTFN(15, "%p slot %u dci %u", xfer, xs->xs_idx, dci, 0);
 #endif
 
 	if (sc->sc_dying)
@@ -2831,7 +2911,7 @@ xhci_device_intr_start(usbd_xfer_handle 
 
 	if (sc->sc_bus.use_polling) {
 #ifdef XHCI_DEBUG
-		device_printf(sc->sc_dev, "%s polling\n", __func__);
+		DPRINTFN(1, "polling", 0, 0, 0, 0);
 #endif
 		//xhci_waitintr(sc, xfer);
 	}
@@ -2850,11 +2930,10 @@ xhci_device_intr_done(usbd_xfer_handle x
 #endif
 	const u_int endpt = xfer->pipe->endpoint->edesc->bEndpointAddress;
 	const bool isread = UE_GET_DIR(endpt) == UE_DIR_IN;
-	DPRINTF(("%s\n", __func__));
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 #ifdef XHCI_DEBUG
-	device_printf(sc->sc_dev, "%s %p slot %u dci %u\n", __func__, xfer,
-	    xs->xs_idx, dci);
+	DPRINTFN(15, "%p slot %u dci %u", xfer, xs->xs_idx, dci, 0);
 #endif
 
 	KASSERT(sc->sc_bus.use_polling || mutex_owned(&sc->sc_lock));
@@ -2881,11 +2960,13 @@ xhci_device_intr_done(usbd_xfer_handle x
 static void
 xhci_device_intr_abort(usbd_xfer_handle xfer)
 {
-	struct xhci_softc * const sc = xfer->pipe->device->bus->hci_private;
-	DPRINTF(("%s\n", __func__));
+	struct xhci_softc * const sc __diagused =
+				    xfer->pipe->device->bus->hci_private;
+
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 	KASSERT(mutex_owned(&sc->sc_lock));
-	device_printf(sc->sc_dev, "%s %p\n", __func__, xfer);
+	DPRINTFN(15, "%p", xfer, 0, 0, 0);
 	KASSERT(xfer->pipe->intrxfer == xfer);
 	xfer->status = USBD_CANCELLED;
 	usb_transfer_complete(xfer);
@@ -2894,9 +2975,11 @@ xhci_device_intr_abort(usbd_xfer_handle 
 static void
 xhci_device_intr_close(usbd_pipe_handle pipe)
 {
-	struct xhci_softc * const sc = pipe->device->bus->hci_private;
-	DPRINTF(("%s\n", __func__));
-	device_printf(sc->sc_dev, "%s %p\n", __func__, pipe);
+	//struct xhci_softc * const sc = pipe->device->bus->hci_private;
+
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+	DPRINTFN(15, "%p", pipe, 0, 0, 0);
+
 	xhci_unconfigure_endpoint(pipe);
 }
 
@@ -2909,6 +2992,8 @@ xhci_timeout(void *addr)
 	usbd_xfer_handle const xfer = &xx->xx_xfer;
 	struct xhci_softc * const sc = xfer->pipe->device->bus->hci_private;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	if (sc->sc_dying) {
 		return;
 	}
@@ -2925,6 +3010,8 @@ xhci_timeout_task(void *addr)
 	usbd_xfer_handle const xfer = addr;
 	struct xhci_softc * const sc = xfer->pipe->device->bus->hci_private;
 
+	XHCIHIST_FUNC(); XHCIHIST_CALLED();
+
 	mutex_enter(&sc->sc_lock);
 #if 0
 	xhci_abort_xfer(xfer, USBD_TIMEOUT);
--- src/sys/dev/usb/xhci.c.orig	2014-08-12 23:29:37.000000000 +0900
+++ src/sys/dev/usb/xhci.c	2014-09-25 19:12:42.000000000 +0900
@@ -1988,73 +2902,77 @@ xhci_noop(usbd_pipe_handle pipe)
 /* root hub descriptors */
 
 static const usb_device_descriptor_t xhci_devd = {
-	USB_DEVICE_DESCRIPTOR_SIZE,
-	UDESC_DEVICE,		/* type */
-	{0x00, 0x02},		/* USB version */
-	UDCLASS_HUB,		/* class */
-	UDSUBCLASS_HUB,		/* subclass */
-	UDPROTO_HSHUBSTT,	/* protocol */
-	64,			/* max packet */
-	{0},{0},{0x00,0x01},	/* device id */
-	1,2,0,			/* string indexes */
-	1			/* # of configurations */
+	.bLength		= USB_DEVICE_DESCRIPTOR_SIZE,
+	.bDescriptorType	= UDESC_DEVICE,		/* type */
+	.bcdUSB			= {0x00, 0x02},		/* USB version */
+	.bDeviceClass		= UDCLASS_HUB,		/* class */
+	.bDeviceSubClass	= UDSUBCLASS_HUB,	/* subclass */
+	.bDeviceProtocol	= UDPROTO_HSHUBSTT,	/* protocol */
+	.bMaxPacketSize		= 64,			/* max packet */
+	.idVendor		= {0},
+	.idProduct		= {0},
+	.bcdDevice		= {0x00,0x01},		/* device id */
+	.iManufacturer		= 1,			/* string indexes */
+	.iProduct		= 2,
+	.iSerialNumber		= 0,
+	.bNumConfigurations	= 1		/* # of configurations */
 };
 
 static const usb_device_qualifier_t xhci_odevd = {
-	USB_DEVICE_DESCRIPTOR_SIZE,
-	UDESC_DEVICE_QUALIFIER,	/* type */
-	{0x00, 0x02},		/* USB version */
-	UDCLASS_HUB,		/* class */
-	UDSUBCLASS_HUB,		/* subclass */
-	UDPROTO_FSHUB,		/* protocol */
-	64,                     /* max packet */
-	1,                      /* # of configurations */
-	0
+	.bLength		= USB_DEVICE_DESCRIPTOR_SIZE,
+	.bDescriptorType	= UDESC_DEVICE_QUALIFIER,	/* type */
+	.bcdUSB			= {0x00, 0x02},		/* USB version */
+	.bDeviceClass		= UDCLASS_HUB,		/* class */
+	.bDeviceSubClass	= UDSUBCLASS_HUB,	/* subclass */
+	.bDeviceProtocol	= UDPROTO_FSHUB,	/* protocol */
+	.bMaxPacketSize0	= 64,			/* max packet */
+	.bNumConfigurations	= 1,		/* # of configurations */
+	.bReserved		= 0
 };
 
 static const usb_config_descriptor_t xhci_confd = {
-	USB_CONFIG_DESCRIPTOR_SIZE,
-	UDESC_CONFIG,
-	{USB_CONFIG_DESCRIPTOR_SIZE +
-	 USB_INTERFACE_DESCRIPTOR_SIZE +
-	 USB_ENDPOINT_DESCRIPTOR_SIZE},
-	1,
-	1,
-	0,
-	UC_ATTR_MBO | UC_SELF_POWERED,
-	0                      /* max power */
+	.bLength		= USB_CONFIG_DESCRIPTOR_SIZE,
+	.bDescriptorType	= UDESC_CONFIG,
+	.wTotalLength		= {USB_CONFIG_DESCRIPTOR_SIZE +
+				 USB_INTERFACE_DESCRIPTOR_SIZE +
+				 USB_ENDPOINT_DESCRIPTOR_SIZE},
+	.bNumInterface		= 1,
+	.bConfigurationValue	= 1,
+	.iConfiguration		= 0,
+	.bmAttributes		= UC_ATTR_MBO | UC_SELF_POWERED,
+	.bMaxPower		= 0	/* max current in 2 mA units */
 };
 
 static const usb_interface_descriptor_t xhci_ifcd = {
-	USB_INTERFACE_DESCRIPTOR_SIZE,
-	UDESC_INTERFACE,
-	0,
-	0,
-	1,
-	UICLASS_HUB,
-	UISUBCLASS_HUB,
-	UIPROTO_HSHUBSTT,
-	0
+	.bLength		= USB_INTERFACE_DESCRIPTOR_SIZE,
+	.bDescriptorType	= UDESC_INTERFACE,
+	.bInterfaceNumber	= 0,
+	.bAlternateSetting	= 0,
+	.bNumEndpoints		= 1,
+	.bInterfaceClass	= UICLASS_HUB,
+	.bInterfaceSubClass	= UISUBCLASS_HUB,
+	.bInterfaceProtocol	= UIPROTO_HSHUBSTT,
+	.iInterface		= 0
 };
 
 static const usb_endpoint_descriptor_t xhci_endpd = {
-	USB_ENDPOINT_DESCRIPTOR_SIZE,
-	UDESC_ENDPOINT,
-	UE_DIR_IN | XHCI_INTR_ENDPT,
-	UE_INTERRUPT,
-	{8, 0},                 /* max packet */
-	12
+	.bLength		= USB_ENDPOINT_DESCRIPTOR_SIZE,
+	.bDescriptorType	= UDESC_ENDPOINT,
+	.bEndpointAddress	= UE_DIR_IN | XHCI_INTR_ENDPT,
+	.bmAttributes		= UE_INTERRUPT,
+	.wMaxPacketSize		= {8, 0},	/* max packet */
+	.bInterval		= 12
 };
 
 static const usb_hub_descriptor_t xhci_hubd = {
-	USB_HUB_DESCRIPTOR_SIZE,
-	UDESC_HUB,
-	0,
-	{0,0},
-	0,
-	0,
-	{""},
-	{""},
+	.bDescLength		= USB_HUB_DESCRIPTOR_SIZE,
+	.bDescriptorType	= UDESC_HUB,
+	.bNbrPorts		= 0,
+	.wHubCharacteristics	= {0,0},
+	.bPwrOn2PwrGood		= 0,		/* delay in 2 ms units */
+	.bHubContrCurrent	= 0,
+	.DeviceRemovable	= {""},		/* max 255 ports */
+	.PortPowerCtrlMask	= {""},		/* deprecated */ 
 };
 
 /* root hub control */
--- src/sys/dev/usb/usb.h.orig	2014-09-19 15:57:04.000000000 +0900
+++ src/sys/dev/usb/usb.h	2014-09-25 21:33:49.000000000 +0900
@@ -165,6 +165,8 @@
 #define  UDESC_OTG		0x09
 #define  UDESC_DEBUG		0x0a
 #define  UDESC_INTERFACE_ASSOC	0x0b
+#define  UDESC_BOS		0x0f
+#define  UDESC_DEVICE_CAPABILITY 0x10
 #define  UDESC_CS_DEVICE	0x21	/* class specific */
 #define  UDESC_CS_CONFIG	0x22
 #define  UDESC_CS_STRING	0x23
@@ -172,23 +174,47 @@
 #define  UDESC_CS_ENDPOINT	0x25
 #define  UDESC_HUB		0x29
 #define  UDESC_SSHUB		0x2a
+#define  UDESC_ENDPOINT_SS_COMP 0x30 /* SUPERSPEED_USB_ENDPOINT_COMPANION */
+#define  UDESC_ENDPOINT_ISOCH_SSP_COMP	0x31
+			/* SUPERSPEEDPLUS_ISOCHRONOUS_ENDPOINT_COMPANION */
 #define UR_SET_DESCRIPTOR	0x07
 #define UR_GET_CONFIG		0x08
 #define UR_SET_CONFIG		0x09
 #define UR_GET_INTERFACE	0x0a
 #define UR_SET_INTERFACE	0x0b
 #define UR_SYNCH_FRAME		0x0c
+#define UR_SET_ENCRYPTION	0x0d
+#define UR_GET_ENCRYPTION	0x0e
+#define UR_SET_HANDSHAKE	0x0f
+#define UR_GET_HANDSHAKE	0x10
+#define UR_SET_CONNECTION	0x11
+#define UR_SET_SECURITY_DATA	0x12
+#define UR_GET_SECURITY_DATA	0x13
+#define UR_SET_WUSB_DATA	0x14
+#define UR_LOOPBACK_DATA_WRITE	0x15
+#define UR_LOOPBACK_DATA_READ	0x16
+#define UR_SET_INTERFACE_DS	0x17
+#define UR_SET_SEL		0x30
+#define UR_SET_ISOCH_DELAY	0x31
 
 /*
  * Feature selectors. USB 2.0 spec, table 9-6 and OTG and EH suppliment,
  * table 6-2
  */
 #define UF_ENDPOINT_HALT	0
+#define UF_INTERFACE_FUNCTION_SUSPEND	0
 #define UF_DEVICE_REMOTE_WAKEUP	1
 #define UF_TEST_MODE		2
 #define UF_DEVICE_B_HNP_ENABLE	3
 #define UF_DEVICE_A_HNP_SUPPORT	4
 #define UF_DEVICE_A_ALT_HNP_SUPPORT 5
+#define UF_DEVICE_WUSB_DEVICE	6
+#define UF_DEVICE_U1_ENABLE	48
+#define UF_DEVICE_U2_ENABLE	49
+#define UF_DEVICE_LTM_ENABLE	50
+#define UF_DEVICE_B3_NTF_HOST_SEL	51
+#define UF_DEVICE_B3_RESP_ENABLE	52
+#define UF_DEVICE_LDM_ENABLE	53
 
 #define USB_MAX_IPACKET		8 /* maximum size of the initial packet */
 
@@ -207,6 +233,7 @@
 	uByte		bDescriptorType;
 	uWord		bcdUSB;
 #define UD_USB_2_0		0x0200
+#define UD_USB_3_0		0x0300
 #define UD_IS_USB2(d) (UGETW((d)->bcdUSB) >= UD_USB_2_0)
 	uByte		bDeviceClass;
 	uByte		bDeviceSubClass;
@@ -295,6 +322,105 @@
 
 typedef struct {
 	uByte		bLength;
+	uByte		bDescriptorType;	/* 0x30 */
+	uByte		bMaxBurst;
+	uByte		bmAttributes;
+#define USSE_MAXSTREAMS(x)	__SHIFTOUT(x, __BITS(4,0))	/* bulk */
+#define USSE_MULT(x)		__SHIFTOUT(x, __BITS(1,0))	/* isoch */
+#define USSE_SSP_ISO(x) 	__SHIFTOUT(x, __BIT(7))		/* isoch */
+	/* The fields below are only valid for periodic endpoints */
+	uWord		wBytesPerInterval;
+} UPACKED usb_endpoint_ss_comp_descriptor_t;
+#define USB_ENDPOINT_SS_COMP_DESCRIPTOR_SIZE 6
+
+typedef struct {
+	uByte		bLength;
+	uByte		bDescriptorType;
+	uWord		wTotalLength;
+	uByte		bNumDeviceCaps;
+} UPACKED usb_bos_descriptor_t;
+#define USB_BOS_DESCRIPTOR_SIZE 5
+
+typedef struct {
+	uByte		bLength;
+	uByte		bDescriptorType;
+	uByte		bDevCapabilityType;
+#define USB_DEVCAP_RESERVED			0x00
+#define USB_DEVCAP_WUSB				0x01
+#define USB_DEVCAP_USB2EXT			0x02
+#define USB_DEVCAP_SUPER_SPEED			0x03
+#define USB_DEVCAP_CONTAINER_ID			0x04
+#define USB_DEVCAP_PLATFORM			0x05
+#define USB_DEVCAP_POWER_DELIVERY_CAPABILITY	0x06
+#define USB_DEVCAP_BATTERY_INFO_CAPABILITY	0x07
+#define USB_DEVCAP_PD_CONSUMER_PORT_CAPABILITY	0x08
+#define USB_DEVCAP_PD_PROVIDER_PORT_CAPABILITY	0x09
+#define USB_DEVCAP_SUPERSPEED_PLUS		0x0A
+#define USB_DEVCAP_PRECISION_TIME_MEASUREMENT	0x0B
+#define USB_DEVCAP_WUSB_EXT			0x0C
+	/* data ... */
+} UPACKED usb_device_capability_descriptor_t;
+#define USB_DEVICE_CAPABILITY_DESCRIPTOR_SIZE 3 /* variable length */
+
+typedef struct {
+	uByte		bLength;
+	uByte		bDescriptorType;
+	uByte		bDevCapabilityType;
+	uDWord		bmAttributes;
+#define USB_DEVCAP_USB2EXT_LPM __BIT(1)
+} UPACKED usb_usb2ext_descriptor_t;
+#define USB_DEVCAP_USB2EXT_DESCRIPTOR_SIZE 7
+
+typedef struct {
+	uByte		bLength;
+	uByte		bDescriptorType;
+	uByte		bDevCapabilityType;
+	uByte		bmAttributes;
+#define USB_DEVCAP_SS_LTM __BIT(1)
+	uWord		wSpeedsSupported;
+#define USB_DEVCAP_SS_SPEED_SS __BIT(0)
+#define USB_DEVCAP_SS_SPEED_FS __BIT(1)
+#define USB_DEVCAP_SS_SPEED_HS __BIT(2)
+#define USB_DEVCAP_SS_SPEED_LS __BIT(3)
+	uByte		bFunctionalitySupport;
+	uByte		bU1DevExitLat;
+	uWord		wU2DevExitLat;
+} UPACKED usb_devcap_ss_descriptor_t;
+#define USB_DEVCAP_SS_DESCRIPTOR_SIZE 10
+
+typedef struct {
+	uByte		bLength;
+	uByte		bDescriptorType;
+	uByte		bDevCapabilityType;
+	uByte		bReserved;
+	uByte		ContainerID[16];
+} UPACKED usb_devcap_container_id_descriptor_t;
+#define USB_DEVCAP_CONTAINER_ID_DESCRIPTOR_SIZE 20
+
+typedef struct {
+	uByte		bLength;
+	uByte		bDescriptorType;
+	uByte		bDevCapabilityType;
+	uByte		bReserved;
+	uByte		PlatformCapabilityUUID[16];
+	uByte		CapabilityData[0];
+} UPACKED usb_devcap_platform_descriptor_t;
+#define USB_DEVCAP_PLATFORM_DESCRIPTOR_SIZE 20
+
+typedef struct {
+	uByte		bLength;
+	uByte		bDescriptorType;
+	uByte		bDevCapabilityType;
+	uByte		bReserved;
+	uDWord		bmAttributes;
+	uWord		wFunctionalitySupport;
+	uWord		wReserved;
+	uDWord		bmSublinkSpeedAttr[0];
+} UPACKED usb_devcap_ssp_descriptor_t;
+#define USB_DEVCAP_SSP_DESCRIPTOR_SIZE 12 /* variable length */
+
+typedef struct {
+	uByte		bLength;
 	uByte		bDescriptorType;
 	uWord		bString[126];
 } UPACKED usb_string_descriptor_t;
@@ -308,6 +434,9 @@
 #define UR_RESET_TT		0x09
 #define UR_GET_TT_STATE		0x0a
 #define UR_STOP_TT		0x0b
+#define UR_SET_AND_TEST		0x0c
+#define UR_SET_HUB_DEPTH	0x0c
+#define UR_GET_PORT_ERR_COUNT	0x0d
 
 /*
  * Hub features from USB 2.0 spec, table 11-17 and updated by the
@@ -365,6 +494,19 @@
 typedef struct {
 	uByte		bLength;
 	uByte		bDescriptorType;
+	uByte		bNbrPorts;
+	uWord		wHubCharacteristics;
+	uByte		bPwrOn2PwrGood;	/* delay in 2 ms units */
+	uByte		bHubContrCurrent;
+	uByte		bHubHdrDecLat;
+	uWord		wHubDelay;
+	uByte		DeviceRemovable[2]; /* max 15 ports */
+} UPACKED usb_hub_ss_descriptor_t;
+#define USB_HUB_SS_DESCRIPTOR_SIZE 12
+
+typedef struct {
+	uByte		bLength;
+	uByte		bDescriptorType;
 	uWord		bcdUSB;
 	uByte		bDeviceClass;
 	uByte		bDeviceSubClass;
@@ -501,6 +643,7 @@
 #define  UIPROTO_MASS_CBI	1
 #define  UIPROTO_MASS_BBB_OLD	2	/* Not in the spec anymore */
 #define  UIPROTO_MASS_BBB	80	/* 'P' for the Iomega Zip drive */
+#define  UIPROTO_MASS_UAS	98	/* USB Attached SCSI */
 
 #define UICLASS_HUB		0x09
 #define  UISUBCLASS_HUB		0
--- src/sys/dev/usb/xhcireg.h.orig	2014-09-09 11:24:29.000000000 +0900
+++ src/sys/dev/usb/xhcireg.h	2014-09-25 21:43:15.000000000 +0900
@@ -38,6 +38,11 @@
 #define	 PCI_USBREV_3_0		0x30	/* USB 3.0 */
 #define	PCI_XHCI_FLADJ		0x61	/* RW frame length adjust */
 
+#define	PCI_XHCI_INTEL_XUSB2PR	0xD0    /* Intel USB2 Port Routing */
+#define	PCI_XHCI_INTEL_USB2PRM	0xD4    /* Intel USB2 Port Routing Mask */
+#define	PCI_XHCI_INTEL_USB3_PSSEN 0xD8  /* Intel USB3 Port SuperSpeed Enable */
+#define	PCI_XHCI_INTEL_USB3PRM	0xDC    /* Intel USB3 Port Routing Mask */
+
 /* XHCI capability registers */
 #define XHCI_CAPLENGTH		0x00	/* RO capability */
 #define	XHCI_CAP_CAPLENGTH(x)	((x) & 0xFF)
@@ -188,18 +193,20 @@
 /* XHCI legacy support */
 #define	XHCI_XECP_ID(x)		((x) & 0xFF)
 #define	XHCI_XECP_NEXT(x)	(((x) >> 8) & 0xFF)
-#if 0
 #define	XHCI_XECP_BIOS_SEM	0x0002
 #define	XHCI_XECP_OS_SEM	0x0003
-#endif
 
-/* XHCI capability ID's */
-#define	XHCI_ID_USB_LEGACY	0x0001
-#define	XHCI_ID_PROTOCOLS	0x0002
-#define	XHCI_ID_POWER_MGMT	0x0003
-#define	XHCI_ID_VIRTUALIZATION	0x0004
-#define	XHCI_ID_MSG_IRQ		0x0005
-#define	XHCI_ID_USB_LOCAL_MEM	0x0006
+/* XHCI extended capability ID's */
+#define	XHCI_ID_USB_LEGACY	0x0001	/* USB Legacy Support */
+#define	 XHCI_XECP_USBLESUP	0x0000	/* Legacy Support Capability Reg */
+#define	 XHCI_XECP_USBLEGCTLSTS	0x0004	/* Legacy Support Ctrl & Status Reg */
+#define	XHCI_ID_PROTOCOLS	0x0002	/* Supported Protocol */
+#define	XHCI_ID_POWER_MGMT	0x0003	/* Extended Power Management */
+#define	XHCI_ID_VIRTUALIZATION	0x0004	/* I/O Virtualization */
+#define	XHCI_ID_MSG_IRQ		0x0005	/* Message Interrupt */
+#define	XHCI_ID_USB_LOCAL_MEM	0x0006	/* Local Memory */
+#define	XHCI_ID_USB_DEBUG	0x000A	/* USB Debug Capability */
+#define	XHCI_ID_XMSG_IRQ	0x0011	/* Extended Message Interrupt */
 
 #define XHCI_PAGE_SIZE(sc) ((sc)->sc_pgsz)
 
@@ -243,6 +250,7 @@ struct xhci_trb {
 #define XHCI_TRB_3_TC_BIT               (1U << 1)       /* command ring only */
 #define XHCI_TRB_3_ENT_BIT              (1U << 1)       /* transfer ring only */
 #define XHCI_TRB_3_ISP_BIT              (1U << 2)
+#define XHCI_TRB_3_ED_BIT               (1U << 2)
 #define XHCI_TRB_3_NSNOOP_BIT           (1U << 3)
 #define XHCI_TRB_3_CHAIN_BIT            (1U << 4)
 #define XHCI_TRB_3_IOC_BIT              (1U << 5)
@@ -266,6 +274,8 @@ struct xhci_trb {
 #define XHCI_TRB_3_FRID_SET(x)          (((x) & 0x7FF) << 20)
 #define XHCI_TRB_3_ISO_SIA_BIT          (1U << 31)
 #define XHCI_TRB_3_SUSP_EP_BIT          (1U << 23)
+#define XHCI_TRB_3_VFID_GET(x)          (((x) >> 16) & 0xFF)
+#define XHCI_TRB_3_VFID_SET(x)          (((x) & 0xFF) << 16)
 #define XHCI_TRB_3_SLOT_GET(x)          (((x) >> 24) & 0xFF)
 #define XHCI_TRB_3_SLOT_SET(x)          (((x) & 0xFF) << 24)
 
@@ -375,10 +385,20 @@ struct xhci_trb {
 #define XHCI_SCTX_3_DEV_ADDR_GET(x)             ((x) & 0xFF)
 #define XHCI_SCTX_3_SLOT_STATE_SET(x)           (((x) & 0x1F) << 27)
 #define XHCI_SCTX_3_SLOT_STATE_GET(x)           (((x) >> 27) & 0x1F)
+#define XHCI_SLOTSTATE_DISABLED			0 /* disabled or enabled */
+#define XHCI_SLOTSTATE_ENABLED			0
+#define XHCI_SLOTSTATE_DEFAULT			1
+#define XHCI_SLOTSTATE_ADDRESSED		2
+#define XHCI_SLOTSTATE_CONFIGURED		3
 
 
 #define XHCI_EPCTX_0_EPSTATE_SET(x)             ((x) & 0x7)
 #define XHCI_EPCTX_0_EPSTATE_GET(x)             ((x) & 0x7)
+#define XHCI_EPSTATE_DISABLED			0
+#define XHCI_EPSTATE_RUNNING			1
+#define XHCI_EPSTATE_HALTED			2
+#define XHCI_EPSTATE_STOPPED			3
+#define XHCI_EPSTATE_ERROR			4
 #define XHCI_EPCTX_0_MULT_SET(x)                (((x) & 0x3) << 8)
 #define XHCI_EPCTX_0_MULT_GET(x)                (((x) >> 8) & 0x3)
 #define XHCI_EPCTX_0_MAXP_STREAMS_SET(x)        (((x) & 0x1F) << 10)
--- src/sys/dev/usb/xhci.c.orig	2014-09-25 21:23:07.000000000 +0900
+++ src/sys/dev/usb/xhci.c	2014-09-25 21:44:21.000000000 +0900
@@ -113,7 +113,9 @@ fail:
 #define XHCI_COMMAND_RING_TRBS 256
 #define XHCI_EVENT_RING_TRBS 256
 #define XHCI_EVENT_RING_SEGMENTS 1
+#ifndef XHCI_TRB_3_ED_BIT
 #define XHCI_TRB_3_ED_BIT XHCI_TRB_3_ISP_BIT
+#endif
 
 struct xhci_pipe {
 	struct usbd_pipe xp_pipe;
--- src/sys/dev/usb/xhci.c.orig	2014-08-12 23:29:37.000000000 +0900
+++ src/sys/dev/usb/xhci.c	2014-09-25 22:26:41.000000000 +0900
@@ -490,17 +627,24 @@ xhci_detach(struct xhci_softc *sc, int f
 	xhci_rt_write_8(sc, XHCI_ERDP(0), 0|XHCI_ERDP_LO_BUSY);
 	xhci_ring_free(sc, &sc->sc_er);
 
-	usb_freemem(&sc->sc_bus, &sc->sc_eventst_dma);
+	/* avoid null dereference when rebooting if init fails */
+	if (sc->sc_eventst_dma.block != NULL)
+		usb_freemem(&sc->sc_bus, &sc->sc_eventst_dma);
 
 	xhci_op_write_8(sc, XHCI_DCBAAP, 0);
-	usb_freemem(&sc->sc_bus, &sc->sc_dcbaa_dma);
+	if (sc->sc_dcbaa_dma.block != NULL)
+		usb_freemem(&sc->sc_bus, &sc->sc_dcbaa_dma);
 
-	kmem_free(sc->sc_slots, sizeof(*sc->sc_slots) * sc->sc_maxslots);
+	if (sc->sc_slots)
+		kmem_free(sc->sc_slots,
+		    sizeof(*sc->sc_slots) * sc->sc_maxslots);
 
 	mutex_destroy(&sc->sc_lock);
 	mutex_destroy(&sc->sc_intr_lock);
+	cv_destroy(&sc->sc_softwake_cv);
 
-	pool_cache_destroy(sc->sc_xferpool);
+	if (sc->sc_xferpool)
+		pool_cache_destroy(sc->sc_xferpool);
 
 	return rv;
 }
@@ -1609,9 +2395,12 @@ xhci_ring_init(struct xhci_softc * const
 static void
 xhci_ring_free(struct xhci_softc * const sc, struct xhci_ring * const xr)
 {
-	usb_freemem(&sc->sc_bus, &xr->xr_dma);
-	mutex_destroy(&xr->xr_lock);
-	kmem_free(xr->xr_cookies, sizeof(*xr->xr_cookies) * xr->xr_ntrb);
+	if (xr->xr_cookies != NULL) {
+		usb_freemem(&sc->sc_bus, &xr->xr_dma);
+		mutex_destroy(&xr->xr_lock);
+		kmem_free(xr->xr_cookies,
+		    sizeof(*xr->xr_cookies) * xr->xr_ntrb);
+	}
 }
 
 static void


Home | Main Index | Thread Index | Old Index