#if !defined(__STD_ATOMIC__)
#define __STD_ATOMIC__

#include <atomic>
//#include "normbase.hpp"

// -- atomic value wrapper: make it copiable so that it can be used in containers. . However, copy (including copy construction) is not atomic.
template<typename TINT>
class CAtomicWrap
{
public:
    CAtomicWrap(void):
        m_data(0){};
        
    CAtomicWrap(TINT && v):
    m_data(move(v)){};

    
    CAtomicWrap(const CAtomicWrap & other):
        m_data(0)
    {
        m_data.store(other.m_data.load());
    }
    
    CAtomicWrap & operator = (const CAtomicWrap & other)
    {
        m_data.store(other.m_data.load());
    }
    
    operator TINT (void) const {return m_data.load();}
    
    std::atomic<TINT> & get_data(void) {return m_data;}
    const std::atomic<TINT> & get_data(void) const {return m_data;}
    
    CAtomicWrap & operator += (const CAtomicWrap & other)
    {
        m_data += other.m_data.load();
    }
    
    CAtomicWrap & operator -= (const CAtomicWrap & other)
    {
        m_data -= other.m_data.load();
    }
    
        
private:
    std::atomic<TINT> m_data;
};


//std::atomic guarantees whatever alignment is necessary
typedef INT64 TAtomicCounterValueType;
typedef std::atomic<TAtomicCounterValueType> CRefCounter;
	
//class CRefCounter
//{
//public:
//	
//	CRefCounter(TAtomicCounterValueType ini = 0):
//		m_count(ini)
//	{};
//	
//	TAtomicCounterValueType operator ++(void)
//	{
//		return 1 + m_count.fetch_add(1, std::memory_order_relaxed);
//	}
//	TAtomicCounterValueType operator ++(int)
//	{
//		return m_count.fetch_add(1, std::memory_order_relaxed);
//	}
//	
//	TAtomicCounterValueType operator --(void)
//	{
//		return m_count.fetch_sub(1, std::memory_order_acq_rel) - 1;
//	}
//	
//	TAtomicCounterValueType operator --(int)
//	{
//		return m_count.fetch_sub(1, std::memory_order_acq_rel);
//	}
//	
//	TAtomicCounterValueType Get(void) const
//	{
//		return m_count.load(std::memory_order_relaxed);
//	}
//	
//private:
//	TAtomicCounterType m_count;
//};



#endif
