core/smn_keyvalues.cpp
author Matt Woodrow <pred@alliedmods.net>
Wed Nov 21 22:15:05 2007 +0000 (2007-11-21)
changeset 1710 5f09761c40ce
parent 1709 1caf5bfb1c52
child 1734 32aa9dc8ac1a
permissions -rw-r--r--
Build fix attempt 1
faluco@654
     1
/**
faluco@654
     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
 * =============================================================================
faluco@654
     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>.
faluco@654
    28
 *
faluco@654
    29
 * Version: $Id$
faluco@654
    30
 */
faluco@654
    31
faluco@654
    32
#include "sourcemod.h"
faluco@654
    33
#include "sourcemm_api.h"
faluco@654
    34
#include "sm_stringutil.h"
faluco@654
    35
#include "HandleSys.h"
faluco@654
    36
#include <KeyValues.h>
faluco@654
    37
faluco@654
    38
HandleType_t g_KeyValueType;
faluco@654
    39
faluco@654
    40
struct KeyValueStack 
faluco@654
    41
{
faluco@654
    42
	KeyValues *pBase;
faluco@654
    43
	CStack<KeyValues *> pCurRoot;
faluco@654
    44
};
faluco@654
    45
faluco@703
    46
class KeyValueNatives : 
faluco@654
    47
	public SMGlobalClass,
faluco@654
    48
	public IHandleTypeDispatch
faluco@654
    49
{
faluco@654
    50
public:
faluco@654
    51
	void OnSourceModAllInitialized()
faluco@654
    52
	{
faluco@654
    53
		g_KeyValueType = g_HandleSys.CreateType("KeyValues", this, 0, NULL, NULL, g_pCoreIdent, NULL);
faluco@654
    54
	}
faluco@654
    55
	void OnSourceModShutdown()
faluco@654
    56
	{
faluco@654
    57
		g_HandleSys.RemoveType(g_KeyValueType, g_pCoreIdent);
faluco@654
    58
		g_KeyValueType = 0;
faluco@654
    59
	}
faluco@654
    60
	void OnHandleDestroy(HandleType_t type, void *object)
faluco@654
    61
	{
faluco@654
    62
		KeyValueStack *pStk = reinterpret_cast<KeyValueStack *>(object);
faluco@654
    63
		pStk->pBase->deleteThis();
faluco@654
    64
		delete pStk;
faluco@654
    65
	}
faluco@654
    66
};
faluco@654
    67
faluco@682
    68
KeyValues *SourceModBase::ReadKeyValuesHandle(Handle_t hndl, HandleError *err, bool root)
faluco@682
    69
{
faluco@682
    70
	HandleError herr;
faluco@682
    71
	HandleSecurity sec;
faluco@682
    72
	KeyValueStack *pStk;
faluco@682
    73
faluco@682
    74
	sec.pOwner = NULL;
faluco@682
    75
	sec.pIdentity = g_pCoreIdent;
faluco@682
    76
faluco@682
    77
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@682
    78
		!= HandleError_None)
faluco@682
    79
	{
faluco@682
    80
		if (err)
faluco@682
    81
		{
faluco@682
    82
			*err = herr;
faluco@682
    83
		}
faluco@682
    84
		return NULL;
faluco@682
    85
	}
faluco@682
    86
faluco@682
    87
	if (err)
faluco@682
    88
	{
faluco@682
    89
		*err = HandleError_None;
faluco@682
    90
	}
faluco@682
    91
faluco@682
    92
	return (root) ? pStk->pBase : pStk->pCurRoot.front();
faluco@682
    93
}
faluco@682
    94
faluco@654
    95
static cell_t smn_KvSetString(IPluginContext *pCtx, const cell_t *params)
faluco@654
    96
{
faluco@654
    97
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
    98
	HandleError herr;
faluco@654
    99
	HandleSecurity sec;
faluco@654
   100
	KeyValueStack *pStk;
faluco@654
   101
faluco@654
   102
	sec.pOwner = NULL;
faluco@654
   103
	sec.pIdentity = g_pCoreIdent;
faluco@654
   104
faluco@654
   105
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   106
		!= HandleError_None)
faluco@654
   107
	{
faluco@654
   108
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   109
	}
faluco@654
   110
faluco@654
   111
	char *key, *value;
dvander@1000
   112
	pCtx->LocalToStringNULL(params[2], &key);
faluco@654
   113
	pCtx->LocalToString(params[3], &value);
faluco@654
   114
faluco@654
   115
	pStk->pCurRoot.front()->SetString(key, value);
faluco@654
   116
faluco@654
   117
	return 1;
faluco@654
   118
}
faluco@654
   119
faluco@654
   120
static cell_t smn_KvSetNum(IPluginContext *pCtx, const cell_t *params)
faluco@654
   121
{
faluco@654
   122
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   123
	HandleError herr;
faluco@654
   124
	HandleSecurity sec;
faluco@654
   125
	KeyValueStack *pStk;
faluco@654
   126
faluco@654
   127
	sec.pOwner = NULL;
faluco@654
   128
	sec.pIdentity = g_pCoreIdent;
faluco@654
   129
faluco@654
   130
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   131
		!= HandleError_None)
faluco@654
   132
	{
faluco@654
   133
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   134
	}
faluco@654
   135
faluco@654
   136
	char *key;
dvander@1000
   137
	pCtx->LocalToStringNULL(params[2], &key);
faluco@654
   138
faluco@654
   139
	pStk->pCurRoot.front()->SetInt(key, params[3]);
faluco@654
   140
faluco@654
   141
	return 1;
faluco@654
   142
}
faluco@654
   143
dvander@816
   144
static cell_t smn_KvSetUInt64(IPluginContext *pCtx, const cell_t *params)
faluco@654
   145
{
faluco@654
   146
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   147
	HandleError herr;
faluco@654
   148
	HandleSecurity sec;
faluco@654
   149
	KeyValueStack *pStk;
faluco@654
   150
faluco@654
   151
	sec.pOwner = NULL;
faluco@654
   152
	sec.pIdentity = g_pCoreIdent;
faluco@654
   153
faluco@654
   154
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   155
		!= HandleError_None)
