Decompiled source of VoidPouch v1.3.0

BepInEx/plugins/VoidPouch.dll

Decompiled 2 weeks ago
#define DEBUG
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
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.Versioning;
using System.Text;
using System.Threading;
using BepInEx;
using HarmonyLib;
using SQLite;
using TMPro;
using Unity.Netcode;
using UnityEngine;
using UnityEngine.EventSystems;
using UnityEngine.Events;
using UnityEngine.InputSystem;
using UnityEngine.InputSystem.Controls;
using UnityEngine.Localization.Settings;
using UnityEngine.SceneManagement;
using UnityEngine.UI;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)]
[assembly: AssemblyTitle("VoidPouch")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("VoidPouch")]
[assembly: AssemblyCopyright("Copyright ©  2025")]
[assembly: AssemblyTrademark("")]
[assembly: ComVisible(false)]
[assembly: Guid("283868D3-098F-45B8-8765-597AD223EB42")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: TargetFramework(".NETFramework,Version=v4.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")]
[assembly: AssemblyVersion("1.0.0.0")]
public class BagHook : BaseUnityPlugin
{
	[HarmonyPatch(typeof(PlayerInventory))]
	[HarmonyPatch("CheckBag")]
	[HarmonyPostfix]
	public static void CheckBag(PlayerInventory __instance)
	{
		VoidPouch.playerInventory = __instance;
	}

	[HarmonyPatch(typeof(PlayerInventory))]
	[HarmonyPatch("HandleDrop")]
	[HarmonyPostfix]
	public static void HandleDrop(PlayerInventory __instance)
	{
		//IL_0042: Unknown result type (might be due to invalid IL or missing references)
		//IL_0075: Unknown result type (might be due to invalid IL or missing references)
		//IL_0090: 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_00c6: Unknown result type (might be due to invalid IL or missing references)
		//IL_00f7: Unknown result type (might be due to invalid IL or missing references)
		//IL_011e: Unknown result type (might be due to invalid IL or missing references)
		if (((ButtonControl)Keyboard.current.cKey).wasPressedThisFrame)
		{
			if (VoidPouch.playerInventory == null)
			{
				VoidPouch.playerInventory = __instance;
			}
			if (__instance.slots[__instance.currentSlot.Value].itemId != -1)
			{
				LanVoidPouch lanVoidPouch = new LanVoidPouch(VoidPouch.slotName, VoidPouch.mapName, __instance.slots[__instance.currentSlot.Value].itemId, __instance.slots[__instance.currentSlot.Value].amount, __instance.slots[__instance.currentSlot.Value].cost, __instance.slots[__instance.currentSlot.Value].dayCounter, IsSave: false, deleted: false);
				lanVoidPouch.Insert(VoidPouch.connection);
				__instance.slots[__instance.currentSlot.Value] = new InventorySlot
				{
					itemId = -1L,
					amount = -1,
					cost = -1,
					dayCounter = -1
				};
			}
		}
	}

	[HarmonyPatch(typeof(GameManager))]
	[HarmonyPatch("OnDayChanged")]
	[HarmonyPostfix]
	public static void OnDayChanged(GameManager __instance)
	{
		LanVoidPouch.Save(VoidPouch.connection, VoidPouch.slotName, VoidPouch.mapName);
	}

	[HarmonyPostfix]
	[HarmonyPatch(typeof(PlayerInteraction), "Update")]
	public static void PlayerInteraction_Update_Postfix(PlayerInteraction __instance)
	{
		if (GameManager.Instance != null && Mouse.current != null && Mouse.current.leftButton.wasPressedThisFrame && ((Object)(object)VoidPouch._myVoidPanel == (Object)null || !VoidPouch._myVoidPanel.activeSelf) && !Cursor.visible)
		{
			AttemptDeleteItem(__instance);
		}
	}

	private static void AttemptDeleteItem(PlayerInteraction playerInteraction)
	{
		//IL_004c: 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_0060: Unknown result type (might be due to invalid IL or missing references)
		//IL_0061: 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)
		Camera main = Camera.main;
		if ((Object)(object)main == (Object)null)
		{
			return;
		}
		FieldInfo field = typeof(PlayerInteraction).GetField("isInteractionEnabled", BindingFlags.Instance | BindingFlags.NonPublic);
		if (!(bool)field.GetValue(playerInteraction))
		{
			return;
		}
		Ray val = main.ViewportPointToRay(Vector3.one / 2f);
		RaycastHit val2 = default(RaycastHit);
		if (Physics.Raycast(val, ref val2, playerInteraction.interactionDistance, LayerMask.op_Implicit(playerInteraction.layerMask), (QueryTriggerInteraction)1))
		{
			Item componentInParent = ((Component)((RaycastHit)(ref val2)).collider).GetComponentInParent<Item>();
			if ((Object)(object)componentInParent != (Object)null && ((Interactable)componentInParent).CanInteract())
			{
				ExecuteItemDeletion(componentInParent);
			}
		}
	}

	private static void ExecuteItemDeletion(Item item)
	{
		LanVoidPouch lanVoidPouch = new LanVoidPouch(VoidPouch.slotName, VoidPouch.mapName, item.itemSO.id, item.amount.Value, item.cost, item.dayCounter.Value, IsSave: false, deleted: false);
		lanVoidPouch.Insert(VoidPouch.connection);
		((Component)item).gameObject.SetActive(false);
		if ((Object)(object)((NetworkBehaviour)item).NetworkObject != (Object)null)
		{
			((NetworkBehaviour)item).NetworkObject.Despawn(true);
		}
	}
}
public class CustomButton : MonoBehaviour, IPointerEnterHandler, IEventSystemHandler, IPointerExitHandler
{
	public Image image;

	public TextMeshProUGUI textSubtitle;

	public TextMeshProUGUI textAmount;

	private int lanVoidPouchId;

	private long itemSoId;

	private string localName;

	private int number;

	private TextMeshProUGUI _targetInfoText;

	public void SetData(int lanVoidPouchId, long itemSoId, int amount, string localName, int number, TextMeshProUGUI infoText)
	{
		this.lanVoidPouchId = lanVoidPouchId;
		this.itemSoId = itemSoId;
		_targetInfoText = infoText;
		this.localName = localName;
		this.number = number;
		if ((Object)(object)textAmount != (Object)null)
		{
			((TMP_Text)textAmount).text = amount.ToString();
		}
	}

	public void OnPointerEnter(PointerEventData eventData)
	{
		if ((Object)(object)_targetInfoText != (Object)null)
		{
			((TMP_Text)_targetInfoText).text = $"{localName}: {number}";
		}
	}

	public void OnPointerExit(PointerEventData eventData)
	{
		if ((Object)(object)_targetInfoText != (Object)null)
		{
			((TMP_Text)_targetInfoText).text = "";
		}
	}
}
public class LanVoidPouch
{
	[PrimaryKey]
	[AutoIncrement]
	[Column("id")]
	public int Id { get; set; }

	[NotNull]
	[Column("saveName")]
	public string SaveName { get; set; }

	[NotNull]
	[Column("mapName")]
	public string MapName { get; set; }

	[NotNull]
	[Column("itemsoId")]
	public long ItemsoId { get; set; }

	[NotNull]
	[Column("amount")]
	public int Amount { get; set; }

	[NotNull]
	[Column("cost")]
	public int Cost { get; set; }

	[NotNull]
	[Column("dayCounter")]
	public int DayCounter { get; set; }

	[NotNull]
	[Column("isSave")]
	public bool IsSave { get; set; }

	[NotNull]
	[Column("Deleted")]
	public bool Deleted { get; set; }

	public LanVoidPouch()
	{
	}

	public LanVoidPouch(string saveName, string mapName, long itemsoId, int amount, int cost, int dayCounter, bool IsSave, bool deleted)
	{
		SaveName = saveName;
		MapName = mapName;
		ItemsoId = itemsoId;
		Amount = amount;
		Cost = cost;
		DayCounter = dayCounter;
		this.IsSave = IsSave;
		Deleted = deleted;
	}

	public long Insert(SQLiteConnection connection)
	{
		return connection.Execute("INSERT INTO LanVoidPouch (SaveName, MapName, ItemsoId, Amount, Cost, DayCounter, IsSave, Deleted) VALUES (?, ?, ?, ?, ?, ?, ?, ?)", SaveName, MapName, ItemsoId, Amount, Cost, DayCounter, IsSave, Deleted);
	}

	public void Delete(SQLiteConnection connection)
	{
		connection.Execute("UPDATE LanVoidPouch SET Deleted = 1 , isSave = 0 WHERE Id = ?", Id);
	}

	public static void Save(SQLiteConnection connection, string saveName, string mapName)
	{
		connection.Execute("UPDATE LanVoidPouch SET IsSave = TRUE WHERE SaveName = ? AND MapName = ?", saveName, mapName);
		connection.Execute("DELETE FROM LanVoidPouch WHERE SaveName = ? AND MapName = ? AND Deleted = TRUE", saveName, mapName);
	}

	public static void DeleteNotSave(SQLiteConnection connection, string saveName, string mapName)
	{
		connection.Execute("UPDATE LanVoidPouch SET IsSave = TRUE, Deleted = FALSE WHERE SaveName = ? AND MapName = ? AND Deleted = TRUE", saveName, mapName);
		connection.Execute("DELETE FROM LanVoidPouch WHERE SaveName = ? AND MapName = ? AND IsSave = 0", saveName, mapName);
	}

	public static List<LanVoidPouch> FindBySaveNameAndMapName(SQLiteConnection connection, string saveName, string mapName)
	{
		return connection.Query<LanVoidPouch>("SELECT * FROM LanVoidPouch WHERE SaveName = ? AND MapName = ? AND Deleted = 0 ORDER BY ItemsoId", new object[2] { saveName, mapName });
	}

	public static List<LanVoidPouch> FindBySaveNameAndMapNameAndItemSoId(SQLiteConnection connection, string saveName, string mapName, long itemSoId)
	{
		return connection.Query<LanVoidPouch>("SELECT * FROM LanVoidPouch WHERE SaveName = ? AND MapName = ? AND ItemsoId = ? AND Deleted = 0", new object[3] { saveName, mapName, itemSoId });
	}

	public static LanVoidPouch HasItemInSlot(SQLiteConnection connection, string saveName, string mapName, int slot)
	{
		return connection.Query<LanVoidPouch>("SELECT * FROM LanVoidPouch WHERE SaveName = ? AND MapName = ? AND Slot = ? AND Deleted = 0 ORDER BY Amount ASC", new object[3] { saveName, mapName, slot }).FirstOrDefault();
	}

	public static void DecreaseItemInSlot(SQLiteConnection connection, string saveName, string mapName, int itemSoId)
	{
		List<LanVoidPouch> list = connection.Query<LanVoidPouch>("SELECT * FROM LanVoidPouch WHERE SaveName = ? AND MapName = ? AND itemsoId = ? AND Deleted = 0 ORDER BY Amount ASC", new object[3] { saveName, mapName, itemSoId });
		if (list.Count > 0)
		{
			LanVoidPouch lanVoidPouch = list[0];
			if (lanVoidPouch.Amount == 1)
			{
				lanVoidPouch.Delete(connection);
				return;
			}
			lanVoidPouch.Delete(connection);
			connection.Insert(new LanVoidPouch(saveName, mapName, itemSoId, lanVoidPouch.Amount - 1, lanVoidPouch.Cost, lanVoidPouch.DayCounter, IsSave: false, deleted: false));
		}
	}

	public static int GetItemAmountInSlot(SQLiteConnection connection, string saveName, string mapName, long itemSoId)
	{
		List<LanVoidPouch> list = connection.Query<LanVoidPouch>("SELECT * FROM LanVoidPouch WHERE SaveName = ? AND MapName = ? AND ItemsoId = ? AND Deleted = 0", new object[3] { saveName, mapName, itemSoId });
		ItemSO itemById = GameManager.Instance.GetItemById(itemSoId);
		if (itemById.amount > 0)
		{
			int num = 0;
			foreach (LanVoidPouch item in list)
			{
				num += item.Amount;
			}
			return num;
		}
		return list.Sum((LanVoidPouch lanVoidPouch) => lanVoidPouch.Amount);
	}
}
public class RestockHook : BaseUnityPlugin
{
	[HarmonyPrefix]
	[HarmonyPatch(typeof(RestockerWait), "OnUpdate")]
	public static bool OnUpdate(RestockerWait __instance)
	{
		//IL_003b: Unknown result type (might be due to invalid IL or missing references)
		//IL_0041: Expected O, but got Unknown
		//IL_007e: Unknown result type (might be due to invalid IL or missing references)
		//IL_0084: Unknown result type (might be due to invalid IL or missing references)
		//IL_0094: Unknown result type (might be due to invalid IL or missing references)
		//IL_0117: Unknown result type (might be due to invalid IL or missing references)
		//IL_011d: Unknown result type (might be due to invalid IL or missing references)
		if (!((NetworkBehaviour)GameManager.Instance).IsHost)
		{
			return true;
		}
		FieldInfo field = typeof(RestockerWait).GetField("rc", BindingFlags.Instance | BindingFlags.NonPublic);
		RestockerController val = (RestockerController)field.GetValue(__instance);
		if (val.HasReachedDestination(1f))
		{
			val.agent.isStopped = true;
			val.ChangeAnimationState(__instance.idleAnimation, 0.05f);
			((Component)val).transform.rotation = Quaternion.Slerp(((Component)val).transform.rotation, val.GetInitialRotation(), 5f * Time.deltaTime);
		}
		FieldInfo field2 = typeof(RestockerWait).GetField("timer", BindingFlags.Instance | BindingFlags.NonPublic);
		float num = (float)field2.GetValue(__instance);
		num += Time.deltaTime;
		field2.SetValue(__instance, num);
		if (num < __instance.waitTime)
		{
			return false;
		}
		if (!FindItemToRestock(__instance))
		{
			field2.SetValue(__instance, 0f);
			if ((double)Vector3.Distance(((Component)val).transform.position, val.GetInitialPosition()) <= 1.0)
			{
				return false;
			}
			val.agent.isStopped = false;
			val.GoToStartPosition();
			val.ChangeAnimationState(__instance.walkAnimation, 0.05f);
		}
		return false;
	}

