Decompiled source of Self Sufficient v3.3.0

Computery.SelfSufficient.dll

Decompiled 8 months ago
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Reflection;
using System.Reflection.Emit;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using BepInEx;
using BepInEx.Configuration;
using BepInEx.Logging;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using Photon.Pun;
using SelfSufficient.Utilities;
using Steamworks;
using UnityEngine;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: IgnoresAccessChecksTo("Assembly-CSharp")]
[assembly: IgnoresAccessChecksTo("Zorro.UI.Runtime")]
[assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")]
[assembly: AssemblyCompany("Computery")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyDescription("Run your own Photon instance.")]
[assembly: AssemblyFileVersion("3.3.0.0")]
[assembly: AssemblyInformationalVersion("3.3.0+60f84884aab4d79fc75e7c6888325a88b4bbf8df")]
[assembly: AssemblyProduct("Computery.SelfSufficient")]
[assembly: AssemblyTitle("Computery.SelfSufficient")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("3.3.0.0")]
[module: UnverifiableCode]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	internal sealed class EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	[AttributeUsage(AttributeTargets.Class | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Event | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, AllowMultiple = false, Inherited = false)]
	internal sealed class NullableAttribute : Attribute
	{
		public readonly byte[] NullableFlags;

		public NullableAttribute(byte P_0)
		{
			NullableFlags = new byte[1] { P_0 };
		}

		public NullableAttribute(byte[] P_0)
		{
			NullableFlags = P_0;
		}
	}
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	[AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Method | AttributeTargets.Interface | AttributeTargets.Delegate, AllowMultiple = false, Inherited = false)]
	internal sealed class NullableContextAttribute : Attribute
	{
		public readonly byte Flag;

		public NullableContextAttribute(byte P_0)
		{
			Flag = P_0;
		}
	}
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.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 SelfSufficient
{
	[ContentWarningPlugin("Computery.SelfSufficient", "3.3.0", true)]
	[BepInPlugin("Computery.SelfSufficient", "Computery.SelfSufficient", "3.3.0")]
	public class SelfSufficient : BaseUnityPlugin
	{
		internal static ManualLogSource? SelfSufficientLogger;

		internal static ConfigFile? SelfSufficientConfigFile;

		private void Awake()
		{
			SelfSufficientLogger = ((BaseUnityPlugin)this).Logger;
			SelfSufficientLogger.LogInfo((object)"Plugin Computery.SelfSufficient is loaded!");
			SelfSufficientConfigFile = ((BaseUnityPlugin)this).Config;
			SelfSufficientConfigFile.Bind<string>("Settings", "AppID for PUN", "", "The PUN AppID (Only needed for the host)");
			SelfSufficientConfigFile.Bind<string>("Settings", "AppID for VOICE", "", "The VOICE AppID (Defaults to the PUN AppID)");
			SelfSufficientLogger.LogInfo((object)"Config file is loaded!");
			PhotonCallbackUtility.CreateInstace();
			SelfSufficientLogger.LogInfo((object)"Created PhotonCallbackUtility instance");
			Harmony.CreateAndPatchAll(Assembly.GetExecutingAssembly(), (string)null);
			SelfSufficientLogger.LogInfo((object)"Patched all Harmony patches");
			SelfSufficientLogger.LogInfo((object)(PhotonAppIDUtilities.HasPersonalyOverriddenAppIDs ? "Using custom Photon AppIds for hosting." : "Using default Photon AppIds for hosting"));
		}
	}
	public static class PluginInfo
	{
		public const string PLUGIN_GUID = "Computery.SelfSufficient";

		public const string PLUGIN_NAME = "Computery.SelfSufficient";

		public const string PLUGIN_VERSION = "3.3.0";
	}
}
namespace SelfSufficient.Utilities
{
	internal static class PhotonAppIDUtilities
	{
		internal static readonly string PUN_APP_ID_KEY = "PUN_APP_ID";

		internal static readonly string VOICE_APP_ID_KEY = "VOICE_APP_ID";

		internal static bool HasPersonalyOverriddenAppIDs
		{
			get
			{
				if (string.IsNullOrWhiteSpace(OverridePunAppID))
				{
					return !string.IsNullOrWhiteSpace(OverrideVoiceAppID);
				}
				return true;
			}
		}

		internal static string? OverridePunAppID => SelfSufficient.SelfSufficientConfigFile.Bind<string>("Settings", "AppID for PUN", "", "The PUN AppID (Only needed for the host)").Value;

