Skip to content

Commit

Permalink
Merge branch 'unloadedcontainers' into 'master'
Browse files Browse the repository at this point in the history
Fix Lua memory usage

See merge request OpenMW/openmw!4363
  • Loading branch information
petrmikheev committed Oct 15, 2024
2 parents 34e32b7 + 68ebefc commit bac0018
Show file tree
Hide file tree
Showing 10 changed files with 424 additions and 96 deletions.
59 changes: 59 additions & 0 deletions apps/components_tests/lua/test_scriptscontainer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
#include <components/lua/asyncpackage.hpp>
#include <components/lua/luastate.hpp>
#include <components/lua/scriptscontainer.hpp>
#include <components/lua/scripttracker.hpp>

#include <components/testing/util.hpp>

Expand Down Expand Up @@ -135,6 +136,31 @@ return {
end,
},
}
)X");

constexpr VFS::Path::NormalizedView unloadPath("unload.lua");

VFSTestFile unloadScript(R"X(
x = 0
y = 0
z = 0
return {
engineHandlers = {
onSave = function(state)
print('saving', x, y, z)
return {x = x, y = y}
end,
onLoad = function(state)
x, y = state.x, state.y
print('loaded', x, y, z)
end
},
eventHandlers = {
Set = function(eventData)
x, y, z = eventData.x, eventData.y, eventData.z
end
}
}
)X");

struct LuaScriptsContainerTest : Test
Expand All @@ -151,6 +177,7 @@ return {
{ testInterfacePath, &interfaceScript },
{ overrideInterfacePath, &overrideInterfaceScript },
{ useInterfacePath, &useInterfaceScript },
{ unloadPath, &unloadScript },
});

LuaUtil::ScriptsConfiguration mCfg;
Expand All @@ -171,6 +198,7 @@ CUSTOM, NPC: loadSave2.lua
CUSTOM, PLAYER: testInterface.lua
CUSTOM, PLAYER: overrideInterface.lua
CUSTOM, PLAYER: useInterface.lua
CUSTOM: unload.lua
)X");
mCfg.init(std::move(cfg));
}
Expand Down Expand Up @@ -511,4 +539,35 @@ CUSTOM, PLAYER: useInterface.lua
Log::sMinDebugLevel = level;
}

TEST_F(LuaScriptsContainerTest, Unload)
{
LuaUtil::ScriptTracker tracker;
LuaUtil::ScriptsContainer scripts1(&mLua, "Test", &tracker, false);

EXPECT_TRUE(scripts1.addCustomScript(*mCfg.findId(unloadPath)));
EXPECT_EQ(tracker.size(), 1);

mLua.protectedCall([&](LuaUtil::LuaView& lua) {
scripts1.receiveEvent("Set", LuaUtil::serialize(lua.sol().create_table_with("x", 3, "y", 2, "z", 1)));
testing::internal::CaptureStdout();
for (int i = 0; i < 600; ++i)
tracker.unloadInactiveScripts(lua);
EXPECT_EQ(tracker.size(), 0);
scripts1.receiveEvent("Set", LuaUtil::serialize(lua.sol().create_table_with("x", 10, "y", 20, "z", 30)));
EXPECT_EQ(internal::GetCapturedStdout(),
"Test[unload.lua]:\tsaving\t3\t2\t1\n"
"Test[unload.lua]:\tloaded\t3\t2\t0\n");
});
EXPECT_EQ(tracker.size(), 1);
ESM::LuaScripts data;
scripts1.save(data);
EXPECT_EQ(tracker.size(), 1);
mLua.protectedCall([&](LuaUtil::LuaView& lua) {
for (int i = 0; i < 600; ++i)
tracker.unloadInactiveScripts(lua);
});
EXPECT_EQ(tracker.size(), 0);
scripts1.load(data);
EXPECT_EQ(tracker.size(), 0);
}
}
4 changes: 2 additions & 2 deletions apps/openmw/mwlua/localscripts.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -224,8 +224,8 @@ namespace MWLua
};
}

LocalScripts::LocalScripts(LuaUtil::LuaState* lua, const LObject& obj)
: LuaUtil::ScriptsContainer(lua, "L" + obj.id().toString())
LocalScripts::LocalScripts(LuaUtil::LuaState* lua, const LObject& obj, LuaUtil::ScriptTracker* tracker)
: LuaUtil::ScriptsContainer(lua, "L" + obj.id().toString(), tracker, false)
, mData(obj)
{
lua->protectedCall(
Expand Down
3 changes: 2 additions & 1 deletion apps/openmw/mwlua/localscripts.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -62,12 +62,13 @@ namespace MWLua
{
public:
static void initializeSelfPackage(const Context&);
LocalScripts(LuaUtil::LuaState* lua, const LObject& obj);
LocalScripts(LuaUtil::LuaState* lua, const LObject& obj, LuaUtil::ScriptTracker* tracker = nullptr);

MWBase::LuaManager::ActorControls* getActorControls() { return &mData.mControls; }
const MWWorld::Ptr& getPtrOrEmpty() const { return mData.ptrOrEmpty(); }

void setActive(bool active);
bool isActive() const override { return mData.mIsActive; }
void onConsume(const LObject& consumable) { callEngineHandlers(mOnConsumeHandlers, consumable); }
void onActivated(const LObject& actor) { callEngineHandlers(mOnActivatedHandlers, actor); }
void onTeleported() { callEngineHandlers(mOnTeleportedHandlers); }
Expand Down
4 changes: 3 additions & 1 deletion apps/openmw/mwlua/luamanagerimp.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -210,6 +210,8 @@ namespace MWLua
scripts->update(frameDuration);
mGlobalScripts.update(frameDuration);
}

mLua.protectedCall([&](LuaUtil::LuaView& lua) { mScriptTracker.unloadInactiveScripts(lua); });
}

void LuaManager::objectTeleported(const MWWorld::Ptr& ptr)
Expand Down Expand Up @@ -560,7 +562,7 @@ namespace MWLua
}
else
{
scripts = std::make_shared<LocalScripts>(&mLua, LObject(getId(ptr)));
scripts = std::make_shared<LocalScripts>(&mLua, LObject(getId(ptr)), &mScriptTracker);
if (!autoStartConf.has_value())
autoStartConf = mConfiguration.getLocalConf(type, ptr.getCellRef().getRefId(), getId(ptr));
scripts->setAutoStartConf(std::move(*autoStartConf));
Expand Down
3 changes: 3 additions & 0 deletions apps/openmw/mwlua/luamanagerimp.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@

#include <components/lua/inputactions.hpp>
#include <components/lua/luastate.hpp>
#include <components/lua/scripttracker.hpp>
#include <components/lua/storage.hpp>
#include <components/lua_ui/resources.hpp>
#include <components/misc/color.hpp>
Expand Down Expand Up @@ -234,6 +235,8 @@ namespace MWLua

LuaUtil::InputAction::Registry mInputActions;
LuaUtil::InputTrigger::Registry mInputTriggers;

LuaUtil::ScriptTracker mScriptTracker;
};

}
Expand Down
2 changes: 1 addition & 1 deletion components/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ list(APPEND COMPONENT_FILES "${OpenMW_BINARY_DIR}/${OSG_PLUGIN_CHECKER_CPP_FILE}

add_component_dir (lua
luastate scriptscontainer asyncpackage utilpackage serialization configuration l10n storage utf8
shapes/box inputactions yamlloader
shapes/box inputactions yamlloader scripttracker
)

add_component_dir (l10n
Expand Down
Loading

0 comments on commit bac0018

Please sign in to comment.