[DEV] update to the new ETK allocator wrapper

This commit is contained in:
Edouard DUPIN 2017-10-21 19:05:21 +02:00
parent c2248bb20b
commit 8e594532a1
8 changed files with 86 additions and 43 deletions

View File

@ -11,7 +11,7 @@ ememory::Counter::Counter(bool _fromWeak):
m_counterShared(1), m_counterShared(1),
m_counterWeak(0), m_counterWeak(0),
m_mutex() { m_mutex() {
EMEMORY_DBG("new counter(" << _fromWeak << ")"); EMEMORY_DBG("Create counter(" << _fromWeak << ")");
if (_fromWeak == true) { if (_fromWeak == true) {
m_counterShared = 0; m_counterShared = 0;
m_counterWeak = 1; m_counterWeak = 1;
@ -20,7 +20,7 @@ ememory::Counter::Counter(bool _fromWeak):
} }
ememory::Counter::~Counter() { ememory::Counter::~Counter() {
EMEMORY_DBG("delete counter"); EMEMORY_DBG("Delete counter");
} }
int64_t ememory::Counter::incrementShared(bool _fromWeak) { int64_t ememory::Counter::incrementShared(bool _fromWeak) {

View File

@ -13,7 +13,6 @@
namespace ememory { namespace ememory {
template<typename> class WeakPtr; template<typename> class WeakPtr;
template<typename> class EnableSharedFromThis; template<typename> class EnableSharedFromThis;
using deleterCall = etk::Function<void(void* _data)>;
/** /**
* @brief ememory::SharedPtr is a smart pointer that retains shared ownership of an object through a pointer. * @brief ememory::SharedPtr is a smart pointer that retains shared ownership of an object through a pointer.
* Several SharedPtr objects may own the same object. The object is destroyed and its memory deallocated when * Several SharedPtr objects may own the same object. The object is destroyed and its memory deallocated when
@ -31,6 +30,7 @@ namespace ememory {
*/ */
template<typename EMEMORY_TYPE> template<typename EMEMORY_TYPE>
class SharedPtr { class SharedPtr {
using deleterCall = etk::Function<void(void* _data)>;
friend class WeakPtr<EMEMORY_TYPE>; friend class WeakPtr<EMEMORY_TYPE>;
private: private:
EMEMORY_TYPE* m_element; //!< Pointer on the Data EMEMORY_TYPE* m_element; //!< Pointer on the Data
@ -41,7 +41,7 @@ namespace ememory {
* @return deleter function (need access to a voind data access) * @return deleter function (need access to a voind data access)
*/ */
deleterCall createDeleter() const { deleterCall createDeleter() const {
return [](void* _data) { delete((EMEMORY_TYPE*)_data);}; return [](void* _data) { ETK_DELETE(EMEMORY_TYPE, _data);};
} }
public: public:
#ifndef PARSE_DOXYGEN #ifndef PARSE_DOXYGEN
@ -49,12 +49,12 @@ namespace ememory {
typename etk::EnableIf< etk::IsSame<EMEMORY_TYPE2, EMEMORY_TYPE>::value typename etk::EnableIf< etk::IsSame<EMEMORY_TYPE2, EMEMORY_TYPE>::value
&& etk::IsBaseOf<ememory::EnableSharedFromThisBase, EMEMORY_TYPE2>::value && etk::IsBaseOf<ememory::EnableSharedFromThisBase, EMEMORY_TYPE2>::value
, int>::type = 0> , int>::type = 0>
SharedPtr(EMEMORY_TYPE2* _element, deleterCall&& _deleter = [](void* _data) { delete((EMEMORY_TYPE*)_data);}); SharedPtr(EMEMORY_TYPE2* _element, deleterCall&& _deleter = [](void* _data) { ETK_DELETE(EMEMORY_TYPE, _data);});
template<class EMEMORY_TYPE2, template<class EMEMORY_TYPE2,
typename etk::EnableIf< etk::IsSame<EMEMORY_TYPE2, EMEMORY_TYPE>::value typename etk::EnableIf< etk::IsSame<EMEMORY_TYPE2, EMEMORY_TYPE>::value
&& !etk::IsBaseOf<ememory::EnableSharedFromThisBase, EMEMORY_TYPE2>::value && !etk::IsBaseOf<ememory::EnableSharedFromThisBase, EMEMORY_TYPE2>::value
, int>::type = 0> , int>::type = 0>
SharedPtr(EMEMORY_TYPE2* _element, deleterCall&& _deleter = [](void* _data) { delete((EMEMORY_TYPE*)_data);}); SharedPtr(EMEMORY_TYPE2* _element, deleterCall&& _deleter = [](void* _data) { ETK_DELETE(EMEMORY_TYPE, _data);});
#else #else
/** /**
* @brief Contructor whith the pointer of data * @brief Contructor whith the pointer of data

View File

@ -5,9 +5,12 @@
namespace ememory { namespace ememory {
template <class EMEM_UPTR_TYPE> template <class EMEM_UPTR_TYPE>
class UniquePtr { class UniquePtr {
//private: Do it better ... public:
using deleterCall = etk::Function<void(void* _data)>;
//private: Do it better ...
public: public:
EMEM_UPTR_TYPE* m_pointer; EMEM_UPTR_TYPE* m_pointer;
deleterCall m_deleter; //!< Function to call to delete the data pointer
private: private:
template <class EMEM_UPTR_TYPE_2> template <class EMEM_UPTR_TYPE_2>
UniquePtr(UniquePtr<EMEM_UPTR_TYPE_2> &) = delete; UniquePtr(UniquePtr<EMEM_UPTR_TYPE_2> &) = delete;
@ -16,23 +19,26 @@ namespace ememory {
UniquePtr &operator=(UniquePtr<EMEM_UPTR_TYPE_2> &) = delete; UniquePtr &operator=(UniquePtr<EMEM_UPTR_TYPE_2> &) = delete;
public: public:
UniquePtr() : UniquePtr() :
m_pointer(nullptr) { m_pointer(nullptr),
m_deleter(nullptr) {
} }
UniquePtr(etk::NullPtr) : UniquePtr(etk::NullPtr) :
m_pointer(nullptr) { m_pointer(nullptr),
m_deleter(nullptr) {
} }
explicit UniquePtr(EMEM_UPTR_TYPE* _obj) : explicit UniquePtr(EMEM_UPTR_TYPE* _obj, deleterCall&& _deleter = [](void* _data) { ETK_DELETE(EMEM_UPTR_TYPE, _data);}) :
m_pointer(_obj) { m_pointer(_obj),
m_deleter(_deleter) {
ETK_MEM_CHECK_POINTER(_obj);
} }
template <class EMEM_UPTR_TYPE_2> template <class EMEM_UPTR_TYPE_2>
UniquePtr(UniquePtr<EMEM_UPTR_TYPE_2>&& _obj) : UniquePtr(UniquePtr<EMEM_UPTR_TYPE_2>&& _obj) :
m_pointer(nullptr) { m_pointer(nullptr),
// TODO: Better: _obj.swap(*this); m_deleter(nullptr) {
m_pointer = _obj.m_pointer; etk::swap(_obj.m_pointer, m_pointer);
_obj.m_pointer = nullptr; etk::swap(_obj.m_deleter, m_deleter);
} }
~UniquePtr() { ~UniquePtr() {
reset(); reset();
@ -43,8 +49,8 @@ namespace ememory {
} }
UniquePtr& operator=(UniquePtr&& _obj) { UniquePtr& operator=(UniquePtr&& _obj) {
reset(); reset();
m_pointer = _obj.m_pointer; etk::swap(_obj.m_pointer, m_pointer);
_obj.m_pointer = nullptr; etk::swap(_obj.m_deleter, m_deleter);
return *this; return *this;
} }
/* /*
@ -76,11 +82,14 @@ namespace ememory {
return tmp; return tmp;
} }
void reset(){ void reset(){
delete m_pointer; if (m_deleter != nullptr) {
m_deleter(m_pointer);
}
m_pointer = nullptr; m_pointer = nullptr;
} }
void swap(UniquePtr &_obj){ void swap(UniquePtr &_obj){
etk::swap(m_pointer, _obj.m_pointer); etk::swap(_obj.m_pointer, m_pointer);
etk::swap(_obj.m_deleter, m_deleter);
} }
/** /**
* @brief Check if the UniquePtr have an internal data (not nullptr) * @brief Check if the UniquePtr have an internal data (not nullptr)
@ -106,7 +115,7 @@ namespace ememory {
template<class EMEM_UPTR_TYPE, class... EMEM_UPTR_ARG> template<class EMEM_UPTR_TYPE, class... EMEM_UPTR_ARG>
UniquePtr<EMEM_UPTR_TYPE> makeUniquePtr(EMEM_UPTR_ARG ... _obj) { UniquePtr<EMEM_UPTR_TYPE> makeUniquePtr(EMEM_UPTR_ARG ... _obj) {
return ememory::UniquePtr<EMEM_UPTR_TYPE>(new EMEM_UPTR_TYPE(_obj...)); return ememory::UniquePtr<EMEM_UPTR_TYPE>(ETK_NEW(EMEM_UPTR_TYPE, _obj...));
} }
template <class EMEM_UPTR_TYPE> template <class EMEM_UPTR_TYPE>

View File

@ -17,10 +17,12 @@ ememory::SharedPtr<EMEMORY_TYPE>::SharedPtr(EMEMORY_TYPE2* _element, deleterCall
m_element(_element), m_element(_element),
m_counter(nullptr), m_counter(nullptr),
m_deleter(_deleter) { m_deleter(_deleter) {
EMEMORY_DBG("new shared"); EMEMORY_DBG("Create shared");
if (m_element == nullptr) { if (m_element == nullptr) {
return; return;
} }
EMEMORY_DBG("Check if the user use the memory allocator or personal system...");
ETK_MEM_CHECK_POINTER(_element);
EMEMORY_DBG(" ==> get previous pointer"); EMEMORY_DBG(" ==> get previous pointer");
m_counter = m_element->weakFromThis().getCounter(); m_counter = m_element->weakFromThis().getCounter();
if (m_counter != nullptr) { if (m_counter != nullptr) {
@ -40,11 +42,13 @@ ememory::SharedPtr<EMEMORY_TYPE>::SharedPtr(EMEMORY_TYPE2* _element, deleterCall
m_element(_element), m_element(_element),
m_counter(nullptr), m_counter(nullptr),
m_deleter(_deleter) { m_deleter(_deleter) {
EMEMORY_DBG("new shared"); EMEMORY_DBG("Create shared");
if (m_element == nullptr) { if (m_element == nullptr) {
return; return;
} }
m_counter = new ememory::Counter(false); EMEMORY_DBG("Check if the user use the memory allocator or personal system...");
ETK_MEM_CHECK_POINTER(_element);
m_counter = ETK_NEW(ememory::Counter, false);
} }
template<typename EMEMORY_TYPE> template<typename EMEMORY_TYPE>
@ -52,7 +56,7 @@ ememory::SharedPtr<EMEMORY_TYPE>::SharedPtr():
m_element(nullptr), m_element(nullptr),
m_counter(nullptr), m_counter(nullptr),
m_deleter(createDeleter()) { m_deleter(createDeleter()) {
EMEMORY_DBG("new shared"); EMEMORY_DBG("Create shared");
} }
template<typename EMEMORY_TYPE> template<typename EMEMORY_TYPE>
@ -60,7 +64,7 @@ ememory::SharedPtr<EMEMORY_TYPE>::SharedPtr(etk::NullPtr):
m_element(nullptr), m_element(nullptr),
m_counter(nullptr), m_counter(nullptr),
m_deleter(createDeleter()) { m_deleter(createDeleter()) {
EMEMORY_DBG("new shared"); EMEMORY_DBG("Create shared");
} }
template<typename EMEMORY_TYPE> template<typename EMEMORY_TYPE>
@ -68,7 +72,7 @@ ememory::SharedPtr<EMEMORY_TYPE>::SharedPtr(EMEMORY_TYPE* _obj, ememory::Counter
m_element(_obj), m_element(_obj),
m_counter(_counter), m_counter(_counter),
m_deleter(createDeleter()) { m_deleter(createDeleter()) {
EMEMORY_DBG("new shared (from a cast)"); EMEMORY_DBG("Create shared (from a cast)");
if (_obj == nullptr) { if (_obj == nullptr) {
m_counter = nullptr; m_counter = nullptr;
return; return;
@ -191,7 +195,7 @@ void ememory::SharedPtr<EMEMORY_TYPE>::reset() {
ememory::Counter::remove rmData = m_counter->decrementShared(); ememory::Counter::remove rmData = m_counter->decrementShared();
switch(rmData) { switch(rmData) {
case ememory::Counter::remove::all: case ememory::Counter::remove::all:
delete m_counter; ETK_DELETE(ememory::Counter, m_counter);
if (m_deleter != nullptr) { if (m_deleter != nullptr) {
if (m_element != nullptr) { if (m_element != nullptr) {
m_deleter((void*)m_element); m_deleter((void*)m_element);
@ -210,7 +214,7 @@ void ememory::SharedPtr<EMEMORY_TYPE>::reset() {
} }
break; break;
case ememory::Counter::remove::counter: case ememory::Counter::remove::counter:
delete m_counter; ETK_DELETE(ememory::Counter, m_counter);
break; break;
case ememory::Counter::remove::none: case ememory::Counter::remove::none:
break; break;
@ -329,21 +333,21 @@ namespace ememory {
SharedPtr(etk::NullPtr): SharedPtr(etk::NullPtr):
m_element(nullptr), m_element(nullptr),
m_counter(nullptr) { m_counter(nullptr) {
EMEMORY_DBG("new shared<void>"); EMEMORY_DBG("Create shared<void>");
} }
SharedPtr(): SharedPtr():
m_element(nullptr), m_element(nullptr),
m_counter(nullptr) { m_counter(nullptr) {
EMEMORY_DBG("new shared<void>"); EMEMORY_DBG("Create shared<void>");
} }
~SharedPtr() { ~SharedPtr() {
EMEMORY_DBG("delete shared"); EMEMORY_DBG("delete shared");
reset(); reset();
} }
SharedPtr(void* _obj, ememory::Counter* _counter): SharedPtr(void* _obj, ememory::Counter* _counter):
m_element(_obj), m_element(_obj),
m_counter(_counter) { m_counter(_counter) {
EMEMORY_DBG("new shared (from a cast)"); EMEMORY_DBG("Create shared (from a cast)");
if (_obj == nullptr) { if (_obj == nullptr) {
m_counter = nullptr; m_counter = nullptr;
return; return;
@ -402,14 +406,14 @@ namespace ememory {
ememory::Counter::remove rmData = m_counter->decrementShared(); ememory::Counter::remove rmData = m_counter->decrementShared();
switch(rmData) { switch(rmData) {
case ememory::Counter::remove::all: case ememory::Counter::remove::all:
delete m_counter; ETK_DELETE(ememory::Counter, m_counter);
EMEMORY_WARNING("Maybe a leak ==> no deleter of the SharedPtr<void>"); EMEMORY_WARNING("Maybe a leak ==> no deleter of the SharedPtr<void>");
break; break;
case ememory::Counter::remove::data: case ememory::Counter::remove::data:
EMEMORY_WARNING("Maybe a leak ==> no deleter of the SharedPtr<void>"); EMEMORY_WARNING("Maybe a leak ==> no deleter of the SharedPtr<void>");
break; break;
case ememory::Counter::remove::counter: case ememory::Counter::remove::counter:
delete m_counter; ETK_DELETE(ememory::Counter, m_counter);
break; break;
case ememory::Counter::remove::none: case ememory::Counter::remove::none:
break; break;

View File

@ -27,11 +27,11 @@ template<typename EMEMORY_TYPE>
ememory::WeakPtr<EMEMORY_TYPE>::WeakPtr(EMEMORY_TYPE* _element): ememory::WeakPtr<EMEMORY_TYPE>::WeakPtr(EMEMORY_TYPE* _element):
m_element(_element), m_element(_element),
m_counter(nullptr) { m_counter(nullptr) {
EMEMORY_DBG("new weak"); EMEMORY_DBG("New weak");
if (m_element == nullptr) { if (m_element == nullptr) {
return; return;
} }
m_counter = new ememory::Counter(true); m_counter = ETK_NEW(ememory::Counter, true);
} }
template<typename EMEMORY_TYPE> template<typename EMEMORY_TYPE>
@ -221,7 +221,7 @@ void ememory::WeakPtr<EMEMORY_TYPE>::reset() {
EMEMORY_ERROR("in WeakPtr request remove all (impossible case ...)"); EMEMORY_ERROR("in WeakPtr request remove all (impossible case ...)");
break; break;
case ememory::Counter::remove::counter: case ememory::Counter::remove::counter:
delete m_counter; ETK_DELETE(ememory::Counter, m_counter);
break; break;
case ememory::Counter::remove::none: case ememory::Counter::remove::none:
break; break;

View File

@ -10,6 +10,7 @@
#include <ememory/SharedPtr.hpp> #include <ememory/SharedPtr.hpp>
#include <ememory/WeakPtr.hpp> #include <ememory/WeakPtr.hpp>
#include <ememory/EnableSharedFromThis.hpp> #include <ememory/EnableSharedFromThis.hpp>
#include <etk/Allocator.hpp>
/** /**
* @brief Ememory is a namespace to represent the @code #include <memory> @endcode part ==> simple memory access abstraction * @brief Ememory is a namespace to represent the @code #include <memory> @endcode part ==> simple memory access abstraction
@ -22,7 +23,7 @@ namespace ememory {
*/ */
template<class EMEMORY_TYPE, typename... EMEMORY_ARGS> template<class EMEMORY_TYPE, typename... EMEMORY_ARGS>
static ememory::SharedPtr<EMEMORY_TYPE> makeShared(EMEMORY_ARGS && ..._args) { static ememory::SharedPtr<EMEMORY_TYPE> makeShared(EMEMORY_ARGS && ..._args) {
return ememory::SharedPtr<EMEMORY_TYPE>(new EMEMORY_TYPE(etk::forward<EMEMORY_ARGS>(_args)...)); return ememory::SharedPtr<EMEMORY_TYPE>(ETK_NEW(EMEMORY_TYPE, etk::forward<EMEMORY_ARGS>(_args)...));
} }
/** /**
* @brief Cast in Dynamic the input SharedPtr into an other type like dynamic_cast on pointer * @brief Cast in Dynamic the input SharedPtr into an other type like dynamic_cast on pointer

View File

@ -22,6 +22,30 @@ TEST(TestShared, createAndDestroy) {
EXPECT_EQ(data != nullptr, false); EXPECT_EQ(data != nullptr, false);
} }
TEST(TestShared, createAndDestroy_2) {
ememory::SharedPtr<etk::String> data = ememory::SharedPtr<etk::String>(ETK_NEW(etk::String, "coucou"));
EXPECT_EQ(data.useCount(), 1);
EXPECT_EQ(*data, "coucou");
EXPECT_EQ(data == nullptr, false);
EXPECT_EQ(data != nullptr, true);
data.reset();
EXPECT_EQ(data.useCount(), 0);
EXPECT_EQ(data == nullptr, true);
EXPECT_EQ(data != nullptr, false);
}
TEST(TestShared, createAndDestroy_3) {
ememory::SharedPtr<etk::String> data = ememory::SharedPtr<etk::String>(new etk::String("coucou"));
EXPECT_EQ(data.useCount(), 1);
EXPECT_EQ(*data, "coucou");
EXPECT_EQ(data == nullptr, false);
EXPECT_EQ(data != nullptr, true);
data.reset();
EXPECT_EQ(data.useCount(), 0);
EXPECT_EQ(data == nullptr, true);
EXPECT_EQ(data != nullptr, false);
}
TEST(TestShared, copy) { TEST(TestShared, copy) {
ememory::SharedPtr<etk::String> data = ememory::makeShared<etk::String>("coucou"); ememory::SharedPtr<etk::String> data = ememory::makeShared<etk::String>("coucou");
EXPECT_EQ(data.useCount(), 1); EXPECT_EQ(data.useCount(), 1);

View File

@ -22,6 +22,11 @@ TEST(TestEmemoryUniquePtr, Creation_2) {
EXPECT_EQ(*testData.get(), 55); EXPECT_EQ(*testData.get(), 55);
} }
TEST(TestEmemoryUniquePtr, Creation_3) { TEST(TestEmemoryUniquePtr, Creation_3) {
ememory::UniquePtr<uint32_t> testData(ETK_NEW(uint32_t, 55));
EXPECT_NE(testData.get(), nullptr);
EXPECT_EQ(*testData.get(), 55);
}
TEST(TestEmemoryUniquePtr, Creation_4) {
ememory::UniquePtr<uint32_t> testData = ememory::makeUniquePtr<uint32_t>(456789); ememory::UniquePtr<uint32_t> testData = ememory::makeUniquePtr<uint32_t>(456789);
EXPECT_NE(testData.get(), nullptr); EXPECT_NE(testData.get(), nullptr);
EXPECT_EQ(*testData.get(), 456789); EXPECT_EQ(*testData.get(), 456789);