aboutsummaryrefslogtreecommitdiff
path: root/src/parser.y
diff options
context:
space:
mode:
Diffstat (limited to 'src/parser.y')
-rw-r--r--src/parser.y185
1 files changed, 141 insertions, 44 deletions
diff --git a/src/parser.y b/src/parser.y
index 6ec2eb2..023c10a 100644
--- a/src/parser.y
+++ b/src/parser.y
@@ -36,7 +36,6 @@
%token <dbl> FLOAT
%token <str> STRING
%token <str> ID
-%token <str> APPLY
%token QUESTION "?"
%token SQUOTE "'"
@@ -70,6 +69,7 @@
%token RBRACE "}"
%token LBRACKET "["
%token RBRACKET "]"
+%token AS "as"
%token IF "if"
%token ELSE "else"
%token NIL "nil"
@@ -79,7 +79,6 @@
%token IMPORT "import"
%token ERROR "error"
%token DOT "."
-%token SCOPE "::"
%token FATARROW "=>"
%right "[" "]"
@@ -95,19 +94,26 @@
%left "*" "/" "%"
%left "as" "sizeof"
%right "'" "!" "~"
+%right ".."
%left "." "=>" "(" ")"
-%left "::"
-%nterm <node> top unit proc proc_decl call closure var expr statement body
-%nterm <node> vars exprs statements closures trailing_closure
-%nterm <node> opt_vars opt_exprs opt_statements opt_trailing_closure
-%nterm <node> rev_vars rev_exprs rev_closures rev_statements
+%nterm <node> top unit proc proc_decl call closure expr statement body
+%nterm <node> exprs statements closures trailing_closure
+%nterm <node> opt_exprs opt_statements opt_trailing_closure
+%nterm <node> rev_exprs rev_closures rev_statements
%nterm <node> let if nil unop binop construct import
+%nterm <node> opt_vars vars rev_vars var
+%nterm <node> opt_params params rev_params param
+
%nterm <node> struct struct_cont trait
%nterm <node> type_param type_params opt_type_params
%nterm <node> behaviour behaviours opt_behaviours
%nterm <node> member members opt_members
+%nterm <node> opt_elements elements rev_elements element
+%nterm <node> instance template supertemplate
+%nterm <node> opt_constructions constructions construction
+%nterm <node> id impl forget assign
%nterm <type> type rev_types types opt_types
@@ -189,12 +195,29 @@ static char *strip(const char *s);
%start input;
%%
-var
+param
: type ID { $$ = gen_var($2, $1, src_loc(@$)); }
+rev_params
+ : rev_params "," param { $$ = $3; $$->n = $1; }
+ | rev_params "|" param { $$ = $3; $$->n = $1; opt_group($1, $3); }
+ | param
+
+params
+ : rev_params { $$ = reverse_ast_list($1); }
+ | rev_params "," { $$ = reverse_ast_list($1); }
+
+opt_params
+ : params
+ | {$$ = NULL;}
+
+
+var
+ : param
+ | ID { $$ = gen_var($1, NULL, src_loc(@$)); }
+
rev_vars
: rev_vars "," var { $$ = $3; $$->n = $1; }
- | rev_vars "|" var { $$ = $3; $$->n = $1; opt_group($1, $3); }
| var
vars
@@ -206,13 +229,13 @@ opt_vars
| {$$ = NULL;}
proc
- : ID "(" opt_vars ")" body {
- $$ = gen_proc($[ID], $[opt_vars], NULL, $[body], src_loc(@$));
+ : ID "(" opt_params ")" body {
+ $$ = gen_proc($[ID], $[opt_params], NULL, $[body], src_loc(@$));
}
proc_decl
- : ID "(" opt_vars ")" ";" {
- $$ = gen_proc($[ID], $[opt_vars], NULL, NULL, src_loc(@$));
+ : ID "(" opt_params ")" ";" {
+ $$ = gen_proc($[ID], $[opt_params], NULL, NULL, src_loc(@$));
}
binop
@@ -229,17 +252,20 @@ binop
| expr ">=" expr { $$ = gen_comparison(AST_GE, $1, $3, src_loc(@$)); }
| expr "!=" expr { $$ = gen_comparison(AST_NE, $1, $3, src_loc(@$)); }
| expr "==" expr { $$ = gen_comparison(AST_EQ, $1, $3, src_loc(@$)); }
+ | id "~" id { $$ = gen_paste($1, $3, src_loc(@$)); }
unop
: "-" expr { $$ = gen_unop(AST_NEG, $2, src_loc(@$)); }
- | "!" expr { $$ = gen_unop(AST_LNOT, $2, src_loc(@$)); }
+ | "!" expr { $$ = gen_unop(AST_LNOT, $2, src_loc(@$)); }
+ | "~" expr { $$ = gen_unop(AST_BNEG, $2, src_loc(@$)); }
type
- : ID { $$ = tgen_id($[ID], src_loc(@$)); }
- | APPLY "[" opt_types "]" {
- $$ = tgen_construct($[APPLY], $[opt_types], src_loc(@$));
- }
+ : ID { $$ = tgen_id($1, src_loc(@$)); }
| "(" opt_types ")" { $$ = tgen_closure($2, src_loc(@$)); }
+ | "[" "]" type {
+ /* TODO static sizes? */
+ $$ = tgen_arr($3, NULL, src_loc(@$));
+ }
| "&&" type {
if ($2->k == TYPE_CLOSURE) {
$$ = $2; $$->k = TYPE_PURE_CLOSURE;
@@ -276,26 +302,43 @@ opt_types
: types
| { $$ = NULL; }
-construct
- : APPLY "{" opt_exprs "}" {
- $$ = gen_init($[APPLY], NULL, $[opt_exprs], src_loc(@$));
+construction
+ : expr "=>" ID {
+ $$ = gen_construction($3, $1, src_loc(@$));
}
- | APPLY "[" opt_types "]" "{" opt_exprs "}" {
- $$ = gen_init($[APPLY], $[opt_types], $[opt_exprs], src_loc(@$));
+
+constructions
+ : constructions "," construction { $$ = $3; $$->n = $1; }
+ | construction
+
+opt_constructions
+ : constructions
+ | { $$ = NULL; }
+
+construct
+ : "(" opt_constructions ")" ID {
+ $$ = gen_construct($4, $2, src_loc(@$));
}
+id
+ : ID { $$ = gen_id($1, src_loc(@$)); }
+
expr
- : expr "." ID { $$ = gen_dot($3, $1, src_loc(@$)); }
+ : "sizeof" "(" type ")" { $$ = gen_sizeof($3, src_loc(@$)); }
+ | expr "." ID { $$ = gen_dot($3, $1, src_loc(@$)); }
+ | expr "[" expr "]" { $$ = gen_arr($1, $3, src_loc(@$)); }
| STRING { $$ = gen_const_str(strip($1), src_loc(@$)); }
| FLOAT { $$ = gen_const_float($1, src_loc(@$)); }
| BOOL { $$ = gen_const_bool($1, src_loc(@$)); }
| CHAR { $$ = gen_const_char($1, src_loc(@$)); }
| INT { $$ = gen_const_int($1, src_loc(@$)); }
- | ID { $$ = gen_id($1, src_loc(@$)); }
+ | "*" { $$ = gen_nil(src_loc(@$)); }
| "(" expr ")" { $$ = $2; }
| expr "&" { $$ = gen_ref($1, src_loc(@$)); }
| expr "*" { $$ = gen_deref($1, src_loc(@$)); }
+ | expr "as" type { $$ = gen_as($1, $3, src_loc(@$)); }
| construct
+ | id
| binop
| unop
@@ -369,12 +412,24 @@ if
| "if" expr body "else" if { $$ = gen_if($2, $3, $5, src_loc(@$)); }
nil
- : "nil" ID body "=>" var {
- $$ = gen_nil($2, $3, $5, src_loc(@$));
+ : "nil" expr body "=>" var ";" {
+ $$ = gen_nil_check($2, $3, $5, src_loc(@$));
+ }
+
+forget
+ : "nil" ID ";" {
+ $$ = gen_forget($2, src_loc(@$));
+ }
+
+assign
+ : expr "=" expr ";" {
+ $$ = gen_assign($1, $3, src_loc(@$));
}
statement
: call
+ | forget
+ | assign
| body
| let
| nil
@@ -398,9 +453,9 @@ body
}
behaviour
- : APPLY ";" { $$ = gen_trait_apply($1, src_loc(@$)); }
- | proc_decl ";"
+ : proc_decl
| proc
+ | impl
behaviours
: behaviours behaviour { $$ = $1; $1->n = $2; }
@@ -410,16 +465,18 @@ opt_behaviours
: behaviours
| { $$ = NULL; }
+impl
+ : ID "!" { $$ = gen_implements($1, src_loc(@$)); }
+
member
- : var ";"
- | behaviour
+ : param
members
- : members member { $$ = $1; $1->n = $2; }
+ : members ";" member { $$ = $3; $$->n = $1; }
| member
opt_members
- : members
+ : members ";"
| { $$ = NULL; }
type_param
@@ -438,19 +495,53 @@ opt_type_params
: type_params
| { $$ = NULL; }
+element
+ : proc
+ | struct
+ | impl
+ | var ";"
+
+rev_elements
+ : rev_elements element { $$ = $2; $$->n = $1; }
+ | element
+
+elements
+ : rev_elements { $$ = reverse_ast_list($1); }
+
+opt_elements
+ : elements
+ | { $$ = NULL; }
+
+template
+ : ID "[" opt_type_params "]" "(" opt_vars ")" "{" opt_elements "}" {
+ $$ = gen_template($1, $3, $6, $9, src_loc(@$));
+ }
+
+supertemplate
+ : ID "[" opt_type_params "]" "(" opt_vars ")" "="
+ id "[" opt_types "]" "(" opt_exprs ")" "{" opt_elements "}" {
+ struct ast *pseudoinst = gen_instance(NULL, $9, $11, $14, src_loc(@$));
+ $$ = gen_supertemplate($1, $3, $6, pseudoinst, $17, src_loc(@$));
+ }
+
struct
- : ID "[" opt_type_params "]" "{" opt_members "}" {
- $$ = gen_struct($1, $3, $6, src_loc(@$));
+ : ID "{" opt_members "}" {
+ $$ = gen_struct($1, $3, src_loc(@$));
}
struct_cont
- : "continue" ID "[" opt_type_params "]" "{" opt_behaviours "}" {
- $$ = gen_struct_cont($2, $4, $7, src_loc(@$));
+ : "continue" ID "{" opt_behaviours "}" {
+ $$ = gen_instance_cont($2, $4, src_loc(@$));
}
trait
- : ID "{" opt_behaviours "}" {
- $$ = gen_trait($1, $3, src_loc(@$));
+ : ID "=" "{" opt_behaviours "}" {
+ $$ = gen_trait($1, $4, src_loc(@$));
+ }
+
+instance
+ : ID "=" id "[" opt_types "]" "(" opt_exprs ")" {
+ $$ = gen_instance($1, $3, $5, $8, src_loc(@$));
}
import
@@ -464,11 +555,17 @@ top
| struct_cont
| import
| trait
- | "pub" proc { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
- | "pub" struct { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
- | "pub" struct_cont { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
- | "pub" import { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
- | "pub" trait { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
+ | instance
+ | template
+ | supertemplate
+ | "pub" proc { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
+ | "pub" struct { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
+ | "pub" struct_cont { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
+ | "pub" import { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
+ | "pub" trait { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
+ | "pub" instance { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
+ | "pub" template { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
+ | "pub" supertemplate { $$ = $2; ast_set_flags($$, AST_FLAG_PUBLIC); }
| error {
$$ = gen_empty(src_loc(@$));
parser->failed = true;