mirror of
https://github.com/minetest/minetest.git
synced 2024-08-19 21:14:15 +02:00
Optimize pushing collision data for entity on_step
Since this is fixed overhead for every entity, this is important to optimize. This optimizes one very common case. before: push_collision_move_result [us] _____________ 64512x 3.562 after: push_collision_move_result [us] _____________ 72636x 0.831
This commit is contained in:
parent
2e89529eef
commit
c24a04d246
@ -97,3 +97,25 @@ function core.encode_png(width, height, data, compression)
|
|||||||
|
|
||||||
return o_encode_png(width, height, data, compression or 6)
|
return o_encode_png(width, height, data, compression or 6)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
-- Helper that pushes a collisionMoveResult structure
|
||||||
|
if core.set_push_moveresult1 then
|
||||||
|
-- must match CollisionAxis in collision.h
|
||||||
|
local AXES = {"x", "y", "z"}
|
||||||
|
-- <=> script/common/c_content.cpp push_collision_move_result()
|
||||||
|
core.set_push_moveresult1(function(b0, b1, b2, axis, npx, npy, npz, v0x, v0y, v0z, v1x, v1y, v1z)
|
||||||
|
return {
|
||||||
|
touching_ground = b0,
|
||||||
|
collides = b1,
|
||||||
|
standing_on_object = b2,
|
||||||
|
collisions = {{
|
||||||
|
type = "node",
|
||||||
|
axis = AXES[axis],
|
||||||
|
node_pos = vector.new(npx, npy, npz),
|
||||||
|
old_velocity = vector.new(v0x, v0y, v0z),
|
||||||
|
new_velocity = vector.new(v1x, v1y, v1z),
|
||||||
|
}},
|
||||||
|
}
|
||||||
|
end)
|
||||||
|
core.set_push_moveresult1 = nil
|
||||||
|
end
|
||||||
|
@ -2480,6 +2480,27 @@ static const char *collision_axis_str[] = {
|
|||||||
|
|
||||||
void push_collision_move_result(lua_State *L, const collisionMoveResult &res)
|
void push_collision_move_result(lua_State *L, const collisionMoveResult &res)
|
||||||
{
|
{
|
||||||
|
// use faster Lua helper if possible
|
||||||
|
if (res.collisions.size() == 1 && res.collisions.front().type == COLLISION_NODE) {
|
||||||
|
lua_rawgeti(L, LUA_REGISTRYINDEX, CUSTOM_RIDX_PUSH_MOVERESULT1);
|
||||||
|
const auto &c = res.collisions.front();
|
||||||
|
lua_pushboolean(L, res.touching_ground);
|
||||||
|
lua_pushboolean(L, res.collides);
|
||||||
|
lua_pushboolean(L, res.standing_on_object);
|
||||||
|
assert(c.axis != COLLISION_AXIS_NONE);
|
||||||
|
lua_pushinteger(L, static_cast<int>(c.axis));
|
||||||
|
lua_pushinteger(L, c.node_p.X);
|
||||||
|
lua_pushinteger(L, c.node_p.Y);
|
||||||
|
lua_pushinteger(L, c.node_p.Z);
|
||||||
|
for (v3f v : {c.old_speed / BS, c.new_speed / BS}) {
|
||||||
|
lua_pushnumber(L, v.X);
|
||||||
|
lua_pushnumber(L, v.Y);
|
||||||
|
lua_pushnumber(L, v.Z);
|
||||||
|
}
|
||||||
|
lua_call(L, 3 + 1 + 3 + 3 * 2, 1);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
lua_createtable(L, 0, 4);
|
lua_createtable(L, 0, 4);
|
||||||
|
|
||||||
setboolfield(L, -1, "touching_ground", res.touching_ground);
|
setboolfield(L, -1, "touching_ground", res.touching_ground);
|
||||||
|
@ -58,12 +58,13 @@ enum {
|
|||||||
CUSTOM_RIDX_HTTP_API_LUA,
|
CUSTOM_RIDX_HTTP_API_LUA,
|
||||||
CUSTOM_RIDX_METATABLE_MAP,
|
CUSTOM_RIDX_METATABLE_MAP,
|
||||||
|
|
||||||
// The following four functions are implemented in Lua because LuaJIT can
|
// The following functions are implemented in Lua because LuaJIT can
|
||||||
// trace them and optimize tables/string better than from the C API.
|
// trace them and optimize tables/string better than from the C API.
|
||||||
CUSTOM_RIDX_READ_VECTOR,
|
CUSTOM_RIDX_READ_VECTOR,
|
||||||
CUSTOM_RIDX_PUSH_VECTOR,
|
CUSTOM_RIDX_PUSH_VECTOR,
|
||||||
CUSTOM_RIDX_READ_NODE,
|
CUSTOM_RIDX_READ_NODE,
|
||||||
CUSTOM_RIDX_PUSH_NODE,
|
CUSTOM_RIDX_PUSH_NODE,
|
||||||
|
CUSTOM_RIDX_PUSH_MOVERESULT1,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -141,6 +141,11 @@ ScriptApiBase::ScriptApiBase(ScriptingType type):
|
|||||||
return 0;
|
return 0;
|
||||||
});
|
});
|
||||||
lua_setfield(m_luastack, -2, "set_push_node");
|
lua_setfield(m_luastack, -2, "set_push_node");
|
||||||
|
lua_pushcfunction(m_luastack, [](lua_State *L) -> int {
|
||||||
|
lua_rawseti(L, LUA_REGISTRYINDEX, CUSTOM_RIDX_PUSH_MOVERESULT1);
|
||||||
|
return 0;
|
||||||
|
});
|
||||||
|
lua_setfield(m_luastack, -2, "set_push_moveresult1");
|
||||||
// Finally, put the table into the global environment:
|
// Finally, put the table into the global environment:
|
||||||
lua_setglobal(m_luastack, "core");
|
lua_setglobal(m_luastack, "core");
|
||||||
|
|
||||||
@ -195,29 +200,30 @@ void ScriptApiBase::clientOpenLibs(lua_State *L)
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#define CHECK(ridx, name) do { \
|
||||||
|
lua_rawgeti(L, LUA_REGISTRYINDEX, ridx); \
|
||||||
|
FATAL_ERROR_IF(lua_type(L, -1) != LUA_TFUNCTION, "missing " name); \
|
||||||
|
lua_pop(L, 1); \
|
||||||
|
} while (0)
|
||||||
|
|
||||||
void ScriptApiBase::checkSetByBuiltin()
|
void ScriptApiBase::checkSetByBuiltin()
|
||||||
{
|
{
|
||||||
lua_State *L = getStack();
|
lua_State *L = getStack();
|
||||||
|
|
||||||
if (m_gamedef) {
|
if (m_gamedef) {
|
||||||
lua_rawgeti(L, LUA_REGISTRYINDEX, CUSTOM_RIDX_READ_VECTOR);
|
CHECK(CUSTOM_RIDX_READ_VECTOR, "read_vector");
|
||||||
FATAL_ERROR_IF(lua_type(L, -1) != LUA_TFUNCTION, "missing read_vector");
|
CHECK(CUSTOM_RIDX_PUSH_VECTOR, "push_vector");
|
||||||
lua_pop(L, 1);
|
CHECK(CUSTOM_RIDX_READ_NODE, "read_node");
|
||||||
|
CHECK(CUSTOM_RIDX_PUSH_NODE, "push_node");
|
||||||
|
}
|
||||||
|
|
||||||
lua_rawgeti(L, LUA_REGISTRYINDEX, CUSTOM_RIDX_PUSH_VECTOR);
|
if (getType() == ScriptingType::Server) {
|
||||||
FATAL_ERROR_IF(lua_type(L, -1) != LUA_TFUNCTION, "missing push_vector");
|
CHECK(CUSTOM_RIDX_PUSH_MOVERESULT1, "push_moveresult1");
|
||||||
lua_pop(L, 1);
|
|
||||||
|
|
||||||
lua_rawgeti(L, LUA_REGISTRYINDEX, CUSTOM_RIDX_READ_NODE);
|
|
||||||
FATAL_ERROR_IF(lua_type(L, -1) != LUA_TFUNCTION, "missing read_node");
|
|
||||||
lua_pop(L, 1);
|
|
||||||
|
|
||||||
lua_rawgeti(L, LUA_REGISTRYINDEX, CUSTOM_RIDX_PUSH_NODE);
|
|
||||||
FATAL_ERROR_IF(lua_type(L, -1) != LUA_TFUNCTION, "missing push_node");
|
|
||||||
lua_pop(L, 1);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#undef CHECK
|
||||||
|
|
||||||
std::string ScriptApiBase::getCurrentModNameInsecure(lua_State *L)
|
std::string ScriptApiBase::getCurrentModNameInsecure(lua_State *L)
|
||||||
{
|
{
|
||||||
lua_rawgeti(L, LUA_REGISTRYINDEX, CUSTOM_RIDX_CURRENT_MOD_NAME);
|
lua_rawgeti(L, LUA_REGISTRYINDEX, CUSTOM_RIDX_CURRENT_MOD_NAME);
|
||||||
|
Loading…
Reference in New Issue
Block a user