Decompiled source of Spawn That v1.2.15

Valheim.SpawnThat.dll

Decompiled 2 months ago
using System;
using System.Collections;
using System.Collections.Generic;
using System.ComponentModel;
using System.Diagnostics;
using System.Globalization;
using System.IO;
using System.IO.Compression;
using System.Linq;
using System.Reflection;
using System.Reflection.Emit;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading;
using System.Threading.Tasks;
using BepInEx;
using BepInEx.Configuration;
using BepInEx.Logging;
using CreatureLevelControl;
using EpicLoot;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using RagnarsRokare.MobAI;
using SpawnThat.Caches;
using SpawnThat.Configuration;
using SpawnThat.Configuration.Sync;
using SpawnThat.ConsoleCommands;
using SpawnThat.Core;
using SpawnThat.Core.Cache;
using SpawnThat.Core.Configuration;
using SpawnThat.Core.Network;
using SpawnThat.Core.Toml;
using SpawnThat.Core.Toml.Parsers;
using SpawnThat.Core.Toml.Writers;
using SpawnThat.Debugging;
using SpawnThat.Integrations;
using SpawnThat.Integrations.CLLC.Conditions;
using SpawnThat.Integrations.CLLC.Models;
using SpawnThat.Integrations.CLLC.Modifiers;
using SpawnThat.Integrations.EpicLoot.Conditions;
using SpawnThat.Integrations.EpicLoot.Models;
using SpawnThat.Integrations.MobAi.Modifiers;
using SpawnThat.Lifecycle;
using SpawnThat.Options.Conditions;
using SpawnThat.Options.Identifiers;
using SpawnThat.Options.Modifiers;
using SpawnThat.Options.PositionConditions;
using SpawnThat.Spawners;
using SpawnThat.Spawners.Contexts;
using SpawnThat.Spawners.LocalSpawner;
using SpawnThat.Spawners.LocalSpawner.Caches;
using SpawnThat.Spawners.LocalSpawner.Configuration;
using SpawnThat.Spawners.LocalSpawner.Configuration.BepInEx;
using SpawnThat.Spawners.LocalSpawner.Managers;
using SpawnThat.Spawners.LocalSpawner.Models;
using SpawnThat.Spawners.LocalSpawner.Services;
using SpawnThat.Spawners.LocalSpawner.Startup;
using SpawnThat.Spawners.LocalSpawner.Sync;
using SpawnThat.Spawners.SpawnAreaSpawner;
using SpawnThat.Spawners.SpawnAreaSpawner.Configuration;
using SpawnThat.Spawners.SpawnAreaSpawner.Configuration.BepInEx;
using SpawnThat.Spawners.SpawnAreaSpawner.Debug;
using SpawnThat.Spawners.SpawnAreaSpawner.Managers;
using SpawnThat.Spawners.SpawnAreaSpawner.Models;
using SpawnThat.Spawners.SpawnAreaSpawner.Services;
using SpawnThat.Spawners.SpawnAreaSpawner.Startup;
using SpawnThat.Spawners.SpawnAreaSpawner.Sync;
using SpawnThat.Spawners.WorldSpawner;
using SpawnThat.Spawners.WorldSpawner.Configurations;
using SpawnThat.Spawners.WorldSpawner.Configurations.BepInEx;
using SpawnThat.Spawners.WorldSpawner.Debug;
using SpawnThat.Spawners.WorldSpawner.Managers;
using SpawnThat.Spawners.WorldSpawner.Services;
using SpawnThat.Spawners.WorldSpawner.Startup;
using SpawnThat.Spawners.WorldSpawner.Sync;
using SpawnThat.Utilities;
using SpawnThat.Utilities.Enums;
using SpawnThat.Utilities.Extensions;
using SpawnThat.Utilities.Spatial;
using SpawnThat.World.Dungeons;
using SpawnThat.World.Locations;
using SpawnThat.World.Maps;
using SpawnThat.World.Maps.Area;
using SpawnThat.World.Queries;
using SpawnThat.World.Zone;
using UnityEngine;
using YamlDotNet.Core;
using YamlDotNet.Core.Events;
using YamlDotNet.Serialization;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: InternalsVisibleTo("SpawnThat.Tests")]
[assembly: TargetFramework(".NETFramework,Version=v4.8", FrameworkDisplayName = ".NET Framework 4.8")]
[assembly: AssemblyCompany("A Sharp Pen")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyDescription("Valheim mod and tool for configuring spawners.")]
[assembly: AssemblyFileVersion("1.2.15.0")]
[assembly: AssemblyInformationalVersion("1.2.15+3ad8093f58e4fa30b30f11375af5f9de730be68f")]
[assembly: AssemblyProduct("Valheim.SpawnThat")]
[assembly: AssemblyTitle("Valheim.SpawnThat")]
[assembly: AssemblyMetadata("RepositoryUrl", "https://github.com/ASharpPen/Valheim.SpawnThat")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("1.2.15.0")]
[module: UnverifiableCode]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	internal sealed class EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	[AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)]
	internal sealed class RefSafetyRulesAttribute : Attribute
	{
		public readonly int Version;

		public RefSafetyRulesAttribute(int P_0)
		{
			Version = P_0;
		}
	}
}
namespace SpawnThat
{
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	[BepInPlugin("asharppen.valheim.spawn_that", "Spawn That!", "1.2.15")]
	public class SpawnThatPlugin : BaseUnityPlugin
	{
		public const string ModId = "asharppen.valheim.spawn_that";

		public const string PluginName = "Spawn That!";

		public const string Version = "1.2.15";

		private void Awake()
		{
			//IL_0035: Unknown result type (might be due to invalid IL or missing references)
			Log.Logger = ((BaseUnityPlugin)this).Logger;
			ConfigurationManager.GeneralConfig = ConfigurationManager.LoadGeneral();
			Startup.SetupServices();
			if ((object)Type.GetType("YamlDotNet.Serialization.SerializerBuilder, YamlDotNet") == null)
			{
				Log.LogWarning("Unable to detect required YamlDotNet type. Verify that YamlDotNet.dll is installed.");
			}
			new Harmony("asharppen.valheim.spawn_that").PatchAll();
		}
	}
	internal static class Startup
	{
		public static void SetupServices()
		{
			GeneralConfigurationSetup.SetupMainConfiguration();
			LocalSpawnerSetup.SetupLocalSpawners();
			WorldSpawnerSetup.SetupWorldSpawners();
			SpawnAreaSpawnerSetup.SetupSpawnAreaSpawners();
			LifecycleManager.OnLateInit += InitConfiguration;
			ZoneSystemSyncSetup.Configure();
			RegisterCommands();
		}

		private static void InitConfiguration()
		{
			if (LifecycleManager.GameState == GameState.Singleplayer || LifecycleManager.GameState == GameState.DedicatedServer)
			{
				SpawnerConfigurationManager.BuildConfigurations();
			}
		}

		private static void RegisterCommands()
		{
			AreaCommand.Register();
			AreaRollCommand.Register();
			AreaRollHeatmapCommand.Register();
			RoomCommand.Register();
			WhereDoesItSpawnCommand.Register();
		}
	}
}
namespace SpawnThat.World
{
	internal class ZoneHeightmap : IZone
	{
		private Heightmap Heightmap { get; }

		public int Width { get; }

		public Biome Biome { get; }

		public Vector2i ZoneId { get; }

		public Vector3 ZonePos { get; }

		public Biome[] BiomeCorners { get; }

		public BiomeArea BiomeArea { get; }

		public ZoneHeightmap(Heightmap heightmap)
		{
			//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_0020: Unknown result type (might be due to invalid IL or missing references)
			//IL_0025: Unknown result type (might be due to invalid IL or missing references)
			//IL_002a: Unknown result type (might be due to invalid IL or missing references)
			//IL_003e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0049: 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_0066: Unknown result type (might be due to invalid IL or missing references)
			//IL_006b: Unknown result type (might be due to invalid IL or missing references)
			Heightmap = heightmap;
			ZonePos = ((Component)heightmap).transform.position;
			ZoneId = ZonePos.GetZoneId();
			Width = heightmap.m_width;
			Biome = heightmap.GetBiome(ZonePos, 0.02f, false);
			BiomeCorners = heightmap.m_cornerBiomes.ToArray();
			BiomeArea = heightmap.GetBiomeArea();
		}

		public bool HasBiome(Biome biome)
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			return Heightmap.HaveBiome(biome);
		}

		public Biome GetBiome(Vector3 pos)
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_000d: Unknown result type (might be due to invalid IL or missing references)
			return Heightmap.GetBiome(pos, 0.02f, false);
		}

		public float Height(Vector3 worldCoordinate)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			float result = default(float);
			Heightmap.GetHeight(worldCoordinate, ref result);
			return result;
		}

		public float Height(Vector2i zoneLocalCoordinate)
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_000c: Unknown result type (might be due to invalid IL or missing references)
			return Heightmap.GetHeight(zoneLocalCoordinate.x, zoneLocalCoordinate.y);
		}

		public float OceanDepth(Vector3 worldCoordinate)
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			return Heightmap.GetOceanDepth(worldCoordinate);
		}

		public float OceanDepth(Vector2i zoneLocalCoordinate)
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_000c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0012: Unknown result type (might be due to invalid IL or missing references)
			//IL_0017: Unknown result type (might be due to invalid IL or missing references)
			//IL_0019: Unknown result type (might be due to invalid IL or missing references)
			Vector3 worldCoordinate = Heightmap.CalcVertex(zoneLocalCoordinate.x, zoneLocalCoordinate.y);
			return OceanDepth(worldCoordinate);
		}

		public float Tilt(Vector3 worldCoordinate)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_000b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0010: Unknown result type (might be due to invalid IL or missing references)
			//IL_0015: Unknown result type (might be due to invalid IL or missing references)
			//IL_0034: Unknown result type (might be due to invalid IL or missing references)
			//IL_0039: Unknown result type (might be due to invalid IL or missing references)
			//IL_003f: Unknown result type (might be due to invalid IL or missing references)
			RaycastHit val = default(RaycastHit);
			if (Physics.Raycast(worldCoordinate + Vector3.up * 5000f, Vector3.down, ref val, 10000f, ZoneSystem.instance.m_terrainRayMask))
			{
				Vector3 normal = ((RaycastHit)(ref val)).normal;
				return 90f - Mathf.Asin(normal.y) * 57.29578f;
			}
			return 0f;
		}

		public Vector2i WorldToZoneCoordinate(Vector3 worldCoordinate)
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_0012: Unknown result type (might be due to invalid IL or missing references)
			int num = default(int);
			int num2 = default(int);
			Heightmap.WorldToVertex(worldCoordinate, ref num, ref num2);
			return new Vector2i(num, num2);
		}
	}
	internal class ZoneSimulated : IZone
	{
		private BiomeArea? _biomeArea;

		private float[] _oceanDepthCorners;

		public int Width { get; } = 64;


		public Biome Biome { get; }

		public Vector2i ZoneId { get; }

		public Vector3 ZonePos { get; }

		public Biome[] BiomeCorners { get; }

		public BiomeArea BiomeArea
		{
			get
			{
				//IL_0006: Unknown result type (might be due to invalid IL or missing references)
				//IL_000b: 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_0036: Unknown result type (might be due to invalid IL or missing references)
				//IL_0038: Unknown result type (might be due to invalid IL or missing references)
				//IL_0043: Unknown result type (might be due to invalid IL or missing references)
				BiomeArea valueOrDefault = _biomeArea.GetValueOrDefault();
				if (!_biomeArea.HasValue)
				{
					valueOrDefault = (BiomeArea)((!BiomeCorners.All((Biome x) => (int)BiomeCorners[0] == (int)x)) ? 1 : 2);
					_biomeArea = valueOrDefault;
					return valueOrDefault;
				}
				return valueOrDefault;
			}
		}

		private float[] OceanDepthCorners => _oceanDepthCorners ?? (_oceanDepthCorners = CalculateOceanDepths());

		private static Vector2i North { get; } = new Vector2i(0, 1);


		private static Vector2i South { get; } = new Vector2i(0, -1);


		private static Vector2i West { get; } = new Vector2i(-1, 0);


		private static Vector2i East { get; } = new Vector2i(1, 0);


		public ZoneSimulated(Vector2i zoneId)
		{
			//IL_000f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0010: Unknown result type (might be due to invalid IL or missing references)
			//IL_0035: Unknown result type (might be due to invalid IL or missing references)
			//IL_0048: Unknown result type (might be due to invalid IL or missing references)
			//IL_0056: Unknown result type (might be due to invalid IL or missing references)
			//IL_005b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0023: Unknown result type (might be due to invalid IL or missing references)
			//IL_0028: Unknown result type (might be due to invalid IL or missing references)
			//IL_002d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0063: Unknown result type (might be due to invalid IL or missing references)
			//IL_007a: Unknown result type (might be due to invalid IL or missing references)
			//IL_007b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0084: Invalid comparison between Unknown and I4
			//IL_00a7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ac: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b1: Unknown result type (might be due to invalid IL or missing references)
			//IL_0086: Unknown result type (might be due to invalid IL or missing references)
			//IL_008f: Invalid comparison between Unknown and I4
			//IL_0091: Unknown result type (might be due to invalid IL or missing references)
			//IL_009a: Invalid comparison between Unknown and I4
			//IL_009d: 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)
			ZoneId = zoneId;
			if (((Object)(object)ZoneSystem.instance).IsNotNull())
			{
				ZonePos = ZoneSystem.GetZonePos(ZoneId);
			}
			else
			{
				ZonePos = new Vector3((float)(zoneId.x * Width), 0f, (float)(zoneId.y * Width));
			}
			BiomeCorners = CalculateCornerBiomes(ZonePos);
			Biome val = BiomeCorners[0];
			if ((int)val == (int)BiomeCorners[1] && (int)val == (int)BiomeCorners[2] && (int)val == (int)BiomeCorners[3])
			{
				Biome = val;
			}
			else
			{
				Biome = GetBiome(ZonePos);
			}
		}

		public bool HasBiome(Biome biome)
		{
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_0008: Unknown result type (might be due to invalid IL or missing references)
			return BiomeCorners.Any((Biome x) => (x & biome) > 0);
		}

		public Vector2i WorldToZoneCoordinate(Vector3 worldCoordinate)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_000c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0043: Unknown result type (might be due to invalid IL or missing references)
			Vector3 val = worldCoordinate - ZonePos;
			int num = Mathf.FloorToInt(val.x + 0.5f) + Width / 2;
			int num2 = Mathf.FloorToInt(val.z + 0.5f) + Width / 2;
			return new Vector2i(num, num2);
		}

		public float Height(Vector3 worldCoordinate)
		{
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Unknown result type (might be due to invalid IL or missing references)
			return Height(WorldToZoneCoordinate(worldCoordinate));
		}

		public float Height(Vector2i zoneLocalCoordinate)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_000f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0033: Unknown result type (might be due to invalid IL or missing references)
			//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_0095: 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)
			//IL_00a1: Invalid comparison between Unknown and I4
			//IL_00d0: 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_00ad: Invalid comparison between Unknown and I4
			//IL_00af: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b9: Invalid comparison between Unknown and I4
			//IL_00bd: Unknown result type (might be due to invalid IL or missing references)
			int y = zoneLocalCoordinate.y;
			int x = zoneLocalCoordinate.x;
			Vector3 val = ZonePos + new Vector3((float)Width * -0.5f, 0f, (float)Width * -0.5f);
			float num = val.z + (float)y;
			float num2 = Mathf.SmoothStep(0f, 1f, (float)y / (float)Width);
			float num3 = val.x + (float)x;
			float num4 = Mathf.SmoothStep(0f, 1f, (float)x / (float)Width);
			WorldGenerator instance = WorldGenerator.instance;
			Biome val2 = BiomeCorners[0];
			Color val3 = default(Color);
			if ((int)val2 == (int)BiomeCorners[1] && (int)val2 == (int)BiomeCorners[2] && (int)val2 == (int)BiomeCorners[3])
			{
				return instance.GetBiomeHeight(val2, num3, num, ref val3, false);
			}
			float biomeHeight = instance.GetBiomeHeight(val2, num3, num, ref val3, false);
			float biomeHeight2 = instance.GetBiomeHeight(BiomeCorners[1], num3, num, ref val3, false);
			float biomeHeight3 = instance.GetBiomeHeight(BiomeCorners[2], num3, num, ref val3, false);
			float biomeHeight4 = instance.GetBiomeHeight(BiomeCorners[3], num3, num, ref val3, false);
			float num5 = Mathf.Lerp(biomeHeight, biomeHeight2, num4);
			float num6 = Mathf.Lerp(biomeHeight3, biomeHeight4, num4);
			return Mathf.Lerp(num5, num6, num2);
		}

		public float OceanDepth(Vector3 worldCoordinate)
		{
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Unknown result type (might be due to invalid IL or missing references)
			return OceanDepth(WorldToZoneCoordinate(worldCoordinate));
		}

		public float OceanDepth(Vector2i zoneLocalCoordinate)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0010: Unknown result type (might be due to invalid IL or missing references)
			float num = (float)zoneLocalCoordinate.x / (float)Width;
			float num2 = (float)zoneLocalCoordinate.y / (float)Width;
			float num3 = Mathf.Lerp(OceanDepthCorners[3], OceanDepthCorners[2], num);
			float num4 = Mathf.Lerp(OceanDepthCorners[0], OceanDepthCorners[1], num);
			return Mathf.Lerp(num3, num4, num2);
		}

		private Biome[] CalculateCornerBiomes(Vector3 pos)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0020: Unknown result type (might be due to invalid IL or missing references)
			//IL_0025: Unknown result type (might be due to invalid IL or missing references)
			//IL_002a: Unknown result type (might be due to invalid IL or missing references)
			//IL_003a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0040: Unknown result type (might be due to invalid IL or missing references)
			//IL_004c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0052: Expected I4, but got Unknown
			//IL_0055: Unknown result type (might be due to invalid IL or missing references)
			//IL_0063: Unknown result type (might be due to invalid IL or missing references)
			//IL_006f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0075: Expected I4, but got Unknown
			//IL_0078: Unknown result type (might be due to invalid IL or missing references)
			//IL_007e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0092: Unknown result type (might be due to invalid IL or missing references)
			//IL_0098: Expected I4, but got Unknown
			//IL_009b: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00bd: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c3: Expected I4, but got Unknown
			Vector3 val = pos + new Vector3((float)Width * -0.5f, 0f, (float)Width * -0.5f);
			WorldGenerator instance = WorldGenerator.instance;
			return (Biome[])(object)new Biome[4]
			{
				(Biome)(int)instance.GetBiome(val.x, val.z, 0.02f, false),
				(Biome)(int)instance.GetBiome(val.x + (float)Width, val.z, 0.02f, false),
				(Biome)(int)instance.GetBiome(val.x, val.z + (float)Width, 0.02f, false),
				(Biome)(int)instance.GetBiome(val.x + (float)Width, val.z + (float)Width, 0.02f, false)
			};
		}

		private float[] CalculateOceanDepths()
		{
			//IL_0034: Unknown result type (might be due to invalid IL or missing references)
			//IL_005a: Unknown result type (might be due to invalid IL or missing references)
			//IL_007b: 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)
			float[] array = new float[4];
			float num = (Object.op_Implicit((Object)(object)ZoneSystem.instance) ? ZoneSystem.instance.m_waterLevel : 30f);
			array[0] = Mathf.Max(0f, num - this.Height(new Vector2i(0, Width)));
			array[1] = Mathf.Max(0f, num - this.Height(new Vector2i(Width, Width)));
			array[2] = Mathf.Max(0f, num - this.Height(new Vector2i(Width, 0)));
			array[3] = Mathf.Max(0f, num - this.Height(new Vector2i(0, 0)));
			return array;
		}

		public float Tilt(Vector3 worldCoordinate)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_0008: Unknown result type (might be due to invalid IL or missing references)
			//IL_0009: Unknown result type (might be due to invalid IL or missing references)
			//IL_000e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0013: Unknown result type (might be due to invalid IL or missing references)
			//IL_0014: Unknown result type (might be due to invalid IL or missing references)
			//IL_0015: Unknown result type (might be due to invalid IL or missing references)
			//IL_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_0020: Unknown result type (might be due to invalid IL or missing references)
			//IL_0021: Unknown result type (might be due to invalid IL or missing references)
			//IL_0026: Unknown result type (might be due to invalid IL or missing references)
			//IL_002b: Unknown result type (might be due to invalid IL or missing references)
			//IL_002c: Unknown result type (might be due to invalid IL or missing references)
			//IL_002d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0032: 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_003a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0043: Unknown result type (might be due to invalid IL or missing references)
			//IL_004c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0055: Unknown result type (might be due to invalid IL or missing references)
			//IL_005e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0069: Unknown result type (might be due to invalid IL or missing references)
			//IL_0079: Unknown result type (might be due to invalid IL or missing references)
			//IL_008b: Unknown result type (might be due to invalid IL or missing references)
			//IL_009b: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ad: Unknown result type (might be due to invalid IL or missing references)
			//IL_00bd: Unknown result type (might be due to invalid IL or missing references)
			//IL_00cf: Unknown result type (might be due to invalid IL or missing references)
			//IL_00df: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f6: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fa: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ff: Unknown result type (might be due to invalid IL or missing references)
			//IL_0103: Unknown result type (might be due to invalid IL or missing references)
			//IL_0108: Unknown result type (might be due to invalid IL or missing references)
			//IL_010c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0111: Unknown result type (might be due to invalid IL or missing references)
			//IL_0113: Unknown result type (might be due to invalid IL or missing references)
			//IL_0115: Unknown result type (might be due to invalid IL or missing references)
			//IL_011c: Unknown result type (might be due to invalid IL or missing references)
			//IL_011e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0127: Unknown result type (might be due to invalid IL or missing references)
			//IL_0129: Unknown result type (might be due to invalid IL or missing references)
			//IL_0132: Unknown result type (might be due to invalid IL or missing references)
			//IL_0134: Unknown result type (might be due to invalid IL or missing references)
			Vector2i val = WorldToZoneCoordinate(worldCoordinate);
			Vector2i zoneLocalCoordinate = val + North;
			Vector2i zoneLocalCoordinate2 = val + South;
			Vector2i zoneLocalCoordinate3 = val + West;
			Vector2i zoneLocalCoordinate4 = val + East;
			float num = Height(val);
			float num2 = Height(zoneLocalCoordinate);
			float num3 = Height(zoneLocalCoordinate2);
			float num4 = Height(zoneLocalCoordinate3);
			float num5 = Height(zoneLocalCoordinate4);
			Vector3 normalized = default(Vector3);
			((Vector3)(ref normalized))..ctor((float)North.x, num2 - num, (float)North.y);
			Vector3 normalized2 = default(Vector3);
			((Vector3)(ref normalized2))..ctor((float)South.x, num3 - num, (float)South.y);
			Vector3 normalized3 = default(Vector3);
			((Vector3)(ref normalized3))..ctor((float)West.x, num4 - num, (float)West.y);
			Vector3 normalized4 = default(Vector3);
			((Vector3)(ref normalized4))..ctor((float)East.x, num5 - num, (float)East.y);
			normalized = ((Vector3)(ref normalized)).normalized;
			normalized2 = ((Vector3)(ref normalized2)).normalized;
			normalized3 = ((Vector3)(ref normalized3)).normalized;
			normalized4 = ((Vector3)(ref normalized4)).normalized;
			float num6 = AngleByCross(normalized, normalized4);
			float num7 = AngleByCross(normalized4, normalized2);
			float num8 = AngleByCross(normalized2, normalized3);
			float num9 = AngleByCross(normalized3, normalized);
			return (num6 + num8 + num9 + num7) / 4f;
			static float AngleByCross(Vector3 p1, Vector3 p2)
			{
				//IL_0000: Unknown result type (might be due to invalid IL or missing references)
				//IL_0001: Unknown result type (might be due to invalid IL or missing references)
				//IL_0002: Unknown result type (might be due to invalid IL or missing references)
				//IL_0007: Unknown result type (might be due to invalid IL or missing references)
				//IL_0008: Unknown result type (might be due to invalid IL or missing references)
				//IL_000d: Unknown result type (might be due to invalid IL or missing references)
				//IL_0012: Unknown result type (might be due to invalid IL or missing references)
				Vector3 val2 = Vector3.Cross(p1, p2);
				return Mathf.Abs(Vector3.Angle(Vector2.op_Implicit(Vector2.up), val2));
			}
		}

		public Biome GetBiome(Vector3 pos)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c2: Unknown result type (might be due to invalid IL or missing references)
			(float x, float z) tuple = WorldCoordToNormalizedZoneCoord(pos);
			float item = tuple.x;
			float item2 = tuple.z;
			Dictionary<Biome, float> dictionary = new Dictionary<Biome, float>(4);
			AddWeight(dictionary, BiomeCorners[0], Distance(item, item2, 0f, 0f));
			AddWeight(dictionary, BiomeCorners[1], Distance(item, item2, 1f, 0f));
			AddWeight(dictionary, BiomeCorners[2], Distance(item, item2, 0f, 1f));
			AddWeight(dictionary, BiomeCorners[3], Distance(item, item2, 1f, 1f));
			return dictionary.OrderBy((KeyValuePair<Biome, float> v) => v.Value).First().Key;
			static void AddWeight(Dictionary<Biome, float> weights, Biome key, float weight)
			{
				//IL_0001: Unknown result type (might be due to invalid IL or missing references)
				//IL_0017: Unknown result type (might be due to invalid IL or missing references)
				//IL_000c: Unknown result type (might be due to invalid IL or missing references)
				if (weights.TryGetValue(key, out var value))
				{
					weights[key] = value + weight;
				}
				else
				{
					weights[key] = weight;
				}
			}
			static float Distance(float x1, float z1, float x2, float z2)
			{
				float num = x1 - x2;
				float num2 = z1 - z2;
				return Mathf.Sqrt(num * num + num2 * num2);
			}
		}

		private (float x, float z) WorldCoordToNormalizedZoneCoord(Vector3 pos)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_000c: Unknown result type (might be due to invalid IL or missing references)
			Vector3 val = pos - ZonePos;
			float item = val.x / (float)Width + 0.5f;
			float item2 = val.z / (float)Width + 0.5f;
			return (item, item2);
		}
	}
}
namespace SpawnThat.World.Zone
{
	public interface IZone
	{
		int Width { get; }

