using System;
using System.Diagnostics;
using System.IO;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Text;
using System.Text.RegularExpressions;
using BepInEx;
using BepInEx.Core.Logging.Interpolation;
using BepInEx.Logging;
using BepInEx.Unity.IL2CPP;
using GameData;
using HarmonyLib;
using Il2CppInterop.Runtime.InteropTypes;
using Il2CppInterop.Runtime.InteropTypes.Arrays;
using Il2CppSystem.Collections.Generic;
using LevelGeneration;
using Microsoft.CodeAnalysis;
using SNetwork;
using UnityEngine;
[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETCoreApp,Version=v6.0", FrameworkDisplayName = ".NET 6.0")]
[assembly: AssemblyCompany("GTFOCheckpointPrototype")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0+42eea22b2cc538ae364395df4e0684210c1cfa86")]
[assembly: AssemblyProduct("GTFOCheckpointPrototype")]
[assembly: AssemblyTitle("GTFOCheckpointPrototype")]
[assembly: AssemblyVersion("1.0.0.0")]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
[CompilerGenerated]
[Embedded]
internal sealed class EmbeddedAttribute : Attribute
{
}
}
namespace System.Runtime.CompilerServices
{
[CompilerGenerated]
[Embedded]
[AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)]
internal sealed class RefSafetyRulesAttribute : Attribute
{
public readonly int Version;
public RefSafetyRulesAttribute(int P_0)
{
Version = P_0;
}
}
}
namespace GTFOCheckpointPrototype
{
public class GuiBehaviour : MonoBehaviour
{
private static string _message = "";
private static float _messageUntil;
private static GUIStyle _style;
private static GuiBehaviour _instance;
private static bool _overlayWasVisible;
private static GUIStyle _headingStyle;
private static GUIStyle _slotStyle;
private static GUIStyle _seedStyle;
private static GUIStyle _dateTimeStyle;
private static GUIStyle _cowStyle;
private static GUIStyle _footerStyle;
public GuiBehaviour(IntPtr ptr)
: base(ptr)
{
}
private void Awake()
{
_instance = this;
}
public static void QueueF8Apply()
{
if ((Object)(object)_instance == (Object)null)
{
Plugin instance = Plugin.Instance;
if (instance != null)
{
((BasePlugin)instance).Log.LogWarning((object)"F8: GUI instance unavailable.");
}
}
else
{
((MonoBehaviour)_instance).CancelInvoke("ApplyF8NextFrame");
((MonoBehaviour)_instance).Invoke("ApplyF8NextFrame", 0f);
}
}
private void ApplyF8NextFrame()
{
PlayerGuiLayerUpdatePatch.ExecuteQueuedF8();
}
private void EnsureStyle()
{
//IL_0012: Unknown result type (might be due to invalid IL or missing references)
//IL_0017: Unknown result type (might be due to invalid IL or missing references)
//IL_001f: Unknown result type (might be due to invalid IL or missing references)
//IL_002b: Expected O, but got Unknown
//IL_0035: Unknown result type (might be due to invalid IL or missing references)
if (_style == null)
{
_style = new GUIStyle(GUI.skin.label)
{
fontSize = 24,
alignment = (TextAnchor)1
};
_style.normal.textColor = Color.red;
}
}
public void OnGUI()
{
//IL_004a: Unknown result type (might be due to invalid IL or missing references)
//IL_0054: Expected O, but got Unknown
//IL_004f: Unknown result type (might be due to invalid IL or missing references)
//IL_0054: Unknown result type (might be due to invalid IL or missing references)
//IL_005f: Unknown result type (might be due to invalid IL or missing references)
//IL_0070: Unknown result type (might be due to invalid IL or missing references)
//IL_0075: Unknown result type (might be due to invalid IL or missing references)
//IL_007f: Unknown result type (might be due to invalid IL or missing references)
//IL_0094: Unknown result type (might be due to invalid IL or missing references)
EnsureStyle();
bool isSaveSlotSelectorVisible = PlayerGuiLayerUpdatePatch.IsSaveSlotSelectorVisible;
if (isSaveSlotSelectorVisible && !_overlayWasVisible)
{
PlayerGuiLayerUpdatePatch.RefreshSaveSlotCache();
}
_overlayWasVisible = isSaveSlotSelectorVisible;
if (isSaveSlotSelectorVisible)
{
DrawSaveSlotSelector();
}
if (!(Time.unscaledTime >= _messageUntil) && !string.IsNullOrEmpty(_message))
{
Vector2 val = _style.CalcSize(new GUIContent(_message));
Rect val2 = new Rect(10f, 25f, val.x + 10f, 35f);
GUI.color = Color.black;
GUI.DrawTexture(val2, (Texture)(object)Texture2D.whiteTexture);
GUI.color = _style.normal.textColor;
GUI.Label(val2, _message, _style);
}
}
private static void BuildOverlayStyles()
{
//IL_000a: Unknown result type (might be due to invalid IL or missing references)
//IL_0014: Expected O, but got Unknown
//IL_0035: Unknown result type (might be due to invalid IL or missing references)
//IL_0054: Unknown result type (might be due to invalid IL or missing references)
//IL_005e: Expected O, but got Unknown
//IL_007f: Unknown result type (might be due to invalid IL or missing references)
//IL_009e: Unknown result type (might be due to invalid IL or missing references)
//IL_00a8: Expected O, but got Unknown
//IL_00dd: Unknown result type (might be due to invalid IL or missing references)
//IL_00fc: Unknown result type (might be due to invalid IL or missing references)
//IL_0106: Expected O, but got Unknown
//IL_013b: Unknown result type (might be due to invalid IL or missing references)
//IL_015a: Unknown result type (might be due to invalid IL or missing references)
//IL_0164: Expected O, but got Unknown
//IL_0184: Unknown result type (might be due to invalid IL or missing references)
//IL_0198: Unknown result type (might be due to invalid IL or missing references)
//IL_01a2: Expected O, but got Unknown
//IL_01c3: Unknown result type (might be due to invalid IL or missing references)
_headingStyle = new GUIStyle(GUI.skin.label);
_headingStyle.fontSize = 22;
_headingStyle.fontStyle = (FontStyle)1;
_headingStyle.normal.textColor = Color.red;
_headingStyle.alignment = (TextAnchor)4;
_slotStyle = new GUIStyle(GUI.skin.label);
_slotStyle.fontSize = 20;
_slotStyle.alignment = (TextAnchor)4;
_slotStyle.normal.textColor = Color.red;
_slotStyle.wordWrap = true;
_seedStyle = new GUIStyle(GUI.skin.label);
_seedStyle.fontSize = 11;
_seedStyle.alignment = (TextAnchor)4;
_seedStyle.normal.textColor = new Color(1f, 0.35f, 0.35f, 1f);
_seedStyle.wordWrap = false;
_dateTimeStyle = new GUIStyle(GUI.skin.label);
_dateTimeStyle.fontSize = 10;
_dateTimeStyle.alignment = (TextAnchor)4;
_dateTimeStyle.normal.textColor = new Color(1f, 0.55f, 0.55f, 1f);
_dateTimeStyle.wordWrap = false;
_cowStyle = new GUIStyle(GUI.skin.label);
_cowStyle.fontSize = 7;
_cowStyle.alignment = (TextAnchor)4;
_cowStyle.normal.textColor = Color.red;
_footerStyle = new GUIStyle(GUI.skin.label);
_footerStyle.fontSize = 18;
_footerStyle.alignment = (TextAnchor)4;
_footerStyle.normal.textColor = Color.red;
}
private static void DrawSaveSlotSelector()
{
//IL_004f: Unknown result type (might be due to invalid IL or missing references)
//IL_0085: Unknown result type (might be due to invalid IL or missing references)
//IL_00bb: Unknown result type (might be due to invalid IL or missing references)
//IL_0217: Unknown result type (might be due to invalid IL or missing references)
//IL_023e: Unknown result type (might be due to invalid IL or missing references)
//IL_00fa: Unknown result type (might be due to invalid IL or missing references)
//IL_00df: Unknown result type (might be due to invalid IL or missing references)
//IL_028d: Unknown result type (might be due to invalid IL or missing references)
//IL_027d: Unknown result type (might be due to invalid IL or missing references)
//IL_0104: Unknown result type (might be due to invalid IL or missing references)
//IL_010f: Unknown result type (might be due to invalid IL or missing references)
//IL_0178: Unknown result type (might be due to invalid IL or missing references)
//IL_01b7: Unknown result type (might be due to invalid IL or missing references)
//IL_014e: Unknown result type (might be due to invalid IL or missing references)
//IL_01f8: Unknown result type (might be due to invalid IL or missing references)
if (_headingStyle == null)
{
BuildOverlayStyles();
}
float num = 798f;
float num2 = ((float)Screen.width - num) * 0.5f;
float num3 = Mathf.Max(150f, (float)Screen.height * 0.48f);
GUI.Label(new Rect(0f, num3 - 48f, (float)Screen.width, 34f), "Select a save slot with the arrow keys", _headingStyle);
GUI.Label(new Rect((float)Screen.width - 40f, (float)Screen.height - 35f, 50f, 45f), "MT", _cowStyle);
for (int i = 0; i < 5; i++)
{
float num4 = num2 + (float)i * 162f;
Rect val = new Rect(num4, num3, 150f, 112f);
GUI.color = ((i == PlayerGuiLayerUpdatePatch.SelectedSaveSlot) ? new Color(0.3f, 0.02f, 0.02f, 0.96f) : new Color(0f, 0f, 0f, 0.92f));
GUI.DrawTexture(val, (Texture)(object)Texture2D.whiteTexture);
GUI.color = Color.red;
GUI.Box(val, GUIContent.none);
string saveSlotDateTimeLabel = PlayerGuiLayerUpdatePatch.GetSaveSlotDateTimeLabel(i);
if (!string.IsNullOrEmpty(saveSlotDateTimeLabel))
{
GUI.Label(new Rect(num4 + 5f, num3 + 2f, 140f, 16f), saveSlotDateTimeLabel, _dateTimeStyle);
}
GUI.Label(new Rect(num4 + 5f, num3 + 18f, 140f, 34f), "SLOT " + (i + 1), _slotStyle);
GUI.Label(new Rect(num4 + 5f, num3 + 50f, 140f, 42f), PlayerGuiLayerUpdatePatch.GetSaveSlotLabel(i), _slotStyle);
string saveSlotSessionSeedLabel = PlayerGuiLayerUpdatePatch.GetSaveSlotSessionSeedLabel(i);
if (!string.IsNullOrEmpty(saveSlotSessionSeedLabel))
{
GUI.Label(new Rect(num4 + 5f, num3 + 91f, 140f, 20f), saveSlotSessionSeedLabel, _seedStyle);
}
}
GUI.color = Color.red;
GUI.Label(new Rect(0f, num3 + 112f + 14f, (float)Screen.width, 30f), "F5 - Save F8 - Force Seed F9 - Load Solo F10 - Load Multiplayer", _footerStyle);
string overlaySeedStatus = PlayerGuiLayerUpdatePatch.GetOverlaySeedStatus();
if (!string.IsNullOrEmpty(overlaySeedStatus))
{
GUI.Label(new Rect(0f, num3 + 112f + 43f, (float)Screen.width, 26f), overlaySeedStatus, _footerStyle);
}
GUI.color = Color.white;
}
public static void ShowTemporary(string message, float seconds)
{
_message = message;
_messageUntil = Time.unscaledTime + seconds;
}
}
[BepInPlugin("com.example.gtfocheckpointprototype", "GTFO Checkpoint Prototype", "1.0.0")]
public class Plugin : BasePlugin
{
public static Plugin Instance { get; private set; }
public override void Load()
{
//IL_0012: Unknown result type (might be due to invalid IL or missing references)
Instance = this;
((BasePlugin)this).AddComponent<GuiBehaviour>();
new Harmony("com.example.gtfocheckpointprototype").PatchAll();
((BasePlugin)this).Log.LogInfo((object)"GTFO checkpoint mod loaded.");
}
}
[HarmonyPatch(typeof(RundownManager), "MasterSelectActiveExpedition")]
public static class RundownManagerMasterSelectActiveExpeditionPatch
{
public static void Postfix()
{
//IL_002c: Unknown result type (might be due to invalid IL or missing references)
//IL_0032: Expected O, but got Unknown
try
{
if (PlayerGuiLayerUpdatePatch.IsF8Armed && SNet.IsMaster)
{
GuiBehaviour.QueueF8Apply();
}
}
catch (Exception ex)
{
Plugin instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log = ((BasePlugin)instance).Log;
bool flag = default(bool);
BepInExErrorLogInterpolatedStringHandler val = new BepInExErrorLogInterpolatedStringHandler(22, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("F8 scheduling failed: ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(ex.Message);
}
log.LogError(val);
}
}
}
}
[HarmonyPatch(typeof(PlayerGuiLayer), "Update")]
public static class PlayerGuiLayerUpdatePatch
{
private struct SaveSlotInfo
{
public string Label;
public string SessionSeedLabel;
public string DateTimeLabel;
}
private struct SavedMetadata
{
public string LevelId;
public bool HasSeeds;
public int HostIDSeed;
public int SessionSeed;
public bool HasSaveDateTime;
public DateTime SaveDateTime;
}
private const int SaveSlotCount = 5;
private static SNet_CaptureBuffer _clonedCheckpoint;
private static bool _f8Armed;
private static bool _f8AppliedThisSelection;
private static int _f8SaveSlot;
private static int _selectedSaveSlot;
private static readonly SaveSlotInfo[] _saveSlotCache = new SaveSlotInfo[5];
private static bool _forcingSeedKnown;
private static int _forcingSeed;
public static int SelectedSaveSlot => _selectedSaveSlot;
public static bool IsSaveSlotSelectorVisible => Input.GetKey((KeyCode)96);
public static bool IsF8Armed => _f8Armed;
private static string GetCheckpointSavePath(int slot)
{
string path = Path.Combine(Paths.PluginPath, "SaveAnywhere");
string path2 = ((slot == 0) ? "checkpoint.dat" : $"checkpoint-slot-{slot + 1}.dat");
return Path.Combine(path, path2);
}
private static string GetSelectedCheckpointSavePath()
{
return GetCheckpointSavePath(_selectedSaveSlot);
}
private static void ChangeSelectedSaveSlot(int delta)
{
//IL_0024: Unknown result type (might be due to invalid IL or missing references)
//IL_002a: Expected O, but got Unknown
_selectedSaveSlot = (_selectedSaveSlot + delta + 5) % 5;
Plugin instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log = ((BasePlugin)instance).Log;
bool flag = default(bool);
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(35, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("Slot selector: selected save slot ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<int>(_selectedSaveSlot + 1);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(".");
}
log.LogInfo(val);
}
}
public static void RefreshSaveSlotCache()
{
for (int i = 0; i < 5; i++)
{
SaveSlotInfo saveSlotInfo = default(SaveSlotInfo);
string checkpointSavePath = GetCheckpointSavePath(i);
if (!File.Exists(checkpointSavePath))
{
saveSlotInfo.Label = "EMPTY";
saveSlotInfo.SessionSeedLabel = string.Empty;
saveSlotInfo.DateTimeLabel = string.Empty;
}
else
{
SavedMetadata saved;
bool flag = TryReadSavedMetadataFromPath(checkpointSavePath, out saved);
saveSlotInfo.Label = ((flag && !string.IsNullOrEmpty(saved.LevelId)) ? saved.LevelId : "SAVED");
saveSlotInfo.SessionSeedLabel = ((flag && saved.HasSeeds) ? ("SessionSeed: " + saved.SessionSeed) : "SessionSeed: unavailable");
saveSlotInfo.DateTimeLabel = ((flag && saved.HasSaveDateTime) ? saved.SaveDateTime.ToString("dd/MM/yyyy HH:mm") : string.Empty);
}
_saveSlotCache[i] = saveSlotInfo;
}
_forcingSeedKnown = false;
if (_f8Armed && TryReadSavedMetadataFromPath(GetCheckpointSavePath(_f8SaveSlot), out var saved2) && saved2.HasSeeds)
{
_forcingSeed = saved2.SessionSeed;
_forcingSeedKnown = true;
}
}
public static string GetSaveSlotLabel(int slot)
{
return _saveSlotCache[slot].Label;
}
public static string GetSaveSlotSessionSeedLabel(int slot)
{
return _saveSlotCache[slot].SessionSeedLabel;
}
public static string GetSaveSlotDateTimeLabel(int slot)
{
return _saveSlotCache[slot].DateTimeLabel;
}
public static string GetOverlaySeedStatus()
{
try
{
ExpeditionInTierData activeExpedition = RundownManager.ActiveExpedition;
if (activeExpedition != null)
{
return "Current seed: " + activeExpedition.SessionSeed;
}
}
catch (Exception ex)
{
Plugin instance = Plugin.Instance;
if (instance != null)
{
((BasePlugin)instance).Log.LogDebug((object)("Save-slot overlay: current SessionSeed unavailable: " + ex.Message));
}
}
if (_f8Armed && _forcingSeedKnown)
{
return "Currently forcing seed: " + _forcingSeed;
}
return string.Empty;
}
public static void Postfix()
{
//IL_0141: Unknown result type (might be due to invalid IL or missing references)
//IL_0148: Expected O, but got Unknown
//IL_00d5: Unknown result type (might be due to invalid IL or missing references)
//IL_00db: Expected O, but got Unknown
bool flag = default(bool);
try
{
if (Input.GetKeyDown((KeyCode)286))
{
SaveWithF5();
RefreshSaveSlotCache();
}
if (Input.GetKey((KeyCode)96))
{
if (Input.GetKeyDown((KeyCode)276))
{
ChangeSelectedSaveSlot(-1);
}
else if (Input.GetKeyDown((KeyCode)275))
{
ChangeSelectedSaveSlot(1);
}
}
if (Input.GetKeyDown((KeyCode)289))
{
_f8SaveSlot = _selectedSaveSlot;
if (!TryReadSavedMetadataFromPath(GetCheckpointSavePath(_f8SaveSlot), out var saved) || !saved.HasSeeds)
{
_f8Armed = false;
GuiBehaviour.ShowTemporary("(F8) No valid save with seeds", 3f);
}
else
{
_f8Armed = true;
_f8AppliedThisSelection = false;
string text = saved.LevelId ?? "unknown (v2)";
GuiBehaviour.ShowTemporary("(F8) Forcing level generation for level: " + text, 10f);
Plugin instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(45, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("F8 armed for saved level '");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(text);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("' (read from disk).");
}
log.LogInfo(val);
}
}
RefreshSaveSlotCache();
}
if (Input.GetKeyDown((KeyCode)290))
{
LoadSoloWithF9();
}
if (Input.GetKeyDown((KeyCode)291))
{
LoadMultiplayerWithF10();
}
}
catch (Exception ex)
{
Plugin instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log2 = ((BasePlugin)instance).Log;
BepInExErrorLogInterpolatedStringHandler val2 = new BepInExErrorLogInterpolatedStringHandler(25, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral("Hotkey operation failed: ");
((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<Exception>(ex);
}
log2.LogError(val2);
}
}
}
private static void SaveWithF5()
{
//IL_0067: Unknown result type (might be due to invalid IL or missing references)
//IL_006d: Expected O, but got Unknown
if (!IsInLevel())
{
GuiBehaviour.ShowTemporary("(F5) Only available in level", 2f);
return;
}
if (!IsHost())
{
GuiBehaviour.ShowTemporary("(F5) Host only", 2f);
return;
}
CaptureCheckpointBuffer();
BuildCheckpointClone();
SaveCheckpointToDisk();
if (HasLoadedCheckpoint())
{
GuiBehaviour.ShowTemporary("(F5) Game saved", 2f);
Plugin instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log = ((BasePlugin)instance).Log;
bool flag = default(bool);
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(30, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("F5: checkpoint saved to slot ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<int>(_selectedSaveSlot + 1);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(".");
}
log.LogInfo(val);
}
}
else
{
GuiBehaviour.ShowTemporary("(F5) Save failed", 2f);
}
}
private static bool TryExtractLevelId(string value, out string levelId)
{
levelId = null;
if (string.IsNullOrEmpty(value))
{
return false;
}
Match match = Regex.Match(value.Trim().ToUpperInvariant(), "(?<![A-Z0-9])R\\d+[A-E]\\d+(?![A-Z0-9])");
if (!match.Success)
{
return false;
}
levelId = match.Value;
return true;
}
private static bool TryGetCurrentLevelId(out string levelId)
{
levelId = null;
try
{
return TryExtractLevelId(RundownManager.ActiveExpeditionHeader, out levelId);
}
catch
{
return false;
}
}
private static bool ValidateSavedLevel(SavedMetadata saved)
{
//IL_003b: Unknown result type (might be due to invalid IL or missing references)
//IL_0041: Expected O, but got Unknown
//IL_00b1: Unknown result type (might be due to invalid IL or missing references)
//IL_00b7: Expected O, but got Unknown
if (string.IsNullOrEmpty(saved.LevelId))
{
return true;
}
bool flag = default(bool);
if (!TryGetCurrentLevelId(out var levelId))
{
GuiBehaviour.ShowTemporary("(Load) Could not identify current GTFO level", 3f);
Plugin instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log = ((BasePlugin)instance).Log;
BepInExWarningLogInterpolatedStringHandler val = new BepInExWarningLogInterpolatedStringHandler(70, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("Saved level is '");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(saved.LevelId);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("', but the current GTFO level could not be identified.");
}
log.LogWarning(val);
}
return false;
}
if (!string.Equals(levelId, saved.LevelId, StringComparison.OrdinalIgnoreCase))
{
GuiBehaviour.ShowTemporary("(Load) Wrong level. Save: " + saved.LevelId + ", Current: " + levelId, 4f);
Plugin instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log2 = ((BasePlugin)instance).Log;
BepInExWarningLogInterpolatedStringHandler val = new BepInExWarningLogInterpolatedStringHandler(43, 2, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("Checkpoint level mismatch. Save=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(saved.LevelId);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(", Current=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(levelId);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(".");
}
log2.LogWarning(val);
}
return false;
}
return true;
}
private static bool ValidateSavedSessionSeed(SavedMetadata saved)
{
//IL_0082: Unknown result type (might be due to invalid IL or missing references)
//IL_0088: Expected O, but got Unknown
//IL_018f: Unknown result type (might be due to invalid IL or missing references)
//IL_0195: Expected O, but got Unknown
//IL_012e: Unknown result type (might be due to invalid IL or missing references)
//IL_0135: Expected O, but got Unknown
if (!saved.HasSeeds)
{
GuiBehaviour.ShowTemporary("(Load) Save has no SessionSeed", 3f);
Plugin instance = Plugin.Instance;
if (instance != null)
{
((BasePlugin)instance).Log.LogWarning((object)"Checkpoint SessionSeed validation failed: save has no stored generation seeds.");
}
return false;
}
ExpeditionInTierData activeExpedition = RundownManager.ActiveExpedition;
if (activeExpedition == null)
{
GuiBehaviour.ShowTemporary("(Load) Expedition unavailable", 3f);
Plugin instance2 = Plugin.Instance;
if (instance2 != null)
{
((BasePlugin)instance2).Log.LogWarning((object)"Checkpoint SessionSeed validation failed: no active expedition.");
}
return false;
}
int sessionSeed = activeExpedition.SessionSeed;
Plugin instance3 = Plugin.Instance;
bool flag = default(bool);
if (instance3 != null)
{
ManualLogSource log = ((BasePlugin)instance3).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(52, 2, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("Checkpoint SessionSeed validation: saved=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<int>(saved.SessionSeed);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(", current=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<int>(sessionSeed);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(".");
}
log.LogInfo(val);
}
if (sessionSeed != saved.SessionSeed)
{
GuiBehaviour.ShowTemporary($"(Load) SessionSeed mismatch. Save: {saved.SessionSeed}, Current: {sessionSeed}", 4f);
instance3 = Plugin.Instance;
if (instance3 != null)
{
ManualLogSource log2 = ((BasePlugin)instance3).Log;
BepInExWarningLogInterpolatedStringHandler val2 = new BepInExWarningLogInterpolatedStringHandler(63, 2, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral("Checkpoint SessionSeed mismatch. Save=");
((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<int>(saved.SessionSeed);
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral(", Current=");
((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<int>(sessionSeed);
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral(". Load refused.");
}
log2.LogWarning(val2);
}
return false;
}
instance3 = Plugin.Instance;
if (instance3 != null)
{
ManualLogSource log3 = ((BasePlugin)instance3).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(33, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("Checkpoint SessionSeed matched: ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<int>(saved.SessionSeed);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(".");
}
log3.LogInfo(val);
}
return true;
}
private static void LoadSoloWithF9()
{
//IL_0086: Unknown result type (might be due to invalid IL or missing references)
//IL_008c: Expected O, but got Unknown
SavedMetadata saved;
if (!IsInLevel())
{
GuiBehaviour.ShowTemporary("(F9) Only available in level", 2f);
}
else if (!IsHost())
{
GuiBehaviour.ShowTemporary("(F9) Host only", 2f);
}
else if (!LoadCheckpointFromDisk(out saved))
{
GuiBehaviour.ShowTemporary("(F9) No savegame found", 2f);
}
else
{
if (!ValidateSavedLevel(saved) || !ValidateSavedSessionSeed(saved))
{
return;
}
InstallCloneAndRecall();
CaptureCheckpointBuffer();
GuiBehaviour.ShowTemporary("(F9) Game loaded (solo)", 2f);
Plugin instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log = ((BasePlugin)instance).Log;
bool flag = default(bool);
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(33, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("F9: checkpoint loaded from slot ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<int>(_selectedSaveSlot + 1);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(".");
}
log.LogInfo(val);
}
}
}
private static void LoadMultiplayerWithF10()
{
//IL_0013: Unknown result type (might be due to invalid IL or missing references)
//IL_001a: Expected O, but got Unknown
//IL_007f: Unknown result type (might be due to invalid IL or missing references)
//IL_0086: Expected O, but got Unknown
//IL_00c2: Unknown result type (might be due to invalid IL or missing references)
//IL_00c9: Expected O, but got Unknown
//IL_0109: Unknown result type (might be due to invalid IL or missing references)
//IL_0110: Expected O, but got Unknown
//IL_01a9: Unknown result type (might be due to invalid IL or missing references)
//IL_01b0: Expected O, but got Unknown
//IL_028c: Unknown result type (might be due to invalid IL or missing references)
//IL_0293: Expected O, but got Unknown
//IL_024d: Unknown result type (might be due to invalid IL or missing references)
//IL_0254: Expected O, but got Unknown
//IL_0203: Unknown result type (might be due to invalid IL or missing references)
//IL_02e6: Unknown result type (might be due to invalid IL or missing references)
//IL_02ed: Expected O, but got Unknown
//IL_0379: Unknown result type (might be due to invalid IL or missing references)
//IL_0380: Expected O, but got Unknown
//IL_03c0: Unknown result type (might be due to invalid IL or missing references)
//IL_03c7: Expected O, but got Unknown
//IL_0407: Unknown result type (might be due to invalid IL or missing references)
//IL_040e: Expected O, but got Unknown
//IL_0445: Unknown result type (might be due to invalid IL or missing references)
//IL_044c: Expected O, but got Unknown
//IL_04ca: Unknown result type (might be due to invalid IL or missing references)
//IL_04d1: Expected O, but got Unknown
//IL_0508: Unknown result type (might be due to invalid IL or missing references)
//IL_050f: Expected O, but got Unknown
//IL_054b: Unknown result type (might be due to invalid IL or missing references)
//IL_0552: Expected O, but got Unknown
//IL_0598: Unknown result type (might be due to invalid IL or missing references)
//IL_059f: Expected O, but got Unknown
Plugin instance = Plugin.Instance;
bool flag = default(bool);
if (instance != null)
{
ManualLogSource log = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(7, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": BEGIN");
}
log.LogInfo(val);
}
if (!IsInLevel())
{
GuiBehaviour.ShowTemporary("(F10) Only available in level", 2f);
return;
}
if (!IsHost())
{
GuiBehaviour.ShowTemporary("(F10) Host only", 2f);
return;
}
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log2 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(32, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": before CaptureCheckpointBuffer");
}
log2.LogInfo(val);
}
CaptureCheckpointBuffer();
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log3 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(31, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": after CaptureCheckpointBuffer");
}
log3.LogInfo(val);
}
SNet_Capture capture = GetCapture();
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log4 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(20, 3, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": capture=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(((Object)(object)capture == (Object)null) ? "NULL" : "OK");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(", buffers=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>((((capture != null) ? capture.m_buffers : null) == null) ? "NULL" : ((Il2CppArrayBase<SNet_CaptureBuffer>)(object)capture.m_buffers).Length.ToString());
}
log4.LogInfo(val);
}
SNet_CaptureBuffer liveCheckpoint = GetLiveCheckpoint(capture);
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log5 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(19, 2, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": nativeCheckpoint=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>((liveCheckpoint == null) ? "NULL" : $"OK valid={liveCheckpoint.isValid} type={liveCheckpoint.type}");
}
log5.LogInfo(val);
}
if (liveCheckpoint == null)
{
GuiBehaviour.ShowTemporary("(F10) Cannot load save - Try pressing F9 first", 2f);
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log6 = ((BasePlugin)instance).Log;
BepInExWarningLogInterpolatedStringHandler val2 = new BepInExWarningLogInterpolatedStringHandler(42, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral(": native checkpoint is NULL; aborting F10.");
}
log6.LogWarning(val2);
}
return;
}
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log7 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(31, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": before LoadCheckpointFromDisk");
}
log7.LogInfo(val);
}
if (!LoadCheckpointFromDisk(out var saved))
{
GuiBehaviour.ShowTemporary("(F10) No savegame found", 2f);
return;
}
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log8 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(44, 4, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": disk save loaded level=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(saved.LevelId ?? "null");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(", hasSeeds=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<bool>(saved.HasSeeds);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(", clone=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>((_clonedCheckpoint == null) ? "NULL" : "OK");
}
log8.LogInfo(val);
}
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log9 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(27, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": before ValidateSavedLevel");
}
log9.LogInfo(val);
}
if (!ValidateSavedLevel(saved))
{
return;
}
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log10 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(26, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": after ValidateSavedLevel");
}
log10.LogInfo(val);
}
if (!ValidateSavedSessionSeed(saved))
{
return;
}
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log11 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(32, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": after ValidateSavedSessionSeed");
}
log11.LogInfo(val);
}
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log12 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(50, 3, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": before ReplaceCheckpointContents target=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>((liveCheckpoint == null) ? "NULL" : "OK");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(" source=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>((_clonedCheckpoint == null) ? "NULL" : "OK");
}
log12.LogInfo(val);
}
ReplaceCheckpointContents(liveCheckpoint, _clonedCheckpoint);
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log13 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(33, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": after ReplaceCheckpointContents");
}
log13.LogInfo(val);
}
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log14 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(27, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": before TryEndPlayingViaGS");
}
log14.LogInfo(val);
}
TryEndPlayingViaGS();
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log15 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(26, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("F10");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": after TryEndPlayingViaGS");
}
log15.LogInfo(val);
}
GuiBehaviour.ShowTemporary("(F10) Ready to load checkpoint (multiplayer)", 3f);
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log16 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(48, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("F10: multiplayer checkpoint prepared from slot ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<int>(_selectedSaveSlot + 1);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(".");
}
log16.LogInfo(val);
}
}
public static void ExecuteQueuedF8()
{
//IL_0038: Unknown result type (might be due to invalid IL or missing references)
//IL_003e: Expected O, but got Unknown
try
{
if (_f8Armed && !_f8AppliedThisSelection)
{
_f8AppliedThisSelection = true;
_f8Armed = false;
ApplySavedExpeditionSeeds();
}
}
catch (Exception ex)
{
Plugin instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log = ((BasePlugin)instance).Log;
bool flag = default(bool);
BepInExErrorLogInterpolatedStringHandler val = new BepInExErrorLogInterpolatedStringHandler(21, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("F8 execution failed: ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(ex.Message);
}
log.LogError(val);
}
GuiBehaviour.ShowTemporary("(F8) Failed - see log", 3f);
}
}
private static void ApplySavedExpeditionSeeds()
{
//IL_010d: Unknown result type (might be due to invalid IL or missing references)
//IL_0114: Expected O, but got Unknown
if (!IsHost())
{
GuiBehaviour.ShowTemporary("(F8) Host only", 2f);
return;
}
if (!TryReadSavedMetadataFromPath(GetCheckpointSavePath(_f8SaveSlot), out var saved) || !saved.HasSeeds)
{
GuiBehaviour.ShowTemporary("(F8) Selected save has no usable seeds", 3f);
Plugin instance = Plugin.Instance;
if (instance != null)
{
((BasePlugin)instance).Log.LogWarning((object)"F8: checkpoint.dat missing, invalid, or has no seeds.");
}
return;
}
ExpeditionInTierData activeExpedition = RundownManager.ActiveExpedition;
if (activeExpedition == null)
{
GuiBehaviour.ShowTemporary("(F8) No active expedition", 2f);
return;
}
if (!ValidateSavedLevel(saved))
{
Plugin instance2 = Plugin.Instance;
if (instance2 != null)
{
((BasePlugin)instance2).Log.LogWarning((object)"F8: saved checkpoint belongs to a different level.");
}
return;
}
activeExpedition.SetSeeds(saved.HostIDSeed, saved.SessionSeed);
pActiveExpedition activeExpeditionData = RundownManager.GetActiveExpeditionData();
activeExpeditionData.hostIDSeed = saved.HostIDSeed;
activeExpeditionData.sessionSeed = saved.SessionSeed;
RundownManager current = RundownManager.Current;
if ((Object)(object)current == (Object)null)
{
throw new InvalidOperationException("RundownManager.Current is null.");
}
current.SetActiveExpeditionData(activeExpeditionData);
RefreshSyncManagerLevelChecksum();
GuiBehaviour.ShowTemporary("(F8) Seeds applied successfully", 3f);
Plugin instance3 = Plugin.Instance;
if (instance3 != null)
{
ManualLogSource log = ((BasePlugin)instance3).Log;
bool flag = default(bool);
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(53, 3, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("F8: saved expedition seeds applied from slot ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<int>(_f8SaveSlot + 1);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": H=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<int>(saved.HostIDSeed);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(" S=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<int>(saved.SessionSeed);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(".");
}
log.LogInfo(val);
}
}
private static void RefreshSyncManagerLevelChecksum()
{
//IL_0034: Unknown result type (might be due to invalid IL or missing references)
//IL_003b: Expected O, but got Unknown
//IL_00c1: Unknown result type (might be due to invalid IL or missing references)
//IL_00c8: Expected O, but got Unknown
if (!IsHost())
{
return;
}
ExpeditionInTierData activeExpedition = RundownManager.ActiveExpedition;
if (activeExpedition == null)
{
return;
}
uint checksum;
bool flag = default(bool);
Plugin instance;
try
{
checksum = activeExpedition.GetChecksum();
}
catch (Exception ex)
{
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log = ((BasePlugin)instance).Log;
BepInExWarningLogInterpolatedStringHandler val = new BepInExWarningLogInterpolatedStringHandler(33, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("F8: failed to recreate checksum: ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(ex.Message);
}
log.LogWarning(val);
}
return;
}
Il2CppArrayBase<SNet_SyncManager> val2 = Object.FindObjectsOfType<SNet_SyncManager>();
if (val2 == null)
{
return;
}
foreach (SNet_SyncManager item in val2)
{
if ((Object)(object)item != (Object)null)
{
item.SetLevelChecksum(checksum);
}
}
instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log2 = ((BasePlugin)instance).Log;
BepInExInfoLogInterpolatedStringHandler val3 = new BepInExInfoLogInterpolatedStringHandler(27, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("F8: refreshed checksum to ");
((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<uint>(checksum);
((BepInExLogInterpolatedStringHandler)val3).AppendLiteral(".");
}
log2.LogInfo(val3);
}
}
private static SNet_Capture GetCapture()
{
Il2CppArrayBase<SNet_Capture> val = Object.FindObjectsOfType<SNet_Capture>();
if (val == null || val.Length <= 0)
{
return null;
}
return val[0];
}
private static bool IsHost()
{
return SNet.IsMaster;
}
private static bool IsInLevel()
{
//IL_0000: Unknown result type (might be due to invalid IL or missing references)
//IL_0007: Invalid comparison between Unknown and I4
return (int)GameStateManager.CurrentStateName == 10;
}
private static SNet_CaptureBuffer GetLiveCheckpoint(SNet_Capture capture)
{
//IL_0029: Unknown result type (might be due to invalid IL or missing references)
//IL_002f: Invalid comparison between Unknown and I4
if (((capture != null) ? capture.m_buffers : null) == null)
{
return null;
}
foreach (SNet_CaptureBuffer item in (Il2CppArrayBase<SNet_CaptureBuffer>)(object)capture.m_buffers)
{
if (item != null && (int)item.type == 3)
{
return item;
}
}
return null;
}
private static void CaptureCheckpointBuffer()
{
//IL_003c: Unknown result type (might be due to invalid IL or missing references)
//IL_0042: Expected O, but got Unknown
//IL_0099: Unknown result type (might be due to invalid IL or missing references)
//IL_009f: Expected O, but got Unknown
Plugin instance = Plugin.Instance;
if (instance != null)
{
((BasePlugin)instance).Log.LogInfo((object)"Checkpoint capture: BEGIN");
}
if (!IsHost())
{
return;
}
SNet_Capture capture = GetCapture();
Plugin instance2 = Plugin.Instance;
bool flag = default(bool);
if (instance2 != null)
{
ManualLogSource log = ((BasePlugin)instance2).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(33, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("Checkpoint capture: SNet_Capture=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(((Object)(object)capture == (Object)null) ? "NULL" : "OK");
}
log.LogInfo(val);
}
if ((Object)(object)capture == (Object)null)
{
throw new InvalidOperationException("No SNet_Capture found.");
}
instance2 = Plugin.Instance;
if (instance2 != null)
{
ManualLogSource log2 = ((BasePlugin)instance2).Log;
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(28, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("Checkpoint capture: buffers=");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>((capture.m_buffers == null) ? "NULL" : ((Il2CppArrayBase<SNet_CaptureBuffer>)(object)capture.m_buffers).Length.ToString());
}
log2.LogInfo(val);
}
capture.CaptureGameState((eBufferType)3);
Plugin instance3 = Plugin.Instance;
if (instance3 != null)
{
((BasePlugin)instance3).Log.LogInfo((object)"Checkpoint capture: CaptureGameState returned");
}
_clonedCheckpoint = null;
}
private static void BuildCheckpointClone()
{
//IL_0028: Unknown result type (might be due to invalid IL or missing references)
//IL_002d: Unknown result type (might be due to invalid IL or missing references)
//IL_002f: Unknown result type (might be due to invalid IL or missing references)
//IL_0039: Unknown result type (might be due to invalid IL or missing references)
//IL_003b: Unknown result type (might be due to invalid IL or missing references)
//IL_0046: Expected O, but got Unknown
if (!IsHost())
{
return;
}
SNet_CaptureBuffer liveCheckpoint = GetLiveCheckpoint(GetCapture());
if (liveCheckpoint == null || !liveCheckpoint.isValid || liveCheckpoint.m_passes == null)
{
return;
}
SNet_CaptureBuffer val = new SNet_CaptureBuffer((eBufferType)3)
{
type = liveCheckpoint.type,
data = liveCheckpoint.data
};
Il2CppReferenceArray<List<Il2CppStructArray<byte>>> val2 = new Il2CppReferenceArray<List<Il2CppStructArray<byte>>>((long)((Il2CppArrayBase<List<Il2CppStructArray<byte>>>)(object)liveCheckpoint.m_passes).Length);
for (int i = 0; i < ((Il2CppArrayBase<List<Il2CppStructArray<byte>>>)(object)liveCheckpoint.m_passes).Length; i++)
{
List<Il2CppStructArray<byte>> val3 = ((Il2CppArrayBase<List<Il2CppStructArray<byte>>>)(object)liveCheckpoint.m_passes)[i];
List<Il2CppStructArray<byte>> val4 = new List<Il2CppStructArray<byte>>();
if (val3 != null)
{
for (int j = 0; j < val3.Count; j++)
{
Il2CppStructArray<byte> val5 = val3[j];
if (val5 != null)
{
val4.Add(CopyByteArray(val5));
}
}
}
((Il2CppArrayBase<List<Il2CppStructArray<byte>>>)(object)val2)[i] = val4;
}
val.m_passes = val2;
val.isValid = true;
_clonedCheckpoint = val;
}
private static void TryEndPlayingViaGS()
{
//IL_0020: Unknown result type (might be due to invalid IL or missing references)
if (IsHost() && GameStateManager.CurrentState != null && IsInLevel())
{
new GS_InLevel(((Il2CppObjectBase)GameStateManager.CurrentState).Pointer).TryEndPlaying(GS_InLevel.FAIL_COMMAND_CODE);
}
}
private static void ReplaceCheckpointContents(SNet_CaptureBuffer target, SNet_CaptureBuffer source)
{
if (IsHost() && target != null && source != null && source.isValid && source.m_passes != null)
{
target.m_passes = source.m_passes;
}
}
private static void InstallCloneAndRecall()
{
if (IsHost() && HasLoadedCheckpoint())
{
SNet_Capture capture = GetCapture();
if (((capture != null) ? capture.m_buffers : null) != null && ((Il2CppArrayBase<SNet_CaptureBuffer>)(object)capture.m_buffers).Length > 3)
{
((Il2CppArrayBase<SNet_CaptureBuffer>)(object)capture.m_buffers)[3] = _clonedCheckpoint;
capture.RecallGameState((eBufferType)3);
}
}
}
private static void SaveCheckpointToDisk()
{
//IL_00e2: Unknown result type (might be due to invalid IL or missing references)
//IL_00ec: Expected I4, but got Unknown
//IL_00f1: Unknown result type (might be due to invalid IL or missing references)
//IL_00f6: Unknown result type (might be due to invalid IL or missing references)
//IL_00fa: Unknown result type (might be due to invalid IL or missing references)
//IL_0108: Unknown result type (might be due to invalid IL or missing references)
//IL_0116: Unknown result type (might be due to invalid IL or missing references)
//IL_0124: Unknown result type (might be due to invalid IL or missing references)
//IL_0132: Unknown result type (might be due to invalid IL or missing references)
if (!IsHost() || !HasLoadedCheckpoint())
{
return;
}
SeedRandom buildSeedRandom = Builder.BuildSeedRandom;
SeedRandom hostIDSeedRandom = Builder.HostIDSeedRandom;
SeedRandom sessionSeedRandom = Builder.SessionSeedRandom;
if (buildSeedRandom == null || hostIDSeedRandom == null || sessionSeedRandom == null)
{
throw new InvalidOperationException("GTFO generation seeds are unavailable.");
}
if (!TryGetCurrentLevelId(out var levelId))
{
throw new InvalidOperationException("Could not identify the current GTFO level.");
}
string directoryName = Path.GetDirectoryName(GetSelectedCheckpointSavePath());
if (!Directory.Exists(directoryName))
{
Directory.CreateDirectory(directoryName);
}
using FileStream output = new FileStream(GetSelectedCheckpointSavePath(), FileMode.Create, FileAccess.Write, FileShare.None);
using BinaryWriter binaryWriter = new BinaryWriter(output, Encoding.UTF8);
binaryWriter.Write("GTFOCP");
binaryWriter.Write(4);
binaryWriter.Write(levelId);
binaryWriter.Write(DateTime.Now.ToBinary());
binaryWriter.Write(buildSeedRandom.Seed);
binaryWriter.Write(hostIDSeedRandom.Seed);
binaryWriter.Write(sessionSeedRandom.Seed);
binaryWriter.Write((byte)(int)_clonedCheckpoint.type);
pBufferData data = _clonedCheckpoint.data;
binaryWriter.Write(data.sendingPlayerLookup);
binaryWriter.Write(data.levelChecksum);
binaryWriter.Write(data.bufferID);
binaryWriter.Write(data.progressionTime);
binaryWriter.Write(data.recallCount);
binaryWriter.Write(((Il2CppArrayBase<List<Il2CppStructArray<byte>>>)(object)_clonedCheckpoint.m_passes).Length);
foreach (List<Il2CppStructArray<byte>> item in (Il2CppArrayBase<List<Il2CppStructArray<byte>>>)(object)_clonedCheckpoint.m_passes)
{
if (item == null)
{
binaryWriter.Write(-1);
continue;
}
binaryWriter.Write(item.Count);
for (int i = 0; i < item.Count; i++)
{
Il2CppStructArray<byte> val = item[i];
if (val == null)
{
binaryWriter.Write(-1);
continue;
}
binaryWriter.Write(((Il2CppArrayBase<byte>)(object)val).Length);
for (int j = 0; j < ((Il2CppArrayBase<byte>)(object)val).Length; j++)
{
binaryWriter.Write(((Il2CppArrayBase<byte>)(object)val)[j]);
}
}
}
}
private static bool LoadCheckpointFromDisk(out SavedMetadata saved)
{
//IL_0179: Unknown result type (might be due to invalid IL or missing references)
//IL_017a: Unknown result type (might be due to invalid IL or missing references)
//IL_017b: Unknown result type (might be due to invalid IL or missing references)
//IL_0182: Expected O, but got Unknown
//IL_0186: Unknown result type (might be due to invalid IL or missing references)
//IL_01cd: Unknown result type (might be due to invalid IL or missing references)
//IL_01d6: Unknown result type (might be due to invalid IL or missing references)
saved = default(SavedMetadata);
_clonedCheckpoint = null;
if (!IsHost() || !File.Exists(GetSelectedCheckpointSavePath()))
{
return false;
}
using (FileStream input = new FileStream(GetSelectedCheckpointSavePath(), FileMode.Open, FileAccess.Read, FileShare.Read))
{
using BinaryReader binaryReader = new BinaryReader(input, Encoding.UTF8);
if (binaryReader.ReadString() != "GTFOCP")
{
throw new InvalidDataException("Invalid checkpoint file.");
}
int num = binaryReader.ReadInt32();
switch (num)
{
case 3:
case 4:
{
string text = binaryReader.ReadString();
if (!Regex.IsMatch(text ?? "", "^R\\d+[A-E]\\d+$"))
{
throw new InvalidDataException("Invalid saved GTFO level ID: '" + text + "'.");
}
saved.LevelId = text;
if (num == 4)
{
saved.SaveDateTime = DateTime.FromBinary(binaryReader.ReadInt64());
saved.HasSaveDateTime = true;
}
saved.HasSeeds = true;
binaryReader.ReadInt32();
saved.HostIDSeed = binaryReader.ReadInt32();
saved.SessionSeed = binaryReader.ReadInt32();
break;
}
case 2:
saved.HasSeeds = true;
binaryReader.ReadInt32();
saved.HostIDSeed = binaryReader.ReadInt32();
saved.SessionSeed = binaryReader.ReadInt32();
break;
case 1:
{
Plugin instance = Plugin.Instance;
if (instance != null)
{
((BasePlugin)instance).Log.LogInfo((object)"Loaded v1 checkpoint: generation seeds are unavailable; F8 is disabled for this save.");
}
break;
}
default:
throw new InvalidDataException($"Unsupported checkpoint file version: {num}.");
}
eBufferType val = (eBufferType)binaryReader.ReadByte();
SNet_CaptureBuffer val2 = new SNet_CaptureBuffer(val);
val2.data = new pBufferData
{
sendingPlayerLookup = binaryReader.ReadUInt64(),
levelChecksum = binaryReader.ReadUInt64(),
bufferID = binaryReader.ReadUInt16(),
progressionTime = binaryReader.ReadSingle(),
recallCount = binaryReader.ReadUInt64()
};
val2.type = val;
int num2 = binaryReader.ReadInt32();
if (num2 < 0 || num2 > 100)
{
throw new InvalidDataException("Invalid pass count.");
}
Il2CppReferenceArray<List<Il2CppStructArray<byte>>> val3 = new Il2CppReferenceArray<List<Il2CppStructArray<byte>>>((long)num2);
for (int i = 0; i < num2; i++)
{
int num3 = binaryReader.ReadInt32();
if (num3 < 0)
{
((Il2CppArrayBase<List<Il2CppStructArray<byte>>>)(object)val3)[i] = new List<Il2CppStructArray<byte>>();
continue;
}
if (num3 > 100000)
{
throw new InvalidDataException("Invalid chunk count.");
}
List<Il2CppStructArray<byte>> val4 = new List<Il2CppStructArray<byte>>();
for (int j = 0; j < num3; j++)
{
int num4 = binaryReader.ReadInt32();
if (num4 >= 0)
{
if (num4 > 104857600)
{
throw new InvalidDataException("Invalid chunk length.");
}
Il2CppStructArray<byte> val5 = new Il2CppStructArray<byte>((long)num4);
for (int k = 0; k < num4; k++)
{
((Il2CppArrayBase<byte>)(object)val5)[k] = binaryReader.ReadByte();
}
val4.Add(val5);
}
}
((Il2CppArrayBase<List<Il2CppStructArray<byte>>>)(object)val3)[i] = val4;
}
val2.m_passes = val3;
val2.isValid = true;
_clonedCheckpoint = val2;
}
return true;
}
private static Il2CppStructArray<byte> CopyByteArray(Il2CppStructArray<byte> source)
{
if (source == null)
{
return null;
}
Il2CppStructArray<byte> val = new Il2CppStructArray<byte>((long)((Il2CppArrayBase<byte>)(object)source).Length);
for (int i = 0; i < ((Il2CppArrayBase<byte>)(object)source).Length; i++)
{
((Il2CppArrayBase<byte>)(object)val)[i] = ((Il2CppArrayBase<byte>)(object)source)[i];
}
return val;
}
private static bool TryReadSavedMetadataFromPath(string path, out SavedMetadata saved)
{
//IL_0166: Unknown result type (might be due to invalid IL or missing references)
//IL_016d: Expected O, but got Unknown
saved = default(SavedMetadata);
try
{
if (!File.Exists(path))
{
return false;
}
using FileStream input = new FileStream(path, FileMode.Open, FileAccess.Read, FileShare.Read);
using BinaryReader binaryReader = new BinaryReader(input, Encoding.UTF8);
if (binaryReader.ReadString() != "GTFOCP")
{
throw new InvalidDataException("Invalid checkpoint file signature.");
}
int num = binaryReader.ReadInt32();
switch (num)
{
case 3:
case 4:
saved.LevelId = binaryReader.ReadString();
if (!Regex.IsMatch(saved.LevelId ?? "", "^R\\d+[A-E]\\d+$"))
{
throw new InvalidDataException("Invalid saved level ID.");
}
if (num == 4)
{
saved.SaveDateTime = DateTime.FromBinary(binaryReader.ReadInt64());
saved.HasSaveDateTime = true;
}
break;
default:
throw new InvalidDataException($"Unsupported checkpoint version: {num}.");
case 1:
case 2:
break;
}
if (num == 2 || num == 3 || num == 4)
{
binaryReader.ReadInt32();
saved.HostIDSeed = binaryReader.ReadInt32();
saved.SessionSeed = binaryReader.ReadInt32();
saved.HasSeeds = true;
}
binaryReader.ReadByte();
binaryReader.ReadUInt64();
binaryReader.ReadUInt64();
return true;
}
catch (Exception ex)
{
saved = default(SavedMetadata);
Plugin instance = Plugin.Instance;
if (instance != null)
{
ManualLogSource log = ((BasePlugin)instance).Log;
bool flag = default(bool);
BepInExWarningLogInterpolatedStringHandler val = new BepInExWarningLogInterpolatedStringHandler(33, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("Checkpoint metadata read failed: ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(ex.Message);
}
log.LogWarning(val);
}
return false;
}
}
private static bool HasLoadedCheckpoint()
{
if (_clonedCheckpoint != null && _clonedCheckpoint.isValid)
{
return _clonedCheckpoint.m_passes != null;
}
return false;
}
}
}