summaryrefslogtreecommitdiff
path: root/sys/arch/sparc64/dev
diff options
context:
space:
mode:
Diffstat (limited to 'sys/arch/sparc64/dev')
-rw-r--r--sys/arch/sparc64/dev/vbus.c45
-rw-r--r--sys/arch/sparc64/dev/vbusvar.h6
-rw-r--r--sys/arch/sparc64/dev/vcons.c25
3 files changed, 57 insertions, 19 deletions
diff --git a/sys/arch/sparc64/dev/vbus.c b/sys/arch/sparc64/dev/vbus.c
index 11894593e8e..381876fd85e 100644
--- a/sys/arch/sparc64/dev/vbus.c
+++ b/sys/arch/sparc64/dev/vbus.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: vbus.c,v 1.10 2017/12/22 15:52:36 kettenis Exp $ */
+/* $OpenBSD: vbus.c,v 1.11 2018/06/27 11:38:59 kettenis Exp $ */
/*
* Copyright (c) 2008 Mark Kettenis
*
@@ -190,6 +190,34 @@ vbus_intr_map(int node, int ino, uint64_t *sysino)
return (-1);
}
+int
+vbus_intr_setstate(bus_space_tag_t t, uint64_t sysino, uint64_t state)
+{
+ struct vbus_softc *sc = t->cookie;
+ uint64_t devhandle = sc->sc_devhandle;
+ int err;
+
+ err = sun4v_intr_setstate(devhandle, sysino, state);
+ if (err != H_EOK)
+ return (-1);
+
+ return (0);
+}
+
+int
+vbus_intr_setenabled(bus_space_tag_t t, uint64_t sysino, uint64_t enabled)
+{
+ struct vbus_softc *sc = t->cookie;
+ uint64_t devhandle = sc->sc_devhandle;
+ int err;
+
+ err = sun4v_intr_setenabled(devhandle, sysino, enabled);
+ if (err != H_EOK)
+ return (-1);
+
+ return (0);
+}
+
void *
vbus_intr_establish(bus_space_tag_t t, bus_space_tag_t t0, int ihandle,
int level, int flags, int (*handler)(void *), void *arg, const char *what)
@@ -208,6 +236,10 @@ vbus_intr_establish(bus_space_tag_t t, bus_space_tag_t t0, int ihandle,
if (flags & BUS_INTR_ESTABLISH_MPSAFE)
ih->ih_mpsafe = 1;
+ err = sun4v_intr_setenabled(devhandle, sysino, INTR_DISABLED);
+ if (err != H_EOK)
+ return (NULL);
+
err = sun4v_intr_setcookie(devhandle, sysino, (vaddr_t)ih);
if (err != H_EOK)
return (NULL);
@@ -224,22 +256,13 @@ vbus_intr_establish(bus_space_tag_t t, bus_space_tag_t t0, int ihandle,
if (err != H_EOK)
return (NULL);
- err = sun4v_intr_setenabled(devhandle, sysino, INTR_ENABLED);
- if (err != H_EOK)
- return (NULL);
-
return (ih);
}
void
vbus_intr_ack(struct intrhand *ih)
{
- bus_space_tag_t t = ih->ih_bus;
- struct vbus_softc *sc = t->cookie;
- uint64_t devhandle = sc->sc_devhandle;
- uint64_t sysino = INTVEC(ih->ih_number);
-
- sun4v_intr_setstate(devhandle, sysino, INTR_IDLE);
+ /* Drivers explicitly ack interrupts. */
}
bus_space_tag_t
diff --git a/sys/arch/sparc64/dev/vbusvar.h b/sys/arch/sparc64/dev/vbusvar.h
index 74439df8011..ebc2cee462b 100644
--- a/sys/arch/sparc64/dev/vbusvar.h
+++ b/sys/arch/sparc64/dev/vbusvar.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: vbusvar.h,v 1.3 2008/12/30 21:23:33 kettenis Exp $ */
+/* $OpenBSD: vbusvar.h,v 1.4 2018/06/27 11:38:59 kettenis Exp $ */
/*
* Copyright (c) 2008 Mark Kettenis
*
@@ -32,6 +32,8 @@ struct vbus_attach_args {
int va_nintr;
};
-int vbus_intr_map(int, int, uint64_t *);
+int vbus_intr_map(int, int, uint64_t *);
+int vbus_intr_setstate(bus_space_tag_t, uint64_t, uint64_t);
+int vbus_intr_setenabled(bus_space_tag_t, uint64_t, uint64_t);
#endif
diff --git a/sys/arch/sparc64/dev/vcons.c b/sys/arch/sparc64/dev/vcons.c
index 3e138ed2734..df533c062e5 100644
--- a/sys/arch/sparc64/dev/vcons.c
+++ b/sys/arch/sparc64/dev/vcons.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: vcons.c,v 1.16 2018/02/19 08:59:52 mpi Exp $ */
+/* $OpenBSD: vcons.c,v 1.17 2018/06/27 11:38:59 kettenis Exp $ */
/*
* Copyright (c) 2008 Mark Kettenis
*
@@ -36,7 +36,10 @@
struct vcons_softc {
struct device sc_dv;
+ bus_space_tag_t sc_bustag;
+
void *sc_ih;
+ uint64_t sc_sysino;
struct tty *sc_tty;
void *sc_si;
};
@@ -78,7 +81,6 @@ vcons_attach(struct device *parent, struct device *self, void *aux)
{
struct vcons_softc *sc = (struct vcons_softc *)self;
struct vbus_attach_args *va = aux;
- uint64_t sysino;
int vcons_is_input, vcons_is_output;
int node, maj;
@@ -86,11 +88,12 @@ vcons_attach(struct device *parent, struct device *self, void *aux)
if (sc->sc_si == NULL)
panic(": can't establish soft interrupt");
- if (vbus_intr_map(va->va_node, va->va_intr[0], &sysino))
+ if (vbus_intr_map(va->va_node, va->va_intr[0], &sc->sc_sysino))
printf(": can't map interrupt\n");
- printf(": ivec 0x%llx", sysino);
+ printf(": ivec 0x%llx", sc->sc_sysino);
- sc->sc_ih = bus_intr_establish(va->va_bustag, sysino, IPL_TTY,
+ sc->sc_bustag = va->va_bustag;
+ sc->sc_ih = bus_intr_establish(sc->sc_bustag, sc->sc_sysino, IPL_TTY,
BUS_INTR_ESTABLISH_MPSAFE, vcons_intr, sc, sc->sc_dv.dv_xname);
if (sc->sc_ih == NULL) {
printf(", can't establish interrupt\n");
@@ -129,6 +132,7 @@ vcons_intr(void *arg)
if (sc->sc_tty)
softintr_schedule(sc->sc_si);
+
return (1);
}
@@ -172,6 +176,7 @@ vconsopen(dev_t dev, int flag, int mode, struct proc *p)
struct vcons_softc *sc;
struct tty *tp;
int unit = minor(dev);
+ int err;
if (unit >= vcons_cd.cd_ndevs)
return (ENXIO);
@@ -199,7 +204,11 @@ vconsopen(dev_t dev, int flag, int mode, struct proc *p)
return (EBUSY);
tp->t_state |= TS_CARR_ON;
- return ((*linesw[tp->t_line].l_open)(dev, tp, p));
+ err = (*linesw[tp->t_line].l_open)(dev, tp, p);
+ if (err == 0)
+ vbus_intr_setenabled(sc->sc_bustag, sc->sc_sysino, INTR_ENABLED);
+
+ return err;
}
int
@@ -215,6 +224,8 @@ vconsclose(dev_t dev, int flag, int mode, struct proc *p)
if (sc == NULL)
return (ENXIO);
+ vbus_intr_setenabled(sc->sc_bustag, sc->sc_sysino, INTR_DISABLED);
+
tp = sc->sc_tty;
(*linesw[tp->t_line].l_close)(tp, flag, p);
ttyclose(tp);
@@ -346,4 +357,6 @@ vcons_softintr(void *arg)
if (tp->t_state & TS_ISOPEN)
(*linesw[tp->t_line].l_rint)(c, tp);
}
+
+ vbus_intr_setstate(sc->sc_bustag, sc->sc_sysino, INTR_IDLE);
}