From 00e513f5c18fdd983364f9781d90835a9ee7a3de Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Mon, 3 Mar 2014 13:58:16 -0600 Subject: [PATCH 01/21] partway through implementing OPA using C11 --- src/opa_primitives.h | 2 + src/primitives/opa_c11_atomics.h | 125 +++++++++++++++++++++++++++++++ 2 files changed, 127 insertions(+) create mode 100644 src/primitives/opa_c11_atomics.h diff --git a/src/opa_primitives.h b/src/opa_primitives.h index 8e5d40b..8a4e220 100644 --- a/src/opa_primitives.h +++ b/src/opa_primitives.h @@ -112,6 +112,8 @@ #include "primitives/opa_gcc_sicortex.h" #elif defined(OPA_HAVE_GCC_INTRINSIC_ATOMICS) #include "primitives/opa_gcc_intrinsics.h" +#elif defined(OPA_HAVE_C11_ATOMICS) +#include "primitives/opa_c11_atomics.h" #elif defined(OPA_HAVE_SUN_ATOMIC_OPS) #include "primitives/opa_sun_atomic_ops.h" #elif defined(OPA_HAVE_NT_INTRINSICS) diff --git a/src/primitives/opa_c11_atomics.h b/src/primitives/opa_c11_atomics.h new file mode 100644 index 0000000..11ae382 --- /dev/null +++ b/src/primitives/opa_c11_atomics.h @@ -0,0 +1,125 @@ +/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil ; -*- */ +/* + * (C) 2008 by Argonne National Laboratory. + * See COPYRIGHT in top-level directory. + */ + +/* FIXME needs to be converted to new style functions with OPA_int_t/OPA_ptr_t-types */ +#ifndef OPA_C11_ATOMICS_H_INCLUDED +#define OPA_C11_ATOMICS_H_INCLUDED + +#ifdef __STDC_NO_ATOMICS__ +#error stdatomic header is not available. +#else +#include +#endif + +#ifndef ATOMIC_INT_LOCK_FREE +#error atomic_int is not lock-free. +#else +typedef atomic_int OPA_int_t; +#endif + +#ifndef ATOMIC_POINTER_LOCK_FREE +#error atomic_pointer is not lock-free. +#else +/* TODO Is this really the right type to use here? */ +typedef atomic_intptr_t OPA_ptr_t; +#endif + +#define OPA_INT_T_INITIALIZER(val_) ATOMIC_VAR_INIT(val_) +#define OPA_PTR_T_INITIALIZER(val_) ATOMIC_VAR_INIT(val_) + +static _opa_inline int OPA_load_int(_opa_const OPA_int_t *ptr) +{ + return atomic_load_explicit(ptr, memory_order_relaxed); +} + +static _opa_inline void OPA_store_int(OPA_int_t *ptr, int val) +{ + atomic_store_explicit(ptr, val, memory_order_relaxed); +} + +static _opa_inline void *OPA_load_ptr(_opa_const OPA_ptr_t *ptr) +{ + return atomic_load_explicit(ptr, memory_order_relaxed); +} + +static _opa_inline void OPA_store_ptr(OPA_ptr_t *ptr, void *val) +{ + atomic_store_explicit(ptr, val, memory_order_relaxed); +} + +static _opa_inline int OPA_load_acquire_int(_opa_const OPA_int_t *ptr) +{ + return atomic_load_explicit(ptr, memory_order_acquire); +} + +static _opa_inline void OPA_store_release_int(OPA_int_t *ptr, int val) +{ + atomic_store_explicit(ptr, val, memory_order_release); +} + +static _opa_inline void *OPA_load_acquire_ptr(_opa_const OPA_ptr_t *ptr) +{ + return atomic_load_explicit(ptr, memory_order_acquire); +} + +static _opa_inline void OPA_store_release_ptr(OPA_ptr_t *ptr, void *val) +{ + atomic_store_explicit(ptr, val, memory_order_release); +} + +static _opa_inline int OPA_fetch_and_add_int(OPA_int_t *ptr, int val) +{ + return atomic_fetch_add_explicit(ptr, val, memory_order_relaxed); +} + +static _opa_inline int OPA_decr_and_test_int(OPA_int_t *ptr) +{ + return (1 == atomic_fetch_add_explicit(ptr, -1, memory_order_relaxed)); +} + +#define OPA_fetch_and_incr_int_by_faa OPA_fetch_and_incr_int +#define OPA_fetch_and_decr_int_by_faa OPA_fetch_and_decr_int +#define OPA_add_int_by_faa OPA_add_int +#define OPA_incr_int_by_fai OPA_incr_int +#define OPA_decr_int_by_fad OPA_decr_int + + +static _opa_inline void *OPA_cas_ptr(OPA_ptr_t *ptr, void *oldv, void *newv) +{ + return __sync_val_compare_and_swap(&ptr->v, oldv, newv); +} + +static _opa_inline int OPA_cas_int(OPA_int_t *ptr, int oldv, int newv) +{ + return __sync_val_compare_and_swap(&ptr->v, oldv, newv); +} + +#ifdef SYNC_LOCK_TEST_AND_SET_IS_SWAP +static _opa_inline void *OPA_swap_ptr(OPA_ptr_t *ptr, void *val) +{ + return __sync_lock_test_and_set(&ptr->v, val); +} + +static _opa_inline int OPA_swap_int(OPA_int_t *ptr, int val) +{ + return __sync_lock_test_and_set(&ptr->v, val); +} + +#else +#define OPA_swap_ptr_by_cas OPA_swap_ptr +#define OPA_swap_int_by_cas OPA_swap_int +#endif + +#define OPA_write_barrier() __sync_synchronize() +#define OPA_read_barrier() __sync_synchronize() +#define OPA_read_write_barrier() __sync_synchronize() +#define OPA_compiler_barrier() __asm__ __volatile__ ( "" ::: "memory" ) + + + +#include"opa_emulated.h" + +#endif /* OPA_C11_ATOMICS_H_INCLUDED */ From ccd1d2855f66405cbea7cac97b4d961aefffc5c2 Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Mon, 3 Mar 2014 14:11:04 -0600 Subject: [PATCH 02/21] finish off impl of existing features; removed emulation. need to add missing stuff. --- src/primitives/opa_c11_atomics.h | 37 +++++++++++--------------------- 1 file changed, 12 insertions(+), 25 deletions(-) diff --git a/src/primitives/opa_c11_atomics.h b/src/primitives/opa_c11_atomics.h index 11ae382..0d7a035 100644 --- a/src/primitives/opa_c11_atomics.h +++ b/src/primitives/opa_c11_atomics.h @@ -1,6 +1,7 @@ /* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil ; -*- */ /* * (C) 2008 by Argonne National Laboratory. + * (C) 2014 by Argonne National Laboratory, Leadership Computing Facility. * See COPYRIGHT in top-level directory. */ @@ -80,46 +81,32 @@ static _opa_inline int OPA_decr_and_test_int(OPA_int_t *ptr) return (1 == atomic_fetch_add_explicit(ptr, -1, memory_order_relaxed)); } -#define OPA_fetch_and_incr_int_by_faa OPA_fetch_and_incr_int -#define OPA_fetch_and_decr_int_by_faa OPA_fetch_and_decr_int -#define OPA_add_int_by_faa OPA_add_int -#define OPA_incr_int_by_fai OPA_incr_int -#define OPA_decr_int_by_fad OPA_decr_int - - static _opa_inline void *OPA_cas_ptr(OPA_ptr_t *ptr, void *oldv, void *newv) { - return __sync_val_compare_and_swap(&ptr->v, oldv, newv); + return atomic_compare_exchange_strong_explicit(ptr, &oldv, &newv, memory_order_relaxed); } static _opa_inline int OPA_cas_int(OPA_int_t *ptr, int oldv, int newv) { - return __sync_val_compare_and_swap(&ptr->v, oldv, newv); + return atomic_compare_exchange_strong_explicit(ptr, &oldv, &newv, memory_order_relaxed); } -#ifdef SYNC_LOCK_TEST_AND_SET_IS_SWAP static _opa_inline void *OPA_swap_ptr(OPA_ptr_t *ptr, void *val) { - return __sync_lock_test_and_set(&ptr->v, val); + return atomic_exchange_explicit(ptr, val, memory_order_relaxed); } static _opa_inline int OPA_swap_int(OPA_int_t *ptr, int val) { - return __sync_lock_test_and_set(&ptr->v, val); + return atomic_exchange_explicit(ptr, val, memory_order_relaxed); } -#else -#define OPA_swap_ptr_by_cas OPA_swap_ptr -#define OPA_swap_int_by_cas OPA_swap_int -#endif - -#define OPA_write_barrier() __sync_synchronize() -#define OPA_read_barrier() __sync_synchronize() -#define OPA_read_write_barrier() __sync_synchronize() -#define OPA_compiler_barrier() __asm__ __volatile__ ( "" ::: "memory" ) - - - -#include"opa_emulated.h" +/* TODO: write/read use of release/acquire might be backwards. */ +#define OPA_write_barrier() atomic_thread_fence(memory_order_release); +#define OPA_read_barrier() atomic_thread_fence(memory_order_acquire); +#define OPA_read_write_barrier() atomic_thread_fence(memory_order_acq_rel); +/* FYI: According to C11 7.17.4.2 NOTE 2, atomic_signal_fence acts as + * a compiler barrier. Note sure how memory_order affects this. */ +#define OPA_compiler_barrier() atomic_signal_fence(memory_order_acq_rel); #endif /* OPA_C11_ATOMICS_H_INCLUDED */ From 9bb6bd5fb1efc9c2b15b299ea0b5dff61dfd3714 Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Tue, 4 Mar 2014 11:57:51 -0800 Subject: [PATCH 03/21] implement the rest of the operations found in opa_unsafe.h --- src/primitives/opa_c11_atomics.h | 34 ++++++++++++++++++++++++++++---- 1 file changed, 30 insertions(+), 4 deletions(-) diff --git a/src/primitives/opa_c11_atomics.h b/src/primitives/opa_c11_atomics.h index 0d7a035..e677480 100644 --- a/src/primitives/opa_c11_atomics.h +++ b/src/primitives/opa_c11_atomics.h @@ -70,25 +70,51 @@ static _opa_inline void OPA_store_release_ptr(OPA_ptr_t *ptr, void *val) { atomic_store_explicit(ptr, val, memory_order_release); } +static _opa_inline void OPA_add_int(OPA_int_t *ptr, int val) +{ + atomic_fetch_add_explicit(ptr, val, memory_order_relaxed); +} static _opa_inline int OPA_fetch_and_add_int(OPA_int_t *ptr, int val) { return atomic_fetch_add_explicit(ptr, val, memory_order_relaxed); } +static _opa_inline int OPA_fetch_and_decr_int(OPA_int_t *ptr) +{ + return atomic_fetch_add_explicit(ptr, -1, memory_order_relaxed); +} + +static _opa_inline int OPA_fetch_and_incr_int(OPA_int_t *ptr) +{ + return atomic_fetch_add_explicit(ptr, 1, memory_order_relaxed); +} + +static _opa_inline void OPA_incr_int(OPA_int_t *ptr) +{ + atomic_fetch_add_explicit(ptr, 1, memory_order_relaxed); +} + +static _opa_inline void OPA_decr_int(OPA_int_t *ptr) +{ + atomic_fetch_add_explicit(ptr, -1, memory_order_relaxed); +} + static _opa_inline int OPA_decr_and_test_int(OPA_int_t *ptr) { return (1 == atomic_fetch_add_explicit(ptr, -1, memory_order_relaxed)); } +/* Dave Goodell says weak is fine. OpenPA does not expect strong. */ + static _opa_inline void *OPA_cas_ptr(OPA_ptr_t *ptr, void *oldv, void *newv) { - return atomic_compare_exchange_strong_explicit(ptr, &oldv, &newv, memory_order_relaxed); + return atomic_compare_exchange_weak_explicit(ptr, &oldv, &newv, memory_order_relaxed); } static _opa_inline int OPA_cas_int(OPA_int_t *ptr, int oldv, int newv) { - return atomic_compare_exchange_strong_explicit(ptr, &oldv, &newv, memory_order_relaxed); + return atomic_compare_exchange_weak_explicit(ptr, &oldv, &newv, memory_order_relaxed); } static _opa_inline void *OPA_swap_ptr(OPA_ptr_t *ptr, void *val) @@ -102,8 +128,8 @@ static _opa_inline int OPA_swap_int(OPA_int_t *ptr, int val) } /* TODO: write/read use of release/acquire might be backwards. */ -#define OPA_write_barrier() atomic_thread_fence(memory_order_release); -#define OPA_read_barrier() atomic_thread_fence(memory_order_acquire); +#define OPA_write_barrier() atomic_thread_fence(memory_order_acq_rel); +#define OPA_read_barrier() atomic_thread_fence(memory_order_acq_rel); #define OPA_read_write_barrier() atomic_thread_fence(memory_order_acq_rel); /* FYI: According to C11 7.17.4.2 NOTE 2, atomic_signal_fence acts as * a compiler barrier. Note sure how memory_order affects this. */ From 13711b7756c579a9e454626e289a8a316a654aad Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Tue, 4 Mar 2014 12:00:48 -0800 Subject: [PATCH 04/21] choose C11 atomics before anything else (besides unsafe) --- src/opa_primitives.h | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/opa_primitives.h b/src/opa_primitives.h index 8a4e220..f56474e 100644 --- a/src/opa_primitives.h +++ b/src/opa_primitives.h @@ -98,9 +98,11 @@ #if defined(OPA_USE_UNSAFE_PRIMITIVES) /* comes first to permit user overrides in the style of NDEBUG */ #include "primitives/opa_unsafe.h" -#elif defined(OPA_HAVE_GCC_AND_POWERPC_ASM) +#elif defined(OPA_HAVE_C11_ATOMICS) +#include "primitives/opa_c11_atomics.h" +#elif defined(OPA_HAVE_GCC_AND_POWERPC_ASM) #include "primitives/opa_gcc_ppc.h" -#elif defined(OPA_HAVE_GCC_AND_ARM_ASM) +#elif defined(OPA_HAVE_GCC_AND_ARM_ASM) #include "primitives/opa_gcc_arm.h" #elif defined(OPA_HAVE_GCC_X86_32_64) #include "primitives/opa_gcc_intel_32_64.h" @@ -112,8 +114,6 @@ #include "primitives/opa_gcc_sicortex.h" #elif defined(OPA_HAVE_GCC_INTRINSIC_ATOMICS) #include "primitives/opa_gcc_intrinsics.h" -#elif defined(OPA_HAVE_C11_ATOMICS) -#include "primitives/opa_c11_atomics.h" #elif defined(OPA_HAVE_SUN_ATOMIC_OPS) #include "primitives/opa_sun_atomic_ops.h" #elif defined(OPA_HAVE_NT_INTRINSICS) From bfc89733ee0c0a66c5bdf550381d0c24f63bd94f Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Tue, 4 Mar 2014 12:25:16 -0800 Subject: [PATCH 05/21] add some configure magic for C11 impl --- configure.ac | 1 + src/primitives/opa_c11_atomics.h | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/configure.ac b/configure.ac index 3e4434e..8465771 100644 --- a/configure.ac +++ b/configure.ac @@ -341,6 +341,7 @@ dnl without AC_TRY_RUN(). OPA_TRY_PRIMITIVE_HEADER([opa_gcc_sicortex.h], [GCC_AND_SICORTEX_ASM], [gcc SiCortex atomics]) fi + OPA_TRY_PRIMITIVE_HEADER([opa_c11_atomics.h], [C11_ATOMICS], [C11 atomics]) OPA_TRY_PRIMITIVE_HEADER([opa_gcc_intrinsics.h], [GCC_INTRINSIC_ATOMICS], [gcc atomic intrinsics]) OPA_TRY_PRIMITIVE_HEADER([opa_nt_intrinsics.h], [NT_INTRINSICS], [Windows NT atomic intrinsics]) OPA_TRY_PRIMITIVE_HEADER([opa_sun_atomic_ops.h], [SUN_ATOMIC_OPS], [Sun atomic operations library]) diff --git a/src/primitives/opa_c11_atomics.h b/src/primitives/opa_c11_atomics.h index e677480..03af1aa 100644 --- a/src/primitives/opa_c11_atomics.h +++ b/src/primitives/opa_c11_atomics.h @@ -127,7 +127,7 @@ static _opa_inline int OPA_swap_int(OPA_int_t *ptr, int val) return atomic_exchange_explicit(ptr, val, memory_order_relaxed); } -/* TODO: write/read use of release/acquire might be backwards. */ +/* Dave says that read/write don't match acq/rel perfectly so we use heavy hammer. */ #define OPA_write_barrier() atomic_thread_fence(memory_order_acq_rel); #define OPA_read_barrier() atomic_thread_fence(memory_order_acq_rel); #define OPA_read_write_barrier() atomic_thread_fence(memory_order_acq_rel); From 8e6dc9d0e52eca9af4b0ecb84c4e9561eb4aa682 Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Tue, 4 Mar 2014 13:49:36 -0800 Subject: [PATCH 06/21] fix a pass-by-val/ref bug and add a bunch of explicit casts for void* <-> intptr_t --- src/primitives/opa_c11_atomics.h | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/src/primitives/opa_c11_atomics.h b/src/primitives/opa_c11_atomics.h index 03af1aa..9b9d566 100644 --- a/src/primitives/opa_c11_atomics.h +++ b/src/primitives/opa_c11_atomics.h @@ -33,7 +33,7 @@ typedef atomic_intptr_t OPA_ptr_t; static _opa_inline int OPA_load_int(_opa_const OPA_int_t *ptr) { - return atomic_load_explicit(ptr, memory_order_relaxed); + return (void*)atomic_load_explicit(ptr, memory_order_relaxed); } static _opa_inline void OPA_store_int(OPA_int_t *ptr, int val) @@ -43,12 +43,12 @@ static _opa_inline void OPA_store_int(OPA_int_t *ptr, int val) static _opa_inline void *OPA_load_ptr(_opa_const OPA_ptr_t *ptr) { - return atomic_load_explicit(ptr, memory_order_relaxed); + return (void*)atomic_load_explicit(ptr, memory_order_relaxed); } static _opa_inline void OPA_store_ptr(OPA_ptr_t *ptr, void *val) { - atomic_store_explicit(ptr, val, memory_order_relaxed); + atomic_store_explicit(ptr, (intptr_t)val, memory_order_relaxed); } static _opa_inline int OPA_load_acquire_int(_opa_const OPA_int_t *ptr) @@ -63,13 +63,14 @@ static _opa_inline void OPA_store_release_int(OPA_int_t *ptr, int val) static _opa_inline void *OPA_load_acquire_ptr(_opa_const OPA_ptr_t *ptr) { - return atomic_load_explicit(ptr, memory_order_acquire); + return (void*)atomic_load_explicit(ptr, memory_order_acquire); } static _opa_inline void OPA_store_release_ptr(OPA_ptr_t *ptr, void *val) { - atomic_store_explicit(ptr, val, memory_order_release); + atomic_store_explicit(ptr, (intptr_t)val, memory_order_release); } + static _opa_inline void OPA_add_int(OPA_int_t *ptr, int val) { atomic_fetch_add_explicit(ptr, val, memory_order_relaxed); @@ -109,17 +110,17 @@ static _opa_inline int OPA_decr_and_test_int(OPA_int_t *ptr) static _opa_inline void *OPA_cas_ptr(OPA_ptr_t *ptr, void *oldv, void *newv) { - return atomic_compare_exchange_weak_explicit(ptr, &oldv, &newv, memory_order_relaxed); + return atomic_compare_exchange_weak_explicit(ptr, (intptr_t*)&oldv, (intptr_t)newv, memory_order_relaxed, memory_order_relaxed); } static _opa_inline int OPA_cas_int(OPA_int_t *ptr, int oldv, int newv) { - return atomic_compare_exchange_weak_explicit(ptr, &oldv, &newv, memory_order_relaxed); + return atomic_compare_exchange_weak_explicit(ptr, (intptr_t*)&oldv, (intptr_t)newv, memory_order_relaxed, memory_order_relaxed); } static _opa_inline void *OPA_swap_ptr(OPA_ptr_t *ptr, void *val) { - return atomic_exchange_explicit(ptr, val, memory_order_relaxed); + return (void*)atomic_exchange_explicit(ptr, (intptr_t)val, memory_order_relaxed); } static _opa_inline int OPA_swap_int(OPA_int_t *ptr, int val) From 2df63762cefbb0086497ec84867aec6d1e71860b Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Tue, 4 Mar 2014 13:53:10 -0800 Subject: [PATCH 07/21] remove incorrect casting --- src/primitives/opa_c11_atomics.h | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/primitives/opa_c11_atomics.h b/src/primitives/opa_c11_atomics.h index 9b9d566..0bde8e6 100644 --- a/src/primitives/opa_c11_atomics.h +++ b/src/primitives/opa_c11_atomics.h @@ -25,6 +25,7 @@ typedef atomic_int OPA_int_t; #error atomic_pointer is not lock-free. #else /* TODO Is this really the right type to use here? */ +#include typedef atomic_intptr_t OPA_ptr_t; #endif @@ -33,7 +34,7 @@ typedef atomic_intptr_t OPA_ptr_t; static _opa_inline int OPA_load_int(_opa_const OPA_int_t *ptr) { - return (void*)atomic_load_explicit(ptr, memory_order_relaxed); + return atomic_load_explicit(ptr, memory_order_relaxed); } static _opa_inline void OPA_store_int(OPA_int_t *ptr, int val) @@ -115,7 +116,7 @@ static _opa_inline void *OPA_cas_ptr(OPA_ptr_t *ptr, void *oldv, void *newv) static _opa_inline int OPA_cas_int(OPA_int_t *ptr, int oldv, int newv) { - return atomic_compare_exchange_weak_explicit(ptr, (intptr_t*)&oldv, (intptr_t)newv, memory_order_relaxed, memory_order_relaxed); + return atomic_compare_exchange_weak_explicit(ptr, &oldv, newv, memory_order_relaxed, memory_order_relaxed); } static _opa_inline void *OPA_swap_ptr(OPA_ptr_t *ptr, void *val) From df0d39c99f146ba850c6d426e2e15cfb6f71bcbf Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Tue, 4 Mar 2014 14:19:16 -0800 Subject: [PATCH 08/21] add FIXME related to CAS --- src/primitives/opa_c11_atomics.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/primitives/opa_c11_atomics.h b/src/primitives/opa_c11_atomics.h index 0bde8e6..066fe1b 100644 --- a/src/primitives/opa_c11_atomics.h +++ b/src/primitives/opa_c11_atomics.h @@ -111,11 +111,13 @@ static _opa_inline int OPA_decr_and_test_int(OPA_int_t *ptr) static _opa_inline void *OPA_cas_ptr(OPA_ptr_t *ptr, void *oldv, void *newv) { + /* FIXME return value */ return atomic_compare_exchange_weak_explicit(ptr, (intptr_t*)&oldv, (intptr_t)newv, memory_order_relaxed, memory_order_relaxed); } static _opa_inline int OPA_cas_int(OPA_int_t *ptr, int oldv, int newv) { + /* FIXME return value */ return atomic_compare_exchange_weak_explicit(ptr, &oldv, newv, memory_order_relaxed, memory_order_relaxed); } From 298e0d63ff81fa5efda7aa1e32e0a0a69f7248cc Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Tue, 4 Mar 2014 16:11:47 -0800 Subject: [PATCH 09/21] resolve issues with CAS return value by resorting to not-actually-atomic impl --- src/primitives/opa_c11_atomics.h | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/src/primitives/opa_c11_atomics.h b/src/primitives/opa_c11_atomics.h index 066fe1b..ba3a165 100644 --- a/src/primitives/opa_c11_atomics.h +++ b/src/primitives/opa_c11_atomics.h @@ -111,14 +111,18 @@ static _opa_inline int OPA_decr_and_test_int(OPA_int_t *ptr) static _opa_inline void *OPA_cas_ptr(OPA_ptr_t *ptr, void *oldv, void *newv) { - /* FIXME return value */ - return atomic_compare_exchange_weak_explicit(ptr, (intptr_t*)&oldv, (intptr_t)newv, memory_order_relaxed, memory_order_relaxed); + /* FIXME This is not safe at all but C11 does not appear to give me any other choice. */ + void * before = atomic_load_explicit(ptr, memory_order_relaxed); + atomic_compare_exchange_weak_explicit(ptr, (intptr_t*)&oldv, (intptr_t)newv, memory_order_relaxed, memory_order_relaxed); + return before; } static _opa_inline int OPA_cas_int(OPA_int_t *ptr, int oldv, int newv) { - /* FIXME return value */ - return atomic_compare_exchange_weak_explicit(ptr, &oldv, newv, memory_order_relaxed, memory_order_relaxed); + /* FIXME This is not safe at all but C11 does not appear to give me any other choice. */ + int before = atomic_load_explicit(ptr, memory_order_relaxed); + atomic_compare_exchange_weak_explicit(ptr, &oldv, newv, memory_order_relaxed, memory_order_relaxed); + return before; } static _opa_inline void *OPA_swap_ptr(OPA_ptr_t *ptr, void *val) From 4e7aa022f9f35b31f0a2f8fa8c404d28019777cd Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Wed, 5 Mar 2014 14:16:11 -0500 Subject: [PATCH 10/21] learned about returning old value in expected but not able to get correct results yet --- src/primitives/opa_c11_atomics.h | 18 ++++++++---------- 1 file changed, 8 insertions(+), 10 deletions(-) diff --git a/src/primitives/opa_c11_atomics.h b/src/primitives/opa_c11_atomics.h index ba3a165..b3ee37a 100644 --- a/src/primitives/opa_c11_atomics.h +++ b/src/primitives/opa_c11_atomics.h @@ -109,20 +109,18 @@ static _opa_inline int OPA_decr_and_test_int(OPA_int_t *ptr) /* Dave Goodell says weak is fine. OpenPA does not expect strong. */ -static _opa_inline void *OPA_cas_ptr(OPA_ptr_t *ptr, void *oldv, void *newv) +#include + +static _opa_inline void *OPA_cas_ptr(OPA_ptr_t *ptr, void *comparand, void *swaperand) { - /* FIXME This is not safe at all but C11 does not appear to give me any other choice. */ - void * before = atomic_load_explicit(ptr, memory_order_relaxed); - atomic_compare_exchange_weak_explicit(ptr, (intptr_t*)&oldv, (intptr_t)newv, memory_order_relaxed, memory_order_relaxed); - return before; + _Bool rc = atomic_compare_exchange_strong_explicit(ptr, (intptr_t*)&comparand, (intptr_t)swaperand, memory_order_relaxed, memory_order_relaxed); + return (rc == false ? comparand : swaperand); } -static _opa_inline int OPA_cas_int(OPA_int_t *ptr, int oldv, int newv) +static _opa_inline int OPA_cas_int(OPA_int_t *ptr, int comparand, int swaperand) { - /* FIXME This is not safe at all but C11 does not appear to give me any other choice. */ - int before = atomic_load_explicit(ptr, memory_order_relaxed); - atomic_compare_exchange_weak_explicit(ptr, &oldv, newv, memory_order_relaxed, memory_order_relaxed); - return before; + _Bool rc = atomic_compare_exchange_strong_explicit(ptr, &comparand, swaperand, memory_order_relaxed, memory_order_relaxed); + return (rc == false ? comparand : swaperand); } static _opa_inline void *OPA_swap_ptr(OPA_ptr_t *ptr, void *val) From 320d966a26205d956e9b7a42df35e764632a611f Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Tue, 18 Mar 2014 16:33:17 -0500 Subject: [PATCH 11/21] add c11 test to automake and git --- test/Makefile.am | 3 ++- test/test_c11.c | 58 ++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 60 insertions(+), 1 deletion(-) create mode 100644 test/test_c11.c diff --git a/test/Makefile.am b/test/Makefile.am index 9efd79c..40a7746 100644 --- a/test/Makefile.am +++ b/test/Makefile.am @@ -3,7 +3,7 @@ # (C) 2008 by Argonne National Laboratory. # See COPYRIGHT in top-level directory. -TESTS = sanity test_primitives test_barriers test_queue +TESTS = sanity test_primitives test_barriers test_queue test_c11 check_PROGRAMS = $(TESTS) @@ -15,5 +15,6 @@ sanity_SOURCES = sanity.c test_primitives_SOURCES = test_primitives.c opa_test.h test_barriers_SOURCES = test_barriers.c opa_test.h test_queue_SOURCES = test_queue.c opa_test.h +test_c11_SOURCES = test_c11.c AM_CPPFLAGS = -I$(top_srcdir)/src diff --git a/test/test_c11.c b/test/test_c11.c new file mode 100644 index 0000000..2acc50e --- /dev/null +++ b/test/test_c11.c @@ -0,0 +1,58 @@ +#if __STDC_VERSION__ < 201112L + +#warning Empty test due to lack of C11 support. +int main(void) { return 1; } + +#else + +#include +#include +#include +#include + +#include + +int main(int argc, char **argv) +{ + atomic_int a, b; + int c; + + //OPA_store_int(&a, 0); + atomic_store_explicit(&a, 0, memory_order_relaxed); + + //OPA_store_int(&b, 1); + atomic_store_explicit(&b, 1, memory_order_relaxed); + + //OPA_add_int(&a, 10); + atomic_fetch_add_explicit(&a, 10, memory_order_relaxed); + + //assert(10 == OPA_load_int(&a)); + assert(10 == atomic_load_explicit(&a, memory_order_relaxed)); + + //c = OPA_cas_int(&a, 10, 11); + { + int old = 10; + int new = 11; + atomic_compare_exchange_weak_explicit(&a, &old, new, + memory_order_relaxed, + memory_order_relaxed); + c = old; + } + assert(10 == c); + + //c = OPA_swap_int(&a, OPA_load_int(&b)); + c = atomic_exchange_explicit(&a, + atomic_load_explicit(&b, memory_order_relaxed), + memory_order_relaxed); + + assert(11 == c); + + //assert(1 == OPA_load_int(&a)); + assert(1 == atomic_load_explicit(&a, memory_order_relaxed)); + + printf("success!\n"); + + return 0; +} + +#endif From 9eedd62ab2eb98f07022b39390e383c9d8bb5131 Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Tue, 18 Mar 2014 16:34:00 -0500 Subject: [PATCH 12/21] fix cas impl. expected holds old val either way. --- src/primitives/opa_c11_atomics.h | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/primitives/opa_c11_atomics.h b/src/primitives/opa_c11_atomics.h index b3ee37a..e4dbdc5 100644 --- a/src/primitives/opa_c11_atomics.h +++ b/src/primitives/opa_c11_atomics.h @@ -113,14 +113,14 @@ static _opa_inline int OPA_decr_and_test_int(OPA_int_t *ptr) static _opa_inline void *OPA_cas_ptr(OPA_ptr_t *ptr, void *comparand, void *swaperand) { - _Bool rc = atomic_compare_exchange_strong_explicit(ptr, (intptr_t*)&comparand, (intptr_t)swaperand, memory_order_relaxed, memory_order_relaxed); - return (rc == false ? comparand : swaperand); + atomic_compare_exchange_strong_explicit(ptr, (intptr_t*)&comparand, (intptr_t)swaperand, memory_order_relaxed, memory_order_relaxed); + return comparand; } static _opa_inline int OPA_cas_int(OPA_int_t *ptr, int comparand, int swaperand) { - _Bool rc = atomic_compare_exchange_strong_explicit(ptr, &comparand, swaperand, memory_order_relaxed, memory_order_relaxed); - return (rc == false ? comparand : swaperand); + atomic_compare_exchange_strong_explicit(ptr, &comparand, swaperand, memory_order_relaxed, memory_order_relaxed); + return comparand; } static _opa_inline void *OPA_swap_ptr(OPA_ptr_t *ptr, void *val) From 689920af1c5da72de77acf3de32b08873fa8c8ce Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Sun, 4 Sep 2016 15:41:19 -0700 Subject: [PATCH 13/21] fix bugs in C11 implementation 1) cannot use const according to clang-3.8 2) ATOMIC_INT_LOCK_FREE (and similar) are named wrong in Clang (they have an extra _T_ in the middle) and thus the macros fail. we need to check to see if the macro is defined before testing its value. --- src/primitives/opa_c11_atomics.h | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/primitives/opa_c11_atomics.h b/src/primitives/opa_c11_atomics.h index e4dbdc5..6f6f6ee 100644 --- a/src/primitives/opa_c11_atomics.h +++ b/src/primitives/opa_c11_atomics.h @@ -15,13 +15,13 @@ #include #endif -#ifndef ATOMIC_INT_LOCK_FREE +#if defined(ATOMIC_INT_LOCK_FREE) && (ATOMIC_INT_LOCK_FREE < 2) #error atomic_int is not lock-free. #else typedef atomic_int OPA_int_t; #endif -#ifndef ATOMIC_POINTER_LOCK_FREE +#if defined(ATOMIC_POINTER_LOCK_FREE) && (ATOMIC_POINTER_LOCK_FREE < 2) #error atomic_pointer is not lock-free. #else /* TODO Is this really the right type to use here? */ @@ -32,7 +32,7 @@ typedef atomic_intptr_t OPA_ptr_t; #define OPA_INT_T_INITIALIZER(val_) ATOMIC_VAR_INIT(val_) #define OPA_PTR_T_INITIALIZER(val_) ATOMIC_VAR_INIT(val_) -static _opa_inline int OPA_load_int(_opa_const OPA_int_t *ptr) +static _opa_inline int OPA_load_int(OPA_int_t *ptr) { return atomic_load_explicit(ptr, memory_order_relaxed); } @@ -42,7 +42,7 @@ static _opa_inline void OPA_store_int(OPA_int_t *ptr, int val) atomic_store_explicit(ptr, val, memory_order_relaxed); } -static _opa_inline void *OPA_load_ptr(_opa_const OPA_ptr_t *ptr) +static _opa_inline void *OPA_load_ptr(OPA_ptr_t *ptr) { return (void*)atomic_load_explicit(ptr, memory_order_relaxed); } @@ -52,7 +52,7 @@ static _opa_inline void OPA_store_ptr(OPA_ptr_t *ptr, void *val) atomic_store_explicit(ptr, (intptr_t)val, memory_order_relaxed); } -static _opa_inline int OPA_load_acquire_int(_opa_const OPA_int_t *ptr) +static _opa_inline int OPA_load_acquire_int(OPA_int_t *ptr) { return atomic_load_explicit(ptr, memory_order_acquire); } @@ -62,7 +62,7 @@ static _opa_inline void OPA_store_release_int(OPA_int_t *ptr, int val) atomic_store_explicit(ptr, val, memory_order_release); } -static _opa_inline void *OPA_load_acquire_ptr(_opa_const OPA_ptr_t *ptr) +static _opa_inline void *OPA_load_acquire_ptr(OPA_ptr_t *ptr) { return (void*)atomic_load_explicit(ptr, memory_order_acquire); } From 6c88ee1ebbe5f41f0ec6a9866994f768c6cc0e93 Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Sun, 4 Sep 2016 15:59:47 -0700 Subject: [PATCH 14/21] workaround ATOMIC_*_LOCK_FREE bug in Clang --- src/primitives/opa_c11_atomics.h | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/primitives/opa_c11_atomics.h b/src/primitives/opa_c11_atomics.h index 6f6f6ee..e221b3c 100644 --- a/src/primitives/opa_c11_atomics.h +++ b/src/primitives/opa_c11_atomics.h @@ -15,13 +15,15 @@ #include #endif -#if defined(ATOMIC_INT_LOCK_FREE) && (ATOMIC_INT_LOCK_FREE < 2) +/* Clang 3.x has a bug in stdatomic.h, wherein there is an extra _T + * in the following macros. It is fixed in Clang 4.x. */ +#if !defined(ATOMIC_INT_LOCK_FREE) && !defined(ATOMIC_INT_T_LOCK_FREE) #error atomic_int is not lock-free. #else typedef atomic_int OPA_int_t; #endif -#if defined(ATOMIC_POINTER_LOCK_FREE) && (ATOMIC_POINTER_LOCK_FREE < 2) +#if !defined(ATOMIC_POINTER_LOCK_FREE) && !defined(ATOMIC_POINTER_T_LOCK_FREE) #error atomic_pointer is not lock-free. #else /* TODO Is this really the right type to use here? */ From cf1cb555f8b998c884eccb5346b114f3b42fa1ec Mon Sep 17 00:00:00 2001 From: "Antonio J. Pena" Date: Fri, 27 Jun 2014 17:13:27 -0500 Subject: [PATCH 15/21] Updated trac URLs --- README | 2 +- configure.ac | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/README b/README index bf6ea8b..7553eb8 100644 --- a/README +++ b/README @@ -10,7 +10,7 @@ derived from work on the MPICH2 project. Project documentation and bug tracking can be found at: - https://trac.mcs.anl.gov/projects/openpa/ + https://trac.mpich.org/projects/openpa/ If you would like to email questions or discuss topics related to OpenPA you can send mail to opa-discuss@lists.mcs.anl.gov. diff --git a/configure.ac b/configure.ac index 8465771..03777b4 100644 --- a/configure.ac +++ b/configure.ac @@ -6,7 +6,7 @@ AC_PREREQ(2.62) -AC_INIT([OpenPA], [1.0.4], [https://trac.mcs.anl.gov/projects/openpa/newticket]) +AC_INIT([OpenPA], [1.0.4], [https://trac.mpich.org/projects/openpa/newticket]) dnl Set the directory that contains support scripts such as install-sh and dnl config.guess. It also contains autoconf macro files. AC_CONFIG_AUX_DIR(confdb) From e0a3ea1e6d32034f39e45d84963fac509c9126f7 Mon Sep 17 00:00:00 2001 From: "Antonio J. Pena" Date: Fri, 27 Jun 2014 17:15:14 -0500 Subject: [PATCH 16/21] Updated contact information in COPYRIGHT Fixes #26 --- COPYRIGHT | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/COPYRIGHT b/COPYRIGHT index 6f6c81e..065ccfb 100644 --- a/COPYRIGHT +++ b/COPYRIGHT @@ -12,10 +12,9 @@ Permission is hereby granted to use, reproduce, prepare derivative works, and to redistribute to others. This software was authored by: Argonne National Laboratory Group -D. Goodell: (630) 252-6082; FAX: (630) 252-5986; e-mail: goodell@mcs.anl.gov -D. Buntinas: (630) 252-7928; FAX: (630) 252-5986; e-mail: buntinas@mcs.anl.gov Mathematics and Computer Science Division Argonne National Laboratory, Argonne IL 60439 +Contact: devel@mpich.org GOVERNMENT LICENSE From d2f8908954b7292b076d7064783cfffe6af9712e Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Sun, 4 Sep 2016 16:11:36 -0700 Subject: [PATCH 17/21] add Travis script try various std flags install autotools debug travis add missing script create dir before using autotools build failed with c11 flags brute force debug configure --- .travis-install-autotools.sh | 139 +++++++++++++++++++++++++++++++++++ .travis.yml | 49 ++++++++++++ 2 files changed, 188 insertions(+) create mode 100755 .travis-install-autotools.sh create mode 100644 .travis.yml diff --git a/.travis-install-autotools.sh b/.travis-install-autotools.sh new file mode 100755 index 0000000..7b81d66 --- /dev/null +++ b/.travis-install-autotools.sh @@ -0,0 +1,139 @@ +#!/bin/sh + +set +e +set -x + +os=`uname` +TRAVIS_ROOT="$1" + +case "$os" in + Darwin) + set +e # do not fail on error + brew update + brew info autoconf automake libtool + brew install autoconf automake libtool + brew upgrade autoconf automake libtool + which glibtool + which glibtoolize + glibtool --version + ln -s `which glibtool` ${TRAVIS_ROOT}/bin/libtool + ln -s `which glibtoolize` ${TRAVIS_ROOT}/bin/libtoolize + set -e # restore fail on error + ;; + Linux) + MAKE_JNUM=2 + M4_VERSION=1.4.17 + LIBTOOL_VERSION=2.4.6 + AUTOCONF_VERSION=2.69 + AUTOMAKE_VERSION=1.15 + + cd ${TRAVIS_ROOT} + TOOL=m4 + TDIR=${TOOL}-${M4_VERSION} + FILE=${TDIR}.tar.gz + BIN=${TRAVIS_ROOT}/bin/${TOOL} + if [ -f ${FILE} ] ; then + echo ${FILE} already exists! Using existing copy. + else + wget http://ftp.gnu.org/gnu/${TOOL}/${FILE} + fi + if [ -d ${TDIR} ] ; then + echo ${TDIR} already exists! Using existing copy. + else + echo Unpacking ${FILE} + tar -xzf ${FILE} + fi + if [ -f ${BIN} ] ; then + echo ${BIN} already exists! Skipping build. + else + cd ${TRAVIS_ROOT}/${TDIR} + ./configure CC=cc --prefix=${TRAVIS_ROOT} && make -j ${MAKE_JNUM} && make install + if [ "x$?" != "x0" ] ; then + echo FAILURE 1 + exit + fi + fi + + cd ${TRAVIS_ROOT} + TOOL=libtool + TDIR=${TOOL}-${LIBTOOL_VERSION} + FILE=${TDIR}.tar.gz + BIN=${TRAVIS_ROOT}/bin/${TOOL} + if [ ! -f ${FILE} ] ; then + wget http://ftp.gnu.org/gnu/${TOOL}/${FILE} + else + echo ${FILE} already exists! Using existing copy. + fi + if [ ! -d ${TDIR} ] ; then + echo Unpacking ${FILE} + tar -xzf ${FILE} + else + echo ${TDIR} already exists! Using existing copy. + fi + if [ -f ${BIN} ] ; then + echo ${BIN} already exists! Skipping build. + else + cd ${TRAVIS_ROOT}/${TDIR} + ./configure CC=cc --prefix=${TRAVIS_ROOT} M4=${TRAVIS_ROOT}/bin/m4 && make -j ${MAKE_JNUM} && make install + if [ "x$?" != "x0" ] ; then + echo FAILURE 2 + exit + fi + fi + + cd ${TRAVIS_ROOT} + TOOL=autoconf + TDIR=${TOOL}-${AUTOCONF_VERSION} + FILE=${TDIR}.tar.gz + BIN=${TRAVIS_ROOT}/bin/${TOOL} + if [ ! -f ${FILE} ] ; then + wget http://ftp.gnu.org/gnu/${TOOL}/${FILE} + else + echo ${FILE} already exists! Using existing copy. + fi + if [ ! -d ${TDIR} ] ; then + echo Unpacking ${FILE} + tar -xzf ${FILE} + else + echo ${TDIR} already exists! Using existing copy. + fi + if [ -f ${BIN} ] ; then + echo ${BIN} already exists! Skipping build. + else + cd ${TRAVIS_ROOT}/${TDIR} + ./configure CC=cc --prefix=${TRAVIS_ROOT} M4=${TRAVIS_ROOT}/bin/m4 && make -j ${MAKE_JNUM} && make install + if [ "x$?" != "x0" ] ; then + echo FAILURE 3 + exit + fi + fi + + cd ${TRAVIS_ROOT} + TOOL=automake + TDIR=${TOOL}-${AUTOMAKE_VERSION} + FILE=${TDIR}.tar.gz + BIN=${TRAVIS_ROOT}/bin/${TOOL} + if [ ! -f ${FILE} ] ; then + wget http://ftp.gnu.org/gnu/${TOOL}/${FILE} + else + echo ${FILE} already exists! Using existing copy. + fi + if [ ! -d ${TDIR} ] ; then + echo Unpacking ${FILE} + tar -xzf ${FILE} + else + echo ${TDIR} already exists! Using existing copy. + fi + if [ -f ${BIN} ] ; then + echo ${BIN} already exists! Skipping build. + else + cd ${TRAVIS_ROOT}/${TDIR} + ./configure CC=cc --prefix=${TRAVIS_ROOT} M4=${TRAVIS_ROOT}/bin/m4 && make -j ${MAKE_JNUM} && make install + if [ "x$?" != "x0" ] ; then + echo FAILURE 4 + exit + fi + fi + ;; +esac + diff --git a/.travis.yml b/.travis.yml new file mode 100644 index 0000000..aafd8ea --- /dev/null +++ b/.travis.yml @@ -0,0 +1,49 @@ +sudo: false +language: c +os: +- linux +- osx +compiler: +- gcc +- clang +env: + matrix: + - OPA_CFLAGS=-std=c89 + - OPA_CFLAGS=-std=c99 + - OPA_CFLAGS=-std=c11 + - OPA_CFLAGS=-std=gnu89 + - OPA_CFLAGS=-std=gnu99 + - OPA_CFLAGS=-std=gnu11 +addons: + apt: + sources: + - ubuntu-toolchain-r-test + # clang-3.8 comes from this + - llvm-toolchain-precise + packages: + - gcc-4.9 + - gcc-5 + - gcc-6 + - clang-3.8 +install: +- export WORKING_DIRECTORY=$PWD +- mkdir -p $WORKING_DIRECTORY/deps +- export PATH=$WORKING_DIRECTORY/deps/bin:$PATH +- sh .travis-install-autotools.sh $WORKING_DIRECTORY/deps +before_script: +- ./autogen.sh +script: +- ./configure CFLAGS=$OPA_CFLAGS +- make +- make check +after_failure: +- echo "Sad panda" +- find . -name config.log -exec cat {} ";" +notifications: + email: + recipients: + - jeff.science@gmail.com + on_success: + - change + on_failure: + - always From af1a04cfc24572b9a5b346c9e92f9861b3ae58fc Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Mon, 19 Sep 2016 16:11:46 -0700 Subject: [PATCH 18/21] declare pthread_yield --- test/opa_test.h | 1 + 1 file changed, 1 insertion(+) diff --git a/test/opa_test.h b/test/opa_test.h index 490b916..08c26e1 100644 --- a/test/opa_test.h +++ b/test/opa_test.h @@ -20,6 +20,7 @@ #include #include #if defined(OPA_HAVE_PTHREAD_H) +# define _GNU_SOURCE # include #endif /* HAVE_PTHREAD_H */ From 95d36c79a349e1935d1c6d3d28f61ae3b5edafdf Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Mon, 19 Sep 2016 16:20:09 -0700 Subject: [PATCH 19/21] older GCC doesn't understand C11 --- .travis.yml | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/.travis.yml b/.travis.yml index aafd8ea..59f4948 100644 --- a/.travis.yml +++ b/.travis.yml @@ -14,6 +14,14 @@ env: - OPA_CFLAGS=-std=gnu89 - OPA_CFLAGS=-std=gnu99 - OPA_CFLAGS=-std=gnu11 +matrix: + allow_failures: + - os: linux + compiler: gcc + env: OPA_CFLAGS=-std=c11 + - os: linux + compiler: gcc + env: OPA_CFLAGS=-std=gnu11 addons: apt: sources: From 56f55479da7c273769da7a33abf6dc01f0fd637d Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Tue, 20 Sep 2016 15:03:47 -0700 Subject: [PATCH 20/21] soft fail on missing C11 --- test/test_c11.c | 21 +++++++++------------ 1 file changed, 9 insertions(+), 12 deletions(-) diff --git a/test/test_c11.c b/test/test_c11.c index 2acc50e..43e9a4b 100644 --- a/test/test_c11.c +++ b/test/test_c11.c @@ -1,19 +1,15 @@ -#if __STDC_VERSION__ < 201112L - -#warning Empty test due to lack of C11 support. -int main(void) { return 1; } - -#else - #include #include -#include -#include - #include +#if __STDC_VERSION__ >= 201112L +# include +# include +#endif + int main(int argc, char **argv) { +#if __STDC_VERSION__ >= 201112L atomic_int a, b; int c; @@ -51,8 +47,9 @@ int main(int argc, char **argv) assert(1 == atomic_load_explicit(&a, memory_order_relaxed)); printf("success!\n"); - +#else + printf("C11 not supported!\n"); +#endif return 0; } -#endif From 4c2e1874b73782a82efd8436860f299bb95ccdf5 Mon Sep 17 00:00:00 2001 From: Jeff Hammond Date: Mon, 29 Apr 2019 16:44:56 -0700 Subject: [PATCH 21/21] remove notifications --- .travis.yml | 8 -------- 1 file changed, 8 deletions(-) diff --git a/.travis.yml b/.travis.yml index 59f4948..3aac0aa 100644 --- a/.travis.yml +++ b/.travis.yml @@ -47,11 +47,3 @@ script: after_failure: - echo "Sad panda" - find . -name config.log -exec cat {} ";" -notifications: - email: - recipients: - - jeff.science@gmail.com - on_success: - - change - on_failure: - - always