This commit is contained in:
parent
b316e3b3b7
commit
a16f357ab9
108
luna/include/luna/Atomic.h
Normal file
108
luna/include/luna/Atomic.h
Normal file
@ -0,0 +1,108 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
enum class MemoryOrder
|
||||||
|
{
|
||||||
|
Relaxed = __ATOMIC_RELAXED,
|
||||||
|
Consume = __ATOMIC_CONSUME,
|
||||||
|
Acquire = __ATOMIC_ACQUIRE,
|
||||||
|
Release = __ATOMIC_RELEASE,
|
||||||
|
AcqRel = __ATOMIC_ACQ_REL,
|
||||||
|
SeqCst = __ATOMIC_SEQ_CST,
|
||||||
|
};
|
||||||
|
|
||||||
|
template <typename T> class Atomic
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
Atomic() : m_value()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
Atomic(T value) : m_value(value)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
T operator=(T other)
|
||||||
|
{
|
||||||
|
store(other);
|
||||||
|
return other;
|
||||||
|
}
|
||||||
|
|
||||||
|
T load(MemoryOrder order = MemoryOrder::SeqCst) const
|
||||||
|
{
|
||||||
|
return __atomic_load_n(&m_value, (int)order);
|
||||||
|
}
|
||||||
|
|
||||||
|
operator T() const
|
||||||
|
{
|
||||||
|
return load();
|
||||||
|
}
|
||||||
|
|
||||||
|
void store(T value, MemoryOrder order = MemoryOrder::SeqCst)
|
||||||
|
{
|
||||||
|
return __atomic_store_n(&m_value, value, (int)order);
|
||||||
|
}
|
||||||
|
|
||||||
|
T exchange(T value, MemoryOrder order = MemoryOrder::SeqCst)
|
||||||
|
{
|
||||||
|
return __atomic_exchange_n(&m_value, value, (int)order);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool compare_exchange_strong(T& expected, T desired, MemoryOrder success, MemoryOrder failure)
|
||||||
|
{
|
||||||
|
return __atomic_compare_exchange_n(&m_value, &expected, desired, false, (int)success, (int)failure);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool compare_exchange_strong(T& expected, T desired, MemoryOrder order = MemoryOrder::SeqCst)
|
||||||
|
{
|
||||||
|
MemoryOrder failure = (order == MemoryOrder::AcqRel) ? MemoryOrder::Acquire
|
||||||
|
: (order == MemoryOrder::Release) ? MemoryOrder::Relaxed
|
||||||
|
: order;
|
||||||
|
return __atomic_compare_exchange_n(&m_value, &expected, desired, false, (int)order, (int)failure);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool compare_exchange_weak(T& expected, T desired, MemoryOrder success, MemoryOrder failure)
|
||||||
|
{
|
||||||
|
return __atomic_compare_exchange_n(&m_value, &expected, desired, true, (int)success, (int)failure);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool compare_exchange_weak(T& expected, T desired, MemoryOrder order = MemoryOrder::SeqCst)
|
||||||
|
{
|
||||||
|
MemoryOrder failure = (order == MemoryOrder::AcqRel) ? MemoryOrder::Acquire
|
||||||
|
: (order == MemoryOrder::Release) ? MemoryOrder::Relaxed
|
||||||
|
: order;
|
||||||
|
return __atomic_compare_exchange_n(&m_value, &expected, desired, true, (int)order, (int)failure);
|
||||||
|
}
|
||||||
|
|
||||||
|
T fetch_add(T other, MemoryOrder order = MemoryOrder::SeqCst)
|
||||||
|
{
|
||||||
|
return __atomic_fetch_add(&m_value, other, (int)order);
|
||||||
|
}
|
||||||
|
|
||||||
|
T fetch_sub(T other, MemoryOrder order = MemoryOrder::SeqCst)
|
||||||
|
{
|
||||||
|
return __atomic_fetch_sub(&m_value, other, (int)order);
|
||||||
|
}
|
||||||
|
|
||||||
|
T operator++()
|
||||||
|
{
|
||||||
|
return fetch_add(1) + 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
T operator++(int)
|
||||||
|
{
|
||||||
|
return fetch_add(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
T operator--()
|
||||||
|
{
|
||||||
|
return fetch_sub(1) - 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
T operator--(int)
|
||||||
|
{
|
||||||
|
return fetch_sub(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
T m_value;
|
||||||
|
};
|
Loading…
Reference in New Issue
Block a user