	public static bool FindItemToRestock(RestockerWait __instance)
	{
		//IL_0026: Unknown result type (might be due to invalid IL or missing references)
		//IL_0030: Expected O, but got Unknown
		//IL_011a: Unknown result type (might be due to invalid IL or missing references)
		//IL_0170: Unknown result type (might be due to invalid IL or missing references)
		FieldInfo field = typeof(RestockerWait).GetField("rc", BindingFlags.Instance | BindingFlags.NonPublic);
		RestockerController rc = (RestockerController)field.GetValue(__instance);
		foreach (Item item2 in (from x in Object.FindObjectsOfType<Item>()
			where x.onStand.Value && x.amount.Value <= 0 && !x.IsRestockTarget()
			select x into go
			orderby Vector3.Distance(((Component)go).transform.position, ((Component)rc).transform.position)
			select go).ToList())
		{
			Item item = item2;
			List<LanVoidPouch> list = LanVoidPouch.FindBySaveNameAndMapNameAndItemSoId(VoidPouch.connection, VoidPouch.slotName, VoidPouch.mapName, item.itemSO.id);
			if (list != null && list.Count > 0)
			{
				FieldInfo field2 = typeof(RestockerController).GetField("inventorySlot", BindingFlags.Instance | BindingFlags.NonPublic);
				NetworkVariable<InventorySlot> val = (NetworkVariable<InventorySlot>)field2.GetValue(rc);
				val.Value = new InventorySlot
				{
					itemId = list[0].ItemsoId,
					amount = list[0].Amount,
					cost = list[0].Cost,
					dayCounter = list[0].DayCounter
				};
				list[0].Delete(VoidPouch.connection);
				Item val2 = Object.FindAnyObjectByType<Item>();
				rc.SetItems(item, val2);
				rc.SetDestination(((Component)rc.targetItem).transform);
				rc.ChangeState(rc.stateRestockTarget);
				return true;
			}
			List<Item> list2 = (from x in Object.FindObjectsOfType<Item>()
				where (Object)(object)x.itemSO == (Object)(object)item.itemSO && x.IsInFreezer() && x.amount.Value > 0 && !x.IsRestockSource()
				select x into go
				orderby Vector3.Distance(((Component)go).transform.position, ((Component)rc).transform.position)
				select go).ToList();
			if (list2.Count > 0)
			{
				rc.SetItems(item, list2[0]);
				rc.SetDestination(((Component)rc.sourceItem).transform);
				rc.ChangeState(__instance.stateTakeSource);
				return true;
			}
		}
		return false;
	}
}
[BepInPlugin("com.lan.VoidPouch", "储物魂导器", "1.3.0")]
public class VoidPouch : BaseUnityPlugin
{
	public class Listen : MonoBehaviour
	{
		private void Update()
		{
			if (GameManager.Instance == null || UIManager.Instance == null)
			{
				return;
			}
			bool flag = (Object)(object)_myVoidPanel != (Object)null && _myVoidPanel.activeSelf;
			if (flag && ((ButtonControl)Keyboard.current.escapeKey).wasPressedThisFrame)
			{
				HidePanel();
				return;
			}
			if (((ButtonControl)Keyboard.current.bKey).wasPressedThisFrame)
			{
				if (!flag)
				{
					mouseIsShow = Cursor.visible;
					ui();
					Cursor.lockState = (CursorLockMode)0;
					Cursor.visible = true;
				}
				else
				{
					HidePanel();
				}
			}
			if (Mouse.current != null && Mouse.current.backButton.wasPressedThisFrame)
			{
				if (!flag)
				{
					mouseIsShow = Cursor.visible;
					ui();
					Cursor.lockState = (CursorLockMode)0;
					Cursor.visible = true;
				}
				else
				{
					HidePanel();
				}
			}
			if (Mouse.current != null && Mouse.current.rightButton.wasPressedThisFrame && flag)
			{
				HidePanel();
			}
		}

		public static void HidePanel()
		{
			if ((Object)(object)_myVoidPanel != (Object)null && _myVoidPanel.activeSelf)
			{
				_myVoidPanel.SetActive(false);
				((Behaviour)playerInventory).enabled = true;
				if (!mouseIsShow)
				{
					Cursor.lockState = (CursorLockMode)1;
					Cursor.visible = false;
				}
			}
			if (!_myVoidPanel.activeSelf)
			{
				((Behaviour)playerInventory).enabled = true;
				if (!mouseIsShow)
				{
					Cursor.lockState = (CursorLockMode)1;
					Cursor.visible = false;
				}
			}
		}
	}

	[Serializable]
	[CompilerGenerated]
	private sealed class <>c
	{
		public static readonly <>c <>9 = new <>c();

		public static UnityAction <>9__10_0;

		public static Func<LanVoidPouch, int> <>9__10_4;

		internal void <ui>b__10_0()
		{
			((Behaviour)playerInventory).enabled = true;
			if (!mouseIsShow)
			{
				Cursor.lockState = (CursorLockMode)1;
				Cursor.visible = false;
			}
		}

		internal int <ui>b__10_4(LanVoidPouch x)
		{
			return x.Amount;
		}
	}

	public static PlayerInventory playerInventory;

	public static string mapName;

	public static string slotName;

	public static string dbPath;

	public static SQLiteConnection connection;

	public static GameObject _myVoidPanel;

	private static Transform _myListContainer;

	public static bool mouseIsShow;

	private void Awake()
	{
		//IL_0006: Unknown result type (might be due to invalid IL or missing references)
		//IL_000c: Expected O, but got Unknown
		//IL_00e9: Unknown result type (might be due to invalid IL or missing references)
		//IL_00ef: Expected O, but got Unknown
		Harmony val = new Harmony("com.lan.VoidPouch");
		val.PatchAll();
		val.PatchAll(typeof(BagHook));
		val.PatchAll(typeof(RestockHook));
		string directoryName = Path.GetDirectoryName(Application.dataPath);
		dbPath = Path.Combine(directoryName, "lan.mod.db");
		if (!File.Exists(dbPath))
		{
			using (File.Create(dbPath))
			{
			}
			Debug.Log((object)("数据库文件已创建: " + dbPath));
		}
		try
		{
			connection = new SQLiteConnection(dbPath);
			connection.CreateTable<LanVoidPouch>();
		}
		catch (Exception ex)
		{
			Debug.LogError((object)("数据库连接失败,请下载前置Mod:https://thunderstore.io/c/old-market-simulator/p/Lan/WheelchairRanch" + ex.Message));
			throw;
		}
		SceneManager.sceneLoaded += OnSceneLoaded;
		GameObject val2 = new GameObject("Listen");
		((Object)val2).hideFlags = (HideFlags)61;
		val2.AddComponent<Listen>();
		Debug.LogWarning((object)"储物魂导器加载完成 --作者:她说缝上都不给我");
	}

	private void OnSceneLoaded(Scene scene, LoadSceneMode mode)
	{
		//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)
		if (GameManager.Instance != null)
		{
			FieldInfo field = ((object)SaveManager.Instance).GetType().GetField("currentSlot", BindingFlags.Instance | BindingFlags.NonPublic);
			slotName = field.GetValue(SaveManager.Instance).ToString();
			Scene activeScene = SceneManager.GetActiveScene();
			mapName = ((Scene)(ref activeScene)).name;
			LanVoidPouch.DeleteNotSave(connection, slotName, mapName);
		}
	}

	public static void ui()
	{
		//IL_022f: Unknown result type (might be due to invalid IL or missing references)
		//IL_0245: Unknown result type (might be due to invalid IL or missing references)
		//IL_033b: Unknown result type (might be due to invalid IL or missing references)
		//IL_0342: Expected O, but got Unknown
		//IL_036a: Unknown result type (might be due to invalid IL or missing references)
		//IL_0381: Unknown result type (might be due to invalid IL or missing references)
		//IL_039a: Unknown result type (might be due to invalid IL or missing references)
		//IL_03a1: Expected O, but got Unknown
		//IL_03b7: Unknown result type (might be due to invalid IL or missing references)
		//IL_03c4: Unknown result type (might be due to invalid IL or missing references)
		//IL_03db: Unknown result type (might be due to invalid IL or missing references)
		//IL_03f2: Unknown result type (might be due to invalid IL or missing references)
		//IL_0402: Unknown result type (might be due to invalid IL or missing references)
		//IL_0409: Expected O, but got Unknown
		//IL_041f: Unknown result type (might be due to invalid IL or missing references)
		//IL_042c: Unknown result type (might be due to invalid IL or missing references)
		//IL_0439: Unknown result type (might be due to invalid IL or missing references)
		//IL_0446: Unknown result type (might be due to invalid IL or missing references)
		//IL_0480: Unknown result type (might be due to invalid IL or missing references)
		//IL_0487: Expected O, but got Unknown
		//IL_04a7: Unknown result type (might be due to invalid IL or missing references)
		//IL_04b4: Unknown result type (might be due to invalid IL or missing references)
		//IL_0501: Unknown result type (might be due to invalid IL or missing references)
		//IL_05f3: Unknown result type (might be due to invalid IL or missing references)
		//IL_05fd: Expected O, but got Unknown
		//IL_0197: Unknown result type (might be due to invalid IL or missing references)
		//IL_019c: Unknown result type (might be due to invalid IL or missing references)
		//IL_01a2: Expected O, but got Unknown
		if ((Object)(object)_myVoidPanel == (Object)null)
		{
			_myVoidPanel = Object.Instantiate<GameObject>(UIManager.Instance.panelDockOrders, UIManager.Instance.panelDockOrders.transform.parent);
			((Object)_myVoidPanel).name = "Panel_VoidPouch";
			MonoBehaviour[] components = _myVoidPanel.GetComponents<MonoBehaviour>();
			MonoBehaviour[] array = components;
			foreach (MonoBehaviour val in array)
			{
				Type type = ((object)val).GetType();
				string @namespace = type.Namespace;
				if (@namespace == null || (!@namespace.StartsWith("UnityEngine") && !@namespace.StartsWith("TMPro")))
				{
					Object.DestroyImmediate((Object)(object)val);
				}
			}
			string transformPath = GetTransformPath(((Component)UIManager.Instance.listDockOrders).transform, UIManager.Instance.panelDockOrders.transform);
			_myListContainer = _myVoidPanel.transform.Find(transformPath);
			if ((Object)(object)_myListContainer == (Object)null)
			{
				VerticalLayoutGroup componentInChildren = _myVoidPanel.GetComponentInChildren<VerticalLayoutGroup>();
				object obj = ((componentInChildren != null) ? ((Component)componentInChildren).transform : null);
				if (obj == null)
				{
					GridLayoutGroup componentInChildren2 = _myVoidPanel.GetComponentInChildren<GridLayoutGroup>();
					obj = ((componentInChildren2 != null) ? ((Component)componentInChildren2).transform : null);
				}
				_myListContainer = (Transform)obj;
			}
			Button[] componentsInChildren = _myVoidPanel.GetComponentsInChildren<Button>(true);
			Button[] array2 = componentsInChildren;
			foreach (Button val2 in array2)
			{
				if (!(((Object)val2).name == "ButtonClose"))
				{
					continue;
				}
				ButtonClickedEvent onClick = val2.onClick;
				object obj2 = <>c.<>9__10_0;
				if (obj2 == null)
				{
					UnityAction val3 = delegate
					{
						((Behaviour)playerInventory).enabled = true;
						if (!mouseIsShow)
						{
							Cursor.lockState = (CursorLockMode)1;
							Cursor.visible = false;
						}
					};
					<>c.<>9__10_0 = val3;
					obj2 = (object)val3;
				}
				((UnityEvent)onClick).AddListener((UnityAction)obj2);
				break;
			}
		}
		GridLayoutGroup val4 = ((Component)_myListContainer).GetComponent<GridLayoutGroup>();
		if ((Object)(object)val4 == (Object)null)
		{
			LayoutGroup[] components2 = ((Component)_myListContainer).GetComponents<LayoutGroup>();
			foreach (LayoutGroup val5 in components2)
			{
				Object.DestroyImmediate((Object)(object)val5);
			}
			val4 = ((Component)_myListContainer).gameObject.AddComponent<GridLayoutGroup>();
		}
		val4.constraint = (Constraint)1;
		val4.constraintCount = 10;
		val4.cellSize = new Vector2(90f, 90f);
		val4.spacing = new Vector2(8f, 8f);
		val4.startCorner = (Corner)0;
		val4.startAxis = (Axis)0;
		((LayoutGroup)val4).childAlignment = (TextAnchor)4;
		for (int num = _myListContainer.childCount - 1; num >= 0; num--)
		{
			Object.DestroyImmediate((Object)(object)((Component)_myListContainer.GetChild(num)).gameObject);
		}
		List<Button> list = new List<Button>();
		List<LanVoidPouch> list2 = LanVoidPouch.FindBySaveNameAndMapName(connection, slotName, mapName);
		TextMeshProUGUI[] componentsInChildren2 = _myVoidPanel.GetComponentsInChildren<TextMeshProUGUI>();
		TextMeshProUGUI val6 = componentsInChildren2[^2];
		((TMP_Text)val6).text = "";
		((TMP_Text)componentsInChildren2[^1]).text = "";
		for (int l = 0; l < list2.Count(); l++)
		{
			LanVoidPouch item = list2[l];
			ItemSO itemById = GameManager.Instance.GetItemById(item.ItemsoId);
			GameObject val7 = new GameObject($"CustomItem_{l}");
			val7.transform.SetParent(_myListContainer, false);
			RectTransform val8 = val7.AddComponent<RectTransform>();
			val8.pivot = new Vector2(0.5f, 0.5f);
			val8.sizeDelta = new Vector2(90f, 90f);
			Button val9 = val7.AddComponent<Button>();
			GameObject val10 = new GameObject("Content");
			RectTransform val11 = val10.AddComponent<RectTransform>();
			((Transform)val11).SetParent((Transform)(object)val8, false);
			val11.anchorMin = Vector2.zero;
			val11.anchorMax = Vector2.one;
			val11.offsetMin = new Vector2(5f, 5f);
			val11.offsetMax = new Vector2(-5f, -5f);
			GameObject val12 = new GameObject("ItemImage");
			RectTransform val13 = val12.AddComponent<RectTransform>();
			((Transform)val13).SetParent((Transform)(object)val11, false);
			val13.anchorMin = Vector2.zero;
			val13.anchorMax = Vector2.one;
			val13.sizeDelta = Vector2.zero;
			val13.anchoredPosition = Vector2.zero;
			Image val14 = val12.AddComponent<Image>();
			val14.sprite = itemById.sprite;
			val14.preserveAspect = true;
			((Graphic)val14).raycastTarget = true;
			GameObject val15 = new GameObject("AmountText");
			RectTransform val16 = val15.AddComponent<RectTransform>();
			((Transform)val16).SetParent((Transform)(object)val8, false);
			val16.anchorMin = new Vector2(0.8f, 0.8f);
			val16.anchorMax = Vector2.one;
			TextMeshProUGUI val17 = val15.AddComponent<TextMeshProUGUI>();
			((TMP_Text)val17).text = item.Amount.ToString();
			((TMP_Text)val17).fontSize = 30f;
			((TMP_Text)val17).alignment = (TextAlignmentOptions)514;
			((Graphic)val17).color = Color.white;
			((Graphic)val17).raycastTarget = false;
			CustomButton customButton = val7.AddComponent<CustomButton>();
			customButton.image = val14;
			customButton.textAmount = val17;
			int num2 = 0;
			if (itemById.amount > 1)
			{
				num2 = list2.Where((LanVoidPouch x) => x.ItemsoId == item.ItemsoId).Count();
			}
			else
			{
				List<LanVoidPouch> source = list2.Where((LanVoidPouch x) => x.ItemsoId == item.ItemsoId).ToList();
				num2 = source.Sum((LanVoidPouch x) => x.Amount);
			}
			customButton.SetData(item.Id, itemById.id, item.Amount, itemById.GetLocalizedName(), num2, val6);
			((UnityEventBase)val9.onClick).RemoveAllListeners();
			((UnityEvent)val9.onClick).AddListener((UnityAction)delegate
			{
				playerInventory.GiveItemServerRpc(item.ItemsoId, item.Amount, item.Cost, item.DayCounter);
				item.Delete(connection);
				ui();
			});
			list.Add(val9);
		}
		MethodInfo method = typeof(UIManager).GetMethod("SetupSmartWrappedGridNavigation", BindingFlags.Instance | BindingFlags.NonPublic);
		if (method != null)
		{
			method.Invoke(UIManager.Instance, new object[3] { list, 10, true });
		}
		_myVoidPanel.SetActive(true);
		((Behaviour)playerInventory).enabled = false;
		if (((object)LocalizationSettings.SelectedLocale).ToString().Contains("Chinese"))
		{
			((TMP_Text)componentsInChildren2[^3]).text = "点击物品可以将其取回背包";
		}
		else
		{
			((TMP_Text)componentsInChildren2[^3]).text = "Click on the item to put it in your backpack";
		}
		((TMP_Text)componentsInChildren2[^4]).text = "储物魂导器(VoidPouch)";
	}

