00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031 #ifndef _GLIBCXX_ATOMIC_2_H
00032 #define _GLIBCXX_ATOMIC_2_H 1
00033
00034 #pragma GCC system_header
00035
00036 namespace std _GLIBCXX_VISIBILITY(default)
00037 {
00038 _GLIBCXX_BEGIN_NAMESPACE_VERSION
00039
00040
00041
00042
00043
00044
00045
00046 namespace __atomic2
00047 {
00048
00049 struct atomic_flag : public __atomic_flag_base
00050 {
00051 atomic_flag() = default;
00052 ~atomic_flag() = default;
00053 atomic_flag(const atomic_flag&) = delete;
00054 atomic_flag& operator=(const atomic_flag&) = delete;
00055 atomic_flag& operator=(const atomic_flag&) volatile = delete;
00056
00057
00058 atomic_flag(bool __i): __atomic_flag_base({ __i }) { }
00059
00060 bool
00061 test_and_set(memory_order __m = memory_order_seq_cst)
00062 {
00063
00064 if (__m != memory_order_acquire && __m != memory_order_acq_rel)
00065 __sync_synchronize();
00066 return __sync_lock_test_and_set(&_M_i, 1);
00067 }
00068
00069 bool
00070 test_and_set(memory_order __m = memory_order_seq_cst) volatile
00071 {
00072
00073 if (__m != memory_order_acquire && __m != memory_order_acq_rel)
00074 __sync_synchronize();
00075 return __sync_lock_test_and_set(&_M_i, 1);
00076 }
00077
00078 void
00079 clear(memory_order __m = memory_order_seq_cst)
00080 {
00081 __glibcxx_assert(__m != memory_order_consume);
00082 __glibcxx_assert(__m != memory_order_acquire);
00083 __glibcxx_assert(__m != memory_order_acq_rel);
00084
00085 __sync_lock_release(&_M_i);
00086 if (__m != memory_order_acquire && __m != memory_order_acq_rel)
00087 __sync_synchronize();
00088 }
00089
00090 void
00091 clear(memory_order __m = memory_order_seq_cst) volatile
00092 {
00093 __glibcxx_assert(__m != memory_order_consume);
00094 __glibcxx_assert(__m != memory_order_acquire);
00095 __glibcxx_assert(__m != memory_order_acq_rel);
00096
00097 __sync_lock_release(&_M_i);
00098 if (__m != memory_order_acquire && __m != memory_order_acq_rel)
00099 __sync_synchronize();
00100 }
00101 };
00102
00103
00104
00105 struct atomic_address
00106 {
00107 private:
00108 void* _M_i;
00109
00110 public:
00111 atomic_address() = default;
00112 ~atomic_address() = default;
00113 atomic_address(const atomic_address&) = delete;
00114 atomic_address& operator=(const atomic_address&) = delete;
00115 atomic_address& operator=(const atomic_address&) volatile = delete;
00116
00117 constexpr atomic_address(void* __v): _M_i (__v) { }
00118
00119 bool
00120 is_lock_free() const { return true; }
00121
00122 bool
00123 is_lock_free() const volatile { return true; }
00124
00125 void
00126 store(void* __v, memory_order __m = memory_order_seq_cst)
00127 {
00128 __glibcxx_assert(__m != memory_order_acquire);
00129 __glibcxx_assert(__m != memory_order_acq_rel);
00130 __glibcxx_assert(__m != memory_order_consume);
00131
00132 if (__m == memory_order_relaxed)
00133 _M_i = __v;
00134 else
00135 {
00136
00137 _M_i = __v;
00138 if (__m == memory_order_seq_cst)
00139 __sync_synchronize();
00140 }
00141 }
00142
00143 void
00144 store(void* __v, memory_order __m = memory_order_seq_cst) volatile
00145 {
00146 __glibcxx_assert(__m != memory_order_acquire);
00147 __glibcxx_assert(__m != memory_order_acq_rel);
00148 __glibcxx_assert(__m != memory_order_consume);
00149
00150 if (__m == memory_order_relaxed)
00151 _M_i = __v;
00152 else
00153 {
00154
00155 _M_i = __v;
00156 if (__m == memory_order_seq_cst)
00157 __sync_synchronize();
00158 }
00159 }
00160
00161 void*
00162 load(memory_order __m = memory_order_seq_cst) const
00163 {
00164 __glibcxx_assert(__m != memory_order_release);
00165 __glibcxx_assert(__m != memory_order_acq_rel);
00166
00167 __sync_synchronize();
00168 void* __ret = _M_i;
00169 __sync_synchronize();
00170 return __ret;
00171 }
00172
00173 void*
00174 load(memory_order __m = memory_order_seq_cst) const volatile
00175 {
00176 __glibcxx_assert(__m != memory_order_release);
00177 __glibcxx_assert(__m != memory_order_acq_rel);
00178
00179 __sync_synchronize();
00180 void* __ret = _M_i;
00181 __sync_synchronize();
00182 return __ret;
00183 }
00184
00185 void*
00186 exchange(void* __v, memory_order __m = memory_order_seq_cst)
00187 {
00188
00189 return __sync_lock_test_and_set(&_M_i, __v);
00190 }
00191
00192 void*
00193 exchange(void* __v, memory_order __m = memory_order_seq_cst) volatile
00194 {
00195
00196 return __sync_lock_test_and_set(&_M_i, __v);
00197 }
00198
00199 bool
00200 compare_exchange_weak(void*& __v1, void* __v2, memory_order __m1,
00201 memory_order __m2)
00202 { return compare_exchange_strong(__v1, __v2, __m1, __m2); }
00203
00204 bool
00205 compare_exchange_weak(void*& __v1, void* __v2, memory_order __m1,
00206 memory_order __m2) volatile
00207 { return compare_exchange_strong(__v1, __v2, __m1, __m2); }
00208
00209 bool
00210 compare_exchange_weak(void*& __v1, void* __v2,
00211 memory_order __m = memory_order_seq_cst)
00212 {
00213 return compare_exchange_weak(__v1, __v2, __m,
00214 __calculate_memory_order(__m));
00215 }
00216
00217 bool
00218 compare_exchange_weak(void*& __v1, void* __v2,
00219 memory_order __m = memory_order_seq_cst) volatile
00220 {
00221 return compare_exchange_weak(__v1, __v2, __m,
00222 __calculate_memory_order(__m));
00223 }
00224
00225 bool
00226 compare_exchange_weak(const void*& __v1, const void* __v2,
00227 memory_order __m1, memory_order __m2)
00228 { return compare_exchange_strong(__v1, __v2, __m1, __m2); }
00229
00230 bool
00231 compare_exchange_weak(const void*& __v1, const void* __v2,
00232 memory_order __m1, memory_order __m2) volatile
00233 { return compare_exchange_strong(__v1, __v2, __m1, __m2); }
00234
00235 bool
00236 compare_exchange_weak(const void*& __v1, const void* __v2,
00237 memory_order __m = memory_order_seq_cst)
00238 {
00239 return compare_exchange_weak(__v1, __v2, __m,
00240 __calculate_memory_order(__m));
00241 }
00242
00243 bool
00244 compare_exchange_weak(const void*& __v1, const void* __v2,
00245 memory_order __m = memory_order_seq_cst) volatile
00246 {
00247 return compare_exchange_weak(__v1, __v2, __m,
00248 __calculate_memory_order(__m));
00249 }
00250
00251 bool
00252 compare_exchange_strong(void*& __v1, void* __v2, memory_order __m1,
00253 memory_order __m2)
00254 {
00255 __glibcxx_assert(__m2 != memory_order_release);
00256 __glibcxx_assert(__m2 != memory_order_acq_rel);
00257 __glibcxx_assert(__m2 <= __m1);
00258
00259 void* __v1o = __v1;
00260 void* __v1n = __sync_val_compare_and_swap(&_M_i, __v1o, __v2);
00261
00262
00263 __v1 = __v1n;
00264 return __v1o == __v1n;
00265 }
00266
00267 bool
00268 compare_exchange_strong(void*& __v1, void* __v2, memory_order __m1,
00269 memory_order __m2) volatile
00270 {
00271 __glibcxx_assert(__m2 != memory_order_release);
00272 __glibcxx_assert(__m2 != memory_order_acq_rel);
00273 __glibcxx_assert(__m2 <= __m1);
00274
00275 void* __v1o = __v1;
00276 void* __v1n = __sync_val_compare_and_swap(&_M_i, __v1o, __v2);
00277
00278
00279 __v1 = __v1n;
00280 return __v1o == __v1n;
00281 }
00282
00283 bool
00284 compare_exchange_strong(void*& __v1, void* __v2,
00285 memory_order __m = memory_order_seq_cst)
00286 {
00287 return compare_exchange_strong(__v1, __v2, __m,
00288 __calculate_memory_order(__m));
00289 }
00290
00291 bool
00292 compare_exchange_strong(void*& __v1, void* __v2,
00293 memory_order __m = memory_order_seq_cst) volatile
00294 {
00295 return compare_exchange_strong(__v1, __v2, __m,
00296 __calculate_memory_order(__m));
00297 }
00298
00299 bool
00300 compare_exchange_strong(const void*& __v1, const void* __v2,
00301 memory_order __m1, memory_order __m2)
00302 {
00303 __glibcxx_assert(__m2 != memory_order_release);
00304 __glibcxx_assert(__m2 != memory_order_acq_rel);
00305 __glibcxx_assert(__m2 <= __m1);
00306
00307 const void* __v1o = __v1;
00308 const void* __v1n = __sync_val_compare_and_swap(&_M_i, __v1o, __v2);
00309
00310
00311 __v1 = __v1n;
00312 return __v1o == __v1n;
00313 }
00314
00315 bool
00316 compare_exchange_strong(const void*& __v1, const void* __v2,
00317 memory_order __m1, memory_order __m2) volatile
00318 {
00319 __glibcxx_assert(__m2 != memory_order_release);
00320 __glibcxx_assert(__m2 != memory_order_acq_rel);
00321 __glibcxx_assert(__m2 <= __m1);
00322
00323 const void* __v1o = __v1;
00324 const void* __v1n = __sync_val_compare_and_swap(&_M_i, __v1o, __v2);
00325
00326
00327 __v1 = __v1n;
00328 return __v1o == __v1n;
00329 }
00330
00331 bool
00332 compare_exchange_strong(const void*& __v1, const void* __v2,
00333 memory_order __m = memory_order_seq_cst)
00334 {
00335 return compare_exchange_strong(__v1, __v2, __m,
00336 __calculate_memory_order(__m));
00337 }
00338
00339 bool
00340 compare_exchange_strong(const void*& __v1, const void* __v2,
00341 memory_order __m = memory_order_seq_cst) volatile
00342 {
00343 return compare_exchange_strong(__v1, __v2, __m,
00344 __calculate_memory_order(__m));
00345 }
00346
00347 void*
00348 fetch_add(ptrdiff_t __d, memory_order __m = memory_order_seq_cst)
00349 { return __sync_fetch_and_add(&_M_i, __d); }
00350
00351 void*
00352 fetch_add(ptrdiff_t __d, memory_order __m = memory_order_seq_cst) volatile
00353 { return __sync_fetch_and_add(&_M_i, __d); }
00354
00355 void*
00356 fetch_sub(ptrdiff_t __d, memory_order __m = memory_order_seq_cst)
00357 { return __sync_fetch_and_sub(&_M_i, __d); }
00358
00359 void*
00360 fetch_sub(ptrdiff_t __d, memory_order __m = memory_order_seq_cst) volatile
00361 { return __sync_fetch_and_sub(&_M_i, __d); }
00362
00363 operator void*() const
00364 { return load(); }
00365
00366 operator void*() const volatile
00367 { return load(); }
00368
00369 void*
00370 #if 0
00371
00372
00373
00374 operator=(const void* __v)
00375 #else
00376 operator=(void* __v)
00377 #endif
00378 {
00379 store(__v);
00380 return __v;
00381 }
00382
00383 void*
00384 #if 0
00385
00386
00387
00388 operator=(const void* __v) volatile
00389 #else
00390 operator=(void* __v) volatile
00391 #endif
00392 {
00393 store(__v);
00394 return __v;
00395 }
00396
00397 void*
00398 operator+=(ptrdiff_t __d)
00399 { return __sync_add_and_fetch(&_M_i, __d); }
00400
00401 void*
00402 operator+=(ptrdiff_t __d) volatile
00403 { return __sync_add_and_fetch(&_M_i, __d); }
00404
00405 void*
00406 operator-=(ptrdiff_t __d)
00407 { return __sync_sub_and_fetch(&_M_i, __d); }
00408
00409 void*
00410 operator-=(ptrdiff_t __d) volatile
00411 { return __sync_sub_and_fetch(&_M_i, __d); }
00412 };
00413
00414
00415
00416
00417
00418
00419
00420
00421
00422
00423
00424
00425
00426
00427
00428
00429
00430
00431
00432
00433
00434
00435
00436
00437
00438 template<typename _ITp>
00439 struct __atomic_base
00440 {
00441 private:
00442 typedef _ITp __int_type;
00443
00444 __int_type _M_i;
00445
00446 public:
00447 __atomic_base() = default;
00448 ~__atomic_base() = default;
00449 __atomic_base(const __atomic_base&) = delete;
00450 __atomic_base& operator=(const __atomic_base&) = delete;
00451 __atomic_base& operator=(const __atomic_base&) volatile = delete;
00452
00453
00454 constexpr __atomic_base(__int_type __i): _M_i (__i) { }
00455
00456 operator __int_type() const
00457 { return load(); }
00458
00459 operator __int_type() const volatile
00460 { return load(); }
00461
00462 __int_type
00463 operator=(__int_type __i)
00464 {
00465 store(__i);
00466 return __i;
00467 }
00468
00469 __int_type
00470 operator=(__int_type __i) volatile
00471 {
00472 store(__i);
00473 return __i;
00474 }
00475
00476 __int_type
00477 operator++(int)
00478 { return fetch_add(1); }
00479
00480 __int_type
00481 operator++(int) volatile
00482 { return fetch_add(1); }
00483
00484 __int_type
00485 operator--(int)
00486 { return fetch_sub(1); }
00487
00488 __int_type
00489 operator--(int) volatile
00490 { return fetch_sub(1); }
00491
00492 __int_type
00493 operator++()
00494 { return __sync_add_and_fetch(&_M_i, 1); }
00495
00496 __int_type
00497 operator++() volatile
00498 { return __sync_add_and_fetch(&_M_i, 1); }
00499
00500 __int_type
00501 operator--()
00502 { return __sync_sub_and_fetch(&_M_i, 1); }
00503
00504 __int_type
00505 operator--() volatile
00506 { return __sync_sub_and_fetch(&_M_i, 1); }
00507
00508 __int_type
00509 operator+=(__int_type __i)
00510 { return __sync_add_and_fetch(&_M_i, __i); }
00511
00512 __int_type
00513 operator+=(__int_type __i) volatile
00514 { return __sync_add_and_fetch(&_M_i, __i); }
00515
00516 __int_type
00517 operator-=(__int_type __i)
00518 { return __sync_sub_and_fetch(&_M_i, __i); }
00519
00520 __int_type
00521 operator-=(__int_type __i) volatile
00522 { return __sync_sub_and_fetch(&_M_i, __i); }
00523
00524 __int_type
00525 operator&=(__int_type __i)
00526 { return __sync_and_and_fetch(&_M_i, __i); }
00527
00528 __int_type
00529 operator&=(__int_type __i) volatile
00530 { return __sync_and_and_fetch(&_M_i, __i); }
00531
00532 __int_type
00533 operator|=(__int_type __i)
00534 { return __sync_or_and_fetch(&_M_i, __i); }
00535
00536 __int_type
00537 operator|=(__int_type __i) volatile
00538 { return __sync_or_and_fetch(&_M_i, __i); }
00539
00540 __int_type
00541 operator^=(__int_type __i)
00542 { return __sync_xor_and_fetch(&_M_i, __i); }
00543
00544 __int_type
00545 operator^=(__int_type __i) volatile
00546 { return __sync_xor_and_fetch(&_M_i, __i); }
00547
00548 bool
00549 is_lock_free() const
00550 { return true; }
00551
00552 bool
00553 is_lock_free() const volatile
00554 { return true; }
00555
00556 void
00557 store(__int_type __i, memory_order __m = memory_order_seq_cst)
00558 {
00559 __glibcxx_assert(__m != memory_order_acquire);
00560 __glibcxx_assert(__m != memory_order_acq_rel);
00561 __glibcxx_assert(__m != memory_order_consume);
00562
00563 if (__m == memory_order_relaxed)
00564 _M_i = __i;
00565 else
00566 {
00567
00568 _M_i = __i;
00569 if (__m == memory_order_seq_cst)
00570 __sync_synchronize();
00571 }
00572 }
00573
00574 void
00575 store(__int_type __i, memory_order __m = memory_order_seq_cst) volatile
00576 {
00577 __glibcxx_assert(__m != memory_order_acquire);
00578 __glibcxx_assert(__m != memory_order_acq_rel);
00579 __glibcxx_assert(__m != memory_order_consume);
00580
00581 if (__m == memory_order_relaxed)
00582 _M_i = __i;
00583 else
00584 {
00585
00586 _M_i = __i;
00587 if (__m == memory_order_seq_cst)
00588 __sync_synchronize();
00589 }
00590 }
00591
00592 __int_type
00593 load(memory_order __m = memory_order_seq_cst) const
00594 {
00595 __glibcxx_assert(__m != memory_order_release);
00596 __glibcxx_assert(__m != memory_order_acq_rel);
00597
00598 __sync_synchronize();
00599 __int_type __ret = _M_i;
00600 __sync_synchronize();
00601 return __ret;
00602 }
00603
00604 __int_type
00605 load(memory_order __m = memory_order_seq_cst) const volatile
00606 {
00607 __glibcxx_assert(__m != memory_order_release);
00608 __glibcxx_assert(__m != memory_order_acq_rel);
00609
00610 __sync_synchronize();
00611 __int_type __ret = _M_i;
00612 __sync_synchronize();
00613 return __ret;
00614 }
00615
00616 __int_type
00617 exchange(__int_type __i, memory_order __m = memory_order_seq_cst)
00618 {
00619
00620 return __sync_lock_test_and_set(&_M_i, __i);
00621 }
00622
00623
00624 __int_type
00625 exchange(__int_type __i, memory_order __m = memory_order_seq_cst) volatile
00626 {
00627
00628 return __sync_lock_test_and_set(&_M_i, __i);
00629 }
00630
00631 bool
00632 compare_exchange_weak(__int_type& __i1, __int_type __i2,
00633 memory_order __m1, memory_order __m2)
00634 { return compare_exchange_strong(__i1, __i2, __m1, __m2); }
00635
00636 bool
00637 compare_exchange_weak(__int_type& __i1, __int_type __i2,
00638 memory_order __m1, memory_order __m2) volatile
00639 { return compare_exchange_strong(__i1, __i2, __m1, __m2); }
00640
00641 bool
00642 compare_exchange_weak(__int_type& __i1, __int_type __i2,
00643 memory_order __m = memory_order_seq_cst)
00644 {
00645 return compare_exchange_weak(__i1, __i2, __m,
00646 __calculate_memory_order(__m));
00647 }
00648
00649 bool
00650 compare_exchange_weak(__int_type& __i1, __int_type __i2,
00651 memory_order __m = memory_order_seq_cst) volatile
00652 {
00653 return compare_exchange_weak(__i1, __i2, __m,
00654 __calculate_memory_order(__m));
00655 }
00656
00657 bool
00658 compare_exchange_strong(__int_type& __i1, __int_type __i2,
00659 memory_order __m1, memory_order __m2)
00660 {
00661 __glibcxx_assert(__m2 != memory_order_release);
00662 __glibcxx_assert(__m2 != memory_order_acq_rel);
00663 __glibcxx_assert(__m2 <= __m1);
00664
00665 __int_type __i1o = __i1;
00666 __int_type __i1n = __sync_val_compare_and_swap(&_M_i, __i1o, __i2);
00667
00668
00669 __i1 = __i1n;
00670 return __i1o == __i1n;
00671 }
00672
00673 bool
00674 compare_exchange_strong(__int_type& __i1, __int_type __i2,
00675 memory_order __m1, memory_order __m2) volatile
00676 {
00677 __glibcxx_assert(__m2 != memory_order_release);
00678 __glibcxx_assert(__m2 != memory_order_acq_rel);
00679 __glibcxx_assert(__m2 <= __m1);
00680
00681 __int_type __i1o = __i1;
00682 __int_type __i1n = __sync_val_compare_and_swap(&_M_i, __i1o, __i2);
00683
00684
00685 __i1 = __i1n;
00686 return __i1o == __i1n;
00687 }
00688
00689 bool
00690 compare_exchange_strong(__int_type& __i1, __int_type __i2,
00691 memory_order __m = memory_order_seq_cst)
00692 {
00693 return compare_exchange_strong(__i1, __i2, __m,
00694 __calculate_memory_order(__m));
00695 }
00696
00697 bool
00698 compare_exchange_strong(__int_type& __i1, __int_type __i2,
00699 memory_order __m = memory_order_seq_cst) volatile
00700 {
00701 return compare_exchange_strong(__i1, __i2, __m,
00702 __calculate_memory_order(__m));
00703 }
00704
00705 __int_type
00706 fetch_add(__int_type __i, memory_order __m = memory_order_seq_cst)
00707 { return __sync_fetch_and_add(&_M_i, __i); }
00708
00709 __int_type
00710 fetch_add(__int_type __i,
00711 memory_order __m = memory_order_seq_cst) volatile
00712 { return __sync_fetch_and_add(&_M_i, __i); }
00713
00714 __int_type
00715 fetch_sub(__int_type __i, memory_order __m = memory_order_seq_cst)
00716 { return __sync_fetch_and_sub(&_M_i, __i); }
00717
00718 __int_type
00719 fetch_sub(__int_type __i,
00720 memory_order __m = memory_order_seq_cst) volatile
00721 { return __sync_fetch_and_sub(&_M_i, __i); }
00722
00723 __int_type
00724 fetch_and(__int_type __i, memory_order __m = memory_order_seq_cst)
00725 { return __sync_fetch_and_and(&_M_i, __i); }
00726
00727 __int_type
00728 fetch_and(__int_type __i,
00729 memory_order __m = memory_order_seq_cst) volatile
00730 { return __sync_fetch_and_and(&_M_i, __i); }
00731
00732 __int_type
00733 fetch_or(__int_type __i, memory_order __m = memory_order_seq_cst)
00734 { return __sync_fetch_and_or(&_M_i, __i); }
00735
00736 __int_type
00737 fetch_or(__int_type __i,
00738 memory_order __m = memory_order_seq_cst) volatile
00739 { return __sync_fetch_and_or(&_M_i, __i); }
00740
00741 __int_type
00742 fetch_xor(__int_type __i, memory_order __m = memory_order_seq_cst)
00743 { return __sync_fetch_and_xor(&_M_i, __i); }
00744
00745 __int_type
00746 fetch_xor(__int_type __i,
00747 memory_order __m = memory_order_seq_cst) volatile
00748 { return __sync_fetch_and_xor(&_M_i, __i); }
00749 };
00750 }
00751
00752 _GLIBCXX_END_NAMESPACE_VERSION
00753 }
00754
00755 #endif