Пример #1
0
        private static ASTIf ParseIf()
        {
            currentToken++;

            if (currentTokens[currentToken].Token == "(")
            {
                currentToken++;
                ASTStatement   ifCondition = ParseStatement();
                List <ASTNode> ifCodeBlock;
                List <ASTNode> elseCodeBlock;
                currentToken++;
                ifCodeBlock = ParseCodeBlockOrSingleLineStatement();
                if (currentTokens[currentToken].Token == "else")
                {
                    currentToken++;
                    elseCodeBlock = ParseCodeBlockOrSingleLineStatement();
                }
                else
                {
                    elseCodeBlock = null;
                }

                return(new ASTIf()
                {
                    Condition = ifCondition,
                    CodeBlock = ifCodeBlock,
                    ElseCodeBlock = elseCodeBlock
                });
            }
            else
            {
                throw new ParserException("Expected ( after if.", currentTokens[currentToken].LineNumber);
            }
        }
Пример #2
0
        private static List <ASTNode> ParseCodeBlock()
        {
            List <ASTNode> codeBlock = new List <ASTNode>();

            if (currentToken < currentTokens.Count)
            {
                if (currentTokens[currentToken].Token == "{")
                {
                    currentToken++;

                    while (currentToken < currentTokens.Count && currentTokens[currentToken].Token != "}")
                    {
                        if (currentTokens[currentToken] is ReservedWordToken && currentTokens[currentToken].Token == "if")
                        {
                            ASTIf ifNode = ParseIf();
                            codeBlock.Add(ifNode);
                        }
                        else if (currentTokens[currentToken] is ReservedWordToken && currentTokens[currentToken].Token == "for")
                        {
                            ASTFor forNode = ParseFor();
                            codeBlock.Add(forNode);
                        }
                        else if (currentTokens[currentToken] is ReservedWordToken && currentTokens[currentToken].Token == "while")
                        {
                            ASTWhile whileNode = ParseWhile();
                            codeBlock.Add(whileNode);
                        }
                        else
                        {
                            ASTStatement statement = ParseStatement();
                            if (statement != null)
                            {
                                codeBlock.Add(statement);
                            }
                        }
                    }

                    if (currentToken == currentTokens.Count)
                    {
                        throw new ParserException("SourceCode can't end in Code Block.", -1);
                    }

                    return(codeBlock);
                }
                // No '{' means just one line of code
                else
                {
                    ASTStatement statement = ParseStatement();

                    if (statement != null)
                    {
                        codeBlock.Add(statement);
                    }

                    return(codeBlock);
                }
            }
            throw new ParserException("Expected Code Block found End of File.", -1);
        }
Пример #3
0
 public ASTSelectionStatement(List <ASTNode> cond,
                              ASTStatement then,
                              ASTStatement otherwise) : base("SelectionStatement")
 {
     Condition = cond;
     Then      = then;
     Otherwise = otherwise;
 }
Пример #4
0
 public ASTIterationStatement(List <ASTNode> init,
                              List <ASTNode> cond,
                              List <ASTNode> step,
                              ASTStatement stat) : base("IterationStatement")
 {
     Initilize = init;
     Condition = cond;
     Step      = step;
     Stat      = stat;
 }
Пример #5
0
        private static ASTFor ParseFor()
        {
            currentToken++;

            if (currentTokens[currentToken].Token == "(")
            {
                currentToken++;
                ASTStatement   forInitialise = null;
                ASTStatement   forCondition  = null;
                ASTStatement   forCount      = null;
                List <ASTNode> codeBlock;


                if (currentTokens[currentToken].Token != ";")
                {
                    forInitialise = ParseStatement();
                }
                else
                {
                    currentToken++;
                }

                if (currentTokens[currentToken].Token != ";")
                {
                    forCondition = ParseStatement();
                }
                else
                {
                    currentToken++;
                }

                if (currentTokens[currentToken].Token != ")")
                {
                    forCount = ParseStatement();
                }
                currentToken++;

                codeBlock = ParseCodeBlockOrSingleLineStatement();

                return(new ASTFor()
                {
                    Initialise = forInitialise,
                    Condition = forCondition,
                    Count = forCount,
                    CodeBlock = codeBlock
                });
            }
            else
            {
                throw new ParserException("Expected ( after for.", currentTokens[currentToken].LineNumber);
            }
        }
