diff --git a/CS2Fixes.vcxproj b/CS2Fixes.vcxproj
index 40a1b174..797abd0e 100644
--- a/CS2Fixes.vcxproj
+++ b/CS2Fixes.vcxproj
@@ -261,6 +261,7 @@
+
diff --git a/CS2Fixes.vcxproj.filters b/CS2Fixes.vcxproj.filters
index 8da178c1..d03d6a9b 100644
--- a/CS2Fixes.vcxproj.filters
+++ b/CS2Fixes.vcxproj.filters
@@ -466,5 +466,8 @@
Header Files\cs2_sdk\entity
+
+ Header Files\cs2_sdk\entity
+
\ No newline at end of file
diff --git a/cfg/cs2fixes/cs2fixes.cfg b/cfg/cs2fixes/cs2fixes.cfg
index f052491a..8d400411 100644
--- a/cfg/cs2fixes/cs2fixes.cfg
+++ b/cfg/cs2fixes/cs2fixes.cfg
@@ -28,6 +28,7 @@ cs2f_cvarwhitelist_enable 0 // Whether to enable the custom ConVar whitelist f
cs2f_block_particle_msgs 0 // Whether to block CUserMsg_ParticleManager messages to fix lag/crashes, experimental
cs2f_disable_setmodel 0 // Whether to disable SetModel usage from maps (custom input, cs_script function)
cs2f_allow_duck_spam 0 // Whether to allow duck spamming by removing the duck slowdown, clients will only partially predict [0 = disabled, 1 = both teams, 2 = T only, 3 = CT only]
+cs2f_thirdperson_enable 0 // Whether to enable thirdperson
cs2f_beacon_particle "particles/cs2fixes/admin_beacon.vpcf" // .vpcf file to be precached and used for player beacon
cs2f_motd_url "" // Server MOTD URL, shows up as a "Server Website" button in scoreboard
@@ -71,7 +72,7 @@ cs2f_topdefender_print 1 // Whether to print defender stats to console at rou
cs2f_topdefender_score 5000 // Score given to the top defender
cs2f_topdefender_threshold 1000 // Damage threshold for Top Defenders to be shown on round end
cs2f_topdefender_rate 1.0 // How often TopDefender stats get updated
-cs2f_topdefender_clantag "[Top Defender]" // Clan tag given to the top defender
+cs2f_topdefender_clantag "Top Defender" // Clan tag given to the top defender
// Chat flood settings
cs2f_flood_interval 0.75 // Amount of time allowed between chat messages acquiring flood tokens
@@ -161,8 +162,6 @@ cs2f_enable_button_watch 0 // Whether to enable button watch or not.
entwatch_enable 0 // Whether to enable EntWatch features
entwatch_auto_filter 1 // Whether to automatically block non-item holders from triggering uses
entwatch_clantag 1 // Whether to set item holder's clantag and set 9999 score
-entwatch_clantag_colour_mode 1 // Whether to set item clantag colours (0=No colour, 1=Use item colour, 2=Use entwatch_clantag_colour value)
-entwatch_clantag_colour "FFFFFF" // Hex colour (RRGGBB) to use if entwatch_clantag_colour_mode 2
entwatch_hud 1 // Whether to enable the EntWatch hud and related commands
entwatch_score 9999 // Score to give item holders (0 = dont change score at all) Requires entwatch_clantag 1
entwatch_glow 1000 // Distance that dropped item weapon glow will be visible (0 = glow disabled)
@@ -175,4 +174,5 @@ cs2f_hud_duration_leeway 2 // Extra seconds duration to leave hud messages vis
// Map migrations
cs2f_mapmigrations_20260121 2 // Current mode for 2026-01-21 CS2 update map migrations. [0 = Force disabled, 1 = Force enabled, 2 = Automatically enabled for maps updated before 2026-01-21 & disabled if updated after]
-cs2f_mapmigrations_20260420 2 // Current mode for 2026-04-20 CS2 update map migrations. [0 = Force disabled, 1 = Force enabled, 2 = Automatically enabled for maps updated before 2026-04-20 & disabled if updated after]
\ No newline at end of file
+cs2f_mapmigrations_20260420 2 // Current mode for 2026-04-20 CS2 update map migrations. [0 = Force disabled, 1 = Force enabled, 2 = Automatically enabled for maps updated before 2026-04-20 & disabled if updated after]
+cs2f_mapmigrations_20260922 2 // Current mode for 2026-09-22 CS2 update map migrations. [0 = Force disabled, 1 = Force enabled, 2 = Automatically enabled for maps updated before 2026-09-22 & disabled if updated after]
\ No newline at end of file
diff --git a/gamedata/cs2fixes.jsonc b/gamedata/cs2fixes.jsonc
index 186bea51..62a7a3c5 100644
--- a/gamedata/cs2fixes.jsonc
+++ b/gamedata/cs2fixes.jsonc
@@ -5,15 +5,15 @@
"UTIL_SayTextFilter":
{
"library": "server",
- "windows": "48 89 5C 24 ? 48 89 74 24 ? 48 89 7C 24 ? 55 41 56 41 57 48 8D 6C 24 ? 48 81 EC ? ? ? ? 49 8B F0 48 89 4D",
- "linux": "55 48 8D 05 ? ? ? ? 48 89 E5 41 57 41 56 4C 8D 75 ? 41 55 49 89 D5"
+ "windows": "48 89 5C 24 ? 48 89 74 24 ? 48 89 7C 24 ? 55 41 56 41 57 48 8D 6C 24 ? 48 81 EC ? ? ? ? 49 8B D8",
+ "linux": "55 48 8D 05 ? ? ? ? 48 89 E5 41 57 41 56 4C 8D 75 ? 41 55 41 89 CD"
},
// Called from Host_Say
"UTIL_SayText2Filter":
{
"library": "server",
- "windows": "48 89 5C 24 ? 48 89 74 24 ? 48 89 7C 24 ? 55 41 56 41 57 48 8D 6C 24 ? 48 81 EC ? ? ? ? 41 8B F8",
- "linux": "55 48 8D 05 ? ? ? ? 48 89 E5 41 57 41 56 41 89 D6 31 D2"
+ "windows": "48 89 5C 24 ? 48 89 74 24 ? 48 89 7C 24 ? 55 41 56 41 57 48 8D 6C 24 ? 48 81 EC ? ? ? ? 41 8B D8",
+ "linux": "55 48 8D 05 ? ? ? ? 48 89 E5 41 57 41 89 D7 31 D2"
},
// idk a good way to find this again, i just brute forced the vtable. offset is 136 on CTriggerPush
"TriggerPush_Touch":
@@ -27,14 +27,14 @@
{
"library": "server",
"windows": "48 89 5C 24 ? 55 56 57 41 55 41 57 48 83 EC ? 44 8B 89",
- "linux": "55 48 89 E5 41 57 49 89 FF 41 56 41 55 41 54 49 89 D4 53 48 89 F3 48 81 EC"
+ "linux": "55 48 89 E5 41 57 49 89 FF 41 56 41 55 41 54 49 89 D4 53 48 89 F3 48 81 EC ? ? ? ? 8B 97"
},
// Check vauff's pin in #scripting
"ServerMovementUnlock":
{
"library": "server",
"windows": "0F 86 AF ? ? ? 0F 57 C0 0F 2E C2",
- "linux": "0F 87 ? ? ? ? F3 0F 10 25 ? ? ? ? F3 0F 11 A5 ? ? ? ? 48 89 DE"
+ "linux": "76 ? F3 0F 51 C0 F3 0F 7E DB 49 8B 06"
},
// String: "CCSPlayerPawnBase::SwitchTeam", just keep in mind this is actually CCSPlayerController::SwitchTeam
"CCSPlayerController_SwitchTeam":
@@ -47,28 +47,28 @@
"CheckJumpButtonWater":
{
"library": "server",
- "windows": "C8 42 EB ? 4C 8B 77 ? 4D 39 66",
- "linux": "C8 42 41 C7 85 ? ? ? ? ? ? ? ? 41 C7 85 ? ? ? ? ? ? ? ? E9"
+ "windows": "C8 42 EB ? 4C 8B 73 ? 4D 39 6E",
+ "linux": "C8 42 41 C7 84 24 ? ? ? ? ? ? ? ? 41 C7 84 24 ? ? ? ? ? ? ? ? E9"
},
// "SetPosition" is passed to this
"CEntitySystem_AddEntityIOEvent":
{
"library": "server",
- "windows": "48 89 5C 24 18 4C 89 4C 24 20 48 89 4C 24 08 55 56 57 41 54 41 55 41 56 41 57 48 83 EC 20",
+ "windows": "48 89 5C 24 ? 48 89 74 24 ? 57 48 83 EC ? 49 8B F1 48 8B F9",
"linux": "55 48 89 E5 41 55 49 89 CD 41 54 49 89 FC 53 BB"
},
// "BombPlanted" is passed to this
"CEntityInstance_AcceptInput":
{
"library": "server",
- "windows": "48 89 5C 24 ? 48 89 74 24 ? 57 48 83 EC ? 49 8B F0 48 8B D9 48 8B 0D",
- "linux": "55 48 89 E5 41 56 49 89 FE 41 55 48 8D 7D"
+ "windows": "48 89 5C 24 ? 48 89 6C 24 ? 56 57 41 56 48 81 EC ? ? ? ? 4D 8B F0 48 8B F1",
+ "linux": "55 48 89 E5 41 57 49 89 FF 41 56 48 8D BD ? ? ? ? 41 55 4C 8D AD"
},
// Called by CEntityInstance_AcceptInput
"CEntityIdentity_AcceptInput":
{
"library": "server",
- "windows": "48 89 5C 24 ? 48 89 54 24 ? 48 89 4C 24 ? 55 56 57 41 54 41 55 41 56 41 57 48 8D 6C 24 ? 48 81 EC ? ? ? ? 48 8B 02",
+ "windows": "48 89 54 24 ? 48 89 4C 24 ? 55 53 56 57 41 55 41 56 41 57 48 8D 6C 24",
"linux": "55 48 89 E5 41 57 41 56 4C 8D BD ? ? ? ? 4D 89 CE"
},
// func_pushable inside CTriggerBrush::Use calls CEntityIOOutput::FireOutputInternal
@@ -78,8 +78,8 @@
"CEntityIOOutput_FireOutputInternal":
{
"library": "server",
- "windows": "4C 89 4C 24 ? 48 89 4C 24 ? 53 56",
- "linux": "55 48 89 E5 41 57 49 89 FF 41 56 41 55 41 54 49 89 D4 53 48 89 F3 48 83 EC ? 48 8D 05"
+ "windows": "48 8B C4 48 89 58 ? 48 89 70 ? 48 89 48 ? 55",
+ "linux": "55 48 89 E5 41 57 49 89 FF 41 56 41 55 41 54 49 89 D4 53 48 89 F3 48 81 EC ? ? ? ? 48 8D 05"
},
// "multi_manager" is passed to this
"CGameEntitySystem_FindEntityByClassName":
@@ -160,13 +160,13 @@
{
"library": "server",
"windows": "48 8B C4 4C 89 48 ? 48 89 48 ? 55 41 54",
- "linux": "55 48 89 E5 41 57 41 56 41 55 41 54 41 89 F4 53 48 8D 35 ? ? ? ? 48 89 FB"
+ "linux": "55 48 89 E5 41 57 41 56 49 89 FE 41 55 41 54 53 48 81 EC ? ? ? ? 48 8D 05 ? ? ? ? F3 0F 11 85 ? ? ? ? 89 B5"
},
"CCSPlayer_WeaponServices_CanUse":
{
"library": "server",
"windows": "48 89 5C 24 ? 48 89 6C 24 ? 56 57 41 54 41 56 41 57 48 83 EC ? 48 8B 01 48 8B FA",
- "linux": "55 48 8D 15 ? ? ? ? 48 89 E5 41 55 41 54 49 89 FC 53 48 89 F3 48 83 EC ? 48 8B 07 48 8B 80"
+ "linux": "55 48 8D 15 ? ? ? ? 48 89 E5 41 55 41 54 49 89 F4 53 48 89 FB 48 83 EC ? 48 8B 07 48 8B 80 ? ? ? ? 48 39 D0 0F 85 ? ? ? ? 80 BF"
},
"CCSPlayer_WeaponServices_EquipWeapon":
{
@@ -198,7 +198,7 @@
{
"library": "server",
"windows": "48 89 5C 24 08 48 89 74 24 10 48 89 7C 24 18 4C 89 74 24 20 55 48 8D 6C 24 D1",
- "linux": "55 48 89 E5 41 57 41 56 41 55 41 89 CD 41 54 53 48 89 D3"
+ "linux": "55 48 89 E5 41 57 41 56 41 55 41 89 CD 41 54 53 48 81 EC"
},
// search for "land_%s", this is called after that string is referenced (the one with 4 parameters).
// (function that calls it also contains "T_Default.SuitLand").
@@ -238,8 +238,8 @@
"CGamePlayerEquip_InputTriggerForActivatedPlayer":
{
"library": "server",
- "windows": "48 89 5C 24 18 56 48 83 EC 20 48 8B 1A",
- "linux": "55 48 89 E5 41 56 41 55 41 54 53 48 83 EC ? 48 8B 1E"
+ "windows": "48 89 5C 24 ? 56 48 83 EC ? 48 8B 1A",
+ "linux": "55 48 89 E5 41 56 41 55 41 54 53 48 8B 1E 48 85 DB 74"
},
// Return value of this function is used to determine whether "NETWORK_DISCONNECT_REJECT_SERVERFULL to %s: Cannot get free client\n" gets printed
"GetFreeClient":
@@ -261,7 +261,7 @@
{
"library": "server",
"windows": "4C 89 44 24 ? F3 0F 11 4C 24 ? 55 53 56",
- "linux": "55 48 89 E5 41 57 41 56 41 55 41 54 49 89 FC 53 48 8D 3D ? ? ? ? 48 81 EC ? ? ? ? 48 89 B5 ? ? ? ? BE ? ? ? ? F3 0F 11 85"
+ "linux": "48 B9 ? ? ? ? ? ? ? ? 55 48 89 E5 41 57 49 89 FF"
},
"TraceFunc":
{
@@ -273,8 +273,8 @@
"TraceShape":
{
"library": "server",
- "windows": "48 89 54 24 ? 48 89 4C 24 ? 55 53 56 57 41 56 41 57 48 8D AC 24 ? ? ? ? B8",
- "linux": "55 48 89 E5 41 57 49 89 CF 41 56 49 89 F6 41 55 4D 89 C5 41 54 49 89 D4"
+ "windows": "48 89 54 24 ? 48 89 4C 24 ? 55 53 56 57 41 54 41 56 41 57",
+ "linux": "55 48 8D 05 ? ? ? ? 48 89 E5 41 57 49 89 F7 41 56 48 8D 35 ? ? ? ? 49 89 CE"
},
"CBasePlayerPawn_GetEyePosition":
{
@@ -288,19 +288,20 @@
"windows": "48 89 5C 24 ? 57 48 81 EC ? ? ? ? 48 8B F9 48 8B DA 48 8B 89 ? ? ? ? 48 85 C9",
"linux": "55 48 89 E5 41 54 53 48 89 FB 48 83 C4 ? 48 8B BF ? ? ? ? 48 85 FF"
},
- // Only ever referenced right next to string "TestActivator"
+ // Called by function with "TestActivator" string
"CBaseFilter_InputTestActivator":
{
"library": "server",
- "windows": "48 89 5C 24 ? 57 48 83 EC ? 4C 8B 02",
- "linux": "55 48 89 E5 41 54 49 89 F4 53 48 89 FB 48 83 EC ? 48 8B 07 48 8B 16"
+ // Inlined by MSVC as of 2026-09-22 CS2 update
+ //"windows": "48 89 5C 24 ? 57 48 83 EC ? 4C 8B 02",
+ "linux": "55 48 89 E5 41 55 41 54 49 89 F4 53 48 89 FB 48 81 EC ? ? ? ? 48 8B 07 48 8B 16"
},
// "Kicking user %s (sv_kick_players_with_cooldown=%d)\n"
"GameSystem_Think_CheckSteamBan":
{
"library": "server",
- "windows": "41 54 48 81 EC ? ? ? ? BA ? ? ? ? 48 8D 0D ? ? ? ? E8 ? ? ? ? 48 85 C0",
- "linux": "55 48 8D 3D ? ? ? ? BE ? ? ? ? 48 89 E5 41 57 41 56 41 55 41 54 53 48 83 EC"
+ "windows": "41 54 48 81 EC ? ? ? ? 48 8B 05 ? ? ? ? 44 8B 60",
+ "linux": "55 48 89 E5 41 57 41 56 41 55 41 54 53 48 83 EC ? 48 8B 05 ? ? ? ? 44 8B 68 ? 45 85 ED 0F 8E ? ? ? ? 8B 15"
},
// Location to CUtlMap unk that is referenced on Windows by function with "Notification about user penalty: %u/%u (%u sec)\n" string
// On Linux, a qword appears twice in GameSystem_Think_CheckSteamBan, and thrice in a sub-function of the function used for Windows (1 top, 2 bottom), the only other reference to this qword is some convar registration function with two unks above, sm_mapGcBanInformation is the unk further away
@@ -322,8 +323,8 @@
"CCSPlayer_ItemServices_CanAcquire":
{
"library": "server",
- "windows": "44 89 44 24 ? 48 89 54 24 ? 48 89 4C 24 ? 55 53 56 57 41 55 41 56 41 57 48 8B EC",
- "linux": "55 48 89 E5 41 57 41 56 41 55 49 89 CD 41 54 49 89 FC 53 48 89 F3 48 83 EC"
+ "windows": "44 89 44 24 ? 48 89 54 24 ? 48 89 4C 24 ? 55 53 56 57 41 54 41 55 41 56 41 57 48 8B EC",
+ "linux": "55 48 89 E5 41 57 41 56 49 89 F6 41 55 41 54 49 89 CC 53 48 89 FB 48 83 EC ? 4C 8B 6F"
},
"CTriggerGravity_GravityTouch":
{
@@ -343,13 +344,13 @@
{
"library": "server",
"windows": "48 89 5C 24 ? 55 56 57 41 54 41 55 41 56 41 57 48 8D AC 24 ? ? ? ? 48 81 EC ? ? ? ? 4C 8B E9",
- "linux": "55 31 C0 48 89 E5 41 57 41 56 41 55 41 54 41 89 F4"
+ "linux": "55 31 C0 48 89 E5 41 57 41 56 41 55 41 54 53 48 89 FB 48 8D 3D ? ? ? ? 48 81 EC ? ? ? ? 89 B5"
},
// Called in return by function with "Usage: setang_exact pitch yaw " string
"CBasePlayerPawn_SnapViewAngles":
{
"library": "server",
- "windows": "48 89 5C 24 ? 48 89 74 24 ? 48 89 7C 24 ? 55 48 8D 6C 24 ? 48 81 EC ? ? ? ? 48 8B DA 48 8B F1 48 8D 55",
+ "windows": "48 89 7C 24 ? 55 48 8B EC 48 81 EC ? ? ? ? 48 8B F9 48 8D 4D ? E8 ? ? ? ? F2 0F 10 87",
"linux": "55 48 89 E5 41 57 49 89 FF 48 89 F7 41 56 41 55 41 54 53 48 81 EC ? ? ? ? E8"
},
// These two functions are called by CEnvBeam & CEnvLaser member functions, one of those functions has "env_beams cannot have the end entity be the beam itself" string
@@ -390,63 +391,63 @@
},
"CBaseEntity::SetOwner":
{
- "windows": 53,
- "linux": 52
+ "windows": 54,
+ "linux": 53
},
"CBaseEntity::Use":
{
- "windows": 145,
- "linux": 144
+ "windows": 147,
+ "linux": 146
},
"CBaseEntity::StartTouch":
{
- "windows": 148,
- "linux": 147
+ "windows": 150,
+ "linux": 149
},
"CBaseEntity::Touch":
{
- "windows": 149,
- "linux": 148
+ "windows": 151,
+ "linux": 150
},
"CBaseEntity::EndTouch":
{
- "windows": 150,
- "linux": 149
+ "windows": 152,
+ "linux": 151
},
"Teleport":
{
- "windows": 163,
- "linux": 162
+ "windows": 165,
+ "linux": 164
},
"CollisionRulesChanged":
{
- "windows": 186,
- "linux": 185
+ "windows": 188,
+ "linux": 187
},
"CCSPlayerController_Respawn":
{
- "windows": 270,
- "linux": 272
+ "windows": 274,
+ "linux": 276
},
// CBaseTrigger
"PassesTriggerFilters":
{
- "windows": 269,
- "linux": 270
+ "windows": 271,
+ "linux": 272
},
// Actually a bit of a wrapper function now? Eventually calls a long function with "player_hurt" in the middle and then inserts userid, health, priority, attacker strings
"CCSPlayerPawn::OnTakeDamage_Alive":
{
- "windows": 252,
- "linux": 253
+ "windows": 255,
+ "linux": 256
},
// Look for the kill command, go through its callback and you should a find call like this, with v9 being a pawn pointer:
- // return (*(*v9 + 2976LL))(v9, v27, 0LL);
- // 2976 (372 * 8) is the offset
+ // return (*(*v9 + 3096LL))(v9, v27, 0LL);
+ // 3096 (387 * 8) is the offset
"CBasePlayerPawn_CommitSuicide":
{
- "windows": 384,
- "linux": 384
+ "windows": 387,
+ "linux": 387
},
"GameEntitySystem":
{
@@ -456,15 +457,15 @@
// In the function with "[%03d] Found: %s, firing\n", you'll find a call into a pointer offset just a bit higher, that's the offset * 8
"CGameRules_FindPickerEntity":
{
- "windows": 26,
- "linux": 27
+ "windows": 25,
+ "linux": 26
},
// engine
- // "tried to sprint to a non-client", there will be a check above like this: if ( a2 >= *(v5 + 632) ), note that this is a CUtlVector
+ // "tried to sprint to a non-client", there will be a check above like this: if ( a2 >= *(v5 + 616) ), note that this is a CUtlVector
"CNetworkGameServer_ClientList":
{
- "windows": 73,
- "linux": 73
+ "windows": 77,
+ "linux": 77
},
// Right above "mapgroup workshop;" string there is a virtual call to this on g_pGameTypes using "workshop" string
"IGameTypes_CreateWorkshopMapGroup":
@@ -475,8 +476,8 @@
// There's no easy way to find this, but it's a function that checks entity flags (0x370) and ends by calling RemoveFlag with 0x800000 (FL_BASEVELOCITY)
"CCSPlayer_MovementServices::CheckMovingGround":
{
- "windows": 44,
- "linux": 45
+ "windows": 45,
+ "linux": 46
},
"CCSPlayer_WeaponServices::DropWeapon":
{
@@ -491,8 +492,8 @@
// server.dll -> xref 'sv_phys_stop_at_collision' first __fastcall
"CVPhys2World::GetTouchingList":
{
- "windows": 121,
- "linux": 121
+ "windows": 122,
+ "linux": 122
}
},
"Patches":
@@ -500,7 +501,7 @@
"ServerMovementUnlock":
{
"windows": "E9 B0 00 00 00 90",
- "linux": "90 90 90 90 90 90"
+ "linux": "EB"
},
"FixWaterFloorJump":
{
diff --git a/sdk b/sdk
index bd17582b..625bfd4e 160000
--- a/sdk
+++ b/sdk
@@ -1 +1 @@
-Subproject commit bd17582be4bc18970e4fe4c518359872fda8276d
+Subproject commit 625bfd4e39816ad0e1eae3b3144a3b5425c5c7a0
diff --git a/src/addresses.h b/src/addresses.h
index 09ac769e..a168a8b1 100644
--- a/src/addresses.h
+++ b/src/addresses.h
@@ -60,6 +60,8 @@ class CTakeDamageInfo;
class CCSPlayer_WeaponServices;
class CBasePlayerWeapon;
class CSpawnGroupMgrGameSystem;
+struct CPulseArgumentPack;
+struct CPulseInputParamMap;
struct EmitSound_t;
struct StartSoundEventInfo;
struct CTakeDamageResult;
@@ -88,7 +90,7 @@ namespace addresses
inline void(FASTCALL* UTIL_Remove)(CEntityInstance*);
inline void(FASTCALL* CEntitySystem_AddEntityIOEvent)(CEntitySystem* pEntitySystem, CEntityInstance* pTarget, const char* pszInput,
- CEntityInstance* pActivator, CEntityInstance* pCaller, variant_t* value, float flDelay, void*, void*);
+ CEntityInstance* pActivator, CEntityInstance* pCaller, variant_t* value, float flDelay, CPulseArgumentPack* pArgumentPack, CPulseInputParamMap* pParamMap);
inline void(FASTCALL* CEntityInstance_AcceptInput)(CEntityInstance* pThis, const char* pInputName,
CEntityInstance* pActivator, CEntityInstance* pCaller, variant_t* value);
diff --git a/src/buttonwatch.cpp b/src/buttonwatch.cpp
index 016a4e1d..d92d1968 100644
--- a/src/buttonwatch.cpp
+++ b/src/buttonwatch.cpp
@@ -75,7 +75,7 @@ CON_COMMAND_CHAT_FLAGS(bw, "- Toggle button watch display", ADMFLAG_GENERIC)
}
std::map mapRecentEnts;
-void ButtonWatch(const CEntityIOOutput* pThis, CEntityInstance* pActivator, CEntityInstance* pCaller, const CVariant* value, float flDelay)
+void ButtonWatch(const CEntityIOOutput* pThis, CEntityInstance* pActivator, CEntityInstance* pCaller, float flDelay)
{
if (!GetGlobals() || V_stricmp(pThis->m_pDesc->m_pName, "OnPressed") || !pActivator || !((CBaseEntity*)pActivator)->IsPawn() || !pCaller || mapRecentEnts.contains(pCaller->GetEntityIndex().Get()))
return;
diff --git a/src/buttonwatch.h b/src/buttonwatch.h
index d7e9a825..bb72ffa2 100644
--- a/src/buttonwatch.h
+++ b/src/buttonwatch.h
@@ -22,4 +22,4 @@
extern CConVar g_cvarEnableButtonWatch;
-void ButtonWatch(const CEntityIOOutput* pThis, CEntityInstance* pActivator, CEntityInstance* pCaller, const CVariant* value, float flDelay);
\ No newline at end of file
+void ButtonWatch(const CEntityIOOutput* pThis, CEntityInstance* pActivator, CEntityInstance* pCaller, float flDelay);
\ No newline at end of file
diff --git a/src/cfgparser.cpp b/src/cfgparser.cpp
index 5b80cf7a..906e1806 100644
--- a/src/cfgparser.cpp
+++ b/src/cfgparser.cpp
@@ -98,7 +98,10 @@ void CCfgParser::ParseCfg(const char* pszCfgPath)
if (convar.IsValidRef())
{
- if (args.ArgC() > 1 && !convar.SetString(args[1]))
+ // Hold on to ConVarRefAbstract's so they don't get destroyed on next iteration loop, this could cause memory issues with deferred FCVAR_PERFORMING_CALLBACKS cvar's
+ ConVarRefAbstract& cachedConvar = m_mapConVars.insert_or_assign(convar.GetAccessIndex(), convar).first->second;
+
+ if (args.ArgC() > 1 && !cachedConvar.SetString(args[1]))
Message("Failed to execute \"%s %s\"\n", args[0], args[1]);
continue;
diff --git a/src/cfgparser.h b/src/cfgparser.h
index 53f3296c..baee9275 100644
--- a/src/cfgparser.h
+++ b/src/cfgparser.h
@@ -19,6 +19,9 @@
#pragma once
+#include "convar.h"
+#include