On Sun, Sep 24, 2023 at 11:03:54PM +0300, Vitaliy Makkoveev wrote:
> Please test this diff, I have no midi(4) devices.
> 
> midi(4) already uses `audio_lock' mutex(9) for filterops, but they are
> still kernel locked. Wipe out old selwakeup API and make them MP safe.
> knote_locked(9) will not grab kernel lock, so call it directly from
> interrupt handlers instead of scheduling software interrupts.
> 

Works for me (tested with a usb device), pulling the usb cable
properly wakes up any process waiting for input/output.

ok ratchov@ with the two changes below

> @@ -531,20 +518,8 @@ midiattach(struct device *parent, struct
>       }
>  #endif
>  
> -     sc->inbuf.softintr = softintr_establish(IPL_SOFTMIDI,
> -         midi_buf_wakeup, &sc->inbuf);
> -     if (sc->inbuf.softintr == NULL) {
> -             printf("%s: can't establish input softintr\n", DEVNAME(sc));
> -             return;
> -     }
> -
> -     sc->outbuf.softintr = softintr_establish(IPL_SOFTMIDI,
> -         midi_buf_wakeup, &sc->outbuf);
> -     if (sc->outbuf.softintr == NULL) {
> -             printf("%s: can't establish output softintr\n", DEVNAME(sc));
> -             softintr_disestablish(sc->inbuf.softintr);
> -             return;
> -     }
> +     klist_init_mutex(&sc->inbuf.klist, &audio_lock);
> +     klist_init_mutex(&sc->outbuf.klist, &audio_lock);
>  
>       sc->hw_if = hwif;
>       sc->hw_hdl = hdl;
> @@ -580,27 +555,19 @@ mididetach(struct device *self, int flag
>               KERNEL_ASSERT_LOCKED();
>               if (sc->flags & FREAD) {
>                       wakeup(&sc->inbuf.blocking);
> -                     mtx_enter(&audio_lock);
> -                     selwakeup(&sc->inbuf.sel);
> -                     mtx_leave(&audio_lock);
> +                     knote(&sc->inbuf.klist, 0);

AFAIU, the knote() calls are not necessary because klist_invalidate()
already does the job.

>               }
>               if (sc->flags & FWRITE) {
>                       wakeup(&sc->outbuf.blocking);
> -                     mtx_enter(&audio_lock);
> -                     selwakeup(&sc->outbuf.sel);
> -                     mtx_leave(&audio_lock);
> +                     knote(&sc->outbuf.klist, 0);
>               }
>               sc->hw_if->close(sc->hw_hdl);
>               sc->flags = 0;
>       }
>  
> -     klist_invalidate(&sc->inbuf.sel.si_note);
> -     klist_invalidate(&sc->outbuf.sel.si_note);
> +     klist_invalidate(&sc->inbuf.klist);
> +     klist_invalidate(&sc->outbuf.klist);
>

Could you add two klist_free() calls here? They are simple asserts,
but they'd make the attach/detach functions more midi(4) would look
more like audio(4).

Reply via email to