Decompiled source of balrond core optimizer v0.1.0

plugins/BalrondCoreOptimizer.dll

Decompiled 3 hours ago
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using System.Threading;
using BalrondVisualOptimizer.Compatibility;
using BalrondVisualOptimizer.Config;
using BalrondVisualOptimizer.Core;
using BalrondVisualOptimizer.Patches.ArmorStandOptimizations;
using BalrondVisualOptimizer.Patches.CookingStationOptimizations;
using BalrondVisualOptimizer.Patches.CraftingStationOptimizations;
using BalrondVisualOptimizer.Patches.EffectFadeOptimizations;
using BalrondVisualOptimizer.Patches.FireplaceOptimizations;
using BalrondVisualOptimizer.Patches.ItemStandOptimizations;
using BalrondVisualOptimizer.Patches.LightFlickerOptimizations;
using BalrondVisualOptimizer.Patches.LightLodOptimizations;
using BalrondVisualOptimizer.Patches.LineConnectOptimizations;
using BalrondVisualOptimizer.Patches.MaterialFaderOptimizations;
using BalrondVisualOptimizer.Patches.PieceOptimizations;
using BalrondVisualOptimizer.Patches.PrivateAreaOptimizations;
using BalrondVisualOptimizer.Patches.SmelterOptimizations;
using BalrondVisualOptimizer.Patches.SmokeRendererOptimizations;
using BalrondVisualOptimizer.Patches.StationExtensionOptimizations;
using BalrondVisualOptimizer.Patches.TeleportWorldOptimizations;
using BalrondVisualOptimizer.Patches.VagonOptimizations;
using BalrondVisualOptimizer.Patches.VisEquipmentOptimizations;
using BalrondVisualOptimizer.Patches.WindmillOptimizations;
using BalrondVisualOptimizer.Patches.ZSFXOptimizations;
using BalrondVisualOptimizer.Services;
using BepInEx;
using BepInEx.Bootstrap;
using BepInEx.Configuration;
using HarmonyLib;
using UnityEngine;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)]
[assembly: AssemblyTitle("BalrondVisualOptimizer")]
[assembly: AssemblyDescription("Publicized event/cache/dormancy presentation optimizer for Valheim")]
[assembly: AssemblyCompany("Balrond")]
[assembly: AssemblyProduct("BalrondVisualOptimizer")]
[assembly: ComVisible(false)]
[assembly: Guid("14f622c7-d1e8-44ec-b28b-86f0d5543b4b")]
[assembly: AssemblyFileVersion("0.1.4.0")]
[assembly: TargetFramework(".NETFramework,Version=v4.8", FrameworkDisplayName = ".NET Framework 4.8")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("0.1.4.0")]
[module: UnverifiableCode]
namespace BalrondVisualOptimizer
{
	[BepInPlugin("balrond.astafaraios.BalrondCoreOptimizer", "BalrondCoreOptimizer", "0.1.0")]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	public sealed class Launch : BaseUnityPlugin
	{
		public const string PluginGuid = "balrond.astafaraios.BalrondCoreOptimizer";

		public const string PluginName = "BalrondCoreOptimizer";

		public const string PluginVersion = "0.1.0";

		internal static Launch Instance;

		internal static OptimizerConfig Settings;

		private Harmony harmony;

		private PatchInstaller patchInstaller;

		private float nextCompatibilityCheck;

		private float nextStatsLog;

		private bool refreshRequested;

		private bool lastDiagnostics;

		private void Awake()
		{
			//IL_0141: Unknown result type (might be due to invalid IL or missing references)
			//IL_014b: Expected O, but got Unknown
			Instance = this;
			try
			{
				Settings = new OptimizerConfig(((BaseUnityPlugin)this).Config);
				RuntimeTuning.Refresh(Settings);
				RuntimeStats.Enabled = Settings.Diagnostics.Value;
				RuntimeStats.ResetBaseline();
				lastDiagnostics = RuntimeStats.Enabled;
				((BaseUnityPlugin)this).Config.SettingChanged += OnSettingChanged;
				((BaseUnityPlugin)this).Logger.LogInfo((object)"BalrondCoreOptimizer 0.1.0 starting (publicized fast-path build).");
				((BaseUnityPlugin)this).Logger.LogInfo((object)("assembly_valheim MVID: " + GameAssemblyGuard.CurrentValheimMvid.ToString() + " (audited: " + GameAssemblyGuard.ExpectedValheimMvid.ToString() + ")."));
				if (Application.isBatchMode)
				{
					((BaseUnityPlugin)this).Logger.LogInfo((object)"Dedicated/batch mode detected. Client presentation patches are not installed.");
					return;
				}
				((BaseUnityPlugin)this).Logger.LogInfo((object)("Compatibility: BetterBuild=" + ModCompatibility.BetterBuildInstalled + ", FiresGhettoNetworking=" + ModCompatibility.FiresGhettoNetworkingInstalled + "."));
				harmony = new Harmony("balrond.astafaraios.BalrondCoreOptimizer");
				patchInstaller = new PatchInstaller(harmony, Settings);
				VanillaCollectionRegistry.Initialize();
				ArmorStandPatches.Install(patchInstaller);
				ItemStandPatches.Install(patchInstaller);
				PrivateAreaPatches.Install(patchInstaller);
				TeleportWorldPatches.Install(patchInstaller);
				VisEquipmentPatches.Install(patchInstaller);
				SmelterPatches.Install(patchInstaller);
				FireplacePatches.Install(patchInstaller);
				CookingStationPatches.Install(patchInstaller);
				CraftingStationDormancyPatches.Install(patchInstaller);
				LightFlickerPatches.Install(patchInstaller);
				LightLodPatches.Install(patchInstaller);
				SmokeRendererPatches.Install(patchInstaller);
				WindmillPatches.Install(patchInstaller);
				VagonPatches.Install(patchInstaller);
				EffectFadePatches.Install(patchInstaller);
				MaterialFaderPatches.Install(patchInstaller);
				ZSFXPatches.Install(patchInstaller);
				LineConnectPatches.Install(patchInstaller);
				PiecePatches.Install(patchInstaller);
				CraftingStationPatches.Install(patchInstaller);
				StationExtensionPatches.Install(patchInstaller);
				RefreshSubsystemOwnership();
				nextCompatibilityCheck = Time.unscaledTime + Settings.CompatibilityRecheckSeconds.Value;
				nextStatsLog = Time.unscaledTime + Settings.DiagnosticsIntervalSeconds.Value;
				((BaseUnityPlugin)this).Logger.LogInfo((object)("[patches] " + patchInstaller.BuildStatusSummary()));
				((BaseUnityPlugin)this).Logger.LogInfo((object)"BalrondCoreOptimizer initialization complete.");
			}
			catch (Exception ex)
			{
				((BaseUnityPlugin)this).Logger.LogError((object)("Fatal initialization error. Rolling back BVO and restoring vanilla dispatch: " + ex));
				ShutdownSubsystems();
				try
				{
					if (harmony != null)
					{
						harmony.UnpatchSelf();
					}
				}
				catch (Exception ex2)
				{
					((BaseUnityPlugin)this).Logger.LogWarning((object)("Rollback failed: " + ex2.Message));
				}
				patchInstaller = null;
			}
		}

		private void OnSettingChanged(object sender, SettingChangedEventArgs args)
		{
			refreshRequested = true;
		}

		private void Update()
		{
			if (Settings != null)
			{
				float unscaledTime = Time.unscaledTime;
				if (patchInstaller != null && (refreshRequested || unscaledTime >= nextCompatibilityCheck))
				{
					refreshRequested = false;
					RuntimeTuning.Refresh(Settings);
					patchInstaller.RefreshAll();
					RefreshSubsystemOwnership();
					nextCompatibilityCheck = unscaledTime + Mathf.Max(2f, Settings.CompatibilityRecheckSeconds.Value);
				}
				LightLodScheduler.Tick(Time.deltaTime);
				ZSFXPatches.Tick(unscaledTime);
				bool value = Settings.Diagnostics.Value;
				if (value != lastDiagnostics)
				{
					lastDiagnostics = value;
					RuntimeStats.Enabled = value;
					RuntimeStats.ResetBaseline();
					nextStatsLog = unscaledTime + Mathf.Max(10f, Settings.DiagnosticsIntervalSeconds.Value);
				}
				if (value && unscaledTime >= nextStatsLog)
				{
					float num = Mathf.Max(10f, Settings.DiagnosticsIntervalSeconds.Value);
					nextStatsLog = unscaledTime + num;
					((BaseUnityPlugin)this).Logger.LogInfo((object)("[stats] " + RuntimeStats.BuildDeltaSummary(num)));
				}
			}
		}

		private static void RefreshSubsystemOwnership()
		{
			CraftingStationDormancyPatches.RefreshDormancy();
			EffectFadePatches.RefreshDormancy();
			MaterialFaderPatches.RefreshDormancy();
			ZSFXPatches.RefreshDormancy();
			LightLodPatches.RefreshScheduler();
		}

		private static void ShutdownSubsystems()
		{
			try
			{
				LightLodScheduler.RestoreVanilla();
			}
			catch
			{
			}
			try
			{
				CraftingStationDormancyPatches.Shutdown();
			}
			catch
			{
			}
			try
			{
				EffectFadePatches.Shutdown();
			}
			catch
			{
			}
			try
			{
				MaterialFaderPatches.Shutdown();
			}
			catch
			{
			}
			try
			{
				ZSFXPatches.Shutdown();
			}
			catch
			{
			}
		}

		private void OnDestroy()
		{
			if (((BaseUnityPlugin)this).Config != null)
			{
				((BaseUnityPlugin)this).Config.SettingChanged -= OnSettingChanged;
			}
			ShutdownSubsystems();
			try
			{
				if (harmony != null)
				{
					harmony.UnpatchSelf();
				}
			}
			catch (Exception ex)
			{
				((BaseUnityPlugin)this).Logger.LogWarning((object)("Failed to unpatch cleanly: " + ex.Message));
			}
			Instance = null;
		}

		internal static void LogInfo(object message)
		{
			if ((Object)(object)Instance != (Object)null)
			{
				((BaseUnityPlugin)Instance).Logger.LogInfo(message);
			}
		}

		internal static void LogWarning(object message)
		{
			if ((Object)(object)Instance != (Object)null)
			{
				((BaseUnityPlugin)Instance).Logger.LogWarning(message);
			}
		}

		internal static void LogError(object message)
		{
			if ((Object)(object)Instance != (Object)null)
			{
				((BaseUnityPlugin)Instance).Logger.LogError(message);
			}
		}
	}
}
namespace BalrondVisualOptimizer.Services
{
	internal static class LightLodScheduler
	{
		private sealed class Entry
		{
			internal LightLod Lod;

			internal int Index;

			internal bool TargetLight;

			internal bool TargetShadow;

			internal bool Fading;
		}

		private static readonly List<Entry> Entries = new List<Entry>();

		private static readonly Dictionary<int, Entry> Map = new Dictionary<int, Entry>();

		private static readonly List<Entry> Fading = new List<Entry>();

		private static int cursor;

		private static bool enabled;

		internal static void SetEnabled(bool value)
		{
			if (enabled != value)
			{
				enabled = value;
				if (enabled)
				{
					TakeOwnershipOfExisting();
				}
				else
				{
					RestoreVanilla();
				}
			}
		}

		internal static void Register(LightLod lod)
		{
			//IL_0076: Unknown result type (might be due to invalid IL or missing references)
			if (!enabled || (Object)(object)lod == (Object)null)
			{
				return;
			}
			int instanceID = ((Object)lod).GetInstanceID();
			if (!Map.ContainsKey(instanceID))
			{
				Entry entry = new Entry
				{
					Lod = lod,
					Index = Entries.Count
				};
				Entries.Add(entry);
				Map[instanceID] = entry;
				if (TryGetReferencePoint(out var point))
				{
					Evaluate(entry, point);
				}
			}
		}

		internal static void Unregister(LightLod lod)
		{
			if (!((Object)(object)lod == (Object)null) && Map.TryGetValue(((Object)lod).GetInstanceID(), out var value))
			{
				RemoveEntry(value);
			}
		}

		internal static void Tick(float dt)
		{
			//IL_011a: Unknown result type (might be due to invalid IL or missing references)
			if (!enabled || Entries.Count == 0)
			{
				return;
			}
			if (TryGetReferencePoint(out var point))
			{
				float num = Mathf.Max(0.25f, RuntimeTuning.LightLodDecisionInterval);
				int num2 = Mathf.Max(1, Mathf.CeilToInt((float)Entries.Count * Mathf.Min(0.25f, Mathf.Max(0f, dt)) / num));
				int num3 = Mathf.Min(Entries.Count, Mathf.Min(RuntimeTuning.LightLodChecksPerFrame, num2));
				for (int i = 0; i < num3; i++)
				{
					if (Entries.Count <= 0)
					{
						break;
					}
					if (cursor >= Entries.Count)
					{
						cursor = 0;
					}
					Entry entry = Entries[cursor++];
					if ((Object)(object)entry.Lod == (Object)null || !((Behaviour)entry.Lod).enabled || !((Component)entry.Lod).gameObject.activeInHierarchy)
					{
						RemoveEntry(entry);
						continue;
					}
					Evaluate(entry, point);
					RuntimeStats.Inc(ref RuntimeStats.LightLodDecisionChecks);
				}
			}
			for (int num4 = Fading.Count - 1; num4 >= 0; num4--)
			{
				Entry entry2 = Fading[num4];
				if (!entry2.Fading)
				{
					Fading.RemoveAt(num4);
				}
				else if ((Object)(object)entry2.Lod == (Object)null || !((Behaviour)entry2.Lod).enabled || !((Component)entry2.Lod).gameObject.activeInHierarchy)
				{
					entry2.Fading = false;
					Fading.RemoveAt(num4);
				}
				else if (AdvanceFade(entry2, dt))
				{
					entry2.Fading = false;
					Fading.RemoveAt(num4);
				}
			}
		}