faluco@654
   156
	{
faluco@654
   157
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   158
	}
faluco@654
   159
faluco@654
   160
	char *key;
faluco@654
   161
	cell_t *addr;
faluco@654
   162
	uint64 value;
dvander@1000
   163
	pCtx->LocalToStringNULL(params[2], &key);
faluco@654
   164
	pCtx->LocalToPhysAddr(params[3], &addr);
faluco@654
   165
faluco@654
   166
	value = static_cast<uint64>(*addr);
faluco@654
   167
	pStk->pCurRoot.front()->SetUint64(key, value);
faluco@654
   168
faluco@654
   169
	return 1;
faluco@654
   170
}
faluco@654
   171
faluco@654
   172
static cell_t smn_KvSetFloat(IPluginContext *pCtx, const cell_t *params)
faluco@654
   173
{
faluco@654
   174
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   175
	HandleError herr;
faluco@654
   176
	HandleSecurity sec;
faluco@654
   177
	KeyValueStack *pStk;
faluco@654
   178
faluco@654
   179
	sec.pOwner = NULL;
faluco@654
   180
	sec.pIdentity = g_pCoreIdent;
faluco@654
   181
faluco@654
   182
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   183
		!= HandleError_None)
faluco@654
   184
	{
faluco@654
   185
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   186
	}
faluco@654
   187
faluco@654
   188
	char *key;
dvander@1000
   189
	pCtx->LocalToStringNULL(params[2], &key);
faluco@654
   190
faluco@654
   191
	pStk->pCurRoot.front()->SetFloat(key, sp_ctof(params[3]));
faluco@654
   192
faluco@654
   193
	return 1;
faluco@654
   194
}
faluco@654
   195
faluco@654
   196
static cell_t smn_KvSetColor(IPluginContext *pCtx, const cell_t *params)
faluco@654
   197
{
faluco@654
   198
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   199
	HandleError herr;
faluco@654
   200
	HandleSecurity sec;
faluco@654
   201
	KeyValueStack *pStk;
faluco@654
   202
faluco@654
   203
	sec.pOwner = NULL;
faluco@654
   204
	sec.pIdentity = g_pCoreIdent;
faluco@654
   205
faluco@654
   206
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   207
		!= HandleError_None)
faluco@654
   208
	{
faluco@654
   209
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   210
	}
faluco@654
   211
faluco@654
   212
	char *key;
dvander@1000
   213
	pCtx->LocalToStringNULL(params[2], &key);
faluco@654
   214
faluco@654
   215
	Color color(params[3], params[4], params[5], params[6]);
faluco@654
   216
	pStk->pCurRoot.front()->SetColor(key, color);
faluco@654
   217
faluco@654
   218
	return 1;
faluco@654
   219
}
faluco@654
   220
faluco@654
   221
static cell_t smn_KvGetString(IPluginContext *pCtx, const cell_t *params)
faluco@654
   222
{
faluco@654
   223
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   224
	HandleError herr;
faluco@654
   225
	HandleSecurity sec;
faluco@654
   226
	KeyValueStack *pStk;
faluco@654
   227
faluco@654
   228
	sec.pOwner = NULL;
faluco@654
   229
	sec.pIdentity = g_pCoreIdent;
faluco@654
   230
faluco@654
   231
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   232
		!= HandleError_None)
faluco@654
   233
	{
faluco@654
   234
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   235
	}
faluco@654
   236
faluco@654
   237
	const char *value;
faluco@654
   238
	char *key, *defvalue;
dvander@1000
   239
	pCtx->LocalToStringNULL(params[2], &key);
faluco@654
   240
	pCtx->LocalToString(params[5], &defvalue);
faluco@654
   241
faluco@654
   242
	value = pStk->pCurRoot.front()->GetString(key, defvalue);
faluco@654
   243
	pCtx->StringToLocalUTF8(params[3], params[4], value, NULL);
faluco@654
   244
faluco@654
   245
	return 1;
faluco@654
   246
}
faluco@654
   247
faluco@654
   248
static cell_t smn_KvGetNum(IPluginContext *pCtx, const cell_t *params)
faluco@654
   249
{
faluco@654
   250
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   251
	HandleError herr;
faluco@654
   252
	HandleSecurity sec;
faluco@654
   253
	KeyValueStack *pStk;
faluco@654
   254
faluco@654
   255
	sec.pOwner = NULL;
faluco@654
   256
	sec.pIdentity = g_pCoreIdent;
faluco@654
   257
faluco@654
   258
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   259
		!= HandleError_None)
faluco@654
   260
	{
faluco@654
   261
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   262
	}
faluco@654
   263
faluco@654
   264
	int value;
faluco@654
   265
	char *key;
dvander@1000
   266
	pCtx->LocalToStringNULL(params[2], &key);
faluco@654
   267
faluco@654
   268
	value = pStk->pCurRoot.front()->GetInt(key, params[3]);
faluco@654
   269
faluco@654
   270
	return value;
faluco@654
   271
}
faluco@654
   272
faluco@654
   273
static cell_t smn_KvGetFloat(IPluginContext *pCtx, const cell_t *params)
faluco@654
   274
{
faluco@654
   275
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   276
	HandleError herr;
faluco@654
   277
	HandleSecurity sec;
faluco@654
   278
	KeyValueStack *pStk;
faluco@654
   279
faluco@654
   280
	sec.pOwner = NULL;
faluco@654
   281
	sec.pIdentity = g_pCoreIdent;
faluco@654
   282
faluco@654
   283
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   284
		!= HandleError_None)
faluco@654
   285
	{
faluco@654
   286
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   287
	}
faluco@654
   288
faluco@654
   289
	float value;
faluco@654
   290
	char *key;
