L L4D2node

CDirector::TryOfferingTankFromLastMap

0x00881390 · 774 bytes · __thiscall

_ZN9CDirector26TryOfferingTankFromLastMapEv

Decompiled

undefined (1 param)

/* CDirector::TryOfferingTankFromLastMap() */

void __thiscall CDirector::TryOfferingTankFromLastMap(CDirector *this)

{
  int *piVar1;
  float fVar2;
  float fVar3;
  uint uVar4;
  uint uVar5;
  char cVar6;
  CCSPlayer *this_00;
  uint *puVar7;
  int iVar8;
  CEventLog *this_01;
  undefined4 uVar9;
  undefined4 uVar10;
  undefined4 *puVar11;
  undefined *puVar12;
  int iVar13;
  int iVar14;
  longdouble lVar15;
  undefined4 local_20 [4];
  
  if ((((*(int *)(this + 0x394) != 0) &&
       (this_00 = (CCSPlayer *)UTIL_PlayerByUserId(*(int *)(this + 0x394)),
       this_00 != (CCSPlayer *)0x0)) &&
      (cVar6 = (**(code **)(*(int *)this_00 + 0x16c))(this_00), cVar6 != '\0')) &&
     (*(undefined4 *)(this + 0x394) = 0, *(int *)(this + 0x1c0) < 1)) {
    fVar2 = *(float *)(DirectorSpecialOriginalOfferLength._28_4_ + 0x2c);
    puVar7 = (uint *)(**(code **)(*(int *)this_00 + 0xc))(this_00);
    uVar4 = *puVar7;
    if (0 < *(int *)(this + 0x40c)) {
      iVar8 = 0;
      piVar1 = (int *)(g_pEntityList + (uVar4 & 0xfff) * 0x10 + 4);
      do {
        iVar13 = 0;
        if (uVar4 != 0xffffffff) {
          if (piVar1 == (int *)0x0) {
            iVar13 = 0;
          }
          else if (piVar1[1] == uVar4 >> 0xc) {
            iVar13 = *piVar1;
          }
        }
        uVar5 = *(uint *)(*(int *)(this + 0x400) + iVar8 * 4);
        iVar14 = 0;
        if (((uVar5 != 0xffffffff) &&
            (puVar12 = g_pEntityList + (uVar5 & 0xfff) * 0x10, puVar12 != (undefined *)0xfffffffc))
           && (*(uint *)(puVar12 + 8) == uVar5 >> 0xc)) {
          iVar14 = *(int *)(puVar12 + 4);
        }
        if (iVar13 == iVar14) {
          return;
        }
        iVar8 = iVar8 + 1;
      } while (iVar8 != *(int *)(this + 0x40c));
    }
    lVar15 = (longdouble)
             RandomFloat(*(undefined4 *)(DirectorTankMinInterval._28_4_ + 0x2c),
                         *(undefined4 *)(DirectorTankMaxInterval._28_4_ + 0x2c));
    fVar3 = (float)lVar15;
    lVar15 = (longdouble)CountdownTimer::Now();
    if ((float)lVar15 + fVar3 != *(float *)(this + 0x174)) {
      (**(code **)(*(int *)(this + 0x16c) + 4))(this + 0x16c,this + 0x174);
      *(float *)(this + 0x174) = (float)lVar15 + fVar3;
    }
    if (fVar3 != *(float *)(this + 0x170)) {
      (**(code **)(*(int *)(this + 0x16c) + 4))(this + 0x16c,this + 0x170);
      *(float *)(this + 0x170) = fVar3;
    }
    this_01 = (CEventLog *)TheLog();
    uVar9 = CEventLog::FormatPlayer(this_01,(CBaseEntity *)this_00);
    uVar10 = ZombieClassName(8);
    UTIL_LogPrintf("Offer for %s: %s re-accepted the offer after transition.  Spawning in %d seconds.\n"
                   ,uVar10,uVar9,(int)fVar2);
    local_20[0] = 0xffffffff;
    puVar11 = (undefined4 *)(**(code **)(*(int *)this_00 + 0xc))(this_00);
    local_20[0] = *puVar11;
    CUtlVector<CHandle<CTerrorPlayer>,CUtlMemory<CHandle<CTerrorPlayer>,int>>::InsertBefore
              ((CUtlVector<CHandle<CTerrorPlayer>,CUtlMemory<CHandle<CTerrorPlayer>,int>> *)
               (this + 0x400),*(int *)(this + 0x40c),(CHandle *)local_20);
    lVar15 = (longdouble)CountdownTimer::Now();
    if ((float)lVar15 + fVar2 != *(float *)(this + 0x3fc)) {
      (**(code **)(*(int *)(this + 0x3f4) + 4))(this + 0x3f4,this + 0x3fc);
      *(float *)(this + 0x3fc) = (float)lVar15 + fVar2;
    }
    if (fVar2 != *(float *)(this + 0x3f8)) {
      (**(code **)(*(int *)(this + 0x3f4) + 4))(this + 0x3f4,this + 0x3f8);
      *(float *)(this + 0x3f8) = fVar2;
    }
    CCSPlayer::EmitPrivateSound(this_00,"Event.NewAvailableZombie");
  }
  return;
}

SourceMod gamedata

paste into addons/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.



        

        

          

Type inference is best-effort from the C signature - sanity-check the DHooks types before shipping.

Return-type handling cheatsheet (DHookReturn)