From dbc4a22d3c8c4189459f0361cb9da06415ec2dc9 Mon Sep 17 00:00:00 2001 From: Patrick Schönberger Date: Wed, 4 Aug 2021 14:51:23 +0200 Subject: pre change --- src/check.h | 12 +- src/main.cpp | 21 ++- src/repr.h | 134 +++++++++++------ src/repr_get.h | 456 ++++++++++++++++++++++++++------------------------------- src/toc.h | 190 +++++++++++++++--------- 5 files changed, 435 insertions(+), 378 deletions(-) (limited to 'src') diff --git a/src/check.h b/src/check.h index d85bd81..091b646 100644 --- a/src/check.h +++ b/src/check.h @@ -4,8 +4,7 @@ bool checkStmt( const Stmt & s, - std::vector structs, - std::vector funcs, + std::vector namespaces, std::vector vars) { return true; @@ -13,15 +12,14 @@ bool checkStmt( bool checkFunction( const Function & f, - std::vector structs, - std::vector funcs, + std::vector namespaces, std::vector vars) { vars.insert(vars.end(), f.parameters.begin(), f.parameters.end()); vars.insert(vars.end(), f.body.variables.begin(), f.body.variables.end()); for (auto s : f.body.statements) { - if (!checkStmt(s, structs, funcs, vars)) + if (!checkStmt(s, namespaces, vars)) return false; } return true; @@ -31,7 +29,7 @@ bool checkProgram(const Program & p) { for (auto f : p.functions) { - if (!checkFunction(f, p.structs, p.functions, p.variables)) + if (!checkFunction(f, p.namespaces, p.variables)) return false; } for (auto s : p.structs) @@ -41,7 +39,7 @@ bool checkProgram(const Program & p) vars.push_back(v); for (auto f : s.methods) { - if (!checkFunction(f, p.structs, p.functions, vars)) + if (!checkFunction(f, p.namespaces, vars)) return false; } } diff --git a/src/main.cpp b/src/main.cpp index 4c78f5b..19b35f3 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -14,7 +14,7 @@ using namespace antlr4; int main(int argc, const char * argv[]) { - std::ifstream ifs("test.toc"); + std::ifstream ifs("test/test2.toc"); ANTLRInputStream input(ifs); @@ -37,14 +37,21 @@ int main(int argc, const char * argv[]) Program prg = getProgram(prog); - tocProgram(std::cout, prg); + try + { + tocProgram(std::cout, prg); - if (!checkProgram(prg)) - std::cerr << "Error" << std::endl; + if (!checkProgram(prg)) + std::cerr << "Error" << std::endl; - //std::ofstream ofs("output.c"); - //tocProg(ofs, prg); - //ofs.close(); + std::ofstream ofs("output.c"); + tocProgram(ofs, prg); + ofs.close(); + } + catch (const std::string & e) + { + std::cerr << "Error: " << e << std::endl; + } return 0; } \ No newline at end of file diff --git a/src/repr.h b/src/repr.h index 47a78d7..f196427 100644 --- a/src/repr.h +++ b/src/repr.h @@ -13,18 +13,22 @@ struct Variable; struct Body; struct Function; struct Struct; +struct Namespace; struct Program; + struct FuncExpr; +struct MethodExpr; struct LitExpr; -struct IdentifierExpr; -struct AccessExpr; -struct BracketsExpr; -struct UnaryOperatorExpr; +struct ParenExpr; +struct DotExpr; +struct PrefixOperatorExpr; +struct PostfixOperatorExpr; struct BinaryOperatorExpr; struct TernaryOperatorExpr; -struct DotExpr; -struct ParenExpr; +struct BracketsExpr; +struct IdentifierExpr; struct Expr; + struct IfStmt; struct SwitchStmt; struct ForStmt; @@ -48,6 +52,7 @@ struct TypeModifier struct Type { + std::vector namespacePrefixes; std::string name; std::vector modifiers; }; @@ -72,11 +77,28 @@ struct Function Body body; }; +template +struct StructMember +{ + T t; + bool isPublic; + operator T() { return t; } +}; + struct Struct { std::string name; - std::vector members; - std::vector methods; + std::vector> members; + std::vector> methods; +}; + +struct Namespace +{ + std::string name; + std::vector variables; + std::vector structs; + std::vector functions; + std::vector namespaces; }; struct Program @@ -84,19 +106,28 @@ struct Program std::vector variables; std::vector structs; std::vector functions; + std::vector namespaces; }; enum class ExprType { - Func, Lit, Identifier, Brackets, UnaryOperator, BinaryOperator, TernaryOperator, Dot + Func, Method, Lit, Paren, Dot, PrefixOp, PostfixOp, BinaryOp, TernaryOp, Bracket, Identifier }; struct FuncExpr { + std::vector namespacePrefixes; std::string functionName; std::vector arguments; }; +struct MethodExpr +{ + std::shared_ptr expr; + std::string methodName; + std::vector arguments; +}; + enum class LitType { Int, Decimal, String, Bool @@ -112,24 +143,47 @@ struct LitExpr bool _bool; }; -// TODO: accessExpr -struct IdentifierExpr +struct ParenExpr { - std::string name; + std::shared_ptr expr; }; -struct BracketsExpr +struct DotExpr { - std::shared_ptr lexpr; - std::shared_ptr rexpr; + std::shared_ptr expr; + std::string identifier; }; -enum class UnaryOperatorType +enum class PrefixOperatorType { - Plus, Minus, IncrementPre, DecrementPre, IncrementPost, DecrementPost, + Plus, Minus, Increment, Decrement, LogicalNot, BitwiseNot, Dereference, AddressOf, COUNT }; +static std::string PrefixOperatorTypeStrings[] = +{ + "+", "-", "++", "--", "!", "~", "*", "&" }; + +struct PrefixOperatorExpr +{ + PrefixOperatorType type; + std::shared_ptr expr; +}; + +enum class PostfixOperatorType +{ + Increment, Decrement, + COUNT +}; +static std::string PostfixOperatorTypeStrings[] = +{ + "++", "--" }; + +struct PostfixOperatorExpr +{ + PostfixOperatorType type; + std::shared_ptr expr; +}; enum class BinaryOperatorType { @@ -139,10 +193,6 @@ enum class BinaryOperatorType LeftShiftEquals, RightShiftEquals, COUNT }; -static std::string UnaryOperatorTypeStrings[] = -{ - "+", "-", "++", "--", "++", "--", "!", "~", "*", "&" }; - static std::string BinaryOperatorTypeStrings[] = { "+", "-", "*", "/", "%", "&", "|", "^", "<", ">", @@ -150,12 +200,6 @@ static std::string BinaryOperatorTypeStrings[] = "+=","-=","*=","/=","%=", "<<=",">>=" }; -struct UnaryOperatorExpr -{ - UnaryOperatorType type; - std::shared_ptr expr; -}; - struct BinaryOperatorExpr { BinaryOperatorType type; @@ -170,27 +214,33 @@ struct TernaryOperatorExpr std::shared_ptr rexprFalse; }; -struct DotExpr +struct BracketsExpr { - std::shared_ptr expr; - IdentifierExpr ident; + std::shared_ptr lexpr; + std::shared_ptr rexpr; +}; + +struct IdentifierExpr +{ + std::vector namespacePrefixes; + std::string identifier; }; -// TODO: paren expr struct Expr { ExprType type; - bool parenthesized; - FuncExpr _func; + MethodExpr _method; LitExpr _lit; - IdentifierExpr _identifier; - BracketsExpr _brackets; - UnaryOperatorExpr _unaryOperator; - BinaryOperatorExpr _binaryOperator; - TernaryOperatorExpr _ternaryOperator; + ParenExpr _paren; DotExpr _dot; + PrefixOperatorExpr _prefixOp; + PostfixOperatorExpr _postfixOp; + BinaryOperatorExpr _binaryOp; + TernaryOperatorExpr _ternaryOp; + BracketsExpr _brackets; + IdentifierExpr _identifier; }; enum class StmtType @@ -219,15 +269,14 @@ struct SwitchCase struct SwitchStmt { - IdentifierExpr ident; + std::shared_ptr ident; std::vector cases; }; // TODO: int i = 0 (var decl) struct ForStmt { - std::string varName; - std::shared_ptr initValue; + std::shared_ptr init; std::shared_ptr condition; std::shared_ptr action; Body body; @@ -241,8 +290,7 @@ struct WhileStmt struct AssignStmt { - std::string name; - Expr expr; + Expr lexpr, rexpr; }; struct ReturnStmt diff --git a/src/repr_get.h b/src/repr_get.h index 118d7b3..54aea6f 100644 --- a/src/repr_get.h +++ b/src/repr_get.h @@ -7,20 +7,30 @@ Variable getVariable(TocParser::VarContext * ctx); Body getBody(TocParser::BodyContext * ctx); Function getFunction(TocParser::FuncContext * ctx); Struct getStruct(TocParser::StructDeclContext * ctx); +Namespace getNamespace(TocParser::NamespaceDeclContext * ctx); Program getProgram(TocParser::ProgContext * ctx); -UnaryOperatorType getUnaryOperatorType(const std::string & s); -BinaryOperatorType getBinaryOperatorType(const std::string & s); -UnaryOperatorExpr getUnaryOperatorExpr(TocParser::OpExprContext * ctx); -BinaryOperatorExpr getBinaryOperatorExpr(TocParser::OpExprContext * ctx); -TernaryOperatorExpr getTernaryOperatorExpr(TocParser::OpExprContext * ctx); -Expr getExpr(TocParser::NonOpExprContext * ctx); -Expr getExpr(TocParser::NonAccessExprContext * ctx); + + +Expr getExpr(TocParser::FuncExprContext * ctx); +Expr getExpr(TocParser::MethodExprContext * ctx); +Expr getExpr(TocParser::LitExprContext * ctx); +Expr getExpr(TocParser::ParenExprContext * ctx); +Expr getExpr(TocParser::DotExprContext * ctx); +Expr getExpr(TocParser::PrefixOpExprContext * ctx); +Expr getExpr(TocParser::PostfixOpExprContext * ctx); +Expr getExpr(TocParser::BinaryOpExprContext * ctx); +Expr getExpr(TocParser::TernaryOpExprContext * ctx); +Expr getExpr(TocParser::BracketExprContext * ctx); +Expr getExpr(TocParser::IdentifierExprContext * ctx); Expr getExpr(TocParser::ExprContext * ctx); + Stmt getStmt(TocParser::StmtContext * ctx); Type getType(TocParser::TypeContext * ctx) { Type result; + for (auto n : ctx->namespaceSpecifier()) + result.namespacePrefixes.push_back(n->typeName()->getText()); result.name = ctx->typeName()->NAME()->toString(); for (auto m : ctx->typeModifier()) { @@ -81,18 +91,25 @@ Struct getStruct(TocParser::StructDeclContext * ctx) { if (m->structVar() != nullptr) { - result.members.push_back(getVariable(m->structVar()->var())); + result.members.push_back({ + getVariable(m->structVar()->var()), + m->privateDecl() != nullptr + }); } if (m->structMethod() != nullptr) { - result.methods.push_back(getFunction(m->structMethod()->func())); + result.methods.push_back({ + getFunction(m->structMethod()->func()), + m->privateDecl() != nullptr + }); } } return result; } -Program getProgram(TocParser::ProgContext * ctx) +Namespace getNamespace(TocParser::NamespaceDeclContext * ctx) { - Program result; + Namespace result; + result.name = ctx->typeName()->getText(); for (auto d : ctx->decl()) { if (d->varDecl() != nullptr) @@ -107,277 +124,217 @@ Program getProgram(TocParser::ProgContext * ctx) { result.structs.push_back(getStruct(d->structDecl())); } + if (d->namespaceDecl() != nullptr) + { + result.namespaces.push_back(getNamespace(d->namespaceDecl())); + } } return result; } -UnaryOperatorType getUnaryOperatorType(const std::string & s) +Program getProgram(TocParser::ProgContext * ctx) { - for (int i = 0; i < (int)UnaryOperatorType::COUNT; i++) + Program result; + for (auto d : ctx->decl()) { - if (UnaryOperatorTypeStrings[i] == s) + if (d->varDecl() != nullptr) { - return (UnaryOperatorType)i; + result.variables.push_back(getVariable(d->varDecl()->var())); + } + if (d->funcDecl() != nullptr) + { + result.functions.push_back(getFunction(d->funcDecl()->func())); + } + if (d->structDecl() != nullptr) + { + result.structs.push_back(getStruct(d->structDecl())); + } + if (d->namespaceDecl() != nullptr) + { + result.namespaces.push_back(getNamespace(d->namespaceDecl())); } } - return UnaryOperatorType::COUNT; + return result; } -BinaryOperatorType getBinaryOperatorType(const std::string & s) +template +OpType getOperatorType(const std::string & s, std::string typeStrings[]) { - for (int i = 0; i < (int)BinaryOperatorType::COUNT; i++) + for (int i = 0; i < (int)OpType::COUNT; i++) { - if (BinaryOperatorTypeStrings[i] == s) + if (typeStrings[i] == s) { - return (BinaryOperatorType)i; + return (OpType)i; } } - return BinaryOperatorType::COUNT; + return OpType::COUNT; } -UnaryOperatorExpr getUnaryOperatorExpr(TocParser::OpExprContext * ctx) -{ - UnaryOperatorExpr result; - if (ctx->prefixOp() != nullptr) - result.expr = std::make_unique(getExpr(ctx->prefixOp()->nonOpExpr())); - else - result.expr = std::make_unique(getExpr(ctx->postfixOp()->nonOpExpr())); - std::string op; - if (ctx->prefixOp() != nullptr) - op = ctx->prefixOp()->prefix_op()->getText(); - else - op = ctx->postfixOp()->postfix_op()->getText(); - // TODO: postfix type - result.type = getUnaryOperatorType(op); - return result; -} -BinaryOperatorExpr getBinaryOperatorExpr(TocParser::OpExprContext * ctx) -{ - BinaryOperatorExpr result; - result.lexpr = std::make_unique(getExpr(ctx->binaryOp()->nonOpExpr(0))); - result.rexpr = std::make_unique(getExpr(ctx->binaryOp()->nonOpExpr(1))); - - std::string op = ctx->binaryOp()->binary_op(0)->getText(); - result.type = getBinaryOperatorType(op); + + + + + + + +Expr getExpr(TocParser::FuncExprContext * ctx) +{ + Expr result; + result.type = ExprType::Func; + for (auto n : ctx->namespaceSpecifier()) + result._func.namespacePrefixes.push_back(n->typeName()->getText()); + result._func.functionName = ctx->funcName()->NAME()->toString(); + for (auto e : ctx->expr()) + result._func.arguments.push_back(getExpr(e)); return result; } -TernaryOperatorExpr getTernaryOperatorExpr(TocParser::OpExprContext * ctx) +Expr getExpr(TocParser::MethodExprContext * ctx) { - TernaryOperatorExpr result; - result.lexpr = std::make_unique(getExpr(ctx->ternaryOp()->nonOpExpr())); - result.rexprTrue = std::make_unique(getExpr(ctx->ternaryOp()->expr(0))); - result.rexprFalse = std::make_unique(getExpr(ctx->ternaryOp()->expr(1))); + Expr result; + result.type = ExprType::Method; + result._method.expr = std::make_unique(getExpr(ctx->expr(0))); + result._method.methodName = ctx->funcName()->NAME()->toString(); + for (int i = 1; i < ctx->expr().size(); i++) + result._method.arguments.push_back(getExpr(ctx->expr(i))); return result; } -Expr getExpr(TocParser::NonOpExprContext * ctx) +Expr getExpr(TocParser::LitExprContext * ctx) { Expr result; - result.parenthesized = false; - if (ctx->funcExpr() != nullptr) + result.type = ExprType::Lit; + if (ctx->literal()->INT_LIT() != nullptr) { - result.type = ExprType::Func; - result._func.functionName = ctx->funcExpr()->funcName()->NAME()->toString(); - for (auto e : ctx->funcExpr()->expr()) - result._func.arguments.push_back(getExpr(e)); + result._lit.type = LitType::Int; + result._lit._int = atoi(ctx->literal()->INT_LIT()->toString().c_str()); } - if (ctx->litExpr() != nullptr) + else if (ctx->literal()->DECIMAL_LIT() != nullptr) { - result.type = ExprType::Lit; - if (ctx->litExpr()->INT_LIT() != nullptr) - { - result._lit.type = LitType::Int; - result._lit._int = atoi(ctx->litExpr()->INT_LIT()->toString().c_str()); - } - else if (ctx->litExpr()->DECIMAL_LIT() != nullptr) - { - result._lit.type = LitType::Decimal; - result._lit._decimal = atof(ctx->litExpr()->DECIMAL_LIT()->toString().c_str()); - } - else if (ctx->litExpr()->STRING_LIT() != nullptr) - { - result._lit.type = LitType::String; - result._lit._string = ctx->litExpr()->STRING_LIT()->toString(); - } - else if (ctx->litExpr()->BOOL_LIT() != nullptr) - { - result._lit.type = LitType::Bool; - result._lit._bool = ctx->litExpr()->BOOL_LIT()->toString() == "true"; - } - } - if (ctx->identifierExpr() != nullptr) - { - result.type = ExprType::Identifier; - result._identifier.name = ctx->identifierExpr()->varName()->NAME()->toString(); + result._lit.type = LitType::Decimal; + result._lit._decimal = atof(ctx->literal()->DECIMAL_LIT()->toString().c_str()); } - if (ctx->parenExpr() != nullptr) + else if (ctx->literal()->STRING_LIT() != nullptr) { - result = getExpr(ctx->parenExpr()->expr()); - result.parenthesized = true; + result._lit.type = LitType::String; + result._lit._string = ctx->literal()->STRING_LIT()->toString(); } - if (ctx->accessExpr() != nullptr) + else if (ctx->literal()->BOOL_LIT() != nullptr) { - auto firstSub = ctx->accessExpr()->accessSubExpr(0); - if (firstSub->accessMember() != nullptr) - { - result.type = ExprType::Dot; - result._dot.expr = std::make_unique(getExpr(ctx->accessExpr()->nonAccessExpr())); - result._dot.ident.name = firstSub->accessMember()->identifierExpr()->varName()->NAME()->toString(); - } - else - { - result.type = ExprType::Brackets; - result._brackets.lexpr = std::make_unique(getExpr(ctx->accessExpr()->nonAccessExpr())); - result._brackets.rexpr = std::make_unique(getExpr(firstSub->accessBrackets()->expr())); - } - for (int i = 1; i < ctx->accessExpr()->accessSubExpr().size(); i++) - { - Expr tmp = result; - auto sub = ctx->accessExpr()->accessSubExpr(i); - if (sub->accessMember() != nullptr) - { - result.type = ExprType::Dot; - result._dot.expr = std::make_unique(tmp); - result._dot.ident.name = sub->accessMember()->identifierExpr()->varName()->NAME()->toString(); - } - else - { - result.type = ExprType::Brackets; - result._brackets.lexpr = std::make_unique(tmp); - result._brackets.rexpr = std::make_unique(getExpr(sub->accessBrackets()->expr())); - } - } + result._lit.type = LitType::Bool; + result._lit._bool = ctx->literal()->BOOL_LIT()->toString() == "true"; } return result; } -Expr getExpr(TocParser::NonAccessExprContext * ctx) +Expr getExpr(TocParser::ParenExprContext * ctx) { Expr result; - result.parenthesized = false; - if (ctx->funcExpr() != nullptr) - { - result.type = ExprType::Func; - result._func.functionName = ctx->funcExpr()->funcName()->NAME()->toString(); - for (auto e : ctx->funcExpr()->expr()) - result._func.arguments.push_back(getExpr(e)); - } - if (ctx->identifierExpr() != nullptr) - { - result.type = ExprType::Identifier; - result._identifier.name = ctx->identifierExpr()->varName()->NAME()->toString(); - } - if (ctx->parenExpr() != nullptr) - { - result = getExpr(ctx->parenExpr()->expr()); - result.parenthesized = true; - } + result.type = ExprType::Paren; + result._paren.expr = std::make_unique(getExpr(ctx->expr())); return result; } +Expr getExpr(TocParser::DotExprContext * ctx) +{ + Expr result; + result.type = ExprType::Dot; + result._dot.expr = std::make_unique(getExpr(ctx->expr())); + result._dot.identifier = ctx->varName()->getText(); + return result; +} +Expr getExpr(TocParser::PrefixOpExprContext * ctx) +{ + Expr result; + result.type = ExprType::PrefixOp; + result._prefixOp.expr = std::make_unique(getExpr(ctx->expr())); + result._prefixOp.type = getOperatorType( + ctx->prefix_op()->getText(), + PrefixOperatorTypeStrings); + return result; +} +Expr getExpr(TocParser::PostfixOpExprContext * ctx) +{ + Expr result; + result.type = ExprType::PostfixOp; + result._postfixOp.expr = std::make_unique(getExpr(ctx->expr())); + result._postfixOp.type = getOperatorType( + ctx->postfix_op()->getText(), + PostfixOperatorTypeStrings); + return result; +} +Expr getExpr(TocParser::BinaryOpExprContext * ctx) +{ + Expr result; + result.type = ExprType::BinaryOp; + result._binaryOp.lexpr = std::make_unique(getExpr(ctx->expr(0))); + result._binaryOp.rexpr = std::make_unique(getExpr(ctx->expr(1))); + result._binaryOp.type = getOperatorType( + ctx->binary_op()->getText(), + BinaryOperatorTypeStrings); + return result; +} +Expr getExpr(TocParser::TernaryOpExprContext * ctx) +{ + Expr result; + result.type = ExprType::TernaryOp; + result._ternaryOp.lexpr = std::make_unique(getExpr(ctx->expr(0))); + result._ternaryOp.rexprTrue = std::make_unique(getExpr(ctx->expr(1))); + result._ternaryOp.rexprFalse = std::make_unique(getExpr(ctx->expr(2))); + return result; +} +Expr getExpr(TocParser::BracketExprContext * ctx) +{ + Expr result; + result.type = ExprType::Bracket; + result._brackets.lexpr = std::make_unique(getExpr(ctx->expr(0))); + result._brackets.rexpr = std::make_unique(getExpr(ctx->expr(1))); + return result; +} +Expr getExpr(TocParser::IdentifierExprContext * ctx) +{ + Expr result; + result.type = ExprType::Identifier; + for (auto n : ctx->namespaceSpecifier()) + result._identifier.namespacePrefixes.push_back(n->typeName()->getText()); + result._identifier.identifier = ctx->varName()->getText(); + return result; +} + + + + + + + + + + + Expr getExpr(TocParser::ExprContext * ctx) { Expr result; - result.parenthesized = false; - if (ctx->funcExpr() != nullptr) - { - result.type = ExprType::Func; - result._func.functionName = ctx->funcExpr()->funcName()->NAME()->toString(); - for (auto e : ctx->funcExpr()->expr()) - result._func.arguments.push_back(getExpr(e)); - } - if (ctx->litExpr() != nullptr) - { - result.type = ExprType::Lit; - if (ctx->litExpr()->INT_LIT() != nullptr) - { - result._lit.type = LitType::Int; - result._lit._int = atoi(ctx->litExpr()->INT_LIT()->toString().c_str()); - } - else if (ctx->litExpr()->DECIMAL_LIT() != nullptr) - { - result._lit.type = LitType::Decimal; - result._lit._decimal = atof(ctx->litExpr()->DECIMAL_LIT()->toString().c_str()); - } - else if (ctx->litExpr()->STRING_LIT() != nullptr) - { - result._lit.type = LitType::String; - result._lit._string = ctx->litExpr()->STRING_LIT()->toString(); - } - else if (ctx->litExpr()->BOOL_LIT() != nullptr) - { - result._lit.type = LitType::Bool; - result._lit._bool = ctx->litExpr()->BOOL_LIT()->toString() == "true"; - } - } - if (ctx->identifierExpr() != nullptr) - { - result.type = ExprType::Identifier; - result._identifier.name = ctx->identifierExpr()->varName()->NAME()->toString(); - } - if (ctx->parenExpr() != nullptr) - { - result = getExpr(ctx->parenExpr()->expr()); - result.parenthesized = true; - } - if (ctx->accessExpr() != nullptr) - { - auto firstSub = ctx->accessExpr()->accessSubExpr(0); - if (firstSub->accessMember() != nullptr) - { - result.type = ExprType::Dot; - result._dot.expr = std::make_unique(getExpr(ctx->accessExpr()->nonAccessExpr())); - result._dot.ident.name = firstSub->accessMember()->identifierExpr()->varName()->NAME()->toString(); - } - else - { - result.type = ExprType::Brackets; - result._brackets.lexpr = std::make_unique(getExpr(ctx->accessExpr()->nonAccessExpr())); - result._brackets.rexpr = std::make_unique(getExpr(firstSub->accessBrackets()->expr())); - } - for (int i = 1; i < ctx->accessExpr()->accessSubExpr().size(); i++) - { - Expr tmp = result; - auto sub = ctx->accessExpr()->accessSubExpr(i); - if (sub->accessMember() != nullptr) - { - result.type = ExprType::Dot; - result._dot.expr = std::make_unique(tmp); - result._dot.ident.name = sub->accessMember()->identifierExpr()->varName()->NAME()->toString(); - } - else - { - result.type = ExprType::Brackets; - result._brackets.lexpr = std::make_unique(tmp); - result._brackets.rexpr = std::make_unique(getExpr(sub->accessBrackets()->expr())); - } - } - } - if (ctx->opExpr() != nullptr) - { - if (ctx->opExpr()->prefixOp() != nullptr || ctx->opExpr()->postfixOp() != nullptr) - { - result.type = ExprType::UnaryOperator; - result._unaryOperator = getUnaryOperatorExpr(ctx->opExpr()); - } - else if (ctx->opExpr()->binaryOp() != nullptr) - { - result.type = ExprType::BinaryOperator; - result._binaryOperator = getBinaryOperatorExpr(ctx->opExpr()); - for (int i = 1; i < ctx->opExpr()->binaryOp()->binary_op().size(); i++) - { - Expr tmp = result; - result._binaryOperator.lexpr = std::make_unique(tmp); - result._binaryOperator.type = getBinaryOperatorType(ctx->opExpr()->binaryOp()->binary_op(i)->getText()); - result._binaryOperator.rexpr = std::make_unique(getExpr(ctx->opExpr()->binaryOp()->nonOpExpr(i+1))); - } - } - else if (ctx->opExpr()->ternaryOp() != nullptr) - { - result.type = ExprType::TernaryOperator; - result._ternaryOperator = getTernaryOperatorExpr(ctx->opExpr()); - } - } + if (dynamic_cast(ctx) != nullptr) + result = getExpr(dynamic_cast(ctx)); + if (dynamic_cast(ctx) != nullptr) + result = getExpr(dynamic_cast(ctx)); + if (dynamic_cast(ctx) != nullptr) + result = getExpr(dynamic_cast(ctx)); + if (dynamic_cast(ctx) != nullptr) + result = getExpr(dynamic_cast(ctx)); + if (dynamic_cast(ctx) != nullptr) + result = getExpr(dynamic_cast(ctx)); + if (dynamic_cast(ctx) != nullptr) + result = getExpr(dynamic_cast(ctx)); + if (dynamic_cast(ctx) != nullptr) + result = getExpr(dynamic_cast(ctx)); + if (dynamic_cast(ctx) != nullptr) + result = getExpr(dynamic_cast(ctx)); + if (dynamic_cast(ctx) != nullptr) + result = getExpr(dynamic_cast(ctx)); + if (dynamic_cast(ctx) != nullptr) + result = getExpr(dynamic_cast(ctx)); + if (dynamic_cast(ctx) != nullptr) + result = getExpr(dynamic_cast(ctx)); return result; } Stmt getStmt(TocParser::StmtContext * ctx) @@ -386,8 +343,9 @@ Stmt getStmt(TocParser::StmtContext * ctx) if (ctx->varDecl() != nullptr && ctx->varDecl()->var()->expr() != nullptr) { result.type = StmtType::Assign; - result._assign.name = ctx->varDecl()->var()->varName()->NAME()->toString(); - result._assign.expr = getExpr(ctx->varDecl()->var()->expr()); + result._assign.lexpr.type = ExprType::Identifier; + result._assign.lexpr._identifier.identifier = ctx->varDecl()->var()->varName()->getText(); + result._assign.rexpr = getExpr(ctx->varDecl()->var()->expr()); } if (ctx->ifStmt() != nullptr) { @@ -414,7 +372,7 @@ Stmt getStmt(TocParser::StmtContext * ctx) if (ctx->switchStmt() != nullptr) { result.type = StmtType::Switch; - result._switch.ident.name = ctx->switchStmt()->identifierExpr()->varName()->NAME()->toString(); + result._switch.ident = std::make_unique(getExpr(ctx->switchStmt()->expr())); for (auto c : ctx->switchStmt()->switchBody()->switchCase()) { result._switch.cases.emplace_back( @@ -426,16 +384,10 @@ Stmt getStmt(TocParser::StmtContext * ctx) if (ctx->forStmt() != nullptr) { result.type = StmtType::For; - if (ctx->forStmt()->varInit() != nullptr) - { - result._for.varName = ctx->forStmt()->varInit()->varName()->NAME()->toString(); - result._for.initValue = std::make_unique(getExpr(ctx->forStmt()->varInit()->expr())); - } - else - { - result._for.varName = ctx->forStmt()->assignStmt()->identifierExpr()->varName()->NAME()->toString(); - result._for.initValue = std::make_unique(getExpr(ctx->forStmt()->assignStmt()->expr())); - } + result._for.init = std::make_unique(); + result._for.init->lexpr.type = ExprType::Identifier; + result._for.init->lexpr._identifier.identifier = ctx->forStmt()->varInit()->varName()->getText(); + result._for.init->rexpr = getExpr(ctx->forStmt()->varInit()->expr()); result._for.condition = std::make_unique(getExpr(ctx->forStmt()->expr(0))); result._for.action = std::make_unique(getExpr(ctx->forStmt()->expr(1))); result._for.body = getBody(ctx->forStmt()->body()); @@ -449,8 +401,8 @@ Stmt getStmt(TocParser::StmtContext * ctx) if (ctx->assignStmt() != nullptr) { result.type = StmtType::Assign; - result._assign.name = ctx->assignStmt()->identifierExpr()->varName()->NAME()->toString(); - result._assign.expr = getExpr(ctx->assignStmt()->expr()); + result._assign.lexpr = getExpr(ctx->assignStmt()->expr(0)); + result._assign.rexpr = getExpr(ctx->assignStmt()->expr(1)); } if (ctx->returnStmt() != nullptr) { diff --git a/src/toc.h b/src/toc.h index e4f36e5..95c24d8 100644 --- a/src/toc.h +++ b/src/toc.h @@ -4,32 +4,36 @@ #include #include "repr.h" +#include "typeInfo.h" template -std::ostream & operator<< (std::ostream & out, const std::vector & v) +std::string vectorStr (const std::vector & v, const std::string & separator, bool end = false) { - bool comma = false; + std::stringstream sstr; + + bool putSeparator = false; for (auto t : v) { - if (comma) out << ", "; - else comma = true; - out << t; + if (putSeparator) sstr << separator; + else putSeparator = true; + sstr << t; } - return out; + if (end && !v.empty()) + sstr << separator; + + return sstr.str(); } std::ostream & operator<< (std::ostream & out, const Type & t); std::ostream & operator<< (std::ostream & out, const Variable & v); std::ostream & operator<< (std::ostream & out, const Body & b); -std::ostream & operator<< (std::ostream & out, const UnaryOperatorExpr & o); -std::ostream & operator<< (std::ostream & out, const BinaryOperatorExpr & o); -std::ostream & operator<< (std::ostream & out, const TernaryOperatorExpr & o); std::ostream & operator<< (std::ostream & out, const Expr & e); std::ostream & operator<< (std::ostream & out, const Stmt & s); void tocFunction (std::ostream & out, const Function & f, bool stub); void tocStruct (std::ostream & out, const Struct & s, bool stub); void tocProgram (std::ostream & out, const Program & p); +void tocNamespace (std::ostream & out, const Namespace & n, bool stub); static const int TAB_WIDTH = 2; static int indentation = 0; @@ -39,9 +43,21 @@ static void indent(std::ostream & out, int change = 0) out << std::string(indentation, ' '); } +static std::vector namespaces; +static std::string namespacePrefix() { + std::stringstream sstr; + for (auto n : namespaces) + { + sstr << n << "_"; + } + return sstr.str(); +} + +static Program globalPrg; + std::ostream & operator<< (std::ostream & out, const Type & t) { - out << t.name; + out << vectorStr(t.namespacePrefixes, "_", true) << t.name; return out; } @@ -99,62 +115,46 @@ std::ostream & operator<< (std::ostream & out, const Body & b) return out; } -std::ostream & operator<< (std::ostream & out, const UnaryOperatorExpr & o) -{ - if (o.type == UnaryOperatorType::IncrementPost || o.type == UnaryOperatorType::DecrementPost) - { - out << UnaryOperatorTypeStrings[(int)o.type] << *o.expr; - } - else - { - out << *o.expr << UnaryOperatorTypeStrings[(int)o.type]; - } - - return out; -} -std::ostream & operator<< (std::ostream & out, const BinaryOperatorExpr & o) -{ - out << *o.lexpr << " " << BinaryOperatorTypeStrings[(int)o.type] << " " << *o.rexpr; - - return out; -} -std::ostream & operator<< (std::ostream & out, const TernaryOperatorExpr & o) -{ - out << *o.lexpr << " ? " << *o.rexprTrue << " : " << *o.rexprFalse; - - return out; -} std::ostream & operator<< (std::ostream & out, const Expr & e) { - if (e.parenthesized) - out << "("; - switch (e.type) { case ExprType::Func: - out << e._func.functionName << "(" << e._func.arguments << ")"; break; + out << vectorStr(e._func.namespacePrefixes, "_", true) << e._func.functionName << "(" << vectorStr(e._func.arguments, ", ") << ")"; break; + case ExprType::Method: + { + TypeInfo ti = typeExpr(globalPrg, namespaces, *e._method.expr); + out << + vectorStr(ti.type.namespacePrefixes, "_", true) << + ti.type.name << "_" << e._method.methodName << "(" << *e._method.expr << vectorStr(e._method.arguments, ", ") << ")"; break; + } case ExprType::Lit: /**/ if (e._lit.type == LitType::Int) out << e._lit._int; else if (e._lit.type == LitType::Decimal) out << e._lit._decimal; else if (e._lit.type == LitType::String) out << e._lit._string; else if (e._lit.type == LitType::Bool) out << e._lit._bool; break; - case ExprType::Identifier: - out << e._identifier.name; break; - case ExprType::Brackets: - out << *e._brackets.lexpr << "[" << *e._brackets.rexpr << "]"; break; + case ExprType::Paren: + out << "(" << e._paren.expr << ")"; break; case ExprType::Dot: - out << *e._dot.expr << "." << e._dot.ident.name; break; - case ExprType::UnaryOperator: - out << e._unaryOperator; break; - case ExprType::BinaryOperator: - out << e._binaryOperator; break; - case ExprType::TernaryOperator: - out << e._ternaryOperator; break; + out << *e._dot.expr << "." << e._dot.identifier; break; + case ExprType::PrefixOp: + out << PrefixOperatorTypeStrings[(int)e._prefixOp.type] << *e._prefixOp.expr; break; + case ExprType::PostfixOp: + out << *e._postfixOp.expr << PostfixOperatorTypeStrings[(int)e._postfixOp.type]; break; + case ExprType::BinaryOp: + out << *e._binaryOp.lexpr << + " " << BinaryOperatorTypeStrings[(int)e._binaryOp.type] << " " << + *e._binaryOp.rexpr; break; + case ExprType::TernaryOp: + out << *e._ternaryOp.lexpr << + " ? " << *e._ternaryOp.rexprTrue << + " : " << *e._ternaryOp.rexprFalse; break; + case ExprType::Bracket: + out << *e._brackets.lexpr << "[" << *e._brackets.rexpr << "]"; break; + case ExprType::Identifier: + out << vectorStr(e._identifier.namespacePrefixes, "_", true) << e._identifier.identifier; break; } - - if (e.parenthesized) - out << ")"; return out; } @@ -165,7 +165,7 @@ std::ostream & operator<< (std::ostream & out, const Stmt & s) case StmtType::If: out << "if (" << s._if.condition << ")\n" << s._if.body; break; case StmtType::Switch: - out << "switch (" << s._switch.ident.name << ")\n{\n"; + out << "switch (" << s._switch.ident << ")\n{\n"; for (auto c : s._switch.cases) { indent(out, 2); @@ -176,14 +176,14 @@ std::ostream & operator<< (std::ostream & out, const Stmt & s) break; case StmtType::For: out << "for (" << - s._for.varName << " = " << *s._for.initValue << "; " << + s._for.init << "; " << *s._for.condition << "; " << *s._for.action << ")\n" << s._for.body; break; case StmtType::While: out << "while (" << s._while.condition << ")\n" << s._while.body; break; case StmtType::Assign: - out << s._assign.name << " = " << s._assign.expr << ";"; break; + out << s._assign.lexpr << " = " << s._assign.rexpr << ";"; break; case StmtType::Return: out << "return " << s._return.expr << ";"; break; case StmtType::Expr: @@ -196,7 +196,7 @@ std::ostream & operator<< (std::ostream & out, const Stmt & s) void tocFunction (std::ostream & out, const Function & f, bool stub) { - out << f.returnType << " " << f.name << " (" << f.parameters << ")"; + out << f.returnType << " " << namespacePrefix() << f.name << " (" << vectorStr(f.parameters, ", ") << ")"; if (stub) { @@ -209,19 +209,27 @@ void tocFunction (std::ostream & out, const Function & f, bool stub) } void tocStruct (std::ostream & out, const Struct & s, bool stub) { - out << "struct " << s.name; + out << "struct " << namespacePrefix() << s.name; if (stub) { out << ";\n"; for (auto m : s.methods) { - m.parameters.insert(m.parameters.begin(), + Function f = m; + + f.parameters.insert(f.parameters.begin(), {"this", - {s.name, - {{TypeModifierType::Pointer, false, -1}}}}); - out << m.returnType << " " << - s.name << "_" << m.name << - " (" << m.parameters << ");\n"; + { + namespaces, + s.name, + { + {TypeModifierType::Pointer, false, -1} + } + } + }); + out << f.returnType << " " << + namespacePrefix() << s.name << "_" << f.name << + " (" << vectorStr(f.parameters, ", ") << ");\n"; } return; } @@ -239,15 +247,29 @@ void tocStruct (std::ostream & out, const Struct & s, bool stub) for (auto m : s.methods) { - m.parameters.insert(m.parameters.begin(), - {"this", - {s.name, - {{TypeModifierType::Pointer, false, -1}}}}); - out << m.returnType << " " << s.name << "_" << m.name << " (" << m.parameters << ")\n" << m.body; + Function f = m; + f.parameters.insert(f.parameters.begin(), + {"this", + { + namespaces, + s.name, + { + {TypeModifierType::Pointer, false, -1} + } + } + }); + out << f.returnType << " " << + namespacePrefix() << s.name << "_" << f.name << + " (" << vectorStr(f.parameters, ", ") << ")\n" << f.body; } } void tocProgram (std::ostream & out, const Program & p) { + globalPrg = p; + for (auto n : p.namespaces) + { + tocNamespace(out, n, true); + } for (auto s : p.structs) { tocStruct(out, s, true); @@ -261,6 +283,10 @@ void tocProgram (std::ostream & out, const Program & p) { out << v << ";\n"; } + for (auto n : p.namespaces) + { + tocNamespace(out, n, false); + } for (auto s : p.structs) { tocStruct(out, s, false); @@ -270,3 +296,29 @@ void tocProgram (std::ostream & out, const Program & p) tocFunction(out, f, false); } } + + +void tocNamespace (std::ostream & out, const Namespace & n, bool stub) +{ + namespaces.push_back(n.name); + if (!stub) + { + for (auto v : n.variables) + { + out << v << ";\n"; + } + } + for (auto n : n.namespaces) + { + tocNamespace(out, n, stub); + } + for (auto s : n.structs) + { + tocStruct(out, s, stub); + } + for (auto f : n.functions) + { + tocFunction(out, f, stub); + } + namespaces.pop_back(); +} \ No newline at end of file -- cgit v1.2.3