spl

Unnamed repository; edit this file 'description' to name the repository.
Log | Files | Refs | README | LICENSE

commit e2482b85232411aea48dd00a6845a6e336d1d8ad
parent b71972a7869f2b010a650745663dfd88fe225669
Author: Brian Swetland <swetland@frotz.net>
Date:   Fri, 20 Oct 2023 00:09:48 -0700

compiler: create full Type for functions, add it to AST

Diffstat:
Mcompiler/compiler.spl | 40++++++++++++++++++++++++++++------------
1 file changed, 28 insertions(+), 12 deletions(-)

diff --git a/compiler/compiler.spl b/compiler/compiler.spl @@ -81,7 +81,7 @@ enum TypeKind { TYPE_SLICE, TYPE_STR, TYPE_STRUCT, - TYPE_FUNC, + TYPE_FN, TYPE_ENUM, TYPE_UNDEFINED, }; @@ -89,8 +89,8 @@ enum TypeKind { struct Type { next *Type, name *String, - of *Type, // for slice, array, ptr - fields *Symbol, // for struct + of *Type, // for slice, array, ptr, fn (return type) + list *Symbol, // for struct (fields), fn (params) kind TypeKind, count u32, }; @@ -326,10 +326,11 @@ fn scope_push(kind ScopeKind) Scope { return scope; } -fn scope_pop() Scope { +// returns symbol list for the popped scope +fn scope_pop() Symbol { var scope Scope = ctx.scope; ctx.scope = scope.parent; - return scope; + return scope.first; } fn scope_find(kind ScopeKind) Scope { @@ -390,11 +391,11 @@ fn symbol_make(name String, type Type) Symbol { return symbol_make_in_scope(name, type, ctx.scope); } -fn type_make(name String, kind TypeKind, of Type, fields Symbol, count u32) Type { +fn type_make(name String, kind TypeKind, of Type, list Symbol, count u32) Type { var type Type = new(Type); type.name = name; type.of = of; - type.fields = fields; + type.list = list; type.kind = kind; type.count = count; if name != nil { @@ -421,7 +422,7 @@ fn type_find_field(type Type, name String) Symbol { if type.kind != TYPE_STRUCT { error("not a struct"); } - var s Symbol = type.fields; + var s Symbol = type.list; while s != nil { if s.name == name { return s; @@ -1086,7 +1087,7 @@ fn parse_struct_type(name String) Type { require(tCOMMA); } } - type.fields = scope_pop().first; + type.list = scope_pop(); return type; } @@ -1233,7 +1234,7 @@ fn parse_struct_init(sym Symbol) { break; } var name String = parse_name("field name"); - var field Symbol = sym.type.fields; + var field Symbol = sym.type.list; while true { // TODO: field_find if field == nil { error("structure has no '", @str name.text, "' field"); @@ -1410,12 +1411,14 @@ fn parse_fn() Ast { scope_push(SCOPE_FUNC); require(tOPAREN); + var n u32 = 0; if ctx.tok != tCPAREN { parse_param(fname); while ctx.tok == tCOMMA { next(); parse_param(fname); } + n++; } require(tCPAREN); @@ -1425,13 +1428,15 @@ fn parse_fn() Ast { var sym Symbol = symbol_make_global(fname, rtype); sym.kind = SYMBOL_FN; + sym.type = type_make(fname, TYPE_FN, rtype, nil, n); var node Ast = ast_make_simple(AST_FUNC, 0); node.name = fname; node.sym = sym; - node.left = parse_fn_body(sym); + node.right = parse_fn_body(sym); - scope_pop(); + // save parameters + sym.type.list = scope_pop(); return node; } @@ -1521,6 +1526,17 @@ fn _dump_ast_node(fd i32, node Ast) { writex(fd, node.ival); } else if kind == AST_FUNC { writes(fd, node.name.text); + writes(fd, "("); + var param Symbol = node.sym.type.list; + while param != nil { + writes(fd, param.name.text); + if param.next != nil { + writes(fd, ", "); + } + param = param.next; + } + writes(fd, ") "); + writes(fd, node.sym.type.of.name.text); } else if kind == AST_STRING { printstr(fd, node.name.text); } else if kind == AST_SYMBOL {