dvander@1000
   291
	pCtx->LocalToStringNULL(params[2], &key);
faluco@654
   292
faluco@654
   293
	value = pStk->pCurRoot.front()->GetFloat(key, sp_ctof(params[3]));
faluco@654
   294
faluco@654
   295
	return sp_ftoc(value);
faluco@654
   296
}
faluco@654
   297
faluco@654
   298
static cell_t smn_KvGetColor(IPluginContext *pCtx, const cell_t *params)
faluco@654
   299
{
faluco@654
   300
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   301
	HandleError herr;
faluco@654
   302
	HandleSecurity sec;
faluco@654
   303
	KeyValueStack *pStk;
faluco@654
   304
faluco@654
   305
	sec.pOwner = NULL;
faluco@654
   306
	sec.pIdentity = g_pCoreIdent;
faluco@654
   307
faluco@654
   308
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   309
		!= HandleError_None)
faluco@654
   310
	{
faluco@654
   311
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   312
	}
faluco@654
   313
faluco@654
   314
	Color color;
faluco@654
   315
	char *key;
faluco@654
   316
	cell_t *r, *g, *b, *a;
dvander@1000
   317
	pCtx->LocalToStringNULL(params[2], &key);
faluco@654
   318
	pCtx->LocalToPhysAddr(params[3], &r);
faluco@654
   319
	pCtx->LocalToPhysAddr(params[4], &g);
faluco@654
   320
	pCtx->LocalToPhysAddr(params[5], &b);
faluco@654
   321
	pCtx->LocalToPhysAddr(params[6], &a);
faluco@654
   322
faluco@654
   323
	color = pStk->pCurRoot.front()->GetColor(key);
faluco@654
   324
	*r = color.r();
faluco@654
   325
	*g = color.g();
faluco@654
   326
	*b = color.b();
faluco@654
   327
	*a = color.a();
faluco@654
   328
faluco@654
   329
	return 1;
faluco@654
   330
}
faluco@654
   331
dvander@816
   332
static cell_t smn_KvGetUInt64(IPluginContext *pCtx, const cell_t *params)
faluco@654
   333
{
faluco@654
   334
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   335
	HandleError herr;
faluco@654
   336
	HandleSecurity sec;
faluco@654
   337
	KeyValueStack *pStk;
faluco@654
   338
faluco@654
   339
	sec.pOwner = NULL;
faluco@654
   340
	sec.pIdentity = g_pCoreIdent;
faluco@654
   341
faluco@654
   342
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   343
		!= HandleError_None)
faluco@654
   344
	{
faluco@654
   345
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   346
	}
faluco@654
   347
faluco@654
   348
	char *key;
faluco@654
   349
	cell_t *addr, *defvalue;
faluco@654
   350
	uint64 value;
dvander@1000
   351
	pCtx->LocalToStringNULL(params[2], &key);
faluco@654
   352
	pCtx->LocalToPhysAddr(params[3], &addr);
faluco@654
   353
	pCtx->LocalToPhysAddr(params[4], &defvalue);
faluco@654
   354
faluco@654
   355
	value = pStk->pCurRoot.front()->GetUint64(key, static_cast<uint64>(*defvalue));
faluco@654
   356
	*reinterpret_cast<uint64 *>(addr) = value;
faluco@654
   357
faluco@654
   358
	return 1;
faluco@654
   359
}
faluco@654
   360
faluco@654
   361
static cell_t smn_CreateKeyValues(IPluginContext *pCtx, const cell_t *params)
faluco@654
   362
{
faluco@654
   363
	KeyValueStack *pStk;
faluco@654
   364
	char *name, *firstkey, *firstvalue;
faluco@654
   365
	bool is_empty;
faluco@654
   366
faluco@654
   367
	pCtx->LocalToString(params[1], &name);
faluco@654
   368
	pCtx->LocalToString(params[2], &firstkey);
faluco@654
   369
	pCtx->LocalToString(params[3], &firstvalue);
faluco@654
   370
faluco@654
   371
	is_empty = (firstkey[0] == '\0');
faluco@654
   372
	pStk = new KeyValueStack;
faluco@654
   373
	pStk->pBase = new KeyValues(name, is_empty ? NULL : firstkey, (is_empty||(firstvalue[0]=='\0')) ? NULL : firstvalue);
faluco@654
   374
	pStk->pCurRoot.push(pStk->pBase);
faluco@654
   375
faluco@654
   376
	return g_HandleSys.CreateHandle(g_KeyValueType, pStk, pCtx->GetIdentity(), g_pCoreIdent, NULL);
faluco@654
   377
}
faluco@654
   378
faluco@654
   379
static cell_t smn_KvJumpToKey(IPluginContext *pCtx, const cell_t *params)
faluco@654
   380
{
faluco@654
   381
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   382
	HandleError herr;
faluco@654
   383
	HandleSecurity sec;
faluco@654
   384
	char *name;	
faluco@654
   385
	KeyValueStack *pStk;
faluco@654
   386
faluco@654
   387
	sec.pOwner = NULL;
faluco@654
   388
	sec.pIdentity = g_pCoreIdent;
faluco@654
   389
faluco@654
   390
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   391
		!= HandleError_None)
faluco@654
   392
	{
faluco@654
   393
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   394
	}
faluco@654
   395
faluco@654
   396
	pCtx->LocalToString(params[2], &name);
faluco@654
   397
dvander@726
   398
	KeyValues *pSubKey = pStk->pCurRoot.front();
dvander@726
   399
	pSubKey = pSubKey->FindKey(name, (params[3]) ? true : false);
faluco@654
   400
	if (!pSubKey)
faluco@654
   401
	{
faluco@654
   402
		return 0;
faluco@654
   403
	}
faluco@654
   404
	pStk->pCurRoot.push(pSubKey);
faluco@654
   405
faluco@654
   406
	return 1;
faluco@654
   407
}
faluco@654
   408
pred@1707
   409
