public void MergeCombinesDeeper()
 {
     foreach (bool w in new[] { false, true })
     {
         BindingRestrictions bW = BindingRestrictions.GetExpressionRestriction(Expression.Constant(w));
         foreach (bool x in new[] { false, true })
         {
             BindingRestrictions bX = BindingRestrictions.GetExpressionRestriction(Expression.Constant(x));
             foreach (bool y in new[] { false, true })
             {
                 BindingRestrictions bY     = BindingRestrictions.GetExpressionRestriction(Expression.Constant(y));
                 BindingRestrictions merged = bW.Merge(bX).Merge(bY);
                 Assert.Equal(w & x & y, Expression.Lambda <Func <bool> >(merged.ToExpression()).Compile()());
                 foreach (bool z in new[] { false, true })
                 {
                     BindingRestrictions bZ = BindingRestrictions.GetExpressionRestriction(
                         Expression.Constant(z));
                     merged = bW.Merge(bX).Merge(bY).Merge(bZ);
                     Assert.Equal(
                         w & x & y & z, Expression.Lambda <Func <bool> >(merged.ToExpression()).Compile()());
                 }
             }
         }
     }
 }
Beispiel #2
0
        public void EmptyRestiction()
        {
            BindingRestrictions           empty = BindingRestrictions.Empty;
            BindingRestrictionsProxyProxy view  = GetDebugViewObject(empty);

            Assert.True(view.IsEmpty);
            BindingRestrictions[] restrictions = view.Restrictions;
            Assert.Equal(1, restrictions.Length);
            Assert.Same(empty, restrictions[0]);
            Assert.Same(empty.ToExpression(), view.Test);
            Assert.Equal(empty.ToExpression().ToString(), view.ToString());
        }
        public void MergedRestrictionsProperties()
        {
            var exps = new Expression[]
            {
                Expression.Constant(false), Expression.Constant(true),
                Expression.Equal(Expression.Constant(2), Expression.Constant(3))
            };

            BindingRestrictions br = BindingRestrictions.Empty;
            var restrictions       = new List <BindingRestrictions>();

            foreach (var exp in exps)
            {
                BindingRestrictions res = BindingRestrictions.GetExpressionRestriction(exp);
                restrictions.Add(res);
                br = br.Merge(res);
            }

            if (BindingRestrictionsDebugViewType == null)
            {
                return;
            }

            BindingRestrictionsProxyProxy view = GetDebugViewObject(br);

            Assert.False(view.IsEmpty);

            Assert.Equal(br.ToExpression().ToString(), view.ToString());

            BindingRestrictions[] viewedRestrictions = view.Restrictions;

            // Check equal to source restrictions, but not insisting on order.
            Assert.Equal(3, viewedRestrictions.Length);
            Assert.True(viewedRestrictions.All(r => restrictions.Contains(r)));
        }
        public void EmptyRestiction()
        {
            if (BindingRestrictionsDebugViewType == null)
            {
                throw new SkipTestException("Didn't find DebuggerTypeProxyAttribute on BindingRestrictions.");
            }
            BindingRestrictions           empty = BindingRestrictions.Empty;
            BindingRestrictionsProxyProxy view  = GetDebugViewObject(empty);

            Assert.True(view.IsEmpty);
            BindingRestrictions[] restrictions = view.Restrictions;
            Assert.Equal(1, restrictions.Length);
            Assert.Same(empty, restrictions[0]);
            Assert.Same(empty.ToExpression(), view.Test);
            Assert.Equal(empty.ToExpression().ToString(), view.ToString());
        }
        public void MergeWithSelfHasSameExpression()
        {
            Expression          exp      = Expression.Constant(true);
            BindingRestrictions allowAll = BindingRestrictions.GetExpressionRestriction(exp);
            BindingRestrictions doubled  = allowAll.Merge(allowAll);

            Assert.Same(exp, doubled.ToExpression());
        }
        public void InstanceRestrictionForNull()
        {
            Expression          exp     = Expression.Default(typeof(Egalitarian));
            BindingRestrictions hasNull = BindingRestrictions.GetInstanceRestriction(exp, null);

            Assert.True(Expression.Lambda <Func <bool> >(hasNull.ToExpression()).Compile()());
            BindingRestrictions hasInst = BindingRestrictions.GetInstanceRestriction(exp, new Egalitarian());

            Assert.False(Expression.Lambda <Func <bool> >(hasInst.ToExpression()).Compile()());
        }
