diff --git a/libjlx/modules/ast.cppm b/libjlx/modules/ast.cppm index 83b579c..0d698f0 100644 --- a/libjlx/modules/ast.cppm +++ b/libjlx/modules/ast.cppm @@ -466,6 +466,12 @@ namespace jlx { next(false); return previous; + } else { + if (previous != nullptr) { + return previous; + } + + fail_invalid_token(*current); } } fail_invalid_token(*current); @@ -508,7 +514,7 @@ namespace jlx { std::optional return_type; bool first = true; - while (current->type != Punctuation && current->content != ")") { + while (current->type != Punctuation || current->content != ")") { if (!first) { if(current->type != Punctuation || current->content != ",") { fail_invalid_token(*current); @@ -534,8 +540,8 @@ namespace jlx { auto param_type = parse_type(); params.emplace_back(std::move(name), std::move(param_type)); - next(); + first = false; } next(); diff --git a/libjlx/modules/tokenizer.cppm b/libjlx/modules/tokenizer.cppm index 93fff78..d04b2c2 100644 --- a/libjlx/modules/tokenizer.cppm +++ b/libjlx/modules/tokenizer.cppm @@ -64,17 +64,11 @@ namespace jlx { return std::format("{}({})", token_type_to_string(t.type), t.content); } - export class tokenizer_exception { - protected: - std::string msg; + export class tokenizer_exception : public std::runtime_error { public: - tokenizer_exception(std::string msg, std::size_t line, std::size_t col) : msg(std::format("Tokenizer exception at %d:%d. %s", line, col, msg)) { + tokenizer_exception(std::string msg, std::size_t line, std::size_t col) : std::runtime_error(std::format("Tokenizer exception at {}:{}. {}", line, col, msg).c_str()) { } - - const std::string& what() const { - return msg; - } }; export class tokenizer { @@ -90,14 +84,15 @@ namespace jlx { "return" }}; - static constexpr std::array punctuations = {{ + static constexpr std::array punctuations = {{ '.', '(', - '(', + ')', '{', '}', ':', - ';' + ';', + ',' }}; static constexpr std::array operators = {{ @@ -329,7 +324,8 @@ namespace jlx { }; } - throw tokenizer_exception(std::format("Unknown operator '%s'", word), line, col); + //throw tokenizer_exception(std::format("Unknown operator '{}'", word), line, col); + return std::nullopt; } public: @@ -372,7 +368,7 @@ namespace jlx { return op_res; } - throw tokenizer_exception(std::format("Unknown character '%c'", val), source.current_line(), source.current_col()); + throw tokenizer_exception(std::format("Unknown character '{}'", val), source.current_line(), source.current_col()); } }; } diff --git a/libjlx/modules/type_checker.cppm b/libjlx/modules/type_checker.cppm index 09bd756..18d2303 100644 --- a/libjlx/modules/type_checker.cppm +++ b/libjlx/modules/type_checker.cppm @@ -478,6 +478,9 @@ namespace jlx { scopes[scopes.size() - 1].functions.insert_or_assign(decl->name, f); auto& function_scope = scopes.emplace_back(type_checker_scope{}); + for (auto& a : decl->parameters) { + function_scope.variables.insert_or_assign(a.name, a.type); + } function_scope.intended_return_type = decl->return_type; check_statement(*decl->body, true);