1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
|
use super::*;
// test param_list
// fn a() {}
// fn b(x: i32) {}
// fn c(x: i32, ) {}
// fn d(x: i32, y: ()) {}
pub(super) fn param_list(p: &mut Parser) {
list_(p, Flavor::Normal)
}
// test param_list_opt_patterns
// fn foo<F: FnMut(&mut Foo<'a>)>(){}
pub(super) fn param_list_opt_patterns(p: &mut Parser) {
list_(p, Flavor::OptionalPattern)
}
pub(super) fn param_list_opt_types(p: &mut Parser) {
list_(p, Flavor::OptionalType)
}
#[derive(Clone, Copy, Eq, PartialEq)]
enum Flavor {
OptionalType,
OptionalPattern,
Normal,
}
impl Flavor {
fn type_required(self) -> bool {
match self {
Flavor::OptionalType => false,
_ => true,
}
}
}
fn list_(p: &mut Parser, flavor: Flavor) {
let (bra, ket) = if flavor.type_required() {
(L_PAREN, R_PAREN)
} else {
(PIPE, PIPE)
};
assert!(p.at(bra));
let m = p.start();
p.bump();
if flavor.type_required() {
self_param(p);
}
while !p.at(EOF) && !p.at(ket) {
value_parameter(p, flavor);
if !p.at(ket) {
p.expect(COMMA);
}
}
p.expect(ket);
m.complete(p, PARAM_LIST);
}
fn value_parameter(p: &mut Parser, flavor: Flavor) {
let m = p.start();
match flavor {
Flavor::OptionalType | Flavor::Normal => {
patterns::pattern(p);
if p.at(COLON) || flavor.type_required() {
types::ascription(p)
}
},
// test value_parameters_no_patterns
// type F = Box<Fn(a: i32, &b: &i32, &mut c: &i32, ())>;
Flavor::OptionalPattern => {
let la0 = p.current();
let la1 = p.nth(1);
let la2 = p.nth(2);
let la3 = p.nth(3);
if la0 == IDENT && la1 == COLON
|| la0 == AMP && la1 == IDENT && la2 == COLON
|| la0 == AMP && la1 == MUT_KW && la2 == IDENT && la3 == COLON {
patterns::pattern(p);
types::ascription(p);
} else {
types::type_(p);
}
},
}
m.complete(p, PARAM);
}
// test self_param
// impl S {
// fn a(self) {}
// fn b(&self,) {}
// fn c(&'a self,) {}
// fn d(&'a mut self, x: i32) {}
// }
fn self_param(p: &mut Parser) {
let la1 = p.nth(1);
let la2 = p.nth(2);
let la3 = p.nth(3);
let n_toks = match (p.current(), la1, la2, la3) {
(SELF_KW, _, _, _) => 1,
(AMP, SELF_KW, _, _) => 2,
(AMP, MUT_KW, SELF_KW, _) => 3,
(AMP, LIFETIME, SELF_KW, _) => 3,
(AMP, LIFETIME, MUT_KW, SELF_KW) => 4,
_ => return,
};
let m = p.start();
for _ in 0..n_toks {
p.bump();
}
m.complete(p, SELF_PARAM);
if !p.at(R_PAREN) {
p.expect(COMMA);
}
}
|