CDirector::TryToStartSurvivorRescue
0x00881ca0 · 1068 bytes · __thiscall
_ZN9CDirector24TryToStartSurvivorRescueEbP13CTerrorPlayer
Decompiled
undefined (3 params)
/* CDirector::TryToStartSurvivorRescue(bool, CTerrorPlayer*) */
void __thiscall
CDirector::TryToStartSurvivorRescue(CDirector *this,bool param_1,CTerrorPlayer *param_2)
{
float fVar1;
float fVar2;
char cVar3;
TerrorNavArea *pTVar4;
undefined4 uVar5;
undefined4 uVar6;
undefined4 *puVar7;
Vector *pVVar8;
int iVar9;
CSurvivorRescue *this_00;
CSurvivorRescue *this_01;
longdouble lVar10;
undefined4 uVar11;
undefined4 uVar12;
float local_3c;
undefined4 local_20 [4];
if (param_1) {
fVar1 = *(float *)(RescueFinaleSpawnRange._28_4_ + 0x2c);
}
else {
fVar1 = *(float *)(RescueSpawnRange._28_4_ + 0x2c);
}
this_01 = (CSurvivorRescue *)0x0;
local_3c = 3.4028235e+38;
this_00 = (CSurvivorRescue *)0x0;
LAB_00881cf0:
do {
do {
this_01 = (CSurvivorRescue *)
CGlobalEntityList::FindEntityByClassname
((CGlobalEntityList *)gEntList,(CBaseEntity *)this_01,
"info_survivor_rescue");
if (this_01 == (CSurvivorRescue *)0x0) {
if (this_00 != (CSurvivorRescue *)0x0) {
cVar3 = CSurvivorRescue::CloseDoors(this_00);
uVar11 = SUB84((double)local_3c,0);
uVar12 = (undefined4)((ulonglong)(double)local_3c >> 0x20);
if (cVar3 != '\0') {
uVar5 = CBaseEntity::GetDebugName((CBaseEntity *)this_00);
if (*(int *)(this_00 + 0x30) == 0) {
iVar9 = 0;
}
else {
iVar9 = *(int *)(this_00 + 0x30) - *(int *)(gpGlobals + 0x58) >> 4;
}
DevMsg("rescue spot %d(%s) closes door to start calling for help with nearest survivor %.1f path units away\n"
,iVar9,uVar5,uVar11,uVar12);
return;
}
uVar5 = (**(code **)(*(int *)param_2 + 0xb8))(param_2);
uVar6 = CBaseEntity::GetDebugName((CBaseEntity *)this_00);
if (*(int *)(this_00 + 0x30) == 0) {
iVar9 = 0;
}
else {
iVar9 = *(int *)(this_00 + 0x30) - *(int *)(gpGlobals + 0x58) >> 4;
}
DevMsg("rescue spot %d(%s) starts calling for help for %s with nearest survivor %.1f path units away\n"
,iVar9,uVar6,uVar5,uVar11,uVar12);
local_20[0] = 0xffffffff;
puVar7 = (undefined4 *)(**(code **)(*(int *)this_00 + 0xc))(this_00);
local_20[0] = *puVar7;
CUtlVector<CHandle<CSurvivorRescue>,CUtlMemory<CHandle<CSurvivorRescue>,int>>::
InsertBefore((CUtlVector<CHandle<CSurvivorRescue>,CUtlMemory<CHandle<CSurvivorRescue>,int>>
*)(this + 0x3e0),*(int *)(this + 0x3ec),(CHandle *)local_20);
CSurvivorRescue::CallForHelp(this_00,param_2);
lVar10 = (longdouble)CountdownTimer::Now();
if ((float)lVar10 + 0.1 != *(float *)(this + 0x3dc)) {
(**(code **)(*(int *)(this + 0x3d4) + 4))(this + 0x3d4,this + 0x3dc);
*(float *)(this + 0x3dc) = (float)lVar10 + 0.1;
}
if (*(float *)(this + 0x3d8) != 0.1) {
(**(code **)(*(int *)(this + 0x3d4) + 4))(this + 0x3d4,this + 0x3d8);
*(undefined4 *)(this + 0x3d8) = 0x3dcccccd;
return;
}
}
return;
}
cVar3 = CSurvivorRescue::IsCallingForHelp(this_01);
} while (cVar3 != '\0');
if (param_1) goto LAB_00881e00;
} while (*(int *)(this_01 + 0x1934) != 0);
pTVar4 = (TerrorNavArea *)CSurvivorRescue::GetRescueNavArea(this_01);
goto LAB_00881d3c;
LAB_00881e00:
pTVar4 = (TerrorNavArea *)CSurvivorRescue::GetRescueNavArea(this_01);
if ((pTVar4 != (TerrorNavArea *)0x0) && ((*(uint *)(pTVar4 + 300) & 0x140) != 0)) {
LAB_00881d3c:
cVar3 = CSurvivorRescue::IsLiveSurvivorInside(this_01);
if (cVar3 == '\0') {
cVar3 = CSurvivorRescue::IsBehindClosedDoor(this_01);
if (cVar3 == '\0') {
pVVar8 = (Vector *)(**(code **)(*(int *)this_01 + 0x288))(this_01);
cVar3 = CDirectorTacticalServices::IsVisibleToTeam
(*(CDirectorTacticalServices **)(this + 0x628),pVVar8,2,0,0.0,pTVar4,
(CBaseEntity *)this_01);
if (cVar3 != '\0') goto LAB_00881cf0;
}
if (this_00 == (CSurvivorRescue *)0x0) {
lVar10 = (longdouble)CSurvivorRescue::GetDistanceToNearestSurvivor(this_01,fVar1 + 500.0);
fVar2 = (float)lVar10;
if (0.0 <= fVar2) {
if (fVar2 <= fVar1) {
this_00 = this_01;
}
local_3c = (float)(~-(uint)(fVar1 < fVar2) & (uint)fVar2 |
(uint)local_3c & -(uint)(fVar1 < fVar2));
}
}
else if ((*(int *)(this_01 + 0x1934) <= *(int *)(this_00 + 0x1934)) &&
((cVar3 = CSurvivorRescue::IsBehindClosedDoor(this_01), cVar3 != '\0' ||
(cVar3 = CSurvivorRescue::IsBehindClosedDoor(this_00), cVar3 == '\0')))) {
lVar10 = (longdouble)CSurvivorRescue::GetDistanceToNearestSurvivor(this_01,fVar1 + 500.0);
fVar2 = (float)lVar10;
if (((0.0 <= fVar2) && (fVar2 <= fVar1)) &&
((((cVar3 = CSurvivorRescue::IsBehindClosedDoor(this_00), cVar3 == '\0' &&
(cVar3 = CSurvivorRescue::IsBehindClosedDoor(this_01), cVar3 != '\0')) ||
(*(int *)(this_01 + 0x1934) < *(int *)(this_00 + 0x1934))) || (fVar2 < local_3c)))) {
this_00 = this_01;
local_3c = fVar2;
}
}
}
}
goto LAB_00881cf0;
}
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.