1 //===----------------------------------------------------------------------===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is dual licensed under the MIT and the University of Illinois Open 6 // Source Licenses. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 // <atomic> 11 12 // template <class Integral> 13 // Integral 14 // atomic_fetch_sub_explicit(volatile atomic<Integral>* obj, Integral op, 15 // memory_order m); 16 // template <class Integral> 17 // Integral 18 // atomic_fetch_sub_explicit(atomic<Integral>* obj, Integral op, 19 // memory_order m); 20 // 21 // template <class T> 22 // T* 23 // atomic_fetch_sub_explicit(volatile atomic<T*>* obj, ptrdiff_t op, 24 // memory_order m); 25 // template <class T> 26 // T* 27 // atomic_fetch_sub_explicit(atomic<T*>* obj, ptrdiff_t op, memory_order m); 28 29 #include <atomic> 30 #include <type_traits> 31 #include <cassert> 32 33 template <class T> 34 void 35 test() 36 { 37 { 38 typedef std::atomic<T> A; 39 A t; 40 std::atomic_init(&t, T(3)); 41 assert(std::atomic_fetch_sub_explicit(&t, T(2), 42 std::memory_order_seq_cst) == T(3)); 43 assert(t == T(1)); 44 } 45 { 46 typedef std::atomic<T> A; 47 volatile A t; 48 std::atomic_init(&t, T(3)); 49 assert(std::atomic_fetch_sub_explicit(&t, T(2), 50 std::memory_order_seq_cst) == T(3)); 51 assert(t == T(1)); 52 } 53 } 54 55 template <class T> 56 void 57 testp() 58 { 59 { 60 typedef std::atomic<T> A; 61 typedef typename std::remove_pointer<T>::type X; 62 A t; 63 std::atomic_init(&t, T(3*sizeof(X))); 64 assert(std::atomic_fetch_sub_explicit(&t, 2, 65 std::memory_order_seq_cst) == T(3*sizeof(X))); 66 assert(t == T(1*sizeof(X))); 67 } 68 { 69 typedef std::atomic<T> A; 70 typedef typename std::remove_pointer<T>::type X; 71 volatile A t; 72 std::atomic_init(&t, T(3*sizeof(X))); 73 assert(std::atomic_fetch_sub_explicit(&t, 2, 74 std::memory_order_seq_cst) == T(3*sizeof(X))); 75 assert(t == T(1*sizeof(X))); 76 } 77 } 78 79 struct A 80 { 81 int i; 82 83 explicit A(int d = 0) : i(d) {} 84 A(const A& a) : i(a.i) {} 85 A(const volatile A& a) : i(a.i) {} 86 87 void operator=(const volatile A& a) volatile {i = a.i;} 88 89 friend bool operator==(const A& x, const A& y) 90 {return x.i == y.i;} 91 }; 92 93 int main() 94 { 95 test<char>(); 96 test<signed char>(); 97 test<unsigned char>(); 98 test<short>(); 99 test<unsigned short>(); 100 test<int>(); 101 test<unsigned int>(); 102 test<long>(); 103 test<unsigned long>(); 104 test<long long>(); 105 test<unsigned long long>(); 106 test<wchar_t>(); 107 #ifndef _LIBCPP_HAS_NO_UNICODE_CHARS 108 test<char16_t>(); 109 test<char32_t>(); 110 #endif // _LIBCPP_HAS_NO_UNICODE_CHARS 111 testp<int*>(); 112 testp<const int*>(); 113 } 114