	private static string GetTransformPath(Transform target, Transform root)
	{
		if ((Object)(object)target == (Object)(object)root)
		{
			return "";
		}
		string text = ((Object)target).name;
		while ((Object)(object)target.parent != (Object)null && (Object)(object)target.parent != (Object)(object)root)
		{
			target = target.parent;
			text = ((Object)target).name + "/" + text;
		}
		return text;
	}
}
namespace SQLite;

public class SQLiteException : Exception
{
	public SQLite3.Result Result { get; private set; }

	protected SQLiteException(SQLite3.Result r, string message)
		: base(message)
	{
		Result = r;
	}

	public static SQLiteException New(SQLite3.Result r, string message)
	{
		return new SQLiteException(r, message);
	}
}
public class NotNullConstraintViolationException : SQLiteException
{
	public IEnumerable<TableMapping.Column> Columns { get; protected set; }

	protected NotNullConstraintViolationException(SQLite3.Result r, string message)
		: this(r, message, null, null)
	{
	}

	protected NotNullConstraintViolationException(SQLite3.Result r, string message, TableMapping mapping, object obj)
		: base(r, message)
	{
		if (mapping != null && obj != null)
		{
			Columns = mapping.Columns.Where((TableMapping.Column c) => !c.IsNullable && c.GetValue(obj) == null);
		}
	}

	public new static NotNullConstraintViolationException New(SQLite3.Result r, string message)
	{
		return new NotNullConstraintViolationException(r, message);
	}

	public static NotNullConstraintViolationException New(SQLite3.Result r, string message, TableMapping mapping, object obj)
	{
		return new NotNullConstraintViolationException(r, message, mapping, obj);
	}

	public static NotNullConstraintViolationException New(SQLiteException exception, TableMapping mapping, object obj)
	{
		return new NotNullConstraintViolationException(exception.Result, exception.Message, mapping, obj);
	}
}
[Flags]
public enum SQLiteOpenFlags
{
	ReadOnly = 1,
	ReadWrite = 2,
	Create = 4,
	Uri = 0x40,
	Memory = 0x80,
	NoMutex = 0x8000,
	FullMutex = 0x10000,
	SharedCache = 0x20000,
	PrivateCache = 0x40000,
	ProtectionComplete = 0x100000,
	ProtectionCompleteUnlessOpen = 0x200000,
	ProtectionCompleteUntilFirstUserAuthentication = 0x300000,
	ProtectionNone = 0x400000
}
[Flags]
public enum CreateFlags
{
	None = 0,
	ImplicitPK = 1,
	ImplicitIndex = 2,
	AllImplicit = 3,
	AutoIncPK = 4,
	FullTextSearch3 = 0x100,
	FullTextSearch4 = 0x200
}
public interface ISQLiteConnection : IDisposable
{
	IntPtr Handle { get; }

	string DatabasePath { get; }

	int LibVersionNumber { get; }

	bool TimeExecution { get; set; }

	bool Trace { get; set; }

	Action<string> Tracer { get; set; }

	bool StoreDateTimeAsTicks { get; }

	bool StoreTimeSpanAsTicks { get; }

	string DateTimeStringFormat { get; }

	TimeSpan BusyTimeout { get; set; }

	IEnumerable<TableMapping> TableMappings { get; }

	bool IsInTransaction { get; }

	event EventHandler<NotifyTableChangedEventArgs> TableChanged;

	void Backup(string destinationDatabasePath, string databaseName = "main");

	void BeginTransaction();

	void Close();

	void Commit();

	SQLiteCommand CreateCommand(string cmdText, params object[] ps);

	SQLiteCommand CreateCommand(string cmdText, Dictionary<string, object> args);

	int CreateIndex(string indexName, string tableName, string[] columnNames, bool unique = false);

	int CreateIndex(string indexName, string tableName, string columnName, bool unique = false);

	int CreateIndex(string tableName, string columnName, bool unique = false);

	int CreateIndex(string tableName, string[] columnNames, bool unique = false);

	int CreateIndex<T>(Expression<Func<T, object>> property, bool unique = false);

	CreateTableResult CreateTable<T>(CreateFlags createFlags = CreateFlags.None);

	CreateTableResult CreateTable(Type ty, CreateFlags createFlags = CreateFlags.None);

	CreateTablesResult CreateTables<T, T2>(CreateFlags createFlags = CreateFlags.None) where T : new() where T2 : new();

	CreateTablesResult CreateTables<T, T2, T3>(CreateFlags createFlags = CreateFlags.None) where T : new() where T2 : new() where T3 : new();

	CreateTablesResult CreateTables<T, T2, T3, T4>(CreateFlags createFlags = CreateFlags.None) where T : new() where T2 : new() where T3 : new() where T4 : new();

	CreateTablesResult CreateTables<T, T2, T3, T4, T5>(CreateFlags createFlags = CreateFlags.None) where T : new() where T2 : new() where T3 : new() where T4 : new() where T5 : new();

	CreateTablesResult CreateTables(CreateFlags createFlags = CreateFlags.None, params Type[] types);

	IEnumerable<T> DeferredQuery<T>(string query, params object[] args) where T : new();

	IEnumerable<object> DeferredQuery(TableMapping map, string query, params object[] args);

	int Delete(object objectToDelete);

	int Delete<T>(object primaryKey);

	int Delete(object primaryKey, TableMapping map);

	int DeleteAll<T>();

	int DeleteAll(TableMapping map);

	int DropTable<T>();

	int DropTable(TableMapping map);

	void EnableLoadExtension(bool enabled);

	void EnableWriteAheadLogging();

	int Execute(string query, params object[] args);

	T ExecuteScalar<T>(string query, params object[] args);

	T Find<T>(object pk) where T : new();

	object Find(object pk, TableMapping map);

	T Find<T>(Expression<Func<T, bool>> predicate) where T : new();

	T FindWithQuery<T>(string query, params object[] args) where T : new();

	object FindWithQuery(TableMapping map, string query, params object[] args);

	T Get<T>(object pk) where T : new();

	object Get(object pk, TableMapping map);

	T Get<T>(Expression<Func<T, bool>> predicate) where T : new();

	TableMapping GetMapping(Type type, CreateFlags createFlags = CreateFlags.None);

	TableMapping GetMapping<T>(CreateFlags createFlags = CreateFlags.None);

	List<SQLiteConnection.ColumnInfo> GetTableInfo(string tableName);

	int Insert(object obj);

	int Insert(object obj, Type objType);

	int Insert(object obj, string extra);

	int Insert(object obj, string extra, Type objType);

	int InsertAll(IEnumerable objects, bool runInTransaction = true);

	int InsertAll(IEnumerable objects, string extra, bool runInTransaction = true);

	int InsertAll(IEnumerable objects, Type objType, bool runInTransaction = true);

	int InsertOrReplace(object obj);

	int InsertOrReplace(object obj, Type objType);

	List<T> Query<T>(string query, params object[] args) where T : new();

	List<object> Query(TableMapping map, string query, params object[] args);

	List<T> QueryScalars<T>(string query, params object[] args);

	void ReKey(string key);

	void ReKey(byte[] key);

	void Release(string savepoint);

	void Rollback();

	void RollbackTo(string savepoint);

	void RunInTransaction(Action action);

	string SaveTransactionPoint();

	TableQuery<T> Table<T>() where T : new();

	int Update(object obj);

	int Update(object obj, Type objType);

	int UpdateAll(IEnumerable objects, bool runInTransaction = true);
}
[Preserve(AllMembers = true)]
public class SQLiteConnection : ISQLiteConnection, IDisposable
{
	private struct IndexedColumn
	{
		public int Order;

		public string ColumnName;
	}

	private struct IndexInfo
	{
		public string IndexName;

		public string TableName;

		public bool Unique;

		public List<IndexedColumn> Columns;
	}

	[Preserve(AllMembers = true)]
	public class ColumnInfo
	{
		[Column("name")]
		public string Name { get; set; }

		public int notnull { get; set; }

		public override string ToString()
		{
			return Name;
		}
	}

	private bool _open;

	private TimeSpan _busyTimeout;

	private static readonly Dictionary<string, TableMapping> _mappings = new Dictionary<string, TableMapping>();

	private Stopwatch _sw;

	private long _elapsedMilliseconds = 0L;

	private int _transactionDepth = 0;

	private Random _rand = new Random();

	private static readonly IntPtr NullHandle = default(IntPtr);

	private static readonly IntPtr NullBackupHandle = default(IntPtr);

	private readonly Dictionary<Tuple<string, string>, PreparedSqlLiteInsertCommand> _insertCommandMap = new Dictionary<Tuple<string, string>, PreparedSqlLiteInsertCommand>();

	public IntPtr Handle { get; private set; }

	public string DatabasePath { get; private set; }

	public int LibVersionNumber { get; private set; }

	public bool TimeExecution { get; set; }

	public bool Trace { get; set; }

	public Action<string> Tracer { get; set; }

	public bool StoreDateTimeAsTicks { get; private set; }

	public bool StoreTimeSpanAsTicks { get; private set; }

	public string DateTimeStringFormat { get; private set; }

	internal DateTimeStyles DateTimeStyle { get; private set; }

	public TimeSpan BusyTimeout
	{
		get
		{
			return _busyTimeout;
		}
		set
		{
			_busyTimeout = value;
			if (Handle != NullHandle)
			{
				SQLite3.BusyTimeout(Handle, (int)_busyTimeout.TotalMilliseconds);
			}
		}
	}

	public IEnumerable<TableMapping> TableMappings
	{
		get
		{
			lock (_mappings)
			{
				return new List<TableMapping>(_mappings.Values);
			}
		}
	}

	public bool IsInTransaction => _transactionDepth > 0;

	public event EventHandler<NotifyTableChangedEventArgs> TableChanged;

	public SQLiteConnection(string databasePath, bool storeDateTimeAsTicks = true)
		: this(new SQLiteConnectionString(databasePath, SQLiteOpenFlags.ReadWrite | SQLiteOpenFlags.Create, storeDateTimeAsTicks))
	{
	}

	public SQLiteConnection(string databasePath, SQLiteOpenFlags openFlags, bool storeDateTimeAsTicks = true)
		: this(new SQLiteConnectionString(databasePath, openFlags, storeDateTimeAsTicks))
	{
	}

	public SQLiteConnection(SQLiteConnectionString connectionString)
	{
		if (connectionString == null)
		{
			throw new ArgumentNullException("connectionString");
		}
		if (connectionString.DatabasePath == null)
		{
			throw new InvalidOperationException("DatabasePath must be specified");
		}
		DatabasePath = connectionString.DatabasePath;
		LibVersionNumber = SQLite3.LibVersionNumber();
		byte[] nullTerminatedUtf = GetNullTerminatedUtf8(connectionString.DatabasePath);
		IntPtr db;
		SQLite3.Result result = SQLite3.Open(nullTerminatedUtf, out db, (int)connectionString.OpenFlags, connectionString.VfsName);
		Handle = db;
		if (result != 0)
		{
			throw SQLiteException.New(result, $"Could not open database file: {DatabasePath} ({result})");
		}
		_open = true;
		StoreDateTimeAsTicks = connectionString.StoreDateTimeAsTicks;
		StoreTimeSpanAsTicks = connectionString.StoreTimeSpanAsTicks;
		DateTimeStringFormat = connectionString.DateTimeStringFormat;
		DateTimeStyle = connectionString.DateTimeStyle;
		BusyTimeout = TimeSpan.FromSeconds(1.0);
		Tracer = delegate(string line)
		{
			Debug.WriteLine(line);
		};
		connectionString.PreKeyAction?.Invoke(this);
		if (connectionString.Key is string key)
		{
			SetKey(key);
		}
		else if (connectionString.Key is byte[] key2)
		{
			SetKey(key2);
		}
		else if (connectionString.Key != null)
		{
			throw new InvalidOperationException("Encryption keys must be strings or byte arrays");
		}
		connectionString.PostKeyAction?.Invoke(this);
	}

	public void EnableWriteAheadLogging()
	{
		ExecuteScalar<string>("PRAGMA journal_mode=WAL", Array.Empty<object>());
	}

	private static string Quote(string unsafeString)
	{
		if (unsafeString == null)
		{
			return "NULL";
		}
		string text = unsafeString.Replace("'", "''");
		return "'" + text + "'";
	}

	private void SetKey(string key)
	{
		if (key == null)
		{
			throw new ArgumentNullException("key");
		}
		string text = Quote(key);
		ExecuteScalar<string>("pragma key = " + text, Array.Empty<object>());
	}

