Пример #1
0
        public void Visit(MainFuncNode n)
        {
            n.Table = GlobalSymbolTable.FunctionSymbolTable;

            var tableEntry = new FunctionSymbolTableEntry();

            tableEntry.Name = "main";

            foreach (var child in n.GetChildren())
            {
                child.SymTable = tableEntry;
                child.Accept(this);
            }

            var localScope = n.GetChildren().First().GetChildren().SelectMany(x => x.GetChildren()).ToList();

            for (int i = 0; i < localScope.Count; i += 3)
            {
                var paramType = localScope[i + 0].Token;
                var paramName = localScope[i + 1].Token.Lexeme;
                var arrayDims = NodeUtils.ExtractArrayDimListNode(localScope.GetCast <ArrayDimListNode>(i + 2));

                if (!CheckTypeExists(paramType.Lexeme))
                {
                    _errorStream.WriteLine($"Use of undeclared class, \"{paramType.Lexeme}\"({paramType.StartLine}:{paramType.StartColumn})");
                    Console.WriteLine($"Error: Use of undeclared class, \"{paramType.Lexeme}\"({paramType.StartLine}:{paramType.StartColumn})");
                }

                var entry = new FunctionSymbolTableEntryLocalScope()
                {
                    Type      = paramType,
                    Name      = paramName,
                    ArrayDims = arrayDims,
                };

                tableEntry.AddLocalScopeEntry(entry);
            }

            n.Table.AddEntry(tableEntry);
            n.SymTable = tableEntry;
        }
Пример #2
0
        public void Visit(FuncDefNode n)
        {
            var children = n.GetChildren();

            var tableEntry = new FunctionSymbolTableEntry();
            List <ASTNodeBase> funcParamList;
            List <ASTNodeBase> localScope;

            bool hasScopeSpec = children[1] is IdentifierNode;

            if (hasScopeSpec)
            {
                tableEntry.ScopeSpec  = children[0].Token.Lexeme;
                tableEntry.Name       = children[1].Token.Lexeme;
                funcParamList         = children[2].GetChildren();
                tableEntry.ReturnType = children[3].Token;
                localScope            = children.GetCast <FuncBodyNode>(4).GetChildren().First().GetChildren().SelectMany(x => x.GetChildren()).ToList();
            }
            else
            {
                tableEntry.Name       = children[0].Token.Lexeme;
                funcParamList         = children[1].GetChildren();
                tableEntry.ReturnType = children[2].Token;
                localScope            = children.GetCast <FuncBodyNode>(3).GetChildren().First().GetChildren().SelectMany(x => x.GetChildren()).ToList();
            }

            for (int i = 0; i < funcParamList.Count; i += 3)
            {
                var paramType = funcParamList[i + 0].Token;
                var paramName = funcParamList[i + 1].Token.Lexeme;
                var arrayDims = NodeUtils.ExtractArrayDimListNode(funcParamList.GetCast <ArrayDimListNode>(i + 2));

                var entry = new FunctionSymbolTableEntryParam()
                {
                    TypeToken = paramType,
                    Name      = paramName,
                    ArrayDims = arrayDims,
                };

                tableEntry.AddParamEntry(entry);
            }

            for (int i = 0; i < localScope.Count; i += 3)
            {
                var paramType = localScope[i + 0].Token;
                var paramName = localScope[i + 1].Token.Lexeme;
                var arrayDims = NodeUtils.ExtractArrayDimListNode(localScope.GetCast <ArrayDimListNode>(i + 2));

                if (!CheckTypeExists(paramType.Lexeme))
                {
                    _errorStream.WriteLine($"Use of undeclared class, \"{paramType.Lexeme}\"({paramType.StartLine}:{paramType.StartColumn})");
                    Console.WriteLine($"Error: Use of undeclared class, \"{paramType.Lexeme}\"({paramType.StartLine}:{paramType.StartColumn})");
                }

                var entry = new FunctionSymbolTableEntryLocalScope()
                {
                    Type      = paramType,
                    Name      = paramName,
                    ArrayDims = arrayDims,
                };

                tableEntry.AddLocalScopeEntry(entry);
            }

            n.Table = tableEntry;
            GlobalSymbolTable.FunctionSymbolTable.AddEntry(tableEntry);
        }