mirror of
https://github.com/alliedmodders/amxmodx.git
synced 2024-12-24 13:55:36 +03:00
fixed bcompat trans + optimized it a bit
added bcompat trans support to format() and copy()
This commit is contained in:
parent
3d74b7cf09
commit
2df8b4269e
@ -2,52 +2,28 @@
|
|||||||
#include "amxmod_compat.h"
|
#include "amxmod_compat.h"
|
||||||
#include "format.h"
|
#include "format.h"
|
||||||
|
|
||||||
struct translate_result
|
bool GetTranslation(amxtrans_t trans, int &key, int &dest, int &lang)
|
||||||
{
|
{
|
||||||
int suki;
|
key = (trans & BCOMPAT_TRANSLATE_KEYMASK);
|
||||||
int dest;
|
dest = (trans >> BCOMPAT_TRANSLATE_DESTRSH) & BCOMPAT_TRANSLATE_DESTMASK;
|
||||||
int lang;
|
lang = (trans >> BCOMPAT_TRANSLATE_LANGRSH) & BCOMPAT_TRANSLATE_LANGMASK;
|
||||||
};
|
|
||||||
|
|
||||||
CVector<translate_result *> g_tr_results;
|
if (dest == 0x3F)
|
||||||
CStack<size_t> g_old_ids;
|
|
||||||
|
|
||||||
bool GetTranslation(int id, int &key, int &dest, int &lang)
|
|
||||||
{
|
|
||||||
if (id < 0 || (unsigned int)id > g_tr_results.size())
|
|
||||||
{
|
{
|
||||||
return false;
|
dest = -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (lang == 0x1F)
|
||||||
|
{
|
||||||
|
lang = -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
translate_result *pRes = g_tr_results[id];
|
|
||||||
|
|
||||||
key = pRes->suki;
|
|
||||||
dest = pRes->dest;
|
|
||||||
lang = pRes->lang;
|
|
||||||
|
|
||||||
g_old_ids.push((size_t)id);
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ClearTransCache()
|
|
||||||
{
|
|
||||||
for (size_t i=0; i<g_tr_results.size(); i++)
|
|
||||||
{
|
|
||||||
delete g_tr_results[i];
|
|
||||||
}
|
|
||||||
g_tr_results.clear();
|
|
||||||
|
|
||||||
while (!g_old_ids.empty())
|
|
||||||
{
|
|
||||||
g_old_ids.pop();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
bool translate_bcompat(AMX *amx, cell *source, const char **_key, const char **_def)
|
bool translate_bcompat(AMX *amx, cell *source, const char **_key, const char **_def)
|
||||||
{
|
{
|
||||||
unsigned int trans = static_cast<unsigned int>(*source);
|
amxtrans_t trans = static_cast<amxtrans_t>(*source);
|
||||||
trans &= ~BCOMPAT_TRANSLATE_BITS;
|
|
||||||
int key, _dest, lang;
|
int key, _dest, lang;
|
||||||
if (!GetTranslation(trans, key, _dest, lang))
|
if (!GetTranslation(trans, key, _dest, lang))
|
||||||
{
|
{
|
||||||
@ -95,36 +71,41 @@ static cell AMX_NATIVE_CALL amx_translate(AMX *amx, cell *params)
|
|||||||
int len;
|
int len;
|
||||||
char *key = get_amxstring(amx, params[1], 0, len);
|
char *key = get_amxstring(amx, params[1], 0, len);
|
||||||
|
|
||||||
translate_result *pRes;
|
amxtrans_t trans;
|
||||||
size_t id;
|
|
||||||
if (g_old_ids.empty())
|
|
||||||
{
|
|
||||||
pRes = new translate_result;
|
|
||||||
id = g_tr_results.size();
|
|
||||||
g_tr_results.push_back(pRes);
|
|
||||||
} else {
|
|
||||||
if (g_tr_results.size() >= BCOMPAT_TRANSLATE_MAX)
|
|
||||||
{
|
|
||||||
LogError(amx, AMX_ERR_NATIVE, "Exceeded bcompat translation limit of %d!", BCOMPAT_TRANSLATE_MAX);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
id = g_old_ids.front();
|
|
||||||
g_old_ids.pop();
|
|
||||||
pRes = g_tr_results[id];
|
|
||||||
}
|
|
||||||
|
|
||||||
pRes->suki = g_langMngr.GetKeyEntry(key);
|
|
||||||
|
|
||||||
|
int suki = g_langMngr.GetKeyEntry(key);
|
||||||
//Some AMX Mod plugins do not register everything they need. Prevent a crash.
|
//Some AMX Mod plugins do not register everything they need. Prevent a crash.
|
||||||
if (pRes->suki == -1)
|
if (suki == -1)
|
||||||
{
|
{
|
||||||
pRes->suki = g_langMngr.AddKeyEntry(key);
|
suki = g_langMngr.AddKeyEntry(key);
|
||||||
}
|
}
|
||||||
|
|
||||||
pRes->dest = params[2];
|
if (suki > BCOMPAT_TRANSLATE_KEYMASK)
|
||||||
pRes->lang = params[3];
|
{
|
||||||
|
LogError(amx, AMX_ERR_NATIVE, "Not enough translation space, aborting!");
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
return (cell)((unsigned int)BCOMPAT_TRANSLATE_BITS | (unsigned int)id);
|
trans = suki & BCOMPAT_TRANSLATE_KEYMASK;
|
||||||
|
int dest = static_cast<int>(params[2]);
|
||||||
|
int lang = static_cast<int>(params[3]);
|
||||||
|
if (dest == -1)
|
||||||
|
{
|
||||||
|
trans |= (0x3F << BCOMPAT_TRANSLATE_DESTRSH);
|
||||||
|
} else {
|
||||||
|
trans |= (dest & BCOMPAT_TRANSLATE_DESTMASK) << BCOMPAT_TRANSLATE_DESTRSH;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (lang == -1)
|
||||||
|
{
|
||||||
|
trans |= (0x1F << BCOMPAT_TRANSLATE_LANGRSH);
|
||||||
|
} else {
|
||||||
|
trans |= (lang & BCOMPAT_TRANSLATE_LANGMASK) << BCOMPAT_TRANSLATE_LANGRSH;
|
||||||
|
}
|
||||||
|
|
||||||
|
trans |= BCOMPAT_TRANSLATE_BITS;
|
||||||
|
|
||||||
|
return static_cast<cell>(trans);
|
||||||
}
|
}
|
||||||
|
|
||||||
AMX_NATIVE_INFO g_BcompatNatives[] =
|
AMX_NATIVE_INFO g_BcompatNatives[] =
|
||||||
|
@ -1,11 +1,27 @@
|
|||||||
#ifndef _INCLUDE_AMXMOD_CORE_COMPAT_H
|
#ifndef _INCLUDE_AMXMOD_CORE_COMPAT_H
|
||||||
#define _INCLUDE_AMXMOD_CORE_COMPAT_H
|
#define _INCLUDE_AMXMOD_CORE_COMPAT_H
|
||||||
|
|
||||||
#define BCOMPAT_TRANSLATE_BITS 0xFFFFF400
|
/**
|
||||||
#define BCOMPAT_TRANSLATE_MAX 0x400
|
* New format for translation:
|
||||||
|
* Note that we only support:
|
||||||
|
* 4k keys
|
||||||
|
* 32 languages
|
||||||
|
* 0000 0000 0000 0000 0000 0000 0000 0000
|
||||||
|
* | key id |
|
||||||
|
* | | <- dest id
|
||||||
|
* | | <- lang id
|
||||||
|
*/
|
||||||
|
|
||||||
bool GetTranslation(int id, int &key, int &dest, int &lang);
|
#define BCOMPAT_TRANSLATE_BITS 0xFF000000
|
||||||
void ClearTransCache();
|
#define BCOMPAT_TRANSLATE_KEYMASK 0xFFF
|
||||||
|
#define BCOMPAT_TRANSLATE_DESTMASK 0x3F
|
||||||
|
#define BCOMPAT_TRANSLATE_DESTRSH 12
|
||||||
|
#define BCOMPAT_TRANSLATE_LANGMASK 0x1F
|
||||||
|
#define BCOMPAT_TRANSLATE_LANGRSH 18
|
||||||
|
|
||||||
|
typedef unsigned int amxtrans_t;
|
||||||
|
|
||||||
|
bool GetTranslation(amxtrans_t trans, int &key, int &dest, int &lang);
|
||||||
|
|
||||||
extern AMX_NATIVE_INFO g_BcompatNatives[];
|
extern AMX_NATIVE_INFO g_BcompatNatives[];
|
||||||
|
|
||||||
|
@ -628,7 +628,6 @@ void C_ServerDeactivate_Post()
|
|||||||
g_xvars.clear();
|
g_xvars.clear();
|
||||||
g_plugins.clear();
|
g_plugins.clear();
|
||||||
ClearPluginLibraries();
|
ClearPluginLibraries();
|
||||||
ClearTransCache();
|
|
||||||
modules_callPluginsUnloaded();
|
modules_callPluginsUnloaded();
|
||||||
|
|
||||||
ClearMessages();
|
ClearMessages();
|
||||||
|
@ -443,15 +443,42 @@ static cell AMX_NATIVE_CALL add(AMX *amx, cell *params) /* 4 param */
|
|||||||
static cell AMX_NATIVE_CALL copy(AMX *amx, cell *params) /* 4 param */
|
static cell AMX_NATIVE_CALL copy(AMX *amx, cell *params) /* 4 param */
|
||||||
{
|
{
|
||||||
cell *src = get_amxaddr(amx, params[3]);
|
cell *src = get_amxaddr(amx, params[3]);
|
||||||
cell *dest = get_amxaddr(amx, params[1]);
|
|
||||||
cell *start = dest;
|
|
||||||
int c = params[2];
|
int c = params[2];
|
||||||
|
|
||||||
while (c-- && *src)
|
if (amx->flags & AMX_FLAG_OLDFILE)
|
||||||
*dest++ =* src++;
|
{
|
||||||
*dest = 0;
|
if (*src & BCOMPAT_TRANSLATE_BITS)
|
||||||
|
{
|
||||||
return (dest - start);
|
const char *key, *def;
|
||||||
|
if (!translate_bcompat(amx, src, &key, &def))
|
||||||
|
{
|
||||||
|
goto normal_string;
|
||||||
|
}
|
||||||
|
cell *dest = get_amxaddr(amx, params[1]);
|
||||||
|
cell *start = dest;
|
||||||
|
while (c-- && *def)
|
||||||
|
{
|
||||||
|
*dest++ = static_cast<cell>(*def++);
|
||||||
|
}
|
||||||
|
*dest = '\0';
|
||||||
|
|
||||||
|
return dest-start;
|
||||||
|
} else {
|
||||||
|
goto normal_string;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
normal_string:
|
||||||
|
cell *dest = get_amxaddr(amx, params[1]);
|
||||||
|
cell *start = dest;
|
||||||
|
|
||||||
|
while (c-- && *src)
|
||||||
|
{
|
||||||
|
*dest++ = *src++;
|
||||||
|
}
|
||||||
|
*dest = '\0';
|
||||||
|
|
||||||
|
return (dest - start);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static cell AMX_NATIVE_CALL copyc(AMX *amx, cell *params) /* 4 param */
|
static cell AMX_NATIVE_CALL copyc(AMX *amx, cell *params) /* 4 param */
|
||||||
@ -568,7 +595,26 @@ static cell AMX_NATIVE_CALL format(AMX *amx, cell *params) /* 3 param */
|
|||||||
if (copy)
|
if (copy)
|
||||||
buf = g_cpbuf;
|
buf = g_cpbuf;
|
||||||
int param = 4;
|
int param = 4;
|
||||||
size_t total = atcprintf(buf, maxlen, fmt, amx, params, ¶m);
|
size_t total = 0;
|
||||||
|
|
||||||
|
if (amx->flags & AMX_FLAG_OLDFILE)
|
||||||
|
{
|
||||||
|
if (*fmt & BCOMPAT_TRANSLATE_BITS)
|
||||||
|
{
|
||||||
|
const char *key, *def;
|
||||||
|
if (!translate_bcompat(amx, fmt, &key, &def))
|
||||||
|
{
|
||||||
|
goto normal_string;
|
||||||
|
}
|
||||||
|
total = atcprintf(buf, maxlen, def, amx, params, ¶m);
|
||||||
|
} else {
|
||||||
|
goto normal_string;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
normal_string:
|
||||||
|
total = atcprintf(buf, maxlen, fmt, amx, params, ¶m);
|
||||||
|
}
|
||||||
|
|
||||||
if (copy)
|
if (copy)
|
||||||
{
|
{
|
||||||
/* copy back */
|
/* copy back */
|
||||||
|
Loading…
Reference in New Issue
Block a user