	private void SetKey(byte[] key)
	{
		if (key == null)
		{
			throw new ArgumentNullException("key");
		}
		if (key.Length != 32 && key.Length != 48)
		{
			throw new ArgumentException("Key must be 32 bytes (256-bit) or 48 bytes (384-bit)", "key");
		}
		string text = string.Join("", key.Select((byte x) => x.ToString("X2")));
		ExecuteScalar<string>("pragma key = \"x'" + text + "'\"", Array.Empty<object>());
	}

	public void ReKey(string key)
	{
		if (key == null)
		{
			throw new ArgumentNullException("key");
		}
		string text = Quote(key);
		ExecuteScalar<string>("pragma rekey = " + text, Array.Empty<object>());
	}

	public void ReKey(byte[] key)
	{
		if (key == null)
		{
			throw new ArgumentNullException("key");
		}
		if (key.Length != 32 && key.Length != 48)
		{
			throw new ArgumentException("Key must be 32 bytes (256-bit) or 48 bytes (384-bit)", "key");
		}
		string text = string.Join("", key.Select((byte x) => x.ToString("X2")));
		ExecuteScalar<string>("pragma rekey = \"x'" + text + "'\"", Array.Empty<object>());
	}

	public void EnableLoadExtension(bool enabled)
	{
		SQLite3.Result result = SQLite3.EnableLoadExtension(Handle, enabled ? 1 : 0);
		if (result != 0)
		{
			string errmsg = SQLite3.GetErrmsg(Handle);
			throw SQLiteException.New(result, errmsg);
		}
	}

	private static byte[] GetNullTerminatedUtf8(string s)
	{
		int byteCount = Encoding.UTF8.GetByteCount(s);
		byte[] array = new byte[byteCount + 1];
		byteCount = Encoding.UTF8.GetBytes(s, 0, s.Length, array, 0);
		return array;
	}

	public TableMapping GetMapping(Type type, CreateFlags createFlags = CreateFlags.None)
	{
		string fullName = type.FullName;
		TableMapping value;
		lock (_mappings)
		{
			if (_mappings.TryGetValue(fullName, out value))
			{
				if (createFlags != 0 && createFlags != value.CreateFlags)
				{
					value = new TableMapping(type, createFlags);
					_mappings[fullName] = value;
				}
			}
			else
			{
				value = new TableMapping(type, createFlags);
				_mappings.Add(fullName, value);
			}
		}
		return value;
	}

	public TableMapping GetMapping<T>(CreateFlags createFlags = CreateFlags.None)
	{
		return GetMapping(typeof(T), createFlags);
	}

	public int DropTable<T>()
	{
		return DropTable(GetMapping(typeof(T)));
	}

	public int DropTable(TableMapping map)
	{
		string query = $"drop table if exists \"{map.TableName}\"";
		return Execute(query);
	}

	public CreateTableResult CreateTable<T>(CreateFlags createFlags = CreateFlags.None)
	{
		return CreateTable(typeof(T), createFlags);
	}

	public CreateTableResult CreateTable(Type ty, CreateFlags createFlags = CreateFlags.None)
	{
		TableMapping mapping = GetMapping(ty, createFlags);
		if (mapping.Columns.Length == 0)
		{
			throw new Exception($"Cannot create a table without columns (does '{ty.FullName}' have public properties?)");
		}
		CreateTableResult result = CreateTableResult.Created;
		List<ColumnInfo> tableInfo = GetTableInfo(mapping.TableName);
		if (tableInfo.Count == 0)
		{
			bool flag = (createFlags & CreateFlags.FullTextSearch3) != 0;
			bool flag2 = (createFlags & CreateFlags.FullTextSearch4) != 0;
			string text = ((flag || flag2) ? "virtual " : string.Empty);
			string text2 = (flag ? "using fts3 " : (flag2 ? "using fts4 " : string.Empty));
			string text3 = "create " + text + "table if not exists \"" + mapping.TableName + "\" " + text2 + "(\n";
			IEnumerable<string> source = mapping.Columns.Select((TableMapping.Column p) => Orm.SqlDecl(p, StoreDateTimeAsTicks, StoreTimeSpanAsTicks));
			string text4 = string.Join(",\n", source.ToArray());
			text3 += text4;
			text3 += ")";
			if (mapping.WithoutRowId)
			{
				text3 += " without rowid";
			}
			Execute(text3);
		}
		else
		{
			result = CreateTableResult.Migrated;
			MigrateTable(mapping, tableInfo);
		}
		Dictionary<string, IndexInfo> dictionary = new Dictionary<string, IndexInfo>();
		TableMapping.Column[] columns = mapping.Columns;
		foreach (TableMapping.Column column in columns)
		{
			foreach (IndexedAttribute index in column.Indices)
			{
				string text5 = index.Name ?? (mapping.TableName + "_" + column.Name);
				if (!dictionary.TryGetValue(text5, out var value))
				{
					IndexInfo indexInfo = default(IndexInfo);
					indexInfo.IndexName = text5;
					indexInfo.TableName = mapping.TableName;
					indexInfo.Unique = index.Unique;
					indexInfo.Columns = new List<IndexedColumn>();
					value = indexInfo;
					dictionary.Add(text5, value);
				}
				if (index.Unique != value.Unique)
				{
					throw new Exception("All the columns in an index must have the same value for their Unique property");
				}
				value.Columns.Add(new IndexedColumn
				{
					Order = index.Order,
					ColumnName = column.Name
				});
			}
		}
		foreach (string key in dictionary.Keys)
		{
			IndexInfo indexInfo2 = dictionary[key];
			string[] columnNames = (from i in indexInfo2.Columns
				orderby i.Order
				select i.ColumnName).ToArray();
			CreateIndex(key, indexInfo2.TableName, columnNames, indexInfo2.Unique);
		}
		return result;
	}

	public CreateTablesResult CreateTables<T, T2>(CreateFlags createFlags = CreateFlags.None) where T : new() where T2 : new()
	{
		return CreateTables(createFlags, typeof(T), typeof(T2));
	}

	public CreateTablesResult CreateTables<T, T2, T3>(CreateFlags createFlags = CreateFlags.None) where T : new() where T2 : new() where T3 : new()
	{
		return CreateTables(createFlags, typeof(T), typeof(T2), typeof(T3));
	}

	public CreateTablesResult CreateTables<T, T2, T3, T4>(CreateFlags createFlags = CreateFlags.None) where T : new() where T2 : new() where T3 : new() where T4 : new()
	{
		return CreateTables(createFlags, typeof(T), typeof(T2), typeof(T3), typeof(T4));
	}

	public CreateTablesResult CreateTables<T, T2, T3, T4, T5>(CreateFlags createFlags = CreateFlags.None) where T : new() where T2 : new() where T3 : new() where T4 : new() where T5 : new()
	{
		return CreateTables(createFlags, typeof(T), typeof(T2), typeof(T3), typeof(T4), typeof(T5));
	}

	public CreateTablesResult CreateTables(CreateFlags createFlags = CreateFlags.None, params Type[] types)
	{
		CreateTablesResult createTablesResult = new CreateTablesResult();
		foreach (Type type in types)
		{
			CreateTableResult value = CreateTable(type, createFlags);
			createTablesResult.Results[type] = value;
		}
		return createTablesResult;
	}

	public int CreateIndex(string indexName, string tableName, string[] columnNames, bool unique = false)
	{
		string query = string.Format("create {2} index if not exists \"{3}\" on \"{0}\"(\"{1}\")", tableName, string.Join("\", \"", columnNames), unique ? "unique" : "", indexName);
		return Execute(query);
	}

	public int CreateIndex(string indexName, string tableName, string columnName, bool unique = false)
	{
		return CreateIndex(indexName, tableName, new string[1] { columnName }, unique);
	}

	public int CreateIndex(string tableName, string columnName, bool unique = false)
	{
		return CreateIndex(tableName + "_" + columnName, tableName, columnName, unique);
	}

	public int CreateIndex(string tableName, string[] columnNames, bool unique = false)
	{
		return CreateIndex(tableName + "_" + string.Join("_", columnNames), tableName, columnNames, unique);
	}

	public int CreateIndex<T>(Expression<Func<T, object>> property, bool unique = false)
	{
		MemberExpression memberExpression = ((property.Body.NodeType != ExpressionType.Convert) ? (property.Body as MemberExpression) : (((UnaryExpression)property.Body).Operand as MemberExpression));
		PropertyInfo propertyInfo = memberExpression.Member as PropertyInfo;
		if (propertyInfo == null)
		{
			throw new ArgumentException("The lambda expression 'property' should point to a valid Property");
		}
		string name = propertyInfo.Name;
		TableMapping mapping = GetMapping<T>();
		string name2 = mapping.FindColumnWithPropertyName(name).Name;
		return CreateIndex(mapping.TableName, name2, unique);
	}

	public List<ColumnInfo> GetTableInfo(string tableName)
	{
		string query = "pragma table_info(\"" + tableName + "\")";
		return Query<ColumnInfo>(query, Array.Empty<object>());
	}

	private void MigrateTable(TableMapping map, List<ColumnInfo> existingCols)
	{
		List<TableMapping.Column> list = new List<TableMapping.Column>();
		TableMapping.Column[] columns = map.Columns;
		foreach (TableMapping.Column column in columns)
		{
			bool flag = false;
			foreach (ColumnInfo existingCol in existingCols)
			{
				flag = string.Compare(column.Name, existingCol.Name, StringComparison.OrdinalIgnoreCase) == 0;
				if (flag)
				{
					break;
				}
			}
			if (!flag)
			{
				list.Add(column);
			}
		}
		foreach (TableMapping.Column item in list)
		{
			string query = "alter table \"" + map.TableName + "\" add column " + Orm.SqlDecl(item, StoreDateTimeAsTicks, StoreTimeSpanAsTicks);
			Execute(query);
		}
	}

	protected virtual SQLiteCommand NewCommand()
	{
		return new SQLiteCommand(this);
	}

	public SQLiteCommand CreateCommand(string cmdText, params object[] ps)
	{
		if (!_open)
		{
			throw SQLiteException.New(SQLite3.Result.Error, "Cannot create commands from unopened database");
		}
		SQLiteCommand sQLiteCommand = NewCommand();
		sQLiteCommand.CommandText = cmdText;
		foreach (object val in ps)
		{
			sQLiteCommand.Bind(val);
		}
		return sQLiteCommand;
	}

	public SQLiteCommand CreateCommand(string cmdText, Dictionary<string, object> args)
	{
		if (!_open)
		{
			throw SQLiteException.New(SQLite3.Result.Error, "Cannot create commands from unopened database");
		}
		SQLiteCommand sQLiteCommand = NewCommand();
		sQLiteCommand.CommandText = cmdText;
		foreach (KeyValuePair<string, object> arg in args)
		{
			sQLiteCommand.Bind(arg.Key, arg.Value);
		}
		return sQLiteCommand;
	}

	public int Execute(string query, params object[] args)
	{
		SQLiteCommand sQLiteCommand = CreateCommand(query, args);
		if (TimeExecution)
		{
			if (_sw == null)
			{
				_sw = new Stopwatch();
			}
			_sw.Reset();
			_sw.Start();
		}
		int result = sQLiteCommand.ExecuteNonQuery();
		if (TimeExecution)
		{
			_sw.Stop();
			_elapsedMilliseconds += _sw.ElapsedMilliseconds;
			Tracer?.Invoke($"Finished in {_sw.ElapsedMilliseconds} ms ({(double)_elapsedMilliseconds / 1000.0:0.0} s total)");
		}
		return result;
	}

	public T ExecuteScalar<T>(string query, params object[] args)
	{
		SQLiteCommand sQLiteCommand = CreateCommand(query, args);
		if (TimeExecution)
		{
			if (_sw == null)
			{
				_sw = new Stopwatch();
			}
			_sw.Reset();
			_sw.Start();
		}
		T result = sQLiteCommand.ExecuteScalar<T>();
		if (TimeExecution)
		{
			_sw.Stop();
			_elapsedMilliseconds += _sw.ElapsedMilliseconds;
			Tracer?.Invoke($"Finished in {_sw.ElapsedMilliseconds} ms ({(double)_elapsedMilliseconds / 1000.0:0.0} s total)");
		}
		return result;
	}

	public List<T> Query<T>(string query, params object[] args) where T : new()
	{
		SQLiteCommand sQLiteCommand = CreateCommand(query, args);
		return sQLiteCommand.ExecuteQuery<T>();
	}

	public List<T> QueryScalars<T>(string query, params object[] args)
	{
		SQLiteCommand sQLiteCommand = CreateCommand(query, args);
		return sQLiteCommand.ExecuteQueryScalars<T>().ToList();
	}

	public IEnumerable<T> DeferredQuery<T>(string query, params object[] args) where T : new()
	{
		SQLiteCommand sQLiteCommand = CreateCommand(query, args);
		return sQLiteCommand.ExecuteDeferredQuery<T>();
	}

	public List<object> Query(TableMapping map, string query, params object[] args)
	{
		SQLiteCommand sQLiteCommand = CreateCommand(query, args);
		return sQLiteCommand.ExecuteQuery<object>(map);
	}

	public IEnumerable<object> DeferredQuery(TableMapping map, string query, params object[] args)
	{
		SQLiteCommand sQLiteCommand = CreateCommand(query, args);
		return sQLiteCommand.ExecuteDeferredQuery<object>(map);
	}

	public TableQuery<T> Table<T>() where T : new()
	{
		return new TableQuery<T>(this);
	}

	public T Get<T>(object pk) where T : new()
	{
		TableMapping mapping = GetMapping(typeof(T));
		return Query<T>(mapping.GetByPrimaryKeySql, new object[1] { pk }).First();
	}

	public object Get(object pk, TableMapping map)
	{
		return Query(map, map.GetByPrimaryKeySql, pk).First();
	}

	public T Get<T>(Expression<Func<T, bool>> predicate) where T : new()
	{
		return Table<T>().Where(predicate).First();
	}

	public T Find<T>(object pk) where T : new()
	{
		TableMapping mapping = GetMapping(typeof(T));
		return Query<T>(mapping.GetByPrimaryKeySql, new object[1] { pk }).FirstOrDefault();
	}

	public object Find(object pk, TableMapping map)
	{
		return Query(map, map.GetByPrimaryKeySql, pk).FirstOrDefault();
	}

	public T Find<T>(Expression<Func<T, bool>> predicate) where T : new()
	{
		return Table<T>().Where(predicate).FirstOrDefault();
	}

	public T FindWithQuery<T>(string query, params object[] args) where T : new()
	{
		return Query<T>(query, args).FirstOrDefault();
	}

	public object FindWithQuery(TableMapping map, string query, params object[] args)
	{
		return Query(map, query, args).FirstOrDefault();
	}