Beispiel #7
0
 public void AddRestriction(BindingRestrictions /*!*/ restriction)
 {
     if (_treatRestrictionsAsConditions)
     {
         AddCondition(restriction.ToExpression());
     }
     else
     {
         Add(restriction);
     }
 }
 public void MergeCombines()
 {
     foreach (bool x in new[] { false, true })
     {
         foreach (bool y in new[] { false, true })
         {
             BindingRestrictions bX     = BindingRestrictions.GetExpressionRestriction(Expression.Constant(x));
             BindingRestrictions bY     = BindingRestrictions.GetExpressionRestriction(Expression.Constant(y));
             BindingRestrictions merged = bX.Merge(bY);
             Assert.Equal(x & y, Expression.Lambda <Func <bool> >(merged.ToExpression()).Compile()());
         }
     }
 }
        public void InstanceRestrictionRequiresIdentity()
        {
            Egalitarian         instance     = new Egalitarian();
            Expression          exp          = Expression.Constant(instance);
            BindingRestrictions sameInstance = BindingRestrictions.GetInstanceRestriction(exp, instance);

            Assert.True(Expression.Lambda <Func <bool> >(sameInstance.ToExpression()).Compile()());
            BindingRestrictions diffInstance = BindingRestrictions.GetInstanceRestriction(exp, new Egalitarian());

            Assert.False(Expression.Lambda <Func <bool> >(diffInstance.ToExpression()).Compile()());
            BindingRestrictions noInstance = BindingRestrictions.GetInstanceRestriction(exp, null);

            Assert.False(Expression.Lambda <Func <bool> >(noInstance.ToExpression()).Compile()());
        }
