public override void AfterVisit(BinaryExpression node)
        {
            var expType = ToExpressionType(node.Operator);
            switch (node.GetExtension<BinaryExpressionExtension>().AccessType)
            {
                case ExpressionAccessType.Read:
                    analyzeReadAccessExpression(node, expType);
                    break;
                //This case is only included as a sanity test
                //analysis for writable expressions are handled by their parent BinaryExpression (the assignment expression itself)
                case ExpressionAccessType.Write:
                    switch (node.Operator.Operation)
                    {
                        //The only writeable expression types are:
                        case OperationKind.Index:
                        case OperationKind.MemberAccess:
                            break;
                        default:
                            throw new UnhandledCaseException("Expression returnType " + expType + " is not writable.  (user error?)");
                    }
                    break;
                default:
                    throw new UnhandledCaseException();
            }

            base.AfterVisit(node);
        }
Пример #2
0
        public override void BeforeVisit(BinaryExpression node)
        {
            base.BeforeVisit(node);
            if (node.Operator.Operation == OperationKind.Assign)
                node.LeftValue.GetExtension<BinaryExpressionExtension>().AccessType = ExpressionAccessType.Write;

            if (node.Operator.Operation == OperationKind.MemberAccess)
                node.RightValue.GetExtension<NamedExpressionNodeExtension>().IsMemberReference = true;
        }
Пример #3
0
 public override void BeforeVisit(BinaryExpression expression)
 {
     base.BeforeVisit(expression);
     switch (expression.Operator.Operation)
     {
         case OperationKind.Not:
             _errorCollector.OperatorIsNotBinary(expression.Location, expression.Operator.ToString());
             break;
     }
 }
        void analyzeAssignmentExpression(BinaryExpression node, Expression rvalue)
        {
            if (rvalue.Type.IsValueType)
                rvalue = Expression.Convert(rvalue, typeof(object));

            switch (node.LeftValue.NodeKind)
            {
                case AstNodeKind.IdentifierExpression:
                    var identifierExp = (IdentifierExpression)node.LeftValue;
                    _expressionStack.Push(node, identifierExp.GetExtension<SymbolExtension>().Symbol.GetSetExpression(rvalue));
                    return;
                case AstNodeKind.BinaryExpression:
                    if (node.LeftValue.NodeKind != AstNodeKind.BinaryExpression)
                        return;
                    analyzeAssignmentToBinaryExpression(rvalue, node);
                    return;
                default:
                    _errorCollector.InvalidLValueForAssignment(node.LeftValue.Location);
                    return;
            }
        }
 void analyzeAssignmentToBinaryExpression(Expression rvalue, BinaryExpression node)
 {
     BinaryExpression binaryLvalue = (BinaryExpression)node.LeftValue;
     //A BinaryExpression on as the LeftValue can be either an Index or MemberAccess operation
     switch (binaryLvalue.Operator.Operation)
     {
         case OperationKind.Index:
             //Have to handle array index and member assignments here because we don't know the rvalue until now.
             var args = popIndexArguments(binaryLvalue);
             args.Add(rvalue);
             var indexExpression = this.dynamicSetIndex(args.ToArray());
             _expressionStack.Push(node, indexExpression);
             return;
         case OperationKind.MemberAccess:
             //In this case, the rvalue is the value to be assigned (it does not correspond to node.RightValue)
             var instanceExpr = _expressionStack.Pop();
             _expressionStack.Push(node, this.PropertyOrFieldSet(((IdentifierExpression)binaryLvalue.RightValue).Identifier.Text, instanceExpr, rvalue));
             return;
         default:
             _errorCollector.InvalidLValueForAssignment(binaryLvalue.Location);
             break;
     }
 }
 List<Expression> popIndexArguments(BinaryExpression node)
 {
     ArgumentList argList = (ArgumentList)node.RightValue;
     List<Expression> args = new List<Expression>();
     List<Expression> indexerArguments = _expressionStack.Pop(argList.Arguments.Length);
     Expression array = _expressionStack.Pop();
     args.Add(array);
     args.AddRange(indexerArguments);
     return args;
 }
 void analyzeReadMemberAccess(BinaryExpression node)
 {
     switch (node.RightValue.NodeKind)
     {
         case AstNodeKind.IdentifierExpression:
             Expression instanceExpr = _expressionStack.Pop();
             var propertyOrFieldGet = this.PropertyOrFieldGet(((IdentifierExpression)node.RightValue).Identifier.Text, instanceExpr);
             _expressionStack.Push(node, propertyOrFieldGet);
             break;
         case AstNodeKind.FunctionCallExpression:
             FunctionCallExpression funcCallExpression = (FunctionCallExpression)node.RightValue;
             List<Expression> args = _expressionStack.Pop(funcCallExpression.Arguments.Length);
             args.Insert(0, _expressionStack.Pop()); //<--object instance
             _expressionStack.Push(node, this.dynamicCall(funcCallExpression.Identifier.Text, args.ToArray()));
             break;
         default:
             throw new UnhandledCaseException();
     }
 }
 void analyzeReadIndexExpression(BinaryExpression node)
 {
     var args = popIndexArguments(node).ToArray();
     var indexExpression = this.dynamicGetIndex(args);
     _expressionStack.Push(node, indexExpression);
 }
        void analyzeReadAccessExpression(BinaryExpression node, ExpressionType expType)
        {
            //Read operations which do not pop rvalue or lvalues from the stack.
            switch (expType)
            {
                case ExpressionType.Index:
                    analyzeReadIndexExpression(node);
                    return;
                case ExpressionType.MemberAccess:
                    analyzeReadMemberAccess(node);
                    return;
            }

            Expression rvalue = _expressionStack.Pop();
            //These operations easily pop their rvalue from _expressionStack but lvalue requires special handling
            if (expType == ExpressionType.Assign)
            {
                analyzeAssignmentExpression(node, rvalue);
                return;
            }

            //All other operations can expect to find both their rvalue and lvalues on the stack.
            Expression lvalue = _expressionStack.Pop();
            switch (expType)
            {
                case ExpressionType.OrElse:
                    _expressionStack.Push(node, Expression.OrElse(RuntimeHelpers.EnsureBoolResult(lvalue), RuntimeHelpers.EnsureBoolResult(rvalue)));
                    return;
                case ExpressionType.AndAlso:
                    _expressionStack.Push(node, Expression.AndAlso(RuntimeHelpers.EnsureBoolResult(lvalue), RuntimeHelpers.EnsureBoolResult(rvalue)));
                    return;
                default:
                    //_expressionStack.Push(node, this.DynamicExpression(_languageContext.CreateBinaryOperationBinder(expType), typeof(object), lvalue, rvalue));
                    _expressionStack.Push(node, this.dynamicBinaryExpression(expType, lvalue, rvalue));
                    return;
            }
        }
