summaryrefslogtreecommitdiff
path: root/usr.bin/sndiod
diff options
context:
space:
mode:
authorAlexandre Ratchov <ratchov@cvs.openbsd.org>2020-06-12 15:40:19 +0000
committerAlexandre Ratchov <ratchov@cvs.openbsd.org>2020-06-12 15:40:19 +0000
commit5b2e18a31a0d18522b6b22c14c11b783cf1bac1a (patch)
tree0dc6e1cef669f9c70b52b9818d539589c10f8b0b /usr.bin/sndiod
parentf19dafd86bd5567b8f7d4eb4b6d7b7597267be01 (diff)
On error, drop clients and close the device only if it's still open
Fixes crashes when USB devices are disconnected, caused by an attempt to close the already closed device: it was closed once when its ref counter drops to zero (after the last client is disconnected) and once with an explicit call to dev_close() on the error code-path.
Diffstat (limited to 'usr.bin/sndiod')
-rw-r--r--usr.bin/sndiod/dev.c11
-rw-r--r--usr.bin/sndiod/dev.h4
-rw-r--r--usr.bin/sndiod/midi.c9
-rw-r--r--usr.bin/sndiod/midi.h3
-rw-r--r--usr.bin/sndiod/miofile.c4
-rw-r--r--usr.bin/sndiod/siofile.c6
6 files changed, 20 insertions, 17 deletions
diff --git a/usr.bin/sndiod/dev.c b/usr.bin/sndiod/dev.c
index 9515664107c..fe224a7f6a3 100644
--- a/usr.bin/sndiod/dev.c
+++ b/usr.bin/sndiod/dev.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: dev.c,v 1.71 2020/04/24 11:33:28 ratchov Exp $ */
+/* $OpenBSD: dev.c,v 1.72 2020/06/12 15:40:18 ratchov Exp $ */
/*
* Copyright (c) 2008-2012 Alexandre Ratchov <alex@caoua.org>
*
@@ -59,7 +59,6 @@ struct dev *dev_new(char *, struct aparams *, unsigned int, unsigned int,
void dev_adjpar(struct dev *, int, int, int);
int dev_allocbufs(struct dev *);
int dev_open(struct dev *);
-void dev_exitall(struct dev *);
void dev_freebufs(struct dev *);
void dev_close(struct dev *);
int dev_ref(struct dev *);
@@ -1193,10 +1192,10 @@ dev_open(struct dev *d)
}
/*
- * Force all slots to exit
+ * Force all slots to exit and close device, called after an error
*/
void
-dev_exitall(struct dev *d)
+dev_abort(struct dev *d)
{
int i;
struct slot *s;
@@ -1214,6 +1213,9 @@ dev_exitall(struct dev *d)
c->ops->exit(c->arg);
c->ops = NULL;
}
+
+ if (d->pstate != DEV_CFG)
+ dev_close(d);
}
/*
@@ -1249,7 +1251,6 @@ dev_close(struct dev *d)
{
struct ctl *c;
- dev_exitall(d);
d->pstate = DEV_CFG;
dev_sio_close(d);
dev_freebufs(d);
diff --git a/usr.bin/sndiod/dev.h b/usr.bin/sndiod/dev.h
index 5e1521f3830..0c600d793e1 100644
--- a/usr.bin/sndiod/dev.h
+++ b/usr.bin/sndiod/dev.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: dev.h,v 1.25 2020/04/16 12:26:55 ratchov Exp $ */
+/* $OpenBSD: dev.h,v 1.26 2020/06/12 15:40:18 ratchov Exp $ */
/*
* Copyright (c) 2008-2012 Alexandre Ratchov <alex@caoua.org>
*
@@ -260,7 +260,7 @@ struct dev {
extern struct dev *dev_list;
void dev_log(struct dev *);
-void dev_close(struct dev *);
+void dev_abort(struct dev *);
int dev_reopen(struct dev *);
struct dev *dev_new(char *, struct aparams *, unsigned int, unsigned int,
unsigned int, unsigned int, unsigned int, unsigned int);
diff --git a/usr.bin/sndiod/midi.c b/usr.bin/sndiod/midi.c
index d3bd018de32..a739cb474e9 100644
--- a/usr.bin/sndiod/midi.c
+++ b/usr.bin/sndiod/midi.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: midi.c,v 1.24 2020/04/25 05:03:54 ratchov Exp $ */
+/* $OpenBSD: midi.c,v 1.25 2020/06/12 15:40:18 ratchov Exp $ */
/*
* Copyright (c) 2008-2012 Alexandre Ratchov <alex@caoua.org>
*
@@ -563,7 +563,7 @@ port_open(struct port *c)
}
void
-port_exitall(struct port *c)
+port_abort(struct port *c)
{
int i;
struct midi *ep;
@@ -574,6 +574,9 @@ port_exitall(struct port *c)
(c->midi->txmask & ep->self))
ep->ops->exit(ep->arg);
}
+
+ if (c->state != PORT_CFG)
+ port_close(c);
}
int
@@ -588,8 +591,6 @@ port_close(struct port *c)
#endif
c->state = PORT_CFG;
port_mio_close(c);
-
- port_exitall(c);
return 1;
}
diff --git a/usr.bin/sndiod/midi.h b/usr.bin/sndiod/midi.h
index bdcc2b7d7e0..8c51a6e9975 100644
--- a/usr.bin/sndiod/midi.h
+++ b/usr.bin/sndiod/midi.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: midi.h,v 1.12 2020/04/25 05:03:54 ratchov Exp $ */
+/* $OpenBSD: midi.h,v 1.13 2020/06/12 15:40:18 ratchov Exp $ */
/*
* Copyright (c) 2008-2012 Alexandre Ratchov <alex@caoua.org>
*
@@ -124,5 +124,6 @@ void port_done(struct port *);
void port_drain(struct port *);
int port_close(struct port *);
int port_reopen(struct port *);
+void port_abort(struct port *);
#endif /* !defined(MIDI_H) */
diff --git a/usr.bin/sndiod/miofile.c b/usr.bin/sndiod/miofile.c
index bf6feb8071b..6da4ecdb996 100644
--- a/usr.bin/sndiod/miofile.c
+++ b/usr.bin/sndiod/miofile.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: miofile.c,v 1.6 2020/01/23 05:40:09 ratchov Exp $ */
+/* $OpenBSD: miofile.c,v 1.7 2020/06/12 15:40:18 ratchov Exp $ */
/*
* Copyright (c) 2008-2012 Alexandre Ratchov <alex@caoua.org>
*
@@ -188,5 +188,5 @@ port_mio_hup(void *arg)
struct port *p = arg;
if (!port_reopen(p))
- port_close(p);
+ port_abort(p);
}
diff --git a/usr.bin/sndiod/siofile.c b/usr.bin/sndiod/siofile.c
index a33558c81eb..4cc0be02a49 100644
--- a/usr.bin/sndiod/siofile.c
+++ b/usr.bin/sndiod/siofile.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: siofile.c,v 1.19 2020/04/24 11:33:28 ratchov Exp $ */
+/* $OpenBSD: siofile.c,v 1.20 2020/06/12 15:40:18 ratchov Exp $ */
/*
* Copyright (c) 2008-2012 Alexandre Ratchov <alex@caoua.org>
*
@@ -84,7 +84,7 @@ dev_sio_timeout(void *arg)
dev_log(d);
log_puts(": watchdog timeout\n");
- dev_close(d);
+ dev_abort(d);
}
/*
@@ -641,5 +641,5 @@ dev_sio_hup(void *arg)
}
#endif
if (!dev_reopen(d))
- dev_close(d);
+ dev_abort(d);
}