diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 70017c8..c0b95d2 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -20,6 +20,7 @@ add_executable(sysyc LLVMIRGenerator.cpp ) target_include_directories(sysyc PRIVATE ${CMAKE_CURRENT_BINARY_DIR}) +target_compile_options(sysyc PRIVATE -frtti) target_link_libraries(sysyc PRIVATE SysYParser) # set(THREADS_PREFER_PTHREAD_FLAG ON) diff --git a/src/LLVMIRGenerator.cpp b/src/LLVMIRGenerator.cpp index 32c4a23..7c1419d 100644 --- a/src/LLVMIRGenerator.cpp +++ b/src/LLVMIRGenerator.cpp @@ -219,9 +219,13 @@ std::any LLVMIRGenerator::visitBlockStmt(SysYParser::BlockStmtContext* ctx) { } std::any LLVMIRGenerator::visitAssignStmt(SysYParser::AssignStmtContext *ctx) { + irStream << "|||Start "; std::string lhsAlloca = std::any_cast(ctx->lValue()->accept(this)); + irStream << "End||| \n"; std::string lhsType = symbolTable[ctx->lValue()->Ident()->getText()].second; + irStream << "[[[Start "; std::string rhs = std::any_cast(ctx->exp()->accept(this)); + irStream << "End]]] \n"; if (lhsType == "float") { try { @@ -397,14 +401,7 @@ std::any LLVMIRGenerator::visitReturnStmt(SysYParser::ReturnStmtContext *ctx) std::any LLVMIRGenerator::visitLValue(SysYParser::LValueContext* ctx) { std::string varName = ctx->Ident()->getText(); - std::string allocaPtr = symbolTable[varName].first; - std::string type = symbolTable[varName].second; - std::string temp = getNextTemp(); - irStream << " " << temp << " = load " << type << ", " << type << "* " << allocaPtr << ", align 4\n"; - tmpTable[temp] = type; - return temp; - // std::string varName = ctx->Ident()->getText(); - // return symbolTable[varName].first; + return symbolTable[varName].first; } // std::any LLVMIRGenerator::visitPrimaryExp(SysYParser::PrimaryExpContext* ctx) { @@ -423,8 +420,36 @@ std::any LLVMIRGenerator::visitLValue(SysYParser::LValueContext* ctx) { // } // } -std::any LLVMIRGenerator::visitPrimExp(SysYParser::PrimaryExpContext* ctx) { - return visitChildren(ctx); + +std::any LLVMIRGenerator::visitPrimExp(SysYParser::PrimExpContext *ctx){ + std::cout << "Type name: " << typeid(*ctx).name() << std::endl; + irStream << " PrimExp "; + if (auto *lvalCtx = dynamic_cast(ctx)) { + // 是 LValContext,可以安全地调用 lValue() + return visit(lvalCtx->lValue()); + } + return visitChildren(ctx); +} + +std::any LLVMIRGenerator::visitPrimaryExp(SysYParser::PrimaryExpContext* ctx) { + irStream << " Primaryexp \n"; + if (auto *lvalCtx = dynamic_cast(ctx)) { + std::string allocaPtr = std::any_cast(lvalCtx->lValue()->accept(this)); + std::string varName = lvalCtx->lValue()->Ident()->getText(); + std::string type = symbolTable[varName].second; + std::string temp = getNextTemp(); + irStream << " " << temp << " = load " << type << ", " << type << "* " << allocaPtr << ", align 4\n"; + tmpTable[temp] = type; + return temp; + } else if (auto *numCtx = dynamic_cast(ctx)) { + return numCtx->number()->accept(this); + } else if (auto *strCtx = dynamic_cast(ctx)) { + return strCtx->string()->accept(this); + } +} + +std::any LLVMIRGenerator::visitParenExp(SysYParser::ParenExpContext* ctx) { + return ctx->exp()->accept(this); } std::any LLVMIRGenerator::visitNumber(SysYParser::NumberContext* ctx) { @@ -436,6 +461,29 @@ std::any LLVMIRGenerator::visitNumber(SysYParser::NumberContext* ctx) { return ""; } +std::any LLVMIRGenerator::visitString(SysYParser::StringContext *ctx) +{ + if (ctx->STRING()) { + // 处理字符串常量 + std::string str = ctx->STRING()->getText(); + // 去掉引号 + str = str.substr(1, str.size() - 2); + // 转义处理 + std::string escapedStr; + for (char c : str) { + if (c == '\\') { + escapedStr += "\\\\"; + } else if (c == '"') { + escapedStr += "\\\""; + } else { + escapedStr += c; + } + } + return "\"" + escapedStr + "\""; + } + return ctx->STRING()->getText(); +} + std::any LLVMIRGenerator::visitUnExp(SysYParser::UnExpContext* ctx) { if (ctx->unaryOp()) { std::string operand = std::any_cast(ctx->unaryExp()->accept(this)); diff --git a/src/LLVMIRGenerator.h b/src/LLVMIRGenerator.h index a02419f..2d3aada 100644 --- a/src/LLVMIRGenerator.h +++ b/src/LLVMIRGenerator.h @@ -43,8 +43,11 @@ private: std::any visitBlockStmt(SysYParser::BlockStmtContext* ctx); // std::any visitStmt(SysYParser::StmtContext* ctx); std::any visitLValue(SysYParser::LValueContext* ctx); - std::any visitPrimExp(SysYParser::PrimaryExpContext* ctx); + std::any visitPrimaryExp(SysYParser::PrimaryExpContext* ctx); + std::any visitPrimExp(SysYParser::PrimExpContext* ctx); + std::any visitParenExp(SysYParser::ParenExpContext* ctx); std::any visitNumber(SysYParser::NumberContext* ctx); + std::any visitString(SysYParser::StringContext* ctx); std::any visitCall(SysYParser::CallContext *ctx); std::any visitUnExp(SysYParser::UnExpContext* ctx); std::any visitMulExp(SysYParser::MulExpContext* ctx);