static cell_t smn_KvJumpToKeySymbol(IPluginContext *pCtx, const cell_t *params)
pred@1707
   410
{
pred@1707
   411
	Handle_t hndl = static_cast<Handle_t>(params[1]);
pred@1707
   412
	HandleError herr;
pred@1707
   413
	HandleSecurity sec;
pred@1707
   414
	KeyValueStack *pStk;
pred@1707
   415
pred@1707
   416
	sec.pOwner = NULL;
pred@1707
   417
	sec.pIdentity = g_pCoreIdent;
pred@1707
   418
pred@1707
   419
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
pred@1707
   420
		!= HandleError_None)
pred@1707
   421
	{
pred@1707
   422
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
pred@1707
   423
	}
pred@1707
   424
pred@1707
   425
	KeyValues *pSubKey = pStk->pCurRoot.front();
pred@1707
   426
	pSubKey = pSubKey->FindKey(params[2]);
pred@1707
   427
	if (!pSubKey)
pred@1707
   428
	{
pred@1707
   429
		return 0;
pred@1707
   430
	}
pred@1707
   431
	pStk->pCurRoot.push(pSubKey);
pred@1707
   432
pred@1707
   433
	return 1;
pred@1707
   434
}
pred@1707
   435
dvander@753
   436
static cell_t smn_KvGotoFirstSubKey(IPluginContext *pCtx, const cell_t *params)
faluco@654
   437
{
faluco@654
   438
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   439
	HandleError herr;
faluco@654
   440
	HandleSecurity sec;
faluco@654
   441
	KeyValueStack *pStk;
faluco@654
   442
faluco@654
   443
	sec.pOwner = NULL;
faluco@654
   444
	sec.pIdentity = g_pCoreIdent;
faluco@654
   445
faluco@654
   446
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   447
		!= HandleError_None)
faluco@654
   448
	{
faluco@654
   449
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   450
	}
faluco@654
   451
faluco@654
   452
	KeyValues *pSubKey = pStk->pCurRoot.front();
dvander@753
   453
	KeyValues *pFirstSubKey;
dvander@753
   454
	if (params[2])
dvander@753
   455
	{
dvander@753
   456
		pFirstSubKey = pSubKey->GetFirstTrueSubKey();
dvander@753
   457
	} else {
dvander@753
   458
		pFirstSubKey = pSubKey->GetFirstSubKey();
dvander@753
   459
	}
dvander@753
   460
faluco@654
   461
	if (!pFirstSubKey)
faluco@654
   462
	{
faluco@654
   463
		return 0;
faluco@654
   464
	}
faluco@654
   465
	pStk->pCurRoot.push(pFirstSubKey);
faluco@654
   466
faluco@654
   467
	return 1;
faluco@654
   468
}
faluco@654
   469
dvander@753
   470
static cell_t smn_KvGotoNextKey(IPluginContext *pCtx, const cell_t *params)
dvander@753
   471
{
dvander@753
   472
	Handle_t hndl = static_cast<Handle_t>(params[1]);
dvander@753
   473
	HandleError herr;
dvander@753
   474
	HandleSecurity sec;
dvander@753
   475
	KeyValueStack *pStk;
dvander@753
   476
dvander@753
   477
	sec.pOwner = NULL;
dvander@753
   478
	sec.pIdentity = g_pCoreIdent;
dvander@753
   479
dvander@753
   480
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
dvander@753
   481
		!= HandleError_None)
dvander@753
   482
	{
dvander@753
   483
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
dvander@753
   484
	}
dvander@753
   485
dvander@753
   486
	KeyValues *pSubKey = pStk->pCurRoot.front();
dvander@753
   487
	if (params[2])
dvander@753
   488
	{
dvander@1002
   489
		pSubKey = pSubKey->GetNextTrueSubKey();
dvander@753
   490
	} else {
dvander@1002
   491
		pSubKey = pSubKey->GetNextKey();
dvander@753
   492
	}
dvander@753
   493
	if (!pSubKey)
dvander@753
   494
	{
dvander@753
   495
		return 0;
dvander@753
   496
	}
dvander@753
   497
	pStk->pCurRoot.pop();
dvander@753
   498
	pStk->pCurRoot.push(pSubKey);
dvander@753
   499
dvander@753
   500
	return 1;	
dvander@753
   501
}
dvander@753
   502
faluco@654
   503
static cell_t smn_KvJumpNextSubKey(IPluginContext *pCtx, const cell_t *params)
faluco@654
   504
{
faluco@654
   505
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   506
	HandleError herr;
faluco@654
   507
	HandleSecurity sec;
faluco@654
   508
	KeyValueStack *pStk;
faluco@654
   509
faluco@654
   510
	sec.pOwner = NULL;
faluco@654
   511
	sec.pIdentity = g_pCoreIdent;
faluco@654
   512
faluco@654
   513
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   514
		!= HandleError_None)
faluco@654
   515
	{
faluco@654
   516
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   517
	}
faluco@654
   518
faluco@654
   519
	KeyValues *pSubKey = pStk->pCurRoot.front();
faluco@654
   520
	KeyValues *pNextKey = pSubKey->GetNextKey();
faluco@654
   521
	if (!pNextKey)
faluco@654
   522
	{
faluco@654
   523
		return 0;
faluco@654
   524
	}
faluco@654
   525
	pStk->pCurRoot.push(pNextKey);
faluco@654
   526
faluco@654
   527
	return 1;	
faluco@654
   528
}
faluco@654
   529
faluco@654
   530
static cell_t smn_KvGoBack(IPluginContext *pCtx, const cell_t *params)
faluco@654
   531
{
faluco@654
   532
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   533
	HandleError herr;
faluco@654
   534
	HandleSecurity sec;
faluco@654
   535
	KeyValueStack *pStk;
faluco@654
   536
faluco@654
   537
	sec.pOwner = NULL;
faluco@654
   538
	sec.pIdentity = g_pCoreIdent;
faluco@654
   539
faluco@654
   540
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   541
		!= HandleError_None)