	public void BeginTransaction()
	{
		if (Interlocked.CompareExchange(ref _transactionDepth, 1, 0) == 0)
		{
			try
			{
				Execute("begin transaction");
				return;
			}
			catch (Exception ex)
			{
				if (ex is SQLiteException ex2)
				{
					switch (ex2.Result)
					{
					case SQLite3.Result.Busy:
					case SQLite3.Result.NoMem:
					case SQLite3.Result.Interrupt:
					case SQLite3.Result.IOError:
					case SQLite3.Result.Full:
						RollbackTo(null, noThrow: true);
						break;
					}
				}
				else
				{
					Interlocked.Decrement(ref _transactionDepth);
				}
				throw;
			}
		}
		throw new InvalidOperationException("Cannot begin a transaction while already in a transaction.");
	}

	public string SaveTransactionPoint()
	{
		int num = Interlocked.Increment(ref _transactionDepth) - 1;
		string text = "S" + _rand.Next(32767) + "D" + num;
		try
		{
			Execute("savepoint " + text);
		}
		catch (Exception ex)
		{
			if (ex is SQLiteException ex2)
			{
				switch (ex2.Result)
				{
				case SQLite3.Result.Busy:
				case SQLite3.Result.NoMem:
				case SQLite3.Result.Interrupt:
				case SQLite3.Result.IOError:
				case SQLite3.Result.Full:
					RollbackTo(null, noThrow: true);
					break;
				}
			}
			else
			{
				Interlocked.Decrement(ref _transactionDepth);
			}
			throw;
		}
		return text;
	}

	public void Rollback()
	{
		RollbackTo(null, noThrow: false);
	}

	public void RollbackTo(string savepoint)
	{
		RollbackTo(savepoint, noThrow: false);
	}

	private void RollbackTo(string savepoint, bool noThrow)
	{
		try
		{
			if (string.IsNullOrEmpty(savepoint))
			{
				if (Interlocked.Exchange(ref _transactionDepth, 0) > 0)
				{
					Execute("rollback");
				}
			}
			else
			{
				DoSavePointExecute(savepoint, "rollback to ");
			}
		}
		catch (SQLiteException)
		{
			if (!noThrow)
			{
				throw;
			}
		}
	}

	public void Release(string savepoint)
	{
		try
		{
			DoSavePointExecute(savepoint, "release ");
		}
		catch (SQLiteException ex)
		{
			if (ex.Result == SQLite3.Result.Busy)
			{
				try
				{
					Execute("rollback");
				}
				catch
				{
				}
			}
			throw;
		}
	}

	private void DoSavePointExecute(string savepoint, string cmd)
	{
		int num = savepoint.IndexOf('D');
		if (num >= 2 && savepoint.Length > num + 1 && int.TryParse(savepoint.Substring(num + 1), out var result) && 0 <= result && result < _transactionDepth)
		{
			Thread.VolatileWrite(ref _transactionDepth, result);
			Execute(cmd + savepoint);
			return;
		}
		throw new ArgumentException("savePoint is not valid, and should be the result of a call to SaveTransactionPoint.", "savePoint");
	}

	public void Commit()
	{
		if (Interlocked.Exchange(ref _transactionDepth, 0) == 0)
		{
			return;
		}
		try
		{
			Execute("commit");
		}
		catch
		{
			try
			{
				Execute("rollback");
			}
			catch
			{
			}
			throw;
		}
	}

	public void RunInTransaction(Action action)
	{
		try
		{
			string savepoint = SaveTransactionPoint();
			action();
			Release(savepoint);
		}
		catch (Exception)
		{
			Rollback();
			throw;
		}
	}

	public int InsertAll(IEnumerable objects, bool runInTransaction = true)
	{
		int c = 0;
		if (runInTransaction)
		{
			RunInTransaction(delegate
			{
				foreach (object @object in objects)
				{
					c += Insert(@object);
				}
			});
		}
		else
		{
			foreach (object object2 in objects)
			{
				c += Insert(object2);
			}
		}
		return c;
	}

	public int InsertAll(IEnumerable objects, string extra, bool runInTransaction = true)
	{
		int c = 0;
		if (runInTransaction)
		{
			RunInTransaction(delegate
			{
				foreach (object @object in objects)
				{
					c += Insert(@object, extra);
				}
			});
		}
		else
		{
			foreach (object object2 in objects)
			{
				c += Insert(object2, extra);
			}
		}
		return c;
	}

	public int InsertAll(IEnumerable objects, Type objType, bool runInTransaction = true)
	{
		int c = 0;
		if (runInTransaction)
		{
			RunInTransaction(delegate
			{
				foreach (object @object in objects)
				{
					c += Insert(@object, objType);
				}
			});
		}
		else
		{
			foreach (object object2 in objects)
			{
				c += Insert(object2, objType);
			}
		}
		return c;
	}

	public int Insert(object obj)
	{
		if (obj == null)
		{
			return 0;
		}
		return Insert(obj, "", Orm.GetType(obj));
	}

	public int InsertOrReplace(object obj)
	{
		if (obj == null)
		{
			return 0;
		}
		return Insert(obj, "OR REPLACE", Orm.GetType(obj));
	}

	public int Insert(object obj, Type objType)
	{
		return Insert(obj, "", objType);
	}

	public int InsertOrReplace(object obj, Type objType)
	{
		return Insert(obj, "OR REPLACE", objType);
	}

	public int Insert(object obj, string extra)
	{
		if (obj == null)
		{
			return 0;
		}
		return Insert(obj, extra, Orm.GetType(obj));
	}

	public int Insert(object obj, string extra, Type objType)
	{
		if (obj == null || objType == null)
		{
			return 0;
		}
		TableMapping mapping = GetMapping(objType);
		if (mapping.PK != null && mapping.PK.IsAutoGuid && mapping.PK.GetValue(obj).Equals(Guid.Empty))
		{
			mapping.PK.SetValue(obj, Guid.NewGuid());
		}
		TableMapping.Column[] array = ((string.Compare(extra, "OR REPLACE", StringComparison.OrdinalIgnoreCase) == 0) ? mapping.InsertOrReplaceColumns : mapping.InsertColumns);
		object[] array2 = new object[array.Length];
		for (int i = 0; i < array2.Length; i++)
		{
			array2[i] = array[i].GetValue(obj);
		}
		PreparedSqlLiteInsertCommand insertCommand = GetInsertCommand(mapping, extra);
		int num;
		lock (insertCommand)
		{
			try
			{
				num = insertCommand.ExecuteNonQuery(array2);
			}
			catch (SQLiteException ex)
			{
				if (SQLite3.ExtendedErrCode(Handle) == SQLite3.ExtendedResult.ConstraintNotNull)
				{
					throw NotNullConstraintViolationException.New(ex.Result, ex.Message, mapping, obj);
				}
				throw;
			}
			if (mapping.HasAutoIncPK)
			{
				long id = SQLite3.LastInsertRowid(Handle);
				mapping.SetAutoIncPK(obj, id);
			}
		}
		if (num > 0)
		{
			OnTableChanged(mapping, NotifyTableChangedAction.Insert);
		}
		return num;
	}

	private PreparedSqlLiteInsertCommand GetInsertCommand(TableMapping map, string extra)
	{
		Tuple<string, string> key = Tuple.Create(map.MappedType.FullName, extra);
		PreparedSqlLiteInsertCommand value;
		lock (_insertCommandMap)
		{
			if (_insertCommandMap.TryGetValue(key, out value))
			{
				return value;
			}
		}
		value = CreateInsertCommand(map, extra);
		lock (_insertCommandMap)
		{
			if (_insertCommandMap.TryGetValue(key, out var value2))
			{
				value.Dispose();
				return value2;
			}
			_insertCommandMap.Add(key, value);
		}
		return value;
	}

	private PreparedSqlLiteInsertCommand CreateInsertCommand(TableMapping map, string extra)
	{
		TableMapping.Column[] array = map.InsertColumns;
		string commandText;
		if (array.Length == 0 && map.Columns.Length == 1 && map.Columns[0].IsAutoInc)
		{
			commandText = string.Format("insert {1} into \"{0}\" default values", map.TableName, extra);
		}
		else
		{
			if (string.Compare(extra, "OR REPLACE", StringComparison.OrdinalIgnoreCase) == 0)
			{
				array = map.InsertOrReplaceColumns;
			}
			commandText = string.Format("insert {3} into \"{0}\"({1}) values ({2})", map.TableName, string.Join(",", array.Select((TableMapping.Column c) => "\"" + c.Name + "\"").ToArray()), string.Join(",", array.Select((TableMapping.Column c) => "?").ToArray()), extra);
		}
		return new PreparedSqlLiteInsertCommand(this, commandText);
	}

	public int Update(object obj)
	{
		if (obj == null)
		{
			return 0;
		}
		return Update(obj, Orm.GetType(obj));
	}

	public int Update(object obj, Type objType)
	{
		int num = 0;
		if (obj == null || objType == null)
		{
			return 0;
		}
		TableMapping mapping = GetMapping(objType);
		TableMapping.Column pk = mapping.PK;
		if (pk == null)
		{
			throw new NotSupportedException("Cannot update " + mapping.TableName + ": it has no PK");
		}
		IEnumerable<TableMapping.Column> source = mapping.Columns.Where((TableMapping.Column p) => p != pk);
		IEnumerable<object> collection = source.Select((TableMapping.Column c) => c.GetValue(obj));
		List<object> list = new List<object>(collection);
		if (list.Count == 0)
		{
			source = mapping.Columns;
			collection = source.Select((TableMapping.Column c) => c.GetValue(obj));
			list = new List<object>(collection);
		}
		list.Add(pk.GetValue(obj));
		string query = string.Format("update \"{0}\" set {1} where \"{2}\" = ? ", mapping.TableName, string.Join(",", source.Select((TableMapping.Column c) => "\"" + c.Name + "\" = ? ").ToArray()), pk.Name);
		try
		{
			num = Execute(query, list.ToArray());
		}
		catch (SQLiteException ex)
		{
			if (ex.Result == SQLite3.Result.Constraint && SQLite3.ExtendedErrCode(Handle) == SQLite3.ExtendedResult.ConstraintNotNull)
			{
				throw NotNullConstraintViolationException.New(ex, mapping, obj);
			}
			throw;
		}
		if (num > 0)
		{
			OnTableChanged(mapping, NotifyTableChangedAction.Update);
		}
		return num;
	}

	public int UpdateAll(IEnumerable objects, bool runInTransaction = true)
	{
		int c = 0;
		if (runInTransaction)
		{
			RunInTransaction(delegate
			{
				foreach (object @object in objects)
				{
					c += Update(@object);
				}
			});
		}
		else
		{
			foreach (object object2 in objects)
			{
				c += Update(object2);
			}
		}
		return c;
	}

	public int Delete(object objectToDelete)
	{
		TableMapping mapping = GetMapping(Orm.GetType(objectToDelete));
		TableMapping.Column pK = mapping.PK;
		if (pK == null)
		{
			throw new NotSupportedException("Cannot delete " + mapping.TableName + ": it has no PK");
		}
		string query = $"delete from \"{mapping.TableName}\" where \"{pK.Name}\" = ?";
		int num = Execute(query, pK.GetValue(objectToDelete));
		if (num > 0)
		{
			OnTableChanged(mapping, NotifyTableChangedAction.Delete);
		}
		return num;
	}

	public int Delete<T>(object primaryKey)
	{
		return Delete(primaryKey, GetMapping(typeof(T)));
	}

	public int Delete(object primaryKey, TableMapping map)
	{
		TableMapping.Column pK = map.PK;
		if (pK == null)
		{
			throw new NotSupportedException("Cannot delete " + map.TableName + ": it has no PK");
		}
		string query = $"delete from \"{map.TableName}\" where \"{pK.Name}\" = ?";
		int num = Execute(query, primaryKey);
		if (num > 0)
		{
			OnTableChanged(map, NotifyTableChangedAction.Delete);
		}
		return num;
	}

	public int DeleteAll<T>()
	{
		TableMapping mapping = GetMapping(typeof(T));
		return DeleteAll(mapping);
	}

	public int DeleteAll(TableMapping map)
	{
		string query = $"delete from \"{map.TableName}\"";
		int num = Execute(query);
		if (num > 0)
		{
			OnTableChanged(map, NotifyTableChangedAction.Delete);
		}
		return num;
	}

	public void Backup(string destinationDatabasePath, string databaseName = "main")
	{
		SQLite3.Result result = SQLite3.Open(destinationDatabasePath, out var db);
		if (result != 0)
		{
			throw SQLiteException.New(result, "Failed to open destination database");
		}
		IntPtr intPtr = SQLite3.BackupInit(db, databaseName, Handle, databaseName);
		if (intPtr == NullBackupHandle)
		{
			SQLite3.Close(db);
			throw new Exception("Failed to create backup");
		}
		SQLite3.BackupStep(intPtr, -1);
		SQLite3.BackupFinish(intPtr);
		result = SQLite3.GetResult(db);
		string message = "";
		if (result != 0)
		{
			message = SQLite3.GetErrmsg(db);
		}
		SQLite3.Close(db);
		if (result != 0)
		{
			throw SQLiteException.New(result, message);
		}
	}

	~SQLiteConnection()
	{
		Dispose(disposing: false);
	}

	public void Dispose()
	{
		Dispose(disposing: true);
		GC.SuppressFinalize(this);
	}

	public void Close()
	{
		Dispose(disposing: true);
	}

	protected virtual void Dispose(bool disposing)
	{
		bool flag = LibVersionNumber >= 3007014;
		if (!_open || !(Handle != NullHandle))
		{
			return;
		}
		try
		{
			if (disposing)
			{
				lock (_insertCommandMap)
				{
					foreach (PreparedSqlLiteInsertCommand value in _insertCommandMap.Values)
					{
						value.Dispose();
					}
					_insertCommandMap.Clear();
				}
				SQLite3.Result result = (flag ? SQLite3.Close2(Handle) : SQLite3.Close(Handle));
				if (result != 0)
				{
					string errmsg = SQLite3.GetErrmsg(Handle);
					throw SQLiteException.New(result, errmsg);
				}
			}
			else
			{
				SQLite3.Result result2 = (flag ? SQLite3.Close2(Handle) : SQLite3.Close(Handle));
			}
		}
		finally
		{
			Handle = NullHandle;
			_open = false;
		}
	}

	private void OnTableChanged(TableMapping table, NotifyTableChangedAction action)
	{
		this.TableChanged?.Invoke(this, new NotifyTableChangedEventArgs(table, action));
	}
}
public class NotifyTableChangedEventArgs : EventArgs
{
	public TableMapping Table { get; private set; }

