diff --git a/core/Makefile b/core/Makefile index 0e83152b..7226cf2c 100644 --- a/core/Makefile +++ b/core/Makefile @@ -18,7 +18,7 @@ OBJECTS = AdminCache.cpp CDataPack.cpp ConCmdManager.cpp ConVarManager.cpp CoreC sm_autonatives.cpp sm_memtable.cpp sm_srvcmds.cpp sm_stringutil.cpp sm_trie.cpp \ sourcemm_api.cpp sourcemod.cpp MenuStyle_Base.cpp MenuStyle_Valve.cpp MenuManager.cpp \ MenuStyle_Radio.cpp ChatTriggers.cpp ADTFactory.cpp MenuVoting.cpp sm_crc32.cpp \ - frame_hooks.cpp concmd_cleaner.cpp Profiler.cpp PhraseCollection.cpp NextMap.cpp \ + frame_hooks.cpp concmd_cleaner.cpp PhraseCollection.cpp NextMap.cpp \ NativeOwner.cpp logic_bridge.cpp OBJECTS += smn_admin.cpp smn_bitbuffer.cpp smn_console.cpp smn_core.cpp \ smn_datapacks.cpp smn_entities.cpp smn_events.cpp smn_fakenatives.cpp \ @@ -26,7 +26,7 @@ OBJECTS += smn_admin.cpp smn_bitbuffer.cpp smn_console.cpp smn_core.cpp \ smn_handles.cpp smn_keyvalues.cpp smn_banning.cpp \ smn_lang.cpp smn_player.cpp smn_string.cpp smn_timers.cpp \ smn_usermsgs.cpp smn_menus.cpp smn_database.cpp smn_vector.cpp \ - smn_adt_trie.cpp smn_hudtext.cpp smn_nextmap.cpp + smn_hudtext.cpp smn_nextmap.cpp OBJECTS += ExtensionSys.cpp \ ForwardSys.cpp \ HandleSys.cpp \ diff --git a/core/logic/Makefile b/core/logic/Makefile index b235f975..8ef9c957 100644 --- a/core/logic/Makefile +++ b/core/logic/Makefile @@ -22,7 +22,9 @@ OBJECTS = \ ThreadSupport.cpp \ smn_float.cpp \ TextParsers.cpp \ - smn_textparse.cpp + smn_textparse.cpp \ + smn_adt_trie.cpp \ + Profiler.cpp ############################################## ### CONFIGURE ANY OTHER FLAGS/OPTIONS HERE ### diff --git a/core/Profiler.cpp b/core/logic/Profiler.cpp similarity index 85% rename from core/Profiler.cpp rename to core/logic/Profiler.cpp index fab086fb..5354ca2f 100644 --- a/core/Profiler.cpp +++ b/core/logic/Profiler.cpp @@ -30,13 +30,12 @@ */ #include "Profiler.h" -#include "PluginSys.h" -#include "sm_stringutil.h" -#include "Logger.h" +#include #if defined PLATFORM_POSIX #include #include #endif +#include ProfileEngine g_Profiler; IProfiler *sm_profiler = &g_Profiler; @@ -314,28 +313,28 @@ void ProfileEngine::Clear() void ProfileEngine::OnSourceModAllInitialized() { - g_RootMenu.AddRootConsoleCommand("profiler", "Profiler commands", this); + rootmenu->AddRootConsoleCommand2("profiler", "Profiler commands", this); } void ProfileEngine::OnSourceModShutdown() { - g_RootMenu.RemoveRootConsoleCommand("profiler", this); + rootmenu->RemoveRootConsoleCommand("profiler", this); } -void ProfileEngine::OnRootConsoleCommand(const char *cmdname, const CCommand &command) +void ProfileEngine::OnRootConsoleCommand2(const char *cmdname, const ICommandArgs *command) { - if (command.ArgC() >= 3) + if (command->ArgC() >= 3) { - if (strcmp(command.Arg(2), "flush") == 0) + if (strcmp(command->Arg(2), "flush") == 0) { FILE *fp; char path[256]; - g_SourceMod.BuildPath(Path_SM, path, sizeof(path), "logs/profile_%d.xml", (int)time(NULL)); + g_pSM->BuildPath(Path_SM, path, sizeof(path), "logs/profile_%d.xml", (int)time(NULL)); if ((fp = fopen(path, "wt")) == NULL) { - g_RootMenu.ConsolePrint("Failed, could not open file for writing: %s", path); + rootmenu->ConsolePrint("Failed, could not open file for writing: %s", path); return; } @@ -343,14 +342,14 @@ void ProfileEngine::OnRootConsoleCommand(const char *cmdname, const CCommand &co fclose(fp); - g_RootMenu.ConsolePrint("Profiler report generated as: %s\n", path); + rootmenu->ConsolePrint("Profiler report generated as: %s\n", path); return; } } - g_RootMenu.ConsolePrint("Profiler commands:"); - g_RootMenu.DrawGenericOption("flush", "Flushes statistics to disk and starts over"); + rootmenu->ConsolePrint("Profiler commands:"); + rootmenu->DrawGenericOption("flush", "Flushes statistics to disk and starts over"); } bool ProfileEngine::GenerateReport(FILE *fp) @@ -387,9 +386,9 @@ void ProfileEngine::WriteReport(FILE *fp, ProfileReport *report, const char *nam { ar = report->GetReport(i); - strncopy(new_name, ar->atom_name, sizeof(new_name)); - UTIL_ReplaceAll(new_name, sizeof(new_name), "<", "<"); - UTIL_ReplaceAll(new_name, sizeof(new_name), ">", ">"); + smcore.strncopy(new_name, ar->atom_name, sizeof(new_name)); + smcore.ReplaceAll(new_name, sizeof(new_name), "<", "<", true); + smcore.ReplaceAll(new_name, sizeof(new_name), ">", ">", true); fprintf(fp, " \n", new_name, @@ -438,20 +437,20 @@ void ProfileReport::SaveAtom(const prof_atom_t &atom) if (atom.atom_type == SP_PROF_NATIVES) { - strncopy(full_name, atom.name, sizeof(full_name)); + smcore.strncopy(full_name, atom.name, sizeof(full_name)); } else { - CPlugin *pl; + IPlugin *pl; const char *file; file = "unknown"; - if ((pl = g_PluginSys.GetPluginByCtx(atom.ctx)) != NULL) + if ((pl = pluginsys->FindPluginByContext(atom.ctx)) != NULL) { file = pl->GetFilename(); } - UTIL_Format(full_name, sizeof(full_name), "%s!%s", file, atom.name); + smcore.Format(full_name, sizeof(full_name), "%s!%s", file, atom.name); } atom_time = CalcAtomTime(atom); @@ -460,7 +459,7 @@ void ProfileReport::SaveAtom(const prof_atom_t &atom) { report = new prof_atom_report_t; - strncopy(report->atom_name, full_name, sizeof(report->atom_name)); + smcore.strncopy(report->atom_name, full_name, sizeof(report->atom_name)); report->max_time = atom_time; report->min_time = atom_time; report->num_calls = 1; diff --git a/core/Profiler.h b/core/logic/Profiler.h similarity index 93% rename from core/Profiler.h rename to core/logic/Profiler.h index b6588f49..471724cd 100644 --- a/core/Profiler.h +++ b/core/logic/Profiler.h @@ -38,8 +38,8 @@ #include #include #include -#include "sm_globals.h" -#include "sm_srvcmds.h" +#include "common_logic.h" +#include using namespace SourcePawn; using namespace SourceHook; @@ -103,7 +103,7 @@ public: //SMGlobalClass void OnSourceModAllInitialized(); void OnSourceModShutdown(); public: //IRootConsoleCommand - void OnRootConsoleCommand(const char *cmdname, const CCommand &command); + void OnRootConsoleCommand2(const char *cmdname, const ICommandArgs *command); public: //IProfiler void OnNativeBegin(IPluginContext *pContext, sp_native_t *native); void OnNativeEnd() ; diff --git a/core/logic/common_logic.cpp b/core/logic/common_logic.cpp index 7a75fe73..3049a782 100644 --- a/core/logic/common_logic.cpp +++ b/core/logic/common_logic.cpp @@ -45,6 +45,8 @@ ILibrarySys *libsys; ITextParsers *textparser = &g_TextParser; IVEngineServer *engine; IShareSys *sharesys; +IRootConsole *rootmenu; +IPluginManager *pluginsys; static sm_logic_t logic = { @@ -65,6 +67,8 @@ static void logic_init(const sm_core_t* core, sm_logic_t* _logic) g_pCoreIdent = core->core_ident; g_pSM = core->sm; sharesys = core->sharesys; + rootmenu = core->rootmenu; + pluginsys = core->pluginsys; } PLATFORM_EXTERN_C ITextParsers *get_textparsers() diff --git a/core/logic/common_logic.h b/core/logic/common_logic.h index 5084acda..96e51ca7 100644 --- a/core/logic/common_logic.h +++ b/core/logic/common_logic.h @@ -44,6 +44,8 @@ extern ILibrarySys *libsys; extern ITextParsers *textparser; extern IVEngineServer *engine; extern IShareSys *sharesys; +extern IRootConsole *rootmenu; +extern IPluginManager *pluginsys; #endif /* _INCLUDE_SOURCEMOD_COMMON_LOGIC_H_ */ diff --git a/core/logic/intercom.h b/core/logic/intercom.h index f9e80522..b6d489bf 100644 --- a/core/logic/intercom.h +++ b/core/logic/intercom.h @@ -42,7 +42,7 @@ using namespace SourceMod; * Add 1 to the RHS of this expression to bump the intercom file * This is to prevent mismatching core/logic binaries */ -#define SM_LOGIC_MAGIC (0x0F47C0DE - 0) +#define SM_LOGIC_MAGIC (0x0F47C0DE - 1) #if defined SM_LOGIC class IVEngineServer @@ -60,6 +60,8 @@ namespace SourceMod class ILibrarySys; class ITextParsers; class IThreader; + class IRootConsole; + class IPluginManager; } class IVEngineServer; @@ -74,6 +76,8 @@ struct sm_core_t ILibrarySys *libsys; IVEngineServer *engine; IShareSys *sharesys; + IRootConsole *rootmenu; + IPluginManager *pluginsys; /* Functions */ void (*AddNatives)(sp_nativeinfo_t* nlist); ConVar * (*FindConVar)(const char*); @@ -82,12 +86,14 @@ struct sm_core_t void (*LogError)(const char*, ...); const char * (*GetCvarString)(ConVar*); size_t (*Format)(char*, size_t, const char*, ...); + unsigned int (*ReplaceAll)(char*, size_t, const char *, const char *, bool); }; struct sm_logic_t { SMGlobalClass *head; IThreader *threader; + IProfiler *profiler; }; typedef void (*LogicInitFunction)(const sm_core_t *core, sm_logic_t *logic); diff --git a/core/smn_adt_trie.cpp b/core/logic/smn_adt_trie.cpp similarity index 87% rename from core/smn_adt_trie.cpp rename to core/logic/smn_adt_trie.cpp index 623e2dd6..f09e82a2 100644 --- a/core/smn_adt_trie.cpp +++ b/core/logic/smn_adt_trie.cpp @@ -30,10 +30,8 @@ */ #include -#include "sm_globals.h" -#include "sm_stringutil.h" -#include "HandleSys.h" -#include "sm_trie_tpl.h" +#include "common_logic.h" +#include HandleType_t htCellTrie; @@ -85,11 +83,11 @@ class TrieHelpers : public: //SMGlobalClass void OnSourceModAllInitialized() { - htCellTrie = g_HandleSys.CreateType("Trie", this, 0, NULL, NULL, g_pCoreIdent, NULL); + htCellTrie = handlesys->CreateType("Trie", this, 0, NULL, NULL, g_pCoreIdent, NULL); } void OnSourceModShutdown() { - g_HandleSys.RemoveType(htCellTrie, g_pCoreIdent); + handlesys->RemoveType(htCellTrie, g_pCoreIdent); } public: //IHandleTypeDispatch static void DestroySmartTrieNode(SmartTrieNode *pNode) @@ -119,7 +117,7 @@ static cell_t CreateTrie(IPluginContext *pContext, const cell_t *params) pTrie->mem_usage = 0; - if ((hndl = g_HandleSys.CreateHandle(htCellTrie, pTrie, pContext->GetIdentity(), g_pCoreIdent, NULL)) + if ((hndl = handlesys->CreateHandle(htCellTrie, pTrie, pContext->GetIdentity(), g_pCoreIdent, NULL)) == BAD_HANDLE) { delete pTrie; @@ -191,7 +189,7 @@ static cell_t SetTrieValue(IPluginContext *pContext, const cell_t *params) hndl = params[1]; - if ((err = g_HandleSys.ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) + if ((err = handlesys->ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) != HandleError_None) { return pContext->ThrowNativeError("Invalid Handle %x (error %d)", hndl, err); @@ -227,7 +225,7 @@ static cell_t SetTrieArray(IPluginContext *pContext, const cell_t *params) hndl = params[1]; - if ((err = g_HandleSys.ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) + if ((err = handlesys->ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) != HandleError_None) { return pContext->ThrowNativeError("Invalid Handle %x (error %d)", hndl, err); @@ -275,7 +273,7 @@ static cell_t SetTrieString(IPluginContext *pContext, const cell_t *params) hndl = params[1]; - if ((err = g_HandleSys.ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) + if ((err = handlesys->ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) != HandleError_None) { return pContext->ThrowNativeError("Invalid Handle %x (error %d)", hndl, err); @@ -317,7 +315,7 @@ static cell_t RemoveFromTrie(IPluginContext *pContext, const cell_t *params) hndl = params[1]; - if ((err = g_HandleSys.ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) + if ((err = handlesys->ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) != HandleError_None) { return pContext->ThrowNativeError("Invalid Handle %x (error %d)", hndl, err); @@ -347,7 +345,7 @@ static cell_t ClearTrie(IPluginContext *pContext, const cell_t *params) hndl = params[1]; - if ((err = g_HandleSys.ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) + if ((err = handlesys->ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) != HandleError_None) { return pContext->ThrowNativeError("Invalid Handle %x (error %d)", hndl, err); @@ -368,7 +366,7 @@ static cell_t GetTrieValue(IPluginContext *pContext, const cell_t *params) hndl = params[1]; - if ((err = g_HandleSys.ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) + if ((err = handlesys->ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) != HandleError_None) { return pContext->ThrowNativeError("Invalid Handle %x (error %d)", hndl, err); @@ -403,7 +401,7 @@ static cell_t GetTrieArray(IPluginContext *pContext, const cell_t *params) hndl = params[1]; - if ((err = g_HandleSys.ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) + if ((err = handlesys->ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) != HandleError_None) { return pContext->ThrowNativeError("Invalid Handle %x (error %d)", hndl, err); @@ -460,7 +458,7 @@ static cell_t GetTrieString(IPluginContext *pContext, const cell_t *params) hndl = params[1]; - if ((err = g_HandleSys.ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) + if ((err = handlesys->ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) != HandleError_None) { return pContext->ThrowNativeError("Invalid Handle %x (error %d)", hndl, err); @@ -507,7 +505,7 @@ static cell_t GetTrieSize(IPluginContext *pContext, const cell_t *params) hndl = params[1]; - if ((err = g_HandleSys.ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) + if ((err = handlesys->ReadHandle(hndl, htCellTrie, &sec, (void **)&pTrie)) != HandleError_None) { return pContext->ThrowNativeError("Invalid Handle %x (error %d)", hndl, err); diff --git a/core/logic_bridge.cpp b/core/logic_bridge.cpp index 71440dfe..e6e8df2c 100644 --- a/core/logic_bridge.cpp +++ b/core/logic_bridge.cpp @@ -41,6 +41,7 @@ #include "sm_stringutil.h" #include "Logger.h" #include "ShareSys.h" +#include "sm_srvcmds.h" static ILibrary *g_pLogic = NULL; static LogicInitFunction logic_init_fn; @@ -92,6 +93,8 @@ static sm_core_t core_bridge = &g_LibSys, reinterpret_cast(&logic_engine), &g_ShareSys, + &g_RootMenu, + &g_PluginSys, /* Functions */ add_natives, find_convar, @@ -119,6 +122,7 @@ void InitLogicBridge() glob->m_pGlobalClassNext = logic.head; g_pThreader = logic.threader; + g_pSourcePawn2->SetProfiler(logic.profiler); } bool StartLogicBridge(char *error, size_t maxlength) diff --git a/core/sm_srvcmds.cpp b/core/sm_srvcmds.cpp index d73dd95a..785dee95 100644 --- a/core/sm_srvcmds.cpp +++ b/core/sm_srvcmds.cpp @@ -1,8 +1,8 @@ /** - * vim: set ts=4 : + * vim: set ts=4 sw=4 : * ============================================================================= * SourceMod - * Copyright (C) 2004-2008 AlliedModders LLC. All rights reserved. + * Copyright (C) 2004-2009 AlliedModders LLC. All rights reserved. * ============================================================================= * * This program is free software; you can redistribute it and/or modify it under @@ -116,14 +116,25 @@ void RootConsoleMenu::ConsolePrint(const char *fmt, ...) } bool RootConsoleMenu::AddRootConsoleCommand(const char *cmd, const char *text, IRootConsoleCommand *pHandler) +{ + return _AddRootConsoleCommand(cmd, text, pHandler, false); +} + +bool RootConsoleMenu::AddRootConsoleCommand2(const char *cmd, const char *text, IRootConsoleCommand *pHandler) +{ + return _AddRootConsoleCommand(cmd, text, pHandler, true); +} + +bool RootConsoleMenu::_AddRootConsoleCommand(const char *cmd, + const char *text, + IRootConsoleCommand *pHandler, + bool version2) { if (sm_trie_retrieve(m_pCommands, cmd, NULL)) { return false; } - sm_trie_insert(m_pCommands, cmd, pHandler); - /* Sort this into the menu */ List::iterator iter = m_Menu.begin(); ConsoleEntry *pEntry; @@ -136,6 +147,9 @@ bool RootConsoleMenu::AddRootConsoleCommand(const char *cmd, const char *text, I ConsoleEntry *pNew = new ConsoleEntry; pNew->command.assign(cmd); pNew->description.assign(text); + pNew->version2 = version2; + pNew->cmd = pHandler; + sm_trie_insert(m_pCommands, cmd, pNew); m_Menu.insert(iter, pNew); inserted = true; break; @@ -148,6 +162,9 @@ bool RootConsoleMenu::AddRootConsoleCommand(const char *cmd, const char *text, I ConsoleEntry *pNew = new ConsoleEntry; pNew->command.assign(cmd); pNew->description.assign(text); + pNew->version2 = version2; + pNew->cmd = pHandler; + sm_trie_insert(m_pCommands, cmd, pNew); m_Menu.push_back(pNew); } @@ -156,18 +173,6 @@ bool RootConsoleMenu::AddRootConsoleCommand(const char *cmd, const char *text, I bool RootConsoleMenu::RemoveRootConsoleCommand(const char *cmd, IRootConsoleCommand *pHandler) { - /* Sanity tests */ - IRootConsoleCommand *object; - if (sm_trie_retrieve(m_pCommands, cmd, (void **)&object)) - { - if (object != pHandler) - { - return false; - } - } else { - return false; - } - sm_trie_delete(m_pCommands, cmd); List::iterator iter; @@ -214,6 +219,49 @@ unsigned int RootConsoleMenu::GetInterfaceVersion() return SMINTERFACE_ROOTCONSOLE_VERSION; } +#if SOURCE_ENGINE==SE_EPISODEONE || SOURCE_ENGINE==SE_DARKMESSIAH +class CCommandArgs : public ICommandArgs +{ +public: + CCommandArgs(const CCommand& _cmd) + { + } + const char *Arg(int n) const + { + return engine->Cmd_Argv(n); + } + int ArgC() const + { + return engine->Cmd_Argc(); + } + const char *ArgS() const + { + return engine->Cmd_Args(); + } +}; +#else +class CCommandArgs : public ICommandArgs +{ + const CCommand *cmd; +public: + CCommandArgs(const CCommand& _cmd) : cmd(&_cmd) + { + } + const char *Arg(int n) const + { + return cmd->Arg(n); + } + int ArgC() const + { + return cmd->ArgC(); + } + const char *ArgS() const + { + return cmd->ArgS(); + } +}; +#endif + void RootConsoleMenu::GotRootCmd(const CCommand &cmd) { unsigned int argnum = cmd.ArgC(); @@ -241,10 +289,19 @@ void RootConsoleMenu::GotRootCmd(const CCommand &cmd) return; } - IRootConsoleCommand *pHandler; - if (sm_trie_retrieve(m_pCommands, cmdname, (void **)&pHandler)) + CCommandArgs ocmd(cmd); + + ConsoleEntry *entry; + if (sm_trie_retrieve(m_pCommands, cmdname, (void **)&entry)) { - pHandler->OnRootConsoleCommand(cmdname, cmd); + if (entry->version2) + { + entry->cmd->OnRootConsoleCommand2(cmdname, &ocmd); + } + else + { + entry->cmd->OnRootConsoleCommand(cmdname, cmd); + } return; } } @@ -357,3 +414,4 @@ CON_COMMAND(sm_dump_handles, "Dumps Handle usage to a file for finding Handle le g_HandleSys.Dump(write_handles_to_game); } } + diff --git a/core/sm_srvcmds.h b/core/sm_srvcmds.h index ea8d172b..6f6d3771 100644 --- a/core/sm_srvcmds.h +++ b/core/sm_srvcmds.h @@ -1,8 +1,8 @@ /** - * vim: set ts=4 : + * vim: set ts=4 sw=4 : * ============================================================================= * SourceMod - * Copyright (C) 2004-2008 AlliedModders LLC. All rights reserved. + * Copyright (C) 2004-2009 AlliedModders LLC. All rights reserved. * ============================================================================= * * This program is free software; you can redistribute it and/or modify it under @@ -48,6 +48,8 @@ struct ConsoleEntry { String command; String description; + bool version2; + IRootConsoleCommand *cmd; }; class RootConsoleMenu : @@ -75,6 +77,13 @@ public: //IRootConsole bool RemoveRootConsoleCommand(const char *cmd, IRootConsoleCommand *pHandler); void ConsolePrint(const char *fmt, ...); void DrawGenericOption(const char *cmd, const char *text); + bool AddRootConsoleCommand2(const char *cmd, + const char *text, + IRootConsoleCommand *pHandler); + bool _AddRootConsoleCommand(const char *cmd, + const char *text, + IRootConsoleCommand *pHandler, + bool version2); public: void GotRootCmd(const CCommand &cmd); private: diff --git a/core/sourcemod.cpp b/core/sourcemod.cpp index 88dbb4f5..aa6b38bc 100644 --- a/core/sourcemod.cpp +++ b/core/sourcemod.cpp @@ -47,7 +47,6 @@ #include "TimerSys.h" #include "GameConfigs.h" #include "DebugReporter.h" -#include "Profiler.h" #include "frame_hooks.h" #include "logic_bridge.h" @@ -244,7 +243,6 @@ bool SourceModBase::InitializeSourceMod(char *error, size_t maxlength, bool late } g_pSourcePawn2->SetDebugListener(&g_DbgReporter); - g_pSourcePawn2->SetProfiler(&g_Profiler); /* Hook this now so we can detect startup without calling StartSourceMod() */ SH_ADD_HOOK_MEMFUNC(IServerGameDLL, LevelInit, gamedll, this, &SourceModBase::LevelInit, false); diff --git a/public/IRootConsoleMenu.h b/public/IRootConsoleMenu.h index 4adfc3ae..98804f38 100644 --- a/public/IRootConsoleMenu.h +++ b/public/IRootConsoleMenu.h @@ -1,8 +1,8 @@ /** - * vim: set ts=4 : + * vim: set ts=4 sw=4 : * ============================================================================= * SourceMod - * Copyright (C) 2004-2008 AlliedModders LLC. All rights reserved. + * Copyright (C) 2004-2009 AlliedModders LLC. All rights reserved. * ============================================================================= * * This program is free software; you can redistribute it and/or modify it under @@ -41,19 +41,54 @@ */ #define SMINTERFACE_ROOTCONSOLE_NAME "IRootConsole" -#define SMINTERFACE_ROOTCONSOLE_VERSION 1 +#define SMINTERFACE_ROOTCONSOLE_VERSION 2 class CCommand; namespace SourceMod { + /** + * @brief Wrapper around CCommand. + */ + class ICommandArgs + { + public: + /** + * @brief Returns an argument by number. + * + * @brief n Argument number. + * @return Argument string. + */ + virtual const char *Arg(int n) const = 0; + + /** + * @brief Returns the argument count. + * + * @return Argument count. + */ + virtual int ArgC() const = 0; + + /** + * @brief Returns the full argument string. + * + * @return Argument string. + */ + virtual const char *ArgS() const = 0; + }; + /** * @brief Handles a root console menu action. */ class IRootConsoleCommand { public: - virtual void OnRootConsoleCommand(const char *cmdname, const CCommand &command) =0; + virtual void OnRootConsoleCommand(const char *cmdname, const CCommand &command) + { + } + + virtual void OnRootConsoleCommand2(const char *cmdname, const ICommandArgs *args) + { + } }; /** @@ -99,7 +134,22 @@ namespace SourceMod * @param text String containing the command description. */ virtual void DrawGenericOption(const char *cmd, const char *text) =0; + + /** + * @brief Adds a root console command handler. The command must be unique. + * + * This version of the function uses the OnRootConsoleCommand2 callback. + * + * @param cmd String containing the console command. + * @param text Description text. + * @param pHandler An IRootConsoleCommand pointer to handle the command. + * @return True on success, false on too many commands or duplicate command. + */ + virtual bool AddRootConsoleCommand2(const char *cmd, + const char *text, + IRootConsoleCommand *pHandler) =0; }; } #endif //_INCLUDE_SOURCEMOD_ROOT_CONSOLE_MENU_H_ +