fix whitelist registration of generic type parameters
All checks were successful
Build / Compute Version (push) Successful in 6s
Build / Build Nuget package (CringeBootstrap.Abstractions) (push) Successful in 44s
Build / Build Nuget package (NuGet) (push) Successful in 46s
Build / Build Nuget package (SharedCringe) (push) Successful in 47s
Build / Build Nuget package (CringePlugins) (push) Successful in 3m2s
Build / Build Launcher (push) Successful in 6m2s

This commit is contained in:
zznty
2025-05-12 18:51:44 +07:00
parent 295ee6806e
commit 4ac3989115

View File

@@ -1,6 +1,5 @@
using System.Diagnostics; using HarmonyLib;
using System.Reflection.Emit; using Microsoft.CodeAnalysis;
using HarmonyLib;
using VRage.Scripting; using VRage.Scripting;
namespace CringeLauncher.Patches; namespace CringeLauncher.Patches;
@@ -8,18 +7,37 @@ namespace CringeLauncher.Patches;
[HarmonyPatch(typeof(MyScriptWhitelist.Batch), nameof(MyScriptWhitelist.Batch.ResolveTypeSymbol))] [HarmonyPatch(typeof(MyScriptWhitelist.Batch), nameof(MyScriptWhitelist.Batch.ResolveTypeSymbol))]
public static class WhitelistTypeResolutionPatch public static class WhitelistTypeResolutionPatch
{ {
private static IEnumerable<CodeInstruction> Transpiler(IEnumerable<CodeInstruction> instructions) [HarmonyReversePatch]
private static INamedTypeSymbol ResolveTypeSymbol(MyScriptWhitelist.Batch batch, Type type) => throw null!;
// cant be assed to write a transpiler so heres a prefix
private static bool Prefix(MyScriptWhitelist.Batch __instance, Type type, ref INamedTypeSymbol __result)
{ {
var call = CodeInstruction.CallClosure((MyWhitelistException ex) => // fast path
{ if (!type.IsGenericType || !type.IsConstructedGenericType)
Debug.WriteLine(ex); return true;
});
return instructions.Manipulator(i => i.opcode == OpCodes.Throw, __result = ResolveGenericTypeSymbol(__instance, type);
i => return false;
{ }
i.opcode = call.opcode;
i.operand = call.operand; private static INamedTypeSymbol ResolveGenericTypeSymbol(MyScriptWhitelist.Batch batch, Type type)
}); {
// if type is not generic or constructed generic, run regular lookup
if (!type.IsGenericType || !type.IsConstructedGenericType)
return ResolveTypeSymbol(batch, type);
var unconstructedSymbol = ResolveTypeSymbol(batch, type.GetGenericTypeDefinition());
var typeArguments = type.GetGenericArguments();
var typeSymbolArguments = new ITypeSymbol[typeArguments.Length];
for (var i = 0; i < typeArguments.Length; i++)
{
// recursively resolve (possibly) generic arguments
typeSymbolArguments[i] = ResolveGenericTypeSymbol(batch, typeArguments[i]);
}
return unconstructedSymbol.Construct(typeSymbolArguments);
} }
} }