faluco@654
   542
	{
faluco@654
   543
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   544
	}
faluco@654
   545
faluco@654
   546
	if (pStk->pCurRoot.size() == 1)
faluco@654
   547
	{
faluco@654
   548
		return 0;
faluco@654
   549
	}
faluco@654
   550
	pStk->pCurRoot.pop();
faluco@654
   551
faluco@654
   552
	return 1;
faluco@654
   553
}
faluco@654
   554
faluco@654
   555
static cell_t smn_KvRewind(IPluginContext *pCtx, const cell_t *params)
faluco@654
   556
{
faluco@654
   557
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   558
	HandleError herr;
faluco@654
   559
	HandleSecurity sec;
faluco@654
   560
	KeyValueStack *pStk;
faluco@654
   561
faluco@654
   562
	sec.pOwner = NULL;
faluco@654
   563
	sec.pIdentity = g_pCoreIdent;
faluco@654
   564
faluco@654
   565
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   566
		!= HandleError_None)
faluco@654
   567
	{
faluco@654
   568
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   569
	}
faluco@654
   570
faluco@654
   571
	while (pStk->pCurRoot.size() > 1)
faluco@654
   572
	{
faluco@654
   573
		pStk->pCurRoot.pop();
faluco@654
   574
	}
faluco@654
   575
faluco@654
   576
	return 1;
faluco@654
   577
}
faluco@654
   578
faluco@654
   579
static cell_t smn_KvGetSectionName(IPluginContext *pCtx, const cell_t *params)
faluco@654
   580
{
faluco@654
   581
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   582
	HandleError herr;
faluco@654
   583
	HandleSecurity sec;
faluco@654
   584
	KeyValueStack *pStk;
faluco@654
   585
faluco@654
   586
	sec.pOwner = NULL;
faluco@654
   587
	sec.pIdentity = g_pCoreIdent;
faluco@654
   588
faluco@654
   589
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   590
		!= HandleError_None)
faluco@654
   591
	{
faluco@654
   592
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   593
	}
faluco@654
   594
faluco@654
   595
	KeyValues *pSection = pStk->pCurRoot.front();
faluco@654
   596
	const char *name = pSection->GetName();
faluco@654
   597
	if (!name)
faluco@654
   598
	{
faluco@654
   599
		return 0;
faluco@654
   600
	}
faluco@654
   601
	pCtx->StringToLocalUTF8(params[2], params[3], name, NULL);
faluco@654
   602
faluco@654
   603
	return 1;
faluco@654
   604
}
faluco@654
   605
faluco@654
   606
static cell_t smn_KvSetSectionName(IPluginContext *pCtx, const cell_t *params)
faluco@654
   607
{
faluco@654
   608
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   609
	HandleError herr;
faluco@654
   610
	HandleSecurity sec;
faluco@654
   611
	char *name;
faluco@654
   612
	KeyValueStack *pStk;
faluco@654
   613
faluco@654
   614
	sec.pOwner = NULL;
faluco@654
   615
	sec.pIdentity = g_pCoreIdent;
faluco@654
   616
faluco@654
   617
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   618
		!= HandleError_None)
faluco@654
   619
	{
faluco@654
   620
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   621
	}
faluco@654
   622
faluco@654
   623
	pCtx->LocalToString(params[2], &name);
faluco@654
   624
faluco@654
   625
	KeyValues *pSection = pStk->pCurRoot.front();
faluco@654
   626
	pSection->SetName(name);
faluco@654
   627
faluco@654
   628
	return 1;
faluco@654
   629
}
faluco@654
   630
faluco@654
   631
static cell_t smn_KvGetDataType(IPluginContext *pCtx, const cell_t *params)
faluco@654
   632
{
faluco@654
   633
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   634
	HandleError herr;
faluco@654
   635
	HandleSecurity sec;
faluco@654
   636
	char *name;
faluco@654
   637
	KeyValueStack *pStk;
faluco@654
   638
faluco@654
   639
	sec.pOwner = NULL;
faluco@654
   640
	sec.pIdentity = g_pCoreIdent;
faluco@654
   641
faluco@654
   642
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   643
		!= HandleError_None)
faluco@654
   644
	{
faluco@654
   645
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   646
	}
faluco@654
   647
faluco@654
   648
	pCtx->LocalToString(params[2], &name);
faluco@654
   649
faluco@654
   650
	return pStk->pCurRoot.front()->GetDataType(name);
faluco@654
   651
}
faluco@654
   652
faluco@654
   653
static cell_t smn_KeyValuesToFile(IPluginContext *pCtx, const cell_t *params)
faluco@654
   654
{
faluco@654
   655
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   656
	HandleError herr;
faluco@654
   657
	HandleSecurity sec;
faluco@654
   658
	char *path;
faluco@654
   659
	KeyValueStack *pStk;
faluco@654
   660
faluco@654
   661
	sec.pOwner = NULL;
faluco@654
   662
	sec.pIdentity = g_pCoreIdent;
faluco@654
   663
faluco@654
   664
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   665
		!= HandleError_None)
faluco@654
   666
	{
faluco@654
   667
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   668
	}
faluco@654
   669
faluco@654
   670
	pCtx->LocalToString(params[2], &path);
faluco@654
   671
faluco@654
   672
	char realpath[PLATFORM_MAX_PATH];
faluco@654
   673
	g_SourceMod.BuildPath(Path_Game, realpath, sizeof(realpath), "%s", path);
faluco@654
   674
faluco@654
   675
	return pStk->pCurRoot.front()->SaveToFile(basefilesystem, realpath);
faluco@654
   676
}
faluco@654
   677
faluco@654
   678
static cell_t smn_FileToKeyValues(IPluginContext *pCtx, const cell_t *params)
faluco@654
   679
{
faluco@654
   680
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   681
	HandleError herr;
faluco@654
   682
	HandleSecurity sec;
faluco@654
   683
	char *path;
faluco@654
   684
	KeyValueStack *pStk;
faluco@654
   685
faluco@654
   686
	sec.pOwner = NULL;
faluco@654
   687
	sec.pIdentity = g_pCoreIdent;
faluco@654
   688
faluco@654
   689
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   690
		!= HandleError_None)
