aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGarrett D'Amore <garrett@damore.org>2018-03-28 13:04:22 -0700
committerGarrett D'Amore <garrett@damore.org>2018-03-30 12:38:56 -0700
commit19546a81a5995cdca5d3f599d7c12b7219248f36 (patch)
tree114883b1c37b6d9d219e99d63653e6da57a97a16
parent69ee01320f3eda2f08e97a755512763079224e8a (diff)
downloadnng-19546a81a5995cdca5d3f599d7c12b7219248f36.tar.gz
nng-19546a81a5995cdca5d3f599d7c12b7219248f36.tar.bz2
nng-19546a81a5995cdca5d3f599d7c12b7219248f36.zip
fixes #318 Assertion on macOS -- kevent() returns EINPROGRESS.
-rw-r--r--src/platform/posix/posix_pollq_kqueue.c26
1 files changed, 15 insertions, 11 deletions
diff --git a/src/platform/posix/posix_pollq_kqueue.c b/src/platform/posix/posix_pollq_kqueue.c
index 5a2b2c69..cff0dcf4 100644
--- a/src/platform/posix/posix_pollq_kqueue.c
+++ b/src/platform/posix/posix_pollq_kqueue.c
@@ -93,7 +93,6 @@ nni_posix_pollq_add(nni_posix_pollq_node *node)
static void
nni_posix_pollq_remove_helper(nni_posix_pollq *pq, nni_posix_pollq_node *node)
{
- int rv;
struct kevent kevents[2];
node->events = 0;
@@ -105,11 +104,11 @@ nni_posix_pollq_remove_helper(nni_posix_pollq *pq, nni_posix_pollq_node *node)
EV_SET(&kevents[1], (uintptr_t) node->fd, EVFILT_WRITE, EV_DELETE, 0,
0, (kevent_udata_t) node);
- rv = kevent(pq->kq, kevents, 2, NULL, 0, NULL);
- // allow errnos that indicate the fd has already been removed
- if (rv < 0 && errno != EBADF && errno != ENOENT) {
- NNI_ASSERT(false);
- }
+ // So it turns out that we can get EBADF, ENOENT, and apparently
+ // also EINPROGRESS (new on macOS Sierra). Frankly, we're deleting
+ // an event, and its harmless if the event removal fails (worst
+ // case would be a spurious wakeup), so lets ignore it.
+ (void) kevent(pq->kq, kevents, 2, NULL, 0, NULL);
}
// nni_posix_pollq_remove removes the node from the pollq, but
@@ -192,9 +191,14 @@ nni_posix_pollq_arm(nni_posix_pollq_node *node, int events)
}
if (nevents > 0) {
- int rv;
- rv = kevent(pq->kq, kevents, nevents, NULL, 0, NULL);
- NNI_ASSERT(rv >= 0);
+ // This call should never fail, really. The only possible
+ // legitimate failure would be ENOMEM, but in that case
+ // lots of other things are going to be failing, or ENOENT
+ // or ESRCH, indicating we already lost interest; the
+ // only consequence of ignoring these errors is that a given
+ // descriptor might appear "stuck". This beats the alternative
+ // of just blithely crashing the application with an assertion.
+ (void) kevent(pq->kq, kevents, nevents, NULL, 0, NULL);
node->events |= events;
}
@@ -303,7 +307,7 @@ nni_posix_poll_thr(void *arg)
// this will only fail if the fd is already
// closed/invalid which we don't mind anyway,
// so ignore return value.
- kevent(pq->kq, &ev_disable, 1, NULL, 0, NULL);
+ (void) kevent(pq->kq, &ev_disable, 1, NULL, 0, NULL);
// mark events as cleared
node->events &= ~node->revents;
@@ -341,7 +345,7 @@ nni_posix_pollq_destroy(nni_posix_pollq *pq)
nni_mtx_lock(&pq->mtx);
pq->close = true;
pq->started = false;
- kevent(pq->kq, &ev, 1, NULL, 0, NULL);
+ (void) kevent(pq->kq, &ev, 1, NULL, 0, NULL);
nni_mtx_unlock(&pq->mtx);
}
nni_thr_fini(&pq->thr);