mirror of
https://github.com/roflmuffin/CounterStrikeSharp.git
synced 2025-12-05 23:58:24 -08:00
chore: cleanup cpp & add clang format linting (#862)
This commit is contained in:
@@ -38,7 +38,7 @@ BraceWrapping:
|
|||||||
SplitEmptyNamespace: true
|
SplitEmptyNamespace: true
|
||||||
|
|
||||||
PointerAlignment: Left
|
PointerAlignment: Left
|
||||||
SortIncludes: CaseSensitive
|
SortIncludes: Never
|
||||||
IncludeBlocks: Regroup
|
IncludeBlocks: Regroup
|
||||||
IncludeCategories:
|
IncludeCategories:
|
||||||
# External headers in <> with extension or /
|
# External headers in <> with extension or /
|
||||||
|
|||||||
@@ -1,11 +1,18 @@
|
|||||||
{
|
{
|
||||||
"name": "SteamRT Sniper SDK",
|
"name": "SteamRT Sniper SDK",
|
||||||
"image": "registry.gitlab.steamos.cloud/steamrt/sniper/sdk:latest",
|
"image": "registry.gitlab.steamos.cloud/steamrt/sniper/sdk:latest",
|
||||||
"customizations": {
|
"updateContentCommand": "git submodule update --init --recursive",
|
||||||
|
"customizations": {
|
||||||
"vscode": {
|
"vscode": {
|
||||||
"extensions": [
|
"extensions": [
|
||||||
"ms-vscode.cpptools"
|
"ms-vscode.cpptools",
|
||||||
|
"ms-vscode.cpptools-extension-pack",
|
||||||
|
"GitHub.copilot",
|
||||||
|
"jeff-hykin.better-cpp-syntax"
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
"features": {
|
||||||
|
"ghcr.io/devcontainers/features/dotnet": "8.0"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
25
.github/workflows/lint-code.yaml
vendored
Normal file
25
.github/workflows/lint-code.yaml
vendored
Normal file
@@ -0,0 +1,25 @@
|
|||||||
|
name: Code format checks
|
||||||
|
|
||||||
|
on:
|
||||||
|
pull_request:
|
||||||
|
paths:
|
||||||
|
- '.github/workflows/**'
|
||||||
|
- 'src/**'
|
||||||
|
- '.clang-format'
|
||||||
|
push:
|
||||||
|
paths:
|
||||||
|
- '.github/workflows/**'
|
||||||
|
- 'src/**'
|
||||||
|
- '.clang-format'
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
lint:
|
||||||
|
name: Lint code with clang-format
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@v4
|
||||||
|
- uses: jidicula/clang-format-action@4726374d1aa3c6aecf132e5197e498979588ebc8
|
||||||
|
with:
|
||||||
|
clang-format-version: '20'
|
||||||
|
check-path: 'src'
|
||||||
|
exclude-regex: '(sdk|\.proto)'
|
||||||
@@ -1,41 +1,41 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of CounterStrikeSharp.
|
* This file is part of CounterStrikeSharp.
|
||||||
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
* (at your option) any later version.
|
* (at your option) any later version.
|
||||||
*
|
*
|
||||||
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
* GNU General Public License for more details.
|
* GNU General Public License for more details.
|
||||||
*
|
*
|
||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
||||||
*/
|
*/
|
||||||
#include "UserMessage.h"
|
#include "UserMessage.h"
|
||||||
|
|
||||||
#include "networksystem/inetworkserializer.h"
|
#include "networksystem/inetworkserializer.h"
|
||||||
|
|
||||||
using namespace google;
|
using namespace google;
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
int UserMessage::GetMessageID() { return msgSerializable->GetNetMessageInfo()->m_MessageId; }
|
int UserMessage::GetMessageID() { return msgSerializable->GetNetMessageInfo()->m_MessageId; }
|
||||||
|
|
||||||
std::string UserMessage::GetMessageName() { return msgSerializable->GetUnscopedName(); }
|
std::string UserMessage::GetMessageName() { return msgSerializable->GetUnscopedName(); }
|
||||||
|
|
||||||
bool UserMessage::HasField(std::string fieldName)
|
bool UserMessage::HasField(std::string fieldName)
|
||||||
{
|
{
|
||||||
const google::protobuf::Descriptor* descriptor = msg->GetDescriptor();
|
const google::protobuf::Descriptor* descriptor = msg->GetDescriptor();
|
||||||
const google::protobuf::FieldDescriptor* field = descriptor->FindFieldByName(fieldName);
|
const google::protobuf::FieldDescriptor* field = descriptor->FindFieldByName(fieldName);
|
||||||
|
|
||||||
if (field == nullptr || (field->label() == google::protobuf::FieldDescriptor::LABEL_REPEATED))
|
if (field == nullptr || (field->label() == google::protobuf::FieldDescriptor::LABEL_REPEATED))
|
||||||
{
|
{
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return this->msg->GetReflection()->HasField(*this->msg, field);
|
return this->msg->GetReflection()->HasField(*this->msg, field);
|
||||||
}
|
}
|
||||||
|
|
||||||
const CNetMessagePB<google::protobuf::Message>* UserMessage::GetProtobufMessage() { return msg; }
|
const CNetMessagePB<google::protobuf::Message>* UserMessage::GetProtobufMessage() { return msg; }
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -28,8 +28,7 @@ class CGameResourceService
|
|||||||
public:
|
public:
|
||||||
CGameEntitySystem* GetGameEntitySystem()
|
CGameEntitySystem* GetGameEntitySystem()
|
||||||
{
|
{
|
||||||
return *reinterpret_cast<CGameEntitySystem**>(
|
return *reinterpret_cast<CGameEntitySystem**>((uintptr_t)(this) +
|
||||||
(uintptr_t)(this) +
|
counterstrikesharp::globals::gameConfig->GetOffset("GameEntitySystem"));
|
||||||
counterstrikesharp::globals::gameConfig->GetOffset("GameEntitySystem"));
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -26,11 +26,10 @@
|
|||||||
#include "tier0/memdbgon.h"
|
#include "tier0/memdbgon.h"
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
void interfaces::Initialize() {
|
void interfaces::Initialize()
|
||||||
pGameResourceServiceServer = (CGameResourceService*)modules::engine->FindInterface(
|
{
|
||||||
GAMERESOURCESERVICESERVER_INTERFACE_VERSION);
|
pGameResourceServiceServer = (CGameResourceService*)modules::engine->FindInterface(GAMERESOURCESERVICESERVER_INTERFACE_VERSION);
|
||||||
g_pCVar = (ICvar*)modules::tier0->FindInterface(CVAR_INTERFACE_VERSION);
|
g_pCVar = (ICvar*)modules::tier0->FindInterface(CVAR_INTERFACE_VERSION);
|
||||||
g_pSource2GameEntities = (ISource2GameEntities*)modules::server->FindInterface(
|
g_pSource2GameEntities = (ISource2GameEntities*)modules::server->FindInterface(SOURCE2GAMEENTITIES_INTERFACE_VERSION);
|
||||||
SOURCE2GAMEENTITIES_INTERFACE_VERSION);
|
|
||||||
}
|
}
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -25,6 +25,6 @@ namespace counterstrikesharp {
|
|||||||
namespace interfaces {
|
namespace interfaces {
|
||||||
void Initialize();
|
void Initialize();
|
||||||
|
|
||||||
inline CGameResourceService *pGameResourceServiceServer = nullptr;
|
inline CGameResourceService* pGameResourceServiceServer = nullptr;
|
||||||
} // namespace interfaces
|
} // namespace interfaces
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -33,8 +33,10 @@
|
|||||||
using SchemaKeyValueMap_t = CUtlMap<uint32_t, SchemaKey>;
|
using SchemaKeyValueMap_t = CUtlMap<uint32_t, SchemaKey>;
|
||||||
using SchemaTableMap_t = CUtlMap<uint32_t, SchemaKeyValueMap_t*>;
|
using SchemaTableMap_t = CUtlMap<uint32_t, SchemaKeyValueMap_t*>;
|
||||||
|
|
||||||
bool IsFieldNetworked(SchemaClassFieldData_t& field) {
|
bool IsFieldNetworked(SchemaClassFieldData_t& field)
|
||||||
for (int i = 0; i < field.m_nStaticMetadataCount; i++) {
|
{
|
||||||
|
for (int i = 0; i < field.m_nStaticMetadataCount; i++)
|
||||||
|
{
|
||||||
static auto networkEnabled = hash_32_fnv1a_const("MNetworkEnable");
|
static auto networkEnabled = hash_32_fnv1a_const("MNetworkEnable");
|
||||||
if (networkEnabled == hash_32_fnv1a_const(field.m_pStaticMetadata[i].m_pszName)) return true;
|
if (networkEnabled == hash_32_fnv1a_const(field.m_pStaticMetadata[i].m_pszName)) return true;
|
||||||
}
|
}
|
||||||
@@ -42,16 +44,16 @@ bool IsFieldNetworked(SchemaClassFieldData_t& field) {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool InitSchemaFieldsForClass(SchemaTableMap_t* tableMap,
|
static bool InitSchemaFieldsForClass(SchemaTableMap_t* tableMap, const char* className, uint32_t classKey)
|
||||||
const char* className,
|
{
|
||||||
uint32_t classKey) {
|
|
||||||
CSchemaSystemTypeScope* pType = counterstrikesharp::globals::schemaSystem->FindTypeScopeForModule(MODULE_PREFIX "server" MODULE_EXT);
|
CSchemaSystemTypeScope* pType = counterstrikesharp::globals::schemaSystem->FindTypeScopeForModule(MODULE_PREFIX "server" MODULE_EXT);
|
||||||
|
|
||||||
if (!pType) return false;
|
if (!pType) return false;
|
||||||
|
|
||||||
SchemaClassInfoData_t* pClassInfo = pType->FindDeclaredClass(className).Get();
|
SchemaClassInfoData_t* pClassInfo = pType->FindDeclaredClass(className).Get();
|
||||||
|
|
||||||
if (!pClassInfo) {
|
if (!pClassInfo)
|
||||||
|
{
|
||||||
SchemaKeyValueMap_t* map = new SchemaKeyValueMap_t(0, 0, DefLessFunc(uint32_t));
|
SchemaKeyValueMap_t* map = new SchemaKeyValueMap_t(0, 0, DefLessFunc(uint32_t));
|
||||||
tableMap->Insert(classKey, map);
|
tableMap->Insert(classKey, map);
|
||||||
|
|
||||||
@@ -66,31 +68,34 @@ static bool InitSchemaFieldsForClass(SchemaTableMap_t* tableMap,
|
|||||||
keyValueMap->EnsureCapacity(fieldsSize);
|
keyValueMap->EnsureCapacity(fieldsSize);
|
||||||
tableMap->Insert(classKey, keyValueMap);
|
tableMap->Insert(classKey, keyValueMap);
|
||||||
|
|
||||||
for (int i = 0; i < fieldsSize; ++i) {
|
for (int i = 0; i < fieldsSize; ++i)
|
||||||
|
{
|
||||||
SchemaClassFieldData_t& field = pFields[i];
|
SchemaClassFieldData_t& field = pFields[i];
|
||||||
|
|
||||||
keyValueMap->Insert(hash_32_fnv1a_const(field.m_pszName),
|
keyValueMap->Insert(hash_32_fnv1a_const(field.m_pszName), { field.m_nSingleInheritanceOffset, IsFieldNetworked(field) });
|
||||||
{field.m_nSingleInheritanceOffset, IsFieldNetworked(field)});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
int16_t schema::FindChainOffset(const char* className) {
|
int16_t schema::FindChainOffset(const char* className)
|
||||||
CSchemaSystemTypeScope* pType =
|
{
|
||||||
counterstrikesharp::globals::schemaSystem->FindTypeScopeForModule(MODULE_PREFIX "server" MODULE_EXT);
|
CSchemaSystemTypeScope* pType = counterstrikesharp::globals::schemaSystem->FindTypeScopeForModule(MODULE_PREFIX "server" MODULE_EXT);
|
||||||
|
|
||||||
if (!pType) return false;
|
if (!pType) return false;
|
||||||
|
|
||||||
auto* pClassInfo = pType->FindDeclaredClass(className).Get();
|
auto* pClassInfo = pType->FindDeclaredClass(className).Get();
|
||||||
|
|
||||||
do {
|
do
|
||||||
|
{
|
||||||
SchemaClassFieldData_t* pFields = pClassInfo->m_pFields;
|
SchemaClassFieldData_t* pFields = pClassInfo->m_pFields;
|
||||||
short fieldsSize = pClassInfo->m_nFieldCount;
|
short fieldsSize = pClassInfo->m_nFieldCount;
|
||||||
for (int i = 0; i < fieldsSize; ++i) {
|
for (int i = 0; i < fieldsSize; ++i)
|
||||||
|
{
|
||||||
SchemaClassFieldData_t& field = pFields[i];
|
SchemaClassFieldData_t& field = pFields[i];
|
||||||
|
|
||||||
if (V_strcmp(field.m_pszName, "__m_pChainEntity") == 0) {
|
if (V_strcmp(field.m_pszName, "__m_pChainEntity") == 0)
|
||||||
|
{
|
||||||
return field.m_nSingleInheritanceOffset;
|
return field.m_nSingleInheritanceOffset;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -99,29 +104,29 @@ int16_t schema::FindChainOffset(const char* className) {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
SchemaKey schema::GetOffset(const char* className,
|
SchemaKey schema::GetOffset(const char* className, uint32_t classKey, const char* memberName, uint32_t memberKey)
|
||||||
uint32_t classKey,
|
{
|
||||||
const char* memberName,
|
|
||||||
uint32_t memberKey) {
|
|
||||||
static SchemaTableMap_t schemaTableMap(0, 0, DefLessFunc(uint32_t));
|
static SchemaTableMap_t schemaTableMap(0, 0, DefLessFunc(uint32_t));
|
||||||
int16_t tableMapIndex = schemaTableMap.Find(classKey);
|
int16_t tableMapIndex = schemaTableMap.Find(classKey);
|
||||||
if (!schemaTableMap.IsValidIndex(tableMapIndex)) {
|
if (!schemaTableMap.IsValidIndex(tableMapIndex))
|
||||||
if (InitSchemaFieldsForClass(&schemaTableMap, className, classKey))
|
{
|
||||||
return GetOffset(className, classKey, memberName, memberKey);
|
if (InitSchemaFieldsForClass(&schemaTableMap, className, classKey)) return GetOffset(className, classKey, memberName, memberKey);
|
||||||
|
|
||||||
return {0, 0};
|
return { 0, 0 };
|
||||||
}
|
}
|
||||||
|
|
||||||
SchemaKeyValueMap_t* tableMap = schemaTableMap[tableMapIndex];
|
SchemaKeyValueMap_t* tableMap = schemaTableMap[tableMapIndex];
|
||||||
int16_t memberIndex = tableMap->Find(memberKey);
|
int16_t memberIndex = tableMap->Find(memberKey);
|
||||||
if (!tableMap->IsValidIndex(memberIndex)) {
|
if (!tableMap->IsValidIndex(memberIndex))
|
||||||
return {0, 0};
|
{
|
||||||
|
return { 0, 0 };
|
||||||
}
|
}
|
||||||
|
|
||||||
return tableMap->Element(memberIndex);
|
return tableMap->Element(memberIndex);
|
||||||
}
|
}
|
||||||
|
|
||||||
void SetStateChanged(Z_CBaseEntity* pEntity, int offset) {
|
void SetStateChanged(Z_CBaseEntity* pEntity, int offset)
|
||||||
|
{
|
||||||
// addresses::StateChanged(pEntity->m_NetworkTransmitComponent(), pEntity, offset, -1, -1);
|
// addresses::StateChanged(pEntity->m_NetworkTransmitComponent(), pEntity, offset, -1, -1);
|
||||||
auto vars = counterstrikesharp::globals::getGlobalVars();
|
auto vars = counterstrikesharp::globals::getGlobalVars();
|
||||||
|
|
||||||
|
|||||||
@@ -30,29 +30,28 @@
|
|||||||
|
|
||||||
#undef schema
|
#undef schema
|
||||||
|
|
||||||
struct SchemaKey {
|
struct SchemaKey
|
||||||
|
{
|
||||||
int32_t offset;
|
int32_t offset;
|
||||||
bool networked;
|
bool networked;
|
||||||
};
|
};
|
||||||
|
|
||||||
class Z_CBaseEntity;
|
class Z_CBaseEntity;
|
||||||
void SetStateChanged(Z_CBaseEntity *pEntity, int offset);
|
void SetStateChanged(Z_CBaseEntity* pEntity, int offset);
|
||||||
|
|
||||||
inline uint32_t val_32_const = 0x811c9dc5;
|
inline uint32_t val_32_const = 0x811c9dc5;
|
||||||
inline uint32_t prime_32_const = 0x1000193;
|
inline uint32_t prime_32_const = 0x1000193;
|
||||||
inline uint64_t val_64_const = 0xcbf29ce484222325;
|
inline uint64_t val_64_const = 0xcbf29ce484222325;
|
||||||
inline uint64_t prime_64_const = 0x100000001b3;
|
inline uint64_t prime_64_const = 0x100000001b3;
|
||||||
|
|
||||||
inline uint32_t hash_32_fnv1a_const(const char *str, const uint32_t value = val_32_const) noexcept {
|
inline uint32_t hash_32_fnv1a_const(const char* str, const uint32_t value = val_32_const) noexcept
|
||||||
return (str[0] == '\0')
|
{
|
||||||
? value
|
return (str[0] == '\0') ? value : hash_32_fnv1a_const(&str[1], (value ^ uint32_t(str[0])) * prime_32_const);
|
||||||
: hash_32_fnv1a_const(&str[1], (value ^ uint32_t(str[0])) * prime_32_const);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
inline uint64_t hash_64_fnv1a_const(const char *str, const uint64_t value = val_64_const) noexcept {
|
inline uint64_t hash_64_fnv1a_const(const char* str, const uint64_t value = val_64_const) noexcept
|
||||||
return (str[0] == '\0')
|
{
|
||||||
? value
|
return (str[0] == '\0') ? value : hash_64_fnv1a_const(&str[1], (value ^ uint64_t(str[0])) * prime_64_const);
|
||||||
: hash_64_fnv1a_const(&str[1], (value ^ uint64_t(str[0])) * prime_64_const);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
namespace schema {
|
namespace schema {
|
||||||
@@ -95,6 +94,6 @@ static std::vector<std::string> CS2BadList = {
|
|||||||
"m_nMusicID",
|
"m_nMusicID",
|
||||||
};
|
};
|
||||||
|
|
||||||
int16_t FindChainOffset(const char *className);
|
int16_t FindChainOffset(const char* className);
|
||||||
SchemaKey GetOffset(const char *className, uint32_t classKey, const char *memberName, uint32_t memberKey);
|
SchemaKey GetOffset(const char* className, uint32_t classKey, const char* memberName, uint32_t memberKey);
|
||||||
} // namespace schema
|
} // namespace schema
|
||||||
|
|||||||
@@ -52,30 +52,30 @@ std::map<dyno::Hook*, ValveFunction*> g_HookMap;
|
|||||||
// ============================================================================
|
// ============================================================================
|
||||||
int GetDynCallConvention(Convention_t eConv)
|
int GetDynCallConvention(Convention_t eConv)
|
||||||
{
|
{
|
||||||
switch (eConv) {
|
switch (eConv)
|
||||||
case CONV_CUSTOM:
|
{
|
||||||
return -1;
|
case CONV_CUSTOM:
|
||||||
case CONV_CDECL:
|
return -1;
|
||||||
return DC_CALL_C_DEFAULT;
|
case CONV_CDECL:
|
||||||
case CONV_THISCALL:
|
return DC_CALL_C_DEFAULT;
|
||||||
|
case CONV_THISCALL:
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
return DC_CALL_C_X86_WIN32_THIS_MS;
|
return DC_CALL_C_X86_WIN32_THIS_MS;
|
||||||
#else
|
#else
|
||||||
return DC_CALL_C_X86_WIN32_THIS_GNU;
|
return DC_CALL_C_X86_WIN32_THIS_GNU;
|
||||||
#endif
|
#endif
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
case CONV_STDCALL:
|
case CONV_STDCALL:
|
||||||
return DC_CALL_C_X86_WIN32_STD;
|
return DC_CALL_C_X86_WIN32_STD;
|
||||||
case CONV_FASTCALL:
|
case CONV_FASTCALL:
|
||||||
return DC_CALL_C_X86_WIN32_FAST_MS;
|
return DC_CALL_C_X86_WIN32_FAST_MS;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
ValveFunction::ValveFunction(void* ulAddr, Convention_t callingConvention,
|
ValveFunction::ValveFunction(void* ulAddr, Convention_t callingConvention, std::vector<DataType_t> args, DataType_t returnType)
|
||||||
std::vector<DataType_t> args, DataType_t returnType)
|
|
||||||
: m_ulAddr(ulAddr)
|
: m_ulAddr(ulAddr)
|
||||||
{
|
{
|
||||||
m_Args = args;
|
m_Args = args;
|
||||||
@@ -87,8 +87,7 @@ ValveFunction::ValveFunction(void* ulAddr, Convention_t callingConvention,
|
|||||||
m_iCallingConvention = GetDynCallConvention(m_eCallingConvention);
|
m_iCallingConvention = GetDynCallConvention(m_eCallingConvention);
|
||||||
}
|
}
|
||||||
|
|
||||||
ValveFunction::ValveFunction(void* ulAddr, Convention_t callingConvention, DataType_t* args,
|
ValveFunction::ValveFunction(void* ulAddr, Convention_t callingConvention, DataType_t* args, int argCount, DataType_t returnType)
|
||||||
int argCount, DataType_t returnType)
|
|
||||||
: m_ulAddr(ulAddr)
|
: m_ulAddr(ulAddr)
|
||||||
|
|
||||||
{
|
{
|
||||||
@@ -101,13 +100,9 @@ ValveFunction::ValveFunction(void* ulAddr, Convention_t callingConvention, DataT
|
|||||||
|
|
||||||
ValveFunction::~ValveFunction() {}
|
ValveFunction::~ValveFunction() {}
|
||||||
|
|
||||||
bool ValveFunction::IsCallable()
|
bool ValveFunction::IsCallable() { return (m_eCallingConvention != CONV_CUSTOM) && (m_iCallingConvention != -1); }
|
||||||
{
|
|
||||||
return (m_eCallingConvention != CONV_CUSTOM) && (m_iCallingConvention != -1);
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class ReturnType, class Function>
|
template <class ReturnType, class Function> ReturnType CallHelper(Function func, DCCallVM* vm, void* addr)
|
||||||
ReturnType CallHelper(Function func, DCCallVM* vm, void* addr)
|
|
||||||
{
|
{
|
||||||
ReturnType result;
|
ReturnType result;
|
||||||
result = (ReturnType)func(vm, (void*)addr);
|
result = (ReturnType)func(vm, (void*)addr);
|
||||||
@@ -118,119 +113,120 @@ void CallHelperVoid(DCCallVM* vm, void* addr) { dcCallVoid(vm, (void*)addr); }
|
|||||||
|
|
||||||
void ValveFunction::Call(ScriptContext& script_context, int offset)
|
void ValveFunction::Call(ScriptContext& script_context, int offset)
|
||||||
{
|
{
|
||||||
if (!IsCallable())
|
if (!IsCallable()) return;
|
||||||
return;
|
|
||||||
|
|
||||||
dcReset(g_pCallVM);
|
dcReset(g_pCallVM);
|
||||||
dcMode(g_pCallVM, m_iCallingConvention);
|
dcMode(g_pCallVM, m_iCallingConvention);
|
||||||
|
|
||||||
for (size_t i = 0; i < m_Args.size(); i++) {
|
for (size_t i = 0; i < m_Args.size(); i++)
|
||||||
|
{
|
||||||
int contextIndex = i + offset;
|
int contextIndex = i + offset;
|
||||||
switch (m_Args[i]) {
|
switch (m_Args[i])
|
||||||
case DATA_TYPE_BOOL:
|
{
|
||||||
dcArgBool(g_pCallVM, script_context.GetArgument<bool>(contextIndex));
|
case DATA_TYPE_BOOL:
|
||||||
break;
|
dcArgBool(g_pCallVM, script_context.GetArgument<bool>(contextIndex));
|
||||||
case DATA_TYPE_CHAR:
|
break;
|
||||||
dcArgChar(g_pCallVM, script_context.GetArgument<char>(contextIndex));
|
case DATA_TYPE_CHAR:
|
||||||
break;
|
dcArgChar(g_pCallVM, script_context.GetArgument<char>(contextIndex));
|
||||||
case DATA_TYPE_UCHAR:
|
break;
|
||||||
dcArgChar(g_pCallVM, script_context.GetArgument<unsigned char>(contextIndex));
|
case DATA_TYPE_UCHAR:
|
||||||
break;
|
dcArgChar(g_pCallVM, script_context.GetArgument<unsigned char>(contextIndex));
|
||||||
case DATA_TYPE_SHORT:
|
break;
|
||||||
dcArgShort(g_pCallVM, script_context.GetArgument<short>(contextIndex));
|
case DATA_TYPE_SHORT:
|
||||||
break;
|
dcArgShort(g_pCallVM, script_context.GetArgument<short>(contextIndex));
|
||||||
case DATA_TYPE_USHORT:
|
break;
|
||||||
dcArgShort(g_pCallVM, script_context.GetArgument<unsigned short>(contextIndex));
|
case DATA_TYPE_USHORT:
|
||||||
break;
|
dcArgShort(g_pCallVM, script_context.GetArgument<unsigned short>(contextIndex));
|
||||||
case DATA_TYPE_INT:
|
break;
|
||||||
dcArgInt(g_pCallVM, script_context.GetArgument<int>(contextIndex));
|
case DATA_TYPE_INT:
|
||||||
break;
|
dcArgInt(g_pCallVM, script_context.GetArgument<int>(contextIndex));
|
||||||
case DATA_TYPE_UINT:
|
break;
|
||||||
dcArgInt(g_pCallVM, script_context.GetArgument<unsigned int>(contextIndex));
|
case DATA_TYPE_UINT:
|
||||||
break;
|
dcArgInt(g_pCallVM, script_context.GetArgument<unsigned int>(contextIndex));
|
||||||
case DATA_TYPE_LONG:
|
break;
|
||||||
dcArgLong(g_pCallVM, script_context.GetArgument<long>(contextIndex));
|
case DATA_TYPE_LONG:
|
||||||
break;
|
dcArgLong(g_pCallVM, script_context.GetArgument<long>(contextIndex));
|
||||||
case DATA_TYPE_ULONG:
|
break;
|
||||||
dcArgLong(g_pCallVM, script_context.GetArgument<unsigned long>(contextIndex));
|
case DATA_TYPE_ULONG:
|
||||||
break;
|
dcArgLong(g_pCallVM, script_context.GetArgument<unsigned long>(contextIndex));
|
||||||
case DATA_TYPE_LONG_LONG:
|
break;
|
||||||
dcArgLongLong(g_pCallVM, script_context.GetArgument<long long>(contextIndex));
|
case DATA_TYPE_LONG_LONG:
|
||||||
break;
|
dcArgLongLong(g_pCallVM, script_context.GetArgument<long long>(contextIndex));
|
||||||
case DATA_TYPE_ULONG_LONG:
|
break;
|
||||||
dcArgLongLong(g_pCallVM, script_context.GetArgument<unsigned long long>(contextIndex));
|
case DATA_TYPE_ULONG_LONG:
|
||||||
break;
|
dcArgLongLong(g_pCallVM, script_context.GetArgument<unsigned long long>(contextIndex));
|
||||||
case DATA_TYPE_FLOAT:
|
break;
|
||||||
dcArgFloat(g_pCallVM, script_context.GetArgument<float>(contextIndex));
|
case DATA_TYPE_FLOAT:
|
||||||
break;
|
dcArgFloat(g_pCallVM, script_context.GetArgument<float>(contextIndex));
|
||||||
case DATA_TYPE_DOUBLE:
|
break;
|
||||||
dcArgDouble(g_pCallVM, script_context.GetArgument<double>(contextIndex));
|
case DATA_TYPE_DOUBLE:
|
||||||
break;
|
dcArgDouble(g_pCallVM, script_context.GetArgument<double>(contextIndex));
|
||||||
case DATA_TYPE_POINTER:
|
break;
|
||||||
dcArgPointer(g_pCallVM, script_context.GetArgument<void*>(contextIndex));
|
case DATA_TYPE_POINTER:
|
||||||
break;
|
dcArgPointer(g_pCallVM, script_context.GetArgument<void*>(contextIndex));
|
||||||
case DATA_TYPE_STRING:
|
break;
|
||||||
dcArgPointer(g_pCallVM, (void*)script_context.GetArgument<const char*>(contextIndex));
|
case DATA_TYPE_STRING:
|
||||||
break;
|
dcArgPointer(g_pCallVM, (void*)script_context.GetArgument<const char*>(contextIndex));
|
||||||
default:
|
break;
|
||||||
assert(!"Unknown function parameter type!");
|
default:
|
||||||
break;
|
assert(!"Unknown function parameter type!");
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
switch (m_eReturnType) {
|
switch (m_eReturnType)
|
||||||
case DATA_TYPE_VOID:
|
{
|
||||||
CallHelperVoid(g_pCallVM, m_ulAddr);
|
case DATA_TYPE_VOID:
|
||||||
break;
|
CallHelperVoid(g_pCallVM, m_ulAddr);
|
||||||
case DATA_TYPE_BOOL:
|
break;
|
||||||
script_context.SetResult(CallHelper<bool>(dcCallBool, g_pCallVM, m_ulAddr));
|
case DATA_TYPE_BOOL:
|
||||||
break;
|
script_context.SetResult(CallHelper<bool>(dcCallBool, g_pCallVM, m_ulAddr));
|
||||||
case DATA_TYPE_CHAR:
|
break;
|
||||||
script_context.SetResult(CallHelper<char>(dcCallChar, g_pCallVM, m_ulAddr));
|
case DATA_TYPE_CHAR:
|
||||||
break;
|
script_context.SetResult(CallHelper<char>(dcCallChar, g_pCallVM, m_ulAddr));
|
||||||
case DATA_TYPE_UCHAR:
|
break;
|
||||||
script_context.SetResult(CallHelper<unsigned char>(dcCallChar, g_pCallVM, m_ulAddr));
|
case DATA_TYPE_UCHAR:
|
||||||
break;
|
script_context.SetResult(CallHelper<unsigned char>(dcCallChar, g_pCallVM, m_ulAddr));
|
||||||
case DATA_TYPE_SHORT:
|
break;
|
||||||
script_context.SetResult(CallHelper<short>(dcCallShort, g_pCallVM, m_ulAddr));
|
case DATA_TYPE_SHORT:
|
||||||
break;
|
script_context.SetResult(CallHelper<short>(dcCallShort, g_pCallVM, m_ulAddr));
|
||||||
case DATA_TYPE_USHORT:
|
break;
|
||||||
script_context.SetResult(CallHelper<unsigned short>(dcCallShort, g_pCallVM, m_ulAddr));
|
case DATA_TYPE_USHORT:
|
||||||
break;
|
script_context.SetResult(CallHelper<unsigned short>(dcCallShort, g_pCallVM, m_ulAddr));
|
||||||
case DATA_TYPE_INT:
|
break;
|
||||||
script_context.SetResult(CallHelper<int>(dcCallInt, g_pCallVM, m_ulAddr));
|
case DATA_TYPE_INT:
|
||||||
break;
|
script_context.SetResult(CallHelper<int>(dcCallInt, g_pCallVM, m_ulAddr));
|
||||||
case DATA_TYPE_UINT:
|
break;
|
||||||
script_context.SetResult(CallHelper<unsigned int>(dcCallInt, g_pCallVM, m_ulAddr));
|
case DATA_TYPE_UINT:
|
||||||
break;
|
script_context.SetResult(CallHelper<unsigned int>(dcCallInt, g_pCallVM, m_ulAddr));
|
||||||
case DATA_TYPE_LONG:
|
break;
|
||||||
script_context.SetResult(CallHelper<long>(dcCallLong, g_pCallVM, m_ulAddr));
|
case DATA_TYPE_LONG:
|
||||||
break;
|
script_context.SetResult(CallHelper<long>(dcCallLong, g_pCallVM, m_ulAddr));
|
||||||
case DATA_TYPE_ULONG:
|
break;
|
||||||
script_context.SetResult(CallHelper<unsigned long>(dcCallLong, g_pCallVM, m_ulAddr));
|
case DATA_TYPE_ULONG:
|
||||||
break;
|
script_context.SetResult(CallHelper<unsigned long>(dcCallLong, g_pCallVM, m_ulAddr));
|
||||||
case DATA_TYPE_LONG_LONG:
|
break;
|
||||||
script_context.SetResult(CallHelper<long long>(dcCallLongLong, g_pCallVM, m_ulAddr));
|
case DATA_TYPE_LONG_LONG:
|
||||||
break;
|
script_context.SetResult(CallHelper<long long>(dcCallLongLong, g_pCallVM, m_ulAddr));
|
||||||
case DATA_TYPE_ULONG_LONG:
|
break;
|
||||||
script_context.SetResult(
|
case DATA_TYPE_ULONG_LONG:
|
||||||
CallHelper<unsigned long long>(dcCallLongLong, g_pCallVM, m_ulAddr));
|
script_context.SetResult(CallHelper<unsigned long long>(dcCallLongLong, g_pCallVM, m_ulAddr));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_FLOAT:
|
case DATA_TYPE_FLOAT:
|
||||||
script_context.SetResult(CallHelper<float>(dcCallFloat, g_pCallVM, m_ulAddr));
|
script_context.SetResult(CallHelper<float>(dcCallFloat, g_pCallVM, m_ulAddr));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_DOUBLE:
|
case DATA_TYPE_DOUBLE:
|
||||||
script_context.SetResult(CallHelper<double>(dcCallDouble, g_pCallVM, m_ulAddr));
|
script_context.SetResult(CallHelper<double>(dcCallDouble, g_pCallVM, m_ulAddr));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_POINTER:
|
case DATA_TYPE_POINTER:
|
||||||
script_context.SetResult(CallHelper<void*>(dcCallPointer, g_pCallVM, m_ulAddr));
|
script_context.SetResult(CallHelper<void*>(dcCallPointer, g_pCallVM, m_ulAddr));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_STRING:
|
case DATA_TYPE_STRING:
|
||||||
script_context.SetResult(CallHelper<const char*>(dcCallPointer, g_pCallVM, m_ulAddr));
|
script_context.SetResult(CallHelper<const char*>(dcCallPointer, g_pCallVM, m_ulAddr));
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
assert(!"Unknown function return type!");
|
assert(!"Unknown function return type!");
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -240,23 +236,24 @@ dyno::ReturnAction HookHandler(dyno::HookType hookType, dyno::Hook& hook)
|
|||||||
|
|
||||||
auto callback = hookType == dyno::HookType::Pre ? vf->m_precallback : vf->m_postcallback;
|
auto callback = hookType == dyno::HookType::Pre ? vf->m_precallback : vf->m_postcallback;
|
||||||
|
|
||||||
if (callback == nullptr) {
|
if (callback == nullptr)
|
||||||
|
{
|
||||||
return dyno::ReturnAction::Ignored;
|
return dyno::ReturnAction::Ignored;
|
||||||
}
|
}
|
||||||
|
|
||||||
callback->Reset();
|
callback->Reset();
|
||||||
callback->ScriptContext().Push(&hook);
|
callback->ScriptContext().Push(&hook);
|
||||||
|
|
||||||
for (auto fnMethodToCall : callback->GetFunctions()) {
|
for (auto fnMethodToCall : callback->GetFunctions())
|
||||||
if (!fnMethodToCall)
|
{
|
||||||
continue;
|
if (!fnMethodToCall) continue;
|
||||||
fnMethodToCall(&callback->ScriptContextStruct());
|
fnMethodToCall(&callback->ScriptContextStruct());
|
||||||
|
|
||||||
auto result = callback->ScriptContext().GetResult<HookResult>();
|
auto result = callback->ScriptContext().GetResult<HookResult>();
|
||||||
CSSHARP_CORE_TRACE("Received hook callback result of {}, hook mode {}", result,
|
CSSHARP_CORE_TRACE("Received hook callback result of {}, hook mode {}", result, (int)hookType);
|
||||||
(int)hookType);
|
|
||||||
|
|
||||||
if (result >= HookResult::Handled) {
|
if (result >= HookResult::Handled)
|
||||||
|
{
|
||||||
return dyno::ReturnAction::Supercede;
|
return dyno::ReturnAction::Supercede;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -269,7 +266,8 @@ std::vector<dyno::DataObject> ConvertArgsToDynoHook(const std::vector<DataType_t
|
|||||||
std::vector<dyno::DataObject> converted;
|
std::vector<dyno::DataObject> converted;
|
||||||
converted.reserve(dataTypes.size());
|
converted.reserve(dataTypes.size());
|
||||||
|
|
||||||
for (DataType_t dt : dataTypes) {
|
for (DataType_t dt : dataTypes)
|
||||||
|
{
|
||||||
converted.push_back(dyno::DataObject(static_cast<dyno::DataType>(dt)));
|
converted.push_back(dyno::DataObject(static_cast<dyno::DataType>(dt)));
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -290,19 +288,25 @@ void ValveFunction::AddHook(CallbackT callable, bool post)
|
|||||||
hook->addCallback(dyno::HookType::Post, (dyno::HookHandler*)&HookHandler);
|
hook->addCallback(dyno::HookType::Post, (dyno::HookHandler*)&HookHandler);
|
||||||
hook->addCallback(dyno::HookType::Pre, (dyno::HookHandler*)&HookHandler);
|
hook->addCallback(dyno::HookType::Pre, (dyno::HookHandler*)&HookHandler);
|
||||||
|
|
||||||
if (post) {
|
if (post)
|
||||||
if (m_postcallback == nullptr) {
|
{
|
||||||
|
if (m_postcallback == nullptr)
|
||||||
|
{
|
||||||
m_postcallback = globals::callbackManager.CreateCallback("");
|
m_postcallback = globals::callbackManager.CreateCallback("");
|
||||||
}
|
}
|
||||||
m_postcallback->AddListener(callable);
|
m_postcallback->AddListener(callable);
|
||||||
} else {
|
}
|
||||||
if (m_precallback == nullptr) {
|
else
|
||||||
|
{
|
||||||
|
if (m_precallback == nullptr)
|
||||||
|
{
|
||||||
m_precallback = globals::callbackManager.CreateCallback("");
|
m_precallback = globals::callbackManager.CreateCallback("");
|
||||||
}
|
}
|
||||||
m_precallback->AddListener(callable);
|
m_precallback->AddListener(callable);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
void ValveFunction::RemoveHook(CallbackT callable, bool post) {
|
void ValveFunction::RemoveHook(CallbackT callable, bool post)
|
||||||
|
{
|
||||||
dyno::HookManager& manager = dyno::HookManager::Get();
|
dyno::HookManager& manager = dyno::HookManager::Get();
|
||||||
dyno::Hook* hook = manager.hook((void*)m_ulAddr, [this] {
|
dyno::Hook* hook = manager.hook((void*)m_ulAddr, [this] {
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
@@ -313,12 +317,17 @@ void ValveFunction::RemoveHook(CallbackT callable, bool post) {
|
|||||||
});
|
});
|
||||||
g_HookMap[hook] = this;
|
g_HookMap[hook] = this;
|
||||||
|
|
||||||
if (post) {
|
if (post)
|
||||||
if (m_postcallback != nullptr) {
|
{
|
||||||
|
if (m_postcallback != nullptr)
|
||||||
|
{
|
||||||
m_postcallback->RemoveListener(callable);
|
m_postcallback->RemoveListener(callable);
|
||||||
}
|
}
|
||||||
} else {
|
}
|
||||||
if (m_precallback != nullptr) {
|
else
|
||||||
|
{
|
||||||
|
if (m_precallback != nullptr)
|
||||||
|
{
|
||||||
m_precallback->RemoveListener(callable);
|
m_precallback->RemoveListener(callable);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -40,7 +40,8 @@ class Hook;
|
|||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
|
|
||||||
enum DataType_t {
|
enum DataType_t
|
||||||
|
{
|
||||||
DATA_TYPE_VOID,
|
DATA_TYPE_VOID,
|
||||||
DATA_TYPE_BOOL,
|
DATA_TYPE_BOOL,
|
||||||
DATA_TYPE_CHAR,
|
DATA_TYPE_CHAR,
|
||||||
@@ -60,7 +61,8 @@ enum DataType_t {
|
|||||||
DATA_TYPE_VARIANT
|
DATA_TYPE_VARIANT
|
||||||
};
|
};
|
||||||
|
|
||||||
enum Protection_t {
|
enum Protection_t
|
||||||
|
{
|
||||||
PROTECTION_NONE,
|
PROTECTION_NONE,
|
||||||
PROTECTION_READ,
|
PROTECTION_READ,
|
||||||
PROTECTION_READ_WRITE,
|
PROTECTION_READ_WRITE,
|
||||||
@@ -69,19 +71,20 @@ enum Protection_t {
|
|||||||
PROTECTION_EXECUTE_READ_WRITE
|
PROTECTION_EXECUTE_READ_WRITE
|
||||||
};
|
};
|
||||||
|
|
||||||
enum Convention_t { CONV_CUSTOM, CONV_CDECL, CONV_THISCALL, CONV_STDCALL, CONV_FASTCALL };
|
enum Convention_t
|
||||||
|
{
|
||||||
|
CONV_CUSTOM,
|
||||||
|
CONV_CDECL,
|
||||||
|
CONV_THISCALL,
|
||||||
|
CONV_STDCALL,
|
||||||
|
CONV_FASTCALL
|
||||||
|
};
|
||||||
|
|
||||||
class ValveFunction {
|
class ValveFunction
|
||||||
public:
|
{
|
||||||
ValveFunction(void* ulAddr,
|
public:
|
||||||
Convention_t callingConvention,
|
ValveFunction(void* ulAddr, Convention_t callingConvention, std::vector<DataType_t> args, DataType_t returnType);
|
||||||
std::vector<DataType_t> args,
|
ValveFunction(void* ulAddr, Convention_t callingConvention, DataType_t* args, int argCount, DataType_t returnType);
|
||||||
DataType_t returnType);
|
|
||||||
ValveFunction(void* ulAddr,
|
|
||||||
Convention_t callingConvention,
|
|
||||||
DataType_t* args,
|
|
||||||
int argCount,
|
|
||||||
DataType_t returnType);
|
|
||||||
|
|
||||||
~ValveFunction();
|
~ValveFunction();
|
||||||
|
|
||||||
@@ -110,4 +113,4 @@ public:
|
|||||||
ScriptCallback* m_postcallback = nullptr;
|
ScriptCallback* m_postcallback = nullptr;
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -36,7 +36,8 @@ bool InitGameSystems()
|
|||||||
// bytes so we skip those
|
// bytes so we skip those
|
||||||
uint8* ptr = (uint8*)counterstrikesharp::globals::gameConfig->ResolveSignature("IGameSystem_InitAllSystems_pFirst") + 3;
|
uint8* ptr = (uint8*)counterstrikesharp::globals::gameConfig->ResolveSignature("IGameSystem_InitAllSystems_pFirst") + 3;
|
||||||
|
|
||||||
if (!ptr) {
|
if (!ptr)
|
||||||
|
{
|
||||||
CSSHARP_CORE_ERROR("Failed to InitGameSystems, see warnings above.");
|
CSSHARP_CORE_ERROR("Failed to InitGameSystems, see warnings above.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@@ -63,4 +64,4 @@ GS_EVENT_MEMBER(CGameSystem, BuildGameSessionManifest)
|
|||||||
CSSHARP_CORE_INFO("CGameSystem::BuildGameSessionManifest");
|
CSSHARP_CORE_INFO("CGameSystem::BuildGameSessionManifest");
|
||||||
|
|
||||||
counterstrikesharp::globals::serverManager.OnPrecacheResources(pResourceManifest);
|
counterstrikesharp::globals::serverManager.OnPrecacheResources(pResourceManifest);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -37,11 +37,10 @@ class CGameSystem : public CBaseGameSystem
|
|||||||
|
|
||||||
void SetGameSystemGlobalPtrs(void* pValue) override
|
void SetGameSystemGlobalPtrs(void* pValue) override
|
||||||
{
|
{
|
||||||
if (sm_Factory)
|
if (sm_Factory) sm_Factory->SetGlobalPtr(pValue);
|
||||||
sm_Factory->SetGlobalPtr(pValue);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool DoesGameSystemReallocate() override { return sm_Factory->ShouldAutoAdd(); }
|
bool DoesGameSystemReallocate() override { return sm_Factory->ShouldAutoAdd(); }
|
||||||
|
|
||||||
static IGameSystemFactory* sm_Factory;
|
static IGameSystemFactory* sm_Factory;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,6 +1,5 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
|
||||||
#include "core/globals.h"
|
#include "core/globals.h"
|
||||||
#include "core/memory_module.h"
|
#include "core/memory_module.h"
|
||||||
#include <KeyValues.h>
|
#include <KeyValues.h>
|
||||||
|
|||||||
@@ -32,34 +32,37 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
class GlobalClass {
|
class GlobalClass
|
||||||
public:
|
{
|
||||||
|
public:
|
||||||
virtual ~GlobalClass() = default;
|
virtual ~GlobalClass() = default;
|
||||||
|
|
||||||
GlobalClass() {
|
GlobalClass()
|
||||||
|
{
|
||||||
m_pGlobalClassNext = GlobalClass::head;
|
m_pGlobalClassNext = GlobalClass::head;
|
||||||
GlobalClass::head = this;
|
GlobalClass::head = this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public:
|
public:
|
||||||
virtual void OnStartup() {}
|
virtual void OnStartup() {}
|
||||||
virtual void OnShutdown() {}
|
virtual void OnShutdown() {}
|
||||||
virtual void OnAllInitialized() {}
|
virtual void OnAllInitialized() {}
|
||||||
virtual void OnGameLoopInitialized() {}
|
virtual void OnGameLoopInitialized() {}
|
||||||
virtual void OnAllInitialized_Post() {}
|
virtual void OnAllInitialized_Post() {}
|
||||||
virtual void OnLevelChange(const char *mapName) {}
|
virtual void OnLevelChange(const char* mapName) {}
|
||||||
virtual void OnLevelEnd() {}
|
virtual void OnLevelEnd() {}
|
||||||
|
|
||||||
public:
|
public:
|
||||||
GlobalClass *m_pGlobalClassNext;
|
GlobalClass* m_pGlobalClassNext;
|
||||||
static GlobalClass *head;
|
static GlobalClass* head;
|
||||||
};
|
};
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|
||||||
#define CALL_GLOBAL_LISTENER(func) \
|
#define CALL_GLOBAL_LISTENER(func) \
|
||||||
GlobalClass *pBase = GlobalClass::head; \
|
GlobalClass* pBase = GlobalClass::head; \
|
||||||
pBase = GlobalClass::head; \
|
pBase = GlobalClass::head; \
|
||||||
while (pBase) { \
|
while (pBase) \
|
||||||
|
{ \
|
||||||
pBase->func; \
|
pBase->func; \
|
||||||
pBase = pBase->m_pGlobalClassNext; \
|
pBase = pBase->m_pGlobalClassNext; \
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,4 +1,3 @@
|
|||||||
// clang-format off
|
|
||||||
#include "mm_plugin.h"
|
#include "mm_plugin.h"
|
||||||
#include "core/globals.h"
|
#include "core/globals.h"
|
||||||
#include "core/managers/player_manager.h"
|
#include "core/managers/player_manager.h"
|
||||||
@@ -28,7 +27,6 @@
|
|||||||
#include <public/entity2/entitysystem.h>
|
#include <public/entity2/entitysystem.h>
|
||||||
|
|
||||||
#include <funchook.h>
|
#include <funchook.h>
|
||||||
// clang-format on
|
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
|
|
||||||
@@ -142,7 +140,8 @@ void DetourGameEventManagerInit(IGameEventManager2* pGameEventManager)
|
|||||||
}
|
}
|
||||||
|
|
||||||
int source_hook_pluginid = 0;
|
int source_hook_pluginid = 0;
|
||||||
CGlobalVars* getGlobalVars() {
|
CGlobalVars* getGlobalVars()
|
||||||
|
{
|
||||||
INetworkGameServer* server = networkServerService->GetIGameServer();
|
INetworkGameServer* server = networkServerService->GetIGameServer();
|
||||||
if (!server) return nullptr;
|
if (!server) return nullptr;
|
||||||
return networkServerService->GetIGameServer()->GetGlobals();
|
return networkServerService->GetIGameServer()->GetGlobals();
|
||||||
|
|||||||
@@ -7,7 +7,8 @@
|
|||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
std::shared_ptr<spdlog::logger> Log::m_core_logger;
|
std::shared_ptr<spdlog::logger> Log::m_core_logger;
|
||||||
|
|
||||||
void Log::Init() {
|
void Log::Init()
|
||||||
|
{
|
||||||
std::vector<spdlog::sink_ptr> log_sinks;
|
std::vector<spdlog::sink_ptr> log_sinks;
|
||||||
auto color_sink = std::make_shared<spdlog::sinks::stderr_color_sink_mt>();
|
auto color_sink = std::make_shared<spdlog::sinks::stderr_color_sink_mt>();
|
||||||
#if _WIN32
|
#if _WIN32
|
||||||
@@ -17,8 +18,7 @@ void Log::Init() {
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
log_sinks.emplace_back(color_sink);
|
log_sinks.emplace_back(color_sink);
|
||||||
log_sinks.emplace_back(
|
log_sinks.emplace_back(std::make_shared<spdlog::sinks::basic_file_sink_mt>("counterstrikesharp.log", true));
|
||||||
std::make_shared<spdlog::sinks::basic_file_sink_mt>("counterstrikesharp.log", true));
|
|
||||||
|
|
||||||
log_sinks[0]->set_pattern("%^[%T.%e] %n: %v%$");
|
log_sinks[0]->set_pattern("%^[%T.%e] %n: %v%$");
|
||||||
log_sinks[1]->set_pattern("[%T.%e] [%l] %n: %v");
|
log_sinks[1]->set_pattern("[%T.%e] [%l] %n: %v");
|
||||||
@@ -31,8 +31,9 @@ void Log::Init() {
|
|||||||
spdlog::cfg::load_env_levels();
|
spdlog::cfg::load_env_levels();
|
||||||
}
|
}
|
||||||
|
|
||||||
void Log::Close() {
|
void Log::Close()
|
||||||
|
{
|
||||||
spdlog::drop("CSSharp");
|
spdlog::drop("CSSharp");
|
||||||
m_core_logger = nullptr;
|
m_core_logger = nullptr;
|
||||||
}
|
}
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -6,21 +6,22 @@
|
|||||||
#include <spdlog/spdlog.h>
|
#include <spdlog/spdlog.h>
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
class Log {
|
class Log
|
||||||
public:
|
{
|
||||||
|
public:
|
||||||
static void Init();
|
static void Init();
|
||||||
static void Close();
|
static void Close();
|
||||||
|
|
||||||
static std::shared_ptr<spdlog::logger> &GetCoreLogger() { return m_core_logger; }
|
static std::shared_ptr<spdlog::logger>& GetCoreLogger() { return m_core_logger; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
static std::shared_ptr<spdlog::logger> m_core_logger;
|
static std::shared_ptr<spdlog::logger> m_core_logger;
|
||||||
};
|
};
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|
||||||
#define CSSHARP_CORE_TRACE(...) ::counterstrikesharp::Log::GetCoreLogger()->trace(__VA_ARGS__)
|
#define CSSHARP_CORE_TRACE(...) ::counterstrikesharp::Log::GetCoreLogger()->trace(__VA_ARGS__)
|
||||||
#define CSSHARP_CORE_DEBUG(...) ::counterstrikesharp::Log::GetCoreLogger()->debug(__VA_ARGS__)
|
#define CSSHARP_CORE_DEBUG(...) ::counterstrikesharp::Log::GetCoreLogger()->debug(__VA_ARGS__)
|
||||||
#define CSSHARP_CORE_INFO(...) ::counterstrikesharp::Log::GetCoreLogger()->info(__VA_ARGS__)
|
#define CSSHARP_CORE_INFO(...) ::counterstrikesharp::Log::GetCoreLogger()->info(__VA_ARGS__)
|
||||||
#define CSSHARP_CORE_WARN(...) ::counterstrikesharp::Log::GetCoreLogger()->warn(__VA_ARGS__)
|
#define CSSHARP_CORE_WARN(...) ::counterstrikesharp::Log::GetCoreLogger()->warn(__VA_ARGS__)
|
||||||
#define CSSHARP_CORE_ERROR(...) ::counterstrikesharp::Log::GetCoreLogger()->error(__VA_ARGS__)
|
#define CSSHARP_CORE_ERROR(...) ::counterstrikesharp::Log::GetCoreLogger()->error(__VA_ARGS__)
|
||||||
#define CSSHARP_CORE_CRITICAL(...) ::counterstrikesharp::Log::GetCoreLogger()->critical(__VA_ARGS__)
|
#define CSSHARP_CORE_CRITICAL(...) ::counterstrikesharp::Log::GetCoreLogger()->critical(__VA_ARGS__)
|
||||||
|
|||||||
@@ -1,127 +1,127 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of CounterStrikeSharp.
|
* This file is part of CounterStrikeSharp.
|
||||||
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
* (at your option) any later version.
|
* (at your option) any later version.
|
||||||
*
|
*
|
||||||
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
* GNU General Public License for more details.
|
* GNU General Public License for more details.
|
||||||
*
|
*
|
||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "core/managers/chat_manager.h"
|
#include "core/managers/chat_manager.h"
|
||||||
|
|
||||||
#include <funchook.h>
|
#include <funchook.h>
|
||||||
#include <igameevents.h>
|
#include <igameevents.h>
|
||||||
#include <public/eiface.h>
|
#include <public/eiface.h>
|
||||||
|
|
||||||
#include "characterset.h"
|
#include "characterset.h"
|
||||||
#include "core/coreconfig.h"
|
#include "core/coreconfig.h"
|
||||||
#include "core/gameconfig.h"
|
#include "core/gameconfig.h"
|
||||||
#include "core/log.h"
|
#include "core/log.h"
|
||||||
#include "core/managers/con_command_manager.h"
|
#include "core/managers/con_command_manager.h"
|
||||||
#include "core/memory.h"
|
#include "core/memory.h"
|
||||||
#include "core/memory_module.h"
|
#include "core/memory_module.h"
|
||||||
#include "scripting/callback_manager.h"
|
#include "scripting/callback_manager.h"
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
|
|
||||||
ChatManager::ChatManager() {}
|
ChatManager::ChatManager() {}
|
||||||
|
|
||||||
ChatManager::~ChatManager() {}
|
ChatManager::~ChatManager() {}
|
||||||
|
|
||||||
void ChatManager::OnAllInitialized()
|
void ChatManager::OnAllInitialized()
|
||||||
{
|
{
|
||||||
m_pHostSay = reinterpret_cast<HostSay>(modules::server->FindSignature(globals::gameConfig->GetSignature("Host_Say")));
|
m_pHostSay = reinterpret_cast<HostSay>(modules::server->FindSignature(globals::gameConfig->GetSignature("Host_Say")));
|
||||||
|
|
||||||
if (m_pHostSay == nullptr)
|
if (m_pHostSay == nullptr)
|
||||||
{
|
{
|
||||||
CSSHARP_CORE_ERROR("Failed to find signature for \'Host_Say\'");
|
CSSHARP_CORE_ERROR("Failed to find signature for \'Host_Say\'");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto m_hook = funchook_create();
|
auto m_hook = funchook_create();
|
||||||
funchook_prepare(m_hook, (void**)&m_pHostSay, (void*)&DetourHostSay);
|
funchook_prepare(m_hook, (void**)&m_pHostSay, (void*)&DetourHostSay);
|
||||||
funchook_install(m_hook, 0);
|
funchook_install(m_hook, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ChatManager::OnShutdown() {}
|
void ChatManager::OnShutdown() {}
|
||||||
|
|
||||||
void DetourHostSay(CEntityInstance* pController, CCommand& args, bool teamonly, int unk1, const char* unk2)
|
void DetourHostSay(CEntityInstance* pController, CCommand& args, bool teamonly, int unk1, const char* unk2)
|
||||||
{
|
{
|
||||||
if (pController)
|
if (pController)
|
||||||
{
|
{
|
||||||
auto pEvent = globals::gameEventManager->CreateEvent("player_chat", true);
|
auto pEvent = globals::gameEventManager->CreateEvent("player_chat", true);
|
||||||
if (pEvent)
|
if (pEvent)
|
||||||
{
|
{
|
||||||
pEvent->SetBool("teamonly", teamonly);
|
pEvent->SetBool("teamonly", teamonly);
|
||||||
pEvent->SetInt("userid", pController->GetEntityIndex().Get() - 1);
|
pEvent->SetInt("userid", pController->GetEntityIndex().Get() - 1);
|
||||||
pEvent->SetString("text", args[1]);
|
pEvent->SetString("text", args[1]);
|
||||||
|
|
||||||
globals::gameEventManager->FireEvent(pEvent, true);
|
globals::gameEventManager->FireEvent(pEvent, true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string prefix;
|
std::string prefix;
|
||||||
bool bSilent = globals::coreConfig->IsSilentChatTrigger(args[1], prefix);
|
bool bSilent = globals::coreConfig->IsSilentChatTrigger(args[1], prefix);
|
||||||
bool bCommand = globals::coreConfig->IsPublicChatTrigger(args[1], prefix) || bSilent;
|
bool bCommand = globals::coreConfig->IsPublicChatTrigger(args[1], prefix) || bSilent;
|
||||||
|
|
||||||
if (!bSilent)
|
if (!bSilent)
|
||||||
{
|
{
|
||||||
m_pHostSay(pController, args, teamonly, unk1, unk2);
|
m_pHostSay(pController, args, teamonly, unk1, unk2);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (bCommand)
|
if (bCommand)
|
||||||
{
|
{
|
||||||
char* pszMessage = (char*)(args.ArgS() + prefix.length() + 1);
|
char* pszMessage = (char*)(args.ArgS() + prefix.length() + 1);
|
||||||
|
|
||||||
// Trailing slashes are only removed if Host_Say has been called.
|
// Trailing slashes are only removed if Host_Say has been called.
|
||||||
if (bSilent) pszMessage[V_strlen(pszMessage) - 1] = 0;
|
if (bSilent) pszMessage[V_strlen(pszMessage) - 1] = 0;
|
||||||
|
|
||||||
CCommand args;
|
CCommand args;
|
||||||
args.Tokenize(pszMessage);
|
args.Tokenize(pszMessage);
|
||||||
|
|
||||||
auto prefixedPhrase = std::string("css_") + args.Arg(0);
|
auto prefixedPhrase = std::string("css_") + args.Arg(0);
|
||||||
auto bValidWithPrefix = globals::conCommandManager.IsValidValveCommand(prefixedPhrase.c_str());
|
auto bValidWithPrefix = globals::conCommandManager.IsValidValveCommand(prefixedPhrase.c_str());
|
||||||
|
|
||||||
if (bValidWithPrefix)
|
if (bValidWithPrefix)
|
||||||
{
|
{
|
||||||
// Re-tokenize with a `css_` prefix if we have found that its a valid command.
|
// Re-tokenize with a `css_` prefix if we have found that its a valid command.
|
||||||
args.Tokenize(("css_" + std::string(pszMessage)).c_str());
|
args.Tokenize(("css_" + std::string(pszMessage)).c_str());
|
||||||
}
|
}
|
||||||
|
|
||||||
globals::chatManager.OnSayCommandPost(pController, args);
|
globals::chatManager.OnSayCommandPost(pController, args);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ChatManager::OnSayCommandPre(CEntityInstance* pController, CCommand& command) { return false; }
|
bool ChatManager::OnSayCommandPre(CEntityInstance* pController, CCommand& command) { return false; }
|
||||||
|
|
||||||
void ChatManager::OnSayCommandPost(CEntityInstance* pController, CCommand& command)
|
void ChatManager::OnSayCommandPost(CEntityInstance* pController, CCommand& command)
|
||||||
{
|
{
|
||||||
auto commandStr = command.Arg(0);
|
auto commandStr = command.Arg(0);
|
||||||
|
|
||||||
return InternalDispatch(pController, commandStr, command);
|
return InternalDispatch(pController, commandStr, command);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ChatManager::InternalDispatch(CEntityInstance* pPlayerController, const char* szTriggerPhase, CCommand& fullCommand)
|
void ChatManager::InternalDispatch(CEntityInstance* pPlayerController, const char* szTriggerPhase, CCommand& fullCommand)
|
||||||
{
|
{
|
||||||
if (pPlayerController == nullptr)
|
if (pPlayerController == nullptr)
|
||||||
{
|
{
|
||||||
globals::conCommandManager.ExecuteCommandCallbacks(fullCommand.Arg(0),
|
globals::conCommandManager.ExecuteCommandCallbacks(fullCommand.Arg(0),
|
||||||
CCommandContext(CommandTarget_t::CT_NO_TARGET, CPlayerSlot(-1)), fullCommand,
|
CCommandContext(CommandTarget_t::CT_NO_TARGET, CPlayerSlot(-1)), fullCommand,
|
||||||
HookMode::Pre, CommandCallingContext::Chat);
|
HookMode::Pre, CommandCallingContext::Chat);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto index = pPlayerController->GetEntityIndex().Get();
|
auto index = pPlayerController->GetEntityIndex().Get();
|
||||||
auto slot = CPlayerSlot(index - 1);
|
auto slot = CPlayerSlot(index - 1);
|
||||||
|
|
||||||
globals::conCommandManager.ExecuteCommandCallbacks(fullCommand.Arg(0), CCommandContext(CommandTarget_t::CT_NO_TARGET, slot),
|
globals::conCommandManager.ExecuteCommandCallbacks(fullCommand.Arg(0), CCommandContext(CommandTarget_t::CT_NO_TARGET, slot),
|
||||||
fullCommand, HookMode::Pre, CommandCallingContext::Chat);
|
fullCommand, HookMode::Pre, CommandCallingContext::Chat);
|
||||||
}
|
}
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -1,68 +1,68 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of CounterStrikeSharp.
|
* This file is part of CounterStrikeSharp.
|
||||||
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
* (at your option) any later version.
|
* (at your option) any later version.
|
||||||
*
|
*
|
||||||
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
* GNU General Public License for more details.
|
* GNU General Public License for more details.
|
||||||
*
|
*
|
||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <map>
|
#include <map>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
#include "core/global_listener.h"
|
#include "core/global_listener.h"
|
||||||
#include "core/globals.h"
|
#include "core/globals.h"
|
||||||
#include "scripting/script_engine.h"
|
#include "scripting/script_engine.h"
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
class ScriptCallback;
|
class ScriptCallback;
|
||||||
|
|
||||||
typedef void (*HostSay)(CEntityInstance*, CCommand&, bool, int, const char*);
|
typedef void (*HostSay)(CEntityInstance*, CCommand&, bool, int, const char*);
|
||||||
|
|
||||||
class ChatCommandInfo
|
class ChatCommandInfo
|
||||||
{
|
{
|
||||||
friend class ChatManager;
|
friend class ChatManager;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
ChatCommandInfo() {}
|
ChatCommandInfo() {}
|
||||||
|
|
||||||
public:
|
public:
|
||||||
ScriptCallback* GetCallback() { return callback_pre; }
|
ScriptCallback* GetCallback() { return callback_pre; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::string command;
|
std::string command;
|
||||||
ScriptCallback* callback_pre;
|
ScriptCallback* callback_pre;
|
||||||
ScriptCallback* callback_post;
|
ScriptCallback* callback_post;
|
||||||
};
|
};
|
||||||
|
|
||||||
class ChatManager : public GlobalClass
|
class ChatManager : public GlobalClass
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
ChatManager();
|
ChatManager();
|
||||||
~ChatManager();
|
~ChatManager();
|
||||||
void OnAllInitialized() override;
|
void OnAllInitialized() override;
|
||||||
void OnShutdown() override;
|
void OnShutdown() override;
|
||||||
|
|
||||||
bool OnSayCommandPre(CEntityInstance* pController, CCommand& args);
|
bool OnSayCommandPre(CEntityInstance* pController, CCommand& args);
|
||||||
void OnSayCommandPost(CEntityInstance* pController, CCommand& args);
|
void OnSayCommandPost(CEntityInstance* pController, CCommand& args);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void InternalDispatch(CEntityInstance* pPlayerController, const char* szTriggerPhrase, CCommand& pFullCommand);
|
void InternalDispatch(CEntityInstance* pPlayerController, const char* szTriggerPhrase, CCommand& pFullCommand);
|
||||||
|
|
||||||
std::vector<ChatCommandInfo*> m_cmd_list;
|
std::vector<ChatCommandInfo*> m_cmd_list;
|
||||||
std::map<std::string, ChatCommandInfo*> m_cmd_lookup;
|
std::map<std::string, ChatCommandInfo*> m_cmd_lookup;
|
||||||
};
|
};
|
||||||
|
|
||||||
static void DetourHostSay(CEntityInstance* pController, CCommand& args, bool teamonly, int unk1, const char* unk2);
|
static void DetourHostSay(CEntityInstance* pController, CCommand& args, bool teamonly, int unk1, const char* unk2);
|
||||||
static HostSay m_pHostSay = nullptr;
|
static HostSay m_pHostSay = nullptr;
|
||||||
|
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -1,18 +1,18 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of CounterStrikeSharp.
|
* This file is part of CounterStrikeSharp.
|
||||||
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
* (at your option) any later version.
|
* (at your option) any later version.
|
||||||
*
|
*
|
||||||
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
* GNU General Public License for more details.
|
* GNU General Public License for more details.
|
||||||
*
|
*
|
||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "core/managers/entity_manager.h"
|
#include "core/managers/entity_manager.h"
|
||||||
#include "core/gameconfig.h"
|
#include "core/gameconfig.h"
|
||||||
@@ -25,18 +25,28 @@
|
|||||||
#include <public/eiface.h>
|
#include <public/eiface.h>
|
||||||
#include "scripting/callback_manager.h"
|
#include "scripting/callback_manager.h"
|
||||||
|
|
||||||
SH_DECL_HOOK7_void(ISource2GameEntities, CheckTransmit, SH_NOATTRIB, 0, CCheckTransmitInfo**, int, CBitVec<16384>&, const Entity2Networkable_t**, const uint16*, int, bool);
|
SH_DECL_HOOK7_void(ISource2GameEntities,
|
||||||
|
CheckTransmit,
|
||||||
|
SH_NOATTRIB,
|
||||||
|
0,
|
||||||
|
CCheckTransmitInfo**,
|
||||||
|
int,
|
||||||
|
CBitVec<16384>&,
|
||||||
|
const Entity2Networkable_t**,
|
||||||
|
const uint16*,
|
||||||
|
int,
|
||||||
|
bool);
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
|
|
||||||
EntityManager::EntityManager()
|
EntityManager::EntityManager() { m_profile_name = "EntityManager"; }
|
||||||
{
|
|
||||||
m_profile_name = "EntityManager";
|
|
||||||
}
|
|
||||||
|
|
||||||
EntityManager::~EntityManager() {}
|
EntityManager::~EntityManager() {}
|
||||||
|
|
||||||
CCheckTransmitInfoList::CCheckTransmitInfoList(CCheckTransmitInfo** pInfoInfoList, int nInfoCount) : infoList(pInfoInfoList), infoCount(nInfoCount) {}
|
CCheckTransmitInfoList::CCheckTransmitInfoList(CCheckTransmitInfo** pInfoInfoList, int nInfoCount)
|
||||||
|
: infoList(pInfoInfoList), infoCount(nInfoCount)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
void EntityManager::OnAllInitialized()
|
void EntityManager::OnAllInitialized()
|
||||||
{
|
{
|
||||||
@@ -46,13 +56,13 @@ void EntityManager::OnAllInitialized()
|
|||||||
on_entity_spawned_callback = globals::callbackManager.CreateCallback("OnEntitySpawned");
|
on_entity_spawned_callback = globals::callbackManager.CreateCallback("OnEntitySpawned");
|
||||||
on_entity_created_callback = globals::callbackManager.CreateCallback("OnEntityCreated");
|
on_entity_created_callback = globals::callbackManager.CreateCallback("OnEntityCreated");
|
||||||
on_entity_deleted_callback = globals::callbackManager.CreateCallback("OnEntityDeleted");
|
on_entity_deleted_callback = globals::callbackManager.CreateCallback("OnEntityDeleted");
|
||||||
on_entity_parent_changed_callback =
|
on_entity_parent_changed_callback = globals::callbackManager.CreateCallback("OnEntityParentChanged");
|
||||||
globals::callbackManager.CreateCallback("OnEntityParentChanged");
|
|
||||||
|
|
||||||
m_pFireOutputInternal = reinterpret_cast<FireOutputInternal>(modules::server->FindSignature(
|
m_pFireOutputInternal = reinterpret_cast<FireOutputInternal>(
|
||||||
globals::gameConfig->GetSignature("CEntityIOOutput_FireOutputInternal")));
|
modules::server->FindSignature(globals::gameConfig->GetSignature("CEntityIOOutput_FireOutputInternal")));
|
||||||
|
|
||||||
if (m_pFireOutputInternal == nullptr) {
|
if (m_pFireOutputInternal == nullptr)
|
||||||
|
{
|
||||||
CSSHARP_CORE_CRITICAL("Failed to find signature for \'CEntityIOOutput_FireOutputInternal\'");
|
CSSHARP_CORE_CRITICAL("Failed to find signature for \'CEntityIOOutput_FireOutputInternal\'");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -73,7 +83,7 @@ void EntityManager::OnAllInitialized()
|
|||||||
CSSHARP_CORE_CRITICAL("Failed to find signature for \'CEntitySystem_AddEntityIOEvent\'");
|
CSSHARP_CORE_CRITICAL("Failed to find signature for \'CEntitySystem_AddEntityIOEvent\'");
|
||||||
}
|
}
|
||||||
|
|
||||||
CBaseEntity_EmitSoundFilter = decltype(CBaseEntity_EmitSoundFilter) (
|
CBaseEntity_EmitSoundFilter = decltype(CBaseEntity_EmitSoundFilter)(
|
||||||
modules::server->FindSignature(globals::gameConfig->GetSignature("CBaseEntity_EmitSoundFilter")));
|
modules::server->FindSignature(globals::gameConfig->GetSignature("CBaseEntity_EmitSoundFilter")));
|
||||||
|
|
||||||
if (!CBaseEntity_EmitSoundFilter)
|
if (!CBaseEntity_EmitSoundFilter)
|
||||||
@@ -104,7 +114,8 @@ void CEntityListener::OnEntitySpawned(CEntityInstance* pEntity)
|
|||||||
{
|
{
|
||||||
auto callback = globals::entityManager.on_entity_spawned_callback;
|
auto callback = globals::entityManager.on_entity_spawned_callback;
|
||||||
|
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
callback->ScriptContext().Push(pEntity);
|
callback->ScriptContext().Push(pEntity);
|
||||||
callback->Execute();
|
callback->Execute();
|
||||||
@@ -114,7 +125,8 @@ void CEntityListener::OnEntityCreated(CEntityInstance* pEntity)
|
|||||||
{
|
{
|
||||||
auto callback = globals::entityManager.on_entity_created_callback;
|
auto callback = globals::entityManager.on_entity_created_callback;
|
||||||
|
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
callback->ScriptContext().Push(pEntity);
|
callback->ScriptContext().Push(pEntity);
|
||||||
callback->Execute();
|
callback->Execute();
|
||||||
@@ -124,7 +136,8 @@ void CEntityListener::OnEntityDeleted(CEntityInstance* pEntity)
|
|||||||
{
|
{
|
||||||
auto callback = globals::entityManager.on_entity_deleted_callback;
|
auto callback = globals::entityManager.on_entity_deleted_callback;
|
||||||
|
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
callback->ScriptContext().Push(pEntity);
|
callback->ScriptContext().Push(pEntity);
|
||||||
callback->Execute();
|
callback->Execute();
|
||||||
@@ -134,7 +147,8 @@ void CEntityListener::OnEntityParentChanged(CEntityInstance* pEntity, CEntityIns
|
|||||||
{
|
{
|
||||||
auto callback = globals::entityManager.on_entity_parent_changed_callback;
|
auto callback = globals::entityManager.on_entity_parent_changed_callback;
|
||||||
|
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
callback->ScriptContext().Push(pEntity);
|
callback->ScriptContext().Push(pEntity);
|
||||||
callback->ScriptContext().Push(pNewParent);
|
callback->ScriptContext().Push(pNewParent);
|
||||||
@@ -142,49 +156,58 @@ void CEntityListener::OnEntityParentChanged(CEntityInstance* pEntity, CEntityIns
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void EntityManager::HookEntityOutput(const char* szClassname, const char* szOutput,
|
void EntityManager::HookEntityOutput(const char* szClassname, const char* szOutput, CallbackT fnCallback, HookMode mode)
|
||||||
CallbackT fnCallback, HookMode mode)
|
|
||||||
{
|
{
|
||||||
auto outputKey = OutputKey_t(szClassname, szOutput);
|
auto outputKey = OutputKey_t(szClassname, szOutput);
|
||||||
CallbackPair* pCallbackPair;
|
CallbackPair* pCallbackPair;
|
||||||
|
|
||||||
auto search = m_pHookMap.find(outputKey);
|
auto search = m_pHookMap.find(outputKey);
|
||||||
if (search == m_pHookMap.end()) {
|
if (search == m_pHookMap.end())
|
||||||
|
{
|
||||||
m_pHookMap[outputKey] = new CallbackPair();
|
m_pHookMap[outputKey] = new CallbackPair();
|
||||||
pCallbackPair = m_pHookMap[outputKey];
|
pCallbackPair = m_pHookMap[outputKey];
|
||||||
} else
|
}
|
||||||
|
else
|
||||||
pCallbackPair = search->second;
|
pCallbackPair = search->second;
|
||||||
|
|
||||||
auto* pCallback = mode == HookMode::Pre ? pCallbackPair->pre : pCallbackPair->post;
|
auto* pCallback = mode == HookMode::Pre ? pCallbackPair->pre : pCallbackPair->post;
|
||||||
pCallback->AddListener(fnCallback);
|
pCallback->AddListener(fnCallback);
|
||||||
}
|
}
|
||||||
|
|
||||||
void EntityManager::UnhookEntityOutput(const char* szClassname, const char* szOutput,
|
void EntityManager::UnhookEntityOutput(const char* szClassname, const char* szOutput, CallbackT fnCallback, HookMode mode)
|
||||||
CallbackT fnCallback, HookMode mode)
|
|
||||||
{
|
{
|
||||||
auto outputKey = OutputKey_t(szClassname, szOutput);
|
auto outputKey = OutputKey_t(szClassname, szOutput);
|
||||||
|
|
||||||
auto search = m_pHookMap.find(outputKey);
|
auto search = m_pHookMap.find(outputKey);
|
||||||
if (search != m_pHookMap.end()) {
|
if (search != m_pHookMap.end())
|
||||||
|
{
|
||||||
auto* pCallbackPair = search->second;
|
auto* pCallbackPair = search->second;
|
||||||
|
|
||||||
auto* pCallback = mode == Pre ? pCallbackPair->pre : pCallbackPair->post;
|
auto* pCallback = mode == Pre ? pCallbackPair->pre : pCallbackPair->post;
|
||||||
|
|
||||||
pCallback->RemoveListener(fnCallback);
|
pCallback->RemoveListener(fnCallback);
|
||||||
|
|
||||||
if (!pCallbackPair->HasCallbacks()) {
|
if (!pCallbackPair->HasCallbacks())
|
||||||
|
{
|
||||||
m_pHookMap.erase(outputKey);
|
m_pHookMap.erase(outputKey);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void EntityManager::CheckTransmit(CCheckTransmitInfo** pInfoInfoList, int nInfoCount, CBitVec<16384>& unionTransmitEdicts, const Entity2Networkable_t** pNetworkables, const uint16* pEntityIndicies, int nEntityIndices, bool bEnablePVSBits)
|
void EntityManager::CheckTransmit(CCheckTransmitInfo** pInfoInfoList,
|
||||||
|
int nInfoCount,
|
||||||
|
CBitVec<16384>& unionTransmitEdicts,
|
||||||
|
const Entity2Networkable_t** pNetworkables,
|
||||||
|
const uint16* pEntityIndicies,
|
||||||
|
int nEntityIndices,
|
||||||
|
bool bEnablePVSBits)
|
||||||
{
|
{
|
||||||
VPROF_BUDGET(m_profile_name.c_str(), "CS# CheckTransmit");
|
VPROF_BUDGET(m_profile_name.c_str(), "CS# CheckTransmit");
|
||||||
|
|
||||||
auto callback = globals::entityManager.check_transmit;
|
auto callback = globals::entityManager.check_transmit;
|
||||||
|
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
CCheckTransmitInfoList* infoList = new CCheckTransmitInfoList(pInfoInfoList, nInfoCount);
|
CCheckTransmitInfoList* infoList = new CCheckTransmitInfoList(pInfoInfoList, nInfoCount);
|
||||||
|
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
@@ -195,39 +218,43 @@ void EntityManager::CheckTransmit(CCheckTransmitInfo** pInfoInfoList, int nInfoC
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void DetourFireOutputInternal(CEntityIOOutput* const pThis, CEntityInstance* pActivator,
|
void DetourFireOutputInternal(
|
||||||
CEntityInstance* pCaller, const CVariant* const value, float flDelay)
|
CEntityIOOutput* const pThis, CEntityInstance* pActivator, CEntityInstance* pCaller, const CVariant* const value, float flDelay)
|
||||||
{
|
{
|
||||||
std::vector vecSearchKeys{OutputKey_t("*", pThis->m_pDesc->m_pName),
|
std::vector vecSearchKeys{ OutputKey_t("*", pThis->m_pDesc->m_pName), OutputKey_t("*", "*") };
|
||||||
OutputKey_t("*", "*")};
|
|
||||||
|
|
||||||
if (pCaller) {
|
if (pCaller)
|
||||||
|
{
|
||||||
vecSearchKeys.push_back(OutputKey_t(pCaller->GetClassname(), pThis->m_pDesc->m_pName));
|
vecSearchKeys.push_back(OutputKey_t(pCaller->GetClassname(), pThis->m_pDesc->m_pName));
|
||||||
OutputKey_t(pCaller->GetClassname(), "*");
|
OutputKey_t(pCaller->GetClassname(), "*");
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<CallbackPair*> vecCallbackPairs;
|
std::vector<CallbackPair*> vecCallbackPairs;
|
||||||
|
|
||||||
if (pCaller) {
|
if (pCaller)
|
||||||
CSSHARP_CORE_TRACE("[EntityManager][FireOutputHook] - {}, {}", pThis->m_pDesc->m_pName,
|
{
|
||||||
pCaller->GetClassname());
|
CSSHARP_CORE_TRACE("[EntityManager][FireOutputHook] - {}, {}", pThis->m_pDesc->m_pName, pCaller->GetClassname());
|
||||||
|
|
||||||
auto& hookMap = globals::entityManager.m_pHookMap;
|
auto& hookMap = globals::entityManager.m_pHookMap;
|
||||||
|
|
||||||
for (auto& searchKey : vecSearchKeys) {
|
for (auto& searchKey : vecSearchKeys)
|
||||||
|
{
|
||||||
auto search = hookMap.find(searchKey);
|
auto search = hookMap.find(searchKey);
|
||||||
if (search != hookMap.end()) {
|
if (search != hookMap.end())
|
||||||
|
{
|
||||||
vecCallbackPairs.push_back(search->second);
|
vecCallbackPairs.push_back(search->second);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else
|
}
|
||||||
CSSHARP_CORE_TRACE("[EntityManager][FireOutputHook] - {}, unknown caller",
|
else
|
||||||
pThis->m_pDesc->m_pName);
|
CSSHARP_CORE_TRACE("[EntityManager][FireOutputHook] - {}, unknown caller", pThis->m_pDesc->m_pName);
|
||||||
|
|
||||||
HookResult result = HookResult::Continue;
|
HookResult result = HookResult::Continue;
|
||||||
|
|
||||||
for (auto pCallbackPair : vecCallbackPairs) {
|
for (auto pCallbackPair : vecCallbackPairs)
|
||||||
if (pCallbackPair->pre->GetFunctionCount()) {
|
{
|
||||||
|
if (pCallbackPair->pre->GetFunctionCount())
|
||||||
|
{
|
||||||
pCallbackPair->pre->ScriptContext().Reset();
|
pCallbackPair->pre->ScriptContext().Reset();
|
||||||
pCallbackPair->pre->ScriptContext().Push(pThis);
|
pCallbackPair->pre->ScriptContext().Push(pThis);
|
||||||
pCallbackPair->pre->ScriptContext().Push(pThis->m_pDesc->m_pName);
|
pCallbackPair->pre->ScriptContext().Push(pThis->m_pDesc->m_pName);
|
||||||
@@ -236,32 +263,37 @@ void DetourFireOutputInternal(CEntityIOOutput* const pThis, CEntityInstance* pAc
|
|||||||
pCallbackPair->pre->ScriptContext().Push(value);
|
pCallbackPair->pre->ScriptContext().Push(value);
|
||||||
pCallbackPair->pre->ScriptContext().Push(flDelay);
|
pCallbackPair->pre->ScriptContext().Push(flDelay);
|
||||||
|
|
||||||
for (auto fnMethodToCall : pCallbackPair->pre->GetFunctions()) {
|
for (auto fnMethodToCall : pCallbackPair->pre->GetFunctions())
|
||||||
if (!fnMethodToCall)
|
{
|
||||||
continue;
|
if (!fnMethodToCall) continue;
|
||||||
fnMethodToCall(&pCallbackPair->pre->ScriptContextStruct());
|
fnMethodToCall(&pCallbackPair->pre->ScriptContextStruct());
|
||||||
|
|
||||||
auto thisResult = pCallbackPair->pre->ScriptContext().GetResult<HookResult>();
|
auto thisResult = pCallbackPair->pre->ScriptContext().GetResult<HookResult>();
|
||||||
|
|
||||||
if (thisResult >= HookResult::Stop) {
|
if (thisResult >= HookResult::Stop)
|
||||||
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (thisResult > result) {
|
if (thisResult > result)
|
||||||
|
{
|
||||||
result = thisResult;
|
result = thisResult;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (result >= HookResult::Handled) {
|
if (result >= HookResult::Handled)
|
||||||
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
m_pFireOutputInternal(pThis, pActivator, pCaller, value, flDelay);
|
m_pFireOutputInternal(pThis, pActivator, pCaller, value, flDelay);
|
||||||
|
|
||||||
for (auto pCallbackPair : vecCallbackPairs) {
|
for (auto pCallbackPair : vecCallbackPairs)
|
||||||
if (pCallbackPair->post->GetFunctionCount()) {
|
{
|
||||||
|
if (pCallbackPair->post->GetFunctionCount())
|
||||||
|
{
|
||||||
pCallbackPair->post->ScriptContext().Reset();
|
pCallbackPair->post->ScriptContext().Reset();
|
||||||
pCallbackPair->post->ScriptContext().Push(pThis);
|
pCallbackPair->post->ScriptContext().Push(pThis);
|
||||||
pCallbackPair->post->ScriptContext().Push(pThis->m_pDesc->m_pName);
|
pCallbackPair->post->ScriptContext().Push(pThis->m_pDesc->m_pName);
|
||||||
@@ -276,8 +308,10 @@ void DetourFireOutputInternal(CEntityIOOutput* const pThis, CEntityInstance* pAc
|
|||||||
|
|
||||||
SndOpEventGuid_t EntityEmitSoundFilter(IRecipientFilter& filter, uint32 ent, const char* pszSound, float flVolume, float flPitch)
|
SndOpEventGuid_t EntityEmitSoundFilter(IRecipientFilter& filter, uint32 ent, const char* pszSound, float flVolume, float flPitch)
|
||||||
{
|
{
|
||||||
if (!CBaseEntity_EmitSoundFilter) {
|
if (!CBaseEntity_EmitSoundFilter)
|
||||||
CSSHARP_CORE_ERROR("[EntityManager][EmitSoundFilter] - Failed to emit a sound. Signature for \'CBaseEntity_EmitSoundFilter\' is not found. The latest update may have broken it.");
|
{
|
||||||
|
CSSHARP_CORE_ERROR("[EntityManager][EmitSoundFilter] - Failed to emit a sound. Signature for \'CBaseEntity_EmitSoundFilter\' is "
|
||||||
|
"not found. The latest update may have broken it.");
|
||||||
return SndOpEventGuid_t{};
|
return SndOpEventGuid_t{};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,18 +1,18 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of CounterStrikeSharp.
|
* This file is part of CounterStrikeSharp.
|
||||||
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
* (at your option) any later version.
|
* (at your option) any later version.
|
||||||
*
|
*
|
||||||
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
* GNU General Public License for more details.
|
* GNU General Public License for more details.
|
||||||
*
|
*
|
||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
@@ -34,24 +34,29 @@ class ScriptCallback;
|
|||||||
|
|
||||||
typedef std::pair<std::string, std::string> OutputKey_t;
|
typedef std::pair<std::string, std::string> OutputKey_t;
|
||||||
|
|
||||||
class CEntityListener : public IEntityListener {
|
class CEntityListener : public IEntityListener
|
||||||
void OnEntitySpawned(CEntityInstance *pEntity) override;
|
{
|
||||||
void OnEntityCreated(CEntityInstance *pEntity) override;
|
void OnEntitySpawned(CEntityInstance* pEntity) override;
|
||||||
void OnEntityDeleted(CEntityInstance *pEntity) override;
|
void OnEntityCreated(CEntityInstance* pEntity) override;
|
||||||
void OnEntityParentChanged(CEntityInstance *pEntity, CEntityInstance *pNewParent) override;
|
void OnEntityDeleted(CEntityInstance* pEntity) override;
|
||||||
|
void OnEntityParentChanged(CEntityInstance* pEntity, CEntityInstance* pNewParent) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
class CCheckTransmitInfoList {
|
class CCheckTransmitInfoList
|
||||||
public:
|
{
|
||||||
|
public:
|
||||||
CCheckTransmitInfoList(CCheckTransmitInfo** pInfoInfoList, int nInfoCount);
|
CCheckTransmitInfoList(CCheckTransmitInfo** pInfoInfoList, int nInfoCount);
|
||||||
private:
|
|
||||||
|
private:
|
||||||
CCheckTransmitInfo** infoList;
|
CCheckTransmitInfo** infoList;
|
||||||
int infoCount;
|
int infoCount;
|
||||||
};
|
};
|
||||||
|
|
||||||
class EntityManager : public GlobalClass {
|
class EntityManager : public GlobalClass
|
||||||
|
{
|
||||||
friend CEntityListener;
|
friend CEntityListener;
|
||||||
public:
|
|
||||||
|
public:
|
||||||
EntityManager();
|
EntityManager();
|
||||||
~EntityManager();
|
~EntityManager();
|
||||||
void OnAllInitialized() override;
|
void OnAllInitialized() override;
|
||||||
@@ -60,19 +65,25 @@ public:
|
|||||||
void UnhookEntityOutput(const char* szClassname, const char* szOutput, CallbackT fnCallback, HookMode mode);
|
void UnhookEntityOutput(const char* szClassname, const char* szOutput, CallbackT fnCallback, HookMode mode);
|
||||||
CEntityListener entityListener;
|
CEntityListener entityListener;
|
||||||
std::map<OutputKey_t, CallbackPair*> m_pHookMap;
|
std::map<OutputKey_t, CallbackPair*> m_pHookMap;
|
||||||
private:
|
|
||||||
void CheckTransmit(CCheckTransmitInfo** pInfoInfoList, int nInfoCount, CBitVec<16384>& unionTransmitEdicts, const Entity2Networkable_t** pNetworkables, const uint16* pEntityIndicies, int nEntityIndices, bool bEnablePVSBits);
|
|
||||||
|
|
||||||
ScriptCallback *on_entity_spawned_callback;
|
private:
|
||||||
ScriptCallback *on_entity_created_callback;
|
void CheckTransmit(CCheckTransmitInfo** pInfoInfoList,
|
||||||
ScriptCallback *on_entity_deleted_callback;
|
int nInfoCount,
|
||||||
ScriptCallback *on_entity_parent_changed_callback;
|
CBitVec<16384>& unionTransmitEdicts,
|
||||||
ScriptCallback *check_transmit;
|
const Entity2Networkable_t** pNetworkables,
|
||||||
|
const uint16* pEntityIndicies,
|
||||||
|
int nEntityIndices,
|
||||||
|
bool bEnablePVSBits);
|
||||||
|
|
||||||
|
ScriptCallback* on_entity_spawned_callback;
|
||||||
|
ScriptCallback* on_entity_created_callback;
|
||||||
|
ScriptCallback* on_entity_deleted_callback;
|
||||||
|
ScriptCallback* on_entity_parent_changed_callback;
|
||||||
|
ScriptCallback* check_transmit;
|
||||||
|
|
||||||
std::string m_profile_name;
|
std::string m_profile_name;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
enum EntityIOTargetType_t
|
enum EntityIOTargetType_t
|
||||||
{
|
{
|
||||||
ENTITY_IO_TARGET_INVALID = 0xFFFFFFFF,
|
ENTITY_IO_TARGET_INVALID = 0xFFFFFFFF,
|
||||||
@@ -118,16 +129,16 @@ class CEntityIOOutput
|
|||||||
EntityIOOutputDesc_t* m_pDesc;
|
EntityIOOutputDesc_t* m_pDesc;
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef void (*FireOutputInternal)(CEntityIOOutput* const, CEntityInstance*, CEntityInstance*,
|
typedef void (*FireOutputInternal)(CEntityIOOutput* const, CEntityInstance*, CEntityInstance*, const CVariant* const, float);
|
||||||
const CVariant* const, float);
|
|
||||||
|
|
||||||
static void DetourFireOutputInternal(CEntityIOOutput* const pThis, CEntityInstance* pActivator,
|
static void DetourFireOutputInternal(
|
||||||
CEntityInstance* pCaller, const CVariant* const value, float flDelay);
|
CEntityIOOutput* const pThis, CEntityInstance* pActivator, CEntityInstance* pCaller, const CVariant* const value, float flDelay);
|
||||||
|
|
||||||
static FireOutputInternal m_pFireOutputInternal = nullptr;
|
static FireOutputInternal m_pFireOutputInternal = nullptr;
|
||||||
|
|
||||||
// Do it in here because i didn't found a good place to do this
|
// Do it in here because i didn't found a good place to do this
|
||||||
inline void (*CEntityInstance_AcceptInput)(CEntityInstance* pThis, const char* pInputName, CEntityInstance* pActivator, CEntityInstance* pCaller, variant_t* value, int nOutputID);
|
inline void (*CEntityInstance_AcceptInput)(
|
||||||
|
CEntityInstance* pThis, const char* pInputName, CEntityInstance* pActivator, CEntityInstance* pCaller, variant_t* value, int nOutputID);
|
||||||
|
|
||||||
inline void (*CEntitySystem_AddEntityIOEvent)(CEntitySystem* pEntitySystem,
|
inline void (*CEntitySystem_AddEntityIOEvent)(CEntitySystem* pEntitySystem,
|
||||||
CEntityInstance* pTarget,
|
CEntityInstance* pTarget,
|
||||||
@@ -142,66 +153,53 @@ typedef uint32 SoundEventGuid_t;
|
|||||||
|
|
||||||
enum gender_t : uint8
|
enum gender_t : uint8
|
||||||
{
|
{
|
||||||
GENDER_NONE = 0x0,
|
GENDER_NONE = 0x0,
|
||||||
GENDER_MALE = 0x1,
|
GENDER_MALE = 0x1,
|
||||||
GENDER_FEMALE = 0x2,
|
GENDER_FEMALE = 0x2,
|
||||||
GENDER_NAMVET = 0x3,
|
GENDER_NAMVET = 0x3,
|
||||||
GENDER_TEENGIRL = 0x4,
|
GENDER_TEENGIRL = 0x4,
|
||||||
GENDER_BIKER = 0x5,
|
GENDER_BIKER = 0x5,
|
||||||
GENDER_MANAGER = 0x6,
|
GENDER_MANAGER = 0x6,
|
||||||
GENDER_GAMBLER = 0x7,
|
GENDER_GAMBLER = 0x7,
|
||||||
GENDER_PRODUCER = 0x8,
|
GENDER_PRODUCER = 0x8,
|
||||||
GENDER_COACH = 0x9,
|
GENDER_COACH = 0x9,
|
||||||
GENDER_MECHANIC = 0xA,
|
GENDER_MECHANIC = 0xA,
|
||||||
GENDER_CEDA = 0xB,
|
GENDER_CEDA = 0xB,
|
||||||
GENDER_CRAWLER = 0xC,
|
GENDER_CRAWLER = 0xC,
|
||||||
GENDER_UNDISTRACTABLE = 0xD,
|
GENDER_UNDISTRACTABLE = 0xD,
|
||||||
GENDER_FALLEN = 0xE,
|
GENDER_FALLEN = 0xE,
|
||||||
GENDER_RIOT_CONTROL = 0xF,
|
GENDER_RIOT_CONTROL = 0xF,
|
||||||
GENDER_CLOWN = 0x10,
|
GENDER_CLOWN = 0x10,
|
||||||
GENDER_JIMMY = 0x11,
|
GENDER_JIMMY = 0x11,
|
||||||
GENDER_HOSPITAL_PATIENT = 0x12,
|
GENDER_HOSPITAL_PATIENT = 0x12,
|
||||||
GENDER_BRIDE = 0x13,
|
GENDER_BRIDE = 0x13,
|
||||||
GENDER_LAST = 0x14,
|
GENDER_LAST = 0x14,
|
||||||
};
|
};
|
||||||
|
|
||||||
struct EmitSound_t
|
struct EmitSound_t
|
||||||
{
|
{
|
||||||
EmitSound_t() :
|
EmitSound_t()
|
||||||
m_nChannel(0),
|
: m_nChannel(0), m_pSoundName(0), m_flVolume(VOL_NORM), m_SoundLevel(SNDLVL_NONE), m_nFlags(0), m_nPitch(PITCH_NORM), m_pOrigin(0),
|
||||||
m_pSoundName(0),
|
m_flSoundTime(0.0f), m_pflSoundDuration(0), m_bEmitCloseCaption(true), m_bWarnOnMissingCloseCaption(false),
|
||||||
m_flVolume(VOL_NORM),
|
m_bWarnOnDirectWaveReference(false), m_nSpeakerEntity(-1), m_UtlVecSoundOrigin(), m_nForceGuid(0), m_SpeakerGender(GENDER_NONE)
|
||||||
m_SoundLevel(SNDLVL_NONE),
|
{
|
||||||
m_nFlags(0),
|
}
|
||||||
m_nPitch(PITCH_NORM),
|
int m_nChannel;
|
||||||
m_pOrigin(0),
|
const char* m_pSoundName;
|
||||||
m_flSoundTime(0.0f),
|
float m_flVolume;
|
||||||
m_pflSoundDuration(0),
|
soundlevel_t m_SoundLevel;
|
||||||
m_bEmitCloseCaption(true),
|
int m_nFlags;
|
||||||
m_bWarnOnMissingCloseCaption(false),
|
int m_nPitch;
|
||||||
m_bWarnOnDirectWaveReference(false),
|
const Vector* m_pOrigin;
|
||||||
m_nSpeakerEntity(-1),
|
float m_flSoundTime;
|
||||||
m_UtlVecSoundOrigin(),
|
float* m_pflSoundDuration;
|
||||||
m_nForceGuid(0),
|
bool m_bEmitCloseCaption;
|
||||||
m_SpeakerGender(GENDER_NONE)
|
bool m_bWarnOnMissingCloseCaption;
|
||||||
{
|
bool m_bWarnOnDirectWaveReference;
|
||||||
}
|
CEntityIndex m_nSpeakerEntity;
|
||||||
int m_nChannel;
|
CUtlVector<Vector, CUtlMemory<Vector, int>> m_UtlVecSoundOrigin;
|
||||||
const char* m_pSoundName;
|
SoundEventGuid_t m_nForceGuid;
|
||||||
float m_flVolume;
|
gender_t m_SpeakerGender;
|
||||||
soundlevel_t m_SoundLevel;
|
|
||||||
int m_nFlags;
|
|
||||||
int m_nPitch;
|
|
||||||
const Vector* m_pOrigin;
|
|
||||||
float m_flSoundTime;
|
|
||||||
float* m_pflSoundDuration;
|
|
||||||
bool m_bEmitCloseCaption;
|
|
||||||
bool m_bWarnOnMissingCloseCaption;
|
|
||||||
bool m_bWarnOnDirectWaveReference;
|
|
||||||
CEntityIndex m_nSpeakerEntity;
|
|
||||||
CUtlVector<Vector, CUtlMemory<Vector, int> > m_UtlVecSoundOrigin;
|
|
||||||
SoundEventGuid_t m_nForceGuid;
|
|
||||||
gender_t m_SpeakerGender;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
struct SndOpEventGuid_t
|
struct SndOpEventGuid_t
|
||||||
@@ -212,5 +210,6 @@ struct SndOpEventGuid_t
|
|||||||
|
|
||||||
inline SndOpEventGuid_t(FASTCALL* CBaseEntity_EmitSoundFilter)(IRecipientFilter& filter, CEntityIndex ent, const EmitSound_t& params);
|
inline SndOpEventGuid_t(FASTCALL* CBaseEntity_EmitSoundFilter)(IRecipientFilter& filter, CEntityIndex ent, const EmitSound_t& params);
|
||||||
|
|
||||||
SndOpEventGuid_t EntityEmitSoundFilter(IRecipientFilter& filter, uint32 ent, const char* pszSound, float flVolume = 1.0f, float flPitch = 1.0f);
|
SndOpEventGuid_t
|
||||||
} // namespace counterstrikesharp
|
EntityEmitSoundFilter(IRecipientFilter& filter, uint32 ent, const char* pszSound, float flVolume = 1.0f, float flPitch = 1.0f);
|
||||||
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -44,19 +44,15 @@
|
|||||||
#include <iplayerinfo.h>
|
#include <iplayerinfo.h>
|
||||||
// extern CEntitySystem *g_pEntitySystem;
|
// extern CEntitySystem *g_pEntitySystem;
|
||||||
|
|
||||||
SH_DECL_HOOK4_void(IServerGameClients, ClientActive, SH_NOATTRIB, 0, CPlayerSlot, bool, const char*,
|
SH_DECL_HOOK4_void(IServerGameClients, ClientActive, SH_NOATTRIB, 0, CPlayerSlot, bool, const char*, uint64);
|
||||||
uint64);
|
SH_DECL_HOOK5_void(
|
||||||
SH_DECL_HOOK5_void(IServerGameClients, ClientDisconnect, SH_NOATTRIB, 0, CPlayerSlot,
|
IServerGameClients, ClientDisconnect, SH_NOATTRIB, 0, CPlayerSlot, ENetworkDisconnectionReason, const char*, uint64, const char*);
|
||||||
ENetworkDisconnectionReason, const char*, uint64, const char*);
|
|
||||||
|
|
||||||
SH_DECL_HOOK1_void(IServerGameClients, ClientVoice, SH_NOATTRIB, 0, CPlayerSlot);
|
SH_DECL_HOOK1_void(IServerGameClients, ClientVoice, SH_NOATTRIB, 0, CPlayerSlot);
|
||||||
SH_DECL_HOOK4_void(IServerGameClients, ClientPutInServer, SH_NOATTRIB, 0, CPlayerSlot, char const*,
|
SH_DECL_HOOK4_void(IServerGameClients, ClientPutInServer, SH_NOATTRIB, 0, CPlayerSlot, char const*, int, uint64);
|
||||||
int, uint64);
|
|
||||||
SH_DECL_HOOK1_void(IServerGameClients, ClientSettingsChanged, SH_NOATTRIB, 0, CPlayerSlot);
|
SH_DECL_HOOK1_void(IServerGameClients, ClientSettingsChanged, SH_NOATTRIB, 0, CPlayerSlot);
|
||||||
SH_DECL_HOOK6_void(IServerGameClients, OnClientConnected, SH_NOATTRIB, 0, CPlayerSlot, const char*,
|
SH_DECL_HOOK6_void(IServerGameClients, OnClientConnected, SH_NOATTRIB, 0, CPlayerSlot, const char*, uint64, const char*, const char*, bool);
|
||||||
uint64, const char*, const char*, bool);
|
SH_DECL_HOOK6(IServerGameClients, ClientConnect, SH_NOATTRIB, 0, bool, CPlayerSlot, const char*, uint64, const char*, bool, CBufferString*);
|
||||||
SH_DECL_HOOK6(IServerGameClients, ClientConnect, SH_NOATTRIB, 0, bool, CPlayerSlot, const char*,
|
|
||||||
uint64, const char*, bool, CBufferString*);
|
|
||||||
|
|
||||||
SH_DECL_HOOK2_void(IServerGameClients, ClientCommand, SH_NOATTRIB, 0, CPlayerSlot, const CCommand&);
|
SH_DECL_HOOK2_void(IServerGameClients, ClientCommand, SH_NOATTRIB, 0, CPlayerSlot, const CCommand&);
|
||||||
|
|
||||||
@@ -66,48 +62,39 @@ void PlayerManager::OnStartup() {}
|
|||||||
|
|
||||||
void PlayerManager::OnAllInitialized()
|
void PlayerManager::OnAllInitialized()
|
||||||
{
|
{
|
||||||
SH_ADD_HOOK(IServerGameClients, ClientConnect, globals::serverGameClients,
|
SH_ADD_HOOK(IServerGameClients, ClientConnect, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientConnect), false);
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientConnect), false);
|
SH_ADD_HOOK(IServerGameClients, ClientConnect, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientConnect_Post), true);
|
||||||
SH_ADD_HOOK(IServerGameClients, ClientConnect, globals::serverGameClients,
|
SH_ADD_HOOK(IServerGameClients, ClientPutInServer, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientPutInServer),
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientConnect_Post), true);
|
true);
|
||||||
SH_ADD_HOOK(IServerGameClients, ClientPutInServer, globals::serverGameClients,
|
SH_ADD_HOOK(IServerGameClients, ClientDisconnect, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientDisconnect),
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientPutInServer), true);
|
false);
|
||||||
SH_ADD_HOOK(IServerGameClients, ClientDisconnect, globals::serverGameClients,
|
SH_ADD_HOOK(IServerGameClients, ClientDisconnect, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientDisconnect_Post),
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientDisconnect), false);
|
true);
|
||||||
SH_ADD_HOOK(IServerGameClients, ClientDisconnect, globals::serverGameClients,
|
SH_ADD_HOOK(IServerGameClients, ClientCommand, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientCommand), false);
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientDisconnect_Post), true);
|
SH_ADD_HOOK(IServerGameClients, ClientVoice, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientVoice), true);
|
||||||
SH_ADD_HOOK(IServerGameClients, ClientCommand, globals::serverGameClients,
|
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientCommand), false);
|
|
||||||
SH_ADD_HOOK(IServerGameClients, ClientVoice, globals::serverGameClients,
|
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientVoice), true);
|
|
||||||
|
|
||||||
m_on_client_connect_callback = globals::callbackManager.CreateCallback("OnClientConnect");
|
m_on_client_connect_callback = globals::callbackManager.CreateCallback("OnClientConnect");
|
||||||
m_on_client_connected_callback = globals::callbackManager.CreateCallback("OnClientConnected");
|
m_on_client_connected_callback = globals::callbackManager.CreateCallback("OnClientConnected");
|
||||||
m_on_client_put_in_server_callback =
|
m_on_client_put_in_server_callback = globals::callbackManager.CreateCallback("OnClientPutInServer");
|
||||||
globals::callbackManager.CreateCallback("OnClientPutInServer");
|
|
||||||
m_on_client_disconnect_callback = globals::callbackManager.CreateCallback("OnClientDisconnect");
|
m_on_client_disconnect_callback = globals::callbackManager.CreateCallback("OnClientDisconnect");
|
||||||
m_on_client_disconnect_post_callback =
|
m_on_client_disconnect_post_callback = globals::callbackManager.CreateCallback("OnClientDisconnectPost");
|
||||||
globals::callbackManager.CreateCallback("OnClientDisconnectPost");
|
|
||||||
m_on_client_voice_callback = globals::callbackManager.CreateCallback("OnClientVoice");
|
m_on_client_voice_callback = globals::callbackManager.CreateCallback("OnClientVoice");
|
||||||
m_on_client_authorized_callback = globals::callbackManager.CreateCallback("OnClientAuthorized");
|
m_on_client_authorized_callback = globals::callbackManager.CreateCallback("OnClientAuthorized");
|
||||||
}
|
}
|
||||||
|
|
||||||
void PlayerManager::OnShutdown()
|
void PlayerManager::OnShutdown()
|
||||||
{
|
{
|
||||||
SH_REMOVE_HOOK(IServerGameClients, ClientConnect, globals::serverGameClients,
|
SH_REMOVE_HOOK(IServerGameClients, ClientConnect, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientConnect), false);
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientConnect), false);
|
SH_REMOVE_HOOK(IServerGameClients, ClientConnect, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientConnect_Post),
|
||||||
SH_REMOVE_HOOK(IServerGameClients, ClientConnect, globals::serverGameClients,
|
true);
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientConnect_Post), true);
|
SH_REMOVE_HOOK(IServerGameClients, ClientPutInServer, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientPutInServer),
|
||||||
SH_REMOVE_HOOK(IServerGameClients, ClientPutInServer, globals::serverGameClients,
|
true);
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientPutInServer), true);
|
SH_REMOVE_HOOK(IServerGameClients, ClientDisconnect, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientDisconnect),
|
||||||
SH_REMOVE_HOOK(IServerGameClients, ClientDisconnect, globals::serverGameClients,
|
false);
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientDisconnect), false);
|
|
||||||
SH_REMOVE_HOOK(IServerGameClients, ClientDisconnect, globals::serverGameClients,
|
SH_REMOVE_HOOK(IServerGameClients, ClientDisconnect, globals::serverGameClients,
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientDisconnect_Post), true);
|
SH_MEMBER(this, &PlayerManager::OnClientDisconnect_Post), true);
|
||||||
SH_REMOVE_HOOK(IServerGameClients, ClientCommand, globals::serverGameClients,
|
SH_REMOVE_HOOK(IServerGameClients, ClientCommand, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientCommand), false);
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientCommand), false);
|
SH_REMOVE_HOOK(IServerGameClients, ClientVoice, globals::serverGameClients, SH_MEMBER(this, &PlayerManager::OnClientVoice), true);
|
||||||
SH_REMOVE_HOOK(IServerGameClients, ClientVoice, globals::serverGameClients,
|
|
||||||
SH_MEMBER(this, &PlayerManager::OnClientVoice), true);
|
|
||||||
|
|
||||||
globals::callbackManager.ReleaseCallback(m_on_client_connect_callback);
|
globals::callbackManager.ReleaseCallback(m_on_client_connect_callback);
|
||||||
globals::callbackManager.ReleaseCallback(m_on_client_connected_callback);
|
globals::callbackManager.ReleaseCallback(m_on_client_connected_callback);
|
||||||
@@ -118,21 +105,18 @@ void PlayerManager::OnShutdown()
|
|||||||
globals::callbackManager.ReleaseCallback(m_on_client_voice_callback);
|
globals::callbackManager.ReleaseCallback(m_on_client_voice_callback);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool PlayerManager::OnClientConnect(CPlayerSlot slot, const char* pszName, uint64 xuid,
|
bool PlayerManager::OnClientConnect(
|
||||||
const char* pszNetworkID, bool unk1,
|
CPlayerSlot slot, const char* pszName, uint64 xuid, const char* pszNetworkID, bool unk1, CBufferString* pRejectReason)
|
||||||
CBufferString* pRejectReason)
|
|
||||||
{
|
{
|
||||||
CSSHARP_CORE_TRACE("[PlayerManager][OnClientConnect] - {}, {}, {}", slot.Get(), pszName,
|
CSSHARP_CORE_TRACE("[PlayerManager][OnClientConnect] - {}, {}, {}", slot.Get(), pszName, pszNetworkID);
|
||||||
pszNetworkID);
|
|
||||||
|
|
||||||
int client = slot.Get();
|
int client = slot.Get();
|
||||||
CPlayer* pPlayer = &m_players[client];
|
CPlayer* pPlayer = &m_players[client];
|
||||||
|
|
||||||
if (pPlayer->IsConnected()) {
|
if (pPlayer->IsConnected())
|
||||||
OnClientDisconnect(slot, ENetworkDisconnectionReason::NETWORK_DISCONNECT_INVALID, pszName,
|
{
|
||||||
xuid, pszNetworkID);
|
OnClientDisconnect(slot, ENetworkDisconnectionReason::NETWORK_DISCONNECT_INVALID, pszName, xuid, pszNetworkID);
|
||||||
OnClientDisconnect_Post(slot, ENetworkDisconnectionReason::NETWORK_DISCONNECT_INVALID,
|
OnClientDisconnect_Post(slot, ENetworkDisconnectionReason::NETWORK_DISCONNECT_INVALID, pszName, xuid, pszNetworkID);
|
||||||
pszName, xuid, pszNetworkID);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pPlayer->Initialize(pszName, pszNetworkID, slot);
|
pPlayer->Initialize(pszName, pszNetworkID, slot);
|
||||||
@@ -143,7 +127,8 @@ bool PlayerManager::OnClientConnect(CPlayerSlot slot, const char* pszName, uint6
|
|||||||
m_on_client_connect_callback->ScriptContext().Push(pszNetworkID);
|
m_on_client_connect_callback->ScriptContext().Push(pszNetworkID);
|
||||||
m_on_client_connect_callback->Execute();
|
m_on_client_connect_callback->Execute();
|
||||||
|
|
||||||
if (m_on_client_connect_callback->GetFunctionCount() > 0) {
|
if (m_on_client_connect_callback->GetFunctionCount() > 0)
|
||||||
|
{
|
||||||
// auto cancel = m_on_client_connect_callback->ScriptContext().GetArgument<bool>(0);
|
// auto cancel = m_on_client_connect_callback->ScriptContext().GetArgument<bool>(0);
|
||||||
// auto cancelReason =
|
// auto cancelReason =
|
||||||
// m_on_client_connect_callback->ScriptContext().GetArgument<const char *>(1);
|
// m_on_client_connect_callback->ScriptContext().GetArgument<const char *>(1);
|
||||||
@@ -167,47 +152,47 @@ bool PlayerManager::OnClientConnect(CPlayerSlot slot, const char* pszName, uint6
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool PlayerManager::OnClientConnect_Post(CPlayerSlot slot, const char* pszName, uint64 xuid,
|
bool PlayerManager::OnClientConnect_Post(
|
||||||
const char* pszNetworkID, bool unk1,
|
CPlayerSlot slot, const char* pszName, uint64 xuid, const char* pszNetworkID, bool unk1, CBufferString* pRejectReason)
|
||||||
CBufferString* pRejectReason)
|
|
||||||
{
|
{
|
||||||
CSSHARP_CORE_TRACE("[PlayerManager][OnClientConnect_Post] - {}, {}, {}", slot.Get(), pszName,
|
CSSHARP_CORE_TRACE("[PlayerManager][OnClientConnect_Post] - {}, {}, {}", slot.Get(), pszName, pszNetworkID);
|
||||||
pszNetworkID);
|
|
||||||
|
|
||||||
int client = slot.Get();
|
int client = slot.Get();
|
||||||
bool orig_value = META_RESULT_ORIG_RET(bool);
|
bool orig_value = META_RESULT_ORIG_RET(bool);
|
||||||
CPlayer* pPlayer = &m_players[client];
|
CPlayer* pPlayer = &m_players[client];
|
||||||
|
|
||||||
if (orig_value) {
|
if (orig_value)
|
||||||
|
{
|
||||||
m_on_client_connected_callback->ScriptContext().Reset();
|
m_on_client_connected_callback->ScriptContext().Reset();
|
||||||
m_on_client_connected_callback->ScriptContext().Push(pPlayer->m_slot.Get());
|
m_on_client_connected_callback->ScriptContext().Push(pPlayer->m_slot.Get());
|
||||||
m_on_client_connected_callback->Execute();
|
m_on_client_connected_callback->Execute();
|
||||||
|
|
||||||
if (!pPlayer->IsFakeClient() && m_is_listen_server &&
|
if (!pPlayer->IsFakeClient() && m_is_listen_server && strncmp(pszNetworkID, "127.0.0.1", 9) == 0)
|
||||||
strncmp(pszNetworkID, "127.0.0.1", 9) == 0) {
|
{
|
||||||
m_listen_client = client;
|
m_listen_client = client;
|
||||||
}
|
}
|
||||||
} else {
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
InvalidatePlayer(pPlayer);
|
InvalidatePlayer(pPlayer);
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void PlayerManager::OnClientPutInServer(CPlayerSlot slot, char const* pszName, int type,
|
void PlayerManager::OnClientPutInServer(CPlayerSlot slot, char const* pszName, int type, uint64 xuid)
|
||||||
uint64 xuid)
|
|
||||||
{
|
{
|
||||||
CSSHARP_CORE_TRACE("[PlayerManager][OnClientPutInServer] - {}, {}, {}", slot.Get(), pszName,
|
CSSHARP_CORE_TRACE("[PlayerManager][OnClientPutInServer] - {}, {}, {}", slot.Get(), pszName, type);
|
||||||
type);
|
|
||||||
|
|
||||||
int client = slot.Get();
|
int client = slot.Get();
|
||||||
CPlayer* pPlayer = &m_players[client];
|
CPlayer* pPlayer = &m_players[client];
|
||||||
|
|
||||||
if (!pPlayer->IsConnected()) {
|
if (!pPlayer->IsConnected())
|
||||||
|
{
|
||||||
pPlayer->m_is_fake_client = true;
|
pPlayer->m_is_fake_client = true;
|
||||||
|
|
||||||
if (!OnClientConnect(slot, pszName, 0, "127.0.0.1", false,
|
if (!OnClientConnect(slot, pszName, 0, "127.0.0.1", false, new CBufferStringGrowable<255>()))
|
||||||
new CBufferStringGrowable<255>())) {
|
{
|
||||||
/* :TODO: kick the bot if it's rejected */
|
/* :TODO: kick the bot if it's rejected */
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -233,39 +218,39 @@ void PlayerManager::OnClientPutInServer(CPlayerSlot slot, char const* pszName, i
|
|||||||
m_on_client_put_in_server_callback->Execute();
|
m_on_client_put_in_server_callback->Execute();
|
||||||
}
|
}
|
||||||
|
|
||||||
void PlayerManager::OnClientDisconnect(CPlayerSlot slot, ENetworkDisconnectionReason reason,
|
void PlayerManager::OnClientDisconnect(
|
||||||
const char* pszName, uint64 xuid, const char* pszNetworkID)
|
CPlayerSlot slot, ENetworkDisconnectionReason reason, const char* pszName, uint64 xuid, const char* pszNetworkID)
|
||||||
{
|
{
|
||||||
CSSHARP_CORE_TRACE("[PlayerManager][OnClientDisconnect] - {}, {}, {}", slot.Get(), pszName,
|
CSSHARP_CORE_TRACE("[PlayerManager][OnClientDisconnect] - {}, {}, {}", slot.Get(), pszName, pszNetworkID);
|
||||||
pszNetworkID);
|
|
||||||
|
|
||||||
int client = slot.Get();
|
int client = slot.Get();
|
||||||
CPlayer* pPlayer = &m_players[client];
|
CPlayer* pPlayer = &m_players[client];
|
||||||
|
|
||||||
if (pPlayer->IsConnected()) {
|
if (pPlayer->IsConnected())
|
||||||
|
{
|
||||||
m_on_client_disconnect_callback->ScriptContext().Reset();
|
m_on_client_disconnect_callback->ScriptContext().Reset();
|
||||||
m_on_client_disconnect_callback->ScriptContext().Push(pPlayer->m_slot.Get());
|
m_on_client_disconnect_callback->ScriptContext().Push(pPlayer->m_slot.Get());
|
||||||
m_on_client_disconnect_callback->ScriptContext().Push(reason);
|
m_on_client_disconnect_callback->ScriptContext().Push(reason);
|
||||||
m_on_client_disconnect_callback->Execute();
|
m_on_client_disconnect_callback->Execute();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pPlayer->WasCountedAsInGame()) {
|
if (pPlayer->WasCountedAsInGame())
|
||||||
|
{
|
||||||
m_player_count--;
|
m_player_count--;
|
||||||
}
|
}
|
||||||
|
|
||||||
// globals::entityListener.HandleEntityDeleted(pPlayer->GetBaseEntity(), client);
|
// globals::entityListener.HandleEntityDeleted(pPlayer->GetBaseEntity(), client);
|
||||||
}
|
}
|
||||||
|
|
||||||
void PlayerManager::OnClientDisconnect_Post(CPlayerSlot slot, ENetworkDisconnectionReason reason,
|
void PlayerManager::OnClientDisconnect_Post(
|
||||||
const char* pszName, uint64 xuid,
|
CPlayerSlot slot, ENetworkDisconnectionReason reason, const char* pszName, uint64 xuid, const char* pszNetworkID) const
|
||||||
const char* pszNetworkID) const
|
|
||||||
{
|
{
|
||||||
CSSHARP_CORE_TRACE("[PlayerManager][OnClientDisconnect_Post] - {}, {}, {}", slot.Get(), pszName,
|
CSSHARP_CORE_TRACE("[PlayerManager][OnClientDisconnect_Post] - {}, {}, {}", slot.Get(), pszName, pszNetworkID);
|
||||||
pszNetworkID);
|
|
||||||
|
|
||||||
int client = slot.Get();
|
int client = slot.Get();
|
||||||
CPlayer* pPlayer = &m_players[client];
|
CPlayer* pPlayer = &m_players[client];
|
||||||
if (!pPlayer->IsConnected()) {
|
if (!pPlayer->IsConnected())
|
||||||
|
{
|
||||||
/* We don't care, prevent a double call */
|
/* We don't care, prevent a double call */
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -291,14 +276,14 @@ void PlayerManager::OnLevelEnd()
|
|||||||
{
|
{
|
||||||
CSSHARP_CORE_TRACE("[PlayerManager][OnLevelEnd]");
|
CSSHARP_CORE_TRACE("[PlayerManager][OnLevelEnd]");
|
||||||
|
|
||||||
for (int i = 0; i <= MaxClients(); i++) {
|
for (int i = 0; i <= MaxClients(); i++)
|
||||||
if (m_players[i].IsConnected()) {
|
{
|
||||||
OnClientDisconnect(m_players[i].m_slot,
|
if (m_players[i].IsConnected())
|
||||||
ENetworkDisconnectionReason::NETWORK_DISCONNECT_INVALID,
|
{
|
||||||
m_players[i].GetName(), 0, m_players[i].GetIpAddress());
|
OnClientDisconnect(m_players[i].m_slot, ENetworkDisconnectionReason::NETWORK_DISCONNECT_INVALID, m_players[i].GetName(), 0,
|
||||||
OnClientDisconnect_Post(m_players[i].m_slot,
|
m_players[i].GetIpAddress());
|
||||||
ENetworkDisconnectionReason::NETWORK_DISCONNECT_INVALID,
|
OnClientDisconnect_Post(m_players[i].m_slot, ENetworkDisconnectionReason::NETWORK_DISCONNECT_INVALID, m_players[i].GetName(), 0,
|
||||||
m_players[i].GetName(), 0, m_players[i].GetIpAddress());
|
m_players[i].GetIpAddress());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
m_player_count = 0;
|
m_player_count = 0;
|
||||||
@@ -306,17 +291,17 @@ void PlayerManager::OnLevelEnd()
|
|||||||
|
|
||||||
void PlayerManager::OnClientCommand(CPlayerSlot slot, const CCommand& args) const
|
void PlayerManager::OnClientCommand(CPlayerSlot slot, const CCommand& args) const
|
||||||
{
|
{
|
||||||
CSSHARP_CORE_TRACE("[PlayerManager][OnClientCommand] - {}, {}, {}", slot.Get(), args.Arg(0),
|
CSSHARP_CORE_TRACE("[PlayerManager][OnClientCommand] - {}, {}, {}", slot.Get(), args.Arg(0), (void*)&args);
|
||||||
(void*)&args);
|
|
||||||
|
|
||||||
const char* cmd = args.Arg(0);
|
const char* cmd = args.Arg(0);
|
||||||
|
|
||||||
globals::voiceManager.OnClientCommand(slot, args);
|
globals::voiceManager.OnClientCommand(slot, args);
|
||||||
|
|
||||||
auto result = globals::conCommandManager.ExecuteCommandCallbacks(
|
auto result = globals::conCommandManager.ExecuteCommandCallbacks(cmd, CCommandContext(CommandTarget_t::CT_NO_TARGET, slot), args,
|
||||||
cmd, CCommandContext(CommandTarget_t::CT_NO_TARGET, slot), args, HookMode::Pre, CommandCallingContext::Console);
|
HookMode::Pre, CommandCallingContext::Console);
|
||||||
|
|
||||||
if (result >= HookResult::Handled) {
|
if (result >= HookResult::Handled)
|
||||||
|
{
|
||||||
RETURN_META(MRES_SUPERCEDE);
|
RETURN_META(MRES_SUPERCEDE);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -329,7 +314,8 @@ int PlayerManager::MaxClients() const { return globals::getGlobalVars()->maxClie
|
|||||||
|
|
||||||
CPlayer* PlayerManager::GetPlayerBySlot(int client) const
|
CPlayer* PlayerManager::GetPlayerBySlot(int client) const
|
||||||
{
|
{
|
||||||
if (client > MaxClients() || client < 0) {
|
if (client > MaxClients() || client < 0)
|
||||||
|
{
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -378,8 +364,7 @@ CPlayer* PlayerManager::GetPlayerBySlot(int client) const
|
|||||||
void PlayerManager::InvalidatePlayer(CPlayer* pPlayer) const
|
void PlayerManager::InvalidatePlayer(CPlayer* pPlayer) const
|
||||||
{
|
{
|
||||||
auto userid = globals::engine->GetPlayerUserId(pPlayer->m_slot);
|
auto userid = globals::engine->GetPlayerUserId(pPlayer->m_slot);
|
||||||
if (userid.Get() != -1)
|
if (userid.Get() != -1) m_user_id_lookup[userid.Get()] = 0;
|
||||||
m_user_id_lookup[userid.Get()] = 0;
|
|
||||||
|
|
||||||
pPlayer->Disconnect();
|
pPlayer->Disconnect();
|
||||||
}
|
}
|
||||||
@@ -406,7 +391,8 @@ bool CPlayer::IsAuthorized() const { return m_is_authorized; }
|
|||||||
|
|
||||||
bool CPlayer::IsAuthStringValidated() const
|
bool CPlayer::IsAuthStringValidated() const
|
||||||
{
|
{
|
||||||
if (!IsFakeClient()) {
|
if (!IsFakeClient())
|
||||||
|
{
|
||||||
return globals::engine->IsClientFullyAuthenticated(m_slot);
|
return globals::engine->IsClientFullyAuthenticated(m_slot);
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
@@ -416,12 +402,14 @@ void CPlayer::Authorize() { m_is_authorized = true; }
|
|||||||
|
|
||||||
void CPlayer::PrintToConsole(const char* message) const
|
void CPlayer::PrintToConsole(const char* message) const
|
||||||
{
|
{
|
||||||
if (m_is_connected == false || m_is_fake_client == true) {
|
if (m_is_connected == false || m_is_fake_client == true)
|
||||||
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
INetChannelInfo* pNetChan = globals::engine->GetPlayerNetInfo(m_slot);
|
INetChannelInfo* pNetChan = globals::engine->GetPlayerNetInfo(m_slot);
|
||||||
if (pNetChan == nullptr) {
|
if (pNetChan == nullptr)
|
||||||
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -457,18 +445,21 @@ PlayerManager::PlayerManager()
|
|||||||
|
|
||||||
void PlayerManager::RunAuthChecks()
|
void PlayerManager::RunAuthChecks()
|
||||||
{
|
{
|
||||||
if (globals::timerSystem.GetTickedTime() - m_last_auth_check_time < 0.5F) {
|
if (globals::timerSystem.GetTickedTime() - m_last_auth_check_time < 0.5F)
|
||||||
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
m_last_auth_check_time = globals::timerSystem.GetTickedTime();
|
m_last_auth_check_time = globals::timerSystem.GetTickedTime();
|
||||||
|
|
||||||
for (int i = 0; i <= MaxClients(); i++) {
|
for (int i = 0; i <= MaxClients(); i++)
|
||||||
if (m_players[i].IsConnected()) {
|
{
|
||||||
if (m_players[i].IsAuthorized() || m_players[i].IsFakeClient())
|
if (m_players[i].IsConnected())
|
||||||
continue;
|
{
|
||||||
|
if (m_players[i].IsAuthorized() || m_players[i].IsFakeClient()) continue;
|
||||||
|
|
||||||
if (globals::engine->IsClientFullyAuthenticated(i)) {
|
if (globals::engine->IsClientFullyAuthenticated(i))
|
||||||
|
{
|
||||||
m_players[i].Authorize();
|
m_players[i].Authorize();
|
||||||
m_players[i].SetSteamId(globals::engine->GetClientSteamID(i));
|
m_players[i].SetSteamId(globals::engine->GetClientSteamID(i));
|
||||||
OnAuthorized(&m_players[i]);
|
OnAuthorized(&m_players[i]);
|
||||||
@@ -479,8 +470,7 @@ void PlayerManager::RunAuthChecks()
|
|||||||
|
|
||||||
void PlayerManager::OnAuthorized(CPlayer* player) const
|
void PlayerManager::OnAuthorized(CPlayer* player) const
|
||||||
{
|
{
|
||||||
CSSHARP_CORE_TRACE("[PlayerManager][OnAuthorized] - {} {}", player->GetName(),
|
CSSHARP_CORE_TRACE("[PlayerManager][OnAuthorized] - {} {}", player->GetName(), player->GetSteamId()->ConvertToUint64());
|
||||||
player->GetSteamId()->ConvertToUint64());
|
|
||||||
|
|
||||||
m_on_client_authorized_callback->ScriptContext().Reset();
|
m_on_client_authorized_callback->ScriptContext().Reset();
|
||||||
m_on_client_authorized_callback->ScriptContext().Push(player->m_slot.Get());
|
m_on_client_authorized_callback->ScriptContext().Push(player->m_slot.Get());
|
||||||
@@ -492,7 +482,8 @@ bool CPlayer::WasCountedAsInGame() const { return m_is_in_game; }
|
|||||||
|
|
||||||
int CPlayer::GetUserId()
|
int CPlayer::GetUserId()
|
||||||
{
|
{
|
||||||
if (m_user_id == -1) {
|
if (m_user_id == -1)
|
||||||
|
{
|
||||||
m_user_id = globals::engine->GetPlayerUserId(m_slot).Get();
|
m_user_id = globals::engine->GetPlayerUserId(m_slot).Get();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -523,10 +514,7 @@ int CPlayer::GetFrags() const { return m_info->GetFragCount(); }
|
|||||||
|
|
||||||
int CPlayer::GetDeaths() const { return m_info->GetDeathCount(); }
|
int CPlayer::GetDeaths() const { return m_info->GetDeathCount(); }
|
||||||
|
|
||||||
const char* CPlayer::GetKeyValue(const char* key) const
|
const char* CPlayer::GetKeyValue(const char* key) const { return globals::engine->GetClientConVarValue(m_slot, key); }
|
||||||
{
|
|
||||||
return globals::engine->GetClientConVarValue(m_slot, key);
|
|
||||||
}
|
|
||||||
|
|
||||||
Vector CPlayer::GetMaxSize() const { return m_info->GetPlayerMaxs(); }
|
Vector CPlayer::GetMaxSize() const { return m_info->GetPlayerMaxs(); }
|
||||||
|
|
||||||
@@ -542,17 +530,15 @@ int CPlayer::GetUserId() const { return m_user_id; }
|
|||||||
|
|
||||||
float CPlayer::GetTimeConnected() const
|
float CPlayer::GetTimeConnected() const
|
||||||
{
|
{
|
||||||
if (!IsConnected() || IsFakeClient()) {
|
if (!IsConnected() || IsFakeClient())
|
||||||
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
return GetNetInfo()->GetTimeConnected();
|
return GetNetInfo()->GetTimeConnected();
|
||||||
}
|
}
|
||||||
|
|
||||||
void CPlayer::SetListen(CPlayerSlot slot, ListenOverride listen)
|
void CPlayer::SetListen(CPlayerSlot slot, ListenOverride listen) { m_listenMap[slot.Get()] = listen; }
|
||||||
{
|
|
||||||
m_listenMap[slot.Get()] = listen;
|
|
||||||
}
|
|
||||||
|
|
||||||
void CPlayer::SetVoiceFlags(VoiceFlag_t flags) { m_voiceFlag = flags; }
|
void CPlayer::SetVoiceFlags(VoiceFlag_t flags) { m_voiceFlag = flags; }
|
||||||
|
|
||||||
@@ -562,7 +548,8 @@ ListenOverride CPlayer::GetListen(CPlayerSlot slot) const { return m_listenMap[s
|
|||||||
|
|
||||||
void CPlayer::Connect()
|
void CPlayer::Connect()
|
||||||
{
|
{
|
||||||
if (m_is_in_game) {
|
if (m_is_in_game)
|
||||||
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -590,7 +577,8 @@ Vector CPlayer::GetAbsOrigin() const { return m_info->GetAbsOrigin(); }
|
|||||||
|
|
||||||
bool CPlayer::IsAlive() const
|
bool CPlayer::IsAlive() const
|
||||||
{
|
{
|
||||||
if (!IsInGame()) {
|
if (!IsInGame())
|
||||||
|
{
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -599,4 +587,4 @@ bool CPlayer::IsAlive() const
|
|||||||
const CSteamID* CPlayer::GetSteamId() { return m_steamId; }
|
const CSteamID* CPlayer::GetSteamId() { return m_steamId; }
|
||||||
void CPlayer::SetSteamId(const CSteamID* steam_id) { m_steamId = steam_id; }
|
void CPlayer::SetSteamId(const CSteamID* steam_id) { m_steamId = steam_id; }
|
||||||
|
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -143,15 +143,15 @@ class PlayerManager : public GlobalClass
|
|||||||
PlayerManager();
|
PlayerManager();
|
||||||
void OnStartup() override;
|
void OnStartup() override;
|
||||||
void OnAllInitialized() override;
|
void OnAllInitialized() override;
|
||||||
bool OnClientConnect(CPlayerSlot slot, const char* pszName, uint64 xuid,
|
bool
|
||||||
const char* pszNetworkID, bool unk1, CBufferString* pRejectReason);
|
OnClientConnect(CPlayerSlot slot, const char* pszName, uint64 xuid, const char* pszNetworkID, bool unk1, CBufferString* pRejectReason);
|
||||||
bool OnClientConnect_Post(CPlayerSlot slot, const char* pszName, uint64 xuid,
|
bool OnClientConnect_Post(
|
||||||
const char* pszNetworkID, bool unk1, CBufferString* pRejectReason);
|
CPlayerSlot slot, const char* pszName, uint64 xuid, const char* pszNetworkID, bool unk1, CBufferString* pRejectReason);
|
||||||
void OnClientPutInServer(CPlayerSlot slot, char const* pszName, int type, uint64 xuid);
|
void OnClientPutInServer(CPlayerSlot slot, char const* pszName, int type, uint64 xuid);
|
||||||
void OnClientDisconnect(CPlayerSlot slot, ENetworkDisconnectionReason reason,
|
void
|
||||||
const char* pszName, uint64 xuid, const char* pszNetworkID);
|
OnClientDisconnect(CPlayerSlot slot, ENetworkDisconnectionReason reason, const char* pszName, uint64 xuid, const char* pszNetworkID);
|
||||||
void OnClientDisconnect_Post(CPlayerSlot slot, ENetworkDisconnectionReason reason,
|
void OnClientDisconnect_Post(
|
||||||
const char* pszName, uint64 xuid, const char* pszNetworkID) const;
|
CPlayerSlot slot, ENetworkDisconnectionReason reason, const char* pszName, uint64 xuid, const char* pszNetworkID) const;
|
||||||
void OnClientVoice(CPlayerSlot slot) const;
|
void OnClientVoice(CPlayerSlot slot) const;
|
||||||
void OnAuthorized(CPlayer* player) const;
|
void OnAuthorized(CPlayer* player) const;
|
||||||
void OnServerActivate(edict_t* pEdictList, int edictCount, int clientMax) const;
|
void OnServerActivate(edict_t* pEdictList, int edictCount, int clientMax) const;
|
||||||
@@ -188,4 +188,4 @@ class PlayerManager : public GlobalClass
|
|||||||
ScriptCallback* m_on_client_authorized_callback;
|
ScriptCallback* m_on_client_authorized_callback;
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -1,18 +1,18 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of CounterStrikeSharp.
|
* This file is part of CounterStrikeSharp.
|
||||||
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
* (at your option) any later version.
|
* (at your option) any later version.
|
||||||
*
|
*
|
||||||
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
* GNU General Public License for more details.
|
* GNU General Public License for more details.
|
||||||
*
|
*
|
||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "core/managers/server_manager.h"
|
#include "core/managers/server_manager.h"
|
||||||
|
|
||||||
@@ -36,21 +36,17 @@ ServerManager::ServerManager() = default;
|
|||||||
|
|
||||||
ServerManager::~ServerManager() = default;
|
ServerManager::~ServerManager() = default;
|
||||||
|
|
||||||
void ServerManager::OnAllInitialized() {
|
void ServerManager::OnAllInitialized()
|
||||||
SH_ADD_HOOK(ISource2Server, ServerHibernationUpdate, globals::server,
|
{
|
||||||
SH_MEMBER(this, &ServerManager::ServerHibernationUpdate), true);
|
SH_ADD_HOOK(ISource2Server, ServerHibernationUpdate, globals::server, SH_MEMBER(this, &ServerManager::ServerHibernationUpdate), true);
|
||||||
SH_ADD_HOOK(ISource2Server, GameServerSteamAPIActivated, globals::server,
|
SH_ADD_HOOK(ISource2Server, GameServerSteamAPIActivated, globals::server, SH_MEMBER(this, &ServerManager::GameServerSteamAPIActivated),
|
||||||
SH_MEMBER(this, &ServerManager::GameServerSteamAPIActivated), true);
|
true);
|
||||||
SH_ADD_HOOK(ISource2Server, GameServerSteamAPIDeactivated, globals::server,
|
SH_ADD_HOOK(ISource2Server, GameServerSteamAPIDeactivated, globals::server,
|
||||||
SH_MEMBER(this, &ServerManager::GameServerSteamAPIDeactivated), true);
|
SH_MEMBER(this, &ServerManager::GameServerSteamAPIDeactivated), true);
|
||||||
SH_ADD_HOOK(ISource2Server, OnHostNameChanged, globals::server,
|
SH_ADD_HOOK(ISource2Server, OnHostNameChanged, globals::server, SH_MEMBER(this, &ServerManager::OnHostNameChanged), true);
|
||||||
SH_MEMBER(this, &ServerManager::OnHostNameChanged), true);
|
SH_ADD_HOOK(ISource2Server, PreFatalShutdown, globals::server, SH_MEMBER(this, &ServerManager::PreFatalShutdown), true);
|
||||||
SH_ADD_HOOK(ISource2Server, PreFatalShutdown, globals::server,
|
SH_ADD_HOOK(ISource2Server, UpdateWhenNotInGame, globals::server, SH_MEMBER(this, &ServerManager::UpdateWhenNotInGame), true);
|
||||||
SH_MEMBER(this, &ServerManager::PreFatalShutdown), true);
|
SH_ADD_HOOK(ISource2Server, PreWorldUpdate, globals::server, SH_MEMBER(this, &ServerManager::PreWorldUpdate), true);
|
||||||
SH_ADD_HOOK(ISource2Server, UpdateWhenNotInGame, globals::server,
|
|
||||||
SH_MEMBER(this, &ServerManager::UpdateWhenNotInGame), true);
|
|
||||||
SH_ADD_HOOK(ISource2Server, PreWorldUpdate, globals::server,
|
|
||||||
SH_MEMBER(this, &ServerManager::PreWorldUpdate), true);
|
|
||||||
|
|
||||||
on_server_hibernation_update_callback = globals::callbackManager.CreateCallback("OnServerHibernationUpdate");
|
on_server_hibernation_update_callback = globals::callbackManager.CreateCallback("OnServerHibernationUpdate");
|
||||||
on_server_steam_api_activated_callback = globals::callbackManager.CreateCallback("OnGameServerSteamAPIActivated");
|
on_server_steam_api_activated_callback = globals::callbackManager.CreateCallback("OnGameServerSteamAPIActivated");
|
||||||
@@ -63,21 +59,18 @@ void ServerManager::OnAllInitialized() {
|
|||||||
on_server_precache_resources = globals::callbackManager.CreateCallback("OnServerPrecacheResources");
|
on_server_precache_resources = globals::callbackManager.CreateCallback("OnServerPrecacheResources");
|
||||||
}
|
}
|
||||||
|
|
||||||
void ServerManager::OnShutdown() {
|
void ServerManager::OnShutdown()
|
||||||
SH_REMOVE_HOOK(ISource2Server, ServerHibernationUpdate, globals::server,
|
{
|
||||||
SH_MEMBER(this, &ServerManager::ServerHibernationUpdate), true);
|
SH_REMOVE_HOOK(ISource2Server, ServerHibernationUpdate, globals::server, SH_MEMBER(this, &ServerManager::ServerHibernationUpdate),
|
||||||
|
true);
|
||||||
SH_REMOVE_HOOK(ISource2Server, GameServerSteamAPIActivated, globals::server,
|
SH_REMOVE_HOOK(ISource2Server, GameServerSteamAPIActivated, globals::server,
|
||||||
SH_MEMBER(this, &ServerManager::GameServerSteamAPIActivated), true);
|
SH_MEMBER(this, &ServerManager::GameServerSteamAPIActivated), true);
|
||||||
SH_REMOVE_HOOK(ISource2Server, GameServerSteamAPIDeactivated, globals::server,
|
SH_REMOVE_HOOK(ISource2Server, GameServerSteamAPIDeactivated, globals::server,
|
||||||
SH_MEMBER(this, &ServerManager::GameServerSteamAPIDeactivated), true);
|
SH_MEMBER(this, &ServerManager::GameServerSteamAPIDeactivated), true);
|
||||||
SH_REMOVE_HOOK(ISource2Server, OnHostNameChanged, globals::server,
|
SH_REMOVE_HOOK(ISource2Server, OnHostNameChanged, globals::server, SH_MEMBER(this, &ServerManager::OnHostNameChanged), true);
|
||||||
SH_MEMBER(this, &ServerManager::OnHostNameChanged), true);
|
SH_REMOVE_HOOK(ISource2Server, PreFatalShutdown, globals::server, SH_MEMBER(this, &ServerManager::PreFatalShutdown), true);
|
||||||
SH_REMOVE_HOOK(ISource2Server, PreFatalShutdown, globals::server,
|
SH_REMOVE_HOOK(ISource2Server, UpdateWhenNotInGame, globals::server, SH_MEMBER(this, &ServerManager::UpdateWhenNotInGame), true);
|
||||||
SH_MEMBER(this, &ServerManager::PreFatalShutdown), true);
|
SH_REMOVE_HOOK(ISource2Server, PreWorldUpdate, globals::server, SH_MEMBER(this, &ServerManager::PreWorldUpdate), true);
|
||||||
SH_REMOVE_HOOK(ISource2Server, UpdateWhenNotInGame, globals::server,
|
|
||||||
SH_MEMBER(this, &ServerManager::UpdateWhenNotInGame), true);
|
|
||||||
SH_REMOVE_HOOK(ISource2Server, PreWorldUpdate, globals::server,
|
|
||||||
SH_MEMBER(this, &ServerManager::PreWorldUpdate), true);
|
|
||||||
|
|
||||||
globals::callbackManager.ReleaseCallback(on_server_hibernation_update_callback);
|
globals::callbackManager.ReleaseCallback(on_server_hibernation_update_callback);
|
||||||
globals::callbackManager.ReleaseCallback(on_server_steam_api_activated_callback);
|
globals::callbackManager.ReleaseCallback(on_server_steam_api_activated_callback);
|
||||||
@@ -86,19 +79,13 @@ void ServerManager::OnShutdown() {
|
|||||||
globals::callbackManager.ReleaseCallback(on_server_pre_fatal_shutdown);
|
globals::callbackManager.ReleaseCallback(on_server_pre_fatal_shutdown);
|
||||||
globals::callbackManager.ReleaseCallback(on_server_update_when_not_in_game);
|
globals::callbackManager.ReleaseCallback(on_server_update_when_not_in_game);
|
||||||
globals::callbackManager.ReleaseCallback(on_server_pre_world_update);
|
globals::callbackManager.ReleaseCallback(on_server_pre_world_update);
|
||||||
|
|
||||||
globals::callbackManager.ReleaseCallback(on_server_precache_resources);
|
globals::callbackManager.ReleaseCallback(on_server_precache_resources);
|
||||||
}
|
}
|
||||||
|
|
||||||
void* ServerManager::GetEconItemSystem()
|
void* ServerManager::GetEconItemSystem() { return globals::server->GetEconItemSystem(); }
|
||||||
{
|
|
||||||
return globals::server->GetEconItemSystem();
|
|
||||||
}
|
|
||||||
|
|
||||||
bool ServerManager::IsPaused()
|
bool ServerManager::IsPaused() { return globals::server->IsPaused(); }
|
||||||
{
|
|
||||||
return globals::server->IsPaused();
|
|
||||||
}
|
|
||||||
|
|
||||||
void ServerManager::ServerHibernationUpdate(bool bHibernating)
|
void ServerManager::ServerHibernationUpdate(bool bHibernating)
|
||||||
{
|
{
|
||||||
@@ -106,7 +93,8 @@ void ServerManager::ServerHibernationUpdate(bool bHibernating)
|
|||||||
|
|
||||||
auto callback = globals::serverManager.on_server_hibernation_update_callback;
|
auto callback = globals::serverManager.on_server_hibernation_update_callback;
|
||||||
|
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
callback->ScriptContext().Push(bHibernating);
|
callback->ScriptContext().Push(bHibernating);
|
||||||
callback->Execute();
|
callback->Execute();
|
||||||
@@ -119,7 +107,8 @@ void ServerManager::GameServerSteamAPIActivated()
|
|||||||
|
|
||||||
auto callback = globals::serverManager.on_server_steam_api_activated_callback;
|
auto callback = globals::serverManager.on_server_steam_api_activated_callback;
|
||||||
|
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
callback->Execute();
|
callback->Execute();
|
||||||
}
|
}
|
||||||
@@ -131,19 +120,21 @@ void ServerManager::GameServerSteamAPIDeactivated()
|
|||||||
|
|
||||||
auto callback = globals::serverManager.on_server_steam_api_deactivated_callback;
|
auto callback = globals::serverManager.on_server_steam_api_deactivated_callback;
|
||||||
|
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
callback->Execute();
|
callback->Execute();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ServerManager::OnHostNameChanged(const char *pHostname)
|
void ServerManager::OnHostNameChanged(const char* pHostname)
|
||||||
{
|
{
|
||||||
CSSHARP_CORE_TRACE("Server hostname changed {0}", pHostname);
|
CSSHARP_CORE_TRACE("Server hostname changed {0}", pHostname);
|
||||||
|
|
||||||
auto callback = globals::serverManager.on_server_hostname_changed_callback;
|
auto callback = globals::serverManager.on_server_hostname_changed_callback;
|
||||||
|
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
callback->ScriptContext().Push(pHostname);
|
callback->ScriptContext().Push(pHostname);
|
||||||
callback->Execute();
|
callback->Execute();
|
||||||
@@ -156,7 +147,8 @@ void ServerManager::PreFatalShutdown()
|
|||||||
|
|
||||||
auto callback = globals::serverManager.on_server_pre_fatal_shutdown;
|
auto callback = globals::serverManager.on_server_pre_fatal_shutdown;
|
||||||
|
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
callback->Execute();
|
callback->Execute();
|
||||||
}
|
}
|
||||||
@@ -168,7 +160,8 @@ void ServerManager::UpdateWhenNotInGame(float flFrameTime)
|
|||||||
|
|
||||||
auto callback = globals::serverManager.on_server_update_when_not_in_game;
|
auto callback = globals::serverManager.on_server_update_when_not_in_game;
|
||||||
|
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
callback->ScriptContext().Push(flFrameTime);
|
callback->ScriptContext().Push(flFrameTime);
|
||||||
callback->Execute();
|
callback->Execute();
|
||||||
@@ -181,18 +174,20 @@ void ServerManager::PreWorldUpdate(bool bSimulating)
|
|||||||
|
|
||||||
auto size = m_nextWorldUpdateTasks.try_dequeue_bulk(out_list.begin(), 1024);
|
auto size = m_nextWorldUpdateTasks.try_dequeue_bulk(out_list.begin(), 1024);
|
||||||
|
|
||||||
if (size > 0) {
|
if (size > 0)
|
||||||
CSSHARP_CORE_TRACE("Executing queued tasks of size: {0} at time {1}", size,
|
{
|
||||||
globals::getGlobalVars()->curtime);
|
CSSHARP_CORE_TRACE("Executing queued tasks of size: {0} at time {1}", size, globals::getGlobalVars()->curtime);
|
||||||
|
|
||||||
for (size_t i = 0; i < size; i++) {
|
for (size_t i = 0; i < size; i++)
|
||||||
|
{
|
||||||
out_list[i]();
|
out_list[i]();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
auto callback = globals::serverManager.on_server_pre_world_update;
|
auto callback = globals::serverManager.on_server_pre_world_update;
|
||||||
|
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
callback->ScriptContext().Push(bSimulating);
|
callback->ScriptContext().Push(bSimulating);
|
||||||
callback->Execute();
|
callback->Execute();
|
||||||
@@ -208,11 +203,12 @@ void ServerManager::OnPrecacheResources(IEntityResourceManifest* pResourceManife
|
|||||||
{
|
{
|
||||||
CSSHARP_CORE_TRACE("Precache resources");
|
CSSHARP_CORE_TRACE("Precache resources");
|
||||||
auto callback = globals::serverManager.on_server_precache_resources;
|
auto callback = globals::serverManager.on_server_precache_resources;
|
||||||
if (callback && callback->GetFunctionCount()) {
|
if (callback && callback->GetFunctionCount())
|
||||||
|
{
|
||||||
callback->ScriptContext().Reset();
|
callback->ScriptContext().Reset();
|
||||||
callback->ScriptContext().Push(pResourceManifest);
|
callback->ScriptContext().Push(pResourceManifest);
|
||||||
callback->Execute();
|
callback->Execute();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -1,18 +1,18 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of CounterStrikeSharp.
|
* This file is part of CounterStrikeSharp.
|
||||||
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
* (at your option) any later version.
|
* (at your option) any later version.
|
||||||
*
|
*
|
||||||
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
* GNU General Public License for more details.
|
* GNU General Public License for more details.
|
||||||
*
|
*
|
||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
@@ -26,8 +26,9 @@
|
|||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
class ScriptCallback;
|
class ScriptCallback;
|
||||||
|
|
||||||
class ServerManager : public GlobalClass {
|
class ServerManager : public GlobalClass
|
||||||
public:
|
{
|
||||||
|
public:
|
||||||
ServerManager();
|
ServerManager();
|
||||||
~ServerManager();
|
~ServerManager();
|
||||||
void OnAllInitialized() override;
|
void OnAllInitialized() override;
|
||||||
@@ -37,27 +38,26 @@ public:
|
|||||||
void AddTaskForNextWorldUpdate(std::function<void()>&& task);
|
void AddTaskForNextWorldUpdate(std::function<void()>&& task);
|
||||||
void OnPrecacheResources(IEntityResourceManifest* pResourceManifest);
|
void OnPrecacheResources(IEntityResourceManifest* pResourceManifest);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void ServerHibernationUpdate(bool bHibernating);
|
void ServerHibernationUpdate(bool bHibernating);
|
||||||
void GameServerSteamAPIActivated();
|
void GameServerSteamAPIActivated();
|
||||||
void GameServerSteamAPIDeactivated();
|
void GameServerSteamAPIDeactivated();
|
||||||
void OnHostNameChanged(const char *pHostname);
|
void OnHostNameChanged(const char* pHostname);
|
||||||
void PreFatalShutdown();
|
void PreFatalShutdown();
|
||||||
void UpdateWhenNotInGame(float flFrameTime);
|
void UpdateWhenNotInGame(float flFrameTime);
|
||||||
void PreWorldUpdate(bool bSimulating);
|
void PreWorldUpdate(bool bSimulating);
|
||||||
|
|
||||||
|
ScriptCallback* on_server_hibernation_update_callback;
|
||||||
|
ScriptCallback* on_server_steam_api_activated_callback;
|
||||||
|
ScriptCallback* on_server_steam_api_deactivated_callback;
|
||||||
|
ScriptCallback* on_server_hostname_changed_callback;
|
||||||
|
ScriptCallback* on_server_pre_fatal_shutdown;
|
||||||
|
ScriptCallback* on_server_update_when_not_in_game;
|
||||||
|
ScriptCallback* on_server_pre_world_update;
|
||||||
|
|
||||||
ScriptCallback *on_server_hibernation_update_callback;
|
ScriptCallback* on_server_precache_resources;
|
||||||
ScriptCallback *on_server_steam_api_activated_callback;
|
|
||||||
ScriptCallback *on_server_steam_api_deactivated_callback;
|
|
||||||
ScriptCallback *on_server_hostname_changed_callback;
|
|
||||||
ScriptCallback *on_server_pre_fatal_shutdown;
|
|
||||||
ScriptCallback *on_server_update_when_not_in_game;
|
|
||||||
ScriptCallback *on_server_pre_world_update;
|
|
||||||
|
|
||||||
ScriptCallback *on_server_precache_resources;
|
|
||||||
|
|
||||||
moodycamel::ConcurrentQueue<std::function<void()>> m_nextWorldUpdateTasks;
|
moodycamel::ConcurrentQueue<std::function<void()>> m_nextWorldUpdateTasks;
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -32,7 +32,8 @@ class VoiceManager : public GlobalClass
|
|||||||
void OnShutdown() override;
|
void OnShutdown() override;
|
||||||
bool SetClientListening(CPlayerSlot iReceiver, CPlayerSlot iSender, bool bListen);
|
bool SetClientListening(CPlayerSlot iReceiver, CPlayerSlot iSender, bool bListen);
|
||||||
void OnClientCommand(CPlayerSlot slot, const CCommand& args);
|
void OnClientCommand(CPlayerSlot slot, const CCommand& args);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -22,9 +22,11 @@
|
|||||||
#include "gameconfig.h"
|
#include "gameconfig.h"
|
||||||
#include "memory_module.h"
|
#include "memory_module.h"
|
||||||
|
|
||||||
void* FindSignature(const char* moduleName, const char* bytesStr) {
|
void* FindSignature(const char* moduleName, const char* bytesStr)
|
||||||
|
{
|
||||||
auto module = counterstrikesharp::modules::GetModuleByName(moduleName);
|
auto module = counterstrikesharp::modules::GetModuleByName(moduleName);
|
||||||
if (module == nullptr) {
|
if (module == nullptr)
|
||||||
|
{
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,15 +1,15 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
#define ROOTBIN "/bin/win64/"
|
#define ROOTBIN "/bin/win64/"
|
||||||
#define GAMEBIN "/csgo/bin/win64/"
|
#define GAMEBIN "/csgo/bin/win64/"
|
||||||
#define MODULE_PREFIX ""
|
#define MODULE_PREFIX ""
|
||||||
#define MODULE_EXT ".dll"
|
#define MODULE_EXT ".dll"
|
||||||
#else
|
#else
|
||||||
#define ROOTBIN "/bin/linuxsteamrt64/"
|
#define ROOTBIN "/bin/linuxsteamrt64/"
|
||||||
#define GAMEBIN "/csgo/bin/linuxsteamrt64/"
|
#define GAMEBIN "/csgo/bin/linuxsteamrt64/"
|
||||||
#define MODULE_PREFIX "lib"
|
#define MODULE_PREFIX "lib"
|
||||||
#define MODULE_EXT ".so"
|
#define MODULE_EXT ".so"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
void* FindSignature(const char* moduleName, const char* bytesStr);
|
void* FindSignature(const char* moduleName, const char* bytesStr);
|
||||||
|
|||||||
@@ -63,8 +63,7 @@ void Initialize()
|
|||||||
moduleList.emplace_back(std::move(mod));
|
moduleList.emplace_back(std::move(mod));
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
dl_iterate_phdr(
|
dl_iterate_phdr([](struct dl_phdr_info* info, size_t, void*) {
|
||||||
[](struct dl_phdr_info* info, size_t, void*) {
|
|
||||||
std::string name = info->dlpi_name;
|
std::string name = info->dlpi_name;
|
||||||
|
|
||||||
if (name.rfind(MODULE_EXT) != name.length() - strlen(MODULE_EXT)) return 0;
|
if (name.rfind(MODULE_EXT) != name.length() - strlen(MODULE_EXT)) return 0;
|
||||||
@@ -80,8 +79,7 @@ void Initialize()
|
|||||||
|
|
||||||
moduleList.emplace_back(std::move(mod));
|
moduleList.emplace_back(std::move(mod));
|
||||||
return 0;
|
return 0;
|
||||||
},
|
}, nullptr);
|
||||||
nullptr);
|
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -77,8 +77,8 @@ class CModule
|
|||||||
std::uintptr_t m_baseAddress{};
|
std::uintptr_t m_baseAddress{};
|
||||||
std::unordered_map<std::string, std::uintptr_t> _symbols{};
|
std::unordered_map<std::string, std::uintptr_t> _symbols{};
|
||||||
std::unordered_map<std::string, std::uintptr_t> _interfaces{};
|
std::unordered_map<std::string, std::uintptr_t> _interfaces{};
|
||||||
using fnCreateInterface = void*(*)(const char*);
|
using fnCreateInterface = void* (*)(const char*);
|
||||||
fnCreateInterface m_fnCreateInterface {};
|
fnCreateInterface m_fnCreateInterface{};
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
void DumpSymbols();
|
void DumpSymbols();
|
||||||
@@ -86,7 +86,8 @@ class CModule
|
|||||||
void DumpSymbols(ElfW(Dyn) * dyn);
|
void DumpSymbols(ElfW(Dyn) * dyn);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
std::optional<std::vector<std::uint8_t>> GetOriginalBytes(const std::vector<std::uint8_t>& disk_data, std::uintptr_t rva, std::size_t size);
|
std::optional<std::vector<std::uint8_t>>
|
||||||
|
GetOriginalBytes(const std::vector<std::uint8_t>& disk_data, std::uintptr_t rva, std::size_t size);
|
||||||
|
|
||||||
void* FindSignature(const std::vector<int16_t>& sigBytes);
|
void* FindSignature(const std::vector<int16_t>& sigBytes);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,84 +1,84 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of CounterStrikeSharp.
|
* This file is part of CounterStrikeSharp.
|
||||||
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
* (at your option) any later version.
|
* (at your option) any later version.
|
||||||
*
|
*
|
||||||
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
* GNU General Public License for more details.
|
* GNU General Public License for more details.
|
||||||
*
|
*
|
||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "irecipientfilter.h"
|
#include "irecipientfilter.h"
|
||||||
|
|
||||||
class CSingleRecipientFilter : public IRecipientFilter
|
class CSingleRecipientFilter : public IRecipientFilter
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
CSingleRecipientFilter(CPlayerSlot iRecipient, NetChannelBufType_t nBufType = BUF_RELIABLE, bool bInitMessage = false)
|
CSingleRecipientFilter(CPlayerSlot iRecipient, NetChannelBufType_t nBufType = BUF_RELIABLE, bool bInitMessage = false)
|
||||||
: m_iRecipient(iRecipient), m_nBufType(nBufType), m_bInitMessage(bInitMessage)
|
: m_iRecipient(iRecipient), m_nBufType(nBufType), m_bInitMessage(bInitMessage)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
~CSingleRecipientFilter() override {}
|
~CSingleRecipientFilter() override {}
|
||||||
|
|
||||||
NetChannelBufType_t GetNetworkBufType(void) const override { return m_nBufType; }
|
NetChannelBufType_t GetNetworkBufType(void) const override { return m_nBufType; }
|
||||||
bool IsInitMessage(void) const override { return m_bInitMessage; }
|
bool IsInitMessage(void) const override { return m_bInitMessage; }
|
||||||
int GetRecipientCount(void) const override { return 1; }
|
int GetRecipientCount(void) const override { return 1; }
|
||||||
CPlayerSlot GetRecipientIndex(int slot) const override { return m_iRecipient; }
|
CPlayerSlot GetRecipientIndex(int slot) const override { return m_iRecipient; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
CPlayerSlot m_iRecipient;
|
CPlayerSlot m_iRecipient;
|
||||||
NetChannelBufType_t m_nBufType;
|
NetChannelBufType_t m_nBufType;
|
||||||
bool m_bInitMessage;
|
bool m_bInitMessage;
|
||||||
};
|
};
|
||||||
|
|
||||||
class CRecipientFilter : public IRecipientFilter
|
class CRecipientFilter : public IRecipientFilter
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
CRecipientFilter()
|
CRecipientFilter()
|
||||||
{
|
{
|
||||||
m_nBufType = BUF_RELIABLE;
|
m_nBufType = BUF_RELIABLE;
|
||||||
m_bInitMessage = false;
|
m_bInitMessage = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
~CRecipientFilter() override {}
|
~CRecipientFilter() override {}
|
||||||
|
|
||||||
NetChannelBufType_t GetNetworkBufType(void) const override { return m_nBufType; }
|
NetChannelBufType_t GetNetworkBufType(void) const override { return m_nBufType; }
|
||||||
bool IsInitMessage(void) const override { return m_bInitMessage; }
|
bool IsInitMessage(void) const override { return m_bInitMessage; }
|
||||||
int GetRecipientCount(void) const override { return m_Recipients.Count(); }
|
int GetRecipientCount(void) const override { return m_Recipients.Count(); }
|
||||||
|
|
||||||
CPlayerSlot GetRecipientIndex(int slot) const override
|
CPlayerSlot GetRecipientIndex(int slot) const override
|
||||||
{
|
{
|
||||||
if (slot < 0 || slot >= GetRecipientCount()) return CPlayerSlot(-1);
|
if (slot < 0 || slot >= GetRecipientCount()) return CPlayerSlot(-1);
|
||||||
|
|
||||||
return m_Recipients[slot];
|
return m_Recipients[slot];
|
||||||
}
|
}
|
||||||
|
|
||||||
void AddRecipient(CPlayerSlot slot)
|
void AddRecipient(CPlayerSlot slot)
|
||||||
{
|
{
|
||||||
if (m_Recipients.Find(slot) != m_Recipients.InvalidIndex()) return;
|
if (m_Recipients.Find(slot) != m_Recipients.InvalidIndex()) return;
|
||||||
|
|
||||||
m_Recipients.AddToTail(slot);
|
m_Recipients.AddToTail(slot);
|
||||||
}
|
}
|
||||||
|
|
||||||
void AddRecipientsFromMask(uint64 mask)
|
void AddRecipientsFromMask(uint64 mask)
|
||||||
{
|
{
|
||||||
for (int i = 0; i < 64; ++i)
|
for (int i = 0; i < 64; ++i)
|
||||||
{
|
{
|
||||||
if (mask & (uint64)1 << i)
|
if (mask & (uint64)1 << i)
|
||||||
{
|
{
|
||||||
AddRecipient(CPlayerSlot(i));
|
AddRecipient(CPlayerSlot(i));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
NetChannelBufType_t m_nBufType;
|
NetChannelBufType_t m_nBufType;
|
||||||
bool m_bInitMessage;
|
bool m_bInitMessage;
|
||||||
CUtlVectorFixed<CPlayerSlot, 64> m_Recipients;
|
CUtlVectorFixed<CPlayerSlot, 64> m_Recipients;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,45 +1,47 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of CounterStrikeSharp.
|
* This file is part of CounterStrikeSharp.
|
||||||
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
* (at your option) any later version.
|
* (at your option) any later version.
|
||||||
*
|
*
|
||||||
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
* GNU General Public License for more details.
|
* GNU General Public License for more details.
|
||||||
*
|
*
|
||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "tick_scheduler.h"
|
#include "tick_scheduler.h"
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
|
|
||||||
void TickScheduler::schedule(int tick, std::function<void()> callback)
|
void TickScheduler::schedule(int tick, std::function<void()> callback)
|
||||||
{
|
{
|
||||||
std::lock_guard<std::mutex> lock(taskMutex);
|
std::lock_guard<std::mutex> lock(taskMutex);
|
||||||
scheduledTasks.push(std::make_pair(tick, callback));
|
scheduledTasks.push(std::make_pair(tick, callback));
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<std::function<void()>> TickScheduler::getCallbacks(int currentTick)
|
std::vector<std::function<void()>> TickScheduler::getCallbacks(int currentTick)
|
||||||
{
|
{
|
||||||
std::vector<std::function<void()>> callbacksToRun;
|
std::vector<std::function<void()>> callbacksToRun;
|
||||||
|
|
||||||
std::lock_guard<std::mutex> lock(taskMutex);
|
std::lock_guard<std::mutex> lock(taskMutex);
|
||||||
|
|
||||||
if (scheduledTasks.empty()) {
|
if (scheduledTasks.empty())
|
||||||
return callbacksToRun;
|
{
|
||||||
}
|
return callbacksToRun;
|
||||||
|
}
|
||||||
// Process tasks due for the current tick
|
|
||||||
while (!scheduledTasks.empty() && scheduledTasks.top().first <= currentTick) {
|
// Process tasks due for the current tick
|
||||||
callbacksToRun.push_back(scheduledTasks.top().second);
|
while (!scheduledTasks.empty() && scheduledTasks.top().first <= currentTick)
|
||||||
scheduledTasks.pop();
|
{
|
||||||
}
|
callbacksToRun.push_back(scheduledTasks.top().second);
|
||||||
|
scheduledTasks.pop();
|
||||||
return callbacksToRun;
|
}
|
||||||
}
|
|
||||||
} // namespace counterstrikesharp
|
return callbacksToRun;
|
||||||
|
}
|
||||||
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -1,44 +1,42 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of CounterStrikeSharp.
|
* This file is part of CounterStrikeSharp.
|
||||||
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
* (at your option) any later version.
|
* (at your option) any later version.
|
||||||
*
|
*
|
||||||
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
* GNU General Public License for more details.
|
* GNU General Public License for more details.
|
||||||
*
|
*
|
||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <functional>
|
#include <functional>
|
||||||
#include <queue>
|
#include <queue>
|
||||||
#include <mutex>
|
#include <mutex>
|
||||||
#include <condition_variable>
|
#include <condition_variable>
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
class TickScheduler
|
class TickScheduler
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
struct TaskComparator
|
struct TaskComparator
|
||||||
{
|
{
|
||||||
bool operator()(const std::pair<int, std::function<void()>>& a,
|
bool operator()(const std::pair<int, std::function<void()>>& a, const std::pair<int, std::function<void()>>& b) const
|
||||||
const std::pair<int, std::function<void()>>& b) const
|
{
|
||||||
{
|
return a.first > b.first;
|
||||||
return a.first > b.first;
|
}
|
||||||
}
|
};
|
||||||
};
|
|
||||||
|
void schedule(int tick, std::function<void()> callback);
|
||||||
void schedule(int tick, std::function<void()> callback);
|
std::vector<std::function<void()>> getCallbacks(int currentTick);
|
||||||
std::vector<std::function<void()>> getCallbacks(int currentTick);
|
|
||||||
private:
|
private:
|
||||||
std::priority_queue<std::pair<int, std::function<void()>>,
|
std::priority_queue<std::pair<int, std::function<void()>>, std::vector<std::pair<int, std::function<void()>>>, TaskComparator>
|
||||||
std::vector<std::pair<int, std::function<void()>>>,
|
scheduledTasks;
|
||||||
TaskComparator>
|
std::mutex taskMutex;
|
||||||
scheduledTasks;
|
};
|
||||||
std::mutex taskMutex;
|
} // namespace counterstrikesharp
|
||||||
};
|
|
||||||
} // namespace counterstrikesharp
|
|
||||||
|
|||||||
@@ -41,30 +41,32 @@ class TimerSystem;
|
|||||||
class ScriptCallback;
|
class ScriptCallback;
|
||||||
|
|
||||||
namespace timers {
|
namespace timers {
|
||||||
#define TIMER_FLAG_REPEAT (1 << 0) /**< Timer will repeat until stopped */
|
#define TIMER_FLAG_REPEAT (1 << 0) /**< Timer will repeat until stopped */
|
||||||
#define TIMER_FLAG_NO_MAPCHANGE (1 << 1) /**< Timer will not carry over mapchanges */
|
#define TIMER_FLAG_NO_MAPCHANGE (1 << 1) /**< Timer will not carry over mapchanges */
|
||||||
|
|
||||||
class Timer {
|
class Timer
|
||||||
|
{
|
||||||
friend class TimerSystem;
|
friend class TimerSystem;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
Timer(float interval, float exec_time, CallbackT callback, int flags);
|
Timer(float interval, float exec_time, CallbackT callback, int flags);
|
||||||
~Timer();
|
~Timer();
|
||||||
|
|
||||||
float m_interval;
|
float m_interval;
|
||||||
ScriptCallback *m_callback;
|
ScriptCallback* m_callback;
|
||||||
int m_flags;
|
int m_flags;
|
||||||
float m_exec_time;
|
float m_exec_time;
|
||||||
bool m_in_exec;
|
bool m_in_exec;
|
||||||
bool m_kill_me;
|
bool m_kill_me;
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace timers
|
} // namespace timers
|
||||||
|
|
||||||
class ScriptCallback;
|
class ScriptCallback;
|
||||||
|
|
||||||
class TimerSystem : public GlobalClass {
|
class TimerSystem : public GlobalClass
|
||||||
public:
|
{
|
||||||
|
public:
|
||||||
TimerSystem();
|
TimerSystem();
|
||||||
void OnAllInitialized() override;
|
void OnAllInitialized() override;
|
||||||
void OnShutdown() override;
|
void OnShutdown() override;
|
||||||
@@ -74,19 +76,18 @@ public:
|
|||||||
double CalculateNextThink(double last_think_time, float interval);
|
double CalculateNextThink(double last_think_time, float interval);
|
||||||
void RunFrame();
|
void RunFrame();
|
||||||
void RemoveMapChangeTimers();
|
void RemoveMapChangeTimers();
|
||||||
timers::Timer *CreateTimer(float interval, CallbackT callback, int flags);
|
timers::Timer* CreateTimer(float interval, CallbackT callback, int flags);
|
||||||
void KillTimer(timers::Timer *timer);
|
void KillTimer(timers::Timer* timer);
|
||||||
double GetTickedTime();
|
double GetTickedTime();
|
||||||
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
bool m_has_map_ticked = false;
|
bool m_has_map_ticked = false;
|
||||||
bool m_has_map_simulated = false;
|
bool m_has_map_simulated = false;
|
||||||
float m_last_ticked_time = 0.0f;
|
float m_last_ticked_time = 0.0f;
|
||||||
ScriptCallback *m_on_tick_callback_ = nullptr;
|
ScriptCallback* m_on_tick_callback_ = nullptr;
|
||||||
ScriptCallback *on_map_end_callback = nullptr;
|
ScriptCallback* on_map_end_callback = nullptr;
|
||||||
|
|
||||||
std::vector<timers::Timer *> m_once_off_timers;
|
std::vector<timers::Timer*> m_once_off_timers;
|
||||||
std::vector<timers::Timer *> m_repeat_timers;
|
std::vector<timers::Timer*> m_repeat_timers;
|
||||||
};
|
};
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -10,8 +10,10 @@ namespace utils {
|
|||||||
|
|
||||||
static std::string gameDirectory;
|
static std::string gameDirectory;
|
||||||
|
|
||||||
inline std::string GameDirectory() {
|
inline std::string GameDirectory()
|
||||||
if (gameDirectory.empty()) {
|
{
|
||||||
|
if (gameDirectory.empty())
|
||||||
|
{
|
||||||
CBufferStringGrowable<255> gamePath;
|
CBufferStringGrowable<255> gamePath;
|
||||||
globals::engine->GetGameDir(gamePath);
|
globals::engine->GetGameDir(gamePath);
|
||||||
gameDirectory = std::string(gamePath.Get());
|
gameDirectory = std::string(gamePath.Get());
|
||||||
@@ -25,5 +27,5 @@ inline std::string PluginsDirectory() { return GameDirectory() + "/addons/counte
|
|||||||
inline std::string ConfigsDirectory() { return GameDirectory() + "/addons/counterstrikesharp/configs"; }
|
inline std::string ConfigsDirectory() { return GameDirectory() + "/addons/counterstrikesharp/configs"; }
|
||||||
inline std::string GamedataDirectory() { return GameDirectory() + "/addons/counterstrikesharp/gamedata"; }
|
inline std::string GamedataDirectory() { return GameDirectory() + "/addons/counterstrikesharp/gamedata"; }
|
||||||
|
|
||||||
} // namespace utils
|
} // namespace utils
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -17,7 +17,6 @@
|
|||||||
#ifndef _INCLUDE_METAMOD_SOURCE_STUB_PLUGIN_H_
|
#ifndef _INCLUDE_METAMOD_SOURCE_STUB_PLUGIN_H_
|
||||||
#define _INCLUDE_METAMOD_SOURCE_STUB_PLUGIN_H_
|
#define _INCLUDE_METAMOD_SOURCE_STUB_PLUGIN_H_
|
||||||
|
|
||||||
// clang-format off
|
|
||||||
#include <ISmmPlugin.h>
|
#include <ISmmPlugin.h>
|
||||||
#include <functional>
|
#include <functional>
|
||||||
#include <iserver.h>
|
#include <iserver.h>
|
||||||
@@ -27,7 +26,6 @@
|
|||||||
#include <vector>
|
#include <vector>
|
||||||
#include "entitysystem.h"
|
#include "entitysystem.h"
|
||||||
#include "concurrentqueue.h"
|
#include "concurrentqueue.h"
|
||||||
// clang-format on
|
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
class ScriptCallback;
|
class ScriptCallback;
|
||||||
@@ -74,9 +72,7 @@ static ScriptCallback* on_activate_callback;
|
|||||||
static ScriptCallback* on_metamod_all_plugins_loaded_callback;
|
static ScriptCallback* on_metamod_all_plugins_loaded_callback;
|
||||||
extern CounterStrikeSharpMMPlugin gPlugin;
|
extern CounterStrikeSharpMMPlugin gPlugin;
|
||||||
|
|
||||||
|
|
||||||
#endif //_INCLUDE_METAMOD_SOURCE_STUB_PLUGIN_H_
|
#endif //_INCLUDE_METAMOD_SOURCE_STUB_PLUGIN_H_
|
||||||
}
|
}
|
||||||
|
|
||||||
PLUGIN_GLOBALVARS();
|
PLUGIN_GLOBALVARS();
|
||||||
|
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -20,29 +20,31 @@
|
|||||||
#include "core/globals.h"
|
#include "core/globals.h"
|
||||||
#include "scripting/script_engine.h"
|
#include "scripting/script_engine.h"
|
||||||
|
|
||||||
#define REGISTER_NATIVE(name, func) \
|
#define REGISTER_NATIVE(name, func) counterstrikesharp::ScriptEngine::RegisterNativeHandler(#name, func);
|
||||||
counterstrikesharp::ScriptEngine::RegisterNativeHandler(#name, func);
|
|
||||||
|
|
||||||
#define REGISTER_NATIVES(name, method) \
|
#define REGISTER_NATIVES(name, method) \
|
||||||
class Natives##name : public counterstrikesharp::GlobalClass { \
|
class Natives##name : public counterstrikesharp::GlobalClass \
|
||||||
public: \
|
{ \
|
||||||
void OnAllInitialized() override method \
|
public: \
|
||||||
}; \
|
void OnAllInitialized() override method \
|
||||||
\
|
}; \
|
||||||
|
\
|
||||||
Natives##name g_natives_##name;
|
Natives##name g_natives_##name;
|
||||||
|
|
||||||
#define CREATE_GETTER_FUNCTION(object_name, parameter_type, parameter_name, from_type, getter) \
|
#define CREATE_GETTER_FUNCTION(object_name, parameter_type, parameter_name, from_type, getter) \
|
||||||
static parameter_type object_name##Get##parameter_name(ScriptContext &script_context) { \
|
static parameter_type object_name##Get##parameter_name(ScriptContext& script_context) \
|
||||||
|
{ \
|
||||||
auto obj = script_context.GetArgument<from_type>(0); \
|
auto obj = script_context.GetArgument<from_type>(0); \
|
||||||
return getter; \
|
return getter; \
|
||||||
}
|
}
|
||||||
|
|
||||||
#define CREATE_STATIC_GETTER_FUNCTION(parameter_name, parameter_type, getter) \
|
#define CREATE_STATIC_GETTER_FUNCTION(parameter_name, parameter_type, getter) \
|
||||||
static parameter_type Get##parameter_name(ScriptContext &script_context) { return getter; }
|
static parameter_type Get##parameter_name(ScriptContext& script_context) { return getter; }
|
||||||
|
|
||||||
#define CREATE_SETTER_FUNCTION(type_name, get_type, name, from_type, setter) \
|
#define CREATE_SETTER_FUNCTION(type_name, get_type, name, from_type, setter) \
|
||||||
static void type_name##Set##name(ScriptContext &script_context) { \
|
static void type_name##Set##name(ScriptContext& script_context) \
|
||||||
|
{ \
|
||||||
auto obj = script_context.GetArgument<from_type>(0); \
|
auto obj = script_context.GetArgument<from_type>(0); \
|
||||||
auto value = script_context.GetArgument<get_type>(1); \
|
auto value = script_context.GetArgument<get_type>(1); \
|
||||||
setter; \
|
setter; \
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -26,13 +26,13 @@
|
|||||||
#include <Windows.h>
|
#include <Windows.h>
|
||||||
#include <direct.h>
|
#include <direct.h>
|
||||||
|
|
||||||
#define STR(s) L##s
|
#define STR(s) L##s
|
||||||
#define CH(c) L##c
|
#define CH(c) L##c
|
||||||
#define DIR_SEPARATOR L'\\'
|
#define DIR_SEPARATOR L'\\'
|
||||||
|
|
||||||
#else
|
#else
|
||||||
#define STR(s) s
|
#define STR(s) s
|
||||||
#define CH(c) c
|
#define CH(c) c
|
||||||
#define DIR_SEPARATOR '/'
|
#define DIR_SEPARATOR '/'
|
||||||
|
|
||||||
#include <dlfcn.h>
|
#include <dlfcn.h>
|
||||||
@@ -99,8 +99,7 @@ bool load_hostfxr()
|
|||||||
std::string base_dir = counterstrikesharp::utils::GetRootDirectory();
|
std::string base_dir = counterstrikesharp::utils::GetRootDirectory();
|
||||||
namespace css = counterstrikesharp;
|
namespace css = counterstrikesharp;
|
||||||
#if _WIN32
|
#if _WIN32
|
||||||
std::wstring buffer =
|
std::wstring buffer = std::wstring(css::widen(base_dir) + L"\\dotnet\\host\\fxr\\8.0.3\\hostfxr.dll");
|
||||||
std::wstring(css::widen(base_dir) + L"\\dotnet\\host\\fxr\\8.0.3\\hostfxr.dll");
|
|
||||||
CSSHARP_CORE_INFO("Loading hostfxr from {0}", css::narrow(buffer).c_str());
|
CSSHARP_CORE_INFO("Loading hostfxr from {0}", css::narrow(buffer).c_str());
|
||||||
#else
|
#else
|
||||||
std::string buffer = std::string(base_dir + "/dotnet/host/fxr/8.0.3/libhostfxr.so");
|
std::string buffer = std::string(base_dir + "/dotnet/host/fxr/8.0.3/libhostfxr.so");
|
||||||
@@ -109,21 +108,21 @@ bool load_hostfxr()
|
|||||||
|
|
||||||
// Load hostfxr and get desired exports
|
// Load hostfxr and get desired exports
|
||||||
void* lib = load_library(buffer.c_str());
|
void* lib = load_library(buffer.c_str());
|
||||||
init_fptr = (hostfxr_initialize_for_runtime_config_fn)get_export(
|
init_fptr = (hostfxr_initialize_for_runtime_config_fn)get_export(lib, "hostfxr_initialize_for_runtime_config");
|
||||||
lib, "hostfxr_initialize_for_runtime_config");
|
if (init_fptr == nullptr)
|
||||||
if (init_fptr == nullptr) {
|
{
|
||||||
CSSHARP_CORE_CRITICAL(
|
CSSHARP_CORE_CRITICAL("unable to get export function: \"hostfxr_initialize_for_runtime_config\"");
|
||||||
"unable to get export function: \"hostfxr_initialize_for_runtime_config\"");
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
get_delegate_fptr =
|
get_delegate_fptr = (hostfxr_get_runtime_delegate_fn)get_export(lib, "hostfxr_get_runtime_delegate");
|
||||||
(hostfxr_get_runtime_delegate_fn)get_export(lib, "hostfxr_get_runtime_delegate");
|
if (!get_delegate_fptr)
|
||||||
if (!get_delegate_fptr) {
|
{
|
||||||
CSSHARP_CORE_CRITICAL("unable to get export function: \"hostfxr_get_runtime_delegate\"");
|
CSSHARP_CORE_CRITICAL("unable to get export function: \"hostfxr_get_runtime_delegate\"");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
close_fptr = (hostfxr_close_fn)get_export(lib, "hostfxr_close");
|
close_fptr = (hostfxr_close_fn)get_export(lib, "hostfxr_close");
|
||||||
if (!close_fptr) {
|
if (!close_fptr)
|
||||||
|
{
|
||||||
CSSHARP_CORE_CRITICAL("unable to get export function: \"hostfxr_close\"");
|
CSSHARP_CORE_CRITICAL("unable to get export function: \"hostfxr_close\"");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@@ -139,16 +138,17 @@ load_assembly_and_get_function_pointer_fn get_dotnet_load_assembly(const char_t*
|
|||||||
// Load .NET Core
|
// Load .NET Core
|
||||||
void* load_assembly_and_get_function_pointer = nullptr;
|
void* load_assembly_and_get_function_pointer = nullptr;
|
||||||
int rc = init_fptr(config_path, nullptr, &cxt);
|
int rc = init_fptr(config_path, nullptr, &cxt);
|
||||||
if (rc != 0 || cxt == nullptr) {
|
if (rc != 0 || cxt == nullptr)
|
||||||
|
{
|
||||||
CSSHARP_CORE_CRITICAL("Init failed: {0:x}", rc);
|
CSSHARP_CORE_CRITICAL("Init failed: {0:x}", rc);
|
||||||
close_fptr(cxt);
|
close_fptr(cxt);
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get the load assembly function pointer
|
// Get the load assembly function pointer
|
||||||
rc = get_delegate_fptr(cxt, hdt_load_assembly_and_get_function_pointer,
|
rc = get_delegate_fptr(cxt, hdt_load_assembly_and_get_function_pointer, &load_assembly_and_get_function_pointer);
|
||||||
&load_assembly_and_get_function_pointer);
|
if (rc != 0 || load_assembly_and_get_function_pointer == nullptr)
|
||||||
if (rc != 0 || load_assembly_and_get_function_pointer == nullptr) {
|
{
|
||||||
CSSHARP_CORE_ERROR("Get delegate failed: {0:x}", rc);
|
CSSHARP_CORE_ERROR("Get delegate failed: {0:x}", rc);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -168,54 +168,51 @@ bool CDotNetManager::Initialize()
|
|||||||
|
|
||||||
CSSHARP_CORE_INFO("Loading .NET runtime...");
|
CSSHARP_CORE_INFO("Loading .NET runtime...");
|
||||||
|
|
||||||
if (!load_hostfxr()) {
|
if (!load_hostfxr())
|
||||||
|
{
|
||||||
CSSHARP_CORE_ERROR("Failed to initialize .NET runtime.");
|
CSSHARP_CORE_ERROR("Failed to initialize .NET runtime.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
CSSHARP_CORE_INFO(".NET Runtime Initialised.");
|
CSSHARP_CORE_INFO(".NET Runtime Initialised.");
|
||||||
namespace css = counterstrikesharp;
|
namespace css = counterstrikesharp;
|
||||||
#if _WIN32
|
#if _WIN32
|
||||||
const auto wide_str =
|
const auto wide_str = std::wstring(css::widen(base_dir) + L"\\api\\CounterStrikeSharp.API.runtimeconfig.json");
|
||||||
std::wstring(css::widen(base_dir) + L"\\api\\CounterStrikeSharp.API.runtimeconfig.json");
|
CSSHARP_CORE_INFO("Loading CSS API, Runtime config: {}", counterstrikesharp::narrow(wide_str).c_str());
|
||||||
CSSHARP_CORE_INFO("Loading CSS API, Runtime config: {}",
|
|
||||||
counterstrikesharp::narrow(wide_str).c_str());
|
|
||||||
#else
|
#else
|
||||||
std::string wide_str =
|
std::string wide_str = std::string((base_dir + "/api/CounterStrikeSharp.API.runtimeconfig.json").c_str());
|
||||||
std::string((base_dir + "/api/CounterStrikeSharp.API.runtimeconfig.json").c_str());
|
|
||||||
CSSHARP_CORE_INFO("Loading CSS API, Runtime Config: {}", wide_str);
|
CSSHARP_CORE_INFO("Loading CSS API, Runtime Config: {}", wide_str);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
const auto load_assembly_and_get_function_pointer = get_dotnet_load_assembly(wide_str.c_str());
|
const auto load_assembly_and_get_function_pointer = get_dotnet_load_assembly(wide_str.c_str());
|
||||||
if (load_assembly_and_get_function_pointer == nullptr) {
|
if (load_assembly_and_get_function_pointer == nullptr)
|
||||||
|
{
|
||||||
CSSHARP_CORE_ERROR("Failed to load CSS API.");
|
CSSHARP_CORE_ERROR("Failed to load CSS API.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
#if _WIN32
|
#if _WIN32
|
||||||
const auto dotnetlib_path =
|
const auto dotnetlib_path = std::wstring(css::widen(base_dir) + L"\\api\\CounterStrikeSharp.API.dll");
|
||||||
std::wstring(css::widen(base_dir) + L"\\api\\CounterStrikeSharp.API.dll");
|
|
||||||
CSSHARP_CORE_INFO("CSS API DLL: {}", counterstrikesharp::narrow(dotnetlib_path));
|
CSSHARP_CORE_INFO("CSS API DLL: {}", counterstrikesharp::narrow(dotnetlib_path));
|
||||||
#else
|
#else
|
||||||
const std::string dotnetlib_path =
|
const std::string dotnetlib_path = std::string((base_dir + "/api/CounterStrikeSharp.API.dll").c_str());
|
||||||
std::string((base_dir + "/api/CounterStrikeSharp.API.dll").c_str());
|
|
||||||
#endif
|
#endif
|
||||||
const auto dotnet_type = STR("CounterStrikeSharp.API.Bootstrap, CounterStrikeSharp.API");
|
const auto dotnet_type = STR("CounterStrikeSharp.API.Bootstrap, CounterStrikeSharp.API");
|
||||||
// Namespace, assembly name
|
// Namespace, assembly name
|
||||||
|
|
||||||
typedef int(CORECLR_DELEGATE_CALLTYPE * custom_entry_point_fn)();
|
typedef int(CORECLR_DELEGATE_CALLTYPE * custom_entry_point_fn)();
|
||||||
custom_entry_point_fn entry_point = nullptr;
|
custom_entry_point_fn entry_point = nullptr;
|
||||||
const int rc = load_assembly_and_get_function_pointer(
|
const int rc = load_assembly_and_get_function_pointer(dotnetlib_path.c_str(), dotnet_type, STR("Run"), UNMANAGEDCALLERSONLY_METHOD,
|
||||||
dotnetlib_path.c_str(), dotnet_type, STR("Run"), UNMANAGEDCALLERSONLY_METHOD,
|
nullptr, reinterpret_cast<void**>(&entry_point));
|
||||||
nullptr, reinterpret_cast<void**>(&entry_point));
|
if (entry_point == nullptr)
|
||||||
if (entry_point == nullptr) {
|
{
|
||||||
CSSHARP_CORE_ERROR("Trying to get entry point \"Bootstrap::Run\" but failed.");
|
CSSHARP_CORE_ERROR("Trying to get entry point \"Bootstrap::Run\" but failed.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
assert(rc == 0 && entry_point != nullptr &&
|
assert(rc == 0 && entry_point != nullptr && "Failure: load_assembly_and_get_function_pointer()");
|
||||||
"Failure: load_assembly_and_get_function_pointer()");
|
|
||||||
|
|
||||||
if (const int invoke_result_code = entry_point(); invoke_result_code == 0) {
|
if (const int invoke_result_code = entry_point(); invoke_result_code == 0)
|
||||||
|
{
|
||||||
CSSHARP_CORE_ERROR("Bootstrap::Run return failure.");
|
CSSHARP_CORE_ERROR("Bootstrap::Run return failure.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -21,29 +21,30 @@
|
|||||||
#include <unordered_map>
|
#include <unordered_map>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
class PluginContext {
|
class PluginContext
|
||||||
|
{
|
||||||
friend class CDotNetManager;
|
friend class CDotNetManager;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
PluginContext(std::string dll_path)
|
PluginContext(std::string dll_path) : m_dll_path(dll_path) {}
|
||||||
: m_dll_path(dll_path) {}
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::string m_dll_path;
|
std::string m_dll_path;
|
||||||
};
|
};
|
||||||
|
|
||||||
class CDotNetManager {
|
class CDotNetManager
|
||||||
|
{
|
||||||
friend class PluginContext;
|
friend class PluginContext;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
CDotNetManager();
|
CDotNetManager();
|
||||||
~CDotNetManager();
|
~CDotNetManager();
|
||||||
|
|
||||||
bool Initialize();
|
bool Initialize();
|
||||||
void UnloadPlugin(PluginContext *context);
|
void UnloadPlugin(PluginContext* context);
|
||||||
void Shutdown();
|
void Shutdown();
|
||||||
PluginContext *FindContext(std::string path);
|
PluginContext* FindContext(std::string path);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::vector<std::shared_ptr<PluginContext>> m_app_domains;
|
std::vector<std::shared_ptr<PluginContext>> m_app_domains;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -20,15 +20,17 @@
|
|||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
|
|
||||||
static bool AddListener(ScriptContext &script_context) {
|
static bool AddListener(ScriptContext& script_context)
|
||||||
auto name = script_context.GetArgument<const char *>(0);
|
{
|
||||||
|
auto name = script_context.GetArgument<const char*>(0);
|
||||||
auto callback = script_context.GetArgument<CallbackT>(1);
|
auto callback = script_context.GetArgument<CallbackT>(1);
|
||||||
|
|
||||||
return globals::callbackManager.TryAddFunction(name, callback);
|
return globals::callbackManager.TryAddFunction(name, callback);
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool RemoveListener(ScriptContext &script_context) {
|
static bool RemoveListener(ScriptContext& script_context)
|
||||||
auto name = script_context.GetArgument<const char *>(0);
|
{
|
||||||
|
auto name = script_context.GetArgument<const char*>(0);
|
||||||
auto callback = script_context.GetArgument<CallbackT>(1);
|
auto callback = script_context.GetArgument<CallbackT>(1);
|
||||||
|
|
||||||
return globals::callbackManager.TryRemoveFunction(name, callback);
|
return globals::callbackManager.TryRemoveFunction(name, callback);
|
||||||
@@ -38,4 +40,4 @@ REGISTER_NATIVES(callbacks, {
|
|||||||
ScriptEngine::RegisterNativeHandler("ADD_LISTENER", AddListener);
|
ScriptEngine::RegisterNativeHandler("ADD_LISTENER", AddListener);
|
||||||
ScriptEngine::RegisterNativeHandler("REMOVE_LISTENER", RemoveListener);
|
ScriptEngine::RegisterNativeHandler("REMOVE_LISTENER", RemoveListener);
|
||||||
})
|
})
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -1,283 +1,288 @@
|
|||||||
/*
|
/*
|
||||||
* This file is part of CounterStrikeSharp.
|
* This file is part of CounterStrikeSharp.
|
||||||
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
* CounterStrikeSharp is free software: you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
* (at your option) any later version.
|
* (at your option) any later version.
|
||||||
*
|
*
|
||||||
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
* CounterStrikeSharp is distributed in the hope that it will be useful,
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
* GNU General Public License for more details.
|
* GNU General Public License for more details.
|
||||||
*
|
*
|
||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
||||||
*/
|
*/
|
||||||
|
|
||||||
// clang-format off
|
#include "mm_plugin.h"
|
||||||
#include "mm_plugin.h"
|
#include "core/timer_system.h"
|
||||||
#include "core/timer_system.h"
|
#include "scripting/autonative.h"
|
||||||
#include "scripting/autonative.h"
|
#include "scripting/script_engine.h"
|
||||||
#include "scripting/script_engine.h"
|
#include "core/function.h"
|
||||||
#include "core/function.h"
|
#include "pch.h"
|
||||||
#include "pch.h"
|
#include "dynohook/core.h"
|
||||||
#include "dynohook/core.h"
|
#include "dynohook/manager.h"
|
||||||
#include "dynohook/manager.h"
|
|
||||||
|
namespace counterstrikesharp {
|
||||||
// clang-format on
|
|
||||||
|
void DHookGetReturn(ScriptContext& script_context)
|
||||||
namespace counterstrikesharp {
|
{
|
||||||
|
auto hook = script_context.GetArgument<dyno::Hook*>(0);
|
||||||
void DHookGetReturn(ScriptContext& script_context)
|
auto dataType = script_context.GetArgument<DataType_t>(1);
|
||||||
{
|
if (hook == nullptr)
|
||||||
auto hook = script_context.GetArgument<dyno::Hook*>(0);
|
{
|
||||||
auto dataType = script_context.GetArgument<DataType_t>(1);
|
script_context.ThrowNativeError("Invalid hook");
|
||||||
if (hook == nullptr) {
|
}
|
||||||
script_context.ThrowNativeError("Invalid hook");
|
|
||||||
}
|
switch (dataType)
|
||||||
|
{
|
||||||
switch (dataType) {
|
case DATA_TYPE_BOOL:
|
||||||
case DATA_TYPE_BOOL:
|
script_context.SetResult(hook->getReturnValue<bool>());
|
||||||
script_context.SetResult(hook->getReturnValue<bool>());
|
break;
|
||||||
break;
|
case DATA_TYPE_CHAR:
|
||||||
case DATA_TYPE_CHAR:
|
script_context.SetResult(hook->getReturnValue<char>());
|
||||||
script_context.SetResult(hook->getReturnValue<char>());
|
break;
|
||||||
break;
|
case DATA_TYPE_UCHAR:
|
||||||
case DATA_TYPE_UCHAR:
|
script_context.SetResult(hook->getReturnValue<unsigned char>());
|
||||||
script_context.SetResult(hook->getReturnValue<unsigned char>());
|
break;
|
||||||
break;
|
case DATA_TYPE_SHORT:
|
||||||
case DATA_TYPE_SHORT:
|
script_context.SetResult(hook->getReturnValue<short>());
|
||||||
script_context.SetResult(hook->getReturnValue<short>());
|
break;
|
||||||
break;
|
case DATA_TYPE_USHORT:
|
||||||
case DATA_TYPE_USHORT:
|
script_context.SetResult(hook->getReturnValue<unsigned short>());
|
||||||
script_context.SetResult(hook->getReturnValue<unsigned short>());
|
break;
|
||||||
break;
|
case DATA_TYPE_INT:
|
||||||
case DATA_TYPE_INT:
|
script_context.SetResult(hook->getReturnValue<int>());
|
||||||
script_context.SetResult(hook->getReturnValue<int>());
|
break;
|
||||||
break;
|
case DATA_TYPE_UINT:
|
||||||
case DATA_TYPE_UINT:
|
script_context.SetResult(hook->getReturnValue<unsigned int>());
|
||||||
script_context.SetResult(hook->getReturnValue<unsigned int>());
|
break;
|
||||||
break;
|
case DATA_TYPE_LONG:
|
||||||
case DATA_TYPE_LONG:
|
script_context.SetResult(hook->getReturnValue<long>());
|
||||||
script_context.SetResult(hook->getReturnValue<long>());
|
break;
|
||||||
break;
|
case DATA_TYPE_ULONG:
|
||||||
case DATA_TYPE_ULONG:
|
script_context.SetResult(hook->getReturnValue<unsigned long>());
|
||||||
script_context.SetResult(hook->getReturnValue<unsigned long>());
|
break;
|
||||||
break;
|
case DATA_TYPE_LONG_LONG:
|
||||||
case DATA_TYPE_LONG_LONG:
|
script_context.SetResult(hook->getReturnValue<long long>());
|
||||||
script_context.SetResult(hook->getReturnValue<long long>());
|
break;
|
||||||
break;
|
case DATA_TYPE_ULONG_LONG:
|
||||||
case DATA_TYPE_ULONG_LONG:
|
script_context.SetResult(hook->getReturnValue<unsigned long long>());
|
||||||
script_context.SetResult(hook->getReturnValue<unsigned long long>());
|
break;
|
||||||
break;
|
case DATA_TYPE_FLOAT:
|
||||||
case DATA_TYPE_FLOAT:
|
script_context.SetResult(hook->getReturnValue<float>());
|
||||||
script_context.SetResult(hook->getReturnValue<float>());
|
break;
|
||||||
break;
|
case DATA_TYPE_DOUBLE:
|
||||||
case DATA_TYPE_DOUBLE:
|
script_context.SetResult(hook->getReturnValue<double>());
|
||||||
script_context.SetResult(hook->getReturnValue<double>());
|
break;
|
||||||
break;
|
case DATA_TYPE_POINTER:
|
||||||
case DATA_TYPE_POINTER:
|
script_context.SetResult(hook->getReturnValue<void*>());
|
||||||
script_context.SetResult(hook->getReturnValue<void*>());
|
break;
|
||||||
break;
|
case DATA_TYPE_STRING:
|
||||||
case DATA_TYPE_STRING:
|
script_context.SetResult(hook->getReturnValue<const char*>());
|
||||||
script_context.SetResult(hook->getReturnValue<const char*>());
|
break;
|
||||||
break;
|
default:
|
||||||
default:
|
assert(!"Unknown function parameter type!");
|
||||||
assert(!"Unknown function parameter type!");
|
break;
|
||||||
break;
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
void DHookSetReturn(ScriptContext& script_context)
|
||||||
void DHookSetReturn(ScriptContext& script_context)
|
{
|
||||||
{
|
auto hook = script_context.GetArgument<dyno::Hook*>(0);
|
||||||
auto hook = script_context.GetArgument<dyno::Hook*>(0);
|
auto dataType = script_context.GetArgument<DataType_t>(1);
|
||||||
auto dataType = script_context.GetArgument<DataType_t>(1);
|
if (hook == nullptr)
|
||||||
if (hook == nullptr) {
|
{
|
||||||
script_context.ThrowNativeError("Invalid hook");
|
script_context.ThrowNativeError("Invalid hook");
|
||||||
}
|
}
|
||||||
|
|
||||||
auto valueIndex = 2;
|
auto valueIndex = 2;
|
||||||
|
|
||||||
switch (dataType) {
|
switch (dataType)
|
||||||
case DATA_TYPE_BOOL:
|
{
|
||||||
hook->setReturnValue(script_context.GetArgument<bool>(valueIndex));
|
case DATA_TYPE_BOOL:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<bool>(valueIndex));
|
||||||
case DATA_TYPE_CHAR:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<char>(valueIndex));
|
case DATA_TYPE_CHAR:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<char>(valueIndex));
|
||||||
case DATA_TYPE_UCHAR:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<unsigned char>(valueIndex));
|
case DATA_TYPE_UCHAR:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<unsigned char>(valueIndex));
|
||||||
case DATA_TYPE_SHORT:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<short>(valueIndex));
|
case DATA_TYPE_SHORT:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<short>(valueIndex));
|
||||||
case DATA_TYPE_USHORT:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<unsigned short>(valueIndex));
|
case DATA_TYPE_USHORT:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<unsigned short>(valueIndex));
|
||||||
case DATA_TYPE_INT:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<int>(valueIndex));
|
case DATA_TYPE_INT:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<int>(valueIndex));
|
||||||
case DATA_TYPE_UINT:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<unsigned int>(valueIndex));
|
case DATA_TYPE_UINT:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<unsigned int>(valueIndex));
|
||||||
case DATA_TYPE_LONG:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<long>(valueIndex));
|
case DATA_TYPE_LONG:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<long>(valueIndex));
|
||||||
case DATA_TYPE_ULONG:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<unsigned long>(valueIndex));
|
case DATA_TYPE_ULONG:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<unsigned long>(valueIndex));
|
||||||
case DATA_TYPE_LONG_LONG:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<long long>(valueIndex));
|
case DATA_TYPE_LONG_LONG:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<long long>(valueIndex));
|
||||||
case DATA_TYPE_ULONG_LONG:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<unsigned long long>(valueIndex));
|
case DATA_TYPE_ULONG_LONG:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<unsigned long long>(valueIndex));
|
||||||
case DATA_TYPE_FLOAT:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<float>(valueIndex));
|
case DATA_TYPE_FLOAT:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<float>(valueIndex));
|
||||||
case DATA_TYPE_DOUBLE:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<double>(valueIndex));
|
case DATA_TYPE_DOUBLE:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<double>(valueIndex));
|
||||||
case DATA_TYPE_POINTER:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<void*>(valueIndex));
|
case DATA_TYPE_POINTER:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<void*>(valueIndex));
|
||||||
case DATA_TYPE_STRING:
|
break;
|
||||||
hook->setReturnValue(script_context.GetArgument<const char*>(valueIndex));
|
case DATA_TYPE_STRING:
|
||||||
break;
|
hook->setReturnValue(script_context.GetArgument<const char*>(valueIndex));
|
||||||
default:
|
break;
|
||||||
assert(!"Unknown function parameter type!");
|
default:
|
||||||
break;
|
assert(!"Unknown function parameter type!");
|
||||||
}
|
break;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
void DHookGetParam(ScriptContext& script_context)
|
|
||||||
{
|
void DHookGetParam(ScriptContext& script_context)
|
||||||
auto hook = script_context.GetArgument<dyno::Hook*>(0);
|
{
|
||||||
auto dataType = script_context.GetArgument<DataType_t>(1);
|
auto hook = script_context.GetArgument<dyno::Hook*>(0);
|
||||||
auto paramIndex = script_context.GetArgument<int>(2);
|
auto dataType = script_context.GetArgument<DataType_t>(1);
|
||||||
if (hook == nullptr) {
|
auto paramIndex = script_context.GetArgument<int>(2);
|
||||||
script_context.ThrowNativeError("Invalid hook");
|
if (hook == nullptr)
|
||||||
}
|
{
|
||||||
|
script_context.ThrowNativeError("Invalid hook");
|
||||||
switch (dataType) {
|
}
|
||||||
case DATA_TYPE_BOOL:
|
|
||||||
script_context.SetResult(hook->getArgument<bool>(paramIndex));
|
switch (dataType)
|
||||||
break;
|
{
|
||||||
case DATA_TYPE_CHAR:
|
case DATA_TYPE_BOOL:
|
||||||
script_context.SetResult(hook->getArgument<char>(paramIndex));
|
script_context.SetResult(hook->getArgument<bool>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_UCHAR:
|
case DATA_TYPE_CHAR:
|
||||||
script_context.SetResult(hook->getArgument<unsigned char>(paramIndex));
|
script_context.SetResult(hook->getArgument<char>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_SHORT:
|
case DATA_TYPE_UCHAR:
|
||||||
script_context.SetResult(hook->getArgument<short>(paramIndex));
|
script_context.SetResult(hook->getArgument<unsigned char>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_USHORT:
|
case DATA_TYPE_SHORT:
|
||||||
script_context.SetResult(hook->getArgument<unsigned short>(paramIndex));
|
script_context.SetResult(hook->getArgument<short>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_INT:
|
case DATA_TYPE_USHORT:
|
||||||
script_context.SetResult(hook->getArgument<int>(paramIndex));
|
script_context.SetResult(hook->getArgument<unsigned short>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_UINT:
|
case DATA_TYPE_INT:
|
||||||
script_context.SetResult(hook->getArgument<unsigned int>(paramIndex));
|
script_context.SetResult(hook->getArgument<int>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_LONG:
|
case DATA_TYPE_UINT:
|
||||||
script_context.SetResult(hook->getArgument<long>(paramIndex));
|
script_context.SetResult(hook->getArgument<unsigned int>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_ULONG:
|
case DATA_TYPE_LONG:
|
||||||
script_context.SetResult(hook->getArgument<unsigned long>(paramIndex));
|
script_context.SetResult(hook->getArgument<long>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_LONG_LONG:
|
case DATA_TYPE_ULONG:
|
||||||
script_context.SetResult(hook->getArgument<long long>(paramIndex));
|
script_context.SetResult(hook->getArgument<unsigned long>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_ULONG_LONG:
|
case DATA_TYPE_LONG_LONG:
|
||||||
script_context.SetResult(hook->getArgument<unsigned long long>(paramIndex));
|
script_context.SetResult(hook->getArgument<long long>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_FLOAT:
|
case DATA_TYPE_ULONG_LONG:
|
||||||
script_context.SetResult(hook->getArgument<float>(paramIndex));
|
script_context.SetResult(hook->getArgument<unsigned long long>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_DOUBLE:
|
case DATA_TYPE_FLOAT:
|
||||||
script_context.SetResult(hook->getArgument<double>(paramIndex));
|
script_context.SetResult(hook->getArgument<float>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_POINTER:
|
case DATA_TYPE_DOUBLE:
|
||||||
script_context.SetResult(hook->getArgument<void*>(paramIndex));
|
script_context.SetResult(hook->getArgument<double>(paramIndex));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_STRING:
|
case DATA_TYPE_POINTER:
|
||||||
script_context.SetResult(hook->getArgument<const char*>(paramIndex));
|
script_context.SetResult(hook->getArgument<void*>(paramIndex));
|
||||||
break;
|
break;
|
||||||
default:
|
case DATA_TYPE_STRING:
|
||||||
assert(!"Unknown function parameter type!");
|
script_context.SetResult(hook->getArgument<const char*>(paramIndex));
|
||||||
break;
|
break;
|
||||||
}
|
default:
|
||||||
}
|
assert(!"Unknown function parameter type!");
|
||||||
|
break;
|
||||||
void DHookSetParam(ScriptContext& script_context)
|
}
|
||||||
{
|
}
|
||||||
auto hook = script_context.GetArgument<dyno::Hook*>(0);
|
|
||||||
auto dataType = script_context.GetArgument<DataType_t>(1);
|
void DHookSetParam(ScriptContext& script_context)
|
||||||
auto paramIndex = script_context.GetArgument<int>(2);
|
{
|
||||||
if (hook == nullptr) {
|
auto hook = script_context.GetArgument<dyno::Hook*>(0);
|
||||||
script_context.ThrowNativeError("Invalid hook");
|
auto dataType = script_context.GetArgument<DataType_t>(1);
|
||||||
}
|
auto paramIndex = script_context.GetArgument<int>(2);
|
||||||
|
if (hook == nullptr)
|
||||||
auto valueIndex = 3;
|
{
|
||||||
|
script_context.ThrowNativeError("Invalid hook");
|
||||||
switch (dataType) {
|
}
|
||||||
case DATA_TYPE_BOOL:
|
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<bool>(valueIndex));
|
auto valueIndex = 3;
|
||||||
break;
|
|
||||||
case DATA_TYPE_CHAR:
|
switch (dataType)
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<char>(valueIndex));
|
{
|
||||||
break;
|
case DATA_TYPE_BOOL:
|
||||||
case DATA_TYPE_UCHAR:
|
hook->setArgument(paramIndex, script_context.GetArgument<bool>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<unsigned char>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_CHAR:
|
||||||
case DATA_TYPE_SHORT:
|
hook->setArgument(paramIndex, script_context.GetArgument<char>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<short>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_UCHAR:
|
||||||
case DATA_TYPE_USHORT:
|
hook->setArgument(paramIndex, script_context.GetArgument<unsigned char>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<unsigned short>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_SHORT:
|
||||||
case DATA_TYPE_INT:
|
hook->setArgument(paramIndex, script_context.GetArgument<short>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<int>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_USHORT:
|
||||||
case DATA_TYPE_UINT:
|
hook->setArgument(paramIndex, script_context.GetArgument<unsigned short>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<unsigned int>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_INT:
|
||||||
case DATA_TYPE_LONG:
|
hook->setArgument(paramIndex, script_context.GetArgument<int>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<long>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_UINT:
|
||||||
case DATA_TYPE_ULONG:
|
hook->setArgument(paramIndex, script_context.GetArgument<unsigned int>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<unsigned long>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_LONG:
|
||||||
case DATA_TYPE_LONG_LONG:
|
hook->setArgument(paramIndex, script_context.GetArgument<long>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<long long>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_ULONG:
|
||||||
case DATA_TYPE_ULONG_LONG:
|
hook->setArgument(paramIndex, script_context.GetArgument<unsigned long>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<unsigned long long>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_LONG_LONG:
|
||||||
case DATA_TYPE_FLOAT:
|
hook->setArgument(paramIndex, script_context.GetArgument<long long>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<float>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_ULONG_LONG:
|
||||||
case DATA_TYPE_DOUBLE:
|
hook->setArgument(paramIndex, script_context.GetArgument<unsigned long long>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<double>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_FLOAT:
|
||||||
case DATA_TYPE_POINTER:
|
hook->setArgument(paramIndex, script_context.GetArgument<float>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<void*>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_DOUBLE:
|
||||||
case DATA_TYPE_STRING:
|
hook->setArgument(paramIndex, script_context.GetArgument<double>(valueIndex));
|
||||||
hook->setArgument(paramIndex, script_context.GetArgument<const char*>(valueIndex));
|
break;
|
||||||
break;
|
case DATA_TYPE_POINTER:
|
||||||
default:
|
hook->setArgument(paramIndex, script_context.GetArgument<void*>(valueIndex));
|
||||||
assert(!"Unknown function parameter type!");
|
break;
|
||||||
break;
|
case DATA_TYPE_STRING:
|
||||||
}
|
hook->setArgument(paramIndex, script_context.GetArgument<const char*>(valueIndex));
|
||||||
}
|
break;
|
||||||
|
default:
|
||||||
REGISTER_NATIVES(dynamichooks, {
|
assert(!"Unknown function parameter type!");
|
||||||
ScriptEngine::RegisterNativeHandler("DYNAMIC_HOOK_GET_RETURN", DHookGetReturn);
|
break;
|
||||||
ScriptEngine::RegisterNativeHandler("DYNAMIC_HOOK_SET_RETURN", DHookSetReturn);
|
}
|
||||||
ScriptEngine::RegisterNativeHandler("DYNAMIC_HOOK_GET_PARAM", DHookGetParam);
|
}
|
||||||
ScriptEngine::RegisterNativeHandler("DYNAMIC_HOOK_SET_PARAM", DHookSetParam);
|
|
||||||
})
|
REGISTER_NATIVES(dynamichooks, {
|
||||||
} // namespace counterstrikesharp
|
ScriptEngine::RegisterNativeHandler("DYNAMIC_HOOK_GET_RETURN", DHookGetReturn);
|
||||||
|
ScriptEngine::RegisterNativeHandler("DYNAMIC_HOOK_SET_RETURN", DHookSetReturn);
|
||||||
|
ScriptEngine::RegisterNativeHandler("DYNAMIC_HOOK_GET_PARAM", DHookGetParam);
|
||||||
|
ScriptEngine::RegisterNativeHandler("DYNAMIC_HOOK_SET_PARAM", DHookSetParam);
|
||||||
|
})
|
||||||
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -20,7 +20,6 @@
|
|||||||
#include <filesystem.h>
|
#include <filesystem.h>
|
||||||
#include <public/worldsize.h>
|
#include <public/worldsize.h>
|
||||||
|
|
||||||
// clang-format off
|
|
||||||
#include "mm_plugin.h"
|
#include "mm_plugin.h"
|
||||||
#include "core/timer_system.h"
|
#include "core/timer_system.h"
|
||||||
#include "core/utils.h"
|
#include "core/utils.h"
|
||||||
@@ -32,7 +31,6 @@
|
|||||||
#include "core/managers/player_manager.h"
|
#include "core/managers/player_manager.h"
|
||||||
#include "core/managers/server_manager.h"
|
#include "core/managers/server_manager.h"
|
||||||
#include "core/tick_scheduler.h"
|
#include "core/tick_scheduler.h"
|
||||||
// clang-format on
|
|
||||||
|
|
||||||
#if _WIN32
|
#if _WIN32
|
||||||
#undef GetCurrentTime
|
#undef GetCurrentTime
|
||||||
|
|||||||
@@ -20,44 +20,49 @@
|
|||||||
#include "scripting/autonative.h"
|
#include "scripting/autonative.h"
|
||||||
#include "igameevents.h"
|
#include "igameevents.h"
|
||||||
|
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
|
|
||||||
std::vector<IGameEvent *> managed_game_events;
|
std::vector<IGameEvent*> managed_game_events;
|
||||||
|
|
||||||
static void HookEvent(ScriptContext &script_context) {
|
static void HookEvent(ScriptContext& script_context)
|
||||||
const char *name = script_context.GetArgument<const char *>(0);
|
{
|
||||||
|
const char* name = script_context.GetArgument<const char*>(0);
|
||||||
auto callback = script_context.GetArgument<CallbackT>(1);
|
auto callback = script_context.GetArgument<CallbackT>(1);
|
||||||
auto post = script_context.GetArgument<bool>(2);
|
auto post = script_context.GetArgument<bool>(2);
|
||||||
|
|
||||||
globals::eventManager.HookEvent(name, callback, post);
|
globals::eventManager.HookEvent(name, callback, post);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void UnhookEvent(ScriptContext &script_context) {
|
static void UnhookEvent(ScriptContext& script_context)
|
||||||
const char *name = script_context.GetArgument<const char *>(0);
|
{
|
||||||
|
const char* name = script_context.GetArgument<const char*>(0);
|
||||||
auto callback = script_context.GetArgument<CallbackT>(1);
|
auto callback = script_context.GetArgument<CallbackT>(1);
|
||||||
auto post = script_context.GetArgument<bool>(2);
|
auto post = script_context.GetArgument<bool>(2);
|
||||||
|
|
||||||
globals::eventManager.UnhookEvent(name, callback, post);
|
globals::eventManager.UnhookEvent(name, callback, post);
|
||||||
}
|
}
|
||||||
|
|
||||||
static IGameEvent *CreateEvent(ScriptContext &script_context) {
|
static IGameEvent* CreateEvent(ScriptContext& script_context)
|
||||||
auto name = script_context.GetArgument<const char *>(0);
|
{
|
||||||
|
auto name = script_context.GetArgument<const char*>(0);
|
||||||
bool force = script_context.GetArgument<bool>(1);
|
bool force = script_context.GetArgument<bool>(1);
|
||||||
|
|
||||||
auto pEvent = globals::gameEventManager->CreateEvent(name, force);
|
auto pEvent = globals::gameEventManager->CreateEvent(name, force);
|
||||||
|
|
||||||
if (pEvent != nullptr) {
|
if (pEvent != nullptr)
|
||||||
|
{
|
||||||
managed_game_events.push_back(pEvent);
|
managed_game_events.push_back(pEvent);
|
||||||
}
|
}
|
||||||
|
|
||||||
return pEvent;
|
return pEvent;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void FireEvent(ScriptContext &script_context) {
|
static void FireEvent(ScriptContext& script_context)
|
||||||
auto game_event = script_context.GetArgument<IGameEvent *>(0);
|
{
|
||||||
|
auto game_event = script_context.GetArgument<IGameEvent*>(0);
|
||||||
bool dont_broadcast = script_context.GetArgument<bool>(1);
|
bool dont_broadcast = script_context.GetArgument<bool>(1);
|
||||||
if (!game_event) {
|
if (!game_event)
|
||||||
|
{
|
||||||
script_context.ThrowNativeError("Invalid game event");
|
script_context.ThrowNativeError("Invalid game event");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -66,17 +71,19 @@ static void FireEvent(ScriptContext &script_context) {
|
|||||||
managed_game_events.erase(std::remove(managed_game_events.begin(), managed_game_events.end(), game_event), managed_game_events.end());
|
managed_game_events.erase(std::remove(managed_game_events.begin(), managed_game_events.end(), game_event), managed_game_events.end());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void FireEventToClient(ScriptContext& script_context)
|
||||||
static void FireEventToClient(ScriptContext& script_context) {
|
{
|
||||||
auto game_event = script_context.GetArgument<IGameEvent*>(0);
|
auto game_event = script_context.GetArgument<IGameEvent*>(0);
|
||||||
int entityIndex = script_context.GetArgument<int>(1);
|
int entityIndex = script_context.GetArgument<int>(1);
|
||||||
if (!game_event) {
|
if (!game_event)
|
||||||
|
{
|
||||||
script_context.ThrowNativeError("Invalid game event");
|
script_context.ThrowNativeError("Invalid game event");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
IGameEventListener2* pListener = globals::GetLegacyGameEventListener(CPlayerSlot(entityIndex - 1));
|
IGameEventListener2* pListener = globals::GetLegacyGameEventListener(CPlayerSlot(entityIndex - 1));
|
||||||
if (!pListener) {
|
if (!pListener)
|
||||||
|
{
|
||||||
script_context.ThrowNativeError("Could not get player event listener");
|
script_context.ThrowNativeError("Could not get player event listener");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -84,21 +91,25 @@ static void FireEventToClient(ScriptContext& script_context) {
|
|||||||
pListener->FireGameEvent(game_event);
|
pListener->FireGameEvent(game_event);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void FreeEvent(ScriptContext& script_context) {
|
static void FreeEvent(ScriptContext& script_context)
|
||||||
|
{
|
||||||
auto game_event = script_context.GetArgument<IGameEvent*>(0);
|
auto game_event = script_context.GetArgument<IGameEvent*>(0);
|
||||||
if (!game_event) {
|
if (!game_event)
|
||||||
script_context.ThrowNativeError("Invalid game event");
|
{
|
||||||
return;
|
script_context.ThrowNativeError("Invalid game event");
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
globals::gameEventManager->FreeEvent(game_event);
|
globals::gameEventManager->FreeEvent(game_event);
|
||||||
managed_game_events.erase(std::remove(managed_game_events.begin(), managed_game_events.end(), game_event), managed_game_events.end());
|
managed_game_events.erase(std::remove(managed_game_events.begin(), managed_game_events.end(), game_event), managed_game_events.end());
|
||||||
}
|
}
|
||||||
|
|
||||||
static const char *GetEventName(ScriptContext &script_context) {
|
static const char* GetEventName(ScriptContext& script_context)
|
||||||
IGameEvent *game_event = script_context.GetArgument<IGameEvent *>(0);
|
{
|
||||||
|
IGameEvent* game_event = script_context.GetArgument<IGameEvent*>(0);
|
||||||
|
|
||||||
if (!game_event) {
|
if (!game_event)
|
||||||
|
{
|
||||||
script_context.ThrowNativeError("Invalid game event");
|
script_context.ThrowNativeError("Invalid game event");
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
@@ -106,11 +117,13 @@ static const char *GetEventName(ScriptContext &script_context) {
|
|||||||
return game_event->GetName();
|
return game_event->GetName();
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool GetEventBool(ScriptContext &script_context) {
|
static bool GetEventBool(ScriptContext& script_context)
|
||||||
IGameEvent *game_event = script_context.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *key_name = script_context.GetArgument<const char *>(1);
|
IGameEvent* game_event = script_context.GetArgument<IGameEvent*>(0);
|
||||||
|
const char* key_name = script_context.GetArgument<const char*>(1);
|
||||||
|
|
||||||
if (!game_event) {
|
if (!game_event)
|
||||||
|
{
|
||||||
script_context.ThrowNativeError("Invalid game event");
|
script_context.ThrowNativeError("Invalid game event");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@@ -118,11 +131,13 @@ static bool GetEventBool(ScriptContext &script_context) {
|
|||||||
return game_event->GetBool(key_name);
|
return game_event->GetBool(key_name);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int GetEventInt(ScriptContext &script_context) {
|
static int GetEventInt(ScriptContext& script_context)
|
||||||
IGameEvent *game_event = script_context.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *key_name = script_context.GetArgument<const char *>(1);
|
IGameEvent* game_event = script_context.GetArgument<IGameEvent*>(0);
|
||||||
|
const char* key_name = script_context.GetArgument<const char*>(1);
|
||||||
|
|
||||||
if (!game_event) {
|
if (!game_event)
|
||||||
|
{
|
||||||
script_context.ThrowNativeError("Invalid game event");
|
script_context.ThrowNativeError("Invalid game event");
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
@@ -130,11 +145,13 @@ static int GetEventInt(ScriptContext &script_context) {
|
|||||||
return game_event->GetInt(key_name);
|
return game_event->GetInt(key_name);
|
||||||
}
|
}
|
||||||
|
|
||||||
static float GetEventFloat(ScriptContext &script_context) {
|
static float GetEventFloat(ScriptContext& script_context)
|
||||||
IGameEvent *game_event = script_context.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *key_name = script_context.GetArgument<const char *>(1);
|
IGameEvent* game_event = script_context.GetArgument<IGameEvent*>(0);
|
||||||
|
const char* key_name = script_context.GetArgument<const char*>(1);
|
||||||
|
|
||||||
if (!game_event) {
|
if (!game_event)
|
||||||
|
{
|
||||||
script_context.ThrowNativeError("Invalid game event");
|
script_context.ThrowNativeError("Invalid game event");
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
@@ -142,11 +159,13 @@ static float GetEventFloat(ScriptContext &script_context) {
|
|||||||
return game_event->GetFloat(key_name);
|
return game_event->GetFloat(key_name);
|
||||||
}
|
}
|
||||||
|
|
||||||
static const char *GetEventString(ScriptContext &script_context) {
|
static const char* GetEventString(ScriptContext& script_context)
|
||||||
IGameEvent *game_event = script_context.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *key_name = script_context.GetArgument<const char *>(1);
|
IGameEvent* game_event = script_context.GetArgument<IGameEvent*>(0);
|
||||||
|
const char* key_name = script_context.GetArgument<const char*>(1);
|
||||||
|
|
||||||
if (!game_event) {
|
if (!game_event)
|
||||||
|
{
|
||||||
script_context.ThrowNativeError("Invalid game event");
|
script_context.ThrowNativeError("Invalid game event");
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
@@ -154,51 +173,61 @@ static const char *GetEventString(ScriptContext &script_context) {
|
|||||||
return game_event->GetString(key_name);
|
return game_event->GetString(key_name);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void SetEventBool(ScriptContext &script_context) {
|
static void SetEventBool(ScriptContext& script_context)
|
||||||
IGameEvent *game_event = script_context.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *key_name = script_context.GetArgument<const char *>(1);
|
IGameEvent* game_event = script_context.GetArgument<IGameEvent*>(0);
|
||||||
|
const char* key_name = script_context.GetArgument<const char*>(1);
|
||||||
const bool value = script_context.GetArgument<bool>(2);
|
const bool value = script_context.GetArgument<bool>(2);
|
||||||
|
|
||||||
if (game_event) {
|
if (game_event)
|
||||||
|
{
|
||||||
game_event->SetBool(key_name, value);
|
game_event->SetBool(key_name, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void SetEventInt(ScriptContext &script_context) {
|
static void SetEventInt(ScriptContext& script_context)
|
||||||
IGameEvent *game_event = script_context.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *key_name = script_context.GetArgument<const char *>(1);
|
IGameEvent* game_event = script_context.GetArgument<IGameEvent*>(0);
|
||||||
|
const char* key_name = script_context.GetArgument<const char*>(1);
|
||||||
const int value = script_context.GetArgument<int>(2);
|
const int value = script_context.GetArgument<int>(2);
|
||||||
|
|
||||||
if (game_event) {
|
if (game_event)
|
||||||
|
{
|
||||||
game_event->SetInt(key_name, value);
|
game_event->SetInt(key_name, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void SetEventFloat(ScriptContext &script_context) {
|
static void SetEventFloat(ScriptContext& script_context)
|
||||||
IGameEvent *game_event = script_context.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *key_name = script_context.GetArgument<const char *>(1);
|
IGameEvent* game_event = script_context.GetArgument<IGameEvent*>(0);
|
||||||
|
const char* key_name = script_context.GetArgument<const char*>(1);
|
||||||
const float value = script_context.GetArgument<float>(2);
|
const float value = script_context.GetArgument<float>(2);
|
||||||
|
|
||||||
if (game_event) {
|
if (game_event)
|
||||||
|
{
|
||||||
game_event->SetFloat(key_name, value);
|
game_event->SetFloat(key_name, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void SetEventString(ScriptContext &script_context) {
|
static void SetEventString(ScriptContext& script_context)
|
||||||
IGameEvent *game_event = script_context.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *key_name = script_context.GetArgument<const char *>(1);
|
IGameEvent* game_event = script_context.GetArgument<IGameEvent*>(0);
|
||||||
const char *value = script_context.GetArgument<const char *>(2);
|
const char* key_name = script_context.GetArgument<const char*>(1);
|
||||||
|
const char* value = script_context.GetArgument<const char*>(2);
|
||||||
|
|
||||||
if (game_event) {
|
if (game_event)
|
||||||
|
{
|
||||||
game_event->SetString(key_name, value);
|
game_event->SetString(key_name, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void *GetPlayerController(ScriptContext &scriptContext) {
|
static void* GetPlayerController(ScriptContext& scriptContext)
|
||||||
IGameEvent *gameEvent = scriptContext.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *keyName = scriptContext.GetArgument<const char *>(1);
|
IGameEvent* gameEvent = scriptContext.GetArgument<IGameEvent*>(0);
|
||||||
|
const char* keyName = scriptContext.GetArgument<const char*>(1);
|
||||||
|
|
||||||
if (gameEvent == nullptr) {
|
if (gameEvent == nullptr)
|
||||||
|
{
|
||||||
scriptContext.ThrowNativeError("Invalid game event");
|
scriptContext.ThrowNativeError("Invalid game event");
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
@@ -206,41 +235,49 @@ static void *GetPlayerController(ScriptContext &scriptContext) {
|
|||||||
return gameEvent->GetPlayerController(keyName);
|
return gameEvent->GetPlayerController(keyName);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void SetPlayerController(ScriptContext &scriptContext) {
|
static void SetPlayerController(ScriptContext& scriptContext)
|
||||||
IGameEvent *gameEvent = scriptContext.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *keyName = scriptContext.GetArgument<const char *>(1);
|
IGameEvent* gameEvent = scriptContext.GetArgument<IGameEvent*>(0);
|
||||||
auto *value = scriptContext.GetArgument<CEntityInstance *>(2);
|
const char* keyName = scriptContext.GetArgument<const char*>(1);
|
||||||
|
auto* value = scriptContext.GetArgument<CEntityInstance*>(2);
|
||||||
|
|
||||||
if (gameEvent != nullptr) {
|
if (gameEvent != nullptr)
|
||||||
|
{
|
||||||
gameEvent->SetPlayer(keyName, value);
|
gameEvent->SetPlayer(keyName, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void SetEntity(ScriptContext &scriptContext) {
|
static void SetEntity(ScriptContext& scriptContext)
|
||||||
IGameEvent *gameEvent = scriptContext.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *keyName = scriptContext.GetArgument<const char *>(1);
|
IGameEvent* gameEvent = scriptContext.GetArgument<IGameEvent*>(0);
|
||||||
auto *value = scriptContext.GetArgument<CEntityInstance *>(2);
|
const char* keyName = scriptContext.GetArgument<const char*>(1);
|
||||||
|
auto* value = scriptContext.GetArgument<CEntityInstance*>(2);
|
||||||
|
|
||||||
if (gameEvent != nullptr) {
|
if (gameEvent != nullptr)
|
||||||
|
{
|
||||||
gameEvent->SetEntity(keyName, value);
|
gameEvent->SetEntity(keyName, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void SetEntityIndex(ScriptContext &scriptContext) {
|
static void SetEntityIndex(ScriptContext& scriptContext)
|
||||||
IGameEvent *gameEvent = scriptContext.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *keyName = scriptContext.GetArgument<const char *>(1);
|
IGameEvent* gameEvent = scriptContext.GetArgument<IGameEvent*>(0);
|
||||||
|
const char* keyName = scriptContext.GetArgument<const char*>(1);
|
||||||
auto index = scriptContext.GetArgument<int>(2);
|
auto index = scriptContext.GetArgument<int>(2);
|
||||||
|
|
||||||
if (gameEvent != nullptr) {
|
if (gameEvent != nullptr)
|
||||||
|
{
|
||||||
gameEvent->SetEntity(keyName, CEntityIndex{ index });
|
gameEvent->SetEntity(keyName, CEntityIndex{ index });
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void *GetPlayerPawn(ScriptContext& scriptContext) {
|
static void* GetPlayerPawn(ScriptContext& scriptContext)
|
||||||
IGameEvent *gameEvent = scriptContext.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *keyName = scriptContext.GetArgument<const char *>(1);
|
IGameEvent* gameEvent = scriptContext.GetArgument<IGameEvent*>(0);
|
||||||
|
const char* keyName = scriptContext.GetArgument<const char*>(1);
|
||||||
|
|
||||||
if (gameEvent == nullptr) {
|
if (gameEvent == nullptr)
|
||||||
|
{
|
||||||
scriptContext.ThrowNativeError("Invalid game event");
|
scriptContext.ThrowNativeError("Invalid game event");
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
@@ -248,11 +285,13 @@ static void *GetPlayerPawn(ScriptContext& scriptContext) {
|
|||||||
return gameEvent->GetPlayerPawn(keyName);
|
return gameEvent->GetPlayerPawn(keyName);
|
||||||
}
|
}
|
||||||
|
|
||||||
static uint64 GetUint64(ScriptContext &scriptContext) {
|
static uint64 GetUint64(ScriptContext& scriptContext)
|
||||||
IGameEvent *gameEvent = scriptContext.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *keyName = scriptContext.GetArgument<const char *>(1);
|
IGameEvent* gameEvent = scriptContext.GetArgument<IGameEvent*>(0);
|
||||||
|
const char* keyName = scriptContext.GetArgument<const char*>(1);
|
||||||
|
|
||||||
if (gameEvent == nullptr) {
|
if (gameEvent == nullptr)
|
||||||
|
{
|
||||||
scriptContext.ThrowNativeError("Invalid game event");
|
scriptContext.ThrowNativeError("Invalid game event");
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -260,18 +299,21 @@ static uint64 GetUint64(ScriptContext &scriptContext) {
|
|||||||
return gameEvent->GetUint64(keyName);
|
return gameEvent->GetUint64(keyName);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void SetUint64(ScriptContext &scriptContext) {
|
static void SetUint64(ScriptContext& scriptContext)
|
||||||
IGameEvent *gameEvent = scriptContext.GetArgument<IGameEvent *>(0);
|
{
|
||||||
const char *keyName = scriptContext.GetArgument<const char *>(1);
|
IGameEvent* gameEvent = scriptContext.GetArgument<IGameEvent*>(0);
|
||||||
|
const char* keyName = scriptContext.GetArgument<const char*>(1);
|
||||||
auto value = scriptContext.GetArgument<uint64>(2);
|
auto value = scriptContext.GetArgument<uint64>(2);
|
||||||
|
|
||||||
if (gameEvent != nullptr) {
|
if (gameEvent != nullptr)
|
||||||
|
{
|
||||||
gameEvent->SetUint64(keyName, value);
|
gameEvent->SetUint64(keyName, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static int LoadEventsFromFile(ScriptContext &script_context) {
|
static int LoadEventsFromFile(ScriptContext& script_context)
|
||||||
auto [path, searchAll] = script_context.GetArguments<const char *, bool>();
|
{
|
||||||
|
auto [path, searchAll] = script_context.GetArguments<const char*, bool>();
|
||||||
|
|
||||||
return globals::gameEventManager->LoadEventsFromFile(path, searchAll);
|
return globals::gameEventManager->LoadEventsFromFile(path, searchAll);
|
||||||
}
|
}
|
||||||
@@ -304,8 +346,7 @@ REGISTER_NATIVES(events, {
|
|||||||
ScriptEngine::RegisterNativeHandler("GET_EVENT_UINT64", GetUint64);
|
ScriptEngine::RegisterNativeHandler("GET_EVENT_UINT64", GetUint64);
|
||||||
ScriptEngine::RegisterNativeHandler("SET_EVENT_UINT64", SetUint64);
|
ScriptEngine::RegisterNativeHandler("SET_EVENT_UINT64", SetUint64);
|
||||||
|
|
||||||
|
|
||||||
ScriptEngine::RegisterNativeHandler("LOAD_EVENTS_FROM_FILE", LoadEventsFromFile);
|
ScriptEngine::RegisterNativeHandler("LOAD_EVENTS_FROM_FILE", LoadEventsFromFile);
|
||||||
})
|
})
|
||||||
|
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -26,7 +26,5 @@ static void* MetaFactory(ScriptContext& script_context)
|
|||||||
return ptr;
|
return ptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
REGISTER_NATIVES(metamod, {
|
REGISTER_NATIVES(metamod, { ScriptEngine::RegisterNativeHandler("META_FACTORY", MetaFactory); })
|
||||||
ScriptEngine::RegisterNativeHandler("META_FACTORY", MetaFactory);
|
|
||||||
})
|
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -57,12 +57,10 @@ int GetSchemaClassSize(ScriptContext& script_context)
|
|||||||
{
|
{
|
||||||
auto className = script_context.GetArgument<const char*>(0);
|
auto className = script_context.GetArgument<const char*>(0);
|
||||||
|
|
||||||
CSchemaSystemTypeScope* pType =
|
CSchemaSystemTypeScope* pType = globals::schemaSystem->FindTypeScopeForModule(MODULE_PREFIX "server" MODULE_EXT);
|
||||||
globals::schemaSystem->FindTypeScopeForModule(MODULE_PREFIX "server" MODULE_EXT);
|
|
||||||
|
|
||||||
SchemaClassInfoData_t* pClassInfo = pType->FindDeclaredClass(className).Get();
|
SchemaClassInfoData_t* pClassInfo = pType->FindDeclaredClass(className).Get();
|
||||||
if (!pClassInfo)
|
if (!pClassInfo) return -1;
|
||||||
return -1;
|
|
||||||
|
|
||||||
return pClassInfo->m_nSize;
|
return pClassInfo->m_nSize;
|
||||||
}
|
}
|
||||||
@@ -78,70 +76,56 @@ void GetSchemaValueByName(ScriptContext& script_context)
|
|||||||
|
|
||||||
const auto m_key = schema::GetOffset(className, classKey, memberName, memberKey);
|
const auto m_key = schema::GetOffset(className, classKey, memberName, memberKey);
|
||||||
|
|
||||||
switch (returnType) {
|
switch (returnType)
|
||||||
case DATA_TYPE_BOOL:
|
{
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<bool>>(
|
case DATA_TYPE_BOOL:
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<bool>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_CHAR:
|
case DATA_TYPE_CHAR:
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<char>>(
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<char>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
break;
|
||||||
break;
|
case DATA_TYPE_UCHAR:
|
||||||
case DATA_TYPE_UCHAR:
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<unsigned char>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<unsigned char>>(
|
break;
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
case DATA_TYPE_SHORT:
|
||||||
break;
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<short>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
case DATA_TYPE_SHORT:
|
break;
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<short>>(
|
case DATA_TYPE_USHORT:
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<unsigned short>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_USHORT:
|
case DATA_TYPE_INT:
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<unsigned short>>(
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<int>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
break;
|
||||||
break;
|
case DATA_TYPE_UINT:
|
||||||
case DATA_TYPE_INT:
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<unsigned int>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<int>>(
|
break;
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
case DATA_TYPE_LONG:
|
||||||
break;
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<long>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
case DATA_TYPE_UINT:
|
break;
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<unsigned int>>(
|
case DATA_TYPE_ULONG:
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<unsigned long>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_LONG:
|
case DATA_TYPE_LONG_LONG:
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<long>>(
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<long long>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
break;
|
||||||
break;
|
case DATA_TYPE_ULONG_LONG:
|
||||||
case DATA_TYPE_ULONG:
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<uint64_t>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<unsigned long>>(
|
break;
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
case DATA_TYPE_FLOAT:
|
||||||
break;
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<float>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
case DATA_TYPE_LONG_LONG:
|
break;
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<long long>>(
|
case DATA_TYPE_DOUBLE:
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<double>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_ULONG_LONG:
|
case DATA_TYPE_POINTER:
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<uint64_t>>(
|
script_context.SetResult(reinterpret_cast<std::add_pointer_t<void>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
break;
|
||||||
break;
|
case DATA_TYPE_STRING:
|
||||||
case DATA_TYPE_FLOAT:
|
script_context.SetResult(reinterpret_cast<std::add_pointer_t<char>>((uintptr_t)(instancePointer) + m_key.offset));
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<float>>(
|
break;
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
default:
|
||||||
break;
|
assert(!"Unknown function return type!");
|
||||||
case DATA_TYPE_DOUBLE:
|
break;
|
||||||
script_context.SetResult(*reinterpret_cast<std::add_pointer_t<double>>(
|
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
|
||||||
break;
|
|
||||||
case DATA_TYPE_POINTER:
|
|
||||||
script_context.SetResult(reinterpret_cast<std::add_pointer_t<void>>(
|
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
|
||||||
break;
|
|
||||||
case DATA_TYPE_STRING:
|
|
||||||
script_context.SetResult(reinterpret_cast<std::add_pointer_t<char>>(
|
|
||||||
(uintptr_t)(instancePointer) + m_key.offset));
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
assert(!"Unknown function return type!");
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -152,7 +136,9 @@ void SetSchemaValueByName(ScriptContext& script_context)
|
|||||||
auto className = script_context.GetArgument<const char*>(2);
|
auto className = script_context.GetArgument<const char*>(2);
|
||||||
auto memberName = script_context.GetArgument<const char*>(3);
|
auto memberName = script_context.GetArgument<const char*>(3);
|
||||||
|
|
||||||
if (globals::coreConfig->FollowCS2ServerGuidelines && std::find(schema::CS2BadList.begin(), schema::CS2BadList.end(), memberName) != schema::CS2BadList.end()) {
|
if (globals::coreConfig->FollowCS2ServerGuidelines &&
|
||||||
|
std::find(schema::CS2BadList.begin(), schema::CS2BadList.end(), memberName) != schema::CS2BadList.end())
|
||||||
|
{
|
||||||
CSSHARP_CORE_ERROR("Cannot set '{}::{}' with \"FollowCS2ServerGuidelines\" option enabled.", className, memberName);
|
CSSHARP_CORE_ERROR("Cannot set '{}::{}' with \"FollowCS2ServerGuidelines\" option enabled.", className, memberName);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -162,76 +148,68 @@ void SetSchemaValueByName(ScriptContext& script_context)
|
|||||||
|
|
||||||
const auto m_key = schema::GetOffset(className, classKey, memberName, memberKey);
|
const auto m_key = schema::GetOffset(className, classKey, memberName, memberKey);
|
||||||
|
|
||||||
switch (dataType) {
|
switch (dataType)
|
||||||
case DATA_TYPE_BOOL:
|
{
|
||||||
*reinterpret_cast<std::add_pointer_t<bool>>((uintptr_t)(instancePointer) + m_key.offset) =
|
case DATA_TYPE_BOOL:
|
||||||
script_context.GetArgument<bool>(4);
|
*reinterpret_cast<std::add_pointer_t<bool>>((uintptr_t)(instancePointer) + m_key.offset) = script_context.GetArgument<bool>(4);
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_CHAR:
|
case DATA_TYPE_CHAR:
|
||||||
*reinterpret_cast<std::add_pointer_t<char>>((uintptr_t)(instancePointer) + m_key.offset) =
|
*reinterpret_cast<std::add_pointer_t<char>>((uintptr_t)(instancePointer) + m_key.offset) = script_context.GetArgument<char>(4);
|
||||||
script_context.GetArgument<char>(4);
|
break;
|
||||||
break;
|
case DATA_TYPE_UCHAR:
|
||||||
case DATA_TYPE_UCHAR:
|
*reinterpret_cast<std::add_pointer_t<unsigned char>>((uintptr_t)(instancePointer) + m_key.offset) =
|
||||||
*reinterpret_cast<std::add_pointer_t<unsigned char>>((uintptr_t)(instancePointer) +
|
script_context.GetArgument<unsigned char>(4);
|
||||||
m_key.offset) =
|
break;
|
||||||
script_context.GetArgument<unsigned char>(4);
|
case DATA_TYPE_SHORT:
|
||||||
break;
|
*reinterpret_cast<std::add_pointer_t<short>>((uintptr_t)(instancePointer) + m_key.offset) =
|
||||||
case DATA_TYPE_SHORT:
|
script_context.GetArgument<short>(4);
|
||||||
*reinterpret_cast<std::add_pointer_t<short>>((uintptr_t)(instancePointer) + m_key.offset) =
|
break;
|
||||||
script_context.GetArgument<short>(4);
|
case DATA_TYPE_USHORT:
|
||||||
break;
|
*reinterpret_cast<std::add_pointer_t<unsigned short>>((uintptr_t)(instancePointer) + m_key.offset) =
|
||||||
case DATA_TYPE_USHORT:
|
script_context.GetArgument<unsigned short>(4);
|
||||||
*reinterpret_cast<std::add_pointer_t<unsigned short>>((uintptr_t)(instancePointer) +
|
break;
|
||||||
m_key.offset) =
|
case DATA_TYPE_INT:
|
||||||
script_context.GetArgument<unsigned short>(4);
|
*reinterpret_cast<std::add_pointer_t<int>>((uintptr_t)(instancePointer) + m_key.offset) = script_context.GetArgument<int>(4);
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_INT:
|
case DATA_TYPE_UINT:
|
||||||
*reinterpret_cast<std::add_pointer_t<int>>((uintptr_t)(instancePointer) + m_key.offset) =
|
*reinterpret_cast<std::add_pointer_t<unsigned int>>((uintptr_t)(instancePointer) + m_key.offset) =
|
||||||
script_context.GetArgument<int>(4);
|
script_context.GetArgument<unsigned int>(4);
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_UINT:
|
case DATA_TYPE_LONG:
|
||||||
*reinterpret_cast<std::add_pointer_t<unsigned int>>((uintptr_t)(instancePointer) +
|
*reinterpret_cast<std::add_pointer_t<long>>((uintptr_t)(instancePointer) + m_key.offset) = script_context.GetArgument<long>(4);
|
||||||
m_key.offset) =
|
break;
|
||||||
script_context.GetArgument<unsigned int>(4);
|
case DATA_TYPE_ULONG:
|
||||||
break;
|
*reinterpret_cast<std::add_pointer_t<unsigned long>>((uintptr_t)(instancePointer) + m_key.offset) =
|
||||||
case DATA_TYPE_LONG:
|
script_context.GetArgument<unsigned long>(4);
|
||||||
*reinterpret_cast<std::add_pointer_t<long>>((uintptr_t)(instancePointer) + m_key.offset) =
|
break;
|
||||||
script_context.GetArgument<long>(4);
|
case DATA_TYPE_LONG_LONG:
|
||||||
break;
|
*reinterpret_cast<std::add_pointer_t<long long>>((uintptr_t)(instancePointer) + m_key.offset) =
|
||||||
case DATA_TYPE_ULONG:
|
script_context.GetArgument<long long>(4);
|
||||||
*reinterpret_cast<std::add_pointer_t<unsigned long>>((uintptr_t)(instancePointer) +
|
break;
|
||||||
m_key.offset) =
|
case DATA_TYPE_ULONG_LONG:
|
||||||
script_context.GetArgument<unsigned long>(4);
|
*reinterpret_cast<std::add_pointer_t<uint64_t>>((uintptr_t)(instancePointer) + m_key.offset) =
|
||||||
break;
|
script_context.GetArgument<uint64_t>(4);
|
||||||
case DATA_TYPE_LONG_LONG:
|
break;
|
||||||
*reinterpret_cast<std::add_pointer_t<long long>>(
|
case DATA_TYPE_FLOAT:
|
||||||
(uintptr_t)(instancePointer) + m_key.offset) = script_context.GetArgument<long long>(4);
|
*reinterpret_cast<std::add_pointer_t<float>>((uintptr_t)(instancePointer) + m_key.offset) =
|
||||||
break;
|
script_context.GetArgument<float>(4);
|
||||||
case DATA_TYPE_ULONG_LONG:
|
break;
|
||||||
*reinterpret_cast<std::add_pointer_t<uint64_t>>(
|
case DATA_TYPE_DOUBLE:
|
||||||
(uintptr_t)(instancePointer) + m_key.offset) = script_context.GetArgument<uint64_t>(4);
|
*reinterpret_cast<std::add_pointer_t<double>>((uintptr_t)(instancePointer) + m_key.offset) =
|
||||||
break;
|
script_context.GetArgument<double>(4);
|
||||||
case DATA_TYPE_FLOAT:
|
break;
|
||||||
*reinterpret_cast<std::add_pointer_t<float>>((uintptr_t)(instancePointer) + m_key.offset) =
|
case DATA_TYPE_POINTER:
|
||||||
script_context.GetArgument<float>(4);
|
*reinterpret_cast<void**>((uintptr_t)(instancePointer) + m_key.offset) = script_context.GetArgument<void*>(4);
|
||||||
break;
|
break;
|
||||||
case DATA_TYPE_DOUBLE:
|
case DATA_TYPE_STRING:
|
||||||
*reinterpret_cast<std::add_pointer_t<double>>((uintptr_t)(instancePointer) + m_key.offset) =
|
{
|
||||||
script_context.GetArgument<double>(4);
|
auto duplicated = strdup(script_context.GetArgument<const char*>(4));
|
||||||
break;
|
*reinterpret_cast<char**>((uintptr_t)(instancePointer) + m_key.offset) = duplicated;
|
||||||
case DATA_TYPE_POINTER:
|
break;
|
||||||
*reinterpret_cast<void**>((uintptr_t)(instancePointer) + m_key.offset) =
|
}
|
||||||
script_context.GetArgument<void*>(4);
|
default:
|
||||||
break;
|
assert(!"Unknown function data type!");
|
||||||
case DATA_TYPE_STRING: {
|
break;
|
||||||
auto duplicated = strdup(script_context.GetArgument<const char*>(4));
|
|
||||||
*reinterpret_cast<char**>((uintptr_t)(instancePointer) + m_key.offset) =
|
|
||||||
duplicated;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
default:
|
|
||||||
assert(!"Unknown function data type!");
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -242,4 +220,4 @@ REGISTER_NATIVES(schema, {
|
|||||||
ScriptEngine::RegisterNativeHandler("SET_SCHEMA_VALUE_BY_NAME", SetSchemaValueByName);
|
ScriptEngine::RegisterNativeHandler("SET_SCHEMA_VALUE_BY_NAME", SetSchemaValueByName);
|
||||||
ScriptEngine::RegisterNativeHandler("GET_SCHEMA_CLASS_SIZE", GetSchemaClassSize);
|
ScriptEngine::RegisterNativeHandler("GET_SCHEMA_CLASS_SIZE", GetSchemaClassSize);
|
||||||
})
|
})
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -20,18 +20,13 @@
|
|||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
|
|
||||||
static void *GetEconItemSystem(ScriptContext& scriptContext) {
|
static void* GetEconItemSystem(ScriptContext& scriptContext) { return globals::serverManager.GetEconItemSystem(); }
|
||||||
return globals::serverManager.GetEconItemSystem();
|
|
||||||
}
|
|
||||||
|
|
||||||
static bool IsServerPaused(ScriptContext& scriptContext)
|
static bool IsServerPaused(ScriptContext& scriptContext) { return globals::serverManager.IsPaused(); }
|
||||||
{
|
|
||||||
return globals::serverManager.IsPaused();
|
|
||||||
}
|
|
||||||
|
|
||||||
REGISTER_NATIVES(server, {
|
REGISTER_NATIVES(server, {
|
||||||
ScriptEngine::RegisterNativeHandler("GET_ECON_ITEM_SYSTEM", GetEconItemSystem);
|
ScriptEngine::RegisterNativeHandler("GET_ECON_ITEM_SYSTEM", GetEconItemSystem);
|
||||||
ScriptEngine::RegisterNativeHandler("IS_SERVER_PAUSED", IsServerPaused);
|
ScriptEngine::RegisterNativeHandler("IS_SERVER_PAUSED", IsServerPaused);
|
||||||
})
|
})
|
||||||
|
|
||||||
}
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -21,7 +21,8 @@
|
|||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
|
|
||||||
timers::Timer *CreateTimer(ScriptContext &script_context) {
|
timers::Timer* CreateTimer(ScriptContext& script_context)
|
||||||
|
{
|
||||||
auto interval = script_context.GetArgument<float>(0);
|
auto interval = script_context.GetArgument<float>(0);
|
||||||
auto callback = script_context.GetArgument<CallbackT>(1);
|
auto callback = script_context.GetArgument<CallbackT>(1);
|
||||||
auto flags = script_context.GetArgument<int>(2);
|
auto flags = script_context.GetArgument<int>(2);
|
||||||
@@ -29,8 +30,9 @@ timers::Timer *CreateTimer(ScriptContext &script_context) {
|
|||||||
return globals::timerSystem.CreateTimer(interval, callback, flags);
|
return globals::timerSystem.CreateTimer(interval, callback, flags);
|
||||||
}
|
}
|
||||||
|
|
||||||
void KillTimer(ScriptContext &script_context) {
|
void KillTimer(ScriptContext& script_context)
|
||||||
auto timer = script_context.GetArgument<timers::Timer *>(0);
|
{
|
||||||
|
auto timer = script_context.GetArgument<timers::Timer*>(0);
|
||||||
globals::timerSystem.KillTimer(timer);
|
globals::timerSystem.KillTimer(timer);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -38,4 +40,4 @@ REGISTER_NATIVES(timers, {
|
|||||||
ScriptEngine::RegisterNativeHandler("CREATE_TIMER", CreateTimer);
|
ScriptEngine::RegisterNativeHandler("CREATE_TIMER", CreateTimer);
|
||||||
ScriptEngine::RegisterNativeHandler("KILL_TIMER", KillTimer);
|
ScriptEngine::RegisterNativeHandler("KILL_TIMER", KillTimer);
|
||||||
})
|
})
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -13,8 +13,6 @@
|
|||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
* along with CounterStrikeSharp. If not, see <https://www.gnu.org/licenses/>. *
|
||||||
*/
|
*/
|
||||||
// clang-format off
|
|
||||||
|
|
||||||
#include "core/UserMessage.h"
|
#include "core/UserMessage.h"
|
||||||
#include "core/globals.h"
|
#include "core/globals.h"
|
||||||
#include "core/log.h"
|
#include "core/log.h"
|
||||||
@@ -24,8 +22,6 @@
|
|||||||
|
|
||||||
#include "core/recipientfilters.h"
|
#include "core/recipientfilters.h"
|
||||||
|
|
||||||
// clang-format on
|
|
||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
|
|
||||||
#define GET_MESSAGE_OR_ERR() \
|
#define GET_MESSAGE_OR_ERR() \
|
||||||
@@ -620,13 +616,16 @@ static void UserMessageSend(ScriptContext& scriptContext)
|
|||||||
CRecipientFilter filter{};
|
CRecipientFilter filter{};
|
||||||
filter.AddRecipientsFromMask(message->GetRecipientMask() ? *message->GetRecipientMask() : 0);
|
filter.AddRecipientsFromMask(message->GetRecipientMask() ? *message->GetRecipientMask() : 0);
|
||||||
|
|
||||||
// This is for calling send in a UM hook, if calling normal send using the UM instance from the UM hook, it will cause an inifinite loop, then crashing the server
|
// This is for calling send in a UM hook, if calling normal send using the UM instance from the UM hook, it will cause an inifinite
|
||||||
static void (IGameEventSystem::*PostEventAbstract)(CSplitScreenSlot, bool, IRecipientFilter*, INetworkMessageInternal*, const CNetMessage*, unsigned long) = &IGameEventSystem::PostEventAbstract;
|
// loop, then crashing the server
|
||||||
|
static void (IGameEventSystem::*PostEventAbstract)(CSplitScreenSlot, bool, IRecipientFilter*, INetworkMessageInternal*,
|
||||||
|
const CNetMessage*, unsigned long) = &IGameEventSystem::PostEventAbstract;
|
||||||
|
|
||||||
if (message->IsManuallyAllocated())
|
if (message->IsManuallyAllocated())
|
||||||
globals::gameEventSystem->PostEventAbstract(0, false, &filter, message->GetSerializableMessage(), message->GetProtobufMessage(), 0);
|
globals::gameEventSystem->PostEventAbstract(0, false, &filter, message->GetSerializableMessage(), message->GetProtobufMessage(), 0);
|
||||||
else
|
else
|
||||||
SH_CALL(globals::gameEventSystem, PostEventAbstract)(0, false, &filter, message->GetSerializableMessage(), message->GetProtobufMessage(), 0);
|
SH_CALL(globals::gameEventSystem, PostEventAbstract)(0, false, &filter, message->GetSerializableMessage(),
|
||||||
|
message->GetProtobufMessage(), 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void UserMessageDelete(ScriptContext& scriptContext)
|
static void UserMessageDelete(ScriptContext& scriptContext)
|
||||||
|
|||||||
@@ -37,7 +37,8 @@ namespace counterstrikesharp {
|
|||||||
|
|
||||||
std::stack<std::string> errors;
|
std::stack<std::string> errors;
|
||||||
|
|
||||||
void ScriptContext::ThrowNativeError(const char *msg, ...) {
|
void ScriptContext::ThrowNativeError(const char* msg, ...)
|
||||||
|
{
|
||||||
va_list arglist;
|
va_list arglist;
|
||||||
char dest[256];
|
char dest[256];
|
||||||
va_start(arglist, msg);
|
va_start(arglist, msg);
|
||||||
@@ -49,13 +50,15 @@ void ScriptContext::ThrowNativeError(const char *msg, ...) {
|
|||||||
auto error_string = std::string(buff);
|
auto error_string = std::string(buff);
|
||||||
errors.push(error_string);
|
errors.push(error_string);
|
||||||
|
|
||||||
const char *ptr = errors.top().c_str();
|
const char* ptr = errors.top().c_str();
|
||||||
this->SetResult(ptr);
|
this->SetResult(ptr);
|
||||||
*this->m_has_error = 1;
|
*this->m_has_error = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ScriptContext::Reset() {
|
void ScriptContext::Reset()
|
||||||
if (*m_has_error) {
|
{
|
||||||
|
if (*m_has_error)
|
||||||
|
{
|
||||||
errors.pop();
|
errors.pop();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -63,36 +66,43 @@ void ScriptContext::Reset() {
|
|||||||
m_numArguments = 0;
|
m_numArguments = 0;
|
||||||
*m_has_error = 0;
|
*m_has_error = 0;
|
||||||
|
|
||||||
for (int i = 0; i < 32; i++) {
|
for (int i = 0; i < 32; i++)
|
||||||
|
{
|
||||||
m_native_context->arguments[i] = 0;
|
m_native_context->arguments[i] = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
m_native_context->result = 0;
|
m_native_context->result = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
tl::optional<TNativeHandler> ScriptEngine::GetNativeHandler(uint64_t nativeIdentifier) {
|
tl::optional<TNativeHandler> ScriptEngine::GetNativeHandler(uint64_t nativeIdentifier)
|
||||||
|
{
|
||||||
auto it = g_registeredHandlers.find(nativeIdentifier);
|
auto it = g_registeredHandlers.find(nativeIdentifier);
|
||||||
|
|
||||||
if (it != g_registeredHandlers.end()) {
|
if (it != g_registeredHandlers.end())
|
||||||
|
{
|
||||||
return it->second;
|
return it->second;
|
||||||
}
|
}
|
||||||
|
|
||||||
return tl::optional<TNativeHandler>();
|
return tl::optional<TNativeHandler>();
|
||||||
}
|
}
|
||||||
|
|
||||||
tl::optional<TNativeHandler> ScriptEngine::GetNativeHandler(std::string identifier) {
|
tl::optional<TNativeHandler> ScriptEngine::GetNativeHandler(std::string identifier)
|
||||||
|
{
|
||||||
auto it = g_registeredHandlers.find(hash_string(identifier.c_str()));
|
auto it = g_registeredHandlers.find(hash_string(identifier.c_str()));
|
||||||
|
|
||||||
if (it != g_registeredHandlers.end()) {
|
if (it != g_registeredHandlers.end())
|
||||||
|
{
|
||||||
return it->second;
|
return it->second;
|
||||||
}
|
}
|
||||||
|
|
||||||
return tl::optional<TNativeHandler>();
|
return tl::optional<TNativeHandler>();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ScriptEngine::CallNativeHandler(uint64_t nativeIdentifier, ScriptContext &context) {
|
bool ScriptEngine::CallNativeHandler(uint64_t nativeIdentifier, ScriptContext& context)
|
||||||
|
{
|
||||||
auto h = GetNativeHandler(nativeIdentifier);
|
auto h = GetNativeHandler(nativeIdentifier);
|
||||||
if (h) {
|
if (h)
|
||||||
|
{
|
||||||
(*h)(context);
|
(*h)(context);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
@@ -101,27 +111,30 @@ bool ScriptEngine::CallNativeHandler(uint64_t nativeIdentifier, ScriptContext &c
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ScriptEngine::RegisterNativeHandlerInt(uint64_t nativeIdentifier, TNativeHandler function) {
|
void ScriptEngine::RegisterNativeHandlerInt(uint64_t nativeIdentifier, TNativeHandler function)
|
||||||
|
{
|
||||||
g_registeredHandlers[nativeIdentifier] = function;
|
g_registeredHandlers[nativeIdentifier] = function;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ScriptEngine::InvokeNative(counterstrikesharp::fxNativeContext &context) {
|
void ScriptEngine::InvokeNative(counterstrikesharp::fxNativeContext& context)
|
||||||
|
{
|
||||||
if (context.nativeIdentifier == 0) return;
|
if (context.nativeIdentifier == 0) return;
|
||||||
|
|
||||||
auto nativeHandler =
|
auto nativeHandler = counterstrikesharp::ScriptEngine::GetNativeHandler(context.nativeIdentifier);
|
||||||
counterstrikesharp::ScriptEngine::GetNativeHandler(context.nativeIdentifier);
|
|
||||||
|
|
||||||
if (nativeHandler) {
|
if (nativeHandler)
|
||||||
|
{
|
||||||
counterstrikesharp::ScriptContextRaw scriptContext(context);
|
counterstrikesharp::ScriptContextRaw scriptContext(context);
|
||||||
|
|
||||||
(*nativeHandler)(scriptContext);
|
(*nativeHandler)(scriptContext);
|
||||||
} else {
|
}
|
||||||
CSSHARP_CORE_WARN("Native Handler was requested but not found: {0:x}",
|
else
|
||||||
context.nativeIdentifier);
|
{
|
||||||
|
CSSHARP_CORE_WARN("Native Handler was requested but not found: {0:x}", context.nativeIdentifier);
|
||||||
assert(false);
|
assert(false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ScriptContextRaw ScriptEngine::m_context;
|
ScriptContextRaw ScriptEngine::m_context;
|
||||||
|
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -33,41 +33,46 @@
|
|||||||
|
|
||||||
namespace counterstrikesharp {
|
namespace counterstrikesharp {
|
||||||
|
|
||||||
enum HookResult {
|
enum HookResult
|
||||||
|
{
|
||||||
Continue = 0,
|
Continue = 0,
|
||||||
Changed = 1,
|
Changed = 1,
|
||||||
Handled = 3,
|
Handled = 3,
|
||||||
Stop = 4,
|
Stop = 4,
|
||||||
};
|
};
|
||||||
|
|
||||||
enum HookMode {
|
enum HookMode
|
||||||
|
{
|
||||||
Pre = 0,
|
Pre = 0,
|
||||||
Post = 1,
|
Post = 1,
|
||||||
};
|
};
|
||||||
|
|
||||||
inline uint32_t hash_string(const char *string) {
|
inline uint32_t hash_string(const char* string)
|
||||||
unsigned long result = 5381;
|
|
||||||
|
|
||||||
for (size_t i = 0; i < strlen(string); i++) {
|
|
||||||
result = ((result << 5) + result) ^ string[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
template<size_t N>
|
|
||||||
constexpr uint32_t hash_string_const(char const (&string)[N])
|
|
||||||
{
|
{
|
||||||
unsigned long result = 5381;
|
unsigned long result = 5381;
|
||||||
|
|
||||||
for (size_t i = 0; i < N-1; i++) {
|
for (size_t i = 0; i < strlen(string); i++)
|
||||||
|
{
|
||||||
result = ((result << 5) + result) ^ string[i];
|
result = ((result << 5) + result) ^ string[i];
|
||||||
}
|
}
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct fxNativeContext {
|
template <size_t N> constexpr uint32_t hash_string_const(char const (&string)[N])
|
||||||
|
{
|
||||||
|
unsigned long result = 5381;
|
||||||
|
|
||||||
|
for (size_t i = 0; i < N - 1; i++)
|
||||||
|
{
|
||||||
|
result = ((result << 5) + result) ^ string[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct fxNativeContext
|
||||||
|
{
|
||||||
int numArguments;
|
int numArguments;
|
||||||
int numResults;
|
int numResults;
|
||||||
int hasError;
|
int hasError;
|
||||||
@@ -77,76 +82,83 @@ struct fxNativeContext {
|
|||||||
uint64_t result;
|
uint64_t result;
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef void (*CallbackT)(fxNativeContext *);
|
typedef void (*CallbackT)(fxNativeContext*);
|
||||||
|
|
||||||
class ScriptContext {
|
class ScriptContext
|
||||||
public:
|
{
|
||||||
enum { MaxArguments = 32, ArgumentSize = sizeof(uint64_t) };
|
public:
|
||||||
|
enum
|
||||||
|
{
|
||||||
|
MaxArguments = 32,
|
||||||
|
ArgumentSize = sizeof(uint64_t)
|
||||||
|
};
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void *m_argumentBuffer;
|
void* m_argumentBuffer;
|
||||||
|
|
||||||
int m_numArguments;
|
int m_numArguments;
|
||||||
int m_numResults;
|
int m_numResults;
|
||||||
int *m_has_error;
|
int* m_has_error;
|
||||||
uint64_t *m_nativeIdentifier;
|
uint64_t* m_nativeIdentifier;
|
||||||
void *m_result;
|
void* m_result;
|
||||||
|
|
||||||
fxNativeContext *m_native_context;
|
fxNativeContext* m_native_context;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
inline ScriptContext() = default;
|
inline ScriptContext() = default;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
void ThrowNativeError(const char *msg, ...);
|
void ThrowNativeError(const char* msg, ...);
|
||||||
bool HasError() { return *m_has_error == 1; }
|
bool HasError() { return *m_has_error == 1; }
|
||||||
void Reset();
|
void Reset();
|
||||||
|
|
||||||
public:
|
public:
|
||||||
template <int... Is>
|
template <int... Is> struct index
|
||||||
struct index {};
|
{
|
||||||
|
};
|
||||||
|
|
||||||
template <int N, int... Is>
|
template <int N, int... Is> struct gen_seq : gen_seq<N - 1, N - 1, Is...>
|
||||||
struct gen_seq : gen_seq<N - 1, N - 1, Is...> {};
|
{
|
||||||
|
};
|
||||||
|
|
||||||
template <int... Is>
|
template <int... Is> struct gen_seq<0, Is...> : index<Is...>
|
||||||
struct gen_seq<0, Is...> : index<Is...> {};
|
{
|
||||||
|
};
|
||||||
|
|
||||||
template <typename... Ts>
|
template <typename... Ts> inline const std::tuple<Ts...> GetArguments() { return GetArgumentsImpl<Ts...>(gen_seq<sizeof...(Ts)>()); }
|
||||||
inline const std::tuple<Ts...> GetArguments() {
|
|
||||||
return GetArgumentsImpl<Ts...>(gen_seq<sizeof...(Ts)>());
|
|
||||||
}
|
|
||||||
|
|
||||||
template <typename... Ts, int... Is>
|
template <typename... Ts, int... Is> inline const std::tuple<Ts...> GetArgumentsImpl(index<Is...>)
|
||||||
inline const std::tuple<Ts...> GetArgumentsImpl(index<Is...>) {
|
{
|
||||||
return std::make_tuple(GetArgument<Ts>(Is)...);
|
return std::make_tuple(GetArgument<Ts>(Is)...);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename T>
|
template <typename T> inline const T& GetArgument(int index)
|
||||||
inline const T &GetArgument(int index) {
|
{
|
||||||
auto functionData = (uint64_t *)m_argumentBuffer;
|
auto functionData = (uint64_t*)m_argumentBuffer;
|
||||||
|
|
||||||
return *reinterpret_cast<T *>(&functionData[index]);
|
return *reinterpret_cast<T*>(&functionData[index]);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename T>
|
template <typename T> inline void SetArgument(int index, const T& value)
|
||||||
inline void SetArgument(int index, const T &value) {
|
{
|
||||||
auto functionData = (uint64_t *)m_argumentBuffer;
|
auto functionData = (uint64_t*)m_argumentBuffer;
|
||||||
|
|
||||||
static_assert(sizeof(T) <= ArgumentSize, "Argument size of T");
|
static_assert(sizeof(T) <= ArgumentSize, "Argument size of T");
|
||||||
|
|
||||||
if (sizeof(T) < ArgumentSize) {
|
if (sizeof(T) < ArgumentSize)
|
||||||
*reinterpret_cast<uint64_t *>(&functionData[index]) = 0;
|
{
|
||||||
|
*reinterpret_cast<uint64_t*>(&functionData[index]) = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
*reinterpret_cast<T *>(&functionData[index]) = value;
|
*reinterpret_cast<T*>(&functionData[index]) = value;
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename T>
|
template <typename T> inline const T& CheckArgument(int index)
|
||||||
inline const T &CheckArgument(int index) {
|
{
|
||||||
const auto &argument = GetArgument<T>(index);
|
const auto& argument = GetArgument<T>(index);
|
||||||
|
|
||||||
if (argument == T()) {
|
if (argument == T())
|
||||||
|
{
|
||||||
throw std::runtime_error("Argument at index %d was null.");
|
throw std::runtime_error("Argument at index %d was null.");
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -155,56 +167,61 @@ public:
|
|||||||
|
|
||||||
inline int GetArgumentCount() { return m_numArguments; }
|
inline int GetArgumentCount() { return m_numArguments; }
|
||||||
|
|
||||||
template <typename T>
|
template <typename T> inline void Push(const T& value)
|
||||||
inline void Push(const T &value) {
|
{
|
||||||
auto functionData = (uint64_t *)m_argumentBuffer;
|
auto functionData = (uint64_t*)m_argumentBuffer;
|
||||||
|
|
||||||
static_assert(sizeof(T) <= ArgumentSize, "Argument size of T");
|
static_assert(sizeof(T) <= ArgumentSize, "Argument size of T");
|
||||||
|
|
||||||
if (sizeof(T) < ArgumentSize) {
|
if (sizeof(T) < ArgumentSize)
|
||||||
*reinterpret_cast<uint64_t *>(&functionData[m_numArguments]) = 0;
|
{
|
||||||
|
*reinterpret_cast<uint64_t*>(&functionData[m_numArguments]) = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
*reinterpret_cast<T *>(&functionData[m_numArguments]) = value;
|
*reinterpret_cast<T*>(&functionData[m_numArguments]) = value;
|
||||||
m_numArguments++;
|
m_numArguments++;
|
||||||
m_native_context->numArguments++;
|
m_native_context->numArguments++;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline void PushString(const char *value) {
|
inline void PushString(const char* value)
|
||||||
auto functionData = (uint64_t *)m_argumentBuffer;
|
{
|
||||||
|
auto functionData = (uint64_t*)m_argumentBuffer;
|
||||||
|
|
||||||
*reinterpret_cast<const char **>(&functionData[m_numArguments]) = value;
|
*reinterpret_cast<const char**>(&functionData[m_numArguments]) = value;
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename T>
|
template <typename T> inline void SetResult(const T& value)
|
||||||
inline void SetResult(const T &value) {
|
{
|
||||||
auto functionData = (uint64_t *)m_result;
|
auto functionData = (uint64_t*)m_result;
|
||||||
|
|
||||||
if (sizeof(T) < ArgumentSize) {
|
if (sizeof(T) < ArgumentSize)
|
||||||
*reinterpret_cast<uint64_t *>(&functionData[0]) = 0;
|
{
|
||||||
|
*reinterpret_cast<uint64_t*>(&functionData[0]) = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
*reinterpret_cast<T *>(&functionData[0]) = value;
|
*reinterpret_cast<T*>(&functionData[0]) = value;
|
||||||
|
|
||||||
m_numResults = 1;
|
m_numResults = 1;
|
||||||
m_numArguments = 0;
|
m_numArguments = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename T>
|
template <typename T> inline T GetResult()
|
||||||
inline T GetResult() {
|
{
|
||||||
auto functionData = (uint64_t *)m_result;
|
auto functionData = (uint64_t*)m_result;
|
||||||
|
|
||||||
return *reinterpret_cast<T *>(functionData);
|
return *reinterpret_cast<T*>(functionData);
|
||||||
}
|
}
|
||||||
|
|
||||||
inline void *GetArgumentBuffer() { return m_argumentBuffer; }
|
inline void* GetArgumentBuffer() { return m_argumentBuffer; }
|
||||||
|
|
||||||
inline int GetNumArguments() { return m_native_context->numArguments; }
|
inline int GetNumArguments() { return m_native_context->numArguments; }
|
||||||
};
|
};
|
||||||
|
|
||||||
class ScriptContextRaw : public ScriptContext {
|
class ScriptContextRaw : public ScriptContext
|
||||||
public:
|
{
|
||||||
inline ScriptContextRaw(fxNativeContext &context) {
|
public:
|
||||||
|
inline ScriptContextRaw(fxNativeContext& context)
|
||||||
|
{
|
||||||
m_argumentBuffer = context.arguments;
|
m_argumentBuffer = context.arguments;
|
||||||
|
|
||||||
m_numArguments = context.numArguments;
|
m_numArguments = context.numArguments;
|
||||||
@@ -215,31 +232,33 @@ public:
|
|||||||
m_result = &context.result;
|
m_result = &context.result;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline ScriptContextRaw() {
|
inline ScriptContextRaw()
|
||||||
|
{
|
||||||
m_numResults = 0;
|
m_numResults = 0;
|
||||||
m_numArguments = 0;
|
m_numArguments = 0;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
using TNativeHandler = std::function<void(ScriptContext &)>;
|
using TNativeHandler = std::function<void(ScriptContext&)>;
|
||||||
|
|
||||||
template <typename T>
|
template <typename T> using TypedTNativeHandler = T(ScriptContext&);
|
||||||
using TypedTNativeHandler = T(ScriptContext &);
|
|
||||||
|
|
||||||
class ScriptEngine {
|
class ScriptEngine
|
||||||
public:
|
{
|
||||||
|
public:
|
||||||
static tl::optional<TNativeHandler> GetNativeHandler(uint64_t nativeIdentifier);
|
static tl::optional<TNativeHandler> GetNativeHandler(uint64_t nativeIdentifier);
|
||||||
static tl::optional<TNativeHandler> GetNativeHandler(std::string name);
|
static tl::optional<TNativeHandler> GetNativeHandler(std::string name);
|
||||||
|
|
||||||
static bool CallNativeHandler(uint64_t nativeIdentifier, ScriptContext &context);
|
static bool CallNativeHandler(uint64_t nativeIdentifier, ScriptContext& context);
|
||||||
|
|
||||||
static void RegisterNativeHandlerInt(uint64_t nativeIdentifier, TNativeHandler function);
|
static void RegisterNativeHandlerInt(uint64_t nativeIdentifier, TNativeHandler function);
|
||||||
|
|
||||||
template <typename T>
|
template <typename T> static void RegisterNativeHandler(const char* nativeName, TypedTNativeHandler<T> function)
|
||||||
static void RegisterNativeHandler(const char *nativeName, TypedTNativeHandler<T> function) {
|
{
|
||||||
auto lambda = [=](counterstrikesharp::ScriptContext &context) {
|
auto lambda = [=](counterstrikesharp::ScriptContext& context) {
|
||||||
auto value = function(context);
|
auto value = function(context);
|
||||||
if (!context.HasError()) {
|
if (!context.HasError())
|
||||||
|
{
|
||||||
context.SetResult(value);
|
context.SetResult(value);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
@@ -247,13 +266,14 @@ public:
|
|||||||
RegisterNativeHandlerInt(hash_string(nativeName), lambda);
|
RegisterNativeHandlerInt(hash_string(nativeName), lambda);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void RegisterNativeHandler(const char *nativeName, TypedTNativeHandler<void> function) {
|
static void RegisterNativeHandler(const char* nativeName, TypedTNativeHandler<void> function)
|
||||||
|
{
|
||||||
RegisterNativeHandlerInt(hash_string(nativeName), function);
|
RegisterNativeHandlerInt(hash_string(nativeName), function);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void InvokeNative(counterstrikesharp::fxNativeContext &context);
|
static void InvokeNative(counterstrikesharp::fxNativeContext& context);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
static ScriptContextRaw m_context;
|
static ScriptContextRaw m_context;
|
||||||
};
|
};
|
||||||
} // namespace counterstrikesharp
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -23,7 +23,8 @@ std::wstring widen(const std::string& str)
|
|||||||
{
|
{
|
||||||
std::wostringstream wstm;
|
std::wostringstream wstm;
|
||||||
const auto& ctfacet = std::use_facet<std::ctype<wchar_t>>(wstm.getloc());
|
const auto& ctfacet = std::use_facet<std::ctype<wchar_t>>(wstm.getloc());
|
||||||
for (size_t i = 0; i < str.size(); ++i) {
|
for (size_t i = 0; i < str.size(); ++i)
|
||||||
|
{
|
||||||
wstm << ctfacet.widen(str[i]);
|
wstm << ctfacet.widen(str[i]);
|
||||||
}
|
}
|
||||||
return wstm.str();
|
return wstm.str();
|
||||||
@@ -39,9 +40,10 @@ std::string narrow(const std::wstring& str)
|
|||||||
// Correct code.
|
// Correct code.
|
||||||
const auto& ctfacet = std::use_facet<std::ctype<wchar_t>>(stm.getloc());
|
const auto& ctfacet = std::use_facet<std::ctype<wchar_t>>(stm.getloc());
|
||||||
|
|
||||||
for (size_t i = 0; i < str.size(); ++i) {
|
for (size_t i = 0; i < str.size(); ++i)
|
||||||
|
{
|
||||||
stm << ctfacet.narrow(str[i], 0);
|
stm << ctfacet.narrow(str[i], 0);
|
||||||
}
|
}
|
||||||
return stm.str();
|
return stm.str();
|
||||||
}
|
}
|
||||||
}
|
} // namespace counterstrikesharp
|
||||||
|
|||||||
@@ -23,31 +23,34 @@
|
|||||||
#define CALL_VIRTUAL(retType, idx, ...) vmt::CallVirtual<retType>(idx, __VA_ARGS__)
|
#define CALL_VIRTUAL(retType, idx, ...) vmt::CallVirtual<retType>(idx, __VA_ARGS__)
|
||||||
|
|
||||||
namespace vmt {
|
namespace vmt {
|
||||||
template <typename T = void *>
|
template <typename T = void*> inline T GetVMethod(uint32 uIndex, void* pClass)
|
||||||
inline T GetVMethod(uint32 uIndex, void *pClass) {
|
{
|
||||||
if (!pClass) {
|
if (!pClass)
|
||||||
|
{
|
||||||
return T();
|
return T();
|
||||||
}
|
}
|
||||||
|
|
||||||
void **pVTable = *static_cast<void ***>(pClass);
|
void** pVTable = *static_cast<void***>(pClass);
|
||||||
if (!pVTable) {
|
if (!pVTable)
|
||||||
|
{
|
||||||
return T();
|
return T();
|
||||||
}
|
}
|
||||||
|
|
||||||
return reinterpret_cast<T>(pVTable[uIndex]);
|
return reinterpret_cast<T>(pVTable[uIndex]);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename T, typename... Args>
|
template <typename T, typename... Args> inline T CallVirtual(uint32 uIndex, void* pClass, Args... args)
|
||||||
inline T CallVirtual(uint32 uIndex, void *pClass, Args... args) {
|
{
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
auto pFunc = GetVMethod<T(__thiscall *)(void *, Args...)>(uIndex, pClass);
|
auto pFunc = GetVMethod<T(__thiscall*)(void*, Args...)>(uIndex, pClass);
|
||||||
#else
|
#else
|
||||||
auto pFunc = GetVMethod<T(*)(void *, Args...)>(uIndex, pClass);
|
auto pFunc = GetVMethod<T (*)(void*, Args...)>(uIndex, pClass);
|
||||||
#endif
|
#endif
|
||||||
if (!pFunc) {
|
if (!pFunc)
|
||||||
|
{
|
||||||
return T();
|
return T();
|
||||||
}
|
}
|
||||||
|
|
||||||
return pFunc(pClass, args...);
|
return pFunc(pClass, args...);
|
||||||
}
|
}
|
||||||
} // namespace vmt
|
} // namespace vmt
|
||||||
|
|||||||
Reference in New Issue
Block a user