core/sm_srvcmds.cpp
author Scott Ehlert <ds@alliedmods.net>
Wed Aug 15 06:19:30 2007 +0000 (2007-08-15)
changeset 1330 ab94316bb52b
parent 1231 17badaf66ce4
child 1541 e46ad208b9b4
permissions -rw-r--r--
Updated license headers on virtually all files with extremely minor changes in the name of some sort of strange consistency.
All plugin and include file headers also have been changed to say about GPL3 instead of GPL2.

(This day shall henceforth be known as the Eighty Column Massacre of '07)
dvander@370
     1
/**
ds@653
     2
 * vim: set ts=4 :
ds@1330
     3
 * =============================================================================
dvander@1231
     4
 * SourceMod
dvander@1231
     5
 * Copyright (C) 2004-2007 AlliedModders LLC.  All rights reserved.
ds@1330
     6
 * =============================================================================
dvander@370
     7
 *
ds@1330
     8
 * This program is free software; you can redistribute it and/or modify it under
ds@1330
     9
 * the terms of the GNU General Public License, version 3.0, as published by the
ds@1330
    10
 * Free Software Foundation.
dvander@1231
    11
 * 
ds@1330
    12
 * This program is distributed in the hope that it will be useful, but WITHOUT
ds@1330
    13
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
ds@1330
    14
 * FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
ds@1330
    15
 * details.
dvander@1231
    16
 *
ds@1330
    17
 * You should have received a copy of the GNU General Public License along with
ds@1330
    18
 * this program.  If not, see <http://www.gnu.org/licenses/>.
dvander@1231
    19
 *
ds@1330
    20
 * As a special exception, AlliedModders LLC gives you permission to link the
ds@1330
    21
 * code of this program (as well as its derivative works) to "Half-Life 2," the
ds@1330
    22
 * "Source Engine," the "SourcePawn JIT," and any Game MODs that run on software
ds@1330
    23
 * by the Valve Corporation.  You must obey the GNU General Public License in
ds@1330
    24
 * all respects for all other code used.  Additionally, AlliedModders LLC grants
ds@1330
    25
 * this exception to all derivative works.  AlliedModders LLC defines further
ds@1330
    26
 * exceptions, found in LICENSE.txt (as of this writing, version JULY-31-2007),
ds@1330
    27
 * or <http://www.sourcemod.net/license.php>.
dvander@370
    28
 *
dvander@370
    29
 * Version: $Id$
dvander@370
    30
 */
dvander@370
    31
faluco@216
    32
#include "sm_srvcmds.h"
faluco@270
    33
#include "sm_version.h"
faluco@274
    34
#include "sm_stringutil.h"
dvander@900
    35
#include "HandleSys.h"
dvander@978
    36
#include "CoreConfig.h"
faluco@216
    37
dvander@308
    38
RootConsoleMenu g_RootMenu;
faluco@216
    39
dvander@566
    40
ConVar sourcemod_version("sourcemod_version", SVN_FULL_VERSION, FCVAR_SPONLY|FCVAR_REPLICATED|FCVAR_NOTIFY, "SourceMod Version");
dvander@524
    41
dvander@308
    42
RootConsoleMenu::RootConsoleMenu()
faluco@216
    43
{
dvander@308
    44
	m_pCommands = sm_trie_create();
dvander@978
    45
	m_CfgExecDone = false;
faluco@216
    46
}
faluco@216
    47
dvander@308
    48
RootConsoleMenu::~RootConsoleMenu()
dvander@308
    49
{
dvander@308
    50
	sm_trie_destroy(m_pCommands);
dvander@308
    51
dvander@308
    52
	List<ConsoleEntry *>::iterator iter;
dvander@308
    53
	for (iter=m_Menu.begin(); iter!=m_Menu.end(); iter++)
dvander@308
    54
	{
dvander@308
    55
		delete (*iter);
dvander@308
    56
	}
dvander@308
    57
	m_Menu.clear();
dvander@308
    58
}
dvander@308
    59
ds@627
    60
extern void _IntExt_OnHostnameChanged(ConVar *pConVar, char const *oldValue);
ds@627
    61
dvander@308
    62
void RootConsoleMenu::OnSourceModStartup(bool late)
dvander@308
    63
{
dvander@308
    64
	ConCommandBaseMgr::OneTimeInit(this);
dvander@308
    65
	AddRootConsoleCommand("version", "Display version information", this);
dvander@308
    66
	AddRootConsoleCommand("credits", "Display credits listing", this);
ds@627
    67
ds@627
    68
	ConVar *pHost = icvar->FindVar("hostname");
ds@627
    69
	pHost->InstallChangeCallback(_IntExt_OnHostnameChanged);
dvander@308
    70
}
dvander@308
    71
dvander@308
    72
void RootConsoleMenu::OnSourceModShutdown()
dvander@308
    73
{
dvander@308
    74
	RemoveRootConsoleCommand("credits", this);
dvander@308
    75
	RemoveRootConsoleCommand("version", this);
dvander@308
    76
}
dvander@308
    77
dvander@308
    78
bool RootConsoleMenu::RegisterConCommandBase(ConCommandBase *pCommand)
faluco@216
    79
{
faluco@216
    80
	META_REGCVAR(pCommand);
faluco@216
    81
ds@657
    82
	/* Override values of convars created by SourceMod convar manager if specified on command line */
ds@657
    83
	const char *cmdLineValue = icvar->GetCommandLineValue(pCommand->GetName());
ds@657
    84
	if (cmdLineValue && !pCommand->IsCommand())
ds@657
    85
	{
ds@657
    86
		static_cast<ConVar *>(pCommand)->SetValue(cmdLineValue);
ds@657
    87
	}
ds@657
    88
faluco@216
    89
	return true;
faluco@216
    90
}
faluco@216
    91
dvander@308
    92
void RootConsoleMenu::ConsolePrint(const char *fmt, ...)
dvander@308
    93
{
dvander@308
    94
	char buffer[512];
dvander@308
    95
dvander@308
    96
	va_list ap;
dvander@308
    97
	va_start(ap, fmt);
dvander@308
    98
	size_t len = vsnprintf(buffer, sizeof(buffer), fmt, ap);
dvander@308
    99
	va_end(ap);
dvander@308
   100
dvander@324
   101
	if (len >= sizeof(buffer) - 1)
dvander@308
   102
	{
dvander@308
   103
		buffer[510] = '\n';
dvander@308
   104
		buffer[511] = '\0';
dvander@308
   105
	} else {
dvander@308
   106
		buffer[len++] = '\n';
dvander@308
   107
		buffer[len] = '\0';
dvander@308
   108
	}
dvander@308
   109
	
dvander@308
   110
	META_CONPRINT(buffer);
dvander@308
   111
}
dvander@308
   112
dvander@308
   113
bool RootConsoleMenu::AddRootConsoleCommand(const char *cmd, const char *text, IRootConsoleCommand *pHandler)
faluco@216
   114
{
dvander@308
   115
	if (sm_trie_retrieve(m_pCommands, cmd, NULL))
dvander@308
   116
	{
dvander@308
   117
		return false;
dvander@308
   118
	}
dvander@308
   119
dvander@308
   120
	sm_trie_insert(m_pCommands, cmd, pHandler);
dvander@308
   121
dvander@308
   122
	/* Sort this into the menu */
dvander@308
   123
	List<ConsoleEntry *>::iterator iter = m_Menu.begin();
dvander@308
   124
	ConsoleEntry *pEntry;
dvander@308
   125
	bool inserted = false;
dvander@308
   126
	while (iter != m_Menu.end())
dvander@308
   127
	{
dvander@308
   128
		pEntry = (*iter);
dvander@308
   129
		if (strcmp(cmd, pEntry->command.c_str()) < 0)
dvander@308
   130
		{
dvander@308
   131
			ConsoleEntry *pNew = new ConsoleEntry;
dvander@308
   132
			pNew->command.assign(cmd);
dvander@308
   133
			pNew->description.assign(text);
dvander@308
   134
			m_Menu.insert(iter, pNew);
dvander@308
   135
			inserted = true;
dvander@308
   136
			break;
dvander@308
   137
		}
dvander@308
   138
		iter++;
dvander@308
   139
	}
dvander@308
   140
dvander@308
   141
	if (!inserted)
dvander@308
   142
	{
dvander@308
   143
		ConsoleEntry *pNew = new ConsoleEntry;
dvander@308
   144
		pNew->command.assign(cmd);
dvander@308
   145
		pNew->description.assign(text);
dvander@308
   146
		m_Menu.push_back(pNew);
dvander@308
   147
	}
dvander@308
   148
dvander@308
   149
	return true;
dvander@308
   150
}
dvander@308
   151
dvander@308
   152
bool RootConsoleMenu::RemoveRootConsoleCommand(const char *cmd, IRootConsoleCommand *pHandler)
dvander@308
   153
{
dvander@308
   154
	/* Sanity tests */
dvander@308
   155
	IRootConsoleCommand *object;
dvander@308
   156
	if (sm_trie_retrieve(m_pCommands, cmd, (void **)&object))
dvander@308
   157
	{
dvander@308
   158
		if (object != pHandler)
dvander@308
   159
		{
dvander@308
   160
			return false;
dvander@308
   161
		}
dvander@308
   162
	} else {
dvander@308
   163
		return false;
dvander@308
   164
	}
dvander@308
   165
dvander@308
   166
	sm_trie_delete(m_pCommands, cmd);
dvander@308
   167
dvander@308
   168
	List<ConsoleEntry *>::iterator iter;
dvander@308
   169
	ConsoleEntry *pEntry;
dvander@308
   170
	for (iter=m_Menu.begin(); iter!=m_Menu.end(); iter++)
dvander@308
   171
	{
dvander@308
   172
		pEntry = (*iter);
dvander@308
   173
		if (pEntry->command.compare(cmd) == 0)
dvander@308
   174
		{
dvander@308
   175
			delete pEntry;
dvander@308
   176
			m_Menu.erase(iter);
dvander@308
   177
			break;
dvander@308
   178
		}
dvander@308
   179
	}
dvander@308
   180
dvander@308
   181
	return true;
dvander@308
   182
}
dvander@308
   183
dvander@309
   184
void RootConsoleMenu::DrawGenericOption(const char *cmd, const char *text)
dvander@309
   185
{
dvander@309
   186
	char buffer[255];
dvander@309
   187
	size_t len, cmdlen = strlen(cmd);
dvander@309
   188
faluco@651
   189
	len = UTIL_Format(buffer, sizeof(buffer), "    %s", cmd);
dvander@309
   190
	if (cmdlen < 16)
dvander@309
   191
	{
dvander@309
   192
		size_t num = 16 - cmdlen;
dvander@309
   193
		for (size_t i = 0; i < num; i++)
dvander@309
   194
		{
dvander@309
   195
			buffer[len++] = ' ';
dvander@309
   196
		}
dvander@309
   197
		len += snprintf(&buffer[len], sizeof(buffer) - len, " - %s", text);
dvander@309
   198
		ConsolePrint("%s", buffer);
dvander@309
   199
	}
dvander@309
   200
}
dvander@309
   201
dvander@614
   202
extern void _IntExt_EnableYams();
dvander@614
   203
dvander@308
   204
void RootConsoleMenu::GotRootCmd()
dvander@308
   205
{
dvander@308
   206
	unsigned int argnum = GetArgumentCount();
faluco@216
   207
faluco@216
   208
	if (argnum >= 2)
faluco@216
   209
	{
dvander@308
   210
		const char *cmd = GetArgument(1);
dvander@614
   211
		if (strcmp(cmd, "text") == 0)
dvander@614
   212
		{
dvander@614
   213
			_IntExt_EnableYams();
dvander@614
   214
			return;
dvander@978
   215
		} else if (strcmp(cmd, "internal") == 0) {
dvander@978
   216
			if (argnum >= 3)
dvander@978
   217
			{
dvander@978
   218
				const char *arg = GetArgument(2);
dvander@978
   219
				if (strcmp(arg, "1") == 0)
dvander@978
   220
				{
dvander@978
   221
					SM_ConfigsExecuted_Global();
dvander@978
   222
				} else if (strcmp(arg, "2") == 0) {
dvander@978
   223
					if (argnum >= 4)
dvander@978
   224
					{
dvander@978
   225
						SM_ConfigsExecuted_Plugin(atoi(GetArgument(3)));
dvander@978
   226
					}
dvander@978
   227
				}
dvander@978
   228
			}
dvander@978
   229
			return;
dvander@614
   230
		}
dvander@978
   231
dvander@308
   232
		IRootConsoleCommand *pHandler;
dvander@308
   233
		if (sm_trie_retrieve(m_pCommands, cmd, (void **)&pHandler))
faluco@216
   234
		{
dvander@308
   235
			pHandler->OnRootConsoleCommand(cmd, argnum);
faluco@270
   236
			return;
faluco@216
   237
		}
faluco@216
   238
	}
dvander@308
   239
dvander@308
   240
	ConsolePrint("SourceMod Menu:");
dvander@308
   241
	ConsolePrint("Usage: sm <command> [arguments]");
dvander@308
   242
dvander@308
   243
	List<ConsoleEntry *>::iterator iter;
dvander@308
   244
	ConsoleEntry *pEntry;
dvander@308
   245
	for (iter=m_Menu.begin(); iter!=m_Menu.end(); iter++)
dvander@308
   246
	{
dvander@308
   247
		pEntry = (*iter);
dvander@309
   248
		DrawGenericOption(pEntry->command.c_str(), pEntry->description.c_str());
dvander@308
   249
	}
dvander@308
   250
}
dvander@308
   251
dvander@308
   252
const char *RootConsoleMenu::GetArgument(unsigned int argno)
dvander@308
   253
{
dvander@308
   254
	return engine->Cmd_Argv(argno);
dvander@308
   255
}
dvander@308
   256
dvander@308
   257
const char *RootConsoleMenu::GetArguments()
dvander@308
   258
{
dvander@308
   259
	return engine->Cmd_Args();
dvander@282
   260
}
dvander@308
   261
dvander@308
   262
unsigned int RootConsoleMenu::GetArgumentCount()
dvander@308
   263
{
dvander@308
   264
	return engine->Cmd_Argc();
dvander@308
   265
}
dvander@308
   266
dvander@308
   267
void RootConsoleMenu::OnRootConsoleCommand(const char *cmd, unsigned int argcount)
dvander@308
   268
{
dvander@308
   269
	if (strcmp(cmd, "credits") == 0)
dvander@308
   270
	{
dvander@308
   271
		ConsolePrint(" SourceMod was developed by AlliedModders, LLC.");
dvander@308
   272
		ConsolePrint(" Development would not have been possible without the following people:");
dvander@308
   273
		ConsolePrint("  David \"BAILOPAN\" Anderson, lead developer");
dvander@308
   274
		ConsolePrint("  Borja \"faluco\" Ferrer, Core developer");
ds@626
   275
		ConsolePrint("  Scott \"Damaged Soul\" Ehlert, Core developer");
dvander@308
   276
		ConsolePrint("  Pavol \"PM OnoTo\" Marko, SourceHook developer");
dvander@308
   277
		ConsolePrint(" Special thanks to Viper of GameConnect");
dvander@308
   278
		ConsolePrint(" Special thanks to Mani of Mani-Admin-Plugin");
dvander@308
   279
		ConsolePrint(" http://www.sourcemod.net/");
dvander@308
   280
	} else if (strcmp(cmd, "version") == 0) {
dvander@308
   281
		ConsolePrint(" SourceMod Version Information:");
dvander@566
   282
		ConsolePrint("    SourceMod Version: %s", SVN_FULL_VERSION);
dvander@308
   283
		ConsolePrint("    JIT Version: %s, %s", g_pVM->GetVMName(), g_pVM->GetVersionString());
dvander@308
   284
		ConsolePrint("    JIT Settings: %s", g_pVM->GetCPUOptimizations());
dvander@308
   285
		ConsolePrint("    http://www.sourcemod.net/");
dvander@308
   286
	}
dvander@308
   287
}
dvander@308
   288
dvander@308
   289
CON_COMMAND(sm, "SourceMod Menu")
dvander@308
   290
{
dvander@308
   291
	g_RootMenu.GotRootCmd();
dvander@308
   292
}
dvander@900
   293
dvander@900
   294
CON_COMMAND(sm_dump_handles, "Dumps Handle usage to a file for finding Handle leaks")
dvander@900
   295
{
dvander@900
   296
	if (engine->Cmd_Argc() < 2)
dvander@900
   297
	{
dvander@900
   298
		g_RootMenu.ConsolePrint("Usage: sm_dump_handles <file>");
dvander@900
   299
		return;
dvander@900
   300
	}
dvander@900
   301
dvander@900
   302
	const char *arg = engine->Cmd_Argv(1);
dvander@900
   303
	FILE *fp = fopen(arg, "wt");
dvander@900
   304
	if (!fp)
dvander@900
   305
	{
dvander@900
   306
		g_RootMenu.ConsolePrint("Could not find file \"%s\"", arg);
dvander@900
   307
		return;
dvander@900
   308
	}
dvander@900
   309
dvander@900
   310
	g_HandleSys.Dump(fp);
dvander@900
   311
dvander@900
   312
	fclose(fp);
dvander@900
   313
}