Beispiel #10
0
        internal static void DumpRule(CallSiteBinder /*!*/ binder, BindingRestrictions /*!*/ restrictions, Expression /*!*/ expr)
        {
#if DEBUG && FEATURE_FULL_CONSOLE && !CLR2
            if (RubyOptions.ShowRules)
            {
                var oldColor = Console.ForegroundColor;
                try {
                    Console.ForegroundColor = ConsoleColor.Cyan;
                    Console.WriteLine("Rule #{0}: {1}", Interlocked.Increment(ref _ruleCounter), binder);
                    Console.ForegroundColor = ConsoleColor.DarkGray;
                    if (!_DumpingExpression)
                    {
                        var d = (restrictions != BindingRestrictions.Empty) ? Expression.IfThen(restrictions.ToExpression(), expr) : expr;
                        _DumpingExpression = true;
                        try {
                            if (_dumpViewMethod == null)
                            {
                                _dumpViewMethod = typeof(Expression).GetMethod("get_DebugView", BindingFlags.NonPublic | BindingFlags.Instance);
                            }
                            Console.WriteLine(_dumpViewMethod.Invoke(d, ArrayUtils.EmptyObjects));
                            Console.WriteLine();
                        } catch {
                            // nop
                        }
                    }
                } finally {
                    _DumpingExpression      = false;
                    Console.ForegroundColor = oldColor;
                }
            }
#endif
        }
        public void TypeRestrictionFalseForOtherType(object obj, Type type)
        {
            BindingRestrictions isType = BindingRestrictions.GetTypeRestriction(Expression.Constant(obj), type);

            Assert.False(Expression.Lambda <Func <bool> >(isType.ToExpression()).Compile()());
        }
        public void TypeRestrictionTrueForMatchType(object obj)
        {
            BindingRestrictions isType = BindingRestrictions.GetTypeRestriction(Expression.Constant(obj), obj.GetType());

            Assert.True(Expression.Lambda <Func <bool> >(isType.ToExpression()).Compile()());
        }
        /// <summary>
        /// Performs the runtime binding of the dynamic operation on a set of arguments.
        /// </summary>
        /// <param name="args">An array of arguments to the dynamic operation.</param>
        /// <param name="parameters">The array of <see cref="ParameterExpression"/> instances that represent the parameters of the call site in the binding process.</param>
        /// <param name="returnLabel">A LabelTarget used to return the result of the dynamic binding.</param>
        /// <returns>
        /// An Expression that performs tests on the dynamic operation arguments, and
        /// performs the dynamic operation if hte tests are valid. If the tests fail on
        /// subsequent occurrences of the dynamic operation, Bind will be called again
        /// to produce a new <see cref="Expression"/> for the new argument types.
        /// </returns>
        public sealed override Expression Bind(object[] args, ReadOnlyCollection <ParameterExpression> parameters, LabelTarget returnLabel)
        {
            ContractUtils.RequiresNotNull(args, "args");
            ContractUtils.RequiresNotNull(parameters, "parameters");
            ContractUtils.RequiresNotNull(returnLabel, "returnLabel");
            if (args.Length == 0)
            {
                throw Error.OutOfRange("args.Length", 1);
            }
            if (parameters.Count == 0)
            {
                throw Error.OutOfRange("parameters.Count", 1);
            }
            if (args.Length != parameters.Count)
            {
                throw new ArgumentOutOfRangeException("args");
            }

            // Ensure that the binder's ReturnType matches CallSite's return
            // type. We do this so meta objects and language binders can
            // compose trees together without needing to insert converts.
            Type expectedResult;

            if (IsStandardBinder)
            {
                expectedResult = ReturnType;

                if (returnLabel.Type != typeof(void) &&
                    !TypeUtils.AreReferenceAssignable(returnLabel.Type, expectedResult))
                {
                    throw Error.BinderNotCompatibleWithCallSite(expectedResult, this, returnLabel.Type);
                }
            }
            else
            {
                // Even for non-standard binders, we have to at least make sure
                // it works with the CallSite's type to build the return.
                expectedResult = returnLabel.Type;
            }

            DynamicMetaObject target = DynamicMetaObject.Create(args[0], parameters[0]);

            DynamicMetaObject[] metaArgs = CreateArgumentMetaObjects(args, parameters);

            DynamicMetaObject binding = Bind(target, metaArgs);

            if (binding == null)
            {
                throw Error.BindingCannotBeNull();
            }

            Expression          body         = binding.Expression;
            BindingRestrictions restrictions = binding.Restrictions;

            // Ensure the result matches the expected result type.
            if (expectedResult != typeof(void) &&
                !TypeUtils.AreReferenceAssignable(expectedResult, body.Type))
            {
                //
                // Blame the last person that handled the result: assume it's
                // the dynamic object (if any), otherwise blame the language.
                //
                if (target.Value is IDynamicMetaObjectProvider)
                {
                    throw Error.DynamicObjectResultNotAssignable(body.Type, target.Value.GetType(), this, expectedResult);
                }
                else
                {
                    throw Error.DynamicBinderResultNotAssignable(body.Type, this, expectedResult);
                }
            }

            // if the target is IDO, standard binders ask it to bind the rule so we may have a target-specific binding.
            // it makes sense to restrict on the target's type in such cases.
            // ideally IDO metaobjects should do this, but they often miss that type of "this" is significant.
            if (IsStandardBinder && args[0] as IDynamicMetaObjectProvider != null)
            {
                if (restrictions == BindingRestrictions.Empty)
                {
                    throw Error.DynamicBindingNeedsRestrictions(target.Value.GetType(), this);
                }
            }

            restrictions = AddRemoteObjectRestrictions(restrictions, args, parameters);

            // Add the return
            if (body.NodeType != ExpressionType.Goto)
            {
                body = Expression.Return(returnLabel, body);
            }

            // Finally, add restrictions
            if (restrictions != BindingRestrictions.Empty)
            {
                body = Expression.IfThen(restrictions.ToExpression(), body);
            }

            return(body);
        }