File Coverage

/usr/include/c++/5/atomic
Criterion Covered Total %
statement 1 1 100.0
branch n/a
condition n/a
subroutine n/a
pod n/a
total 1 1 100.0


line stmt bran cond sub pod time code
1             // -*- C++ -*- header.
2              
3             // Copyright (C) 2008-2015 Free Software Foundation, Inc.
4             //
5             // This file is part of the GNU ISO C++ Library. This library is free
6             // software; you can redistribute it and/or modify it under the
7             // terms of the GNU General Public License as published by the
8             // Free Software Foundation; either version 3, or (at your option)
9             // any later version.
10              
11             // This library is distributed in the hope that it will be useful,
12             // but WITHOUT ANY WARRANTY; without even the implied warranty of
13             // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14             // GNU General Public License for more details.
15              
16             // Under Section 7 of GPL version 3, you are granted additional
17             // permissions described in the GCC Runtime Library Exception, version
18             // 3.1, as published by the Free Software Foundation.
19              
20             // You should have received a copy of the GNU General Public License and
21             // a copy of the GCC Runtime Library Exception along with this program;
22             // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
23             // .
24              
25             /** @file include/atomic
26             * This is a Standard C++ Library header.
27             */
28              
29             // Based on "C++ Atomic Types and Operations" by Hans Boehm and Lawrence Crowl.
30             // http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2007/n2427.html
31              
32             #ifndef _GLIBCXX_ATOMIC
33             #define _GLIBCXX_ATOMIC 1
34              
35             #pragma GCC system_header
36              
37             #if __cplusplus < 201103L
38             # include
39             #else
40              
41             #include
42              
43             namespace std _GLIBCXX_VISIBILITY(default)
44             {
45             _GLIBCXX_BEGIN_NAMESPACE_VERSION
46              
47             /**
48             * @addtogroup atomics
49             * @{
50             */
51              
52             template
53             struct atomic;
54              
55             /// atomic
56             // NB: No operators or fetch-operations for this type.
57             template<>
58             struct atomic
59             {
60             private:
61             __atomic_base _M_base;
62              
63             public:
64             atomic() noexcept = default;
65             ~atomic() noexcept = default;
66             atomic(const atomic&) = delete;
67             atomic& operator=(const atomic&) = delete;
68             atomic& operator=(const atomic&) volatile = delete;
69              
70             constexpr atomic(bool __i) noexcept : _M_base(__i) { }
71              
72             bool
73             operator=(bool __i) noexcept
74             { return _M_base.operator=(__i); }
75              
76             bool
77             operator=(bool __i) volatile noexcept
78             { return _M_base.operator=(__i); }
79              
80             operator bool() const noexcept
81             { return _M_base.load(); }
82              
83             operator bool() const volatile noexcept
84             { return _M_base.load(); }
85              
86             bool
87             is_lock_free() const noexcept { return _M_base.is_lock_free(); }
88              
89             bool
90             is_lock_free() const volatile noexcept { return _M_base.is_lock_free(); }
91              
92             void
93             store(bool __i, memory_order __m = memory_order_seq_cst) noexcept
94             { _M_base.store(__i, __m); }
95              
96             void
97             store(bool __i, memory_order __m = memory_order_seq_cst) volatile noexcept
98             { _M_base.store(__i, __m); }
99              
100             bool
101             load(memory_order __m = memory_order_seq_cst) const noexcept
102             { return _M_base.load(__m); }
103              
104             bool
105             load(memory_order __m = memory_order_seq_cst) const volatile noexcept
106             { return _M_base.load(__m); }
107              
108             bool
109             exchange(bool __i, memory_order __m = memory_order_seq_cst) noexcept
110             { return _M_base.exchange(__i, __m); }
111              
112             bool
113             exchange(bool __i,
114             memory_order __m = memory_order_seq_cst) volatile noexcept
115             { return _M_base.exchange(__i, __m); }
116              
117             bool
118             compare_exchange_weak(bool& __i1, bool __i2, memory_order __m1,
119             memory_order __m2) noexcept
120             { return _M_base.compare_exchange_weak(__i1, __i2, __m1, __m2); }
121              
122             bool
123             compare_exchange_weak(bool& __i1, bool __i2, memory_order __m1,
124             memory_order __m2) volatile noexcept
125             { return _M_base.compare_exchange_weak(__i1, __i2, __m1, __m2); }
126              
127             bool
128             compare_exchange_weak(bool& __i1, bool __i2,
129             memory_order __m = memory_order_seq_cst) noexcept
130             { return _M_base.compare_exchange_weak(__i1, __i2, __m); }
131              
132             bool
133             compare_exchange_weak(bool& __i1, bool __i2,
134             memory_order __m = memory_order_seq_cst) volatile noexcept
135             { return _M_base.compare_exchange_weak(__i1, __i2, __m); }
136              
137             bool
138             compare_exchange_strong(bool& __i1, bool __i2, memory_order __m1,
139             memory_order __m2) noexcept
140             { return _M_base.compare_exchange_strong(__i1, __i2, __m1, __m2); }
141              
142             bool
143             compare_exchange_strong(bool& __i1, bool __i2, memory_order __m1,
144             memory_order __m2) volatile noexcept
145             { return _M_base.compare_exchange_strong(__i1, __i2, __m1, __m2); }
146              
147             bool
148             compare_exchange_strong(bool& __i1, bool __i2,
149             memory_order __m = memory_order_seq_cst) noexcept
150             { return _M_base.compare_exchange_strong(__i1, __i2, __m); }
151              
152             bool
153             compare_exchange_strong(bool& __i1, bool __i2,
154             memory_order __m = memory_order_seq_cst) volatile noexcept
155             { return _M_base.compare_exchange_strong(__i1, __i2, __m); }
156             };
157              
158              
159             /**
160             * @brief Generic atomic type, primary class template.
161             *
162             * @tparam _Tp Type to be made atomic, must be trivally copyable.
163             */
164             template
165             struct atomic
166             {
167             private:
168             // Align 1/2/4/8/16-byte types to at least their size.
169             static constexpr int _S_min_alignment
170             = (sizeof(_Tp) & (sizeof(_Tp) - 1)) || sizeof(_Tp) > 16
171             ? 0 : sizeof(_Tp);
172              
173             static constexpr int _S_alignment
174             = _S_min_alignment > alignof(_Tp) ? _S_min_alignment : alignof(_Tp);
175              
176             alignas(_S_alignment) _Tp _M_i;
177              
178             static_assert(__is_trivially_copyable(_Tp),
179             "std::atomic requires a trivially copyable type");
180              
181             static_assert(sizeof(_Tp) > 0,
182             "Incomplete or zero-sized types are not supported");
183              
184             public:
185             atomic() noexcept = default;
186             ~atomic() noexcept = default;
187             atomic(const atomic&) = delete;
188             atomic& operator=(const atomic&) = delete;
189             atomic& operator=(const atomic&) volatile = delete;
190              
191             constexpr atomic(_Tp __i) noexcept : _M_i(__i) { }
192              
193             operator _Tp() const noexcept
194             { return load(); }
195              
196             operator _Tp() const volatile noexcept
197             { return load(); }
198              
199             _Tp
200             operator=(_Tp __i) noexcept
201             { store(__i); return __i; }
202              
203             _Tp
204             operator=(_Tp __i) volatile noexcept
205             { store(__i); return __i; }
206              
207             bool
208             is_lock_free() const noexcept
209             {
210             // Produce a fake, minimally aligned pointer.
211             return __atomic_is_lock_free(sizeof(_M_i),
212             reinterpret_cast(-__alignof(_M_i)));
213             }
214              
215             bool
216             is_lock_free() const volatile noexcept
217             {
218             // Produce a fake, minimally aligned pointer.
219             return __atomic_is_lock_free(sizeof(_M_i),
220             reinterpret_cast(-__alignof(_M_i)));
221             }
222              
223             void
224             store(_Tp __i, memory_order __m = memory_order_seq_cst) noexcept
225             { __atomic_store(&_M_i, &__i, __m); }
226              
227             void
228             store(_Tp __i, memory_order __m = memory_order_seq_cst) volatile noexcept
229             { __atomic_store(&_M_i, &__i, __m); }
230              
231             _Tp
232             load(memory_order __m = memory_order_seq_cst) const noexcept
233             {
234             _Tp tmp;
235             __atomic_load(&_M_i, &tmp, __m);
236             return tmp;
237             }
238              
239             _Tp
240             load(memory_order __m = memory_order_seq_cst) const volatile noexcept
241             {
242             _Tp tmp;
243             __atomic_load(&_M_i, &tmp, __m);
244             return tmp;
245             }
246              
247             _Tp
248             exchange(_Tp __i, memory_order __m = memory_order_seq_cst) noexcept
249             {
250             _Tp tmp;
251             __atomic_exchange(&_M_i, &__i, &tmp, __m);
252             return tmp;
253             }
254              
255             _Tp
256             exchange(_Tp __i,
257             memory_order __m = memory_order_seq_cst) volatile noexcept
258             {
259             _Tp tmp;
260             __atomic_exchange(&_M_i, &__i, &tmp, __m);
261             return tmp;
262             }
263              
264             bool
265             compare_exchange_weak(_Tp& __e, _Tp __i, memory_order __s,
266             memory_order __f) noexcept
267             {
268             return __atomic_compare_exchange(&_M_i, &__e, &__i, true, __s, __f);
269             }
270              
271             bool
272             compare_exchange_weak(_Tp& __e, _Tp __i, memory_order __s,
273             memory_order __f) volatile noexcept
274             {
275             return __atomic_compare_exchange(&_M_i, &__e, &__i, true, __s, __f);
276             }
277              
278             bool
279             compare_exchange_weak(_Tp& __e, _Tp __i,
280             memory_order __m = memory_order_seq_cst) noexcept
281             { return compare_exchange_weak(__e, __i, __m,
282             __cmpexch_failure_order(__m)); }
283              
284             bool
285             compare_exchange_weak(_Tp& __e, _Tp __i,
286             memory_order __m = memory_order_seq_cst) volatile noexcept
287             { return compare_exchange_weak(__e, __i, __m,
288             __cmpexch_failure_order(__m)); }
289              
290             bool
291             compare_exchange_strong(_Tp& __e, _Tp __i, memory_order __s,
292             memory_order __f) noexcept
293             {
294             return __atomic_compare_exchange(&_M_i, &__e, &__i, false, __s, __f);
295             }
296              
297             bool
298             compare_exchange_strong(_Tp& __e, _Tp __i, memory_order __s,
299             memory_order __f) volatile noexcept
300             {
301             return __atomic_compare_exchange(&_M_i, &__e, &__i, false, __s, __f);
302             }
303              
304             bool
305             compare_exchange_strong(_Tp& __e, _Tp __i,
306             memory_order __m = memory_order_seq_cst) noexcept
307             { return compare_exchange_strong(__e, __i, __m,
308             __cmpexch_failure_order(__m)); }
309              
310             bool
311             compare_exchange_strong(_Tp& __e, _Tp __i,
312             memory_order __m = memory_order_seq_cst) volatile noexcept
313             { return compare_exchange_strong(__e, __i, __m,
314             __cmpexch_failure_order(__m)); }
315             };
316              
317              
318             /// Partial specialization for pointer types.
319             template
320             struct atomic<_Tp*>
321             {
322             typedef _Tp* __pointer_type;
323             typedef __atomic_base<_Tp*> __base_type;
324             __base_type _M_b;
325              
326             atomic() noexcept = default;
327             ~atomic() noexcept = default;
328             atomic(const atomic&) = delete;
329             atomic& operator=(const atomic&) = delete;
330             atomic& operator=(const atomic&) volatile = delete;
331              
332             constexpr atomic(__pointer_type __p) noexcept : _M_b(__p) { }
333              
334             operator __pointer_type() const noexcept
335             { return __pointer_type(_M_b); }
336              
337             operator __pointer_type() const volatile noexcept
338             { return __pointer_type(_M_b); }
339              
340             __pointer_type
341             operator=(__pointer_type __p) noexcept
342             { return _M_b.operator=(__p); }
343              
344             __pointer_type
345             operator=(__pointer_type __p) volatile noexcept
346             { return _M_b.operator=(__p); }
347              
348             __pointer_type
349             operator++(int) noexcept
350             { return _M_b++; }
351              
352             __pointer_type
353             operator++(int) volatile noexcept
354             { return _M_b++; }
355              
356             __pointer_type
357             operator--(int) noexcept
358             { return _M_b--; }
359              
360             __pointer_type
361             operator--(int) volatile noexcept
362             { return _M_b--; }
363              
364             __pointer_type
365             operator++() noexcept
366             { return ++_M_b; }
367              
368             __pointer_type
369             operator++() volatile noexcept
370             { return ++_M_b; }
371              
372             __pointer_type
373             operator--() noexcept
374             { return --_M_b; }
375              
376             __pointer_type
377             operator--() volatile noexcept
378             { return --_M_b; }
379              
380             __pointer_type
381             operator+=(ptrdiff_t __d) noexcept
382             { return _M_b.operator+=(__d); }
383              
384             __pointer_type
385             operator+=(ptrdiff_t __d) volatile noexcept
386             { return _M_b.operator+=(__d); }
387              
388             __pointer_type
389             operator-=(ptrdiff_t __d) noexcept
390             { return _M_b.operator-=(__d); }
391              
392             __pointer_type
393             operator-=(ptrdiff_t __d) volatile noexcept
394             { return _M_b.operator-=(__d); }
395              
396             bool
397             is_lock_free() const noexcept
398             { return _M_b.is_lock_free(); }
399              
400             bool
401             is_lock_free() const volatile noexcept
402             { return _M_b.is_lock_free(); }
403              
404             void
405             store(__pointer_type __p,
406             memory_order __m = memory_order_seq_cst) noexcept
407             { return _M_b.store(__p, __m); }
408              
409             void
410             store(__pointer_type __p,
411             memory_order __m = memory_order_seq_cst) volatile noexcept
412             { return _M_b.store(__p, __m); }
413              
414             __pointer_type
415             load(memory_order __m = memory_order_seq_cst) const noexcept
416             { return _M_b.load(__m); }
417              
418             __pointer_type
419             load(memory_order __m = memory_order_seq_cst) const volatile noexcept
420             { return _M_b.load(__m); }
421              
422             __pointer_type
423             exchange(__pointer_type __p,
424             memory_order __m = memory_order_seq_cst) noexcept
425             { return _M_b.exchange(__p, __m); }
426              
427             __pointer_type
428             exchange(__pointer_type __p,
429             memory_order __m = memory_order_seq_cst) volatile noexcept
430             { return _M_b.exchange(__p, __m); }
431              
432             bool
433             compare_exchange_weak(__pointer_type& __p1, __pointer_type __p2,
434             memory_order __m1, memory_order __m2) noexcept
435             { return _M_b.compare_exchange_strong(__p1, __p2, __m1, __m2); }
436              
437             bool
438             compare_exchange_weak(__pointer_type& __p1, __pointer_type __p2,
439             memory_order __m1,
440             memory_order __m2) volatile noexcept
441             { return _M_b.compare_exchange_strong(__p1, __p2, __m1, __m2); }
442              
443             bool
444             compare_exchange_weak(__pointer_type& __p1, __pointer_type __p2,
445             memory_order __m = memory_order_seq_cst) noexcept
446             {
447             return compare_exchange_weak(__p1, __p2, __m,
448             __cmpexch_failure_order(__m));
449             }
450              
451             bool
452             compare_exchange_weak(__pointer_type& __p1, __pointer_type __p2,
453             memory_order __m = memory_order_seq_cst) volatile noexcept
454             {
455             return compare_exchange_weak(__p1, __p2, __m,
456             __cmpexch_failure_order(__m));
457             }
458              
459             bool
460             compare_exchange_strong(__pointer_type& __p1, __pointer_type __p2,
461             memory_order __m1, memory_order __m2) noexcept
462             { return _M_b.compare_exchange_strong(__p1, __p2, __m1, __m2); }
463              
464             bool
465             compare_exchange_strong(__pointer_type& __p1, __pointer_type __p2,
466             memory_order __m1,
467             memory_order __m2) volatile noexcept
468             { return _M_b.compare_exchange_strong(__p1, __p2, __m1, __m2); }
469              
470             bool
471             compare_exchange_strong(__pointer_type& __p1, __pointer_type __p2,
472             memory_order __m = memory_order_seq_cst) noexcept
473             {
474             return _M_b.compare_exchange_strong(__p1, __p2, __m,
475             __cmpexch_failure_order(__m));
476             }
477              
478             bool
479             compare_exchange_strong(__pointer_type& __p1, __pointer_type __p2,
480             memory_order __m = memory_order_seq_cst) volatile noexcept
481             {
482             return _M_b.compare_exchange_strong(__p1, __p2, __m,
483             __cmpexch_failure_order(__m));
484             }
485              
486             __pointer_type
487             fetch_add(ptrdiff_t __d,
488             memory_order __m = memory_order_seq_cst) noexcept
489             { return _M_b.fetch_add(__d, __m); }
490              
491             __pointer_type
492             fetch_add(ptrdiff_t __d,
493             memory_order __m = memory_order_seq_cst) volatile noexcept
494             { return _M_b.fetch_add(__d, __m); }
495              
496             __pointer_type
497             fetch_sub(ptrdiff_t __d,
498             memory_order __m = memory_order_seq_cst) noexcept
499             { return _M_b.fetch_sub(__d, __m); }
500              
501             __pointer_type
502             fetch_sub(ptrdiff_t __d,
503             memory_order __m = memory_order_seq_cst) volatile noexcept
504             { return _M_b.fetch_sub(__d, __m); }
505             };
506              
507              
508             /// Explicit specialization for char.
509             template<>
510             struct atomic : __atomic_base
511             {
512             typedef char __integral_type;
513             typedef __atomic_base __base_type;
514              
515             atomic() noexcept = default;
516             ~atomic() noexcept = default;
517             atomic(const atomic&) = delete;
518             atomic& operator=(const atomic&) = delete;
519             atomic& operator=(const atomic&) volatile = delete;
520              
521             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
522              
523             using __base_type::operator __integral_type;
524             using __base_type::operator=;
525             };
526              
527             /// Explicit specialization for signed char.
528             template<>
529             struct atomic : __atomic_base
530             {
531             typedef signed char __integral_type;
532             typedef __atomic_base __base_type;
533              
534             atomic() noexcept= default;
535             ~atomic() noexcept = default;
536             atomic(const atomic&) = delete;
537             atomic& operator=(const atomic&) = delete;
538             atomic& operator=(const atomic&) volatile = delete;
539              
540             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
541              
542             using __base_type::operator __integral_type;
543             using __base_type::operator=;
544             };
545              
546             /// Explicit specialization for unsigned char.
547             template<>
548             struct atomic : __atomic_base
549             {
550             typedef unsigned char __integral_type;
551             typedef __atomic_base __base_type;
552              
553             atomic() noexcept= default;
554             ~atomic() noexcept = default;
555             atomic(const atomic&) = delete;
556             atomic& operator=(const atomic&) = delete;
557             atomic& operator=(const atomic&) volatile = delete;
558              
559             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
560              
561             using __base_type::operator __integral_type;
562             using __base_type::operator=;
563             };
564              
565             /// Explicit specialization for short.
566             template<>
567             struct atomic : __atomic_base
568             {
569             typedef short __integral_type;
570             typedef __atomic_base __base_type;
571              
572             atomic() noexcept = default;
573             ~atomic() noexcept = default;
574             atomic(const atomic&) = delete;
575             atomic& operator=(const atomic&) = delete;
576             atomic& operator=(const atomic&) volatile = delete;
577              
578             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
579              
580             using __base_type::operator __integral_type;
581             using __base_type::operator=;
582             };
583              
584             /// Explicit specialization for unsigned short.
585             template<>
586             struct atomic : __atomic_base
587             {
588             typedef unsigned short __integral_type;
589             typedef __atomic_base __base_type;
590              
591             atomic() noexcept = default;
592             ~atomic() noexcept = default;
593             atomic(const atomic&) = delete;
594             atomic& operator=(const atomic&) = delete;
595             atomic& operator=(const atomic&) volatile = delete;
596              
597             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
598              
599             using __base_type::operator __integral_type;
600             using __base_type::operator=;
601             };
602              
603             /// Explicit specialization for int.
604             template<>
605             struct atomic : __atomic_base
606             {
607             typedef int __integral_type;
608             typedef __atomic_base __base_type;
609              
610             atomic() noexcept = default;
611             ~atomic() noexcept = default;
612             atomic(const atomic&) = delete;
613             atomic& operator=(const atomic&) = delete;
614             atomic& operator=(const atomic&) volatile = delete;
615              
616             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
617              
618             using __base_type::operator __integral_type;
619             using __base_type::operator=;
620             };
621              
622             /// Explicit specialization for unsigned int.
623             template<>
624             struct atomic : __atomic_base
625             {
626             typedef unsigned int __integral_type;
627             typedef __atomic_base __base_type;
628              
629             atomic() noexcept = default;
630             ~atomic() noexcept = default;
631             atomic(const atomic&) = delete;
632             atomic& operator=(const atomic&) = delete;
633             atomic& operator=(const atomic&) volatile = delete;
634              
635 220           constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
636              
637             using __base_type::operator __integral_type;
638             using __base_type::operator=;
639             };
640              
641             /// Explicit specialization for long.
642             template<>
643             struct atomic : __atomic_base
644             {
645             typedef long __integral_type;
646             typedef __atomic_base __base_type;
647              
648             atomic() noexcept = default;
649             ~atomic() noexcept = default;
650             atomic(const atomic&) = delete;
651             atomic& operator=(const atomic&) = delete;
652             atomic& operator=(const atomic&) volatile = delete;
653              
654             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
655              
656             using __base_type::operator __integral_type;
657             using __base_type::operator=;
658             };
659              
660             /// Explicit specialization for unsigned long.
661             template<>
662             struct atomic : __atomic_base
663             {
664             typedef unsigned long __integral_type;
665             typedef __atomic_base __base_type;
666              
667             atomic() noexcept = default;
668             ~atomic() noexcept = default;
669             atomic(const atomic&) = delete;
670             atomic& operator=(const atomic&) = delete;
671             atomic& operator=(const atomic&) volatile = delete;
672              
673             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
674              
675             using __base_type::operator __integral_type;
676             using __base_type::operator=;
677             };
678              
679             /// Explicit specialization for long long.
680             template<>
681             struct atomic : __atomic_base
682             {
683             typedef long long __integral_type;
684             typedef __atomic_base __base_type;
685              
686             atomic() noexcept = default;
687             ~atomic() noexcept = default;
688             atomic(const atomic&) = delete;
689             atomic& operator=(const atomic&) = delete;
690             atomic& operator=(const atomic&) volatile = delete;
691              
692             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
693              
694             using __base_type::operator __integral_type;
695             using __base_type::operator=;
696             };
697              
698             /// Explicit specialization for unsigned long long.
699             template<>
700             struct atomic : __atomic_base
701             {
702             typedef unsigned long long __integral_type;
703             typedef __atomic_base __base_type;
704              
705             atomic() noexcept = default;
706             ~atomic() noexcept = default;
707             atomic(const atomic&) = delete;
708             atomic& operator=(const atomic&) = delete;
709             atomic& operator=(const atomic&) volatile = delete;
710              
711             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
712              
713             using __base_type::operator __integral_type;
714             using __base_type::operator=;
715             };
716              
717             /// Explicit specialization for wchar_t.
718             template<>
719             struct atomic : __atomic_base
720             {
721             typedef wchar_t __integral_type;
722             typedef __atomic_base __base_type;
723              
724             atomic() noexcept = default;
725             ~atomic() noexcept = default;
726             atomic(const atomic&) = delete;
727             atomic& operator=(const atomic&) = delete;
728             atomic& operator=(const atomic&) volatile = delete;
729              
730             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
731              
732             using __base_type::operator __integral_type;
733             using __base_type::operator=;
734             };
735              
736             /// Explicit specialization for char16_t.
737             template<>
738             struct atomic : __atomic_base
739             {
740             typedef char16_t __integral_type;
741             typedef __atomic_base __base_type;
742              
743             atomic() noexcept = default;
744             ~atomic() noexcept = default;
745             atomic(const atomic&) = delete;
746             atomic& operator=(const atomic&) = delete;
747             atomic& operator=(const atomic&) volatile = delete;
748              
749             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
750              
751             using __base_type::operator __integral_type;
752             using __base_type::operator=;
753             };
754              
755             /// Explicit specialization for char32_t.
756             template<>
757             struct atomic : __atomic_base
758             {
759             typedef char32_t __integral_type;
760             typedef __atomic_base __base_type;
761              
762             atomic() noexcept = default;
763             ~atomic() noexcept = default;
764             atomic(const atomic&) = delete;
765             atomic& operator=(const atomic&) = delete;
766             atomic& operator=(const atomic&) volatile = delete;
767              
768             constexpr atomic(__integral_type __i) noexcept : __base_type(__i) { }
769              
770             using __base_type::operator __integral_type;
771             using __base_type::operator=;
772             };
773              
774              
775             /// atomic_bool
776             typedef atomic atomic_bool;
777              
778             /// atomic_char
779             typedef atomic atomic_char;
780              
781             /// atomic_schar
782             typedef atomic atomic_schar;
783              
784             /// atomic_uchar
785             typedef atomic atomic_uchar;
786              
787             /// atomic_short
788             typedef atomic atomic_short;
789              
790             /// atomic_ushort
791             typedef atomic atomic_ushort;
792              
793             /// atomic_int
794             typedef atomic atomic_int;
795              
796             /// atomic_uint
797             typedef atomic atomic_uint;
798              
799             /// atomic_long
800             typedef atomic atomic_long;
801              
802             /// atomic_ulong
803             typedef atomic atomic_ulong;
804              
805             /// atomic_llong
806             typedef atomic atomic_llong;
807              
808             /// atomic_ullong
809             typedef atomic atomic_ullong;
810              
811             /// atomic_wchar_t
812             typedef atomic atomic_wchar_t;
813              
814             /// atomic_char16_t
815             typedef atomic atomic_char16_t;
816              
817             /// atomic_char32_t
818             typedef atomic atomic_char32_t;
819              
820              
821             /// atomic_int_least8_t
822             typedef atomic atomic_int_least8_t;
823              
824             /// atomic_uint_least8_t
825             typedef atomic atomic_uint_least8_t;
826              
827             /// atomic_int_least16_t
828             typedef atomic atomic_int_least16_t;
829              
830             /// atomic_uint_least16_t
831             typedef atomic atomic_uint_least16_t;
832              
833             /// atomic_int_least32_t
834             typedef atomic atomic_int_least32_t;
835              
836             /// atomic_uint_least32_t
837             typedef atomic atomic_uint_least32_t;
838              
839             /// atomic_int_least64_t
840             typedef atomic atomic_int_least64_t;
841              
842             /// atomic_uint_least64_t
843             typedef atomic atomic_uint_least64_t;
844              
845              
846             /// atomic_int_fast8_t
847             typedef atomic atomic_int_fast8_t;
848              
849             /// atomic_uint_fast8_t
850             typedef atomic atomic_uint_fast8_t;
851              
852             /// atomic_int_fast16_t
853             typedef atomic atomic_int_fast16_t;
854              
855             /// atomic_uint_fast16_t
856             typedef atomic atomic_uint_fast16_t;
857              
858             /// atomic_int_fast32_t
859             typedef atomic atomic_int_fast32_t;
860              
861             /// atomic_uint_fast32_t
862             typedef atomic atomic_uint_fast32_t;
863              
864             /// atomic_int_fast64_t
865             typedef atomic atomic_int_fast64_t;
866              
867             /// atomic_uint_fast64_t
868             typedef atomic atomic_uint_fast64_t;
869              
870              
871             /// atomic_intptr_t
872             typedef atomic atomic_intptr_t;
873              
874             /// atomic_uintptr_t
875             typedef atomic atomic_uintptr_t;
876              
877             /// atomic_size_t
878             typedef atomic atomic_size_t;
879              
880             /// atomic_intmax_t
881             typedef atomic atomic_intmax_t;
882              
883             /// atomic_uintmax_t
884             typedef atomic atomic_uintmax_t;
885              
886             /// atomic_ptrdiff_t
887             typedef atomic atomic_ptrdiff_t;
888              
889              
890             // Function definitions, atomic_flag operations.
891             inline bool
892             atomic_flag_test_and_set_explicit(atomic_flag* __a,
893             memory_order __m) noexcept
894             { return __a->test_and_set(__m); }
895              
896             inline bool
897             atomic_flag_test_and_set_explicit(volatile atomic_flag* __a,
898             memory_order __m) noexcept
899             { return __a->test_and_set(__m); }
900              
901             inline void
902             atomic_flag_clear_explicit(atomic_flag* __a, memory_order __m) noexcept
903             { __a->clear(__m); }
904              
905             inline void
906             atomic_flag_clear_explicit(volatile atomic_flag* __a,
907             memory_order __m) noexcept
908             { __a->clear(__m); }
909              
910             inline bool
911             atomic_flag_test_and_set(atomic_flag* __a) noexcept
912             { return atomic_flag_test_and_set_explicit(__a, memory_order_seq_cst); }
913              
914             inline bool
915             atomic_flag_test_and_set(volatile atomic_flag* __a) noexcept
916             { return atomic_flag_test_and_set_explicit(__a, memory_order_seq_cst); }
917              
918             inline void
919             atomic_flag_clear(atomic_flag* __a) noexcept
920             { atomic_flag_clear_explicit(__a, memory_order_seq_cst); }
921              
922             inline void
923             atomic_flag_clear(volatile atomic_flag* __a) noexcept
924             { atomic_flag_clear_explicit(__a, memory_order_seq_cst); }
925              
926              
927             // Function templates generally applicable to atomic types.
928             template
929             inline bool
930             atomic_is_lock_free(const atomic<_ITp>* __a) noexcept
931             { return __a->is_lock_free(); }
932              
933             template
934             inline bool
935             atomic_is_lock_free(const volatile atomic<_ITp>* __a) noexcept
936             { return __a->is_lock_free(); }
937              
938             template
939             inline void
940             atomic_init(atomic<_ITp>* __a, _ITp __i) noexcept
941             { __a->store(__i, memory_order_relaxed); }
942              
943             template
944             inline void
945             atomic_init(volatile atomic<_ITp>* __a, _ITp __i) noexcept
946             { __a->store(__i, memory_order_relaxed); }
947              
948             template
949             inline void
950             atomic_store_explicit(atomic<_ITp>* __a, _ITp __i,
951             memory_order __m) noexcept
952             { __a->store(__i, __m); }
953              
954             template
955             inline void
956             atomic_store_explicit(volatile atomic<_ITp>* __a, _ITp __i,
957             memory_order __m) noexcept
958             { __a->store(__i, __m); }
959              
960             template
961             inline _ITp
962             atomic_load_explicit(const atomic<_ITp>* __a, memory_order __m) noexcept
963             { return __a->load(__m); }
964              
965             template
966             inline _ITp
967             atomic_load_explicit(const volatile atomic<_ITp>* __a,
968             memory_order __m) noexcept
969             { return __a->load(__m); }
970              
971             template
972             inline _ITp
973             atomic_exchange_explicit(atomic<_ITp>* __a, _ITp __i,
974             memory_order __m) noexcept
975             { return __a->exchange(__i, __m); }
976              
977             template
978             inline _ITp
979             atomic_exchange_explicit(volatile atomic<_ITp>* __a, _ITp __i,
980             memory_order __m) noexcept
981             { return __a->exchange(__i, __m); }
982              
983             template
984             inline bool
985             atomic_compare_exchange_weak_explicit(atomic<_ITp>* __a,
986             _ITp* __i1, _ITp __i2,
987             memory_order __m1,
988             memory_order __m2) noexcept
989             { return __a->compare_exchange_weak(*__i1, __i2, __m1, __m2); }
990              
991             template
992             inline bool
993             atomic_compare_exchange_weak_explicit(volatile atomic<_ITp>* __a,
994             _ITp* __i1, _ITp __i2,
995             memory_order __m1,
996             memory_order __m2) noexcept
997             { return __a->compare_exchange_weak(*__i1, __i2, __m1, __m2); }
998              
999             template
1000             inline bool
1001             atomic_compare_exchange_strong_explicit(atomic<_ITp>* __a,
1002             _ITp* __i1, _ITp __i2,
1003             memory_order __m1,
1004             memory_order __m2) noexcept
1005             { return __a->compare_exchange_strong(*__i1, __i2, __m1, __m2); }
1006              
1007             template
1008             inline bool
1009             atomic_compare_exchange_strong_explicit(volatile atomic<_ITp>* __a,
1010             _ITp* __i1, _ITp __i2,
1011             memory_order __m1,
1012             memory_order __m2) noexcept
1013             { return __a->compare_exchange_strong(*__i1, __i2, __m1, __m2); }
1014              
1015              
1016             template
1017             inline void
1018             atomic_store(atomic<_ITp>* __a, _ITp __i) noexcept
1019             { atomic_store_explicit(__a, __i, memory_order_seq_cst); }
1020              
1021             template
1022             inline void
1023             atomic_store(volatile atomic<_ITp>* __a, _ITp __i) noexcept
1024             { atomic_store_explicit(__a, __i, memory_order_seq_cst); }
1025              
1026             template
1027             inline _ITp
1028             atomic_load(const atomic<_ITp>* __a) noexcept
1029             { return atomic_load_explicit(__a, memory_order_seq_cst); }
1030              
1031             template
1032             inline _ITp
1033             atomic_load(const volatile atomic<_ITp>* __a) noexcept
1034             { return atomic_load_explicit(__a, memory_order_seq_cst); }
1035              
1036             template
1037             inline _ITp
1038             atomic_exchange(atomic<_ITp>* __a, _ITp __i) noexcept
1039             { return atomic_exchange_explicit(__a, __i, memory_order_seq_cst); }
1040              
1041             template
1042             inline _ITp
1043             atomic_exchange(volatile atomic<_ITp>* __a, _ITp __i) noexcept
1044             { return atomic_exchange_explicit(__a, __i, memory_order_seq_cst); }
1045              
1046             template
1047             inline bool
1048             atomic_compare_exchange_weak(atomic<_ITp>* __a,
1049             _ITp* __i1, _ITp __i2) noexcept
1050             {
1051             return atomic_compare_exchange_weak_explicit(__a, __i1, __i2,
1052             memory_order_seq_cst,
1053             memory_order_seq_cst);
1054             }
1055              
1056             template
1057             inline bool
1058             atomic_compare_exchange_weak(volatile atomic<_ITp>* __a,
1059             _ITp* __i1, _ITp __i2) noexcept
1060             {
1061             return atomic_compare_exchange_weak_explicit(__a, __i1, __i2,
1062             memory_order_seq_cst,
1063             memory_order_seq_cst);
1064             }
1065              
1066             template
1067             inline bool
1068             atomic_compare_exchange_strong(atomic<_ITp>* __a,
1069             _ITp* __i1, _ITp __i2) noexcept
1070             {
1071             return atomic_compare_exchange_strong_explicit(__a, __i1, __i2,
1072             memory_order_seq_cst,
1073             memory_order_seq_cst);
1074             }
1075              
1076             template
1077             inline bool
1078             atomic_compare_exchange_strong(volatile atomic<_ITp>* __a,
1079             _ITp* __i1, _ITp __i2) noexcept
1080             {
1081             return atomic_compare_exchange_strong_explicit(__a, __i1, __i2,
1082             memory_order_seq_cst,
1083             memory_order_seq_cst);
1084             }
1085              
1086             // Function templates for atomic_integral operations only, using
1087             // __atomic_base. Template argument should be constricted to
1088             // intergral types as specified in the standard, excluding address
1089             // types.
1090             template
1091             inline _ITp
1092             atomic_fetch_add_explicit(__atomic_base<_ITp>* __a, _ITp __i,
1093             memory_order __m) noexcept
1094             { return __a->fetch_add(__i, __m); }
1095              
1096             template
1097             inline _ITp
1098             atomic_fetch_add_explicit(volatile __atomic_base<_ITp>* __a, _ITp __i,
1099             memory_order __m) noexcept
1100             { return __a->fetch_add(__i, __m); }
1101              
1102             template
1103             inline _ITp
1104             atomic_fetch_sub_explicit(__atomic_base<_ITp>* __a, _ITp __i,
1105             memory_order __m) noexcept
1106             { return __a->fetch_sub(__i, __m); }
1107              
1108             template
1109             inline _ITp
1110             atomic_fetch_sub_explicit(volatile __atomic_base<_ITp>* __a, _ITp __i,
1111             memory_order __m) noexcept
1112             { return __a->fetch_sub(__i, __m); }
1113              
1114             template
1115             inline _ITp
1116             atomic_fetch_and_explicit(__atomic_base<_ITp>* __a, _ITp __i,
1117             memory_order __m) noexcept
1118             { return __a->fetch_and(__i, __m); }
1119              
1120             template
1121             inline _ITp
1122             atomic_fetch_and_explicit(volatile __atomic_base<_ITp>* __a, _ITp __i,
1123             memory_order __m) noexcept
1124             { return __a->fetch_and(__i, __m); }
1125              
1126             template
1127             inline _ITp
1128             atomic_fetch_or_explicit(__atomic_base<_ITp>* __a, _ITp __i,
1129             memory_order __m) noexcept
1130             { return __a->fetch_or(__i, __m); }
1131              
1132             template
1133             inline _ITp
1134             atomic_fetch_or_explicit(volatile __atomic_base<_ITp>* __a, _ITp __i,
1135             memory_order __m) noexcept
1136             { return __a->fetch_or(__i, __m); }
1137              
1138             template
1139             inline _ITp
1140             atomic_fetch_xor_explicit(__atomic_base<_ITp>* __a, _ITp __i,
1141             memory_order __m) noexcept
1142             { return __a->fetch_xor(__i, __m); }
1143              
1144             template
1145             inline _ITp
1146             atomic_fetch_xor_explicit(volatile __atomic_base<_ITp>* __a, _ITp __i,
1147             memory_order __m) noexcept
1148             { return __a->fetch_xor(__i, __m); }
1149              
1150             template
1151             inline _ITp
1152             atomic_fetch_add(__atomic_base<_ITp>* __a, _ITp __i) noexcept
1153             { return atomic_fetch_add_explicit(__a, __i, memory_order_seq_cst); }
1154              
1155             template
1156             inline _ITp
1157             atomic_fetch_add(volatile __atomic_base<_ITp>* __a, _ITp __i) noexcept
1158             { return atomic_fetch_add_explicit(__a, __i, memory_order_seq_cst); }
1159              
1160             template
1161             inline _ITp
1162             atomic_fetch_sub(__atomic_base<_ITp>* __a, _ITp __i) noexcept
1163             { return atomic_fetch_sub_explicit(__a, __i, memory_order_seq_cst); }
1164              
1165             template
1166             inline _ITp
1167             atomic_fetch_sub(volatile __atomic_base<_ITp>* __a, _ITp __i) noexcept
1168             { return atomic_fetch_sub_explicit(__a, __i, memory_order_seq_cst); }
1169              
1170             template
1171             inline _ITp
1172             atomic_fetch_and(__atomic_base<_ITp>* __a, _ITp __i) noexcept
1173             { return atomic_fetch_and_explicit(__a, __i, memory_order_seq_cst); }
1174              
1175             template
1176             inline _ITp
1177             atomic_fetch_and(volatile __atomic_base<_ITp>* __a, _ITp __i) noexcept
1178             { return atomic_fetch_and_explicit(__a, __i, memory_order_seq_cst); }
1179              
1180             template
1181             inline _ITp
1182             atomic_fetch_or(__atomic_base<_ITp>* __a, _ITp __i) noexcept
1183             { return atomic_fetch_or_explicit(__a, __i, memory_order_seq_cst); }
1184              
1185             template
1186             inline _ITp
1187             atomic_fetch_or(volatile __atomic_base<_ITp>* __a, _ITp __i) noexcept
1188             { return atomic_fetch_or_explicit(__a, __i, memory_order_seq_cst); }
1189              
1190             template
1191             inline _ITp
1192             atomic_fetch_xor(__atomic_base<_ITp>* __a, _ITp __i) noexcept
1193             { return atomic_fetch_xor_explicit(__a, __i, memory_order_seq_cst); }
1194              
1195             template
1196             inline _ITp
1197             atomic_fetch_xor(volatile __atomic_base<_ITp>* __a, _ITp __i) noexcept
1198             { return atomic_fetch_xor_explicit(__a, __i, memory_order_seq_cst); }
1199              
1200              
1201             // Partial specializations for pointers.
1202             template
1203             inline _ITp*
1204             atomic_fetch_add_explicit(atomic<_ITp*>* __a, ptrdiff_t __d,
1205             memory_order __m) noexcept
1206             { return __a->fetch_add(__d, __m); }
1207              
1208             template
1209             inline _ITp*
1210             atomic_fetch_add_explicit(volatile atomic<_ITp*>* __a, ptrdiff_t __d,
1211             memory_order __m) noexcept
1212             { return __a->fetch_add(__d, __m); }
1213              
1214             template
1215             inline _ITp*
1216             atomic_fetch_add(volatile atomic<_ITp*>* __a, ptrdiff_t __d) noexcept
1217             { return __a->fetch_add(__d); }
1218              
1219             template
1220             inline _ITp*
1221             atomic_fetch_add(atomic<_ITp*>* __a, ptrdiff_t __d) noexcept
1222             { return __a->fetch_add(__d); }
1223              
1224             template
1225             inline _ITp*
1226             atomic_fetch_sub_explicit(volatile atomic<_ITp*>* __a,
1227             ptrdiff_t __d, memory_order __m) noexcept
1228             { return __a->fetch_sub(__d, __m); }
1229              
1230             template
1231             inline _ITp*
1232             atomic_fetch_sub_explicit(atomic<_ITp*>* __a, ptrdiff_t __d,
1233             memory_order __m) noexcept
1234             { return __a->fetch_sub(__d, __m); }
1235              
1236             template
1237             inline _ITp*
1238             atomic_fetch_sub(volatile atomic<_ITp*>* __a, ptrdiff_t __d) noexcept
1239             { return __a->fetch_sub(__d); }
1240              
1241             template
1242             inline _ITp*
1243             atomic_fetch_sub(atomic<_ITp*>* __a, ptrdiff_t __d) noexcept
1244             { return __a->fetch_sub(__d); }
1245             // @} group atomics
1246              
1247             _GLIBCXX_END_NAMESPACE_VERSION
1248             } // namespace
1249              
1250             #endif // C++11
1251              
1252             #endif // _GLIBCXX_ATOMIC