	public NotifyTableChangedAction Action { get; private set; }

	public NotifyTableChangedEventArgs(TableMapping table, NotifyTableChangedAction action)
	{
		Table = table;
		Action = action;
	}
}
public enum NotifyTableChangedAction
{
	Insert,
	Update,
	Delete
}
public class SQLiteConnectionString
{
	private const string DateTimeSqliteDefaultFormat = "yyyy'-'MM'-'dd'T'HH':'mm':'ss'.'fff";

	public string UniqueKey { get; }

	public string DatabasePath { get; }

	public bool StoreDateTimeAsTicks { get; }

	public bool StoreTimeSpanAsTicks { get; }

	public string DateTimeStringFormat { get; }

	public DateTimeStyles DateTimeStyle { get; }

	public object Key { get; }

	public SQLiteOpenFlags OpenFlags { get; }

	public Action<SQLiteConnection> PreKeyAction { get; }

	public Action<SQLiteConnection> PostKeyAction { get; }

	public string VfsName { get; }

	public SQLiteConnectionString(string databasePath, bool storeDateTimeAsTicks = true)
		: this(databasePath, SQLiteOpenFlags.ReadWrite | SQLiteOpenFlags.Create, storeDateTimeAsTicks)
	{
	}

	public SQLiteConnectionString(string databasePath, bool storeDateTimeAsTicks, object key = null, Action<SQLiteConnection> preKeyAction = null, Action<SQLiteConnection> postKeyAction = null, string vfsName = null)
		: this(databasePath, SQLiteOpenFlags.ReadWrite | SQLiteOpenFlags.Create, storeDateTimeAsTicks, key, preKeyAction, postKeyAction, vfsName)
	{
	}

	public SQLiteConnectionString(string databasePath, SQLiteOpenFlags openFlags, bool storeDateTimeAsTicks, object key = null, Action<SQLiteConnection> preKeyAction = null, Action<SQLiteConnection> postKeyAction = null, string vfsName = null, string dateTimeStringFormat = "yyyy'-'MM'-'dd'T'HH':'mm':'ss'.'fff", bool storeTimeSpanAsTicks = true)
	{
		if (key != null && !(key is byte[]) && !(key is string))
		{
			throw new ArgumentException("Encryption keys must be strings or byte arrays", "key");
		}
		UniqueKey = $"{databasePath}_{(uint)openFlags:X8}";
		StoreDateTimeAsTicks = storeDateTimeAsTicks;
		StoreTimeSpanAsTicks = storeTimeSpanAsTicks;
		DateTimeStringFormat = dateTimeStringFormat;
		DateTimeStyle = (("o".Equals(DateTimeStringFormat, StringComparison.OrdinalIgnoreCase) || "r".Equals(DateTimeStringFormat, StringComparison.OrdinalIgnoreCase)) ? DateTimeStyles.RoundtripKind : DateTimeStyles.None);
		Key = key;
		PreKeyAction = preKeyAction;
		PostKeyAction = postKeyAction;
		OpenFlags = openFlags;
		VfsName = vfsName;
		DatabasePath = databasePath;
	}
}
[AttributeUsage(AttributeTargets.Class)]
public class TableAttribute : Attribute
{
	public string Name { get; set; }

	public bool WithoutRowId { get; set; }

	public TableAttribute(string name)
	{
		Name = name;
	}
}
[AttributeUsage(AttributeTargets.Property)]
public class ColumnAttribute : Attribute
{
	public string Name { get; set; }

	public ColumnAttribute(string name)
	{
		Name = name;
	}
}
[AttributeUsage(AttributeTargets.Property)]
public class PrimaryKeyAttribute : Attribute
{
}
[AttributeUsage(AttributeTargets.Property)]
public class AutoIncrementAttribute : Attribute
{
}
[AttributeUsage(AttributeTargets.Property, AllowMultiple = true)]
public class IndexedAttribute : Attribute
{
	public string Name { get; set; }

	public int Order { get; set; }

	public virtual bool Unique { get; set; }

	public IndexedAttribute()
	{
	}

	public IndexedAttribute(string name, int order)
	{
		Name = name;
		Order = order;
	}
}
[AttributeUsage(AttributeTargets.Property)]
public class IgnoreAttribute : Attribute
{
}
[AttributeUsage(AttributeTargets.Property)]
public class UniqueAttribute : IndexedAttribute
{
	public override bool Unique
	{
		get
		{
			return true;
		}
		set
		{
		}
	}
}
[AttributeUsage(AttributeTargets.Property)]
public class MaxLengthAttribute : Attribute
{
	public int Value { get; private set; }

	public MaxLengthAttribute(int length)
	{
		Value = length;
	}
}
public sealed class PreserveAttribute : Attribute
{
	public bool AllMembers;

	public bool Conditional;
}
[AttributeUsage(AttributeTargets.Property)]
public class CollationAttribute : Attribute
{
	public string Value { get; private set; }

	public CollationAttribute(string collation)
	{
		Value = collation;
	}
}
[AttributeUsage(AttributeTargets.Property)]
public class NotNullAttribute : Attribute
{
}
[AttributeUsage(AttributeTargets.Enum)]
public class StoreAsTextAttribute : Attribute
{
}
public class TableMapping
{
	public class Column
	{
		private MemberInfo _member;

		public string Name { get; private set; }

		public PropertyInfo PropertyInfo => _member as PropertyInfo;

		public string PropertyName => _member.Name;

		public Type ColumnType { get; private set; }

		public string Collation { get; private set; }

		public bool IsAutoInc { get; private set; }

		public bool IsAutoGuid { get; private set; }

		public bool IsPK { get; private set; }

		public IEnumerable<IndexedAttribute> Indices { get; set; }

		public bool IsNullable { get; private set; }

		public int? MaxStringLength { get; private set; }

		public bool StoreAsText { get; private set; }

		public Column(MemberInfo member, CreateFlags createFlags = CreateFlags.None)
		{
			_member = member;
			Type memberType = GetMemberType(member);
			CustomAttributeData customAttributeData = member.CustomAttributes.FirstOrDefault((CustomAttributeData x) => x.AttributeType == typeof(ColumnAttribute));
			Name = ((customAttributeData == null || customAttributeData.ConstructorArguments.Count <= 0) ? member.Name : customAttributeData.ConstructorArguments[0].Value?.ToString());
			ColumnType = Nullable.GetUnderlyingType(memberType) ?? memberType;
			Collation = Orm.Collation(member);
			IsPK = Orm.IsPK(member) || ((createFlags & CreateFlags.ImplicitPK) == CreateFlags.ImplicitPK && string.Compare(member.Name, "Id", StringComparison.OrdinalIgnoreCase) == 0);
			bool flag = Orm.IsAutoInc(member) || (IsPK && (createFlags & CreateFlags.AutoIncPK) == CreateFlags.AutoIncPK);
			IsAutoGuid = flag && ColumnType == typeof(Guid);
			IsAutoInc = flag && !IsAutoGuid;
			Indices = Orm.GetIndices(member);
			if (!Indices.Any() && !IsPK && (createFlags & CreateFlags.ImplicitIndex) == CreateFlags.ImplicitIndex && Name.EndsWith("Id", StringComparison.OrdinalIgnoreCase))
			{
				Indices = new IndexedAttribute[1]
				{
					new IndexedAttribute()
				};
			}
			IsNullable = !IsPK && !Orm.IsMarkedNotNull(member);
			MaxStringLength = Orm.MaxStringLength(member);
			StoreAsText = memberType.GetTypeInfo().CustomAttributes.Any((CustomAttributeData x) => x.AttributeType == typeof(StoreAsTextAttribute));
		}

		public Column(PropertyInfo member, CreateFlags createFlags = CreateFlags.None)
			: this((MemberInfo)member, createFlags)
		{
		}

		public void SetValue(object obj, object val)
		{
			if (_member is PropertyInfo propertyInfo)
			{
				if (val != null && ColumnType.GetTypeInfo().IsEnum)
				{
					propertyInfo.SetValue(obj, Enum.ToObject(ColumnType, val));
				}
				else
				{
					propertyInfo.SetValue(obj, val);
				}
				return;
			}
			if (_member is FieldInfo fieldInfo)
			{
				if (val != null && ColumnType.GetTypeInfo().IsEnum)
				{
					fieldInfo.SetValue(obj, Enum.ToObject(ColumnType, val));
				}
				else
				{
					fieldInfo.SetValue(obj, val);
				}
				return;
			}
			throw new InvalidProgramException("unreachable condition");
		}

		public object GetValue(object obj)
		{
			if (_member is PropertyInfo propertyInfo)
			{
				return propertyInfo.GetValue(obj);
			}
			if (_member is FieldInfo fieldInfo)
			{
				return fieldInfo.GetValue(obj);
			}
			throw new InvalidProgramException("unreachable condition");
		}

		private static Type GetMemberType(MemberInfo m)
		{
			return m.MemberType switch
			{
				MemberTypes.Property => ((PropertyInfo)m).PropertyType, 
				MemberTypes.Field => ((FieldInfo)m).FieldType, 
				_ => throw new InvalidProgramException("TableMapping supports properties or fields only."), 
			};
		}
	}

	internal enum MapMethod
	{
		ByName,
		ByPosition
	}

	private readonly Column _autoPk;

	private readonly Column[] _insertColumns;

	private readonly Column[] _insertOrReplaceColumns;

	public Type MappedType { get; private set; }

	public string TableName { get; private set; }

	public bool WithoutRowId { get; private set; }

	public Column[] Columns { get; private set; }

	public Column PK { get; private set; }

	public string GetByPrimaryKeySql { get; private set; }

	public CreateFlags CreateFlags { get; private set; }

	internal MapMethod Method { get; private set; } = MapMethod.ByName;


	public bool HasAutoIncPK { get; private set; }

	public Column[] InsertColumns => _insertColumns;

	public Column[] InsertOrReplaceColumns => _insertOrReplaceColumns;

	public TableMapping(Type type, CreateFlags createFlags = CreateFlags.None)
	{
		MappedType = type;
		CreateFlags = createFlags;
		TypeInfo typeInfo = type.GetTypeInfo();
		TableAttribute tableAttribute = (from x in typeInfo.CustomAttributes
			where x.AttributeType == typeof(TableAttribute)
			select (TableAttribute)Orm.InflateAttribute(x)).FirstOrDefault();
		TableName = ((tableAttribute != null && !string.IsNullOrEmpty(tableAttribute.Name)) ? tableAttribute.Name : MappedType.Name);
		WithoutRowId = tableAttribute?.WithoutRowId ?? false;
		IReadOnlyCollection<MemberInfo> publicMembers = GetPublicMembers(type);
		List<Column> list = new List<Column>(publicMembers.Count);
		foreach (MemberInfo item in publicMembers)
		{
			if (!item.IsDefined(typeof(IgnoreAttribute), inherit: true))
			{
				list.Add(new Column(item, createFlags));
			}
		}
		Columns = list.ToArray();
		Column[] columns = Columns;
		foreach (Column column in columns)
		{
			if (column.IsAutoInc && column.IsPK)
			{
				_autoPk = column;
			}
			if (column.IsPK)
			{
				PK = column;
			}
		}
		HasAutoIncPK = _autoPk != null;
		if (PK != null)
		{
			GetByPrimaryKeySql = $"select * from \"{TableName}\" where \"{PK.Name}\" = ?";
		}
		else
		{
			GetByPrimaryKeySql = $"select * from \"{TableName}\" limit 1";
		}
		_insertColumns = Columns.Where((Column c) => !c.IsAutoInc).ToArray();
		_insertOrReplaceColumns = Columns.ToArray();
	}

	private IReadOnlyCollection<MemberInfo> GetPublicMembers(Type type)
	{
		if (type.Name.StartsWith("ValueTuple`"))
		{
			return GetFieldsFromValueTuple(type);
		}
		List<MemberInfo> list = new List<MemberInfo>();
		HashSet<string> memberNames = new HashSet<string>();
		List<MemberInfo> list2 = new List<MemberInfo>();
		do
		{
			TypeInfo typeInfo = type.GetTypeInfo();
			list2.Clear();
			list2.AddRange(typeInfo.DeclaredProperties.Where((PropertyInfo p) => !memberNames.Contains(p.Name) && p.CanRead && p.CanWrite && p.GetMethod != null && p.SetMethod != null && p.GetMethod.IsPublic && p.SetMethod.IsPublic && !p.GetMethod.IsStatic && !p.SetMethod.IsStatic));
			list.AddRange(list2);
			foreach (MemberInfo item in list2)
			{
				memberNames.Add(item.Name);
			}
			type = typeInfo.BaseType;
		}
		while (type != typeof(object));
		return list;
	}

	private IReadOnlyCollection<MemberInfo> GetFieldsFromValueTuple(Type type)
	{
		Method = MapMethod.ByPosition;
		FieldInfo[] fields = type.GetFields();
		if (fields.Length >= 8)
		{
			throw new NotSupportedException("ValueTuple with more than 7 members not supported due to nesting; see https://docs.microsoft.com/en-us/dotnet/api/system.valuetuple-8.rest");
		}
		return (IReadOnlyCollection<MemberInfo>)(object)fields;
	}

	public void SetAutoIncPK(object obj, long id)
	{
		if (_autoPk != null)
		{
			_autoPk.SetValue(obj, Convert.ChangeType(id, _autoPk.ColumnType, null));
		}
	}

	public Column FindColumnWithPropertyName(string propertyName)
	{
		return Columns.FirstOrDefault((Column c) => c.PropertyName == propertyName);
	}

	public Column FindColumn(string columnName)
	{
		if (Method != 0)
		{
			throw new InvalidOperationException(string.Format("This {0} is not mapped by name, but {1}.", "TableMapping", Method));
		}
		return Columns.FirstOrDefault((Column c) => c.Name.ToLower() == columnName.ToLower());
	}
}
internal class EnumCacheInfo
{
	public bool IsEnum { get; private set; }

	public bool StoreAsText { get; private set; }

	public Dictionary<int, string> EnumValues { get; private set; }

	public EnumCacheInfo(Type type)
	{
		TypeInfo typeInfo = type.GetTypeInfo();
		IsEnum = typeInfo.IsEnum;
		if (!IsEnum)
		{
			return;
		}
		StoreAsText = typeInfo.CustomAttributes.Any((CustomAttributeData x) => x.AttributeType == typeof(StoreAsTextAttribute));
		if (!StoreAsText)
		{
			return;
		}
		EnumValues = new Dictionary<int, string>();
		foreach (object value in Enum.GetValues(type))
		{
			EnumValues[Convert.ToInt32(value)] = value.ToString();
		}
	}
}
internal static class EnumCache
{
	private static readonly Dictionary<Type, EnumCacheInfo> Cache = new Dictionary<Type, EnumCacheInfo>();

