hare

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

commit 388150902e42e135401a2af61fe02784d82f0fba
parent f24d7709d5a2c26db8c070ebe7d2fa8203c9e40a
Author: Alexey Yerin <yyp@disroot.org>
Date:   Fri,  7 May 2021 11:29:21 +0300

hare::parse: handle pointer types in match cases

Earlier match_expr was assuming that * always means default case, which
is not always true for pointers.

Now we also check for => after *, and only then set as the default match
case. In other cases, parse this as a type and wrap it in a pointer
(because it's not possible to unlex 2+ tokens).

Minimal reproduction of the bug:

    match (x) {
    	nullable *foo => spam,
    	*bar => eggs,
    	* => void,
    };

Fixes #420

Diffstat:
Mhare/parse/expr.ha | 24++++++++++++++++++++----
1 file changed, 20 insertions(+), 4 deletions(-)

diff --git a/hare/parse/expr.ha b/hare/parse/expr.ha @@ -984,11 +984,27 @@ fn match_expr(lexer: *lex::lexer) (ast::expr | error) = { match (try(lexer, ltok::TIMES)?) { void => append(cases, match_case(lexer)?), t: lex::token => { - want(lexer, ltok::CASE)?; - if (default != null) { - return syntaxerr(t.2, "More than one default match case"); + match (peek(lexer, ltok::NAME)?) { + t: lex::token => { + let case = match_case(lexer)?; + case._type = alloc(ast::_type { + loc = case._type.loc, + flags = 0, + _type = ast::pointer_type { + referent = case._type, + flags = 0: ast::pointer_flags, + }, + }); + append(cases, case); + }, + void => { + want(lexer, ltok::CASE)?; + if (default != null) { + return syntaxerr(t.2, "More than one default match case"); + }; + default = alloc(expression(lexer)?); + }, }; - default = alloc(expression(lexer)?); }, };