aboutsummaryrefslogtreecommitdiff
path: root/parse.c
diff options
context:
space:
mode:
authorBruce Hill <bruce@bruce-hill.com>2024-04-28 14:58:55 -0400
committerBruce Hill <bruce@bruce-hill.com>2024-04-28 14:58:55 -0400
commit3c0a8f0b899a343f43caf9c95147b2cf77a7b525 (patch)
treeb7193a8021ef9ab57c71319ecad797bf51849025 /parse.c
parent5910998a19aab5dab2c761aea946cfbb09a37918 (diff)
Syntax tweak: use ':' for blocks
Diffstat (limited to 'parse.c')
-rw-r--r--parse.c66
1 files changed, 40 insertions, 26 deletions
diff --git a/parse.c b/parse.c
index e325ebf4..e3fdbb49 100644
--- a/parse.c
+++ b/parse.c
@@ -781,8 +781,10 @@ PARSER(parse_reduction) {
}
ast_t *fallback = NULL;
- if (match_word(&pos, "else"))
+ if (match_word(&pos, "else")) {
+ expect_str(ctx, start, &pos, ":", "I expected a ':' here");
fallback = expect(ctx, pos-4, &pos, parse_expr, "I couldn't parse the expression after this 'else'");
+ }
return NewAST(ctx->file, start, pos, Reduction, .iter=iter, .combination=combination, .fallback=fallback);
}
@@ -838,7 +840,7 @@ PARSER(parse_if) {
if (!condition) condition = expect(ctx, start, &pos, parse_expr,
"I expected to find an expression for this 'if'");
- match_word(&pos, "then"); // optional
+ expect_str(ctx, start, &pos, ":", "I expected a ':' here");
ast_t *body = expect(ctx, start, &pos, parse_opt_indented_block, "I expected a body for this 'if' statement");
@@ -848,6 +850,7 @@ PARSER(parse_if) {
const char *else_start = pos;
if (get_indent(ctx->file, tmp) == starting_indent && match_word(&tmp, "else")) {
pos = tmp;
+ expect_str(ctx, start, &pos, ":", "I expected a ':' here");
else_body = expect(ctx, else_start, &pos, parse_opt_indented_block, "I expected a body for this 'else'");
}
return NewAST(ctx->file, start, pos, If, .condition=condition, .body=body, .else_body=else_body);
@@ -881,7 +884,8 @@ PARSER(parse_when) {
var = NULL;
}
- match_word(&pos, "then"); // optional
+ expect_str(ctx, start, &pos, ":", "I expected a ':' here");
+
ast_t *body = expect(ctx, start, &pos, parse_opt_indented_block, "I expected a body for this 'when' clause");
clauses = new(when_clause_t, .var=var, .tag_name=tag_name, .body=body, .next=clauses);
tmp = pos;
@@ -893,6 +897,7 @@ PARSER(parse_when) {
const char *else_start = pos;
if (get_indent(ctx->file, tmp) == starting_indent && match_word(&tmp, "else")) {
pos = tmp;
+ expect_str(ctx, start, &pos, ":", "I expected a ':' here");
else_body = expect(ctx, else_start, &pos, parse_opt_indented_block, "I expected a body for this 'else'");
}
return NewAST(ctx->file, start, pos, When, .subject=subject, .clauses=clauses, .else_body=else_body);
@@ -911,6 +916,7 @@ PARSER(parse_for) {
}
expect_str(ctx, start, &pos, "in", "I expected an 'in' for this 'for'");
ast_t *iter = expect(ctx, start, &pos, parse_expr, "I expected an iterable value for this 'for'");
+ expect_str(ctx, start, &pos, ":", "I expected a ':' here");
match(&pos, "do"); // optional
ast_t *body = expect(ctx, start, &pos, parse_opt_indented_block, "I expected a body for this 'for'");
@@ -919,6 +925,7 @@ PARSER(parse_for) {
ast_t *empty = NULL;
if (match_word(&else_start, "else") && get_indent(ctx->file, else_start) == starting_indent) {
pos = else_start;
+ expect_str(ctx, start, &pos, ":", "I expected a ':' here");
empty = expect(ctx, pos, &pos, parse_opt_indented_block, "I expected a body for this 'else'");
}
return NewAST(ctx->file, start, pos, For, .index=value ? index : NULL, .value=value ? value : index, .iter=iter, .body=body, .empty=empty);
@@ -929,7 +936,7 @@ PARSER(parse_while) {
const char *start = pos;
if (!match_word(&pos, "while")) return NULL;
ast_t *condition = expect(ctx, start, &pos, parse_expr, "I don't see a viable condition for this 'while'");
- match(&pos, "do"); // optional
+ expect_str(ctx, start, &pos, ":", "I expected a ':' here");
ast_t *body = expect(ctx, start, &pos, parse_opt_indented_block, "I expected a body for this 'while'");
const char *tmp = pos;
whitespace(&tmp);
@@ -1603,7 +1610,7 @@ PARSER(parse_file_body) {
}
PARSER(parse_struct_def) {
- // struct Foo(...) \n body
+ // struct Foo(...) [: \n body]
const char *start = pos;
if (!match_word(&pos, "struct")) return NULL;
@@ -1636,13 +1643,15 @@ PARSER(parse_struct_def) {
expect_closing(ctx, &pos, ")", "I wasn't able to parse the rest of this struct");
- const char *ns_pos = pos;
- whitespace(&ns_pos);
- int64_t ns_indent = get_indent(ctx->file, ns_pos);
ast_t *namespace = NULL;
- if (ns_indent > starting_indent) {
- pos = ns_pos;
- namespace = optional(ctx, &pos, parse_namespace);
+ if (match(&pos, ":")) {
+ const char *ns_pos = pos;
+ whitespace(&ns_pos);
+ int64_t ns_indent = get_indent(ctx->file, ns_pos);
+ if (ns_indent > starting_indent) {
+ pos = ns_pos;
+ namespace = optional(ctx, &pos, parse_namespace);
+ }
}
if (!namespace)
namespace = NewAST(ctx->file, pos, pos, Block, .statements=NULL);
@@ -1650,7 +1659,7 @@ PARSER(parse_struct_def) {
}
ast_t *parse_enum_def(parse_ctx_t *ctx, const char *pos) {
- // tagged union: enum Foo[a, b(x:Int,y:Int)=5, ...] \n namespace
+ // tagged union: enum Foo(a, b(x:Int,y:Int)=5, ...) [: \n namespace]
const char *start = pos;
if (!match_word(&pos, "enum")) return NULL;
int64_t starting_indent = get_indent(ctx->file, pos);
@@ -1713,13 +1722,15 @@ ast_t *parse_enum_def(parse_ctx_t *ctx, const char *pos) {
REVERSE_LIST(tags);
- const char *ns_pos = pos;
- whitespace(&ns_pos);
- int64_t ns_indent = get_indent(ctx->file, ns_pos);
ast_t *namespace = NULL;
- if (ns_indent > starting_indent) {
- pos = ns_pos;
- namespace = optional(ctx, &pos, parse_namespace);
+ if (match(&pos, ":")) {
+ const char *ns_pos = pos;
+ whitespace(&ns_pos);
+ int64_t ns_indent = get_indent(ctx->file, ns_pos);
+ if (ns_indent > starting_indent) {
+ pos = ns_pos;
+ namespace = optional(ctx, &pos, parse_namespace);
+ }
}
if (!namespace)
namespace = NewAST(ctx->file, pos, pos, Block, .statements=NULL);
@@ -1729,7 +1740,7 @@ ast_t *parse_enum_def(parse_ctx_t *ctx, const char *pos) {
PARSER(parse_lang_def) {
const char *start = pos;
- // lang Name [namespace...]
+ // lang Name: [namespace...]
if (!match_word(&pos, "lang")) return NULL;
int64_t starting_indent = get_indent(ctx->file, pos);
spaces(&pos);
@@ -1738,13 +1749,15 @@ PARSER(parse_lang_def) {
parser_err(ctx, start, pos, "I expected a name for this lang");
spaces(&pos);
- const char *ns_pos = pos;
- whitespace(&ns_pos);
- int64_t ns_indent = get_indent(ctx->file, ns_pos);
ast_t *namespace = NULL;
- if (ns_indent > starting_indent) {
- pos = ns_pos;
- namespace = optional(ctx, &pos, parse_namespace);
+ if (match(&pos, ":")) {
+ const char *ns_pos = pos;
+ whitespace(&ns_pos);
+ int64_t ns_indent = get_indent(ctx->file, ns_pos);
+ if (ns_indent > starting_indent) {
+ pos = ns_pos;
+ namespace = optional(ctx, &pos, parse_namespace);
+ }
}
if (!namespace)
namespace = NewAST(ctx->file, pos, pos, Block, .statements=NULL);
@@ -1843,9 +1856,10 @@ PARSER(parse_func_def) {
type_ast_t *ret_type = NULL;
spaces(&pos);
- if (match(&pos, "->") || match(&pos, ":"))
+ if (match(&pos, "->"))
ret_type = optional(ctx, &pos, parse_type);
+ expect_str(ctx, start, &pos, ":", "I expected a ':' here");
ast_t *body = expect(ctx, start, &pos, parse_opt_indented_block,
"This function needs a body block");
return NewAST(ctx->file, start, pos, FunctionDef,