	public static EnumCacheInfo GetInfo<T>()
	{
		return GetInfo(typeof(T));
	}

	public static EnumCacheInfo GetInfo(Type type)
	{
		lock (Cache)
		{
			EnumCacheInfo value = null;
			if (!Cache.TryGetValue(type, out value))
			{
				value = new EnumCacheInfo(type);
				Cache[type] = value;
			}
			return value;
		}
	}
}
public static class Orm
{
	public const int DefaultMaxStringLength = 140;

	public const string ImplicitPkName = "Id";

	public const string ImplicitIndexSuffix = "Id";

	public static Type GetType(object obj)
	{
		if (obj == null)
		{
			return typeof(object);
		}
		if (obj is IReflectableType reflectableType)
		{
			return reflectableType.GetTypeInfo().AsType();
		}
		return obj.GetType();
	}

	public static string SqlDecl(TableMapping.Column p, bool storeDateTimeAsTicks, bool storeTimeSpanAsTicks)
	{
		string text = "\"" + p.Name + "\" " + SqlType(p, storeDateTimeAsTicks, storeTimeSpanAsTicks) + " ";
		if (p.IsPK)
		{
			text += "primary key ";
		}
		if (p.IsAutoInc)
		{
			text += "autoincrement ";
		}
		if (!p.IsNullable)
		{
			text += "not null ";
		}
		if (!string.IsNullOrEmpty(p.Collation))
		{
			text = text + "collate " + p.Collation + " ";
		}
		return text;
	}

	public static string SqlType(TableMapping.Column p, bool storeDateTimeAsTicks, bool storeTimeSpanAsTicks)
	{
		Type columnType = p.ColumnType;
		if (columnType == typeof(bool) || columnType == typeof(byte) || columnType == typeof(ushort) || columnType == typeof(sbyte) || columnType == typeof(short) || columnType == typeof(int) || columnType == typeof(uint) || columnType == typeof(long) || columnType == typeof(ulong))
		{
			return "integer";
		}
		if (columnType == typeof(float) || columnType == typeof(double) || columnType == typeof(decimal))
		{
			return "float";
		}
		if (columnType == typeof(string) || columnType == typeof(StringBuilder) || columnType == typeof(Uri) || columnType == typeof(UriBuilder))
		{
			int? maxStringLength = p.MaxStringLength;
			if (maxStringLength.HasValue)
			{
				return "varchar(" + maxStringLength.Value + ")";
			}
			return "varchar";
		}
		if (columnType == typeof(TimeSpan))
		{
			return storeTimeSpanAsTicks ? "bigint" : "time";
		}
		if (columnType == typeof(DateTime))
		{
			return storeDateTimeAsTicks ? "bigint" : "datetime";
		}
		if (columnType == typeof(DateTimeOffset))
		{
			return "bigint";
		}
		if (columnType.GetTypeInfo().IsEnum)
		{
			if (p.StoreAsText)
			{
				return "varchar";
			}
			return "integer";
		}
		if (columnType == typeof(byte[]))
		{
			return "blob";
		}
		if (columnType == typeof(Guid))
		{
			return "varchar(36)";
		}
		throw new NotSupportedException("Don't know about " + columnType);
	}

	public static bool IsPK(MemberInfo p)
	{
		return p.CustomAttributes.Any((CustomAttributeData x) => x.AttributeType == typeof(PrimaryKeyAttribute));
	}

	public static string Collation(MemberInfo p)
	{
		return p.CustomAttributes.Where((CustomAttributeData x) => typeof(CollationAttribute) == x.AttributeType).Select(delegate(CustomAttributeData x)
		{
			IList<CustomAttributeTypedArgument> constructorArguments = x.ConstructorArguments;
			return (constructorArguments.Count > 0) ? ((constructorArguments[0].Value as string) ?? "") : "";
		}).FirstOrDefault() ?? "";
	}

	public static bool IsAutoInc(MemberInfo p)
	{
		return p.CustomAttributes.Any((CustomAttributeData x) => x.AttributeType == typeof(AutoIncrementAttribute));
	}

	public static FieldInfo GetField(TypeInfo t, string name)
	{
		FieldInfo declaredField = t.GetDeclaredField(name);
		if (declaredField != null)
		{
			return declaredField;
		}
		return GetField(t.BaseType.GetTypeInfo(), name);
	}

	public static PropertyInfo GetProperty(TypeInfo t, string name)
	{
		PropertyInfo declaredProperty = t.GetDeclaredProperty(name);
		if (declaredProperty != null)
		{
			return declaredProperty;
		}
		return GetProperty(t.BaseType.GetTypeInfo(), name);
	}

	public static object InflateAttribute(CustomAttributeData x)
	{
		Type attributeType = x.AttributeType;
		TypeInfo typeInfo = attributeType.GetTypeInfo();
		object[] args = x.ConstructorArguments.Select((CustomAttributeTypedArgument a) => a.Value).ToArray();
		object obj = Activator.CreateInstance(x.AttributeType, args);
		foreach (CustomAttributeNamedArgument namedArgument in x.NamedArguments)
		{
			if (namedArgument.IsField)
			{
				GetField(typeInfo, namedArgument.MemberName).SetValue(obj, namedArgument.TypedValue.Value);
			}
			else
			{
				GetProperty(typeInfo, namedArgument.MemberName).SetValue(obj, namedArgument.TypedValue.Value);
			}
		}
		return obj;
	}

	public static IEnumerable<IndexedAttribute> GetIndices(MemberInfo p)
	{
		TypeInfo indexedInfo = typeof(IndexedAttribute).GetTypeInfo();
		return from x in p.CustomAttributes
			where indexedInfo.IsAssignableFrom(x.AttributeType.GetTypeInfo())
			select (IndexedAttribute)InflateAttribute(x);
	}

	public static int? MaxStringLength(MemberInfo p)
	{
		CustomAttributeData customAttributeData = p.CustomAttributes.FirstOrDefault((CustomAttributeData x) => x.AttributeType == typeof(MaxLengthAttribute));
		if (customAttributeData != null)
		{
			MaxLengthAttribute maxLengthAttribute = (MaxLengthAttribute)InflateAttribute(customAttributeData);
			return maxLengthAttribute.Value;
		}
		return null;
	}

	public static int? MaxStringLength(PropertyInfo p)
	{
		return MaxStringLength((MemberInfo)p);
	}

	public static bool IsMarkedNotNull(MemberInfo p)
	{
		return p.CustomAttributes.Any((CustomAttributeData x) => x.AttributeType == typeof(NotNullAttribute));
	}
}
public class SQLiteCommand
{
	private class Binding
	{
		public string Name { get; set; }

		public object Value { get; set; }

		public int Index { get; set; }
	}

	[CompilerGenerated]
	private sealed class <ExecuteDeferredQuery>d__12<T> : IEnumerable<T>, IEnumerable, IEnumerator<T>, IDisposable, IEnumerator
	{
		private int <>1__state;

		private T <>2__current;

		private int <>l__initialThreadId;

		private TableMapping map;

		public TableMapping <>3__map;

		public SQLiteCommand <>4__this;

		private IntPtr <stmt>5__1;

		private TableMapping.Column[] <cols>5__2;

		private Action<object, IntPtr, int>[] <fastColumnSetters>5__3;

		private MethodInfo <getSetter>5__4;

		private int <i>5__5;

		private string <name>5__6;

		private object <obj>5__7;

		private int <i>5__8;

		private SQLite3.ColType <colType>5__9;

		private object <val>5__10;

		T IEnumerator<T>.Current
		{
			[DebuggerHidden]
			get
			{
				return <>2__current;
			}
		}

		object IEnumerator.Current
		{
			[DebuggerHidden]
			get
			{
				return <>2__current;
			}
		}

		[DebuggerHidden]
		public <ExecuteDeferredQuery>d__12(int <>1__state)
		{
			this.<>1__state = <>1__state;
			<>l__initialThreadId = Environment.CurrentManagedThreadId;
		}

		[DebuggerHidden]
		void IDisposable.Dispose()
		{
			int num = <>1__state;
			if (num == -3 || num == 1)
			{
				try
				{
				}
				finally
				{
					<>m__Finally1();
				}
			}
			<cols>5__2 = null;
			<fastColumnSetters>5__3 = null;
			<getSetter>5__4 = null;
			<name>5__6 = null;
			<obj>5__7 = null;
			<val>5__10 = null;
			<>1__state = -2;
		}

		private bool MoveNext()
		{
			try
			{
				switch (<>1__state)
				{
				default:
					return false;
				case 0:
					<>1__state = -1;
					if (<>4__this._conn.Trace)
					{
						<>4__this._conn.Tracer?.Invoke("Executing Query: " + <>4__this);
					}
					<stmt>5__1 = <>4__this.Prepare();
					<>1__state = -3;
					<cols>5__2 = new TableMapping.Column[SQLite3.ColumnCount(<stmt>5__1)];
					<fastColumnSetters>5__3 = new Action<object, IntPtr, int>[SQLite3.ColumnCount(<stmt>5__1)];
					if (map.Method == TableMapping.MapMethod.ByPosition)
					{
						Array.Copy(map.Columns, <cols>5__2, Math.Min(<cols>5__2.Length, map.Columns.Length));
					}
					else
					{
						if (map.Method != 0)
						{
							break;
						}
						<getSetter>5__4 = null;
						if (typeof(T) != map.MappedType)
						{
							<getSetter>5__4 = FastColumnSetter.GetFastSetterMethodInfoUnsafe(map.MappedType);
						}
						<i>5__5 = 0;
						while (<i>5__5 < <cols>5__2.Length)
						{
							<name>5__6 = SQLite3.ColumnName16(<stmt>5__1, <i>5__5);
							<cols>5__2[<i>5__5] = map.FindColumn(<name>5__6);
							if (<cols>5__2[<i>5__5] != null)
							{
								if (<getSetter>5__4 != null)
								{
									<fastColumnSetters>5__3[<i>5__5] = (Action<object, IntPtr, int>)<getSetter>5__4.Invoke(null, new object[2]
									{
										<>4__this._conn,
										<cols>5__2[<i>5__5]
									});
								}
								else
								{
									<fastColumnSetters>5__3[<i>5__5] = FastColumnSetter.GetFastSetter<T>(<>4__this._conn, <cols>5__2[<i>5__5]);
								}
							}
							<name>5__6 = null;
							<i>5__5++;
						}
						<getSetter>5__4 = null;
					}
					break;
				case 1:
					<>1__state = -3;
					<obj>5__7 = null;
					break;
				}
				if (SQLite3.Step(<stmt>5__1) == SQLite3.Result.Row)
				{
					<obj>5__7 = Activator.CreateInstance(map.MappedType);
					<i>5__8 = 0;
					while (<i>5__8 < <cols>5__2.Length)
					{
						if (<cols>5__2[<i>5__8] != null)
						{
							if (<fastColumnSetters>5__3[<i>5__8] != null)
							{
								<fastColumnSetters>5__3[<i>5__8](<obj>5__7, <stmt>5__1, <i>5__8);
							}
							else
							{
								<colType>5__9 = SQLite3.ColumnType(<stmt>5__1, <i>5__8);
								<val>5__10 = <>4__this.ReadCol(<stmt>5__1, <i>5__8, <colType>5__9, <cols>5__2[<i>5__8].ColumnType);
								<cols>5__2[<i>5__8].SetValue(<obj>5__7, <val>5__10);
								<val>5__10 = null;
							}
						}
						<i>5__8++;
					}
					<>4__this.OnInstanceCreated(<obj>5__7);
					<>2__current = (T)<obj>5__7;
					<>1__state = 1;
					return true;
				}
				<cols>5__2 = null;
				<fastColumnSetters>5__3 = null;
				<>m__Finally1();
				return false;
			}
			catch
			{
				//try-fault
				((IDisposable)this).Dispose();
				throw;
			}
		}

		bool IEnumerator.MoveNext()
		{
			//ILSpy generated this explicit interface implementation from .override directive in MoveNext
			return this.MoveNext();
		}

		private void <>m__Finally1()
		{
			<>1__state = -1;
			SQLite3.Finalize(<stmt>5__1);
		}

		[DebuggerHidden]
		void IEnumerator.Reset()
		{
			throw new NotSupportedException();
		}

		[DebuggerHidden]
		IEnumerator<T> IEnumerable<T>.GetEnumerator()
		{
			<ExecuteDeferredQuery>d__12<T> <ExecuteDeferredQuery>d__;
			if (<>1__state == -2 && <>l__initialThreadId == Environment.CurrentManagedThreadId)
			{
				<>1__state = 0;
				<ExecuteDeferredQuery>d__ = this;
			}
			else
			{
				<ExecuteDeferredQuery>d__ = new <ExecuteDeferredQuery>d__12<T>(0)
				{
					<>4__this = <>4__this
				};
			}
			<ExecuteDeferredQuery>d__.map = <>3__map;
			return <ExecuteDeferredQuery>d__;
		}

		[DebuggerHidden]
		IEnumerator IEnumerable.GetEnumerator()
		{
			return ((IEnumerable<T>)this).GetEnumerator();
		}
	}

	[CompilerGenerated]
	private sealed class <ExecuteQueryScalars>d__14<T> : IEnumerable<T>, IEnumerable, IEnumerator<T>, IDisposable, IEnumerator
	{
		private int <>1__state;

		private T <>2__current;

		private int <>l__initialThreadId;

		public SQLiteCommand <>4__this;

		private IntPtr <stmt>5__1;

		private SQLite3.ColType <colType>5__2;

		private object <val>5__3;

		T IEnumerator<T>.Current
		{
			[DebuggerHidden]
			get
			{
				return <>2__current;
			}
		}

		object IEnumerator.Current
		{
			[DebuggerHidden]
			get
			{
				return <>2__current;
			}
		}

		[DebuggerHidden]
		public <ExecuteQueryScalars>d__14(int <>1__state)
		{
			this.<>1__state = <>1__state;
			<>l__initialThreadId = Environment.CurrentManagedThreadId;
		}

		[DebuggerHidden]
		void IDisposable.Dispose()
		{
			int num = <>1__state;
			if (num == -3 || (uint)(num - 1) <= 1u)
			{
				try
				{
				}
				finally
				{
					<>m__Finally1();
				}
			}
			<val>5__3 = null;
			<>1__state = -2;
		}

