aboutsummaryrefslogtreecommitdiff
path: root/src/core/endpt.c
diff options
context:
space:
mode:
authorGarrett D'Amore <garrett@damore.org>2017-08-04 17:17:42 -0700
committerGarrett D'Amore <garrett@damore.org>2017-08-04 21:20:00 -0700
commitdc334d7193a2a0bc0194221b853a37e1be7f5b9a (patch)
tree1eebf2773745a3a25e8a071fbe4f51cd5490d4e4 /src/core/endpt.c
parent6887900ae033add30ee0151b72abe927c5239588 (diff)
downloadnng-dc334d7193a2a0bc0194221b853a37e1be7f5b9a.tar.gz
nng-dc334d7193a2a0bc0194221b853a37e1be7f5b9a.tar.bz2
nng-dc334d7193a2a0bc0194221b853a37e1be7f5b9a.zip
Refactor AIO logic to close numerous races and reduce complexity.
This passes valgrind 100% clean for both helgrind and deep leak checks. This represents a complete rethink of how the AIOs work, and much simpler synchronization; the provider API is a bit simpler to boot, as a number of failure modes have been simply eliminated. While here a few other minor bugs were squashed.
Diffstat (limited to 'src/core/endpt.c')
-rw-r--r--src/core/endpt.c11
1 files changed, 10 insertions, 1 deletions
diff --git a/src/core/endpt.c b/src/core/endpt.c
index c0f9d399..aa4c5a31 100644
--- a/src/core/endpt.c
+++ b/src/core/endpt.c
@@ -175,6 +175,7 @@ nni_ep_close(nni_ep *ep)
nni_aio_cancel(&ep->ep_acc_aio, NNG_ECLOSED);
nni_aio_cancel(&ep->ep_con_aio, NNG_ECLOSED);
nni_aio_cancel(&ep->ep_con_syn, NNG_ECLOSED);
+ nni_aio_cancel(&ep->ep_backoff, NNG_ECLOSED);
// Stop the underlying transport.
ep->ep_ops.ep_close(ep->ep_data);
@@ -188,6 +189,7 @@ nni_ep_reap(nni_ep *ep)
nni_aio_stop(&ep->ep_acc_aio);
nni_aio_stop(&ep->ep_con_aio);
nni_aio_stop(&ep->ep_con_syn);
+ nni_aio_stop(&ep->ep_backoff);
// Take us off the sock list.
nni_sock_ep_remove(ep->ep_sock, ep);
@@ -233,6 +235,13 @@ nni_ep_stop(nni_ep *ep)
}
static void
+nni_ep_backoff_cancel(nni_aio *aio, int rv)
+{
+ // The only way this ever gets "finished", is via cancellation.
+ nni_aio_finish_error(aio, rv);
+}
+
+static void
nni_ep_backoff_start(nni_ep *ep)
{
nni_duration backoff;
@@ -255,7 +264,7 @@ nni_ep_backoff_start(nni_ep *ep)
// random number, but this really doesn't matter.
ep->ep_backoff.a_expire = nni_clock() + (nni_random() % backoff);
- nni_aio_start(&ep->ep_backoff, NULL, ep);
+ nni_aio_start(&ep->ep_backoff, nni_ep_backoff_cancel, ep);
}
static void