commit 27f960cc6387f9ee0ef5003a55580105bc939662
parent f476566936a2477e30caab1cfbd90257d873a851
Author: Sebastian <sebastian@sebsite.pw>
Date: Fri, 29 Sep 2023 22:19:50 -0400
hare::ast: remove default field from match_expr
The _type field in match_case is already nullable, and not separating
the two preserves the location of the default case relative to the other
cases within the AST.
This removes the check in hare::parse for a duplicate default case,
which is fine since this doesn't belong in the parser anyway.
Signed-off-by: Sebastian <sebastian@sebsite.pw>
Diffstat:
3 files changed, 5 insertions(+), 33 deletions(-)
diff --git a/hare/ast/expr.ha b/hare/ast/expr.ha
@@ -312,7 +312,7 @@ export type len_expr = *expr;
// case let name: type => exprs
export type match_case = struct {
name: str,
- _type: nullable *_type,
+ _type: nullable *_type, // null for default case
exprs: []*expr,
};
@@ -322,7 +322,6 @@ export type match_case = struct {
export type match_expr = struct {
value: *expr,
cases: []match_case,
- default: []*expr,
};
// An offset expression.
@@ -566,10 +565,6 @@ case let e: expr =>
free(exprs);
};
free(m.cases);
- for (let i = 0z; i < len(m.default); i += 1) {
- expr_finish(m.default[i]);
- };
- free(m.default);
case let o: offset_expr =>
expr_finish(o: *expr);
case let p: propagate_expr =>
diff --git a/hare/parse/expr.ha b/hare/parse/expr.ha
@@ -1139,6 +1139,7 @@ fn switch_expr(lexer: *lex::lexer) (ast::expr | error) = {
};
fn match_case(lexer: *lex::lexer) (ast::match_case | error) = {
+ want(lexer, ltok::CASE)?;
let tok = lex::lex(lexer)?;
let loc = tok.2;
let name: str = "", typ: nullable *ast::_type = null;
@@ -1154,7 +1155,8 @@ fn match_case(lexer: *lex::lexer) (ast::match_case | error) = {
name = want(lexer, ltok::NAME)?.1 as str;
want(lexer, ltok::COLON)?;
typ = alloc(_type(lexer)?);
- case ltok::ARROW => void;
+ case ltok::ARROW =>
+ lex::unlex(lexer, tok);
case =>
lex::unlex(lexer, tok);
typ = alloc(_type(lexer)?);
@@ -1183,24 +1185,8 @@ fn match_expr(lexer: *lex::lexer) (ast::expr | error) = {
want(lexer, ltok::LBRACE)?;
let cases: []ast::match_case = [];
- let default: []*ast::expr = [];
for (true) {
- want(lexer, ltok::CASE)?;
-
- match (try(lexer, ltok::ARROW)?) {
- case let t: lex::token =>
- if (len(default) != 0) {
- return syntaxerr(t.2,
- "More than one default match case");
- };
- for (peek(lexer, ltok::CASE, ltok::RBRACE)? is void) {
- append(default, alloc(expr(lexer)?));
- want(lexer, ltok::SEMICOLON)?;
- };
- case void =>
- append(cases, match_case(lexer)?);
- };
-
+ append(cases, match_case(lexer)?);
if (try(lexer, ltok::RBRACE)? is lex::token) {
break;
};
@@ -1212,7 +1198,6 @@ fn match_expr(lexer: *lex::lexer) (ast::expr | error) = {
expr = ast::match_expr {
value = alloc(value),
cases = cases,
- default = default,
},
};
};
diff --git a/hare/unparse/expr.ha b/hare/unparse/expr.ha
@@ -869,14 +869,6 @@ fn match_expr(
z += case_exprs(ctx, syn, item.exprs)?;
};
- if (len(e.default) != 0) {
- z += newline(ctx)?;
- z += syn(ctx, "case", synkind::KEYWORD)?;
- z += space(ctx)?;
- z += syn(ctx, "=>", synkind::OPERATOR)?;
- z += case_exprs(ctx, syn, e.default)?;
- };
-
z += newline(ctx)?;
z += syn(ctx, "}", synkind::PUNCTUATION)?;
return z;