The API implementation is shared between CSM and SSM.
Functions should retrieve a plain env when they do not
need any server-specific functions.
return m_time_of_day_f;
}
+bool Environment::line_of_sight(v3f pos1, v3f pos2, v3s16 *p)
+{
+ // Iterate trough nodes on the line
+ voxalgo::VoxelLineIterator iterator(pos1 / BS, (pos2 - pos1) / BS);
+ do {
+ MapNode n = getMap().getNode(iterator.m_current_node_pos);
+
+ // Return non-air
+ if (n.param0 != CONTENT_AIR) {
+ if (p)
+ *p = iterator.m_current_node_pos;
+ return false;
+ }
+ iterator.next();
+ } while (iterator.m_current_index <= iterator.m_last_index);
+ return true;
+}
+
/*
Check if a node is pointable
*/
u32 getDayCount();
+ /*!
+ * Returns false if the given line intersects with a
+ * non-air node, true otherwise.
+ * \param pos1 start of the line
+ * \param pos2 end of the line
+ * \param p output, position of the first non-air node
+ * the line intersects
+ */
+ bool line_of_sight(v3f pos1, v3f pos2, v3s16 *p = nullptr);
+
/*!
* Gets the objects pointed by the shootline as
* pointed things.
int LuaRaycast::l_next(lua_State *L)
{
- MAP_LOCK_REQUIRED;
- GET_ENV_PTR;
+ GET_PLAIN_ENV_PTR;
bool csm = false;
#ifndef SERVER
// timeofday: nil = current time, 0 = night, 0.5 = day
int ModApiEnvMod::l_get_node_light(lua_State *L)
{
- GET_ENV_PTR;
+ GET_PLAIN_ENV_PTR;
// Do it
v3s16 pos = read_v3s16(L, 1);
// pos = {x=num, y=num, z=num}
int ModApiEnvMod::l_get_node_max_level(lua_State *L)
{
- Environment *env = getEnv(L);
- if (!env) {
- return 0;
- }
+ GET_PLAIN_ENV_PTR;
v3s16 pos = read_v3s16(L, 1);
MapNode n = env->getMap().getNode(pos);
// pos = {x=num, y=num, z=num}
int ModApiEnvMod::l_get_node_level(lua_State *L)
{
- Environment *env = getEnv(L);
- if (!env) {
- return 0;
- }
+ GET_PLAIN_ENV_PTR;
v3s16 pos = read_v3s16(L, 1);
MapNode n = env->getMap().getNode(pos);
// find_nodes_with_meta(pos1, pos2)
int ModApiEnvMod::l_find_nodes_with_meta(lua_State *L)
{
- GET_ENV_PTR;
+ GET_PLAIN_ENV_PTR;
std::vector<v3s16> positions = env->getMap().findNodesWithMetadata(
check_v3s16(L, 1), check_v3s16(L, 2));
// get_timeofday() -> 0...1
int ModApiEnvMod::l_get_timeofday(lua_State *L)
{
- Environment *env = getEnv(L);
- if (!env) {
- return 0;
- }
+ GET_PLAIN_ENV_PTR;
// Do it
int timeofday_mh = env->getTimeOfDay();
// get_day_count() -> int
int ModApiEnvMod::l_get_day_count(lua_State *L)
{
- Environment *env = getEnv(L);
- if (!env) {
- return 0;
- }
+ GET_PLAIN_ENV_PTR;
lua_pushnumber(L, env->getDayCount());
return 1;
// nodenames: eg. {"ignore", "group:tree"} or "default:dirt"
int ModApiEnvMod::l_find_node_near(lua_State *L)
{
- Environment *env = getEnv(L);
- if (!env) {
- return 0;
- }
+ GET_PLAIN_ENV_PTR;
- const NodeDefManager *ndef = getGameDef(L)->ndef();
+ const NodeDefManager *ndef = env->getGameDef()->ndef();
v3s16 pos = read_v3s16(L, 1);
int radius = luaL_checkinteger(L, 2);
std::vector<content_t> filter;
// nodenames: eg. {"ignore", "group:tree"} or "default:dirt"
int ModApiEnvMod::l_find_nodes_in_area(lua_State *L)
{
- GET_ENV_PTR;
+ GET_PLAIN_ENV_PTR;
v3s16 minp = read_v3s16(L, 1);
v3s16 maxp = read_v3s16(L, 2);
sortBoxVerticies(minp, maxp);
+ const NodeDefManager *ndef = env->getGameDef()->ndef();
+
#ifndef SERVER
- const NodeDefManager *ndef = getClient(L) ? getClient(L)->ndef() : getServer(L)->ndef();
if (getClient(L)) {
minp = getClient(L)->CSMClampPos(minp);
maxp = getClient(L)->CSMClampPos(maxp);
}
-#else
- const NodeDefManager *ndef = getServer(L)->ndef();
#endif
v3s16 cube = maxp - minp + 1;
* TODO
*/
- GET_ENV_PTR;
+ GET_PLAIN_ENV_PTR;
v3s16 minp = read_v3s16(L, 1);
v3s16 maxp = read_v3s16(L, 2);
sortBoxVerticies(minp, maxp);
+ const NodeDefManager *ndef = env->getGameDef()->ndef();
+
#ifndef SERVER
- const NodeDefManager *ndef = getClient(L) ? getClient(L)->ndef() : getServer(L)->ndef();
if (getClient(L)) {
minp = getClient(L)->CSMClampPos(minp);
maxp = getClient(L)->CSMClampPos(maxp);
}
-#else
- const NodeDefManager *ndef = getServer(L)->ndef();
#endif
v3s16 cube = maxp - minp + 1;
// line_of_sight(pos1, pos2) -> true/false, pos
int ModApiEnvMod::l_line_of_sight(lua_State *L)
{
- GET_ENV_PTR;
+ GET_PLAIN_ENV_PTR;
// read position 1 from lua
v3f pos1 = checkFloatPos(L, 1);
#define luamethod_aliased(class, name, alias) {#name, class::l_##name}, {#alias, class::l_##name}
#define API_FCT(name) registerFunction(L, #name, l_##name, top)
-#define MAP_LOCK_REQUIRED
-#define NO_MAP_LOCK_REQUIRED
+// For future use
+#define MAP_LOCK_REQUIRED ((void)0)
+#define NO_MAP_LOCK_REQUIRED ((void)0)
+/* In debug mode ensure no code tries to retrieve the server env when it isn't
+ * actually available (in CSM) */
+#if !defined(SERVER) && !defined(NDEBUG)
+#define DEBUG_ASSERT_NO_CLIENTAPI \
+ FATAL_ERROR_IF(getClient(L) != nullptr, "Tried " \
+ "to retrieve ServerEnvironment on client")
+#else
+#define DEBUG_ASSERT_NO_CLIENTAPI ((void)0)
+#endif
+
+// Retrieve ServerEnvironment pointer as `env` (no map lock)
#define GET_ENV_PTR_NO_MAP_LOCK \
+ DEBUG_ASSERT_NO_CLIENTAPI; \
ServerEnvironment *env = (ServerEnvironment *)getEnv(L); \
if (env == NULL) \
return 0
+// Retrieve ServerEnvironment pointer as `env`
#define GET_ENV_PTR \
MAP_LOCK_REQUIRED; \
GET_ENV_PTR_NO_MAP_LOCK
+
+// Retrieve Environment pointer as `env` (no map lock)
+#define GET_PLAIN_ENV_PTR_NO_MAP_LOCK \
+ Environment *env = (Environment *)getEnv(L); \
+ if (env == NULL) \
+ return 0
+
+// Retrieve Environment pointer as `env`
+#define GET_PLAIN_ENV_PTR \
+ MAP_LOCK_REQUIRED; \
+ GET_PLAIN_ENV_PTR_NO_MAP_LOCK
// get_local_animation(self)
int ObjectRef::l_get_local_animation(lua_State *L)
{
- NO_MAP_LOCK_REQUIRED
+ NO_MAP_LOCK_REQUIRED;
ObjectRef *ref = checkobject(L, 1);
RemotePlayer *player = getplayer(ref);
if (player == NULL)
return m_player_database->removePlayer(name);
}
-bool ServerEnvironment::line_of_sight(v3f pos1, v3f pos2, v3s16 *p)
-{
- // Iterate trough nodes on the line
- voxalgo::VoxelLineIterator iterator(pos1 / BS, (pos2 - pos1) / BS);
- do {
- MapNode n = getMap().getNode(iterator.m_current_node_pos);
-
- // Return non-air
- if (n.param0 != CONTENT_AIR) {
- if (p)
- *p = iterator.m_current_node_pos;
- return false;
- }
- iterator.next();
- } while (iterator.m_current_index <= iterator.m_last_index);
- return true;
-}
-
void ServerEnvironment::kickAllPlayers(AccessDeniedCode reason,
const std::string &str_reason, bool reconnect)
{
// This makes stuff happen
void step(f32 dtime);
- /*!
- * Returns false if the given line intersects with a
- * non-air node, true otherwise.
- * \param pos1 start of the line
- * \param pos2 end of the line
- * \param p output, position of the first non-air node
- * the line intersects
- */
- bool line_of_sight(v3f pos1, v3f pos2, v3s16 *p = NULL);
-
u32 getGameTime() const { return m_game_time; }
void reportMaxLagEstimate(float f) { m_max_lag_estimate = f; }