internal static void InvokeSetIndexCallSite(object target, object[] indexesThenValue, string[] tArgNames, Type tContext, bool tStaticContext, ref CallSite tCallSite) { LazyBinder tBinder = null; Type tBinderType = null; if (tCallSite == null) { tBinder = () => { var tList = GetBindingArgumentList(indexesThenValue, tArgNames, tStaticContext); return(Binder.SetIndex(CSharpBinderFlags.None, tContext, tList)); }; tBinderType = typeof(SetIndexBinder); } InvokeMemberAction(ref tCallSite, tBinderType, tBinder, Invocation.IndexBinderName, tStaticContext, tContext, tArgNames, target, indexesThenValue); }
internal static void InvokeSetIndexCallSite(object target, object[] indexesThenValue, string[] argumentNames, Type context, bool staticContext, ref CallSite callSite) { LazyBinder binder = null; Type binderType = null; if (callSite == null) { binder = () => { var bindingArgumentList = GetBindingArgumentList(indexesThenValue, argumentNames, staticContext); return(Binder.SetIndex(CSharpBinderFlags.None, context, bindingArgumentList)); }; binderType = typeof(SetIndexBinder); } MemberActionInvoke(ref callSite, binderType, binder, Invocation.IndexBinderName, staticContext, context, argumentNames, target, indexesThenValue); }
private static Action <IInvocation> CompileInvoker(MethodInfo method) { var methodParameters = method.GetParameters(); var invocationParameter = Expression.Parameter(typeof(IInvocation), "invocation"); var targetAndArgumentInfos = Pack( CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null), methodParameters.Select( mp => CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.NamedArgument, mp.Name))).ToArray(); var targetAndArguments = Pack <Expression>( Expression.Property(invocationParameter, invocationParameter.Type, "InvocationTarget"), methodParameters.Select( (mp, index) => Expression.Convert( Expression.ArrayIndex( Expression.Property(invocationParameter, invocationParameter.Type, "Arguments"), Expression.Constant(index)), mp.ParameterType))).ToArray(); Expression body = null; if (method.IsSpecialName) { if (method.Name.Equals("get_Item")) { body = Expression.Dynamic( Binder.GetIndex( CSharpBinderFlags.InvokeSpecialName, typeof(object), targetAndArgumentInfos), typeof(object), targetAndArguments); } if (body == null && method.Name.Equals("set_Item")) { var targetAndArgumentInfosWithoutTheNameValue = Pack( CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null), methodParameters.Select( mp => mp.Name == "value" ? CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null) : CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.NamedArgument, mp.Name))); body = Expression.Dynamic( Binder.SetIndex( CSharpBinderFlags.InvokeSpecialName, typeof(object), targetAndArgumentInfosWithoutTheNameValue), typeof(object), targetAndArguments); } if (body == null && method.Name.StartsWith("get_")) { // Build lambda containing the following call site: // (IInvocation invocation) => { // invocation.ReturnValue = (object) ((dynamic)invocation.InvocationTarget).{method.Name}; // } body = Expression.Dynamic( Binder.GetMember( CSharpBinderFlags.InvokeSpecialName, method.Name.Substring("get_".Length), typeof(object), targetAndArgumentInfos), typeof(object), targetAndArguments); } if (body == null && method.Name.StartsWith("set_")) { body = Expression.Dynamic( Binder.SetMember( CSharpBinderFlags.InvokeSpecialName, method.Name.Substring("set_".Length), typeof(object), targetAndArgumentInfos), typeof(object), targetAndArguments); } } if (body == null) { // Build lambda containing the following call site: // (IInvocation invocation) => { // invocation.ReturnValue = (object) ((dynamic)invocation.InvocationTarget).{method.Name}( // {methodParameters[*].Name}: ({methodParameters[*].Type})invocation.Arguments[*], // ...); // } body = Expression.Dynamic( Binder.InvokeMember( CSharpBinderFlags.None, method.Name, null, typeof(object), targetAndArgumentInfos), typeof(object), targetAndArguments); } if (method.ReturnType != typeof(void)) { body = Expression.Assign( Expression.Property(invocationParameter, invocationParameter.Type, "ReturnValue"), Expression.Convert(body, typeof(object))); } var lambda = Expression.Lambda <Action <IInvocation> >(body, invocationParameter); return(lambda.Compile()); }