Skip to content

Commit

Permalink
Merge branch 'BepInEx:master' into master
Browse files Browse the repository at this point in the history
  • Loading branch information
CamelCaseName authored Nov 15, 2023
2 parents af44ea4 + a342054 commit 272d5a0
Show file tree
Hide file tree
Showing 7 changed files with 138 additions and 24 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -21,21 +21,12 @@ public static void DoPass(RewriteGlobalContext context)

typeContext.NewType.Methods.Add(emptyCtor);

var local0 = new VariableDefinition(assemblyContext.Imports.Module.IntPtr());
emptyCtor.Body.Variables.Add(local0);

// NOTE(Kas): This used to stackalloc data of the valuetype's size and box it into an object
// but it seems like it caused issues on certain games. If more issues arise - revert this.
var bodyBuilder = emptyCtor.Body.GetILProcessor();
bodyBuilder.Emit(OpCodes.Ldsfld, typeContext.ClassPointerFieldRef);
bodyBuilder.Emit(OpCodes.Ldc_I4_0);
bodyBuilder.Emit(OpCodes.Conv_U);
bodyBuilder.Emit(OpCodes.Call, assemblyContext.Imports.IL2CPP_il2cpp_class_value_size.Value);
bodyBuilder.Emit(OpCodes.Conv_U);
bodyBuilder.Emit(OpCodes.Localloc);
bodyBuilder.Emit(OpCodes.Stloc_0);
bodyBuilder.Emit(OpCodes.Ldarg_0);
bodyBuilder.Emit(OpCodes.Ldsfld, typeContext.ClassPointerFieldRef);
bodyBuilder.Emit(OpCodes.Ldloc_0);
bodyBuilder.Emit(OpCodes.Call, assemblyContext.Imports.IL2CPP_il2cpp_value_box.Value);
bodyBuilder.Emit(OpCodes.Call, assemblyContext.Imports.IL2CPP_il2cpp_object_new.Value);
bodyBuilder.Emit(OpCodes.Call,
new MethodReference(".ctor", assemblyContext.Imports.Module.Void(), typeContext.NewType.BaseType)
{
Expand Down
14 changes: 7 additions & 7 deletions Il2CppInterop.Runtime/IL2CPP.cs
Original file line number Diff line number Diff line change
Expand Up @@ -474,8 +474,8 @@ public static extern bool il2cpp_class_is_subclass_of(IntPtr klass, IntPtr klass
public static extern IntPtr il2cpp_class_from_il2cpp_type(IntPtr type);

[DllImport("GameAssembly", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Ansi)]
public static extern IntPtr il2cpp_class_from_name(IntPtr image, [MarshalAs(UnmanagedType.LPStr)] string namespaze,
[MarshalAs(UnmanagedType.LPStr)] string name);
public static extern IntPtr il2cpp_class_from_name(IntPtr image, [MarshalAs(UnmanagedType.LPUTF8Str)] string namespaze,
[MarshalAs(UnmanagedType.LPUTF8Str)] string name);

[DllImport("GameAssembly", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Ansi)]
public static extern IntPtr il2cpp_class_from_system_type(IntPtr type);
Expand Down Expand Up @@ -503,7 +503,7 @@ public static extern IntPtr il2cpp_class_from_name(IntPtr image, [MarshalAs(Unma

[DllImport("GameAssembly", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Ansi)]
public static extern IntPtr il2cpp_class_get_field_from_name(IntPtr klass,
[MarshalAs(UnmanagedType.LPStr)] string name);
[MarshalAs(UnmanagedType.LPUTF8Str)] string name);

[DllImport("GameAssembly", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Ansi)]
public static extern IntPtr il2cpp_class_get_methods(IntPtr klass, ref IntPtr iter);
Expand Down Expand Up @@ -685,17 +685,17 @@ public static extern IntPtr
public static extern void il2cpp_gc_wbarrier_set_field(IntPtr obj, IntPtr targetAddress, IntPtr gcObj);

[DllImport("GameAssembly", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Ansi)]
public static extern uint il2cpp_gchandle_new(IntPtr obj, [MarshalAs(UnmanagedType.I1)] bool pinned);
public static extern nint il2cpp_gchandle_new(IntPtr obj, [MarshalAs(UnmanagedType.I1)] bool pinned);

[DllImport("GameAssembly", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Ansi)]
public static extern uint il2cpp_gchandle_new_weakref(IntPtr obj,
public static extern nint il2cpp_gchandle_new_weakref(IntPtr obj,
[MarshalAs(UnmanagedType.I1)] bool track_resurrection);

[DllImport("GameAssembly", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Ansi)]
public static extern IntPtr il2cpp_gchandle_get_target(uint gchandle);
public static extern IntPtr il2cpp_gchandle_get_target(nint gchandle);

[DllImport("GameAssembly", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Ansi)]
public static extern void il2cpp_gchandle_free(uint gchandle);
public static extern void il2cpp_gchandle_free(nint gchandle);

[DllImport("GameAssembly", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Ansi)]
public static extern IntPtr il2cpp_unity_liveness_calculation_begin(IntPtr filter, int max_object_count,
Expand Down
24 changes: 24 additions & 0 deletions Il2CppInterop.Runtime/Injection/ClassInjector.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
using Il2CppInterop.Runtime.Runtime;
using Il2CppInterop.Runtime.Runtime.VersionSpecific.Class;
using Il2CppInterop.Runtime.Runtime.VersionSpecific.MethodInfo;
using Il2CppInterop.Runtime.Runtime.VersionSpecific.Type;
using Microsoft.Extensions.Logging;
using ValueType = Il2CppSystem.ValueType;
using Void = Il2CppSystem.Void;
Expand Down Expand Up @@ -1075,9 +1076,15 @@ private static string ExtractSignature(MethodInfo monoMethod)

private static Type RewriteType(Type type)
{
if (type.IsByRef)
return RewriteType(type.GetElementType()).MakeByRefType();

if (type.IsValueType && !type.IsEnum)
return type;

if (type == typeof(string))
return type;

if (type.IsArray)
{
var elementType = type.GetElementType();
Expand Down Expand Up @@ -1142,6 +1149,23 @@ internal static Type SystemTypeFromIl2CppType(Il2CppTypeStruct* typePointer)
{
var fullName = GetIl2CppTypeFullName(typePointer);
var type = Type.GetType(fullName) ?? throw new NullReferenceException($"Couldn't find System.Type for Il2Cpp type: {fullName}");

INativeTypeStruct wrappedType = UnityVersionHandler.Wrap(typePointer);
if (wrappedType.Type == Il2CppTypeEnum.IL2CPP_TYPE_GENERICINST)
{
Il2CppGenericClass* genericClass = (Il2CppGenericClass*)wrappedType.Data;
uint argc = genericClass->context.class_inst->type_argc;
Il2CppTypeStruct** argv = genericClass->context.class_inst->type_argv;
Type[] genericArguments = new Type[argc];

for (int i = 0; i < argc; i++)
{
genericArguments[i] = SystemTypeFromIl2CppType(argv[i]);
}
type = type.MakeGenericType(genericArguments);
}
if (wrappedType.ByRef)
type = type.MakeByRefType();
return RewriteType(type);
}

Expand Down
2 changes: 1 addition & 1 deletion Il2CppInterop.Runtime/InteropTypes/Il2CppObjectBase.cs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ public class Il2CppObjectBase
internal bool isWrapped;
internal IntPtr pooledPtr;

private uint myGcHandle;
private nint myGcHandle;

public Il2CppObjectBase(IntPtr pointer)
{
Expand Down
8 changes: 4 additions & 4 deletions Il2CppInterop.Runtime/Runtime/Il2CppApi.cs
Original file line number Diff line number Diff line change
Expand Up @@ -600,22 +600,22 @@ public static void il2cpp_gc_wbarrier_set_field(IntPtr obj, IntPtr targetAddress

#region GC Handles

public static uint il2cpp_gchandle_new(IntPtr obj, bool pinned)
public static nint il2cpp_gchandle_new(IntPtr obj, bool pinned)
{
return IL2CPP.il2cpp_gchandle_new(obj, pinned);
}

public static uint il2cpp_gchandle_new_weakref(IntPtr obj, bool track_resurrection)
public static nint il2cpp_gchandle_new_weakref(IntPtr obj, bool track_resurrection)
{
return IL2CPP.il2cpp_gchandle_new_weakref(obj, track_resurrection);
}

public static IntPtr il2cpp_gchandle_get_target(uint gchandle)
public static IntPtr il2cpp_gchandle_get_target(nint gchandle)
{
return IL2CPP.il2cpp_gchandle_get_target(gchandle);
}

public static void il2cpp_gchandle_free(uint gchandle)
public static void il2cpp_gchandle_free(nint gchandle)
{
IL2CPP.il2cpp_gchandle_free(gchandle);
}
Expand Down
8 changes: 8 additions & 0 deletions Il2CppInterop.Runtime/Runtime/Il2CppStructs.cs
Original file line number Diff line number Diff line change
Expand Up @@ -277,6 +277,14 @@ public unsafe struct Il2CppGenericContext
public Il2CppGenericInst* method_inst;
}

[StructLayout(LayoutKind.Sequential)]
public unsafe struct Il2CppGenericClass
{
public int typeDefinitionIndex;
public Il2CppGenericContext context;
public Il2CppClass* cached_class;
}

[StructLayout(LayoutKind.Sequential)]
public unsafe struct Il2CppGenericMethod
{
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
using System;
using System.Runtime.InteropServices;
namespace Il2CppInterop.Runtime.Runtime.VersionSpecific.MethodInfo
{
[ApplicableToUnityVersionsSince("2023.2.0")]
public unsafe class NativeMethodInfoStructHandler_29_2 : INativeMethodInfoStructHandler
{
public int Size() => sizeof(Il2CppMethodInfo_29_2);
public INativeMethodInfoStruct CreateNewStruct()
{
IntPtr ptr = Marshal.AllocHGlobal(Size());
Il2CppMethodInfo_29_2* _ = (Il2CppMethodInfo_29_2*)ptr;
*_ = default;
return new NativeStructWrapper(ptr);
}
public INativeMethodInfoStruct Wrap(Il2CppMethodInfo* ptr)
{
if (ptr == null) return null;
return new NativeStructWrapper((IntPtr)ptr);
}
internal unsafe struct Il2CppMethodInfo_29_2
{
public void* methodPointer;
public void* virtualMethodPointer;
public void* invoker_method;
public byte* name;
public Il2CppClass* klass;
public Il2CppTypeStruct* return_type;
public Il2CppTypeStruct** parameters;
public void* runtime_data;
public void* generic_data;
public uint token;
public ushort flags;
public ushort iflags;
public ushort slot;
public byte parameters_count;
public Bitfield0 _bitfield0;
internal enum Bitfield0 : byte
{
BIT_is_generic = 0,
is_generic = (1 << BIT_is_generic),
BIT_is_inflated = 1,
is_inflated = (1 << BIT_is_inflated),
BIT_wrapper_type = 2,
wrapper_type = (1 << BIT_wrapper_type),
BIT_has_full_generic_sharing_signature = 3,
has_full_generic_sharing_signature = (1 << BIT_has_full_generic_sharing_signature),
BIT_is_unmanaged_callers_only = 4,
is_unmanaged_callers_only = (1 << BIT_is_unmanaged_callers_only),
}

}

internal class NativeStructWrapper : INativeMethodInfoStruct
{
public NativeStructWrapper(IntPtr ptr) => Pointer = ptr;
private static int _bitfield0offset = Marshal.OffsetOf<Il2CppMethodInfo_29_2>(nameof(Il2CppMethodInfo_29_2._bitfield0)).ToInt32();
public IntPtr Pointer { get; }
private Il2CppMethodInfo_29_2* _ => (Il2CppMethodInfo_29_2*)Pointer;
public Il2CppMethodInfo* MethodInfoPointer => (Il2CppMethodInfo*)Pointer;
public ref IntPtr Name => ref *(IntPtr*)&_->name;
public ref ushort Slot => ref _->slot;
public ref IntPtr MethodPointer => ref *(IntPtr*)&_->methodPointer;
public ref IntPtr VirtualMethodPointer => ref *(IntPtr*)&_->virtualMethodPointer;
public ref Il2CppClass* Class => ref _->klass;
public ref IntPtr InvokerMethod => ref *(IntPtr*)&_->invoker_method;
public ref Il2CppTypeStruct* ReturnType => ref _->return_type;
public ref Il2CppMethodFlags Flags => ref *(Il2CppMethodFlags*)&_->flags;
public ref byte ParametersCount => ref _->parameters_count;
public ref Il2CppParameterInfo* Parameters => ref *(Il2CppParameterInfo**)&_->parameters;
public ref uint Token => ref _->token;
public bool IsGeneric
{
get => this.CheckBit(_bitfield0offset, (int)Il2CppMethodInfo_29_2.Bitfield0.BIT_is_generic);
set => this.SetBit(_bitfield0offset, (int)Il2CppMethodInfo_29_2.Bitfield0.BIT_is_generic, value);
}
public bool IsInflated
{
get => this.CheckBit(_bitfield0offset, (int)Il2CppMethodInfo_29_2.Bitfield0.BIT_is_inflated);
set => this.SetBit(_bitfield0offset, (int)Il2CppMethodInfo_29_2.Bitfield0.BIT_is_inflated, value);
}
public bool IsMarshalledFromNative
{
get => false;
set { }
}
}

}

}

0 comments on commit 272d5a0

Please sign in to comment.