Cstrike: cs_set/reset_user_model/team - Stagger user's info updates across multiple frames (bug 3134)
This commit is contained in:
parent
aedde87f42
commit
8be119aa6a
|
@ -11,6 +11,12 @@
|
||||||
|
|
||||||
"Game Master"
|
"Game Master"
|
||||||
{
|
{
|
||||||
|
"globalvars.engine.txt"
|
||||||
|
{
|
||||||
|
"engine" "engine_ds"
|
||||||
|
"engine" "engine_ls"
|
||||||
|
}
|
||||||
|
|
||||||
"entities.games/cstrike/offsets-cairtank.txt"
|
"entities.games/cstrike/offsets-cairtank.txt"
|
||||||
{
|
{
|
||||||
"game" "cstrike"
|
"game" "cstrike"
|
||||||
|
|
|
@ -42,11 +42,16 @@ StringHashMap<int> ItemAliasList;
|
||||||
int TeamOffset;
|
int TeamOffset;
|
||||||
int MenuOffset;
|
int MenuOffset;
|
||||||
|
|
||||||
|
server_static_t *ServerStatic;
|
||||||
|
double *RealTime;
|
||||||
|
|
||||||
void InitializeHacks()
|
void InitializeHacks()
|
||||||
{
|
{
|
||||||
CtrlDetours_ClientCommand(true);
|
CtrlDetours_ClientCommand(true);
|
||||||
CtrlDetours_BuyCommands(true);
|
CtrlDetours_BuyCommands(true);
|
||||||
CtrlDetours_Natives(true);
|
CtrlDetours_Natives(true);
|
||||||
|
|
||||||
|
InitGlobalVars();
|
||||||
}
|
}
|
||||||
|
|
||||||
void ShutdownHacks()
|
void ShutdownHacks()
|
||||||
|
@ -301,8 +306,8 @@ void CtrlDetours_ClientCommand(bool set)
|
||||||
#endif
|
#endif
|
||||||
ClientCommandDetour = DETOUR_CREATE_STATIC_FIXED(C_ClientCommand, base);
|
ClientCommandDetour = DETOUR_CREATE_STATIC_FIXED(C_ClientCommand, base);
|
||||||
|
|
||||||
OffsetConfig->GetOffsetByClass("CBasePlayer", "m_iTeam", &TeamOffset);
|
CommonConfig->GetOffsetByClass("CBasePlayer", "m_iTeam", &TeamOffset);
|
||||||
OffsetConfig->GetOffsetByClass("CBasePlayer", "m_iMenu", &MenuOffset);
|
CommonConfig->GetOffsetByClass("CBasePlayer", "m_iMenu", &MenuOffset);
|
||||||
|
|
||||||
if (!ClientCommandDetour || !UseBotArgs || !BotArgs || !TeamOffset || !MenuOffset)
|
if (!ClientCommandDetour || !UseBotArgs || !BotArgs || !TeamOffset || !MenuOffset)
|
||||||
{
|
{
|
||||||
|
@ -506,3 +511,28 @@ void CtrlDetours_Natives(bool set)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void InitGlobalVars()
|
||||||
|
{
|
||||||
|
void *address = nullptr;
|
||||||
|
|
||||||
|
#if defined(WIN32)
|
||||||
|
|
||||||
|
int offset = 0;
|
||||||
|
|
||||||
|
if (CommonConfig->GetOffset("svs", &offset))
|
||||||
|
{
|
||||||
|
uintptr_t base = *reinterpret_cast<uintptr_t*>(reinterpret_cast<byte*>(g_engfuncs.pfnGetCurrentPlayer) + offset);
|
||||||
|
ServerStatic = reinterpret_cast<server_static_t*>(base - 4);
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
if (CommonConfig->GetMemSig("svs", &address))
|
||||||
|
{
|
||||||
|
ServerStatic = reinterpret_cast<server_static_t*>(address);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
if (CommonConfig->GetAddress("realtime", &address))
|
||||||
|
{
|
||||||
|
RealTime = reinterpret_cast<double*>(*reinterpret_cast<uintptr_t*>(address));
|
||||||
|
}
|
||||||
|
}
|
|
@ -17,8 +17,10 @@
|
||||||
#include <amxxmodule.h>
|
#include <amxxmodule.h>
|
||||||
#include <IGameConfigs.h>
|
#include <IGameConfigs.h>
|
||||||
#include <CDetour/detours.h>
|
#include <CDetour/detours.h>
|
||||||
|
#include <engine_strucs.h>
|
||||||
|
|
||||||
void InitializeHacks();
|
void InitializeHacks();
|
||||||
|
void InitGlobalVars();
|
||||||
void ShutdownHacks();
|
void ShutdownHacks();
|
||||||
void ToggleDetour_ClientCommands(bool enable);
|
void ToggleDetour_ClientCommands(bool enable);
|
||||||
void ToggleDetour_BuyCommands(bool enable);
|
void ToggleDetour_BuyCommands(bool enable);
|
||||||
|
@ -26,7 +28,7 @@ void ToggleDetour_BuyCommands(bool enable);
|
||||||
extern AMX_NATIVE_INFO CstrikeNatives[];
|
extern AMX_NATIVE_INFO CstrikeNatives[];
|
||||||
|
|
||||||
extern IGameConfig *MainConfig;
|
extern IGameConfig *MainConfig;
|
||||||
extern IGameConfig *OffsetConfig;
|
extern IGameConfig *CommonConfig;
|
||||||
|
|
||||||
extern int ForwardInternalCommand;
|
extern int ForwardInternalCommand;
|
||||||
extern int ForwardOnBuy;
|
extern int ForwardOnBuy;
|
||||||
|
@ -40,6 +42,10 @@ extern UTIL_FindEntityByStringFunc CS_UTIL_FindEntityByString;
|
||||||
|
|
||||||
extern CDetour *GiveDefaultItemsDetour;
|
extern CDetour *GiveDefaultItemsDetour;
|
||||||
extern enginefuncs_t *g_pengfuncsTable;
|
extern enginefuncs_t *g_pengfuncsTable;
|
||||||
|
extern DLL_FUNCTIONS *g_pFunctionTable;
|
||||||
extern bool NoKifesMode;
|
extern bool NoKifesMode;
|
||||||
|
|
||||||
|
extern server_static_t *ServerStatic;
|
||||||
|
extern double *RealTime;
|
||||||
|
|
||||||
#endif // CSTRIKE_HACKS_H
|
#endif // CSTRIKE_HACKS_H
|
||||||
|
|
|
@ -18,9 +18,7 @@
|
||||||
#include "CstrikeUserMessages.h"
|
#include "CstrikeUserMessages.h"
|
||||||
#include "CstrikeHLTypeConversion.h"
|
#include "CstrikeHLTypeConversion.h"
|
||||||
#include <CDetour/detours.h>
|
#include <CDetour/detours.h>
|
||||||
|
#include <am-vector.h>
|
||||||
CCstrikePlayer g_players[33];
|
|
||||||
int Zooming[33];
|
|
||||||
|
|
||||||
bool NoKifesMode = false;
|
bool NoKifesMode = false;
|
||||||
|
|
||||||
|
@ -536,7 +534,7 @@ static cell AMX_NATIVE_CALL cs_set_user_team(AMX *amx, cell *params)
|
||||||
set_pdata<int>(pPlayer, m_iModelName, model);
|
set_pdata<int>(pPlayer, m_iModelName, model);
|
||||||
}
|
}
|
||||||
|
|
||||||
MDLL_ClientUserInfoChanged(pPlayer, GETINFOKEYBUFFER(pPlayer));
|
Players[index].ResetModel(pPlayer);
|
||||||
|
|
||||||
char teaminfo[32];
|
char teaminfo[32];
|
||||||
|
|
||||||
|
@ -863,17 +861,11 @@ static cell AMX_NATIVE_CALL cs_set_user_model(AMX *amx, cell *params)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
char modelName[32];
|
|
||||||
int length;
|
int length;
|
||||||
|
const char *newModel = MF_GetAmxString(amx, params[2], 0, &length);
|
||||||
|
|
||||||
strcpy(modelName, MF_GetAmxString(amx, params[2], 0, &length));
|
Players[index].SetModel(newModel);
|
||||||
|
Players[index].UpdateModel(MF_GetPlayerEdict(index));
|
||||||
g_players[index].SetModel(modelName);
|
|
||||||
g_players[index].SetModelled(true);
|
|
||||||
|
|
||||||
EnableMessageHooks();
|
|
||||||
|
|
||||||
SETCLIENTKEYVALUE(index, GETINFOKEYBUFFER(pPlayer), "model", const_cast<char*>(g_players[index].GetModel()));
|
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
@ -886,9 +878,7 @@ static cell AMX_NATIVE_CALL cs_reset_user_model(AMX *amx, cell *params)
|
||||||
CHECK_PLAYER(index);
|
CHECK_PLAYER(index);
|
||||||
edict_t *pPlayer = MF_GetPlayerEdict(index);
|
edict_t *pPlayer = MF_GetPlayerEdict(index);
|
||||||
|
|
||||||
g_players[index].SetModelled(false);
|
Players[index].ResetModel(pPlayer);
|
||||||
|
|
||||||
MDLL_ClientUserInfoChanged(pPlayer, GETINFOKEYBUFFER(pPlayer));
|
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
@ -1317,7 +1307,7 @@ static cell AMX_NATIVE_CALL cs_set_user_zoom(AMX *amx, cell *params)
|
||||||
int mode = params[3];
|
int mode = params[3];
|
||||||
int weapon = *static_cast<int *>(MF_PlayerPropAddr(index, Player_CurrentWeapon));
|
int weapon = *static_cast<int *>(MF_PlayerPropAddr(index, Player_CurrentWeapon));
|
||||||
|
|
||||||
Zooming[index] = 0;
|
Players[index].ResetZoom();
|
||||||
|
|
||||||
if (type == CS_RESET_ZOOM)
|
if (type == CS_RESET_ZOOM)
|
||||||
{
|
{
|
||||||
|
@ -1365,7 +1355,7 @@ static cell AMX_NATIVE_CALL cs_set_user_zoom(AMX *amx, cell *params)
|
||||||
|
|
||||||
if (!mode)
|
if (!mode)
|
||||||
{
|
{
|
||||||
Zooming[index] = value;
|
Players[index].SetZoom(value);
|
||||||
EnableMessageHooks();
|
EnableMessageHooks();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1766,42 +1756,3 @@ AMX_NATIVE_INFO CstrikeNatives[] =
|
||||||
|
|
||||||
{nullptr, nullptr}
|
{nullptr, nullptr}
|
||||||
};
|
};
|
||||||
|
|
||||||
void ClientDisconnect(edict_t *pEntity)
|
|
||||||
{
|
|
||||||
int index = ENTINDEX(pEntity);
|
|
||||||
g_players[index].SetModelled(false);
|
|
||||||
Zooming[index] = 0;
|
|
||||||
|
|
||||||
RETURN_META(MRES_IGNORED);
|
|
||||||
}
|
|
||||||
|
|
||||||
void ClientUserInfoChanged(edict_t *pEntity, char *infobuffer)
|
|
||||||
{
|
|
||||||
int index = ENTINDEX(pEntity);
|
|
||||||
|
|
||||||
if(g_players[index].GetModelled() && pEntity->v.deadflag == DEAD_NO)
|
|
||||||
{
|
|
||||||
RETURN_META(MRES_SUPERCEDE);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
RETURN_META(MRES_IGNORED);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void PlayerPostThink(edict_t* pPlayer)
|
|
||||||
{
|
|
||||||
int entityIndex = ENTINDEX(pPlayer);
|
|
||||||
|
|
||||||
if(g_players[entityIndex].GetModelled())
|
|
||||||
{
|
|
||||||
if (g_players[entityIndex].GetInspectModel() && strcmp(g_players[entityIndex].GetModel(), GETCLIENTKEYVALUE(GETINFOKEYBUFFER(pPlayer), "model")) != 0)
|
|
||||||
{
|
|
||||||
//LOG_CONSOLE(PLID, "%s should have model %s and currently has %s", STRING(pPlayer->v.netname), (char*)g_players[entityIndex].GetModel(), GETCLIENTKEYVALUE(GETINFOKEYBUFFER(pPlayer), "model"));
|
|
||||||
SETCLIENTKEYVALUE(entityIndex, GETINFOKEYBUFFER(pPlayer), "model", (char*)g_players[entityIndex].GetModel());
|
|
||||||
g_players[entityIndex].SetInspectModel(false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
RETURN_META(MRES_IGNORED);
|
|
||||||
}
|
|
||||||
|
|
|
@ -12,47 +12,49 @@
|
||||||
//
|
//
|
||||||
|
|
||||||
#include "CstrikePlayer.h"
|
#include "CstrikePlayer.h"
|
||||||
#include <string.h> // strcpy()
|
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////
|
CPlayer Players[33];
|
||||||
// Construction/Destruction
|
ke::Vector<int> ModelsUpdateQueue;
|
||||||
//////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
CCstrikePlayer::CCstrikePlayer()
|
void ClientDisconnect(edict_t *pEntity)
|
||||||
{
|
{
|
||||||
modelled = false;
|
int index = ENTINDEX(pEntity);
|
||||||
inspectModel = false;
|
|
||||||
|
Players[index].ResetModel();
|
||||||
|
Players[index].ResetZoom();
|
||||||
|
|
||||||
|
RETURN_META(MRES_IGNORED);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool CCstrikePlayer::GetModelled()
|
void ClientUserInfoChanged(edict_t *pEntity, char *infobuffer)
|
||||||
{
|
{
|
||||||
return modelled;
|
if (pEntity->pvPrivateData)
|
||||||
|
{
|
||||||
|
Players[ENTINDEX(pEntity)].UpdateModel(pEntity);
|
||||||
|
}
|
||||||
|
|
||||||
|
RETURN_META(MRES_IGNORED);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool CCstrikePlayer::SetModelled(bool modelledIn)
|
void SetClientKeyValue(int clientIndex, char *infobuffer, const char *key, const char *value)
|
||||||
{
|
{
|
||||||
if (!modelledIn)
|
if (!strcmp(key, "model") && Players[clientIndex].HasModel(value))
|
||||||
SetInspectModel(false);
|
{
|
||||||
|
RETURN_META(MRES_SUPERCEDE);
|
||||||
|
}
|
||||||
|
|
||||||
return modelled = modelledIn;
|
RETURN_META(MRES_IGNORED);
|
||||||
}
|
}
|
||||||
|
|
||||||
const char* CCstrikePlayer::GetModel()
|
void StartFrame()
|
||||||
{
|
{
|
||||||
return model;
|
if (ModelsUpdateQueue.empty())
|
||||||
}
|
{
|
||||||
|
g_pFunctionTable->pfnStartFrame = nullptr;
|
||||||
|
RETURN_META(MRES_IGNORED);
|
||||||
|
}
|
||||||
|
|
||||||
void CCstrikePlayer::SetModel(const char* modelIn)
|
ServerStatic->clients[ModelsUpdateQueue.popCopy()].sendinfo = true;
|
||||||
{
|
|
||||||
strcpy(model, modelIn);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool CCstrikePlayer::GetInspectModel()
|
RETURN_META(MRES_IGNORED);
|
||||||
{
|
|
||||||
return inspectModel;
|
|
||||||
}
|
|
||||||
|
|
||||||
void CCstrikePlayer::SetInspectModel(bool inspectModelIn)
|
|
||||||
{
|
|
||||||
inspectModel = inspectModelIn;
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -11,30 +11,125 @@
|
||||||
// Counter-Strike Module
|
// Counter-Strike Module
|
||||||
//
|
//
|
||||||
|
|
||||||
#if !defined(INCLUDED_CCSTRIKEPLAYER)
|
#ifndef _CSTRIKE_PLAYER_H_
|
||||||
#define INCLUDED_CCSTRIKEPLAYER
|
#define _CSTRIKE_PLAYER_H_
|
||||||
|
|
||||||
class CCstrikePlayer
|
#include <amxxmodule.h>
|
||||||
|
#include "CstrikeUtils.h"
|
||||||
|
#include "CstrikeHacks.h"
|
||||||
|
#include <am-vector.h>
|
||||||
|
|
||||||
|
extern ke::Vector<int> ModelsUpdateQueue;
|
||||||
|
|
||||||
|
void StartFrame();
|
||||||
|
void ClientUserInfoChanged(edict_t *pEntity, char *infobuffer);
|
||||||
|
void SetClientKeyValue(int clientIndex, char *infobuffer, const char *key, const char *value);
|
||||||
|
|
||||||
|
class CPlayer
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
CCstrikePlayer();
|
|
||||||
|
|
||||||
bool GetModelled();
|
CPlayer()
|
||||||
bool SetModelled(bool modelledIn);
|
{
|
||||||
const char* GetModel();
|
ResetModel();
|
||||||
void SetModel(const char* modelIn);
|
ResetZoom();
|
||||||
|
}
|
||||||
|
|
||||||
bool GetInspectModel();
|
bool HasModel(const char *model = nullptr)
|
||||||
void SetInspectModel(bool inspectModelIn);
|
{
|
||||||
|
if (*m_Model != '\0')
|
||||||
|
{
|
||||||
|
if (model && *model)
|
||||||
|
{
|
||||||
|
return strcmp(m_Model, model) != 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
private:
|
return false;
|
||||||
bool inspectModel;
|
}
|
||||||
bool modelled;
|
|
||||||
char model[32];
|
void SetModel(const char* modelIn)
|
||||||
|
{
|
||||||
|
if (modelIn && *modelIn)
|
||||||
|
{
|
||||||
|
strncopy(m_Model, modelIn, sizeof(m_Model));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ResetModel();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void ResetModel(edict_t *pPlayer = nullptr)
|
||||||
|
{
|
||||||
|
*m_Model = '\0';
|
||||||
|
|
||||||
|
if (pPlayer)
|
||||||
|
{
|
||||||
|
MDLL_ClientUserInfoChanged(pPlayer, GETINFOKEYBUFFER(pPlayer));
|
||||||
|
|
||||||
|
PostponeModeUpdate(ENTINDEX(pPlayer) - 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void UpdateModel(edict_t *pPlayer)
|
||||||
|
{
|
||||||
|
if (!HasModel())
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
char *infobuffer = GETINFOKEYBUFFER(pPlayer);
|
||||||
|
|
||||||
|
if (strcmp(GETCLIENTKEYVALUE(infobuffer, "model"), m_Model) != 0)
|
||||||
|
{
|
||||||
|
int index = ENTINDEX(pPlayer);
|
||||||
|
|
||||||
|
SETCLIENTKEYVALUE(index, infobuffer, "model", m_Model);
|
||||||
|
|
||||||
|
PostponeModeUpdate(index - 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int GetZoom()
|
||||||
|
{
|
||||||
|
return m_Zooming;
|
||||||
|
}
|
||||||
|
|
||||||
|
void SetZoom(int value)
|
||||||
|
{
|
||||||
|
m_Zooming = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ResetZoom()
|
||||||
|
{
|
||||||
|
m_Zooming = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
void PostponeModeUpdate(int index)
|
||||||
|
{
|
||||||
|
ServerStatic->clients[index].sendinfo = false;
|
||||||
|
|
||||||
|
ModelsUpdateQueue.append(index);
|
||||||
|
|
||||||
|
if (!g_pFunctionTable->pfnStartFrame)
|
||||||
|
{
|
||||||
|
g_pFunctionTable->pfnStartFrame = StartFrame;
|
||||||
|
g_pFunctionTable->pfnClientUserInfoChanged = ClientUserInfoChanged;
|
||||||
|
g_pengfuncsTable->pfnSetClientKeyValue = SetClientKeyValue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
char m_Model[32];
|
||||||
|
int m_Zooming;
|
||||||
};
|
};
|
||||||
|
|
||||||
extern CCstrikePlayer g_players[33];
|
extern CPlayer Players[33];
|
||||||
extern int Zooming[33];
|
|
||||||
|
|
||||||
#endif // !defined(INCLUDED_CCSTRIKEPLAYER)
|
#endif // _CSTRIKE_PLAYER_H_
|
||||||
|
|
|
@ -76,14 +76,15 @@ void OnMessageBegin(int msg_dest, int msg_type, const float *pOrigin, edict_t *p
|
||||||
if (msg_type == MessageIdSetFOV)
|
if (msg_type == MessageIdSetFOV)
|
||||||
{
|
{
|
||||||
int index = ENTINDEX(pEntity);
|
int index = ENTINDEX(pEntity);
|
||||||
|
int zoom = Players[index].GetZoom();
|
||||||
|
|
||||||
if (Zooming[index])
|
if (zoom)
|
||||||
{
|
{
|
||||||
GET_OFFSET_NO_ERROR("CBasePlayer", m_iFOV);
|
GET_OFFSET_NO_ERROR("CBasePlayer", m_iFOV);
|
||||||
|
|
||||||
if (get_pdata<int>(pEntity, m_iFOV) != Zooming[index])
|
if (get_pdata<int>(pEntity, m_iFOV) != zoom)
|
||||||
{
|
{
|
||||||
set_pdata<int>(pEntity, m_iFOV, Zooming[index]);
|
set_pdata<int>(pEntity, m_iFOV, zoom);
|
||||||
|
|
||||||
ShouldBlock = true;
|
ShouldBlock = true;
|
||||||
ShouldBlockHLTV = true;
|
ShouldBlockHLTV = true;
|
||||||
|
@ -96,11 +97,8 @@ void OnMessageBegin(int msg_dest, int msg_type, const float *pOrigin, edict_t *p
|
||||||
{
|
{
|
||||||
int index = ENTINDEX(pEntity);
|
int index = ENTINDEX(pEntity);
|
||||||
|
|
||||||
if (Zooming[index])
|
if (Players[index].GetZoom())
|
||||||
Zooming[index] = 0;
|
Players[index].ResetZoom();
|
||||||
|
|
||||||
if (g_players[index].GetModelled())
|
|
||||||
g_players[index].SetInspectModel(true);
|
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
|
@ -78,7 +78,7 @@ bool UTIL_CheckForPublic(const char *publicname);
|
||||||
static int member = -1; \
|
static int member = -1; \
|
||||||
if (member == -1) \
|
if (member == -1) \
|
||||||
{ \
|
{ \
|
||||||
if (!OffsetConfig->GetOffsetByClass(classname, #member, &member) || member < 0)\
|
if (!CommonConfig->GetOffsetByClass(classname, #member, &member) || member < 0)\
|
||||||
{ \
|
{ \
|
||||||
MF_LogError(amx, AMX_ERR_NATIVE, "Invalid %s offset. Native %s is disabled", #member, __FUNCTION__);\
|
MF_LogError(amx, AMX_ERR_NATIVE, "Invalid %s offset. Native %s is disabled", #member, __FUNCTION__);\
|
||||||
return 0; \
|
return 0; \
|
||||||
|
@ -89,7 +89,7 @@ bool UTIL_CheckForPublic(const char *publicname);
|
||||||
static int member = -1; \
|
static int member = -1; \
|
||||||
if (member == -1) \
|
if (member == -1) \
|
||||||
{ \
|
{ \
|
||||||
if (!OffsetConfig->GetOffsetByClass(classname, #member, &member) || member < 0)\
|
if (!CommonConfig->GetOffsetByClass(classname, #member, &member) || member < 0)\
|
||||||
{ \
|
{ \
|
||||||
return; \
|
return; \
|
||||||
} \
|
} \
|
||||||
|
|
|
@ -17,9 +17,10 @@
|
||||||
#include "CstrikeHacks.h"
|
#include "CstrikeHacks.h"
|
||||||
#include "CstrikeHLTypeConversion.h"
|
#include "CstrikeHLTypeConversion.h"
|
||||||
#include <IGameConfigs.h>
|
#include <IGameConfigs.h>
|
||||||
|
#include "engine_strucs.h"
|
||||||
|
|
||||||
IGameConfig *MainConfig;
|
IGameConfig *MainConfig;
|
||||||
IGameConfig *OffsetConfig;
|
IGameConfig *CommonConfig;
|
||||||
IGameConfigManager *ConfigManager;
|
IGameConfigManager *ConfigManager;
|
||||||
|
|
||||||
int AmxxCheckGame(const char *game)
|
int AmxxCheckGame(const char *game)
|
||||||
|
@ -49,7 +50,7 @@ void OnAmxxAttach()
|
||||||
|
|
||||||
error[0] = '\0';
|
error[0] = '\0';
|
||||||
|
|
||||||
if (!ConfigManager->LoadGameConfigFile("common.games", &OffsetConfig, error, sizeof(error)) && error[0] != '\0')
|
if (!ConfigManager->LoadGameConfigFile("common.games", &CommonConfig, error, sizeof(error)) && error[0] != '\0')
|
||||||
{
|
{
|
||||||
MF_Log("Could not read common.games gamedata: %s", error);
|
MF_Log("Could not read common.games gamedata: %s", error);
|
||||||
return;
|
return;
|
||||||
|
@ -79,12 +80,17 @@ void OnPluginsLoaded()
|
||||||
{
|
{
|
||||||
G_OffsetHandler = new OffsetHandler;
|
G_OffsetHandler = new OffsetHandler;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Used with model natives, enabled on demand.
|
||||||
|
g_pengfuncsTable->pfnSetClientKeyValue = nullptr;
|
||||||
|
g_pFunctionTable->pfnClientUserInfoChanged = nullptr;
|
||||||
|
g_pFunctionTable->pfnStartFrame = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
void OnAmxxDetach()
|
void OnAmxxDetach()
|
||||||
{
|
{
|
||||||
ConfigManager->CloseGameConfigFile(MainConfig);
|
ConfigManager->CloseGameConfigFile(MainConfig);
|
||||||
ConfigManager->CloseGameConfigFile(OffsetConfig);
|
ConfigManager->CloseGameConfigFile(CommonConfig);
|
||||||
|
|
||||||
ShutdownHacks();
|
ShutdownHacks();
|
||||||
}
|
}
|
||||||
|
|
|
@ -122,11 +122,11 @@
|
||||||
// #define FN_ClientKill ClientKill /* pfnClientKill() (wd) Player has typed "kill" */
|
// #define FN_ClientKill ClientKill /* pfnClientKill() (wd) Player has typed "kill" */
|
||||||
// #define FN_ClientPutInServer ClientPutInServer /* pfnClientPutInServer() (wd) Client is entering the game */
|
// #define FN_ClientPutInServer ClientPutInServer /* pfnClientPutInServer() (wd) Client is entering the game */
|
||||||
// #define FN_ClientCommand ClientCommand /* pfnClientCommand() (wd) Player has sent a command (typed or from a bind) */
|
// #define FN_ClientCommand ClientCommand /* pfnClientCommand() (wd) Player has sent a command (typed or from a bind) */
|
||||||
#define FN_ClientUserInfoChanged ClientUserInfoChanged /* pfnClientUserInfoChanged() (wd) Client has updated their setinfo structure */
|
// #define FN_ClientUserInfoChanged ClientUserInfoChanged /* pfnClientUserInfoChanged() (wd) Client has updated their setinfo structure */
|
||||||
// #define FN_ServerActivate ServerActivate /* pfnServerActivate() (wd) Server is starting a new map */
|
// #define FN_ServerActivate ServerActivate /* pfnServerActivate() (wd) Server is starting a new map */
|
||||||
// #define FN_ServerDeactivate ServerDeactivate /* pfnServerDeactivate() (wd) Server is leaving the map (shutdown or changelevel); SDK2 */
|
// #define FN_ServerDeactivate ServerDeactivate /* pfnServerDeactivate() (wd) Server is leaving the map (shutdown or changelevel); SDK2 */
|
||||||
// #define FN_PlayerPreThink PlayerPreThink /* pfnPlayerPreThink() */
|
// #define FN_PlayerPreThink PlayerPreThink /* pfnPlayerPreThink() */
|
||||||
#define FN_PlayerPostThink PlayerPostThink /* pfnPlayerPostThink() */
|
// #define FN_PlayerPostThink PlayerPostThink /* pfnPlayerPostThink() */
|
||||||
// #define FN_StartFrame StartFrame /* pfnStartFrame() */
|
// #define FN_StartFrame StartFrame /* pfnStartFrame() */
|
||||||
// #define FN_ParmsNewLevel ParmsNewLevel /* pfnParmsNewLevel() */
|
// #define FN_ParmsNewLevel ParmsNewLevel /* pfnParmsNewLevel() */
|
||||||
// #define FN_ParmsChangeLevel ParmsChangeLevel /* pfnParmsChangeLevel() */
|
// #define FN_ParmsChangeLevel ParmsChangeLevel /* pfnParmsChangeLevel() */
|
||||||
|
|
512
public/engine_strucs.h
Normal file
512
public/engine_strucs.h
Normal file
|
@ -0,0 +1,512 @@
|
||||||
|
//
|
||||||
|
// AMX Mod X, based on AMX Mod by Aleksander Naszko ("OLO").
|
||||||
|
// Copyright (C) The AMX Mod X Development Team.
|
||||||
|
//
|
||||||
|
// This software is licensed under the GNU General Public License, version 3 or higher.
|
||||||
|
// Additional exceptions apply. For full license details, see LICENSE.txt or visit:
|
||||||
|
// https://alliedmods.net/amxmodx-license
|
||||||
|
|
||||||
|
#ifndef _ENGINE_STRUCTS_H_
|
||||||
|
#define _ENGINE_STRUCTS_H_
|
||||||
|
|
||||||
|
#include <extdll.h>
|
||||||
|
#include <meta_api.h>
|
||||||
|
#include <osdep.h>
|
||||||
|
#include <FileSystem.h>
|
||||||
|
#include <entity_state.h>
|
||||||
|
#include <usercmd.h>
|
||||||
|
|
||||||
|
#define MAX_CLIENTS 32
|
||||||
|
#define MAX_EDICTS 900
|
||||||
|
#define MAX_NAME 32
|
||||||
|
#define MAX_LIGHTSTYLES 64
|
||||||
|
#define MAX_PACKET_ENTITIES 256
|
||||||
|
|
||||||
|
#define MAX_LATENT 32
|
||||||
|
#define FRAGMENT_SIZE 1400
|
||||||
|
#define MAX_FRAGMENTS 25000
|
||||||
|
#define MAX_EVENT_QUEUE 64
|
||||||
|
|
||||||
|
#define MAX_FLOWS 2
|
||||||
|
#define FLOW_OUTGOING 0
|
||||||
|
#define FLOW_INCOMING 1
|
||||||
|
|
||||||
|
#define MAX_KV_LEN 127 // Max key/value length (with a NULL char)
|
||||||
|
#define MAX_INFO_STRING 256 // Key + value + 2 x slash + NULL
|
||||||
|
#define INFO_MAX_BUFFER_VALUES 4
|
||||||
|
|
||||||
|
#define FEVENT_ORIGIN (1<<0) // Event was invoked with stated origin
|
||||||
|
#define FEVENT_ANGLES (1<<1) // Event was invoked with stated angles
|
||||||
|
|
||||||
|
#define HL_MODEL_MAX 512
|
||||||
|
#define HL_GENERIC_MAX 512
|
||||||
|
#define HL_EVENT_MAX 256
|
||||||
|
#define HL_SOUND_MAX 512
|
||||||
|
#define HL_SOUND_HASHLOOKUP_SIZE (HL_SOUND_MAX * 2 - 1)
|
||||||
|
|
||||||
|
// Authentication types
|
||||||
|
#define AUTH_IDTYPE_UNKNOWN 0
|
||||||
|
#define AUTH_IDTYPE_STEAM 1
|
||||||
|
#define AUTH_IDTYPE_VALVE 2
|
||||||
|
#define AUTH_IDTYPE_LOCAL 3
|
||||||
|
|
||||||
|
#define NUM_BASELINES 64
|
||||||
|
|
||||||
|
// 0 == regular, 1 == file stream
|
||||||
|
#define MAX_STREAMS 2
|
||||||
|
|
||||||
|
// Flow control bytes per second limits
|
||||||
|
#define MAX_RATE 20000
|
||||||
|
#define MIN_RATE 1000
|
||||||
|
|
||||||
|
// Default data rate
|
||||||
|
#define DEFAULT_RATE (9999.0f)
|
||||||
|
|
||||||
|
// This is the packet payload without any header bytes (which are attached for actual sending)
|
||||||
|
#define NET_MAX_PAYLOAD 3990
|
||||||
|
|
||||||
|
typedef enum netsrc_s
|
||||||
|
{
|
||||||
|
NS_CLIENT,
|
||||||
|
NS_SERVER,
|
||||||
|
NS_MULTICAST
|
||||||
|
|
||||||
|
} netsrc_t;
|
||||||
|
|
||||||
|
typedef enum server_state_e
|
||||||
|
{
|
||||||
|
ss_dead = 0,
|
||||||
|
ss_loading = 1,
|
||||||
|
ss_active = 2,
|
||||||
|
|
||||||
|
} server_state_t;
|
||||||
|
|
||||||
|
typedef enum
|
||||||
|
{
|
||||||
|
NA_UNUSED,
|
||||||
|
NA_LOOPBACK,
|
||||||
|
NA_BROADCAST,
|
||||||
|
NA_IP,
|
||||||
|
NA_IPX,
|
||||||
|
NA_BROADCAST_IPX,
|
||||||
|
|
||||||
|
} netadrtype_t;
|
||||||
|
|
||||||
|
typedef struct netadr_s
|
||||||
|
{
|
||||||
|
netadrtype_t type;
|
||||||
|
unsigned char ip[4];
|
||||||
|
unsigned char ipx[10];
|
||||||
|
unsigned short port;
|
||||||
|
|
||||||
|
} netadr_t;
|
||||||
|
|
||||||
|
typedef struct sizebuf_s
|
||||||
|
{
|
||||||
|
const char* buffername;
|
||||||
|
uint16 flags;
|
||||||
|
byte* data;
|
||||||
|
int maxsize;
|
||||||
|
int cursize;
|
||||||
|
|
||||||
|
} sizebuf_t;
|
||||||
|
|
||||||
|
typedef struct flowstats_s
|
||||||
|
{
|
||||||
|
int size; // Size of message sent/received
|
||||||
|
double time; // Time that message was sent/received
|
||||||
|
|
||||||
|
} flowstats_t;
|
||||||
|
|
||||||
|
typedef struct flow_s
|
||||||
|
{
|
||||||
|
|
||||||
|
flowstats_t stats[MAX_LATENT]; // Data for last MAX_LATENT messages
|
||||||
|
int current; // Current message position
|
||||||
|
double nextcompute; // Time when we should recompute k/sec data
|
||||||
|
float kbytespersec; // Average data
|
||||||
|
float avgkbytespersec;
|
||||||
|
|
||||||
|
} flow_t;
|
||||||
|
|
||||||
|
typedef struct fragbuf_s
|
||||||
|
{
|
||||||
|
|
||||||
|
fragbuf_s* next; // Next buffer in chain
|
||||||
|
int bufferid; // Id of this buffer
|
||||||
|
|
||||||
|
sizebuf_t frag_message; // Message buffer where raw data is stored
|
||||||
|
byte frag_message_buf[FRAGMENT_SIZE]; // The actual data sits here
|
||||||
|
|
||||||
|
qboolean isfile; // Is this a file buffer?
|
||||||
|
qboolean isbuffer; // Is this file buffer from memory ( custom decal, etc. ).
|
||||||
|
qboolean iscompressed;
|
||||||
|
|
||||||
|
char filename[MAX_PATH]; // Name of the file to save out on remote host
|
||||||
|
int foffset; // Offset in file from which to read data
|
||||||
|
int size; // Size of data to read at that offset
|
||||||
|
|
||||||
|
} fragbuf_t;
|
||||||
|
|
||||||
|
typedef struct fragbufwaiting_s
|
||||||
|
{
|
||||||
|
fragbufwaiting_s* next; // Next chain in waiting list
|
||||||
|
int fragbufcount; // Number of buffers in this chain
|
||||||
|
fragbuf_t* fragbufs; // The actual buffers
|
||||||
|
|
||||||
|
} fragbufwaiting_t;
|
||||||
|
|
||||||
|
typedef struct netchan_s
|
||||||
|
{
|
||||||
|
netsrc_t sock; // NS_SERVER or NS_CLIENT, depending on channel.
|
||||||
|
netadr_t remote_address; // Address this channel is talking to.
|
||||||
|
|
||||||
|
int player_slot;
|
||||||
|
|
||||||
|
float last_received; // For timeouts. Time last message was received.
|
||||||
|
float connect_time; // Time when channel was connected.
|
||||||
|
|
||||||
|
double rate; // Bandwidth choke, Bytes per second
|
||||||
|
double cleartime; // If realtime > cleartime, free to send next packet
|
||||||
|
|
||||||
|
// Sequencing variables
|
||||||
|
int incoming_sequence; // Increasing count of sequence numbers
|
||||||
|
int incoming_acknowledged; // # of last outgoing message that has been ack'd.
|
||||||
|
int incoming_reliable_acknowledged;// Toggles T/F as reliable messages are received.
|
||||||
|
int incoming_reliable_sequence; // single bit, maintained local
|
||||||
|
int outgoing_sequence; // Message we are sending to remote
|
||||||
|
int reliable_sequence; // Whether the message contains reliable payload, single bit
|
||||||
|
int last_reliable_sequence; // Outgoing sequence number of last send that had reliable data
|
||||||
|
|
||||||
|
void* connection_status;
|
||||||
|
int (*pfnNetchan_Blocksize)(void *);
|
||||||
|
|
||||||
|
sizebuf_t message; // Staging and holding areas
|
||||||
|
byte message_buf[NET_MAX_PAYLOAD];
|
||||||
|
|
||||||
|
|
||||||
|
int reliable_length; // Reliable message buffer. We keep adding to it until reliable is acknowledged. Then we clear it.
|
||||||
|
byte reliable_buf[NET_MAX_PAYLOAD];
|
||||||
|
|
||||||
|
fragbufwaiting_t* waitlist[MAX_STREAMS]; // Waiting list of buffered fragments to go onto queue. Multiple outgoing buffers can be queued in succession.
|
||||||
|
|
||||||
|
int reliable_fragment[MAX_STREAMS]; // Is reliable waiting buf a fragment?
|
||||||
|
unsigned int reliable_fragid[MAX_STREAMS]; // Buffer id for each waiting fragment
|
||||||
|
|
||||||
|
|
||||||
|
fragbuf_t* fragbufs[MAX_STREAMS]; // The current fragment being set
|
||||||
|
int fragbufcount[MAX_STREAMS]; // The total number of fragments in this stream
|
||||||
|
|
||||||
|
short int frag_startpos[MAX_STREAMS]; // Position in outgoing buffer where frag data starts
|
||||||
|
short int frag_length[MAX_STREAMS]; // Length of frag data in the buffer
|
||||||
|
|
||||||
|
fragbuf_t* incomingbufs[MAX_STREAMS]; // Incoming fragments are stored here
|
||||||
|
qboolean incomingready[MAX_STREAMS]; // Set to true when incoming data is ready
|
||||||
|
|
||||||
|
char incomingfilename[MAX_PATH]; // Only referenced by the FRAG_FILE_STREAM component
|
||||||
|
// Name of file being downloaded
|
||||||
|
void* tempbuffer;
|
||||||
|
int tempbuffersize;
|
||||||
|
|
||||||
|
flow_t flow[MAX_FLOWS]; // Incoming and outgoing flow metrics
|
||||||
|
|
||||||
|
} netchan_t;
|
||||||
|
|
||||||
|
typedef struct packet_entities_s
|
||||||
|
{
|
||||||
|
int num_entities;
|
||||||
|
unsigned char flags[32];
|
||||||
|
entity_state_t* entities;
|
||||||
|
|
||||||
|
} packet_entities_t;
|
||||||
|
|
||||||
|
|
||||||
|
typedef struct client_frame_s
|
||||||
|
{
|
||||||
|
double senttime;
|
||||||
|
float ping_time;
|
||||||
|
clientdata_t clientdata;
|
||||||
|
weapon_data_t weapondata[64];
|
||||||
|
packet_entities_t entities;
|
||||||
|
|
||||||
|
} client_frame_t;
|
||||||
|
|
||||||
|
typedef struct event_args_s
|
||||||
|
{
|
||||||
|
int flags;
|
||||||
|
|
||||||
|
int entindex; // Transmitted
|
||||||
|
|
||||||
|
float origin[3];
|
||||||
|
float angles[3];
|
||||||
|
float velocity[3];
|
||||||
|
|
||||||
|
int ducking;
|
||||||
|
|
||||||
|
float fparam1;
|
||||||
|
float fparam2;
|
||||||
|
|
||||||
|
int iparam1;
|
||||||
|
int iparam2;
|
||||||
|
|
||||||
|
int bparam1;
|
||||||
|
int bparam2;
|
||||||
|
|
||||||
|
} event_args_t;
|
||||||
|
|
||||||
|
struct event_info_s
|
||||||
|
{
|
||||||
|
unsigned short index; // 0 implies not in use
|
||||||
|
|
||||||
|
short packet_index; // Use data from state info for entity in delta_packet . -1 implies separate info based on event
|
||||||
|
short entity_index; // The edict this event is associated with
|
||||||
|
|
||||||
|
float fire_time; // if non-zero, the time when the event should be fired ( fixed up on the client )
|
||||||
|
|
||||||
|
event_args_t args;
|
||||||
|
int flags; // Client only - Reliable or not, etc.
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct event_state_s
|
||||||
|
{
|
||||||
|
struct event_info_s ei[MAX_EVENT_QUEUE];
|
||||||
|
|
||||||
|
} event_state_t;
|
||||||
|
|
||||||
|
typedef struct USERID_s
|
||||||
|
{
|
||||||
|
int idtype;
|
||||||
|
uint64 m_SteamID;
|
||||||
|
unsigned int clientip;
|
||||||
|
|
||||||
|
} USERID_t;
|
||||||
|
|
||||||
|
typedef struct consistency_s
|
||||||
|
{
|
||||||
|
char* filename;
|
||||||
|
int issound;
|
||||||
|
int orig_index;
|
||||||
|
int value;
|
||||||
|
int check_type;
|
||||||
|
float mins[3];
|
||||||
|
float maxs[3];
|
||||||
|
|
||||||
|
} consistency_t;
|
||||||
|
|
||||||
|
typedef struct event_s
|
||||||
|
{
|
||||||
|
unsigned short index;
|
||||||
|
const char* filename;
|
||||||
|
int filesize;
|
||||||
|
const char* pszScript;
|
||||||
|
|
||||||
|
} event_t;
|
||||||
|
|
||||||
|
typedef struct extra_baselines_s
|
||||||
|
{
|
||||||
|
int number;
|
||||||
|
int classname[NUM_BASELINES];
|
||||||
|
entity_state_t baseline[NUM_BASELINES];
|
||||||
|
} extra_baselines_t;
|
||||||
|
|
||||||
|
typedef struct server_log_s
|
||||||
|
{
|
||||||
|
qboolean active;
|
||||||
|
qboolean net_log_;
|
||||||
|
netadr_t net_address_;
|
||||||
|
void* file;
|
||||||
|
|
||||||
|
} server_log_t;
|
||||||
|
|
||||||
|
typedef struct server_stats_s
|
||||||
|
{
|
||||||
|
int num_samples;
|
||||||
|
|
||||||
|
int at_capacity;
|
||||||
|
int at_empty;
|
||||||
|
|
||||||
|
float capacity_percent;
|
||||||
|
float empty_percent;
|
||||||
|
|
||||||
|
int minusers;
|
||||||
|
int maxusers;
|
||||||
|
|
||||||
|
float cumulative_occupancy;
|
||||||
|
float occupancy;
|
||||||
|
|
||||||
|
int num_sessions;
|
||||||
|
float cumulative_sessiontime;
|
||||||
|
float average_session_len;
|
||||||
|
|
||||||
|
float cumulative_latency;
|
||||||
|
float average_latency;
|
||||||
|
|
||||||
|
} server_stats_t;
|
||||||
|
|
||||||
|
typedef struct server_static_s
|
||||||
|
{
|
||||||
|
qboolean dll_initialized;
|
||||||
|
|
||||||
|
struct client_s* clients;
|
||||||
|
int maxclients;
|
||||||
|
int maxclientslimit;
|
||||||
|
|
||||||
|
int spawncount;
|
||||||
|
int serverflags;
|
||||||
|
|
||||||
|
server_log_t log;
|
||||||
|
|
||||||
|
double next_cleartime;
|
||||||
|
double next_sampletime;
|
||||||
|
|
||||||
|
server_stats_t stats;
|
||||||
|
qboolean isSecure;
|
||||||
|
|
||||||
|
} server_static_t;
|
||||||
|
|
||||||
|
typedef struct server_s
|
||||||
|
{
|
||||||
|
qboolean active;
|
||||||
|
qboolean paused;
|
||||||
|
qboolean loadgame;
|
||||||
|
|
||||||
|
double time;
|
||||||
|
double oldtime;
|
||||||
|
|
||||||
|
int lastcheck;
|
||||||
|
double lastchecktime;
|
||||||
|
|
||||||
|
char name[64];
|
||||||
|
char oldname[64];
|
||||||
|
char startspot[64];
|
||||||
|
char modelname[64];
|
||||||
|
|
||||||
|
struct model_s* worldmodel;
|
||||||
|
CRC32_t worldmapCRC;
|
||||||
|
|
||||||
|
unsigned char clientdllmd5[16];
|
||||||
|
|
||||||
|
resource_t resourcelist[1280];
|
||||||
|
int num_resources;
|
||||||
|
|
||||||
|
consistency_t consistency_list[512];
|
||||||
|
int num_consistency;
|
||||||
|
|
||||||
|
const char* model_precache[HL_MODEL_MAX];
|
||||||
|
struct model_s* models[HL_MODEL_MAX];
|
||||||
|
unsigned char model_precache_flags[HL_MODEL_MAX];
|
||||||
|
struct event_s event_precache[HL_EVENT_MAX];
|
||||||
|
|
||||||
|
const char* sound_precache[HL_SOUND_MAX];
|
||||||
|
short int sound_precache_hashedlookup[HL_SOUND_HASHLOOKUP_SIZE];
|
||||||
|
qboolean sound_precache_hashedlookup_built;
|
||||||
|
|
||||||
|
const char* generic_precache[HL_GENERIC_MAX];
|
||||||
|
char generic_precache_names[HL_GENERIC_MAX][64];
|
||||||
|
int num_generic_names;
|
||||||
|
|
||||||
|
char* lightstyles[MAX_LIGHTSTYLES];
|
||||||
|
|
||||||
|
int num_edicts;
|
||||||
|
int max_edicts;
|
||||||
|
edict_t* edicts;
|
||||||
|
|
||||||
|
struct entity_state_s* baselines;
|
||||||
|
extra_baselines_t* instance_baselines;
|
||||||
|
server_state_t state;
|
||||||
|
|
||||||
|
sizebuf_t datagram;
|
||||||
|
unsigned char datagram_buf[4000];
|
||||||
|
|
||||||
|
sizebuf_t reliable_datagram;
|
||||||
|
unsigned char reliable_datagram_buf[4000];
|
||||||
|
|
||||||
|
sizebuf_t multicast;
|
||||||
|
unsigned char multicast_buf[1024];
|
||||||
|
|
||||||
|
sizebuf_t spectator;
|
||||||
|
unsigned char spectator_buf[1024];
|
||||||
|
|
||||||
|
sizebuf_t signon;
|
||||||
|
unsigned char signon_data[32768];
|
||||||
|
|
||||||
|
} server_t;
|
||||||
|
|
||||||
|
typedef struct client_s
|
||||||
|
{
|
||||||
|
qboolean active;
|
||||||
|
qboolean spawned;
|
||||||
|
qboolean fully_connected;
|
||||||
|
qboolean connected;
|
||||||
|
qboolean uploading;
|
||||||
|
qboolean hasusrmsgs;
|
||||||
|
qboolean has_force_unmodified;
|
||||||
|
|
||||||
|
netchan_t netchan;
|
||||||
|
|
||||||
|
int chokecount;
|
||||||
|
int delta_sequence;
|
||||||
|
|
||||||
|
qboolean fakeclient;
|
||||||
|
qboolean proxy;
|
||||||
|
usercmd_t lastcmd;
|
||||||
|
|
||||||
|
double connecttime;
|
||||||
|
double cmdtime;
|
||||||
|
double ignorecmdtime;
|
||||||
|
|
||||||
|
float latency;
|
||||||
|
float packet_loss;
|
||||||
|
|
||||||
|
double localtime;
|
||||||
|
double nextping;
|
||||||
|
double svtimebase;
|
||||||
|
|
||||||
|
sizebuf_t datagram;
|
||||||
|
byte datagram_buf[4000];
|
||||||
|
|
||||||
|
double connection_started;
|
||||||
|
double next_messagetime;
|
||||||
|
double next_messageinterval;
|
||||||
|
qboolean send_message;
|
||||||
|
qboolean skip_message;
|
||||||
|
|
||||||
|
client_frame_t* frames;
|
||||||
|
event_state_t events;
|
||||||
|
edict_t* edict;
|
||||||
|
const edict_t* pViewEntity;
|
||||||
|
int userid;
|
||||||
|
USERID_t network_userid;
|
||||||
|
|
||||||
|
char userinfo[MAX_INFO_STRING];
|
||||||
|
|
||||||
|
qboolean sendinfo;
|
||||||
|
float sendinfo_time;
|
||||||
|
|
||||||
|
char hashedcdkey[64];
|
||||||
|
char name[32];
|
||||||
|
int topcolor;
|
||||||
|
int bottomcolor;
|
||||||
|
int entityId;
|
||||||
|
|
||||||
|
resource_t resourcesonhand;
|
||||||
|
resource_t resourcesneeded;
|
||||||
|
|
||||||
|
FileHandle_t upload;
|
||||||
|
qboolean uploaddoneregistering;
|
||||||
|
customization_t customdata;
|
||||||
|
|
||||||
|
int crcValue;
|
||||||
|
int lw;
|
||||||
|
int lc;
|
||||||
|
|
||||||
|
char physinfo[MAX_INFO_STRING];
|
||||||
|
|
||||||
|
qboolean m_bLoopback;
|
||||||
|
uint32 m_VoiceStreams[2];
|
||||||
|
double m_lastvoicetime;
|
||||||
|
int m_sendrescount;
|
||||||
|
|
||||||
|
} client_t;
|
||||||
|
|
||||||
|
#endif //_ENGINE_STRUCTS_H_
|
|
@ -3151,3 +3151,27 @@ size_t UTIL_Format(char *buffer, size_t maxlength, const char *fmt, ...)
|
||||||
return len;
|
return len;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template unsigned int strncopy<char, char>(char *, const char *src, size_t count);
|
||||||
|
template unsigned int strncopy<cell, char>(cell *, const char *src, size_t count);
|
||||||
|
template unsigned int strncopy<cell, cell>(cell *, const cell *src, size_t count);
|
||||||
|
|
||||||
|
template <typename D, typename S>
|
||||||
|
unsigned int strncopy(D *dest, const S *src, size_t count)
|
||||||
|
{
|
||||||
|
if (!count)
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
D *start = dest;
|
||||||
|
|
||||||
|
while ((*src) && (--count))
|
||||||
|
{
|
||||||
|
*dest++ = *(unsigned char*)src++;
|
||||||
|
}
|
||||||
|
|
||||||
|
*dest = '\0';
|
||||||
|
|
||||||
|
return (dest - start);
|
||||||
|
}
|
||||||
|
|
|
@ -2509,5 +2509,6 @@ void Mem_Deallocator(const char *sourceFile, const unsigned int sourceLine, cons
|
||||||
#endif //MEMORY_TEST
|
#endif //MEMORY_TEST
|
||||||
|
|
||||||
size_t UTIL_Format(char *buffer, size_t maxlength, const char *fmt, ...);
|
size_t UTIL_Format(char *buffer, size_t maxlength, const char *fmt, ...);
|
||||||
|
template <typename D, typename S> unsigned int strncopy(D *dest, const S *src, size_t count);
|
||||||
|
|
||||||
#endif // #ifndef __AMXXMODULE_H__
|
#endif // #ifndef __AMXXMODULE_H__
|
||||||
|
|
Loading…
Reference in New Issue
Block a user