faluco@654
   691
	{
faluco@654
   692
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   693
	}
faluco@654
   694
faluco@654
   695
	pCtx->LocalToString(params[2], &path);
faluco@654
   696
faluco@654
   697
	char realpath[PLATFORM_MAX_PATH];
faluco@654
   698
	g_SourceMod.BuildPath(Path_Game, realpath, sizeof(realpath), "%s", path);
faluco@654
   699
faluco@654
   700
	return pStk->pCurRoot.front()->LoadFromFile(basefilesystem, realpath);
faluco@654
   701
}
faluco@654
   702
faluco@654
   703
static cell_t smn_KvSetEscapeSequences(IPluginContext *pCtx, const cell_t *params)
faluco@654
   704
{
faluco@654
   705
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@654
   706
	HandleError herr;
faluco@654
   707
	HandleSecurity sec;
faluco@654
   708
	KeyValueStack *pStk;
faluco@654
   709
faluco@654
   710
	sec.pOwner = NULL;
faluco@654
   711
	sec.pIdentity = g_pCoreIdent;
faluco@654
   712
faluco@654
   713
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@654
   714
		!= HandleError_None)
faluco@654
   715
	{
faluco@654
   716
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@654
   717
	}
faluco@654
   718
faluco@654
   719
	pStk->pCurRoot.front()->UsesEscapeSequences(params[2] ? true : false);
faluco@654
   720
faluco@654
   721
	return 1;
faluco@654
   722
}
faluco@654
   723
dvander@750
   724
static cell_t smn_KvNodesInStack(IPluginContext *pCtx, const cell_t *params)
dvander@750
   725
{
dvander@750
   726
	Handle_t hndl = static_cast<Handle_t>(params[1]);
dvander@750
   727
	HandleError herr;
dvander@750
   728
	HandleSecurity sec;
dvander@750
   729
	KeyValueStack *pStk;
dvander@750
   730
dvander@750
   731
	sec.pOwner = NULL;
dvander@750
   732
	sec.pIdentity = g_pCoreIdent;
dvander@750
   733
dvander@750
   734
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
dvander@750
   735
		!= HandleError_None)
dvander@750
   736
	{
dvander@750
   737
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
dvander@750
   738
	}
dvander@750
   739
dvander@751
   740
	return pStk->pCurRoot.size() - 1;
dvander@750
   741
}
dvander@750
   742
dvander@743
   743
static cell_t smn_KvDeleteThis(IPluginContext *pContext, const cell_t *params)
dvander@743
   744
{
dvander@743
   745
	Handle_t hndl = static_cast<Handle_t>(params[1]);
dvander@743
   746
	HandleError herr;
dvander@743
   747
	HandleSecurity sec;
dvander@743
   748
	KeyValueStack *pStk;
dvander@743
   749
dvander@743
   750
	sec.pOwner = NULL;
dvander@743
   751
	sec.pIdentity = g_pCoreIdent;
dvander@743
   752
dvander@743
   753
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
dvander@743
   754
		!= HandleError_None)
dvander@743
   755
	{
dvander@743
   756
		return pContext->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
dvander@743
   757
	}
dvander@743
   758
dvander@743
   759
	if (pStk->pCurRoot.size() < 2)
dvander@743
   760
	{
dvander@743
   761
		return 0;
dvander@743
   762
	}
dvander@743
   763
dvander@743
   764
	KeyValues *pValues = pStk->pCurRoot.front();
dvander@743
   765
	pStk->pCurRoot.pop();
dvander@753
   766
	KeyValues *pRoot = pStk->pCurRoot.front();
dvander@743
   767
dvander@753
   768
	/* We have to manually verify this since Valve sucks
dvander@753
   769
	 * :TODO: make our own KeyValues.h file and make
dvander@753
   770
	 * the sub stuff private so we can do this ourselves!
dvander@753
   771
 	 */
dvander@753
   772
	KeyValues *sub = pRoot->GetFirstSubKey();
dvander@753
   773
	while (sub)
dvander@753
   774
	{
dvander@753
   775
		if (sub == pValues)
dvander@753
   776
		{
dvander@753
   777
			KeyValues *pNext = pValues->GetNextKey();
dvander@753
   778
			pRoot->RemoveSubKey(pValues);
dvander@753
   779
			pValues->deleteThis();
dvander@753
   780
			if (pNext)
dvander@753
   781
			{
dvander@753
   782
				pStk->pCurRoot.push(pNext);
dvander@753
   783
				return 1;
dvander@753
   784
			} else {
dvander@753
   785
				return -1;
dvander@753
   786
			}
dvander@753
   787
		}
dvander@753
   788
		sub = sub->GetNextKey();
dvander@753
   789
	}
dvander@753
   790
dvander@753
   791
	/* Push this back on :( */
dvander@753
   792
	pStk->pCurRoot.push(pValues);
dvander@753
   793
dvander@753
   794
	return 0;
dvander@743
   795
}
dvander@743
   796
dvander@743
   797
static cell_t smn_KvDeleteKey(IPluginContext *pContext, const cell_t *params)
dvander@743
   798
{
dvander@743
   799
	Handle_t hndl = static_cast<Handle_t>(params[1]);
dvander@743
   800
	HandleError herr;
dvander@743
   801
	HandleSecurity sec;
dvander@743
   802
	KeyValueStack *pStk;
dvander@743
   803
dvander@743
   804
	sec.pOwner = NULL;
dvander@743
   805
	sec.pIdentity = g_pCoreIdent;
dvander@743
   806
dvander@743
   807
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
dvander@743
   808
		!= HandleError_None)
dvander@743
   809
	{
dvander@743
   810
		return pContext->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
dvander@743
   811
	}
