]> git.xonotic.org Git - xonotic/xonotic-data.pk3dir.git/blob - qcsrc/server/command/banning.qc
Transifex autosync
[xonotic/xonotic-data.pk3dir.git] / qcsrc / server / command / banning.qc
1 #include "banning.qh"
2
3 #include <common/command/_mod.qh>
4 #include <common/minigames/sv_minigames.qh>
5 #include <common/state.qh>
6 #include <common/stats.qh>
7 #include <common/util.qh>
8 #include <common/weapons/_all.qh>
9 #include <server/command/banning.qh>
10 #include <server/command/common.qh>
11 #include <server/ipban.qh>
12 #include <server/player.qh>
13
14 // =====================================================
15 //  Banning and kicking command code, written by Samual
16 //  Last updated: December 29th, 2011
17 // =====================================================
18
19 void BanCommand_ban(int request, int argc, string command)
20 {
21         switch (request)
22         {
23                 case CMD_REQUEST_COMMAND:
24                 {
25                         if (argc >= 2)
26                         {
27                                 string ip = argv(1);
28                                 float reason_arg, bantime;
29                                 string reason;
30
31                                 reason_arg = 2;
32
33                                 GET_BAN_ARG(bantime, autocvar_g_ban_default_bantime);
34                                 GET_BAN_REASON(reason, "No reason provided");
35
36                                 Ban_Insert(ip, bantime, reason, 1);
37                                 return;
38                         }
39                 }
40
41                 default:
42                         LOG_INFOF("Incorrect parameters for ^2%s^7", argv(0));
43                 case CMD_REQUEST_USAGE:
44                 {
45                         LOG_HELP("Usage:^3 sv_cmd ban <address> [<bantime>] [<reason>]");
46                         LOG_HELP("  <address> is the IP address or range of the player to ban,");
47                         LOG_HELP("  <bantime> is the amount of time that the ban is active (default if not provided),");
48                         LOG_HELP("  and <reason> is the string to label the ban with as reason for banning.");
49                         LOG_HELP("See also: ^2banlist, kickban, unban^7");
50                         return;
51                 }
52         }
53 }
54
55 void BanCommand_banlist(int request)
56 {
57         switch (request)
58         {
59                 case CMD_REQUEST_COMMAND:
60                 {
61                         Ban_View();
62                         return;
63                 }
64
65                 default:
66                 case CMD_REQUEST_USAGE:
67                 {
68                         LOG_HELP("Usage:^3 sv_cmd banlist");
69                         LOG_HELP("  No arguments required.");
70                         LOG_HELP("See also: ^2ban, kickban, unban^7");
71                         return;
72                 }
73         }
74 }
75
76 void BanCommand_kickban(int request, int argc, string command)
77 {
78         switch (request)
79         {
80                 case CMD_REQUEST_COMMAND:
81                 {
82                         if (argc >= 2)
83                         {
84                                 entity client = GetIndexedEntity(argc, 1);
85                                 float accepted = VerifyKickableEntity(client);
86                                 float reason_arg, bantime, masksize;
87                                 string reason;
88
89                                 if (accepted > 0)
90                                 {
91                                         reason_arg = next_token;
92
93                                         GET_BAN_ARG(bantime, autocvar_g_ban_default_bantime);
94                                         GET_BAN_ARG(masksize, autocvar_g_ban_default_masksize);
95                                         GET_BAN_REASON(reason, "No reason provided");
96
97                                         Ban_KickBanClient(client, bantime, masksize, reason);
98
99                                         return;
100                                 }
101                                 else
102                                 {
103                                         LOG_INFO("kickban: ", GetClientErrorString(accepted, argv(1)), ".");
104                                 }
105                         }
106                 }
107
108                 default:
109                         LOG_INFOF("Incorrect parameters for ^2%s^7", argv(0));
110                 case CMD_REQUEST_USAGE:
111                 {
112                         LOG_HELP("Usage:^3 sv_cmd kickban <client> [<bantime>] [<masksize>] [<reason>]");
113                         LOG_HELP("  <client> is the entity number or name of the player to ban,");
114                         LOG_HELP("  <bantime> is the amount of time that the ban is active (default if not provided),");
115                         LOG_HELP("  <masksize> is the range of the IP address (1-thru-4, default if not provided),");
116                         LOG_HELP("  and <reason> is the string to label the ban with as reason for banning.");
117                         LOG_HELP("See also: ^2ban, banlist, unban^7");
118                         return;
119                 }
120         }
121 }
122
123 void BanCommand_mute(int request, int argc, string command)
124 {
125         switch (request)
126         {
127                 case CMD_REQUEST_COMMAND:
128                 {
129                         if (argc >= 2)
130                         {
131                                 entity client = GetIndexedEntity(argc, 1);
132                                 float accepted = VerifyClientEntity(client, true, false);
133
134                                 if (accepted > 0)
135                                 {
136                                         string theid = "";
137                                         if(!PlayerInIPList(client, autocvar_g_chatban_list))
138                                                 theid = cons(theid, client.netaddress);
139                                         if(!PlayerInIDList(client, autocvar_g_chatban_list))
140                                                 theid = cons(theid, client.crypto_idfp);
141                                         CS(client).muted = true;
142                                         LOG_INFO(strcat("Mute-banning player ", GetCallerName(client), " (", argv(1), ")."));
143                                         cvar_set("g_chatban_list", cons(autocvar_g_chatban_list, theid));
144
145                                         return;
146                                 }
147                                 else
148                                 {
149                                         LOG_INFO("mute: ", GetClientErrorString(accepted, argv(1)), ".");
150                                 }
151                         }
152                 }
153
154                 default:
155                         LOG_INFOF("Incorrect parameters for ^2%s^7", argv(0));
156                 case CMD_REQUEST_USAGE:
157                 {
158                         LOG_HELP("Usage:^3 sv_cmd mute <client>");
159                         LOG_HELP("  <client> is the entity number or name of the player to mute.");
160                         LOG_HELP("See also: ^2unmute, g_chatban_list^7");
161                         return;
162                 }
163         }
164 }
165
166 void BanCommand_playban(int request, int argc, string command)
167 {
168         switch (request)
169         {
170                 case CMD_REQUEST_COMMAND:
171                 {
172                         if (argc >= 2)
173                         {
174                                 entity client = GetIndexedEntity(argc, 1);
175                                 float accepted = VerifyClientEntity(client, true, false);
176
177                                 if (accepted > 0)
178                                 {
179                                         string theid = "";
180                                         if(!PlayerInIPList(client, autocvar_g_playban_list))
181                                                 theid = cons(theid, client.netaddress);
182                                         if(!PlayerInIDList(client, autocvar_g_playban_list))
183                                                 theid = cons(theid, client.crypto_idfp);
184
185                                         LOG_INFO(strcat("Play-banning player ", GetCallerName(client), " (", argv(1), ")."));
186                                         PutObserverInServer(client, true, true);
187                                         if (autocvar_g_playban_minigames) 
188                                                 part_minigame(client);
189                                         cvar_set("g_playban_list", cons(autocvar_g_playban_list, theid));
190
191                                         return;
192                                 }
193                                 else
194                                 {
195                                         LOG_INFO("playban: ", GetClientErrorString(accepted, argv(1)), ".");
196                                 }
197                         }
198                 }
199
200                 default:
201                         LOG_INFOF("Incorrect parameters for ^2%s^7", argv(0));
202                 case CMD_REQUEST_USAGE:
203                 {
204                         LOG_HELP("Usage:^3 sv_cmd playban <client>");
205                         LOG_HELP("  <client> is the entity number or name of the player to ban being forced to spectate permanently,");
206                         LOG_HELP("See also: ^2g_playban_list, unplayban^7");
207                         return;
208                 }
209         }
210 }
211
212 void BanCommand_unban(int request, int argc)
213 {
214         switch (request)
215         {
216                 case CMD_REQUEST_COMMAND:
217                 {
218                         if (argv(1))
219                         {
220                                 float tmp_number = -1;
221                                 string tmp_string;
222
223                                 if (substring(argv(1), 0, 1) == "#")
224                                 {
225                                         tmp_string = substring(argv(1), 1, -1);
226
227                                         if (tmp_string != "") // is it all one token? like #1
228                                                 tmp_number = stof(tmp_string);
229                                         else if (argc > 2)    // no, it's two tokens? # 1
230                                                 tmp_number = stof(argv(2));
231                                         else tmp_number = -1;
232                                 }
233                                 else  // maybe it's ONLY a number?
234                                 {
235                                         tmp_number = stof(argv(1));
236
237                                         if ((tmp_number == 0) && (argv(1) != "0")) tmp_number = -1; }
238
239                                 if (tmp_number >= 0)
240                                 {
241                                         Ban_Delete(tmp_number);
242                                         return;
243                                 }
244                         }
245                 }
246
247                 default:
248                 case CMD_REQUEST_USAGE:
249                 {
250                         LOG_HELP("Usage:^3 sv_cmd unban <banid>");
251                         LOG_HELP("  Where <banid> is the ID of the ban of which to remove.");
252                         LOG_HELP("See also: ^2ban, banlist, kickban^7");
253                         return;
254                 }
255         }
256 }
257
258 void BanCommand_unmute(int request, int argc)
259 {
260         switch (request)
261         {
262                 case CMD_REQUEST_COMMAND:
263                 {
264                         if (argc >= 2)
265                         {
266                                 entity client = GetIndexedEntity(argc, 1);
267                                 float accepted = VerifyClientEntity(client, true, false);
268                                 string original_arg = argv(1);
269
270                                 if (accepted > 0)
271                                 {
272                                         string tmp_string = "";
273                                         FOREACH_WORD(autocvar_g_chatban_list, it != client.netaddress,
274                                         {
275                                                 if(client.crypto_idfp && it == substring(client.crypto_idfp, 0, strlen(it)))
276                                                         continue;
277                                                 tmp_string = cons(tmp_string, it);
278                                         });
279
280                                         cvar_set("g_chatban_list", tmp_string);
281                                         LOG_INFO(strcat("Unmuting player ", GetCallerName(client), " (", original_arg, ")."));
282                                         CS(client).muted = false;
283
284                                         return;
285                                 }
286                                 else
287                                 {
288                                         LOG_INFO("unmute: ", GetClientErrorString(accepted, argv(1)), ".");
289                                 }
290                         }
291                 }
292
293                 default:
294                         LOG_INFOF("Incorrect parameters for ^2%s^7", argv(0));
295                 case CMD_REQUEST_USAGE:
296                 {
297                         LOG_HELP("Usage:^3 sv_cmd unmute <client>");
298                         LOG_HELP("  <client> is the entity number or name of the player to unmute.");
299                         LOG_HELP("See also: ^2mute, g_chatban_list^7");
300                         return;
301                 }
302         }
303 }
304
305 void BanCommand_unplayban(int request, int argc)
306 {
307         switch (request)
308         {
309                 case CMD_REQUEST_COMMAND:
310                 {
311                         if (argv(1))
312                         {
313                                 entity client = GetIndexedEntity(argc, 1);
314                                 float accepted = VerifyClientEntity(client, true, false);
315                                 string original_arg = argv(1);
316
317                                 if (accepted > 0)
318                                 {
319                                         string tmp_string = "";
320                                         FOREACH_WORD(autocvar_g_playban_list, it != client.netaddress,
321                                         {
322                                                 if(client.crypto_idfp && it == substring(client.crypto_idfp, 0, strlen(it)))
323                                                         continue;
324                                                 tmp_string = cons(tmp_string, it);
325                                         });
326
327                                         cvar_set("g_playban_list", tmp_string);
328                                         LOG_INFO(strcat("Releasing forced to spectate player ", GetCallerName(client), " (", original_arg, ")."));
329
330                                         return;
331                                 }
332                                 else
333                                 {
334                                         LOG_INFO("unplayban: ", GetClientErrorString(accepted, argv(1)), ".");
335                                 }
336                         }
337                 }
338
339                 default:
340                 case CMD_REQUEST_USAGE:
341                 {
342                         LOG_HELP("Usage:^3 sv_cmd unplayban <banid>");
343                         LOG_HELP("  Where <banid> is the ID of the forced to spectate ban of which to remove.");
344                         LOG_HELP("See also: ^2playban, g_playban_list^7");
345                         return;
346                 }
347         }
348 }
349
350 void BanCommand_unvoteban(int request, int argc)
351 {
352         switch (request)
353         {
354                 case CMD_REQUEST_COMMAND:
355                 {
356                         if (argv(1))
357                         {
358                                 entity client = GetIndexedEntity(argc, 1);
359                                 float accepted = VerifyClientEntity(client, true, false);
360                                 string original_arg = argv(1);
361
362                                 if (accepted > 0)
363                                 {
364                                         string tmp_string = "";
365                                         FOREACH_WORD(autocvar_g_voteban_list, it != client.netaddress,
366                                         {
367                                                 if(client.crypto_idfp && it == substring(client.crypto_idfp, 0, strlen(it)))
368                                                         continue;
369                                                 tmp_string = cons(tmp_string, it);
370                                         });
371
372                                         cvar_set("g_voteban_list", tmp_string);
373                                         LOG_INFO(strcat("Unvote-banning player ", GetCallerName(client), " (", original_arg, ")."));
374
375                                         return;
376                                 }
377                                 else
378                                 {
379                                         LOG_INFO("unvoteban: ", GetClientErrorString(accepted, argv(1)), ".");
380                                 }
381                         }
382                 }
383
384                 default:
385                 case CMD_REQUEST_USAGE:
386                 {
387                         LOG_HELP("Usage:^3 sv_cmd unvoteban <banid>");
388                         LOG_HELP("  Where <banid> is the ID of the ban from voting of which to remove.");
389                         LOG_HELP("See also: ^2voteban, g_voteban_list^7");
390                         return;
391                 }
392         }
393 }
394
395 void BanCommand_voteban(int request, int argc, string command)
396 {
397         switch (request)
398         {
399                 case CMD_REQUEST_COMMAND:
400                 {
401                         if (argc >= 2)
402                         {
403                                 entity client = GetIndexedEntity(argc, 1);
404                                 float accepted = VerifyClientEntity(client, true, false);
405
406                                 if (accepted > 0)
407                                 {
408                                         string theid = "";
409                                         if(!PlayerInIPList(client, autocvar_g_voteban_list))
410                                                 theid = cons(theid, client.netaddress);
411                                         if(!PlayerInIDList(client, autocvar_g_voteban_list))
412                                                 theid = cons(theid, client.crypto_idfp);
413
414                                         LOG_INFO(strcat("Vote-banning player ", GetCallerName(client), " (", argv(1), ")."));
415                                         cvar_set("g_voteban_list", cons(autocvar_g_voteban_list, theid));
416
417                                         return;
418                                 }
419                                 else
420                                 {
421                                         LOG_INFO("voteban: ", GetClientErrorString(accepted, argv(1)), ".");
422                                 }
423                         }
424                 }
425
426                 default:
427                         LOG_INFOF("Incorrect parameters for ^2%s^7", argv(0));
428                 case CMD_REQUEST_USAGE:
429                 {
430                         LOG_HELP("Usage:^3 sv_cmd voteban <client>");
431                         LOG_HELP("  <client> is the entity number or name of the player to ban from voting,");
432                         LOG_HELP("See also: ^2g_voteban_list, unvoteban^7");
433                         return;
434                 }
435         }
436 }
437
438 /* use this when creating a new command, making sure to place it in alphabetical order... also,
439 ** ADD ALL NEW COMMANDS TO commands.cfg WITH PROPER ALIASES IN THE SAME FASHION!
440 void BanCommand_(int request)
441 {
442     switch(request)
443     {
444         case CMD_REQUEST_COMMAND:
445         {
446
447             return;
448         }
449
450         default:
451         case CMD_REQUEST_USAGE:
452         {
453             LOG_HELP("Usage:^3 sv_cmd ");
454             LOG_HELP("  No arguments required.");
455             return;
456         }
457     }
458 }
459 */
460
461
462 // ==================================
463 //  Macro system for server commands
464 // ==================================
465
466 // Do not hard code aliases for these, instead create them in commands.cfg... also: keep in alphabetical order, please ;)
467 #define BAN_COMMANDS(request, arguments, command) \
468         BAN_COMMAND("ban",          BanCommand_ban(request, arguments, command),        "Ban an IP address or a range of addresses (like 1.2.3)") \
469         BAN_COMMAND("banlist",      BanCommand_banlist(request),                        "List all existing bans") \
470         BAN_COMMAND("kickban",      BanCommand_kickban(request, arguments, command),    "Disconnect a client and ban it at the same time") \
471         BAN_COMMAND("mute",         BanCommand_mute(request, arguments, command),       "Disallow a client from talking by muting them") \
472         BAN_COMMAND("playban",      BanCommand_playban(request, arguments, command),    "Force to spectate a client permanently") \
473         BAN_COMMAND("unban",        BanCommand_unban(request, arguments),               "Remove an existing ban") \
474         BAN_COMMAND("unmute",       BanCommand_unmute(request, arguments),              "Unmute a client") \
475         BAN_COMMAND("unvoteban",    BanCommand_unvoteban(request, arguments),           "Remove an existing voting ban") \
476         BAN_COMMAND("unplayban",    BanCommand_unplayban(request, arguments),           "Remove an existing forced to spectate ban") \
477         BAN_COMMAND("voteban",      BanCommand_voteban(request, arguments, command),    "Disallow a client from voting") \
478         /* nothing */
479
480 void BanCommand_macro_help()
481 {
482         #define BAN_COMMAND(name, function, description) \
483                 { if (strtolower(description) != "") { LOG_INFO("  ^2", name, "^7: ", description); } }
484
485         BAN_COMMANDS(0, 0, "");
486 #undef BAN_COMMAND
487 }
488
489 float BanCommand_macro_command(int argc, string command)
490 {
491         #define BAN_COMMAND(name, function, description) \
492                 { if (name == strtolower(argv(0))) { function; return true; } }
493
494         BAN_COMMANDS(CMD_REQUEST_COMMAND, argc, command);
495 #undef BAN_COMMAND
496
497         return false;
498 }
499
500 float BanCommand_macro_usage(int argc)
501 {
502         #define BAN_COMMAND(name, function, description) \
503                 { if (name == strtolower(argv(1))) { function; return true; } }
504
505         BAN_COMMANDS(CMD_REQUEST_USAGE, argc, "");
506 #undef BAN_COMMAND
507
508         return false;
509 }
510
511 void BanCommand_macro_write_aliases(float fh)
512 {
513         #define BAN_COMMAND(name, function, description) \
514                 { if (strtolower(description) != "") { CMD_Write_Alias("qc_cmd_sv", name, description); } }
515
516         BAN_COMMANDS(0, 0, "");
517 #undef BAN_COMMAND
518 }
519
520 float BanCommand(string command)
521 {
522         int argc = tokenize_console(command);
523
524         // Guide for working with argc arguments by example:
525         // argc:   1    - 2      - 3     - 4
526         // argv:   0    - 1      - 2     - 3
527         // cmd     vote - master - login - password
528
529         if (BanCommand_macro_command(argc, command)) // continue as usual and scan for normal commands
530                 return true;                             // handled by one of the above GenericCommand_* functions
531
532         return false;
533 }