]> git.lizzy.rs Git - dragonfireclient.git/blob - src/script/lua_api/l_settings.cpp
Pathfinder: Fix style
[dragonfireclient.git] / src / script / lua_api / l_settings.cpp
1 /*
2 Minetest
3 Copyright (C) 2013 PilzAdam <pilzadam@minetest.net>
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU Lesser General Public License as published by
7 the Free Software Foundation; either version 2.1 of the License, or
8 (at your option) any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13 GNU Lesser General Public License for more details.
14
15 You should have received a copy of the GNU Lesser General Public License along
16 with this program; if not, write to the Free Software Foundation, Inc.,
17 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 */
19
20 #include "lua_api/l_settings.h"
21 #include "lua_api/l_internal.h"
22 #include "cpp_api/s_security.h"
23 #include "settings.h"
24 #include "log.h"
25
26 // garbage collector
27 int LuaSettings::gc_object(lua_State* L)
28 {
29         LuaSettings* o = *(LuaSettings **)(lua_touserdata(L, 1));
30         delete o;
31         return 0;
32 }
33
34 // get(self, key) -> value
35 int LuaSettings::l_get(lua_State* L)
36 {
37         NO_MAP_LOCK_REQUIRED;
38         LuaSettings* o = checkobject(L, 1);
39
40         std::string key = std::string(luaL_checkstring(L, 2));
41         if (o->m_settings->exists(key)) {
42                 std::string value = o->m_settings->get(key);
43                 lua_pushstring(L, value.c_str());
44         } else {
45                 lua_pushnil(L);
46         }
47
48         return 1;
49 }
50
51 // get_bool(self, key) -> boolean
52 int LuaSettings::l_get_bool(lua_State* L)
53 {
54         NO_MAP_LOCK_REQUIRED;
55         LuaSettings* o = checkobject(L, 1);
56
57         std::string key = std::string(luaL_checkstring(L, 2));
58         if (o->m_settings->exists(key)) {
59                 bool value = o->m_settings->getBool(key);
60                 lua_pushboolean(L, value);
61         } else {
62                 lua_pushnil(L);
63         }
64
65         return 1;
66 }
67
68 // set(self, key, value)
69 int LuaSettings::l_set(lua_State* L)
70 {
71         NO_MAP_LOCK_REQUIRED;
72         LuaSettings* o = checkobject(L, 1);
73
74         std::string key = std::string(luaL_checkstring(L, 2));
75         const char* value = luaL_checkstring(L, 3);
76
77         if (!o->m_settings->set(key, value))
78                 throw LuaError("Invalid sequence found in setting parameters");
79
80         return 0;
81 }
82
83 // remove(self, key) -> success
84 int LuaSettings::l_remove(lua_State* L)
85 {
86         NO_MAP_LOCK_REQUIRED;
87         LuaSettings* o = checkobject(L, 1);
88
89         std::string key = std::string(luaL_checkstring(L, 2));
90
91         bool success = o->m_settings->remove(key);
92         lua_pushboolean(L, success);
93
94         return 1;
95 }
96
97 // get_names(self) -> {key1, ...}
98 int LuaSettings::l_get_names(lua_State* L)
99 {
100         NO_MAP_LOCK_REQUIRED;
101         LuaSettings* o = checkobject(L, 1);
102
103         std::vector<std::string> keys = o->m_settings->getNames();
104
105         lua_newtable(L);
106         for (unsigned int i=0; i < keys.size(); i++)
107         {
108                 lua_pushstring(L, keys[i].c_str());
109                 lua_rawseti(L, -2, i + 1);
110         }
111
112         return 1;
113 }
114
115 // write(self) -> success
116 int LuaSettings::l_write(lua_State* L)
117 {
118         NO_MAP_LOCK_REQUIRED;
119         LuaSettings* o = checkobject(L, 1);
120
121         bool success = o->m_settings->updateConfigFile(o->m_filename.c_str());
122         lua_pushboolean(L, success);
123
124         return 1;
125 }
126
127 // to_table(self) -> {[key1]=value1,...}
128 int LuaSettings::l_to_table(lua_State* L)
129 {
130         NO_MAP_LOCK_REQUIRED;
131         LuaSettings* o = checkobject(L, 1);
132
133         std::vector<std::string> keys = o->m_settings->getNames();
134
135         lua_newtable(L);
136         for (unsigned int i=0; i < keys.size(); i++)
137         {
138                 lua_pushstring(L, o->m_settings->get(keys[i]).c_str());
139                 lua_setfield(L, -2, keys[i].c_str());
140         }
141
142         return 1;
143 }
144
145 LuaSettings::LuaSettings(const char* filename)
146 {
147         m_filename = std::string(filename);
148
149         m_settings = new Settings();
150         m_settings->readConfigFile(m_filename.c_str());
151 }
152
153 LuaSettings::~LuaSettings()
154 {
155         delete m_settings;
156 }
157
158 void LuaSettings::Register(lua_State* L)
159 {
160         lua_newtable(L);
161         int methodtable = lua_gettop(L);
162         luaL_newmetatable(L, className);
163         int metatable = lua_gettop(L);
164
165         lua_pushliteral(L, "__metatable");
166         lua_pushvalue(L, methodtable);
167         lua_settable(L, metatable);  // hide metatable from Lua getmetatable()
168
169         lua_pushliteral(L, "__index");
170         lua_pushvalue(L, methodtable);
171         lua_settable(L, metatable);
172
173         lua_pushliteral(L, "__gc");
174         lua_pushcfunction(L, gc_object);
175         lua_settable(L, metatable);
176
177         lua_pop(L, 1);  // drop metatable
178
179         luaL_openlib(L, 0, methods, 0);  // fill methodtable
180         lua_pop(L, 1);  // drop methodtable
181
182         // Can be created from Lua (Settings(filename))
183         lua_register(L, className, create_object);
184 }
185
186 // LuaSettings(filename)
187 // Creates an LuaSettings and leaves it on top of stack
188 int LuaSettings::create_object(lua_State* L)
189 {
190         NO_MAP_LOCK_REQUIRED;
191         const char* filename = luaL_checkstring(L, 1);
192         CHECK_SECURE_PATH_OPTIONAL(L, filename);
193         LuaSettings* o = new LuaSettings(filename);
194         *(void **)(lua_newuserdata(L, sizeof(void *))) = o;
195         luaL_getmetatable(L, className);
196         lua_setmetatable(L, -2);
197         return 1;
198 }
199
200 LuaSettings* LuaSettings::checkobject(lua_State* L, int narg)
201 {
202         NO_MAP_LOCK_REQUIRED;
203         luaL_checktype(L, narg, LUA_TUSERDATA);
204         void *ud = luaL_checkudata(L, narg, className);
205         if(!ud) luaL_typerror(L, narg, className);
206         return *(LuaSettings**)ud;  // unbox pointer
207 }
208
209 const char LuaSettings::className[] = "Settings";
210 const luaL_reg LuaSettings::methods[] = {
211         luamethod(LuaSettings, get),
212         luamethod(LuaSettings, get_bool),
213         luamethod(LuaSettings, set),
214         luamethod(LuaSettings, remove),
215         luamethod(LuaSettings, get_names),
216         luamethod(LuaSettings, write),
217         luamethod(LuaSettings, to_table),
218         {0,0}
219 };