Page MenuHomeWildfire Games

Fix MapReader / LoadThunks memory leak
ClosedPublic

Authored by elexis on Sep 27 2019, 1:13 PM.

Details

Summary

When running valgrind, clicking on start match, then ending the program after frames of the loading screen were rendered, I get this memory leak:

==160587== 24 bytes in 1 blocks are definitely lost in loss record 215 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x30EC8E: RegMemFun<CSimulation2> (LoaderThunks.h:70)
	==160587==    by 0x30EC8E: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:227)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587==    by 0x4847809: ???
	==160587==    by 0x4C74A5A: EnterBaseline(JSContext*, js::jit::EnterJitData&) (BaselineJIT.cpp:145)
	==160587== 
	==160587== 24 bytes in 1 blocks are definitely lost in loss record 216 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x3B39AF: RegMemFun<CGameView> (LoaderThunks.h:70)
	==160587==    by 0x3B39AF: CGameView::RegisterInit() (GameView.cpp:465)
	==160587==    by 0x30ECC8: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:235)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587==    by 0x4847809: ???
	==160587== 
	==160587== 24 bytes in 1 blocks are definitely lost in loss record 217 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x3B3A63: RegMemFun<CTerrainTextureManager> (LoaderThunks.h:70)
	==160587==    by 0x3B3A63: CGameView::RegisterInit() (GameView.cpp:467)
	==160587==    by 0x30ECC8: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:235)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587==    by 0x4847809: ???
	==160587== 
	==160587== 24 bytes in 1 blocks are definitely lost in loss record 218 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x3BBCC5: CMapReader::LoadMap(Path const&, JSRuntime*, JS::Handle<JS::Value>, CTerrain*, WaterManager*, SkyManager*, CLightEnv*, CGameView*, CCinemaManager*, CTriggerManager*, CPostprocManager*, CSimulation2*, CSimContext const*, int, bool) (MapReader.cpp:0)
	==160587==    by 0x37519C: CWorld::RegisterInit(CStrW const&, JSRuntime*, JS::Handle<JS::Value>, int) (World.cpp:78)
	==160587==    by 0x30EF3B: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:255)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587== 
	==160587== 24 bytes in 1 blocks are definitely lost in loss record 219 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x3BBD2E: RegMemFun<CMapReader> (LoaderThunks.h:70)
	==160587==    by 0x3BBD2E: CMapReader::LoadMap(Path const&, JSRuntime*, JS::Handle<JS::Value>, CTerrain*, WaterManager*, SkyManager*, CLightEnv*, CGameView*, CCinemaManager*, CTriggerManager*, CPostprocManager*, CSimulation2*, CSimContext const*, int, bool) (MapReader.cpp:122)
	==160587==    by 0x37519C: CWorld::RegisterInit(CStrW const&, JSRuntime*, JS::Handle<JS::Value>, int) (World.cpp:78)
	==160587==    by 0x30EF3B: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:255)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587== 
	==160587== 24 bytes in 1 blocks are definitely lost in loss record 220 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x3BBD70: RegMemFun<CMapReader> (LoaderThunks.h:70)
	==160587==    by 0x3BBD70: CMapReader::LoadMap(Path const&, JSRuntime*, JS::Handle<JS::Value>, CTerrain*, WaterManager*, SkyManager*, CLightEnv*, CGameView*, CCinemaManager*, CTriggerManager*, CPostprocManager*, CSimulation2*, CSimContext const*, int, bool) (MapReader.cpp:126)
	==160587==    by 0x37519C: CWorld::RegisterInit(CStrW const&, JSRuntime*, JS::Handle<JS::Value>, int) (World.cpp:78)
	==160587==    by 0x30EF3B: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:255)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587== 
	==160587== 24 bytes in 1 blocks are definitely lost in loss record 221 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x3BBDA9: RegMemFun<CMapReader> (LoaderThunks.h:70)
	==160587==    by 0x3BBDA9: CMapReader::LoadMap(Path const&, JSRuntime*, JS::Handle<JS::Value>, CTerrain*, WaterManager*, SkyManager*, CLightEnv*, CGameView*, CCinemaManager*, CTriggerManager*, CPostprocManager*, CSimulation2*, CSimContext const*, int, bool) (MapReader.cpp:129)
	==160587==    by 0x37519C: CWorld::RegisterInit(CStrW const&, JSRuntime*, JS::Handle<JS::Value>, int) (World.cpp:78)
	==160587==    by 0x30EF3B: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:255)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587== 
	==160587== 24 bytes in 1 blocks are definitely lost in loss record 222 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x3BBDE5: RegMemFun<CMapReader> (LoaderThunks.h:70)
	==160587==    by 0x3BBDE5: CMapReader::LoadMap(Path const&, JSRuntime*, JS::Handle<JS::Value>, CTerrain*, WaterManager*, SkyManager*, CLightEnv*, CGameView*, CCinemaManager*, CTriggerManager*, CPostprocManager*, CSimulation2*, CSimContext const*, int, bool) (MapReader.cpp:132)
	==160587==    by 0x37519C: CWorld::RegisterInit(CStrW const&, JSRuntime*, JS::Handle<JS::Value>, int) (World.cpp:78)
	==160587==    by 0x30EF3B: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:255)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587== 
	==160587== 24 bytes in 1 blocks are definitely lost in loss record 223 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x3BBE1A: RegMemFun<CMapReader> (LoaderThunks.h:70)
	==160587==    by 0x3BBE1A: CMapReader::LoadMap(Path const&, JSRuntime*, JS::Handle<JS::Value>, CTerrain*, WaterManager*, SkyManager*, CLightEnv*, CGameView*, CCinemaManager*, CTriggerManager*, CPostprocManager*, CSimulation2*, CSimContext const*, int, bool) (MapReader.cpp:135)
	==160587==    by 0x37519C: CWorld::RegisterInit(CStrW const&, JSRuntime*, JS::Handle<JS::Value>, int) (World.cpp:78)
	==160587==    by 0x30EF3B: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:255)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587== 
	==160587== 24 bytes in 1 blocks are definitely lost in loss record 224 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x3BBE4F: RegMemFun<CMapReader> (LoaderThunks.h:70)
	==160587==    by 0x3BBE4F: CMapReader::LoadMap(Path const&, JSRuntime*, JS::Handle<JS::Value>, CTerrain*, WaterManager*, SkyManager*, CLightEnv*, CGameView*, CCinemaManager*, CTriggerManager*, CPostprocManager*, CSimulation2*, CSimContext const*, int, bool) (MapReader.cpp:138)
	==160587==    by 0x37519C: CWorld::RegisterInit(CStrW const&, JSRuntime*, JS::Handle<JS::Value>, int) (World.cpp:78)
	==160587==    by 0x30EF3B: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:255)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587== 
	==160587== 24 bytes in 1 blocks are definitely lost in loss record 225 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x3BBE84: RegMemFun<CMapReader> (LoaderThunks.h:70)
	==160587==    by 0x3BBE84: CMapReader::LoadMap(Path const&, JSRuntime*, JS::Handle<JS::Value>, CTerrain*, WaterManager*, SkyManager*, CLightEnv*, CGameView*, CCinemaManager*, CTriggerManager*, CPostprocManager*, CSimulation2*, CSimContext const*, int, bool) (MapReader.cpp:141)
	==160587==    by 0x37519C: CWorld::RegisterInit(CStrW const&, JSRuntime*, JS::Handle<JS::Value>, int) (World.cpp:78)
	==160587==    by 0x30EF3B: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:255)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587== 
	==160587== 24 bytes in 1 blocks are definitely lost in loss record 226 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x3751AA: RegMemFun<CWorld> (LoaderThunks.h:70)
	==160587==    by 0x3751AA: CWorld::RegisterInit(CStrW const&, JSRuntime*, JS::Handle<JS::Value>, int) (World.cpp:86)
	==160587==    by 0x30EF3B: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:255)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587==    by 0x4847809: ???
	==160587== 
	==160587== 24 bytes in 1 blocks are definitely lost in loss record 227 of 3,206
	==160587==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
	==160587==    by 0x30F00B: RegMemFun<WaterManager> (LoaderThunks.h:70)
	==160587==    by 0x30F00B: CGame::RegisterInit(JS::Handle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:258)
	==160587==    by 0x30EB3F: CGame::StartGame(JS::MutableHandle<JS::Value>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (Game.cpp:373)
	==160587==    by 0x601CEE: JSI_Game::StartGame(ScriptInterface::CxPrivate*, JS::Handle<JS::Value>, int) (JSInterface_Game.cpp:58)
	==160587==    by 0x602C18: call<void (ScriptInterface::CxPrivate *, JS::Handle<JS::Value>, int), JS::Handle<JS::Value>, int> (NativeWrapperDefns.h:85)
	==160587==    by 0x602C18: bool ScriptInterface::call<void, JS::Handle<JS::Value>, int, &JSI_Game::StartGame>(JSContext*, unsigned int, JS::Value*) (NativeWrapperDefns.h:124)
	==160587==    by 0x50969E7: CallJSNative (jscntxtinlines.h:235)
	==160587==    by 0x50969E7: js::Invoke(JSContext*, JS::CallArgs const&, js::MaybeConstruct) (Interpreter.cpp:444)
	==160587==    by 0x50972FB: js::Invoke(JSContext*, JS::Value const&, JS::Value const&, unsigned int, JS::Value const*, JS::MutableHandle<JS::Value>) (Interpreter.cpp:496)
	==160587==    by 0x4CA0F96: js::jit::DoCallFallback(JSContext*, js::jit::BaselineFrame*, js::jit::ICCall_Fallback*, unsigned int, JS::Value*, JS::MutableHandle<JS::Value>) (BaselineIC.cpp:6162)
	==160587==    by 0x484F0D9: ???
	==160587==    by 0x2E5103E7: ???
	==160587==    by 0x4847809: ???
	==160587==    by 0x4C74A5A: EnterBaseline(JSContext*, js::jit::EnterJitData&) (BaselineJIT.cpp:145)

refs P178

It seems the param thing is created locally, then received without taking over ownership (i.e. later on deleting).

Test Plan

See above how to reproduce.
Run with the patch applied to see that the filename is gone from the valgrind log (except for a texture leak which occurs elsewhere).
Notice that there was a delete upon ldr_was_interrupted but not in the general case!?
Check the revision history as to whodunnit.
Consider the alternative to a shared_ptr, which would be implementing an interface, similar to IGUISetting and CGUISetting<T>.
But this would still mean its complicated to decide when to delete, whereas with the shared_ptr we have less possibility to do it wrongly.

Keep https://trac.wildfiregames.com/wiki/Loading in sync (no diff).

Diff Detail

Repository
rP 0 A.D. Public Repository
Lint
Automatic diff as part of commit; lint not applicable.
Unit
Automatic diff as part of commit; unit tests not applicable.

Event Timeline

elexis created this revision.Sep 27 2019, 1:13 PM

Build failure - The Moirai have given mortals hearts that can endure.

Link to build: https://jenkins.wildfiregames.com/job/vs2015-differential/326/display/redirect

Build failure - The Moirai have given mortals hearts that can endure.

Link to build: https://jenkins.wildfiregames.com/job/docker-differential/841/display/redirect

elexis added a comment.EditedSep 28 2019, 4:05 PM

2005-03/2005-03-19-QuakeNet-#wfg-Meeting-0080.log:
16:23 <janwas> i'll need a day or two to gin up the loader (and probably won't get far this evening), so we'd need the current code to remain intact before the switch

