Re: drm(4), multi-threaded task queues and barriers

2019-06-13 Thread Jonathan Gray
On Thu, Jun 13, 2019 at 11:27:57PM +0200, Mark Kettenis wrote:
> > Date: Wed, 12 Jun 2019 23:57:27 +0200 (CEST)
> > From: Mark Kettenis 
> > 
> > > From: "Sven M. Hallberg" 
> > > Date: Wed, 12 Jun 2019 23:18:24 +0200
> > > 
> > > Mark Kettenis on Tue, Jun 11 2019:
> > > > The drm(4) codebase really needs multi-threaded task queues [...]
> > > >
> > > > The diff also starts 4 threads for each workqueue that gets created by
> > > > the drm(4) layer.  The number 4 is a bit arbitrary but it is the
> > > > number of threads that Linux creates per CPU for a so-called "unbound"
> > > > workqueue which hopefully is enough to always make progress.
> > > > 
> > > > Please test.
> > > 
> > > Looks good and appears to work fine with two displays (one internal, one
> > > external). Will test with three at work tomorrow.
> > > 
> > > 
> > > > -   dev_priv->hotplug.poll_init_work.tq = systq;
> > > 
> > > Intentional?
> > 
> > Yes.  It removes a local modification that should no longer be necessary.
> > 
> > Unfortunately the diff doesn't work with amdgpu.  Some more thinking
> > needed...
> 
> So here is a diff that fixes the problem as far as I can tell.
> Jonathan, Sven, can you give this a go?

This revised diff does not introduce any new problems with amdgpu as
far as I can tell.  Xorg starts/runs, piglit starts and later gets stuck
in dmafence/scheduler related wait channels (as it did before).