		Biome Biome { get; }

		Vector2i ZoneId { get; }

		Vector3 ZonePos { get; }

		Biome[] BiomeCorners { get; }

		BiomeArea BiomeArea { get; }

		bool HasBiome(Biome biome);

		Biome GetBiome(Vector3 pos);

		Vector2i WorldToZoneCoordinate(Vector3 worldCoordinate);

		float Height(Vector3 worldCoordinate);

		float Height(Vector2i zoneLocalCoordinate);

		float OceanDepth(Vector3 worldCoordinate);

		float OceanDepth(Vector2i zoneLocalCoordinate);

		float Tilt(Vector3 worldCoordinate);
	}
	public static class ZoneManager
	{
		[HarmonyPatch]
		private static class PatchHeightmap
		{
			[HarmonyPatch(typeof(Heightmap), "Regenerate")]
			[HarmonyPostfix]
			private static void Record(Heightmap __instance)
			{
				//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_001e: Unknown result type (might be due to invalid IL or missing references)
				//IL_0024: Unknown result type (might be due to invalid IL or missing references)
				if (__instance.m_isDistantLod)
				{
					Vector2i zoneId = ((Component)__instance).gameObject.transform.position.GetZoneId();
					HeightmapsLoaded[zoneId] = new ZoneHeightmap(__instance);
				}
			}

			[HarmonyPatch(typeof(Heightmap), "OnDestroy")]
			[HarmonyPostfix]
			private static void RemoveRecord(Heightmap __instance)
			{
				//IL_000b: Unknown result type (might be due to invalid IL or missing references)
				//IL_0010: Unknown result type (might be due to invalid IL or missing references)
				//IL_0015: Unknown result type (might be due to invalid IL or missing references)
				//IL_001b: Unknown result type (might be due to invalid IL or missing references)
				Vector2i zoneId = ((Component)__instance).gameObject.transform.position.GetZoneId();
				HeightmapsLoaded.Remove(zoneId);
			}
		}

		private static Dictionary<Vector2i, ZoneHeightmap> HeightmapsLoaded;

		private static Dictionary<Vector2i, ZoneSimulated> SimulatedCache;

		static ZoneManager()
		{
			HeightmapsLoaded = new Dictionary<Vector2i, ZoneHeightmap>();
			SimulatedCache = new Dictionary<Vector2i, ZoneSimulated>();
			LifecycleManager.SubscribeToWorldInit(delegate
			{
				HeightmapsLoaded = new Dictionary<Vector2i, ZoneHeightmap>();
				SimulatedCache = new Dictionary<Vector2i, ZoneSimulated>();
			});
		}

		public static IZone GetZone(Vector2i zoneId)
		{
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_0016: Unknown result type (might be due to invalid IL or missing references)
			//IL_0027: Unknown result type (might be due to invalid IL or missing references)
			//IL_0028: Unknown result type (might be due to invalid IL or missing references)
			if (HeightmapsLoaded.TryGetValue(zoneId, out var value))
			{
				return value;
			}
			if (SimulatedCache.TryGetValue(zoneId, out var value2))
			{
				return value2;
			}
			return SimulatedCache[zoneId] = new ZoneSimulated(zoneId);
		}
	}
	public static class ZoneUtils
	{
		public static List<Vector2i> GetZonesInSquare(int minX, int minZ, int maxX, int maxZ)
		{
			//IL_002f: Unknown result type (might be due to invalid IL or missing references)
			List<Vector2i> list = new List<Vector2i>();
			int num = Zonify(minX);
			int num2 = Zonify(maxX);
			int num3 = Zonify(minZ);
			int num4 = Zonify(maxZ);
			for (int i = num; i <= num2; i++)
			{
				for (int j = num3; j <= num4; j++)
				{
					list.Add(new Vector2i(i, j));
				}
			}
			return list;
		}

		public static Vector2i GetZone(Vector3 pos)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			return ZoneSystem.GetZone(pos);
		}

		public static Vector2i GetZone(int x, int z)
		{
			//IL_000c: Unknown result type (might be due to invalid IL or missing references)
			return new Vector2i(Zonify(x), Zonify(z));
		}

		public static int GetZoneIndex(Vector2i zone)
		{
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			return ZDOMan.instance.SectorToIndex(zone);
		}

		public static int Zonify(int coordinate)
		{
			return Mathf.FloorToInt((float)(coordinate + 32) / 64f);
		}
	}
}
namespace SpawnThat.World.Queries
{
	public abstract class BaseZdoQuery
	{
		private bool initialized;

		protected Vector3 Center { get; }

		protected int Range { get; }

		protected List<Vector2i> ZoneIds { get; private set; }

		protected List<ZDO> Zdos { get; private set; }

		protected int MinX { get; private set; }

		protected int MinZ { get; private set; }

		protected int MaxX { get; private set; }

		protected int MaxZ { get; private set; }

		protected BaseZdoQuery(Vector3 center, int range)
		{
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_0008: Unknown result type (might be due to invalid IL or missing references)
			Center = center;
			Range = range;
			Initialize();
		}

		protected virtual void Initialize()
		{
			//IL_000a: Unknown result type (might be due to invalid IL or missing references)
			//IL_003a: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ac: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b2: Unknown result type (might be due to invalid IL or missing references)
			if (initialized)
			{
				return;
			}
			(int, int) range = GetRange((int)Center.x, Range);
			MinX = range.Item1;
			MaxX = range.Item2;
			range = GetRange((int)Center.z, Range);
			MinZ = range.Item1;
			MaxZ = range.Item2;
			ZoneIds = ZoneUtils.GetZonesInSquare(MinX, MinZ, MaxX, MaxZ);
			Zdos = new List<ZDO>();
			foreach (Vector2i zoneId in ZoneIds)
			{
				ZDOMan.instance.FindObjects(zoneId, Zdos);
			}
			initialized = true;
		}

		protected static (int min, int max) GetRange(int center, int range)
		{
			return (center - range, center + range);
		}

		protected bool IsWithinRangeManhattan(ZDO zdo)
		{
			if (zdo.m_position.x < (float)MinX || zdo.m_position.x > (float)MaxX)
			{
				return false;
			}
			if (zdo.m_position.z < (float)MinZ || zdo.m_position.z > (float)MaxZ)
			{
				return false;
			}
			return true;
		}

		protected bool IsWithinRange(ZDO zdo)
		{
			//IL_0055: Unknown result type (might be due to invalid IL or missing references)
			//IL_005b: Unknown result type (might be due to invalid IL or missing references)
			if (zdo.m_position.x < (float)MinX || zdo.m_position.x > (float)MaxX)
			{
				return false;
			}
			if (zdo.m_position.z < (float)MinZ || zdo.m_position.z > (float)MaxZ)
			{
				return false;
			}
			return zdo.m_position.WithinHorizontalDistance(Center, Range);
		}
	}
	public class ZdoPrefabQuery : BaseZdoQuery
	{
		private Dictionary<int, int> CachedPrefabResults = new Dictionary<int, int>();

		public ZdoPrefabQuery(Vector3 center, int range)
			: base(center, range)
		{
		}//IL_000c: Unknown result type (might be due to invalid IL or missing references)


		public int CountEntities(int prefabHash, Predicate<ZDO> condition = null)
		{
			Initialize();
			if (CachedPrefabResults.TryGetValue(prefabHash, out var value))
			{
				return value;
			}
			int num = 0;
			num = ((condition != null) ? base.Zdos.Count((ZDO x) => IsWithinRange(x, prefabHash) && condition(x)) : base.Zdos.Count((ZDO x) => IsWithinRange(x, prefabHash)));
			CachedPrefabResults[prefabHash] = num;
			return num;
		}

		public bool HasAny(int prefabHash)
		{
			Initialize();
			if (CachedPrefabResults.TryGetValue(prefabHash, out var value))
			{
				return value > 0;
			}
			return base.Zdos.Any((ZDO x) => IsWithinRange(x, prefabHash));
		}

		private bool IsWithinRange(ZDO zdo, int prefabId)
		{
			if (zdo.m_prefab != prefabId)
			{
				return false;
			}
			return IsWithinRange(zdo);
		}
	}
}
namespace SpawnThat.World.Maps
{
	public static class MapManager
	{
		internal static AreaMap AreaMap { get; set; }

		private static int Seed { get; set; }

		public static void Initialize()
		{
			Seed = WorldGenerator.instance.GetSeed();
			AreaMap = AreaMapBuilder.BiomeMap(10500).CompileMap();
		}

		public static int GetAreaId(Vector3 position)
		{
			//IL_0010: 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)
			int num = Math.Min(AreaMap.MapWidth, Math.Max(0, AreaMap.CoordinateToIndex((int)position.x)));
			int num2 = Math.Min(AreaMap.MapWidth, Math.Max(0, AreaMap.CoordinateToIndex((int)position.z)));
			return AreaMap.AreaIds[num][num2];
		}

		public static float GetAreaChance(Vector3 position, int modifier = 0)
		{
			//IL_0010: 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)
			int num = Math.Min(AreaMap.MapWidth, Math.Max(0, AreaMap.CoordinateToIndex((int)position.x)));
			int num2 = Math.Min(AreaMap.MapWidth, Math.Max(0, AreaMap.CoordinateToIndex((int)position.z)));
			return (float)new Random(AreaMap.AreaIds[num][num2] + Seed + modifier).NextDouble();
		}

		public static float[][] GetTemplateAreaChanceMap(int templateIndex, int scaling = 1)
		{
			float[][] array = new float[AreaMap.MapWidth][];
			Dictionary<int, float> dictionary = new Dictionary<int, float>();
			for (int i = 0; i < AreaMap.MapWidth; i++)
			{
				array[i] = new float[AreaMap.MapWidth];
				for (int j = 0; j < AreaMap.MapWidth; j++)
				{
					int num = AreaMap.AreaIds[i][j];
					if (dictionary.ContainsKey(num))
					{
						array[i][j] = dictionary[num];
						continue;
					}
					Random random = new Random(num + Seed + templateIndex);
					dictionary[num] = (float)random.NextDouble() * (float)scaling;
				}
			}
			return array;
		}
	}
}
namespace SpawnThat.World.Maps.Patches
{
	[HarmonyPatch(typeof(Game))]
	internal class Patch_Game_FindSpawnPoint_PrintMaps
	{
		private static bool FirstTime;

		static Patch_Game_FindSpawnPoint_PrintMaps()
		{
			FirstTime = true;
			LifecycleManager.SubscribeToWorldInit(delegate
			{
				FirstTime = true;
			});
		}

		[HarmonyPatch("FindSpawnPoint")]
		[HarmonyPostfix]
		private static void PrintMaps()
		{
			try
			{
				if (!FirstTime)
				{
					return;
				}
				FirstTime = false;
				GeneralConfiguration generalConfig = ConfigurationManager.GeneralConfig;
				if (generalConfig != null && generalConfig.PrintAreaMap?.Value == true)
				{
					ImageBuilder.SetIds(MapManager.AreaMap).Print("area_ids_map");
				}
				GeneralConfiguration generalConfig2 = ConfigurationManager.GeneralConfig;
				if (generalConfig2 != null && generalConfig2.PrintBiomeMap?.Value == true)
				{
					ImageBuilder.SetBiomes(MapManager.AreaMap).Print("biome_map");
				}
				GeneralConfiguration generalConfig3 = ConfigurationManager.GeneralConfig;
				if (generalConfig3 == null || generalConfig3.PrintFantasticBeastsAndWhereToKillThem?.Value != true)
				{
					return;
				}
				foreach (var template in WorldSpawnTemplateManager.GetTemplates())
				{
					if (template.template.Enabled)
					{
						int[][] mapOfTemplatesActiveAreas = WorldSpawnerSpawnMapService.GetMapOfTemplatesActiveAreas(template.id);
						if (mapOfTemplatesActiveAreas != null)
						{
							ImageBuilder.SetGrayscaleBiomes(MapManager.AreaMap).AddHeatZones(mapOfTemplatesActiveAreas).Print($"spawn_map_{template.id}_{template.template.PrefabName ?? template.template.TemplateName ?? string.Empty}");
						}
					}
				}
			}
			catch (Exception e)
			{
				Log.LogWarning("Error while attempting to print spawn area maps. Skipping map printing.", e);
			}
		}
	}
	[HarmonyPatch(typeof(ZNet))]
	internal static class Patch_ZNet_Awake_ScanWorld
	{
		[HarmonyPatch("Awake")]
		[HarmonyPostfix]
		private static void ScanWorld()
		{
			if (WorldGenerator.instance != null)
			{
				Log.LogDebug("Scanning map for biomes..");
				DateTimeOffset utcNow = DateTimeOffset.UtcNow;
				MapManager.Initialize();
				DateTimeOffset utcNow2 = DateTimeOffset.UtcNow;
				Log.LogDebug("Scanning map and assigning id's to areas took: " + (utcNow2 - utcNow));
			}
		}

		[HarmonyPatch("RPC_PeerInfo")]
		[HarmonyPostfix]
		private static void ScanJoinedWorld()
		{
			if (WorldGenerator.instance != null)
			{
				Log.LogDebug("Scanning map for biomes..");
				DateTimeOffset utcNow = DateTimeOffset.UtcNow;
				MapManager.Initialize();
				DateTimeOffset utcNow2 = DateTimeOffset.UtcNow;
				Log.LogDebug("Scanning map and assigning id's to areas took: " + (utcNow2 - utcNow));
			}
		}
	}
}
namespace SpawnThat.World.Maps.Area
{
	internal class AreaMap
	{
		public const int ZoneSize = 64;

		public const int ZoneSizeOffset = 32;

		public int[][] Biomes { get; private set; }

		public int[][] AreaIds { get; private set; }

		public int ZoneOffset { get; private set; }

		public int MapWidth { get; private set; }

		public int IndexStartCoordinate { get; private set; }

		public AreaMap(int mapRadius)
		{
			ZoneOffset = (int)Math.Ceiling((double)mapRadius / 64.0);
			IndexStartCoordinate = -(ZoneOffset * 64);
			MapWidth = ZoneOffset * 2;
			Biomes = new int[MapWidth][];
			AreaIds = new int[MapWidth][];
			for (int i = 0; i < MapWidth; i++)
			{
				Biomes[i] = new int[MapWidth];
				AreaIds[i] = new int[MapWidth];
			}
		}

		public int IndexToCoordinate(int index)
		{
			return IndexStartCoordinate + index * 64;
		}

		public int CoordinateToIndex(int coordinate)
		{
			return coordinate / 64 + ZoneOffset;
		}
	}
	internal class AreaMapBuilder
	{
		private class Label
		{
			public int Id { get; set; }

			public int Area { get; set; }
		}

		private IAreaProvider AreaProvider { get; set; }

		private AreaMap AreaMap { get; }

		private Label[][] LabelGrid { get; }

		private Dictionary<int, int> MergeTable { get; } = new Dictionary<int, int>();


		private int Size => AreaMap.MapWidth;

		private AreaMapBuilder(IAreaProvider areaProvider, int mapRadius)
		{
			AreaProvider = areaProvider;
			AreaMap = new AreaMap(mapRadius);
			LabelGrid = new Label[Size][];
			for (int i = 0; i < Size; i++)
			{
				LabelGrid[i] = new Label[Size];
			}
		}

		public static AreaMapBuilder BiomeMap(int mapRadius)
		{
			return new AreaMapBuilder(new WorldGeneratorAreaProvider(), mapRadius);
		}

		public AreaMapBuilder UseAreaProvider(IAreaProvider areaProvider)
		{
			AreaProvider = areaProvider;
			return this;
		}

		public AreaMap CompileMap()
		{
			ScanAreas();
			MergeLabels();
			Build();
			return AreaMap;
		}

		private void ScanAreas()
		{
			int num = 0;
			for (int i = 0; i < AreaMap.Biomes.Length; i++)
			{
				Label[] array = ((i == 0) ? null : LabelGrid[i - 1]);
				Label label = ((i == 0) ? null : array[0]);
				int[] array2 = ((i == 0) ? null : AreaMap.Biomes[i - 1]);
				int num2 = ((i == 0) ? (-1) : array2[0]);
				for (int j = 0; j < AreaMap.Biomes.Length; j++)
				{
					int area = GetArea(i, j);
					AreaMap.Biomes[i][j] = area;
					if (num2 != area)
					{
						if (i > 0 && array2[j] == area)
						{
							label = array[j];
						}
						else
						{
							label = new Label
							{
								Id = num++,
								Area = area
							};
							MergeTable[label.Id] = label.Id;
						}
					}
					LabelGrid[i][j] = label;
					num2 = area;
				}
			}
		}

		private int GetArea(int x, int y)
		{
			return AreaProvider.GetArea(AreaMap.IndexToCoordinate(x), AreaMap.IndexToCoordinate(y));
		}

		private void MergeLabels()
		{
			for (int i = 0; i < LabelGrid.Length; i++)
			{
				for (int j = 0; j < LabelGrid.Length; j++)
				{
					Label label3 = LabelGrid[i][j];
					if (j > 0)
					{
						Label label4 = LabelGrid[i][j - 1];
						_ = label3.Area;
						_ = label4.Area;
						if (MergeLabels(label4, label3, out var result2))
						{
							LabelGrid[i][j] = result2;
							continue;
						}
					}
					if (i > 0)
					{
						Label label5 = LabelGrid[i - 1][j];
						if (MergeLabels(label5, label3, out var result3))
						{
							LabelGrid[i][j] = result3;
							continue;
						}
					}
					if (j + 1 < LabelGrid.Length)
					{
						Label label6 = LabelGrid[i][j + 1];
						if (MergeLabels(label6, label3, out var result4))
						{
							LabelGrid[i][j] = result4;
							continue;
						}
					}
					if (i + 1 < LabelGrid.Length)
					{
						Label label7 = LabelGrid[i + 1][j];
						if (MergeLabels(label7, label3, out var result5))
						{
							LabelGrid[i][j] = result5;
						}
					}
				}
			}
			bool MergeLabels(Label label1, Label label2, out Label result)
			{
				result = null;
				if (label1.Area == label2.Area && label1.Id != label2.Id)
				{
					if (label1.Id > label2.Id)
					{
						if (MergeTable[label1.Id] > label2.Id)
						{
							MergeTable[label1.Id] = label2.Id;
						}
						result = label2;
						label1.Id = label2.Id;
					}
					else
					{
						if (MergeTable[label2.Id] > label1.Id)
						{
							MergeTable[label2.Id] = label1.Id;
						}
						result = label1;
						label2.Id = label1.Id;
					}
					return true;
				}
				return false;
			}
		}

		private void Build()
		{
			for (int i = 0; i < LabelGrid.Length; i++)
			{
				for (int j = 0; j < LabelGrid.Length; j++)
				{
					int id = LabelGrid[i][j].Id;
					int num = MergeTable[id];
					while (MergeTable[num] < num)
					{
						num = MergeTable[num];
						MergeTable[id] = num;
					}
					AreaMap.AreaIds[i][j] = num;
				}
			}
		}
	}
	internal static class ColourMapper
	{
		public static (int r, int g, int b) IntegerToColor255(int value)
		{
			int item;
			if (value > 255)
			{
				item = 255;
				value -= 255;
				int item2;
				if (value > 255)
				{
					item2 = 255;
					value -= 255;
					int item3 = ((value <= 255) ? value : 255);
					return (item3, item2, item);
				}
				item2 = value;
				return (0, item2, item);
			}
			item = value;
			return (0, 0, item);
		}

		public static (int r, int g, int b) IntegerToColour3Byte(int value)
		{
			byte[] bytes = BitConverter.GetBytes(value);
			return (bytes[2], bytes[1], bytes[0]);
		}

		public static (float r, float g, float b) IntegerToColor(int value)
		{
			var (num, num2, num3) = IntegerToColour3Byte(value);
			return (num / 255, num2 / 255, num3 / 255);
		}

		public static (float r, float g, float b) Rainbow255(int id)
		{
			float num = (float)new Random(id).NextDouble();
			int num2 = (int)(num * 6f);
			int num3 = (int)(num * 255f);
			int num4 = 1 - num3;
			return num2 switch
			{
				0 => (255f, num3, 0f), 
				1 => (num4, 255f, 0f), 
				2 => (0f, 255f, num3), 
				3 => (0f, num4, 255f), 
				4 => (num3, 0f, 255f), 
				_ => (255f, 0f, num4), 
			};
		}

		public static (float r, float g, float b) Rainbow(int id)
		{
			float num = (float)new Random(id).NextDouble();
			int num2 = (int)(num * 6f);
			float num3 = num;
			float num4 = 1f - num3;
			return num2 switch
			{
				0 => (1f, num3, 0f), 
				1 => (num4, 1f, 0f), 
				2 => (0f, 1f, num3), 
				3 => (0f, num4, 1f), 
				4 => (num3, 0f, 1f), 
				_ => (1f, 0f, num4), 
			};
		}

		public static (int r, int g, int b) ToBiomeColour255(int biome)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0005: Invalid comparison between Unknown and I4
			//IL_0046: Unknown result type (might be due to invalid IL or missing references)
			//IL_0049: Invalid comparison between Unknown and I4
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_0031: Expected I4, but got Unknown
			//IL_004e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0054: Invalid comparison between Unknown and I4
			//IL_0031: Unknown result type (might be due to invalid IL or missing references)
			//IL_0034: Invalid comparison between Unknown and I4
			//IL_0059: Unknown result type (might be due to invalid IL or missing references)
			//IL_005f: Invalid comparison between Unknown and I4
			//IL_0039: Unknown result type (might be due to invalid IL or missing references)
			//IL_003c: Invalid comparison between Unknown and I4
			Biome val = (Biome)biome;
			if ((int)val <= 32)
			{
				switch ((int)val)
				{
				default:
					if ((int)val != 16)
					{
						if ((int)val != 32)
						{
							break;
						}
						return (255, 0, 0);
					}
					return (255, 255, 0);
				case 0:
					return (0, 0, 0);
				case 1:
					return (0, 255, 0);
				case 2:
					return (128, 0, 0);
				case 4:
					return (255, 255, 255);
				case 8:
					return (0, 128, 0);
				case 3:
				case 5:
				case 6:
				case 7:
					break;
				}
			}
			else
			{
				if ((int)val == 64)
				{
					return (0, 255, 255);
				}
				if ((int)val == 256)
				{
					return (0, 0, 255);
				}
				if ((int)val == 512)
				{
					return (128, 128, 128);
				}
			}
			return (0, 0, 0);
		}

