[libjlx] Fix type checking for function declarations
This commit is contained in:
parent
e3d912c6a5
commit
693487a62a
3 changed files with 20 additions and 15 deletions
|
|
@ -466,6 +466,12 @@ namespace jlx {
|
||||||
next(false);
|
next(false);
|
||||||
|
|
||||||
return previous;
|
return previous;
|
||||||
|
} else {
|
||||||
|
if (previous != nullptr) {
|
||||||
|
return previous;
|
||||||
|
}
|
||||||
|
|
||||||
|
fail_invalid_token(*current);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
fail_invalid_token(*current);
|
fail_invalid_token(*current);
|
||||||
|
|
@ -508,7 +514,7 @@ namespace jlx {
|
||||||
std::optional<std::string> return_type;
|
std::optional<std::string> return_type;
|
||||||
|
|
||||||
bool first = true;
|
bool first = true;
|
||||||
while (current->type != Punctuation && current->content != ")") {
|
while (current->type != Punctuation || current->content != ")") {
|
||||||
if (!first) {
|
if (!first) {
|
||||||
if(current->type != Punctuation || current->content != ",") {
|
if(current->type != Punctuation || current->content != ",") {
|
||||||
fail_invalid_token(*current);
|
fail_invalid_token(*current);
|
||||||
|
|
@ -534,8 +540,8 @@ namespace jlx {
|
||||||
|
|
||||||
auto param_type = parse_type();
|
auto param_type = parse_type();
|
||||||
params.emplace_back(std::move(name), std::move(param_type));
|
params.emplace_back(std::move(name), std::move(param_type));
|
||||||
|
|
||||||
next();
|
next();
|
||||||
|
|
||||||
first = false;
|
first = false;
|
||||||
}
|
}
|
||||||
next();
|
next();
|
||||||
|
|
|
||||||
|
|
@ -64,17 +64,11 @@ namespace jlx {
|
||||||
return std::format("{}({})", token_type_to_string(t.type), t.content);
|
return std::format("{}({})", token_type_to_string(t.type), t.content);
|
||||||
}
|
}
|
||||||
|
|
||||||
export class tokenizer_exception {
|
export class tokenizer_exception : public std::runtime_error {
|
||||||
protected:
|
|
||||||
std::string msg;
|
|
||||||
public:
|
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 {
|
export class tokenizer {
|
||||||
|
|
@ -90,14 +84,15 @@ namespace jlx {
|
||||||
"return"
|
"return"
|
||||||
}};
|
}};
|
||||||
|
|
||||||
static constexpr std::array<char, 7> punctuations = {{
|
static constexpr std::array<char, 8> punctuations = {{
|
||||||
'.',
|
'.',
|
||||||
'(',
|
'(',
|
||||||
'(',
|
')',
|
||||||
'{',
|
'{',
|
||||||
'}',
|
'}',
|
||||||
':',
|
':',
|
||||||
';'
|
';',
|
||||||
|
','
|
||||||
}};
|
}};
|
||||||
|
|
||||||
static constexpr std::array<std::string, 13> operators = {{
|
static constexpr std::array<std::string, 13> 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:
|
public:
|
||||||
|
|
@ -372,7 +368,7 @@ namespace jlx {
|
||||||
return op_res;
|
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());
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -478,6 +478,9 @@ namespace jlx {
|
||||||
scopes[scopes.size() - 1].functions.insert_or_assign(decl->name, f);
|
scopes[scopes.size() - 1].functions.insert_or_assign(decl->name, f);
|
||||||
|
|
||||||
auto& function_scope = scopes.emplace_back(type_checker_scope{});
|
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;
|
function_scope.intended_return_type = decl->return_type;
|
||||||
|
|
||||||
check_statement(*decl->body, true);
|
check_statement(*decl->body, true);
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue