RAJA
RAJA provides a collection of platform portability abstractions for C++ HPC applications.
atomic.hpp
Go to the documentation of this file.
1 
11 //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~//
12 // Copyright (c) Lawrence Livermore National Security, LLC and other
13 // RAJA Project Developers. See top-level LICENSE and COPYRIGHT
14 // files for dates and other details. No copyright assignment is required
15 // to contribute to RAJA.
16 //
17 // SPDX-License-Identifier: (BSD-3-Clause)
18 //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~//
19 
20 #ifndef RAJA_pattern_atomic_HPP
21 #define RAJA_pattern_atomic_HPP
22 
23 #include "RAJA/config.hpp"
24 
27 
28 #include "RAJA/util/macros.hpp"
29 
30 namespace RAJA
31 {
32 
33 
91 template<typename Policy, typename T>
92 RAJA_INLINE RAJA_HOST_DEVICE T atomicLoad(T* acc)
93 {
94  return RAJA::atomicLoad(Policy {}, acc);
95 }
96 
103 template<typename Policy, typename T>
104 RAJA_INLINE RAJA_HOST_DEVICE void atomicStore(T* acc, T value)
105 {
106  RAJA::atomicStore(Policy {}, acc, value);
107 }
108 
116 template<typename Policy, typename T>
117 RAJA_INLINE RAJA_HOST_DEVICE T atomicAdd(T* acc, T value)
118 {
119  return RAJA::atomicAdd(Policy {}, acc, value);
120 }
121 
129 template<typename Policy, typename T>
130 RAJA_INLINE RAJA_HOST_DEVICE T atomicSub(T* acc, T value)
131 {
132  return RAJA::atomicSub(Policy {}, acc, value);
133 }
134 
142 template<typename Policy, typename T>
143 RAJA_INLINE RAJA_HOST_DEVICE T atomicMin(T* acc, T value)
144 {
145  return RAJA::atomicMin(Policy {}, acc, value);
146 }
147 
155 template<typename Policy, typename T>
156 RAJA_INLINE RAJA_HOST_DEVICE T atomicMax(T* acc, T value)
157 {
158  return RAJA::atomicMax(Policy {}, acc, value);
159 }
160 
167 template<typename Policy, typename T>
168 RAJA_INLINE RAJA_HOST_DEVICE T atomicInc(T* acc)
169 {
170  return RAJA::atomicInc(Policy {}, acc);
171 }
172 
182 template<typename Policy, typename T>
183 RAJA_INLINE RAJA_HOST_DEVICE T atomicInc(T* acc, T compare)
184 {
185  return RAJA::atomicInc(Policy {}, acc, compare);
186 }
187 
194 template<typename Policy, typename T>
195 RAJA_INLINE RAJA_HOST_DEVICE T atomicDec(T* acc)
196 {
197  return RAJA::atomicDec(Policy {}, acc);
198 }
199 
209 template<typename Policy, typename T>
210 RAJA_INLINE RAJA_HOST_DEVICE T atomicDec(T* acc, T compare)
211 {
212  return RAJA::atomicDec(Policy {}, acc, compare);
213 }
214 
223 template<typename Policy, typename T>
224 RAJA_INLINE RAJA_HOST_DEVICE T atomicAnd(T* acc, T value)
225 {
226  static_assert(std::is_integral<T>::value,
227  "atomicAnd can only be used on integral types");
228  return RAJA::atomicAnd(Policy {}, acc, value);
229 }
230 
239 template<typename Policy, typename T>
240 RAJA_INLINE RAJA_HOST_DEVICE T atomicOr(T* acc, T value)
241 {
242  static_assert(std::is_integral<T>::value,
243  "atomicOr can only be used on integral types");
244  return RAJA::atomicOr(Policy {}, acc, value);
245 }
246 
255 template<typename Policy, typename T>
256 RAJA_INLINE RAJA_HOST_DEVICE T atomicXor(T* acc, T value)
257 {
258  static_assert(std::is_integral<T>::value,
259  "atomicXor can only be used on integral types");
260  return RAJA::atomicXor(Policy {}, acc, value);
261 }
262 
270 template<typename Policy, typename T>
271 RAJA_INLINE RAJA_HOST_DEVICE T atomicExchange(T* acc, T value)
272 {
273  return RAJA::atomicExchange(Policy {}, acc, value);
274 }
275 
285 template<typename Policy, typename T>
286 RAJA_INLINE RAJA_HOST_DEVICE T atomicCAS(T* acc, T compare, T value)
287 {
288  return RAJA::atomicCAS(Policy {}, acc, compare, value);
289 }
290 
300 template<typename T, typename Policy = auto_atomic>
302 {
303 public:
304  using value_type = T;
305 
306  RAJA_INLINE
307 
309  constexpr explicit AtomicRef(value_type* value_ptr) : m_value_ptr(value_ptr)
310  {}
311 
312  RAJA_INLINE
313 
315  constexpr AtomicRef(AtomicRef const& c) : m_value_ptr(c.m_value_ptr) {}
316 
317  AtomicRef& operator=(AtomicRef const&) = delete;
318 
319  RAJA_INLINE
320 
322  value_type* getPointer() const { return m_value_ptr; }
323 
324  RAJA_INLINE
325 
327  void store(value_type rhs) const
328  {
329  RAJA::atomicStore<Policy>(m_value_ptr, rhs);
330  }
331 
332  RAJA_INLINE
333 
336  {
337  RAJA::atomicStore<Policy>(m_value_ptr, rhs);
338  return rhs;
339  }
340 
341  RAJA_INLINE
342 
344  value_type load() const { return RAJA::atomicLoad<Policy>(m_value_ptr); }
345 
346  RAJA_INLINE
347 
349  operator value_type() const { return RAJA::atomicLoad<Policy>(m_value_ptr); }
350 
351  RAJA_INLINE
352 
355  {
356  return RAJA::atomicExchange<Policy>(m_value_ptr, rhs);
357  }
358 
359  RAJA_INLINE
360 
362  value_type CAS(value_type compare, value_type rhs) const
363  {
364  return RAJA::atomicCAS<Policy>(m_value_ptr, compare, rhs);
365  }
366 
367  RAJA_INLINE
368 
371  {
372  value_type compare = expect;
373  value_type old = RAJA::atomicCAS<Policy>(m_value_ptr, compare, rhs);
374  if (compare == old)
375  {
376  return true;
377  }
378  else
379  {
380  expect = old;
381  return false;
382  }
383  }
384 
385  RAJA_INLINE
386 
388  bool compare_exchange_weak(value_type& expect, value_type rhs) const
389  {
390  return this->compare_exchange_strong(expect, rhs);
391  }
392 
393  RAJA_INLINE
394 
397  {
398  return RAJA::atomicInc<Policy>(m_value_ptr) + 1;
399  }
400 
401  RAJA_INLINE
402 
405  {
406  return RAJA::atomicInc<Policy>(m_value_ptr);
407  }
408 
409  RAJA_INLINE
410 
413  {
414  return RAJA::atomicDec<Policy>(m_value_ptr) - 1;
415  }
416 
417  RAJA_INLINE
418 
421  {
422  return RAJA::atomicDec<Policy>(m_value_ptr);
423  }
424 
425  RAJA_INLINE
426 
429  {
430  return RAJA::atomicAdd<Policy>(m_value_ptr, rhs);
431  }
432 
433  RAJA_INLINE
434 
437  {
438  return RAJA::atomicAdd<Policy>(m_value_ptr, rhs) + rhs;
439  }
440 
441  RAJA_INLINE
442 
445  {
446  return RAJA::atomicSub<Policy>(m_value_ptr, rhs);
447  }
448 
449  RAJA_INLINE
450 
453  {
454  return RAJA::atomicSub<Policy>(m_value_ptr, rhs) - rhs;
455  }
456 
457  RAJA_INLINE
458 
461  {
462  return RAJA::atomicMin<Policy>(m_value_ptr, rhs);
463  }
464 
465  RAJA_INLINE
466 
469  {
470  value_type old = RAJA::atomicMin<Policy>(m_value_ptr, rhs);
471  return old < rhs ? old : rhs;
472  }
473 
474  RAJA_INLINE
475 
478  {
479  return RAJA::atomicMax<Policy>(m_value_ptr, rhs);
480  }
481 
482  RAJA_INLINE
483 
486  {
487  value_type old = RAJA::atomicMax<Policy>(m_value_ptr, rhs);
488  return old > rhs ? old : rhs;
489  }
490 
491  RAJA_INLINE
492 
495  {
496  return RAJA::atomicAnd<Policy>(m_value_ptr, rhs);
497  }
498 
499  RAJA_INLINE
500 
503  {
504  return RAJA::atomicAnd<Policy>(m_value_ptr, rhs) & rhs;
505  }
506 
507  RAJA_INLINE
508 
511  {
512  return RAJA::atomicOr<Policy>(m_value_ptr, rhs);
513  }
514 
515  RAJA_INLINE
516 
519  {
520  return RAJA::atomicOr<Policy>(m_value_ptr, rhs) | rhs;
521  }
522 
523  RAJA_INLINE
524 
527  {
528  return RAJA::atomicXor<Policy>(m_value_ptr, rhs);
529  }
530 
531  RAJA_INLINE
532 
535  {
536  return RAJA::atomicXor<Policy>(m_value_ptr, rhs) ^ rhs;
537  }
538 
539 private:
540  value_type* m_value_ptr;
541 };
542 
543 
544 } // namespace RAJA
545 
546 #endif
RAJA header file defining automatic and builtin atomic operations.
RAJA header file defining automatic and builtin atomic operations.
Atomic wrapper object.
Definition: atomic.hpp:302
RAJA_INLINE constexpr RAJA_HOST_DEVICE AtomicRef(AtomicRef const &c)
Definition: atomic.hpp:315
RAJA_INLINE RAJA_HOST_DEVICE value_type operator++() const
Definition: atomic.hpp:396
RAJA_INLINE RAJA_HOST_DEVICE void store(value_type rhs) const
Definition: atomic.hpp:327
RAJA_INLINE RAJA_HOST_DEVICE value_type max(value_type rhs) const
Definition: atomic.hpp:485
RAJA_INLINE RAJA_HOST_DEVICE bool compare_exchange_strong(value_type &expect, value_type rhs) const
Definition: atomic.hpp:370
RAJA_INLINE RAJA_HOST_DEVICE value_type operator-=(value_type rhs) const
Definition: atomic.hpp:452
RAJA_INLINE RAJA_HOST_DEVICE value_type fetch_max(value_type rhs) const
Definition: atomic.hpp:477
RAJA_INLINE RAJA_HOST_DEVICE value_type CAS(value_type compare, value_type rhs) const
Definition: atomic.hpp:362
RAJA_INLINE RAJA_HOST_DEVICE value_type fetch_xor(value_type rhs) const
Definition: atomic.hpp:526
RAJA_INLINE RAJA_HOST_DEVICE value_type operator^=(value_type rhs) const
Definition: atomic.hpp:534
RAJA_INLINE RAJA_HOST_DEVICE value_type fetch_add(value_type rhs) const
Definition: atomic.hpp:428
RAJA_INLINE RAJA_HOST_DEVICE value_type operator=(value_type rhs) const
Definition: atomic.hpp:335
RAJA_INLINE RAJA_HOST_DEVICE value_type * getPointer() const
Definition: atomic.hpp:322
RAJA_INLINE RAJA_HOST_DEVICE value_type operator+=(value_type rhs) const
Definition: atomic.hpp:436
RAJA_INLINE RAJA_HOST_DEVICE value_type operator++(int) const
Definition: atomic.hpp:404
RAJA_INLINE RAJA_HOST_DEVICE value_type fetch_sub(value_type rhs) const
Definition: atomic.hpp:444
RAJA_INLINE RAJA_HOST_DEVICE value_type operator--() const
Definition: atomic.hpp:412
RAJA_INLINE RAJA_HOST_DEVICE value_type min(value_type rhs) const
Definition: atomic.hpp:468
RAJA_INLINE RAJA_HOST_DEVICE value_type operator&=(value_type rhs) const
Definition: atomic.hpp:502
T value_type
Definition: atomic.hpp:304
RAJA_INLINE RAJA_HOST_DEVICE value_type fetch_min(value_type rhs) const
Definition: atomic.hpp:460
RAJA_INLINE RAJA_HOST_DEVICE value_type exchange(value_type rhs) const
Definition: atomic.hpp:354
RAJA_INLINE RAJA_HOST_DEVICE value_type load() const
Definition: atomic.hpp:344
RAJA_INLINE RAJA_HOST_DEVICE value_type fetch_or(value_type rhs) const
Definition: atomic.hpp:510
RAJA_INLINE RAJA_HOST_DEVICE bool compare_exchange_weak(value_type &expect, value_type rhs) const
Definition: atomic.hpp:388
RAJA_INLINE RAJA_HOST_DEVICE value_type fetch_and(value_type rhs) const
Definition: atomic.hpp:494
RAJA_INLINE RAJA_HOST_DEVICE value_type operator--(int) const
Definition: atomic.hpp:420
AtomicRef & operator=(AtomicRef const &)=delete
RAJA_INLINE RAJA_HOST_DEVICE value_type operator|=(value_type rhs) const
Definition: atomic.hpp:518
RAJA_INLINE constexpr RAJA_HOST_DEVICE AtomicRef(value_type *value_ptr)
Definition: atomic.hpp:309
Header file for common RAJA internal macro definitions.
#define RAJA_HOST_DEVICE
Definition: macros.hpp:65
#define RAJA_SUPPRESS_HD_WARN
Definition: macros.hpp:68
Definition: AlignedRangeIndexSetBuilders.cpp:35
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE T atomicAnd(T *acc, T value)
Atomic bitwise AND equivalent to (*acc) = (*acc) & value This only works with integral data types.
Definition: atomic.hpp:224
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE T atomicOr(T *acc, T value)
Atomic bitwise OR equivalent to (*acc) = (*acc) | value This only works with integral data types.
Definition: atomic.hpp:240
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE T atomicLoad(T *acc)
Atomic load.
Definition: atomic.hpp:92
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE T atomicDec(T *acc)
Atomic decrement.
Definition: atomic.hpp:195
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE T atomicAdd(T *acc, T value)
Atomic add.
Definition: atomic.hpp:117
Policy
Definition: PolicyBase.hpp:32
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE T atomicXor(T *acc, T value)
Atomic bitwise XOR equivalent to (*acc) = (*acc) ^ value This only works with integral data types.
Definition: atomic.hpp:256
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE void atomicStore(T *acc, T value)
Atomic store.
Definition: atomic.hpp:104
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE T atomicMax(T *acc, T value)
Atomic maximum equivalent to (*acc) = std::max(*acc, value)
Definition: atomic.hpp:156
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE T atomicCAS(T *acc, T compare, T value)
Atomic compare and swap.
Definition: atomic.hpp:286
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE T atomicInc(T *acc)
Atomic increment.
Definition: atomic.hpp:168
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE T atomicMin(T *acc, T value)
Atomic minimum equivalent to (*acc) = std::min(*acc, value)
Definition: atomic.hpp:143
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE T atomicSub(T *acc, T value)
Atomic subtract.
Definition: atomic.hpp:130
RAJA_SUPPRESS_HD_WARN RAJA_INLINE RAJA_HOST_DEVICE T atomicExchange(T *acc, T value)
Atomic value exchange.
Definition: atomic.hpp:271