diff options
author | anton <anton@cvs.openbsd.org> | 2018-11-19 19:19:25 +0000 |
---|---|---|
committer | anton <anton@cvs.openbsd.org> | 2018-11-19 19:19:25 +0000 |
commit | fd8856b4c3298aeafc2766dc60c782e3c5257d94 (patch) | |
tree | f3676b3f913ac4656082032bf4e757e40c2eed85 /sys | |
parent | 6872c56497ebd6722c499ebcef8c07ee73a930a2 (diff) |
Utilize sigio with wscons. The old behavior of always making the process group
of the process who opens the device the default recipient of sigio is removed as
a side-effect of this change. Issuing ioctl(FIOSETOWN) is therefore mandatory in
order to receive sigio, which is more consistent with other subsystems
supporting sigio.
This change is all made possible by the new sigio(9) API and prevents wscons
from keeping a pointer to the recipient process. Usage of such pointer could
cause a panic since wscons is not inform on process deallocation, leaving a
dangling pointer behind.
ok mpi@ visa@
Diffstat (limited to 'sys')
-rw-r--r-- | sys/dev/wscons/wsevent.c | 6 | ||||
-rw-r--r-- | sys/dev/wscons/wseventvar.h | 8 | ||||
-rw-r--r-- | sys/dev/wscons/wskbd.c | 23 | ||||
-rw-r--r-- | sys/dev/wscons/wsmouse.c | 24 | ||||
-rw-r--r-- | sys/dev/wscons/wsmux.c | 14 |
5 files changed, 38 insertions, 37 deletions
diff --git a/sys/dev/wscons/wsevent.c b/sys/dev/wscons/wsevent.c index 52e0096440b..993a33e45ec 100644 --- a/sys/dev/wscons/wsevent.c +++ b/sys/dev/wscons/wsevent.c @@ -1,4 +1,4 @@ -/* $OpenBSD: wsevent.c,v 1.17 2017/04/11 14:43:49 dhill Exp $ */ +/* $OpenBSD: wsevent.c,v 1.18 2018/11/19 19:19:24 anton Exp $ */ /* $NetBSD: wsevent.c,v 1.16 2003/08/07 16:31:29 agc Exp $ */ /* @@ -111,6 +111,8 @@ wsevent_init(struct wseventvar *ev) ev->get = ev->put = 0; ev->q = malloc(WSEVENT_QSIZE * sizeof(struct wscons_event), M_DEVBUF, M_WAITOK | M_ZERO); + + sigio_init(&ev->sigio); } /* @@ -127,6 +129,8 @@ wsevent_fini(struct wseventvar *ev) } free(ev->q, M_DEVBUF, 0); ev->q = NULL; + + sigio_free(&ev->sigio); } /* diff --git a/sys/dev/wscons/wseventvar.h b/sys/dev/wscons/wseventvar.h index f959486c9ee..5424fff9dc5 100644 --- a/sys/dev/wscons/wseventvar.h +++ b/sys/dev/wscons/wseventvar.h @@ -1,4 +1,4 @@ -/* $OpenBSD: wseventvar.h,v 1.8 2015/09/10 18:14:52 mpi Exp $ */ +/* $OpenBSD: wseventvar.h,v 1.9 2018/11/19 19:19:24 anton Exp $ */ /* $NetBSD: wseventvar.h,v 1.1 1998/03/22 14:24:03 drochner Exp $ */ /* @@ -71,6 +71,8 @@ * @(#)event_var.h 8.1 (Berkeley) 6/11/93 */ +#include <sys/sigio.h> + /* * Internal "wscons_event" queue interface for the keyboard and mouse drivers. * The drivers are expected not to place events in the queue above spltty(), @@ -84,7 +86,7 @@ struct wseventvar { u_int get; /* get (read) index (modified synchronously) */ volatile u_int put; /* put (write) index (modified by interrupt) */ struct selinfo sel; /* process selecting */ - struct process *io; /* process that opened queue (can get SIGIO) */ + struct sigio_ref sigio; /* async I/O registration */ int wanted; /* wake up on input ready */ int async; /* send SIGIO on input ready */ struct wscons_event *q; /* circular buffer (queue) of events */ @@ -99,7 +101,7 @@ struct wseventvar { wakeup((caddr_t)(ev)); \ } \ if ((ev)->async) \ - pgsignal((ev)->io->ps_pgrp, SIGIO, 0); \ + pgsigio(&(ev)->sigio, SIGIO, 0); \ } void wsevent_init(struct wseventvar *); diff --git a/sys/dev/wscons/wskbd.c b/sys/dev/wscons/wskbd.c index ed37b923606..9b26a5eef42 100644 --- a/sys/dev/wscons/wskbd.c +++ b/sys/dev/wscons/wskbd.c @@ -1,4 +1,4 @@ -/* $OpenBSD: wskbd.c,v 1.91 2018/04/18 10:24:32 mpi Exp $ */ +/* $OpenBSD: wskbd.c,v 1.92 2018/11/19 19:19:24 anton Exp $ */ /* $NetBSD: wskbd.c,v 1.80 2005/05/04 01:52:16 augustss Exp $ */ /* @@ -603,7 +603,7 @@ wskbd_detach(struct device *self, int flags) } evar = sc->sc_base.me_evp; - if (evar != NULL && evar->io != NULL) { + if (evar != NULL) { s = spltty(); if (--sc->sc_refcnt >= 0) { /* Wake everyone by generating a dummy event. */ @@ -823,7 +823,6 @@ wskbdopen(dev_t dev, int flags, int mode, struct proc *p) evar = &sc->sc_base.me_evar; wsevent_init(evar); - evar->io = p->p_p; error = wskbd_do_open(sc, evar); if (error) { @@ -942,6 +941,7 @@ int wskbd_do_ioctl_sc(struct wskbd_softc *sc, u_long cmd, caddr_t data, int flag, struct proc *p) { + struct wseventvar *evar; int error; /* @@ -958,19 +958,18 @@ wskbd_do_ioctl_sc(struct wskbd_softc *sc, u_long cmd, caddr_t data, int flag, return (0); case FIOSETOWN: - if (sc->sc_base.me_evp == NULL) + evar = sc->sc_base.me_evp; + if (evar == NULL) return (EINVAL); - if (-*(int *)data != sc->sc_base.me_evp->io->ps_pgid && - *(int *)data != sc->sc_base.me_evp->io->ps_pid) - return (EPERM); - return (0); + return (sigio_setown(&evar->sigio, *(int *)data)); case TIOCSPGRP: - if (sc->sc_base.me_evp == NULL) + if (*(int *)data < 0) return (EINVAL); - if (*(int *)data != sc->sc_base.me_evp->io->ps_pgid) - return (EPERM); - return (0); + evar = sc->sc_base.me_evp; + if (evar == NULL) + return (EINVAL); + return (sigio_setown(&evar->sigio, -*(int *)data)); } /* diff --git a/sys/dev/wscons/wsmouse.c b/sys/dev/wscons/wsmouse.c index ca23252e786..ec6c0dd0923 100644 --- a/sys/dev/wscons/wsmouse.c +++ b/sys/dev/wscons/wsmouse.c @@ -1,4 +1,4 @@ -/* $OpenBSD: wsmouse.c,v 1.47 2018/11/11 01:49:04 deraadt Exp $ */ +/* $OpenBSD: wsmouse.c,v 1.48 2018/11/19 19:19:24 anton Exp $ */ /* $NetBSD: wsmouse.c,v 1.35 2005/02/27 00:27:52 perry Exp $ */ /* @@ -261,7 +261,7 @@ wsmouse_detach(struct device *self, int flags) /* If we're open ... */ evar = sc->sc_base.me_evp; - if (evar != NULL && evar->io != NULL) { + if (evar != NULL) { s = spltty(); if (--sc->sc_refcnt >= 0) { /* Wake everyone by generating a dummy event. */ @@ -327,7 +327,6 @@ wsmouseopen(dev_t dev, int flags, int mode, struct proc *p) evar = &sc->sc_base.me_evar; wsevent_init(evar); - evar->io = p->p_p; error = wsmousedoopen(sc, evar); if (error) { @@ -471,6 +470,7 @@ int wsmouse_do_ioctl(struct wsmouse_softc *sc, u_long cmd, caddr_t data, int flag, struct proc *p) { + struct wseventvar *evar; int error; if (sc->sc_dying) @@ -499,19 +499,19 @@ wsmouse_do_ioctl(struct wsmouse_softc *sc, u_long cmd, caddr_t data, int flag, return (0); case FIOSETOWN: - if (sc->sc_base.me_evp == NULL) + evar = sc->sc_base.me_evp; + if (evar == NULL) return (EINVAL); - if (-*(int *)data != sc->sc_base.me_evp->io->ps_pgid - && *(int *)data != sc->sc_base.me_evp->io->ps_pid) - return (EPERM); - return (0); + return (sigio_setown(&evar->sigio, *(int *)data)); case TIOCSPGRP: - if (sc->sc_base.me_evp == NULL) + if (*(int *)data < 0) return (EINVAL); - if (*(int *)data != sc->sc_base.me_evp->io->ps_pgid) - return (EPERM); - return (0); + evar = sc->sc_base.me_evp; + if (evar == NULL) + return (EINVAL); + return (sigio_setown(&evar->sigio, -*(int *)data)); + case WSMOUSEIO_GETPARAMS: case WSMOUSEIO_SETPARAMS: return (wsmouse_param_ioctl(sc, cmd, diff --git a/sys/dev/wscons/wsmux.c b/sys/dev/wscons/wsmux.c index c8654dc01e1..11710829475 100644 --- a/sys/dev/wscons/wsmux.c +++ b/sys/dev/wscons/wsmux.c @@ -1,4 +1,4 @@ -/* $OpenBSD: wsmux.c,v 1.32 2017/06/12 13:45:39 deraadt Exp $ */ +/* $OpenBSD: wsmux.c,v 1.33 2018/11/19 19:19:24 anton Exp $ */ /* $NetBSD: wsmux.c,v 1.37 2005/04/30 03:47:12 augustss Exp $ */ /* @@ -192,7 +192,6 @@ wsmuxopen(dev_t dev, int flags, int mode, struct proc *p) evar = &sc->sc_base.me_evar; wsevent_init(evar); - evar->io = p->p_p; #ifdef WSDISPLAY_COMPAT_RAWKBD sc->sc_rawkbd = 0; #endif @@ -476,18 +475,15 @@ wsmux_do_ioctl(struct device *dv, u_long cmd, caddr_t data, int flag, evar = sc->sc_base.me_evp; if (evar == NULL) return (EINVAL); - if (-*(int *)data != evar->io->ps_pgid - && *(int *)data != evar->io->ps_pid) - return (EPERM); - return (0); + return (sigio_setown(&evar->sigio, *(int *)data)); case TIOCSPGRP: DPRINTF(("%s: TIOCSPGRP\n", sc->sc_base.me_dv.dv_xname)); + if (*(int *)data < 0) + return (EINVAL); evar = sc->sc_base.me_evp; if (evar == NULL) return (EINVAL); - if (*(int *)data != evar->io->ps_pgid) - return (EPERM); - return (0); + return (sigio_setown(&evar->sigio, -*(int *)data)); default: DPRINTF(("%s: unknown\n", sc->sc_base.me_dv.dv_xname)); break; |