Beispiel #1
0
        public BinaryExpr(TotemOperator op, Expr left, Expr right)
        {
            ContractUtils.RequiresNotNull(left, "left");
            ContractUtils.RequiresNotNull(right, "right");

            switch (op)
            {
                case TotemOperator.Add:
                case TotemOperator.Subtract:
                case TotemOperator.Modulo:
                case TotemOperator.Multiply:
                case TotemOperator.Divide:
                case TotemOperator.LessThan:
                case TotemOperator.LessThanOrEqual:
                case TotemOperator.GreaterThan:
                case TotemOperator.GreaterThanOrEqual:
                case TotemOperator.Equal:
                case TotemOperator.NotEqual:
                case TotemOperator.LogicalAnd:
                case TotemOperator.LogicalOr:
                case TotemOperator.Attatch:
                    break;

                default: throw Assert.Unreachable;
            }

            _left = left;
            _right = right;
            _op = op;
        }
Beispiel #2
0
        public UnaryExpr(TotemOperator op, Expr expr)
        {
            _expr = expr;
            _op = op;
            switch (op)
            {
                case TotemOperator.Increment:
                case TotemOperator.Decrement:
                case TotemOperator.PostIncrement:
                case TotemOperator.PostDecrement:
                case TotemOperator.Not:
                case TotemOperator.Negate:
                case TotemOperator.Pos:
                    break;

                default: throw Assert.Unreachable;
            }
        }
Beispiel #3
0
 private static MethodInfo GetHelperMethod(TotemOperator op)
 {
     switch (op)
     {
         default:
             Debug.Assert(false, "Invalid TotemOperator: " + op.ToString());
             return null;
     }
 }
Beispiel #4
0
        private static TotemOperationKind TotemOperatorToAction(TotemOperator op)
        {
            switch (op)
            {
                case TotemOperator.Add: return TotemOperationKind.Add;
                case TotemOperator.Subtract: return TotemOperationKind.Subtract;
                case TotemOperator.Multiply: return TotemOperationKind.Multiply;
                case TotemOperator.Divide: return TotemOperationKind.Divide;
                case TotemOperator.Modulo: return TotemOperationKind.Mod;
                case TotemOperator.BitwiseAnd: return TotemOperationKind.BitwiseAnd;
                case TotemOperator.BitwiseOr: return TotemOperationKind.BitwiseOr;
                case TotemOperator.Xor: return TotemOperationKind.ExclusiveOr;
                case TotemOperator.LeftShift: return TotemOperationKind.LeftShift;
                case TotemOperator.RightShift: return TotemOperationKind.RightShift;
                case TotemOperator.Power: return TotemOperationKind.Power;
                case TotemOperator.FloorDivide: return TotemOperationKind.FloorDivide;

                // Comparisons
                case TotemOperator.LessThan: return TotemOperationKind.LessThan;
                case TotemOperator.LessThanOrEqual: return TotemOperationKind.LessThanOrEqual;
                case TotemOperator.GreaterThan: return TotemOperationKind.GreaterThan;
                case TotemOperator.GreaterThanOrEqual: return TotemOperationKind.GreaterThanOrEqual;
                case TotemOperator.Equal: return TotemOperationKind.Equal;
                case TotemOperator.NotEqual: return TotemOperationKind.NotEqual;

                case TotemOperator.In: return TotemOperationKind.Contains;
                    
                case TotemOperator.NotIn:
                case TotemOperator.IsNot:
                case TotemOperator.Is:
                    return TotemOperationKind.None;

                default:
                    Debug.Assert(false, "Unexpected TotemOperator: " + op.ToString());
                    return TotemOperationKind.None;
            }
        }
Beispiel #5
0
        private bool IsPrefixToken(Token t, out TotemOperator op)
        {
            switch(t.Kind)
            {
                case TokenType.Increment:
                    op = TotemOperator.Increment;
                    return true;

                case TokenType.Decrement:
                    op = TotemOperator.Decrement;
                    return true;

                case TokenType.Subtract:
                    op = TotemOperator.Negate;
                    return true;

                case TokenType.Add:
                    op = TotemOperator.Pos;
                    return true;

                case TokenType.LogicalNot:
                    op = TotemOperator.Not;
                    return true;

                default:
                    op = TotemOperator.None;
                    return false;
            }
        }