		internal static void RestoreVanilla()
		{
			for (int i = 0; i < Entries.Count; i++)
			{
				LightLod lod = Entries[i].Lod;
				if ((Object)(object)lod != (Object)null && ((Behaviour)lod).enabled && ((Component)lod).gameObject.activeInHierarchy)
				{
					((MonoBehaviour)lod).StopCoroutine("UpdateLoop");
					((MonoBehaviour)lod).StartCoroutine("UpdateLoop");
				}
			}
			Entries.Clear();
			Map.Clear();
			Fading.Clear();
			cursor = 0;
		}

		private static void TakeOwnershipOfExisting()
		{
			foreach (LightLod light in LightLod.m_lights)
			{
				if (!((Object)(object)light == (Object)null) && ((Behaviour)light).enabled && ((Component)light).gameObject.activeInHierarchy)
				{
					((MonoBehaviour)light).StopCoroutine("UpdateLoop");
					Register(light);
				}
			}
		}

		private static bool TryGetReferencePoint(out Vector3 point)
		{
			//IL_0014: Unknown result type (might be due to invalid IL or missing references)
			//IL_0019: Unknown result type (might be due to invalid IL or missing references)
			//IL_004e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0053: Unknown result type (might be due to invalid IL or missing references)
			//IL_0041: Unknown result type (might be due to invalid IL or missing references)
			Camera mainCamera = Utils.GetMainCamera();
			if ((Object)(object)mainCamera == (Object)null)
			{
				point = Vector3.zero;
				return false;
			}
			point = ((GameCamera.InFreeFly() || (Object)(object)Player.m_localPlayer == (Object)null) ? ((Component)mainCamera).transform.position : ((Component)Player.m_localPlayer).transform.position);
			return true;
		}

		private static void Evaluate(Entry e, Vector3 reference)
		{
			//IL_0031: Unknown result type (might be due to invalid IL or missing references)
			//IL_0036: Unknown result type (might be due to invalid IL or missing references)
			//IL_0037: Unknown result type (might be due to invalid IL or missing references)
			//IL_003c: Unknown result type (might be due to invalid IL or missing references)
			LightLod lod = e.Lod;
			if (!((Object)(object)lod == (Object)null) && !((Object)(object)lod.m_light == (Object)null))
			{
				Vector3 val = ((Component)lod).transform.position - reference;
				float sqrMagnitude = ((Vector3)(ref val)).sqrMagnitude;
				bool flag = !lod.m_lightLod || (sqrMagnitude < lod.m_lightDistance * lod.m_lightDistance && (lod.m_lightPrio < LightLod.m_lightLimit || LightLod.m_lightLimit < 0));
				bool flag2 = !lod.m_shadowLod || (sqrMagnitude < lod.m_shadowDistance * lod.m_shadowDistance && (lod.m_lightPrio < LightLod.m_shadowLimit || LightLod.m_shadowLimit < 0));
				bool flag3 = e.TargetLight != flag || e.TargetShadow != flag2;
				e.TargetLight = flag;
				e.TargetShadow = flag2;
				if (flag3 || !IsSettled(e))
				{
					AddFading(e);
				}
			}
		}

		private static bool AdvanceFade(Entry e, float dt)
		{
			LightLod lod = e.Lod;
			Light light = lod.m_light;
			if ((Object)(object)light == (Object)null)
			{
				return true;
			}
			if (lod.m_lightLod)
			{
				if (e.TargetLight)
				{
					((Behaviour)light).enabled = true;
					light.range = Mathf.Min(lod.m_baseRange, light.range + dt * lod.m_baseRange);
				}
				else
				{
					light.range = Mathf.Max(0f, light.range - dt * lod.m_baseRange);
					if (light.range <= 0f)
					{
						((Behaviour)light).enabled = false;
					}
				}
			}
			if (lod.m_shadowLod)
			{
				if (e.TargetShadow)
				{
					light.shadows = (LightShadows)2;
					light.shadowStrength = Mathf.Min(lod.m_baseShadowStrength, light.shadowStrength + dt * lod.m_baseShadowStrength);
				}
				else
				{
					light.shadowStrength = Mathf.Max(0f, light.shadowStrength - dt * lod.m_baseShadowStrength);
					if (light.shadowStrength <= 0f)
					{
						light.shadows = (LightShadows)0;
					}
				}
			}
			return IsSettled(e);
		}

		private static bool IsSettled(Entry e)
		{
			//IL_00b4: Unknown result type (might be due to invalid IL or missing references)
			//IL_0097: Unknown result type (might be due to invalid IL or missing references)
			LightLod lod = e.Lod;
			Light val = (((Object)(object)lod == (Object)null) ? null : lod.m_light);
			if ((Object)(object)val == (Object)null)
			{
				return true;
			}
			bool flag = true;
			if (lod.m_lightLod)
			{
				flag = ((!e.TargetLight) ? (!((Behaviour)val).enabled && val.range <= 0f) : (((Behaviour)val).enabled && val.range >= lod.m_baseRange));
			}
			bool flag2 = true;
			if (lod.m_shadowLod)
			{
				flag2 = ((!e.TargetShadow) ? ((int)val.shadows == 0 && val.shadowStrength <= 0f) : ((int)val.shadows != 0 && val.shadowStrength >= lod.m_baseShadowStrength));
			}
			return flag && flag2;
		}

		private static void AddFading(Entry e)
		{
			if (!e.Fading)
			{
				e.Fading = true;
				Fading.Add(e);
			}
		}

		private static void RemoveEntry(Entry e)
		{
			if (e != null && e.Index >= 0 && e.Index < Entries.Count)
			{
				int num = ((!((Object)(object)e.Lod == (Object)null)) ? ((Object)e.Lod).GetInstanceID() : 0);
				int index = Entries.Count - 1;
				Entry entry = Entries[index];
				Entries[e.Index] = entry;
				entry.Index = e.Index;
				Entries.RemoveAt(index);
				if (num != 0)
				{
					Map.Remove(num);
				}
				e.Index = -1;
				e.Fading = false;
				if (cursor > Entries.Count)
				{
					cursor = Entries.Count;
				}
			}
		}
	}
	internal static class RuntimeTuning
	{
		internal static float VisualSafety;

		internal static float StaticVisualSafety;

		internal static float ArmorClothInterval;

		internal static float LightNearSqr;

		internal static float LightMidSqr;

		internal static float LightFarSqr;

		internal static float LightMidInterval;

		internal static float LightFarInterval;

		internal static float LightDistantInterval;

		internal static float LightDistanceCheckInterval;

		internal static float LightLodDecisionInterval;

		internal static int LightLodChecksPerFrame;

		internal static float SmokeRendererInterval;

		internal static float WindmillAudioInterval;

		internal static float VagonAudioInterval;

		internal static void Refresh(OptimizerConfig c)
		{
			VisualSafety = Mathf.Max(5f, c.VisualSafetyRefreshSeconds.Value);
			StaticVisualSafety = Mathf.Max(10f, c.StaticVisualSafetyRefreshSeconds.Value);
			ArmorClothInterval = UpdateRateLimiter.IntervalFromRate(c.ArmorStandClothRate.Value);
			float num = Mathf.Max(0f, c.LightFlickerNearDistance.Value);
			float num2 = Mathf.Max(num, c.LightFlickerMidDistance.Value);
			float num3 = Mathf.Max(num2, c.LightFlickerFarDistance.Value);
			LightNearSqr = num * num;
			LightMidSqr = num2 * num2;
			LightFarSqr = num3 * num3;
			LightMidInterval = UpdateRateLimiter.IntervalFromRate(c.LightFlickerMidRate.Value);
			LightFarInterval = UpdateRateLimiter.IntervalFromRate(c.LightFlickerFarRate.Value);
			LightDistantInterval = UpdateRateLimiter.IntervalFromRate(c.LightFlickerDistantRate.Value);
			LightDistanceCheckInterval = UpdateRateLimiter.IntervalFromRate(c.LightFlickerDistanceCheckRate.Value);
			LightLodDecisionInterval = UpdateRateLimiter.IntervalFromRate(c.LightLodDistanceCheckRate.Value);
			LightLodChecksPerFrame = Mathf.Clamp(c.LightLodChecksPerFrame.Value, 32, 4096);
			SmokeRendererInterval = UpdateRateLimiter.IntervalFromRate(c.SmokeRendererRate.Value);
			WindmillAudioInterval = UpdateRateLimiter.IntervalFromRate(c.WindmillAudioRate.Value);
			VagonAudioInterval = UpdateRateLimiter.IntervalFromRate(c.VagonAudioRate.Value);
		}
	}
	internal static class UpdateRateLimiter
	{
		internal static float IntervalFromRate(float updatesPerSecond)
		{
			return 1f / Mathf.Max(0.01f, updatesPerSecond);
		}

		internal static bool IsDue(ref float nextTime, float interval, float now, int phaseSeed)
		{
			if (interval <= 0f)
			{
				nextTime = now;
				return true;
			}
			if (nextTime <= 0f)
			{
				nextTime = now + interval * Phase01(phaseSeed);
				return true;
			}
			if (now < nextTime)
			{
				return false;
			}
			nextTime = now + interval;
			return true;
		}

		internal static float StaggeredSafetyDeadline(float now, float maximumInterval, int phaseSeed)
		{
			if (maximumInterval <= 0f)
			{
				return now;
			}
			float num = 0.75f + 0.25f * Phase01(phaseSeed);
			return now + maximumInterval * num;
		}

		internal static bool IsDiscontinuous(ref float lastSeenTime, float now, float maximumGap)
		{
			bool result = lastSeenTime > 0f && (now < lastSeenTime || now - lastSeenTime > maximumGap);
			lastSeenTime = now;
			return result;
		}

		internal static float Phase01Public(int seed)
		{
			return Phase01(seed);
		}

		private static float Phase01(int seed)
		{
			uint num = (uint)seed;
			num ^= num >> 16;
			num *= 2146121005;
			num ^= num >> 15;
			num *= 2221713035u;
			num ^= num >> 16;
			return (float)(num & 0xFFFFFF) / 16777215f;
		}
	}
	internal static class VanillaCollectionRegistry
	{
		internal static List<Piece> Pieces { get; private set; }

		internal static HashSet<Piece> ComfortPieces { get; private set; }

		internal static List<CraftingStation> CraftingStations { get; private set; }

		internal static List<StationExtension> StationExtensions { get; private set; }

		internal static int GhostLayer { get; private set; }

		internal static void Initialize()
		{
			Pieces = Piece.s_allPieces;
			ComfortPieces = Piece.s_allComfortPieces;
			CraftingStations = CraftingStation.m_allStations;
			StationExtensions = StationExtension.m_allExtensions;
			GhostLayer = LayerMask.NameToLayer("ghost");
		}
	}
	internal static class WeakStateStore<TKey, TState> where TKey : class where TState : class, new()
	{
		private static readonly ConditionalWeakTable<TKey, TState> States = new ConditionalWeakTable<TKey, TState>();

		internal static TState Get(TKey key)
		{
			return States.GetValue(key, Create);
		}

		internal static bool TryGet(TKey key, out TState state)
		{
			state = null;
			return key != null && States.TryGetValue(key, out state);
		}

		private static TState Create(TKey key)
		{
			return new TState();
		}

		internal static void Remove(TKey key)
		{
			if (key != null)
			{
				States.Remove(key);
			}
		}
	}
	internal sealed class WeakUnityRegistry<T> where T : Object
	{
		private readonly Dictionary<int, WeakReference> entries = new Dictionary<int, WeakReference>();

		private readonly List<int> dead = new List<int>();

		internal int Count => entries.Count;

		internal void Add(T value)
		{
			if (!((Object)(object)value == (Object)null))
			{
				int instanceID = ((Object)value).GetInstanceID();
				entries[instanceID] = new WeakReference(value);
			}
		}

		internal void Remove(T value)
		{
			if ((Object)(object)value != (Object)null)
			{
				entries.Remove(((Object)value).GetInstanceID());
			}
		}

		internal void ForEachAlive(Action<T> action)
		{
			dead.Clear();
			foreach (KeyValuePair<int, WeakReference> entry in entries)
			{
				object? target = entry.Value.Target;
				T val = (T)((target is T) ? target : null);
				if ((Object)(object)val == (Object)null)
				{
					dead.Add(entry.Key);
				}
				else
				{
					action(val);
				}
			}
			for (int i = 0; i < dead.Count; i++)
			{
				entries.Remove(dead[i]);
			}
		}

		internal void Clear()
		{
			entries.Clear();
			dead.Clear();
		}
	}
}
namespace BalrondVisualOptimizer.Patches.ZSFXOptimizations
{
	internal static class ZSFXPatches
	{
		private static readonly WeakUnityRegistry<ZSFX> Sleepers = new WeakUnityRegistry<ZSFX>();

		private static readonly List<ZSFX> UnexpectedPlayers = new List<ZSFX>();

		private static PatchRuntimeGate updateGate;

		private static PatchRuntimeGate playGate;

