let const_uint int = 123;
let const_string string = "";
-var var_true bool = true
-var var_false bool = false
-var var_uint int = 123
-var var_string string = ""
+var var_true bool = true;
+var var_false bool = false;
+var var_uint int = 123;
+var var_string string = "";
type type_int = int;
-# type type_intary int[]
-# type type_intary42 int[42]
-# type type_intaryary int[][]
-# type type_intptrary int*[]
-# type type_intrefary int&[]
-# type type_intptr int*
-# type type_intptrptr int**
-# type type_intref int&
+type type_intary = int[];
+type type_intaryary = int[][];
+type type_intptrary = int*[];
+type type_intptr = int*;
+type type_intptrptr = int**;
+type type_struct = struct {
+ foo = int;
+ bar = float;
+};
+type type_union = union {
+ foo = int;
+ bar = float;
+};
fun main() int {
}
[ \t\r\n] { /* whitespace is insignificant */ }
#.*[\r\n] { /* skip line comments */ }
-"require" { return T_REQUIRES; }
-"provide" { return T_PROVIDES; }
-"let" { return T_LET; }
-"var" { return T_VAR; }
-"fun" { return T_FUN; }
-"type" { return T_TYPE; }
+"require" { return T_REQUIRES; }
+"provide" { return T_PROVIDES; }
+"let" { return T_LET; }
+"var" { return T_VAR; }
+"fun" { return T_FUN; }
+"type" { return T_TYPE; }
+"struct" { return T_STRUCT; }
+"union" { return T_UNION; }
"if" { return T_IF; }
"else" { return T_ELSE; }
"&" { return T_AMP; }
"=" { return T_ASSIGN; }
";" { return T_SEMI; }
+"*" { return T_MUL; }
\\. { Value.character = yytext[1]; return T_CHAR; }
\\space { Value.character = ' '; return T_CHAR; }
static AST* type_definition(Parser* p);
static AST* func_definition(Parser* p);
static AST* type_expression(Parser* p);
+static AST* struct_fields(Parser* p);
static AST* const_expression(Parser* p);
static AST* definition(Parser* p);
static AST* expression(Parser* p);
/* Grammar Definition
*****************************************************************************/
AST* toplevel(Parser* p) {
- if (matches(p, T_REQUIRES)) {
+ if (matches(p, T_REQUIRES))
require_list(p);
- }
- if (matches(p, T_PROVIDES)) {
+ if (matches(p, T_PROVIDES))
provide_list(p);
- }
definition_list(p);
return NULL;
}
}
static AST* type_expression(Parser* p) {
- expect(p, T_ID);
+ if (matches(p, T_STRUCT)) {
+ expect(p, T_STRUCT);
+ struct_fields(p);
+ } else if (matches(p, T_UNION)) {
+ expect(p, T_UNION);
+ struct_fields(p);
+ } else {
+ expect(p, T_ID);
+ }
+ while (matches(p, T_MUL) || matches(p, T_LBRACK)) {
+ if (matches(p, T_LBRACK)) {
+ expect(p, T_LBRACK);
+ expect(p, T_RBRACK);
+ } else {
+ expect(p, T_MUL);
+ }
+ }
return NULL;
}
+static AST* struct_fields(Parser* p) {
+ expect(p, T_LBRACE);
+ do {
+ expect(p, T_ID);
+ expect(p, T_ASSIGN);
+ type_expression(p);
+ expect(p, T_SEMI);
+ } while(!matches(p, T_RBRACE));
+ expect(p, T_RBRACE);
+ return NULL;
+}
*****************************************************************************/
typedef enum {
T_NONE, T_ERROR, T_END_FILE,
- T_PACKAGE, T_REQUIRES, T_PROVIDES, T_LET, T_VAR, T_FUN, T_TYPE,
+ T_PACKAGE, T_REQUIRES, T_PROVIDES, T_LET, T_VAR, T_FUN, T_TYPE, T_STRUCT,
+ T_UNION,
T_ID, T_CHAR, T_INT, T_FLOAT, T_BOOL, T_STRING,
T_LBRACE, T_RBRACE, T_LBRACK, T_RBRACK, T_LPAR, T_RPAR, T_COMMA, T_SQUOTE,
- T_DQUOTE, T_COLON, T_AMP, T_IF, T_ELSE, T_ASSIGN, T_SEMI
+ T_DQUOTE, T_COLON, T_AMP, T_IF, T_ELSE, T_ASSIGN, T_SEMI, T_MUL
} TokType;
typedef struct {