March 20th 2005 rP2027 was committed

March 21st 2005 rP2032 added documentation

March 22nd 2005 rP2038 was committed

May 3rd 2005 rP2232 introduced the leak consciously?

2005-05/2005-05-07-QuakeNet-#wfg-Meeting-adjourned.log:
17:01 <janwas> hm, one thing from me: i ginned up some docs in ps/Loader.h (can't add to wiki or TDD obviously). any comments?
...
17:10 <Ykkrosh> Did you see the response I posted to the forums before they exploded? The bit where it allocates a CMapReader in one place, then destroys it a couple of function calls away in a different file, executed much later, is rather messy :-(
17:10 <janwas> Ykkrosh: hm, i only now realize we need to register a second "dtor" function for what i'm thinking of
17:10 <janwas> after a failure, the loader could call all dtors associated with the tasks that have started
...
17:14 <janwas> say the map has been loaded successfully, and then the actor subsystem decides to call a halt
17:14 <janwas> what happens with the map loaded into memory?
17:14 <janwas> one simple solution would be to leave it until the next load, which then clears out any previous state
...
17:25 <janwas> Ykkrosh: that's exactly the poor design you correctly pointed out - it sucks that it's allocated in one spot and then freed in another (it does delete this IIRC - ugh)
...
17:30 <janwas> Ykkrosh: i thought we'd been through the UpdateProgress() thing ;) anything that fits into that one function has the disadvantages outlined in the Loader.h rationale dox
17:30 <Ykkrosh> Who's going to test that all the possible failure routes actually work? :-)
...
17:37 <janwas> as to calling dtors, what did ya'll think of having each task do its own cleanup before the next load?
...
18:46 <Ykkrosh> I suppose the "Somebody Else's Problem" method is occasionally useful ;-)

The comments surprise me with supposed C compatibility, but then only in the interface and not in the cpp implementation.
In the context of that time it might be more understandable than in 2019, since JS was new and the alternative was Ferite C language was on the table, since C++3 was either not out yet or very new (possibly not supported by all compilers), so C compatibility was more achievable than now.

2006/2006-08/2006-08-12-QuakeNet-#wfg-Meeting-adjourned.log
17:13 <janwas> (seems like a stupid and needless break of compat with C)
17:14 <janwas> options:
17:14 <janwas> 1) revert to using math.h; 2) change code to use std::isfinite and also add a cmath.h - equivalent for our #defines 3) try to prevent gcc from doing #undef
17:15 <janwas> 1 sounds easiest. heck, who writes std::cos? :P
17:15 <Ykkrosh> (I guess the idea is that's not needless because you might want to have functions called isfinite in other namespaces, which is the whole point of having C++ with namespaces instead of just being exactly like C :-) )

2004/2004-02/2004-02-28-QuakeNet-#wfg-Meeting-0026.log:
<janwas> i am beginning to see the light, and have started writing some C++ code, but i still often think like a C coder

2006/2006-09/2006-09-23-QuakeNet-#wfg-Meeting-0149.log:
18:19 <janwas> ya know what? since i've broken all other projects anyway with the error code change, we may as well add an additional C++ layer on top of C api, eh?

source/ps/Loader.cpp
71 ↗(On Diff #9976)

// - the module interface must work in C, so we get/set as wchar_t*.

source/ps/LoaderThunks.h
24 ↗(On Diff #9976)

we don't want to break C compat in the Loader.h interface

elexis updated this revision to Diff 10008.Sep 29 2019, 12:32 PM

shared_ptr for MemFun1Thunk too, remove C compatibility comments, bump years.

Successful build - Chance fights ever on the side of the prudent.

Link to build: https://jenkins.wildfiregames.com/job/vs2015-differential/352/display/redirect

Successful build - Chance fights ever on the side of the prudent.

Linter detected issues:
Executing section Source...

source/ps/LoaderThunks.h
|  38| template<class·T>·struct·MemFun_t
|    | [MAJOR] CPPCheckBear (syntaxError):
|    | Code 'template<...' is invalid C code. Use --std or --language to configure the language.
Executing section JS...
Executing section cli...

Link to build: https://jenkins.wildfiregames.com/job/docker-differential/868/display/redirect

After applying the patch, I still get this leak:

==1954645== 65,560 (24 direct, 65,536 indirect) bytes in 1 blocks are definitely lost in loss record 3,198 of 3,208
==1954645==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
==1954645==    by 0x46874E: allocate (new_allocator.h:114)
==1954645==    by 0x46874E: allocate (alloc_traits.h:444)
==1954645==    by 0x46874E: __allocate_guarded<std::allocator<std::_Sp_counted_deleter<unsigned char *, AlignedDeleter, std::allocator<void>, __gnu_cxx::_S_atomic> > > (allocated_ptr.h:97)
==1954645==    by 0x46874E: __shared_count<unsigned char *, AlignedDeleter, std::allocator<void>, void> (shared_ptr_base.h:658)
==1954645==    by 0x46874E: __shared_count<unsigned char *, AlignedDeleter, void> (shared_ptr_base.h:647)
==1954645==    by 0x46874E: __shared_ptr<unsigned char, AlignedDeleter, void> (shared_ptr_base.h:1134)
==1954645==    by 0x46874E: reset<unsigned char, AlignedDeleter> (shared_ptr_base.h:1301)
==1954645==    by 0x46874E: AllocateAligned<unsigned char> (shared_ptr.h:71)
==1954645==    by 0x46874E: CTerrainTextureEntry::LoadAlphaMaps(Path&) (TerrainTextureEntry.cpp:290)
==1954645==    by 0x4674E1: CTerrainTextureEntry::CTerrainTextureEntry(std::shared_ptr<CTerrainProperties>, Path const&) (TerrainTextureEntry.cpp:147)
==1954645==    by 0x3F6C3B: CTerrainTextureManager::AddTexture(std::shared_ptr<CTerrainProperties> const&, Path const&) (TerrainTextureManager.cpp:87)
==1954645==    by 0x3F7318: AddTextureCallback(Path const&, CFileInfo const&, unsigned long) (TerrainTextureManager.cpp:123)
==1954645==    by 0x565C72: vfs::ForEachFile(std::shared_ptr<IVFS> const&, Path const&, long (*)(Path const&, CFileInfo const&, unsigned long), unsigned long, wchar_t const*, unsigned long, long (*)(Path const&, unsigned long), unsigned long) (vfs_util.cpp:84)
==1954645==    by 0x3F7093: CTerrainTextureManager::LoadTerrainTextures() (TerrainTextureManager.cpp:131)
==1954645==    by 0x3B8570: int MemFunThunk<CTerrainTextureManager>(std::shared_ptr<void>, double) (LoaderThunks.h:51)
==1954645==    by 0x3364D0: LDR_ProgressiveLoad(double, wchar_t*, unsigned long, int*) (Loader.cpp:227)
==1954645==    by 0x164F55: ProgressiveLoad (main.cpp:267)
==1954645==    by 0x164F55: Frame (main.cpp:363)
==1954645==    by 0x164F55: RunGameOrAtlas(int, char const**) (main.cpp:638)
==1954645==    by 0x162D64: main (main.cpp:684)
==1954645== 
==1954645== 65,560 (24 direct, 65,536 indirect) bytes in 1 blocks are definitely lost in loss record 3,199 of 3,208
==1954645==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
==1954645==    by 0x41D59F: allocate (new_allocator.h:114)
==1954645==    by 0x41D59F: allocate (alloc_traits.h:444)
==1954645==    by 0x41D59F: __allocate_guarded<std::allocator<std::_Sp_counted_deleter<unsigned char *, AlignedDeleter, std::allocator<void>, __gnu_cxx::_S_atomic> > > (allocated_ptr.h:97)
==1954645==    by 0x41D59F: __shared_count<unsigned char *, AlignedDeleter, std::allocator<void>, void> (shared_ptr_base.h:658)
==1954645==    by 0x41D59F: __shared_count<unsigned char *, AlignedDeleter, void> (shared_ptr_base.h:647)
==1954645==    by 0x41D59F: __shared_ptr<unsigned char, AlignedDeleter, void> (shared_ptr_base.h:1134)
==1954645==    by 0x41D59F: reset<unsigned char, AlignedDeleter> (shared_ptr_base.h:1301)
==1954645==    by 0x41D59F: AllocateAligned<unsigned char> (shared_ptr.h:71)
==1954645==    by 0x41D59F: CRenderer::LoadAlphaMaps() (Renderer.cpp:1831)
==1954645==    by 0x3B85C0: int MemFunThunk<CRenderer>(std::shared_ptr<void>, double) (LoaderThunks.h:51)
==1954645==    by 0x3364D0: LDR_ProgressiveLoad(double, wchar_t*, unsigned long, int*) (Loader.cpp:227)
==1954645==    by 0x164F55: ProgressiveLoad (main.cpp:267)
==1954645==    by 0x164F55: Frame (main.cpp:363)
==1954645==    by 0x164F55: RunGameOrAtlas(int, char const**) (main.cpp:638)
==1954645==    by 0x162D64: main (main.cpp:684)

Using static_pointer_cast also doesn't save the mentioned leak (but it uses more voodoo, so I don't upload it as a diff).

shared_ptr<MemFun_t<T> > mf = std::static_pointer_cast<MemFun_t<T> >(param);
shared_ptr<MemFun1_t<T, Arg> > mf = std::static_pointer_cast<MemFun1_t<T, Arg> >(param);

Here the complete valgrind log if the patch is not applied:

We can see that those are distinct types of leaks. They are present already, so they're not regressions in this patch.

Notice that we get the same leak in other places, so it really seems like this LoaderThunk.h is innocent as to the last reported leak.

==2044518== 2,829,264 bytes in 2 blocks are possibly lost in loss record 3,205 of 3,208
==2044518==    at 0x483AEC3: memalign (vg_replace_malloc.c:898)
==2044518==    by 0x483AFF0: posix_memalign (vg_replace_malloc.c:1062)
==2044518==    by 0x57E300: rtl_AllocateAligned(unsigned long, unsigned long) (gcc.cpp:39)
==2044518==    by 0x55EA03: AllocateAligned<unsigned char> (shared_ptr.h:68)
==2044518==    by 0x55EA03: VFS::LoadFile(Path const&, std::shared_ptr<unsigned char>&, unsigned long&) (vfs.cpp:188)
==2044518==    by 0x56FD35: OglTex_reload(OglTex*, std::shared_ptr<IVFS> const&, Path const&, long) (ogl_tex.cpp:475)
==2044518==    by 0x5708D8: call_init_and_reload (h_mgr.cpp:446)
==2044518==    by 0x5708D8: alloc_new_handle (h_mgr.cpp:489)
==2044518==    by 0x5708D8: h_alloc(H_VTbl*, std::shared_ptr<IVFS> const&, Path const&, unsigned long, ...) (h_mgr.cpp:526)
==2044518==    by 0x56E16E: ogl_tex_load(std::shared_ptr<IVFS> const&, Path const&, unsigned long) (ogl_tex.cpp:548)
==2044518==    by 0x400D7B: CTextureManagerImpl::LoadTexture(std::shared_ptr<CTexture> const&, Path const&) (TextureManager.cpp:188)
==2044518==    by 0x3FE566: CTextureManagerImpl::TryLoadingCached(std::shared_ptr<CTexture> const&) (TextureManager.cpp:276)
==2044518==    by 0x3FD836: CTexture::TryLoad() (TextureManager.cpp:572)
==2044518==    by 0x3FD78A: CTexture::GetHandle() (TextureManager.cpp:559)
==2044518==    by 0x3E8C55: CShaderProgram::BindTexture(CStrIntern, std::shared_ptr<CTexture>) (ShaderProgram.cpp:700)
==2044518== 
==2044518== 4,585,672 (984 direct, 4,584,688 indirect) bytes in 41 blocks are definitely lost in loss record 3,206 of 3,208
==2044518==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
==2044518==    by 0x55EA15: allocate (new_allocator.h:114)
==2044518==    by 0x55EA15: allocate (alloc_traits.h:444)
==2044518==    by 0x55EA15: __allocate_guarded<std::allocator<std::_Sp_counted_deleter<unsigned char *, AlignedDeleter, std::allocator<void>, __gnu_cxx::_S_atomic> > > (allocated_ptr.h:97)
==2044518==    by 0x55EA15: __shared_count<unsigned char *, AlignedDeleter, std::allocator<void>, void> (shared_ptr_base.h:658)
==2044518==    by 0x55EA15: __shared_count<unsigned char *, AlignedDeleter, void> (shared_ptr_base.h:647)
==2044518==    by 0x55EA15: __shared_ptr<unsigned char, AlignedDeleter, void> (shared_ptr_base.h:1134)
==2044518==    by 0x55EA15: reset<unsigned char, AlignedDeleter> (shared_ptr_base.h:1301)
==2044518==    by 0x55EA15: AllocateAligned<unsigned char> (shared_ptr.h:71)
==2044518==    by 0x55EA15: VFS::LoadFile(Path const&, std::shared_ptr<unsigned char>&, unsigned long&) (vfs.cpp:188)
==2044518==    by 0x56FD35: OglTex_reload(OglTex*, std::shared_ptr<IVFS> const&, Path const&, long) (ogl_tex.cpp:475)
==2044518==    by 0x5708D8: call_init_and_reload (h_mgr.cpp:446)
==2044518==    by 0x5708D8: alloc_new_handle (h_mgr.cpp:489)
==2044518==    by 0x5708D8: h_alloc(H_VTbl*, std::shared_ptr<IVFS> const&, Path const&, unsigned long, ...) (h_mgr.cpp:526)
==2044518==    by 0x56E16E: ogl_tex_load(std::shared_ptr<IVFS> const&, Path const&, unsigned long) (ogl_tex.cpp:548)
==2044518==    by 0x400D7B: CTextureManagerImpl::LoadTexture(std::shared_ptr<CTexture> const&, Path const&) (TextureManager.cpp:188)
==2044518==    by 0x3FE566: CTextureManagerImpl::TryLoadingCached(std::shared_ptr<CTexture> const&) (TextureManager.cpp:276)
==2044518==    by 0x3FD836: CTexture::TryLoad() (TextureManager.cpp:572)
==2044518==    by 0x3FD78A: CTexture::GetHandle() (TextureManager.cpp:559)
==2044518==    by 0x3E8C55: CShaderProgram::BindTexture(CStrIntern, std::shared_ptr<CTexture>) (ShaderProgram.cpp:700)
==2044518==    by 0x515BE7: GUIRenderer::Draw(GUIRenderer::DrawCalls&, float) (GUIRenderer.cpp:373)
==2044518==    by 0x4F47A4: CGUISpriteInstance::Draw(CGUI&, CRect const&, int, std::map<CStr8, CGUISprite const*, std::less<CStr8>, std::allocator<std::pair<CStr8 const, CGUISprite const*> > >&, float) const (CGUISprite.cpp:41)
==2044518== 
==2044518== 14,182,136 (192 direct, 14,181,944 indirect) bytes in 8 blocks are definitely lost in loss record 3,207 of 3,208
==2044518==    at 0x4838DEF: operator new(unsigned long) (vg_replace_malloc.c:334)
==2044518==    by 0x55EA15: allocate (new_allocator.h:114)
==2044518==    by 0x55EA15: allocate (alloc_traits.h:444)
==2044518==    by 0x55EA15: __allocate_guarded<std::allocator<std::_Sp_counted_deleter<unsigned char *, AlignedDeleter, std::allocator<void>, __gnu_cxx::_S_atomic> > > (allocated_ptr.h:97)
==2044518==    by 0x55EA15: __shared_count<unsigned char *, AlignedDeleter, std::allocator<void>, void> (shared_ptr_base.h:658)
==2044518==    by 0x55EA15: __shared_count<unsigned char *, AlignedDeleter, void> (shared_ptr_base.h:647)
==2044518==    by 0x55EA15: __shared_ptr<unsigned char, AlignedDeleter, void> (shared_ptr_base.h:1134)
==2044518==    by 0x55EA15: reset<unsigned char, AlignedDeleter> (shared_ptr_base.h:1301)
==2044518==    by 0x55EA15: AllocateAligned<unsigned char> (shared_ptr.h:71)
==2044518==    by 0x55EA15: VFS::LoadFile(Path const&, std::shared_ptr<unsigned char>&, unsigned long&) (vfs.cpp:188)
==2044518==    by 0x56FD35: OglTex_reload(OglTex*, std::shared_ptr<IVFS> const&, Path const&, long) (ogl_tex.cpp:475)
==2044518==    by 0x5708D8: call_init_and_reload (h_mgr.cpp:446)
==2044518==    by 0x5708D8: alloc_new_handle (h_mgr.cpp:489)
==2044518==    by 0x5708D8: h_alloc(H_VTbl*, std::shared_ptr<IVFS> const&, Path const&, unsigned long, ...) (h_mgr.cpp:526)
==2044518==    by 0x56E16E: ogl_tex_load(std::shared_ptr<IVFS> const&, Path const&, unsigned long) (ogl_tex.cpp:548)
==2044518==    by 0x400D7B: CTextureManagerImpl::LoadTexture(std::shared_ptr<CTexture> const&, Path const&) (TextureManager.cpp:188)
==2044518==    by 0x3FE566: CTextureManagerImpl::TryLoadingCached(std::shared_ptr<CTexture> const&) (TextureManager.cpp:276)
==2044518==    by 0x3FD836: CTexture::TryLoad() (TextureManager.cpp:572)
==2044518==    by 0x3FD78A: CTexture::GetHandle() (TextureManager.cpp:559)
==2044518==    by 0x3E8C55: CShaderProgram::BindTexture(CStrIntern, std::shared_ptr<CTexture>) (ShaderProgram.cpp:700)
==2044518==    by 0x3FBF2C: CTextRenderer::Render() (TextRenderer.cpp:251)
==2044518==    by 0x54D0D1: CGUIText::Draw(CGUI&, CGUIColor const&, CPos const&, float, CRect const&) const (CGUIText.cpp:462)

So I must conclude that this diff fixes this one leak without adding regressions and also solves the problem that one doesnt have to keep track of conditional ownership in different classes, while making Loader.h use C++ syntax (notice that LoaderThunks.h already uses template class cpp syntax).

source/ps/LoaderThunks.h
93 ↗(On Diff #10008)

(just removing this condition leads to a doublefree btw)

With the patch applied:


This revision was not accepted when it landed; it landed in state Needs Review.Sep 30 2019, 10:49 AM
This revision was automatically updated to reflect the committed changes.
elexis edited the test plan for this revision. (Show Details)Sep 30 2019, 10:51 AM