diff --git a/LameXP.vcproj b/LameXP.vcproj index b11bdc91..0461e2c2 100644 --- a/LameXP.vcproj +++ b/LameXP.vcproj @@ -65,7 +65,7 @@ +#endif //_DEBUG /////////////////////////////////////////////////////////////////////////////// // GLOBAL VARS @@ -278,18 +282,19 @@ bool lamexp_clean_folder(const QString folderPath) } /* - * Finalization function (Clean-up) + * Finalization function (final clean-up) */ void lamexp_finalization(void) { //Free all tools - while(!g_lamexp_tool_registry.isEmpty()) + if(!g_lamexp_tool_registry.isEmpty()) { QStringList keys = g_lamexp_tool_registry.keys(); for(int i = 0; i < keys.count(); i++) { - delete g_lamexp_tool_registry.take(keys.at(i)); + LAMEXP_DELETE(g_lamexp_tool_registry[keys.at(i)]); } + g_lamexp_tool_registry.clear(); } //Delete temporary files @@ -304,10 +309,11 @@ void lamexp_finalization(void) } //Destroy Qt application object - QCoreApplication *application = QApplication::instance(); + QApplication *application = dynamic_cast(QApplication::instance()); LAMEXP_DELETE(application); //Detach from shared memory + if(g_lamexp_sharedmem_ptr) g_lamexp_sharedmem_ptr->detach(); LAMEXP_DELETE(g_lamexp_sharedmem_ptr); } @@ -337,4 +343,19 @@ const QString lamexp_lookup_tool(const QString &toolName) { return QString(); } -} \ No newline at end of file +} + +/* + * Get number private bytes [debug only] + */ +SIZE_T lamexp_dbg_private_bytes(void) +{ +#ifdef _DEBUG + PROCESS_MEMORY_COUNTERS_EX memoryCounters; + memoryCounters.cb = sizeof(PROCESS_MEMORY_COUNTERS_EX); + GetProcessMemoryInfo(GetCurrentProcess(), (PPROCESS_MEMORY_COUNTERS) &memoryCounters, sizeof(PROCESS_MEMORY_COUNTERS_EX)); + return memoryCounters.PrivateUsage; +#else + throw "Cannot call this function in a non-debug build!"; +#endif //_DEBUG +} diff --git a/src/Global.h b/src/Global.h index 3364addf..4e28e1c2 100644 --- a/src/Global.h +++ b/src/Global.h @@ -55,6 +55,9 @@ const QString &lamexp_temp_folder(void); //Auxiliary functions bool lamexp_clean_folder(const QString folderPath); +//Debug-only functions +SIZE_T lamexp_dbg_private_bytes(void); + //Helper macros #define LAMEXP_DELETE(PTR) if(PTR) { delete PTR; PTR = NULL; } #define LAMEXP_CLOSE(HANDLE) if(HANDLE != NULL && HANDLE != INVALID_HANDLE_VALUE) { CloseHandle(HANDLE); HANDLE = NULL; } @@ -73,3 +76,18 @@ bool lamexp_clean_folder(const QString folderPath); FatalAppExit(0, L"Not a debug build. Please unload debugger and try again!"); \ TerminateProcess(GetCurrentProcess, -1); } #endif + +//Memory check +#if defined(_DEBUG) +#define LAMEXP_MEMORY_CHECK(CMD) \ +{ \ + SIZE_T _privateBytesBefore = lamexp_dbg_private_bytes(); \ + CMD; \ + SIZE_T _privateBytesLeak = (lamexp_dbg_private_bytes() - _privateBytesBefore) / 1024; \ + if(_privateBytesLeak > 10) { \ + qWarning("Memory leak: Lost %u KiloBytes.", _privateBytesLeak); \ + } \ +} +#else +#define LAMEXP_MEMORY_CHECK(CMD) CMD +#endif diff --git a/src/Main.cpp b/src/Main.cpp index 847c5a6e..c7b64f94 100644 --- a/src/Main.cpp +++ b/src/Main.cpp @@ -142,8 +142,9 @@ int main(int argc, char* argv[]) { try { + int iResult; qInstallMsgHandler(lamexp_message_handler); - int iResult = lamexp_main(argc, argv); + LAMEXP_MEMORY_CHECK(iResult = lamexp_main(argc, argv)); lamexp_finalization(); return iResult; }