// native TrieSetString(Trie:handle, const key[], const data[], bool:replace = true); static cell AMX_NATIVE_CALL TrieSetString(AMX *amx, cell *params) { CellTrie *t = TrieHandles.lookup(params[1]); if (!t) { LogError(amx, AMX_ERR_NATIVE, "Invalid map handle provided (%d)", params[1]); return 0; } int len; const char *key = get_amxstring(amx, params[2], 0, len); const char *value = get_amxstring(amx, params[3], 1, len); StringHashMap<Entry>::Insert i = t->map.findForAdd(key); if (!i.found()) { if (!t->map.add(i, key)) { return 0; } i->value.setString(value); return 1; } // Old plugin doesn't have 'replace' parameter. if (*params / sizeof(cell) == 4 && !params[4]) { return 0; } i->value.setString(value); return 1; }
// native SMCError:SMC_ParseFile(SMCParser:handle, const file[], &line = 0, &col = 0, any:data = 0); static cell AMX_NATIVE_CALL SMC_ParseFile(AMX *amx, cell *params) { ParseInfo *p = TextParsersHandles.lookup(params[1]); if (!p) { LogError(amx, AMX_ERR_NATIVE, "Invalid SMC parse handle (%d)", params[1]); return 0; } if (*params / sizeof(cell) >= 5) { p->data = params[5]; } int length; const char *file = build_pathname("%s", get_amxstring(amx, params[2], 0, length)); SMCStates states; SMCError p_err = textparsers->ParseFile_SMC(file, p, &states); *get_amxaddr(amx, params[3]) = states.line; *get_amxaddr(amx, params[4]) = states.col; return static_cast<cell>(p_err); }
// native ArraySwap(Array:which, item1, item2); static cell AMX_NATIVE_CALL ArraySwap(AMX* amx, cell* params) { CellArray* vec = ArrayHandles.lookup(params[1]); if (!vec) { LogError(amx, AMX_ERR_NATIVE, "Invalid array handle provided (%d)", params[1]); return 0; } size_t idx1 = (size_t)params[2]; size_t idx2 = (size_t)params[3]; if (idx1 >= vec->size()) { LogError(amx, AMX_ERR_NATIVE, "Invalid index %d (count: %d)", idx1, vec->size()); return 0; } if (idx2 >= vec->size()) { LogError(amx, AMX_ERR_NATIVE, "Invalid index %d (count: %d)", idx2, vec->size()); return 0; } vec->swap(idx1, idx2); return 1; }
// native ArrayFindString(Array:which, const item[]); static cell AMX_NATIVE_CALL ArrayFindString(AMX* amx, cell* params) { CellArray* vec = ArrayHandles.lookup(params[1]); if (!vec) { LogError(amx, AMX_ERR_NATIVE, "Invalid array handle provided (%d)", params[1]); return -1; } cell *b, *a = get_amxaddr(amx, params[2]); size_t cellcount = vec->blocksize(); size_t a_len = ke::Max(1, amxstring_len(a)); size_t len = a_len > cellcount ? cellcount : a_len; for (size_t i = 0; i < vec->size(); i++) { b = vec->at(i); if (fastcellcmp(a, b, len)) { return static_cast<cell>(i); } } return -1; }
// native bool:INI_ParseFile(INIParser:handle, const file[], &line = 0, &col = 0, any:data = 0); static cell AMX_NATIVE_CALL INI_ParseFile(AMX *amx, cell *params) { ParseInfo *p = TextParsersHandles.lookup(params[1]); if (!p) { LogError(amx, AMX_ERR_NATIVE, "Invalid INI parse handle (%d)", params[1]); return 0; } int length; const char *file = build_pathname("%s", get_amxstring(amx, params[2], 0, length)); if (*params / sizeof(cell) >= 5) { p->data = params[5]; } unsigned int line, col; bool result = textparsers->ParseFile_INI(file, p, &line, &col); *get_amxaddr(amx, params[3]) = line; *get_amxaddr(amx, params[4]) = col; return result; }
// native GameConfig:LoadGameConfigFile(const file[]); static cell AMX_NATIVE_CALL LoadGameConfigFile(AMX *amx, cell *params) { int length; const char *filename = get_amxstring(amx, params[1], 0, length); IGameConfig *config = nullptr; char error[128]; if (!ConfigManager.LoadGameConfigFile(filename, &config, error, sizeof(error))) { LogError(amx, AMX_ERR_NATIVE, "Unable to open %s: %s", filename, error); return 0; } int handle = GameConfigHandle.create(); auto configHandle = GameConfigHandle.lookup(handle); if (!configHandle) { return 0; } configHandle->m_config = config; return handle; }
// native INI_SetReaders(INIParser:smc, const kvFunc[], const nsFunc[] = "" ); static cell AMX_NATIVE_CALL INI_SetReaders(AMX *amx, cell *params) { ParseInfo *p = TextParsersHandles.lookup(params[1]); if (!p) { LogError(amx, AMX_ERR_NATIVE, "Invalid INI parse handle (%d)", params[1]); return 0; } int kvLength = 0, nsLength = 0; const char *funcName = nullptr; if ((funcName = get_amxstring(amx, params[2], 0, kvLength)) && kvLength) { p->key_value = registerSPForwardByName(amx, funcName, FP_CELL, FP_STRING, FP_STRING, FP_CELL, FP_CELL, FP_CELL, FP_CELL, FP_DONE); } if (kvLength && (funcName = get_amxstring(amx, params[3], 1, nsLength)) && nsLength) { p->new_section = registerSPForwardByName(amx, funcName, FP_CELL, FP_STRING, FP_CELL, FP_CELL, FP_CELL, FP_CELL, FP_DONE); } if (p->key_value == -1 || (nsLength && p->new_section == -1)) { LogError(amx, AMX_ERR_NATIVE, "Function is not present (function \"%s\") (plugin \"%s\")", funcName, g_plugins.findPluginFast(amx)->getName()); return 0; } return 1; }
// native bool:TrieGetString(Trie:handle, const key[], buff[], len, &size = 0); static cell AMX_NATIVE_CALL TrieGetString(AMX *amx, cell *params) { CellTrie *t = TrieHandles.lookup(params[1]); if (!t) { LogError(amx, AMX_ERR_NATIVE, "Invalid map handle provided (%d)", params[1]); return 0; } if (params[4] < 0) { LogError(amx, AMX_ERR_NATIVE, "Invalid buffer size (%d)", params[4]); return 0; } int len; const char *key = get_amxstring(amx, params[2], 0, len); cell *pSize = get_amxaddr(amx, params[5]); StringHashMap<Entry>::Result r = t->map.find(key); if (!r.found() || !r->value.isString()) { return 0; } *pSize = (cell)set_amxstring_utf8(amx, params[3], r->value.chars(), strlen(r->value.chars()), params[4]); return 1; }
// native DoNotUse : ArrayGetStringHandle(Array : which, item); static cell AMX_NATIVE_CALL ArrayGetStringHandle(AMX* amx, cell* params) { CellArray* vec = ArrayHandles.lookup(params[1]); if (!vec) { LogError(amx, AMX_ERR_NATIVE, "Invalid array handle provided (%d)", params[1]); return 0; } size_t idx = (size_t)params[2]; if (idx >= vec->size()) { LogError(amx, AMX_ERR_NATIVE, "Invalid index %d (count: %d)", idx, vec->size()); return 0; } cell* ptr = vec->at(idx); if (ptr == NULL) { return 0; } return reinterpret_cast<cell>(ptr); }
// native ArraySetString(Array:which, item, const input[]); static cell AMX_NATIVE_CALL ArraySetString(AMX* amx, cell* params) { CellArray* vec = ArrayHandles.lookup(params[1]); if (!vec) { LogError(amx, AMX_ERR_NATIVE, "Invalid array handle provided (%d)", params[1]); return 0; } size_t idx = (size_t)params[2]; if (idx >= vec->size()) { LogError(amx, AMX_ERR_NATIVE, "Invalid index %d (count: %d)", idx, vec->size()); return 0; } cell *blk = vec->at(idx); int len; char *str = get_amxstring(amx, params[3], 0, len); return strncopy(blk, str, ke::Min((size_t)len + 1, vec->blocksize())); }
// native ArrayPushArray(Array:which, const any:input[], size = -1); static cell AMX_NATIVE_CALL ArrayPushArray(AMX* amx, cell* params) { CellArray* vec = ArrayHandles.lookup(params[1]); if (!vec) { LogError(amx, AMX_ERR_NATIVE, "Invalid array handle provided (%d)", params[1]); return 0; } cell *blk = vec->push(); if (!blk) { LogError(amx, AMX_ERR_NATIVE, "Failed to grow array"); return 0; } cell *addr = get_amxaddr(amx, params[2]); size_t indexes = vec->blocksize(); if (*params / sizeof(cell) == 3) { if (params[3] != -1 && (size_t)params[3] <= vec->blocksize()) { indexes = params[3]; } } memcpy(blk, addr, sizeof(cell) * indexes); return static_cast<cell>((vec->size() - 1)); }
// native ArraySetArray(Array:which, item, const any:input[], size =-1); static cell AMX_NATIVE_CALL ArraySetArray(AMX* amx, cell* params) { CellArray* vec = ArrayHandles.lookup(params[1]); if (!vec) { LogError(amx, AMX_ERR_NATIVE, "Invalid array handle provided (%d)", params[1]); return 0; } size_t idx = (size_t)params[2]; if (idx >= vec->size()) { LogError(amx, AMX_ERR_NATIVE, "Invalid index %d (count: %d)", idx, vec->size()); return 0; } cell *blk = vec->at(idx); size_t indexes = vec->blocksize(); if (*params / sizeof(cell) == 4) { if (params[4] != -1 && (size_t)params[4] <= vec->blocksize()) { indexes = params[4]; } } cell *addr = get_amxaddr(amx, params[3]); memcpy(blk, addr, sizeof(cell) * indexes); return indexes; }
// native SMC_SetParseEnd(SMCParser:handle, const func[]); static cell AMX_NATIVE_CALL SMC_SetParseEnd(AMX *amx, cell *params) { ParseInfo *p = TextParsersHandles.lookup(params[1]); if (!p) { LogError(amx, AMX_ERR_NATIVE, "Invalid SMC parse handle (%d)", params[1]); return 0; } int length = 0; const char *funcName = nullptr; if ((funcName = get_amxstring(amx, params[2], 0, length)) && length) { p->parse_end = registerSPForwardByName(amx, funcName, FP_CELL, FP_CELL, FP_CELL, FP_DONE); } if (p->parse_end == -1) { LogError(amx, AMX_ERR_NATIVE, "Function is not present (function \"%s\") (plugin \"%s\")", funcName, g_plugins.findPluginFast(amx)->getName()); return 0; } return 1; }
// native bool:TrieGetCell(Trie:handle, const key[], &any:value); static cell AMX_NATIVE_CALL TrieGetCell(AMX *amx, cell *params) { CellTrie *t = TrieHandles.lookup(params[1]); if (!t) { LogError(amx, AMX_ERR_NATIVE, "Invalid map handle provided (%d)", params[1]); return 0; } int len; const char *key = get_amxstring(amx, params[2], 0, len); StringHashMap<Entry>::Result r = t->map.find(key); if (!r.found()) { return 0; } cell *ptr = get_amxaddr(amx, params[3]); if (r->value.isCell()) { *ptr = r->value.cell_(); return 1; } return 0; }
// native Array:ArrayClone(Array:which); static cell AMX_NATIVE_CALL ArrayClone(AMX* amx, cell* params) { CellArray* vec = ArrayHandles.lookup(params[1]); if (!vec) { LogError(amx, AMX_ERR_NATIVE, "Invalid array handle provided (%d)", params[1]); return 0; } return ArrayHandles.clone(vec->clone()); }
// native TrieGetSize(Trie:handle); static cell AMX_NATIVE_CALL TrieGetSize(AMX *amx, cell *params) { CellTrie *t = TrieHandles.lookup(params[1]); if (!t) { LogError(amx, AMX_ERR_NATIVE, "Invalid map handle provided (%d)", params[1]); return 0; } return t->map.elements(); }
// native Trie::TrieClear(Trie:handle); static cell AMX_NATIVE_CALL TrieClear(AMX *amx, cell *params) { CellTrie *t = TrieHandles.lookup(params[1]); if (!t) { LogError(amx, AMX_ERR_NATIVE, "Invalid map handle provided (%d)", params[1]); return 0; } t->map.clear(); return 1; }
static cell AMX_NATIVE_CALL TrieSnapshotLength(AMX *amx, cell *params) { TrieSnapshot *snapshot = TrieSnapshotHandles.lookup(params[1]); if (!snapshot) { LogError(amx, AMX_ERR_NATIVE, "Invalid snapshot handle provided (%d)", params[1]); return 0; } return snapshot->length; }
// native any:ArrayGetCell(Array:which, item, block = 0, bool:asChar = false); static cell AMX_NATIVE_CALL ArrayGetCell(AMX* amx, cell* params) { CellArray* vec = ArrayHandles.lookup(params[1]); if (!vec) { LogError(amx, AMX_ERR_NATIVE, "Invalid array handle provided (%d)", params[1]); return 0; } size_t idx = (size_t)params[2]; if (idx >= vec->size()) { LogError(amx, AMX_ERR_NATIVE, "Invalid index %d (count: %d)", idx, vec->size()); return 0; } cell *blk = vec->at(idx); if (*params / sizeof(cell) <= 2) { return *blk; } idx = (size_t)params[3]; if (!params[4]) { if (idx >= vec->blocksize()) { LogError(amx, AMX_ERR_NATIVE, "Invalid block %d (blocksize: %d)", idx, vec->blocksize()); return 0; } return blk[idx]; } else { if (idx >= vec->blocksize() * 4) { LogError(amx, AMX_ERR_NATIVE, "Invalid byte %d (blocksize: %d bytes)", idx, vec->blocksize() * 4); return 0; } return (cell)*((char *)blk + idx); } return 0; }
// native bool:TrieGetArray(Trie:handle, const key[], any:buff[], len, &size = 0); static cell AMX_NATIVE_CALL TrieGetArray(AMX *amx, cell *params) { CellTrie *t = TrieHandles.lookup(params[1]); if (!t) { LogError(amx, AMX_ERR_NATIVE, "Invalid map handle provided (%d)", params[1]); return 0; } if (params[4] < 0) { LogError(amx, AMX_ERR_NATIVE, "Invalid array size (%d)", params[4]); return 0; } int len; const char *key = get_amxstring(amx, params[2], 0, len); cell *pValue = get_amxaddr(amx, params[3]); cell *pSize = get_amxaddr(amx, params[5]); StringHashMap<Entry>::Result r = t->map.find(key); if (!r.found() || !r->value.isArray()) { return 0; } if (!r->value.array()) { *pSize = 0; return 1; } if (!params[4]) { return 1; } size_t length = r->value.arrayLength(); cell *base = r->value.array(); if (length > size_t(params[4])) *pSize = params[4]; else *pSize = length; memcpy(pValue, base, sizeof(cell) * pSize[0]); return 1; }
// native bool:TrieKeyExists(Trie:handle, const key[]); static cell AMX_NATIVE_CALL TrieKeyExists(AMX *amx, cell *params) { CellTrie *t = TrieHandles.lookup(params[1]); if (!t) { LogError(amx, AMX_ERR_NATIVE, "Invalid map handle provided (%d)", params[1]); return 0; } int len; const char *key = get_amxstring(amx, params[2], 0, len); return static_cast<cell>(t->map.contains(key)); }
static cell AMX_NATIVE_CALL TrieSnapshotCreate(AMX *amx, cell *params) { CellTrie *t = TrieHandles.lookup(params[1]); if (!t) { LogError(amx, AMX_ERR_NATIVE, "Invalid map handle provided (%d)", params[1]); return 0; } int index = TrieSnapshotHandles.create(); TrieSnapshot *snapshot = TrieSnapshotHandles.lookup(index); snapshot->length = t->map.elements(); snapshot->keys = new int[snapshot->length]; size_t i = 0; for (StringHashMap<Entry>::iterator iter = t->map.iter(); !iter.empty(); iter.next(), i++) { snapshot->keys[i] = snapshot->strings.AddString(iter->key.chars(), iter->key.length()); } assert(i == snapshot->length); return static_cast<cell>(index); }
cell destroyParser(cell *handle) { ParseInfo *p = TextParsersHandles.lookup(*handle); if (!p) { return 0; } if (TextParsersHandles.destroy(*handle)) { *handle = 0; return 1; } return 0; }
// native bool:ArrayResize(Array:which, newsize); static cell AMX_NATIVE_CALL ArrayResize(AMX* amx, cell* params) { CellArray* vec = ArrayHandles.lookup(params[1]); if (!vec) { LogError(amx, AMX_ERR_NATIVE, "Invalid array handle provided (%d)", params[1]); return 0; } if (!vec->resize(params[2])) { LogError(amx, AMX_ERR_NATIVE, "Unable to resize array to \"%u\"", params[2]); return 0; } return 1; }
// native CloseGameConfigFile(&GameConfig:handle); static cell AMX_NATIVE_CALL CloseGameConfigFile(AMX *amx, cell *params) { cell *address = get_amxaddr(amx, params[1]); GameConfigNative *handle = GameConfigHandle.lookup(*address); if (!handle) { return 0; } if (GameConfigHandle.destroy(*address)) { *address = 0; return 1; } return 0; }
//native TrieSnapshotDestroy(&Snapshot:handle) static cell AMX_NATIVE_CALL TrieSnapshotDestroy(AMX *amx, cell *params) { cell *ptr = get_amxaddr(amx, params[1]); TrieSnapshot *t = TrieSnapshotHandles.lookup(*ptr); if (!t) { return 0; } if (TrieSnapshotHandles.destroy(*ptr)) { *ptr = 0; return 1; } return 0; }
// native ArrayDestroy(&Array:which); static cell AMX_NATIVE_CALL ArrayDestroy(AMX* amx, cell* params) { cell *handle = get_amxaddr(amx, params[1]); CellArray* vec = ArrayHandles.lookup(*handle); if (!vec) { return 0; } if (ArrayHandles.destroy(*handle)) { *handle = 0; return 1; } return 1; }
// native ArraySort(Array:array, const comparefunc[], data[]="", data_size=0); static cell AMX_NATIVE_CALL ArraySort(AMX* amx, cell* params) { cell handle = params[1]; CellArray* vec = ArrayHandles.lookup(handle); if (!vec) { LogError(amx, AMX_ERR_NATIVE, "Invalid array handle provided (%d)", handle); return 0; } int len; char* funcName = get_amxstring(amx, params[2], 0, len); // MySortFunc(Array:array, item1, item2, const data[], data_size) int func = registerSPForwardByName(amx, funcName, FP_CELL, FP_CELL, FP_CELL, FP_CELL, FP_CELL, FP_DONE); if (func < 0) { LogError(amx, AMX_ERR_NATIVE, "The public function \"%s\" was not found.", funcName); return 0; } size_t arraysize = vec->size(); size_t blocksize = vec->blocksize(); cell *array = vec->base(); ArraySort_s oldinfo = SortInfo; SortInfo.func = func; SortInfo.array_base = array; SortInfo.array_bsize = static_cast<cell>(blocksize); SortInfo.array_hndl = handle; SortInfo.data = params[3]; SortInfo.size = params[4]; qsort(array, arraysize, blocksize * sizeof(cell), SortArrayList); SortInfo = oldinfo; unregisterSPForward(func); return 1; }
static cell AMX_NATIVE_CALL TrieSnapshotKeyBufferSize(AMX *amx, cell *params) { TrieSnapshot *snapshot = TrieSnapshotHandles.lookup(params[1]); if (!snapshot) { LogError(amx, AMX_ERR_NATIVE, "Invalid snapshot handle provided (%d)", params[1]); return 0; } unsigned index = params[2]; if (index >= snapshot->length) { LogError(amx, AMX_ERR_NATIVE, "Invalid index %d", index); return 0; } return strlen(snapshot->strings.GetString(snapshot->keys[index])) + 1; }
// native ArrayFindValue(Array:which, any:item); static cell AMX_NATIVE_CALL ArrayFindValue(AMX* amx, cell* params) { CellArray* vec = ArrayHandles.lookup(params[1]); if (!vec) { LogError(amx, AMX_ERR_NATIVE, "Invalid array handle provided (%d)", params[1]); return -1; } for (size_t i = 0; i < vec->size(); i++) { if (params[2] == *vec->at(i)) { return static_cast<cell>(i); } } return -1; }