aboutsummaryrefslogtreecommitdiff
path: root/src/grammar/type_params.rs
diff options
context:
space:
mode:
authorAleksey Kladov <[email protected]>2018-07-31 21:38:19 +0100
committerAleksey Kladov <[email protected]>2018-07-31 21:44:31 +0100
commit7912189ec304b28c4df0030b5282cf3d21074154 (patch)
tree03a0a1b128439fdefbd1d012b392995ca8a6e264 /src/grammar/type_params.rs
parentd1400e95d7ad701fcba1191cb00968c2eae8b394 (diff)
reorganize
Diffstat (limited to 'src/grammar/type_params.rs')
-rw-r--r--src/grammar/type_params.rs95
1 files changed, 95 insertions, 0 deletions
diff --git a/src/grammar/type_params.rs b/src/grammar/type_params.rs
new file mode 100644
index 000000000..1227482ad
--- /dev/null
+++ b/src/grammar/type_params.rs
@@ -0,0 +1,95 @@
1use super::*;
2
3pub(super) fn type_param_list(p: &mut Parser) {
4 if !p.at(L_ANGLE) {
5 return;
6 }
7 let m = p.start();
8 p.bump();
9
10 while !p.at(EOF) && !p.at(R_ANGLE) {
11 match p.current() {
12 LIFETIME => lifetime_param(p),
13 IDENT => type_param(p),
14 _ => p.err_and_bump("expected type parameter"),
15 }
16 if !p.at(R_ANGLE) && !p.expect(COMMA) {
17 break;
18 }
19 }
20 p.expect(R_ANGLE);
21 m.complete(p, TYPE_PARAM_LIST);
22
23 fn lifetime_param(p: &mut Parser) {
24 assert!(p.at(LIFETIME));
25 let m = p.start();
26 p.bump();
27 if p.eat(COLON) {
28 while p.at(LIFETIME) {
29 p.bump();
30 if !p.eat(PLUS) {
31 break;
32 }
33 }
34 }
35 m.complete(p, LIFETIME_PARAM);
36 }
37
38 fn type_param(p: &mut Parser) {
39 assert!(p.at(IDENT));
40 let m = p.start();
41 name(p);
42 if p.at(COLON) {
43 bounds(p);
44 }
45 // test type_param_default
46 // struct S<T = i32>;
47 if p.at(EQ) {
48 p.bump();
49 types::type_(p)
50 }
51 m.complete(p, TYPE_PARAM);
52 }
53}
54
55// test type_param_bounds
56// struct S<T: 'a + ?Sized + (Copy)>;
57pub(super) fn bounds(p: &mut Parser) {
58 assert!(p.at(COLON));
59 p.bump();
60 bounds_without_colon(p);
61}
62
63pub(super) fn bounds_without_colon(p: &mut Parser) {
64 loop {
65 let has_paren = p.eat(L_PAREN);
66 p.eat(QUESTION);
67 if p.at(FOR_KW) {
68 //TODO
69 }
70 if p.at(LIFETIME) {
71 p.bump();
72 } else if paths::is_path_start(p) {
73 paths::type_path(p);
74 } else {
75 break;
76 }
77 if has_paren {
78 p.expect(R_PAREN);
79 }
80 if !p.eat(PLUS) {
81 break;
82 }
83 }
84}
85
86pub(super) fn where_clause(p: &mut Parser) {
87 if p.at(WHERE_KW) {
88 let m = p.start();
89 p.bump();
90 p.expect(IDENT);
91 p.expect(COLON);
92 p.expect(IDENT);
93 m.complete(p, WHERE_CLAUSE);
94 }
95}