Пример #6
0
        private static ASTWhile ParseWhile()
        {
            currentToken++;

            if (currentTokens[currentToken].Token == "(")
            {
                currentToken++;
                ASTStatement   condition = ParseStatement();
                List <ASTNode> codeBlock;
                currentToken++;
                codeBlock = ParseCodeBlockOrSingleLineStatement();

                return(new ASTWhile()
                {
                    Condition = condition,
                    CodeBlock = codeBlock
                });
            }
            else
            {
                throw new ParserException("Expected ( after if.", currentTokens[currentToken].LineNumber);
            }
        }
Пример #7
0
 public void AddStatement(ASTStatement statement)
 {
     statements.AddStatement(statement);
 }
Пример #8
0
 /// <summary>
 /// Initializes a new instance of the <see cref="While"/> class with structure like:
 /// while (Condition)
 ///     Body
 /// </summary>
 /// <param name="condition">The condition.</param>
 /// <param name="body">The body.</param>
 public While(ASTExpression condition, ASTStatement body)
 {
     Condition = condition;
     Body      = body;
 }
Пример #9
0
 /// <summary>
 /// Initializes a new instance of the <see cref="If"/> class with structure like:
 /// if (Condition)
 ///     TrueBody
 /// else
 ///     FalseBody
 /// </summary>
 /// <param name="condition">The condition.</param>
 /// <param name="trueBody">The true body.</param>
 /// <param name="falseBody">The false body.</param>
 public If(ASTExpression condition, ASTStatement trueBody, ASTStatement falseBody)
 {
     Condition = condition;
     TrueBody  = trueBody;
     FalseBody = falseBody;
 }
Пример #10
0
 /// <summary>
 /// Initializes a new instance of the <see cref="If"/> class with structure like:
 /// if (Condition)
 ///     Body
 /// </summary>
 /// <param name="condition">The condition.</param>
 /// <param name="body">The body.</param>
 public If(ASTExpression condition, ASTStatement body)
 {
     Condition = condition;
     TrueBody  = body;
     FalseBody = null;
 }
Пример #11
0
        private static ASTNode ParseSingleStatement()
        {
            ASTNode ret = null;

            if (currentTokens[currentToken] is StringToken)
            {
                ret = new ASTString {
                    String = currentTokens[currentToken].Token
                };
                currentToken++;
            }
            else if (currentTokens[currentToken] is NumberToken)
            {
                double dResult;
                if (double.TryParse(currentTokens[currentToken].Token, NumberStyles.Any, CultureInfo.GetCultureInfo("en"), out dResult))
                {
                    ret = new ASTNumber {
                        Number = dResult
                    };
                }
                else
                {
                    throw new ParserException(string.Format("Number {0} is not valid.", currentTokens[currentToken].Token), currentTokens[currentToken].LineNumber);
                }
                currentToken++;
            }
            else if (currentTokens[currentToken] is ReservedWordToken)
            {
                if (currentTokens[currentToken].Token == "this" || currentTokens[currentToken].Token == "VM")
                {
                    string scope = currentTokens[currentToken].Token;
                    currentToken++;
                    if (currentTokens[currentToken] is SpecialToken && currentTokens[currentToken].Token == ".")
                    {
                        currentToken++;
                        ret = ParseFunctionCallOrParameterAccess(scope);
                    }
                    else
                    {
                        throw new ParserException(string.Format("Expected '.' instead of '{0}'.", currentTokens[currentToken].Token), currentTokens[currentToken].LineNumber);
                    }
                }
                else if (currentTokens[currentToken].Token == "object" ||
                         currentTokens[currentToken].Token == "string" ||
                         currentTokens[currentToken].Token == "number")
                {
                    VMType type = currentTokens[currentToken].Token == "number" ? VMType.Number : (currentTokens[currentToken].Token == "string" ? VMType.String : VMType.Object);
                    currentToken++;
                    if (currentTokens[currentToken] is IdentifierToken)
                    {
                        ret = new ASTLocalVariable()
                        {
                            Type = type,
                            Name = currentTokens[currentToken].Token
                        };
                    }
                    else
                    {
                        throw new ParserException("Expected Identifier.", currentTokens[currentToken].LineNumber);
                    }
                    currentToken++;
                }
                else if (currentTokens[currentToken].Token == "new")
                {
                    currentToken++;
                    ASTNode createClass = ParseFunctionCallOrParameterAccess("constructor");
                    if (createClass is ASTFunctionCall)
                    {
                        ASTFunctionCall fc = (ASTFunctionCall)createClass;
                        ret = new ASTCreateClass()
                        {
                            Scope        = fc.FunctionName,
                            FunctionName = fc.FunctionName,
                            Parameter    = fc.Parameter
                        };
                    }
                    else
                    {
                        throw new ParserException("Error with new.", currentTokens[currentToken].LineNumber);
                    }
                }
                else if (currentTokens[currentToken].Token == "return")
                {
                    currentToken++;
                    ret = new ASTReturn()
                    {
                        Return = ParseStatement()
                    };

                    // Point to ';' again!!!
                    --currentToken;
                }
                else
                {
                    throw new ParserException(string.Format("Reserved Word {0} is not legal in Statement.", currentTokens[currentToken].Token), currentTokens[currentToken].LineNumber);
                }
            }
            else if (currentTokens[currentToken] is IdentifierToken)
            {
                string identifierOrScope = currentTokens[currentToken].Token;
                currentToken++;
                if (currentTokens[currentToken] is SpecialToken)
                {
                    if (currentTokens[currentToken].Token == ".")
                    {
                        currentToken++;
                        TokenBase isFunction = currentTokens[currentToken + 1];
                        ret = ParseFunctionCallOrParameterAccess(identifierOrScope);
                    }
                    else if (currentTokens[currentToken].Token == "(")
                    {
                        // Set focus again to the function name
                        --currentToken;
                        ret = ParseFunctionCallOrParameterAccess("this");
                    }
                    else if (currentTokens[currentToken].Token == "[")
                    {
                        currentToken++;
                        ASTStatement statement = ParseStatement();
                        if (statement == null)
                        {
                            throw new ParserException("Expected Statement for Parameter Access.", currentTokens[currentToken].LineNumber);
                        }
                        ret = new ASTClassParameter()
                        {
                            Scope     = identifierOrScope,
                            Parameter = statement
                        };
                    }
                    else
                    {
                        ret = new ASTIdentifier()
                        {
                            Identifier = identifierOrScope
                        };
                    }
                }
                else
                {
                    ret = new ASTIdentifier()
                    {
                        Identifier = identifierOrScope
                    };
                }
            }

            if (ret == null)
            {
                throw new ParserException(String.Format("Problems parsing the Identifier/Function Call/String/Number {0}.", currentTokens[currentToken].Token), currentTokens[currentToken].LineNumber);
            }
            return(ret);
        }
