HLMOD.HU Forrás Megtekintés - www.hlmod.hu
  1. #include <amxmodx>
  2. #include <amxmisc>
  3. #include <cromchat>
  4.  
  5. //Comment this line to use on a mod different than Counter-Strike.
  6. #define USE_CSTRIKE
  7.  
  8. //Uncomment to log restrictions in the server's console.
  9. //#define CRX_CMDRESTRICTIONS_DEBUG
  10.  
  11. #if defined USE_CSTRIKE
  12. #include <cstrike>
  13. #endif
  14.  
  15. #define PLUGIN_VERSION "1.2"
  16. #define CMD_ARG_SAY "say"
  17. #define CMD_ARG_SAYTEAM "say_team"
  18. #define MAX_COMMANDS 128
  19. #define MAX_CMDLINE_LENGTH 128
  20. #define MAX_STATUS_LENGTH 12
  21. #define MAX_TYPE_LENGTH 12
  22. #define MAX_MSG_LENGTH 160
  23. #define INVALID_ENTRY -1
  24.  
  25. enum _:Types
  26. {
  27. TYPE_ALL,
  28. TYPE_NAME,
  29. TYPE_IP,
  30. TYPE_STEAM,
  31. TYPE_FLAGS,
  32. #if defined USE_CSTRIKE
  33. TYPE_TEAM,
  34. #endif
  35. TYPE_LIFE
  36. }
  37.  
  38. enum _:PlayerData
  39. {
  40. PDATA_NAME[32],
  41. PDATA_IP[20],
  42. PDATA_STEAM[35]
  43. }
  44.  
  45. enum _:RestrictionData
  46. {
  47. bool:Block,
  48. Type,
  49. #if defined USE_CSTRIKE
  50. CsTeams:ValueTeam,
  51. #endif
  52. ValueString[35],
  53. ValueInt,
  54. Message[MAX_MSG_LENGTH]
  55. }
  56.  
  57. new const g_szCommandArg[] = "$cmd$"
  58. new const g_szNoMessageArg[] = "#none"
  59. new const g_szLogs[] = "CommandRestrictions.log"
  60. new const g_szFilename[] = "CommandRestrictions.ini"
  61.  
  62. new Array:g_aRestrictions[MAX_COMMANDS],
  63. Trie:g_tCommands,
  64. g_ePlayerData[33][PlayerData],
  65. g_iTotalCommands = INVALID_ENTRY,
  66. g_iRestrictions[MAX_COMMANDS],
  67. g_szQueue[MAX_CMDLINE_LENGTH]
  68.  
  69. public plugin_init()
  70. {
  71. register_plugin("Command Restrictions", PLUGIN_VERSION, "OciXCrom")
  72. register_cvar("CRXCommandRestrictions", PLUGIN_VERSION, FCVAR_SERVER|FCVAR_SPONLY|FCVAR_UNLOGGED)
  73. register_dictionary("common.txt")
  74. }
  75.  
  76. public plugin_precache()
  77. {
  78. register_clcmd(CMD_ARG_SAY, "OnSay")
  79. register_clcmd(CMD_ARG_SAYTEAM, "OnSay")
  80. g_tCommands = TrieCreate()
  81. ReadFile()
  82. }
  83.  
  84. public plugin_end()
  85. {
  86. for(new i; i < g_iTotalCommands; i++)
  87. ArrayDestroy(g_aRestrictions[i])
  88.  
  89. TrieDestroy(g_tCommands)
  90. }
  91.  
  92. public client_putinserver(id)
  93. {
  94. get_user_name(id, g_ePlayerData[id][PDATA_NAME], charsmax(g_ePlayerData[][PDATA_NAME]))
  95. strtolower(g_ePlayerData[id][PDATA_NAME])
  96. get_user_ip(id, g_ePlayerData[id][PDATA_IP], charsmax(g_ePlayerData[][PDATA_IP]), 1)
  97. get_user_authid(id, g_ePlayerData[id][PDATA_STEAM], charsmax(g_ePlayerData[][PDATA_STEAM]))
  98. }
  99.  
  100. public client_infochanged(id)
  101. {
  102. if(!is_user_connected(id))
  103. return
  104.  
  105. static szNewName[32]
  106. get_user_info(id, "name", szNewName, charsmax(szNewName))
  107.  
  108. if(!equali(szNewName, g_ePlayerData[id][PDATA_NAME]))
  109. {
  110. copy(g_ePlayerData[id][PDATA_NAME], charsmax(g_ePlayerData[][PDATA_NAME]), szNewName)
  111. strtolower(g_ePlayerData[id][PDATA_NAME])
  112. }
  113. }
  114.  
  115. ReadFile()
  116. {
  117. new szConfigsName[256], szFilename[256]
  118. get_configsdir(szConfigsName, charsmax(szConfigsName))
  119. formatex(szFilename, charsmax(szFilename), "%s/%s", szConfigsName, g_szFilename)
  120. new iFilePointer = fopen(szFilename, "rt")
  121.  
  122. if(iFilePointer)
  123. {
  124. new szData[MAX_CMDLINE_LENGTH + MAX_STATUS_LENGTH + MAX_TYPE_LENGTH + MAX_MSG_LENGTH], szStatus[MAX_TYPE_LENGTH], szType[MAX_STATUS_LENGTH],\
  125. eItem[RestrictionData], bool:bQueue, iSize, iLine
  126.  
  127. while(!feof(iFilePointer))
  128. {
  129. fgets(iFilePointer, szData, charsmax(szData))
  130. trim(szData)
  131. iLine++
  132.  
  133. switch(szData[0])
  134. {
  135. case EOS, ';': continue
  136. case '[':
  137. {
  138. if(bQueue && g_iTotalCommands > INVALID_ENTRY)
  139. register_commands_in_queue()
  140.  
  141. iSize = strlen(szData)
  142.  
  143. if(szData[iSize - 1] != ']')
  144. {
  145. log_config_error(iLine, "Closing bracket not found for command ^"%s^"", szData[1])
  146. continue
  147. }
  148.  
  149. szData[0] = ' '
  150. szData[iSize - 1] = ' '
  151. trim(szData)
  152.  
  153. if(contain(szData, ",") != -1)
  154. {
  155. strtok(szData, szData, charsmax(szData), g_szQueue, charsmax(g_szQueue), ',')
  156. trim(szData); trim(g_szQueue)
  157. bQueue = true
  158. }
  159. else bQueue = false
  160.  
  161. if(contain(szData, CMD_ARG_SAY) != -1)
  162. {
  163. replace(szData, charsmax(szData), CMD_ARG_SAY, "")
  164. trim(szData)
  165. }
  166. else register_clcmd(szData, "OnRestrictedCommand")
  167.  
  168. g_aRestrictions[++g_iTotalCommands] = ArrayCreate(RestrictionData)
  169. TrieSetCell(g_tCommands, szData, g_iTotalCommands)
  170.  
  171. #if defined CRX_CMDRESTRICTIONS_DEBUG
  172. log_config_error(_, "RN #%i: %s", g_iTotalCommands, szData)
  173. #endif
  174. }
  175. default:
  176. {
  177. eItem[ValueString][0] = EOS
  178. eItem[Message][0] = EOS
  179. parse(szData, szStatus, charsmax(szStatus), szType, charsmax(szType), eItem[ValueString], charsmax(eItem[ValueString]), eItem[Message], charsmax(eItem[Message]))
  180.  
  181. switch(szStatus[0])
  182. {
  183. case 'A', 'a': eItem[Block] = false
  184. case 'B', 'b': eItem[Block] = true
  185. default:
  186. {
  187. log_config_error(iLine, "Unknown status type ^"%s^"", szStatus)
  188. continue
  189. }
  190. }
  191.  
  192. switch(szType[0])
  193. {
  194. case 'A', 'a': eItem[Type] = TYPE_ALL
  195. case 'N', 'n':
  196. {
  197. eItem[Type] = TYPE_NAME
  198.  
  199. if(!eItem[ValueString][0])
  200. {
  201. log_config_error(iLine, "Name not specified")
  202. continue
  203. }
  204. else
  205. strtolower(eItem[ValueString])
  206. }
  207. case 'I', 'i':
  208. {
  209. eItem[Type] = TYPE_IP
  210.  
  211. if(!eItem[ValueString][0])
  212. {
  213. log_config_error(iLine, "IP address not specified")
  214. continue
  215. }
  216. }
  217. case 'S', 's':
  218. {
  219. eItem[Type] = TYPE_STEAM
  220.  
  221. if(!eItem[ValueString][0])
  222. {
  223. log_config_error(iLine, "SteamID not specified")
  224. continue
  225. }
  226. }
  227. case 'F', 'f':
  228. {
  229. eItem[Type] = TYPE_FLAGS
  230.  
  231. if(!eItem[ValueString][0])
  232. {
  233. log_config_error(iLine, "Flag(s) not specified")
  234. continue
  235. }
  236. }
  237. #if defined USE_CSTRIKE
  238. case 'T', 't':
  239. {
  240. eItem[Type] = TYPE_TEAM
  241.  
  242. if(!eItem[ValueString][0])
  243. {
  244. log_config_error(iLine, "Flag(s) not specified")
  245. continue
  246. }
  247.  
  248. switch(eItem[ValueString][0])
  249. {
  250. case 'C', 'c': eItem[ValueTeam] = _:CS_TEAM_CT
  251. case 'T', 't': eItem[ValueTeam] = _:CS_TEAM_T
  252. case 'S', 's': eItem[ValueTeam] = _:CS_TEAM_SPECTATOR
  253. case 'U', 'u': eItem[ValueTeam] = _:CS_TEAM_UNASSIGNED
  254. default:
  255. {
  256. log_config_error(iLine, "Unknown team name ^"%s^"", eItem[ValueString])
  257. continue
  258. }
  259. }
  260. }
  261. #endif
  262. case 'L', 'l':
  263. {
  264. eItem[Type] = TYPE_LIFE
  265.  
  266. if(!eItem[ValueString][0])
  267. {
  268. log_config_error(iLine, "Life status not specified")
  269. continue
  270. }
  271.  
  272. switch(eItem[ValueString][0])
  273. {
  274. case 'A', 'a': eItem[ValueInt] = 1
  275. case 'D', 'd': eItem[ValueInt] = 0
  276. default:
  277. {
  278. log_config_error(iLine, "Unknown life status ^"%s^"", eItem[ValueString])
  279. continue
  280. }
  281. }
  282. }
  283. default:
  284. {
  285. log_config_error(iLine, "Unknown information type ^"%s^"", szType)
  286. continue
  287. }
  288. }
  289.  
  290. g_iRestrictions[g_iTotalCommands]++
  291. ArrayPushArray(g_aRestrictions[g_iTotalCommands], eItem)
  292. }
  293. }
  294. }
  295.  
  296. fclose(iFilePointer)
  297.  
  298. if(bQueue)
  299. register_commands_in_queue()
  300.  
  301. if(g_iTotalCommands == INVALID_ENTRY)
  302. {
  303. log_config_error(_, "No command restrictions found.")
  304. pause("ad")
  305. }
  306. }
  307. else
  308. {
  309. log_config_error(_, "Configuration file not found or cannot be opened.")
  310. pause("ad")
  311. }
  312. }
  313.  
  314. public OnSay(id)
  315. {
  316. new szArg[32], szCommand[32]
  317. read_argv(1, szArg, charsmax(szArg))
  318. parse(szArg, szCommand, charsmax(szCommand), szArg, charsmax(szArg))
  319.  
  320. if(!TrieKeyExists(g_tCommands, szCommand))
  321. return PLUGIN_CONTINUE
  322.  
  323. return is_restricted(id, szCommand) ? PLUGIN_HANDLED : PLUGIN_CONTINUE
  324. }
  325.  
  326. public OnRestrictedCommand(id)
  327. {
  328. new szCommand[32]
  329. read_argv(0, szCommand, charsmax(szCommand))
  330. return is_restricted(id, szCommand) ? PLUGIN_HANDLED : PLUGIN_CONTINUE
  331. }
  332.  
  333. bool:is_restricted(const id, const szCommand[])
  334. {
  335. static eItem[RestrictionData], bool:bBlock, iCommand, iAlive, i
  336. TrieGetCell(g_tCommands, szCommand, iCommand)
  337. bBlock = false
  338.  
  339. #if defined USE_CSTRIKE
  340. static CsTeams:iTeam
  341. #endif
  342.  
  343. iAlive = is_user_alive(id)
  344. iTeam = cs_get_user_team(id)
  345.  
  346. for(i = 0; i < g_iRestrictions[iCommand]; i++)
  347. {
  348. ArrayGetArray(g_aRestrictions[iCommand], i, eItem)
  349.  
  350. switch(eItem[Type])
  351. {
  352. case TYPE_ALL: bBlock = eItem[Block]
  353. case TYPE_NAME:
  354. {
  355. if(equal(g_ePlayerData[id][PDATA_NAME], eItem[ValueString]))
  356. {
  357. bBlock = eItem[Block]
  358.  
  359. if(bBlock)
  360. break
  361. }
  362. }
  363. case TYPE_IP:
  364. {
  365. if(equal(g_ePlayerData[id][PDATA_IP], eItem[ValueString]))
  366. {
  367. bBlock = eItem[Block]
  368.  
  369. if(bBlock)
  370. break
  371. }
  372. }
  373. case TYPE_STEAM:
  374. {
  375. if(equal(g_ePlayerData[id][PDATA_STEAM], eItem[ValueString]))
  376. {
  377. bBlock = eItem[Block]
  378.  
  379. if(bBlock)
  380. break
  381. }
  382. }
  383. case TYPE_FLAGS:
  384. {
  385. if(has_all_flags(id, eItem[ValueString]))
  386. {
  387. bBlock = eItem[Block]
  388.  
  389. if(bBlock)
  390. break
  391. }
  392. }
  393. #if defined USE_CSTRIKE
  394. case TYPE_TEAM:
  395. {
  396. if(iTeam == eItem[ValueTeam])
  397. {
  398. bBlock = eItem[Block]
  399.  
  400. if(bBlock)
  401. break
  402. }
  403. }
  404. #endif
  405. case TYPE_LIFE:
  406. {
  407. if(iAlive == eItem[ValueInt])
  408. {
  409. bBlock = eItem[Block]
  410.  
  411. if(bBlock)
  412. break
  413. }
  414. }
  415. }
  416. }
  417.  
  418. if(bBlock)
  419. {
  420. if(eItem[Message][0])
  421. {
  422. if(equal(eItem[Message], g_szNoMessageArg))
  423. return true
  424.  
  425. static szMessage[MAX_MSG_LENGTH]
  426. copy(szMessage, charsmax(szMessage), eItem[Message])
  427. replace_all(szMessage, charsmax(szMessage), g_szCommandArg, szCommand)
  428. client_print(id, print_console, szMessage)
  429. CC_SendMessage(id, szMessage)
  430. }
  431. else
  432. {
  433. client_print(id, print_console, "%L (%s)", id, "NO_ACC_COM", szCommand)
  434. CC_SendMessage(id, "&x07%L &x01(&x04%s&x01)", id, "NO_ACC_COM", szCommand)
  435. }
  436.  
  437. return true
  438. }
  439.  
  440. return false
  441. }
  442.  
  443. register_commands_in_queue()
  444. {
  445. static szData[MAX_CMDLINE_LENGTH]
  446.  
  447. while(g_szQueue[0] != 0 && strtok(g_szQueue, szData, charsmax(szData), g_szQueue, charsmax(g_szQueue), ','))
  448. {
  449. trim(g_szQueue); trim(szData)
  450.  
  451. if(contain(szData, CMD_ARG_SAY) != -1)
  452. {
  453. replace(szData, charsmax(szData), CMD_ARG_SAY, "")
  454. trim(szData)
  455. }
  456. else register_clcmd(szData, "OnRestrictedCommand")
  457. TrieSetCell(g_tCommands, szData, g_iTotalCommands)
  458.  
  459. #if defined CRX_CMDRESTRICTIONS_DEBUG
  460. log_config_error(_, "RQ #%i: %s", g_iTotalCommands, szData)
  461. #endif
  462. }
  463.  
  464. g_szQueue[0] = EOS
  465. }
  466.  
  467. log_config_error(const iLine = INVALID_ENTRY, const szInput[], any:...)
  468. {
  469. new szError[128]
  470. vformat(szError, charsmax(szError), szInput, 3)
  471.  
  472. if(iLine == INVALID_ENTRY)
  473. log_to_file(g_szLogs, "%s: %s", g_szFilename, szError)
  474. else
  475. log_to_file(g_szLogs, "%s (%i): %s", g_szFilename, iLine, szError)
  476. }