* Implement minetest.register_on_userlimit_check This new callback permits to bypass the max_users parameter with new mods condition, based on player name or IP Only one mod needs to permit it. Move core part for builtin privileges checks to builtin
210 lines
5.8 KiB
C++
210 lines
5.8 KiB
C++
/*
|
|
Minetest
|
|
Copyright (C) 2013 celeron55, Perttu Ahola <celeron55@gmail.com>
|
|
|
|
This program is free software; you can redistribute it and/or modify
|
|
it under the terms of the GNU Lesser General Public License as published by
|
|
the Free Software Foundation; either version 2.1 of the License, or
|
|
(at your option) any later version.
|
|
|
|
This program is distributed in the hope that it will be useful,
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
GNU Lesser General Public License for more details.
|
|
|
|
You should have received a copy of the GNU Lesser General Public License along
|
|
with this program; if not, write to the Free Software Foundation, Inc.,
|
|
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
|
*/
|
|
|
|
#include "cpp_api/s_player.h"
|
|
#include "cpp_api/s_internal.h"
|
|
#include "common/c_converter.h"
|
|
#include "common/c_content.h"
|
|
#include "debug.h"
|
|
#include "util/string.h"
|
|
|
|
void ScriptApiPlayer::on_newplayer(ServerActiveObject *player)
|
|
{
|
|
SCRIPTAPI_PRECHECKHEADER
|
|
|
|
// Get core.registered_on_newplayers
|
|
lua_getglobal(L, "core");
|
|
lua_getfield(L, -1, "registered_on_newplayers");
|
|
// Call callbacks
|
|
objectrefGetOrCreate(L, player);
|
|
runCallbacks(1, RUN_CALLBACKS_MODE_FIRST);
|
|
}
|
|
|
|
void ScriptApiPlayer::on_dieplayer(ServerActiveObject *player)
|
|
{
|
|
SCRIPTAPI_PRECHECKHEADER
|
|
|
|
// Get core.registered_on_dieplayers
|
|
lua_getglobal(L, "core");
|
|
lua_getfield(L, -1, "registered_on_dieplayers");
|
|
// Call callbacks
|
|
objectrefGetOrCreate(L, player);
|
|
runCallbacks(1, RUN_CALLBACKS_MODE_FIRST);
|
|
}
|
|
|
|
bool ScriptApiPlayer::on_punchplayer(ServerActiveObject *player,
|
|
ServerActiveObject *hitter,
|
|
float time_from_last_punch,
|
|
const ToolCapabilities *toolcap,
|
|
v3f dir,
|
|
s16 damage)
|
|
{
|
|
SCRIPTAPI_PRECHECKHEADER
|
|
// Get core.registered_on_punchplayers
|
|
lua_getglobal(L, "core");
|
|
lua_getfield(L, -1, "registered_on_punchplayers");
|
|
// Call callbacks
|
|
objectrefGetOrCreate(L, player);
|
|
objectrefGetOrCreate(L, hitter);
|
|
lua_pushnumber(L, time_from_last_punch);
|
|
push_tool_capabilities(L, *toolcap);
|
|
push_v3f(L, dir);
|
|
lua_pushnumber(L, damage);
|
|
runCallbacks(6, RUN_CALLBACKS_MODE_OR);
|
|
return lua_toboolean(L, -1);
|
|
}
|
|
|
|
s16 ScriptApiPlayer::on_player_hpchange(ServerActiveObject *player,
|
|
s16 hp_change)
|
|
{
|
|
SCRIPTAPI_PRECHECKHEADER
|
|
|
|
int error_handler = PUSH_ERROR_HANDLER(L);
|
|
|
|
// Get core.registered_on_player_hpchange
|
|
lua_getglobal(L, "core");
|
|
lua_getfield(L, -1, "registered_on_player_hpchange");
|
|
lua_remove(L, -2);
|
|
|
|
objectrefGetOrCreate(L, player);
|
|
lua_pushnumber(L, hp_change);
|
|
PCALL_RES(lua_pcall(L, 2, 1, error_handler));
|
|
hp_change = lua_tointeger(L, -1);
|
|
lua_pop(L, 2); // Pop result and error handler
|
|
return hp_change;
|
|
}
|
|
|
|
bool ScriptApiPlayer::on_respawnplayer(ServerActiveObject *player)
|
|
{
|
|
SCRIPTAPI_PRECHECKHEADER
|
|
|
|
// Get core.registered_on_respawnplayers
|
|
lua_getglobal(L, "core");
|
|
lua_getfield(L, -1, "registered_on_respawnplayers");
|
|
// Call callbacks
|
|
objectrefGetOrCreate(L, player);
|
|
runCallbacks(1, RUN_CALLBACKS_MODE_OR);
|
|
bool positioning_handled_by_some = lua_toboolean(L, -1);
|
|
return positioning_handled_by_some;
|
|
}
|
|
|
|
bool ScriptApiPlayer::on_prejoinplayer(
|
|
const std::string &name,
|
|
const std::string &ip,
|
|
std::string *reason)
|
|
{
|
|
SCRIPTAPI_PRECHECKHEADER
|
|
|
|
// Get core.registered_on_prejoinplayers
|
|
lua_getglobal(L, "core");
|
|
lua_getfield(L, -1, "registered_on_prejoinplayers");
|
|
lua_pushstring(L, name.c_str());
|
|
lua_pushstring(L, ip.c_str());
|
|
runCallbacks(2, RUN_CALLBACKS_MODE_OR);
|
|
if (lua_isstring(L, -1)) {
|
|
reason->assign(lua_tostring(L, -1));
|
|
return true;
|
|
}
|
|
return false;
|
|
}
|
|
|
|
bool ScriptApiPlayer::can_bypass_userlimit(const std::string &name, const std::string &ip)
|
|
{
|
|
SCRIPTAPI_PRECHECKHEADER
|
|
|
|
// Get core.registered_on_prejoinplayers
|
|
lua_getglobal(L, "core");
|
|
lua_getfield(L, -1, "registered_can_bypass_userlimit");
|
|
lua_pushstring(L, name.c_str());
|
|
lua_pushstring(L, ip.c_str());
|
|
runCallbacks(2, RUN_CALLBACKS_MODE_OR);
|
|
FATAL_ERROR_IF(!lua_isboolean(L, -1), "on_user_limitcheck must return a boolean");
|
|
return lua_toboolean(L, -1);
|
|
}
|
|
|
|
void ScriptApiPlayer::on_joinplayer(ServerActiveObject *player)
|
|
{
|
|
SCRIPTAPI_PRECHECKHEADER
|
|
|
|
// Get core.registered_on_joinplayers
|
|
lua_getglobal(L, "core");
|
|
lua_getfield(L, -1, "registered_on_joinplayers");
|
|
// Call callbacks
|
|
objectrefGetOrCreate(L, player);
|
|
runCallbacks(1, RUN_CALLBACKS_MODE_FIRST);
|
|
}
|
|
|
|
void ScriptApiPlayer::on_leaveplayer(ServerActiveObject *player,
|
|
bool timeout)
|
|
{
|
|
SCRIPTAPI_PRECHECKHEADER
|
|
|
|
// Get core.registered_on_leaveplayers
|
|
lua_getglobal(L, "core");
|
|
lua_getfield(L, -1, "registered_on_leaveplayers");
|
|
// Call callbacks
|
|
objectrefGetOrCreate(L, player);
|
|
lua_pushboolean(L, timeout);
|
|
runCallbacks(2, RUN_CALLBACKS_MODE_FIRST);
|
|
}
|
|
|
|
void ScriptApiPlayer::on_cheat(ServerActiveObject *player,
|
|
const std::string &cheat_type)
|
|
{
|
|
SCRIPTAPI_PRECHECKHEADER
|
|
|
|
// Get core.registered_on_cheats
|
|
lua_getglobal(L, "core");
|
|
lua_getfield(L, -1, "registered_on_cheats");
|
|
// Call callbacks
|
|
objectrefGetOrCreate(L, player);
|
|
lua_newtable(L);
|
|
lua_pushlstring(L, cheat_type.c_str(), cheat_type.size());
|
|
lua_setfield(L, -2, "type");
|
|
runCallbacks(2, RUN_CALLBACKS_MODE_FIRST);
|
|
}
|
|
|
|
void ScriptApiPlayer::on_playerReceiveFields(ServerActiveObject *player,
|
|
const std::string &formname,
|
|
const StringMap &fields)
|
|
{
|
|
SCRIPTAPI_PRECHECKHEADER
|
|
|
|
// Get core.registered_on_chat_messages
|
|
lua_getglobal(L, "core");
|
|
lua_getfield(L, -1, "registered_on_player_receive_fields");
|
|
// Call callbacks
|
|
// param 1
|
|
objectrefGetOrCreate(L, player);
|
|
// param 2
|
|
lua_pushstring(L, formname.c_str());
|
|
// param 3
|
|
lua_newtable(L);
|
|
StringMap::const_iterator it;
|
|
for (it = fields.begin(); it != fields.end(); ++it) {
|
|
const std::string &name = it->first;
|
|
const std::string &value = it->second;
|
|
lua_pushstring(L, name.c_str());
|
|
lua_pushlstring(L, value.c_str(), value.size());
|
|
lua_settable(L, -3);
|
|
}
|
|
runCallbacks(3, RUN_CALLBACKS_MODE_OR_SC);
|
|
}
|
|
|