		public static (float r, float g, float b) ToBiomeColour(Biome biome)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0003: Invalid comparison between Unknown and I4
			//IL_0044: Unknown result type (might be due to invalid IL or missing references)
			//IL_0047: Invalid comparison between Unknown and I4
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			//IL_002f: Expected I4, but got Unknown
			//IL_004c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0052: Invalid comparison between Unknown and I4
			//IL_002f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0032: Invalid comparison between Unknown and I4
			//IL_0057: Unknown result type (might be due to invalid IL or missing references)
			//IL_005d: Invalid comparison between Unknown and I4
			//IL_0037: Unknown result type (might be due to invalid IL or missing references)
			//IL_003a: Invalid comparison between Unknown and I4
			if ((int)biome <= 32)
			{
				switch ((int)biome)
				{
				default:
					if ((int)biome != 16)
					{
						if ((int)biome != 32)
						{
							break;
						}
						return (1f, 0f, 0f);
					}
					return (1f, 1f, 0f);
				case 0:
					return (0f, 0f, 0f);
				case 1:
					return (0f, 1f, 0f);
				case 2:
					return (0.5f, 0f, 0f);
				case 4:
					return (1f, 1f, 1f);
				case 8:
					return (0f, 0.5f, 0f);
				case 3:
				case 5:
				case 6:
				case 7:
					break;
				}
			}
			else
			{
				if ((int)biome == 64)
				{
					return (0f, 1f, 1f);
				}
				if ((int)biome == 256)
				{
					return (0f, 0f, 1f);
				}
				if ((int)biome == 512)
				{
					return (0.5f, 0.5f, 0.5f);
				}
			}
			return (0f, 0f, 0f);
		}

		public static (float r, float g, float b) ToBiomeColourGrayscale(int biome)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0005: Invalid comparison between Unknown and I4
			//IL_0046: Unknown result type (might be due to invalid IL or missing references)
			//IL_0049: Invalid comparison between Unknown and I4
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_0031: Expected I4, but got Unknown
			//IL_004e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0054: Invalid comparison between Unknown and I4
			//IL_0031: Unknown result type (might be due to invalid IL or missing references)
			//IL_0034: Invalid comparison between Unknown and I4
			//IL_0059: Unknown result type (might be due to invalid IL or missing references)
			//IL_005f: Invalid comparison between Unknown and I4
			//IL_0039: Unknown result type (might be due to invalid IL or missing references)
			//IL_003c: Invalid comparison between Unknown and I4
			Biome val = (Biome)biome;
			(int, int, int) tuple;
			if ((int)val <= 32)
			{
				switch ((int)val)
				{
				case 0:
					goto IL_0069;
				case 1:
					goto IL_0083;
				case 2:
					goto IL_0094;
				case 4:
					goto IL_00ae;
				case 8:
					goto IL_00c8;
				case 3:
				case 5:
				case 6:
				case 7:
					goto IL_0155;
				}
				if ((int)val != 16)
				{
					if ((int)val != 32)
					{
						goto IL_0155;
					}
					tuple = (220, 220, 220);
				}
				else
				{
					tuple = (200, 200, 200);
				}
			}
			else if ((int)val != 64)
			{
				if ((int)val != 256)
				{
					if ((int)val != 512)
					{
						goto IL_0155;
					}
					tuple = (130, 130, 130);
				}
				else
				{
					tuple = (255, 255, 255);
				}
			}
			else
			{
				tuple = (240, 240, 240);
			}
			goto IL_016a;
			IL_0094:
			tuple = (140, 140, 140);
			goto IL_016a;
			IL_0069:
			tuple = (255, 255, 255);
			goto IL_016a;
			IL_0083:
			tuple = (120, 120, 120);
			goto IL_016a;
			IL_016a:
			(int, int, int) tuple2 = tuple;
			return (tuple2.Item1, tuple2.Item2, tuple2.Item3);
			IL_0155:
			tuple = (255, 255, 255);
			goto IL_016a;
			IL_00c8:
			tuple = (180, 180, 180);
			goto IL_016a;
			IL_00ae:
			tuple = (160, 160, 160);
			goto IL_016a;
		}
	}
	internal interface IAreaProvider
	{
		int GetArea(int x, int y);
	}
	internal class ImageBuilder
	{
		private AreaMap areaMap;

		private Texture2D image;

		private ImageBuilder(AreaMap areaMap)
		{
			//IL_0026: Unknown result type (might be due to invalid IL or missing references)
			//IL_0030: Expected O, but got Unknown
			this.areaMap = areaMap;
			image = new Texture2D(this.areaMap.MapWidth, this.areaMap.MapWidth, (TextureFormat)4, true);
		}

		public static ImageBuilder Init(AreaMap areaMap)
		{
			return new ImageBuilder(areaMap);
		}

		public static ImageBuilder SetBiomes(AreaMap areaMap)
		{
			//IL_0041: Unknown result type (might be due to invalid IL or missing references)
			ImageBuilder imageBuilder = new ImageBuilder(areaMap);
			for (int i = 0; i < areaMap.MapWidth; i++)
			{
				for (int j = 0; j < areaMap.MapWidth; j++)
				{
					var (num, num2, num3) = ColourMapper.ToBiomeColour((Biome)areaMap.Biomes[i][j]);
					imageBuilder.image.SetPixel(i, j, new Color(num, num2, num3));
				}
			}
			return imageBuilder;
		}

		public static ImageBuilder SetGrayscaleBiomes(AreaMap areaMap)
		{
			//IL_0049: 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)
			ImageBuilder imageBuilder = new ImageBuilder(areaMap);
			for (int i = 0; i < areaMap.MapWidth; i++)
			{
				for (int j = 0; j < areaMap.MapWidth; j++)
				{
					var (num, num2, num3) = ColourMapper.ToBiomeColourGrayscale(areaMap.Biomes[i][j]);
					imageBuilder.image.SetPixel(i, j, Color32.op_Implicit(new Color32((byte)num, (byte)num2, (byte)num3, byte.MaxValue)));
				}
			}
			return imageBuilder;
		}

		public static ImageBuilder SetIds(AreaMap areaMap)
		{
			//IL_0050: 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)
			ImageBuilder imageBuilder = new ImageBuilder(areaMap);
			Color32 val = default(Color32);
			for (int i = 0; i < areaMap.MapWidth; i++)
			{
				for (int j = 0; j < areaMap.MapWidth; j++)
				{
					var (num, num2, num3) = ColourMapper.IntegerToColour3Byte(areaMap.AreaIds[i][j]);
					((Color32)(ref val))..ctor((byte)num, (byte)num2, (byte)num3, byte.MaxValue);
					imageBuilder.image.SetPixel(i, j, Color32.op_Implicit(val));
				}
			}
			return imageBuilder;
		}

		public static ImageBuilder SetRainbowIds(AreaMap areaMap)
		{
			//IL_0050: 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)
			ImageBuilder imageBuilder = new ImageBuilder(areaMap);
			Color32 val = default(Color32);
			for (int i = 0; i < areaMap.MapWidth; i++)
			{
				for (int j = 0; j < areaMap.MapWidth; j++)
				{
					var (num, num2, num3) = ColourMapper.Rainbow255(areaMap.AreaIds[i][j]);
					((Color32)(ref val))..ctor((byte)num, (byte)num2, (byte)num3, byte.MaxValue);
					imageBuilder.image.SetPixel(i, j, Color32.op_Implicit(val));
				}
			}
			return imageBuilder;
		}

		public ImageBuilder AddHeatZones(int[][] heatZones, bool ignoreZero = true)
		{
			//IL_0036: Unknown result type (might be due to invalid IL or missing references)
			//IL_003b: Unknown result type (might be due to invalid IL or missing references)
			for (int i = 0; i < heatZones.Length; i++)
			{
				for (int j = 0; j < heatZones.Length; j++)
				{
					int num = heatZones[i][j];
					if (!ignoreZero || num != 0)
					{
						image.SetPixel(i, j, Color32.op_Implicit(new Color32(byte.MaxValue, (byte)(255 - num), (byte)(255 - num), byte.MaxValue)));
					}
				}
			}
			return this;
		}

		public void Print(string filename, string description = null)
		{
			image.Apply();
			DebugFileWriter.WriteFile(ImageConversion.EncodeToPNG(image), filename + ".png", description ?? "map");
		}
	}
	internal class WorldGeneratorAreaProvider : IAreaProvider
	{
		private WorldGenerator _instance;

		private WorldGenerator World => _instance ?? (_instance = WorldGenerator.instance);

		public int GetArea(int x, int y)
		{
			//IL_0010: Unknown result type (might be due to invalid IL or missing references)
			//IL_0016: Expected I4, but got Unknown
			return (int)World.GetBiome((float)x, (float)y, 0.02f, false);
		}
	}
}
namespace SpawnThat.World.Locations
{
	public static class LocationManager
	{
		private static Dictionary<Vector2i, SimpleLocation> _simpleLocationsByZone { get; set; }

		static LocationManager()
		{
			LifecycleManager.SubscribeToWorldInit(delegate
			{
				_simpleLocationsByZone = null;
			});
		}

		public static Dictionary<Vector2i, SimpleLocation> GetLocations()
		{
			//IL_0053: Unknown result type (might be due to invalid IL or missing references)
			//IL_0060: Unknown result type (might be due to invalid IL or missing references)
			//IL_0087: Unknown result type (might be due to invalid IL or missing references)
			//IL_008c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0091: 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_009e: Unknown result type (might be due to invalid IL or missing references)
			if (_simpleLocationsByZone != null)
			{
				return new Dictionary<Vector2i, SimpleLocation>(_simpleLocationsByZone);
			}
			if (((Object)(object)ZoneSystem.instance).IsNotNull() && ZoneSystem.instance.m_locationInstances != null)
			{
				Dictionary<Vector2i, SimpleLocation> dictionary = new Dictionary<Vector2i, SimpleLocation>();
				foreach (KeyValuePair<Vector2i, LocationInstance> locationInstance in ZoneSystem.instance.m_locationInstances)
				{
					dictionary[locationInstance.Key] = new SimpleLocation
					{
						LocationName = (locationInstance.Value.m_location?.m_prefabName ?? ""),
						Position = locationInstance.Value.m_position,
						ZonePosition = locationInstance.Key
					};
				}
				_simpleLocationsByZone = dictionary;
				return dictionary;
			}
			return null;
		}

		public static SimpleLocation GetLocation(Vector3 position)
		{
			//IL_001d: Unknown result type (might be due to invalid IL or missing references)
			//IL_001e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0023: Unknown result type (might be due to invalid IL or missing references)
			//IL_003f: 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_004f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0070: Unknown result type (might be due to invalid IL or missing references)
			//IL_0071: Unknown result type (might be due to invalid IL or missing references)
			//IL_0076: 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)
			ZoneSystem instance = ZoneSystem.instance;
			if (!Object.op_Implicit((Object)(object)instance) || instance == null)
			{
				Log.LogWarning("Attempting to retrieve location before ZoneSystem is initialized.");
				return null;
			}
			Vector2i zoneId = position.GetZoneId();
			if ((instance.m_locationInstances?.Count ?? 0) > 0 && instance.m_locationInstances.TryGetValue(zoneId, out var value))
			{
				return new SimpleLocation
				{
					LocationName = (value.m_location?.m_prefabName ?? ""),
					Position = value.m_position,
					ZonePosition = zoneId
				};
			}
			if (_simpleLocationsByZone != null && _simpleLocationsByZone.TryGetValue(zoneId, out var value2))
			{
				return value2;
			}
			return null;
		}

		internal static void SetLocations(IEnumerable<SimpleLocation> locations)
		{
			//IL_0027: Unknown result type (might be due to invalid IL or missing references)
			if (_simpleLocationsByZone == null)
			{
				_simpleLocationsByZone = new Dictionary<Vector2i, SimpleLocation>();
			}
			foreach (SimpleLocation location in locations)
			{
				_simpleLocationsByZone[location.ZonePosition] = location;
			}
		}
	}
	public class SimpleLocation
	{
		public Vector3 Position;

		public Vector2i ZonePosition;

		public string LocationName;
	}
	internal class SimpleLocationPackage : CompressedPackage
	{
		public string[] LocationNames;

		public SimpleLocationDTO[] Locations;

		protected override void BeforePack()
		{
			//IL_003e: 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_0090: Unknown result type (might be due to invalid IL or missing references)
			Dictionary<Vector2i, LocationInstance> obj = (((Object)(object)ZoneSystem.instance).IsNotNull() ? ZoneSystem.instance.m_locationInstances : null);
			Dictionary<string, ushort> dictionary = new Dictionary<string, ushort>();
			List<string> list = new List<string>();
			List<SimpleLocationDTO> list2 = new List<SimpleLocationDTO>();
			foreach (KeyValuePair<Vector2i, LocationInstance> item in obj)
			{
				string prefabName = item.Value.m_location.m_prefabName;
				ushort num;
				if (dictionary.TryGetValue(item.Value.m_location.m_prefabName, out var value))
				{
					num = value;
				}
				else
				{
					list.Add(prefabName);
					num = (ushort)(list.Count - 1);
					dictionary.Add(prefabName, num);
				}
				list2.Add(new SimpleLocationDTO(item.Key, num));
			}
			LocationNames = list.ToArray();
			Locations = list2.ToArray();
			string[] locationNames = LocationNames;
			Log.LogDebug($"Packaged locations: {((locationNames != null) ? locationNames.Length : 0)}");
		}

		protected override void AfterUnpack(object obj)
		{
			//IL_0069: Unknown result type (might be due to invalid IL or missing references)
			//IL_006b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0070: Unknown result type (might be due to invalid IL or missing references)
			//IL_0076: Unknown result type (might be due to invalid IL or missing references)
			//IL_0078: Unknown result type (might be due to invalid IL or missing references)
			if (obj is SimpleLocationPackage simpleLocationPackage)
			{
				Log.LogDebug("Received and deserialized location package");
				List<SimpleLocation> list = new List<SimpleLocation>(simpleLocationPackage.Locations.Length);
				SimpleLocationDTO[] locations = simpleLocationPackage.Locations;
				Vector2i val = default(Vector2i);
				for (int i = 0; i < locations.Length; i++)
				{
					SimpleLocationDTO simpleLocationDTO = locations[i];
					((Vector2i)(ref val))..ctor(simpleLocationDTO.X, simpleLocationDTO.Y);
					list.Add(new SimpleLocation
					{
						LocationName = simpleLocationPackage.LocationNames[simpleLocationDTO.L],
						Position = ZoneSystem.GetZonePos(val),
						ZonePosition = val
					});
				}
				LocationManager.SetLocations(list);
				Log.LogInfo($"Successfully unpacked locations: {list?.Count ?? 0}");
			}
			else
			{
				Log.LogWarning("Received bad location package. Unable to load.");
			}
		}
	}
	[Serializable]
	public struct SimpleLocationDTO
	{
		public int X;

		public int Y;

		public ushort L;

		public SimpleLocationDTO(Vector2i pos, ushort location)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_000d: Unknown result type (might be due to invalid IL or missing references)
			X = pos.x;
			Y = pos.y;
			L = location;
		}
	}
	internal static class ZoneSystemSyncSetup
	{
		public static void Configure()
		{
			SyncManager.RegisterSyncHandlers("RPC_ReceiveLocationsSpawnThat", GeneratePackage, RPC_ReceiveLocationsSpawnThat);
		}

		private static ZPackage GeneratePackage()
		{
			return new SimpleLocationPackage().Pack();
		}

		private static void RPC_ReceiveLocationsSpawnThat(ZRpc rpc, ZPackage pkg)
		{
			Log.LogInfo("Received locations package.");
			try
			{
				CompressedPackage.Unpack<SimpleLocationPackage>(pkg);
			}
			catch (Exception e)
			{
				Log.LogError("Error while attempting to read received locations package.", e);
			}
		}
	}
}
namespace SpawnThat.World.Dungeons
{
	public sealed class RoomData : IPoint, IHaveVector3, IBox, IManagedValue
	{
		private Vector3 _pos;

		public string Name;

		private Vector2[] RotatedRectangle { get; set; }

		public Vector3Int Size { get; set; }

		public Vector3 Pos
		{
			get
			{
				//IL_0001: Unknown result type (might be due to invalid IL or missing references)
				return _pos;
			}
			set
			{
				//IL_0001: Unknown result type (might be due to invalid IL or missing references)
				//IL_0002: Unknown result type (might be due to invalid IL or missing references)
				//IL_0008: Unknown result type (might be due to invalid IL or missing references)
				//IL_0014: Unknown result type (might be due to invalid IL or missing references)
				_pos = value;
				X = value.x;
				Y = value.z;
			}
		}

		public float X { get; set; }

		public float Y { get; set; }

		public Quaternion Rotation { get; set; }

		public void OnCreate()
		{
		}

		public void OnDestroy()
		{
			RoomManager.RemoveRoom(this);
		}

		public bool Contains(Vector3 pos)
		{
			//IL_0017: Unknown result type (might be due to invalid IL or missing references)
			if (RotatedRectangle == null)
			{
				Vector2[] array2 = (RotatedRectangle = SearchSpatial.CreateRectangle(this));
			}
			return SearchSpatial.Contains(this, pos);
		}
	}
	public static class RoomManager
	{
		[HarmonyPatch(typeof(DungeonGenerator))]
		private static class DungeonGeneratorPatch
		{
			[HarmonyPatch("PlaceRoom", new Type[]
			{
				typeof(RoomData),
				typeof(Vector3),
				typeof(Quaternion),
				typeof(RoomConnection),
				typeof(SpawnMode)
			})]
			[HarmonyPostfix]
			private static void GetRoomObject(Room __result)
			{
				CacheRoom(__result);
			}

			private static void CacheRoom(Room component)
			{
				AddRoom(component);
			}
		}

		private static ManagedCache<RoomData> RoomTable;

		private static HashSet<Vector3> HasAdded;

		private static List<RoomData> RoomList;

		static RoomManager()
		{
			RoomTable = new ManagedCache<RoomData>();
			HasAdded = new HashSet<Vector3>();
			RoomList = new List<RoomData>();
			LifecycleManager.SubscribeToWorldInit(delegate
			{
				HasAdded = new HashSet<Vector3>();
				RoomList = new List<RoomData>();
			});
		}

		public static RoomData GetContainingRoom(Vector3 pos)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			return FindClosestRoom(pos);
		}

		private static RoomData FindClosestRoom(Vector3 pos)
		{
			//IL_0022: Unknown result type (might be due to invalid IL or missing references)
			//IL_0038: Unknown result type (might be due to invalid IL or missing references)
			//IL_005f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0069: Unknown result type (might be due to invalid IL or missing references)
			//IL_007e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0086: Unknown result type (might be due to invalid IL or missing references)
			//IL_008e: 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_00a1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ae: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b6: Unknown result type (might be due to invalid IL or missing references)
			List<RoomData> roomList = RoomList;
			if (roomList == null || roomList.Count == 0)
			{
				return null;
			}
			RoomData result = null;
			float num = float.MaxValue;
			int num2 = RoomList.IndexLeft(pos.x - 20f);
			int num3 = RoomList.IndexRight(pos.x + 20f);
			for (int i = num2; i < num3; i++)
			{
				RoomData roomData = RoomList[i];
				if (!(Math.Abs(roomData.Pos.y - pos.y) > 100f) && roomData.Contains(pos))
				{
					float value = pos.x - roomData.Pos.x;
					float value2 = pos.z - roomData.Pos.z;
					float value3 = pos.y - roomData.Pos.y;
					float num4 = Math.Abs(value) + Math.Abs(value2) + Math.Abs(value3);
					if (num4 < num)
					{
						result = roomData;
						num = num4;
					}
				}
			}
			return result;
		}

		internal static void AddRoom(Room room)
		{
			//IL_0012: Unknown result type (might be due to invalid IL or missing references)
			//IL_0017: Unknown result type (might be due to invalid IL or missing references)
			//IL_001d: 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_009f: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b0: Unknown result type (might be due to invalid IL or missing references)
			RoomData orCreate = RoomTable.GetOrCreate((Object)(object)room);
			Vector3 position = ((Component)room).transform.position;
			if (HasAdded.Add(position))
			{
				orCreate.Name = ((Object)(object)room).GetCleanedName();
				orCreate.Pos = position;
				int num = ((((Vector3Int)(ref room.m_size)).x == 0) ? 10 : ((Vector3Int)(ref room.m_size)).x);
				int num2 = ((((Vector3Int)(ref room.m_size)).y == 0) ? 10 : ((Vector3Int)(ref room.m_size)).y);
				int num3 = ((((Vector3Int)(ref room.m_size)).z == 0) ? 10 : ((Vector3Int)(ref room.m_size)).z);
				orCreate.Size = new Vector3Int(num * 2, num2 * 2, num3 * 2);
				orCreate.Rotation = ((Component)room).transform.rotation;
				RoomList.Insert(orCreate);
			}
		}

		internal static void RemoveRoom(RoomData room)
		{
			//IL_0012: Unknown result type (might be due to invalid IL or missing references)
			RoomList.Remove(room);
			HasAdded.Remove(room.Pos);
		}
	}
}
namespace SpawnThat.Utilities
{
	internal enum Separator
	{
		Comma,
		Slash,
		Dot,
		Newline
	}
	public static class StringExtensions
	{
		private static readonly char[] Comma = new char[1] { ',' };

		private static readonly char[] Slash = new char[2] { '/', '\\' };

		private static readonly char[] Dot = new char[1] { '.' };

		private static readonly char[] Newline = new char[1] { '\n' };

		internal static List<string> SplitBy(this string value, Separator separator, bool toUpper = false)
		{
			return value.SplitBy(separator switch
			{
				Separator.Comma => Comma, 
				Separator.Slash => Slash, 
				Separator.Dot => Dot, 
				Separator.Newline => Newline, 
				_ => throw new NotSupportedException("Separator"), 
			}, toUpper).ToList();
		}

		public static List<string> SplitByComma(this string value, bool toUpper = false)
		{
			return value.SplitBy(Comma, toUpper).ToList();
		}

		internal static string[] SplitBySlash(this string value, bool toUpper = false)
		{
			return value.SplitBy(Slash, toUpper).ToArray();
		}

		public static IEnumerable<string> SplitBy(this string value, char[] chars, bool toUpper = false)
		{
			if (value == null)
			{
				return Enumerable.Empty<string>();
			}
			string[] array = value.Trim().Split(chars, StringSplitOptions.RemoveEmptyEntries);
			if (array == null || array.Length == 0)
			{
				return Enumerable.Empty<string>();
			}
			return array.Select(Clean);
			string Clean(string x)
			{
				string text = x.Trim();
				if (toUpper)
				{
					return text.ToUpperInvariant();
				}
				return text;
			}
		}

		public static bool IsEmpty(this string s)
		{
			return string.IsNullOrWhiteSpace(s);
		}

		public static bool IsNotEmpty(this string s)
		{
			if (string.IsNullOrWhiteSpace(s))
			{
				return false;
			}
			return true;
		}
	}
	public static class FileUtils
	{
		public static void EnsureDirectoryExistsForFile(string filePath)
		{
			string directoryName = Path.GetDirectoryName(filePath);
			if (!Directory.Exists(directoryName))
			{
				Log.LogTrace("Creating missing folders in path.");
				Directory.CreateDirectory(directoryName);
			}
		}
	}
	internal static class HeightmapUtils
	{
		public static Biome ParseBiomeMask(IEnumerable<string> biomeNames)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0013: Unknown result type (might be due to invalid IL or missing references)
			//IL_0030: Unknown result type (might be due to invalid IL or missing references)
			//IL_0031: Unknown result type (might be due to invalid IL or missing references)
			//IL_0032: Unknown result type (might be due to invalid IL or missing references)
			//IL_0033: Unknown result type (might be due to invalid IL or missing references)
			//IL_005f: Unknown result type (might be due to invalid IL or missing references)
			Biome val = (Biome)0;
			if (biomeNames == null || !biomeNames.Any())
			{
				return val;
			}
			foreach (string biomeName in biomeNames)
			{
				if (Enum.TryParse<Biome>(biomeName, ignoreCase: true, out Biome result))
				{
					val |= result;
				}
				else
				{
					Log.LogWarning("Unable to parse biome '" + biomeName + "'. Check spelling.");
				}
			}
			return val;
		}

		public static List<Biome> ParseBiomes(IEnumerable<string> biomeNames)
		{
			//IL_0035: Unknown result type (might be due to invalid IL or missing references)
			List<Biome> list = new List<Biome>();
			if (biomeNames == null || !biomeNames.Any())
			{
				return list;
			}
			foreach (string biomeName in biomeNames)
			{
				if (Enum.TryParse<Biome>(biomeName, ignoreCase: true, out Biome result))
				{
					list.Add(result);
				}
				else
				{
					Log.LogWarning("Unable to parse biome '" + biomeName + "'. Check spelling.");
				}
			}
			return list;
		}

		public static string GetNames(Biome biome)
		{
			//IL_0023: Unknown result type (might be due to invalid IL or missing references)
			//IL_0028: Unknown result type (might be due to invalid IL or missing references)
			//IL_0029: Unknown result type (might be due to invalid IL or missing references)
			//IL_002c: Unknown result type (might be due to invalid IL or missing references)
			//IL_002d: Unknown result type (might be due to invalid IL or missing references)
			//IL_002e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0030: Invalid comparison between Unknown and I4
			List<string> list = new List<string>();
			foreach (Biome value in Enum.GetValues(typeof(Biome)))
			{
				Biome val = value;
				if ((int)val != 0 && (biome & val) > 0)
				{
					list.Add(((object)(Biome)(ref val)).ToString());
				}
			}
			return string.Join(", ", list);
		}
	}
	public static class PlayerUtils
	{
		public static List<Player> GetPlayersInRadius(Vector3 point, float range)
		{
			//IL_0021: Unknown result type (might be due to invalid IL or missing references)
			//IL_0026: Unknown result type (might be due to invalid IL or missing references)
			List<Player> list = new List<Player>();
			foreach (Player allPlayer in Player.GetAllPlayers())
			{
				if (Utils.DistanceXZ(((Component)allPlayer).transform.position, point) < range)
				{
					list.Add(allPlayer);
				}
			}
			return list;
		}

		public static List<ZDO> GetPlayerZdosInRadius(Vector3 point, float range)
		{
			//IL_0021: Unknown result type (might be due to invalid IL or missing references)
			//IL_0026: Unknown result type (might be due to invalid IL or missing references)
			List<ZDO> list = new List<ZDO>();
			foreach (ZDO allCharacterZDO in ZNet.instance.GetAllCharacterZDOS())
			{
				if (Utils.DistanceXZ(allCharacterZDO.GetPosition(), point) < range)
				{
					list.Add(allCharacterZDO);
				}
			}
			return list;
		}
	}
	internal static class ReflectionUtils
	{
		private static MethodInfo InstantiateGameObject;

		public static MethodInfo InstantiateGameObjectMethod => InstantiateGameObject ?? (InstantiateGameObject = (from x in typeof(Object).GetMethods(BindingFlags.Static | BindingFlags.Public)
			where x.Name.Equals("Instantiate")
			select x into m
			where m.IsGenericMethod
			select m).First((MethodInfo m) => m.ContainsGenericParameters && m.GetParameters().Length == 3 && m.GetParameters()[2].ParameterType == typeof(Quaternion)).GetGenericMethodDefinition().MakeGenericMethod(typeof(GameObject)));
	}
}
namespace SpawnThat.Utilities.Spatial
{
	internal interface IBox
	{
		Vector3 Pos { get; }

		Quaternion Rotation { get; }

		Vector3Int Size { get; }
	}
	internal interface IHaveVector3
	{
		Vector3 Pos { get; }
	}
	internal interface IPoint
	{
		float X { get; set; }

