Пример #1
0
        private static ExpressionBase ParseComparison(PositionalTokenizer tokenizer, ExpressionBase left, ComparisonOperation operation, int joinerLine, int joinerColumn)
        {
            var right = ParseExpression(tokenizer, OperationPriority.Compare);

            switch (right.Type)
            {
            case ExpressionType.ParseError:
                return(right);

            case ExpressionType.BooleanConstant:
            case ExpressionType.Conditional:     // will be rebalanced
            case ExpressionType.FloatConstant:
            case ExpressionType.FunctionCall:
            case ExpressionType.IntegerConstant:
            case ExpressionType.Mathematic:
            case ExpressionType.StringConstant:
            case ExpressionType.Variable:
                break;

            default:
                var expressionTokenizer = tokenizer as ExpressionTokenizer;
                if (expressionTokenizer != null)
                {
                    expressionTokenizer.QueueExpression(right);
                }

                right = new KeywordExpression(ComparisonExpression.GetOperatorString(operation), joinerLine, joinerColumn);
                return(ParseError(tokenizer, "Incompatible comparison", right));
            }

            return(new ComparisonExpression(left, operation, right));
        }
Пример #2
0
 public ReturnExpression(KeywordExpression keyword, ExpressionBase value)
     : this(value)
 {
     _keyword = keyword;
     Line     = keyword.Line;
     Column   = keyword.Column;
 }
Пример #3
0
        /// <summary>
        /// Parses a for loop.
        /// </summary>
        /// <remarks>
        /// Assumes the 'for' keyword has already been consumed.
        /// </remarks>
        internal static ExpressionBase Parse(PositionalTokenizer tokenizer, int line = 0, int column = 0)
        {
            ExpressionBase.SkipWhitespace(tokenizer);
            var keywordFor = new KeywordExpression("for", line, column);

            line   = tokenizer.Line;
            column = tokenizer.Column;
            var iteratorName = tokenizer.ReadIdentifier();

            if (iteratorName.IsEmpty)
            {
                return(ParseError(tokenizer, "Invalid function name", line, column));
            }
            var iterator = new VariableDefinitionExpression(iteratorName.ToString(), line, column);

            ExpressionBase.SkipWhitespace(tokenizer);

            line   = tokenizer.Line;
            column = tokenizer.Column;
            if (!tokenizer.Match("in"))
            {
                return(ParseError(tokenizer, "Expected 'in' after loop variable"));
            }
            var keywordIn = new KeywordExpression("in", line, column);

            var range = ExpressionBase.Parse(tokenizer);

            if (range.Type == ExpressionType.ParseError)
            {
                return(range);
            }

            var loop = new ForExpression(iterator, range);

            var error = ExpressionBase.ParseStatementBlock(tokenizer, loop.Expressions);

            if (error != null)
            {
                return(error);
            }

            loop._keywordFor = keywordFor;
            loop._keywordIn  = keywordIn;
            loop.Line        = keywordFor.Line;
            loop.Column      = keywordFor.Column;
            loop.EndLine     = tokenizer.Line;
            loop.EndColumn   = tokenizer.Column;

            return(loop);
        }
Пример #4
0
        private static ExpressionBase ParseConditional(PositionalTokenizer tokenizer, ExpressionBase left, ConditionalOperation operation, int joinerLine, int joinerColumn)
        {
            OperationPriority priority;

            switch (operation)
            {
            case ConditionalOperation.And:
                priority = OperationPriority.And;
                break;

            case ConditionalOperation.Or:
                priority = OperationPriority.Or;
                break;

            case ConditionalOperation.Not:
                priority = OperationPriority.Not;
                break;

            default:
                return(new ParseErrorExpression("Unknown operation: " + operation));
            }

            var right = ParseExpression(tokenizer, priority);

            switch (right.Type)
            {
            case ExpressionType.ParseError:
                return(right);

            case ExpressionType.BooleanConstant:
            case ExpressionType.Comparison:
            case ExpressionType.Conditional:
            case ExpressionType.FunctionCall:
            case ExpressionType.Variable:
                break;

            default:
                var expressionTokenizer = tokenizer as ExpressionTokenizer;
                if (expressionTokenizer != null)
                {
                    expressionTokenizer.QueueExpression(right);
                }

                right = new KeywordExpression(ConditionalExpression.GetOperatorString(operation), joinerLine, joinerColumn);
                return(ParseError(tokenizer, "Incompatible logical condition", right));
            }

            return(new ConditionalExpression(left, operation, right));
        }
