Module Name:    src
Committed By:   mrg
Date:           Sun Sep 16 20:21:56 UTC 2018

Modified Files:
        src/sys/dev/usb: ehci.c ohci.c uhci.c usb.c usbdi.c xhci.c
        src/sys/external/bsd/dwc2: dwc2.c

Log Message:
consolidate the handling of polling across HC drivers, and generic USB:
- don't take mutexes if polling
- normalise the code across all drivers
- add some not yet code to block discovery to/from polling
- minor CSE
- adjust comment for usbd_set_polling() to reality now i properly
  understand what it is used for and why.

this, with a hack to make RB_ASKNAME to wait 5 seconds allows boot -a
work with USB keyboards.  there are still multiple issues remaining:
- discovery and polling need to be mutually exclusive
- attachment of ukbd and wskbd is not handled by config_pending, and
  the 5 second delay isn't going to always be enough.


To generate a diff of this commit:
cvs rdiff -u -r1.263 -r1.264 src/sys/dev/usb/ehci.c
cvs rdiff -u -r1.286 -r1.287 src/sys/dev/usb/ohci.c
cvs rdiff -u -r1.283 -r1.284 src/sys/dev/usb/uhci.c
cvs rdiff -u -r1.171 -r1.172 src/sys/dev/usb/usb.c
cvs rdiff -u -r1.177 -r1.178 src/sys/dev/usb/usbdi.c
cvs rdiff -u -r1.98 -r1.99 src/sys/dev/usb/xhci.c
cvs rdiff -u -r1.54 -r1.55 src/sys/external/bsd/dwc2/dwc2.c

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/sys/dev/usb/ehci.c
diff -u src/sys/dev/usb/ehci.c:1.263 src/sys/dev/usb/ehci.c:1.264
--- src/sys/dev/usb/ehci.c:1.263	Sun Sep 16 09:25:47 2018
+++ src/sys/dev/usb/ehci.c	Sun Sep 16 20:21:56 2018
@@ -1,4 +1,4 @@
-/*	$NetBSD: ehci.c,v 1.263 2018/09/16 09:25:47 skrll Exp $ */
+/*	$NetBSD: ehci.c,v 1.264 2018/09/16 20:21:56 mrg Exp $ */
 
 /*
  * Copyright (c) 2004-2012 The NetBSD Foundation, Inc.
@@ -53,7 +53,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: ehci.c,v 1.263 2018/09/16 09:25:47 skrll Exp $");
+__KERNEL_RCSID(0, "$NetBSD: ehci.c,v 1.264 2018/09/16 20:21:56 mrg Exp $");
 
 #include "ohci.h"
 #include "uhci.h"
@@ -2637,13 +2637,16 @@ Static usbd_status
 ehci_root_intr_start(struct usbd_xfer *xfer)
 {
 	ehci_softc_t *sc = EHCI_XFER2SC(xfer);
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	if (sc->sc_dying)
 		return USBD_IOERROR;
 
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 	sc->sc_intrxfer = xfer;
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 	return USBD_IN_PROGRESS;
 }
@@ -3538,6 +3541,7 @@ ehci_device_ctrl_start(struct usbd_xfer 
 	ehci_softc_t *sc = EHCI_XFER2SC(xfer);
 	ehci_soft_qtd_t *setup, *status, *next;
 	ehci_soft_qh_t *sqh;
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	EHCIHIST_FUNC(); EHCIHIST_CALLED();
 
@@ -3657,7 +3661,8 @@ ehci_device_ctrl_start(struct usbd_xfer 
 	DPRINTFN(5, "--- dump end ---", 0, 0, 0, 0);
 #endif
 
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 
 	/* Insert qTD in QH list - also does usb_syncmem(sqh) */
 	ehci_set_qh_qtd(sqh, setup);