		float Y { get; set; }
	}
	internal static class SearchSpatial
	{
		public static T FindClosest<T>(this IList<T> points, Vector3 pos) where T : class, IHaveVector3, IPoint
		{
			//IL_0024: 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_0060: Unknown result type (might be due to invalid IL or missing references)
			//IL_006a: 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_008a: 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)
			//IL_00a2: Unknown result type (might be due to invalid IL or missing references)
			if (points == null || points.Count == 0)
			{
				return null;
			}
			T result = null;
			float num = float.MaxValue;
			int num2 = points.IndexLeft(pos.x - 20f);
			int num3 = points.IndexRight(pos.x + 20f);
			for (int i = num2; i <= num3 && i < points.Count; i++)
			{
				T val = points[i];
				if (!(Math.Abs(val.Pos.y - pos.y) > 100f))
				{
					float value = pos.x - val.Pos.x;
					float value2 = pos.z - val.Pos.z;
					float num4 = Math.Abs(value) + Math.Abs(value2);
					if (num4 < num)
					{
						result = val;
						num = num4;
					}
				}
			}
			return result;
		}

		public static bool Contains(IBox box, Vector3 pos)
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			return Contains(CreateRectangle(box), pos);
		}

		public static bool Contains(Vector2[] rectangle, Vector3 pos)
		{
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0007: Unknown result type (might be due to invalid IL or missing references)
			//IL_000a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0011: Unknown result type (might be due to invalid IL or missing references)
			//IL_0016: 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_001f: Unknown result type (might be due to invalid IL or missing references)
			//IL_002a: Unknown result type (might be due to invalid IL or missing references)
			//IL_002b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0030: Unknown result type (might be due to invalid IL or missing references)
			//IL_0031: Unknown result type (might be due to invalid IL or missing references)
			//IL_0032: Unknown result type (might be due to invalid IL or missing references)
			//IL_0033: Unknown result type (might be due to invalid IL or missing references)
			//IL_0038: Unknown result type (might be due to invalid IL or missing references)
			//IL_003a: Unknown result type (might be due to invalid IL or missing references)
			//IL_003b: Unknown result type (might be due to invalid IL or missing references)
			//IL_003c: 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)
			//IL_0042: 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_004b: 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_005c: Unknown result type (might be due to invalid IL or missing references)
			//IL_005e: Unknown result type (might be due to invalid IL or missing references)
			Vector2 val = rectangle[0];
			Vector2 val2 = rectangle[1];
			Vector2 val3 = rectangle[3];
			Vector2 val4 = default(Vector2);
			((Vector2)(ref val4))..ctor(pos.x, pos.z);
			Vector2 val5 = val2 - val;
			Vector2 val6 = val3 - val;
			Vector2 val7 = val4 - val;
			float num = Vector2.Dot(val7, val5);
			float num2 = Vector2.Dot(val5, val5);
			float num3 = Vector2.Dot(val7, val6);
			float num4 = Vector2.Dot(val6, val6);
			if (0f < num && num < num2 && 0f < num3 && num3 < num4)
			{
				return true;
			}
			return false;
		}

		public static Vector2[] CreateRectangle(IBox box)
		{
			//IL_000e: Unknown result type (might be due to invalid IL or missing references)
			//IL_001e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0023: Unknown result type (might be due to invalid IL or missing references)
			//IL_0035: 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_005c: Unknown result type (might be due to invalid IL or missing references)
			//IL_006c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0071: Unknown result type (might be due to invalid IL or missing references)
			//IL_0083: Unknown result type (might be due to invalid IL or missing references)
			//IL_0093: Unknown result type (might be due to invalid IL or missing references)
			//IL_0098: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ab: Unknown result type (might be due to invalid IL or missing references)
			//IL_00bb: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e8: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fb: Unknown result type (might be due to invalid IL or missing references)
			//IL_010b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0110: Unknown result type (might be due to invalid IL or missing references)
			//IL_0123: Unknown result type (might be due to invalid IL or missing references)
			//IL_0133: Unknown result type (might be due to invalid IL or missing references)
			//IL_0138: Unknown result type (might be due to invalid IL or missing references)
			//IL_0176: Unknown result type (might be due to invalid IL or missing references)
			//IL_017a: Unknown result type (might be due to invalid IL or missing references)
			//IL_017f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0186: Unknown result type (might be due to invalid IL or missing references)
			//IL_018a: Unknown result type (might be due to invalid IL or missing references)
			//IL_018f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0196: 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_01a6: Unknown result type (might be due to invalid IL or missing references)
			//IL_01aa: Unknown result type (might be due to invalid IL or missing references)
			//IL_01af: Unknown result type (might be due to invalid IL or missing references)
			float x = box.Pos.x;
			Vector3Int size = box.Size;
			float num = x - (float)((Vector3Int)(ref size)).x;
			float z = box.Pos.z;
			size = box.Size;
			float num2 = z + (float)((Vector3Int)(ref size)).z;
			float x2 = box.Pos.x;
			size = box.Size;
			float num3 = x2 + (float)((Vector3Int)(ref size)).x;
			float z2 = box.Pos.z;
			size = box.Size;
			float num4 = z2 + (float)((Vector3Int)(ref size)).z;
			float x3 = box.Pos.x;
			size = box.Size;
			float num5 = x3 + (float)((Vector3Int)(ref size)).x;
			float z3 = box.Pos.z;
			size = box.Size;
			float num6 = z3 - (float)((Vector3Int)(ref size)).z;
			float x4 = box.Pos.x;
			size = box.Size;
			float num7 = x4 - (float)((Vector3Int)(ref size)).x;
			float z4 = box.Pos.z;
			size = box.Size;
			float num8 = z4 - (float)((Vector3Int)(ref size)).z;
			Vector2 point2 = default(Vector2);
			((Vector2)(ref point2))..ctor(num, num2);
			Vector2 point3 = default(Vector2);
			((Vector2)(ref point3))..ctor(num3, num4);
			Vector2 point4 = default(Vector2);
			((Vector2)(ref point4))..ctor(num5, num6);
			Vector2 point5 = default(Vector2);
			((Vector2)(ref point5))..ctor(num7, num8);
			return (Vector2[])(object)new Vector2[4]
			{
				Pivot(point2),
				Pivot(point3),
				Pivot(point4),
				Pivot(point5)
			};
			Vector2 Pivot(Vector2 point)
			{
				//IL_0000: Unknown result type (might be due to invalid IL or missing references)
				//IL_000c: Unknown result type (might be due to invalid IL or missing references)
				//IL_0016: Unknown result type (might be due to invalid IL or missing references)
				//IL_001c: Unknown result type (might be due to invalid IL or missing references)
				//IL_0027: Unknown result type (might be due to invalid IL or missing references)
				//IL_002c: Unknown result type (might be due to invalid IL or missing references)
				//IL_0031: Unknown result type (might be due to invalid IL or missing references)
				//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_003e: Unknown result type (might be due to invalid IL or missing references)
				//IL_0049: 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_0054: Unknown result type (might be due to invalid IL or missing references)
				//IL_005a: Unknown result type (might be due to invalid IL or missing references)
				//IL_0060: Unknown result type (might be due to invalid IL or missing references)
				Vector3 val = new Vector3(point.x, box.Pos.y, point.y) - box.Pos;
				Vector3 val2 = box.Rotation * val + box.Pos;
				return new Vector2(val2.x, val2.z);
			}
		}
	}
	internal static class SpatialListExtensions
	{
		public static void Insert<T>(this List<T> points, T point) where T : IPoint
		{
			int num = points.IndexLeft(point.X) + 1;
			for (int i = num; i < points.Count; i++)
			{
				T val = points[i];
				if (val.X > point.X || val.Y > point.Y)
				{
					break;
				}
				num = i;
			}
			if (num >= points.Count)
			{
				points.Add(point);
			}
			else
			{
				points.Insert(num, point);
			}
		}

		public static int IndexLeft<T>(this IList<T> points, T point) where T : IPoint
		{
			return points.IndexLeft(point.X);
		}

		public static int IndexLeft<T>(this IList<T> points, float x) where T : IPoint
		{
			int count = points.Count;
			int num = 0;
			int num2 = count;
			while (num < num2)
			{
				int num3 = (num + num2) / 2;
				float x2 = points[num3].X;
				float x3 = points[Math.Min(num3 + 1, count - 1)].X;
				if (x2 < x)
				{
					if (x3 > x)
					{
						return num3;
					}
					num = num3 + 1;
				}
				else
				{
					num2 = num3;
				}
			}
			return num;
		}

		public static int IndexRight<T>(this IList<T> points, T point) where T : IPoint
		{
			return points.IndexRight(point.X);
		}

		public static int IndexRight<T>(this IList<T> points, float x) where T : IPoint
		{
			int count = points.Count;
			int num = 0;
			int num2 = count;
			while (num < num2)
			{
				int num3 = (num + num2) / 2;
				float x2 = points[num3].X;
				float x3 = points[Math.Max(num3 - 1, 0)].X;
				if (x2 > x)
				{
					if (x3 < x)
					{
						return num3;
					}
					num2 = num3;
				}
				else
				{
					num = num3 + 1;
				}
			}
			return num2 - 1;
		}

		public static int IndexUp<T>(this IList<T> points, int xLower, int xUpper, T point) where T : IPoint
		{
			return points.IndexUp(xLower, xUpper, point.Y);
		}

		public static int IndexUp<T>(this IList<T> points, int xLower, int xUpper, float y) where T : IPoint
		{
			int count = points.Count;
			int num = xLower;
			int num2 = xUpper;
			while (num < num2)
			{
				int num3 = (num + num2) / 2;
				float y2 = points[num3].Y;
				float y3 = points[Math.Min(num3 + 1, count - 1)].Y;
				if (y2 < y)
				{
					if (y3 > y)
					{
						return num3;
					}
					num = num3 + 1;
				}
				else
				{
					num2 = num3;
				}
			}
			return num;
		}

		public static int IndexDown<T>(this IList<T> points, int xIndex, T point) where T : IPoint
		{
			return points.IndexDown(xIndex, point.Y);
		}

		public static int IndexDown<T>(this IList<T> points, int xIndex, float y) where T : IPoint
		{
			if (xIndex >= points.Count)
			{
				return xIndex;
			}
			float x = points[xIndex].X;
			int num = xIndex;
			int num2 = points.Count;
			while (num < num2)
			{
				int num3 = (num + num2) / 2;
				if (points[num3].X > x)
				{
					return num3 - 1;
				}
				if (points[num3].Y > y)
				{
					num2 = num3;
				}
				else
				{
					num = num3 + 1;
				}
			}
			return num2 - 1;
		}
	}
}
namespace SpawnThat.Utilities.Extensions
{
	internal static class CodeInstructionExtensions
	{
		public static CodeInstruction GetLdlocFromStLoc(this CodeInstruction instruction)
		{
			//IL_0018: Unknown result type (might be due to invalid IL or missing references)
			//IL_001e: Expected O, but got Unknown
			//IL_0036: Unknown result type (might be due to invalid IL or missing references)
			//IL_003c: Expected O, but got Unknown
			//IL_0054: Unknown result type (might be due to invalid IL or missing references)
			//IL_005a: Expected O, but got Unknown
			//IL_0072: Unknown result type (might be due to invalid IL or missing references)
			//IL_0078: Expected O, but got Unknown
			//IL_0095: Unknown result type (might be due to invalid IL or missing references)
			//IL_009b: Expected O, but got Unknown
			//IL_00b8: Unknown result type (might be due to invalid IL or missing references)
			//IL_00be: Expected O, but got Unknown
			if (instruction.opcode == OpCodes.Stloc_0)
			{
				return new CodeInstruction(OpCodes.Ldloc_0, (object)null);
			}
			if (instruction.opcode == OpCodes.Stloc_1)
			{
				return new CodeInstruction(OpCodes.Ldloc_1, (object)null);
			}
			if (instruction.opcode == OpCodes.Stloc_2)
			{
				return new CodeInstruction(OpCodes.Ldloc_2, (object)null);
			}
			if (instruction.opcode == OpCodes.Stloc_3)
			{
				return new CodeInstruction(OpCodes.Ldloc_3, (object)null);
			}
			if (instruction.opcode == OpCodes.Stloc_S)
			{
				return new CodeInstruction(OpCodes.Ldloca_S, instruction.operand);
			}
			if (instruction.opcode == OpCodes.Stloc)
			{
				return new CodeInstruction(OpCodes.Ldloc, instruction.operand);
			}
			throw new ArgumentException($"Unexpected instruction '{instruction}' encountered. Expected an {OpCodes.Stloc}.");
		}

		public static CodeInstruction GetStlocFromLdloc(this CodeInstruction instruction)
		{
			//IL_0018: Unknown result type (might be due to invalid IL or missing references)
			//IL_001e: Expected O, but got Unknown
			//IL_0036: Unknown result type (might be due to invalid IL or missing references)
			//IL_003c: Expected O, but got Unknown
			//IL_0054: Unknown result type (might be due to invalid IL or missing references)
			//IL_005a: Expected O, but got Unknown
			//IL_0072: Unknown result type (might be due to invalid IL or missing references)
			//IL_0078: Expected O, but got Unknown
			//IL_0095: Unknown result type (might be due to invalid IL or missing references)
			//IL_009b: Expected O, but got Unknown
			//IL_00b8: Unknown result type (might be due to invalid IL or missing references)
			//IL_00be: Expected O, but got Unknown
			if (instruction.opcode == OpCodes.Ldloc_0)
			{
				return new CodeInstruction(OpCodes.Stloc_0, (object)null);
			}
			if (instruction.opcode == OpCodes.Ldloc_1)
			{
				return new CodeInstruction(OpCodes.Stloc_1, (object)null);
			}
			if (instruction.opcode == OpCodes.Ldloc_2)
			{
				return new CodeInstruction(OpCodes.Stloc_2, (object)null);
			}
			if (instruction.opcode == OpCodes.Ldloc_3)
			{
				return new CodeInstruction(OpCodes.Stloc_3, (object)null);
			}
			if (instruction.opcode == OpCodes.Ldloca_S)
			{
				return new CodeInstruction(OpCodes.Stloc_S, instruction.operand);
			}
			if (instruction.opcode == OpCodes.Ldloc)
			{
				return new CodeInstruction(OpCodes.Stloc, instruction.operand);
			}
			throw new ArgumentException($"Unexpected instruction '{instruction}' encountered. Expected an {OpCodes.Ldloc}.");
		}
	}
	public static class CodeMatcherExtensions
	{
		public static CodeMatcher GetPosition(this CodeMatcher codeMatcher, out int position)
		{
			position = codeMatcher.Pos;
			return codeMatcher;
		}

		public static CodeMatcher InsertAndAdvance(this CodeMatcher codeMatcher, OpCode opcode)
		{
			//IL_000b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0011: Expected O, but got Unknown
			codeMatcher.InsertAndAdvance((CodeInstruction[])(object)new CodeInstruction[1]
			{
				new CodeInstruction(opcode, (object)null)
			});
			return codeMatcher;
		}

		public static CodeMatcher InsertAndAdvance(this CodeMatcher codeMatcher, MethodInfo method)
		{
			//IL_000f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0015: Expected O, but got Unknown
			codeMatcher.InsertAndAdvance((CodeInstruction[])(object)new CodeInstruction[1]
			{
				new CodeInstruction(OpCodes.Call, (object)method)
			});
			return codeMatcher;
		}

		public static CodeMatcher InsertAndAdvance<T>(this CodeMatcher codeMatcher, string methodName)
		{
			return codeMatcher.InsertAndAdvance(AccessTools.Method(typeof(T), methodName, (Type[])null, (Type[])null));
		}

		public static CodeMatcher GetOpcode(this CodeMatcher codeMatcher, out OpCode opcode)
		{
			opcode = codeMatcher.Opcode;
			return codeMatcher;
		}

		public static CodeMatcher GetInstruction(this CodeMatcher codeMatcher, out CodeInstruction instruction)
		{
			instruction = codeMatcher.Instruction;
			return codeMatcher;
		}

		public static CodeMatcher GetOperand(this CodeMatcher codeMatcher, out object operand)
		{
			operand = codeMatcher.Operand;
			return codeMatcher;
		}

		internal static CodeMatcher Print(this CodeMatcher codeMatcher, int before, int after)
		{
			return codeMatcher;
		}
	}
	internal static class EnumExtensions
	{
		public static List<TEnum> Split<TEnum>(this TEnum enumVal) where TEnum : struct, Enum
		{
			int num = Convert.ToInt32(enumVal);
			List<TEnum> list = new List<TEnum>();
			foreach (TEnum value in Enum.GetValues(typeof(TEnum)))
			{
				if ((num & Convert.ToInt32(value)) > 0)
				{
					list.Add(value);
				}
			}
			return list;
		}

		public static List<Biome> Split(this Biome biomeMask)
		{
			//IL_0023: Unknown result type (might be due to invalid IL or missing references)
			//IL_0028: Unknown result type (might be due to invalid IL or missing references)
			//IL_0029: Unknown result type (might be due to invalid IL or missing references)
			//IL_002f: Invalid comparison between Unknown and I4
			//IL_0042: Unknown result type (might be due to invalid IL or missing references)
			//IL_0043: Unknown result type (might be due to invalid IL or missing references)
			//IL_0044: Unknown result type (might be due to invalid IL or missing references)
			//IL_0046: Invalid comparison between Unknown and I4
			//IL_0031: Unknown result type (might be due to invalid IL or missing references)
			//IL_0037: Invalid comparison between Unknown and I4
			//IL_0049: Unknown result type (might be due to invalid IL or missing references)
			//IL_003a: Unknown result type (might be due to invalid IL or missing references)
			List<Biome> list = new List<Biome>();
			foreach (Biome value in Enum.GetValues(typeof(Biome)))
			{
				if ((int)value == 895)
				{
					if ((int)biomeMask == 895)
					{
						list.Add(value);
					}
				}
				else if ((biomeMask & value) > 0)
				{
					list.Add(value);
				}
			}
			return list;
		}
	}
	internal static class ICollectionExtensions
	{
		public static void AddNullSafe<T>(this ICollection<T> collection, T newEntry) where T : class
		{
			if (collection != null && newEntry != null)
			{
				Object val = (Object)(object)((newEntry is Object) ? newEntry : null);
				if (val == null || Object.op_Implicit(val))
				{
					collection.Add(newEntry);
				}
			}
		}

		public static string Join(this ICollection<float> list)
		{
			return list.Join((float x) => x.ToString(CultureInfo.InvariantCulture));
		}

		public static string Join(this ICollection<double> list)
		{
			return list.Join((double x) => x.ToString(CultureInfo.InvariantCulture));
		}

		public static string Join<T>(this ICollection<T> list)
		{
			if (list == null || list.Count == 0)
			{
				return "";
			}
			return string.Join(", ", list);
		}

		public static string Join<T>(this ICollection<T> list, Func<T, string> tostring)
		{
			if (list == null || list.Count == 0)
			{
				return string.Empty;
			}
			return string.Join(", ", list.Select((T x) => tostring(x)));
		}

		public static string Join<T, K>(this ICollection<T> list, Func<T, K> selector)
		{
			if (list == null || list.Count == 0)
			{
				return string.E

YamlDotNet.dll

Decompiled 2 months ago
using System;
using System.Collections;
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Diagnostics;
using System.Diagnostics.CodeAnalysis;
using System.Globalization;
using System.IO;
using System.Linq;
using System.Linq.Expressions;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.Serialization;
using System.Runtime.Versioning;
using System.Security.Permissions;
using System.Text;
using System.Text.RegularExpressions;
using Microsoft.CodeAnalysis;
using YamlDotNet.Core;
using YamlDotNet.Core.Events;
using YamlDotNet.Core.Tokens;
using YamlDotNet.Helpers;
using YamlDotNet.Serialization;
using YamlDotNet.Serialization.Converters;
using YamlDotNet.Serialization.EventEmitters;
using YamlDotNet.Serialization.NamingConventions;
using YamlDotNet.Serialization.NodeDeserializers;
using YamlDotNet.Serialization.NodeTypeResolvers;
using YamlDotNet.Serialization.ObjectFactories;
using YamlDotNet.Serialization.ObjectGraphTraversalStrategies;
using YamlDotNet.Serialization.ObjectGraphVisitors;
using YamlDotNet.Serialization.Schemas;
using YamlDotNet.Serialization.TypeInspectors;
using YamlDotNet.Serialization.TypeResolvers;
using YamlDotNet.Serialization.Utilities;
using YamlDotNet.Serialization.ValueDeserializers;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: ComVisible(false)]
[assembly: AssemblyFileVersion("11.2.1.0")]
[assembly: AssemblyInformationalVersion("11.2.1")]
[assembly: AssemblyTitle("YamlDotNet")]
[assembly: AssemblyDescription("The YamlDotNet library.")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("YamlDotNet")]
[assembly: AssemblyCopyright("Copyright (c) Antoine Aubry and contributors 2008 - 2019")]
[assembly: AssemblyTrademark("")]
[assembly: CLSCompliant(true)]
[assembly: InternalsVisibleTo("YamlDotNet.Test, PublicKey=002400000480000094000000060200000024000052534131000400000100010065e52a453dde5c5b4be5bbe2205755727fce80244b79b894faf8793d80f7db9a96d360b51c220782db32aacee4cb5b8a91bee33aeec700e1f21895c4baadef501eeeac609220d1651603b378173811ee5bb6a002df973d38821bd2fef820c00c174a69faec326a1983b570f07ec66147026b9c8753465de3a8d0c44b613b02af")]
[assembly: TargetFramework(".NETFramework,Version=v4.5", FrameworkDisplayName = ".NET Framework 4.5")]
[assembly: AssemblyVersion("11.0.0.0")]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	internal sealed class EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	[AttributeUsage(AttributeTargets.Class | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Event | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, AllowMultiple = false, Inherited = false)]
	internal sealed class NullableAttribute : Attribute
	{
		public readonly byte[] NullableFlags;

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

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

		public NullableContextAttribute(byte P_0)
		{
			Flag = P_0;
		}
	}
}
namespace System.Diagnostics.CodeAnalysis
{
	[AttributeUsage(AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter, Inherited = false)]
	internal sealed class AllowNullAttribute : Attribute
	{
	}
	[AttributeUsage(AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter, Inherited = false)]
	internal sealed class DisallowNullAttribute : Attribute
	{
	}
	[AttributeUsage(AttributeTargets.Method, Inherited = false)]
	internal sealed class DoesNotReturnAttribute : Attribute
	{
	}
	[AttributeUsage(AttributeTargets.Parameter, Inherited = false)]
	internal sealed class DoesNotReturnIfAttribute : Attribute
	{
		public bool ParameterValue { get; }

		public DoesNotReturnIfAttribute(bool parameterValue)
		{
			ParameterValue = parameterValue;
		}
	}
	[AttributeUsage(AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter | AttributeTargets.ReturnValue, Inherited = false)]
	internal sealed class MaybeNullAttribute : Attribute
	{
	}
	[AttributeUsage(AttributeTargets.Parameter, Inherited = false)]
	internal sealed class MaybeNullWhenAttribute : Attribute
	{
		public bool ReturnValue { get; }

		public MaybeNullWhenAttribute(bool returnValue)
		{
			ReturnValue = returnValue;
		}
	}
	[AttributeUsage(AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter | AttributeTargets.ReturnValue, Inherited = false)]
	internal sealed class NotNullAttribute : Attribute
	{
	}
	[AttributeUsage(AttributeTargets.Property | AttributeTargets.Parameter | AttributeTargets.ReturnValue, AllowMultiple = true, Inherited = false)]
	internal sealed class NotNullIfNotNullAttribute : Attribute
	{
		public string ParameterName { get; }

		public NotNullIfNotNullAttribute(string parameterName)
		{
			ParameterName = parameterName;
		}
	}
	[AttributeUsage(AttributeTargets.Parameter, Inherited = false)]
	internal sealed class NotNullWhenAttribute : Attribute
	{
		public bool ReturnValue { get; }

		public NotNullWhenAttribute(bool returnValue)
		{
			ReturnValue = returnValue;
		}
	}
}
namespace System.Collections.Generic
{
	internal static class DeconstructionExtensions
	{
		public static void Deconstruct<TKey, TValue>(this KeyValuePair<TKey, TValue> pair, out TKey key, out TValue value)
		{
			key = pair.Key;
			value = pair.Value;
		}
	}
}
namespace YamlDotNet
{
	internal sealed class CultureInfoAdapter : CultureInfo
	{
		private readonly IFormatProvider provider;

		public CultureInfoAdapter(CultureInfo baseCulture, IFormatProvider provider)
			: base(baseCulture.LCID)
		{
			this.provider = provider;
		}

		public override object? GetFormat(Type? formatType)
		{
			return provider.GetFormat(formatType);
		}
	}
	internal static class ReflectionExtensions
	{
		private static readonly FieldInfo? RemoteStackTraceField = typeof(Exception).GetField("_remoteStackTraceString", BindingFlags.Instance | BindingFlags.NonPublic);

		public static Type? BaseType(this Type type)
		{
			return type.BaseType;
		}

		public static bool IsValueType(this Type type)
		{
			return type.IsValueType;
		}

		public static bool IsGenericType(this Type type)
		{
			return type.IsGenericType;
		}

		public static bool IsGenericTypeDefinition(this Type type)
		{
			return type.IsGenericTypeDefinition;
		}

		public static bool IsInterface(this Type type)
		{
			return type.IsInterface;
		}

		public static bool IsEnum(this Type type)
		{
			return type.IsEnum;
		}

		public static bool IsDbNull(this object value)
		{
			return value is DBNull;
		}

		public static bool HasDefaultConstructor(this Type type)
		{
			if (!type.IsValueType)
			{
				return type.GetConstructor(BindingFlags.Instance | BindingFlags.Public, null, Type.EmptyTypes, null) != null;
			}
			return true;
		}

