aboutsummaryrefslogtreecommitdiff
path: root/docs/SYNTAX.md
diff options
context:
space:
mode:
Diffstat (limited to 'docs/SYNTAX.md')
-rw-r--r--docs/SYNTAX.md184
1 files changed, 94 insertions, 90 deletions
diff --git a/docs/SYNTAX.md b/docs/SYNTAX.md
index 49fdd59..a1c8bfb 100644
--- a/docs/SYNTAX.md
+++ b/docs/SYNTAX.md
@@ -1,37 +1,46 @@
# Syntax: A Casual and Formal Look
-...
-
-## A Formal Look
-
-We now shall take a look at a more formal description of Puck's syntax. Syntax rules are described in extended Backus–Naur form (EBNF) - but most rules surrounding whitespace, and scope, and line breaks, are modified to how they would appear after a lexing step (whitespace is removed, line breaks are normalized, scope is switched to use `{` and `}`).
+## Reserved Keywords
+
+The following keywords are reserved:
+- variables: `let` `var` `const`
+- control flow: `if` `elif` `else`
+- pattern matching: `match` `of`
+- loops: `loop` `while` `for` `in`
+- blocks: `block` `break` `continue` `return`
+- functions: `func` `mut` `static` `varargs`
+- modules: `pub` `mod` `use` `as`
+- error handling: `try` `catch` `finally`
+- metaprogramming: `macro` `quote` `when`
+- types: `type` `distinct` `ref`
+- types: `struct` `tuple` `union` `enum` `interface`
+- reserved:
+ - `impl` `object` `class` `concept` `auto` `empty` `effect` `case` `nil`
+ - `suspend` `resume` `spawn` `pool` `thread` `closure`
+ - `cyclic` `acyclic` `sink` `move` `destroy` `copy` `trace` `deepcopy`
+
+## A Formal Grammar
+
+We now shall take a look at a more formal description of Puck's syntax. Syntax rules are described in [extended Backus–Naur form](https://en.wikipedia.org/wiki/Extended_Backus–Naur_form) (EBNF): however, most rules surrounding whitespace, and scope, and line breaks, are modified to how they would appear after a lexing step.
### Identifiers
```
-IDENT ::= LETTER (LETTER | DIGIT | '_')* # todo: support _
-LETTER ::= 'A'..'Z' | 'a'..'z' | '\x80'..'\xff' # todo
-DIGIT ::= '0'..'9'
+Ident ::= (Letter | '_') (Letter | Digit | '_')*
+Letter ::= 'A'..'Z' | 'a'..'z' | '\x80'..'\xff' # todo
+Digit ::= '0'..'9'
```
### Literals
```
-INT_LIT ::= '-'? (DEC_LIT | HEX_LIT | OCT_LIT | BIN_LIT)
-BIN_LIT ::= '0b' BIN_DIGIT ('_'? BIN_DIGIT)*
-OCT_LIT ::= '0o' OCT_DIGIT ('_'? OCT_DIGIT)*
-HEX_LIT ::= '0x' HEX_DIGIT ('_'? HEX_DIGIT)*
-DEC_LIT ::= DIGIT ('_'? DIGIT)*
-BIN_DIGIT ::= '0'..'1'
-OCT_DIGIT ::= '0'..'7'
-HEX_DIGIT ::= DIGIT | 'A'..'F' | 'a'..'f'
-```
-
-### Operators
-```
-OPERATOR ::= 'and' | 'or' | 'not' | 'xor' | 'shl' | 'shr' | # todo: more?
- 'div' | 'mod' | 'rem' | 'is' | 'isnot' | OPR+
-OPR ::= '=' | '+' | '-' | '*' | '/' | '<' | '>' | # todo: more?
- '@' | '$' | '~' | '&' | '%' | '|' |
- '!' | '?' | '^' | '.' | ':' | '\\'
+Int ::= '-'? (DecLit | HexLit | OctLit | BinLit)
+Float ::= '-'? DecLit '.' DecLit
+BinLit ::= '0b' BinDigit ('_'? BinDigit)*
+OctLit ::= '0o' OctDigit ('_'? OctDigit)*
+HexLit ::= '0x' HexDigit ('_'? HexDigit)*
+DecLit ::= Digit ('_'? Digit)*
+BinDigit ::= '0'..'1'
+OctDigit ::= '0'..'7'
+HexDigit ::= Digit | 'A'..'F' | 'a'..'f'
```
### Chars, Strings, and Comments
@@ -52,95 +61,90 @@ PRINT ::= LETTER | DIGIT | OPR |
### Values
```
-VALUE ::= INT_LIT | STRING | CHAR | LIST_DECL | ARRAY_DECL | TUPLE_DECL | STRUCT_DECL
-LIST_DECL ::= '[' (EXPR (',' EXPR)*)? ']'
-ARRAY_DECL ::= '[' (EXPR (',' EXPR)*)? ']'
-TUPLE_DECL ::= '(' (IDENT '=')? EXPR (',' (IDENT '=')? EXPR)* ')'
-STRUCT_DECL ::= '{' IDENT '=' EXPR (',' IDENT '=' EXPR)* '}'
-# note: no union or enum. should struct exist? only in a structural system.
+Value ::= Int | Float | String | Char | Array | Tuple | Struct
+Array ::= '[' (Expr (',' Expr)*)? ']'
+Tuple ::= '(' (Ident ':')? Expr (',' (Ident ':')? Expr)* ')'
+Struct ::= '{' Ident ':' Expr (',' Ident ':' Expr)* '}'
```
### Variables
```
-DECL ::= LET_DECL | VAR_DECL | CONST_DECL | FUNC_DECL | TYPE_DECL
-LET_DECL ::= 'let' GROUP ANNOTATION? '=' EXPR
-VAR_DECL ::= 'var' GROUP ANNOTATION? ('=' EXPR)?
-CONST_DECL ::= 'pub'? 'const' GROUP ANNOTATION? '=' EXPR
-GROUP ::= ('(' IDENT (',' IDENT)* ')') | IDENT
+Decl ::= Let | Var | Const | Func | Type
+Let ::= 'let' Pattern Annotation? '=' Expr
+Var ::= 'var' Pattern Annotation? ('=' Expr)?
+Const ::= 'pub'? 'const' Pattern Annotation? '=' Expr
+Pattern ::= Char | String | Number | Float | Ident | '(' Pattern (',' Pattern)* ')'
+ Ident '(' Pattern (',' Pattern)* ')'
```
-### Functions
+### Declarations
```
-FUNC_DECL ::= SIGNATURE '=' (EXPR | STMT)
-SIGNATURE ::= 'pub'? ('pure' | 'yeet' | IDENT)? 'func' IDENT GENERICS? PARAMETERS?
-PARAMETERS ::= '(' (PARAMETER (',' PARAMETER)?)? ')'
-PARAMETER ::= ('var' | 'static')? IDENT ANNOTATION?
-GENERICS ::= '[' IDENT ANNOTATION? (',' IDENT ANNOTATION?)* ']'
-ANNOTATION ::= ':' TYPE_DESC
+Func ::= 'pub'? 'func' Ident Generics? Parameters? Annotation? '=' Body
+Macro ::= 'pub'? 'macro' Ident Generics? Parameters? Annotation? '=' Body
+Generics ::= '[' Ident Annotation? (',' Ident Annotation?)* ']'
+Parameters ::= '(' Ident Annotation? (',' Ident Annotation?)* ')'
+Annotation ::= ':' Type
```
### Types
```
-TYPE_DECL ::= 'pub'? 'type' IDENT GENERICS? '=' 'ref'? 'distinct'? TYPE_DESC
-TYPE_DESC ::= TUPLE_TYPE | STRUCT_TYPE | UNION_TYPE | ENUM_TYPE | INTERFACE | IDENT |
- (TYPE_DESC ('|' TYPE_DESC)+)
-TUPLE_TYPE ::= 'tuple' '[' (IDENT ':')? TYPE_DESC (',' (IDENT ':')? TYPE_DESC)* ']'
-STRUCT_TYPE ::= 'struct' '[' IDENT ANNOTATION (',' IDENT ANNOTATION)* ']'
-UNION_TYPE ::= 'union' '[' IDENT ANNOTATION (',' IDENT ANNOTATION)* ']'
-ENUM_TYPE ::= 'enum' '[' IDENT ('=' EXPR)? (',' IDENT ('=' EXPR)?)* ']'
-FUNC_TYPE ::= 'func' GENERICS? PARAMETERS? ANNOTATION?
-INTERFACE ::= 'interface' '[' SIGNATURE (',' SIGNATURE)* ('for' TYPE_DESC)? ']'
+TypeDecl ::= 'pub'? 'type' Ident Generics? '=' Type
+Type ::= StructType | TupleType | EnumType | UnionType | Interface |
+ (('distinct' | 'ref' | 'ptr' | 'mut' | 'static') (Type | ('[' Type ']'))?)
+StructType ::= 'struct' ('[' Ident ':' Type (',' Ident ':' Type)* ']')?
+UnionType ::= 'union' ('[' Ident ':' Type (',' Ident ':' Type)* ']')?
+TupleType ::= 'tuple' ('[' (Ident ':')? Type (',' (Ident ':')? Type)* ']')?
+EnumType ::= 'enum' ('[' Ident ('=' Expr)? (',' Ident ('=' Expr)?)* ']')?
+Interface ::= 'interface' ('[' Signature (',' Signature)* ']')?
+Signature ::= Ident Generics? ('(' Type (',' Type)* ')')? Annotation?
```
## Control Flow
```
-IF_EXPR ::= 'if' EXPR '{' EXPR '}' ('elif' EXPR '{' EXPR '}')* 'else' '{' EXPR '}'
-IF_STMT ::= 'if' EXPR '{' STMT '}' ('elif' EXPR '{' STMT '}')* ('else' '{' STMT '}')?
-WHEN_EXPR ::= 'when' EXPR '{' EXPR '}' ('elif' EXPR '{' EXPR '}')* 'else' '{' EXPR '}'
-WHEN_STMT ::= 'when' EXPR '{' STMT '}' ('elif' EXPR '{' EXPR '}')* ('else' '{' STMT '}')?
-BLOCK_EXPR ::= 'block' IDENT? '{' EXPR '}'
-BLOCK_STMT ::= 'block' IDENT? '{' STMT '}'
-MATCH_EXPR ::= 'match' EXPR '{'
- ('case' EXPR ('where' EXPR)? (',' EXPR ('where' EXPR)?)* '{' EXPR '}')+ '}'
-MATCH_STMT ::= 'match' EXPR '{'
- ('case' EXPR ('where' EXPR)? (',' EXPR ('where' EXPR)?)* '{' STMT '}')+ '}'
-LOOP_STMT ::= 'loop' '{' STMT '}'
-WHILE_STMT ::= 'while' EXPR '{' STMT '}'
-FOR_STMT ::= 'for' GROUP 'in' EXPR '{' STMT '}'
+If ::= 'if' Expr ':' Body ('elif' Expr ':' Body)* ('else' ':' Body)?
+When ::= 'when' Expr ':' Body ('elif' Expr ':' Body)* ('else' ':' Body)?
+Try ::= 'try' ':' Body
+ ('except' Ident ('as' Ident)? (',' Ident ('as' Ident)?)*) ':' Body)*
+ ('finally' ':' Body)?
+Match ::= 'match' Expr ('of' Pattern (',' Pattern)* ('where' Expr)? ':' Body)+
+Block ::= 'block' Ident? ':' Body
+Block ::= 'static' ':' Body
+Loop ::= 'loop' ':' Body
+While ::= 'while' Expr ':' Body
+For ::= 'for' Pattern 'in' Expr Body
```
## Modules
```
-IMPORT_STMT ::= 'import' IDENT_AS?
- ('/' (IDENT_AS | '[' (IDENT_AS (',' IDENT_AS)*)? ']'))*
-EXPORT_STMT ::= 'export' IDENT_AS?
- ('/' (IDENT_AS | '[' (IDENT_AS (',' IDENT_AS)*)? ']'))*
-MODULE_STMT ::= 'module' IDENT '{' STMT '}'
-IDENT_AS ::= IDENT ('as' IDENT)?
+Mod ::= 'pub'? 'mod' Ident ':' Body
+Use ::= 'use' Ident ('/' Ident)* ('/' ('[' Ident (',' Ident)* ']'))?
```
-## Macros
+### Operators
```
-MACRO_FUNC ::= IDENT '(' EXPR ')'
-MACRO_BLOCK ::= IDENT '{' EXPR '}' # todo
+Operator ::= 'and' | 'or' | 'not' | 'xor' | 'shl' | 'shr' |
+ 'div' | 'mod' | 'rem' | 'is' | 'in' |
+ Opr+
+Opr ::= '=' | '+' | '-' | '*' | '/' | '<' | '>' |
+ '@' | '$' | '~' | '&' | '%' | '|' |
+ '!' | '?' | '^' | '.' | ':' | '\\'
```
-## Calls, Statements, and Expressions
+## Calls and Expressions
```
-OPERATION ::= EXPR OPERATOR EXPR
-PREFIX ::= OPERATOR EXPR
-SUFFIX ::= EXPR OPERATOR
-APPLICATION ::= IDENT PARAMS? | IDENT EXPR | (APPLICATION | PREFIX | SUFFIX) '.' IDENT PARAMS?
-PARAMS ::= '(' ((IDENT '=')? EXPR (',' (IDENT '=')? EXPR)*)? ')'
+Call ::= Ident ('[' Call (',' Call)* ']')? ('(' (Ident '=')? Call (',' (Ident '=')? Call)* ')')? |
+ Ident Call (',' Call)* |
+ Call Operator Call? |
+ Call ':' Body
+Expr ::= Let | Var | Const | Func | Type | Mod | Use | Block | Static |
+ For | While | Loop | If | When | Try | Match | Call
+Body ::= Expr | ('{' Expr (';' Expr)* '}')
```
-```
-EXPR ::= IF_EXPR | WHEN_EXPR | BLOCK_EXPR | MATCH_EXPR |
- MACRO_FUNC | MACRO_BLOCK |
- APPLICATION | OPERATION | PREFIX | SUFFIX |
- VALUE | (STMT EXPR) # todo
-STMT ::= IF_STMT | WHEN_STMT | BLOCK_STMT | MATCH_STMT |
- LOOP_STMT | WHILE_STMT | FOR_STMT |
- IMPORT_STMT | EXPORT_STMT | MODULE_STMT |
- ((APPLICATION | OPERATION | PREFIX | SUFFIX | DECL) ';') | (STMT+ STMT)
-```
+---
+
+References:
+- https://www.joshwcomeau.com/javascript/statements-vs-expressions/
+- https://pgrandinetti.github.io/compilers/
+- https://docs.swift.org/swift-book/ReferenceManual/LexicalStructure.html
+- https://nim-lang.github.io/Nim/manual.html