Пример #5
0
        private static ExpressionBase ParseAssignment(PositionalTokenizer tokenizer, ExpressionBase variable, int joinerLine, int joinerColumn)
        {
            if (variable.Type != ExpressionType.Variable)
            {
                return(ParseError(tokenizer, "Cannot assign value to non-variable", variable));
            }

            var value = ParseExpression(tokenizer, OperationPriority.Assign);

            switch (value.Type)
            {
            case ExpressionType.ParseError:
                value = new KeywordExpression("=", joinerLine, joinerColumn);
                break;

            case ExpressionType.Array:
            case ExpressionType.BooleanConstant:
            case ExpressionType.Comparison:
            case ExpressionType.Conditional:
            case ExpressionType.Dictionary:
            case ExpressionType.FloatConstant:
            case ExpressionType.FunctionCall:
            case ExpressionType.FunctionDefinition:
            case ExpressionType.IntegerConstant:
            case ExpressionType.Mathematic:
            case ExpressionType.StringConstant:
            case ExpressionType.Variable:
                break;

            default:
                var expressionTokenizer = tokenizer as ExpressionTokenizer;
                if (expressionTokenizer != null)
                {
                    expressionTokenizer.QueueExpression(value);
                }

                value = new KeywordExpression("=", joinerLine, joinerColumn);
                return(ParseError(tokenizer, "Incompatible assignment", value));
            }

            return(new AssignmentExpression((VariableExpression)variable, value));
        }
Пример #6
0
        private static ExpressionBase ParseMathematic(PositionalTokenizer tokenizer, ExpressionBase left, MathematicOperation operation, int joinerLine, int joinerColumn)
        {
            OperationPriority priority;

            switch (operation)
            {
            case MathematicOperation.Add:
                if (left is StringConstantExpression)
                {
                    priority = OperationPriority.AppendString;
                    break;
                }
                priority = OperationPriority.AddSubtract;
                break;

            case MathematicOperation.Subtract:
                priority = OperationPriority.AddSubtract;
                break;

            case MathematicOperation.Multiply:
            case MathematicOperation.Divide:
            case MathematicOperation.Modulus:
                priority = OperationPriority.MulDivMod;
                break;

            case MathematicOperation.BitwiseAnd:
                priority = OperationPriority.BitwiseAnd;
                break;

            default:
                return(new ParseErrorExpression("Unknown operator: " + operation));
            }

            var right = ParseExpression(tokenizer, priority);

            switch (right.Type)
            {
            case ExpressionType.ParseError:
                return(right);

            case ExpressionType.Comparison:     // will be rebalanced
            case ExpressionType.Conditional:    // will be rebalanced
            case ExpressionType.FloatConstant:
            case ExpressionType.FunctionCall:
            case ExpressionType.IntegerConstant:
            case ExpressionType.Mathematic:
            case ExpressionType.StringConstant:
            case ExpressionType.Variable:
                break;

            default:
                var expressionTokenizer = tokenizer as ExpressionTokenizer;
                if (expressionTokenizer != null)
                {
                    expressionTokenizer.QueueExpression(right);
                }

                right = new KeywordExpression(MathematicExpression.GetOperatorCharacter(operation).ToString(), joinerLine, joinerColumn);
                return(ParseError(tokenizer, "Incompatible mathematical operation", right));
            }

            if (priority == OperationPriority.AddSubtract)
            {
                var mathematicRight = right as MathematicExpression;
            }

            return(new MathematicExpression(left, operation, right));
        }
Пример #7
0
 public ReturnExpression(KeywordExpression keyword, ExpressionBase value)
     : this(value)
 {
     _keyword = keyword;
     Location = new Jamiras.Components.TextRange(keyword.Location.Start, value.Location.End);
 }