From d709bf68ddac19adf35774e4db45ef417b4a2857 Mon Sep 17 00:00:00 2001 From: Westin Miller Date: Wed, 4 Oct 2017 21:40:42 -0700 Subject: [PATCH] New system for resolving binaries --- Torch.Server/Initializer.cs | 6 +--- Torch.Server/Program.cs | 9 ++++-- Torch/Torch.csproj | 1 + Torch/Utils/TorchLauncher.cs | 63 ++++++++++++++++++++++++++++++++++++ 4 files changed, 71 insertions(+), 8 deletions(-) create mode 100644 Torch/Utils/TorchLauncher.cs diff --git a/Torch.Server/Initializer.cs b/Torch.Server/Initializer.cs index e4fe99e..7da5757 100644 --- a/Torch.Server/Initializer.cs +++ b/Torch.Server/Initializer.cs @@ -26,8 +26,7 @@ namespace Torch.Server login anonymous app_update 298740 quit"; - - private TorchAssemblyResolver _resolver; + private TorchConfig _config; private TorchServer _server; private string _basePath; @@ -50,7 +49,6 @@ quit"; if (!args.Contains("-noupdate")) RunSteamCmd(); - _resolver = new TorchAssemblyResolver(Path.Combine(_basePath, "DedicatedServer64")); _config = InitConfig(); if (!_config.Parse(args)) return false; @@ -94,8 +92,6 @@ quit"; } else _server.Start(); - - _resolver?.Dispose(); } private TorchConfig InitConfig() diff --git a/Torch.Server/Program.cs b/Torch.Server/Program.cs index efcc40a..ec745b2 100644 --- a/Torch.Server/Program.cs +++ b/Torch.Server/Program.cs @@ -44,13 +44,16 @@ namespace Torch.Server var binDir = Path.Combine(workingDir, "DedicatedServer64"); Directory.SetCurrentDirectory(workingDir); + if (!TorchLauncher.IsTorchWrapped()) + { + TorchLauncher.Launch(Assembly.GetEntryAssembly().FullName,args, binDir); + return; + } + if (!Environment.UserInteractive) { using (var service = new TorchService()) - using (new TorchAssemblyResolver(binDir)) - { ServiceBase.Run(service); - } return; } diff --git a/Torch/Torch.csproj b/Torch/Torch.csproj index 9d94c77..7bd9cb9 100644 --- a/Torch/Torch.csproj +++ b/Torch/Torch.csproj @@ -215,6 +215,7 @@ + diff --git a/Torch/Utils/TorchLauncher.cs b/Torch/Utils/TorchLauncher.cs new file mode 100644 index 0000000..39bcf77 --- /dev/null +++ b/Torch/Utils/TorchLauncher.cs @@ -0,0 +1,63 @@ +using System; +using System.Collections.Generic; +using System.Diagnostics; +using System.IO; +using System.Linq; +using System.Reflection; +using System.Text; +using System.Threading.Tasks; +using Torch.API; + +namespace Torch.Utils +{ + public class TorchLauncher + { + private const string TorchKey = "TorchWrapper"; + + public static bool IsTorchWrapped() + { + return AppDomain.CurrentDomain.GetData(TorchKey) != null; + } + + public static void Launch(string entryPoint, string[] args, params string[] binaryPaths) + { + if (IsTorchWrapped()) + throw new Exception("Can't wrap torch twice"); + string exePath = Path.GetDirectoryName(Assembly.GetEntryAssembly().Location)?.ToLower().Replace('/', '\\'); + if (exePath == null) + throw new ArgumentException("Unable to determine executing assembly's path"); + var allPaths = new HashSet { exePath }; + foreach (string other in binaryPaths) + allPaths.Add(other.ToLower().Replace('/', '\\')); + + var path = new StringBuilder(allPaths.First()); + foreach (string other in binaryPaths) + { + if (path.Length > other.Length) + path.Remove(other.Length, path.Length - other.Length); + for (var i = 0; i < path.Length; i++) + if (path[i] != other[i]) + { + path.Remove(i, path.Length - i); + break; + } + } + AppDomain.CurrentDomain.AppendPrivatePath(String.Join(Path.PathSeparator.ToString(), allPaths)); + AppDomain.CurrentDomain.SetData(TorchKey, true); + AppDomain.CurrentDomain.ExecuteAssemblyByName(entryPoint, args); + return; + // this would be way better but HAVOK IS UNMANAGED :clang: + // exclude application base from probing + var setup = new AppDomainSetup + { + ApplicationBase = path.ToString(), + PrivateBinPathProbe = "", + PrivateBinPath = string.Join(";", allPaths) + }; + AppDomain domain = AppDomain.CreateDomain($"TorchDomain-{Assembly.GetEntryAssembly().GetName().Name}-{new Random().Next():X}", null, setup); + domain.SetData(TorchKey, true); + domain.ExecuteAssemblyByName(entryPoint, args); + AppDomain.Unload(domain); + } + } +}