aboutsummaryrefslogtreecommitdiff
path: root/src/parser
diff options
context:
space:
mode:
authorAleksey Kladov <[email protected]>2018-01-07 18:09:05 +0000
committerAleksey Kladov <[email protected]>2018-01-07 18:09:05 +0000
commit5562931e4f3c6c57e9122c3ce34d941fb1ff6e5b (patch)
tree0e87cba8e91d4bf96d752ada65b4d4a73e4e0ac9 /src/parser
parentfc4d6cc298fe901d2bf92a30a3efd67233c67a3a (diff)
Introduce EOF token
Diffstat (limited to 'src/parser')
-rw-r--r--src/parser/event_parser/grammar.rs23
-rw-r--r--src/parser/event_parser/parser.rs35
2 files changed, 23 insertions, 35 deletions
diff --git a/src/parser/event_parser/grammar.rs b/src/parser/event_parser/grammar.rs
index f676a183c..64c6718cb 100644
--- a/src/parser/event_parser/grammar.rs
+++ b/src/parser/event_parser/grammar.rs
@@ -1,5 +1,6 @@
1use super::parser::Parser; 1use super::parser::Parser;
2use {SyntaxKind}; 2use {SyntaxKind};
3use tree::EOF;
3use syntax_kinds::*; 4use syntax_kinds::*;
4 5
5// Items // 6// Items //
@@ -18,11 +19,7 @@ pub(crate) fn file(p: &mut Parser) {
18} 19}
19 20
20fn item_first(p: &Parser) -> bool { 21fn item_first(p: &Parser) -> bool {
21 let current = match p.current() { 22 match p.current() {
22 Some(c) => c,
23 None => return false,
24 };
25 match current {
26 STRUCT_KW | FN_KW => true, 23 STRUCT_KW | FN_KW => true,
27 _ => false, 24 _ => false,
28 } 25 }
@@ -79,7 +76,7 @@ fn visibility(_: &mut Parser) {
79// Error recovery and high-order utils // 76// Error recovery and high-order utils //
80 77
81fn node_if<F: FnOnce(&mut Parser)>(p: &mut Parser, first: SyntaxKind, node_kind: SyntaxKind, rest: F) -> bool { 78fn node_if<F: FnOnce(&mut Parser)>(p: &mut Parser, first: SyntaxKind, node_kind: SyntaxKind, rest: F) -> bool {
82 p.current_is(first) && { node(p, node_kind, |p| { p.bump(); rest(p); }); true } 79 p.current() == first && { node(p, node_kind, |p| { p.bump(); rest(p); }); true }
83} 80}
84 81
85fn node<F: FnOnce(&mut Parser)>(p: &mut Parser, node_kind: SyntaxKind, rest: F) { 82fn node<F: FnOnce(&mut Parser)>(p: &mut Parser, node_kind: SyntaxKind, rest: F) {
@@ -95,7 +92,7 @@ fn many<F: Fn(&mut Parser) -> bool>(p: &mut Parser, f: F) {
95fn comma_list<F: Fn(&mut Parser) -> bool>(p: &mut Parser, f: F) { 92fn comma_list<F: Fn(&mut Parser) -> bool>(p: &mut Parser, f: F) {
96 many(p, |p| { 93 many(p, |p| {
97 f(p); 94 f(p);
98 if p.is_eof() { 95 if p.current() == EOF {
99 false 96 false
100 } else { 97 } else {
101 p.expect(COMMA); 98 p.expect(COMMA);
@@ -119,7 +116,7 @@ where
119 f(p); 116 f(p);
120 return true; 117 return true;
121 } 118 }
122 if p.is_eof() { 119 if p.current() == EOF {
123 if skipped { 120 if skipped {
124 p.finish(); 121 p.finish();
125 } 122 }
@@ -131,18 +128,14 @@ where
131 .message(message) 128 .message(message)
132 .emit(); 129 .emit();
133 } 130 }
134 p.bump().unwrap(); 131 p.bump();
135 skipped = true; 132 skipped = true;
136 } 133 }
137} 134}
138 135
139impl<'p> Parser<'p> { 136impl<'p> Parser<'p> {
140 fn current_is(&self, kind: SyntaxKind) -> bool {
141 self.current() == Some(kind)
142 }
143
144 pub(crate) fn expect(&mut self, kind: SyntaxKind) -> bool { 137 pub(crate) fn expect(&mut self, kind: SyntaxKind) -> bool {
145 if self.current_is(kind) { 138 if self.current() == kind {
146 self.bump(); 139 self.bump();
147 true 140 true
148 } else { 141 } else {
@@ -154,7 +147,7 @@ impl<'p> Parser<'p> {
154 } 147 }
155 148
156 fn optional(&mut self, kind: SyntaxKind) { 149 fn optional(&mut self, kind: SyntaxKind) {
157 if self.current_is(kind) { 150 if self.current() == kind {
158 self.bump(); 151 self.bump();
159 } 152 }
160 } 153 }
diff --git a/src/parser/event_parser/parser.rs b/src/parser/event_parser/parser.rs
index f0d1d358b..bec9dbab4 100644
--- a/src/parser/event_parser/parser.rs
+++ b/src/parser/event_parser/parser.rs
@@ -2,8 +2,7 @@ use {Token, SyntaxKind, TextUnit};
2use super::{Event}; 2use super::{Event};
3use super::super::is_insignificant; 3use super::super::is_insignificant;
4use syntax_kinds::{L_CURLY, R_CURLY, ERROR}; 4use syntax_kinds::{L_CURLY, R_CURLY, ERROR};
5 5use tree::EOF;
6pub(crate) const EOF: SyntaxKind = SyntaxKind(10000);
7 6
8 7
9pub(crate) struct Parser<'t> { 8pub(crate) struct Parser<'t> {
@@ -46,19 +45,22 @@ impl<'t> Parser<'t> {
46 } 45 }
47 46
48 pub(crate) fn into_events(self) -> Vec<Event> { 47 pub(crate) fn into_events(self) -> Vec<Event> {
49 assert!(self.is_eof()); 48 assert!(self.curly_limit.is_none());
49 assert!(self.current() == EOF);
50 self.events 50 self.events
51 } 51 }
52 52
53 pub(crate) fn is_eof(&self) -> bool { 53 pub(crate) fn current(&self) -> SyntaxKind {
54 if self.pos == self.tokens.len() { 54 if self.pos == self.tokens.len() {
55 return true 55 return EOF;
56 } 56 }
57 let token = self.tokens[self.pos];
57 if let Some(limit) = self.curly_limit { 58 if let Some(limit) = self.curly_limit {
58 let token = self.tokens[self.pos]; 59 if limit == self.curly_level && token.kind == R_CURLY {
59 return limit == self.curly_level && token.kind == R_CURLY; 60 return EOF
61 }
60 } 62 }
61 false 63 token.kind
62 } 64 }
63 65
64 pub(crate) fn start(&mut self, kind: SyntaxKind) { 66 pub(crate) fn start(&mut self, kind: SyntaxKind) {
@@ -73,24 +75,17 @@ impl<'t> Parser<'t> {
73 ErrorBuilder::new(self) 75 ErrorBuilder::new(self)
74 } 76 }
75 77
76 pub(crate) fn current(&self) -> Option<SyntaxKind> { 78 pub(crate) fn bump(&mut self) -> SyntaxKind {
77 if self.is_eof() { 79 let kind = self.current();
78 return None;
79 }
80 let token = self.tokens[self.pos];
81 Some(token.kind)
82 }
83
84 pub(crate) fn bump(&mut self) -> Option<SyntaxKind> {
85 let kind = self.current()?;
86 match kind { 80 match kind {
87 L_CURLY => self.curly_level += 1, 81 L_CURLY => self.curly_level += 1,
88 R_CURLY => self.curly_level -= 1, 82 R_CURLY => self.curly_level -= 1,
83 EOF => return EOF,
89 _ => (), 84 _ => (),
90 } 85 }
91 self.pos += 1; 86 self.pos += 1;
92 self.event(Event::Token { kind, n_raw_tokens: 1 }); 87 self.event(Event::Token { kind, n_raw_tokens: 1 });
93 Some(kind) 88 kind
94 } 89 }
95 90
96 pub(crate) fn lookahead(&self, kinds: &[SyntaxKind]) -> bool { 91 pub(crate) fn lookahead(&self, kinds: &[SyntaxKind]) -> bool {
@@ -114,7 +109,7 @@ impl<'t> Parser<'t> {
114 if !self.expect(R_CURLY) { 109 if !self.expect(R_CURLY) {
115 self.start(ERROR); 110 self.start(ERROR);
116 while self.curly_level > old_level { 111 while self.curly_level > old_level {
117 if self.bump().is_none() { 112 if self.bump() == EOF {
118 break; 113 break;
119 } 114 }
120 } 115 }