		internal static string? OverrideVoiceAppID
		{
			get
			{
				string value = SelfSufficient.SelfSufficientConfigFile.Bind<string>("Settings", "AppID for VOICE", "", "The VOICE AppID (Defaults to the PUN AppID)").Value;
				if (!string.IsNullOrWhiteSpace(value))
				{
					return value;
				}
				return OverridePunAppID;
			}
		}

		internal static bool IsUsingDefaultAppIDs
		{
			get
			{
				if (CurrentPunAppID == DefaultPunAppID)
				{
					return CurrentVoiceAppID == DefaultVoiceAppID;
				}
				return false;
			}
		}

		internal static string DefaultPunAppID { get; private set; } = PhotonNetwork.PhotonServerSettings.AppSettings.AppIdRealtime;


		internal static string DefaultVoiceAppID { get; private set; } = PhotonNetwork.PhotonServerSettings.AppSettings.AppIdVoice;


		internal static string CurrentPunAppID
		{
			get
			{
				return PhotonNetwork.PhotonServerSettings.AppSettings.AppIdRealtime;
			}
			private set
			{
				PhotonNetwork.PhotonServerSettings.AppSettings.AppIdRealtime = value;
			}
		}

		internal static string CurrentVoiceAppID
		{
			get
			{
				return PhotonNetwork.PhotonServerSettings.AppSettings.AppIdVoice;
			}
			private set
			{
				PhotonNetwork.PhotonServerSettings.AppSettings.AppIdVoice = value;
			}
		}

		internal static bool CanUpdateAppID(string? PunAppID, string? VoiceAppID)
		{
			if (string.IsNullOrWhiteSpace(PunAppID) || (PunAppID == CurrentPunAppID && VoiceAppID == CurrentVoiceAppID))
			{
				SelfSufficient.SelfSufficientLogger.LogInfo((object)"AppIDs are already set to the provided values or are empty");
				return false;
			}
			SelfSufficient.SelfSufficientLogger.LogInfo((object)"Can update AppIDs");
			return true;
		}

		internal static void UpdateAppIDs(string PunAppID, string VoiceAppID, bool forceReconnect)
		{
			SelfSufficient.SelfSufficientLogger.LogInfo((object)"Updating AppIDs");
			CurrentPunAppID = PunAppID;
			CurrentVoiceAppID = (string.IsNullOrWhiteSpace(VoiceAppID) ? PunAppID : VoiceAppID);
			if (forceReconnect)
			{
				SelfSufficient.SelfSufficientLogger.LogInfo((object)"Forcing a reconnect");
				PhotonNetwork.Disconnect();
				if (!IsUsingDefaultAppIDs)
				{
					PhotonNetwork.AuthValues = null;
				}
				PhotonNetwork.ConnectUsingSettings();
			}
		}
	}
	internal class PhotonCallbackUtility : MonoBehaviourPunCallbacks
	{
		private static PhotonCallbackUtility? m_Instance;

		public static bool TryingToConnectToMasterServer { get; private set; }

		public static event Action? OnMasterServerConnected;

		public static void CreateInstace()
		{
			//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_001d: Expected O, but got Unknown
			if ((Object)(object)m_Instance == (Object)null)
			{
				GameObject val = new GameObject("PhotonCallbackUtility");
				Object.DontDestroyOnLoad((Object)val);
				m_Instance = val.AddComponent<PhotonCallbackUtility>();
			}
		}

		public override void OnConnectedToMaster()
		{
			PhotonCallbackUtility.OnMasterServerConnected?.Invoke();
		}

		public static void RejoinLobbyOnMasterServerConnected(SteamLobbyHandler steamLobbyHandler, CSteamID lobbyID)
		{
			//IL_000e: Unknown result type (might be due to invalid IL or missing references)
			//IL_000f: Unknown result type (might be due to invalid IL or missing references)
			SteamLobbyHandler steamLobbyHandler2 = steamLobbyHandler;
			if (!TryingToConnectToMasterServer)
			{
				OnMasterServerConnected += rejoinAction;
				TryingToConnectToMasterServer = true;
				SelfSufficient.SelfSufficientLogger.LogInfo((object)"Waiting for master server connection to rejoin lobby");
			}
			void rejoinAction()
			{
				//IL_0007: Unknown result type (might be due to invalid IL or missing references)
				HandleRejoinOnMasterServerConnected(steamLobbyHandler2, lobbyID, rejoinAction);
			}
		}

