Beispiel #1
0
void TypeParser::TypeDefineStatement(TokenStream *lexerStream, TypeSystem *__typeSystem)  throw(ParserError)
{
    // current is `LET
    // read next
    lexerStream->next();

    // 这里指向下一个token
    TypeSpecifier(lexerStream, __typeSystem);

    lexerStream->next();

    if(lexerStream->current().value() == "as") {
        lexerStream->next();

        if(__typeSystem->isRegisterType(lexerStream->current().value())) {
            __typeSystem->registerType(lexerStream->current().value(),
                                       __typeSystem->getHelper()->takeCurrentArgumentTypeMetaData());
            __typeSystem->mapTypeName(lexerStream->current().value(),
                                      __typeSystem->getHelper()->takeFullTypeName());

        } else {
            throw ParserError(-1, "Type "+lexerStream->current().value()+" Already exist.");
        }
        TypeName(lexerStream, __typeSystem);
        lexerStream->next();
    }
}
Beispiel #2
0
// let xx<xx> as xx;
void TypeParser::TypeDefineStatement(TokenStream *lexerStream, TypeSystem *__typeSystem)  throw(ParserError)
{
    // current is `LET
    // read next
    lexerStream->next();

    // 这里指向下一个token
    TypeSpecifier(lexerStream, __typeSystem);

    lexerStream->next();

    TypeSpecifierNode* typeSpecifierNode =  dynamic_cast<TypeSpecifierNode*>(__typeSystem->nodeVar.pop());


    if(lexerStream->current().value() == "as") {
        lexerStream->next();

        if(__typeSystem->isRegisterType(lexerStream->current().value())) {
            __typeSystem->registerType(lexerStream->current().value(),
                                       __typeSystem->getHelper()->takeCurrentArgumentTypeMetaData());
            __typeSystem->mapTypeName(lexerStream->current().value(),
                                      __typeSystem->getHelper()->takeFullTypeName());



        } else {
            throw ParserError(-1, "Type "+lexerStream->current().value()+" Already exist.");
        }
        TypeName(lexerStream, __typeSystem);


        //! 语法树
        TypeNameNode* typeNameNode = __typeSystem->createTypeName();
        typeNameNode->typeName = lexerStream->current().value();

        TypeDefineNode* node = __typeSystem->createTypeDefineNode(typeSpecifierNode, typeNameNode);
        __typeSystem->nodeVar.push(node);
        // 由于忘记设计 TypeDefinesStatement 了。。。所以直接获取一条定义语句
        __typeSystem->astNode = node;

        lexerStream->next();

    }

}
Beispiel #3
0
string Parser::Parameter() {

    _message.print(DBUG, "PARSER: In Parameter()\n");

    //    TypeSpecifier, identifier, [ “[”, “]” ]

    static tokenType firstSet[] = {KW_FLOAT, KW_INT, KW_VOID, (tokenType)-1};

    static tokenType followSet[] = {SYM_COMMA, SYM_CLOSE, (tokenType) - 1};

    string type;
    string identifier;

    if ( synchronized(firstSet, followSet, "Expected Parameter") ) {

        type = TypeSpecifier();

        identifier = _lookAhead.getLexeme();

        if (_lookAhead.getTokenType() == TOK_IDENT)
            if(type != "v" && // make sure its not void type
                    !_symbolTable->define(_lookAhead.getLexeme(), type))
                _message.print(ERROR, "SEMANTIC-ANALYZER: Semantic issue on line: %i col: %i. Redifinition of '%s'", _lookAhead.getRow() , _lookAhead.getCol(), _lookAhead.getLexeme());

        if (type == "v") {
            _message.print(ERROR, "SEMANTIC-ANALYZER: Semantic issue on line: %i col: %i. Variable has incomplete type 'void'", _lookAhead.getRow() , _lookAhead.getCol());
            _symbolTable->remove(identifier);
        }

        match(TOK_IDENT);

        if ( _lookAhead.getTokenType() == SYM_SQ_OPEN ) {
            match(SYM_SQ_OPEN);
            match(SYM_SQ_CLOSE);

            if (type != "v") {
                _symbolTable->reDefine(identifier, type == "i" ? "I" : "F");
            }
        }
    }

    _message.print(DBUG, "PARSER: End of Parameter()\n");
    return type;
}
Beispiel #4
0
void TypeParser::TemplateTypeSpecifier(TokenStream *lexerStream, TypeSystem *__typeSystem)  throw(ParserError)
{
    QString templateTypeName = lexerStream->current().value();

    const int templateArgsCount = __typeSystem->templateArgsCount(templateTypeName);

    Q_ASSERT(templateArgsCount > 0);

    QVector<TypeMetaData *> thizTemplateArguments;

    __typeSystem->getHelper()->newCurrentTemplateTypeName();


    __typeSystem->getHelper()->pushTypeToken(templateTypeName);

    lexerStream->next();
    if(lexerStream->current().value() == "<") {

        __typeSystem->getHelper()->pushTypeToken(lexerStream->current().value());

        lexerStream->next();
        TypeSpecifier(lexerStream, __typeSystem);     // `, or `>,

        lexerStream->next();            // `, or `>, read next
    } else {
        throw ParserError(-1, "Template Type " + templateTypeName+ " lost `< is ");
    }

    thizTemplateArguments.push_back(__typeSystem->getHelper()->takeCurrentArgumentTypeMetaData());

    switch(templateArgsCount)
    {
    case 1: {
        if(lexerStream->current().value() != ">") {
            throw ParserError(-1, "Template Type "+
                              templateTypeName+
                              " templateArgsCount is "+templateArgsCount);
        } else {

            __typeSystem->getHelper()->pushTypeToken(lexerStream->current().value());

            break;
        }
    }       // one template type argument

    default : {
        int commaCount = 0;
        // templateArgsCount-1 个 `,
        // (,TypeSpecifier)*
        if(lexerStream->current().value() == ",") {

            __typeSystem->getHelper()->pushTypeToken(lexerStream->current().value());

            commaCount = 1;
            do {
                lexerStream->next();
                TypeSpecifier(lexerStream, __typeSystem);

                // __typeSystem->getHelper()->pushTypeToken(__typeSystem->getFullTypeName(lexerStream->current().value()));

                lexerStream->next();                // `, or `>

                commaCount++;
                if(commaCount > templateArgsCount) {
                    throw ParserError(-1, "Template Type "+
                                      templateTypeName+
                                      " templateArgsCount is "+templateArgsCount);
                }

                thizTemplateArguments.push_back(__typeSystem->getHelper()->takeCurrentArgumentTypeMetaData());

            } while(lexerStream->current().value() == ",");

            if(lexerStream->current().value() == ">") {

                __typeSystem->getHelper()->pushTypeToken(lexerStream->current().value());

                break;
            }
        }
        throw ParserError(-2, "Template Type "+
                          templateTypeName+
                          " templateArgsCount is "+templateArgsCount);

    }       // two or more templte type arguemnts
    }   // switch

    TypeMetaData* templateTypeMeta = nullptr;
    TemplateTypeMetaDataFactory* templateTypeMetaData = nullptr;
    QString thizTemplateFullTypeName = __typeSystem->getHelper()->takeCurrentTemplateFullTypeName();
    if(__typeSystem->isRegisterType(thizTemplateFullTypeName)) {
        templateTypeMetaData = __typeSystem->getTemplateTypeMetaData(templateTypeName);
        templateTypeMeta =
                templateTypeMetaData->templateTypeMetaData(thizTemplateArguments);
        __typeSystem->registerType(thizTemplateFullTypeName, templateTypeMeta);
    } else {
        templateTypeMeta = __typeSystem->getTypeMetaData(thizTemplateFullTypeName);
    }
    __typeSystem->getHelper()->pushArgumentTypeMetaData(templateTypeMeta);
    __typeSystem->getHelper()->fillTemplateArgument(thizTemplateFullTypeName);

}
Beispiel #5
0
void Parser::Declaration() {
    // repeat same typing as TranslationUnit
    _message.print(DBUG, "PARSER: In Declaration()\n");

    //  TypeSpecifier, identifier, [ “[”, integer, “]” ],
    //    { “,”, identifier, [ “[”, integer, “]” ] }, “;”

    static tokenType firstSet[] = {KW_FLOAT, KW_INT, KW_VOID, (tokenType) -1};

    static tokenType followSet[] = {TOK_EOF, KW_ELSE, SYM_CURLY_CLOSE, KW_VOID, KW_INT, KW_FLOAT, SYM_PLUS, SYM_MINUS, SYM_NOT, SYM_CURLY_OPEN, KW_IF, KW_WHILE, KW_RETURN, SYM_OPEN, LIT_INT, LIT_FLOAT, LIT_STR, TOK_IDENT, (tokenType) - 1};

    string type;
    string identifier;

    if ( synchronized(firstSet, followSet, "Expected Declaration") ) {

        type = TypeSpecifier();
        identifier = _lookAhead.getLexeme();

        if (_lookAhead.getTokenType() == TOK_IDENT)
            if(type != "v" &&
                    !_symbolTable->define(_lookAhead.getLexeme(), type))
                _message.print(ERROR, "SEMANTIC-ANALYZER: Semantic issue on line: %i col: %i. Redifinition of '%s'", _lookAhead.getRow() , _lookAhead.getCol(), identifier.c_str());

        if (type == "v") {
            _message.print(ERROR, "SEMANTIC-ANALYZER: Semantic issue on line: %i col: %i. Variable has incomplete type 'void'", _lookAhead.getRow() , _lookAhead.getCol());
        }

        match(TOK_IDENT);

        if ( _lookAhead.getTokenType() == SYM_SQ_OPEN ) {

            match(SYM_SQ_OPEN);
            match(LIT_INT);
            match(SYM_SQ_CLOSE);

            if (type != "v") {
                _symbolTable->reDefine(identifier, type == "i" ? "I" : "F");
            }
        }

        while ( _lookAhead.getTokenType() == SYM_COMMA ) {

            match(SYM_COMMA);

            identifier = _lookAhead.getLexeme();

            if (_lookAhead.getTokenType() == TOK_IDENT)
                if(type != "v" &&
                        !_symbolTable->define(_lookAhead.getLexeme(), type))
                    _message.print(ERROR, "SEMANTIC-ANALYZER: Semantic issue on line: %i col: %i. Redifinition of '%s'", _lookAhead.getRow() , _lookAhead.getCol(), identifier.c_str());

            match(TOK_IDENT);

            if ( _lookAhead.getTokenType() == SYM_SQ_OPEN ) {

                match(SYM_SQ_OPEN);
                match(LIT_INT);
                match(SYM_SQ_CLOSE);
                if (type != "v") {
                    _symbolTable->reDefine(identifier, type == "i" ? "I" : "F");
                }
            }
        }

        match(SYM_SEMICOLON);
    }
    _message.print(DBUG, "PARSER: End of Declaration()\n");
}
Beispiel #6
0
void Parser::TranslationUnit() {

    _message.print(DBUG, "PARSER: In TranslationUnit()\n");

    // fill with tokens, -1 must be the last one!
    static tokenType translationUnitFirstSet[] = {KW_EXTERN, KW_FLOAT, KW_INT, KW_VOID, (tokenType) - 1 };

    static tokenType parameterFirstSet[] = {KW_FLOAT, KW_INT, KW_VOID, (tokenType) - 1 };

    static tokenType followSet[] = {TOK_EOF, (tokenType) - 1 };

    // grammar rule
    //    { [ “extern” ] TypeSpecifier, identifier,
    //        ( [ “[”, integer, “]”],
    //        { “,”, identifier, [ “[”, integer, “]” ] }, “;”
    //         | “(”, [ Parameter, { “,”, Parameter } ], “)”,
    //         CompoundStatement
    //         )
    //    }

    bool externDef = false; // extern keyword protection
    string type; // identifier type information container
    string identifier; // identifier attribute for functions
    while ( synchronized(translationUnitFirstSet, followSet, "Expected TranslationUnit") ) {

        if ( _lookAhead.getTokenType() == KW_EXTERN ) {
            match(KW_EXTERN);
            externDef = true;
        }

        type = TypeSpecifier();

        identifier = _lookAhead.getLexeme();

        if (_lookAhead.getTokenType() == TOK_IDENT)
            if(!_symbolTable->define(_lookAhead.getLexeme(), type))
                _message.print(ERROR, "SEMANTIC-ANALYZER: Semantic issue on line: %i col: %i. Redifinition of '%s'", _lookAhead.getRow() , _lookAhead.getCol(), _lookAhead.getLexeme());

        match(TOK_IDENT);
        if( _lookAhead.getTokenType() == SYM_SQ_OPEN ||
                _lookAhead.getTokenType() == SYM_COMMA ||
                _lookAhead.getTokenType() == SYM_SEMICOLON ) {  // VARIABLE DECLARATION

            if (type == "v") {
                _message.print(ERROR, "SEMANTIC-ANALYZER: Semantic issue on line: %i col: %i. Variable has incomplete type 'void'", _lookAhead.getRow() , _lookAhead.getCol());
                _symbolTable->remove(identifier);
            }

            if ( _lookAhead.getTokenType() == SYM_SQ_OPEN ) {  // ARRAY

                match(SYM_SQ_OPEN);
                match(LIT_INT);
                if (_lookAhead.getTokenType() == SYM_SQ_CLOSE) {
                    match(SYM_SQ_CLOSE); // MUST MATCH SQUARE BRACKET CLOSE
                }

                if (type != "v") {
                    _symbolTable->reDefine(identifier, type == "i" ? "I" : "F");
                }
            }

            while ( _lookAhead.getTokenType() == SYM_COMMA ) {

                match(SYM_COMMA);

                identifier = _lookAhead.getLexeme();

                if (_lookAhead.getTokenType() == TOK_IDENT)
                    if(type != "v" &&
                            !_symbolTable->define(_lookAhead.getLexeme(), type))
                        _message.print(ERROR, "SEMANTIC-ANALYZER: Semantic issue on line: %i col: %i. Redifinition of '%s'", _lookAhead.getRow() , _lookAhead.getCol(), _lookAhead.getLexeme());

                match(TOK_IDENT);

                if( _lookAhead.getTokenType() == SYM_SQ_OPEN ) {
                    match(SYM_SQ_OPEN);
                    match(LIT_INT);
                    if (_lookAhead.getTokenType() == SYM_SQ_CLOSE) {
                        match(SYM_SQ_CLOSE);
                    }

                    if (type != "v") {
                        _symbolTable->reDefine(identifier, type == "i" ? "I" : "F");
                    }
                }
            }

            match(SYM_SEMICOLON);

        } else if ( _lookAhead.getTokenType() == SYM_OPEN ) { // FUNCTION DECLARATION OR DEFINITION

            _symbolTable->openScope();

            match(SYM_OPEN);

            if ( memberOf(_lookAhead.getTokenType(), parameterFirstSet) ) {

                type += Parameter();

                while( _lookAhead.getTokenType() == SYM_COMMA ) {
                    match(SYM_COMMA);
                    type += Parameter();
                }

            } else {
                type += "v";
            }

            match(SYM_CLOSE);

            _symbolTable->reDefine(identifier, type);

            if ( _lookAhead.getTokenType() == SYM_SEMICOLON )
                match(SYM_SEMICOLON); // FUNCTION DECLARATION
            else {
                if (externDef) {
                    _message.print(ERROR, "SEMANTIC-ANALYZER: Semantic issue on line: %i col: %i. Function defition can not be of 'extern' type", _lookAhead.getRow() , _lookAhead.getCol());
                }
                CompoundStatement(identifier); // FUNCTION DEFINITION
            }
//            _symbolTable->dump();
            _symbolTable->closeScope();
        }
    }

    _message.print(DBUG, "PARSER: End of TranslationUnit()\n");
}