CMatchExtL4D::ParseMissionFromFile
0x000360b0 · 2675 bytes · __thiscall
_ZN12CMatchExtL4D20ParseMissionFromFileEPKcby
Decompiled
undefined (4 params)
/* CMatchExtL4D::ParseMissionFromFile(char const*, bool, unsigned long long) */
void __thiscall
CMatchExtL4D::ParseMissionFromFile(CMatchExtL4D *this,char *param_1,bool param_2,ulonglong param_3)
{
CUtlVector<KeyValues*,CUtlMemory<KeyValues*,int>> *this_00;
CMatchExtL4D CVar1;
char cVar2;
KeyValues *pKVar3;
KeyValues *this_01;
KeyValues *this_02;
IBaseFileSystem *pIVar4;
KeyValues *this_03;
undefined4 uVar5;
int iVar6;
KeyValues *this_04;
KeyValues *this_05;
int iVar7;
undefined4 *puVar8;
undefined4 uVar9;
uint uVar10;
int in_GS_OFFSET;
char *pcVar11;
char *pcVar12;
CMatchExtL4D *pCVar13;
CMatchExtL4D *pCVar14;
int local_26c;
KeyValues *local_25c;
int local_244;
short local_23c;
ushort local_23a;
CFmtStrN<256> local_238 [5];
char local_233 [263];
CFmtStrN<256> local_12c [5];
char local_127 [263];
int local_20;
local_20 = *(int *)(in_GS_OFFSET + 0x14);
pKVar3 = (KeyValues *)KeyValues::FindKey(*(KeyValues **)(this + 4),"GameModes",false);
pCVar13 = (CMatchExtL4D *)0x0;
pcVar12 = "Missions";
pcVar11 = *(char **)(this + 4);
this_01 = (KeyValues *)KeyValues::FindKey((KeyValues *)pcVar11,"Missions",false);
if ((pKVar3 != (KeyValues *)0x0) && (this_01 != (KeyValues *)0x0)) {
this_00 = (CUtlVector<KeyValues*,CUtlMemory<KeyValues*,int>> *)(this + 8);
pCVar14 = this + 0x1c;
pcVar11 = (char *)&local_23a;
pcVar12 = (char *)pCVar14;
pCVar13 = (CMatchExtL4D *)param_1;
CUtlSymbolTable::Find(pcVar11);
if (local_23a == 0xffff) {
CUtlSymbolTable::AddString((char *)&local_23a);
uVar10 = (uint)local_23a;
pCVar13 = *(CMatchExtL4D **)(this + 0x14);
if ((((int)pCVar13 <= (int)uVar10) && ((int)pCVar13 < (int)(uVar10 + 1))) &&
(iVar7 = (uVar10 + 1) - (int)pCVar13, iVar7 != 0)) {
CUtlVector<KeyValues*,CUtlMemory<KeyValues*,int>>::GrowVector(this_00,iVar7);
CUtlVector<KeyValues*,CUtlMemory<KeyValues*,int>>::ShiftElementsRight
(this_00,(int)pCVar13,iVar7);
pCVar14 = pCVar13;
}
*(undefined4 *)(*(int *)(this + 8) + uVar10 * 4) = 0;
this_02 = KeyValues::operator_new((KeyValues *)0x2c,(uint)pCVar14);
/* try { // try from 000361fd to 00036201 has its CatchHandler @ 00036b62 */
KeyValues::KeyValues(this_02,"mission",(IKeyValuesSystem *)0x0,false);
pIVar4 = (IBaseFileSystem *)0x0;
if (g_pFullFileSystem != 0) {
pIVar4 = (IBaseFileSystem *)(g_pFullFileSystem + 4);
}
pCVar13 = (CMatchExtL4D *)param_1;
/* try { // try from 00036231 to 0003624f has its CatchHandler @ 00036b4c */
cVar2 = KeyValues::LoadFromFile(this_02,pIVar4,param_1,(char *)0x0);
if (cVar2 == '\0') {
pcVar11 = "MissionManager: Mission file \"%s\" is malformed, failed to parse.\n";
Warning("MissionManager: Mission file \"%s\" is malformed, failed to parse.\n",param_1);
pcVar12 = param_1;
}
else {
/* try { // try from 00036289 to 0003643a has its CatchHandler @ 00036b4c */
pcVar12 = (char *)KeyValues::GetString(this_02,"name",(char *)0x0);
pCVar14 = (CMatchExtL4D *)0x0;
pCVar13 = (CMatchExtL4D *)KeyValues::GetString(this_02,"version",(char *)0x0);
if ((pCVar13 == (CMatchExtL4D *)0x0) || ((CMatchExtL4D *)pcVar12 == (CMatchExtL4D *)0x0)) {
pcVar11 = "MissionManager: Mission file \"%s\" is missing name and version\n";
/* try { // try from 000364b8 to 000369bb has its CatchHandler @ 00036b4c */
Warning("MissionManager: Mission file \"%s\" is missing name and version\n",param_1);
pcVar12 = param_1;
pCVar13 = pCVar14;
}
else {
CVar1 = (CMatchExtL4D)*pcVar12;
pCVar14 = (CMatchExtL4D *)pcVar12;
while (CVar1 != (CMatchExtL4D)0x0) {
if ((0x19 < (byte)(((byte)CVar1 & 0xdf) + 0xbf)) && (9 < (byte)((char)CVar1 - 0x30U))) {
pcVar11 =
"MissionManager: Only alphanumeric characters allowed in mission name: \"%s\" in \"%s\"\n"
;
Warning("MissionManager: Only alphanumeric characters allowed in mission name: \"%s\" in \"%s\"\n"
,pcVar12,param_1);
pCVar13 = (CMatchExtL4D *)param_1;
goto LAB_00036250;
}
pCVar14 = pCVar14 + 1;
CVar1 = *pCVar14;
}
CVar1 = *pCVar13;
pCVar14 = pCVar13;
while (CVar1 != (CMatchExtL4D)0x0) {
if (9 < (byte)((char)CVar1 - 0x30U)) {
pcVar11 =
"MissionManager: Only numeric characters allowed in mission version: \"%s\" in \"%s\"\n"
;
Warning("MissionManager: Only numeric characters allowed in mission version: \"%s\" in \"%s\"\n"
,pCVar13,param_1);
pcVar12 = (char *)pCVar13;
pCVar13 = (CMatchExtL4D *)param_1;
goto LAB_00036250;
}
pCVar14 = pCVar14 + 1;
CVar1 = *pCVar14;
}
pCVar14 = (CMatchExtL4D *)0x0;
this_03 = (KeyValues *)KeyValues::FindKey(this_02,"modes",false);
if (this_03 == (KeyValues *)0x0) {
pcVar11 = "MissionManager: Mission file \"%s\" is missing data for any game modes\n";
Warning("MissionManager: Mission file \"%s\" is missing data for any game modes\n",
param_1);
pcVar12 = param_1;
pCVar13 = pCVar14;
}
else {
CFmtStrN<256>::CFmtStrN(local_238,"%s_%s",pcVar12,pCVar13);
CUtlSymbolTable::Find((char *)&local_23c);
if (local_23c == -1) {
DevMsg("\tMission %s ver %s loading...\n",pcVar12,pCVar13);
pcVar11 = (char *)KeyValues::GetString(this_02,"DisplayTitle","");
if ((pcVar11 == (char *)0x0) || (*pcVar11 == '\0')) {
KeyValues::SetString(this_02,"DisplayTitle",pcVar12);
}
KeyValues::SetName(this_02,pcVar12);
KeyValues::SetInt(this_02,"BuiltIn",(uint)param_2);
KeyValues::SetInt(this_02,"addon",(uint)!param_2);
KeyValues::SetString(this_02,"CfgFile",param_1);
KeyValues::SetString(this_02,"CfgTag",local_233);
KeyValues::SetUint64((char *)this_02,CONCAT44((undefined4)param_3,"workshopid"));
KeyValues::GetUint64((char *)this_02,0xb0b8f);
uVar5 = 0;
KeyValues::SetUint64((char *)this_02,0xb0b8f);
pCVar14 = (CMatchExtL4D *)0x0;
KeyValues::SetInt(this_02,"dlcrequired",0);
local_25c = (KeyValues *)KeyValues::GetFirstTrueSubKey(pKVar3);
if (local_25c != (KeyValues *)0x0) {
local_26c = 0;
do {
pcVar11 = (char *)KeyValues::GetName(local_25c);
pCVar14 = (CMatchExtL4D *)0x0;
this_04 = (KeyValues *)KeyValues::FindKey(this_03,pcVar11,false);
if (this_04 != (KeyValues *)0x0) {
local_244 = 0;
while( true ) {
iVar7 = local_244 + 1;
CFmtStrN<256>::CFmtStrN(local_12c,"%d",iVar7);
this_05 = (KeyValues *)KeyValues::FindKey(this_04,local_127,false);
if (this_05 == (KeyValues *)0x0) break;
pcVar11 = (char *)KeyValues::GetString(this_05,"map","");
if ((pcVar11 == (char *)0x0) || (*pcVar11 == '\0')) {
/* try { // try from 00036a73 to 00036b37 has its CatchHandler @ 00036b4c */
uVar5 = KeyValues::GetName(this_05);
uVar9 = KeyValues::GetName(local_25c);
Warning("MissionManager: Mission file \"%s\" has invalid map specified for modes/%s/%s\n"
,param_1,uVar9,uVar5);
goto LAB_00036aa6;
}
pcVar11 = (char *)KeyValues::GetString(this_05,"DisplayName","");
if ((pcVar11 == (char *)0x0) || (*pcVar11 == '\0')) {
uVar5 = KeyValues::GetName(this_05);
CFmtStrN<256>::CFmtStrN(local_12c,"%s-%s",pcVar12,uVar5);
KeyValues::SetString(this_05,"DisplayName",local_127);
}
pcVar11 = (char *)KeyValues::GetString(this_05,"image","");
if ((pcVar11 == (char *)0x0) || (*pcVar11 == '\0')) {
KeyValues::SetString(this_05,"image","maps/unknown");
}
KeyValues::SetInt(this_05,"chapter",iVar7);
local_244 = iVar7;
}
if (local_244 == 0) {
LAB_00036aa6:
KeyValues::RemoveSubKey(this_03,this_04);
if (this_03 != this_04) {
KeyValues::deleteThis();
}
pCVar14 = (CMatchExtL4D *)KeyValues::GetName(local_25c);
Warning("MissionManager: Mission file \"%s\" has invalid settings for game mode %s\n"
,param_1,pCVar14);
}
else {
iVar7 = _V_stricmp(pcVar12,"credits");
if (iVar7 != 0) {
iVar6 = KeyValues::GetInt(local_25c,"singlechapter",0);
iVar7 = 1;
if (iVar6 != 0) {
iVar7 = local_244;
}
iVar6 = KeyValues::GetInt(local_25c,"missions",0);
KeyValues::SetInt(local_25c,"missions",iVar6 + iVar7);
}
KeyValues::SetInt(this_04,"chapters",local_244);
pCVar14 = (CMatchExtL4D *)KeyValues::GetName(local_25c);
DevMsg("\t\tloaded %d %s chapters.\n",local_244,pCVar14);
local_26c = local_26c + 1;
}
}
local_25c = (KeyValues *)KeyValues::GetNextTrueSubKey(local_25c);
} while (local_25c != (KeyValues *)0x0);
if (local_26c != 0) {
puVar8 = (undefined4 *)CUtlStringMap<KeyValues*>::operator[]((char *)this_00);
*puVar8 = this_02;
puVar8 = (undefined4 *)
CUtlStringMap<KeyValues*>::operator[]((char *)(this + 0x54));
*puVar8 = this_02;
KeyValues::AddSubKey(this_01,this_02);
/* try { // try from 000369d1 to 00036a63 has its CatchHandler @ 00036b42 */
CFmtStrN<256>::CFmtStrN(local_12c,"missions/%s",pcVar12);
pKVar3 = (KeyValues *)KeyValues::GetFirstTrueSubKey(pKVar3);
for (; pKVar3 != (KeyValues *)0x0;
pKVar3 = (KeyValues *)KeyValues::GetNextTrueSubKey(pKVar3)) {
pcVar11 = (char *)KeyValues::GetName(pKVar3);
iVar7 = KeyValues::FindKey(this_03,pcVar11,false);
if (iVar7 != 0) {
KeyValues::SetPtr(pKVar3,local_127,this_02);
}
}
pcVar11 = "\tMission %s ver %s loaded %d game modes.\n";
DevMsg("\tMission %s ver %s loaded %d game modes.\n",pcVar12,pCVar13,local_26c);
goto LAB_0003612e;
}
}
pcVar11 =
"MissionManager: Mission file \"%s\" does not have valid data for any supported game mode\n"
;
Warning("MissionManager: Mission file \"%s\" does not have valid data for any supported game mode\n"
,param_1,pCVar14,uVar5);
pcVar12 = param_1;
pCVar13 = pCVar14;
}
else {
CUtlSymbolTable::AddString((char *)&local_23a);
uVar10 = (uint)local_23a;
iVar7 = *(int *)(this + 0x60);
if (((iVar7 <= (int)uVar10) && (iVar7 < (int)(uVar10 + 1))) &&
(iVar6 = (uVar10 + 1) - iVar7, iVar6 != 0)) {
CUtlVector<KeyValues*,CUtlMemory<KeyValues*,int>>::GrowVector
((CUtlVector<KeyValues*,CUtlMemory<KeyValues*,int>> *)(this + 0x54),iVar6)
;
CUtlVector<KeyValues*,CUtlMemory<KeyValues*,int>>::ShiftElementsRight
((CUtlVector<KeyValues*,CUtlMemory<KeyValues*,int>> *)(this + 0x54),iVar7,
iVar6);
}
uVar5 = KeyValues::GetString
(*(KeyValues **)(*(int *)(this + 0x54) + uVar10 * 4),"CfgFile","");
pcVar11 =
"MissionManager: Duplicate mission \"%s\" in file \"%s\", already loaded from \"%s\".\n"
;
Warning("MissionManager: Duplicate mission \"%s\" in file \"%s\", already loaded from \"%s\".\n"
,pcVar12,param_1,uVar5);
pCVar13 = (CMatchExtL4D *)param_1;
}
}
}
}
LAB_00036250:
if (this_02 != (KeyValues *)0x0) {
KeyValues::deleteThis();
pcVar11 = (char *)this_02;
}
}
}
LAB_0003612e:
if (local_20 != *(int *)(in_GS_OFFSET + 0x14)) {
/* WARNING: Subroutine does not return */
__stack_chk_fail(pcVar11,pcVar12,pCVar13);
}
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.