]> git.lizzy.rs Git - minetest.git/blobdiff - src/script/lua_api/l_http.cpp
Don't let HTTP API pass through untrusted function
[minetest.git] / src / script / lua_api / l_http.cpp
index 751ec98376a3dfaf12b9e333ad64003342ed0d0c..b385b698c8a56a576b8512bf9727e60c5e4c8069 100644 (file)
@@ -163,6 +163,20 @@ int ModApiHttp::l_http_fetch_async_get(lua_State *L)
        return 1;
 }
 
+int ModApiHttp::l_set_http_api_lua(lua_State *L)
+{
+       NO_MAP_LOCK_REQUIRED;
+
+       // This is called by builtin to give us a function that will later
+       // populate the http_api table with additional method(s).
+       // We need this because access to the HTTP api is security-relevant and
+       // any mod could just mess with a global variable.
+       luaL_checktype(L, 1, LUA_TFUNCTION);
+       lua_rawseti(L, LUA_REGISTRYINDEX, CUSTOM_RIDX_HTTP_API_LUA);
+
+       return 0;
+}
+
 int ModApiHttp::l_request_http_api(lua_State *L)
 {
        NO_MAP_LOCK_REQUIRED;
@@ -205,16 +219,16 @@ int ModApiHttp::l_request_http_api(lua_State *L)
                return 1;
        }
 
-       lua_getglobal(L, "core");
-       lua_getfield(L, -1, "http_add_fetch");
+       lua_rawgeti(L, LUA_REGISTRYINDEX, CUSTOM_RIDX_HTTP_API_LUA);
+       assert(lua_isfunction(L, -1));
 
        lua_newtable(L);
        HTTP_API(fetch_async);
        HTTP_API(fetch_async_get);
 
        // Stack now looks like this:
-       // <core.http_add_fetch> <table with fetch_async, fetch_async_get>
-       // Now call core.http_add_fetch to append .fetch(request, callback) to table
+       // <function> <table with fetch_async, fetch_async_get>
+       // Now call it to append .fetch(request, callback) to table
        lua_call(L, 1, 1);
 
        return 1;
@@ -247,6 +261,7 @@ void ModApiHttp::Initialize(lua_State *L, int top)
                API_FCT(get_http_api);
        } else {
                API_FCT(request_http_api);
+               API_FCT(set_http_api_lua);
        }
 
 #endif