示例#1
0
        private DynamicMetaObject MakeMetaMethodCall(CallSignature signature, OverloadResolverFactory resolverFactory, TargetInfo targetInfo) {
            BindingRestrictions restrictions = BindingRestrictions.Combine(targetInfo.Arguments).Merge(targetInfo.Restrictions);
            if (targetInfo.Instance != null) {
                restrictions = targetInfo.Instance.Restrictions.Merge(restrictions);
            }

            DynamicMetaObject[] args;
            CallTypes callType;
            if (targetInfo.Instance != null) {
                args = ArrayUtils.Insert(targetInfo.Instance, targetInfo.Arguments);
                callType = CallTypes.ImplicitInstance;
            } else {
                args = targetInfo.Arguments;
                callType = CallTypes.None;
            }

            return CallMethod(resolverFactory.CreateOverloadResolver(args, signature, callType), targetInfo.Targets, restrictions);
        }
        private DynamicMetaObject TryMakeInvertedBindingTarget(OverloadResolverFactory resolverFactory, MethodBase[] targets, DynamicMetaObject[] args) {
            var resolver = resolverFactory.CreateOverloadResolver(args, new CallSignature(args.Length), CallTypes.None);
            BindingTarget target = resolver.ResolveOverload(targets[0].Name, targets, NarrowingLevel.None, NarrowingLevel.All);
            if (target.Success) {
                return new DynamicMetaObject(
                    Ast.Not(target.MakeExpression()),
                    target.RestrictedArguments.GetAllRestrictions()
                );
            }

            return null;
        }
        private DynamicMetaObject MakeMethodIndexRule(IndexType oper, OverloadResolverFactory resolverFactory, DynamicMetaObject[] args) {
            MethodInfo[] defaults = GetMethodsFromDefaults(args[0].GetLimitType().GetDefaultMembers(), oper);
            if (defaults.Length != 0) {
                DynamicMetaObject[] selfWithArgs = args;
                ParameterExpression arg2 = null;

                if (oper == IndexType.Set) {
                    Debug.Assert(args.Length >= 2);

                    // need to save arg2 in a temp because it's also our result
                    arg2 = Ast.Variable(args[2].Expression.Type, "arg2Temp");

                    args[2] = new DynamicMetaObject(
                        Ast.Assign(arg2, args[2].Expression),
                        args[2].Restrictions
                    );
                }

                BindingRestrictions restrictions = BindingRestrictions.Combine(args);

                var resolver = resolverFactory.CreateOverloadResolver(selfWithArgs, new CallSignature(selfWithArgs.Length), CallTypes.ImplicitInstance);
                BindingTarget target = resolver.ResolveOverload(oper == IndexType.Get ? "get_Item" : "set_Item", defaults, NarrowingLevel.None, NarrowingLevel.All);
                if (target.Success) {
                    if (oper == IndexType.Get) {
                        return new DynamicMetaObject(
                            target.MakeExpression(),
                            restrictions.Merge(target.RestrictedArguments.GetAllRestrictions())
                        );
                    } else {
                        return new DynamicMetaObject(
                            Ast.Block(
                                new ParameterExpression[] { arg2 },
                                target.MakeExpression(),
                                arg2
                            ),
                            restrictions.Merge(target.RestrictedArguments.GetAllRestrictions())
                        );
                    }
                }

                return MakeError(
                    resolver.MakeInvalidParametersError(target),
                    restrictions,
                    typeof(object)
                );
            }

            return null;
        }
        private DynamicMetaObject TryNumericComparison(OperatorInfo info, OverloadResolverFactory resolverFactory, DynamicMetaObject[] args) {
            MethodInfo[] targets = FilterNonMethods(
                args[0].GetLimitType(),
                GetMember(
                    MemberRequestKind.Operation,
                    args[0].GetLimitType(),
                    "Compare"
                )
            );

            if (targets.Length > 0) {
                var resolver = resolverFactory.CreateOverloadResolver(args, new CallSignature(args.Length), CallTypes.None);
                BindingTarget target = resolver.ResolveOverload(targets[0].Name, targets, NarrowingLevel.None, NarrowingLevel.All);
                if (target.Success) {
                    Expression call = AstUtils.Convert(target.MakeExpression(), typeof(int));
                    switch (info.Operator) {
                        case ExpressionType.GreaterThan: call = Ast.GreaterThan(call, AstUtils.Constant(0)); break;
                        case ExpressionType.LessThan: call = Ast.LessThan(call, AstUtils.Constant(0)); break;
                        case ExpressionType.GreaterThanOrEqual: call = Ast.GreaterThanOrEqual(call, AstUtils.Constant(0)); break;
                        case ExpressionType.LessThanOrEqual: call = Ast.LessThanOrEqual(call, AstUtils.Constant(0)); break;
                        case ExpressionType.Equal: call = Ast.Equal(call, AstUtils.Constant(0)); break;
                        case ExpressionType.NotEqual: call = Ast.NotEqual(call, AstUtils.Constant(0)); break;
                    }

                    return new DynamicMetaObject(
                        call,
                        target.RestrictedArguments.GetAllRestrictions()
                    );
                }
            }

            return null;
        }
示例#5
0
        public DynamicMetaObject MakeCallExpression(OverloadResolverFactory resolverFactory, MethodInfo method, params DynamicMetaObject[] parameters) {
            OverloadResolver resolver;
            if (method.IsStatic) {
                resolver = resolverFactory.CreateOverloadResolver(parameters, new CallSignature(parameters.Length), CallTypes.None);
            } else {
                resolver = resolverFactory.CreateOverloadResolver(parameters, new CallSignature(parameters.Length - 1), CallTypes.ImplicitInstance);
            }
            BindingTarget target = resolver.ResolveOverload(method.Name, new MethodBase[] { method }, NarrowingLevel.None, NarrowingLevel.All);

            if (!target.Success) {
                BindingRestrictions restrictions = BindingRestrictions.Combine(parameters);
                foreach (DynamicMetaObject mo in parameters) {
                    restrictions = restrictions.Merge(BindingRestrictionsHelpers.GetRuntimeTypeRestriction(mo.Expression, mo.GetLimitType()));
                }
                return DefaultBinder.MakeError(
                    resolver.MakeInvalidParametersError(target),
                    restrictions,
                    typeof(object)
                );
            }

            return new DynamicMetaObject(target.MakeExpression(), target.RestrictedArguments.GetAllRestrictions());
        }
        private DynamicMetaObject TryMakeBindingTarget(OverloadResolverFactory resolverFactory, MethodInfo[] targets, DynamicMetaObject[] args, BindingRestrictions restrictions) {
            var resolver = resolverFactory.CreateOverloadResolver(args, new CallSignature(args.Length), CallTypes.None);
            BindingTarget target = resolver.ResolveOverload(targets[0].Name, targets, NarrowingLevel.None, NarrowingLevel.All);
            if (target.Success) {
                return new DynamicMetaObject(
                    target.MakeExpression(),
                    restrictions.Merge(BindingRestrictions.Combine(target.RestrictedArguments.Objects))
                );
            }

            return null;
        }