From c2ba7425955ae538e220cec79d9124756d1b4c8b Mon Sep 17 00:00:00 2001 From: Patrick Schönberger Date: Wed, 4 Aug 2021 17:46:48 +0200 Subject: function resolution, pre generics --- src/find.h | 40 ++++++++++++++++++++-------------------- src/main.cpp | 2 +- src/repr.h | 1 + src/repr_get.h | 14 +++++++++++--- src/toc.h | 42 ++++++++++++++++++++++++++++++++++++++++-- src/typeInfo.h | 20 ++++++++++---------- 6 files changed, 83 insertions(+), 36 deletions(-) (limited to 'src') diff --git a/src/find.h b/src/find.h index a969bae..1876a1e 100644 --- a/src/find.h +++ b/src/find.h @@ -33,15 +33,26 @@ opt findFunction( if (!n.has_value()) return nullopt; + std::vector namespaces = { n.value() }; + for (int i = 1; i < namespacePrefixes.size(); i++) { n = find(n.value().namespaces, [&](Namespace n) { return n.name == namespacePrefixes[i]; }); if (!n.has_value()) return nullopt; + + namespaces.push_back(n.value()); + } + + for (int i = namespaces.size()-1; i >= 0; i--) + { + auto f = find(namespaces[i].functions, [&](Function f) { return f.name == name; }); + if (f.has_value()) + return f.value(); } - return find(n.value().functions, [&](Function f) { return f.name == name; }); + return find(p.functions, [&](Function f) { return f.name == name; }); } opt findStruct( @@ -72,28 +83,17 @@ opt findStruct( opt findVariable( const Program & p, const std::string & name, - const std::vector & namespacePrefixes) + std::shared_ptr ctx) { - for (auto n : namespacePrefixes) - std::cout << n << std::endl; - if (namespacePrefixes.empty()) - { - return find(p.ctx->variables, [&](Variable v) { return v.name == name; }); - } - - auto n = find(p.namespaces, [&](Namespace n) { return n.name == namespacePrefixes[0]; }); - - if (!n.has_value()) - return nullopt; - - for (int i = 1; i < namespacePrefixes.size(); i++) + auto it = ctx; + while (it != nullptr) { - n = find(n.value().namespaces, [&](Namespace n) { return n.name == namespacePrefixes[i]; }); - - if (!n.has_value()) - return nullopt; + auto v = find(it->variables, [&](Variable v) { return v.name == name; }); + if (v.has_value()) + return v; + it = it->parent; } - return find(n.value().ctx->variables, [&](Variable v) { return v.name == name; }); + return nullopt; } opt findStructMethod( diff --git a/src/main.cpp b/src/main.cpp index 461d014..e7c03e6 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -48,7 +48,7 @@ int main(int argc, const char * argv[]) tocProgram(ofs, prg); ofs.close(); } - catch (const std::string & e) + catch (const char * e) { std::cerr << "Error: " << e << std::endl; } diff --git a/src/repr.h b/src/repr.h index fc77d92..f12b0da 100644 --- a/src/repr.h +++ b/src/repr.h @@ -80,6 +80,7 @@ struct Function Type returnType; std::string name; std::vector parameters; + bool defined; Body body; }; diff --git a/src/repr_get.h b/src/repr_get.h index 396c71a..827c02b 100644 --- a/src/repr_get.h +++ b/src/repr_get.h @@ -82,7 +82,15 @@ Function getFunction(TocParser::FuncContext * ctx, std::shared_ptr pare for (auto p : ctx->parameter()->var()) result.parameters.push_back(getVariable(p)); } - result.body = getBody(ctx->body(), parent); + if (ctx->body() != nullptr) + { + result.body = getBody(ctx->body(), parent); + result.defined = true; + } + else + { + result.defined = false; + } return result; } Struct getStruct(TocParser::StructDeclContext * ctx, std::shared_ptr parent) @@ -219,10 +227,10 @@ Expr getExpr(TocParser::LitExprContext * ctx) result._lit.type = LitType::Decimal; result._lit._decimal = atof(ctx->literal()->DECIMAL_LIT()->toString().c_str()); } - else if (ctx->literal()->STRING_LIT() != nullptr) + else if (ctx->literal()->StringLit() != nullptr) { result._lit.type = LitType::String; - result._lit._string = ctx->literal()->STRING_LIT()->toString(); + result._lit._string = ctx->literal()->StringLit()->toString(); } else if (ctx->literal()->BOOL_LIT() != nullptr) { diff --git a/src/toc.h b/src/toc.h index 43ab1ba..c0c73f1 100644 --- a/src/toc.h +++ b/src/toc.h @@ -54,9 +54,13 @@ static std::string namespacePrefix() { } static Program globalPrg; +static std::shared_ptr globalCtx; std::ostream & operator<< (std::ostream & out, const Type & t) { + TypeInfo ti = typeType(globalPrg, t); + if (ti.isStruct) + out << "struct "; out << vectorStr(t.namespacePrefixes, "_", true) << t.name; return out; @@ -92,6 +96,9 @@ std::ostream & operator<< (std::ostream & out, const Variable & v) } std::ostream & operator<< (std::ostream & out, const Body & b) { + b.ctx->parent = globalCtx; + globalCtx = b.ctx; + indent(out); out << "{\n"; indentation += 2; @@ -113,6 +120,8 @@ std::ostream & operator<< (std::ostream & out, const Body & b) indent(out, -2); out << "}\n"; + globalCtx = b.ctx->parent; + return out; } std::ostream & operator<< (std::ostream & out, const Expr & e) @@ -120,13 +129,22 @@ std::ostream & operator<< (std::ostream & out, const Expr & e) switch (e.type) { case ExprType::Func: + { + if (e._func.namespacePrefixes.empty()) + { + TypeInfo ti = typeExpr(globalPrg, namespaces, globalCtx, e); + + } 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); + TypeInfo ti = typeExpr(globalPrg, namespaces, globalCtx, *e._method.expr); out << vectorStr(ti.type.namespacePrefixes, "_", true) << - ti.type.name << "_" << e._method.methodName << "(" << *e._method.expr << vectorStr(e._method.arguments, ", ") << ")"; break; + ti.type.name << "_" << e._method.methodName << + "(&" << *e._method.expr << (e._method.arguments.empty() ? "" : ", ") << + vectorStr(e._method.arguments, ", ") << ")"; break; } case ExprType::Lit: /**/ if (e._lit.type == LitType::Int) out << e._lit._int; @@ -196,6 +214,8 @@ std::ostream & operator<< (std::ostream & out, const Stmt & s) void tocFunction (std::ostream & out, const Function & f, bool stub) { + if (!stub && !f.defined) return; + out << f.returnType << " " << namespacePrefix() << f.name << " (" << vectorStr(f.parameters, ", ") << ")"; if (stub) @@ -265,41 +285,53 @@ void tocStruct (std::ostream & out, const Struct & s, bool stub) } void tocProgram (std::ostream & out, const Program & p) { + globalCtx = p.ctx; + globalPrg = p; for (auto n : p.namespaces) { tocNamespace(out, n, true); } + out << "\n\n"; for (auto s : p.structs) { tocStruct(out, s, true); } + out << "\n\n"; for (auto f : p.functions) { tocFunction(out, f, true); } + out << "\n\n"; for (auto v : p.ctx->variables) { out << v << ";\n"; } + out << "\n\n"; for (auto n : p.namespaces) { tocNamespace(out, n, false); } + out << "\n\n"; for (auto s : p.structs) { tocStruct(out, s, false); } + out << "\n\n"; for (auto f : p.functions) { tocFunction(out, f, false); } + out << "\n\n"; } void tocNamespace (std::ostream & out, const Namespace & n, bool stub) { + n.ctx->parent = globalCtx; + globalCtx = n.ctx; + namespaces.push_back(n.name); if (!stub) { @@ -307,18 +339,24 @@ void tocNamespace (std::ostream & out, const Namespace & n, bool stub) { out << v << ";\n"; } + out << "\n\n"; } for (auto n : n.namespaces) { tocNamespace(out, n, stub); + out << "\n\n"; } for (auto s : n.structs) { tocStruct(out, s, stub); + out << "\n\n"; } for (auto f : n.functions) { tocFunction(out, f, stub); + out << "\n\n"; } namespaces.pop_back(); + + globalCtx = n.ctx->parent; } \ No newline at end of file diff --git a/src/typeInfo.h b/src/typeInfo.h index 3914847..0fd4114 100644 --- a/src/typeInfo.h +++ b/src/typeInfo.h @@ -23,7 +23,7 @@ TypeInfo typeType(const Program & p, Type t) return result; } -TypeInfo typeExpr(const Program & p, const std::vector & globalNamespace, Expr e) +TypeInfo typeExpr(const Program & p, const std::vector & globalNamespace, std::shared_ptr globalCtx, Expr e) { TypeInfo result; @@ -43,7 +43,7 @@ TypeInfo typeExpr(const Program & p, const std::vector & globalNamespace } case ExprType::Method: { - TypeInfo tiCaller = typeExpr(p, globalNamespace, *e._method.expr); + TypeInfo tiCaller = typeExpr(p, globalNamespace, globalCtx, *e._method.expr); auto m = findStructMethod(p, e._method.methodName, tiCaller); if (!m.has_value()) throw "Unknown method"; @@ -61,32 +61,32 @@ TypeInfo typeExpr(const Program & p, const std::vector & globalNamespace } break; case ExprType::Paren: - result = typeExpr(p, globalNamespace, *e._paren.expr); + result = typeExpr(p, globalNamespace, globalCtx, *e._paren.expr); break; case ExprType::Dot: { auto sm = findStructMember(p, - typeExpr(p, globalNamespace, *e._dot.expr), e._dot.identifier); + typeExpr(p, globalNamespace, globalCtx, *e._dot.expr), e._dot.identifier); if (!sm.has_value()) throw "Unknown struct member"; result = typeType(p, sm.value().type); break; } case ExprType::PrefixOp: - result = typeExpr(p, globalNamespace, *e._prefixOp.expr); + result = typeExpr(p, globalNamespace, globalCtx, *e._prefixOp.expr); break; case ExprType::PostfixOp: - result = typeExpr(p, globalNamespace, *e._postfixOp.expr); + result = typeExpr(p, globalNamespace, globalCtx, *e._postfixOp.expr); break; case ExprType::BinaryOp: - result = typeExpr(p, globalNamespace, *e._binaryOp.lexpr); + result = typeExpr(p, globalNamespace, globalCtx, *e._binaryOp.lexpr); break; case ExprType::TernaryOp: - result = typeExpr(p, globalNamespace, *e._ternaryOp.rexprTrue); + result = typeExpr(p, globalNamespace, globalCtx, *e._ternaryOp.rexprTrue); break; case ExprType::Bracket: { - TypeInfo ti = typeExpr(p, globalNamespace, *e._brackets.lexpr); + TypeInfo ti = typeExpr(p, globalNamespace, globalCtx, *e._brackets.lexpr); if (!ti.type.modifiers.empty()) { result = ti; @@ -103,7 +103,7 @@ TypeInfo typeExpr(const Program & p, const std::vector & globalNamespace namespacePrefixes.insert(namespacePrefixes.end(), e._identifier.namespacePrefixes.begin(), e._identifier.namespacePrefixes.end()); - auto v = findVariable(p, e._identifier.identifier, namespacePrefixes); + auto v = findVariable(p, e._identifier.identifier, globalCtx); if (!v.has_value()) throw "Unknown variable"; result = typeType(p, v.value().type); -- cgit v1.2.3