CBaseServer::Shutdown
0x0010c070 · 548 bytes · __thiscall
_ZN11CBaseServer8ShutdownEv
Decompiled
undefined (1 param)
/* CBaseServer::Shutdown() */
void __thiscall CBaseServer::Shutdown(CBaseServer *this)
{
char cVar1;
int *piVar2;
int iVar3;
int iVar4;
int iVar5;
int local_40;
CBaseClient *local_34;
int local_30 [8];
cVar1 = (**(code **)(*(int *)this + 0x58))(this);
if (cVar1 != '\0') {
*(undefined4 *)(this + 4) = 0;
local_30[0] = 0;
local_30[1] = 0;
local_30[2] = 0;
local_30[3] = 0;
local_30[4] = 0;
local_40 = 3;
do {
if (0 < *(int *)(this + 0x120)) {
iVar5 = 0;
do {
piVar2 = *(int **)(*(int *)(this + 0x114) + iVar5 * 4);
/* try { // try from 0010c0e1 to 0010c275 has its CatchHandler @ 0010c29b */
piVar2 = (int *)(**(code **)(*piVar2 + 0x20))(piVar2);
if (piVar2 != (int *)0x0) {
(**(code **)(*piVar2 + 0xc4))(piVar2,0);
}
iVar5 = iVar5 + 1;
} while (iVar5 < *(int *)(this + 0x120));
}
Sys_Sleep(10);
local_40 = local_40 + -1;
} while (local_40 != 0);
local_40 = *(int *)(this + 0x120) + -1;
if (-1 < local_40) {
iVar5 = *(int *)(this + 0x120) << 2;
do {
local_34 = *(CBaseClient **)(*(int *)(this + 0x114) + -4 + iVar5);
cVar1 = (**(code **)(*(int *)local_34 + 0x6c))(local_34);
if (cVar1 == '\0') {
(**(code **)(*(int *)local_34 + 0x54))();
}
else {
cVar1 = (**(code **)(*(int *)local_34 + 0x94))(local_34);
if (cVar1 != '\0') {
local_34[0x10] = (CBaseClient)0x0;
}
(**(code **)(*(int *)local_34 + 0x3c))(local_34,"Server shutting down");
}
CUtlVector<CBaseClient*,CUtlMemory<CBaseClient*,int>>::InsertBefore
((CUtlVector<CBaseClient*,CUtlMemory<CBaseClient*,int>> *)local_30,local_30[3],
&local_34);
iVar3 = *(int *)(this + 0x120);
iVar4 = (iVar3 - local_40) + -1;
if (0 < iVar4) {
_V_memmove((void *)(*(int *)(this + 0x114) + iVar5 + -4),
(void *)(iVar5 + *(int *)(this + 0x114)),iVar4 * 4);
iVar3 = *(int *)(this + 0x120);
}
local_40 = local_40 + -1;
*(int *)(this + 0x120) = iVar3 + -1;
iVar5 = iVar5 + -4;
} while (local_40 != -1);
}
Sys_Sleep(100);
iVar5 = Steam3Server();
if (*(int *)(iVar5 + 4) != 0) {
iVar5 = Steam3Server();
(**(code **)(**(int **)(iVar5 + 4) + 0x1c))(*(int **)(iVar5 + 4));
}
Sys_Sleep(100);
if (0 < local_30[3]) {
iVar5 = 0;
do {
piVar2 = *(int **)(local_30[0] + iVar5 * 4);
if (piVar2 != (int *)0x0) {
(**(code **)(*piVar2 + 4))(piVar2);
}
iVar5 = iVar5 + 1;
} while (iVar5 < local_30[3]);
}
(**(code **)(*(int *)this + 0xa8))(this);
(**(code **)(*(int *)g_pMaster + 0xc))(g_pMaster,this);
local_30[3] = 0;
CUtlMemory<CBaseClient*,int>::Purge((CUtlMemory<CBaseClient*,int> *)local_30);
local_30[4] = local_30[0];
CUtlMemory<CBaseClient*,int>::Purge((CUtlMemory<CBaseClient*,int> *)local_30);
return;
}
return;
}
SourceMod gamedata
paste intoaddons/sourcemod/gamedata/<your_plugin>.txt
used as the SourceMod key — change to fit your plugin's convention
SourceMod library name (server / engine / matchmaking)
Just a Signatures{} block, ready to drop into a gamedata
file. Wire it up in your plugin however you like - SDKCall, DHooks,
raw memory ops, or anything else.
Signatures + Functions block. The plugin uses
DHookCreateFromConf - DHooks reads return type, this-type,
calling convention, and argument types straight from the gamedata. Less
boilerplate in the plugin, types travel with the gamedata.
Gamedata KeyValues
DHooks plugin example
Type inference is best-effort from the C signature - sanity-check the DHooks types before shipping.