dvander@743
   812
dvander@743
   813
	if (pStk->pCurRoot.size() < 2)
dvander@743
   814
	{
dvander@743
   815
		return 0;
dvander@743
   816
	}
dvander@743
   817
dvander@743
   818
	char *keyName;
dvander@743
   819
	pContext->LocalToString(params[2], &keyName);
dvander@743
   820
dvander@743
   821
	KeyValues *pRoot = pStk->pCurRoot.front();
dvander@743
   822
	KeyValues *pValues = pRoot->FindKey(keyName);
dvander@743
   823
	if (!pValues)
dvander@743
   824
	{
dvander@743
   825
		return 0;
dvander@743
   826
	}
dvander@743
   827
dvander@743
   828
	pRoot->RemoveSubKey(pValues);
dvander@743
   829
	pValues->deleteThis();
dvander@743
   830
dvander@743
   831
	return 1;
dvander@743
   832
}
dvander@743
   833
dvander@753
   834
static cell_t smn_KvSavePosition(IPluginContext *pContext, const cell_t *params)
dvander@753
   835
{
dvander@753
   836
	Handle_t hndl = static_cast<Handle_t>(params[1]);
dvander@753
   837
	HandleError herr;
dvander@753
   838
	HandleSecurity sec;
dvander@753
   839
	KeyValueStack *pStk;
dvander@753
   840
dvander@753
   841
	sec.pOwner = NULL;
dvander@753
   842
	sec.pIdentity = g_pCoreIdent;
dvander@753
   843
dvander@753
   844
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
dvander@753
   845
		!= HandleError_None)
dvander@753
   846
	{
dvander@753
   847
		return pContext->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
dvander@753
   848
	}
dvander@753
   849
dvander@753
   850
	if (pStk->pCurRoot.size() < 2)
dvander@753
   851
	{
dvander@753
   852
		return 0;
dvander@753
   853
	}
dvander@753
   854
dvander@753
   855
	KeyValues *pValues = pStk->pCurRoot.front();
dvander@753
   856
	pStk->pCurRoot.push(pValues);
dvander@753
   857
dvander@753
   858
	return 1;
dvander@753
   859
}
dvander@753
   860
faluco@1401
   861
static cell_t smn_CopySubkeys(IPluginContext *pContext, const cell_t *params)
faluco@1401
   862
{
faluco@1401
   863
	Handle_t hndl_copied = static_cast<Handle_t>(params[1]);
faluco@1401
   864
	Handle_t hndl_parent = static_cast<Handle_t>(params[2]);
faluco@1401
   865
	HandleError herr;
faluco@1401
   866
	HandleSecurity sec;
faluco@1401
   867
	KeyValueStack *pStk_copied, *pStk_parent;
faluco@1401
   868
faluco@1401
   869
	sec.pOwner = NULL;
faluco@1401
   870
	sec.pIdentity = g_pCoreIdent;
faluco@1401
   871
faluco@1401
   872
	if ((herr=g_HandleSys.ReadHandle(hndl_copied, g_KeyValueType, &sec, (void **)&pStk_copied))
faluco@1401
   873
		!= HandleError_None)
faluco@1401
   874
	{
faluco@1401
   875
		return pContext->ThrowNativeError("Invalid key value handle %x (error %d)", hndl_copied, herr);
faluco@1401
   876
	}
faluco@1401
   877
	if ((herr=g_HandleSys.ReadHandle(hndl_parent, g_KeyValueType, &sec, (void **)&pStk_parent))
faluco@1401
   878
		!= HandleError_None)
faluco@1401
   879
	{
faluco@1401
   880
		return pContext->ThrowNativeError("Invalid key value handle %x (error %d)", hndl_parent, herr);
faluco@1401
   881
	}
faluco@1401
   882
faluco@1401
   883
	pStk_copied->pCurRoot.front()->CopySubkeys(pStk_parent->pCurRoot.front());
faluco@1401
   884
faluco@1401
   885
	return 1;
faluco@1401
   886
}
faluco@1401
   887
faluco@1401
   888
static cell_t smn_GetNameSymbol(IPluginContext *pContext, const cell_t *params)
faluco@1401
   889
{
faluco@1401
   890
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@1401
   891
	HandleError herr;
faluco@1401
   892
	HandleSecurity sec;
faluco@1401
   893
	KeyValueStack *pStk;
faluco@1401
   894
	cell_t *val;
faluco@1401
   895
	char *key;
faluco@1401
   896
faluco@1401
   897
	sec.pOwner = NULL;
faluco@1401
   898
	sec.pIdentity = g_pCoreIdent;
faluco@1401
   899
faluco@1401
   900
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@1401
   901
		!= HandleError_None)
faluco@1401
   902
	{
faluco@1401
   903
		return pContext->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@1401
   904
	}
faluco@1401
   905
faluco@1401
   906
	if (pStk->pCurRoot.size() < 2)
faluco@1401
   907
	{
faluco@1401
   908
		return 0;
faluco@1401
   909
	}
faluco@1401
   910
faluco@1401
   911
	pContext->LocalToString(params[2], &key);
faluco@1401
   912
faluco@1401
   913
	KeyValues *pKv = pStk->pCurRoot.front()->FindKey(key);
faluco@1401
   914
	if (!pKv)
faluco@1401
   915
	{
faluco@1401
   916
		return 0;
faluco@1401
   917
	}
faluco@1401
   918
	pContext->LocalToPhysAddr(params[3], &val);
faluco@1401
   919
	*val = pKv->GetNameSymbol();
faluco@1401
   920
faluco@1401
   921
	return 1;
faluco@1401
   922
}
faluco@1401
   923
faluco@1401
   924
