///////////////////////////////////////////////////////////////////// // Inline and template implementations for // the Utility Collection of Miscellanious Handy Functions // // Created 2013 by Dan Andersson // Edited 2013 by // * Dan Andersson // * Dennis Andersen ///////////////////////////////////////////////////////////////////// #ifndef UTILITIES_INLINE_IMPL_H #define UTILITIES_INLINE_IMPL_H #include "Utilities.h" namespace Utility { namespace DynamicMemory { template inline void SafeDeleteInstance( Type *dynamicInstance ) { if( dynamicInstance ) { delete dynamicInstance; } } template void SafeDeleteArray( Type dynamicArray[] ) { if( dynamicArray ) { delete [] dynamicArray; } } #pragma region UnuiqePointer template UniquePointer::UniquePointer( Type *assignedInstance ) { this->ownedInstance = assignedInstance; } template UniquePointer::UniquePointer( const UniquePointer &donor ) { this->ownedInstance = donor.ownedInstance; donor.ownedInstance = NULL; } template UniquePointer::~UniquePointer() { SafeDeleteInstance( this->ownedInstance ); } template UniquePointer & UniquePointer::operator = ( const UniquePointer &donor ) { SafeDeleteInstance( this->ownedInstance ); this->ownedInstance = donor.ownedInstance; donor.ownedInstance = NULL; return *this; } template UniquePointer::operator Type* () { return this->ownedInstance; } template UniquePointer::operator const Type* () const { return this->ownedInstance; } template Type * UniquePointer::operator -> () { return this->ownedInstance; } template const Type * UniquePointer::operator -> () const { return this->ownedInstance; } template UniquePointer::operator bool() const { return this->ownedInstance != NULL; } template bool UniquePointer::operator == ( Type *stray ) const { return this->ownedInstance == stray; } template bool UniquePointer::operator != ( Type *stray ) const { return this->ownedInstance != stray; } template Type* UniquePointer::Release() { Type *copy = this->ownedInstance; this->ownedInstance = NULL; return copy; } template inline bool UniquePointer::HaveOwnership() const { return this->operator bool(); } template UniqueArray::UniqueArray( Type assignedArray[] ) { this->ownedArray = assignedArray; } template UniqueArray::UniqueArray( const UniqueArray &donor ) { this->ownedArray = donor.ownedArray; donor.ownedArray = NULL; } template UniqueArray::~UniqueArray() { SafeDeleteArray( this->ownedArray ); } template UniqueArray & UniqueArray::operator = ( const UniqueArray &donor ) { SafeDeleteArray( this->ownedArray ); this->ownedArray = donor.ownedInstance; donor.owned = NULL; } template template Type & UniqueArray::operator [] ( Index i ) { return this->ownedArray[i]; } template template const Type & UniqueArray::operator [] ( Index i ) const { return this->ownedArray[i]; } template UniqueArray::operator bool () const { return this->ownedArray != NULL; } template bool UniqueArray::operator == ( Type *stray ) const { return this->ownedArray == stray; } template bool UniqueArray::operator != ( Type *stray ) const { return this->ownedArray != stray; } template Type* UniqueArray::Release() { Type *copy = this->ownedArray; this->ownedArray = NULL; return copy; } template inline bool UniqueArray::HaveOwnership() const { return this->operator bool(); } #pragma endregion #pragma region SmartPointer template void SmartPointer::Destroy() { delete this->_rc; this->_rc = NULL; //Use default function for memory deallocation. SafeDeleteInstance(this->_ptr); this->_ptr = NULL; } template SmartPointer::SmartPointer() :_rc(0), _ptr(0) { } template SmartPointer::SmartPointer(UniquePointer& p) :_ptr(p.Release()) { this->_rc = new ReferenceCount(); this->_rc->Incref(); } template SmartPointer::SmartPointer(T* p) :_ptr(p) { this->_rc = new ReferenceCount(); this->_rc->Incref(); } template SmartPointer::SmartPointer(const SmartPointer& d) :_ptr(d._ptr), _rc(d._rc) { if(this->_rc) this->_rc->Incref(); } template SmartPointer::~SmartPointer() { this->Release(); } template SmartPointer& SmartPointer::operator= (const SmartPointer& p) { if (this != &p) { //Last to go? if(this->_rc && this->_rc->Decref() == 0) { //Call child specific Destroy(); } this->_ptr = p._ptr; this->_rc = p._rc; if(this->_rc) this->_rc->Incref(); } return *this; } template SmartPointer& SmartPointer::operator= (UniquePointer& p) { //Last to go? if(this->_rc) { if(this->_rc->Decref() == 0) { //Call child specific Destroy(); this->_rc = new ReferenceCount(); } } else { if(p) this->_rc = new ReferenceCount(); } if(this->_rc) this->_rc->Incref(); this->_ptr = p.Release(); return *this; } template SmartPointer& SmartPointer::operator= (T* p) { if (this->_ptr != p) { //Last to go? if(this->_rc) { if(this->_rc->Decref() == 0) { //Call child specific Destroy(); if(p) this->_rc = new ReferenceCount(); } } else if(p) { this->_rc = new ReferenceCount(); } this->_ptr = p; if(p) this->_rc->Incref(); else this->_rc = 0; } return *this; } template inline bool SmartPointer::operator== (const SmartPointer& d) const { return d._ptr == this->_ptr; } template inline bool SmartPointer::operator== (const T& p) const { return &p == this->_ptr; } template inline bool SmartPointer::operator!= (const SmartPointer& d) const { return d._ptr != this->_ptr; } template inline bool SmartPointer::operator!= (const T& p) const { return &p != this->_ptr; } template inline T& SmartPointer::operator* () { return *this->_ptr; } template inline const T& SmartPointer::operator* () const { return *this->_ptr; } template inline T* SmartPointer::operator-> () { return this->_ptr; } template inline const T* SmartPointer::operator-> () const { return this->_ptr; } template inline SmartPointer::operator T* () const { return this->_ptr; } template inline SmartPointer::operator const T* () const { return this->_ptr; } template inline SmartPointer::operator T& () const { return *this->_ptr; } template inline SmartPointer::operator bool() const { return (this->_ptr != 0); } template inline T* SmartPointer::Get() { return this->_ptr; } template inline T* SmartPointer::Get() const { return this->_ptr; } template int SmartPointer::Release() { int returnVal = 0; if(this->_rc && ((returnVal = this->_rc->Decref()) == 0)) { Destroy(); } return returnVal; } template int SmartPointer::ReleaseDummy() { int val = this->_rc->Decref(); this->_rc->Incref(); return val; } template inline bool SmartPointer::IsValid() const { return (this->_ptr != NULL) ? true : false; } #pragma endregion } namespace Thread { #pragma region ThreadSafeSmartPointer template void ThreadSafeSmartPointer::Destroy() { delete this->_rc.load(); this->_rc = NULL; //Use default function for memory deallocation. SafeDeleteInstance(this->_ptr.load()); this->_ptr = NULL; } template ThreadSafeSmartPointer::ThreadSafeSmartPointer() :_rc(0), _ptr(0) { } template ThreadSafeSmartPointer::ThreadSafeSmartPointer(UniquePointer& p) :_ptr(p.Release()) { this->_rc = new ReferenceCount(); this->_rc->Incref(); } template ThreadSafeSmartPointer::ThreadSafeSmartPointer(T* p) :_ptr(p) { this->_rc.store = new ReferenceCount(); this->_rc->Incref(); } template ThreadSafeSmartPointer::ThreadSafeSmartPointer(const ThreadSafeSmartPointer& d) :_ptr(d._ptr), _rc(d._rc) { if(this->_rc) this->_rc->Incref(); } template ThreadSafeSmartPointer::~ThreadSafeSmartPointer() { this->Release(); } template ThreadSafeSmartPointer& ThreadSafeSmartPointer::operator= (const ThreadSafeSmartPointer& p) { if (this != &p) { //Last to go? if(this->_rc.load() && this->_rc.load()->Decref() == 0) { //Call child specific Destroy(); } this->_ptr.store(p._ptr.load()); this->_rc.store(p._rc.load()); if(this->_rc.load()) this->_rc.load()->Incref(); } return *this; } template ThreadSafeSmartPointer& ThreadSafeSmartPointer::operator= (UniquePointer& p) { //Last to go? if(this->_rc) { if(this->_rc->Decref() == 0) { //Call child specific Destroy(); this->_rc = new ReferenceCount(); } } else { if(p) this->_rc = new ReferenceCount(); } if(this->_rc) this->_rc->Incref(); this->_ptr = p.Release(); return *this; } template ThreadSafeSmartPointer& ThreadSafeSmartPointer::operator= (T* p) { if (this->_ptr != p) { //Last to go? if(this->_rc.load()) { if(this->_rc.load()->Decref() == 0) { //Call child specific Destroy(); if(p) this->_rc = new ReferenceCount(); } } else if(p) { this->_rc = new ReferenceCount(); } this->_ptr = p; if(p) this->_rc.load()->Incref(); else this->_rc = 0; } return *this; } template inline bool ThreadSafeSmartPointer::operator== (const ThreadSafeSmartPointer& d) const { return d._ptr == this->_ptr; } template inline bool ThreadSafeSmartPointer::operator== (const T& p) const { return &p == this->_ptr; } template inline bool ThreadSafeSmartPointer::operator!= (const ThreadSafeSmartPointer& d) const { return d._ptr != this->_ptr; } template inline bool ThreadSafeSmartPointer::operator!= (const T& p) const { return &p != this->_ptr; } template inline T& ThreadSafeSmartPointer::operator* () { return *this->_ptr; } template inline const T& ThreadSafeSmartPointer::operator* () const { return *this->_ptr; } template inline T* ThreadSafeSmartPointer::operator-> () { return this->_ptr; } template inline const T* ThreadSafeSmartPointer::operator-> () const { return this->_ptr; } template inline ThreadSafeSmartPointer::operator T* () const { return this->_ptr; } template inline ThreadSafeSmartPointer::operator const T* () const { return this->_ptr; } template inline ThreadSafeSmartPointer::operator T& () const { return *this->_ptr; } template inline ThreadSafeSmartPointer::operator bool() const { return (this->_ptr != 0); } template inline T* ThreadSafeSmartPointer::Get() { return this->_ptr; } template inline T* ThreadSafeSmartPointer::Get() const { return this->_ptr; } template int ThreadSafeSmartPointer::Release() { int returnVal = 0; if(this->_rc.load() && ((returnVal = this->_rc.load()->Decref()) == 0)) { Destroy(); } return returnVal; } template int ThreadSafeSmartPointer::ReleaseDummy() { int val = this->_rc->Decref(); this->_rc->Incref(); return val; } template inline bool ThreadSafeSmartPointer::IsValid() const { return (this->_ptr != NULL) ? true : false; } #pragma endregion } } #endif