hare

[hare] The Hare programming language
git clone https://git.torresjrjr.com/hare.git
Log | Files | Refs | README | LICENSE

decl.ha (1882B)


      1 // License: MPL-2.0
      2 // (c) 2021 Drew DeVault <sir@cmpwn.com>
      3 // (c) 2021 Eyal Sawady <ecs@d2evs.net>
      4 use hare::lex;
      5 
      6 // A constant declaration.
      7 //
      8 // 	def foo: int = 0;
      9 export type decl_const = struct {
     10 	ident: ident,
     11 	_type: _type,
     12 	init: *expr,
     13 };
     14 
     15 // A global declaration.
     16 //
     17 // 	let foo: int = 0;
     18 // 	const foo: int = 0;
     19 export type decl_global = struct {
     20 	is_const: bool,
     21 	symbol: str,
     22 	ident: ident,
     23 	_type: _type,
     24 	init: nullable *expr,
     25 };
     26 
     27 // A type declaration.
     28 //
     29 // 	type foo = int;
     30 export type decl_type = struct {
     31 	ident: ident,
     32 	_type: _type,
     33 };
     34 
     35 // Attributes applicable to a function declaration.
     36 export type fndecl_attrs = enum {
     37 	NONE,
     38 	FINI,
     39 	INIT,
     40 	TEST,
     41 };
     42 
     43 // A function declaration.
     44 //
     45 // fn main() void = void;
     46 export type decl_func = struct {
     47 	symbol: str,
     48 	ident: ident,
     49 	prototype: _type,
     50 	body: (expr | void),
     51 	attrs: fndecl_attrs,
     52 };
     53 
     54 // A Hare declaration.
     55 export type decl = struct {
     56 	exported: bool,
     57 	start: lex::location,
     58 	end: lex::location,
     59 	decl: ([]decl_const | []decl_global | []decl_type | decl_func),
     60 
     61 	// Only valid if the lexer has comments enabled
     62 	docs: str,
     63 };
     64 
     65 // Frees resources associated with a declaration.
     66 export fn decl_finish(d: decl) void = {
     67 	free(d.docs);
     68 	match (d.decl) {
     69 	case let g: []decl_global =>
     70 		for (let i = 0z; i < len(g); i += 1) {
     71 			free(g[i].symbol);
     72 			ident_free(g[i].ident);
     73 			type_finish(g[i]._type);
     74 			expr_finish(g[i].init);
     75 		};
     76 		free(g);
     77 	case let t: []decl_type =>
     78 		for (let i = 0z; i < len(t); i += 1) {
     79 			ident_free(t[i].ident);
     80 			type_finish(t[i]._type);
     81 		};
     82 		free(t);
     83 	case let f: decl_func =>
     84 		free(f.symbol);
     85 		ident_free(f.ident);
     86 		type_finish(f.prototype);
     87 		if (f.body is expr) expr_finish(f.body as expr);
     88 	case let c: []decl_const =>
     89 		for (let i = 0z; i < len(c); i += 1) {
     90 			ident_free(c[i].ident);
     91 			type_finish(c[i]._type);
     92 			expr_finish(c[i].init);
     93 		};
     94 		free(c);
     95 	};
     96 };