static cell_t smn_FindKeyById(IPluginContext *pContext, const cell_t *params)
faluco@1401
   925
{
faluco@1401
   926
	Handle_t hndl = static_cast<Handle_t>(params[1]);
faluco@1401
   927
	HandleError herr;
faluco@1401
   928
	HandleSecurity sec;
faluco@1401
   929
	KeyValueStack *pStk;
faluco@1401
   930
faluco@1401
   931
	sec.pOwner = NULL;
faluco@1401
   932
	sec.pIdentity = g_pCoreIdent;
faluco@1401
   933
faluco@1401
   934
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
faluco@1401
   935
		!= HandleError_None)
faluco@1401
   936
	{
faluco@1401
   937
		return pContext->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
faluco@1401
   938
	}
faluco@1401
   939
faluco@1401
   940
	KeyValues *pKv = pStk->pCurRoot.front()->FindKey(params[2]);
faluco@1401
   941
	if (!pKv)
faluco@1401
   942
	{
faluco@1401
   943
		return 0;
faluco@1401
   944
	}
faluco@1401
   945
faluco@1401
   946
	pContext->StringToLocalUTF8(params[3], params[4], pKv->GetName(), NULL);
faluco@1401
   947
faluco@1401
   948
	return 1;
faluco@1401
   949
}
faluco@1401
   950
pred@1709
   951
static cell_t smn_KvGetSectionSymbol(IPluginContext *pCtx, const cell_t *params)
pred@1709
   952
{
pred@1709
   953
	Handle_t hndl = static_cast<Handle_t>(params[1]);
pred@1709
   954
	HandleError herr;
pred@1709
   955
	HandleSecurity sec;
pred@1709
   956
	KeyValueStack *pStk;
pred@1709
   957
	cell_t *val;
pred@1709
   958
pred@1709
   959
	sec.pOwner = NULL;
pred@1709
   960
	sec.pIdentity = g_pCoreIdent;
pred@1709
   961
pred@1709
   962
	if ((herr=g_HandleSys.ReadHandle(hndl, g_KeyValueType, &sec, (void **)&pStk))
pred@1709
   963
		!= HandleError_None)
pred@1709
   964
	{
pred@1709
   965
		return pCtx->ThrowNativeError("Invalid key value handle %x (error %d)", hndl, herr);
pred@1709
   966
	}
pred@1709
   967
pred@1709
   968
	KeyValues *pSection = pStk->pCurRoot.front();
pred@1709
   969
pred@1710
   970
	pCtx->LocalToPhysAddr(params[2], &val);
pred@1709
   971
	*val = pSection->GetNameSymbol();
pred@1709
   972
pred@1709
   973
	if (!*val)
pred@1709
   974
	{
pred@1709
   975
		return 0;
pred@1709
   976
	}
pred@1709
   977
pred@1709
   978
	return 1;
pred@1709
   979
}
pred@1709
   980
faluco@703
   981
static KeyValueNatives s_KeyValueNatives;
faluco@654
   982
faluco@654
   983
REGISTER_NATIVES(keyvaluenatives)
faluco@654
   984
{
faluco@654
   985
	{"KvSetString",				smn_KvSetString},
faluco@654
   986
	{"KvSetNum",				smn_KvSetNum},
dvander@816
   987
	{"KvSetUInt64",				smn_KvSetUInt64},
faluco@654
   988
	{"KvSetFloat",				smn_KvSetFloat},
faluco@654
   989
	{"KvSetColor",				smn_KvSetColor},
faluco@654
   990
	{"KvGetString",				smn_KvGetString},
faluco@654
   991
	{"KvGetNum",				smn_KvGetNum},
faluco@654
   992
	{"KvGetFloat",				smn_KvGetFloat},
faluco@654
   993
	{"KvGetColor",				smn_KvGetColor},
dvander@816
   994
	{"KvGetUInt64",				smn_KvGetUInt64},
faluco@654
   995
	{"CreateKeyValues",			smn_CreateKeyValues},
faluco@654
   996
	{"KvJumpToKey",				smn_KvJumpToKey},
pred@1707
   997
	{"KvJumpToKeySymbol",		smn_KvJumpToKeySymbol},
dvander@753
   998
	{"KvGotoNextKey",			smn_KvGotoNextKey},
dvander@753
   999
	{"KvJumpFirstSubKey",		smn_KvGotoFirstSubKey},		/* BACKWARDS COMPAT SHIM */
dvander@753
  1000
	{"KvGotoFirstSubKey",		smn_KvGotoFirstSubKey},
dvander@753
  1001
	{"KvJumpNextSubKey",		smn_KvJumpNextSubKey},		/* BACKWARDS COMPAT SHIM */
faluco@654
  1002
	{"KvGoBack",				smn_KvGoBack},
faluco@654
  1003
	{"KvRewind",				smn_KvRewind},
faluco@654
  1004
	{"KvGetSectionName",		smn_KvGetSectionName},
faluco@654
  1005
	{"KvSetSectionName",		smn_KvSetSectionName},
faluco@654
  1006
	{"KvGetDataType",			smn_KvGetDataType},
faluco@654
  1007
	{"KeyValuesToFile",			smn_KeyValuesToFile},
faluco@654
  1008
	{"FileToKeyValues",			smn_FileToKeyValues},
faluco@654
  1009
	{"KvSetEscapeSequences",	smn_KvSetEscapeSequences},
dvander@743
  1010
	{"KvDeleteThis",			smn_KvDeleteThis},
dvander@743
  1011
	{"KvDeleteKey",				smn_KvDeleteKey},
dvander@750
  1012
	{"KvNodesInStack",			smn_KvNodesInStack},
dvander@753
  1013
	{"KvSavePosition",			smn_KvSavePosition},
faluco@1401
  1014
	{"KvCopySubkeys",			smn_CopySubkeys},
faluco@1401
  1015
	{"KvFindKeyById",			smn_FindKeyById},
faluco@1401
  1016
	{"KvGetNameSymbol",			smn_GetNameSymbol},
pred@1709
  1017
	{"KvGetSectionSymbol",		smn_KvGetSectionSymbol},
faluco@654
  1018
	{NULL,						NULL}
faluco@654
  1019
};