Пример #10
0
 public virtual void BeforeVisit(BinaryExpression node)
 {
     this.BeforeVisitCatchAll(node);
 }
Пример #11
0
 public virtual void AfterVisit(BinaryExpression node)
 {
     this.AfterVisitCatchAll(node);
 }
Пример #12
0
        private ExpressionNodeBase RecurseExp(Stack<AstNodeBase> expStack)
        {
            ExpressionNodeBase retval;

            //If there was only one item in the stack, then we must be parsing
            //an expression (or part of an expression) with only a single term.
            if (expStack.Count == 1)
                retval = (ExpressionNodeBase)expStack.Pop();
            else
            {
                ExpressionNodeBase rval;
                AstNodeBase node = expStack.Pop();
                if (!(node is Operator))
                    _errorCollector.ExpectedOperator(node.Location);

                Operator oper = (Operator)node;
                if (expStack.Peek() is Operator)
                    rval = this.RecurseExp(expStack);
                else
                    rval = expStack.Pop() as ExpressionNodeBase;

                if (oper.IsUnary)
                    retval = new UnaryExpression(rval, oper);
                else
                {
                    //DebugAssert.IsNonZero(expStack.Count, "expStack.Count == 0");
                    if(expStack.Count == 0)
                        _errorCollector.SyntaxErrorInExpression(rval.Location);

                    ExpressionNodeBase lval;
                    if(expStack.Peek() is Operator)
                        lval = this.RecurseExp(expStack);
                    else
                        lval = expStack.Pop() as ExpressionNodeBase;

                    retval = new BinaryExpression(lval, oper, rval);
                }
            }
            return retval;
        }