1.1 --- a/extensions/tf2/conditions.cpp Fri Dec 21 01:17:30 2012 -0500
1.2 +++ b/extensions/tf2/conditions.cpp Sun Dec 23 16:59:50 2012 -0500
1.3 @@ -33,33 +33,35 @@
1.4 #include "conditions.h"
1.5 #include "util.h"
1.6
1.7 +#include "bitvec.h"
1.8 +
1.9 #include <iplayerinfo.h>
1.10
1.11 -typedef uint64_t condflags_t;
1.12 +typedef CBitVec<96> condbits_t;
1.13
1.14 -condflags_t g_PlayerConds[MAXPLAYERS+1];
1.15 +condbits_t g_PlayerConds[MAXPLAYERS+1];
1.16
1.17 IForward *g_addCondForward = NULL;
1.18 IForward *g_removeCondForward = NULL;
1.19
1.20 int playerCondOffset = -1;
1.21 int playerCondExOffset = -1;
1.22 +int playerCondEx2Offset = -1;
1.23 int conditionBitsOffset = -1;
1.24
1.25 bool g_bIgnoreRemove;
1.26
1.27 -#define MAX_CONDS (sizeof(uint64_t) * 8)
1.28 -
1.29 -inline condflags_t GetPlayerConds(CBaseEntity *pPlayer)
1.30 +inline void GetPlayerConds(CBaseEntity *pPlayer, condbits_t *pOut)
1.31 {
1.32 - uint32_t playerCond = *(uint32_t *)((intptr_t)pPlayer + playerCondOffset);
1.33 - uint32_t condBits = *(uint32_t *)((intptr_t)pPlayer + conditionBitsOffset);
1.34 - uint32_t playerCondEx = *(uint32_t *)((intptr_t)pPlayer + playerCondExOffset);
1.35 + uint32_t playerCond = *(uint32_t *)((intptr_t)pPlayer + playerCondOffset);
1.36 + uint32_t condBits = *(uint32_t *)((intptr_t)pPlayer + conditionBitsOffset);
1.37 + uint32_t playerCondEx = *(uint32_t *)((intptr_t)pPlayer + playerCondExOffset);
1.38 + uint32_t playerCondEx2 = *(uint32_t *)((intptr_t)pPlayer + playerCondEx2Offset);
1.39
1.40 - uint64_t playerCondExAdj = playerCondEx;
1.41 - playerCondExAdj <<= 32;
1.42 -
1.43 - return playerCond|condBits|playerCondExAdj;
1.44 + pOut->SetDWord(0, playerCond);
1.45 + pOut->Set(0u, condBits);
1.46 + pOut->SetDWord(1, playerCondEx);
1.47 + pOut->SetDWord(2, playerCondEx2);
1.48 }
1.49
1.50 void Conditions_OnGameFrame(bool simulating)
1.51 @@ -67,14 +69,16 @@
1.52 if (!simulating)
1.53 return;
1.54
1.55 - condflags_t oldconds;
1.56 - condflags_t newconds;
1.57 + condbits_t *oldconds;
1.58 + condbits_t newconds;
1.59
1.60 - condflags_t addedconds;
1.61 - condflags_t removedconds;
1.62 + condbits_t *addedconds;
1.63 + condbits_t *removedconds;
1.64 +
1.65 + int i, j;
1.66
1.67 int maxClients = gpGlobals->maxClients;
1.68 - for (int i = 1; i <= maxClients; i++)
1.69 + for (i = 1; i <= maxClients; i++)
1.70 {
1.71 IGamePlayer *pPlayer = playerhelpers->GetGamePlayer(i);
1.72 if (!pPlayer || !pPlayer->IsInGame())
1.73 @@ -85,39 +89,39 @@
1.74 continue;
1.75
1.76 CBaseEntity *pEntity = gamehelpers->ReferenceToEntity(i);
1.77 - oldconds = g_PlayerConds[i];
1.78 - newconds = GetPlayerConds(pEntity);
1.79 + oldconds = &g_PlayerConds[i];
1.80 + GetPlayerConds(pEntity, &newconds);
1.81
1.82 - if (oldconds == newconds)
1.83 + if (*oldconds == newconds)
1.84 continue;
1.85
1.86 - addedconds = newconds &~ oldconds;
1.87 - removedconds = oldconds &~ newconds;
1.88 -
1.89 - uint64_t j;
1.90 - condflags_t bit;
1.91 + addedconds = &newconds;
1.92 + for (j = 0; j < addedconds->GetNumDWords(); ++j)
1.93 + {
1.94 + addedconds->Clear(j * sizeof(int), oldconds->GetDWord(j));
1.95 + }
1.96
1.97 - for (j = 0; j < MAX_CONDS && (bit = ((condflags_t)1 << j)) <= addedconds; j++)
1.98 + removedconds = oldconds;
1.99 + for (j = 0; j < removedconds->GetNumDWords(); ++j)
1.100 {
1.101 - if ((addedconds & bit) == bit)
1.102 - {
1.103 - g_addCondForward->PushCell(i);
1.104 - g_addCondForward->PushCell(j & 0xFFFFFFFF);
1.105 - g_addCondForward->Execute(NULL, NULL);
1.106 - }
1.107 + removedconds->Clear(j * sizeof(int), newconds.GetDWord(j));
1.108 }
1.109
1.110 - for (j = 0; j < MAX_CONDS && (bit = ((condflags_t)1 << j)) <= removedconds; j++)
1.111 + for (j = 0; (j = addedconds->FindNextSetBit( j )) != -1; ++j)
1.112 {
1.113 - if ((removedconds & bit) == bit)
1.114 - {
1.115 - g_removeCondForward->PushCell(i);
1.116 - g_removeCondForward->PushCell(j & 0xFFFFFFFF);
1.117 - g_removeCondForward->Execute(NULL, NULL);
1.118 - }
1.119 + g_addCondForward->PushCell(i);
1.120 + g_addCondForward->PushCell(j);
1.121 + g_addCondForward->Execute(NULL, NULL);
1.122 }
1.123
1.124 - g_PlayerConds[i] = newconds;
1.125 + for (j = 0; (j = addedconds->FindNextSetBit( j )) != -1; ++j)
1.126 + {
1.127 + g_removeCondForward->PushCell(i);
1.128 + g_removeCondForward->PushCell(j);
1.129 + g_removeCondForward->Execute(NULL, NULL);
1.130 + }
1.131 +
1.132 + g_PlayerConds[i].Copy( newconds );
1.133 }
1.134 }
1.135
1.136 @@ -148,8 +152,21 @@
1.137
1.138 playerCondExOffset = prop.actual_offset;
1.139
1.140 - if (playerCondOffset == -1 || playerCondExOffset == -1 || conditionBitsOffset == -1)
1.141 + if (!gamehelpers->FindSendPropInfo("CTFPlayer", "m_nPlayerCondEx2", &prop))
1.142 + {
1.143 + g_pSM->LogError(myself, "Failed to find m_nPlayerCondEx2 prop offset");
1.144 return false;
1.145 + }
1.146 +
1.147 + playerCondEx2Offset = prop.actual_offset;
1.148 +
1.149 + if (playerCondOffset == -1
1.150 + || playerCondExOffset == -1
1.151 + || playerCondEx2Offset == -1
1.152 + || conditionBitsOffset == -1)
1.153 + {
1.154 + return false;
1.155 + }
1.156
1.157 int maxClients = gpGlobals->maxClients;
1.158 for (int i = 1; i <= maxClients; i++)
1.159 @@ -158,7 +175,7 @@
1.160 if (!pPlayer || !pPlayer->IsInGame())
1.161 continue;
1.162
1.163 - g_PlayerConds[i] = GetPlayerConds(gamehelpers->ReferenceToEntity(i));
1.164 + GetPlayerConds(gamehelpers->ReferenceToEntity(i), &g_PlayerConds[i]);
1.165 }
1.166
1.167 g_pSM->AddGameFrameHook(Conditions_OnGameFrame);
1.168 @@ -168,7 +185,7 @@
1.169
1.170 void Conditions_OnClientPutInServer(int client)
1.171 {
1.172 - g_PlayerConds[client] = 0;
1.173 + g_PlayerConds[client].Init();
1.174 }
1.175
1.176 void RemoveConditionChecks()