diff options
| author | Michael Williamson <mike@zwobble.org> | 2023-09-30 11:01:22 +0100 |
|---|---|---|
| committer | Michael Williamson <mike@zwobble.org> | 2023-09-30 11:01:22 +0100 |
| commit | 107ce1646e24b0d30f7fc42e831a7e5f03daecc3 (patch) | |
| tree | bdcf0c83b78e5ef4272964b9fdfe3735f301eb29 /src/main/java | |
| parent | fa6b2a24aad096824790501550623a7c3c2418c1 (diff) | |
Parse when expressions
Diffstat (limited to 'src/main/java')
7 files changed, 70 insertions, 2 deletions
diff --git a/src/main/java/org/shedlang/compiler/ast/untyped/UntypedExpressionNode.java b/src/main/java/org/shedlang/compiler/ast/untyped/UntypedExpressionNode.java index b1d7ba83..107bc20b 100644 --- a/src/main/java/org/shedlang/compiler/ast/untyped/UntypedExpressionNode.java +++ b/src/main/java/org/shedlang/compiler/ast/untyped/UntypedExpressionNode.java @@ -1,5 +1,5 @@ package org.shedlang.compiler.ast.untyped; public sealed interface UntypedExpressionNode extends UntypedNode - permits UntypedBinaryOperationNode, UntypedBoolLiteralNode, UntypedCallNode, UntypedFieldAccessNode, UntypedIfNode, UntypedIntLiteralNode, UntypedReferenceNode, UntypedStringLiteralNode, UntypedTupleNode { + permits UntypedBinaryOperationNode, UntypedBoolLiteralNode, UntypedCallNode, UntypedFieldAccessNode, UntypedIfNode, UntypedIntLiteralNode, UntypedReferenceNode, UntypedStringLiteralNode, UntypedTupleNode, UntypedWhenNode { } diff --git a/src/main/java/org/shedlang/compiler/ast/untyped/UntypedWhenCaseNode.java b/src/main/java/org/shedlang/compiler/ast/untyped/UntypedWhenCaseNode.java new file mode 100644 index 00000000..7b3e95b9 --- /dev/null +++ b/src/main/java/org/shedlang/compiler/ast/untyped/UntypedWhenCaseNode.java @@ -0,0 +1,10 @@ +package org.shedlang.compiler.ast.untyped; + +import org.shedlang.compiler.sources.Source; + +public record UntypedWhenCaseNode( + UntypedTypeLevelExpressionNode caseType, + UntypedBlockNode body, + Source source +) implements UntypedNode { +} diff --git a/src/main/java/org/shedlang/compiler/ast/untyped/UntypedWhenNode.java b/src/main/java/org/shedlang/compiler/ast/untyped/UntypedWhenNode.java new file mode 100644 index 00000000..e8c2d348 --- /dev/null +++ b/src/main/java/org/shedlang/compiler/ast/untyped/UntypedWhenNode.java @@ -0,0 +1,12 @@ +package org.shedlang.compiler.ast.untyped; + +import org.shedlang.compiler.sources.Source; + +import java.util.List; + +public record UntypedWhenNode( + UntypedExpressionNode expression, + List<UntypedWhenCaseNode> cases, + Source source +) implements UntypedExpressionNode { +} diff --git a/src/main/java/org/shedlang/compiler/parser/Parser.java b/src/main/java/org/shedlang/compiler/parser/Parser.java index 84900688..71490933 100644 --- a/src/main/java/org/shedlang/compiler/parser/Parser.java +++ b/src/main/java/org/shedlang/compiler/parser/Parser.java @@ -540,6 +540,8 @@ public class Parser { case KEYWORD_IF -> parseIf(tokens); case KEYWORD_FALSE, KEYWORD_TRUE -> parseBoolLiteral(tokens); + + case KEYWORD_WHEN -> parseWhen(tokens); case STRING -> parseStringLiteral(tokens); @@ -812,7 +814,6 @@ public class Parser { return new UntypedTupleTypeNode(elements, source); } - private static UntypedTypeLevelReferenceNode parseTypeLevelReference(TokenIterator<TokenType> tokens) { var start = tokens.position(); @@ -824,6 +825,44 @@ public class Parser { return new UntypedTypeLevelReferenceNode(name, source); } + private static UntypedExpressionNode parseWhen(TokenIterator<TokenType> tokens) { + var start = tokens.position(); + + tokens.skip(TokenType.KEYWORD_WHEN); + + tokens.skip(TokenType.SYMBOL_PAREN_OPEN); + var expression = parseTopLevelExpression(tokens); + tokens.skip(TokenType.SYMBOL_PAREN_CLOSE); + + tokens.skip(TokenType.SYMBOL_BRACE_OPEN); + var cases = parseMany( + () -> tokens.isNext(TokenType.SYMBOL_BRACE_CLOSE), + () -> parseWhenCase(tokens), + () -> true + ); + tokens.skip(TokenType.SYMBOL_BRACE_CLOSE); + + var end = tokens.position(); + var source = start.to(end); + + return new UntypedWhenNode(expression, cases, source); + } + + private static UntypedWhenCaseNode parseWhenCase(TokenIterator<TokenType> tokens) { + var start = tokens.position(); + + tokens.skip(TokenType.KEYWORD_IS); + + var caseType = parseTopLevelTypeLevelExpression(tokens); + + var body = parseBlock(tokens); + + var end = tokens.position(); + var source = start.to(end); + + return new UntypedWhenCaseNode(caseType, body, source); + } + private static UntypedFunctionStatementNode parseWhile( TokenIterator<TokenType> tokens ) { diff --git a/src/main/java/org/shedlang/compiler/parser/TokenType.java b/src/main/java/org/shedlang/compiler/parser/TokenType.java index 9c8183dc..e2350ae2 100644 --- a/src/main/java/org/shedlang/compiler/parser/TokenType.java +++ b/src/main/java/org/shedlang/compiler/parser/TokenType.java @@ -14,12 +14,14 @@ public enum TokenType { KEYWORD_FALSE, KEYWORD_FUN, KEYWORD_IF, + KEYWORD_IS, KEYWORD_RETURN, KEYWORD_STRUCT, KEYWORD_SUMTYPE, KEYWORD_TRUE, KEYWORD_VAL, KEYWORD_VAR, + KEYWORD_WHEN, KEYWORD_WHILE, SYMBOL_BANG, diff --git a/src/main/java/org/shedlang/compiler/parser/Tokeniser.java b/src/main/java/org/shedlang/compiler/parser/Tokeniser.java index 7659d717..e7f04189 100644 --- a/src/main/java/org/shedlang/compiler/parser/Tokeniser.java +++ b/src/main/java/org/shedlang/compiler/parser/Tokeniser.java @@ -18,12 +18,14 @@ public class Tokeniser { Map.entry("false", TokenType.KEYWORD_FALSE), Map.entry("fun", TokenType.KEYWORD_FUN), Map.entry("if", TokenType.KEYWORD_IF), + Map.entry("is", TokenType.KEYWORD_IS), Map.entry("return", TokenType.KEYWORD_RETURN), Map.entry("struct", TokenType.KEYWORD_STRUCT), Map.entry("sumtype", TokenType.KEYWORD_SUMTYPE), Map.entry("true", TokenType.KEYWORD_TRUE), Map.entry("val", TokenType.KEYWORD_VAL), Map.entry("var", TokenType.KEYWORD_VAR), + Map.entry("when", TokenType.KEYWORD_WHEN), Map.entry("while", TokenType.KEYWORD_WHILE) ); diff --git a/src/main/java/org/shedlang/compiler/typechecker/TypeChecker.java b/src/main/java/org/shedlang/compiler/typechecker/TypeChecker.java index 7c3741e2..c630b9dc 100644 --- a/src/main/java/org/shedlang/compiler/typechecker/TypeChecker.java +++ b/src/main/java/org/shedlang/compiler/typechecker/TypeChecker.java @@ -406,6 +406,9 @@ public class TypeChecker { case UntypedTupleNode untypedTuple -> typeCheckTuple(untypedTuple, context); + + case UntypedWhenNode untypedWhen -> + throw new UnsupportedOperationException(); }; } |
