1use std::path::Path;
11
12use bumpalo::Bump;
13use log::*;
14
15pub use error::Error;
16pub use error::Result;
17
18use crate::ast::{Ast, HierarchicalId};
19use crate::ir::{Attribute, AttributeId, Attributes};
20use crate::parser::error::{Expected, Type, Warning, WarningType};
21use crate::parser::lexer::Token;
22use crate::span::Index;
23use crate::symbol::{keywords, Ident, Symbol};
24use crate::symbol_table::{SymbolDeclaration, SymbolTable};
25use crate::{Preprocessor, SourceMap, Span};
26use rustc_hash::FxHashMap;
27
28pub(crate) mod lexer;
29pub(crate) mod preprocessor;
30#[cfg(test)]
31pub mod test;
32
33#[macro_use]
34mod combinators;
35mod behavior;
36mod branch;
37mod disciplines;
38pub mod error;
39mod expression;
40mod module;
41mod nature;
42mod net_declarations;
43mod parameter;
44mod primaries;
45mod variables;
46
47pub(crate) struct Parser<'lt, 'source_map> {
49 pub preprocessor: Preprocessor<'lt, 'source_map>,
50 pub scope_stack: Vec<SymbolTable>,
51 lookahead: Option<Result<(Token, Span, Index)>>,
52 pub ast: &'lt mut Ast,
53 pub non_critical_errors: Vec<Error>,
54 pub warnings: Vec<Warning>,
55 pub(crate) unrecoverable: bool,
56}
57
58impl<'lt, 'source_map> Parser<'lt, 'source_map> {
59 pub fn new(
60 preprocessor: Preprocessor<'lt, 'source_map>,
61 ast: &'lt mut Ast,
62 errors: Vec<Error>,
63 ) -> Self {
64 Self {
65 preprocessor,
66 scope_stack: Vec::with_capacity(32),
67 lookahead: None,
68 ast,
69 non_critical_errors: errors,
70 warnings: Vec::with_capacity(32),
71 unrecoverable: false,
72 }
73 }
74
75 pub fn run(&mut self) {
76 synchronize!(self;
77 let attributes = self.parse_attributes()?;
78 sync self.next_with_span() => {
79 Token::EOF => end,
80 Token::Module => self.parse_module(attributes),
81 Token::Nature => self.parse_nature(attributes),
82 Token::Discipline => self.parse_discipline(attributes),
83 }
84 )
85 }
86 fn next(&mut self) -> Result<Token> {
88 match self.lookahead.take() {
89 None => {
90 self.preprocessor.advance()?;
91 Ok(self.preprocessor.current_token())
92 }
93 Some(res) => res.map(|(token, _, _)| token),
94 }
95 }
96
97 fn next_with_span(&mut self) -> Result<(Token, Span)> {
99 match self.lookahead.take() {
100 None => {
101 self.preprocessor.advance()?;
102 Ok((self.preprocessor.current_token(), self.preprocessor.span()))
103 }
104 Some(res) => res.map(|(token, span, _)| (token, span)),
105 }
106 }
107
108 fn next_with_span_and_previous_end(&mut self) -> Result<(Token, Span, Index)> {
110 match self.lookahead.take() {
111 None => {
112 let end = self.preprocessor.current_end();
113 self.preprocessor.advance()?;
114 Ok((
115 self.preprocessor.current_token(),
116 self.preprocessor.span(),
117 end,
118 ))
119 }
120 Some(res) => res,
121 }
122 }
123
124 fn look_ahead(&mut self) -> Result<Token> {
127 if let Some(ref lookahead) = self.lookahead {
128 return lookahead.clone().map(|(token, _, _)| token);
129 }
130 let end = self.preprocessor.current_end();
131 let res = self.preprocessor.advance().map(|_| {
132 (
133 self.preprocessor.current_token(),
134 self.preprocessor.span(),
135 end,
136 )
137 });
138 self.lookahead = Some(res.clone());
139 res.map(|(token, _, _)| token)
140 }
141
142 fn look_ahead_with_span(&mut self) -> Result<(Token, Span)> {
145 if let Some(ref lookahead) = self.lookahead {
146 return lookahead.clone().map(|(token, span, _)| (token, span));
147 }
148 let end = self.preprocessor.current_end();
149 let res = self.preprocessor.advance().map(|_| {
150 (
151 self.preprocessor.current_token(),
152 self.preprocessor.span(),
153 end,
154 )
155 });
156 self.lookahead = Some(res.clone());
157 res.map(|(token, span, _)| (token, span))
158 }
159
160 fn look_ahead_with_span_and_previous_end(&mut self) -> Result<(Token, Span, Index)> {
163 if let Some(ref lookahead) = self.lookahead {
164 return lookahead.clone();
165 }
166 let end = self.preprocessor.current_end();
167 let res = self.preprocessor.advance().map(|_| {
168 (
169 self.preprocessor.current_token(),
170 self.preprocessor.span(),
171 end,
172 )
173 });
174 self.lookahead = Some(res.clone());
175 res
176 }
177
178 fn consume_lookahead(&mut self) {
180 self.lookahead = None
181 }
182
183 #[inline]
195 pub fn parse_identifier(&mut self, optional: bool) -> Result<Ident> {
196 let (token, source) = if optional {
197 self.look_ahead_with_span()?
198 } else {
199 self.next_with_span()?
200 };
201
202 let identifier = match token {
203 Token::SimpleIdentifier(_) => self.preprocessor.slice(),
204
205 Token::EscapedIdentifier => {
206 let raw = self.preprocessor.slice();
207 &raw[1..raw.len() - 1]
208 }
209
210 _ => {
211 return Err(Error {
212 source,
213 error_type: error::Type::UnexpectedTokens {
214 expected: vec![Expected::Identifier],
215 },
216 })
217 }
218 };
219
220 if optional {
221 self.consume_lookahead();
222 }
223
224 Ok(Ident::from_str_and_span(identifier, source))
225 }
226
227 pub fn parse_hierarchical_identifier(&mut self) -> Result<HierarchicalId> {
241 let mut names = vec![self.parse_identifier(false)?];
244 while self.look_ahead()? == Token::Accessor {
245 self.consume_lookahead();
246 names.push(self.parse_identifier(false)?)
247 }
248 Ok(HierarchicalId { names })
249 }
250
251 pub fn parse_attributes(&mut self) -> Result<Attributes> {
266 let attr_start = self.ast.attributes.len_idx();
267 let mut attribute_map: FxHashMap<Symbol, AttributeId> = FxHashMap::default();
268 loop {
269 if self.look_ahead()? != Token::AttributeStart {
270 break;
271 }
272 self.consume_lookahead();
273 self.parse_list(
274 |sel| sel.parse_attribute(&mut attribute_map),
275 Token::AttributeEnd,
276 true,
277 )?;
278 }
279 Ok(Attributes::new(attr_start, self.ast.attributes.len_idx()))
280 }
281
282 fn parse_attribute(&mut self, attribute_map: &mut FxHashMap<Symbol, AttributeId>) -> Result {
286 let name = if self.look_ahead()? == Token::Units {
287 self.consume_lookahead();
288 Ident::new(keywords::UNITS, self.preprocessor.span())
289 } else {
290 self.parse_identifier(false)?
291 };
292 let value = if self.look_ahead()? == Token::Assign {
293 self.consume_lookahead();
294 Some(self.parse_expression_id()?)
295 } else {
296 None
297 };
298 if let Some(id) = attribute_map.get(&name.name) {
299 let old_name = self.ast[*id].name;
300 self.warnings.push(Warning {
301 error_type: WarningType::AttributeOverwrite(old_name, name.span),
302 source: old_name.span.extend(name.span),
303 });
304 self.ast[*id] = Attribute { name, value };
305 } else {
306 let id = self.ast.attributes.push(Attribute { name, value });
307 attribute_map.insert(name.name, id);
308 }
309 Ok(())
310 }
311
312 #[inline]
314 pub fn expect(&mut self, token: Token) -> Result {
315 let (found, source, expected_at) = self.next_with_span_and_previous_end()?;
316 if found == token {
317 Ok(())
318 } else {
319 debug!("Parser: Expected {} but found {}", token, found);
320 Err(Error {
321 source,
322 error_type: error::Type::MissingOrUnexpectedToken {
323 expected: vec![token],
324 expected_at,
325 },
326 })
327 }
328 }
329
330 #[inline]
331 pub fn try_expect(&mut self, token: Token) {
332 match self.look_ahead_with_span_and_previous_end() {
333 Ok((found, _, _)) if found == token => {
334 self.consume_lookahead();
335 }
336 Ok((found, source, expected_at)) if found == Token::Unexpected => {
337 debug!(
338 "Parser: Expected {} but found {} lexical error",
339 token, found
340 );
341 self.consume_lookahead();
342 self.non_critical_errors.push(Error {
343 source,
344 error_type: error::Type::MissingOrUnexpectedToken {
345 expected: vec![found],
346 expected_at,
347 },
348 })
349 }
350 Err(error) => {
351 debug!("Parser: Expected {} but found preprocessor error", token);
352 self.consume_lookahead();
353 self.non_critical_errors.push(error)
354 }
355 Ok((found, source, expected_at)) => {
356 debug!(
357 "Parser: Expected {} but found {} (not consumed)",
358 token, found
359 );
360 self.non_critical_errors.push(Error {
361 source,
362 error_type: error::Type::MissingOrUnexpectedToken {
363 expected: vec![token],
364 expected_at,
365 },
366 });
367 }
368 }
369 }
370
371 #[inline]
372 pub fn expect_lookahead(&mut self, token: Token) -> Result {
373 let (found, source, expected_at) = self.look_ahead_with_span_and_previous_end()?;
374 if found == token {
375 self.consume_lookahead();
376 Ok(())
377 } else {
378 Err(Error {
379 source,
380 error_type: error::Type::MissingOrUnexpectedToken {
381 expected: vec![token],
382 expected_at,
383 },
384 })
385 }
386 }
387
388 #[inline]
389 pub fn span_to_current_end(&self, start: Index) -> Span {
390 Span::new(start, self.preprocessor.current_end())
391 }
392
393 #[inline]
394 pub fn insert_symbol(&mut self, name: Ident, declaration: SymbolDeclaration) {
395 let source = declaration.span(&self.ast);
396 if let Some(old_declaration) = self.symbol_table_mut().insert(name.name, declaration) {
397 self.non_critical_errors.push(Error {
398 error_type: Type::AlreadyDeclaredInThisScope {
399 other_declaration: old_declaration.span(&self.ast),
400 name: name.name,
401 },
402 source,
403 });
404 }
405 }
406
407 #[inline]
408 pub fn symbol_table_mut(&mut self) -> &mut SymbolTable {
409 self.scope_stack
410 .last_mut()
411 .unwrap_or(&mut self.ast.top_symbols)
412 }
413
414 #[inline]
415 pub fn symbol_table(&self) -> &SymbolTable {
416 self.scope_stack.last().unwrap_or(&self.ast.top_symbols)
417 }
418}
419
420impl Ast {
421 pub fn parse_from<'source_map, 'lt>(
439 &'lt mut self,
440 main_file: &Path,
441 source_map_allocator: &'source_map Bump,
442 ) -> std::io::Result<(
443 &'source_map SourceMap<'source_map>,
444 Vec<Error>,
445 Vec<Warning>,
446 )> {
447 let allocator = Bump::new();
448
449 let mut preprocessor = Preprocessor::new(&allocator, source_map_allocator, main_file)?;
450
451 let mut errors = Vec::with_capacity(64);
452 if let Err(error) = preprocessor.advance() {
453 errors.push(error);
454 }
455
456 let mut parser = Parser::new(preprocessor, self, errors);
457
458 parser.lookahead = Some(Ok((
461 parser.preprocessor.current_token(),
462 parser.preprocessor.span(),
463 0,
464 )));
465
466 parser.run();
467
468 Ok((
469 parser.preprocessor.done(),
470 parser.non_critical_errors,
471 parser.warnings,
472 ))
473 }
474
475 pub fn parse_from_and_print_errors<'source_map, 'lt>(
491 &'lt mut self,
492 main_file: &Path,
493 source_map_allocator: &'source_map Bump,
494 translate_lines: bool,
495 ) -> Option<&'source_map SourceMap<'source_map>> {
496 match self.parse_from(main_file, source_map_allocator) {
497 Ok((source_map, errors, warnings)) if errors.is_empty() => {
498 warnings
499 .into_iter()
500 .for_each(|warning| warning.print(source_map, translate_lines));
501 Some(source_map)
502 }
503 Ok((source_map, errors, warnings)) => {
504 warnings
505 .into_iter()
506 .for_each(|warning| warning.print(source_map, translate_lines));
507 errors
508 .into_iter()
509 .for_each(|err| err.print(&source_map, translate_lines));
510 None
511 }
512 Err(error) => {
513 error!("failed to open : {}!\n\t caused by {}",main_file.display(),error);
514 None
515 }
516 }
517 }
518}