diff options
author | Alexandre Ratchov <ratchov@cvs.openbsd.org> | 2024-07-23 06:34:04 +0000 |
---|---|---|
committer | Alexandre Ratchov <ratchov@cvs.openbsd.org> | 2024-07-23 06:34:04 +0000 |
commit | 19fb8b273f7235758c33de112b1bfbd866528a84 (patch) | |
tree | 8c224c1d2514953fdd5c24ac8ca596093fa14b26 /usr.bin | |
parent | fe1f61086b39dd6ee1ddd5dda3880153bebae14f (diff) |
sndiod: Properly update the poll(2) event masks after i/o.
If there are no descriptors to poll for an event source, we call
the i/o handlers immediately (before poll(2) is called). As this
may generate output for other descriptors, their the poll(2) event
masks need to be updated.
Diffstat (limited to 'usr.bin')
-rw-r--r-- | usr.bin/sndiod/file.c | 32 |
1 files changed, 24 insertions, 8 deletions
diff --git a/usr.bin/sndiod/file.c b/usr.bin/sndiod/file.c index 3fb8664f529..64a235741b9 100644 --- a/usr.bin/sndiod/file.c +++ b/usr.bin/sndiod/file.c @@ -1,4 +1,4 @@ -/* $OpenBSD: file.c,v 1.26 2022/12/26 19:16:03 jmc Exp $ */ +/* $OpenBSD: file.c,v 1.27 2024/07/23 06:34:03 ratchov Exp $ */ /* * Copyright (c) 2008-2012 Alexandre Ratchov <alex@caoua.org> * @@ -63,7 +63,7 @@ void timo_update(unsigned int); void timo_init(void); void timo_done(void); -void file_process(struct file *, struct pollfd *); +int file_process(struct file *, struct pollfd *); struct timespec file_ts; struct file *file_list; @@ -270,10 +270,10 @@ file_del(struct file *f) #endif } -void +int file_process(struct file *f, struct pollfd *pfd) { - int revents; + int rc, revents; #ifdef DEBUG struct timespec ts0, ts1; long us; @@ -283,14 +283,21 @@ file_process(struct file *f, struct pollfd *pfd) if (log_level >= 3) clock_gettime(CLOCK_UPTIME, &ts0); #endif + rc = 0; revents = (f->state != FILE_ZOMB) ? f->ops->revents(f->arg, pfd) : 0; - if ((revents & POLLHUP) && (f->state != FILE_ZOMB)) + if ((revents & POLLHUP) && (f->state != FILE_ZOMB)) { f->ops->hup(f->arg); - if ((revents & POLLIN) && (f->state != FILE_ZOMB)) + rc = 1; + } + if ((revents & POLLIN) && (f->state != FILE_ZOMB)) { f->ops->in(f->arg); - if ((revents & POLLOUT) && (f->state != FILE_ZOMB)) + rc = 1; + } + if ((revents & POLLOUT) && (f->state != FILE_ZOMB)) { f->ops->out(f->arg); + rc = 1; + } #ifdef DEBUG if (log_level >= 3) { clock_gettime(CLOCK_UPTIME, &ts1); @@ -304,6 +311,7 @@ file_process(struct file *f, struct pollfd *pfd) } } #endif + return rc; } int @@ -370,11 +378,19 @@ file_poll(void) /* * process files that do not rely on poll */ + res = 0; for (f = file_list; f != NULL; f = f->next) { if (f->nfds > 0) continue; - file_process(f, NULL); + res |= file_process(f, NULL); } + /* + * The processing may have changed the poll(2) conditions of + * other files, so restart the loop to force their poll(2) event + * masks to be reevaluated. + */ + if (res) + return 1; /* * Sleep. Calculate the number of milliseconds poll(2) must |