summaryrefslogtreecommitdiff
path: root/sys
diff options
context:
space:
mode:
authorAlexandre Ratchov <ratchov@cvs.openbsd.org>2013-08-30 14:18:39 +0000
committerAlexandre Ratchov <ratchov@cvs.openbsd.org>2013-08-30 14:18:39 +0000
commit525af06e9da286b1c9911c74037586c9f8a90d73 (patch)
tree15ccd8f4bbb3aa9c3edfcbb4d12402d53c94ce7c /sys
parent9698d68c75a4fdfebed055f24ba0a7b4db771f2b (diff)
Lock the audio mutex before invoking the audio(4) call-back, fixes
panics found by David Krause, thanks!
Diffstat (limited to 'sys')
-rw-r--r--sys/arch/zaurus/dev/zaurus_audio.c20
1 files changed, 18 insertions, 2 deletions
diff --git a/sys/arch/zaurus/dev/zaurus_audio.c b/sys/arch/zaurus/dev/zaurus_audio.c
index f640f0ad778..969d45f13d7 100644
--- a/sys/arch/zaurus/dev/zaurus_audio.c
+++ b/sys/arch/zaurus/dev/zaurus_audio.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: zaurus_audio.c,v 1.16 2013/05/15 08:29:24 ratchov Exp $ */
+/* $OpenBSD: zaurus_audio.c,v 1.17 2013/08/30 14:18:38 ratchov Exp $ */
/*
* Copyright (c) 2005 Christopher Pascoe <pascoe@openbsd.org>
@@ -57,6 +57,8 @@ int zaudio_match(struct device *, void *, void *);
void zaudio_attach(struct device *, struct device *, void *);
int zaudio_detach(struct device *, int);
int zaudio_activate(struct device *, int);
+void zaudio_pintr(void *);
+void zaudio_rintr(void *);
#define ZAUDIO_OP_SPKR 0
#define ZAUDIO_OP_HP 1
@@ -92,6 +94,8 @@ struct zaudio_softc {
int sc_state;
int sc_icount;
struct timeout sc_to;
+ void (*sc_pintr)(void *);
+ void *sc_parg;
};
struct cfattach zaudio_ca = {
@@ -979,6 +983,16 @@ zaudio_get_props(void *hdl)
return AUDIO_PROP_MMAP | AUDIO_PROP_INDEPENDENT | AUDIO_PROP_FULLDUPLEX;
}
+void
+zaudio_pintr(void *hdl)
+{
+ struct zaudio_softc *sc = hdl;
+
+ mtx_enter(&audio_lock);
+ sc->sc_pintr(sc->sc_parg);
+ mtx_leave(&audio_lock);
+}
+
/*
* called by interrupt code-path, don't lock
*/
@@ -996,7 +1010,9 @@ zaudio_start_output(void *hdl, void *block, int bsize, void (*intr)(void *),
}
/* Start DMA via I2S */
- err = pxa2x0_i2s_start_output(&sc->sc_i2s, block, bsize, intr, intrarg);
+ sc->sc_pintr = intr;
+ sc->sc_parg = intrarg;
+ err = pxa2x0_i2s_start_output(&sc->sc_i2s, block, bsize, zaudio_pintr, sc);
if (err) {
zaudio_standby(sc);
sc->sc_playing = 0;