From d9048e9a8f3d3b90c91bd693e547a567f46d4e28 Mon Sep 17 00:00:00 2001 From: ds5678 <49847914+ds5678@users.noreply.github.com> Date: Tue, 22 Oct 2024 21:57:01 -0700 Subject: [PATCH] * Reduce allocations * Ensure correct return type * Ensure correct declaring type * Improve output in call analysis --- .../ConcreteGenericMethodAnalysisContext.cs | 15 +++++++++++++-- .../CallAnalysisProcessingLayer.cs | 8 +------- 2 files changed, 14 insertions(+), 9 deletions(-) diff --git a/Cpp2IL.Core/Model/Contexts/ConcreteGenericMethodAnalysisContext.cs b/Cpp2IL.Core/Model/Contexts/ConcreteGenericMethodAnalysisContext.cs index 48ebf466..fea4dcd4 100644 --- a/Cpp2IL.Core/Model/Contexts/ConcreteGenericMethodAnalysisContext.cs +++ b/Cpp2IL.Core/Model/Contexts/ConcreteGenericMethodAnalysisContext.cs @@ -35,20 +35,25 @@ private ConcreteGenericMethodAnalysisContext(Cpp2IlMethodRef methodRef, Assembly DeclaringAsm = declaringAssembly; BaseMethodContext = ResolveBaseMethod(methodRef, declaringAssembly.GetTypeByDefinition(methodRef.DeclaringType)!); + var genericTypeParameters = ResolveTypeArray(methodRef.TypeGenericParams, declaringAssembly); + var genericMethodParameters = ResolveTypeArray(methodRef.MethodGenericParams, declaringAssembly); + for (var i = 0; i < BaseMethodContext.Parameters.Count; i++) { var parameter = BaseMethodContext.Parameters[i]; var parameterType = parameter.ParameterTypeContext; var instantiatedType = GenericInstantiation.Instantiate( parameter.ParameterTypeContext, - ResolveTypeArray(methodRef.TypeGenericParams, declaringAssembly), - ResolveTypeArray(methodRef.MethodGenericParams, declaringAssembly)); + genericTypeParameters, + genericMethodParameters); Parameters.Add(parameterType == instantiatedType ? parameter : new InjectedParameterAnalysisContext(parameter.Name, instantiatedType, i, BaseMethodContext)); } + InjectedReturnType = GenericInstantiation.Instantiate(BaseMethodContext.ReturnTypeContext, genericTypeParameters, genericMethodParameters); + if (UnderlyingPointer != 0) rawMethodBody = AppContext.InstructionSet.GetRawBytesForMethod(this, false); } @@ -64,6 +69,9 @@ private static TypeAnalysisContext ResolveDeclaringType(Cpp2IlMethodRef methodRe var baseType = declaringAssembly.AppContext.ResolveContextForType(methodRef.DeclaringType) ?? throw new($"Unable to resolve declaring type {methodRef.DeclaringType.FullName} for generic method {methodRef}"); + if (methodRef.TypeGenericParams.Length == 0) + return baseType; + var genericParams = ResolveTypeArray(methodRef.TypeGenericParams, declaringAssembly); return new GenericInstanceTypeAnalysisContext(baseType, genericParams, declaringAssembly); @@ -71,6 +79,9 @@ private static TypeAnalysisContext ResolveDeclaringType(Cpp2IlMethodRef methodRe private static TypeAnalysisContext[] ResolveTypeArray(Il2CppTypeReflectionData[] array, AssemblyAnalysisContext declaringAssembly) { + if (array.Length == 0) + return []; + var ret = new TypeAnalysisContext[array.Length]; for (var i = 0; i < array.Length; i++) { diff --git a/Cpp2IL.Core/ProcessingLayers/CallAnalysisProcessingLayer.cs b/Cpp2IL.Core/ProcessingLayers/CallAnalysisProcessingLayer.cs index a84d8917..8f705443 100644 --- a/Cpp2IL.Core/ProcessingLayers/CallAnalysisProcessingLayer.cs +++ b/Cpp2IL.Core/ProcessingLayers/CallAnalysisProcessingLayer.cs @@ -195,10 +195,8 @@ private static void AddAttribute((InjectedMethodAnalysisContext, InjectedFieldAn var memberField = (callsAttributeInfo.Item2[1], targetMethod.Name); - var concreteMethod = targetMethod as ConcreteGenericMethodAnalysisContext; - (FieldAnalysisContext, object)? typeParametersField; - if (concreteMethod is not null) + if (targetMethod is ConcreteGenericMethodAnalysisContext concreteMethod) { if (concreteMethod.MethodRef.MethodGenericParams.Length > 0) { @@ -269,10 +267,6 @@ private static void AddAttribute((InjectedMethodAnalysisContext, InjectedFieldAn { returnType = targetMethod.InjectedReturnType; } - else if (concreteMethod is { BaseMethodContext: { Definition: not null } or { InjectedReturnType: not null } }) - { - returnType = concreteMethod.BaseMethodContext.ReturnTypeContext; - } else if (targetMethod.Definition is null) { returnType = null;