using System;
using System.Diagnostics;
using System.IO;
using System.Runtime.InteropServices;
using System.Text;

namespace SharpQuake
{
	internal static class sys
	{
		public static bool IsWindows
		{
			get
			{
				PlatformID platform = Environment.OSVersion.Platform;
				return platform == PlatformID.Win32Windows || platform == PlatformID.Win32NT || platform == PlatformID.WinCE || platform == PlatformID.Xbox;
			}
		}

		public static void Error(string fmt, params object[] args)
		{
			throw new QuakeSystemError((args.Length != 0) ? string.Format(fmt, args) : fmt);
		}

		public static FileStream FileOpenRead(string path)
		{
			FileStream result;
			try
			{
				result = new FileStream(path, FileMode.Open, FileAccess.Read, FileShare.Read);
			}
			catch (Exception)
			{
				result = null;
			}
			return result;
		}

		public static FileStream FileOpenWrite(string path, bool allowFail = false)
		{
			try
			{
				return new FileStream(path, FileMode.Create, FileAccess.Write, FileShare.Read);
			}
			catch (Exception ex)
			{
				if (!allowFail)
				{
					sys.Error("Error opening {0}: {1}", new object[]
					{
						path,
						ex.Message
					});
					throw;
				}
			}
			return null;
		}

		public static double GetFloatTime()
		{
			if (sys._StopWatch == null)
			{
				sys._StopWatch = new Stopwatch();
				sys._StopWatch.Start();
			}
			return sys._StopWatch.Elapsed.TotalSeconds;
		}

		public static void WriteString(BinaryWriter dest, string value)
		{
			byte[] bytes = Encoding.ASCII.GetBytes(value);
			dest.Write(bytes.Length);
			dest.Write(bytes);
		}

		public static string ReadString(BinaryReader src)
		{
			int num = src.ReadInt32();
			if (num <= 0)
			{
				throw new Exception("Invalid string length: " + num.ToString());
			}
			byte[] array = new byte[num];
			src.Read(array, 0, num);
			return Encoding.ASCII.GetString(array);
		}

		public static DateTime GetFileTime(string path)
		{
			if (string.IsNullOrEmpty(path) || path.LastIndexOf('*') != -1)
			{
				return DateTime.MinValue;
			}
			DateTime result;
			try
			{
				DateTime lastWriteTimeUtc = File.GetLastWriteTimeUtc(path);
				if (lastWriteTimeUtc.Year == 1601)
				{
					result = DateTime.MinValue;
				}
				else
				{
					result = lastWriteTimeUtc.ToLocalTime();
				}
			}
			catch (IOException)
			{
				result = DateTime.MinValue;
			}
			return result;
		}

		public static T ReadStructure<T>(Stream stream)
		{
			int num = Marshal.SizeOf(typeof(T));
			byte[] array = new byte[num];
			if (stream.Read(array, 0, num) < num)
			{
				throw new IOException("Stream reading error!");
			}
			return sys.BytesToStructure<T>(array, 0);
		}

		public static T BytesToStructure<T>(byte[] src, int startIndex)
		{
			GCHandle gchandle = GCHandle.Alloc(src, GCHandleType.Pinned);
			T result;
			try
			{
				IntPtr ptr = gchandle.AddrOfPinnedObject();
				if (startIndex != 0)
				{
					long value = ptr.ToInt64() + (long)startIndex;
					ptr = new IntPtr(value);
				}
				result = (T)((object)Marshal.PtrToStructure(ptr, typeof(T)));
			}
			finally
			{
				gchandle.Free();
			}
			return result;
		}

		public static byte[] StructureToBytes<T>(ref T src)
		{
			byte[] array = new byte[Marshal.SizeOf(typeof(T))];
			GCHandle gchandle = GCHandle.Alloc(array, GCHandleType.Pinned);
			try
			{
				Marshal.StructureToPtr<T>(src, gchandle.AddrOfPinnedObject(), true);
			}
			finally
			{
				gchandle.Free();
			}
			return array;
		}

		public static void StructureToBytes<T>(ref T src, byte[] dest, int offset)
		{
			GCHandle gchandle = GCHandle.Alloc(dest, GCHandleType.Pinned);
			try
			{
				long value = gchandle.AddrOfPinnedObject().ToInt64() + (long)offset;
				Marshal.StructureToPtr<T>(src, new IntPtr(value), true);
			}
			finally
			{
				gchandle.Free();
			}
		}

		public static int Random()
		{
			return sys._Random.Next();
		}

		public static int Random(int maxValue)
		{
			return sys._Random.Next(maxValue);
		}

		public static void SendKeyEvents()
		{
			Scr.SkipUpdate = false;
			mainwindow.Instance.ProcessEvents();
		}

		public static string ConsoleInput()
		{
			return null;
		}

		public static void Quit()
		{
			if (mainwindow.Instance != null)
			{
				mainwindow.Instance.ConfirmExit = false;
				mainwindow.Instance.Exit();
				mainwindow.Instance.Dispose();
			}
		}

		private static Stopwatch _StopWatch;

		private static Random _Random = new Random();
	}
}
