Daemon666 / CSB Command Access Publiczny

Maps arbitrary console/chat commands to access flags in an ini and blocks anyone without the flag - no recompiling.

v1.0.0 176 pobrań GPL-3.0 Ostatnia aktualizacja Aug 22, 2026
csb_command_access.sma v1.0.0 128 wierszy · 3.4 KB Surowy
1 /*
2 * CSB Command Access
3 * Copyright (C) 2026 counter-strike-boost.com
4 *
5 * Maps arbitrary console/chat commands to access flags from
6 * configs/csb_cmdaccess.ini. Each mapped command is registered and, when a
7 * player without the flag runs it, the plugin blocks it (PLUGIN_HANDLED) and
8 * prints a denial. Lets owners restrict third-party or say-based commands
9 * without recompiling them.
10 *
11 * This program is free software: you can redistribute it and/or modify it under
12 * the terms of the GNU General Public License as published by the Free Software
13 * Foundation, either version 3 of the License, or (at your option) any later
14 * version. It is distributed in the hope that it will be useful, but WITHOUT
15 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
16 * FOR A PARTICULAR PURPOSE. See <https://www.gnu.org/licenses/> for details.
17 */
18
19 #include <amxmodx>
20 #include <amxmisc>
21
22 #define MAX_RULES 48
23
24 new const PLUGIN[] = "CSB Command Access"
25 new const VERSION[] = "1.0.0"
26 new const AUTHOR[] = "counter-strike-boost.com"
27
28 new g_szCmd[MAX_RULES][40]
29 new g_iFlags[MAX_RULES]
30 new g_iRuleCount = 0
31
32 new g_pEnabled
33
34 public plugin_init()
35 {
36 register_plugin(PLUGIN, VERSION, AUTHOR)
37
38 g_pEnabled = register_cvar("csb_cmdaccess_enabled", "1")
39
40 loadRules()
41 }
42
43 loadRules()
44 {
45 new dir[128]
46 get_localinfo("amxx_configsdir", dir, charsmax(dir))
47
48 new path[160]
49 formatex(path, charsmax(path), "%s/csb_cmdaccess.ini", dir)
50
51 if (!file_exists(path))
52 {
53 write_file(path, "; CSB Command Access - one rule per line: <command> <flags>")
54 write_file(path, "; the command is blocked for anyone missing the flags.")
55 write_file(path, "; example: restrict the say-based command /rtv to reserved slots")
56 write_file(path, "; say /rtv a")
57 }
58
59 new f = fopen(path, "rt")
60
61 if (!f)
62 {
63 log_amx("[CSB CmdAccess] could not open %s", path)
64 return
65 }
66
67 new line[96], cmd[40], flagStr[24]
68
69 while (!feof(f) && g_iRuleCount < MAX_RULES)
70 {
71 fgets(f, line, charsmax(line))
72 trim(line)
73
74 if (!line[0] || line[0] == ';' || line[0] == '#')
75 continue
76
77 strtok(line, cmd, charsmax(cmd), flagStr, charsmax(flagStr), ' ')
78 trim(cmd)
79 trim(flagStr)
80
81 if (!cmd[0] || !flagStr[0])
82 continue
83
84 copy(g_szCmd[g_iRuleCount], charsmax(g_szCmd[]), cmd)
85 g_iFlags[g_iRuleCount] = read_flags(flagStr)
86
87 register_clcmd(cmd, "blockCheck")
88 g_iRuleCount++
89 }
90
91 fclose(f)
92
93 log_amx("[CSB CmdAccess] loaded %d rule(s).", g_iRuleCount)
94 }
95
96 public blockCheck(id)
97 {
98 if (!get_pcvar_num(g_pEnabled))
99 return PLUGIN_CONTINUE
100
101 new cmd[40]
102 read_argv(0, cmd, charsmax(cmd))
103
104 /* say-based commands arrive as "say" + argv1; rebuild the full command */
105 if (equali(cmd, "say") || equali(cmd, "say_team"))
106 {
107 new rest[64]
108 read_args(rest, charsmax(rest))
109 remove_quotes(rest)
110 trim(rest)
111 formatex(cmd, charsmax(cmd), "%s %s", equali(cmd, "say") ? "say" : "say_team", rest)
112 }
113
114 for (new i = 0; i < g_iRuleCount; i++)
115 {
116 if (!equali(cmd, g_szCmd[i]))
117 continue
118
119 if (get_user_flags(id) & g_iFlags[i])
120 return PLUGIN_CONTINUE
121
122 client_print(id, print_chat, "[CSB] You do not have access to that command.")
123 return PLUGIN_HANDLED
124 }
125
126 return PLUGIN_CONTINUE
127 }
128