		private static PatchRuntimeGate fadeGate;

		private static float nextWatchdog;

		private static bool CanSleep => updateGate != null && playGate != null && fadeGate != null && updateGate.Enabled && playGate.Enabled && fadeGate.Enabled;

		internal static void Install(PatchInstaller installer)
		{
			updateGate = installer.Install("ZSFX.CustomUpdate idle dormancy", AccessTools.Method(typeof(ZSFX), "CustomUpdate", new Type[2]
			{
				typeof(float),
				typeof(float)
			}, (Type[])null), null, AccessTools.Method(typeof(ZSFXPatches), "UpdatePostfix", (Type[])null, (Type[])null), Launch.Settings.ZsfxDormancy, requiresKnownBuild: true, strictForeignPatchCheck: true);
			playGate = installer.Install("ZSFX.Play wake hook", AccessTools.Method(typeof(ZSFX), "Play", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(ZSFXPatches), "WakePrefix", (Type[])null, (Type[])null), null, Launch.Settings.ZsfxDormancy, requiresKnownBuild: true, strictForeignPatchCheck: true);
			fadeGate = installer.Install("ZSFX.FadeOut wake hook", AccessTools.Method(typeof(ZSFX), "FadeOut", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(ZSFXPatches), "WakePrefix", (Type[])null, (Type[])null), null, Launch.Settings.ZsfxDormancy, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static void UpdatePostfix(ZSFX __instance)
		{
			if (CanSleep && !((Object)(object)__instance == (Object)null) && !((Object)(object)__instance.m_audioSource == (Object)null) && !__instance.m_audioSource.loop && !__instance.m_audioSource.isPlaying && (!__instance.m_playOnAwake || !(__instance.m_delay >= 0f)) && !(__instance.m_fadeOutTimer >= 0f) && !(__instance.m_fadeInTimer >= 0f) && ZSFX.Instances.Remove((IMonoUpdater)(object)__instance))
			{
				Sleepers.Add(__instance);
				RuntimeStats.Inc(ref RuntimeStats.ZsfxDormantFrames);
			}
		}

		private static void WakePrefix(ZSFX __instance)
		{
			if (!((Object)(object)__instance == (Object)null) && CanSleep)
			{
				Wake(__instance);
			}
		}

		private static void Wake(ZSFX instance)
		{
			if (!((Object)(object)instance == (Object)null))
			{
				if (((Behaviour)instance).enabled && ((Component)instance).gameObject.activeInHierarchy && !ZSFX.Instances.Contains((IMonoUpdater)(object)instance))
				{
					ZSFX.Instances.Add((IMonoUpdater)(object)instance);
				}
				Sleepers.Remove(instance);
			}
		}

		internal static void Tick(float now)
		{
			if (!CanSleep || now < nextWatchdog || Sleepers.Count == 0)
			{
				return;
			}
			nextWatchdog = now + 1f;
			UnexpectedPlayers.Clear();
			Sleepers.ForEachAlive(delegate(ZSFX s)
			{
				if (((Behaviour)s).enabled && ((Component)s).gameObject.activeInHierarchy && (Object)(object)s.m_audioSource != (Object)null && s.m_audioSource.isPlaying)
				{
					UnexpectedPlayers.Add(s);
				}
			});
			for (int num = 0; num < UnexpectedPlayers.Count; num++)
			{
				Wake(UnexpectedPlayers[num]);
			}
			UnexpectedPlayers.Clear();
		}

		internal static void RefreshDormancy()
		{
			if (!CanSleep)
			{
				WakeAll();
			}
		}

		internal static void Shutdown()
		{
			WakeAll();
		}

		private static void WakeAll()
		{
			Sleepers.ForEachAlive(delegate(ZSFX s)
			{
				if (((Behaviour)s).enabled && ((Component)s).gameObject.activeInHierarchy && !ZSFX.Instances.Contains((IMonoUpdater)(object)s))
				{
					ZSFX.Instances.Add((IMonoUpdater)(object)s);
				}
			});
			Sleepers.Clear();
			UnexpectedPlayers.Clear();
			nextWatchdog = 0f;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.WindmillOptimizations
{
	internal static class WindmillPatches
	{
		private sealed class State
		{
			internal int Epoch;

			internal float NextUpdate;

			internal float AccumulatedDelta;

			internal float LastSeenTime;
		}

		private static PatchRuntimeGate gate;

		internal static void Install(PatchInstaller installer)
		{
			gate = installer.Install("Windmill.UpdateAudio throttle", AccessTools.Method(typeof(Windmill), "UpdateAudio", new Type[1] { typeof(float) }, (Type[])null), AccessTools.Method(typeof(WindmillPatches), "Prefix", (Type[])null, (Type[])null), null, Launch.Settings.WindmillAudio, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool Prefix(Windmill __instance, ref float dt)
		{
			if (gate == null || !gate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			State state = WeakStateStore<Windmill, State>.Get(__instance);
			if (state.Epoch != gate.Epoch)
			{
				Reset(state, gate.Epoch);
			}
			float windmillAudioInterval = RuntimeTuning.WindmillAudioInterval;
			float time = Time.time;
			if (UpdateRateLimiter.IsDiscontinuous(ref state.LastSeenTime, time, Mathf.Max(1f, windmillAudioInterval * 3f)))
			{
				state.NextUpdate = 0f;
				state.AccumulatedDelta = 0f;
			}
			if (UpdateRateLimiter.IsDue(ref state.NextUpdate, windmillAudioInterval, time, ((Object)__instance).GetInstanceID()))
			{
				if (state.AccumulatedDelta > 0f)
				{
					dt += state.AccumulatedDelta;
					state.AccumulatedDelta = 0f;
				}
				return true;
			}
			state.AccumulatedDelta += dt;
			RuntimeStats.Inc(ref RuntimeStats.WindmillAudioSkips);
			return false;
		}

		private static void Reset(State state, int epoch)
		{
			state.Epoch = epoch;
			state.NextUpdate = 0f;
			state.AccumulatedDelta = 0f;
			state.LastSeenTime = 0f;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.VisEquipmentOptimizations
{
	internal static class VisEquipmentPatches
	{
		private struct EquipmentSignature
		{
			internal int Left;

			internal int Right;

			internal int Chest;

			internal int Legs;

			internal int Helmet;

			internal int Shoulder;

			internal int Utility;

			internal int Trinket;

			internal int Beard;

			internal int Hair;

			internal int LeftBack;

			internal int RightBack;

			internal int ShoulderVariant;

			internal int LeftVariant;

			internal int LeftBackVariant;

			internal bool SameAs(EquipmentSignature other)
			{
				return Left == other.Left && Right == other.Right && Chest == other.Chest && Legs == other.Legs && Helmet == other.Helmet && Shoulder == other.Shoulder && Utility == other.Utility && Trinket == other.Trinket && Beard == other.Beard && Hair == other.Hair && LeftBack == other.LeftBack && RightBack == other.RightBack && ShoulderVariant == other.ShoulderVariant && LeftVariant == other.LeftVariant && LeftBackVariant == other.LeftBackVariant;
			}
		}

		private sealed class State
		{
			internal int EquipmentEpoch;

			internal uint EquipmentRevision = uint.MaxValue;

			internal EquipmentSignature Equipment;

			internal bool HasEquipment;

			internal float EquipmentSafetyRefresh;

			internal int ColorEpoch;

			internal Vector3 SkinColor;

			internal Vector3 HairColor;

			internal bool HasColors;

			internal float ColorSafetyRefresh;

			internal uint ColorRevision = uint.MaxValue;

			internal int BeardInstanceId;

			internal int HairInstanceId;

			internal int ModelIndex = int.MinValue;
		}

		private static PatchRuntimeGate equipmentGate;

		private static PatchRuntimeGate colorGate;

		internal static void Install(PatchInstaller installer)
		{
			equipmentGate = installer.Install("VisEquipment.UpdateEquipmentVisuals signature gate", AccessTools.Method(typeof(VisEquipment), "UpdateEquipmentVisuals", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(VisEquipmentPatches), "EquipmentPrefix", (Type[])null, (Type[])null), null, Launch.Settings.VisEquipmentEquipment, requiresKnownBuild: true, strictForeignPatchCheck: true);
			colorGate = installer.Install("VisEquipment.UpdateColors signature gate", AccessTools.Method(typeof(VisEquipment), "UpdateColors", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(VisEquipmentPatches), "ColorPrefix", (Type[])null, (Type[])null), null, Launch.Settings.VisEquipmentColors, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool EquipmentPrefix(VisEquipment __instance)
		{
			if (equipmentGate == null || !equipmentGate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if ((Object)(object)__instance.m_nview == (Object)null)
			{
				return true;
			}
			ZDO zDO = __instance.m_nview.GetZDO();
			if (zDO == null)
			{
				return true;
			}
			State state = WeakStateStore<VisEquipment, State>.Get(__instance);
			if (state.EquipmentEpoch != equipmentGate.Epoch)
			{
				state.EquipmentEpoch = equipmentGate.Epoch;
				state.HasEquipment = false;
				state.EquipmentRevision = uint.MaxValue;
				state.EquipmentSafetyRefresh = 0f;
			}
			float unscaledTime = Time.unscaledTime;
			uint dataRevision = zDO.DataRevision;
			int num = (__instance.m_isPlayer ? zDO.GetInt(ZDOVars.s_shoulderItemVariant, 0) : __instance.m_shoulderItemVariant);
			int num2 = (__instance.m_isPlayer ? zDO.GetInt(ZDOVars.s_leftItemVariant, 0) : __instance.m_leftItemVariant);
			int num3 = (__instance.m_isPlayer ? zDO.GetInt(ZDOVars.s_leftBackItemVariant, 0) : __instance.m_leftBackItemVariant);
			if (state.HasEquipment && dataRevision == state.EquipmentRevision && state.Equipment.ShoulderVariant == num && state.Equipment.LeftVariant == num2 && state.Equipment.LeftBackVariant == num3 && unscaledTime < state.EquipmentSafetyRefresh)
			{
				RuntimeStats.Inc(ref RuntimeStats.VisEquipmentEquipmentSkips);
				return false;
			}
			EquipmentSignature equipmentSignature = ReadEquipmentSignature(__instance, zDO, num, num2, num3);
			bool flag = !state.HasEquipment || !state.Equipment.SameAs(equipmentSignature);
			state.EquipmentRevision = dataRevision;
			if (!flag && unscaledTime < state.EquipmentSafetyRefresh)
			{
				RuntimeStats.Inc(ref RuntimeStats.VisEquipmentEquipmentSkips);
				return false;
			}
			state.Equipment = equipmentSignature;
			state.HasEquipment = true;
			state.EquipmentSafetyRefresh = UpdateRateLimiter.StaggeredSafetyDeadline(unscaledTime, RuntimeTuning.VisualSafety, ((Object)__instance).GetInstanceID());
			return true;
		}

		private static EquipmentSignature ReadEquipmentSignature(VisEquipment instance, ZDO zdo, int shoulderVariant, int leftVariant, int leftBackVariant)
		{
			EquipmentSignature result = new EquipmentSignature
			{
				Left = zdo.GetInt(ZDOVars.s_leftItem, 0),
				Right = zdo.GetInt(ZDOVars.s_rightItem, 0),
				Chest = zdo.GetInt(ZDOVars.s_chestItem, 0),
				Legs = zdo.GetInt(ZDOVars.s_legItem, 0),
				Helmet = zdo.GetInt(ZDOVars.s_helmetItem, 0),
				Shoulder = zdo.GetInt(ZDOVars.s_shoulderItem, 0),
				Utility = zdo.GetInt(ZDOVars.s_utilityItem, 0),
				Trinket = zdo.GetInt(ZDOVars.s_trinketItem, 0),
				ShoulderVariant = shoulderVariant,
				LeftVariant = leftVariant,
				LeftBackVariant = leftBackVariant
			};
			if (instance.m_isPlayer)
			{
				if (!instance.m_isArmorStand)
				{
					result.Beard = zdo.GetInt(ZDOVars.s_beardItem, 0);
					result.Hair = zdo.GetInt(ZDOVars.s_hairItem, 0);
				}
				result.LeftBack = zdo.GetInt(ZDOVars.s_leftBackItem, 0);
				result.RightBack = zdo.GetInt(ZDOVars.s_rightBackItem, 0);
			}
			return result;
		}

		private static bool ColorPrefix(VisEquipment __instance)
		{
			//IL_0183: Unknown result type (might be due to invalid IL or missing references)
			//IL_0188: Unknown result type (might be due to invalid IL or missing references)
			//IL_018d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0195: Unknown result type (might be due to invalid IL or missing references)
			//IL_019a: Unknown result type (might be due to invalid IL or missing references)
			//IL_019f: Unknown result type (might be due to invalid IL or missing references)
			//IL_01ad: Unknown result type (might be due to invalid IL or missing references)
			//IL_01b2: Unknown result type (might be due to invalid IL or missing references)
			//IL_01bc: Unknown result type (might be due to invalid IL or missing references)
			//IL_01c1: Unknown result type (might be due to invalid IL or missing references)
			//IL_01f5: Unknown result type (might be due to invalid IL or missing references)
			//IL_01f7: Unknown result type (might be due to invalid IL or missing references)
			//IL_01fd: Unknown result type (might be due to invalid IL or missing references)
			//IL_01ff: Unknown result type (might be due to invalid IL or missing references)
			if (colorGate == null || !colorGate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if ((Object)(object)__instance.m_nview == (Object)null)
			{
				return true;
			}
			ZDO zDO = __instance.m_nview.GetZDO();
			if (zDO == null)
			{
				return true;
			}
			State state = WeakStateStore<VisEquipment, State>.Get(__instance);
			if (state.ColorEpoch != colorGate.Epoch)
			{
				state.ColorEpoch = colorGate.Epoch;
				state.HasColors = false;
				state.ColorRevision = uint.MaxValue;
				state.ColorSafetyRefresh = 0f;
				state.BeardInstanceId = 0;
				state.HairInstanceId = 0;
			}
			float unscaledTime = Time.unscaledTime;
			uint dataRevision = zDO.DataRevision;
			int num = ((!((Object)(object)__instance.m_beardItemInstance == (Object)null)) ? ((Object)__instance.m_beardItemInstance).GetInstanceID() : 0);
			int num2 = ((!((Object)(object)__instance.m_hairItemInstance == (Object)null)) ? ((Object)__instance.m_hairItemInstance).GetInstanceID() : 0);
			int num3 = zDO.GetInt(ZDOVars.s_modelIndex, __instance.m_modelIndex);
			bool flag = state.BeardInstanceId == num && state.HairInstanceId == num2 && state.ModelIndex == num3;
			if (state.HasColors && state.ColorRevision == dataRevision && flag && unscaledTime < state.ColorSafetyRefresh)
			{
				RuntimeStats.Inc(ref RuntimeStats.VisEquipmentColorSkips);
				return false;
			}
			Vector3 vec = zDO.GetVec3(ZDOVars.s_skinColor, Vector3.one);
			Vector3 vec2 = zDO.GetVec3(ZDOVars.s_hairColor, Vector3.one);
			if (state.HasColors && flag && state.SkinColor == vec && state.HairColor == vec2 && unscaledTime < state.ColorSafetyRefresh)
			{
				state.ColorRevision = dataRevision;
				RuntimeStats.Inc(ref RuntimeStats.VisEquipmentColorSkips);
				return false;
			}
			state.SkinColor = vec;
			state.HairColor = vec2;
			state.ColorRevision = dataRevision;
			state.BeardInstanceId = num;
			state.HairInstanceId = num2;
			state.ModelIndex = num3;
			state.HasColors = true;
			state.ColorSafetyRefresh = UpdateRateLimiter.StaggeredSafetyDeadline(unscaledTime, RuntimeTuning.VisualSafety, ((Object)__instance).GetInstanceID() ^ 0x51C0);
			return true;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.VagonOptimizations
{
	internal static class VagonPatches
	{
		private sealed class AudioState
		{
			internal int Epoch;

			internal float NextUpdate;

			internal float AccumulatedDelta;

			internal float LastSeenTime;
		}

		private static PatchRuntimeGate audioGate;

		private static PatchRuntimeGate tetherGate;

		internal static void Install(PatchInstaller installer)
		{
			audioGate = installer.Install("Vagon.UpdateAudio throttle", AccessTools.Method(typeof(Vagon), "UpdateAudio", new Type[1] { typeof(float) }, (Type[])null), AccessTools.Method(typeof(VagonPatches), "AudioPrefix", (Type[])null, (Type[])null), null, Launch.Settings.VagonAudio, requiresKnownBuild: true, strictForeignPatchCheck: true);
			tetherGate = installer.Install("Vagon.LateUpdate parked tether no-op gate", AccessTools.Method(typeof(Vagon), "LateUpdate", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(VagonPatches), "LateUpdatePrefix", (Type[])null, (Type[])null), null, Launch.Settings.VagonIdleTether, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool AudioPrefix(Vagon __instance, ref float dt)
		{
			if (audioGate == null || !audioGate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			AudioState audioState = WeakStateStore<Vagon, AudioState>.Get(__instance);
			if (audioState.Epoch != audioGate.Epoch)
			{
				Reset(audioState, audioGate.Epoch);
			}
			float vagonAudioInterval = RuntimeTuning.VagonAudioInterval;
			float time = Time.time;
			if (UpdateRateLimiter.IsDiscontinuous(ref audioState.LastSeenTime, time, Mathf.Max(1f, vagonAudioInterval * 3f)))
			{
				audioState.NextUpdate = 0f;
				audioState.AccumulatedDelta = 0f;
			}
			if (UpdateRateLimiter.IsDue(ref audioState.NextUpdate, vagonAudioInterval, time, ((Object)__instance).GetInstanceID()))
			{
				if (audioState.AccumulatedDelta > 0f)
				{
					dt += audioState.AccumulatedDelta;
					audioState.AccumulatedDelta = 0f;
				}
				return true;
			}
			audioState.AccumulatedDelta += dt;
			RuntimeStats.Inc(ref RuntimeStats.VagonAudioSkips);
			return false;
		}

		private static bool LateUpdatePrefix(Vagon __instance)
		{
			if (tetherGate == null || !tetherGate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if ((Object)(object)__instance.m_attachJoin == (Object)null && (Object)(object)__instance.m_lineRenderer != (Object)null && !((Renderer)__instance.m_lineRenderer).enabled)
			{
				RuntimeStats.Inc(ref RuntimeStats.VagonTetherSkips);
				return false;
			}
			return true;
		}

		private static void Reset(AudioState state, int epoch)
		{
			state.Epoch = epoch;
			state.NextUpdate = 0f;
			state.AccumulatedDelta = 0f;
			state.LastSeenTime = 0f;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.TeleportWorldOptimizations
{
	internal static class TeleportWorldPatches
	{
		private sealed class State
		{
			internal int Epoch;

			internal bool HasTarget;

			internal float NextSafety;
		}

		private static PatchRuntimeGate gate;

		internal static void Install(PatchInstaller installer)
		{
			gate = installer.Install("TeleportWorld.Update stable emission gate", AccessTools.Method(typeof(TeleportWorld), "Update", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(TeleportWorldPatches), "Prefix", (Type[])null, (Type[])null), null, Launch.Settings.PortalStableEmission, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool Prefix(TeleportWorld __instance)
		{
			if (gate == null || !gate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			float num = (__instance.m_hadTarget ? 1f : 0f);
			if (!Mathf.Approximately(__instance.m_colorAlpha, num))
			{
				return true;
			}
			State state = WeakStateStore<TeleportWorld, State>.Get(__instance);
			if (state.Epoch != gate.Epoch)
			{
				state.Epoch = gate.Epoch;
				state.HasTarget = !__instance.m_hadTarget;
				state.NextSafety = 0f;
			}
			float unscaledTime = Time.unscaledTime;
			if (state.HasTarget == __instance.m_hadTarget && unscaledTime < state.NextSafety)
			{
				RuntimeStats.Inc(ref RuntimeStats.PortalVisualSkips);
				return false;
			}
			state.HasTarget = __instance.m_hadTarget;
			state.NextSafety = UpdateRateLimiter.StaggeredSafetyDeadline(unscaledTime, RuntimeTuning.StaticVisualSafety, ((Object)__instance).GetInstanceID());
			return true;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.StationExtensionOptimizations
{
	internal static class StationExtensionPatches
	{
		private static PatchRuntimeGate gate;

		internal static void Install(PatchInstaller installer)
		{
			gate = installer.Install("StationExtension.OtherExtensionInRange squared-distance query", AccessTools.Method(typeof(StationExtension), "OtherExtensionInRange", new Type[1] { typeof(float) }, (Type[])null), AccessTools.Method(typeof(StationExtensionPatches), "Prefix", (Type[])null, (Type[])null), null, Launch.Settings.StationExtensionSquaredDistanceQuery, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool Prefix(StationExtension __instance, float radius, ref bool __result)
		{
			//IL_0060: Unknown result type (might be due to invalid IL or missing references)
			//IL_0065: Unknown result type (might be due to invalid IL or missing references)
			//IL_009a: Unknown result type (might be due to invalid IL or missing references)
			//IL_009f: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a5: Unknown result type (might be due to invalid IL or missing references)
			List<StationExtension> stationExtensions = VanillaCollectionRegistry.StationExtensions;
			if (gate == null || !gate.Enabled || stationExtensions == null || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if (!(radius > 0f) || float.IsNaN(radius))
			{
				__result = false;
				return false;
			}
			float num = radius * radius;
			Vector3 position = ((Component)__instance).transform.position;
			for (int i = 0; i < stationExtensions.Count; i++)
			{
				StationExtension val = stationExtensions[i];
				if (!((Object)(object)val == (Object)null) && !((Object)(object)val == (Object)(object)__instance))
				{
					Vector3 val2 = ((Component)val).transform.position - position;
					if (((Vector3)(ref val2)).sqrMagnitude < num)
					{
						__result = true;
						RuntimeStats.Inc(ref RuntimeStats.StationExtensionQueryReplacements);
						return false;
					}
				}
			}
			__result = false;
			RuntimeStats.Inc(ref RuntimeStats.StationExtensionQueryReplacements);
			return false;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.SmokeRendererOptimizations
{
	internal static class SmokeRendererPatches
	{
		private sealed class State
		{
			internal int Epoch;

			internal float NextUpdate;
		}

		private static PatchRuntimeGate gate;

		internal static void Install(PatchInstaller installer)
		{
			gate = installer.Install("SmokeRenderer.LateUpdate presentation throttle", AccessTools.Method(typeof(SmokeRenderer), "LateUpdate", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(SmokeRendererPatches), "Prefix", (Type[])null, (Type[])null), null, Launch.Settings.SmokeRenderer, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool Prefix(SmokeRenderer __instance)
		{
			if (gate == null || !gate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			State state = WeakStateStore<SmokeRenderer, State>.Get(__instance);
			if (state.Epoch != gate.Epoch)
			{
				state.Epoch = gate.Epoch;
				state.NextUpdate = 0f;
			}
			if (!UpdateRateLimiter.IsDue(ref state.NextUpdate, RuntimeTuning.SmokeRendererInterval, Time.time, ((Object)__instance).GetInstanceID()))
			{
				if (__instance.m_chunkedSmoke != null && __instance.m_chunkedSmoke.Count > 0)
				{
					RuntimeStats.Inc(ref RuntimeStats.SmokeRendererSkips);
				}
				return false;
			}
			return true;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.SmelterOptimizations
{
	internal static class SmelterPatches
	{
		private struct Signature
		{
			internal bool Active;

			internal bool HasFuel;

			internal bool HasOre;

			internal bool AnimationActive;

			internal bool SameAs(Signature other)
			{
				return Active == other.Active && HasFuel == other.HasFuel && HasOre == other.HasOre && AnimationActive == other.AnimationActive;
			}
		}

		private sealed class State
		{
			internal int Epoch;

			internal bool HasValue;

			internal uint Revision = uint.MaxValue;

			internal bool HaveRoof;

			internal bool BlockedSmoke;

			internal bool AnimationWindow;

			internal Signature Value;

			internal float NextSafetyRefresh;
		}

		private static PatchRuntimeGate gate;

		internal static void Install(PatchInstaller installer)
		{
			gate = installer.Install("Smelter.UpdateState visual signature gate", AccessTools.Method(typeof(Smelter), "UpdateState", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(SmelterPatches), "Prefix", (Type[])null, (Type[])null), null, Launch.Settings.SmelterVisualState, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool Prefix(Smelter __instance)
		{
			if (gate == null || !gate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if ((Object)(object)__instance.m_nview == (Object)null || !__instance.m_nview.IsValid())
			{
				return true;
			}
			ZDO zDO = __instance.m_nview.GetZDO();
			if (zDO == null)
			{
				return true;
			}
			State state = WeakStateStore<Smelter, State>.Get(__instance);
			if (state.Epoch != gate.Epoch)
			{
				state.Epoch = gate.Epoch;
				state.HasValue = false;
				state.Revision = uint.MaxValue;
				state.NextSafetyRefresh = 0f;
			}
			float unscaledTime = Time.unscaledTime;
			bool flag = __instance.m_addOreAnimationDuration > 0f && Time.time - __instance.m_addedOreTime < __instance.m_addOreAnimationDuration;
			uint dataRevision = zDO.DataRevision;
			if (state.HasValue && dataRevision == state.Revision && state.HaveRoof == __instance.m_haveRoof && state.BlockedSmoke == __instance.m_blockedSmoke && state.AnimationWindow == flag && unscaledTime < state.NextSafetyRefresh)
			{
				RuntimeStats.Inc(ref RuntimeStats.SmelterStateSkips);
				return false;
			}
			float num = zDO.GetFloat(ZDOVars.s_fuel, 0f);
			int num2 = zDO.GetInt(ZDOVars.s_queued, 0);
			bool flag2 = num > 0f;
			bool flag3 = num2 > 0;
			bool flag4 = (__instance.m_maxFuel == 0 || flag2) && (__instance.m_maxOre == 0 || flag3) && (!__instance.m_requiresRoof || __instance.m_haveRoof) && !__instance.m_blockedSmoke;
			Signature signature = new Signature
			{
				Active = flag4,
				HasFuel = flag2,
				HasOre = flag3,
				AnimationActive = (flag4 || flag)
			};
			if (state.HasValue && state.Value.SameAs(signature) && unscaledTime < state.NextSafetyRefresh)
			{
				state.Revision = dataRevision;
				state.HaveRoof = __instance.m_haveRoof;
				state.BlockedSmoke = __instance.m_blockedSmoke;
				state.AnimationWindow = flag;
				RuntimeStats.Inc(ref RuntimeStats.SmelterStateSkips);
				return false;
			}
			state.Value = signature;
			state.HasValue = true;
			state.Revision = dataRevision;
			state.HaveRoof = __instance.m_haveRoof;
			state.BlockedSmoke = __instance.m_blockedSmoke;
			state.AnimationWindow = flag;
			state.NextSafetyRefresh = UpdateRateLimiter.StaggeredSafetyDeadline(unscaledTime, RuntimeTuning.VisualSafety, ((Object)__instance).GetInstanceID());
			return true;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.PrivateAreaOptimizations
{
	internal static class PrivateAreaPatches
	{
		private sealed class State
		{
			internal int Epoch;

			internal bool HasValue;

			internal bool Enabled;

			internal float NextSafety;
		}

		private static PatchRuntimeGate gate;

		internal static void Install(PatchInstaller installer)
		{
			gate = installer.Install("PrivateArea.UpdateStatus stable visual gate", AccessTools.Method(typeof(PrivateArea), "UpdateStatus", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(PrivateAreaPatches), "Prefix", (Type[])null, (Type[])null), null, Launch.Settings.PrivateAreaStatusVisual, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool Prefix(PrivateArea __instance)
		{
			if (gate == null || !gate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			__instance.m_flashAvailable = true;
			bool flag = __instance.IsEnabled();
			State state = WeakStateStore<PrivateArea, State>.Get(__instance);
			if (state.Epoch != gate.Epoch)
			{
				state.Epoch = gate.Epoch;
				state.HasValue = false;
				state.NextSafety = 0f;
			}
			float unscaledTime = Time.unscaledTime;
			if (state.HasValue && state.Enabled == flag && unscaledTime < state.NextSafety)
			{
				RuntimeStats.Inc(ref RuntimeStats.PrivateAreaVisualSkips);
				return false;
			}
			state.HasValue = true;
			state.Enabled = flag;
			state.NextSafety = UpdateRateLimiter.StaggeredSafetyDeadline(unscaledTime, RuntimeTuning.StaticVisualSafety, ((Object)__instance).GetInstanceID());
			return true;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.PieceOptimizations
{
	internal static class PiecePatches
	{
		private static PatchRuntimeGate allPiecesGate;

		private static PatchRuntimeGate comfortPiecesGate;

		internal static void Install(PatchInstaller installer)
		{
			allPiecesGate = installer.Install("Piece.GetAllPiecesInRadius squared-distance query", AccessTools.Method(typeof(Piece), "GetAllPiecesInRadius", new Type[3]
			{
				typeof(Vector3),
				typeof(float),
				typeof(List<Piece>)
			}, (Type[])null), AccessTools.Method(typeof(PiecePatches), "AllPiecesPrefix", (Type[])null, (Type[])null), null, Launch.Settings.PieceSquaredDistanceQueries, requiresKnownBuild: true, strictForeignPatchCheck: true);
			comfortPiecesGate = installer.Install("Piece.GetAllComfortPiecesInRadius squared-distance query", AccessTools.Method(typeof(Piece), "GetAllComfortPiecesInRadius", new Type[3]
			{
				typeof(Vector3),
				typeof(float),
				typeof(List<Piece>)
			}, (Type[])null), AccessTools.Method(typeof(PiecePatches), "ComfortPiecesPrefix", (Type[])null, (Type[])null), null, Launch.Settings.PieceSquaredDistanceQueries, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool AllPiecesPrefix(Vector3 p, float radius, List<Piece> pieces)
		{
			//IL_0094: Unknown result type (might be due to invalid IL or missing references)
			//IL_0099: Unknown result type (might be due to invalid IL or missing references)
			//IL_009a: Unknown result type (might be due to invalid IL or missing references)
			//IL_009f: Unknown result type (might be due to invalid IL or missing references)
			List<Piece> pieces2 = VanillaCollectionRegistry.Pieces;
			if (allPiecesGate == null || !allPiecesGate.Enabled || pieces2 == null || pieces == null)
			{
				return true;
			}
			if (!(radius > 0f) || float.IsNaN(radius))
			{
				return false;
			}
			float num = radius * radius;
			int ghostLayer = VanillaCollectionRegistry.GhostLayer;
			for (int i = 0; i < pieces2.Count; i++)
			{
				Piece val = pieces2[i];
				if (!((Object)(object)val == (Object)null) && ((Component)val).gameObject.layer != ghostLayer)
				{
					Vector3 val2 = ((Component)val).transform.position - p;
					if (((Vector3)(ref val2)).sqrMagnitude < num)
					{
						pieces.Add(val);
					}
				}
			}
			RuntimeStats.Inc(ref RuntimeStats.PieceQueryReplacements);
			return false;
		}

		private static bool ComfortPiecesPrefix(Vector3 p, float radius, List<Piece> pieces)
		{
			//IL_0099: 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_009f: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a4: Unknown result type (might be due to invalid IL or missing references)
			HashSet<Piece> comfortPieces = VanillaCollectionRegistry.ComfortPieces;
			if (comfortPiecesGate == null || !comfortPiecesGate.Enabled || comfortPieces == null || pieces == null)
			{
				return true;
			}
			if (!(radius > 0f) || float.IsNaN(radius))
			{
				return false;
			}
			float num = radius * radius;
			int ghostLayer = VanillaCollectionRegistry.GhostLayer;
			foreach (Piece item in comfortPieces)
			{
				if (!((Object)(object)item == (Object)null) && ((Component)item).gameObject.layer != ghostLayer)
				{
					Vector3 val = ((Component)item).transform.position - p;
					if (((Vector3)(ref val)).sqrMagnitude < num)
					{
						pieces.Add(item);
					}
				}
			}
			RuntimeStats.Inc(ref RuntimeStats.PieceQueryReplacements);
			return false;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.MaterialFaderOptimizations
{
	internal static class MaterialFaderPatches
	{
		private static readonly WeakUnityRegistry<MaterialFader> Sleepers = new WeakUnityRegistry<MaterialFader>();

		private static PatchRuntimeGate updateGate;

		private static PatchRuntimeGate triggerGate;

		private static bool CanSleep => updateGate != null && triggerGate != null && updateGate.Enabled && triggerGate.Enabled;

		internal static void Install(PatchInstaller installer)
		{
			updateGate = installer.Install("MaterialFader.Update endpoint dormancy", AccessTools.Method(typeof(MaterialFader), "Update", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(MaterialFaderPatches), "UpdatePrefix", (Type[])null, (Type[])null), null, Launch.Settings.MaterialFaderDormancy, requiresKnownBuild: true, strictForeignPatchCheck: true);
			triggerGate = installer.Install("MaterialFader.TriggerFade wake hook", AccessTools.Method(typeof(MaterialFader), "TriggerFade", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(MaterialFaderPatches), "TriggerPrefix", (Type[])null, (Type[])null), null, Launch.Settings.MaterialFaderDormancy, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool UpdatePrefix(MaterialFader __instance)
		{
			if (!CanSleep || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if (!__instance.m_started)
			{
				Sleep(__instance);
				return false;
			}
			bool flag = __instance.m_fadeProperties != null;
			if (flag)
			{
				for (int i = 0; i < __instance.m_fadeProperties.Count; i++)
				{
					if (!__instance.m_fadeProperties[i].m_finished)
					{
						flag = false;
						break;
					}
				}
			}
			if (!flag)
			{
				return true;
			}
			Sleep(__instance);
			return false;
		}

		private static void TriggerPrefix(MaterialFader __instance)
		{
			if (!((Object)(object)__instance == (Object)null) && CanSleep)
			{
				Sleepers.Remove(__instance);
				if (!((Behaviour)__instance).enabled)
				{
					((Behaviour)__instance).enabled = true;
				}
			}
		}

		private static void Sleep(MaterialFader instance)
		{
			Sleepers.Add(instance);
			((Behaviour)instance).enabled = false;
			RuntimeStats.Inc(ref RuntimeStats.MaterialFaderDormantFrames);
		}

		internal static void RefreshDormancy()
		{
			if (CanSleep)
			{
				return;
			}
			Sleepers.ForEachAlive(delegate(MaterialFader f)
			{
				if (!((Behaviour)f).enabled)
				{
					((Behaviour)f).enabled = true;
				}
			});
			Sleepers.Clear();
		}

		internal static void Shutdown()
		{
			Sleepers.ForEachAlive(delegate(MaterialFader f)
			{
				if (!((Behaviour)f).enabled)
				{
					((Behaviour)f).enabled = true;
				}
			});
			Sleepers.Clear();
		}
	}
}
namespace BalrondVisualOptimizer.Patches.LineConnectOptimizations
{
	internal static class LineConnectPatches
	{
		private sealed class State
		{
			internal int Epoch;

			internal bool HiddenNoConnection;

			internal uint Revision = uint.MaxValue;

			internal float NextSafety;
		}

		private static PatchRuntimeGate gate;

		internal static void Install(PatchInstaller installer)
		{
			gate = installer.Install("LineConnect.LateUpdate stable no-connection gate", AccessTools.Method(typeof(LineConnect), "LateUpdate", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(LineConnectPatches), "Prefix", (Type[])null, (Type[])null), AccessTools.Method(typeof(LineConnectPatches), "Postfix", (Type[])null, (Type[])null), Launch.Settings.LineConnectStableNoConnection, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool Prefix(LineConnect __instance)
		{
			if (gate == null || !gate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if ((Object)(object)__instance.m_nview == (Object)null || !__instance.m_nview.IsValid())
			{
				if ((Object)(object)__instance.m_lineRenderer != (Object)null && !((Renderer)__instance.m_lineRenderer).enabled)
				{
					RuntimeStats.Inc(ref RuntimeStats.LineConnectSkips);
					return false;
				}
				return true;
			}
			ZDO zDO = __instance.m_nview.GetZDO();
			if (zDO == null)
			{
				return true;
			}
			State state = WeakStateStore<LineConnect, State>.Get(__instance);
			if (state.Epoch != gate.Epoch)
			{
				state.Epoch = gate.Epoch;
				state.HiddenNoConnection = false;
				state.Revision = uint.MaxValue;
				state.NextSafety = 0f;
			}
			float unscaledTime = Time.unscaledTime;
			if (state.HiddenNoConnection && state.Revision == zDO.DataRevision && unscaledTime < state.NextSafety)
			{
				RuntimeStats.Inc(ref RuntimeStats.LineConnectSkips);
				return false;
			}
			return true;
		}

		private static void Postfix(LineConnect __instance)
		{
			if (gate != null && gate.Enabled && !((Object)(object)__instance == (Object)null) && !((Object)(object)__instance.m_nview == (Object)null) && __instance.m_nview.IsValid())
			{
				ZDO zDO = __instance.m_nview.GetZDO();
				if (zDO != null)
				{
					State state = WeakStateStore<LineConnect, State>.Get(__instance);
					state.HiddenNoConnection = __instance.m_hideIfNoConnection && (Object)(object)__instance.m_lineRenderer != (Object)null && !((Renderer)__instance.m_lineRenderer).enabled;
					state.Revision = zDO.DataRevision;
					state.NextSafety = Time.unscaledTime + 1f * (0.75f + 0.25f * UpdateRateLimiter.Phase01Public(((Object)__instance).GetInstanceID()));
				}
			}
		}
	}
}
namespace BalrondVisualOptimizer.Patches.LightLodOptimizations
{
	internal static class LightLodPatches
	{
		private static PatchRuntimeGate enableGate;

		private static PatchRuntimeGate disableGate;

		internal static bool CanManage
		{
			get
			{
				if (enableGate == null || disableGate == null || !enableGate.Enabled || !disableGate.Enabled)
				{
					return false;
				}
				if (Launch.Settings != null && Launch.Settings.DisableOnForeignHarmonyPatches.Value && HarmonyConflictService.TryGetFirstForeignOwner(AccessTools.Method(typeof(LightLod), "UpdateLoop", Type.EmptyTypes, (Type[])null), out var _))
				{
					return false;
				}
				return true;
			}
		}

		internal static void Install(PatchInstaller installer)
		{
			enableGate = installer.Install("LightLod.OnEnable central scheduler hook", AccessTools.Method(typeof(LightLod), "OnEnable", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(LightLodPatches), "OnEnablePrefix", (Type[])null, (Type[])null), null, Launch.Settings.LightLodCentralScheduler, requiresKnownBuild: true, strictForeignPatchCheck: true);
			disableGate = installer.Install("LightLod.OnDisable central scheduler hook", AccessTools.Method(typeof(LightLod), "OnDisable", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(LightLodPatches), "OnDisablePrefix", (Type[])null, (Type[])null), null, Launch.Settings.LightLodCentralScheduler, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool OnEnablePrefix(LightLod __instance)
		{
			if (!CanManage || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			LightLodScheduler.Register(__instance);
			RuntimeStats.Inc(ref RuntimeStats.LightLodCoroutineReplacements);
			return false;
		}

		private static bool OnDisablePrefix(LightLod __instance)
		{
			if (!CanManage || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			LightLodScheduler.Unregister(__instance);
			return false;
		}

		internal static void RefreshScheduler()
		{
			LightLodScheduler.SetEnabled(CanManage);
		}
	}
}
namespace BalrondVisualOptimizer.Patches.LightFlickerOptimizations
{
	internal static class LightFlickerPatches
	{
		private sealed class State
		{
			internal int Epoch;

			internal float NextUpdate;

			internal float NextDistanceCheck;

			internal float CachedInterval;

			internal bool HasDistanceTier;

			internal float AccumulatedDelta;

			internal float LastInternalTime;

			internal bool HasInternalTime;

			internal float LastSeenTime;
		}

		private static PatchRuntimeGate gate;

		internal static void Install(PatchInstaller installer)
		{
			gate = installer.Install("LightFlicker.CustomUpdate persistent distance throttle", AccessTools.Method(typeof(LightFlicker), "CustomUpdate", new Type[2]
			{
				typeof(float),
				typeof(float)
			}, (Type[])null), AccessTools.Method(typeof(LightFlickerPatches), "Prefix", (Type[])null, (Type[])null), null, Launch.Settings.LightFlicker, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool Prefix(LightFlicker __instance, ref float deltaTime)
		{
			if (gate == null || !gate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if ((Object)(object)__instance.m_light == (Object)null)
			{
				return true;
			}
			State state = WeakStateStore<LightFlicker, State>.Get(__instance);
			if (state.Epoch != gate.Epoch)
			{
				Reset(state, gate.Epoch);
			}
			if (!((Behaviour)__instance.m_light).enabled)
			{
				state.NextUpdate = 0f;
				state.AccumulatedDelta = 0f;
				state.LastSeenTime = 0f;
				state.LastInternalTime = __instance.m_time;
				state.HasInternalTime = true;
				return false;
			}
			if (state.HasInternalTime && __instance.m_time < state.LastInternalTime)
			{
				state.NextUpdate = 0f;
				state.AccumulatedDelta = 0f;
				state.LastSeenTime = 0f;
				state.NextDistanceCheck = 0f;
				state.HasDistanceTier = false;
			}
			state.LastInternalTime = __instance.m_time;
			state.HasInternalTime = true;
			if (__instance.m_ttl > 0f || (__instance.m_fadeInDuration > 0f && __instance.m_time < __instance.m_fadeInDuration))
			{
				return FlushAndRunVanilla(state, ref deltaTime);
			}
			float time = Time.time;
			if (!state.HasDistanceTier || time >= state.NextDistanceCheck)
			{
				state.CachedInterval = DetermineInterval(__instance);
				state.HasDistanceTier = true;
				state.NextDistanceCheck = time + RuntimeTuning.LightDistanceCheckInterval * (0.75f + 0.25f * UpdateRateLimiter.Phase01Public(((Object)__instance).GetInstanceID() ^ 0x3A71));
			}
			float cachedInterval = state.CachedInterval;
			if (cachedInterval <= 0f)
			{
				state.LastSeenTime = time;
				return FlushAndRunVanilla(state, ref deltaTime);
			}
			if (UpdateRateLimiter.IsDiscontinuous(ref state.LastSeenTime, time, Mathf.Max(1f, cachedInterval * 3f)))
			{
				state.NextUpdate = 0f;
				state.AccumulatedDelta = 0f;
			}
			if (UpdateRateLimiter.IsDue(ref state.NextUpdate, cachedInterval, time, ((Object)__instance).GetInstanceID()))
			{
				if (state.AccumulatedDelta > 0f)
				{
					deltaTime += state.AccumulatedDelta;
					state.AccumulatedDelta = 0f;
				}
				return true;
			}
			state.AccumulatedDelta += deltaTime;
			RuntimeStats.Inc(ref RuntimeStats.LightFlickerSkips);
			return false;
		}

		private static float DetermineInterval(LightFlicker instance)
		{
			//IL_001a: 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_0045: Unknown result type (might be due to invalid IL or missing references)
			//IL_004a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0052: 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_0058: Unknown result type (might be due to invalid IL or missing references)
			//IL_005d: Unknown result type (might be due to invalid IL or missing references)
			Vector3 position;
			if ((Object)(object)Player.m_localPlayer != (Object)null)
			{
				position = ((Component)Player.m_localPlayer).transform.position;
			}
			else
			{
				Camera mainCamera = Utils.GetMainCamera();
				if ((Object)(object)mainCamera == (Object)null)
				{
					return 0f;
				}
				position = ((Component)mainCamera).transform.position;
			}
			Vector3 val = ((Component)instance).transform.position - position;
			float sqrMagnitude = ((Vector3)(ref val)).sqrMagnitude;
			if (sqrMagnitude <= RuntimeTuning.LightNearSqr)
			{
				return 0f;
			}
			if (sqrMagnitude <= RuntimeTuning.LightMidSqr)
			{
				return RuntimeTuning.LightMidInterval;
			}
			if (sqrMagnitude <= RuntimeTuning.LightFarSqr)
			{
				return RuntimeTuning.LightFarInterval;
			}
			return RuntimeTuning.LightDistantInterval;
		}

		private static bool FlushAndRunVanilla(State state, ref float deltaTime)
		{
			if (state.AccumulatedDelta > 0f)
			{
				deltaTime += state.AccumulatedDelta;
				state.AccumulatedDelta = 0f;
			}
			state.NextUpdate = 0f;
			return true;
		}

		private static void Reset(State state, int epoch)
		{
			state.Epoch = epoch;
			state.NextUpdate = 0f;
			state.NextDistanceCheck = 0f;
			state.CachedInterval = 0f;
			state.HasDistanceTier = false;
			state.AccumulatedDelta = 0f;
			state.LastInternalTime = 0f;
			state.HasInternalTime = false;
			state.LastSeenTime = 0f;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.ItemStandOptimizations
{
	internal static class ItemStandPatches
	{
		private sealed class State
		{
			internal int Epoch;

			internal uint Revision = uint.MaxValue;

			internal float NextSafetyRefresh;
		}

		private static PatchRuntimeGate gate;

		internal static void Install(PatchInstaller installer)
		{
			gate = installer.Install("ItemStand.UpdateVisual revision gate", AccessTools.Method(typeof(ItemStand), "UpdateVisual", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(ItemStandPatches), "Prefix", (Type[])null, (Type[])null), null, Launch.Settings.ItemStandVisualRevision, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool Prefix(ItemStand __instance)
		{
			if (gate == null || !gate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if ((Object)(object)__instance.m_nview == (Object)null || !__instance.m_nview.IsValid())
			{
				return true;
			}
			ZDO zDO = __instance.m_nview.GetZDO();
			if (zDO == null)
			{
				return true;
			}
			State state = WeakStateStore<ItemStand, State>.Get(__instance);
			if (state.Epoch != gate.Epoch)
			{
				state.Epoch = gate.Epoch;
				state.Revision = uint.MaxValue;
				state.NextSafetyRefresh = 0f;
			}
			float unscaledTime = Time.unscaledTime;
			uint dataRevision = zDO.DataRevision;
			if (dataRevision == state.Revision && unscaledTime < state.NextSafetyRefresh)
			{
				RuntimeStats.Inc(ref RuntimeStats.ItemStandVisualSkips);
				return false;
			}
			state.Revision = dataRevision;
			state.NextSafetyRefresh = UpdateRateLimiter.StaggeredSafetyDeadline(unscaledTime, RuntimeTuning.StaticVisualSafety, ((Object)__instance).GetInstanceID());
			return true;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.FireplaceOptimizations
{
	internal static class FireplacePatches
	{
		private struct Signature
		{
			internal bool Burning;

			internal bool Wet;

			internal bool FuelAtLeastHalf;

			internal bool Empty;

			internal bool SameAs(Signature other)
			{
				return Burning == other.Burning && Wet == other.Wet && FuelAtLeastHalf == other.FuelAtLeastHalf && Empty == other.Empty;
			}
		}

		private sealed class State
		{
			internal int Epoch;

			internal bool HasValue;

			internal Signature Value;

			internal float NextSafetyRefresh;
		}

		private static PatchRuntimeGate gate;

		internal static void Install(PatchInstaller installer)
		{
			gate = installer.Install("Fireplace.UpdateState visual signature gate", AccessTools.Method(typeof(Fireplace), "UpdateState", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(FireplacePatches), "Prefix", (Type[])null, (Type[])null), null, Launch.Settings.FireplaceVisualState, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool Prefix(Fireplace __instance)
		{
			if (gate == null || !gate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if ((Object)(object)__instance.m_nview == (Object)null || !__instance.m_nview.IsValid())
			{
				return true;
			}
			ZDO zDO = __instance.m_nview.GetZDO();
			if (zDO == null)
			{
				return true;
			}
			bool flag = __instance.IsBurning();
			if (flag && __instance.m_canTurnOff && __instance.m_wet && __instance.m_nview.IsOwner() && zDO.GetInt(ZDOVars.s_state, 1) == 1)
			{
				return true;
			}
			State state = WeakStateStore<Fireplace, State>.Get(__instance);
			if (state.Epoch != gate.Epoch)
			{
				state.Epoch = gate.Epoch;
				state.HasValue = false;
				state.NextSafetyRefresh = 0f;
			}
			float num = zDO.GetFloat(ZDOVars.s_fuel, 0f);
			Signature signature = new Signature
			{
				Burning = flag,
				Wet = __instance.m_wet,
				FuelAtLeastHalf = (num >= __instance.m_halfThreshold),
				Empty = (num <= 0f)
			};
			float unscaledTime = Time.unscaledTime;
			if (state.HasValue && state.Value.SameAs(signature) && unscaledTime < state.NextSafetyRefresh)
			{
				RuntimeStats.Inc(ref RuntimeStats.FireplaceStateSkips);
				return false;
			}
			state.Value = signature;
			state.HasValue = true;
			state.NextSafetyRefresh = UpdateRateLimiter.StaggeredSafetyDeadline(unscaledTime, RuntimeTuning.VisualSafety, ((Object)__instance).GetInstanceID());
			return true;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.EffectFadeOptimizations
{
	internal static class EffectFadePatches
	{
		private sealed class State
		{
			internal int Epoch;

			internal bool SeenUpdate;

			internal bool Sleeping;
		}

		private static readonly WeakUnityRegistry<EffectFade> Sleepers = new WeakUnityRegistry<EffectFade>();

		private static PatchRuntimeGate updateGate;

		private static PatchRuntimeGate setActiveGate;

		private static bool CanSleep => updateGate != null && setActiveGate != null && updateGate.Enabled && setActiveGate.Enabled;

		internal static void Install(PatchInstaller installer)
		{
			updateGate = installer.Install("EffectFade.Update endpoint dormancy", AccessTools.Method(typeof(EffectFade), "Update", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(EffectFadePatches), "UpdatePrefix", (Type[])null, (Type[])null), null, Launch.Settings.EffectFadeDormancy, requiresKnownBuild: true, strictForeignPatchCheck: true);
			setActiveGate = installer.Install("EffectFade.SetActive wake hook", AccessTools.Method(typeof(EffectFade), "SetActive", new Type[1] { typeof(bool) }, (Type[])null), AccessTools.Method(typeof(EffectFadePatches), "SetActivePrefix", (Type[])null, (Type[])null), null, Launch.Settings.EffectFadeDormancy, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool UpdatePrefix(EffectFade __instance)
		{
			if (!CanSleep || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			State state = WeakStateStore<EffectFade, State>.Get(__instance);
			int num = updateGate.Epoch ^ (setActiveGate.Epoch << 1);
			if (state.Epoch != num)
			{
				state.Epoch = num;
				state.SeenUpdate = false;
				state.Sleeping = false;
			}
			float num2 = (__instance.m_active ? 1f : 0f);
			bool flag = Mathf.Approximately(__instance.m_intensity, num2);
			if (!state.SeenUpdate)
			{
				state.SeenUpdate = true;
				return true;
			}
			if (!flag)
			{
				return true;
			}
			state.Sleeping = true;
			Sleepers.Add(__instance);
			((Behaviour)__instance).enabled = false;
			RuntimeStats.Inc(ref RuntimeStats.EffectFadeDormantFrames);
			return false;
		}

		private static void SetActivePrefix(EffectFade __instance, bool active)
		{
			if (!((Object)(object)__instance == (Object)null) && CanSleep && __instance.m_active != active)
			{
				State state = WeakStateStore<EffectFade, State>.Get(__instance);
				state.SeenUpdate = false;
				state.Sleeping = false;
				Sleepers.Remove(__instance);
				if (!((Behaviour)__instance).enabled)
				{
					((Behaviour)__instance).enabled = true;
				}
			}
		}

		internal static void RefreshDormancy()
		{
			if (CanSleep)
			{
				return;
			}
			Sleepers.ForEachAlive(delegate(EffectFade f)
			{
				if (!((Behaviour)f).enabled)
				{
					((Behaviour)f).enabled = true;
				}
				if (WeakStateStore<EffectFade, State>.TryGet(f, out var state))
				{
					state.Sleeping = false;
					state.SeenUpdate = false;
				}
			});
			Sleepers.Clear();
		}

		internal static void Shutdown()
		{
			Sleepers.ForEachAlive(delegate(EffectFade f)
			{
				if (!((Behaviour)f).enabled)
				{
					((Behaviour)f).enabled = true;
				}
			});
			Sleepers.Clear();
		}
	}
}
namespace BalrondVisualOptimizer.Patches.CraftingStationOptimizations
{
	internal static class CraftingStationDormancyPatches
	{
		private static readonly WeakUnityRegistry<CraftingStation> Sleepers = new WeakUnityRegistry<CraftingStation>();

		private static PatchRuntimeGate updateGate;

		private static PatchRuntimeGate pokeGate;

		private static PatchRuntimeGate extensionsGate;

		private static bool CanSleep => updateGate != null && pokeGate != null && extensionsGate != null && updateGate.Enabled && pokeGate.Enabled && extensionsGate.Enabled;

		internal static void Install(PatchInstaller installer)
		{
			updateGate = installer.Install("CraftingStation.CustomUpdate idle dormancy replacement", AccessTools.Method(typeof(CraftingStation), "CustomUpdate", new Type[2]
			{
				typeof(float),
				typeof(float)
			}, (Type[])null), AccessTools.Method(typeof(CraftingStationDormancyPatches), "UpdatePrefix", (Type[])null, (Type[])null), null, Launch.Settings.CraftingStationIdleDormancy, requiresKnownBuild: true, strictForeignPatchCheck: true);
			pokeGate = installer.Install("CraftingStation.PokeInUse wake hook", AccessTools.Method(typeof(CraftingStation), "PokeInUse", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(CraftingStationDormancyPatches), "PokePrefix", (Type[])null, (Type[])null), null, Launch.Settings.CraftingStationIdleDormancy, requiresKnownBuild: true, strictForeignPatchCheck: true);
			extensionsGate = installer.Install("CraftingStation.GetExtensions wake hook", AccessTools.Method(typeof(CraftingStation), "GetExtensions", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(CraftingStationDormancyPatches), "ExtensionsPrefix", (Type[])null, (Type[])null), null, Launch.Settings.CraftingStationIdleDormancy, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool UpdatePrefix(CraftingStation __instance, float deltaTime)
		{
			if (!CanSleep || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if ((Object)(object)__instance.m_nview == (Object)null || !__instance.m_nview.IsValid())
			{
				return false;
			}
			__instance.m_useTimer = Mathf.Min(1f, __instance.m_useTimer + deltaTime);
			__instance.m_updateExtensionTimer = Mathf.Min(2f, __instance.m_updateExtensionTimer + deltaTime);
			if ((Object)(object)__instance.m_inUseObject != (Object)null)
			{
				bool flag = __instance.m_useTimer < 1f;
				if (__instance.m_inUseObject.activeSelf != flag)
				{
					__instance.m_inUseObject.SetActive(flag);
				}
			}
			if (__instance.m_useTimer >= 1f && __instance.m_updateExtensionTimer >= 2f && ((Object)(object)__instance.m_inUseObject == (Object)null || !__instance.m_inUseObject.activeSelf) && CraftingStation.Instances.Remove((IMonoUpdater)(object)__instance))
			{
				Sleepers.Add(__instance);
				RuntimeStats.Inc(ref RuntimeStats.CraftingStationDormantFrames);
			}
			return false;
		}

		private static void PokePrefix(CraftingStation __instance)
		{
			if ((Object)(object)__instance != (Object)null && CanSleep)
			{
				Wake(__instance);
			}
		}

		private static void ExtensionsPrefix(CraftingStation __instance)
		{
			if ((Object)(object)__instance != (Object)null && CanSleep)
			{
				Wake(__instance);
			}
		}

		private static void Wake(CraftingStation station)
		{
			if (((Behaviour)station).enabled && ((Component)station).gameObject.activeInHierarchy && !CraftingStation.Instances.Contains((IMonoUpdater)(object)station))
			{
				CraftingStation.Instances.Add((IMonoUpdater)(object)station);
			}
			Sleepers.Remove(station);
		}

		internal static void RefreshDormancy()
		{
			if (CanSleep)
			{
				return;
			}
			Sleepers.ForEachAlive(delegate(CraftingStation s)
			{
				if (((Behaviour)s).enabled && ((Component)s).gameObject.activeInHierarchy && !CraftingStation.Instances.Contains((IMonoUpdater)(object)s))
				{
					CraftingStation.Instances.Add((IMonoUpdater)(object)s);
				}
			});
			Sleepers.Clear();
		}

		internal static void Shutdown()
		{
			Sleepers.ForEachAlive(delegate(CraftingStation s)
			{
				if (((Behaviour)s).enabled && ((Component)s).gameObject.activeInHierarchy && !CraftingStation.Instances.Contains((IMonoUpdater)(object)s))
				{
					CraftingStation.Instances.Add((IMonoUpdater)(object)s);
				}
			});
			Sleepers.Clear();
		}
	}
	internal static class CraftingStationPatches
	{
		private static PatchRuntimeGate knownGate;

		private static PatchRuntimeGate haveGate;

		private static PatchRuntimeGate findGate;

		private static PatchRuntimeGate closestGate;

		internal static void Install(PatchInstaller installer)
		{
			knownGate = installer.Install("CraftingStation.UpdateKnownStationsInRange squared-distance query", AccessTools.Method(typeof(CraftingStation), "UpdateKnownStationsInRange", new Type[1] { typeof(Player) }, (Type[])null), AccessTools.Method(typeof(CraftingStationPatches), "UpdateKnownStationsPrefix", (Type[])null, (Type[])null), null, Launch.Settings.CraftingStationSquaredDistanceQueries, requiresKnownBuild: true, strictForeignPatchCheck: true);
			haveGate = installer.Install("CraftingStation.HaveBuildStationInRange squared-distance query", AccessTools.Method(typeof(CraftingStation), "HaveBuildStationInRange", new Type[2]
			{
				typeof(string),
				typeof(Vector3)
			}, (Type[])null), AccessTools.Method(typeof(CraftingStationPatches), "HaveBuildStationPrefix", (Type[])null, (Type[])null), null, Launch.Settings.CraftingStationSquaredDistanceQueries, requiresKnownBuild: true, strictForeignPatchCheck: true);
			findGate = installer.Install("CraftingStation.FindStationsInRange squared-distance query", AccessTools.Method(typeof(CraftingStation), "FindStationsInRange", new Type[4]
			{
				typeof(string),
				typeof(Vector3),
				typeof(float),
				typeof(List<CraftingStation>)
			}, (Type[])null), AccessTools.Method(typeof(CraftingStationPatches), "FindStationsPrefix", (Type[])null, (Type[])null), null, Launch.Settings.CraftingStationSquaredDistanceQueries, requiresKnownBuild: true, strictForeignPatchCheck: true);
			closestGate = installer.Install("CraftingStation.FindClosestStationInRange squared-distance query", AccessTools.Method(typeof(CraftingStation), "FindClosestStationInRange", new Type[3]
			{
				typeof(string),
				typeof(Vector3),
				typeof(float)
			}, (Type[])null), AccessTools.Method(typeof(CraftingStationPatches), "FindClosestStationPrefix", (Type[])null, (Type[])null), null, Launch.Settings.CraftingStationSquaredDistanceQueries, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool UpdateKnownStationsPrefix(Player player)
		{
			//IL_0038: Unknown result type (might be due to invalid IL or missing references)
			//IL_003d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0077: Unknown result type (might be due to invalid IL or missing references)
			//IL_007c: Unknown result type (might be due to invalid IL or missing references)
			//IL_007d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0082: Unknown result type (might be due to invalid IL or missing references)
			List<CraftingStation> craftingStations = VanillaCollectionRegistry.CraftingStations;
			if (knownGate == null || !knownGate.Enabled || craftingStations == null || (Object)(object)player == (Object)null)
			{
				return true;
			}
			Vector3 position = ((Component)player).transform.position;
			for (int i = 0; i < craftingStations.Count; i++)
			{
				CraftingStation val = craftingStations[i];
				if ((Object)(object)val == (Object)null)
				{
					continue;
				}
				float discoverRange = val.m_discoverRange;
				if (discoverRange > 0f)
				{
					Vector3 val2 = ((Component)val).transform.position - position;
					if (((Vector3)(ref val2)).sqrMagnitude < discoverRange * discoverRange)
					{
						player.AddKnownStation(val);
					}
				}
			}
			RuntimeStats.Inc(ref RuntimeStats.CraftingQueryReplacements);
			return false;
		}

		private static bool HaveBuildStationPrefix(string name, Vector3 point, ref CraftingStation __result)
		{
			//IL_007c: Unknown result type (might be due to invalid IL or missing references)
			//IL_007d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0088: 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_00a3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00aa: Unknown result type (might be due to invalid IL or missing references)
			List<CraftingStation> craftingStations = VanillaCollectionRegistry.CraftingStations;
			if (haveGate == null || !haveGate.Enabled || craftingStations == null)
			{
				return true;
			}
			for (int i = 0; i < craftingStations.Count; i++)
			{
				CraftingStation val = craftingStations[i];
				if ((Object)(object)val == (Object)null || val.m_name != name)
				{
					continue;
				}
				float stationBuildRange = val.GetStationBuildRange();
				if (stationBuildRange > 0f)
				{
					Vector3 val2 = point;
					val2.y = ((Component)val).transform.position.y;
					Vector3 val3 = ((Component)val).transform.position - val2;
					if (((Vector3)(ref val3)).sqrMagnitude < stationBuildRange * stationBuildRange)
					{
						__result = val;
						RuntimeStats.Inc(ref RuntimeStats.CraftingQueryReplacements);
						return false;
					}
				}
			}
			__result = null;
			RuntimeStats.Inc(ref RuntimeStats.CraftingQueryReplacements);
			return false;
		}

		private static bool FindStationsPrefix(string name, Vector3 point, float range, List<CraftingStation> stations)
		{
			//IL_008a: Unknown result type (might be due to invalid IL or missing references)
			//IL_008f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0090: Unknown result type (might be due to invalid IL or missing references)
			//IL_0095: Unknown result type (might be due to invalid IL or missing references)
			List<CraftingStation> craftingStations = VanillaCollectionRegistry.CraftingStations;
			if (findGate == null || !findGate.Enabled || craftingStations == null || stations == null)
			{
				return true;
			}
			if (!(range > 0f) || float.IsNaN(range))
			{
				return false;
			}
			float num = range * range;
			for (int i = 0; i < craftingStations.Count; i++)
			{
				CraftingStation val = craftingStations[i];
				if (!((Object)(object)val == (Object)null) && !(val.m_name != name))
				{
					Vector3 val2 = ((Component)val).transform.position - point;
					if (((Vector3)(ref val2)).sqrMagnitude < num)
					{
						stations.Add(val);
					}
				}
			}
			RuntimeStats.Inc(ref RuntimeStats.CraftingQueryReplacements);
			return false;
		}

		private static bool FindClosestStationPrefix(string name, Vector3 point, float range, ref CraftingStation __result)
		{
			//IL_0097: Unknown result type (might be due to invalid IL or missing references)
			//IL_009c: Unknown result type (might be due to invalid IL or missing references)
			//IL_009d: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a2: Unknown result type (might be due to invalid IL or missing references)
			List<CraftingStation> craftingStations = VanillaCollectionRegistry.CraftingStations;
			if (closestGate == null || !closestGate.Enabled || craftingStations == null)
			{
				return true;
			}
			if (!(range > 0f) || float.IsNaN(range))
			{
				__result = null;
				return false;
			}
			float num = range * range;
			float num2 = float.PositiveInfinity;
			CraftingStation val = null;
			for (int i = 0; i < craftingStations.Count; i++)
			{
				CraftingStation val2 = craftingStations[i];
				if (!((Object)(object)val2 == (Object)null) && !(val2.m_name != name))
				{
					Vector3 val3 = ((Component)val2).transform.position - point;
					float sqrMagnitude = ((Vector3)(ref val3)).sqrMagnitude;
					if (sqrMagnitude < num && (sqrMagnitude < num2 || (Object)(object)val == (Object)null))
					{
						val = val2;
						num2 = sqrMagnitude;
					}
				}
			}
			__result = val;
			RuntimeStats.Inc(ref RuntimeStats.CraftingQueryReplacements);
			return false;
		}
	}
}
namespace BalrondVisualOptimizer.Patches.CookingStationOptimizations
{
	internal static class CookingStationPatches
	{
		private sealed class State
		{
			internal int Epoch;

			internal uint Revision = uint.MaxValue;

			internal int[] SlotKeyHashes;

			internal int[] StatusKeyHashes;

			internal string[] Items;

			internal int[] Statuses;

			internal bool HasValue;

			internal bool FireLit;

			internal bool HasFuel;

			internal float NextSafetyRefresh;
		}

		private static PatchRuntimeGate gate;

		internal static void Install(PatchInstaller installer)
		{
			gate = installer.Install("CookingStation.UpdateVisual signature gate", AccessTools.Method(typeof(CookingStation), "UpdateVisual", new Type[1] { typeof(bool) }, (Type[])null), AccessTools.Method(typeof(CookingStationPatches), "Prefix", (Type[])null, (Type[])null), null, Launch.Settings.CookingStationVisual, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool Prefix(CookingStation __instance, bool fireLit)
		{
			if (gate == null || !gate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if ((Object)(object)__instance.m_nview == (Object)null || !__instance.m_nview.IsValid() || __instance.m_slots == null)
			{
				return true;
			}
			ZDO zDO = __instance.m_nview.GetZDO();
			if (zDO == null)
			{
				return true;
			}
			State state = WeakStateStore<CookingStation, State>.Get(__instance);
			if (state.Epoch != gate.Epoch)
			{
				state.Epoch = gate.Epoch;
				state.HasValue = false;
				state.Revision = uint.MaxValue;
				state.NextSafetyRefresh = 0f;
			}
			EnsureArrays(state, __instance.m_slots.Length);
			float unscaledTime = Time.unscaledTime;
			uint dataRevision = zDO.DataRevision;
			if (state.HasValue && state.Revision == dataRevision && state.FireLit == fireLit && unscaledTime < state.NextSafetyRefresh)
			{
				RuntimeStats.Inc(ref RuntimeStats.CookingStationVisualSkips);
				return false;
			}
			bool flag = !state.HasValue || state.FireLit != fireLit;
			bool flag2 = __instance.m_useFuel && zDO.GetFloat(ZDOVars.s_fuel, 0f) > 0f;
			if (!state.HasValue || state.HasFuel != flag2)
			{
				flag = true;
			}
			for (int i = 0; i < state.Items.Length; i++)
			{
				string text = zDO.GetString(state.SlotKeyHashes[i], "");
				int num = zDO.GetInt(state.StatusKeyHashes[i], 0);
				if (!string.Equals(text, state.Items[i], StringComparison.Ordinal) || num != state.Statuses[i])
				{
					flag = true;
				}
				state.Items[i] = text;
				state.Statuses[i] = num;
			}
			state.Revision = dataRevision;
			if (!flag && unscaledTime < state.NextSafetyRefresh)
			{
				RuntimeStats.Inc(ref RuntimeStats.CookingStationVisualSkips);
				return false;
			}
			state.FireLit = fireLit;
			state.HasFuel = flag2;
			state.HasValue = true;
			state.NextSafetyRefresh = UpdateRateLimiter.StaggeredSafetyDeadline(unscaledTime, RuntimeTuning.VisualSafety, ((Object)__instance).GetInstanceID());
			return true;
		}

		private static void EnsureArrays(State state, int count)
		{
			if (state.Items == null || state.Items.Length != count)
			{
				state.SlotKeyHashes = new int[count];
				state.StatusKeyHashes = new int[count];
				state.Items = new string[count];
				state.Statuses = new int[count];
				for (int i = 0; i < count; i++)
				{
					state.SlotKeyHashes[i] = StringExtensionMethods.GetStableHashCode("slot" + i);
					state.StatusKeyHashes[i] = StringExtensionMethods.GetStableHashCode("slotstatus" + i);
				}
				state.HasValue = false;
			}
		}
	}
}
namespace BalrondVisualOptimizer.Patches.ArmorStandOptimizations
{
	internal static class ArmorStandPatches
	{
		private sealed class VisualState
		{
			internal int Epoch;

			internal uint Revision = uint.MaxValue;

			internal float NextSafetyRefresh;
		}

		private sealed class ClothState
		{
			internal int Epoch;

			internal float NextUpdate;
		}

		private static PatchRuntimeGate visualGate;

		private static PatchRuntimeGate clothGate;

		internal static void Install(PatchInstaller installer)
		{
			visualGate = installer.Install("ArmorStand.UpdateVisual revision gate", AccessTools.Method(typeof(ArmorStand), "UpdateVisual", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(ArmorStandPatches), "UpdateVisualPrefix", (Type[])null, (Type[])null), null, Launch.Settings.ArmorStandVisualRevision, requiresKnownBuild: true, strictForeignPatchCheck: true);
			clothGate = installer.Install("ArmorStand.Update publicized cloth replacement", AccessTools.Method(typeof(ArmorStand), "Update", Type.EmptyTypes, (Type[])null), AccessTools.Method(typeof(ArmorStandPatches), "UpdatePrefix", (Type[])null, (Type[])null), null, Launch.Settings.ArmorStandCloth, requiresKnownBuild: true, strictForeignPatchCheck: true);
		}

		private static bool UpdateVisualPrefix(ArmorStand __instance)
		{
			if (visualGate == null || !visualGate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if ((Object)(object)__instance.m_nview == (Object)null || !__instance.m_nview.IsValid())
			{
				return true;
			}
			ZDO zDO = __instance.m_nview.GetZDO();
			if (zDO == null)
			{
				return true;
			}
			VisualState visualState = WeakStateStore<ArmorStand, VisualState>.Get(__instance);
			if (visualState.Epoch != visualGate.Epoch)
			{
				visualState.Epoch = visualGate.Epoch;
				visualState.Revision = uint.MaxValue;
				visualState.NextSafetyRefresh = 0f;
			}
			float unscaledTime = Time.unscaledTime;
			uint dataRevision = zDO.DataRevision;
			if (dataRevision == visualState.Revision && unscaledTime < visualState.NextSafetyRefresh)
			{
				RuntimeStats.Inc(ref RuntimeStats.ArmorStandVisualSkips);
				return false;
			}
			visualState.Revision = dataRevision;
			visualState.NextSafetyRefresh = UpdateRateLimiter.StaggeredSafetyDeadline(unscaledTime, RuntimeTuning.StaticVisualSafety, ((Object)__instance).GetInstanceID());
			return true;
		}

		private static bool UpdatePrefix(ArmorStand __instance)
		{
			//IL_00ec: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f7: 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_0101: Unknown result type (might be due to invalid IL or missing references)
			if (clothGate == null || !clothGate.Enabled || (Object)(object)__instance == (Object)null)
			{
				return true;
			}
			if ((Object)(object)Player.m_localPlayer == (Object)null || __instance.m_cloths == null || __instance.m_cloths.Length == 0)
			{
				return false;
			}
			ClothState clothState = WeakStateStore<ArmorStand, ClothState>.Get(__instance);
			if (clothState.Epoch != clothGate.Epoch)
			{
				clothState.Epoch = clothGate.Epoch;
				clothState.NextUpdate = 0f;
			}
			float time = Time.time;
			if (!UpdateRateLimiter.IsDue(ref clothState.NextUpdate, RuntimeTuning.ArmorClothInterval, time, ((Object)__instance).GetInstanceID()))
			{
				RuntimeStats.Inc(ref RuntimeStats.ArmorStandClothSkips);
				return false;
			}
			float num = __instance.m_clothSimLodDistance * QualitySettings.lodBias;
			Vector3 val = ((Component)Player.m_localPlayer).transform.position - ((Component)__instance).transform.position;
			bool flag = ((Vector3)(ref val)).sqrMagnitude > num * num;
			if (__instance.m_clothLodded == flag)
			{
				return false;
			}
			__instance.m_clothLodded = flag;
			Cloth[] cloths = __instance.m_cloths;
			foreach (Cloth val2 in cloths)
			{
				if ((Object)(object)val2 != (Object)null)
				{
					val2.enabled = !flag;
				}
			}
			return false;
		}
	}
}
namespace BalrondVisualOptimizer.Core
{
	internal static class GameAssemblyGuard
	{
		internal static readonly Guid ExpectedValheimMvid = new Guid("E4CFC702-61AB-46D1-9F39-CC2DEB9BC839");

		private static readonly Guid currentValheimMvid = ResolveCurrentMvid();

		internal static Guid CurrentValheimMvid => currentValheimMvid;

		internal static bool IsExpectedBuild => currentValheimMvid == ExpectedValheimMvid;

		private static Guid ResolveCurrentMvid()
		{
			try
			{
				return typeof(ZNet).Assembly.ManifestModule.ModuleVersionId;
			}
			catch
			{
				return Guid.Empty;
			}
		}
	}
	internal static class HarmonyConflictService
	{
		internal static bool TryGetFirstForeignOwner(MethodBase target, out string owner)
		{
			owner = null;
			Patches patchInfo = GetPatchInfo(target);
			if (patchInfo == null || patchInfo.Owners == null)
			{
				return false;
			}
			foreach (string owner2 in patchInfo.Owners)
			{
				if (string.IsNullOrEmpty(owner2) || owner2 == "balrond.astafaraios.BalrondCoreOptimizer")
				{
					continue;
				}
				owner = owner2;
				return true;
			}
			return false;
		}

		internal static bool HasOwner(MethodBase target, string owner)
		{
			if (string.IsNullOrEmpty(owner))
			{
				return false;
			}
			Patches patchInfo = GetPatchInfo(target);
			if (patchInfo == null || patchInfo.Owners == null)
			{
				return false;
			}
			foreach (string owner2 in patchInfo.Owners)
			{
				if (owner2 == owner)
				{
					return true;
				}
			}
			return false;
		}

		private static Patches GetPatchInfo(MethodBase target)
		{
			return (target == null) ? null : Harmony.GetPatchInfo(target);
		}
	}
	internal sealed class PatchInstaller
	{
		private readonly Harmony harmony;

		private readonly OptimizerConfig config;

		private readonly List<PatchRuntimeGate> gates = new List<PatchRuntimeGate>();

		internal PatchInstaller(Harmony harmony, OptimizerConfig config)
		{
			this.harmony = harmony;
			this.config = config;
		}

		internal PatchRuntimeGate Install(string name, MethodBase target, MethodInfo prefix, MethodInfo postfix, ConfigEntry<bool> toggle, bool requiresKnownBuild, bool strictForeignPatchCheck)
		{
			PatchRuntimeGate patchRuntimeGate = new PatchRuntimeGate(name, target, prefix, postfix, toggle, requiresKnownBuild, strictForeignPatchCheck);
			gates.Add(patchRuntimeGate);
			if (target == null)
			{
				patchRuntimeGate.BlockPermanently("target method not found");
				Launch.LogWarning(name + " disabled: target method not found.");
				return patchRuntimeGate;
			}
			if (prefix == null && postfix == null)
			{
				patchRuntimeGate.BlockPermanently("patch method not found");
				Launch.LogWarning(name + " disabled: no prefix/postfix method was resolved.");
				return patchRuntimeGate;
			}
			if (CompatibilityPolicy.IsProtectedTarget(target, out var reason))
			{
				patchRuntimeGate.BlockPermanently(reason);
				Launch.LogWarning(name + " refused by compatibility policy: " + reason + ".");
				return patchRuntimeGate;
			}
			ReconcileGate(patchRuntimeGate, initial: true);
			return patchRuntimeGate;
		}

		internal void RefreshAll()
		{
			for (int i = 0; i < gates.Count; i++)
			{
				ReconcileGate(gates[i], initial: false);
			}
		}

		internal string BuildStatusSummary()
		{
			int num = 0;
			int num2 = 0;
			int num3 = 0;
			string text = null;
			for (int i = 0; i < gates.Count; i++)
			{
				PatchRuntimeGate patchRuntimeGate = gates[i];
				if (patchRuntimeGate.Enabled && patchRuntimeGate.Installed)
				{
					num++;
				}
				else if (patchRuntimeGate.PermanentlyBlocked)
				{
					num2++;
				}
				else
				{
					num3++;
				}
				if (text == null && !patchRuntimeGate.Enabled && !string.IsNullOrEmpty(patchRuntimeGate.DisabledReason))
				{
					text = patchRuntimeGate.Name + ": " + patchRuntimeGate.DisabledReason;
				}
			}
			string text2 = "patches active=" + num + "/" + gates.Count + ", disabled=" + num3 + ", permanently-blocked=" + num2;
			if (text != null)
			{
				text2 = text2 + ", first-disabled=[" + text + "]";
			}
			return text2;
		}

		private void ReconcileGate(PatchRuntimeGate gate, bool initial)
		{
			if (gate == null)
			{
				return;
			}
			SynchronizeObservedInstallState(gate);
			string owner;
			if (gate.PermanentlyBlocked)
			{
				EnsureUninstalled(gate, gate.PermanentBlockReason, log: false);
			}
			else if (!config.Enabled.Value)
			{
				EnsureUninstalled(gate, "master switch disabled", !initial);
			}
			else if (gate.Toggle == null || !gate.Toggle.Value)
			{
				EnsureUninstalled(gate, "feature disabled in config", !initial);
			}
			else if (gate.RequiresKnownBuild && !GameAssemblyGuard.IsExpectedBuild && !config.AllowUnknownGameBuild.Value)
			{
				EnsureUninstalled(gate, "unknown assembly_valheim MVID", !initial);
				if (initial)
				{
					Launch.LogWarning(gate.Name + " disabled: assembly_valheim MVID " + GameAssemblyGuard.CurrentValheimMvid.ToString() + " does not match audited MVID " + GameAssemblyGuard.ExpectedValheimMvid.ToString() + ".");
				}
			}
			else if (gate.StrictForeignPatchCheck && config.DisableOnForeignHarmonyPatches.Value && HarmonyConflictService.TryGetFirstForeignOwner(gate.Target, out owner))
			{
				bool installed = gate.Installed;
				EnsureUninstalled(gate, "foreign Harmony patch: " + owner, log: false);
				if (initial || installed)
				{
					Launch.LogWarning(gate.Name + " disabled because target " + Describe(gate.Target) + " is patched by " + owner + ".");
				}
			}
			else if (!gate.Installed)
			{
				TryInstall(gate);
			}
			else
			{
				gate.Set(value: true, null);
			}
		}

		private void TryInstall(PatchRuntimeGate gate)
		{
			//IL_0040: Unknown result type (might be due to invalid IL or missing references)
			//IL_005d: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				if (HarmonyConflictService.HasOwner(gate.Target, "balrond.astafaraios.BalrondCoreOptimizer"))
				{
					gate.MarkInstalled();
					gate.Set(value: true, null);
					return;
				}
				HarmonyMethod val = ((gate.Prefix == null) ? ((HarmonyMethod)null) : new HarmonyMethod(gate.Prefix));
				HarmonyMethod val2 = ((gate.Postfix == null) ? ((HarmonyMethod)null) : new HarmonyMethod(gate.Postfix));
				if (val != null)
				{
					val.priority = 0;
				}
				if (val2 != null)
				{
					val2.priority = 0;
				}
				harmony.Patch(gate.Target, val, val2, (HarmonyMethod)null, (HarmonyMethod)null, (HarmonyMethod)null);
				gate.MarkInstalled();
				gate.Set(value: true, null);
				Launch.LogInfo("Installed " + gate.Name + " -> " + Describe(gate.Targe