antimony-lang/antimony

Proper check-phase

garritfra opened this issue · 1 comments

The checking of the AST currently happens through running the generated code. This is obviously a bad idea.

We should implement a check phase after parsing the AST. For now, the following checks should be in place:

  • Check, if an accessed symbol is defined in the scope
  • Check, if types are compatible (function parameters should have the correct type, let x: int = "Hello" is invalid, etc.)

Room for discussion

  • Should this be done while parsing the tree instead?
  • Should this be one large check, or modular checkers that run sequentially?

It would also make sense to move type infers into check. Having them in the parser is a bit unintuitive.

  • Should this be done while parsing the tree instead?

I think this should be a separate build step. Parse step should transform tokens into an AST, and check step should work on that AST (possibly updating it). If we try to merge them together it would overload the parser more than it should.

  • Should this be one large check, or modular checkers that run sequentially?

Let's not go into super modular design as it would complicate things. A single build step but the main check function can sequentially run helpers when needed would work for this.

// Can mutate the AST when doing type infers
fn check(prog: &mut ast::Program, ...) -> CheckResult {
    // ...
    infer_types(prog, ...);
    // ...
    check_compatible(prog, ...);
    // ...
}

fn infer_types(prog: &mut ast::Program, ...) -> CheckResult {
    ...
}

fn check_compatible(prog: &ast::Program, ...) -> CheckResult {
    ...
}