From 43931c7e187bda85e2be12bccb14bd826a6c34c0 Mon Sep 17 00:00:00 2001 From: Markus Mittendrein Date: Sat, 20 Apr 2019 01:54:54 +0200 Subject: Add custom memory management strategies to cppc4group --- src/cppc4group.cpp | 81 ++++++++++++++++++++++++++++++++++++++++++++---------- 1 file changed, 66 insertions(+), 15 deletions(-) (limited to 'src/cppc4group.cpp') diff --git a/src/cppc4group.cpp b/src/cppc4group.cpp index 2d85537..329d6de 100644 --- a/src/cppc4group.cpp +++ b/src/cppc4group.cpp @@ -39,6 +39,66 @@ struct CppC4Group::Private { } }; +struct CppC4Group::MemoryManagement::Private { + bool predefined; + MemoryManagementStrategy strategy; + + Start start; + End end; +}; + +CppC4Group::MemoryManagement::MemoryManagement(MemoryManagementStrategy strategy) : p{new Private{true, strategy}} +{ + +} + +CppC4Group::MemoryManagement::MemoryManagement(Start&& start, End&& end) : p{new Private{false, {}, start, end}} +{ + +} + +CppC4Group::MemoryManagement::~MemoryManagement() +{ + delete p; +} + +CppC4Group::MemoryManagement::MemoryManagementStrategy CppC4Group::MemoryManagement::operator()() const +{ + if(p->predefined) + { + return p->strategy; + } + else + { + struct CustomMemoryManagement { + CC4Group_MemoryManagement_t realMemoryManagement; + + Start start; + End end; + + static void* callStart(void* const data, size_t const size, void* const arg) + { + return reinterpret_cast(arg)->start(data, size); + } + + static void callEndAndCleanup(void* const data, void* const arg) + { + auto customMemoryManagement = reinterpret_cast(arg); + customMemoryManagement->end(data); + delete customMemoryManagement; + } + }; + + auto customManagement = new CustomMemoryManagement{{CustomMemoryManagement::callStart, CustomMemoryManagement::callEndAndCleanup}, p->start, p->end}; + customManagement->realMemoryManagement.arg = static_cast(customManagement); + return reinterpret_cast(&customManagement->realMemoryManagement); + } +} + +const CppC4Group::MemoryManagement CppC4Group::MemoryManagement::Take{reinterpret_cast(cc4group.MemoryManagement.Take)}; +const CppC4Group::MemoryManagement CppC4Group::MemoryManagement::Copy{reinterpret_cast(cc4group.MemoryManagement.Copy)}; +const CppC4Group::MemoryManagement CppC4Group::MemoryManagement::Reference{reinterpret_cast(cc4group.MemoryManagement.Reference)}; + namespace { CC4Group_TmpMemoryStrategy convertTmpMemoryStrategy(const CppC4Group::TmpMemoryStrategy strategy) { @@ -54,22 +114,13 @@ namespace { return cc4group.TmpMemoryStrategies.Auto; } - CC4Group_MemoryManagement convertMemoryManagement(const CppC4Group::MemoryManagement management) + CC4Group_MemoryManagement convertMemoryManagement(const CppC4Group::MemoryManagement& memoryManagement) { - switch(management) - { - case CppC4Group::Take: - return cc4group.MemoryManagement.Take; - case CppC4Group::Copy: - return cc4group.MemoryManagement.Copy; - case CppC4Group::Reference: - return cc4group.MemoryManagement.Reference; - } - return cc4group.MemoryManagement.Copy; + return reinterpret_cast(memoryManagement()); } } -CppC4Group::CppC4Group() : p{new CppC4Group::Private{}} +CppC4Group::CppC4Group() : p{new Private{}} { } @@ -110,12 +161,12 @@ bool CppC4Group::openFilePointer(FILE* file) return cc4group.openFilePointer(p->g, file); } -bool CppC4Group::openMemory(const void* const data, const size_t size, const MemoryManagement management) +bool CppC4Group::openMemory(const void* const data, const size_t size, const MemoryManagement& management) { return cc4group.openMemory(p->g, data, size, convertMemoryManagement(management)); } -bool CppC4Group::openWithReadCallback(const ReadCallback callback, void* const callbackArg, const MemoryManagement management, SetupCallback initCallback, SetupCallback deinitCallback) +bool CppC4Group::openWithReadCallback(const ReadCallback callback, void* const callbackArg, const MemoryManagement& management, SetupCallback initCallback, SetupCallback deinitCallback) { return cc4group.openWithReadCallback(p->g, callback, callbackArg, convertMemoryManagement(management), initCallback, deinitCallback); } @@ -311,7 +362,7 @@ bool CppC4Group::createFile(const std::string& path) return cc4group.createFile(p->g, path.c_str()); } -bool CppC4Group::setEntryData(const std::string& path, const void*const data, const size_t size, const MemoryManagement management) +bool CppC4Group::setEntryData(const std::string& path, const void*const data, const size_t size, const MemoryManagement& management) { return cc4group.setEntryData(p->g, path.c_str(), data, size, convertMemoryManagement(management)); } -- cgit v1.2.3-54-g00ecf