Skip to content

Commit

Permalink
[unity]Class::FromGenericParameter在debug下触发断言,疑似这api因为笔误导致的bug,通过复制过来…
Browse files Browse the repository at this point in the history
…更改的方式解决
  • Loading branch information
chexiongsheng committed Jan 16, 2025
1 parent bd464bb commit 0dc4b6d
Showing 1 changed file with 44 additions and 2 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
#include "il2cpp-api.h"
#include "il2cpp-class-internals.h"
#include "il2cpp-object-internals.h"
#include "mono-structs.h"
#include "vm/InternalCalls.h"
#include "vm/Object.h"
#include "vm/Array.h"
Expand Down Expand Up @@ -2473,6 +2474,45 @@ void DestroyJSEnvPrivate(JsEnvPrivate* jsEnvPrivate)
delete jsEnvPrivate;
}

Il2CppClass* GenericParamGetBaseType(Il2CppMetadataGenericParameterHandle gparam)
{
Il2CppClass** constraints = Class::GetOrCreateMonoGenericParameterInfo(gparam)->constraints;

Il2CppClass* base_class = il2cpp_defaults.object_class;

if (constraints)
{
for (int i = 0; constraints[i]; ++i)
{
Il2CppClass* constraint = constraints[i];

if (Class::IsInterface(constraint))
continue;

Il2CppType* constraint_type = &constraint->byval_arg;
if (constraint_type->type == IL2CPP_TYPE_VAR || constraint_type->type == IL2CPP_TYPE_MVAR)
{
Il2CppMetadataGenericParameterHandle constraint_param = constraint_type->data.genericParameterHandle;
Il2CppGenericParameterInfo constraint_info = MetadataCache::GetGenericParameterInfo(constraint_param);
if ((constraint_info.flags & IL2CPP_GENERIC_PARAMETER_ATTRIBUTE_REFERENCE_TYPE_CONSTRAINT) == 0 &&
(constraint_info.flags & IL2CPP_GENERIC_PARAMETER_ATTRIBUTE_NOT_NULLABLE_VALUE_TYPE_CONSTRAINT) == 0)
continue;
}

base_class = constraint;
}
}

if (base_class == il2cpp_defaults.object_class)
{
Il2CppGenericParameterInfo gparamInfo = MetadataCache::GetGenericParameterInfo(gparam);
if ((gparamInfo.flags & IL2CPP_GENERIC_PARAMETER_ATTRIBUTE_NOT_NULLABLE_VALUE_TYPE_CONSTRAINT) != 0)
base_class = il2cpp_defaults.value_type_class;
}

return base_class;
}

static const MethodInfo* MakeGenericMethodByConstraintedArguments(const MethodInfo* method)
{
if (!Method::IsGeneric(method) || Method::IsInflated(method))
Expand All @@ -2488,8 +2528,10 @@ static const MethodInfo* MakeGenericMethodByConstraintedArguments(const MethodIn
for (uint32_t i = 0; i < count; i++)
{
Il2CppMetadataGenericParameterHandle param = GenericContainer::GetGenericParameter(containerHandle, i);
Il2CppClass* pklass = Class::FromGenericParameter(param);
genericArguments[i] = &(Class::GenericParamGetBaseType(pklass)->byval_arg);
//Il2CppClass* pklass = Class::FromGenericParameter(param);
//genericArguments[i] = &(Class::GenericParamGetBaseType(pklass)->byval_arg); // debug 下 GenericParamGetBaseType对于IL2CPP_TYPE_MVAR,其is_generic_argument判断很奇怪:type->type == IL2CPP_TYPE_VAR || type->type == IL2CPP_TYPE_VAR,疑似笔误,从2022到6000都一样
// 拷贝Class::GenericParamGetBaseType过来修改
genericArguments[i] = &(GenericParamGetBaseType(param)->byval_arg);
}
return MetadataCache::GetGenericInstanceMethod(method, genericArguments, count);
}
Expand Down

2 comments on commit 0dc4b6d

@chexiongsheng
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

commit是笔误,应该是Class::GenericParamGetBaseType

@chexiongsheng
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

如下C#代码编译成il2cpp debug工程执行也会触发assert:

public class Test
{
    public static void G<T>(T o)
    {

    }
}

public class HelloWorlder : MonoBehaviour
{
    void Start()
    {
	 Debug.Log(typeof(Test).GetMethod("G").GetParameters()[0].ParameterType.IsSubclassOf(typeof(Object))); 
    }
}

Please sign in to comment.