luna_lib/luna_impl/
parser.rs

1use super::position::{Located, Position};
2use crate::lang::{ast::*, tokens::Token};
3use std::{error::Error, fmt::Display, iter::Peekable, vec::IntoIter};
4
5pub type Parser = Peekable<IntoIter<Located<Token>>>;
6pub trait Parsable
7where
8    Self: Sized,
9{
10    fn parse(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>>;
11}
12#[derive(Debug, Clone, PartialEq)]
13pub enum ParseError {
14    UnexpectedEOF,
15    UnexpectedToken(Token),
16    ExpectedToken { expected: Token, got: Token },
17    ExpectedIdentNotPath,
18    MultipleParams,
19    NoExprs,
20    MultipleExprs,
21}
22impl Display for ParseError {
23    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
24        match self {
25            ParseError::UnexpectedEOF => write!(f, "unexpected end of file"),
26            ParseError::UnexpectedToken(token) => write!(f, "unexpected {}", token.name()),
27            ParseError::ExpectedToken { expected, got } => {
28                write!(f, "expected {}, got {}", expected.name(), got.name())
29            }
30            ParseError::ExpectedIdentNotPath => write!(
31                f,
32                "expected {} not a path",
33                Token::Ident(Default::default()).name()
34            ),
35            ParseError::MultipleParams => write!(f, "multiple parameters not allowed for let-else"),
36            ParseError::NoExprs => write!(f, "expected one expression for let-else"),
37            ParseError::MultipleExprs => write!(f, "multiple expressions not allowed for let-else"),
38        }
39    }
40}
41impl Error for ParseError {}
42
43macro_rules! expect {
44    ($parser:ident) => {{
45        let Some(loc_token) = $parser.next() else {
46            return Err(Located::new(ParseError::UnexpectedEOF, Position::default()));
47        };
48        loc_token
49    }};
50}
51macro_rules! expect_token {
52    ($parser:ident : $expect:ident) => {{
53        let Located {
54            value: token,
55            pos: token_pos,
56        } = expect!($parser);
57        if token != Token::$expect {
58            return Err(Located::new(
59                ParseError::ExpectedToken {
60                    expected: Token::$expect,
61                    got: token,
62                },
63                token_pos,
64            ));
65        }
66        token_pos
67    }};
68}
69macro_rules! if_token {
70    ($parser:ident : $token:ident : _ => $body:block $(else $else:block)?) => {{
71        if matches!(
72            $parser.peek(),
73            Some(Located {
74                value: Token::$token(_),
75                pos: _
76            })
77        ) {
78            $parser.next();
79            $body
80        } $(else $else)?
81    }};
82    ($parser:ident : $token:ident : $ident:ident $pos:ident => $body:block $(else $else:block)?) => {{
83        if matches!(
84            $parser.peek(),
85            Some(Located {
86                value: Token::$token(_),
87                pos: _
88            })
89        ) {
90            let Located {
91                value: Token::$token($ident),
92                pos: $pos,
93            } = $parser.next().unwrap() else {
94                panic!();
95            };
96            $body
97        } $(else $else)?
98    }};
99    ($parser:ident : $token:ident $pos:pat => $body:block $(else $else:block)?) => {{
100        if matches!(
101            $parser.peek(),
102            Some(Located {
103                value: Token::$token,
104                pos: $pos
105            })
106        ) $body $(else $else)?
107    }};
108    ($parser:ident : $token:ident => $body:block $(else $else:block)?) => {{
109        if matches!(
110            $parser.peek(),
111            Some(Located {
112                value: Token::$token,
113                pos: _
114            })
115        ) {
116            $parser.next();
117            $body
118        } $(else $else)?
119    }};
120}
121macro_rules! skip_token {
122    ($parser:ident : $token:ident) => {{
123        if matches!(
124            $parser.peek(),
125            Some(Located {
126                value: Token::$token,
127                pos: _
128            })
129        ) {
130            $parser.next();
131        }
132    }};
133}
134macro_rules! while_match {
135    ($parser:ident : $token:ident $pos:pat => $body:block) => {{
136        while matches!(
137            $parser.peek(),
138            Some(Located {
139                value: Token::$token,
140                pos: $pos
141            })
142        ) $body
143    }};
144    ($parser:ident : $token:ident $body:block) => {{
145        while matches!(
146            $parser.peek(),
147            Some(Located {
148                value: Token::$token,
149                pos: _
150            })
151        ) {
152            $parser.next();
153            $body
154        }
155    }};
156}
157macro_rules! until_match {
158    ($parser:ident : $token:ident $body:block) => {{
159        while let Some(Located {
160            value: token,
161            pos: _,
162        }) = $parser.peek()
163        {
164            if token == &Token::$token {
165                break;
166            }
167            $body
168        }
169        expect_token!($parser: $token)
170    }};
171}
172
173impl Parsable for Chunk {
174    fn parse(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
175        let mut stats = vec![];
176        let mut pos = Position::default();
177        while parser.peek().is_some() {
178            let stat = Statement::parse(parser)?;
179            pos.extend(&stat.pos);
180            stats.push(stat);
181        }
182        Ok(Located::new(Self(stats), pos))
183    }
184}
185impl Parsable for Block {
186    fn parse(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
187        let mut pos = expect_token!(parser: BraceLeft);
188        let mut stats = vec![];
189        let end_pos = until_match!(parser: BraceRight {
190            let stat = Statement::parse(parser)?;
191            pos.extend(&stat.pos);
192            stats.push(stat);
193        });
194        pos.extend(&end_pos);
195        Ok(Located::new(Self(stats), pos))
196    }
197}
198impl Statement {
199    pub fn parse_let(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
200        let Located { value: _, mut pos } = parser.next().unwrap();
201        if_token!(parser: Fn _ => {
202            return Self::parse_fn(parser, true);
203        });
204        let mut params = vec![];
205        let mut exprs = vec![];
206        let ident = Parameter::parse(parser)?;
207        pos.extend(&ident.pos);
208        params.push(ident);
209        while_match!(parser: Comma {
210            let ident = Path::ident(parser)?;
211            pos.extend(&ident.pos);
212            params.push(Parameter::parse(parser)?);
213        });
214        if_token!(parser: Equal => {
215            let expr = Expression::parse(parser)?;
216            pos.extend(&expr.pos);
217            exprs.push(expr);
218            while_match!(parser: Comma {
219                let expr = Expression::parse(parser)?;
220                pos.extend(&expr.pos);
221                exprs.push(expr);
222            });
223        });
224        if_token!(parser: Else => {
225            if params.len() > 1 {
226                return Err(Located::new(ParseError::MultipleParams, pos))
227            }
228            if exprs.is_empty() {
229                return Err(Located::new(ParseError::NoExprs, pos))
230            }
231            if exprs.len() > 1 {
232                return Err(Located::new(ParseError::MultipleExprs, pos))
233            }
234            let else_case = Block::parse(parser)?;
235            pos.extend(&else_case.pos);
236            Ok(Located::new(Self::LetElse { param: params.remove(0), expr: exprs.remove(0), else_case }, pos))
237        } else {
238            Ok(Located::new(Self::LetBinding { params, exprs }, pos))
239        })
240    }
241    pub fn parse_fn(
242        parser: &mut Parser,
243        local: bool,
244    ) -> Result<Located<Self>, Located<ParseError>> {
245        let Located { value: _, mut pos } = parser.next().unwrap();
246        let path = Path::parse(parser)?;
247        let mut params = vec![];
248        let var_args = None;
249        expect_token!(parser: ParanLeft);
250        until_match!(parser: ParanRight {
251            params.push(Parameter::parse(parser)?);
252            skip_token!(parser: Comma);
253        });
254        let body = Block::parse(parser)?;
255        pos.extend(&body.pos);
256        if local {
257            let Located {
258                value: path,
259                pos: path_pos,
260            } = path;
261            if let Path::Ident(ident) = path {
262                Ok(Located::new(
263                    Self::LetFn {
264                        ident: Located::new(ident, path_pos),
265                        params,
266                        var_args,
267                        body,
268                    },
269                    pos,
270                ))
271            } else {
272                Err(Located::new(ParseError::ExpectedIdentNotPath, path_pos))
273            }
274        } else {
275            Ok(Located::new(
276                Self::Fn {
277                    path,
278                    params,
279                    var_args,
280                    body,
281                },
282                pos,
283            ))
284        }
285    }
286    pub fn parse_if(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
287        let Located { value: _, mut pos } = parser.next().unwrap();
288        if_token!(parser: Let => {
289            let param = Parameter::parse(parser)?;
290            expect_token!(parser: Equal);
291            let expr = Expression::parse(parser)?;
292            let case = Block::parse(parser)?;
293            pos.extend(&case.pos);
294            let mut else_case = None;
295            if_token!(parser: Else => {
296                else_case = Some(
297                    if let Some(Located {
298                        value: Token::If,
299                        pos: _,
300                    }) = parser.peek()
301                    {
302                        let stat = Self::parse_if(parser)?;
303                        pos.extend(&stat.pos);
304                        let pos = stat.pos.clone();
305                        Located::new(Block(vec![stat]), pos)
306                    } else {
307                        let block = Block::parse(parser)?;
308                        pos.extend(&block.pos);
309                        block
310                    },
311                );
312            });
313            Ok(Located::new(
314                Self::IfLet {
315                    param,
316                    expr,
317                    case,
318                    else_case,
319                },
320                pos,
321            ))
322        } else {
323            let cond = Expression::parse(parser)?;
324            let case = Block::parse(parser)?;
325            pos.extend(&case.pos);
326            let mut else_case = None;
327            if_token!(parser: Else => {
328                else_case = Some(
329                    if let Some(Located {
330                        value: Token::If,
331                        pos: _,
332                    }) = parser.peek()
333                    {
334                        let stat = Self::parse_if(parser)?;
335                        pos.extend(&stat.pos);
336                        let pos = stat.pos.clone();
337                        Located::new(Block(vec![stat]), pos)
338                    } else {
339                        let block = Block::parse(parser)?;
340                        pos.extend(&block.pos);
341                        block
342                    },
343                );
344            });
345            Ok(Located::new(
346                Self::If {
347                    cond,
348                    case,
349                    else_case,
350                },
351                pos,
352            ))
353        })
354    }
355    pub fn parse_match(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
356        let Located { value: _, mut pos } = parser.next().unwrap();
357        let expr = Expression::parse(parser)?;
358        let mut cases = vec![];
359        expect_token!(parser: BraceLeft);
360        let end_pos = until_match!(parser: BraceRight {
361            let pattern = Pattern::parse(parser)?;
362            expect_token!(parser: EqualArrow);
363            let body = Block::parse(parser)?;
364            skip_token!(parser: Comma);
365            cases.push((pattern, body));
366        });
367        pos.extend(&end_pos);
368        Ok(Located::new(Self::Match { expr, cases }, pos))
369    }
370    pub fn parse_while(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
371        let Located { value: _, mut pos } = parser.next().unwrap();
372        if_token!(parser: Let => {
373            let param = Parameter::parse(parser)?;
374            expect_token!(parser: Equal);
375            let expr = Expression::parse(parser)?;
376            let body = Block::parse(parser)?;
377            pos.extend(&body.pos);
378            Ok(Located::new(Self::WhileLet { param, expr, body }, pos))
379        } else {
380            let cond = Expression::parse(parser)?;
381            let body = Block::parse(parser)?;
382            pos.extend(&body.pos);
383            Ok(Located::new(Self::While { cond, body }, pos))
384        })
385    }
386    pub fn parse_for(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
387        let Located { value: _, mut pos } = parser.next().unwrap();
388        let ident = Path::ident(parser)?;
389        expect_token!(parser: In);
390        let iter = Expression::parse(parser)?;
391        let body = Block::parse(parser)?;
392        pos.extend(&body.pos);
393        Ok(Located::new(Self::For { ident, iter, body }, pos))
394    }
395}
396impl Parsable for Statement {
397    fn parse(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
398        let Some(Located { value: token, pos }) = parser.peek() else {
399            return Err(Located::new(ParseError::UnexpectedEOF, Position::default()));
400        };
401        match token {
402            Token::BraceLeft => Ok(Block::parse(parser)?.map(Self::Block)),
403            Token::Let => Self::parse_let(parser),
404            Token::Fn => Self::parse_fn(parser, false),
405            Token::If => Self::parse_if(parser),
406            Token::Match => Self::parse_match(parser),
407            Token::While => Self::parse_while(parser),
408            Token::For => Self::parse_for(parser),
409            Token::Break => {
410                let Located { value: _, pos } = parser.next().unwrap();
411                Ok(Located::new(Self::Break, pos))
412            }
413            Token::Continue => {
414                let Located { value: _, pos } = parser.next().unwrap();
415                Ok(Located::new(Self::Continue, pos))
416            }
417            Token::Ident(_) => {
418                let path = Path::parse(parser)?;
419                let mut pos = path.pos.clone();
420                let Located {
421                    value: token,
422                    pos: token_pos,
423                } = expect!(parser);
424                match token {
425                    Token::Comma => {
426                        let mut paths = vec![path];
427                        let path = Path::parse(parser)?;
428                        paths.push(path);
429                        while_match!(parser: Comma {
430                            paths.push(Path::parse(parser)?);
431                        });
432                        expect_token!(parser: Equal);
433                        let mut exprs = vec![];
434                        let expr = Expression::parse(parser)?;
435                        exprs.push(expr);
436                        while_match!(parser: Comma {
437                            let expr = Expression::parse(parser)?;
438                            pos.extend(&expr.pos);
439                            exprs.push(expr);
440                        });
441                        Ok(Located::new(Self::Assign { paths, exprs }, pos))
442                    }
443                    Token::Equal => {
444                        let mut exprs = vec![];
445                        let expr = Expression::parse(parser)?;
446                        exprs.push(expr);
447                        while_match!(parser: Comma {
448                            exprs.push(Expression::parse(parser)?);
449                        });
450                        Ok(Located::new(
451                            Self::Assign {
452                                paths: vec![path],
453                                exprs,
454                            },
455                            pos,
456                        ))
457                    }
458                    token
459                        if matches!(
460                            &token,
461                            Token::PlusEqual
462                                | Token::MinusEqual
463                                | Token::StarEqual
464                                | Token::SlashEqual
465                                | Token::PercentEqual
466                                | Token::ExponentEqual
467                        ) =>
468                    {
469                        let op = AssignOperator::try_from(&token).expect("should transform");
470                        let expr = Expression::parse(parser)?;
471                        Ok(Located::new(Self::AssignOperation { op, path, expr }, pos))
472                    }
473                    Token::ParanLeft => {
474                        let mut args = vec![];
475                        let end_pos = until_match!(parser: ParanRight {
476                            args.push(Expression::parse(parser)?);
477                            skip_token!(parser: Comma);
478                        });
479                        pos.extend(&end_pos);
480                        Ok(Located::new(Self::Call { path, args }, pos))
481                    }
482                    Token::String(string) => {
483                        pos.extend(&token_pos);
484                        Ok(Located::new(
485                            Self::Call {
486                                path,
487                                args: vec![Located::new(
488                                    Expression::Atom(Atom::String(string)),
489                                    token_pos,
490                                )],
491                            },
492                            pos,
493                        ))
494                    }
495                    Token::Colon => {
496                        let field = Path::ident(parser)?;
497                        expect_token!(parser: ParanLeft);
498                        let mut args = vec![];
499                        let end_pos = until_match!(parser: ParanRight {
500                            args.push(Expression::parse(parser)?);
501                            skip_token!(parser: Comma);
502                        });
503                        pos.extend(&end_pos);
504                        Ok(Located::new(
505                            Self::SelfCall {
506                                head: path,
507                                field,
508                                args,
509                            },
510                            pos,
511                        ))
512                    }
513                    token => Err(Located::new(ParseError::UnexpectedToken(token), pos)),
514                }
515            }
516            Token::Return => {
517                let Located { value: _, mut pos } = parser.next().unwrap();
518                let expr = Expression::parse(parser)?;
519                pos.extend(&expr.pos);
520                Ok(Located::new(Self::Return(Some(expr)), pos))
521            }
522            _ => Err(Located::new(
523                ParseError::UnexpectedToken(token.clone()),
524                pos.clone(),
525            )),
526        }
527    }
528}
529impl Parsable for Pattern {
530    fn parse(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
531        let pattern = if_token!(parser: Ident: ident pos => {
532            Located::new(Self::Ident(ident), pos)
533        } else {
534            Atom::parse(parser)?.map(Self::Atom)
535        });
536        if_token!(parser: If => {
537            let cond = Expression::parse(parser)?;
538            let mut pos = pattern.pos.clone();
539            pos.extend(&cond.pos);
540            Ok(Located::new(Self::Guard { pattern: Box::new(pattern), cond }, pos))
541        } else {
542            Ok(pattern)
543        })
544    }
545}
546impl Parsable for Expression {
547    fn parse(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
548        Self::binary(parser, 0)
549    }
550}
551impl Expression {
552    pub fn binary(parser: &mut Parser, layer: usize) -> Result<Located<Self>, Located<ParseError>> {
553        let Some(ops) = BinaryOperator::layer(layer) else {
554            return Self::unary(parser, 0);
555        };
556        let mut left = Self::binary(parser, layer + 1)?;
557        while let Some(Located {
558            value: token,
559            pos: _,
560        }) = parser.peek()
561        {
562            let Ok(op) = BinaryOperator::try_from(token) else {
563                break;
564            };
565            if !ops.contains(&op) {
566                break;
567            }
568            parser.next();
569            let right = Self::binary(parser, layer + 1)?;
570            let mut pos = left.pos.clone();
571            pos.extend(&right.pos);
572            left = Located::new(
573                Self::Binary {
574                    op,
575                    left: Box::new(left),
576                    right: Box::new(right),
577                },
578                pos,
579            );
580        }
581        Ok(left)
582    }
583    pub fn unary(parser: &mut Parser, layer: usize) -> Result<Located<Self>, Located<ParseError>> {
584        let Some(ops) = UnaryOperator::layer(layer) else {
585            return Self::call(parser);
586        };
587        if let Some(Located {
588            value: token,
589            pos: _,
590        }) = parser.peek()
591        {
592            if let Ok(op) = UnaryOperator::try_from(token) {
593                if ops.contains(&op) {
594                    let Located { value: _, mut pos } = parser.next().unwrap();
595                    let right = Self::unary(parser, layer)?;
596                    pos.extend(&right.pos);
597                    return Ok(Located::new(
598                        Self::Unary {
599                            op,
600                            right: Box::new(right),
601                        },
602                        pos,
603                    ));
604                }
605            }
606        }
607        Self::unary(parser, layer + 1)
608    }
609    pub fn call(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
610        let mut head = Atom::parse(parser)?.map(Self::Atom);
611        while let Some(Located {
612            value: token,
613            pos: token_pos,
614        }) = parser.peek()
615        {
616            match token {
617                Token::ParanLeft => {
618                    parser.next();
619                    let mut pos = head.pos.clone();
620                    let mut args = vec![];
621                    let end_pos = until_match!(parser: ParanRight {
622                        args.push(Expression::parse(parser)?);
623                        skip_token!(parser: Comma);
624                    });
625                    pos.extend(&end_pos);
626                    head = Located::new(
627                        Self::Call {
628                            head: Box::new(head),
629                            args,
630                        },
631                        pos,
632                    );
633                }
634                Token::String(string) => {
635                    let mut pos = head.pos.clone();
636                    pos.extend(token_pos);
637                    let token_pos = token_pos.clone();
638                    let string = string.clone();
639                    parser.next();
640                    return Ok(Located::new(
641                        Self::Call {
642                            head: Box::new(head),
643                            args: vec![Located::new(
644                                Expression::Atom(Atom::String(string)),
645                                token_pos,
646                            )],
647                        },
648                        pos,
649                    ));
650                }
651                Token::Colon => {
652                    parser.next().unwrap();
653                    let mut pos = head.pos.clone();
654                    let field = Path::ident(parser)?;
655                    expect_token!(parser: ParanLeft);
656                    let mut args = vec![];
657                    let end_pos = until_match!(parser: ParanRight {
658                        args.push(Expression::parse(parser)?);
659                        skip_token!(parser: Comma)
660                    });
661                    pos.extend(&end_pos);
662                    head = Located::new(
663                        Self::SelfCall {
664                            head: Box::new(head),
665                            field,
666                            args,
667                        },
668                        pos,
669                    );
670                }
671                Token::Dot => {
672                    parser.next().unwrap();
673                    let mut pos = head.pos.clone();
674                    let field = Path::ident(parser)?;
675                    pos.extend(&field.pos);
676                    head = Located::new(
677                        Self::Field {
678                            head: Box::new(head),
679                            field,
680                        },
681                        pos,
682                    );
683                }
684                Token::BracketLeft => {
685                    parser.next();
686                    let index = Expression::parse(parser)?;
687                    let end_pos = expect_token!(parser: BracketRight);
688                    let mut pos = head.pos.clone();
689                    pos.extend(&end_pos);
690                    head = Located::new(
691                        Self::Index {
692                            head: Box::new(head),
693                            index: Box::new(index),
694                        },
695                        pos,
696                    )
697                }
698                _ => break,
699            }
700        }
701        Ok(head)
702    }
703    pub fn atom(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
704        Ok(Atom::parse(parser)?.map(Self::Atom))
705    }
706}
707impl Parsable for Path {
708    fn parse(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
709        let mut head = Self::ident(parser)?.map(Self::Ident);
710        while let Some(Located {
711            value: token,
712            pos: _,
713        }) = parser.peek()
714        {
715            match token {
716                Token::Dot => {
717                    parser.next();
718                    let field = Self::ident(parser)?;
719                    let mut pos = head.pos.clone();
720                    pos.extend(&field.pos);
721                    head = Located::new(
722                        Self::Field {
723                            head: Box::new(head),
724                            field,
725                        },
726                        pos,
727                    )
728                }
729                Token::BracketLeft => {
730                    parser.next();
731                    let index = Expression::parse(parser)?;
732                    let end_pos = expect_token!(parser: BracketRight);
733                    let mut pos = head.pos.clone();
734                    pos.extend(&end_pos);
735                    head = Located::new(
736                        Self::Index {
737                            head: Box::new(head),
738                            index: Box::new(index),
739                        },
740                        pos,
741                    )
742                }
743                _ => break,
744            }
745        }
746        Ok(head)
747    }
748}
749impl Path {
750    pub fn ident(parser: &mut Parser) -> Result<Located<String>, Located<ParseError>> {
751        let Located { value: token, pos } = expect!(parser);
752        if let Token::Ident(ident) = token {
753            Ok(Located::new(ident, pos))
754        } else {
755            Err(Located::new(
756                ParseError::ExpectedToken {
757                    expected: Token::Ident(Default::default()),
758                    got: token,
759                },
760                pos,
761            ))
762        }
763    }
764}
765impl Parsable for Atom {
766    fn parse(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
767        if let Some(Located {
768            value: Token::Ident(_),
769            pos: _,
770        }) = parser.peek()
771        {
772            return Ok(Path::parse(parser)?.map(Self::Path));
773        }
774        let Located {
775            value: token,
776            mut pos,
777        } = expect!(parser);
778        match token {
779            Token::Null => Ok(Located::new(Self::Null, pos)),
780            Token::Int(v) => Ok(Located::new(Self::Int(v), pos)),
781            Token::Float(v) => Ok(Located::new(Self::Float(v), pos)),
782            Token::Bool(v) => Ok(Located::new(Self::Bool(v), pos)),
783            Token::Char(v) => Ok(Located::new(Self::Char(v), pos)),
784            Token::String(v) => Ok(Located::new(Self::String(v), pos)),
785            Token::ParanLeft => {
786                let expr = Expression::parse(parser)?;
787                let end_pos = expect_token!(parser: ParanRight);
788                pos.extend(&end_pos);
789                Ok(Located::new(Self::Expression(Box::new(expr)), pos))
790            }
791            Token::BracketLeft => {
792                let mut exprs = vec![];
793                let end_pos = until_match!(parser: BracketRight {
794                    exprs.push(Expression::parse(parser)?);
795                    skip_token!(parser: Comma)
796                });
797                pos.extend(&end_pos);
798                Ok(Located::new(Self::Vector(exprs), pos))
799            }
800            Token::BraceLeft => {
801                let mut pairs = vec![];
802                let end_pos = until_match!(parser: BraceRight {
803                    let key = Path::ident(parser)?;
804                    expect_token!(parser: Equal);
805                    let expr = Expression::parse(parser)?;
806                    pairs.push((key, expr));
807                    skip_token!(parser: Comma);
808                });
809                pos.extend(&end_pos);
810                Ok(Located::new(Self::Object(pairs), pos))
811            }
812            Token::If => {
813                let cond = Expression::parse(parser)?;
814                let case = Expression::parse(parser)?;
815                expect_token!(parser: Else);
816                let else_case = Expression::parse(parser)?;
817                pos.extend(&else_case.pos);
818                Ok(Located::new(
819                    Self::If {
820                        cond: Box::new(cond),
821                        case: Box::new(case),
822                        else_case: Box::new(else_case),
823                    },
824                    pos,
825                ))
826            }
827            Token::Fn => {
828                let mut params = vec![];
829                let var_args = None;
830                expect_token!(parser: ParanLeft);
831                until_match!(parser: ParanRight {
832                    params.push(Parameter::parse(parser)?);
833                    skip_token!(parser: Comma);
834                });
835                let body = Block::parse(parser)?;
836                pos.extend(&body.pos);
837                Ok(Located::new(
838                    Self::Fn {
839                        params,
840                        var_args,
841                        body,
842                    },
843                    pos,
844                ))
845            }
846            token => Err(Located::new(ParseError::UnexpectedToken(token), pos)),
847        }
848    }
849}
850impl Parsable for Parameter {
851    fn parse(parser: &mut Parser) -> Result<Located<Self>, Located<ParseError>> {
852        if let Some(Located {
853            value: Token::Ident(_),
854            pos: _,
855        }) = parser.peek()
856        {
857            return Ok(Path::ident(parser)?.map(Self::Ident));
858        }
859        let Located {
860            value: token,
861            mut pos,
862        } = expect!(parser);
863        match token {
864            Token::BraceLeft => {
865                let mut fields = vec![];
866                let end_pos = until_match!(parser: BraceRight {
867                    let field = Path::ident(parser)?;
868                    fields.push(field);
869                    skip_token!(parser: Comma);
870                });
871                pos.extend(&end_pos);
872                Ok(Located::new(Self::Object(fields), pos))
873            }
874            Token::BracketLeft => {
875                let mut fields = vec![];
876                let end_pos = until_match!(parser: BracketRight {
877                    let field = Path::ident(parser)?;
878                    fields.push(field);
879                    skip_token!(parser: Comma);
880                });
881                pos.extend(&end_pos);
882                Ok(Located::new(Self::Vector(fields), pos))
883            }
884            token => Err(Located::new(ParseError::UnexpectedToken(token), pos)),
885        }
886    }
887}