Пример #12
0
        private static void PrintNode(ASTNode node, int incident)
        {
            if (node == null)
            {
                return;
            }
            for (int i = 0; i < incident; i++)
            {
                sw.Write("\t");
            }
            if (node is ASTString)
            {
                sw.WriteLine("ASTString: " + ((ASTString)node).String.Replace("\n", "\\n"));
            }
            else if (node is ASTNumber)
            {
                sw.WriteLine("ASTNumber: " + ((ASTNumber)node).Number);
            }
            else if (node is ASTIdentifier)
            {
                sw.WriteLine("ASTIdentifier: " + ((ASTIdentifier)node).Identifier);
            }
            else if (node is ASTOperator)
            {
                ASTOperator op = (ASTOperator)node;
                sw.WriteLine("ASTOperator: " + op.Operator);
                PrintNode(op.Left, incident + 1);
                PrintNode(op.Right, incident + 1);
            }
            else if (node is ASTStatement)
            {
                ASTStatement stm = (ASTStatement)node;
                sw.WriteLine("ASTStatement: ");
                PrintNode(stm.Statement, incident + 1);
            }
            else if (node is ASTFunctionCall)
            {
                ASTFunctionCall call = (ASTFunctionCall)node;
                sw.WriteLine("ASTFunctionCall: " + call.Scope + "." + call.FunctionName);
                foreach (ASTNode param in call.Parameter)
                {
                    PrintNode(param, incident + 1);
                }
            }
            else if (node is ASTClassParameter)
            {
                ASTClassParameter classP = (ASTClassParameter)node;
                sw.WriteLine("ASTClassParameter: " + classP.Scope);
                PrintNode(classP.Parameter, incident + 1);
            }
            else if (node is ASTIf)
            {
                ASTIf ifNode = (ASTIf)node;
                sw.WriteLine("ASTIf:");
                for (int i = 0; i < incident; i++)
                {
                    sw.Write("\t");
                }
                sw.WriteLine("\tCondition:");
                PrintNode(ifNode.Condition, incident + 2);
                for (int i = 0; i < incident; i++)
                {
                    sw.Write("\t");
                }
                sw.WriteLine("\tCodeBlock:");
                foreach (ASTNode codeBlock in ifNode.CodeBlock)
                {
                    PrintNode(codeBlock, incident + 2);
                }
                if (ifNode.ElseCodeBlock != null)
                {
                    for (int i = 0; i < incident; i++)
                    {
                        sw.Write("\t");
                    }
                    sw.WriteLine("\tElse:");
                    foreach (ASTNode codeBlock in ifNode.ElseCodeBlock)
                    {
                        PrintNode(codeBlock, incident + 2);
                    }
                }
            }
            else if (node is ASTFor)
            {
                ASTFor forNode = (ASTFor)node;
                sw.WriteLine("ASTFor:");
                for (int i = 0; i < incident; i++)
                {
                    sw.Write("\t");
                }
                sw.WriteLine("\tInit:");
                PrintNode(forNode.Initialise, incident + 2);
                for (int i = 0; i < incident; i++)
                {
                    sw.Write("\t");
                }
                sw.WriteLine("\tCondition:");
                PrintNode(forNode.Condition, incident + 2);
                for (int i = 0; i < incident; i++)
                {
                    sw.Write("\t");
                }
                sw.WriteLine("\tCounter:");
                PrintNode(forNode.Count, incident + 2);
                for (int i = 0; i < incident; i++)
                {
                    sw.Write("\t");
                }
                sw.WriteLine("\tCodeBlock:");
                foreach (ASTNode codeBlock in forNode.CodeBlock)
                {
                    PrintNode(codeBlock, incident + 2);
                }
            }
            else if (node is ASTWhile)
            {
                ASTWhile wNode = (ASTWhile)node;
                sw.WriteLine("ASTWhile:");
                for (int i = 0; i < incident; i++)
                {
                    sw.Write("\t");
                }
                sw.WriteLine("\tCondition:");
                PrintNode(wNode.Condition, incident + 2);
                for (int i = 0; i < incident; i++)
                {
                    sw.Write("\t");
                }
                sw.WriteLine("\tCodeBlock:");
                foreach (ASTNode codeBlock in wNode.CodeBlock)
                {
                    PrintNode(codeBlock, incident + 2);
                }
            }
            else if (node is ASTFunction)
            {
                ASTFunction func = (ASTFunction)node;
                if (node is ASTConstructor)
                {
                    sw.WriteLine("ASTConstructor:");
                }
                else
                {
                    sw.WriteLine("ASTFunction: " + func.ReturnValue.ToString() + " " + func.Name);
                }
                for (int i = 0; i < incident; i++)
                {
                    sw.Write("\t");
                }
                sw.WriteLine("\tParameter:");
                foreach (ASTNode n in func.Parameter)
                {
                    PrintNode(n, incident + 2);
                }
                for (int i = 0; i < incident; i++)
                {
                    sw.Write("\t");
                }
                sw.WriteLine("\tCodeBlock:");
                foreach (ASTNode codeBlock in func.CodeBlock)
                {
                    PrintNode(codeBlock, incident + 2);
                }
            }
            else if (node is ASTFunctionParameter)
            {
                ASTFunctionParameter param = (ASTFunctionParameter)node;
                switch (param.Type)
                {
                case VMType.Object:
                    sw.WriteLine("Object: " + param.Name);
                    break;

                case VMType.String:
                    sw.WriteLine("String: " + param.Name);
                    break;

                case VMType.Number:
                    sw.WriteLine("Number: " + param.Name);
                    break;
                }
            }
            else if (node is ASTLocalVariable)
            {
                ASTLocalVariable param = (ASTLocalVariable)node;
                switch (param.Type)
                {
                case VMType.Object:
                    sw.WriteLine("var Object: " + param.Name);
                    break;

                case VMType.String:
                    sw.WriteLine("var String: " + param.Name);
                    break;

                case VMType.Number:
                    sw.WriteLine("var Number: " + param.Name);
                    break;
                }
            }
            else if (node is ASTReturn)
            {
                sw.WriteLine("ASTReturn:");
                PrintNode(((ASTReturn)node).Return, incident + 1);
            }
            else if (node is ASTClass)
            {
                ASTClass cNode = (ASTClass)node;
                sw.WriteLine("ASTClass: " + cNode.Name);
                sw.WriteLine("\tAttributes:");
                foreach (ASTNode n in cNode.Attributes)
                {
                    PrintNode(n, incident + 2);
                }
                sw.WriteLine("\tConstructors:");
                foreach (ASTNode n in cNode.Constructors)
                {
                    PrintNode(n, incident + 2);
                }
                sw.WriteLine("\tFunctions:");
                foreach (ASTNode n in cNode.Functions)
                {
                    PrintNode(n, incident + 2);
                }
            }
        }