aboutsummaryrefslogtreecommitdiff
path: root/src/platform/posix
diff options
context:
space:
mode:
authorGarrett D'Amore <garrett@damore.org>2019-05-19 14:33:36 -0700
committerGarrett D'Amore <garrett@damore.org>2019-05-19 14:33:36 -0700
commit6fe3ff90cd86d539371403381f6c580fc097e689 (patch)
treea214819298baf6d6e53d6abd7cff9a0271488d7f /src/platform/posix
parentc40cc5d16dbb22c46e47a1028265b8ee9fb5df27 (diff)
downloadnng-6fe3ff90cd86d539371403381f6c580fc097e689.tar.gz
nng-6fe3ff90cd86d539371403381f6c580fc097e689.tar.bz2
nng-6fe3ff90cd86d539371403381f6c580fc097e689.zip
fix #946 Use after free in TLS
This also introduces a more efficient reference counting usage based on atomics, rather than locks.
Diffstat (limited to 'src/platform/posix')
-rw-r--r--src/platform/posix/posix_atomic.c43
1 files changed, 39 insertions, 4 deletions
diff --git a/src/platform/posix/posix_atomic.c b/src/platform/posix/posix_atomic.c
index 7f735ec0..8f2284b5 100644
--- a/src/platform/posix/posix_atomic.c
+++ b/src/platform/posix/posix_atomic.c
@@ -30,13 +30,13 @@ nni_atomic_flag_reset(nni_atomic_flag *f)
}
void
-nni_atomic_inc64(nni_atomic_u64 *v, uint64_t bump)
+nni_atomic_add64(nni_atomic_u64 *v, uint64_t bump)
{
(void) atomic_fetch_add_explicit(&v->v, bump, memory_order_relaxed);
}
void
-nni_atomic_dec64(nni_atomic_u64 *v, uint64_t bump)
+nni_atomic_sub64(nni_atomic_u64 *v, uint64_t bump)
{
(void) atomic_fetch_sub_explicit(&v->v, bump, memory_order_relaxed);
}
@@ -65,6 +65,22 @@ nni_atomic_init64(nni_atomic_u64 *v)
atomic_init(&v->v, 0);
}
+void
+nni_atomic_inc64(nni_atomic_u64 *v)
+{
+ atomic_fetch_add(&v->v, 1);
+}
+
+uint64_t
+nni_atomic_dec64_nv(nni_atomic_u64 *v)
+{
+ uint64_t ov;
+
+ // C11 atomics give the old rather than new value.
+ ov = atomic_fetch_sub(&v->v, 1);
+ return (ov - 1);
+}
+
#else
#include <pthread.h>
@@ -91,7 +107,7 @@ nni_atomic_flag_reset(nni_atomic_flag *f)
}
void
-nni_atomic_inc64(nni_atomic_u64 *v, uint64_t bump)
+nni_atomic_add64(nni_atomic_u64 *v, uint64_t bump)
{
pthread_mutex_lock(&plat_atomic_lock);
v += bump;
@@ -99,7 +115,7 @@ nni_atomic_inc64(nni_atomic_u64 *v, uint64_t bump)
}
void
-nni_atomic_dec64(nni_atomic_u64 *v, uint64_t bump)
+nni_atomic_sub64(nni_atomic_u64 *v, uint64_t bump)
{
pthread_mutex_lock(&plat_atomic_lock);
v -= bump;
@@ -141,6 +157,25 @@ nni_atomic_init64(nni_atomic_u64 *v)
v->v = 0;
}
+void
+nni_atomic_inc64(nni_atomic_u64 *v)
+{
+ pthread_mutex_lock(&plat_atomic_lock);
+ v->v++;
+ pthread_mutex_unlock(&plat_atomic_lock);
+}
+
+void
+nni_atomic_dec64_nv(nni_atomic_u64 *v)
+{
+ uint64_t nv;
+ pthread_mutex_lock(&plat_atomic_lock);
+ v->v--;
+ nv = v->v;
+ pthread_mutex_unlock(&plat_atomic_lock);
+ return (nv);
+}
+
#endif
#endif // NNG_PLATFORM_POSIX