protected internal override Delegate CreateDelegate() { MemberInfo member = CallInfo.MemberInfo; if (member == null) { member = LookupUtils.GetMember(CallInfo); CallInfo.IsStatic = member.IsStatic(); } bool handleInnerStruct = CallInfo.ShouldHandleInnerStruct; if (handleInnerStruct) { Generator.ldarg_0 // load arg-0 (this) .DeclareLocal(CallInfo.TargetType); // TargetType tmpStr LoadInnerStructToLocal(0); // tmpStr = ((ValueTypeHolder)this)).Value Generator.DeclareLocal(Constants.ObjectType); // object result; } else if (!CallInfo.IsStatic) { Generator.ldarg_0 // load arg-0 (this) .castclass(CallInfo.TargetType); // (TargetType)this } if (member.MemberType == MemberTypes.Field) { var field = member as FieldInfo; if (field.DeclaringType.IsEnum) // special enum handling as ldsfld does not support enums { Generator.ldc_i4((int)field.GetValue(field.DeclaringType)) .boxIfValueType(field.FieldType); } else { Generator.ldfld(field.IsStatic, field) // (this|tmpStr).field OR TargetType.field .boxIfValueType(field.FieldType); // (object)<stack> } } else { var prop = member as PropertyInfo; MethodInfo getMethod = LookupUtils.GetPropertyGetMethod(prop, CallInfo); Generator.call(getMethod.IsStatic || CallInfo.IsTargetTypeStruct, getMethod) // (this|tmpStr).prop OR TargetType.prop .boxIfValueType(prop.PropertyType); // (object)<stack> } if (handleInnerStruct) { Generator.stloc_1.end(); // resultLocal = <stack> StoreLocalToInnerStruct(0); // ((ValueTypeHolder)this)).Value = tmpStr Generator.ldloc_1.end(); // push resultLocal } Generator.ret(); return(Method.CreateDelegate(typeof(MemberGetter))); }
protected internal override Delegate CreateDelegate() { MemberInfo member = CallInfo.MemberInfo; if (member == null) { member = LookupUtils.GetMember(CallInfo); CallInfo.IsStatic = member.IsStatic(); } bool handleInnerStruct = CallInfo.ShouldHandleInnerStruct; if (CallInfo.IsStatic) { Generator.ldarg_1.end(); // load value-to-be-set } else { Generator.ldarg_0.end(); // load arg-0 (this) if (handleInnerStruct) { Generator.DeclareLocal(CallInfo.TargetType); // TargetType tmpStr LoadInnerStructToLocal(0); // tmpStr = ((ValueTypeHolder)this)).Value; Generator.ldarg_1.end(); // load value-to-be-set; } else { Generator.castclass(CallInfo.TargetType) // (TargetType)this .ldarg_1.end(); // load value-to-be-set; } } Generator.CastFromObject(member.Type()); // unbox | cast value-to-be-set if (member.MemberType == MemberTypes.Field) { var field = member as FieldInfo; Generator.stfld(field.IsStatic, field); // (this|tmpStr).field = value-to-be-set; } else { var prop = member as PropertyInfo; MethodInfo setMethod = LookupUtils.GetPropertySetMethod(prop, CallInfo); Generator.call(setMethod.IsStatic || CallInfo.IsTargetTypeStruct, setMethod); // (this|tmpStr).set_Prop(value-to-be-set); } if (handleInnerStruct) { StoreLocalToInnerStruct(0); // ((ValueTypeHolder)this)).Value = tmpStr } Generator.ret(); return(Method.CreateDelegate(typeof(MemberSetter))); }