		public static TypeCode GetTypeCode(this Type type)
		{
			return Type.GetTypeCode(type);
		}

		public static PropertyInfo? GetPublicProperty(this Type type, string name)
		{
			return type.GetProperty(name);
		}

		public static FieldInfo? GetPublicStaticField(this Type type, string name)
		{
			return type.GetField(name, BindingFlags.Static | BindingFlags.Public);
		}

		public static IEnumerable<PropertyInfo> GetProperties(this Type type, bool includeNonPublic)
		{
			BindingFlags bindingFlags = BindingFlags.Instance | BindingFlags.Public;
			if (includeNonPublic)
			{
				bindingFlags |= BindingFlags.NonPublic;
			}
			if (!type.IsInterface)
			{
				return type.GetProperties(bindingFlags);
			}
			return new Type[1] { type }.Concat(type.GetInterfaces()).SelectMany((Type i) => i.GetProperties(bindingFlags));
		}

		public static IEnumerable<PropertyInfo> GetPublicProperties(this Type type)
		{
			return type.GetProperties(includeNonPublic: false);
		}

		public static IEnumerable<FieldInfo> GetPublicFields(this Type type)
		{
			return type.GetFields(BindingFlags.Instance | BindingFlags.Public);
		}

		public static IEnumerable<MethodInfo> GetPublicStaticMethods(this Type type)
		{
			return type.GetMethods(BindingFlags.Static | BindingFlags.Public);
		}

		public static MethodInfo GetPrivateStaticMethod(this Type type, string name)
		{
			return type.GetMethod(name, BindingFlags.Static | BindingFlags.NonPublic) ?? throw new MissingMethodException("Expected to find a method named '" + name + "' in '" + type.FullName + "'.");
		}

		public static MethodInfo? GetPublicStaticMethod(this Type type, string name, params Type[] parameterTypes)
		{
			return type.GetMethod(name, BindingFlags.Static | BindingFlags.Public, null, parameterTypes, null);
		}

		public static MethodInfo? GetPublicInstanceMethod(this Type type, string name)
		{
			return type.GetMethod(name, BindingFlags.Instance | BindingFlags.Public);
		}

		public static Exception Unwrap(this TargetInvocationException ex)
		{
			Exception innerException = ex.InnerException;
			if (innerException == null)
			{
				return ex;
			}
			if (RemoteStackTraceField != null)
			{
				RemoteStackTraceField.SetValue(innerException, innerException.StackTrace + "\r\n");
			}
			return innerException;
		}

		public static bool IsInstanceOf(this Type type, object o)
		{
			return type.IsInstanceOfType(o);
		}

		public static Attribute[] GetAllCustomAttributes<TAttribute>(this PropertyInfo property)
		{
			return Attribute.GetCustomAttributes(property, typeof(TAttribute));
		}
	}
	internal static class PropertyInfoExtensions
	{
		public static object? ReadValue(this PropertyInfo property, object target)
		{
			return property.GetValue(target, null);
		}
	}
	internal static class StandardRegexOptions
	{
		public const RegexOptions Compiled = RegexOptions.Compiled;
	}
}
namespace YamlDotNet.Serialization
{
	public abstract class BuilderSkeleton<TBuilder> where TBuilder : BuilderSkeleton<TBuilder>
	{
		internal INamingConvention namingConvention = NullNamingConvention.Instance;

		internal ITypeResolver typeResolver;

		internal readonly YamlAttributeOverrides overrides;

		internal readonly LazyComponentRegistrationList<Nothing, IYamlTypeConverter> typeConverterFactories;

		internal readonly LazyComponentRegistrationList<ITypeInspector, ITypeInspector> typeInspectorFactories;

		private bool ignoreFields;

		private bool includeNonPublicProperties;

		protected abstract TBuilder Self { get; }

		internal BuilderSkeleton(ITypeResolver typeResolver)
		{
			overrides = new YamlAttributeOverrides();
			typeConverterFactories = new LazyComponentRegistrationList<Nothing, IYamlTypeConverter>
			{
				{
					typeof(YamlDotNet.Serialization.Converters.GuidConverter),
					(Nothing _) => new YamlDotNet.Serialization.Converters.GuidConverter(jsonCompatible: false)
				},
				{
					typeof(SystemTypeConverter),
					(Nothing _) => new SystemTypeConverter()
				}
			};
			typeInspectorFactories = new LazyComponentRegistrationList<ITypeInspector, ITypeInspector>();
			this.typeResolver = typeResolver ?? throw new ArgumentNullException("typeResolver");
		}

		internal ITypeInspector BuildTypeInspector()
		{
			ITypeInspector typeInspector = new ReadablePropertiesTypeInspector(typeResolver, includeNonPublicProperties);
			if (!ignoreFields)
			{
				typeInspector = new CompositeTypeInspector(new ReadableFieldsTypeInspector(typeResolver), typeInspector);
			}
			return typeInspectorFactories.BuildComponentChain(typeInspector);
		}

		public TBuilder IgnoreFields()
		{
			ignoreFields = true;
			return Self;
		}

		public TBuilder IncludeNonPublicProperties()
		{
			includeNonPublicProperties = true;
			return Self;
		}

		public TBuilder WithNamingConvention(INamingConvention namingConvention)
		{
			this.namingConvention = namingConvention ?? throw new ArgumentNullException("namingConvention");
			return Self;
		}

		public TBuilder WithTypeResolver(ITypeResolver typeResolver)
		{
			this.typeResolver = typeResolver ?? throw new ArgumentNullException("typeResolver");
			return Self;
		}

		public abstract TBuilder WithTagMapping(TagName tag, Type type);

		public TBuilder WithAttributeOverride<TClass>(Expression<Func<TClass, object>> propertyAccessor, Attribute attribute)
		{
			overrides.Add(propertyAccessor, attribute);
			return Self;
		}

		public TBuilder WithAttributeOverride(Type type, string member, Attribute attribute)
		{
			overrides.Add(type, member, attribute);
			return Self;
		}

		public TBuilder WithTypeConverter(IYamlTypeConverter typeConverter)
		{
			return WithTypeConverter(typeConverter, delegate(IRegistrationLocationSelectionSyntax<IYamlTypeConverter> w)
			{
				w.OnTop();
			});
		}

