common: port ScopedPtrMT to std::atomic

v2: s/NULL/nullptr/
v3: tentative fix for MSVC
// ScopedPtrMT.h(91, 0): error C2593: 'operator ==' is ambiguous
This commit is contained in:
Gregory Hainaut 2016-02-22 19:36:45 +01:00
parent cb776d2f50
commit 89fad4d3ad
4 changed files with 17 additions and 44 deletions

View File

@ -190,7 +190,7 @@ public:
// (I think it's unsigned int vs signed int)
#include <wx/filefn.h>
#define HAVE_MODE_T
#endif
#endif
#include <stdexcept>
#include <cstring> // string.h under c++
@ -200,6 +200,7 @@ public:
#include <list>
#include <algorithm>
#include <memory>
#include <atomic>
#include "Pcsx2Defs.h"

View File

@ -27,25 +27,23 @@ class ScopedPtrMT
{
DeclareNoncopyableObject(ScopedPtrMT);
typedef T* TPtr;
protected:
volatile TPtr m_ptr;
std::atomic<T*> m_ptr;
Threading::Mutex m_mtx;
public:
typedef T element_type;
wxEXPLICIT ScopedPtrMT(T * ptr = NULL)
wxEXPLICIT ScopedPtrMT(T * ptr = nullptr)
{
m_ptr = ptr;
}
~ScopedPtrMT() throw() { _Delete_unlocked(); }
ScopedPtrMT& Reassign(T * ptr = NULL)
ScopedPtrMT& Reassign(T * ptr = nullptr)
{
TPtr doh = (TPtr)Threading::AtomicExchangePointer( m_ptr, ptr );
T* doh = m_ptr.exchange(ptr);
if ( ptr != doh ) delete doh;
return *this;
}
@ -55,19 +53,17 @@ public:
ScopedLock lock( m_mtx );
_Delete_unlocked();
}
// Removes the pointer from scoped management, but does not delete!
// (ScopedPtr will be NULL after this method)
// (ScopedPtr will be nullptr after this method)
T *DetachPtr()
{
ScopedLock lock( m_mtx );
T *ptr = m_ptr;
m_ptr = NULL;
return ptr;
return m_ptr.exchange(nullptr);
}
// Returns the managed pointer. Can return NULL as a valid result if the ScopedPtrMT
// Returns the managed pointer. Can return nullptr as a valid result if the ScopedPtrMT
// has no object in management.
T* GetPtr() const
{
@ -77,6 +73,7 @@ public:
void SwapPtr(ScopedPtrMT& other)
{
ScopedLock lock( m_mtx );
m_ptr.exchange(other.m_ptr.exchange(m_ptr.load()));
T * const tmp = other.m_ptr;
other.m_ptr = m_ptr;
m_ptr = tmp;
@ -91,7 +88,7 @@ public:
bool operator!() const throw()
{
return m_ptr == NULL;
return m_ptr.load() == nullptr;
}
// Equality
@ -106,7 +103,7 @@ public:
return !operator==(pT);
}
// Convenient assignment operator. ScopedPtrMT = NULL will issue an automatic deletion
// Convenient assignment operator. ScopedPtrMT = nullptr will issue an automatic deletion
// of the managed pointer.
ScopedPtrMT& operator=( T* src )
{
@ -120,16 +117,16 @@ public:
}
// Dereference operator, returns a handle to the managed pointer.
// Generates a debug assertion if the object is NULL!
// Generates a debug assertion if the object is nullptr!
T& operator*() const
{
pxAssert(m_ptr != NULL);
pxAssert(m_ptr != nullptr);
return *m_ptr;
}
T* operator->() const
{
pxAssert(m_ptr != NULL);
pxAssert(m_ptr != nullptr);
return m_ptr;
}
#endif
@ -137,7 +134,6 @@ public:
protected:
void _Delete_unlocked() throw()
{
delete m_ptr;
m_ptr = NULL;
delete m_ptr.exchange(nullptr);
}
};

View File

@ -192,12 +192,6 @@ namespace Threading
extern bool AtomicBitTestAndReset( volatile u32& bitset, u8 bit );
extern bool AtomicBitTestAndReset( volatile s32& bitset, u8 bit );
extern void* _AtomicExchangePointer( volatile uptr& target, uptr value );
extern void* _AtomicCompareExchangePointer( volatile uptr& target, uptr value, uptr comparand );
#define AtomicExchangePointer( dest, src ) _AtomicExchangePointer( (uptr&)dest, (uptr)src )
#define AtomicCompareExchangePointer( dest, comp, src ) _AtomicExchangePointer( (uptr&)dest, (uptr)comp, (uptr)src )
// pthread Cond is an evil api that is not suited for Pcsx2 needs.
// Let's not use it. Use mutexes and semaphores instead to create waits. (Air)
#if 0

View File

@ -828,24 +828,6 @@ __fi s32 Threading::AtomicDecrement(volatile s32& Target) {
return _InterlockedExchangeAdd((volatile vol_t*)&Target, -1);
}
__fi void* Threading::_AtomicExchangePointer(volatile uptr& target, uptr value)
{
#ifdef _M_X86_64 // high-level atomic ops, please leave these 64 bit checks in place.
return (void*)_InterlockedExchange64((volatile s64*)&target, value);
#else
return (void*)_InterlockedExchange((volatile vol_t*)&target, value);
#endif
}
__fi void* Threading::_AtomicCompareExchangePointer(volatile uptr& target, uptr value, uptr comparand)
{
#ifdef _M_X86_64 // high-level atomic ops, please leave these 64 bit checks in place.
return (void*)_InterlockedCompareExchange64((volatile s64*)&target, value, comparand);
#else
return (void*)_InterlockedCompareExchange((volatile vol_t*)&target, value, comparand);
#endif
}
// --------------------------------------------------------------------------------------
// BaseThreadError
// --------------------------------------------------------------------------------------