Convert ParameterLoadInfo to a readonly struct

This commit is contained in:
YoshiRulz 2021-03-26 14:44:31 +10:00
parent d43d8fc38c
commit 23d8417ca8
No known key found for this signature in database
GPG Key ID: C4DE31C245353FB7
1 changed files with 34 additions and 39 deletions

View File

@ -307,17 +307,24 @@ namespace BizHawk.BizInvoke
}; };
} }
private class ParameterLoadInfo private readonly struct ParameterLoadInfo
{ {
/// <summary> /// <summary>
/// The native type for this parameter, to pass to calli /// The native type for this parameter, to pass to calli
/// </summary> /// </summary>
public Type NativeType; public readonly Type NativeType;
/// <summary> /// <summary>
/// Closure that will actually emit the parameter load to the il stream. The evaluation stack will /// Closure that will actually emit the parameter load to the il stream. The evaluation stack will
/// already have other parameters on it at this time. /// already have other parameters on it at this time.
/// </summary> /// </summary>
public Action EmitLoad; public readonly Action EmitLoad;
public ParameterLoadInfo(Type nativeType, Action emitLoad)
{
NativeType = nativeType;
EmitLoad = emitLoad;
}
} }
/// <summary> /// <summary>
@ -475,18 +482,16 @@ namespace BizHawk.BizInvoke
{ {
throw new NotImplementedException("Only refs of primitive or enum types are supported!"); throw new NotImplementedException("Only refs of primitive or enum types are supported!");
} }
return new ParameterLoadInfo return new(
{ typeof(IntPtr),
NativeType = typeof(IntPtr), () =>
EmitLoad = () =>
{ {
var loc = il.DeclareLocal(type, true); var loc = il.DeclareLocal(type, true);
il.Emit(OpCodes.Ldarg, (short)idx); il.Emit(OpCodes.Ldarg, (short)idx);
il.Emit(OpCodes.Dup); il.Emit(OpCodes.Dup);
il.Emit(OpCodes.Stloc, loc); il.Emit(OpCodes.Stloc, loc);
il.Emit(OpCodes.Conv_I); il.Emit(OpCodes.Conv_I);
} });
};
} }
if (type.IsArray) if (type.IsArray)
@ -508,10 +513,9 @@ namespace BizHawk.BizInvoke
throw new NotImplementedException("Only 0-based 1-dimensional arrays are supported!"); throw new NotImplementedException("Only 0-based 1-dimensional arrays are supported!");
} }
return new ParameterLoadInfo return new(
{ typeof(IntPtr),
NativeType = typeof(IntPtr), () =>
EmitLoad = () =>
{ {
var loc = il.DeclareLocal(type, true); var loc = il.DeclareLocal(type, true);
var end = il.DefineLabel(); var end = il.DefineLabel();
@ -531,17 +535,15 @@ namespace BizHawk.BizInvoke
il.MarkLabel(isNull); il.MarkLabel(isNull);
LoadConstant(il, IntPtr.Zero); LoadConstant(il, IntPtr.Zero);
il.MarkLabel(end); il.MarkLabel(end);
} });
};
} }
if (typeof(Delegate).IsAssignableFrom(type)) if (typeof(Delegate).IsAssignableFrom(type))
{ {
// callback -- use the same callingconventionadapter on it that the invoker is being made from // callback -- use the same callingconventionadapter on it that the invoker is being made from
return new ParameterLoadInfo return new(
{ typeof(IntPtr),
NativeType = typeof(IntPtr), () =>
EmitLoad = () =>
{ {
var mi = typeof(ICallingConventionAdapter).GetMethod("GetFunctionPointerForDelegate"); var mi = typeof(ICallingConventionAdapter).GetMethod("GetFunctionPointerForDelegate");
var end = il.DefineLabel(); var end = il.DefineLabel();
@ -559,8 +561,7 @@ namespace BizHawk.BizInvoke
il.MarkLabel(isNull); il.MarkLabel(isNull);
LoadConstant(il, IntPtr.Zero); LoadConstant(il, IntPtr.Zero);
il.MarkLabel(end); il.MarkLabel(end);
} });
};
} }
if (type == typeof(string)) if (type == typeof(string))
@ -621,23 +622,20 @@ namespace BizHawk.BizInvoke
il.Emit(OpCodes.Stloc, bytes); il.Emit(OpCodes.Stloc, bytes);
il.MarkLabel(end); il.MarkLabel(end);
return new ParameterLoadInfo return new(
{ typeof(IntPtr),
NativeType = typeof(IntPtr), () =>
EmitLoad = () =>
{ {
il.Emit(OpCodes.Ldloc, bytes); il.Emit(OpCodes.Ldloc, bytes);
} });
};
} }
if (type.IsClass) if (type.IsClass)
{ {
// non ref of class can just be passed as pointer // non ref of class can just be passed as pointer
return new ParameterLoadInfo return new(
{ typeof(IntPtr),
NativeType = typeof(IntPtr), () =>
EmitLoad = () =>
{ {
var loc = il.DeclareLocal(type, true); var loc = il.DeclareLocal(type, true);
var end = il.DefineLabel(); var end = il.DefineLabel();
@ -659,20 +657,17 @@ namespace BizHawk.BizInvoke
il.MarkLabel(isNull); il.MarkLabel(isNull);
LoadConstant(il, IntPtr.Zero); LoadConstant(il, IntPtr.Zero);
il.MarkLabel(end); il.MarkLabel(end);
} });
};
} }
if (type.IsPrimitive || type.IsEnum || type.IsPointer) if (type.IsPrimitive || type.IsEnum || type.IsPointer)
{ {
return new ParameterLoadInfo return new(
{ type,
NativeType = type, () =>
EmitLoad = () =>
{ {
il.Emit(OpCodes.Ldarg, (short)idx); il.Emit(OpCodes.Ldarg, (short)idx);
} });
};
} }
throw new NotImplementedException("Unrecognized parameter type!"); throw new NotImplementedException("Unrecognized parameter type!");