		public TBuilder WithTypeConverter(IYamlTypeConverter typeConverter, Action<IRegistrationLocationSelectionSyntax<IYamlTypeConverter>> where)
		{
			IYamlTypeConverter typeConverter2 = typeConverter;
			if (typeConverter2 == null)
			{
				throw new ArgumentNullException("typeConverter");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(typeConverterFactories.CreateRegistrationLocationSelector(typeConverter2.GetType(), (Nothing _) => typeConverter2));
			return Self;
		}

		public TBuilder WithTypeConverter<TYamlTypeConverter>(WrapperFactory<IYamlTypeConverter, IYamlTypeConverter> typeConverterFactory, Action<ITrackingRegistrationLocationSelectionSyntax<IYamlTypeConverter>> where) where TYamlTypeConverter : IYamlTypeConverter
		{
			WrapperFactory<IYamlTypeConverter, IYamlTypeConverter> typeConverterFactory2 = typeConverterFactory;
			if (typeConverterFactory2 == null)
			{
				throw new ArgumentNullException("typeConverterFactory");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(typeConverterFactories.CreateTrackingRegistrationLocationSelector(typeof(TYamlTypeConverter), (IYamlTypeConverter wrapped, Nothing _) => typeConverterFactory2(wrapped)));
			return Self;
		}

		public TBuilder WithoutTypeConverter<TYamlTypeConverter>() where TYamlTypeConverter : IYamlTypeConverter
		{
			return WithoutTypeConverter(typeof(TYamlTypeConverter));
		}

		public TBuilder WithoutTypeConverter(Type converterType)
		{
			if (converterType == null)
			{
				throw new ArgumentNullException("converterType");
			}
			typeConverterFactories.Remove(converterType);
			return Self;
		}

		public TBuilder WithTypeInspector<TTypeInspector>(Func<ITypeInspector, TTypeInspector> typeInspectorFactory) where TTypeInspector : ITypeInspector
		{
			return WithTypeInspector(typeInspectorFactory, delegate(IRegistrationLocationSelectionSyntax<ITypeInspector> w)
			{
				w.OnTop();
			});
		}

		public TBuilder WithTypeInspector<TTypeInspector>(Func<ITypeInspector, TTypeInspector> typeInspectorFactory, Action<IRegistrationLocationSelectionSyntax<ITypeInspector>> where) where TTypeInspector : ITypeInspector
		{
			Func<ITypeInspector, TTypeInspector> typeInspectorFactory2 = typeInspectorFactory;
			if (typeInspectorFactory2 == null)
			{
				throw new ArgumentNullException("typeInspectorFactory");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(typeInspectorFactories.CreateRegistrationLocationSelector(typeof(TTypeInspector), (ITypeInspector inner) => typeInspectorFactory2(inner)));
			return Self;
		}

		public TBuilder WithTypeInspector<TTypeInspector>(WrapperFactory<ITypeInspector, ITypeInspector, TTypeInspector> typeInspectorFactory, Action<ITrackingRegistrationLocationSelectionSyntax<ITypeInspector>> where) where TTypeInspector : ITypeInspector
		{
			WrapperFactory<ITypeInspector, ITypeInspector, TTypeInspector> typeInspectorFactory2 = typeInspectorFactory;
			if (typeInspectorFactory2 == null)
			{
				throw new ArgumentNullException("typeInspectorFactory");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(typeInspectorFactories.CreateTrackingRegistrationLocationSelector(typeof(TTypeInspector), (ITypeInspector wrapped, ITypeInspector inner) => typeInspectorFactory2(wrapped, inner)));
			return Self;
		}

		public TBuilder WithoutTypeInspector<TTypeInspector>() where TTypeInspector : ITypeInspector
		{
			return WithoutTypeInspector(typeof(TTypeInspector));
		}

		public TBuilder WithoutTypeInspector(Type inspectorType)
		{
			if (inspectorType == null)
			{
				throw new ArgumentNullException("inspectorType");
			}
			typeInspectorFactories.Remove(inspectorType);
			return Self;
		}

		protected IEnumerable<IYamlTypeConverter> BuildTypeConverters()
		{
			return typeConverterFactories.BuildComponentList();
		}
	}
	public delegate TComponent WrapperFactory<TComponentBase, TComponent>(TComponentBase wrapped) where TComponent : TComponentBase;
	public delegate TComponent WrapperFactory<TArgument, TComponentBase, TComponent>(TComponentBase wrapped, TArgument argument) where TComponent : TComponentBase;
	[Flags]
	public enum DefaultValuesHandling
	{
		Preserve = 0,
		OmitNull = 1,
		OmitDefaults = 2,
		OmitEmptyCollections = 4
	}
	public sealed class Deserializer : IDeserializer
	{
		private readonly IValueDeserializer valueDeserializer;

		public Deserializer()
			: this(new DeserializerBuilder().BuildValueDeserializer())
		{
		}

		private Deserializer(IValueDeserializer valueDeserializer)
		{
			this.valueDeserializer = valueDeserializer ?? throw new ArgumentNullException("valueDeserializer");
		}

		public static Deserializer FromValueDeserializer(IValueDeserializer valueDeserializer)
		{
			return new Deserializer(valueDeserializer);
		}

		public T Deserialize<T>(string input)
		{
			using StringReader input2 = new StringReader(input);
			return Deserialize<T>(input2);
		}

		public T Deserialize<T>(TextReader input)
		{
			return Deserialize<T>(new Parser(input));
		}

		public object? Deserialize(TextReader input)
		{
			return Deserialize(input, typeof(object));
		}

		public object? Deserialize(string input, Type type)
		{
			using StringReader input2 = new StringReader(input);
			return Deserialize(input2, type);
		}

		public object? Deserialize(TextReader input, Type type)
		{
			return Deserialize(new Parser(input), type);
		}

		public T Deserialize<T>(IParser parser)
		{
			return (T)Deserialize(parser, typeof(T));
		}

		public object? Deserialize(IParser parser)
		{
			return Deserialize(parser, typeof(object));
		}

		public object? Deserialize(IParser parser, Type type)
		{
			if (parser == null)
			{
				throw new ArgumentNullException("parser");
			}
			if (type == null)
			{
				throw new ArgumentNullException("type");
			}
			YamlDotNet.Core.Events.StreamStart @event;
			bool flag = parser.TryConsume<YamlDotNet.Core.Events.StreamStart>(out @event);
			YamlDotNet.Core.Events.DocumentStart event2;
			bool flag2 = parser.TryConsume<YamlDotNet.Core.Events.DocumentStart>(out event2);
			object result = null;
			if (!parser.Accept<YamlDotNet.Core.Events.DocumentEnd>(out var _) && !parser.Accept<YamlDotNet.Core.Events.StreamEnd>(out var _))
			{
				using SerializerState serializerState = new SerializerState();
				result = valueDeserializer.DeserializeValue(parser, type, serializerState, valueDeserializer);
				serializerState.OnDeserialization();
			}
			if (flag2)
			{
				parser.Consume<YamlDotNet.Core.Events.DocumentEnd>();
			}
			if (flag)
			{
				parser.Consume<YamlDotNet.Core.Events.StreamEnd>();
			}
			return result;
		}
	}
	public sealed class DeserializerBuilder : BuilderSkeleton<DeserializerBuilder>
	{
		private Lazy<IObjectFactory> objectFactory;

		private readonly LazyComponentRegistrationList<Nothing, INodeDeserializer> nodeDeserializerFactories;

		private readonly LazyComponentRegistrationList<Nothing, INodeTypeResolver> nodeTypeResolverFactories;

		private readonly Dictionary<TagName, Type> tagMappings;

		private readonly Dictionary<Type, Type> typeMappings;

		private bool ignoreUnmatched;

		protected override DeserializerBuilder Self => this;

		public DeserializerBuilder()
			: base((ITypeResolver)new StaticTypeResolver())
		{
			typeMappings = new Dictionary<Type, Type>();
			objectFactory = new Lazy<IObjectFactory>(() => new DefaultObjectFactory(typeMappings), isThreadSafe: true);
			tagMappings = new Dictionary<TagName, Type>
			{
				{
					FailsafeSchema.Tags.Map,
					typeof(Dictionary<object, object>)
				},
				{
					FailsafeSchema.Tags.Str,
					typeof(string)
				},
				{
					JsonSchema.Tags.Bool,
					typeof(bool)
				},
				{
					JsonSchema.Tags.Float,
					typeof(double)
				},
				{
					JsonSchema.Tags.Int,
					typeof(int)
				},
				{
					DefaultSchema.Tags.Timestamp,
					typeof(DateTime)
				}
			};
			typeInspectorFactories.Add(typeof(CachedTypeInspector), (ITypeInspector inner) => new CachedTypeInspector(inner));
			typeInspectorFactories.Add(typeof(NamingConventionTypeInspector), (ITypeInspector inner) => (!(namingConvention is NullNamingConvention)) ? new NamingConventionTypeInspector(inner, namingConvention) : inner);
			typeInspectorFactories.Add(typeof(YamlAttributesTypeInspector), (ITypeInspector inner) => new YamlAttributesTypeInspector(inner));
			typeInspectorFactories.Add(typeof(YamlAttributeOverridesInspector), (ITypeInspector inner) => (overrides == null) ? inner : new YamlAttributeOverridesInspector(inner, overrides.Clone()));
			typeInspectorFactories.Add(typeof(ReadableAndWritablePropertiesTypeInspector), (ITypeInspector inner) => new ReadableAndWritablePropertiesTypeInspector(inner));
			nodeDeserializerFactories = new LazyComponentRegistrationList<Nothing, INodeDeserializer>
			{
				{
					typeof(YamlConvertibleNodeDeserializer),
					(Nothing _) => new YamlConvertibleNodeDeserializer(objectFactory.Value)
				},
				{
					typeof(YamlSerializableNodeDeserializer),
					(Nothing _) => new YamlSerializableNodeDeserializer(objectFactory.Value)
				},
				{
					typeof(TypeConverterNodeDeserializer),
					(Nothing _) => new TypeConverterNodeDeserializer(BuildTypeConverters())
				},
				{
					typeof(NullNodeDeserializer),
					(Nothing _) => new NullNodeDeserializer()
				},
				{
					typeof(ScalarNodeDeserializer),
					(Nothing _) => new ScalarNodeDeserializer()
				},
				{
					typeof(ArrayNodeDeserializer),
					(Nothing _) => new ArrayNodeDeserializer()
				},
				{
					typeof(DictionaryNodeDeserializer),
					(Nothing _) => new DictionaryNodeDeserializer(objectFactory.Value)
				},
				{
					typeof(CollectionNodeDeserializer),
					(Nothing _) => new CollectionNodeDeserializer(objectFactory.Value)
				},
				{
					typeof(EnumerableNodeDeserializer),
					(Nothing _) => new EnumerableNodeDeserializer()
				},
				{
					typeof(ObjectNodeDeserializer),
					(Nothing _) => new ObjectNodeDeserializer(objectFactory.Value, BuildTypeInspector(), ignoreUnmatched)
				}
			};
			nodeTypeResolverFactories = new LazyComponentRegistrationList<Nothing, INodeTypeResolver>
			{
				{
					typeof(MappingNodeTypeResolver),
					(Nothing _) => new MappingNodeTypeResolver(typeMappings)
				},
				{
					typeof(YamlConvertibleTypeResolver),
					(Nothing _) => new YamlConvertibleTypeResolver()
				},
				{
					typeof(YamlSerializableTypeResolver),
					(Nothing _) => new YamlSerializableTypeResolver()
				},
				{
					typeof(TagNodeTypeResolver),
					(Nothing _) => new TagNodeTypeResolver(tagMappings)
				},
				{
					typeof(PreventUnknownTagsNodeTypeResolver),
					(Nothing _) => new PreventUnknownTagsNodeTypeResolver()
				},
				{
					typeof(DefaultContainersNodeTypeResolver),
					(Nothing _) => new DefaultContainersNodeTypeResolver()
				}
			};
		}

		public DeserializerBuilder WithObjectFactory(IObjectFactory objectFactory)
		{
			IObjectFactory objectFactory2 = objectFactory;
			if (objectFactory2 == null)
			{
				throw new ArgumentNullException("objectFactory");
			}
			this.objectFactory = new Lazy<IObjectFactory>(() => objectFactory2, isThreadSafe: true);
			return this;
		}

		public DeserializerBuilder WithObjectFactory(Func<Type, object> objectFactory)
		{
			if (objectFactory == null)
			{
				throw new ArgumentNullException("objectFactory");
			}
			return WithObjectFactory(new LambdaObjectFactory(objectFactory));
		}

		public DeserializerBuilder WithNodeDeserializer(INodeDeserializer nodeDeserializer)
		{
			return WithNodeDeserializer(nodeDeserializer, delegate(IRegistrationLocationSelectionSyntax<INodeDeserializer> w)
			{
				w.OnTop();
			});
		}

		public DeserializerBuilder WithNodeDeserializer(INodeDeserializer nodeDeserializer, Action<IRegistrationLocationSelectionSyntax<INodeDeserializer>> where)
		{
			INodeDeserializer nodeDeserializer2 = nodeDeserializer;
			if (nodeDeserializer2 == null)
			{
				throw new ArgumentNullException("nodeDeserializer");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(nodeDeserializerFactories.CreateRegistrationLocationSelector(nodeDeserializer2.GetType(), (Nothing _) => nodeDeserializer2));
			return this;
		}

		public DeserializerBuilder WithNodeDeserializer<TNodeDeserializer>(WrapperFactory<INodeDeserializer, TNodeDeserializer> nodeDeserializerFactory, Action<ITrackingRegistrationLocationSelectionSyntax<INodeDeserializer>> where) where TNodeDeserializer : INodeDeserializer
		{
			WrapperFactory<INodeDeserializer, TNodeDeserializer> nodeDeserializerFactory2 = nodeDeserializerFactory;
			if (nodeDeserializerFactory2 == null)
			{
				throw new ArgumentNullException("nodeDeserializerFactory");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(nodeDeserializerFactories.CreateTrackingRegistrationLocationSelector(typeof(TNodeDeserializer), (INodeDeserializer wrapped, Nothing _) => nodeDeserializerFactory2(wrapped)));
			return this;
		}

		public DeserializerBuilder WithoutNodeDeserializer<TNodeDeserializer>() where TNodeDeserializer : INodeDeserializer
		{
			return WithoutNodeDeserializer(typeof(TNodeDeserializer));
		}

		public DeserializerBuilder WithoutNodeDeserializer(Type nodeDeserializerType)
		{
			if (nodeDeserializerType == null)
			{
				throw new ArgumentNullException("nodeDeserializerType");
			}
			nodeDeserializerFactories.Remove(nodeDeserializerType);
			return this;
		}

		public DeserializerBuilder WithNodeTypeResolver(INodeTypeResolver nodeTypeResolver)
		{
			return WithNodeTypeResolver(nodeTypeResolver, delegate(IRegistrationLocationSelectionSyntax<INodeTypeResolver> w)
			{
				w.OnTop();
			});
		}

		public DeserializerBuilder WithNodeTypeResolver(INodeTypeResolver nodeTypeResolver, Action<IRegistrationLocationSelectionSyntax<INodeTypeResolver>> where)
		{
			INodeTypeResolver nodeTypeResolver2 = nodeTypeResolver;
			if (nodeTypeResolver2 == null)
			{
				throw new ArgumentNullException("nodeTypeResolver");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(nodeTypeResolverFactories.CreateRegistrationLocationSelector(nodeTypeResolver2.GetType(), (Nothing _) => nodeTypeResolver2));
			return this;
		}

		public DeserializerBuilder WithNodeTypeResolver<TNodeTypeResolver>(WrapperFactory<INodeTypeResolver, TNodeTypeResolver> nodeTypeResolverFactory, Action<ITrackingRegistrationLocationSelectionSyntax<INodeTypeResolver>> where) where TNodeTypeResolver : INodeTypeResolver
		{
			WrapperFactory<INodeTypeResolver, TNodeTypeResolver> nodeTypeResolverFactory2 = nodeTypeResolverFactory;
			if (nodeTypeResolverFactory2 == null)
			{
				throw new ArgumentNullException("nodeTypeResolverFactory");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(nodeTypeResolverFactories.CreateTrackingRegistrationLocationSelector(typeof(TNodeTypeResolver), (INodeTypeResolver wrapped, Nothing _) => nodeTypeResolverFactory2(wrapped)));
			return this;
		}

		public DeserializerBuilder WithoutNodeTypeResolver<TNodeTypeResolver>() where TNodeTypeResolver : INodeTypeResolver
		{
			return WithoutNodeTypeResolver(typeof(TNodeTypeResolver));
		}

		public DeserializerBuilder WithoutNodeTypeResolver(Type nodeTypeResolverType)
		{
			if (nodeTypeResolverType == null)
			{
				throw new ArgumentNullException("nodeTypeResolverType");
			}
			nodeTypeResolverFactories.Remove(nodeTypeResolverType);
			return this;
		}

		public override DeserializerBuilder WithTagMapping(TagName tag, Type type)
		{
			if (tag.IsEmpty)
			{
				throw new ArgumentException("Non-specific tags cannot be maped");
			}
			if (type == null)
			{
				throw new ArgumentNullException("type");
			}
			if (tagMappings.TryGetValue(tag, out Type value))
			{
				throw new ArgumentException($"Type already has a registered type '{value.FullName}' for tag '{tag}'", "tag");
			}
			tagMappings.Add(tag, type);
			return this;
		}

		public DeserializerBuilder WithTypeMapping<TInterface, TConcrete>() where TConcrete : TInterface
		{
			Type typeFromHandle = typeof(TInterface);
			Type typeFromHandle2 = typeof(TConcrete);
			if (!typeFromHandle.IsAssignableFrom(typeFromHandle2))
			{
				throw new InvalidOperationException("The type '" + typeFromHandle2.Name + "' does not implement interface '" + typeFromHandle.Name + "'.");
			}
			if (typeMappings.ContainsKey(typeFromHandle))
			{
				typeMappings[typeFromHandle] = typeFromHandle2;
			}
			else
			{
				typeMappings.Add(typeFromHandle, typeFromHandle2);
			}
			return this;
		}

		public DeserializerBuilder WithoutTagMapping(TagName tag)
		{
			if (tag.IsEmpty)
			{
				throw new ArgumentException("Non-specific tags cannot be maped");
			}
			if (!tagMappings.Remove(tag))
			{
				throw new KeyNotFoundException($"Tag '{tag}' is not registered");
			}
			return this;
		}

		public DeserializerBuilder IgnoreUnmatchedProperties()
		{
			ignoreUnmatched = true;
			return this;
		}

		public IDeserializer Build()
		{
			return Deserializer.FromValueDeserializer(BuildValueDeserializer());
		}

		public IValueDeserializer BuildValueDeserializer()
		{
			return new AliasValueDeserializer(new NodeValueDeserializer(nodeDeserializerFactories.BuildComponentList(), nodeTypeResolverFactories.BuildComponentList()));
		}
	}
	public sealed class EmissionPhaseObjectGraphVisitorArgs
	{
		private readonly IEnumerable<IObjectGraphVisitor<Nothing>> preProcessingPhaseVisitors;

		public IObjectGraphVisitor<IEmitter> InnerVisitor { get; private set; }

		public IEventEmitter EventEmitter { get; private set; }

		public ObjectSerializer NestedObjectSerializer { get; private set; }

		public IEnumerable<IYamlTypeConverter> TypeConverters { get; private set; }

		public EmissionPhaseObjectGraphVisitorArgs(IObjectGraphVisitor<IEmitter> innerVisitor, IEventEmitter eventEmitter, IEnumerable<IObjectGraphVisitor<Nothing>> preProcessingPhaseVisitors, IEnumerable<IYamlTypeConverter> typeConverters, ObjectSerializer nestedObjectSerializer)
		{
			InnerVisitor = innerVisitor ?? throw new ArgumentNullException("innerVisitor");
			EventEmitter = eventEmitter ?? throw new ArgumentNullException("eventEmitter");
			this.preProcessingPhaseVisitors = preProcessingPhaseVisitors ?? throw new ArgumentNullException("preProcessingPhaseVisitors");
			TypeConverters = typeConverters ?? throw new ArgumentNullException("typeConverters");
			NestedObjectSerializer = nestedObjectSerializer ?? throw new ArgumentNullException("nestedObjectSerializer");
		}

		public T GetPreProcessingPhaseObjectGraphVisitor<T>() where T : IObjectGraphVisitor<Nothing>
		{
			return preProcessingPhaseVisitors.OfType<T>().Single();
		}
	}
	public abstract class EventInfo
	{
		public IObjectDescriptor Source { get; }

		protected EventInfo(IObjectDescriptor source)
		{
			Source = source ?? throw new ArgumentNullException("source");
		}
	}
	public class AliasEventInfo : EventInfo
	{
		public AnchorName Alias { get; }

		public bool NeedsExpansion { get; set; }

		public AliasEventInfo(IObjectDescriptor source, AnchorName alias)
			: base(source)
		{
			if (alias.IsEmpty)
			{
				throw new ArgumentNullException("alias");
			}
			Alias = alias;
		}
	}
	public class ObjectEventInfo : EventInfo
	{
		public AnchorName Anchor { get; set; }

		public TagName Tag { get; set; }

		protected ObjectEventInfo(IObjectDescriptor source)
			: base(source)
		{
		}
	}
	public sealed class ScalarEventInfo : ObjectEventInfo
	{
		public string RenderedValue { get; set; }

		public ScalarStyle Style { get; set; }

		public bool IsPlainImplicit { get; set; }

		public bool IsQuotedImplicit { get; set; }

		public ScalarEventInfo(IObjectDescriptor source)
			: base(source)
		{
			Style = source.ScalarStyle;
			RenderedValue = string.Empty;
		}
	}
	public sealed class MappingStartEventInfo : ObjectEventInfo
	{
		public bool IsImplicit { get; set; }

		public MappingStyle Style { get; set; }

		public MappingStartEventInfo(IObjectDescriptor source)
			: base(source)
		{
		}
	}
	public sealed class MappingEndEventInfo : EventInfo
	{
		public MappingEndEventInfo(IObjectDescriptor source)
			: base(source)
		{
		}
	}
	public sealed class SequenceStartEventInfo : ObjectEventInfo
	{
		public bool IsImplicit { get; set; }

		public SequenceStyle Style { get; set; }

		public SequenceStartEventInfo(IObjectDescriptor source)
			: base(source)
		{
		}
	}
	public sealed class SequenceEndEventInfo : EventInfo
	{
		public SequenceEndEventInfo(IObjectDescriptor source)
			: base(source)
		{
		}
	}
	public interface IAliasProvider
	{
		AnchorName GetAlias(object target);
	}
	public interface IDeserializer
	{
		T Deserialize<T>(string input);

		T Deserialize<T>(TextReader input);

		object? Deserialize(TextReader input);

		object? Deserialize(string input, Type type);

		object? Deserialize(TextReader input, Type type);

		T Deserialize<T>(IParser parser);

		object? Deserialize(IParser parser);

		object? Deserialize(IParser parser, Type type);
	}
	public interface IEventEmitter
	{
		void Emit(AliasEventInfo eventInfo, IEmitter emitter);

		void Emit(ScalarEventInfo eventInfo, IEmitter emitter);

		void Emit(MappingStartEventInfo eventInfo, IEmitter emitter);

		void Emit(MappingEndEventInfo eventInfo, IEmitter emitter);

		void Emit(SequenceStartEventInfo eventInfo, IEmitter emitter);

		void Emit(SequenceEndEventInfo eventInfo, IEmitter emitter);
	}
	public interface INamingConvention
	{
		string Apply(string value);
	}
	public interface INodeDeserializer
	{
		bool Deserialize(IParser reader, Type expectedType, Func<IParser, Type, object?> nestedObjectDeserializer, out object? value);
	}
	public interface INodeTypeResolver
	{
		bool Resolve(NodeEvent? nodeEvent, ref Type currentType);
	}
	public interface IObjectDescriptor
	{
		object? Value { get; }

		Type Type { get; }

		Type StaticType { get; }

		ScalarStyle ScalarStyle { get; }
	}
	public static class ObjectDescriptorExtensions
	{
		public static object NonNullValue(this IObjectDescriptor objectDescriptor)
		{
			return objectDescriptor.Value ?? throw new InvalidOperationException("Attempted to use a IObjectDescriptor of type '" + objectDescriptor.Type.FullName + "' whose Value is null at a point whete it is invalid to do so. This may indicate a bug in YamlDotNet.");
		}
	}
	public interface IObjectFactory
	{
		object Create(Type type);
	}
	public interface IObjectGraphTraversalStrategy
	{
		void Traverse<TContext>(IObjectDescriptor graph, IObjectGraphVisitor<TContext> visitor, TContext context);
	}
	public interface IObjectGraphVisitor<TContext>
	{
		bool Enter(IObjectDescriptor value, TContext context);

		bool EnterMapping(IObjectDescriptor key, IObjectDescriptor value, TContext context);

		bool EnterMapping(IPropertyDescriptor key, IObjectDescriptor value, TContext context);

		void VisitScalar(IObjectDescriptor scalar, TContext context);

		void VisitMappingStart(IObjectDescriptor mapping, Type keyType, Type valueType, TContext context);

		void VisitMappingEnd(IObjectDescriptor mapping, TContext context);

		void VisitSequenceStart(IObjectDescriptor sequence, Type elementType, TContext context);

		void VisitSequenceEnd(IObjectDescriptor sequence, TContext context);
	}
	public interface IPropertyDescriptor
	{
		string Name { get; }

		bool CanWrite { get; }

		Type Type { get; }

		Type? TypeOverride { get; set; }

		int Order { get; set; }

		ScalarStyle ScalarStyle { get; set; }

		T GetCustomAttribute<T>() where T : Attribute;

		IObjectDescriptor Read(object target);

		void Write(object target, object? value);
	}
	public interface IRegistrationLocationSelectionSyntax<TBaseRegistrationType>
	{
		void InsteadOf<TRegistrationType>() where TRegistrationType : TBaseRegistrationType;

		void Before<TRegistrationType>() where TRegistrationType : TBaseRegistrationType;

		void After<TRegistrationType>() where TRegistrationType : TBaseRegistrationType;

		void OnTop();

		void OnBottom();
	}
	public interface ITrackingRegistrationLocationSelectionSyntax<TBaseRegistrationType>
	{
		void InsteadOf<TRegistrationType>() where TRegistrationType : TBaseRegistrationType;
	}
	public interface ISerializer
	{
		void Serialize(TextWriter writer, object graph);

		string Serialize(object graph);

		void Serialize(TextWriter writer, object graph, Type type);

		void Serialize(IEmitter emitter, object graph);

		void Serialize(IEmitter emitter, object graph, Type type);
	}
	public interface ITypeInspector
	{
		IEnumerable<IPropertyDescriptor> GetProperties(Type type, object? container);

		IPropertyDescriptor GetProperty(Type type, object? container, string name, [MaybeNullWhen(true)] bool ignoreUnmatched);
	}
	public interface ITypeResolver
	{
		Type Resolve(Type staticType, object? actualValue);
	}
	public interface IValueDeserializer
	{
		object? DeserializeValue(IParser parser, Type expectedType, SerializerState state, IValueDeserializer nestedObjectDeserializer);
	}
	public interface IValuePromise
	{
		event Action<object?> ValueAvailable;
	}
	public interface IValueSerializer
	{
		void SerializeValue(IEmitter emitter, object? value, Type? type);
	}
	public interface IYamlConvertible
	{
		void Read(IParser parser, Type expectedType, ObjectDeserializer nestedObjectDeserializer);

		void Write(IEmitter emitter, ObjectSerializer nestedObjectSerializer);
	}
	public delegate object? ObjectDeserializer(Type type);
	public delegate void ObjectSerializer(object? value, Type? type = null);
	[Obsolete("Please use IYamlConvertible instead")]
	public interface IYamlSerializable
	{
		void ReadYaml(IParser parser);

		void WriteYaml(IEmitter emitter);
	}
	public interface IYamlTypeConverter
	{
		bool Accepts(Type type);

		object? ReadYaml(IParser parser, Type type);

		void WriteYaml(IEmitter emitter, object? value, Type type);
	}
	internal sealed class LazyComponentRegistrationList<TArgument, TComponent> : IEnumerable<Func<TArgument, TComponent>>, IEnumerable
	{
		public sealed class LazyComponentRegistration
		{
			public readonly Type ComponentType;

			public readonly Func<TArgument, TComponent> Factory;

			public LazyComponentRegistration(Type componentType, Func<TArgument, TComponent> factory)
			{
				ComponentType = componentType;
				Factory = factory;
			}
		}

		public sealed class TrackingLazyComponentRegistration
		{
			public readonly Type ComponentType;

			public readonly Func<TComponent, TArgument, TComponent> Factory;

			public TrackingLazyComponentRegistration(Type componentType, Func<TComponent, TArgument, TComponent> factory)
			{
				ComponentType = componentType;
				Factory = factory;
			}
		}

		private class RegistrationLocationSelector : IRegistrationLocationSelectionSyntax<TComponent>
		{
			private readonly LazyComponentRegistrationList<TArgument, TComponent> registrations;

			private readonly LazyComponentRegistration newRegistration;

			public RegistrationLocationSelector(LazyComponentRegistrationList<TArgument, TComponent> registrations, LazyComponentRegistration newRegistration)
			{
				this.registrations = registrations;
				this.newRegistration = newRegistration;
			}

			void IRegistrationLocationSelectionSyntax<TComponent>.InsteadOf<TRegistrationType>()
			{
				if (newRegistration.ComponentType != typeof(TRegistrationType))
				{
					registrations.EnsureNoDuplicateRegistrationType(newRegistration.ComponentType);
				}
				int index = registrations.EnsureRegistrationExists<TRegistrationType>();
				registrations.entries[index] = newRegistration;
			}

			void IRegistrationLocationSelectionSyntax<TComponent>.After<TRegistrationType>()
			{
				registrations.EnsureNoDuplicateRegistrationType(newRegistration.ComponentType);
				int num = registrations.EnsureRegistrationExists<TRegistrationType>();
				registrations.entries.Insert(num + 1, newRegistration);
			}

			void IRegistrationLocationSelectionSyntax<TComponent>.Before<TRegistrationType>()
			{
				registrations.EnsureNoDuplicateRegistrationType(newRegistration.ComponentType);
				int index = registrations.EnsureRegistrationExists<TRegistrationType>();
				registrations.entries.Insert(index, newRegistration);
			}

			void IRegistrationLocationSelectionSyntax<TComponent>.OnBottom()
			{
				registrations.EnsureNoDuplicateRegistrationType(newRegistration.ComponentType);
				registrations.entries.Add(newRegistration);
			}

			void IRegistrationLocationSelectionSyntax<TComponent>.OnTop()
			{
				registrations.EnsureNoDuplicateRegistrationType(newRegistration.ComponentType);
				registrations.entries.Insert(0, newRegistration);
			}
		}

		private class TrackingRegistrationLocationSelector : ITrackingRegistrationLocationSelectionSyntax<TComponent>
		{
			private readonly LazyComponentRegistrationList<TArgument, TComponent> registrations;

			private readonly TrackingLazyComponentRegistration newRegistration;

			public TrackingRegistrationLocationSelector(LazyComponentRegistrationList<TArgument, TComponent> registrations, TrackingLazyComponentRegistration newRegistration)
			{
				this.registrations = registrations;
				this.newRegistration = newRegistration;
			}

			void ITrackingRegistrationLocationSelectionSyntax<TComponent>.InsteadOf<TRegistrationType>()
			{
				if (newRegistration.ComponentType != typeof(TRegistrationType))
				{
					registrations.EnsureNoDuplicateRegistrationType(newRegistration.ComponentType);
				}
				int index = registrations.EnsureRegistrationExists<TRegistrationType>();
				Func<TArgument, TComponent> innerComponentFactory = registrations.entries[index].Factory;
				registrations.entries[index] = new LazyComponentRegistration(newRegistration.ComponentType, (TArgument arg) => newRegistration.Factory(innerComponentFactory(arg), arg));
			}
		}

		private readonly List<LazyComponentRegistration> entries = new List<LazyComponentRegistration>();

		public int Count => entries.Count;

		public IEnumerable<Func<TArgument, TComponent>> InReverseOrder
		{
			get
			{
				int i = entries.Count - 1;
				while (i >= 0)
				{
					yield return entries[i].Factory;
					int num = i - 1;
					i = num;
				}
			}
		}

		public LazyComponentRegistrationList<TArgument, TComponent> Clone()
		{
			LazyComponentRegistrationList<TArgument, TComponent> lazyComponentRegistrationList = new LazyComponentRegistrationList<TArgument, TComponent>();
			foreach (LazyComponentRegistration entry in entries)
			{
				lazyComponentRegistrationList.entries.Add(entry);
			}
			return lazyComponentRegistrationList;
		}

		public void Add(Type componentType, Func<TArgument, TComponent> factory)
		{
			entries.Add(new LazyComponentRegistration(componentType, factory));
		}

		public void Remove(Type componentType)
		{
			for (int i = 0; i < entries.Count; i++)
			{
				if (entries[i].ComponentType == componentType)
				{
					entries.RemoveAt(i);
					return;
				}
			}
			throw new KeyNotFoundException("A component registration of type '" + componentType.FullName + "' was not found.");
		}

		public IRegistrationLocationSelectionSyntax<TComponent> CreateRegistrationLocationSelector(Type componentType, Func<TArgument, TComponent> factory)
		{
			return new RegistrationLocationSelector(this, new LazyComponentRegistration(componentType, factory));
		}

		public ITrackingRegistrationLocationSelectionSyntax<TComponent> CreateTrackingRegistrationLocationSelector(Type componentType, Func<TComponent, TArgument, TComponent> factory)
		{
			return new TrackingRegistrationLocationSelector(this, new TrackingLazyComponentRegistration(componentType, factory));
		}

		public IEnumerator<Func<TArgument, TComponent>> GetEnumerator()
		{
			return entries.Select((LazyComponentRegistration e) => e.Factory).GetEnumerator();
		}

		IEnumerator IEnumerable.GetEnumerator()
		{
			return GetEnumerator();
		}

		private int IndexOfRegistration(Type registrationType)
		{
			for (int i = 0; i < entries.Count; i++)
			{
				if (registrationType == entries[i].ComponentType)
				{
					return i;
				}
			}
			return -1;
		}

		private void EnsureNoDuplicateRegistrationType(Type componentType)
		{
			if (IndexOfRegistration(componentType) != -1)
			{
				throw new InvalidOperationException("A component of type '" + componentType.FullName + "' has already been registered.");
			}
		}

		private int EnsureRegistrationExists<TRegistrationType>()
		{
			int num = IndexOfRegistration(typeof(TRegistrationType));
			if (num == -1)
			{
				throw new InvalidOperationException("A component of type '" + typeof(TRegistrationType).FullName + "' has not been registered.");
			}
			return num;
		}
	}
	internal static class LazyComponentRegistrationListExtensions
	{
		public static TComponent BuildComponentChain<TComponent>(this LazyComponentRegistrationList<TComponent, TComponent> registrations, TComponent innerComponent)
		{
			return registrations.InReverseOrder.Aggregate(innerComponent, (TComponent inner, Func<TComponent, TComponent> factory) => factory(inner));
		}

		public static TComponent BuildComponentChain<TArgument, TComponent>(this LazyComponentRegistrationList<TArgument, TComponent> registrations, TComponent innerComponent, Func<TComponent, TArgument> argumentBuilder)
		{
			Func<TComponent, TArgument> argumentBuilder2 = argumentBuilder;
			return registrations.InReverseOrder.Aggregate(innerComponent, (TComponent inner, Func<TArgument, TComponent> factory) => factory(argumentBuilder2(inner)));
		}

		public static List<TComponent> BuildComponentList<TComponent>(this LazyComponentRegistrationList<Nothing, TComponent> registrations)
		{
			return registrations.Select((Func<Nothing, TComponent> factory) => factory(default(Nothing))).ToList();
		}

		public static List<TComponent> BuildComponentList<TArgument, TComponent>(this LazyComponentRegistrationList<TArgument, TComponent> registrations, TArgument argument)
		{
			TArgument argument2 = argument;
			return registrations.Select((Func<TArgument, TComponent> factory) => factory(argument2)).ToList();
		}
	}
	[StructLayout(LayoutKind.Sequential, Size = 1)]
	public struct Nothing
	{
	}
	public sealed class ObjectDescriptor : IObjectDescriptor
	{
		public object? Value { get; private set; }

		public Type Type { get; private set; }

		public Type StaticType { get; private set; }

		public ScalarStyle ScalarStyle { get; private set; }

		public ObjectDescriptor(object? value, Type type, Type staticType)
			: this(value, type, staticType, ScalarStyle.Any)
		{
		}

		public ObjectDescriptor(object? value, Type type, Type staticType, ScalarStyle scalarStyle)
		{
			Value = value;
			Type = type ?? throw new ArgumentNullException("type");
			StaticType = staticType ?? throw new ArgumentNullException("staticType");
			ScalarStyle = scalarStyle;
		}
	}
	public delegate IObjectGraphTraversalStrategy ObjectGraphTraversalStrategyFactory(ITypeInspector typeInspector, ITypeResolver typeResolver, IEnumerable<IYamlTypeConverter> typeConverters, int maximumRecursion);
	public sealed class PropertyDescriptor : IPropertyDescriptor
	{
		private readonly IPropertyDescriptor baseDescriptor;

		public string Name { get; set; }

		public Type Type => baseDescriptor.Type;

		public Type? TypeOverride
		{
			get
			{
				return baseDescriptor.TypeOverride;
			}
			set
			{
				baseDescriptor.TypeOverride = value;
			}
		}

		public int Order { get; set; }

		public ScalarStyle ScalarStyle
		{
			get
			{
				return baseDescriptor.ScalarStyle;
			}
			set
			{
				baseDescriptor.ScalarStyle = value;
			}
		}

		public bool CanWrite => baseDescriptor.CanWrite;

		public PropertyDescriptor(IPropertyDescriptor baseDescriptor)
		{
			this.baseDescriptor = baseDescriptor;
			Name = baseDescriptor.Name;
		}

		public void Write(object target, object? value)
		{
			baseDescriptor.Write(target, value);
		}

		public T GetCustomAttribute<T>() where T : Attribute
		{
			return baseDescriptor.GetCustomAttribute<T>();
		}

		public IObjectDescriptor Read(object target)
		{
			return baseDescriptor.Read(target);
		}
	}
	public sealed class Serializer : ISerializer
	{
		private readonly IValueSerializer valueSerializer;

		private readonly EmitterSettings emitterSettings;

		public Serializer()
			: this(new SerializerBuilder().BuildValueSerializer(), EmitterSettings.Default)
		{
		}

		private Serializer(IValueSerializer valueSerializer, EmitterSettings emitterSettings)
		{
			this.valueSerializer = valueSerializer ?? throw new ArgumentNullException("valueSerializer");
			this.emitterSettings = emitterSettings ?? throw new ArgumentNullException("emitterSettings");
		}

		public static Serializer FromValueSerializer(IValueSerializer valueSerializer, EmitterSettings emitterSettings)
		{
			return new Serializer(valueSerializer, emitterSettings);
		}

		public void Serialize(TextWriter writer, object graph)
		{
			Serialize(new Emitter(writer, emitterSettings), graph);
		}

		public string Serialize(object graph)
		{
			using StringWriter stringWriter = new StringWriter();
			Serialize(stringWriter, graph);
			return stringWriter.ToString();
		}

		public void Serialize(TextWriter writer, object graph, Type type)
		{
			Serialize(new Emitter(writer, emitterSettings), graph, type);
		}

		public void Serialize(IEmitter emitter, object graph)
		{
			if (emitter == null)
			{
				throw new ArgumentNullException("emitter");
			}
			EmitDocument(emitter, graph, null);
		}

		public void Serialize(IEmitter emitter, object graph, Type type)
		{
			if (emitter == null)
			{
				throw new ArgumentNullException("emitter");
			}
			if (type == null)
			{
				throw new ArgumentNullException("type");
			}
			EmitDocument(emitter, graph, type);
		}

		private void EmitDocument(IEmitter emitter, object graph, Type? type)
		{
			emitter.Emit(new YamlDotNet.Core.Events.StreamStart());
			emitter.Emit(new YamlDotNet.Core.Events.DocumentStart());
			valueSerializer.SerializeValue(emitter, graph, type);
			emitter.Emit(new YamlDotNet.Core.Events.DocumentEnd(isImplicit: true));
			emitter.Emit(new YamlDotNet.Core.Events.StreamEnd());
		}
	}
	public sealed class SerializerBuilder : BuilderSkeleton<SerializerBuilder>
	{
		private class ValueSerializer : IValueSerializer
		{
			private readonly IObjectGraphTraversalStrategy traversalStrategy;

			private readonly IEventEmitter eventEmitter;

			private readonly IEnumerable<IYamlTypeConverter> typeConverters;

			private readonly LazyComponentRegistrationList<IEnumerable<IYamlTypeConverter>, IObjectGraphVisitor<Nothing>> preProcessingPhaseObjectGraphVisitorFactories;

			private readonly LazyComponentRegistrationList<EmissionPhaseObjectGraphVisitorArgs, IObjectGraphVisitor<IEmitter>> emissionPhaseObjectGraphVisitorFactories;

			public ValueSerializer(IObjectGraphTraversalStrategy traversalStrategy, IEventEmitter eventEmitter, IEnumerable<IYamlTypeConverter> typeConverters, LazyComponentRegistrationList<IEnumerable<IYamlTypeConverter>, IObjectGraphVisitor<Nothing>> preProcessingPhaseObjectGraphVisitorFactories, LazyComponentRegistrationList<EmissionPhaseObjectGraphVisitorArgs, IObjectGraphVisitor<IEmitter>> emissionPhaseObjectGraphVisitorFactories)
			{
				this.traversalStrategy = traversalStrategy;
				this.eventEmitter = eventEmitter;
				this.typeConverters = typeConverters;
				this.preProcessingPhaseObjectGraphVisitorFactories = preProcessingPhaseObjectGraphVisitorFactories;
				this.emissionPhaseObjectGraphVisitorFactories = emissionPhaseObjectGraphVisitorFactories;
			}

			public void SerializeValue(IEmitter emitter, object? value, Type? type)
			{
				IEmitter emitter2 = emitter;
				Type type2 = type ?? ((value != null) ? value.GetType() : typeof(object));
				Type staticType = type ?? typeof(object);
				ObjectDescriptor graph = new ObjectDescriptor(value, type2, staticType);
				List<IObjectGraphVisitor<Nothing>> preProcessingPhaseObjectGraphVisitors = preProcessingPhaseObjectGraphVisitorFactories.BuildComponentList(typeConverters);
				foreach (IObjectGraphVisitor<Nothing> item in preProcessingPhaseObjectGraphVisitors)
				{
					traversalStrategy.Traverse(graph, item, default(Nothing));
				}
				IObjectGraphVisitor<IEmitter> visitor = emissionPhaseObjectGraphVisitorFactories.BuildComponentChain<EmissionPhaseObjectGraphVisitorArgs, IObjectGraphVisitor<IEmitter>>(new EmittingObjectGraphVisitor(eventEmitter), (IObjectGraphVisitor<IEmitter> inner) => new EmissionPhaseObjectGraphVisitorArgs(inner, eventEmitter, preProcessingPhaseObjectGraphVisitors, typeConverters, NestedObjectSerializer));
				traversalStrategy.Traverse(graph, visitor, emitter2);
				void NestedObjectSerializer(object? v, Type? t)
				{
					SerializeValue(emitter2, v, t);
				}
			}
		}

		private ObjectGraphTraversalStrategyFactory objectGraphTraversalStrategyFactory;

		private readonly LazyComponentRegistrationList<IEnumerable<IYamlTypeConverter>, IObjectGraphVisitor<Nothing>> preProcessingPhaseObjectGraphVisitorFactories;

		private readonly LazyComponentRegistrationList<EmissionPhaseObjectGraphVisitorArgs, IObjectGraphVisitor<IEmitter>> emissionPhaseObjectGraphVisitorFactories;

		private readonly LazyComponentRegistrationList<IEventEmitter, IEventEmitter> eventEmitterFactories;

		private readonly IDictionary<Type, TagName> tagMappings = new Dictionary<Type, TagName>();

		private int maximumRecursion = 50;

		private EmitterSettings emitterSettings = EmitterSettings.Default;

		private DefaultValuesHandling defaultValuesHandlingConfiguration;

		protected override SerializerBuilder Self => this;

		public SerializerBuilder()
			: base((ITypeResolver)new DynamicTypeResolver())
		{
			typeInspectorFactories.Add(typeof(CachedTypeInspector), (ITypeInspector inner) => new CachedTypeInspector(inner));
			typeInspectorFactories.Add(typeof(NamingConventionTypeInspector), (ITypeInspector inner) => (!(namingConvention is NullNamingConvention)) ? new NamingConventionTypeInspector(inner, namingConvention) : inner);
			typeInspectorFactories.Add(typeof(YamlAttributesTypeInspector), (ITypeInspector inner) => new YamlAttributesTypeInspector(inner));
			typeInspectorFactories.Add(typeof(YamlAttributeOverridesInspector), (ITypeInspector inner) => (overrides == null) ? inner : new YamlAttributeOverridesInspector(inner, overrides.Clone()));
			preProcessingPhaseObjectGraphVisitorFactories = new LazyComponentRegistrationList<IEnumerable<IYamlTypeConverter>, IObjectGraphVisitor<Nothing>> { 
			{
				typeof(AnchorAssigner),
				(IEnumerable<IYamlTypeConverter> typeConverters) => new AnchorAssigner(typeConverters)
			} };
			emissionPhaseObjectGraphVisitorFactories = new LazyComponentRegistrationList<EmissionPhaseObjectGraphVisitorArgs, IObjectGraphVisitor<IEmitter>>
			{
				{
					typeof(CustomSerializationObjectGraphVisitor),
					(EmissionPhaseObjectGraphVisitorArgs args) => new CustomSerializationObjectGraphVisitor(args.InnerVisitor, args.TypeConverters, args.NestedObjectSerializer)
				},
				{
					typeof(AnchorAssigningObjectGraphVisitor),
					(EmissionPhaseObjectGraphVisitorArgs args) => new AnchorAssigningObjectGraphVisitor(args.InnerVisitor, args.EventEmitter, args.GetPreProcessingPhaseObjectGraphVisitor<AnchorAssigner>())
				},
				{
					typeof(DefaultValuesObjectGraphVisitor),
					(EmissionPhaseObjectGraphVisitorArgs args) => new DefaultValuesObjectGraphVisitor(defaultValuesHandlingConfiguration, args.InnerVisitor)
				},
				{
					typeof(CommentsObjectGraphVisitor),
					(EmissionPhaseObjectGraphVisitorArgs args) => new CommentsObjectGraphVisitor(args.InnerVisitor)
				}
			};
			eventEmitterFactories = new LazyComponentRegistrationList<IEventEmitter, IEventEmitter> { 
			{
				typeof(TypeAssigningEventEmitter),
				(IEventEmitter inner) => new TypeAssigningEventEmitter(inner, requireTagWhenStaticAndActualTypesAreDifferent: false, tagMappings)
			} };
			objectGraphTraversalStrategyFactory = (ITypeInspector typeInspector, ITypeResolver typeResolver, IEnumerable<IYamlTypeConverter> typeConverters, int maximumRecursion) => new FullObjectGraphTraversalStrategy(typeInspector, typeResolver, maximumRecursion, namingConvention);
		}

		public SerializerBuilder WithMaximumRecursion(int maximumRecursion)
		{
			if (maximumRecursion <= 0)
			{
				throw new ArgumentOutOfRangeException("maximumRecursion", $"The maximum recursion specified ({maximumRecursion}) is invalid. It should be a positive integer.");
			}
			this.maximumRecursion = maximumRecursion;
			return this;
		}

		public SerializerBuilder WithEventEmitter<TEventEmitter>(Func<IEventEmitter, TEventEmitter> eventEmitterFactory) where TEventEmitter : IEventEmitter
		{
			return WithEventEmitter(eventEmitterFactory, delegate(IRegistrationLocationSelectionSyntax<IEventEmitter> w)
			{
				w.OnTop();
			});
		}

		public SerializerBuilder WithEventEmitter<TEventEmitter>(Func<IEventEmitter, TEventEmitter> eventEmitterFactory, Action<IRegistrationLocationSelectionSyntax<IEventEmitter>> where) where TEventEmitter : IEventEmitter
		{
			Func<IEventEmitter, TEventEmitter> eventEmitterFactory2 = eventEmitterFactory;
			if (eventEmitterFactory2 == null)
			{
				throw new ArgumentNullException("eventEmitterFactory");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(eventEmitterFactories.CreateRegistrationLocationSelector(typeof(TEventEmitter), (IEventEmitter inner) => eventEmitterFactory2(inner)));
			return Self;
		}

		public SerializerBuilder WithEventEmitter<TEventEmitter>(WrapperFactory<IEventEmitter, IEventEmitter, TEventEmitter> eventEmitterFactory, Action<ITrackingRegistrationLocationSelectionSyntax<IEventEmitter>> where) where TEventEmitter : IEventEmitter
		{
			WrapperFactory<IEventEmitter, IEventEmitter, TEventEmitter> eventEmitterFactory2 = eventEmitterFactory;
			if (eventEmitterFactory2 == null)
			{
				throw new ArgumentNullException("eventEmitterFactory");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(eventEmitterFactories.CreateTrackingRegistrationLocationSelector(typeof(TEventEmitter), (IEventEmitter wrapped, IEventEmitter inner) => eventEmitterFactory2(wrapped, inner)));
			return Self;
		}

		public SerializerBuilder WithoutEventEmitter<TEventEmitter>() where TEventEmitter : IEventEmitter
		{
			return WithoutEventEmitter(typeof(TEventEmitter));
		}

		public SerializerBuilder WithoutEventEmitter(Type eventEmitterType)
		{
			if (eventEmitterType == null)
			{
				throw new ArgumentNullException("eventEmitterType");
			}
			eventEmitterFactories.Remove(eventEmitterType);
			return this;
		}

		public override SerializerBuilder WithTagMapping(TagName tag, Type type)
		{
			if (tag.IsEmpty)
			{
				throw new ArgumentException("Non-specific tags cannot be maped");
			}
			if (type == null)
			{
				throw new ArgumentNullException("type");
			}
			if (tagMappings.TryGetValue(type, out var value))
			{
				throw new ArgumentException($"Type already has a registered tag '{value}' for type '{type.FullName}'", "type");
			}
			tagMappings.Add(type, tag);
			return this;
		}

		public SerializerBuilder WithoutTagMapping(Type type)
		{
			if (type == null)
			{
				throw new ArgumentNullException("type");
			}
			if (!tagMappings.Remove(type))
			{
				throw new KeyNotFoundException("Tag for type '" + type.FullName + "' is not registered");
			}
			return this;
		}

		public SerializerBuilder EnsureRoundtrip()
		{
			objectGraphTraversalStrategyFactory = (ITypeInspector typeInspector, ITypeResolver typeResolver, IEnumerable<IYamlTypeConverter> typeConverters, int maximumRecursion) => new RoundtripObjectGraphTraversalStrategy(typeConverters, typeInspector, typeResolver, maximumRecursion, namingConvention);
			WithEventEmitter((IEventEmitter inner) => new TypeAssigningEventEmitter(inner, requireTagWhenStaticAndActualTypesAreDifferent: true, tagMappings), delegate(IRegistrationLocationSelectionSyntax<IEventEmitter> loc)
			{
				loc.InsteadOf<TypeAssigningEventEmitter>();
			});
			return WithTypeInspector((ITypeInspector inner) => new ReadableAndWritablePropertiesTypeInspector(inner), delegate(IRegistrationLocationSelectionSyntax<ITypeInspector> loc)
			{
				loc.OnBottom();
			});
		}

		public SerializerBuilder DisableAliases()
		{
			preProcessingPhaseObjectGraphVisitorFactories.Remove(typeof(AnchorAssigner));
			emissionPhaseObjectGraphVisitorFactories.Remove(typeof(AnchorAssigningObjectGraphVisitor));
			return this;
		}

		[Obsolete("The default behavior is now to always emit default values, thefore calling this method has no effect. This behavior is now controlled by ConfigureDefaultValuesHandling.", true)]
		public SerializerBuilder EmitDefaults()
		{
			return ConfigureDefaultValuesHandling(DefaultValuesHandling.Preserve);
		}

		public SerializerBuilder ConfigureDefaultValuesHandling(DefaultValuesHandling configuration)
		{
			defaultValuesHandlingConfiguration = configuration;
			return this;
		}

		public SerializerBuilder JsonCompatible()
		{
			emitterSettings = emitterSettings.WithMaxSimpleKeyLength(int.MaxValue).WithoutAnchorName();
			return WithTypeConverter(new YamlDotNet.Serialization.Converters.GuidConverter(jsonCompatible: true), delegate(IRegistrationLocationSelectionSyntax<IYamlTypeConverter> w)
			{
				w.InsteadOf<YamlDotNet.Serialization.Converters.GuidConverter>();
			}).WithEventEmitter((IEventEmitter inner) => new JsonEventEmitter(inner), delegate(IRegistrationLocationSelectionSyntax<IEventEmitter> loc)
			{
				loc.InsteadOf<TypeAssigningEventEmitter>();
			});
		}

		public SerializerBuilder WithPreProcessingPhaseObjectGraphVisitor<TObjectGraphVisitor>(TObjectGraphVisitor objectGraphVisitor) where TObjectGraphVisitor : IObjectGraphVisitor<Nothing>
		{
			return WithPreProcessingPhaseObjectGraphVisitor(objectGraphVisitor, delegate(IRegistrationLocationSelectionSyntax<IObjectGraphVisitor<Nothing>> w)
			{
				w.OnTop();
			});
		}

		public SerializerBuilder WithPreProcessingPhaseObjectGraphVisitor<TObjectGraphVisitor>(TObjectGraphVisitor objectGraphVisitor, Action<IRegistrationLocationSelectionSyntax<IObjectGraphVisitor<Nothing>>> where) where TObjectGraphVisitor : IObjectGraphVisitor<Nothing>
		{
			TObjectGraphVisitor objectGraphVisitor2 = objectGraphVisitor;
			if (objectGraphVisitor2 == null)
			{
				throw new ArgumentNullException("objectGraphVisitor");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(preProcessingPhaseObjectGraphVisitorFactories.CreateRegistrationLocationSelector(typeof(TObjectGraphVisitor), (IEnumerable<IYamlTypeConverter> _) => objectGraphVisitor2));
			return this;
		}

		public SerializerBuilder WithPreProcessingPhaseObjectGraphVisitor<TObjectGraphVisitor>(WrapperFactory<IObjectGraphVisitor<Nothing>, TObjectGraphVisitor> objectGraphVisitorFactory, Action<ITrackingRegistrationLocationSelectionSyntax<IObjectGraphVisitor<Nothing>>> where) where TObjectGraphVisitor : IObjectGraphVisitor<Nothing>
		{
			WrapperFactory<IObjectGraphVisitor<Nothing>, TObjectGraphVisitor> objectGraphVisitorFactory2 = objectGraphVisitorFactory;
			if (objectGraphVisitorFactory2 == null)
			{
				throw new ArgumentNullException("objectGraphVisitorFactory");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(preProcessingPhaseObjectGraphVisitorFactories.CreateTrackingRegistrationLocationSelector(typeof(TObjectGraphVisitor), (IObjectGraphVisitor<Nothing> wrapped, IEnumerable<IYamlTypeConverter> _) => objectGraphVisitorFactory2(wrapped)));
			return this;
		}

		public SerializerBuilder WithoutPreProcessingPhaseObjectGraphVisitor<TObjectGraphVisitor>() where TObjectGraphVisitor : IObjectGraphVisitor<Nothing>
		{
			return WithoutPreProcessingPhaseObjectGraphVisitor(typeof(TObjectGraphVisitor));
		}

		public SerializerBuilder WithoutPreProcessingPhaseObjectGraphVisitor(Type objectGraphVisitorType)
		{
			if (objectGraphVisitorType == null)
			{
				throw new ArgumentNullException("objectGraphVisitorType");
			}
			preProcessingPhaseObjectGraphVisitorFactories.Remove(objectGraphVisitorType);
			return this;
		}

		public SerializerBuilder WithObjectGraphTraversalStrategyFactory(ObjectGraphTraversalStrategyFactory objectGraphTraversalStrategyFactory)
		{
			this.objectGraphTraversalStrategyFactory = objectGraphTraversalStrategyFactory;
			return this;
		}

		public SerializerBuilder WithEmissionPhaseObjectGraphVisitor<TObjectGraphVisitor>(Func<EmissionPhaseObjectGraphVisitorArgs, TObjectGraphVisitor> objectGraphVisitorFactory) where TObjectGraphVisitor : IObjectGraphVisitor<IEmitter>
		{
			return WithEmissionPhaseObjectGraphVisitor(objectGraphVisitorFactory, delegate(IRegistrationLocationSelectionSyntax<IObjectGraphVisitor<IEmitter>> w)
			{
				w.OnTop();
			});
		}

		public SerializerBuilder WithEmissionPhaseObjectGraphVisitor<TObjectGraphVisitor>(Func<EmissionPhaseObjectGraphVisitorArgs, TObjectGraphVisitor> objectGraphVisitorFactory, Action<IRegistrationLocationSelectionSyntax<IObjectGraphVisitor<IEmitter>>> where) where TObjectGraphVisitor : IObjectGraphVisitor<IEmitter>
		{
			Func<EmissionPhaseObjectGraphVisitorArgs, TObjectGraphVisitor> objectGraphVisitorFactory2 = objectGraphVisitorFactory;
			if (objectGraphVisitorFactory2 == null)
			{
				throw new ArgumentNullException("objectGraphVisitorFactory");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(emissionPhaseObjectGraphVisitorFactories.CreateRegistrationLocationSelector(typeof(TObjectGraphVisitor), (EmissionPhaseObjectGraphVisitorArgs args) => objectGraphVisitorFactory2(args)));
			return this;
		}

		public SerializerBuilder WithEmissionPhaseObjectGraphVisitor<TObjectGraphVisitor>(WrapperFactory<EmissionPhaseObjectGraphVisitorArgs, IObjectGraphVisitor<IEmitter>, TObjectGraphVisitor> objectGraphVisitorFactory, Action<ITrackingRegistrationLocationSelectionSyntax<IObjectGraphVisitor<IEmitter>>> where) where TObjectGraphVisitor : IObjectGraphVisitor<IEmitter>
		{
			WrapperFactory<EmissionPhaseObjectGraphVisitorArgs, IObjectGraphVisitor<IEmitter>, TObjectGraphVisitor> objectGraphVisitorFactory2 = objectGraphVisitorFactory;
			if (objectGraphVisitorFactory2 == null)
			{
				throw new ArgumentNullException("objectGraphVisitorFactory");
			}
			if (where == null)
			{
				throw new ArgumentNullException("where");
			}
			where(emissionPhaseObjectGraphVisitorFactories.CreateTrackingRegistrationLocationSelector(typeof(TObjectGraphVisitor), (IObjectGraphVisitor<IEmitter> wrapped, EmissionPhaseObjectGraphVisitorArgs args) => objectGraphVisitorFactory2(wrapped, args)));
			return this;
		}

		public SerializerBuilder WithoutEmissionPhaseObjectGraphVisitor<TObjectGraphVisitor>() where TObjectGraphVisitor : IObjectGraphVisitor<IEmitter>
		{
			return WithoutEmissionPhaseObjectGraphVisitor(typeof(TObjectGraphVisitor));
		}

		public SerializerBuilder WithoutEmissionPhaseObjectGraphVisitor(Type objectGraphVisitorType)
		{
			if (objectGraphVisitorType == null)
			{
				throw new ArgumentNullException("objectGraphVisitorType");
			}
			emissionPhaseObjectGraphVisitorFactories.Remove(objectGraphVisitorType);
			return this;
		}

		public SerializerBuilder WithIndentedSequences()
		{
			emitterSettings = emitterSettings.WithIndentedSequences();
			return this;
		}

		public ISerializer Build()
		{
			return Serializer.FromValueSerializer(BuildValueSerializer(), emitterSettings);
		}

		public IValueSerializer BuildValueSerializer()
		{
			IEnumerable<IYamlTypeConverter> typeConverters = BuildTypeConverters();
			ITypeInspector typeInspector = BuildTypeInspector();
			IObjectGraphTraversalStrategy traversalStrategy = objectGraphTraversalStrategyFactory(typeInspector, typeResolver, typeConverters, maximumRecursion);
			IEventEmitter eventEmitter = eventEmitterFactories.BuildComponentChain(new WriterEventEmitter());
			return new ValueSerializer(traversalStrategy, eventEmitter, typeConverters, preProcessingPhaseObjectGraphVisitorFactories.Clone(), emissionPhaseObjectGraphVisitorFactories.Clone());
		}
	}
	public sealed class StreamFragment : IYamlConvertible
	{
		private readonly List<ParsingEvent> events = new List<ParsingEvent>();

		public IList<ParsingEvent> Events => events;

		void IYamlConvertible.Read(IParser parser, Type expectedType, ObjectDeserializer nestedObjectDeserializer)
		{
			events.Clear();
			int num = 0;
			do
			{
				if (!parser.MoveNext())
				{
					throw new InvalidOperationException("The parser has reached the end before deserialization completed.");
				}
				ParsingEvent current = parser.Current;
				events.Add(current);
				num += current.NestingIncrease;
			}
			while (num > 0);
		}

		void IYamlConvertible.Write(IEmitter emitter, ObjectSerializer nestedObjectSerializer)
		{
			foreach (ParsingEvent @event in events)
			{
				emitter.Emit(@event);
			}
		}
	}
	public sealed class TagMappings
	{
		private readonly IDictionary<string, Type> mappings;

		public TagMappings()
		{
			mappings = new Dictionary<string, Type>();
		}

		public TagMappings(IDictionary<string, Type> mappings)
		{
			this.mappings = new Dictionary<string, Type>(mappings);
		}

		public void Add(string tag, Type mapping)
		{
			mappings.Add(tag, mapping);
		}

		internal Type? GetMapping(string tag)
		{
			if (!mappings.TryGetValue(tag, out Type value))
			{
				return null;
			}
			return value;
		}
	}
	public sealed class YamlAttributeOverrides
	{
		private struct AttributeKey
		{
			public readonly Type AttributeType;

			public readonly string PropertyName;

			public AttributeKey(Type attributeType, string propertyName)
			{
				AttributeType = attributeType;
				PropertyName = propertyName;
			}

			public override bool Equals(object? obj)
			{
				if (obj is AttributeKey attributeKey && AttributeType.Equals(attributeKey.AttributeType))
				{
					return PropertyName.Equals(attributeKey.PropertyName);
				}
				return false;
			}

			public override int GetHashCode()
			{
				return YamlDotNet.Core.HashCode.CombineHashCodes(AttributeType.GetHashCode(), PropertyName.GetHashCode());
			}
		}

		private sealed class AttributeMapping
		{
			public readonly Type RegisteredType;

			public readonly Attribute Attribute;

			public AttributeMapping(Type registeredType, Attribute attribute)
			{
				RegisteredType = registeredType;
				Attribute = attribute;
			}

			public override bool Equals(object? obj)
			{
				if (obj is AttributeMapping attributeMapping && RegisteredType.Equals(attributeMapping.RegisteredType))
				{
					return Attribute.Equals(attributeMapping.Attribute);
				}
				return false;
			}

			public override int GetHashCode()
			{
				return YamlDotNet.Core.HashCode.CombineHashCodes(RegisteredType.GetHashCode(), Attribute.GetHashCode());
			}

			public int Matches(Type matchType)
			{
				int num = 0;
				Type type = matchType;
				while (type != null)
				{
					num++;
					if (type == RegisteredType)
					{
						return num;
					}
					type = type.BaseType();
				}
				if (matchType.GetInterfaces().Contains(RegisteredType))
				{
					return num;
				}
				return 0;
			}
		}

		private readonly Dictionary<AttributeKey, List<AttributeMapping>> overrides = new Dictionary<AttributeKey, List<AttributeMapping>>();

		public T? GetAttribute<T>(Type type, string member) where T : Attribute
		{
			if (overrides.TryGetValue(new AttributeKey(typeof(T), member), out List<AttributeMapping> value))
			{
				int num = 0;
				AttributeMapping attributeMapping = null;
				foreach (AttributeMapping item in value)
				{
					int num2 = item.Matches(type);
					if (num2 > num)
					{
						num = num2;
						attributeMapping = item;
					}
				}
				if (num > 0)
				{
					return (T)attributeMapping.Attribute;
				}
			}
			return null;
		}

		public void Add(Type type, string member, Attribute attribute)
		{
			AttributeMapping item = new AttributeMapping(type, attribute);
			AttributeKey key = new AttributeKey(attribute.GetType(), member);
			if (!overrides.TryGetValue(key, out List<AttributeMapping> value))
			{
				value = new List<AttributeMapping>();
				overrides.Add(key, value);
			}
			else if (value.Contains(item))
			{
				throw new InvalidOperationException($"Attribute ({attribute}) already set for Type {type.FullName}, Member {member}");
			}
			value.Add(item);
		}

		public YamlAttributeOverrides Clone()
		{
			YamlAttributeOverrides yamlAttributeOverrides = new YamlAttributeOverrides();
			foreach (KeyValuePair<AttributeKey, List<AttributeMapping>> @override in overrides)
			{
				foreach (AttributeMapping item in @override.Value)
				{
					yamlAttributeOverrides.Add(item.RegisteredType, @override.Key.PropertyName, item.Attribute);
				}
			}
			return yamlAttributeOverrides;
		}

		public void Add<TClass>(Expression<Func<TClass, object>> propertyAccessor, Attribute attribute)
		{
			PropertyInfo propertyInfo = propertyAccessor.AsProperty();
			Add(typeof(TClass), propertyInfo.Name, attribute);
		}
	}
	public sealed class YamlAttributeOverridesInspector : TypeInspectorSkeleton
	{
		public sealed class OverridePropertyDescriptor : IPropertyDescriptor
		{
			private readonly IPropertyDescriptor baseDescriptor;

			private readonly YamlAttributeOverrides overrides;

			private readonly Type classType;

			public string Name => baseDescriptor.Name;

			public bool CanWrite => baseDescriptor.CanWrite;

			public Type Type => baseDescriptor.Type;

			public Type? TypeOverride
			{
				get
				{
					return baseDescriptor.TypeOverride;
				}
				set
				{
					baseDescriptor.TypeOverride = value;
				}
			}

			public int Order
			{
				get
				{
					return baseDescriptor.Order;
				}
				set
				{
					baseDescriptor.Order = value;
				}
			}

			public ScalarStyle ScalarStyle
			{
				get
				{
					return baseDescriptor.ScalarStyle;
				}
				set
				{
					baseDescriptor.ScalarStyle = value;
				}
			}

			public OverridePropertyDescriptor(IPropertyDescriptor baseDescriptor, YamlAttributeOverrides overrides, Type classType)
			{
				this.baseDescriptor = baseDescriptor;
				this.overrides = overrides;
				this.classType = classType;
			}

			public void Write(object target, object? value)
			{
				baseDescriptor.Write(target, value);
			}

			public T GetCustomAttribute<T>() where T : Attribute
			{
				return overrides.GetAttribute<T>(classType, Name) ?? baseDescriptor.GetCustomAttribute<T>();
			}

			public IObjectDescriptor Read(object target)
			{
				return baseDescriptor.Read(target);
			}
		}

		private readonly ITypeInspector innerTypeDescriptor;

		private readonly YamlAttributeOverrides overrides;

		public YamlAttributeOverridesInspector(ITypeInspector innerTypeDescriptor, YamlAttributeOverrides overrides)
		{
			this.innerTypeDescriptor = innerTypeDescriptor;
			this.overrides = overrides;
		}

		public override IEnumerable<IPropertyDescriptor> GetProperties(Type type, object? container)
		{
			Type type2 = type;
			IEnumerable<IPropertyDescriptor> enumerable = innerTypeDescriptor.GetProperties(type2, container);
			if (overrides != null)
			{
				enumerable = enumerable.Select((Func<IPropertyDescriptor, IPropertyDescriptor>)((IPropertyDescriptor p) => new OverridePropertyDescriptor(p, overrides, type2)));
			}
			return enumerable;
		}
	}
	public sealed class YamlAttributesTypeInspector : TypeInspectorSkeleton
	{
		private readonly ITypeInspector innerTypeDescriptor;

		public YamlAttributesTypeInspector(ITypeInspector innerTypeDescriptor)
		{
			this.innerTypeDescriptor = innerTypeDescriptor;
		}

		public override IEnumerable<IPropertyDescriptor> GetProperties(Type type, object? container)
		{
			return from p in (from p in innerTypeDescriptor.GetProperties(type, container)
					where p.GetCustomAttribute<YamlIgnoreAttribute>() == null
					select p).Select((Func<IPropertyDescriptor, IPropertyDescriptor>)delegate(IPropertyDescriptor p)
				{
					PropertyDescriptor propertyDescriptor = new PropertyDescriptor(p);
					YamlMemberAttribute customAttribute = p.GetCustomAttribute<YamlMemberAttribute>();
					if (customAttribute != null)
					{
						if (customAttribute.SerializeAs != null)
						{
							propertyDescriptor.TypeOverride = customAttribute.SerializeAs;
						}
						propertyDescriptor.Order = customAttribute.Order;
						propertyDescriptor.ScalarStyle = customAttribute.ScalarStyle;
						if (customAttribute.Alias != null)
						{
							propertyDescriptor.Name = customAttribute.Alias;
						}
					}
					return propertyDescriptor;
				})
				orderby p.Order
				select p;
		}
	}
	internal static class YamlFormatter
	{
		public static readonly NumberFormatInfo NumberFormat = new NumberFormatInfo
		{
			CurrencyDecimalSeparator = ".",
			CurrencyGroupSeparator = "_",
			CurrencyGroupSizes = new int[1] { 3 },
			CurrencySymbol = string.Empty,
			CurrencyDecimalDigits = 99,
			NumberDecimalSeparator = ".",
			NumberGroupSeparator = "_",
			NumberGroupSizes = new int[1] { 3 },
			NumberDecimalDigits = 99,
			NaNSymbol = ".nan",
			PositiveInfinitySymbol = ".inf",
			NegativeInfinitySymbol = "-.inf"
		};

		public static string FormatNumber(object number)
		{
			return Convert.ToString(number, NumberFormat);
		}

		public static string FormatNumber(double number)
		{
			return number.ToString("G17", NumberFormat);
		}

		public static string FormatNumber(float number)
		{
			return number.ToString("G17", NumberFormat);
		}

		public static string FormatBoolean(object boolean)
		{
			if (!boolean.Equals(true))
			{
				return "false";
			}
			return "true";
		}

		public static string FormatDateTime(object dateTime)
		{
			return ((DateTime)dateTime).ToString("o", CultureInfo.InvariantCulture);
		}

		public static string FormatTimeSpan(object timeSpan)
		{
			return ((TimeSpan)timeSpan).ToString();
		}
	}
	[AttributeUsage(AttributeTargets.Property | AttributeTargets.Field, AllowMultiple = false)]
	public sealed class YamlIgnoreAttribute : Attribute
	{
	}
	[AttributeUsage(AttributeTargets.Property | AttributeTargets.Field, AllowMultiple = false)]
	public sealed class YamlMemberAttribute : Attribute
	{
		private DefaultValuesHandling? defaultValuesHandling;

		public string? Description { get; set; }

		public Type? SerializeAs { get; set; }

		public int Order { get; set; }

		public string? Alias { get; set; }

		public bool ApplyNamingConventions { get; set; }

		public ScalarStyle ScalarStyle { get; set; }

		public DefaultValuesHandling DefaultValuesHandling
		{
			get
			{
				return defaultValuesHandling.GetValueOrDefault();
			}
			set
			{
				defaultValuesHandling = value;
			}
		}

		public bool IsDefaultValuesHandlingSpecified => defaultValuesHandling.HasValue;

		public YamlMemberAttribute()
		{
			ScalarStyle = ScalarStyle.Any;
			ApplyNamingConventions = true;
		}

		public YamlMemberAttribute(Type serializeAs)
			: this()
		{
			SerializeAs = serializeAs ?? throw new ArgumentNullException("serializeAs");
		}
	}
}
namespace YamlDotNet.Serialization.ValueDeserializers
{
	public sealed class AliasValueDeserializer : IValueDeserializer
	{
		private sealed class AliasState : Dictionary<AnchorName, ValuePromise>, IPostDeserializationCallback
		{
			public void OnDeserialization()
			{
				foreach (ValuePromise value in base.Values)
				{
					if (!value.HasValue)
					{
						YamlDotNet.Core.Events.AnchorAlias alias = value.Alias;
						throw new AnchorNotFoundException(alias.Start, alias.End, $"Anchor '{alias.Value}' not found");
					}
				}
			}
		}

		private sealed class ValuePromise : IValuePromise
		{
			private object? value;

			public readonly YamlDotNet.Core.Events.AnchorAlias? Alias;

			public bool HasValue { get; private set; }

			public object? Value
			{
				get
				{
					if (!HasValue)
					{
						throw new InvalidOperationException("Value not set");
					}
					return value;
				}
				set
				{
					if (HasValue)
					{
						throw new InvalidOperationException("Value already set");
					}
					HasValue = true;
					this.value = value;
					this.ValueAvailable?.Invoke(value);
				}
			}

			public event Action<object?>? ValueAvailable;

			public ValuePromise(YamlDotNet.Core.Events.AnchorAlias alias)
			{
				Alias = alias;
			}

			public ValuePromise(object? value)
			{
				HasValue = true;
				this.value = value;
			}
		}

		private readonly IValueDeserializer innerDeserializer;

		public AliasValueDeserializer(IValueDeserializer innerDeserializer)
		{
			this.innerDeserializer = innerDeserializer ?? throw new ArgumentNullException("innerDeserializer");
		}

		public object? DeserializeValue(IParser parser, Type expectedType, SerializerState state, IValueDeserializer nestedObjectDeserializer)
		{
			if (parser.TryConsume<YamlDotNet.Core.Events.AnchorAlias>(out var @event))
			{
				if (!state.Get<AliasState>().TryGetValue(@event.Value, out ValuePromise value))
				{
					throw new AnchorNotFoundException(@event.Start, @event.End, $"Alias ${@event.Value} cannot precede anchor declaration");
				}
				if (!value.HasValue)
				{
					return value;
				}
				return value.Value;
			}
			AnchorName anchorName = AnchorName.Empty;
			if (parser.Accept<NodeEvent>(out var event2) && !event2.Anchor.IsEmpty)
			{
				anchorName = event2.Anchor;
				AliasState aliasState = state.Get<AliasState>();
				if (!aliasState.ContainsKey(anchorName))
				{
					aliasState[anchorName] = new ValuePromise(new YamlDotNet.Core.Events.AnchorAlias(anchorName));
				}
			}
			object obj = innerDeserializer.DeserializeValue(parser, expectedType, state, nestedObjectDeserializer);
			if (!anchorName.IsEmpty)
			{
				AliasState aliasState2 = state.Get<AliasState>();
				if (!aliasState2.TryGetValue(anchorName, out ValuePromise value2))
				{
					aliasState2.Add(anchorName, new ValuePromise(obj));
				}
				else if (!value2.HasValue)
				{
					value2.Value = obj;
				}
				else
				{
					aliasState2[anchorName] = new ValuePromise(obj);
				}
			}
			return obj;
		}
	}
	public sealed class NodeValueDeserializer : IValueDeserializer
	{
		private readonly IList<INodeDeserializer> deserializers;

		private readonly IList<INodeTypeResolver> typeResolvers;

		public NodeValueDeserializer(IList<INodeDeserializer> deserializers, IList<INodeTypeResolver> typeResolvers)
		{
			this.deserializers = deserializers ?? throw new ArgumentNullException("deserializers");
			this.typeResolvers = typeResolvers ?? throw new ArgumentNullException("typeResolvers");
		}

		public object? DeserializeValue(IParser parser, Type expectedType, SerializerState state, IValueDeserializer nestedObjectDeserializer)
		{
			IValueDeserializer nestedObjectDeserializer2 = nestedObjectDeserializer;
			SerializerState state2 = state;
			parser.Accept<NodeEvent>(out var @event);
			Type typeFromEvent = GetTypeFromEvent(@event, expectedType);
			try
			{
				foreach (INodeDeserializer deserializer in deserializers)
				{
					if (deserializer.Deserialize(parser, typeFromEvent, (IParser r, Type t) => nestedObjectDeserializer2.DeserializeValue(r, t, state2, nestedObjectDeserializer2), out object value))
					{
						return YamlDotNet.Serialization.Utilities.TypeConverter.ChangeType(value, expectedType);
					}
				}
			}
			catch (YamlException)
			{
				throw;
			}
			catch (Exception innerException)
			{
				throw new YamlException(@event?.Start ?? Mark.Empty, @event?.End ?? Mark.Empty, "Exception during deserialization", innerException);
			}
			throw new YamlException(@event?.Start ?? Mark.Empty, @event?.End ?? Mark.Empty, "No node deserializer was able to deserialize the node into type " + expectedType.AssemblyQualifiedName);
		}

		private Type GetTypeFromEvent(NodeEvent? nodeEvent, Type currentType)
		{
			using (IEnumerator<INodeTypeResolver> enumerator = typeResolvers.GetEnumerator())
			{
				while (enumerator.MoveNext() && !enumerator.Current.Resolve(nodeEvent, ref currentType))
				{
				}
			}
			return currentType;
		}
	}
}
namespace YamlDotNet.Serialization.Utilities
{
	public interface IPostDeserializationCallback
	{
		void OnDeserialization();
	}
	internal sealed class ObjectAnchorCollection
	{
		private readonly IDictionary<string, object> objectsByAnchor = new Dictionary<string, object>();

		private readonly IDictionary<object, string> anchorsByObject = new Dictionary<object, string>();

		public object this[string anchor]
		{
			get
			{
				if (objectsByAnchor.TryGetValue(anchor, out object value))
				{
					return value;
				}
				throw new AnchorNotFoundException("The anchor '" + anchor + "' does not exists");
			}
		}

		public void Add(string anchor, object @object)
		{
			objectsByAnchor.Add(anchor, @object);
			if (@object != null)
			{
				anchorsByObject.Add(@object, anchor);
			}
		}

		public bool TryGetAnchor(object @object, [MaybeNullWhen(false)] out string? anchor)
		{
			return anchorsByObject.TryGetValue(@object, out anchor);
		}
	}
	internal static class ReflectionUtility
	{
		public static Type? GetImplementedGenericInterface(Type type, Type genericInterfaceType)
		{
			foreach (Type implementedInterface in GetImplementedInterfaces(type))
			{
				if (implementedInterface.IsGenericType() && implementedInterface.GetGenericTypeDefinition() == genericInterfaceType)
				{
					return implementedInterface;
				}
			}
			return null;
		}

		public static IEnumerable<Type> GetImplementedInterfaces(Type type)
		{
			if (type.IsInterface())
			{
				yield return type;
			}
			Type[] interfaces = type.GetInterfaces();
			for (int i = 0; i < interfaces.Length; i++)
			{
				yield return interfaces[i];
			}
		}
	}
	public sealed class SerializerState : IDisposable
	{
		private readonly IDictionary<Type, object> items = new Dictionary<Type, object>();

		public T Get<T>() where T : class, new()
		{
			if (!items.TryGetValue(typeof(T), out object value))
			{
				value = new T();
				items.Add(typeof(T), value);
			}
			return (T)value;
		}

		public void OnDeserialization()
		{
			foreach (IPostDeserializationCallback item in items.Values.OfType<IPostDeserializationCallback>())
			{
				item.OnDeserialization();
			}
		}

		public void Dispose()
		{
			foreach (IDisposable item in items.Values.OfType<IDisposable>())
			{
				item.Dispose();
			}
		}
	}
	internal static class StringExtensions
	{
		private static string ToCamelOrPascalCase(string str, Func<char, char> firstLetterTransform)
		{
			string text = Regex.Replace(str, "([_\\-])(?<char>[a-z])", (Match match) => match.Groups["char"].Value.ToUpperInvariant(), RegexOptions.IgnoreCase);
			return firstLetterTransform(text[0]) + text.Substring(1);
		}

		public static string ToCamelCase(this string str)
		{
			return ToCamelOrPascalCase(str, char.ToLowerInvariant);
		}

		public static string ToPascalCase(this string str)
		{
			return ToCamelOrPascalCase(str, char.ToUpperInvariant);
		}

		public static string FromCamelCase(this string str, string separator)
		{
			string separator2 = separator;
			str = char.ToLower(str[0]) + str.Substring(1);
			str = Regex.Replace(str.ToCamelCase(), "(?<char>[A-Z])", (Match match) => separator2 + match.Groups["char"].Value.ToLowerInvariant());
			return str;
		}
	}
	public static class TypeConverter
	{
		public static T ChangeType<T>(object? value)
		{
			return (T)ChangeType(value, typeof(T));
		}

		public static T ChangeType<T>(object? value, IFormatProvider provider)
		{
			return (T)ChangeType(value, typeof(T), provider);
		}

		public static T ChangeType<T>(object? value, CultureInfo culture)
		{
			return (T)ChangeType(value, typeof(T), culture);
		}

		public static object? ChangeType(object? value, Type destinationType)
		{
			return ChangeType(value, destinationType, CultureInfo.InvariantCulture);
		}

		public static object? ChangeType(object? value, Type destinationType, IFormatProvider provider)
		{
			return ChangeType(value, destinationType, new CultureInfoAdapter(CultureInfo.CurrentCulture, provider));
		}

		public static object? ChangeType(object? value, Type destinationType, CultureInfo culture)
		{
			if (value == null || value.IsDbNull())
			{
				if (!destinationType.IsValueType())
				{
					return null;
				}
				return Activator.CreateInstance(destinationType);
			}
			Type type = value.GetType();
			if (destinationType == type || destinationType.IsAssignableFrom(type))
			{
				return value;
			}
			if (destinationType.IsGenericType() && destinationType.GetGenericTypeDefinition() == typeof(Nullable<>))
			{
				Type destinationType2 = destinationType.GetGenericArguments()[0];
				object obj = ChangeType(value, destinationType2, culture);
				return Activator.CreateInstance(destinationType, obj);
			}
			if (destinationType.IsEnum())
			{
				if (!(value is string value2))
				{
					return value;
				}
				return Enum.Parse(destinationType, value2, ignoreCase: true);
			}
			if (destinationType == typeof(bool))
			{
				if ("0".Equals(value))
				{
					return false;
				}
				if ("1".Equals(value))
				{
					return true;
				}
			}
			System.ComponentModel.TypeConverter converter = TypeDescriptor.GetConverter(type);
			if (converter != null && converter.CanConvertTo(destinationType))
			{
				return converter.ConvertTo(null, culture, value, destinationType);
			}
			System.ComponentModel.TypeConverter converter2 = TypeDescriptor.GetConverter(destinationType);
			if (converter2 != null && converter2.CanConvertFrom(type))
			{
				return converter2.ConvertFrom(null, culture, value);
			}
			Type[] array = new Type[2] { type, destinationType };
			for (int i = 0; i < array.Length; i++)
			{
				foreach (MethodInfo publicStaticMethod2 in array[i].GetPublicStaticMethods())
				{
					if (!publicStaticMethod2.IsSpecialName || (!(publicStaticMethod2.Name == "op_Implicit") && !(publicStaticMethod2.Name == "op_Explicit")) || !destinationType.IsAssignableFrom(publicStaticMethod2.ReturnParameter.ParameterType))
					{
						continue;
					}
					ParameterInfo[] parameters = publicStaticMethod2.GetParameters();
					if (parameters.Length == 1 && parameters[0].ParameterType.IsAssignableFrom(type))
					{
						try
						{
							return publicStaticMethod2.Invoke(null, new object[1] { value });
						}
						catch (TargetInvocationException ex)
						{
							throw ex.Unwrap();
						}
					}
				}
			}
			if (type == typeof(string))
			{
				try
				{
					MethodInfo publicStaticMethod = destinationType.GetPublicStaticMethod("Parse", typeof(string), typeof(IFormatProvider));
					if (publicStaticMethod != null)
					{
						return publicStaticMethod.Invoke(null, new object[2] { value, culture });
					}
					publicStaticMethod = destinationType.GetPublicStaticMethod("Parse", typeof(string));
					if (publicStaticMethod != null)
					{
						return publicStaticMethod.Invoke(null, new object[1] { value });
					}
				}
				catch (TargetInvocationException ex2)
				{
					throw ex2.Unwrap();
				}
			}
			if (destinationType == typeof(TimeSpan))
			{
				return TimeSpan.Parse((string)ChangeType(value, typeof(string), CultureInfo.InvariantCulture));
			}
			return Convert.ChangeType(value, destinationType, CultureInfo.InvariantCulture);
		}

		[PermissionSet(SecurityAction.LinkDemand, Name = "FullTrust")]
		public static void RegisterTypeConverter<TConvertible, TConverter>() where TConverter : System.ComponentModel.TypeConverter
		{
			if (!TypeDescriptor.GetAttributes(typeof(TConvertible)).OfType<TypeConverterAttribute>().Any((TypeConverterAttribute a) => a.ConverterTypeName == typeof(TConverter).AssemblyQualifiedName))
			{
				TypeDescriptor.AddAttributes(typeof(TConvertible), new TypeConverterAttribute(typeof(TConverter)));
			}
		}
	}
}
namespace YamlDotNet.Serialization.TypeResolvers
{
	public sealed class DynamicTypeResolver : ITypeResolver
	{
		public Type Resolve(Type staticType, object? actualValue)
		{
			if (actualValue == null)
			{
				return staticType;
			}
			return actualValue.GetType();
		}
	}
	public sealed class StaticTypeResolver : ITypeResolver
	{
		public Type Resolve(Type staticType, object? actualValue)
		{
			return staticType;
		}
	}
}
namespace YamlDotNet.Serialization.TypeInspectors
{
	public sealed class CachedTypeInspector : TypeInspectorSkeleton
	{
		private readonly ITypeInspector innerTypeDescriptor;

		private readonly ConcurrentDictionary<Type, List<IPropertyDescriptor>> cache = new ConcurrentDictionary<Type, List<IPropertyDescriptor>>();

		public CachedTypeInspector(ITypeInspector innerTypeDescriptor)
		{
			this.innerTypeDescriptor = innerTypeDescriptor ?? throw new ArgumentNullException("innerTypeDescriptor");
		}

		public override IEnumerable<IPropertyDescriptor> GetProperties(Type type, object? container)
		{
			object container2 = container;
			return cache.GetOrAdd(type, (Type t) => innerTypeDescriptor.GetProperties(t, container2).ToList());
		}
	}
	public sealed class CompositeTypeInspector : TypeInspectorSkeleton
	{
		private readonly IEnumerable<ITypeInspector> typeInspectors;

		public CompositeTypeInspector(params ITypeInspector[] typeInspectors)
			: this((IEnumerable<ITypeInspector>)typeInspectors)
		{
		}

		public CompositeTypeInspector(IEnumerable<ITypeInspector> typeInspectors)
		{
			this.typeInspectors = typeInspectors?.ToList() ?? throw new ArgumentNullException("typeInspectors");
		}

		public override IEnumerable<IPropertyDescriptor> GetProperties(Type type, object? container)
		{
			Type type2 = type;
			object container2 = container;
			return typeInspectors.SelectMany((ITypeInspector i) => i.GetProperties(type2, container2));
		}
	}
	public sealed class NamingConventionTypeInspector : TypeInspectorSkeleton
	{
		private readonly ITypeInspector innerTypeDescriptor;

		private readonly INamingConvention namingConvention;

		public NamingConventionTypeInspector(ITypeInspector innerTypeDescriptor, INamingConvention namingConvention)
		{
			this.innerTypeDescriptor = innerTypeDescriptor ?? throw new ArgumentNullException("innerTypeDescriptor");
			this.namingConvention = namingConvention ?? throw new ArgumentNullException("namingConvention");
		}

		public override IEnumerable<IPropertyDescriptor> GetProperties(Type type, object? container)
		{
			return innerTypeDescriptor.GetProperties(type, container).Select(delegate(IPropertyDescriptor p)
			{
				YamlMemberAttribute customAttribute = p.GetCustomAttribute<YamlMemberAttribute>();
				return (customAttribute != null && !customAttribute.ApplyNamingConventions) ? p : new PropertyDescriptor(p)
				{
					Name = namingConvention.Apply(p.Name)
				};
			});
		}
	}
	public sealed class ReadableAndWritablePropertiesTypeInspector : TypeInspectorSkeleton
	{
		private readonly ITypeInspector innerTypeDescriptor;

		public ReadableAndWritablePropertiesTypeInspector(ITypeInspector innerTypeDescriptor)
		{
			this.innerTypeDescriptor = innerTypeDescriptor ?? throw new ArgumentNullException("innerTypeDescriptor");
		}

		public override IEnumerable<IPropertyDescriptor> GetProperties(Type type, object? container)
		{
			return from p in innerTypeDescriptor.GetProperties(type, container)
				where p.CanWrite
				select p;
		}
	}
	public sealed class ReadableFieldsTypeInspector : TypeInspectorSkeleton
	{
		private sealed class ReflectionFieldDescriptor : IPropertyDescriptor
		{
			private readonly FieldInfo fieldInfo;

			private readonly ITypeResolver typeResolver;

			public string Name => fieldInfo.Name;

			public Type Type => fieldInfo.FieldType;

			public Type? TypeOverride { get; set; }

			public int Order { get; set; }

			public bool CanWrite => !fieldInfo.IsInitOnly;

			public ScalarStyle ScalarStyle { get; set; }

			public ReflectionFieldDescriptor(FieldInfo fieldInfo, ITypeResolver typeResolver)
			{
				this.fieldInfo = fieldInfo;
				this.typeResolver = typeResolver;
				ScalarStyle = ScalarStyle.Any;
			}

			public void Write(object target, object? value)
			{
				fieldInfo.SetValue(target, value);
			}

			public T GetCustomAttribute<T>() where T : Attribute
			{
				return (T)fieldInfo.GetCustomAttributes(typeof(T), inherit: true).FirstOrDefault();
			}

			public IObjectDescriptor Read(object target)
			{
				object value = fieldInfo.GetValue(target);
				Type type = TypeOverride ?? typeResolver.Resolve(Type, value);
				return new ObjectDescriptor(value, type, Type, ScalarStyle);
			}
		}

		private readonly ITypeResolver typeResolver;

		public ReadableFieldsTypeInspector(ITypeResolver typeResolver)
		{
			this.typeResolver = typeResolver ?? throw new ArgumentNullException("typeResolver");
		}

		public override IEnumerable<IPropertyDescriptor> GetProperties(Type type, object? container)
		{
			return type.GetPublicFields().Select((Func<FieldInfo, IPropertyDescriptor>)((FieldInfo p) => new ReflectionFieldDescriptor(p, typeResolver)));
		}
	}
	public sealed class ReadablePropertiesTypeInspector : TypeInspectorSkeleton
	{
		private sealed class ReflectionPropertyDescriptor : IPropertyDescriptor
		{
			private readonly PropertyInfo propertyInfo;

			private readonly ITypeResolver typeResolver;

			public string Name => propertyInfo.Name;

			public Type Type => propertyInfo.PropertyType;

			public Type? TypeOverride { get; set; }

			public int Order { get; set; }

			public bool CanWrite => propertyInfo.CanWrite;

			public ScalarStyle ScalarStyle { get; set; }

			public ReflectionPropertyDescriptor(PropertyInfo propertyInfo, ITypeResolver typeResolver)
			{
				this.propertyInfo = propertyInfo ?? throw new ArgumentNullException("propertyInfo");
				this.typeResolver = typeResolver ?? throw new ArgumentNullException("typeResolver");
				ScalarStyle = ScalarStyle.Any;
			}

			public void Write(object target, object? value)
			{
				propertyInfo.SetValue(target, value, null);
			}

			public T GetCustomAttribute<T>() where T : Attribute
			{
				return (T)propertyInfo.GetAllCustomAttributes<T>().FirstOrDefault();
			}

			public IObjectDescriptor Read(object target)
			{
				object obj = propertyInfo.ReadValue(target);
				Type type = TypeOverride ?? typeResolver.Resolve(Type, obj);
				return new ObjectDescriptor(obj, type, Type, ScalarStyle);
			}
		}

		private readonly ITypeResolver typeResolver;

		private readonly bool includeNonPublicProperties;

		public ReadablePropertiesTypeInspector(ITypeResolver typeResolver)
			: this(typeResolver, includeNonPublicProperties: false)
		{
		}

		public ReadablePropertiesTypeInspector(ITypeResolver typeResolver, bool includeNonPublicProperties)
		{
			this.typeResolver = typeResolver ?? throw new ArgumentNullException("typeResolver");
			this.includeNonPublicProperties = includeNonPublicProperties;
		}

		private static bool IsValidProperty(PropertyInfo property)
		{
			if (property.CanRead)
			{
				return property.GetGetMethod(nonPublic: true).GetParameters().Length == 0;
			}
			return false;
		}

		public override IEnumerable<IPropertyDescriptor> GetProperties(Type type, object? container)
		{
			return type.GetProperties(includeNonPublicProperties).Where(IsValidProperty).Select((Func<PropertyInfo, IPropertyDescriptor>)((PropertyInfo p) => new ReflectionPropertyDescriptor(p, typeResolver)));
		}
	}
	public abstract class TypeInspectorSkeleton : ITypeInspector
	{
		public abstract IEnumerable<IPropertyDescriptor> GetProperties(Type type, object? container);

		public IPropertyDescriptor GetProperty(Type type, object? container, string name, [MaybeNullWhen(true)] bool ignoreUnmatched)
		{
			string name2 = name;
			IEnumerable<IPropertyDescriptor> enumerable = from p in GetProperties(type, container)
				where p.Name == name2
				select p;
			using IEnumerator<IPropertyDescriptor> enumerator = enumerable.GetEnumerator();
			if (!enumerator.MoveNext())
			{
				if (ignoreUnmatched)
				{
					return null;
				}
				throw new SerializationException("Property '" + name2 + "' not found on type '" + type.FullName + "'.");
			}
			IPropertyDescriptor current = enumerator.Current;
			if (enumerator.MoveNext())
			{
				throw new SerializationException("Multiple properties with the name/alias '" + name2 + "' already exists on type '" + type.FullName + "', maybe you're misusing YamlAlias or maybe you are using the wrong naming convention? The matching properties are: " + string.Join(", ", enumerable.Select((IPropertyDescriptor p) => p.Name).ToArray()));
			}
			return current;
		}
	}
}
namespace YamlDotNet.Serialization.Schemas
{
	public sealed class FailsafeSchema
	{
		public static class Tags
		{
			public static readonly TagName Map = new TagName("tag:yaml.org,2002:map");

			public static readonly TagName Seq = new TagName("tag:yaml.org,2002:seq");

			public static readonly TagName Str = new TagName("tag:yaml.org,2002:str");
		}
	}
	public sealed class JsonSchema
	{
		public static class Tags
		{
			public static readonly TagName Null = new TagName("tag:yaml.org,2002:null");

			public static readonly TagName Bool = new TagName("tag:yaml.org,2002:bool");

			public static readonly TagName Int = new TagName("tag:yaml.org,2002:int");

			public static readonly TagName Float = new TagName("tag:yaml.org,2002:float");
		}
	}
	public sealed class CoreSchema
	{
		public static class Tags
		{
		}
	}
	public sealed class DefaultSchema
	{
		public stat