Add support for plugin profiles
All checks were successful
Build / Compute Version (push) Successful in 6s
Build / Build Nuget package (NuGet) (push) Successful in 3m59s
Build / Build Nuget package (CringeBootstrap.Abstractions) (push) Successful in 4m5s
Build / Build Nuget package (SharedCringe) (push) Successful in 4m2s
Build / Build Nuget package (CringePlugins) (push) Successful in 4m20s
Build / Build Launcher (push) Successful in 5m11s
All checks were successful
Build / Compute Version (push) Successful in 6s
Build / Build Nuget package (NuGet) (push) Successful in 3m59s
Build / Build Nuget package (CringeBootstrap.Abstractions) (push) Successful in 4m5s
Build / Build Nuget package (SharedCringe) (push) Successful in 4m2s
Build / Build Nuget package (CringePlugins) (push) Successful in 4m20s
Build / Build Launcher (push) Successful in 5m11s
Some minor cleanup
This commit is contained in:
@@ -1,96 +0,0 @@
|
||||
#if false
|
||||
using System.Diagnostics;
|
||||
using System.Reflection;
|
||||
using System.Reflection.Emit;
|
||||
using System.Runtime.Loader;
|
||||
using CringeBootstrap.Abstractions;
|
||||
using CringeLauncher.Loader;
|
||||
using HarmonyLib;
|
||||
using Sandbox.Game.World;
|
||||
using VRage.Collections;
|
||||
using VRage.Scripting;
|
||||
|
||||
namespace CringeLauncher.Patches;
|
||||
|
||||
[HarmonyPatch]
|
||||
public static class ModAssemblyLoadContextPatches //todo: use ModScriptCompilerPatch
|
||||
{
|
||||
private static ModAssemblyLoadContext? _currentSessionContext;
|
||||
private static readonly MyConcurrentHashSet<string> AssemblyNames = [];
|
||||
|
||||
[HarmonyPatch(typeof(MyScriptCompiler), nameof(MyScriptCompiler.Compile), MethodType.Async)]
|
||||
[HarmonyTranspiler]
|
||||
private static IEnumerable<CodeInstruction> CompilerTranspiler(IEnumerable<CodeInstruction> instructions, MethodBase original)
|
||||
{
|
||||
var matcher = new CodeMatcher(instructions);
|
||||
|
||||
var load1Method = AccessTools.DeclaredMethod(typeof(Assembly), nameof(Assembly.Load), [typeof(byte[]), typeof(byte[])]);
|
||||
var load2Method = AccessTools.DeclaredMethod(typeof(Assembly), nameof(Assembly.Load), [typeof(byte[])]);
|
||||
|
||||
return matcher.SearchForward(i => i.Calls(load1Method))
|
||||
.InsertAndAdvance(new(OpCodes.Ldarg_0), CodeInstruction.LoadField(original.DeclaringType, "target"))
|
||||
.SetInstruction(CodeInstruction.CallClosure((byte[] assembly, byte[] symbols, MyApiTarget target) =>
|
||||
{
|
||||
//if (target is not MyApiTarget.Mod) return Assembly.Load(assembly, symbols);
|
||||
ArgumentNullException.ThrowIfNull(_currentSessionContext, "No session context");
|
||||
return _currentSessionContext.LoadFromStream(new MemoryStream(assembly), new MemoryStream(symbols));
|
||||
}))
|
||||
.Start()
|
||||
.SearchForward(i => i.Calls(load2Method))
|
||||
.InsertAndAdvance(new(OpCodes.Ldarg_0), CodeInstruction.LoadField(original.DeclaringType, "target"))
|
||||
.SetInstruction(CodeInstruction.CallClosure((byte[] assembly, MyApiTarget target) =>
|
||||
{
|
||||
//if (target is not MyApiTarget.Mod) return Assembly.Load(assembly);
|
||||
ArgumentNullException.ThrowIfNull(_currentSessionContext, "No session context");
|
||||
return _currentSessionContext.LoadFromStream(new MemoryStream(assembly));
|
||||
}))
|
||||
.Instructions();
|
||||
}
|
||||
|
||||
[HarmonyPatch(typeof(MyScriptManager), "Compile")]
|
||||
[HarmonyPrefix]
|
||||
private static bool CompilePrefix(string assemblyName)
|
||||
{
|
||||
if (!AssemblyNames.Add(assemblyName))
|
||||
{
|
||||
Debug.WriteLine($"Duplicate assembly: {assemblyName}");
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
[HarmonyPatch(typeof(MySession), nameof(MySession.Unload))]
|
||||
[HarmonyPostfix]
|
||||
private static void UnloadPostfix()
|
||||
{
|
||||
AssemblyNames.Clear();
|
||||
if (_currentSessionContext is null) return;
|
||||
|
||||
_currentSessionContext.Unload();
|
||||
_currentSessionContext = null;
|
||||
}
|
||||
|
||||
[HarmonyPatch]
|
||||
private static class LoadPrefixes
|
||||
{
|
||||
[HarmonyTargetMethods]
|
||||
private static IEnumerable<MethodInfo> TargetMethods()
|
||||
{
|
||||
yield return AccessTools.Method(typeof(MySession), nameof(MySession.Load));
|
||||
yield return AccessTools.Method(typeof(MySession), "LoadMultiplayer");
|
||||
}
|
||||
|
||||
[HarmonyPrefix]
|
||||
private static void Prefix()
|
||||
{
|
||||
if (_currentSessionContext is not null)
|
||||
throw new InvalidOperationException("Previous session context was not disposed");
|
||||
|
||||
if (AssemblyLoadContext.GetLoadContext(typeof(MySession).Assembly) is not ICoreLoadContext coreContext)
|
||||
throw new NotSupportedException("Mod loading is not supported in this context");
|
||||
|
||||
_currentSessionContext = new ModAssemblyLoadContext(coreContext);
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
@@ -10,7 +10,7 @@ internal sealed class MissingUsingRewriter : ProtoTagRewriter //use existing rew
|
||||
private readonly SemanticModel _semanticModel;
|
||||
private MissingUsingRewriter(CSharpCompilation compilation, SyntaxTree tree) : base(compilation, tree) => _semanticModel = compilation.GetSemanticModel(tree);
|
||||
|
||||
public static SyntaxTree Rewrite(CSharpCompilation compilation, SyntaxTree tree)
|
||||
public static new SyntaxTree Rewrite(CSharpCompilation compilation, SyntaxTree tree)
|
||||
{
|
||||
SyntaxNode syntaxNode = new MissingUsingRewriter(compilation, tree).Visit(tree.GetRoot());
|
||||
return tree.WithRootAndOptions(syntaxNode, tree.Options);
|
||||
|
Reference in New Issue
Block a user