Skip to content

Commit

Permalink
Improve unstripping support for newarr:
Browse files Browse the repository at this point in the history
* Fail for struct target types
* Use Il2CppStringArray for System.String
  • Loading branch information
ds5678 committed May 13, 2024
1 parent d145384 commit af34228
Showing 1 changed file with 53 additions and 41 deletions.
94 changes: 53 additions & 41 deletions Il2CppInterop.Generator/Utils/UnstripTranslator.cs
Original file line number Diff line number Diff line change
Expand Up @@ -41,47 +41,47 @@ public static bool TranslateMethod(MethodDefinition original, MethodDefinition t
{
if (bodyInstruction.Operand is null)
{
switch (bodyInstruction.OpCode.Code)
switch (bodyInstruction.OpCode.Code)
{
case CilCode.Ldlen:
//This is Il2CppArrayBase.Length
return false;

case CilCode.Ldelema:
//This is Il2CppArrayBase<T>.Pointer + index * sizeof(T) but the T is not known because the operand is null.
return false;

case CilCode.Ldelem:
//This is Il2CppArrayBase<T>.set_Item but the T is not known because the operand is null.
return false;

case CilCode.Stelem:
//This is Il2CppArrayBase<T>.set_Item but the T is not known because the operand is null.
return false;

case CilCode.Ldelem_Ref:
//This is Il2CppReferenceArray<T>.get_Item but the T is not known because the operand is null.
return false;

case CilCode.Stelem_Ref:
//This is Il2CppReferenceArray<T>.set_Item but the T is not known because the operand is null.
return false;

case >= CilCode.Ldelem_I1 and <= CilCode.Ldelem_R8:
//This is Il2CppStructArray<T>.get_Item
return false;

case >= CilCode.Stelem_I and <= CilCode.Stelem_R8:
//This is Il2CppStructArray<T>.set_Item
return false;

case >= CilCode.Ldind_I1 and <= CilCode.Ldind_Ref:
//This is for by ref parameters
break;

case >= CilCode.Stind_Ref and <= CilCode.Stind_R8:
//This is for by ref parameters
break;
case CilCode.Ldlen:
//This is Il2CppArrayBase.Length
return false;

case CilCode.Ldelema:
//This is Il2CppArrayBase<T>.Pointer + index * sizeof(T) but the T is not known because the operand is null.
return false;

case CilCode.Ldelem:
//This is Il2CppArrayBase<T>.set_Item but the T is not known because the operand is null.
return false;

case CilCode.Stelem:
//This is Il2CppArrayBase<T>.set_Item but the T is not known because the operand is null.
return false;

case CilCode.Ldelem_Ref:
//This is Il2CppReferenceArray<T>.get_Item but the T is not known because the operand is null.
return false;

case CilCode.Stelem_Ref:
//This is Il2CppReferenceArray<T>.set_Item but the T is not known because the operand is null.
return false;

case >= CilCode.Ldelem_I1 and <= CilCode.Ldelem_R8:
//This is Il2CppStructArray<T>.get_Item
return false;

case >= CilCode.Stelem_I and <= CilCode.Stelem_R8:
//This is Il2CppStructArray<T>.set_Item
return false;

case >= CilCode.Ldind_I1 and <= CilCode.Ldind_Ref:
//This is for by ref parameters
break;

case >= CilCode.Stind_Ref and <= CilCode.Stind_R8:
//This is for by ref parameters
break;
}

var newInstruction = targetBuilder.Add(bodyInstruction.OpCode);
Expand Down Expand Up @@ -198,7 +198,19 @@ public static bool TranslateMethod(MethodDefinition original, MethodDefinition t
{
var newInstruction = targetBuilder.Add(OpCodes.Conv_I8);

var il2cppTypeArray = imports.Il2CppReferenceArray.MakeGenericInstanceType(targetType).ToTypeDefOrRef();
ITypeDefOrRef il2cppTypeArray;
if (targetType.IsValueType)
{
return false;
}
else if (targetType.FullName == "System.String")
{
il2cppTypeArray = imports.Il2CppStringArray.ToTypeDefOrRef();
}
else
{
il2cppTypeArray = imports.Il2CppReferenceArray.MakeGenericInstanceType(targetType).ToTypeDefOrRef();
}
targetBuilder.Add(OpCodes.Newobj, imports.Module.DefaultImporter.ImportMethod(
CecilAdapter.CreateInstanceMethodReference(".ctor", imports.Module.Void(), il2cppTypeArray, imports.Module.Long())));
instructionMap.Add(bodyInstruction, newInstruction);
Expand Down

0 comments on commit af34228

Please sign in to comment.