@@ -3667,7 +3672,8 @@ ehci_device_ctrl_start(struct usbd_xfer 
 	}
 	ehci_add_intr_list(sc, exfer);
 	xfer->ux_status = USBD_IN_PROGRESS;
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 #if 0
 #ifdef EHCI_DEBUG
@@ -3814,6 +3820,7 @@ ehci_device_bulk_start(struct usbd_xfer 
 	ehci_soft_qh_t *sqh;
 	ehci_soft_qtd_t *end;
 	int len, isread, endpt;
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	EHCIHIST_FUNC(); EHCIHIST_CALLED();
 
@@ -3837,7 +3844,8 @@ ehci_device_bulk_start(struct usbd_xfer 
 #endif
 
 	/* Take lock here to protect nexttoggle */
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 
 	ehci_reset_sqtd_chain(sc, xfer, len, isread, &epipe->nexttoggle, &end);
 
@@ -3864,7 +3872,8 @@ ehci_device_bulk_start(struct usbd_xfer 
 	}
 	ehci_add_intr_list(sc, exfer);
 	xfer->ux_status = USBD_IN_PROGRESS;
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 #if 0
 #ifdef EHCI_DEBUG
@@ -4029,6 +4038,7 @@ ehci_device_intr_start(struct usbd_xfer 
 	ehci_soft_qtd_t *end;
 	ehci_soft_qh_t *sqh;
 	int len, isread, endpt;
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	EHCIHIST_FUNC(); EHCIHIST_CALLED();
 
@@ -4052,7 +4062,8 @@ ehci_device_intr_start(struct usbd_xfer 
 #endif
 
 	/* Take lock to protect nexttoggle */
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 
 	ehci_reset_sqtd_chain(sc, xfer, len, isread, &epipe->nexttoggle, &end);
 
@@ -4079,7 +4090,8 @@ ehci_device_intr_start(struct usbd_xfer 
 	}
 	ehci_add_intr_list(sc, exfer);
 	xfer->ux_status = USBD_IN_PROGRESS;
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 #if 0
 #ifdef EHCI_DEBUG

Index: src/sys/dev/usb/ohci.c
diff -u src/sys/dev/usb/ohci.c:1.286 src/sys/dev/usb/ohci.c:1.287
--- src/sys/dev/usb/ohci.c:1.286	Sun Sep 16 10:29:39 2018
+++ src/sys/dev/usb/ohci.c	Sun Sep 16 20:21:56 2018
@@ -1,4 +1,4 @@
-/*	$NetBSD: ohci.c,v 1.286 2018/09/16 10:29:39 mrg Exp $	*/
+/*	$NetBSD: ohci.c,v 1.287 2018/09/16 20:21:56 mrg Exp $	*/
 
 /*
  * Copyright (c) 1998, 2004, 2005, 2012 The NetBSD Foundation, Inc.
@@ -41,7 +41,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: ohci.c,v 1.286 2018/09/16 10:29:39 mrg Exp $");
+__KERNEL_RCSID(0, "$NetBSD: ohci.c,v 1.287 2018/09/16 20:21:56 mrg Exp $");
 
 #ifdef _KERNEL_OPT
 #include "opt_usb.h"
@@ -2591,14 +2591,17 @@ Static usbd_status
 ohci_root_intr_start(struct usbd_xfer *xfer)
 {
 	ohci_softc_t *sc = OHCI_XFER2SC(xfer);
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	if (sc->sc_dying)
 		return USBD_IOERROR;
 
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 	KASSERT(sc->sc_intrxfer == NULL);
 	sc->sc_intrxfer = xfer;
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 	return USBD_IN_PROGRESS;
 }
@@ -2732,6 +2735,7 @@ ohci_device_ctrl_start(struct usbd_xfer 
 	ohci_soft_ed_t *sed;
 	int isread;
 	int len;
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	OHCIHIST_FUNC(); OHCIHIST_CALLED();
 
@@ -2750,7 +2754,8 @@ ohci_device_ctrl_start(struct usbd_xfer 
 	    UGETW(req->wIndex));
 
 	/* Need to take lock here for pipe->tail.td */
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 
 	/*
 	 * Use the pipe "tail" TD as our first and loan our first TD to the
@@ -2866,7 +2871,7 @@ ohci_device_ctrl_start(struct usbd_xfer 
 	    sizeof(sed->ed.ed_tailp),
 	    BUS_DMASYNC_PREWRITE | BUS_DMASYNC_PREREAD);
 	OWRITE4(sc, OHCI_COMMAND_STATUS, OHCI_CLF);
-	if (xfer->ux_timeout && !sc->sc_bus.ub_usepolling) {
+	if (xfer->ux_timeout && !polling) {
 		callout_reset(&xfer->ux_callout, mstohz(xfer->ux_timeout),
 			    ohci_timeout, xfer);
 	}
@@ -2874,7 +2879,8 @@ ohci_device_ctrl_start(struct usbd_xfer 
 	DPRINTF("done", 0, 0, 0, 0);
 
 	xfer->ux_status = USBD_IN_PROGRESS;
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 	return USBD_IN_PROGRESS;
 }
@@ -3001,6 +3007,7 @@ ohci_device_bulk_start(struct usbd_xfer 
 	ohci_soft_td_t *data, *tail, *tdp;
 	ohci_soft_ed_t *sed;
 	int len, isread, endpt;
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	OHCIHIST_FUNC(); OHCIHIST_CALLED();
 
@@ -3018,7 +3025,8 @@ ohci_device_bulk_start(struct usbd_xfer 
 	    len, isread, xfer->ux_flags);
 	DPRINTFN(4, "endpt=%jd", endpt, 0, 0, 0);
 
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 
 	/*
 	 * Use the pipe "tail" TD as our first and loan our first TD to the
@@ -3084,7 +3092,8 @@ ohci_device_bulk_start(struct usbd_xfer 
 	}
 
 	xfer->ux_status = USBD_IN_PROGRESS;
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 	return USBD_IN_PROGRESS;
 }
@@ -3203,6 +3212,7 @@ ohci_device_intr_start(struct usbd_xfer 
 	ohci_soft_ed_t *sed = opipe->sed;
 	ohci_soft_td_t *data, *last, *tail;
 	int len, isread, endpt;
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	OHCIHIST_FUNC(); OHCIHIST_CALLED();
 
@@ -3218,7 +3228,8 @@ ohci_device_intr_start(struct usbd_xfer 
 	endpt = xfer->ux_pipe->up_endpoint->ue_edesc->bEndpointAddress;
 	isread = UE_GET_DIR(endpt) == UE_DIR_IN;
 
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 
 	/*
 	 * Use the pipe "tail" TD as our first and loan our first TD to the
@@ -3270,7 +3281,8 @@ ohci_device_intr_start(struct usbd_xfer 
 	    BUS_DMASYNC_PREWRITE | BUS_DMASYNC_PREREAD);
 
 	xfer->ux_status = USBD_IN_PROGRESS;
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 	return USBD_IN_PROGRESS;
 }

Index: src/sys/dev/usb/uhci.c
diff -u src/sys/dev/usb/uhci.c:1.283 src/sys/dev/usb/uhci.c:1.284
--- src/sys/dev/usb/uhci.c:1.283	Mon Sep  3 16:29:34 2018
+++ src/sys/dev/usb/uhci.c	Sun Sep 16 20:21:56 2018
@@ -1,4 +1,4 @@
-/*	$NetBSD: uhci.c,v 1.283 2018/09/03 16:29:34 riastradh Exp $	*/
+/*	$NetBSD: uhci.c,v 1.284 2018/09/16 20:21:56 mrg Exp $	*/
 
 /*
  * Copyright (c) 1998, 2004, 2011, 2012 The NetBSD Foundation, Inc.
@@ -42,7 +42,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: uhci.c,v 1.283 2018/09/03 16:29:34 riastradh Exp $");
+__KERNEL_RCSID(0, "$NetBSD: uhci.c,v 1.284 2018/09/16 20:21:56 mrg Exp $");
 
 #ifdef _KERNEL_OPT
 #include "opt_usb.h"
@@ -1555,7 +1555,7 @@ uhci_idone(struct uhci_xfer *ux, ux_comp
 	struct uhci_pipe *upipe = UHCI_PIPE2UPIPE(xfer->ux_pipe);
 	uhci_soft_td_t *std;
 	uint32_t status = 0, nstatus;
-	bool polling __diagused = sc->sc_bus.ub_usepolling;
+	const bool polling __diagused = sc->sc_bus.ub_usepolling;
 	int actlen;
 
 	KASSERT(polling || mutex_owned(&sc->sc_lock));
@@ -2257,6 +2257,7 @@ uhci_device_bulk_start(struct usbd_xfer 
 	uhci_softc_t *sc = UHCI_XFER2SC(xfer);
 	uhci_soft_td_t *data, *dataend;
 	uhci_soft_qh_t *sqh;
+	const bool polling = sc->sc_bus.ub_usepolling;
 	int len;
 	int endpt;
 	int isread;
@@ -2277,7 +2278,8 @@ uhci_device_bulk_start(struct usbd_xfer 
 	sqh = upipe->bulk.sqh;
 
 	/* Take lock here to protect nexttoggle */
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 
 	uhci_reset_std_chain(sc, xfer, len, isread, &upipe->nexttoggle,
 	    &dataend);
@@ -2311,12 +2313,13 @@ uhci_device_bulk_start(struct usbd_xfer 
 	uhci_add_bulk(sc, sqh);
 	uhci_add_intr_list(sc, ux);
 
-	if (xfer->ux_timeout && !sc->sc_bus.ub_usepolling) {
+	if (xfer->ux_timeout && !polling) {
 		callout_reset(&xfer->ux_callout, mstohz(xfer->ux_timeout),
 			    uhci_timeout, xfer);
 	}
 	xfer->ux_status = USBD_IN_PROGRESS;
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 	return USBD_IN_PROGRESS;
 }
@@ -2541,6 +2544,7 @@ uhci_device_ctrl_start(struct usbd_xfer 
 	int endpt = upipe->pipe.up_endpoint->ue_edesc->bEndpointAddress;
 	uhci_soft_td_t *setup, *stat, *next, *dataend;
 	uhci_soft_qh_t *sqh;
+	const bool polling = sc->sc_bus.ub_usepolling;
 	int len;
 	int isread;
 
@@ -2568,7 +2572,8 @@ uhci_device_ctrl_start(struct usbd_xfer 
 	memcpy(KERNADDR(&upipe->ctrl.reqdma, 0), req, sizeof(*req));
 	usb_syncmem(&upipe->ctrl.reqdma, 0, sizeof(*req), BUS_DMASYNC_PREWRITE);
 
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 
 	/* Set up data transaction */
 	if (len != 0) {
@@ -2665,12 +2670,13 @@ uhci_device_ctrl_start(struct usbd_xfer 
 		DPRINTF("--- dump end ---", 0, 0, 0, 0);
 	}
 #endif
-	if (xfer->ux_timeout && !sc->sc_bus.ub_usepolling) {
+	if (xfer->ux_timeout && !polling) {
 		callout_reset(&xfer->ux_callout, mstohz(xfer->ux_timeout),
 			    uhci_timeout, xfer);
 	}
 	xfer->ux_status = USBD_IN_PROGRESS;
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 	return USBD_IN_PROGRESS;
 }
@@ -2743,6 +2749,7 @@ uhci_device_intr_start(struct usbd_xfer 
 	uhci_softc_t *sc = UHCI_XFER2SC(xfer);
 	uhci_soft_td_t *data, *dataend;
 	uhci_soft_qh_t *sqh;
+	const bool polling = sc->sc_bus.ub_usepolling;
 	int isread, endpt;
 	int i;
 
@@ -2768,7 +2775,7 @@ uhci_device_intr_start(struct usbd_xfer 
 #endif
 
 	/* Take lock to protect nexttoggle */
-	if (!sc->sc_bus.ub_usepolling)
+	if (!polling)
 		mutex_enter(&sc->sc_lock);
 	uhci_reset_std_chain(sc, xfer, xfer->ux_length, isread,
 	    &upipe->nexttoggle, &dataend);
@@ -2801,7 +2808,7 @@ uhci_device_intr_start(struct usbd_xfer 
 	}
 	uhci_add_intr_list(sc, ux);
 	xfer->ux_status = USBD_IN_PROGRESS;
-	if (!sc->sc_bus.ub_usepolling)
+	if (!polling)
 		mutex_exit(&sc->sc_lock);
 
 #ifdef UHCI_DEBUG

Index: src/sys/dev/usb/usb.c
diff -u src/sys/dev/usb/usb.c:1.171 src/sys/dev/usb/usb.c:1.172
--- src/sys/dev/usb/usb.c:1.171	Thu Aug  2 06:09:04 2018
+++ src/sys/dev/usb/usb.c	Sun Sep 16 20:21:56 2018
@@ -1,4 +1,4 @@
-/*	$NetBSD: usb.c,v 1.171 2018/08/02 06:09:04 riastradh Exp $	*/
+/*	$NetBSD: usb.c,v 1.172 2018/09/16 20:21:56 mrg Exp $	*/
 
 /*
  * Copyright (c) 1998, 2002, 2008, 2012 The NetBSD Foundation, Inc.
@@ -37,7 +37,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: usb.c,v 1.171 2018/08/02 06:09:04 riastradh Exp $");
+__KERNEL_RCSID(0, "$NetBSD: usb.c,v 1.172 2018/09/16 20:21:56 mrg Exp $");
 
 #ifdef _KERNEL_OPT
 #include "opt_usb.h"
@@ -375,6 +375,10 @@ usb_doattach(device_t self)
 		sc->sc_dying = 1;
 	}
 
+	/*
+	 * Drop this reference after the first set of attachments in the
+	 * event thread.
+	 */
 	config_pending_incr(self);
 
 	if (!pmf_device_register(self, NULL, NULL))
@@ -529,6 +533,7 @@ void
 usb_event_thread(void *arg)
 {
 	struct usb_softc *sc = arg;
+	struct usbd_bus *bus = sc->sc_bus;
 
 	USBHIST_FUNC(); USBHIST_CALLED(usbdebug);
 
@@ -540,30 +545,37 @@ usb_event_thread(void *arg)
 	 * know how to synchronize the creation of the threads so it
 	 * will work.
 	 */
-	usb_delay_ms(sc->sc_bus, 500);
+	usb_delay_ms(bus, 500);
 
 	/* Make sure first discover does something. */
-	mutex_enter(sc->sc_bus->ub_lock);
+	mutex_enter(bus->ub_lock);
 	sc->sc_bus->ub_needsexplore = 1;
 	usb_discover(sc);
-	mutex_exit(sc->sc_bus->ub_lock);
-	config_pending_decr(sc->sc_bus->ub_usbctl);
+	mutex_exit(bus->ub_lock);
+
+	/* Drop the config_pending reference from attach. */
+	config_pending_decr(bus->ub_usbctl);
 
-	mutex_enter(sc->sc_bus->ub_lock);
+	mutex_enter(bus->ub_lock);
 	while (!sc->sc_dying) {
+#if 0 /* not yet */
+		while (sc->sc_bus->ub_usepolling)
+			kpause("usbpoll", true, hz, bus->ub_lock);
+#endif
+
 		if (usb_noexplore < 2)
 			usb_discover(sc);
 
-		cv_timedwait(&sc->sc_bus->ub_needsexplore_cv,
-		    sc->sc_bus->ub_lock, usb_noexplore ? 0 : hz * 60);
+		cv_timedwait(&bus->ub_needsexplore_cv,
+		    bus->ub_lock, usb_noexplore ? 0 : hz * 60);
 
 		DPRINTFN(2, "sc %#jx woke up", (uintptr_t)sc, 0, 0, 0);
 	}
 	sc->sc_event_thread = NULL;
 
 	/* In case parent is waiting for us to exit. */
-	cv_signal(&sc->sc_bus->ub_needsexplore_cv);
-	mutex_exit(sc->sc_bus->ub_lock);
+	cv_signal(&bus->ub_needsexplore_cv);
+	mutex_exit(bus->ub_lock);
 
 	DPRINTF("sc %#jx exit", (uintptr_t)sc, 0, 0, 0);
 	kthread_exit(0);
@@ -997,25 +1009,28 @@ usbkqfilter(dev_t dev, struct knote *kn)
 Static void
 usb_discover(struct usb_softc *sc)
 {
+	struct usbd_bus *bus = sc->sc_bus;
 
 	USBHIST_FUNC(); USBHIST_CALLED(usbdebug);
 
-	KASSERT(mutex_owned(sc->sc_bus->ub_lock));
+	KASSERT(mutex_owned(bus->ub_lock));
 
 	if (usb_noexplore > 1)
 		return;
+
 	/*
 	 * We need mutual exclusion while traversing the device tree,
 	 * but this is guaranteed since this function is only called
 	 * from the event thread for the controller.
 	 *
-	 * Also, we now have sc_bus->ub_lock held.
+	 * Also, we now have bus->ub_lock held, and in combination
+	 * with ub_exploring, avoids interferring with polling.
 	 */
-	while (sc->sc_bus->ub_needsexplore && !sc->sc_dying) {
-		sc->sc_bus->ub_needsexplore = 0;
+	while (bus->ub_needsexplore && !sc->sc_dying) {
+		bus->ub_needsexplore = 0;
 		mutex_exit(sc->sc_bus->ub_lock);
-		sc->sc_bus->ub_roothub->ud_hub->uh_explore(sc->sc_bus->ub_roothub);
-		mutex_enter(sc->sc_bus->ub_lock);
+		bus->ub_roothub->ud_hub->uh_explore(bus->ub_roothub);
+		mutex_enter(bus->ub_lock);
 	}
 }
 

Index: src/sys/dev/usb/usbdi.c
diff -u src/sys/dev/usb/usbdi.c:1.177 src/sys/dev/usb/usbdi.c:1.178
--- src/sys/dev/usb/usbdi.c:1.177	Thu Aug  9 06:26:47 2018
+++ src/sys/dev/usb/usbdi.c	Sun Sep 16 20:21:56 2018
@@ -1,4 +1,4 @@
-/*	$NetBSD: usbdi.c,v 1.177 2018/08/09 06:26:47 mrg Exp $	*/
+/*	$NetBSD: usbdi.c,v 1.178 2018/09/16 20:21:56 mrg Exp $	*/
 
 /*
  * Copyright (c) 1998, 2012, 2015 The NetBSD Foundation, Inc.
@@ -32,7 +32,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: usbdi.c,v 1.177 2018/08/09 06:26:47 mrg Exp $");
+__KERNEL_RCSID(0, "$NetBSD: usbdi.c,v 1.178 2018/09/16 20:21:56 mrg Exp $");
 
 #ifdef _KERNEL_OPT
 #include "opt_usb.h"
@@ -964,19 +964,19 @@ usb_transfer_complete(struct usbd_xfer *
 	    (uintptr_t)xfer, (uintptr_t)xfer->ux_callback, xfer->ux_status, 0);
 
 	if (xfer->ux_callback) {
-		if (!polling)
+		if (!polling) {
 			mutex_exit(pipe->up_dev->ud_bus->ub_lock);
-
-		if (!(pipe->up_flags & USBD_MPSAFE))
-			KERNEL_LOCK(1, curlwp);
+			if (!(pipe->up_flags & USBD_MPSAFE))
+				KERNEL_LOCK(1, curlwp);
+		}
 
 		xfer->ux_callback(xfer, xfer->ux_priv, xfer->ux_status);
 
-		if (!(pipe->up_flags & USBD_MPSAFE))
-			KERNEL_UNLOCK_ONE(curlwp);
-
-		if (!polling)
+		if (!polling) {
+			if (!(pipe->up_flags & USBD_MPSAFE))
+				KERNEL_UNLOCK_ONE(curlwp);
 			mutex_enter(pipe->up_dev->ud_bus->ub_lock);
+		}
 	}
 
 	if (sync && !polling) {
@@ -1175,7 +1175,8 @@ usbd_dopoll(struct usbd_interface *iface
 }
 
 /*
- * XXX use this more???  ub_usepolling it touched manually all over
+ * This is for keyboard driver as well, which only operates in polling
+ * mode from the ask root, etc., prompt and from DDB.
  */
 void
 usbd_set_polling(struct usbd_device *dev, int on)

Index: src/sys/dev/usb/xhci.c
diff -u src/sys/dev/usb/xhci.c:1.98 src/sys/dev/usb/xhci.c:1.99
--- src/sys/dev/usb/xhci.c:1.98	Mon Sep  3 16:29:34 2018
+++ src/sys/dev/usb/xhci.c	Sun Sep 16 20:21:56 2018
@@ -1,4 +1,4 @@
-/*	$NetBSD: xhci.c,v 1.98 2018/09/03 16:29:34 riastradh Exp $	*/
+/*	$NetBSD: xhci.c,v 1.99 2018/09/16 20:21:56 mrg Exp $	*/
 
 /*
  * Copyright (c) 2013 Jonathan A. Kollasch
@@ -34,7 +34,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: xhci.c,v 1.98 2018/09/03 16:29:34 riastradh Exp $");
+__KERNEL_RCSID(0, "$NetBSD: xhci.c,v 1.99 2018/09/16 20:21:56 mrg Exp $");
 
 #ifdef _KERNEL_OPT
 #include "opt_usb.h"
@@ -3705,15 +3705,18 @@ xhci_root_intr_start(struct usbd_xfer *x
 {
 	struct xhci_softc * const sc = XHCI_XFER2SC(xfer);
 	const size_t bn = XHCI_XFER2BUS(xfer) == &sc->sc_bus ? 0 : 1;
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
 	if (sc->sc_dying)
 		return USBD_IOERROR;
 
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 	sc->sc_intrxfer[bn] = xfer;
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 	return USBD_IN_PROGRESS;
 }
@@ -3791,6 +3794,7 @@ xhci_device_ctrl_start(struct usbd_xfer 
 	uint32_t status;
 	uint32_t control;
 	u_int i;
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 	DPRINTFN(12, "req: %04jx %04jx %04jx %04jx",
@@ -3837,9 +3841,11 @@ xhci_device_ctrl_start(struct usbd_xfer 
 	xhci_trb_put(&xx->xx_trb[i++], parameter, status, control);
 	xfer->ux_status = USBD_IN_PROGRESS;
 
-	mutex_enter(&tr->xr_lock);
+	if (!polling)
+		mutex_enter(&tr->xr_lock);
 	xhci_ring_put(sc, tr, xfer, xx->xx_trb, i);
-	mutex_exit(&tr->xr_lock);
+	if (!polling)
+		mutex_exit(&tr->xr_lock);
 
 	xhci_db_write_4(sc, XHCI_DOORBELL(xs->xs_idx), dci);
 
@@ -3922,6 +3928,7 @@ xhci_device_bulk_start(struct usbd_xfer 
 	uint32_t status;
 	uint32_t control;
 	u_int i = 0;
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	XHCIHIST_FUNC(); XHCIHIST_CALLED();
 
@@ -3955,9 +3962,11 @@ xhci_device_bulk_start(struct usbd_xfer 
 	xhci_trb_put(&xx->xx_trb[i++], parameter, status, control);
 	xfer->ux_status = USBD_IN_PROGRESS;
 
-	mutex_enter(&tr->xr_lock);
+	if (!polling)
+		mutex_enter(&tr->xr_lock);
 	xhci_ring_put(sc, tr, xfer, xx->xx_trb, i);
-	mutex_exit(&tr->xr_lock);
+	if (!polling)
+		mutex_exit(&tr->xr_lock);
 
 	xhci_db_write_4(sc, XHCI_DOORBELL(xs->xs_idx), dci);
 

Index: src/sys/external/bsd/dwc2/dwc2.c
diff -u src/sys/external/bsd/dwc2/dwc2.c:1.54 src/sys/external/bsd/dwc2/dwc2.c:1.55
--- src/sys/external/bsd/dwc2/dwc2.c:1.54	Tue Aug 28 08:17:10 2018
+++ src/sys/external/bsd/dwc2/dwc2.c	Sun Sep 16 20:21:56 2018
@@ -1,4 +1,4 @@
-/*	$NetBSD: dwc2.c,v 1.54 2018/08/28 08:17:10 skrll Exp $	*/
+/*	$NetBSD: dwc2.c,v 1.55 2018/09/16 20:21:56 mrg Exp $	*/
 
 /*-
  * Copyright (c) 2013 The NetBSD Foundation, Inc.
@@ -30,7 +30,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: dwc2.c,v 1.54 2018/08/28 08:17:10 skrll Exp $");
+__KERNEL_RCSID(0, "$NetBSD: dwc2.c,v 1.55 2018/09/16 20:21:56 mrg Exp $");
 
 #include "opt_usb.h"
 
@@ -625,16 +625,19 @@ Static usbd_status
 dwc2_root_intr_start(struct usbd_xfer *xfer)
 {
 	struct dwc2_softc *sc = DWC2_XFER2SC(xfer);
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	DPRINTF("\n");
 
 	if (sc->sc_dying)
 		return USBD_IOERROR;
 
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 	KASSERT(sc->sc_intrxfer == NULL);
 	sc->sc_intrxfer = xfer;
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 	return USBD_IN_PROGRESS;
 }
@@ -702,13 +705,16 @@ dwc2_device_ctrl_start(struct usbd_xfer 
 {
 	struct dwc2_softc *sc = DWC2_XFER2SC(xfer);
 	usbd_status err;
+	const bool polling = sc->sc_bus.ub_usepolling;
 
 	DPRINTF("\n");
 
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 	xfer->ux_status = USBD_IN_PROGRESS;
 	err = dwc2_device_start(xfer);
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 	if (err)
 		return err;
@@ -822,11 +828,14 @@ dwc2_device_intr_start(struct usbd_xfer 
 	struct usbd_device *dev = dpipe->pipe.up_dev;
 	struct dwc2_softc *sc = dev->ud_bus->ub_hcpriv;
 	usbd_status err;
+	const bool polling = sc->sc_bus.ub_usepolling;
 
-	mutex_enter(&sc->sc_lock);
+	if (!polling)
+		mutex_enter(&sc->sc_lock);
 	xfer->ux_status = USBD_IN_PROGRESS;
 	err = dwc2_device_start(xfer);
-	mutex_exit(&sc->sc_lock);
+	if (!polling)
+		mutex_exit(&sc->sc_lock);
 
 	if (err)
 		return err;

Reply via email to