> 
> Index: dev/pci/drm/drm_linux.c
> ===
> RCS file: /cvs/src/sys/dev/pci/drm/drm_linux.c,v
> retrieving revision 1.38
> diff -u -p -r1.38 drm_linux.c
> --- dev/pci/drm/drm_linux.c   9 Jun 2019 12:58:30 -   1.38
> +++ dev/pci/drm/drm_linux.c   13 Jun 2019 20:53:23 -
> @@ -1399,15 +1399,15 @@ drm_linux_init(void)
>  {
>   if (system_wq == NULL) {
>   system_wq = (struct workqueue_struct *)
> - taskq_create("drmwq", 1, IPL_HIGH, 0);
> + taskq_create("drmwq", 4, IPL_HIGH, 0);
>   }
>   if (system_unbound_wq == NULL) {
>   system_unbound_wq = (struct workqueue_struct *)
> - taskq_create("drmubwq", 1, IPL_HIGH, 0);
> + taskq_create("drmubwq", 4, IPL_HIGH, 0);
>   }
>   if (system_long_wq == NULL) {
>   system_long_wq = (struct workqueue_struct *)
> - taskq_create("drmlwq", 1, IPL_HIGH, 0);
> + taskq_create("drmlwq", 4, IPL_HIGH, 0);
>   }
>  
>   if (taskletq == NULL)
> Index: dev/pci/drm/i915/intel_hotplug.c
> ===
> RCS file: /cvs/src/sys/dev/pci/drm/i915/intel_hotplug.c,v
> retrieving revision 1.2
> diff -u -p -r1.2 intel_hotplug.c
> --- dev/pci/drm/i915/intel_hotplug.c  14 Apr 2019 10:14:52 -  1.2
> +++ dev/pci/drm/i915/intel_hotplug.c  13 Jun 2019 20:53:23 -
> @@ -619,7 +619,6 @@ void intel_hpd_init_work(struct drm_i915
>   INIT_WORK(&dev_priv->hotplug.hotplug_work, i915_hotplug_work_func);
>   INIT_WORK(&dev_priv->hotplug.dig_port_work, i915_digport_work_func);
>   INIT_WORK(&dev_priv->hotplug.poll_init_work, i915_hpd_poll_init_work);
> - dev_priv->hotplug.poll_init_work.tq = systq;
>   INIT_DELAYED_WORK(&dev_priv->hotplug.reenable_work,
> intel_hpd_irq_storm_reenable_work);
>  }
> Index: kern/kern_task.c
> ===
> RCS file: /cvs/src/sys/kern/kern_task.c,v
> retrieving revision 1.25
> diff -u -p -r1.25 kern_task.c
> --- kern/kern_task.c  28 Apr 2019 04:20:40 -  1.25
> +++ kern/kern_task.c  13 Jun 2019 20:53:23 -
> @@ -43,6 +43,7 @@ struct taskq {
>   TQ_S_DESTROYED
>   }tq_state;
>   unsigned int tq_running;
> + unsigned int tq_waiting;
>   unsigned int tq_nthreads;
>   unsigned int tq_flags;
>   const char  *tq_name;
> @@ -59,6 +60,7 @@ static const char taskq_sys_name[] = "sy
>  struct taskq taskq_sys = {
>   TQ_S_CREATED,
>   0,
> + 0,
>   1,
>   0,
>   taskq_sys_name,
> @@ -77,6 +79,7 @@ static const char taskq_sys_mp_name[] = 
>  struct taskq taskq_sys_mp = {
>   TQ_S_CREATED,
>   0,
> + 0,
>   1,
>   TASKQ_MPSAFE,
>   taskq_sys_mp_name,
> @@ -122,6 +125,7 @@ taskq_create(const char *name, unsigned 
>  
>   tq->tq_state = TQ_S_CREATED;
>   tq->tq_running = 0;
> + tq->tq_waiting = 0;
>   tq->tq_nthreads = nthreads;
>   tq->tq_name = name;
>   tq->tq_flags = flags;
> @@ -223,6 +227,7 @@ taskq_barrier(struct taskq *tq)
>  
>   WITNESS_CHECKORDER(&tq->tq_lock_object, LOP_NEWORDER, NULL);
>  
> + SET(t.t_flags, TASK_BARRIER);
>   task_add(tq, &t);
>   cond_wait(&c, "tqbar");
>  }
> @@ -238,6 +243,7 @@ taskq_del_barrier(struct taskq *tq, stru
>   if (task_del(tq, del))
>   retur

Re: drm(4), multi-threaded task queues and barriers

2019-06-13 Thread Mark Kettenis
> Date: Wed, 12 Jun 2019 23:57:27 +0200 (CEST)
> From: Mark Kettenis 
> 
> > From: "Sven M. Hallberg" 
> > Date: Wed, 12 Jun 2019 23:18:24 +0200
> > 
> > Mark Kettenis on Tue, Jun 11 2019:
> > > The drm(4) codebase really needs multi-threaded task queues [...]
> > >
> > > The diff also starts 4 threads for each workqueue that gets created by
> > > the drm(4) layer.  The number 4 is a bit arbitrary but it is the
> > > number of threads that Linux creates per CPU for a so-called "unbound"
> > > workqueue which hopefully is enough to always make progress.
> > > 
> > > Please test.
> > 
> > Looks good and appears to work fine with two displays (one internal, one
> > external). Will test with three at work tomorrow.
> > 
> > 
> > > - dev_priv->hotplug.poll_init_work.tq = systq;
> > 
> > Intentional?
> 
> Yes.  It removes a local modification that should no longer be necessary.
> 
> Unfortunately the diff doesn't work with amdgpu.  Some more thinking
> needed...

So here is a diff that fixes the problem as far as I can tell.
Jonathan, Sven, can you give this a go?

Index: dev/pci/drm/drm_linux.c
===
RCS file: /cvs/src/sys/dev/pci/drm/drm_linux.c,v
retrieving revision 1.38
diff -u -p -r1.38 drm_linux.c
--- dev/pci/drm/drm_linux.c 9 Jun 2019 12:58:30 -   1.38
+++ dev/pci/drm/drm_linux.c 13 Jun 2019 20:53:23 -
@@ -1399,15 +1399,15 @@ drm_linux_init(void)
 {
if (system_wq == NULL) {
system_wq = (struct workqueue_struct *)
-   taskq_create("drmwq", 1, IPL_HIGH, 0);
+   taskq_create("drmwq", 4, IPL_HIGH, 0);
}
if (system_unbound_wq == NULL) {
system_unbound_wq = (struct workqueue_struct *)
-   taskq_create("drmubwq", 1, IPL_HIGH, 0);
+   taskq_create("drmubwq", 4, IPL_HIGH, 0);
}
if (system_long_wq == NULL) {
system_long_wq = (struct workqueue_struct *)
-   taskq_create("drmlwq", 1, IPL_HIGH, 0);
+   taskq_create("drmlwq", 4, IPL_HIGH, 0);
}
 
if (taskletq == NULL)
Index: dev/pci/drm/i915/intel_hotplug.c
===
RCS file: /cvs/src/sys/dev/pci/drm/i915/intel_hotplug.c,v
retrieving revision 1.2
diff -u -p -r1.2 intel_hotplug.c
--- dev/pci/drm/i915/intel_hotplug.c14 Apr 2019 10:14:52 -  1.2
+++ dev/pci/drm/i915/intel_hotplug.c13 Jun 2019 20:53:23 -
@@ -619,7 +619,6 @@ void intel_hpd_init_work(struct drm_i915
INIT_WORK(&dev_priv->hotplug.hotplug_work, i915_hotplug_work_func);
INIT_WORK(&dev_priv->hotplug.dig_port_work, i915_digport_work_func);
INIT_WORK(&dev_priv->hotplug.poll_init_work, i915_hpd_poll_init_work);
-   dev_priv->hotplug.poll_init_work.tq = systq;
INIT_DELAYED_WORK(&dev_priv->hotplug.reenable_work,
  intel_hpd_irq_storm_reenable_work);
 }
Index: kern/kern_task.c
===
RCS file: /cvs/src/sys/kern/kern_task.c,v
retrieving revision 1.25
diff -u -p -r1.25 kern_task.c
--- kern/kern_task.c28 Apr 2019 04:20:40 -  1.25
+++ kern/kern_task.c13 Jun 2019 20:53:23 -
@@ -43,6 +43,7 @@ struct taskq {
TQ_S_DESTROYED
}tq_state;
unsigned int tq_running;
+   unsigned int tq_waiting;
unsigned int tq_nthreads;
unsigned int tq_flags;
const char  *tq_name;
@@ -59,6 +60,7 @@ static const char taskq_sys_name[] = "sy
 struct taskq taskq_sys = {
TQ_S_CREATED,
0,
+   0,
1,
0,
taskq_sys_name,
@@ -77,6 +79,7 @@ static const char taskq_sys_mp_name[] = 
 struct taskq taskq_sys_mp = {
TQ_S_CREATED,
0,
+   0,
1,
TASKQ_MPSAFE,
taskq_sys_mp_name,
@@ -122,6 +125,7 @@ taskq_create(const char *name, unsigned 
 
tq->tq_state = TQ_S_CREATED;
tq->tq_running = 0;
+   tq->tq_waiting = 0;
tq->tq_nthreads = nthreads;
tq->tq_name = name;
tq->tq_flags = flags;
@@ -223,6 +227,7 @@ taskq_barrier(struct taskq *tq)
 
WITNESS_CHECKORDER(&tq->tq_lock_object, LOP_NEWORDER, NULL);
 
+   SET(t.t_flags, TASK_BARRIER);
task_add(tq, &t);
cond_wait(&c, "tqbar");
 }
@@ -238,6 +243,7 @@ taskq_del_barrier(struct taskq *tq, stru
if (task_del(tq, del))
return;
 
+   SET(t.t_flags, TASK_BARRIER);
task_add(tq, &t);
cond_wait(&c, "tqbar");
 }
@@ -304,13 +310,26 @@ taskq_next_work(struct taskq *tq, struct
struct task *next;
 
mtx_enter(&tq->tq_mtx);
+retry:
while ((next = TAILQ_FIRST(&tq->tq_worklist)) == NULL) {
if (tq->tq_state != TQ_S_RUNNING) {
mtx_leave(&tq->tq_mtx);

upgt: use timeout_add_msec(9)

2019-06-13 Thread Klemens Nanni
Same as with urtw(4) but a tad more obvious:

/usr/include/dev/usb/if_upgtvar.h
312:#define UPGT_LED_ACTION_TMP_DUR 100 /* ms */

OK?

Index: sys/dev/usb/if_upgt.c
===
RCS file: /cvs/src/sys/dev/usb/if_upgt.c,v
retrieving revision 1.83
diff -u -p -r1.83 if_upgt.c
--- sys/dev/usb/if_upgt.c   25 Apr 2019 01:52:14 -  1.83
+++ sys/dev/usb/if_upgt.c   13 Jun 2019 21:18:37 -
@@ -2014,7 +2014,6 @@ upgt_set_led(struct upgt_softc *sc, int 
struct upgt_data *data_cmd = &sc->cmd_data;
struct upgt_lmac_mem *mem;
struct upgt_lmac_led *led;
-   struct timeval t;
int len;
 
/*
@@ -2063,9 +2062,7 @@ upgt_set_led(struct upgt_softc *sc, int 
led->action_tmp_dur = htole16(UPGT_LED_ACTION_TMP_DUR);
/* lock blink */
sc->sc_led_blink = 1;
-   t.tv_sec = 0;
-   t.tv_usec = UPGT_LED_ACTION_TMP_DUR * 1000L;
-   timeout_add(&sc->led_to, tvtohz(&t));
+   timeout_add_msec(&sc->led_to, UPGT_LED_ACTION_TMP_DUR);
break;
default:
return;



urtw: use timeout_add_msec(9)

2019-06-13 Thread Klemens Nanni
Simple sleeps for 100ms that currently use a timeval to specify
miliseconds, convert them to Hz with tvtohz(9) so they can be converted
back by timeout_add(9) - we can do better by now.

I lack appropiate hardware, but the diff is pretty safe imho.  The fact
that the argument has never been zero and will never be with this diff
makes it safe for timeout_add_msec(9) to now always sleep for at least
one tick.

Feedback? OK?

Index: sys/dev/usb/if_urtw.c
===
RCS file: /cvs/src/sys/dev/usb/if_urtw.c,v
retrieving revision 1.67
diff -u -p -r1.67 if_urtw.c
--- sys/dev/usb/if_urtw.c   23 Jan 2018 02:53:26 -  1.67
+++ sys/dev/usb/if_urtw.c   13 Jun 2019 20:56:22 -
@@ -1835,8 +1835,6 @@ fail:
 usbd_status
 urtw_led_mode0(struct urtw_softc *sc, int mode)
 {
-   struct timeval t;
-
switch (mode) {
case URTW_LED_CTL_POWER_ON:
sc->sc_gpio_ledstate = URTW_LED_POWER_ON_BLINK;
@@ -1867,10 +1865,8 @@ urtw_led_mode0(struct urtw_softc *sc, in
sc->sc_gpio_ledinprogress = 1;
sc->sc_gpio_blinkstate = (sc->sc_gpio_ledon != 0) ?
URTW_LED_OFF : URTW_LED_ON;
-   t.tv_sec = 0;
-   t.tv_usec = 100 * 1000L;
if (!usbd_is_dying(sc->sc_udev))
-   timeout_add(&sc->sc_led_ch, tvtohz(&t));
+   timeout_add_msec(&sc->sc_led_ch, 100);
break;
case URTW_LED_POWER_ON_BLINK:
urtw_led_on(sc, URTW_LED_GPIO);
@@ -1952,7 +1948,6 @@ urtw_led_ctl(struct urtw_softc *sc, int 
 usbd_status
 urtw_led_blink(struct urtw_softc *sc)
 {
-   struct timeval t;
uint8_t ing = 0;
usbd_status error;
 
@@ -1987,10 +1982,8 @@ urtw_led_blink(struct urtw_softc *sc)
 
switch (sc->sc_gpio_ledstate) {
case URTW_LED_BLINK_NORMAL:
-   t.tv_sec = 0;
-   t.tv_usec = 100 * 1000L;
if (!usbd_is_dying(sc->sc_udev))
-   timeout_add(&sc->sc_led_ch, tvtohz(&t));
+   timeout_add_msec(&sc->sc_led_ch, 100);
break;
default:
break;



Re: etc/examples/httpd.conf remove acme-challenge location block on port 443

2019-06-13 Thread Klemens Nanni
On Thu, Jun 13, 2019 at 10:08:52AM -0400, Horia Racoviceanu wrote:
> afaik, there is no challenge on port https
https://letsencrypt.org/docs/challenge-types/



Re: etc/examples/httpd.conf remove acme-challenge location block on port 443

2019-06-13 Thread Florian Obser
On Thu, Jun 13, 2019 at 10:08:52AM -0400, Horia Racoviceanu wrote:
> afaik, there is no challenge on port https

That is true, kinda:

RFC 8555, 8.3 HTTP Challenge, page 63:

Because many web servers allocate a default HTTPS virtual host to a
particular low-privilege tenant user in a subtle and non-intuitive
manner, the challenge must be completed over HTTP, not HTTPS.

(Not quite sure what they are going on about though)

However, https://letsencrypt.org/docs/challenge-types/

Our implementation of the HTTP-01 challenge follows redirects, up to
10 redirects deep. It only accepts redirects to "http:" or "https:",
and only to ports 80 or 443.

I could swear that Let's Encrypt actually probed on 443 in case of a
renew in the past. I don't think they do that anymore. (And the
documentation suggests that they don't and only follow redirects.)

I'm fine with the change. But I'm also fine with keeping it, with a
slight preference towards deletion.

> Index: httpd.conf
> ===
> RCS file: /cvs/src/etc/examples/httpd.conf,v
> retrieving revision 1.20
> diff -u -p -r1.20 httpd.conf
> --- httpd.conf13 Jun 2018 15:08:24 -  1.20
> +++ httpd.conf13 Jun 2019 13:57:56 -
> @@ -20,8 +20,4 @@ server "example.com" {
>   location "/pub/*" {
>   directory auto index
>   }
> - location "/.well-known/acme-challenge/*" {
> - root "/acme"
> - request strip 2
> - }
>  }


-- 
I'm not entirely sure you are real.



Re: etc/examples/doas.conf add persist for group wheel

2019-06-13 Thread Theo de Raadt
Horia Racoviceanu  wrote:

> - for convenience, and perhaps best practice

Nope.



etc/examples/httpd.conf remove acme-challenge location block on port 443

2019-06-13 Thread Horia Racoviceanu
afaik, there is no challenge on port https
Index: httpd.conf
===
RCS file: /cvs/src/etc/examples/httpd.conf,v
retrieving revision 1.20
diff -u -p -r1.20 httpd.conf
--- httpd.conf  13 Jun 2018 15:08:24 -  1.20
+++ httpd.conf  13 Jun 2019 13:57:56 -
@@ -20,8 +20,4 @@ server "example.com" {
location "/pub/*" {
directory auto index
}
-   location "/.well-known/acme-challenge/*" {
-   root "/acme"
-   request strip 2
-   }
 }


etc/examples/doas.conf add persist for group wheel

2019-06-13 Thread Horia Racoviceanu
- for convenience, and perhaps best practice
Index: doas.conf
===
RCS file: /cvs/src/etc/examples/doas.conf,v
retrieving revision 1.1
diff -u -p -r1.1 doas.conf
--- doas.conf   3 Sep 2016 11:58:32 -   1.1
+++ doas.conf   13 Jun 2019 13:57:38 -
@@ -11,4 +11,4 @@
 #SUBPACKAGE WRKOBJDIR SUDO_PORT_V1 } :wsrc
 
 # Allow wheel by default
-permit keepenv :wheel
+permit persist keepenv :wheel


Re: drm(4), multi-threaded task queues and barriers

2019-06-13 Thread Sven M. Hallberg
Mark Kettenis on Wed, Jun 12 2019:
>> Looks good and appears to work fine with two displays (one internal, one
>> external). Will test with three at work tomorrow.

Your diff also works for me with three displays (inteldrm).

> Unfortunately the diff doesn't work with amdgpu.  Some more thinking
> needed...

I would be interested to hear what the issue is.

Regards,
pesco



Re: About transient mark mode

2019-06-13 Thread Mark Lumsden
Leonid's diff would seem to be an improvement on current behaviour, any 
objections to adding it to mg? Or comments/ok?


Mark


From openbsd-tech  Tue Jun 11 15:16:29 2019

From: Leonid Bobrov 
Date: Tue, 11 Jun 2019 15:16:29 +
To: openbsd-tech
Subject: About transient mark mode
Message-Id: <20190611151629.GA7591 () mazocomp ! lan>
X-MARC-Message: https://marc.info/?l=openbsd-tech&m=156026622527096

Hi!

If we don't have to follow what GNU Emacs is doing anyway, let's just
change behavior of {beginning,end}-of-buffer to this instead of
implementing a useless mode:

Index: basic.c
===
RCS file: /cvs/src/usr.bin/mg/basic.c,v
retrieving revision 1.48
diff -u -p -r1.48 basic.c
--- basic.c 3 Jun 2019 16:26:30 -   1.48
+++ basic.c 11 Jun 2019 15:15:15 -
@@ -124,7 +124,8 @@ forwchar(int f, int n)
 int
 gotobob(int f, int n)
 {
-   (void) setmark(f, n);
+   if (!curwp->w_markp)
+   (void) setmark(f, n);
curwp->w_dotp = bfirstlp(curbp);
curwp->w_doto = 0;
curwp->w_rflag |= WFFULL;
@@ -150,7 +151,8 @@ gotoeob(int f, int n)
int  ln;
struct line *lp;

-   (void) setmark(f, n);
+   if (!curwp->w_markp)
+   (void) setmark(f, n);
curwp->w_dotp = blastlp(curbp);
curwp->w_doto = llength(curwp->w_dotp);
curwp->w_dotline = curwp->w_bufp->b_lines;
Index: mg.1
===
RCS file: /cvs/src/usr.bin/mg/mg.1,v
retrieving revision 1.114
diff -u -p -r1.114 mg.1
--- mg.16 Jun 2019 18:17:34 -   1.114
+++ mg.111 Jun 2019 15:15:15 -
@@ -1,7 +1,7 @@
 .\"   $OpenBSD: mg.1,v 1.114 2019/06/06 18:17:34 jmc Exp $
 .\" This file is in the public domain.
 .\"
-.Dd $Mdocdate: June 6 2019 $
+.Dd $Mdocdate: June 11 2019 $
 .Dt MG 1
 .Os
 .Sh NAME
@@ -408,6 +408,7 @@ Move cursor to the top of the buffer.
 A numeric argument
 .Va n
 will move n/10th of the way from the top.
+Set mark at previous position if mark is not set.
 .It beginning-of-line
 Move cursor to the beginning of the line.
 .It blink-and-insert
@@ -532,6 +533,7 @@ Move cursor to the end of the buffer.
 A numeric argument
 .Va n
 will move n/10th of the way from the end.
+Set mark at previous position if mark is not set.
 .It end-of-line
 Move cursor to the end of the line.
 .It enlarge-window
Index: region.c
===
RCS file: /cvs/src/usr.bin/mg/region.c,v
retrieving revision 1.37
diff -u -p -r1.37 region.c
--- region.c9 Sep 2016 06:05:51 -   1.37
+++ region.c11 Jun 2019 15:15:15 -
@@ -405,6 +405,7 @@ markbuffer(int f, int n)
 {
if (gotoeob(f,n) == FALSE)
return (FALSE);
+   (void) clearmark(f, n);
if (gotobob(f,n) == FALSE)
return (FALSE);
return (TRUE);



Re: expose host capabilities relative to usb isochronous xfers

2019-06-13 Thread Alexandre Ratchov
On Thu, Jun 13, 2019 at 06:03:03AM +0300, Artturi Alm wrote:
> On Wed, Jun 12, 2019 at 03:55:59PM +0200, Alexandre Ratchov wrote:
> > Currenty USB device driver code has no way to obtain how many frames
> > can be scheduled on the HC. If it attempts to schedule too many
> > frames, usbd_transfer() fails or silently misbehaves.
> > 
> > For audio this is a big problem because the max frames count
> > determines the block size which must be reported to upper layers
> > before any transfer starts. This makes impossible to implement uaudio
> > properly. Currently there's a temporary hack to workaround this, which
> > limits the block size. Now that uaudio is in and works, it's time to
> > start removing such hacks.
> > 
> > Similarly, driver code needs to know the minimum number of frames per
> > transfer to get an interrupt (ie the completion callback). Indeed, if
> > the transfer frame count is not rounded to it, we silently miss the
> > interrupt, the completion call-back is not called and playback
> > stutters.
> > 
> > The diff below adds a new usbd_bus_info() function which reports the
> > maximum frames that can be scheduled and the minimum frames per
> > transfer to get an interrupt.
> > 
> > [snip]
> > Index: usbdi.c
> > ===
> > RCS file: /cvs/src/sys/dev/usb/usbdi.c,v
> > retrieving revision 1.100
> > diff -u -p -u -p -r1.100 usbdi.c
> > --- usbdi.c 18 Nov 2018 16:33:26 -  1.100
> > +++ usbdi.c 12 Jun 2019 13:33:41 -
> > @@ -275,6 +275,12 @@ usbd_close_pipe(struct usbd_pipe *pipe)
> > return (USBD_NORMAL_COMPLETION);
> >  }
> >  
> > +void
> > +usbd_bus_info(struct usbd_device *dev, struct usbd_bus_info *info)
> > +{
> > +   dev->bus->methods->info(dev, info);
> > +}
> > +
> >  usbd_status
> >  usbd_transfer(struct usbd_xfer *xfer)
> >  {
> > [snip]
> 
> i think above is not good enough with only ehci, ohci, uhci and xhci
> being taken care of in [snip]'ed parts of the diff unfortunately:]
> just thinking about dwc2.
> 

Thanks. I grep'ed for usbd_bus_methods, and dwc2 seems to be the only
one I missed. Below is a new diff with dwc2 bits and few fixes. I've
no arm/octeon machines to test, anyone has one for a quick test?

Interestingly, dwc2 supports at most DWC2_MAXISOCPACKETS frames, which
is defined to 16 only. Without this diff, the uaudio driver would
attempt to schedule ~48 frames which would trigger a KASSERT() in
dwc2_device_start() immediately.

BTW, 16 is too small for usb2.0 devices to work at all. I'd recommend
512, which is two blocks of 20ms each.

Index: ehci.c
===
RCS file: /cvs/src/sys/dev/usb/ehci.c,v
retrieving revision 1.204
diff -u -p -r1.204 ehci.c
--- ehci.c  31 Mar 2019 06:16:38 -  1.204
+++ ehci.c  13 Jun 2019 07:25:31 -
@@ -113,6 +113,7 @@ struct ehci_pipe {
 u_int8_t   ehci_reverse_bits(u_int8_t, int);
 
 usbd_statusehci_open(struct usbd_pipe *);
+void   ehci_info(struct usbd_device *, struct usbd_bus_info *);
 intehci_setaddr(struct usbd_device *, int);
 void   ehci_poll(struct usbd_bus *);
 void   ehci_softintr(void *);
@@ -225,6 +226,7 @@ struct usbd_bus_methods ehci_bus_methods
.do_poll = ehci_poll,
.allocx = ehci_allocx,
.freex = ehci_freex,
+   .info = ehci_info,
 };
 
 struct usbd_pipe_methods ehci_root_ctrl_methods = {
@@ -491,6 +493,21 @@ ehci_init(struct ehci_softc *sc)
sc->sc_flsize * sizeof(struct ehci_soft_itd *));
usb_freemem(&sc->sc_bus, &sc->sc_fldma);
return (err);
+}
+
+void
+ehci_info(struct usbd_device *dev, struct usbd_bus_info *info)
+{
+   /*
+* XXX: even if most hosts have 1024 frame lists, only 256
+* frame transfers work reliably. As soon as 256 is exceeded,
+* we start getting zeroed frames if multiple device are
+* running simultaneously. Set this to sc->sc_fl_size, once
+* ehci is fixed. Interrups occur every 1m, despite the
+* EHCI_CMD_ITC_2 setting.
+*/
+   info->nframes_max = 256;
+   info->intr_thres = (dev->speed >= USB_SPEED_HIGH) ? 8 : 1;
 }
 
 int
Index: ohci.c
===
RCS file: /cvs/src/sys/dev/usb/ohci.c,v
retrieving revision 1.156
diff -u -p -r1.156 ohci.c
--- ohci.c  11 Mar 2019 17:50:08 -  1.156
+++ ohci.c  13 Jun 2019 07:25:32 -
@@ -87,6 +87,7 @@ usbd_status   ohci_alloc_std_chain(struct 
struct ohci_soft_td **);
 
 usbd_statusohci_open(struct usbd_pipe *);
+void   ohci_info(struct usbd_device *, struct usbd_bus_info *);
 intohci_setaddr(struct usbd_device *, int);
 void   ohci_poll(struct usbd_bus *);
 void   ohci_softintr(void *);
@@ -236,6 +237,7 @@ struct usbd_bus_methods ohci_bus_methods
.do_poll = ohci_poll,
.allocx = ohci_allocx,