private GetFieldValueDelegate CreateGetFieldValueMethod(FieldInfo field) { DynamicMethod method = ILUtil.CreateDynamicMethod(m_reflectedType, typeof(object), new Type[] { typeof(object) }); ILGenerator il = method.GetILGenerator(); LocalBuilder thisLocal = il.DeclareLocal(m_refinedType); LocalBuilder dataLocal = il.DeclareLocal(typeof(object)); il.Emit(OpCodes.Ldarg_0); ILUtil.EmitCastToReference(il, m_reflectedType); il.Emit(OpCodes.Stloc, thisLocal); ConstructorInfo ci = ReflectionUtil.GetDefaultConstructor(typeof(object)); il.Emit(OpCodes.Newobj, ci); il.Emit(OpCodes.Stloc, dataLocal); // get the value il.Emit(OpCodes.Ldloc, thisLocal); il.Emit(OpCodes.Ldfld, field); ILUtil.BoxIfNeeded(il, field.FieldType); il.Emit(OpCodes.Stloc, dataLocal); il.Emit(OpCodes.Ldloc, dataLocal); il.Emit(OpCodes.Ret); return((GetFieldValueDelegate)method.CreateDelegate(typeof(GetFieldValueDelegate))); }
private GetPropertyValueDelegate CreateGetPropertyValueMethod(PropertyInfo pi) { MethodInfo methodInfo = pi.GetGetMethod(); if (methodInfo == null) { return(null); } DynamicMethod method = ILUtil.CreateDynamicMethod(m_reflectedType, typeof(object), new Type[] { typeof(object) }); ILGenerator il = method.GetILGenerator(); LocalBuilder thisLocal = il.DeclareLocal(m_refinedType); il.Emit(OpCodes.Ldarg_0); ILUtil.EmitCastToReference(il, m_reflectedType); il.Emit(OpCodes.Stloc, thisLocal.LocalIndex); il.Emit(OpCodes.Ldloc, thisLocal); il.EmitCall(OpCodes.Callvirt, methodInfo, null); ILUtil.BoxIfNeeded(il, pi.PropertyType); il.Emit(OpCodes.Ret); return((GetPropertyValueDelegate)method.CreateDelegate(typeof(GetPropertyValueDelegate))); }
private GetFieldValuesDelegate CreateGetFieldValuesMethod(FieldInfo[] fields) { Type[] methodArguments = new Type[] { typeof(object) }; DynamicMethod method = ILUtil.CreateDynamicMethod(m_reflectedType, typeof(object[]), methodArguments); ILGenerator il = method.GetILGenerator(); LocalBuilder thisLocal = il.DeclareLocal(m_refinedType); LocalBuilder dataLocal = il.DeclareLocal(typeof(object[])); il.Emit(OpCodes.Ldarg_0); ILUtil.EmitCastToReference(il, m_reflectedType); il.Emit(OpCodes.Stloc, thisLocal); il.Emit(OpCodes.Ldc_I4, fields.Length); il.Emit(OpCodes.Newarr, typeof(object)); il.Emit(OpCodes.Stloc, dataLocal); for (int i = 0; i < fields.Length; i++) { FieldInfo field = fields[i]; il.Emit(OpCodes.Ldloc, dataLocal); il.Emit(OpCodes.Ldc_I4, i); // get the value il.Emit(OpCodes.Ldloc, thisLocal); il.Emit(OpCodes.Ldfld, field); ILUtil.BoxIfNeeded(il, field.FieldType); il.Emit(OpCodes.Stelem_Ref); } il.Emit(OpCodes.Ldloc, dataLocal.LocalIndex); il.Emit(OpCodes.Ret); return((GetFieldValuesDelegate)method.CreateDelegate(typeof(GetFieldValuesDelegate))); }
public static InvokeMethodDelegate CreateMethodInvoker(MethodInfo methodInfo) { DynamicMethod method = ILUtil.CreateDynamicMethod( methodInfo.DeclaringType, typeof(object), new Type[] { typeof(object), typeof(object[]) }); ILGenerator il = method.GetILGenerator(); ParameterInfo[] parameters = methodInfo.GetParameters(); Type[] paramTypes = new Type[parameters.Length]; for (int i = 0; i < paramTypes.Length; i++) { if (parameters[i].ParameterType.IsByRef) { paramTypes[i] = parameters[i].ParameterType.GetElementType(); } else { paramTypes[i] = parameters[i].ParameterType; } } LocalBuilder[] locals = new LocalBuilder[paramTypes.Length]; for (int i = 0; i < paramTypes.Length; i++) { locals[i] = il.DeclareLocal(paramTypes[i], true); } for (int i = 0; i < paramTypes.Length; i++) { il.Emit(OpCodes.Ldarg_1); if (i >= -1 && i <= 8) { il.Emit(ILUtil.GetOpCodeByInt(i)); } else { if (i > -129 && i < 128) { il.Emit(OpCodes.Ldc_I4_S, (SByte)i); } else { il.Emit(OpCodes.Ldc_I4, i); } } il.Emit(OpCodes.Ldelem_Ref); // ILUtil.EmitCastToReference(il, paramTypes[i]); if (paramTypes[i].IsValueType) { il.Emit(OpCodes.Unbox_Any, paramTypes[i]); } else { il.Emit(OpCodes.Castclass, paramTypes[i]); } il.Emit(OpCodes.Stloc, locals[i]); } if (!methodInfo.IsStatic) { il.Emit(OpCodes.Ldarg_0); } for (int i = 0; i < paramTypes.Length; i++) { if (parameters[i].ParameterType.IsByRef) { il.Emit(OpCodes.Ldloca_S, locals[i]); } else { il.Emit(OpCodes.Ldloc, locals[i]); } } if (methodInfo.IsStatic) { il.EmitCall(OpCodes.Call, methodInfo, null); } else { il.EmitCall(OpCodes.Callvirt, methodInfo, null); } if (methodInfo.ReturnType == typeof(void)) { il.Emit(OpCodes.Ldnull); } else { ILUtil.BoxIfNeeded(il, methodInfo.ReturnType); } for (int i = 0; i < paramTypes.Length; i++) { if (parameters[i].ParameterType.IsByRef) { il.Emit(OpCodes.Ldarg_1); if (i >= -1 && i <= 8) { il.Emit(ILUtil.GetOpCodeByInt(i)); } else { if (i > -129 && i < 128) { il.Emit(OpCodes.Ldc_I4_S, (SByte)i); } else { il.Emit(OpCodes.Ldc_I4, i); } } il.Emit(OpCodes.Ldloc, locals[i]); if (locals[i].LocalType.IsValueType) { il.Emit(OpCodes.Box, locals[i].LocalType); } il.Emit(OpCodes.Stelem_Ref); } } il.Emit(OpCodes.Ret); return((InvokeMethodDelegate)method.CreateDelegate(typeof(InvokeMethodDelegate))); }