C# 反射替换原本的方法,使用反射直接获取到两个methodinfo,然后调用下面代码ReplaceMethod(methodinfo1,methodinfo2)。
class class1
{
public static BindingFlags BindingFlags = BindingFlags.Static | BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public;
public static T GetControl<T>(Type type, Object typeInstance, string fieldname)
{
var fieldInfo = type.GetField(fieldname, BindingFlags);
var control = (T)fieldInfo.GetValue(typeInstance);
return control;
}
public static void SetControlValue(Type type, Object typeInstance, string fieldname, object value)
{
var fieldInfo = type.GetField(fieldname, BindingFlags);
fieldInfo.SetValue(typeInstance, value);
}
public static EventHandler GetEventHandler(Type type, Object typeInstance, string eventname)
{
var method = type.GetMethod(eventname, BindingFlags);
Delegate del = Delegate.CreateDelegate(typeof(EventHandler), typeInstance, method);
return del as EventHandler;
}
public static void InvokeMethod(Type type, Object typeInstance, string eventname, object[] paramters)
{
var method = type.GetMethod(eventname, BindingFlags);
method.Invoke(typeInstance, paramters);
}
public static void ReplaceMethod(MethodInfo methodToReplace, MethodInfo methodToInject)
{
RuntimeHelpers.PrepareMethod(methodToReplace.MethodHandle);
RuntimeHelpers.PrepareMethod(methodToInject.MethodHandle);
unsafe
{
if (IntPtr.Size == 4)
{
int* inj = (int*)methodToInject.MethodHandle.Value.ToPointer() + 2;
int* tar = (int*)methodToReplace.MethodHandle.Value.ToPointer() + 2;
#if DEBUG
Console.WriteLine("\nVersion x86 Debug\n");
byte* injInst = (byte*)*inj;
byte* tarInst = (byte*)*tar;
int* injSrc = (int*)(injInst + 1);
int* tarSrc = (int*)(tarInst + 1);
*tarSrc = (((int)injInst + 5) + *injSrc) - ((int)tarInst + 5);
#else
Console.WriteLine("\nVersion x86 Release\n");
*tar = *inj;
#endif
}
else
{
long* inj = (long*)methodToInject.MethodHandle.Value.ToPointer() + 1;
long* tar = (long*)methodToReplace.MethodHandle.Value.ToPointer() + 1;
#if DEBUG
Console.WriteLine("\nVersion x64 Debug\n");
byte* injInst = (byte*)*inj;
byte* tarInst = (byte*)*tar;
int* injSrc = (int*)(injInst + 1);
int* tarSrc = (int*)(tarInst + 1);
*tarSrc = (((int)injInst + 5) + *injSrc) - ((int)tarInst + 5);
#else
Console.WriteLine("\nVersion x64 Release\n");
*tar = *inj;
#endif
}
}
}
}