Beispiel #6
0
        private Expression MakeBinaryOperation(TotemOperator op, Expression left, Expression right, SourceSpan span)
        {
            if (op == TotemOperator.In || op == TotemOperator.NotIn)
            {
                throw new NotImplementedException("In or NotIn op");
            }

            Type t = Type;
            ParameterExpression tmp;
            if (op == TotemOperator.LogicalAnd)
            {
                tmp = Expression.Variable(t, "$and_tmp");

                return Expression.Block(
                    new[] { tmp },
                    Expression.Condition(
                        GlobalParent.Convert(
                            typeof(bool),
                            ConversionResultKind.ExplicitCast,
                            Expression.Assign(
                                tmp,
                                Utils.Convert(
                                    left,
                                    t
                                )
                            )
                        ),
                        Utils.Convert(
                            right,
                            t
                        ),
                        tmp
                    )
                );
            }
            else if (op == TotemOperator.LogicalOr)
            {
                tmp = Expression.Variable(t, "$or_tmp");

                return Expression.Block(
                    new[] { tmp },
                    Expression.Condition(
                        GlobalParent.Convert(
                            typeof(bool),
                            ConversionResultKind.ExplicitCast,
                            Expression.Assign(
                                tmp,
                                Utils.Convert(
                                    left,
                                    t
                                )
                            )
                        ),
                        tmp,
                        Utils.Convert(
                            right,
                            t
                        )
                    )
                );
            }

            TotemOperationKind action = TotemOperatorToAction(op);
            if (action != TotemOperationKind.None)
            {
                // Create action expression
                return GlobalParent.Operation(
                    typeof(object),
                    action,
                    left,
                    right
                );
            }
            else
            {
                // Call helper method
                return Expression.Call(
                    GetHelperMethod(op),
                    ConvertIfNeeded(left, typeof(object)),
                    ConvertIfNeeded(right, typeof(object))
                );
            }
        }
Beispiel #7
0
        private bool IsMultiplicativeToken(Token t, out TotemOperator op)
        {
            switch(t.Kind)
            {
                case TokenType.Multiply:
                    op = TotemOperator.Multiply;
                    return true;

                case TokenType.Divide:
                    op = TotemOperator.Divide;
                    return true;

                case TokenType.Mod:
                    op = TotemOperator.Modulo;
                    return true;

                default:
                    op = TotemOperator.None;
                    return false;
            }
        }
Beispiel #8
0
        private bool IsAdditiveToken(Token t, out TotemOperator op)
        {
            switch(t.Kind)
            {
                case TokenType.Add:
                    op = TotemOperator.Add;
                    return true;

                case TokenType.Subtract:
                    op = TotemOperator.Subtract;
                    return true;

                default:
                    op = TotemOperator.None;
                    return false;
            }
        }
Beispiel #9
0
        private bool IsRelationalToken(Token t, out TotemOperator op)
        {
            switch(t.Kind)
            {
                case TokenType.LessThan:
                    op = TotemOperator.LessThan;
                    return true;

                case TokenType.LessThanOrEqual:
                    op = TotemOperator.LessThanOrEqual;
                    return true;

                case TokenType.GreaterThan:
                    op = TotemOperator.GreaterThan;
                    return true;

                case TokenType.GreaterThanOrEqual:
                    op = TotemOperator.GreaterThanOrEqual;
                    return true;

                default:
                    op = TotemOperator.None;
                    return false;
            }
        }
Beispiel #10
0
        private bool IsEqualityToken(Token t, out TotemOperator op)
        {
            switch (t.Kind)
            {
                case TokenType.Equals:
                    op = TotemOperator.Equal;
                    return true;

                case TokenType.NotEquals:
                    op = TotemOperator.NotEqual;
                    return true;


                default:
                    op = TotemOperator.None;
                    return false;
            }
        }
Beispiel #11
0
        private bool IsPostfixToken(Token t, out TotemOperator op)
        {
            switch(t.Kind)
            {
                case TokenType.Increment:
                    op = TotemOperator.PostIncrement;
                    return true;

                case TokenType.Decrement:
                    op = TotemOperator.PostDecrement;
                    return true;

                default:
                    op = TotemOperator.None;
                    return false;
            }
        }