🛠️🐜 Antkeeper superbuild with dependencies included https://antkeeper.com
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

33 lines
1.1 KiB

  1. #ifndef AL_ATOMIC_H
  2. #define AL_ATOMIC_H
  3. #include <atomic>
  4. using RefCount = std::atomic<unsigned int>;
  5. inline void InitRef(RefCount *ptr, unsigned int value)
  6. { ptr->store(value, std::memory_order_relaxed); }
  7. inline unsigned int ReadRef(RefCount *ptr)
  8. { return ptr->load(std::memory_order_acquire); }
  9. inline unsigned int IncrementRef(RefCount *ptr)
  10. { return ptr->fetch_add(1u, std::memory_order_acq_rel)+1u; }
  11. inline unsigned int DecrementRef(RefCount *ptr)
  12. { return ptr->fetch_sub(1u, std::memory_order_acq_rel)-1u; }
  13. /* WARNING: A livelock is theoretically possible if another thread keeps
  14. * changing the head without giving this a chance to actually swap in the new
  15. * one (practically impossible with this little code, but...).
  16. */
  17. template<typename T>
  18. inline void AtomicReplaceHead(std::atomic<T> &head, T newhead)
  19. {
  20. T first_ = head.load(std::memory_order_acquire);
  21. do {
  22. newhead->next.store(first_, std::memory_order_relaxed);
  23. } while(!head.compare_exchange_weak(first_, newhead,
  24. std::memory_order_acq_rel, std::memory_order_acquire));
  25. }
  26. #endif /* AL_ATOMIC_H */