diff --git a/reapi/include/cssdk/common/IObjectContainer.h b/reapi/include/cssdk/common/IObjectContainer.h new file mode 100644 index 00000000..333e9d04 --- /dev/null +++ b/reapi/include/cssdk/common/IObjectContainer.h @@ -0,0 +1,47 @@ +/* +* +* This program is free software; you can redistribute it and/or modify it +* under the terms of the GNU General Public License as published by the +* Free Software Foundation; either version 2 of the License, or (at +* your option) any later version. +* +* This program is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +* General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program; if not, write to the Free Software Foundation, +* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +* +* In addition, as a special exception, the author gives permission to +* link the code of this program with the Half-Life Game Engine ("HL +* Engine") and Modified Game Libraries ("MODs") developed by Valve, +* L.L.C ("Valve"). You must obey the GNU General Public License in all +* respects for all of the code used other than the HL Engine and MODs +* from Valve. If you modify this file, you may extend this exception +* to your version of the file, but you are not obligated to do so. If +* you do not wish to do so, delete this exception statement from your +* version. +* +*/ + +#pragma once + +class IObjectContainer { +public: + virtual ~IObjectContainer() {} + + virtual void Init() = 0; + + virtual bool Add(void *newObject) = 0; + virtual bool Remove(void *object) = 0; + virtual void Clear(bool freeElementsMemory) = 0; + + virtual void *GetFirst() = 0; + virtual void *GetNext() = 0; + + virtual int CountElements() = 0; + virtual bool Contains(void *object) = 0; + virtual bool IsEmpty() = 0; +}; diff --git a/reapi/include/cssdk/common/ObjectList.h b/reapi/include/cssdk/common/ObjectList.h new file mode 100644 index 00000000..aa023f84 --- /dev/null +++ b/reapi/include/cssdk/common/ObjectList.h @@ -0,0 +1,65 @@ +/* +* +* This program is free software; you can redistribute it and/or modify it +* under the terms of the GNU General Public License as published by the +* Free Software Foundation; either version 2 of the License, or (at +* your option) any later version. +* +* This program is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +* General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program; if not, write to the Free Software Foundation, +* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +* +* In addition, as a special exception, the author gives permission to +* link the code of this program with the Half-Life Game Engine ("HL +* Engine") and Modified Game Libraries ("MODs") developed by Valve, +* L.L.C ("Valve"). You must obey the GNU General Public License in all +* respects for all of the code used other than the HL Engine and MODs +* from Valve. If you modify this file, you may extend this exception +* to your version of the file, but you are not obligated to do so. If +* you do not wish to do so, delete this exception statement from your +* version. +* +*/ + +#pragma once + +#include "IObjectContainer.h" + +class ObjectList: public IObjectContainer { +public: + EXT_FUNC void Init(); + EXT_FUNC bool Add(void *newObject); + EXT_FUNC void *GetFirst(); + EXT_FUNC void *GetNext(); + + ObjectList(); + virtual ~ObjectList(); + + EXT_FUNC void Clear(bool freeElementsMemory = false); + EXT_FUNC int CountElements(); + void *RemoveTail(); + void *RemoveHead(); + + bool AddTail(void *newObject); + bool AddHead(void *newObject); + EXT_FUNC bool Remove(void *object); + EXT_FUNC bool Contains(void *object); + EXT_FUNC bool IsEmpty(); + + typedef struct element_s { + struct element_s *prev; // pointer to the last element or NULL + struct element_s *next; // pointer to the next elemnet or NULL + void *object; // the element's object + } element_t; + +protected: + element_t *m_head; // first element in list + element_t *m_tail; // last element in list + element_t *m_current; // current element in list + int m_number; +}; diff --git a/reapi/include/cssdk/common/cvardef.h b/reapi/include/cssdk/common/cvardef.h index cc3a2226..7bba22b0 100644 --- a/reapi/include/cssdk/common/cvardef.h +++ b/reapi/include/cssdk/common/cvardef.h @@ -1,9 +1,9 @@ /*** * * Copyright (c) 1996-2002, Valve LLC. All rights reserved. -* -* This product contains software technology licensed from Id -* Software, Inc. ("Id Technology"). Id Technology (c) 1996 Id Software, Inc. +* +* This product contains software technology licensed from Id +* Software, Inc. ("Id Technology"). Id Technology (c) 1996 Id Software, Inc. * All Rights Reserved. * * Use, distribution, and modification of this source code and/or resulting @@ -36,4 +36,15 @@ typedef struct cvar_s struct cvar_s *next; } cvar_t; +using cvar_callback_t = void (*)(const char *pszNewValue); + +struct cvar_listener_t +{ + cvar_listener_t(const char *var_name, cvar_callback_t handler) : + func(handler), name(var_name) {} + + cvar_callback_t func; + const char *name; +}; + #endif // CVARDEF_H diff --git a/reapi/include/cssdk/common/quakedef.h b/reapi/include/cssdk/common/quakedef.h index c587e809..93e67cb5 100644 --- a/reapi/include/cssdk/common/quakedef.h +++ b/reapi/include/cssdk/common/quakedef.h @@ -27,18 +27,18 @@ */ #pragma once -/* <19039> ../common/quakedef.h:29 */ -typedef int BOOL; /* size: 4 */ +typedef int BOOL; + +// The maximum user messages +#define MAX_USERMESSAGES 256 // user message #define MAX_USER_MSG_DATA 192 -/* <627f> ../common/quakedef.h:137 */ //moved to com_model.h //typedef struct cache_user_s //{ // void *data; //} cache_user_t; -/* <4313b> ../common/quakedef.h:162 */ typedef int (*pfnUserMsgHook)(const char *, int, void *); diff --git a/reapi/include/cssdk/engine/IMessageManager.h b/reapi/include/cssdk/engine/IMessageManager.h new file mode 100644 index 00000000..cf818dbc --- /dev/null +++ b/reapi/include/cssdk/engine/IMessageManager.h @@ -0,0 +1,223 @@ +/* +* +* This program is free software; you can redistribute it and/or modify it +* under the terms of the GNU General Public License as published by the +* Free Software Foundation; either version 2 of the License, or (at +* your option) any later version. +* +* This program is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +* General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program; if not, write to the Free Software Foundation, +* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +* +*/ + +#pragma once + +/** + * @brief Interface for defining message parameters and behavior for a individual message object + */ +class IMessage +{ +public: + /** + * @brief The parameter types for a message + */ + enum class ParamType : uint8 + { + Byte, + Char, + Short, + Long, + Angle, + Coord, + String, + Entity, + }; + + /** + * @brief Blocking behavior types for messages + */ + enum class BlockType : uint8 + { + Not, // Not a block + Once, // Block once + Set // Set block + }; + + /** + * @brief Message destinations + */ + enum class Dest : uint8 + { + BROADCAST, // Unreliable to all + ONE, // Reliable to one (msg_entity) + ALL, // Reliable to all + INIT, // Write to the init string + PVS, // Ents in PVS of org + PAS, // Ents in PAS of org + PVS_R, // Reliable to PVS + PAS_R, // Reliable to PAS + ONE_UNRELIABLE, // Send to one client, but don't put in reliable stream, put in unreliable datagram + SPEC, // Sends to all spectator proxies + }; + + virtual ~IMessage() {}; + + /** + * @brief Returns the number of parameters in the message + * @return The number of parameters + */ + virtual int getParamCount() const = 0; + + /** + * @brief Returns the type of the parameter at the given index + * @param index The index of the parameter + * @return The type of the parameter + */ + virtual ParamType getParamType(size_t index) const = 0; + + /** + * @brief Returns the integer value of the parameter at the given index + * @param index The index of the parameter + * @return The integer value of the parameter + */ + virtual int getParamInt(size_t index) const = 0; + + /** + * @brief Returns the float value of the parameter at the given index + * @param index The index of the parameter + * @return The float value of the parameter + */ + virtual float getParamFloat(size_t index) const = 0; + + /** + * @brief Returns the string value of the parameter at the given index + * @param index The index of the parameter + * @return The string value of the parameter + */ + virtual const char* getParamString(size_t index) const = 0; + + /** + * @brief Sets the integer value of the parameter at the given index + * @param index The index of the parameter + * @param value The integer value to set + */ + virtual void setParamInt(size_t index, int value) = 0; + + /** + * @brief Sets the float value of the parameter at the given index + * @param index The index of the parameter + * @param value The float value to set + */ + virtual void setParamFloat(size_t index, float value) = 0; + + /** + * @brief Sets the vector value of the parameter at the given index + * @param index The index of the parameter + * @param pos The vector value to set + */ + virtual void setParamVec(size_t index, const float *pos) = 0; + + /** + * @brief Sets the string value of the parameter at the given index + * @param index The index of the parameter + * @param string The string value to set + */ + virtual void setParamString(size_t index, const char *string) = 0; + + /** + * @brief Returns the destination of the message + * @return The destination of the message + */ + virtual Dest getDest() const = 0; + + /** + * @brief Returns the type of the message + * @return The type of the message + */ + virtual int getType() const = 0; + + /** + * @brief Returns the origin of the message + * @return The origin of the message + */ + virtual const float* getOrigin() const = 0; + + /** + * @brief Returns the edict associated with the message + * @return The edict associated with the message + */ + virtual struct edict_s* getEdict() const = 0; + + /** + * @brief Returns whether the message has been modified + * @return True if the message has been modified, false otherwise + */ + virtual bool isModified() const = 0; + + // This must be the last virtual function in class +#ifdef REHLDS_SELF + // Set the copyback buffer for the message + virtual void setCopybackBuffer(struct sizebuf_s *pbuf) = 0; +#endif +}; + +#define MESSAGEMNGR_VERSION_MAJOR 1 +#define MESSAGEMNGR_VERSION_MINOR 0 + +/** + * @brief Interface manages hooks and blocking behavior game messages + */ +class IMessageManager +{ +public: + using hookfunc_t = void (*)(IVoidHookChain *chain, IMessage *msg); + + virtual ~IMessageManager() {}; + + /** + * @brief Returns the major version of the MessageManager + * @return The major version + */ + virtual int getMajorVersion() const = 0; + + /** + * @brief Returns the minor version of the MessageManager + * @return The minor version + */ + virtual int getMinorVersion() const = 0; + + /** + * @brief Returns the blocking behavior for the given message type + * @param msgType The message type + * @return The blocking behavior for the given message type + */ + virtual IMessage::BlockType getMessageBlock(int msgType) const = 0; + + /** + * @brief Sets the blocking behavior for the given message type + * @param msgType The message type + * @param blockType The blocking behavior to set + */ + virtual void setMessageBlock(int msgType, IMessage::BlockType blockType) = 0; + + /** + * @brief Registers a hook function for the given message type + * @param msgType The message type to register the hook for + * @param handler The hook function to register + * @param priority The priority of the hook function (see enum HookChainPriority) + */ + virtual void registerHook(int msgType, hookfunc_t handler, int priority = HC_PRIORITY_DEFAULT) = 0; + + /** + * @brief Unregisters a hook function for the given message type + * @param msgType The message type to unregister the hook for + * @param handler The hook function to unregister + */ + virtual void unregisterHook(int msgType, hookfunc_t handler) = 0; +}; diff --git a/reapi/include/cssdk/engine/rehlds_api.h b/reapi/include/cssdk/engine/rehlds_api.h index 28f41a1d..0444b60c 100644 --- a/reapi/include/cssdk/engine/rehlds_api.h +++ b/reapi/include/cssdk/engine/rehlds_api.h @@ -31,12 +31,14 @@ #include "rehlds_interfaces.h" #include "hookchains.h" #include "FlightRecorder.h" +#include "IMessageManager.h" #include "interface.h" #include "model.h" +#include "ObjectList.h" #include "pr_dlls.h" #define REHLDS_API_VERSION_MAJOR 3 -#define REHLDS_API_VERSION_MINOR 13 +#define REHLDS_API_VERSION_MINOR 14 //Steam_NotifyClientConnect hook typedef IHookChain IRehldsHook_Steam_NotifyClientConnect; @@ -107,8 +109,8 @@ typedef IVoidHookChain IRehldsHook_ClientConnected; typedef IVoidHookChainRegistry IRehldsHookRegistry_ClientConnected; //HandleNetCommand -typedef IVoidHookChain IRehldsHook_HandleNetCommand; -typedef IVoidHookChainRegistry IRehldsHookRegistry_HandleNetCommand; +typedef IVoidHookChain IRehldsHook_HandleNetCommand; +typedef IVoidHookChainRegistry IRehldsHookRegistry_HandleNetCommand; //Mod_LoadBrushModel typedef IVoidHookChain IRehldsHook_Mod_LoadBrushModel; @@ -187,8 +189,8 @@ typedef IHookChain IRehldsHookRegistry_SV_CreatePacketEntities; //SV_EmitSound2 hook -typedef IHookChain IRehldsHook_SV_EmitSound2; -typedef IHookChainRegistry IRehldsHookRegistry_SV_EmitSound2; +typedef IHookChain IRehldsHook_SV_EmitSound2; +typedef IHookChainRegistry IRehldsHookRegistry_SV_EmitSound2; //CreateFakeClient hook typedef IHookChain IRehldsHook_CreateFakeClient; @@ -227,20 +229,20 @@ typedef IHookChain IRehldsHook_Con_Printf; typedef IHookChainRegistry IRehldsHookRegistry_Con_Printf; //SV_CheckUserInfo hook -typedef IHookChain IRehldsHook_SV_CheckUserInfo; -typedef IHookChainRegistry IRehldsHookRegistry_SV_CheckUserInfo; +typedef IHookChain IRehldsHook_SV_CheckUserInfo; +typedef IHookChainRegistry IRehldsHookRegistry_SV_CheckUserInfo; //PF_precache_generic_I hook -typedef IHookChain IRehldsHook_PF_precache_generic_I; -typedef IHookChainRegistry IRehldsHookRegistry_PF_precache_generic_I; +typedef IHookChain IRehldsHook_PF_precache_generic_I; +typedef IHookChainRegistry IRehldsHookRegistry_PF_precache_generic_I; //PF_precache_model_I hook -typedef IHookChain IRehldsHook_PF_precache_model_I; -typedef IHookChainRegistry IRehldsHookRegistry_PF_precache_model_I; +typedef IHookChain IRehldsHook_PF_precache_model_I; +typedef IHookChainRegistry IRehldsHookRegistry_PF_precache_model_I; //PF_precache_sound_I hook -typedef IHookChain IRehldsHook_PF_precache_sound_I; -typedef IHookChainRegistry IRehldsHookRegistry_PF_precache_sound_I; +typedef IHookChain IRehldsHook_PF_precache_sound_I; +typedef IHookChainRegistry IRehldsHookRegistry_PF_precache_sound_I; //EV_Precache hook typedef IHookChain IRehldsHook_EV_Precache; @@ -358,7 +360,7 @@ struct RehldsFuncs_t { cvar_t*(*GetCvarVars)(); int (*SV_GetChallenge)(const netadr_t& adr); void (*SV_AddResource)(resourcetype_t type, const char *name, int size, unsigned char flags, int index); - int(*MSG_ReadShort)(void); + int(*MSG_ReadShort)(); int(*MSG_ReadBuf)(int iSize, void *pbuf); void(*MSG_WriteBuf)(sizebuf_t *sb, int iSize, void *buf); void(*MSG_WriteByte)(sizebuf_t *sb, int c); @@ -373,6 +375,65 @@ struct RehldsFuncs_t { bool(*SV_EmitSound2)(edict_t *entity, IGameClient *receiver, int channel, const char *sample, float volume, float attenuation, int flags, int pitch, int emitFlags, const float *pOrigin); void(*SV_UpdateUserInfo)(IGameClient *pGameClient); bool(*StripUnprintableAndSpace)(char *pch); + void(*Cmd_RemoveCmd)(const char *cmd_name); + void(*GetCommandMatches)(const char *string, ObjectList *pMatchList); + bool(*AddExtDll)(void *hModule); + void(*AddCvarListener)(const char *var_name, cvar_callback_t func); + void(*RemoveExtDll)(void *hModule); + void(*RemoveCvarListener)(const char *var_name, cvar_callback_t func); + ENTITYINIT(*GetEntityInit)(char *pszClassName); + + // Read functions + int(*MSG_ReadChar)(); + int(*MSG_ReadByte)(); + int(*MSG_ReadLong)(); + float(*MSG_ReadFloat)(); + char*(*MSG_ReadString)(); + char*(*MSG_ReadStringLine)(); + float(*MSG_ReadAngle)(); + float(*MSG_ReadHiresAngle)(); + void(*MSG_ReadUsercmd)(struct usercmd_s *to, struct usercmd_s *from); + float(*MSG_ReadCoord)(); + void(*MSG_ReadVec3Coord)(sizebuf_t *sb, vec3_t fa); + + // Read bit functions + bool(*MSG_IsBitReading)(); + void(*MSG_StartBitReading)(sizebuf_t *buf); + void(*MSG_EndBitReading)(sizebuf_t *buf); + uint32(*MSG_PeekBits)(int numbits); + int(*MSG_ReadOneBit)(); + uint32(*MSG_ReadBits)(int numbits); + int(*MSG_ReadSBits)(int numbits); + float(*MSG_ReadBitCoord)(); + void(*MSG_ReadBitVec3Coord)(vec_t *fa); + float(*MSG_ReadBitAngle)(int numbits); + int(*MSG_ReadBitData)(void *dest, int length); + char*(*MSG_ReadBitString)(); + int(*MSG_CurrentBit)(); + + // Write functions + void(*MSG_WriteLong)(sizebuf_t *sb, int c); + void(*MSG_WriteFloat)(sizebuf_t *sb, float f); + void(*MSG_WriteAngle)(sizebuf_t *sb, float f); + void(*MSG_WriteHiresAngle)(sizebuf_t *sb, float f); + void(*MSG_WriteUsercmd)(sizebuf_t *sb, struct usercmd_s *to, struct usercmd_s *from); + void(*MSG_WriteCoord)(sizebuf_t *sb, float f); + void(*MSG_WriteVec3Coord)(sizebuf_t *sb, const vec3_t fa); + + // Write bit functions + bool(*MSG_IsBitWriting)(); + void(*MSG_WriteOneBit)(int nValue); + void(*MSG_WriteSBits)(uint32 data, int numbits); + void(*MSG_WriteBitCoord)(float f); + void(*MSG_WriteBitAngle)(float fAngle, int numbits); + void(*MSG_WriteBitData)(void *src, int length); + void(*MSG_WriteBitString)(const char *p); + void(*SZ_Write)(sizebuf_t *buf, const void *data, int length); + void(*SZ_Print)(sizebuf_t *buf, const char *data); + void(*SZ_Clear)(sizebuf_t *buf); + void(*MSG_BeginReading)(); + double(*GetHostFrameTime)(); + struct cmd_function_s *(*GetFirstCmdFunctionHandle)(); }; class IRehldsApi { @@ -386,6 +447,7 @@ class IRehldsApi { virtual IRehldsServerStatic* GetServerStatic() = 0; virtual IRehldsServerData* GetServerData() = 0; virtual IRehldsFlightRecorder* GetFlightRecorder() = 0; + virtual IMessageManager *GetMessageManager() = 0; }; #define VREHLDS_HLDS_API_VERSION "VREHLDS_HLDS_API_VERSION001" diff --git a/reapi/src/hook_callback.cpp b/reapi/src/hook_callback.cpp index c37f1d9c..fb228ad6 100644 --- a/reapi/src/hook_callback.cpp +++ b/reapi/src/hook_callback.cpp @@ -175,9 +175,9 @@ int PF_precache_generic_I(IRehldsHook_PF_precache_generic_I *chain, const char * return callForward(RH_PF_precache_generic_I, original, s); } -int PF_precache_model_I(IRehldsHook_PF_precache_model_I *chain, char *s) +int PF_precache_model_I(IRehldsHook_PF_precache_model_I *chain, const char *s) { - auto original = [chain](char *_s) + auto original = [chain](const char *_s) { return chain->callNext(_s); }; diff --git a/reapi/src/hook_callback.h b/reapi/src/hook_callback.h index 9e18c3ed..84356d3a 100644 --- a/reapi/src/hook_callback.h +++ b/reapi/src/hook_callback.h @@ -368,7 +368,7 @@ void SV_EmitPings_AMXX(SV_EmitPings_t *data, IGameClient *client); void SV_EmitPings(IRehldsHook_SV_EmitPings *chain, IGameClient *client, sizebuf_t *msg); void Con_Printf(IRehldsHook_Con_Printf *chain, const char *string); int PF_precache_generic_I(IRehldsHook_PF_precache_generic_I *chain, const char *s); -int PF_precache_model_I(IRehldsHook_PF_precache_model_I *chain, char *s); +int PF_precache_model_I(IRehldsHook_PF_precache_model_I *chain, const char *s); int PF_precache_sound_I(IRehldsHook_PF_precache_sound_I *chain, const char *s); using SV_SendResources_t = hookdata_t;