(&mut self)
| 558 | } |
| 559 | |
| 560 | pub(super) fn parse_params(&mut self) -> (Vec<String>, u16) { |
| 561 | // No `(`: diagnostic, consume `:` so compile_body starts at Indent correctly. |
| 562 | if !matches!(self.peek(), Some(TokenType::Lpar)) { |
| 563 | self.diag_at_peek("expected '('"); |
| 564 | self.eat_if(TokenType::Colon); |
| 565 | return (Vec::new(), 0); |
| 566 | } |
| 567 | self.advance(); |
| 568 | let mut params = Vec::new(); |
| 569 | let mut defaults = 0u16; |
| 570 | // Lone `*` flips kw_only; subsequent params get `~` prefix. |
| 571 | let mut kw_only = false; |
| 572 | // Break on Rarrow: signals end of params (return type follows). |
| 573 | while !matches!(self.peek(), Some(TokenType::Rpar | TokenType::Rarrow) | None) { |
| 574 | if self.eat_if(TokenType::Slash) { |
| 575 | self.eat_if(TokenType::Comma); |
| 576 | continue; |
| 577 | } |
| 578 | if self.eat_if(TokenType::Star) { |
| 579 | // Lone `*`: flip kw-only, no param emitted. |
| 580 | if matches!(self.peek(), Some(TokenType::Comma | TokenType::Rpar)) { |
| 581 | self.eat_if(TokenType::Comma); |
| 582 | kw_only = true; |
| 583 | continue; |
| 584 | } |
| 585 | let nm = self.advance_text(); |
| 586 | params.push(s!("*", str &nm)); |
| 587 | self.drain_annotation(); |
| 588 | self.eat_if(TokenType::Comma); |
| 589 | continue; |
| 590 | } |
| 591 | if self.eat_if(TokenType::DoubleStar) { |
| 592 | let nm = self.advance_text(); |
| 593 | params.push(s!("**", str &nm)); |
| 594 | self.drain_annotation(); |
| 595 | self.eat_if(TokenType::Comma); |
| 596 | continue; |
| 597 | } |
| 598 | let prefix = if kw_only { "~" } else { "" }; |
| 599 | let nm = self.advance_text(); |
| 600 | params.push(if prefix.is_empty() { nm } else { s!(str prefix, str &nm) }); |
| 601 | self.drain_annotation(); |
| 602 | if self.eat_if(TokenType::Equal) { |
| 603 | self.expr(); |
| 604 | defaults += 1; |
| 605 | // Trailing `=` marks this param as carrying a default value. |
| 606 | if let Some(last) = params.last_mut() { last.push('='); } |
| 607 | } |
| 608 | self.eat_if(TokenType::Comma); |
| 609 | } |
| 610 | self.eat(TokenType::Rpar); |
| 611 | if self.eat_if(TokenType::Rarrow) { |
| 612 | while !matches!(self.peek(), Some(TokenType::Colon) | None) { self.advance(); } |
| 613 | } |
| 614 | self.eat(TokenType::Colon); |
| 615 | (params, defaults) |
| 616 | } |
| 617 |
no test coverage detected