		private bool MoveNext()
		{
			try
			{
				switch (<>1__state)
				{
				default:
					return false;
				case 0:
					<>1__state = -1;
					if (<>4__this._conn.Trace)
					{
						<>4__this._conn.Tracer?.Invoke("Executing Query: " + <>4__this);
					}
					<stmt>5__1 = <>4__this.Prepare();
					<>1__state = -3;
					if (SQLite3.ColumnCount(<stmt>5__1) < 1)
					{
						throw new InvalidOperationException("QueryScalars should return at least one column");
					}
					break;
				case 1:
					<>1__state = -3;
					goto IL_0154;
				case 2:
					{
						<>1__state = -3;
						goto IL_0154;
					}
					IL_0154:
					<val>5__3 = null;
					break;
				}
				if (SQLite3.Step(<stmt>5__1) == SQLite3.Result.Row)
				{
					<colType>5__2 = SQLite3.ColumnType(<stmt>5__1, 0);
					<val>5__3 = <>4__this.ReadCol(<stmt>5__1, 0, <colType>5__2, typeof(T));
					if (<val>5__3 == null)
					{
						<>2__current = default(T);
						<>1__state = 1;
						return true;
					}
					<>2__current = (T)<val>5__3;
					<>1__state = 2;
					return true;
				}
				<>m__Finally1();
				return false;
			}
			catch
			{
				//try-fault
				((IDisposable)this).Dispose();
				throw;
			}
		}

		bool IEnumerator.MoveNext()
		{
			//ILSpy generated this explicit interface implementation from .override directive in MoveNext
			return this.MoveNext();
		}

		private void <>m__Finally1()
		{
			<>1__state = -1;
			<>4__this.Finalize(<stmt>5__1);
		}

		[DebuggerHidden]
		void IEnumerator.Reset()
		{
			throw new NotSupportedException();
		}

		[DebuggerHidden]
		IEnumerator<T> IEnumerable<T>.GetEnumerator()
		{
			<ExecuteQueryScalars>d__14<T> result;
			if (<>1__state == -2 && <>l__initialThreadId == Environment.CurrentManagedThreadId)
			{
				<>1__state = 0;
				result = this;
			}
			else
			{
				result = new <ExecuteQueryScalars>d__14<T>(0)
				{
					<>4__this = <>4__this
				};
			}
			return result;
		}

		[DebuggerHidden]
		IEnumerator IEnumerable.GetEnumerator()
		{
			return ((IEnumerable<T>)this).GetEnumerator();
		}
	}

	private SQLiteConnection _conn;

	private List<Binding> _bindings;

	private static IntPtr NegativePointer = new IntPtr(-1);

	public string CommandText { get; set; }

	public SQLiteCommand(SQLiteConnection conn)
	{
		_conn = conn;
		_bindings = new List<Binding>();
		CommandText = "";
	}

	public int ExecuteNonQuery()
	{
		if (_conn.Trace)
		{
			_conn.Tracer?.Invoke("Executing: " + this);
		}
		SQLite3.Result result = SQLite3.Result.OK;
		IntPtr stmt = Prepare();
		result = SQLite3.Step(stmt);
		Finalize(stmt);
		switch (result)
		{
		case SQLite3.Result.Done:
			return SQLite3.Changes(_conn.Handle);
		case SQLite3.Result.Error:
		{
			string errmsg = SQLite3.GetErrmsg(_conn.Handle);
			throw SQLiteException.New(result, errmsg);
		}
		case SQLite3.Result.Constraint:
			if (SQLite3.ExtendedErrCode(_conn.Handle) == SQLite3.ExtendedResult.ConstraintNotNull)
			{
				throw NotNullConstraintViolationException.New(result, SQLite3.GetErrmsg(_conn.Handle));
			}
			break;
		}
		throw SQLiteException.New(result, SQLite3.GetErrmsg(_conn.Handle));
	}

	public IEnumerable<T> ExecuteDeferredQuery<T>()
	{
		return ExecuteDeferredQuery<T>(_conn.GetMapping(typeof(T)));
	}

	public List<T> ExecuteQuery<T>()
	{
		return ExecuteDeferredQuery<T>(_conn.GetMapping(typeof(T))).ToList();
	}

	public List<T> ExecuteQuery<T>(TableMapping map)
	{
		return ExecuteDeferredQuery<T>(map).ToList();
	}

	protected virtual void OnInstanceCreated(object obj)
	{
	}

	[IteratorStateMachine(typeof(<ExecuteDeferredQuery>d__12<>))]
	public IEnumerable<T> ExecuteDeferredQuery<T>(TableMapping map)
	{
		//yield-return decompiler failed: Unexpected instruction in Iterator.Dispose()
		return new <ExecuteDeferredQuery>d__12<T>(-2)
		{
			<>4__this = this,
			<>3__map = map
		};
	}

	public T ExecuteScalar<T>()
	{
		if (_conn.Trace)
		{
			_conn.Tracer?.Invoke("Executing Query: " + this);
		}
		T result = default(T);
		IntPtr stmt = Prepare();
		try
		{
			SQLite3.Result result2 = SQLite3.Step(stmt);
			switch (result2)
			{
			case SQLite3.Result.Row:
			{
				SQLite3.ColType type = SQLite3.ColumnType(stmt, 0);
				object obj = ReadCol(stmt, 0, type, typeof(T));
				if (obj != null)
				{
					result = (T)obj;
					return result;
				}
				break;
			}
			case SQLite3.Result.Done:
				break;
			default:
				throw SQLiteException.New(result2, SQLite3.GetErrmsg(_conn.Handle));
			}
		}
		finally
		{
			Finalize(stmt);
		}
		return result;
	}

	[IteratorStateMachine(typeof(<ExecuteQueryScalars>d__14<>))]
	public IEnumerable<T> ExecuteQueryScalars<T>()
	{
		//yield-return decompiler failed: Unexpected instruction in Iterator.Dispose()
		return new <ExecuteQueryScalars>d__14<T>(-2)
		{
			<>4__this = this
		};
	}

	public void Bind(string name, object val)
	{
		_bindings.Add(new Binding
		{
			Name = name,
			Value = val
		});
	}

	public void Bind(object val)
	{
		Bind(null, val);
	}

	public override string ToString()
	{
		string[] array = new string[1 + _bindings.Count];
		array[0] = CommandText;
		int num = 1;
		foreach (Binding binding in _bindings)
		{
			array[num] = $"  {num - 1}: {binding.Value}";
			num++;
		}
		return string.Join(Environment.NewLine, array);
	}

	private IntPtr Prepare()
	{
		IntPtr intPtr = SQLite3.Prepare2(_conn.Handle, CommandText);
		BindAll(intPtr);
		return intPtr;
	}

	private void Finalize(IntPtr stmt)
	{
		SQLite3.Finalize(stmt);
	}

	private void BindAll(IntPtr stmt)
	{
		int num = 1;
		foreach (Binding binding in _bindings)
		{
			if (binding.Name != null)
			{
				binding.Index = SQLite3.BindParameterIndex(stmt, binding.Name);
			}
			else
			{
				binding.Index = num++;
			}
			BindParameter(stmt, binding.Index, binding.Value, _conn.StoreDateTimeAsTicks, _conn.DateTimeStringFormat, _conn.StoreTimeSpanAsTicks);
		}
	}

	internal static void BindParameter(IntPtr stmt, int index, object value, bool storeDateTimeAsTicks, string dateTimeStringFormat, bool storeTimeSpanAsTicks)
	{
		if (value == null)
		{
			SQLite3.BindNull(stmt, index);
			return;
		}
		if (value is int)
		{
			SQLite3.BindInt(stmt, index, (int)value);
			return;
		}
		if (value is string)
		{
			SQLite3.BindText(stmt, index, (string)value, -1, NegativePointer);
			return;
		}
		if (value is byte || value is ushort || value is sbyte || value is short)
		{
			SQLite3.BindInt(stmt, index, Convert.ToInt32(value));
			return;
		}
		if (value is bool)
		{
			SQLite3.BindInt(stmt, index, ((bool)value) ? 1 : 0);
			return;
		}
		if (value is uint || value is long || value is ulong)
		{
			SQLite3.BindInt64(stmt, index, Convert.ToInt64(value));
			return;
		}
		if (value is float || value is double || value is decimal)
		{
			SQLite3.BindDouble(stmt, index, Convert.ToDouble(value));
			return;
		}
		if (value is TimeSpan)
		{
			if (storeTimeSpanAsTicks)
			{
				SQLite3.BindInt64(stmt, index, ((TimeSpan)value).Ticks);
			}
			else
			{
				SQLite3.BindText(stmt, index, ((TimeSpan)value).ToString(), -1, NegativePointer);
			}
			return;
		}
		if (value is DateTime)
		{
			if (storeDateTimeAsTicks)
			{
				SQLite3.BindInt64(stmt, index, ((DateTime)value).Ticks);
			}
			else
			{
				SQLite3.BindText(stmt, index, ((DateTime)value).ToString(dateTimeStringFormat, CultureInfo.InvariantCulture), -1, NegativePointer);
			}
			return;
		}
		if (value is DateTimeOffset)
		{
			SQLite3.BindInt64(stmt, index, ((DateTimeOffset)value).UtcTicks);
			return;
		}
		if (value is byte[])
		{
			SQLite3.BindBlob(stmt, index, (byte[])value, ((byte[])value).Length, NegativePointer);
			return;
		}
		if (value is Guid)
		{
			SQLite3.BindText(stmt, index, ((Guid)value).ToString(), 72, NegativePointer);
			return;
		}
		if (value is Uri)
		{
			SQLite3.BindText(stmt, index, ((Uri)value).ToString(), -1, NegativePointer);
			return;
		}
		if (value is StringBuilder)
		{
			SQLite3.BindText(stmt, index, ((StringBuilder)value).ToString(), -1, NegativePointer);
			return;
		}
		if (value is UriBuilder)
		{
			SQLite3.BindText(stmt, index, ((UriBuilder)value).ToString(), -1, NegativePointer);
			return;
		}
		Type type = value.GetType();
		EnumCacheInfo info = EnumCache.GetInfo(type);
		if (info.IsEnum)
		{
			int num = Convert.ToInt32(value);
			if (info.StoreAsText)
			{
				SQLite3.BindText(stmt, index, info.EnumValues[num], -1, NegativePointer);
			}
			else
			{
				SQLite3.BindInt(stmt, index, num);
			}
			return;
		}
		throw new NotSupportedException("Cannot store type: " + Orm.GetType(value));
	}

	private object ReadCol(IntPtr stmt, int index, SQLite3.ColType type, Type clrType)
	{
		if (type == SQLite3.ColType.Null)
		{
			return null;
		}
		TypeInfo typeInfo = clrType.GetTypeInfo();
		if (typeInfo.IsGenericType && typeInfo.GetGenericTypeDefinition() == typeof(Nullable<>))
		{
			clrType = typeInfo.GenericTypeArguments[0];
			typeInfo = clrType.GetTypeInfo();
		}
		if (clrType == typeof(string))
		{
			return SQLite3.ColumnString(stmt, index);
		}
		if (clrType == typeof(int))
		{
			return SQLite3.ColumnInt(stmt, index);
		}
		if (clrType == typeof(bool))
		{
			return SQLite3.ColumnInt(stmt, index) == 1;
		}
		if (clrType == typeof(double))
		{
			return SQLite3.ColumnDouble(stmt, index);
		}
		if (clrType == typeof(float))
		{
			return (float)SQLite3.ColumnDouble(stmt, index);
		}
		if (clrType == typeof(TimeSpan))
		{
			if (_conn.StoreTimeSpanAsTicks)
			{
				return new TimeSpan(SQLite3.ColumnInt64(stmt, index));
			}
			string text = SQLite3.ColumnString(stmt, index);
			if (!TimeSpan.TryParseExact(text, "c", CultureInfo.InvariantCulture, TimeSpanStyles.None, out var result))
			{
				result = TimeSpan.Parse(text);
			}
			return result;
		}
		if (clrType == typeof(DateTime))
		{
			if (_conn.StoreDateTimeAsTicks)
			{
				return new DateTime(SQLite3.ColumnInt64(stmt, index));
			}
			string s = SQLite3.ColumnString(stmt, index);
			if (!DateTime.TryParseExact(s, _conn.DateTimeStringFormat, CultureInfo.InvariantCulture, _conn.DateTimeStyle, out var result2))
			{
				result2 = DateTime.Parse(s);
			}
			return result2;
		}
		if (clrType == typeof(DateTimeOffset))
		{
			return new DateTimeOffset(SQLite3.ColumnInt64(stmt, index), TimeSpan.Zero);
		}
		if (typeInfo.IsEnum)
		{
			if (type == SQLite3.ColType.Text)
			{
				string text2 = SQLite3.ColumnString(stmt, index);
				return Enum.Parse(clrType, text2.ToString(), ignoreCase: true);
			}
			return SQLite3.ColumnInt(stmt, index);
		}
		if (clrType == typeof(long))
		{
			return SQLite3.ColumnInt64(stmt, index);
		}
		if (clrType == typeof(ulong))
		{
			return (ulong)SQLite3.ColumnInt64(stmt, index);
		}
		if (clrType == typeof(uint))
		{
			return (uint)SQLite3.ColumnInt64(stmt, index);
		}
		if (clrType == typeof(decimal))
		{
			return (decimal)SQLite3.ColumnDouble(stmt, index);
		}
		if (clrType == typeof(byte))
		{
			return (byte)SQLite3.ColumnInt(stmt, index);
		}
		if (clrType == typeof(ushort))
		{
			return (ushort)SQLite3.ColumnInt(stmt, index);
		}
		if (clrType == typeof(short))
		{
			return (short)SQLite3.ColumnInt(stmt, index);
		}
		if (clrType == typeof(sbyte))
		{
			return (sbyte)SQLite3.ColumnInt(stmt, index);
		}
		if (clrType == typeof(byte[]))
		{
			return SQLite3.ColumnByteArray(stmt, index);
		}
		if (clrType == typeof(Guid))
		{
			string g = SQLite3.ColumnString(stmt, index);
			return new Guid(g);
		}
		if (clrType == typeof(Uri))
		{
			string uriString = SQLite3.ColumnString(stmt, index);
			return new Uri(uriString);
		}
		if (clrType == typeof(StringBuilder))
		{
			string value = SQLite3.ColumnString(stmt, index);
			return new StringBuilder(value);
		}
		if (clrType == typeof(UriBuilder))
		{
			string uri = SQLite3.ColumnString(stmt, index);
			return new UriBuilder(uri);
		}
		throw new NotSupportedException("Don't know how to read " + clrType);
	}
}
internal class FastColumnSetter
{
	internal static MethodInfo GetFastSetterMethodInfoUnsafe(Type mappedTy