Inventory transparency; very loosely based on sapier's commits.
[oweals/minetest.git] / src / servercommand.cpp
1 /*
2 Part of Minetest-c55
3 Copyright (C) 2010-11 celeron55, Perttu Ahola <celeron55@gmail.com>
4 Copyright (C) 2011 Ciaran Gultnieks <ciaran@ciarang.com>
5
6 Permission to use, copy, modify, and distribute this software for any
7 purpose with or without fee is hereby granted, provided that the above
8 copyright notice and this permission notice appear in all copies.
9
10 THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11 WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12 MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13 ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14 WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15 ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16 OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17 */
18
19 #include "servercommand.h"
20 #include "utility.h"
21
22 void cmd_status(std::wostringstream &os,
23         ServerCommandContext *ctx)
24 {
25         os<<ctx->server->getStatusString();
26 }
27
28 void cmd_me(std::wostringstream &os,
29         ServerCommandContext *ctx)
30 {
31         std::wstring name = narrow_to_wide(ctx->player->getName());
32         os << L"* " << name << L" " << ctx->paramstring;
33         ctx->flags |= SEND_TO_OTHERS | SEND_NO_PREFIX;
34 }
35
36 void cmd_privs(std::wostringstream &os,
37         ServerCommandContext *ctx)
38 {
39         if(ctx->parms.size() == 1)
40         {
41                 // Show our own real privs, without any adjustments
42                 // made for admin status
43                 os<<L"-!- " + narrow_to_wide(privsToString(
44                                 ctx->server->getPlayerAuthPrivs(ctx->player->getName())));
45                 return;
46         }
47
48         if((ctx->privs & PRIV_PRIVS) == 0)
49         {
50                 os<<L"-!- You don't have permission to do that";
51                 return;
52         }
53                 
54         Player *tp = ctx->env->getPlayer(wide_to_narrow(ctx->parms[1]).c_str());
55         if(tp == NULL)
56         {
57                 os<<L"-!- No such player";
58                 return;
59         }
60         
61         os<<L"-!- " + narrow_to_wide(privsToString(ctx->server->getPlayerAuthPrivs(tp->getName())));
62 }
63
64 void cmd_grantrevoke(std::wostringstream &os,
65         ServerCommandContext *ctx)
66 {
67         if(ctx->parms.size() != 3)
68         {
69                 os<<L"-!- Missing parameter";
70                 return;
71         }
72
73         if((ctx->privs & PRIV_PRIVS) == 0)
74         {
75                 os<<L"-!- You don't have permission to do that";
76                 return;
77         }
78
79         u64 newprivs = stringToPrivs(wide_to_narrow(ctx->parms[2]));
80         if(newprivs == PRIV_INVALID)
81         {
82                 os<<L"-!- Invalid privileges specified";
83                 return;
84         }
85
86         Player *tp = ctx->env->getPlayer(wide_to_narrow(ctx->parms[1]).c_str());
87         if(tp == NULL)
88         {
89                 os<<L"-!- No such player";
90                 return;
91         }
92         
93         std::string playername = wide_to_narrow(ctx->parms[1]);
94         u64 privs = ctx->server->getPlayerAuthPrivs(playername);
95
96         if(ctx->parms[0] == L"grant")
97                 privs |= newprivs;
98         else
99                 privs &= ~newprivs;
100         
101         ctx->server->setPlayerAuthPrivs(playername, privs);
102         
103         os<<L"-!- Privileges change to ";
104         os<<narrow_to_wide(privsToString(privs));
105 }
106
107 void cmd_time(std::wostringstream &os,
108         ServerCommandContext *ctx)
109 {
110         if(ctx->parms.size() != 2)
111         {
112                 os<<L"-!- Missing parameter";
113                 return;
114         }
115
116         if((ctx->privs & PRIV_SETTIME) ==0)
117         {
118                 os<<L"-!- You don't have permission to do that";
119                 return;
120         }
121
122         u32 time = stoi(wide_to_narrow(ctx->parms[1]));
123         ctx->server->setTimeOfDay(time);
124         os<<L"-!- time_of_day changed.";
125 }
126
127 void cmd_shutdown(std::wostringstream &os,
128         ServerCommandContext *ctx)
129 {
130         if((ctx->privs & PRIV_SERVER) ==0)
131         {
132                 os<<L"-!- You don't have permission to do that";
133                 return;
134         }
135
136         dstream<<DTIME<<" Server: Operator requested shutdown."
137                 <<std::endl;
138         ctx->server->requestShutdown();
139                                         
140         os<<L"*** Server shutting down (operator request)";
141         ctx->flags |= SEND_TO_OTHERS;
142 }
143
144 void cmd_setting(std::wostringstream &os,
145         ServerCommandContext *ctx)
146 {
147         if((ctx->privs & PRIV_SERVER) ==0)
148         {
149                 os<<L"-!- You don't have permission to do that";
150                 return;
151         }
152
153         /*std::string confline = wide_to_narrow(
154                         ctx->parms[1] + L" = " + ctx->params[2]);*/
155
156         std::string confline = wide_to_narrow(ctx->paramstring);
157         
158         g_settings.parseConfigLine(confline);
159         
160         ctx->server->saveConfig();
161
162         os<< L"-!- Setting changed and configuration saved.";
163 }
164
165 void cmd_teleport(std::wostringstream &os,
166         ServerCommandContext *ctx)
167 {
168         if((ctx->privs & PRIV_TELEPORT) ==0)
169         {
170                 os<<L"-!- You don't have permission to do that";
171                 return;
172         }
173
174         if(ctx->parms.size() != 2)
175         {
176                 os<<L"-!- Missing parameter";
177                 return;
178         }
179
180         std::vector<std::wstring> coords = str_split(ctx->parms[1], L',');
181         if(coords.size() != 3)
182         {
183                 os<<L"-!- You can only specify coordinates currently";
184                 return;
185         }
186
187         v3f dest(stoi(coords[0])*10, stoi(coords[1])*10, stoi(coords[2])*10);
188         ctx->player->setPosition(dest);
189         ctx->server->SendMovePlayer(ctx->player);
190
191         os<< L"-!- Teleported.";
192 }
193
194 void cmd_banunban(std::wostringstream &os, ServerCommandContext *ctx)
195 {
196         if((ctx->privs & PRIV_BAN) == 0)
197         {
198                 os<<L"-!- You don't have permission to do that";
199                 return;
200         }
201
202         if(ctx->parms.size() < 2)
203         {
204                 std::string desc = ctx->server->getBanDescription("");
205                 os<<L"-!- Ban list: "<<narrow_to_wide(desc);
206                 return;
207         }
208         if(ctx->parms[0] == L"ban")
209         {
210                 Player *player = ctx->env->getPlayer(wide_to_narrow(ctx->parms[1]).c_str());
211
212                 if(player == NULL)
213                 {
214                         os<<L"-!- No such player";
215                         return;
216                 }
217
218                 con::Peer *peer = ctx->server->getPeerNoEx(player->peer_id);
219                 if(peer == NULL)
220                 {
221                         dstream<<__FUNCTION_NAME<<": peer was not found"<<std::endl;
222                         return;
223                 }
224                 std::string ip_string = peer->address.serializeString();
225                 ctx->server->setIpBanned(ip_string, player->getName());
226                 os<<L"-!- Banned "<<narrow_to_wide(ip_string)<<L"|"
227                                 <<narrow_to_wide(player->getName());
228         }
229         else
230         {
231                 std::string ip_or_name = wide_to_narrow(ctx->parms[1]);
232                 std::string desc = ctx->server->getBanDescription(ip_or_name);
233                 ctx->server->unsetIpBanned(ip_or_name);
234                 os<<L"-!- Unbanned "<<narrow_to_wide(desc);
235         }
236 }
237
238
239 std::wstring processServerCommand(ServerCommandContext *ctx)
240 {
241
242         std::wostringstream os(std::ios_base::binary);
243         ctx->flags = SEND_TO_SENDER;    // Default, unless we change it.
244
245         u64 privs = ctx->privs;
246
247         if(ctx->parms.size() == 0 || ctx->parms[0] == L"help")
248         {
249                 os<<L"-!- Available commands: ";
250                 os<<L"status privs ";
251                 if(privs & PRIV_SERVER)
252                         os<<L"shutdown setting ";
253                 if(privs & PRIV_SETTIME)
254                         os<<L" time";
255                 if(privs & PRIV_TELEPORT)
256                         os<<L" teleport";
257                 if(privs & PRIV_PRIVS)
258                         os<<L" grant revoke";
259                 if(privs & PRIV_BAN)
260                         os<<L" ban unban";
261         }
262         else if(ctx->parms[0] == L"status")
263         {
264                 cmd_status(os, ctx);
265         }
266         else if(ctx->parms[0] == L"privs")
267         {
268                 cmd_privs(os, ctx);
269         }
270         else if(ctx->parms[0] == L"grant" || ctx->parms[0] == L"revoke")
271         {
272                 cmd_grantrevoke(os, ctx);
273         }
274         else if(ctx->parms[0] == L"time")
275         {
276                 cmd_time(os, ctx);
277         }
278         else if(ctx->parms[0] == L"shutdown")
279         {
280                 cmd_shutdown(os, ctx);
281         }
282         else if(ctx->parms[0] == L"setting")
283         {
284                 cmd_setting(os, ctx);
285         }
286         else if(ctx->parms[0] == L"teleport")
287         {
288                 cmd_teleport(os, ctx);
289         }
290         else if(ctx->parms[0] == L"ban" || ctx->parms[0] == L"unban")
291         {
292                 cmd_banunban(os, ctx);
293         }
294         else if(ctx->parms[0] == L"me")
295         {
296                 cmd_me(os, ctx);
297         }
298         else
299         {
300                 os<<L"-!- Invalid command: " + ctx->parms[0];
301         }
302         return os.str();
303 }
304
305