		public static void HandleRejoinOnMasterServerConnected(SteamLobbyHandler steamLobbyHandler, CSteamID lobbyID, Action rejoinAction)
		{
			//IL_000a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0027: Unknown result type (might be due to invalid IL or missing references)
			SelfSufficient.SelfSufficientLogger.LogInfo((object)$"Starting lobby rejoin {lobbyID} after AppID update");
			OnMasterServerConnected -= rejoinAction;
			TryingToConnectToMasterServer = false;
			steamLobbyHandler.JoinLobby(lobbyID);
			SelfSufficient.SelfSufficientLogger.LogInfo((object)"Rejoined lobby");
		}

		public static void RehostOnMasterServerConnected(MainMenuHandler mainMenuHandler, int saveIndex)
		{
			MainMenuHandler mainMenuHandler2 = mainMenuHandler;
			if (!TryingToConnectToMasterServer)
			{
				OnMasterServerConnected += rehostAction;
				TryingToConnectToMasterServer = true;
				SelfSufficient.SelfSufficientLogger.LogInfo((object)"Waiting for master server connection to rejoin lobby");
			}
			void rehostAction()
			{
				HandleOnMasterServerConnected(mainMenuHandler2, saveIndex, rehostAction);
			}
		}

		public static void HandleOnMasterServerConnected(MainMenuHandler mainMenuHandler, int saveIndex, Action rehostAction)
		{
			SelfSufficient.SelfSufficientLogger.LogInfo((object)$"Rehosting save {saveIndex} after AppID update");
			OnMasterServerConnected -= rehostAction;
			TryingToConnectToMasterServer = false;
			mainMenuHandler.Host(saveIndex);
			SelfSufficient.SelfSufficientLogger.LogInfo((object)"Rehosted save");
		}
	}
}
namespace SelfSufficient.Patches
{
	[HarmonyPatch(typeof(Connection))]
	[HarmonyPatch("CheckForErrors")]
	public static class ConnectionPatches
	{
		internal static void UpdateAuthType()
		{
			if (!PhotonAppIDUtilities.IsUsingDefaultAppIDs)
			{
				PhotonNetwork.AuthValues = null;
			}
		}

		[HarmonyTranspiler]
		[HarmonyPatch("Start")]
		private static IEnumerable<CodeInstruction> ConnectionStartPatch(IEnumerable<CodeInstruction> instructions)
		{
			//IL_0011: Unknown result type (might be due to invalid IL or missing references)
			//IL_006d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0073: Expected O, but got Unknown
			SelfSufficient.SelfSufficientLogger.LogInfo((object)"Transpiler running, should be no more auth values on custom AppId.");
			return new CodeMatcher(instructions, (ILGenerator)null).SearchForward((Func<CodeInstruction, bool>)((CodeInstruction i) => i.opcode == OpCodes.Call && CodeInstructionExtensions.OperandIs(i, (MemberInfo)AccessTools.Method(typeof(PhotonNetwork), "ConnectToRegion", (Type[])null, (Type[])null)))).Advance(-1).ThrowIfInvalid("ConnectionStartPatch did not work!")
				.Insert((CodeInstruction[])(object)new CodeInstruction[1]
				{
					new CodeInstruction(OpCodes.Call, (object)AccessTools.Method(typeof(ConnectionPatches), "UpdateAuthType", (Type[])null, (Type[])null))
				})
				.InstructionEnumeration();
		}
	}
	[HarmonyPatch(typeof(MainMenuHandler))]
	[HarmonyPriority(801)]
	internal static class MainMenuHandlerPatches
	{
		[HarmonyPrefix]
		[HarmonyPatch("ConnectToPhoton")]
		private static void ConnectToPhotonPatch()
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_001b: Unknown result type (might be due to invalid IL or missing references)
			if (SteamUtils.GetAppID().m_AppId != 2881650)
			{
				SelfSufficient.SelfSufficientLogger.LogWarning((object)$"Using wong steam AppID {SteamUtils.GetAppID().m_AppId}?");
				Application.Quit();
			}
			if (!PhotonAppIDUtilities.IsUsingDefaultAppIDs)
			{
				SelfSufficient.SelfSufficientLogger.LogInfo((object)"Updating AppIDs back to default values");
				PhotonAppIDUtilities.UpdateAppIDs(PhotonAppIDUtilities.DefaultPunAppID, PhotonAppIDUtilities.DefaultVoiceAppID, forceReconnect: false);
				PhotonNetwork.Disconnect();
			}
		}

		[HarmonyPrefix]
		[HarmonyPatch("Host")]
		private static bool HostPatch(ref MainMenuHandler __instance, int saveIndex)
		{
			if (PhotonCallbackUtility.TryingToConnectToMasterServer)
			{
				return false;
			}
			if (PhotonAppIDUtilities.HasPersonalyOverriddenAppIDs && PhotonAppIDUtilities.CanUpdateAppID(PhotonAppIDUtilities.OverridePunAppID, PhotonAppIDUtilities.OverrideVoiceAppID))
			{
				SelfSufficient.SelfSufficientLogger.LogInfo((object)"Updating AppIDs to personal values");
				PhotonAppIDUtilities.UpdateAppIDs(PhotonAppIDUtilities.OverridePunAppID, PhotonAppIDUtilities.OverrideVoiceAppID, forceReconnect: true);
				PhotonCallbackUtility.RehostOnMasterServerConnected(__instance, saveIndex);
				return false;
			}
			return true;
		}
	}
	[HarmonyPatch(typeof(SteamLobbyHandler))]
	[HarmonyPriority(801)]
	internal static class SteamLobbyHandlerPatches
	{
		[HarmonyPrefix]
		[HarmonyPatch("JoinLobby")]
		private static bool JoinLobbyPatch(ref SteamLobbyHandler __instance, CSteamID lobbyID)
		{
			//IL_0009: Unknown result type (might be due to invalid IL or missing references)
			//IL_0015: Unknown result type (might be due to invalid IL or missing references)
			//IL_0083: Unknown result type (might be due to invalid IL or missing references)
			//IL_0057: Unknown result type (might be due to invalid IL or missing references)
			//IL_0067: Unknown result type (might be due to invalid IL or missing references)
			//IL_0043: Unknown result type (might be due to invalid IL or missing references)
			if (PhotonCallbackUtility.TryingToConnectToMasterServer)
			{
				return false;
			}
			string lobbyData = SteamMatchmaking.GetLobbyData(lobbyID, PhotonAppIDUtilities.PUN_APP_ID_KEY);
			string lobbyData2 = SteamMatchmaking.GetLobbyData(lobbyID, PhotonAppIDUtilities.VOICE_APP_ID_KEY);
			if (PhotonAppIDUtilities.CanUpdateAppID(lobbyData, lobbyData2))
			{
				PhotonAppIDUtilities.UpdateAppIDs(lobbyData, lobbyData2, forceReconnect: true);
				if (PhotonNetwork.IsConnectedAndReady)
				{
					SelfSufficient.SelfSufficientLogger.LogInfo((object)$"Already connected to the master server, joining lobby {lobbyID}");
					return true;
				}
				PhotonCallbackUtility.RejoinLobbyOnMasterServerConnected(__instance, lobbyID);
				SelfSufficient.SelfSufficientLogger.LogInfo((object)$"Rejoining lobby {lobbyID} after AppID update");
				return false;
			}
			SelfSufficient.SelfSufficientLogger.LogInfo((object)$"AppIDs are already set, joining lobby {lobbyID}");
			return true;
		}

		[HarmonyPostfix]
		[HarmonyPatch("OnLobbyCreatedCallback")]
		private static void OnLobbyCreatedCallbackPatch(ref SteamLobbyHandler __instance)
		{
			//IL_0009: Unknown result type (might be due to invalid IL or missing references)
			//IL_000e: Unknown result type (might be due to invalid IL or missing references)
			if (PhotonAppIDUtilities.HasPersonalyOverriddenAppIDs)
			{
				CSteamID currentLobby = __instance.m_CurrentLobby;
				SteamMatchmaking.SetLobbyData(currentLobby, PhotonAppIDUtilities.PUN_APP_ID_KEY, PhotonAppIDUtilities.OverridePunAppID);
				SteamMatchmaking.SetLobbyData(currentLobby, PhotonAppIDUtilities.VOICE_APP_ID_KEY, PhotonAppIDUtilities.OverrideVoiceAppID);
				SelfSufficient.SelfSufficientLogger.LogInfo((object)"Set steam lobby AppIDs");
			}
		}
	}
}
namespace System.Runtime.CompilerServices
{
	[AttributeUsage(AttributeTargets.Assembly, AllowMultiple = true)]
	internal sealed class IgnoresAccessChecksToAttribute : Attribute
	{
		public IgnoresAccessChecksToAttribute(string assemblyName)
		{
		}
	}
}