1use crate::doc_comment_table;
2use crate::resource_table::{self, PathId, StrId, TokenId};
3use crate::text_table::{self, TextId};
4use crate::veryl_grammar_trait::*;
5use once_cell::sync::Lazy;
6use paste::paste;
7use regex::Regex;
8use std::fmt;
9
10#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
11pub enum TokenSource {
12 File { path: PathId, text: TextId },
13 Builtin,
14 External,
15 Generated(PathId),
16}
17
18impl fmt::Display for TokenSource {
19 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
20 let text = match self {
21 TokenSource::File { path, .. } => path.to_string(),
22 TokenSource::Builtin => "builtin".to_string(),
23 TokenSource::External => "external".to_string(),
24 TokenSource::Generated(_) => "generated".to_string(),
25 };
26 text.fmt(f)
27 }
28}
29
30impl PartialEq<PathId> for TokenSource {
31 fn eq(&self, other: &PathId) -> bool {
32 match self {
33 TokenSource::File { path, .. } => path == other,
34 TokenSource::Generated(x) => x == other,
35 _ => false,
36 }
37 }
38}
39
40impl TokenSource {
41 pub fn get_text(&self) -> String {
42 if let TokenSource::File { text, .. } = self {
43 if let Some(x) = text_table::get(*text) {
44 x.text
45 } else {
46 String::new()
47 }
48 } else {
49 String::new()
50 }
51 }
52
53 pub fn get_path(&self) -> Option<PathId> {
54 match self {
55 TokenSource::File { path, .. } => Some(*path),
56 TokenSource::Generated(x) => Some(*x),
57 _ => None,
58 }
59 }
60}
61
62#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
63pub struct Token {
64 pub id: TokenId,
65 pub text: StrId,
66 pub line: u32,
67 pub column: u32,
68 pub length: u32,
69 pub pos: u32,
70 pub source: TokenSource,
71}
72
73impl Token {
74 pub fn new(
75 text: &str,
76 line: u32,
77 column: u32,
78 length: u32,
79 pos: u32,
80 source: TokenSource,
81 ) -> Self {
82 let id = resource_table::new_token_id();
83 let text = resource_table::insert_str(text);
84 Token {
85 id,
86 text,
87 line,
88 column,
89 length,
90 pos,
91 source,
92 }
93 }
94
95 pub fn generate(text: StrId, path: PathId) -> Self {
96 let id = resource_table::new_token_id();
97 Token {
98 id,
99 text,
100 line: 0,
101 column: 0,
102 length: 0,
103 pos: 0,
104 source: TokenSource::Generated(path),
105 }
106 }
107}
108
109pub fn is_anonymous_text(text: StrId) -> bool {
110 let anonymous_id = resource_table::insert_str("_");
111 text == anonymous_id
112}
113
114pub fn is_anonymous_token(token: &Token) -> bool {
115 is_anonymous_text(token.text)
116}
117
118impl fmt::Display for Token {
119 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
120 let text = format!("{}", self.text);
121 text.fmt(f)
122 }
123}
124
125impl<'t> TryFrom<&parol_runtime::lexer::Token<'t>> for Token {
126 type Error = anyhow::Error;
127 fn try_from(x: &parol_runtime::lexer::Token<'t>) -> Result<Self, anyhow::Error> {
128 let id = resource_table::new_token_id();
129 let text = resource_table::insert_str(x.text());
130 let pos = x.location.start;
131 let source = TokenSource::File {
132 path: resource_table::insert_path(&x.location.file_name),
133 text: text_table::get_current_text(),
134 };
135 Ok(Token {
136 id,
137 text,
138 line: x.location.start_line,
139 column: x.location.start_column,
140 length: x.location.len() as u32,
141 pos,
142 source,
143 })
144 }
145}
146
147impl From<&Token> for miette::SourceSpan {
148 fn from(x: &Token) -> Self {
149 (x.pos as usize, x.length as usize).into()
150 }
151}
152
153impl From<Token> for miette::SourceSpan {
154 fn from(x: Token) -> Self {
155 (x.pos as usize, x.length as usize).into()
156 }
157}
158
159#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
160pub struct TokenRange {
161 pub beg: Token,
162 pub end: Token,
163}
164
165impl TokenRange {
166 pub fn new(beg: &VerylToken, end: &VerylToken) -> Self {
167 Self {
168 beg: beg.token,
169 end: end.token,
170 }
171 }
172
173 pub fn include(&self, path: PathId, line: u32, column: u32) -> bool {
174 if self.beg.source == path {
175 if self.beg.line == line {
176 if self.end.line == line {
177 self.beg.column <= column && column <= self.end.column
178 } else {
179 self.beg.column <= column
180 }
181 } else if self.end.line == line {
182 column <= self.end.column
183 } else {
184 self.beg.line < line && line < self.end.line
185 }
186 } else {
187 false
188 }
189 }
190
191 pub fn offset(&mut self, value: u32) {
192 self.beg.pos += value;
193 self.end.pos += value;
194 }
195}
196
197impl From<&TokenRange> for miette::SourceSpan {
198 fn from(x: &TokenRange) -> Self {
199 let length = (x.end.pos - x.beg.pos + x.end.length) as usize;
200 (x.beg.pos as usize, length).into()
201 }
202}
203
204impl From<TokenRange> for miette::SourceSpan {
205 fn from(x: TokenRange) -> Self {
206 let length = (x.end.pos - x.beg.pos + x.end.length) as usize;
207 (x.beg.pos as usize, length).into()
208 }
209}
210
211impl From<Token> for TokenRange {
212 fn from(value: Token) -> Self {
213 let beg = value;
214 let end = value;
215 TokenRange { beg, end }
216 }
217}
218
219impl From<&Token> for TokenRange {
220 fn from(value: &Token) -> Self {
221 let beg = *value;
222 let end = *value;
223 TokenRange { beg, end }
224 }
225}
226
227impl From<&Identifier> for TokenRange {
228 fn from(value: &Identifier) -> Self {
229 let beg = value.identifier_token.token;
230 let end = value.identifier_token.token;
231 TokenRange { beg, end }
232 }
233}
234
235impl From<&HierarchicalIdentifier> for TokenRange {
236 fn from(value: &HierarchicalIdentifier) -> Self {
237 let beg = value.identifier.identifier_token.token;
238 let mut end = value.identifier.identifier_token.token;
239 if let Some(x) = value.hierarchical_identifier_list.last() {
240 end = x.select.r_bracket.r_bracket_token.token;
241 }
242 if let Some(x) = value.hierarchical_identifier_list0.last() {
243 end = x.identifier.identifier_token.token;
244 if let Some(x) = x.hierarchical_identifier_list0_list.last() {
245 end = x.select.r_bracket.r_bracket_token.token;
246 }
247 }
248 TokenRange { beg, end }
249 }
250}
251
252impl From<&ScopedIdentifier> for TokenRange {
253 fn from(value: &ScopedIdentifier) -> Self {
254 let beg = value.identifier().token;
255 let mut end = beg;
256 if let Some(x) = value.scoped_identifier_list.last() {
257 end = x.identifier.identifier_token.token;
258 }
259 TokenRange { beg, end }
260 }
261}
262
263impl From<&ExpressionIdentifier> for TokenRange {
264 fn from(value: &ExpressionIdentifier) -> Self {
265 let mut range: TokenRange = value.scoped_identifier.as_ref().into();
266 if let Some(ref x) = value.expression_identifier_opt {
267 range.end = x.width.r_angle.r_angle_token.token;
268 }
269 for x in &value.expression_identifier_list {
270 range.end = x.select.r_bracket.r_bracket_token.token;
271 }
272 for x in &value.expression_identifier_list0 {
273 range.end = x.identifier.identifier_token.token;
274 for x in &x.expression_identifier_list0_list {
275 range.end = x.select.r_bracket.r_bracket_token.token;
276 }
277 }
278 range
279 }
280}
281
282impl From<&AlwaysFfDeclaration> for TokenRange {
283 fn from(value: &AlwaysFfDeclaration) -> Self {
284 let beg = value.always_ff.always_ff_token.token;
285 let end = value.statement_block.r_brace.r_brace_token.token;
286 TokenRange { beg, end }
287 }
288}
289
290impl From<&Expression12ListGroup> for TokenRange {
291 fn from(value: &Expression12ListGroup) -> Self {
292 let beg = match value {
293 Expression12ListGroup::UnaryOperator(x) => x.unary_operator.unary_operator_token.token,
294 Expression12ListGroup::Operator09(x) => x.operator09.operator09_token.token,
295 Expression12ListGroup::Operator05(x) => x.operator05.operator05_token.token,
296 Expression12ListGroup::Operator04(x) => x.operator04.operator04_token.token,
297 Expression12ListGroup::Operator03(x) => x.operator03.operator03_token.token,
298 };
299 let end = beg;
300 TokenRange { beg, end }
301 }
302}
303
304impl From<&IntegralNumber> for TokenRange {
305 fn from(value: &IntegralNumber) -> Self {
306 let beg = match value {
307 IntegralNumber::Based(x) => x.based.based_token.token,
308 IntegralNumber::BaseLess(x) => x.base_less.base_less_token.token,
309 IntegralNumber::AllBit(x) => x.all_bit.all_bit_token.token,
310 };
311 let end = beg;
312 TokenRange { beg, end }
313 }
314}
315
316impl From<&RealNumber> for TokenRange {
317 fn from(value: &RealNumber) -> Self {
318 let beg = match value {
319 RealNumber::FixedPoint(x) => x.fixed_point.fixed_point_token.token,
320 RealNumber::Exponent(x) => x.exponent.exponent_token.token,
321 };
322 let end = beg;
323 TokenRange { beg, end }
324 }
325}
326
327impl From<&Number> for TokenRange {
328 fn from(value: &Number) -> Self {
329 match value {
330 Number::IntegralNumber(x) => x.integral_number.as_ref().into(),
331 Number::RealNumber(x) => x.real_number.as_ref().into(),
332 }
333 }
334}
335
336impl From<&TypeModifier> for TokenRange {
337 fn from(value: &TypeModifier) -> Self {
338 let beg = match value {
339 TypeModifier::Tri(x) => x.tri.tri_token.token,
340 TypeModifier::Signed(x) => x.signed.signed_token.token,
341 };
342 let end = beg;
343 TokenRange { beg, end }
344 }
345}
346
347macro_rules! impl_token_range {
348 ($typename:ty, $first:ident, $firsttok:ident, $last:ident, $lasttok:ident) => {
349 impl From<&$typename> for TokenRange {
350 fn from(value: &$typename) -> Self {
351 let beg = value.$first.$firsttok.token;
352 let end = value.$last.$lasttok.token;
353 TokenRange { beg, end }
354 }
355 }
356 };
357}
358
359macro_rules! impl_token_range_singular {
360 ($typename:ty, $first:ident) => {
361 impl From<&$typename> for TokenRange {
362 fn from(value: &$typename) -> Self {
363 let beg = value.$first.token;
364 let end = beg;
365 TokenRange { beg, end }
366 }
367 }
368 };
369}
370
371macro_rules! impl_token_range_dual {
372 ($typename:ty, $first:ident, $second:ident) => {
373 impl From<&$typename> for TokenRange {
374 fn from(value: &$typename) -> Self {
375 let beg = value.$first.$second.token;
376 let end = beg;
377 TokenRange { beg, end }
378 }
379 }
380 };
381}
382
383impl_token_range!(IfExpression, r#if, if_token, r_brace0, r_brace_token);
384impl_token_range!(CaseExpression, case, case_token, r_brace, r_brace_token);
385impl_token_range!(
386 FactorLParenExpressionRParen,
387 l_paren,
388 l_paren_token,
389 r_paren,
390 r_paren_token
391);
392impl_token_range!(
393 FactorLBraceConcatenationListRBrace,
394 l_brace,
395 l_brace_token,
396 r_brace,
397 r_brace_token
398);
399impl_token_range!(
400 FactorQuoteLBraceArrayLiteralListRBrace,
401 quote_l_brace,
402 quote_l_brace_token,
403 r_brace,
404 r_brace_token
405);
406impl_token_range_singular!(StringLiteral, string_literal_token);
407impl_token_range_dual!(FactorGroupMsb, msb, msb_token);
408impl_token_range_dual!(FactorGroupLsb, lsb, lsb_token);
409impl_token_range_singular!(Inside, inside_token);
410impl_token_range!(
411 InsideExpression,
412 inside,
413 inside_token,
414 r_brace,
415 r_brace_token
416);
417impl_token_range!(
418 OutsideExpression,
419 outside,
420 outside_token,
421 r_brace,
422 r_brace_token
423);
424impl_token_range!(
425 SwitchExpression,
426 switch,
427 switch_token,
428 r_brace,
429 r_brace_token
430);
431impl_token_range!(TypeExpression, r#type, type_token, r_paren, r_paren_token);
432impl_token_range!(LetStatement, r#let, let_token, semicolon, semicolon_token);
433impl_token_range!(LetDeclaration, r#let, let_token, semicolon, semicolon_token);
434impl_token_range!(
435 ConstDeclaration,
436 r#const,
437 const_token,
438 semicolon,
439 semicolon_token
440);
441impl_token_range!(
442 AssignDeclaration,
443 assign,
444 assign_token,
445 semicolon,
446 semicolon_token
447);
448
449impl From<&IdentifierStatement> for TokenRange {
450 fn from(value: &IdentifierStatement) -> Self {
451 let beg: TokenRange = value.expression_identifier.as_ref().into();
452 let end = value.semicolon.semicolon_token.token;
453 TokenRange { beg: beg.beg, end }
454 }
455}
456
457impl From<&FactorGroup> for TokenRange {
458 fn from(value: &FactorGroup) -> Self {
459 match value {
460 FactorGroup::Msb(x) => x.into(),
461 FactorGroup::Lsb(x) => x.into(),
462 }
463 }
464}
465
466impl From<&FactorTypeFactor> for TokenRange {
467 fn from(value: &FactorTypeFactor) -> Self {
468 let beg: TokenRange = if let Some(x) = value.factor_type_factor_list.first() {
469 x.type_modifier.as_ref().into()
470 } else {
471 value.factor_type.as_ref().into()
472 };
473 let end: TokenRange = value.factor_type.as_ref().into();
474 TokenRange {
475 beg: beg.beg,
476 end: end.end,
477 }
478 }
479}
480
481impl From<&Factor> for TokenRange {
482 fn from(value: &Factor) -> Self {
483 match value {
484 Factor::Number(x) => x.number.as_ref().into(),
485 Factor::IdentifierFactor(x) => {
486 x.identifier_factor.expression_identifier.as_ref().into()
487 }
488 Factor::LParenExpressionRParen(x) => x.into(),
489 Factor::LBraceConcatenationListRBrace(x) => x.into(),
490 Factor::QuoteLBraceArrayLiteralListRBrace(x) => x.into(),
491 Factor::IfExpression(x) => x.if_expression.as_ref().into(),
492 Factor::CaseExpression(x) => x.case_expression.as_ref().into(),
493 Factor::SwitchExpression(x) => x.switch_expression.as_ref().into(),
494 Factor::StringLiteral(x) => x.string_literal.as_ref().into(),
495 Factor::FactorGroup(x) => x.factor_group.as_ref().into(),
496 Factor::InsideExpression(x) => x.inside_expression.as_ref().into(),
497 Factor::OutsideExpression(x) => x.outside_expression.as_ref().into(),
498 Factor::TypeExpression(x) => x.type_expression.as_ref().into(),
499 Factor::FactorTypeFactor(x) => x.factor_type_factor.as_ref().into(),
500 }
501 }
502}
503
504impl From<&Expression11> for TokenRange {
505 fn from(value: &Expression11) -> Self {
506 let beg: TokenRange = value.expression12.as_ref().into();
507 let end = if let Some(ref x) = value.expression11_opt {
508 let end: TokenRange = x.casting_type.as_ref().into();
509 end.end
510 } else {
511 beg.end
512 };
513 let beg = beg.beg;
514 TokenRange { beg, end }
515 }
516}
517
518impl From<&Expression12> for TokenRange {
519 fn from(value: &Expression12) -> Self {
520 let end: TokenRange = value.factor.as_ref().into();
521 let beg = if value.expression12_list.is_empty() {
522 end.beg
523 } else {
524 let first = value.expression12_list.first().unwrap();
525 let t: TokenRange = first.expression12_list_group.as_ref().into();
526 t.beg
527 };
528 let end = end.end;
529 TokenRange { beg, end }
530 }
531}
532
533macro_rules! expression_token_range {
534 ($typename:ty, $beg:ident, $list:ident, $prev:ident) => {
535 impl From<&$typename> for TokenRange {
536 fn from(value: &$typename) -> Self {
537 let beg: TokenRange = value.$beg.as_ref().into();
538 let end = if value.$list.is_empty() {
539 beg.end
540 } else {
541 let last = value.$list.last().unwrap();
542 let end: TokenRange = last.$prev.as_ref().into();
543 end.end
544 };
545 let beg = beg.beg;
546 TokenRange { beg, end }
547 }
548 }
549 };
550}
551
552expression_token_range!(Expression10, expression11, expression10_list, expression11);
553expression_token_range!(Expression09, expression10, expression09_list, expression10);
554expression_token_range!(Expression08, expression09, expression08_list, expression09);
555expression_token_range!(Expression07, expression08, expression07_list, expression08);
556expression_token_range!(Expression06, expression07, expression06_list, expression07);
557expression_token_range!(Expression05, expression06, expression05_list, expression06);
558expression_token_range!(Expression04, expression05, expression04_list, expression05);
559expression_token_range!(Expression03, expression04, expression03_list, expression04);
560expression_token_range!(Expression02, expression03, expression02_list, expression03);
561expression_token_range!(Expression01, expression02, expression01_list, expression02);
562expression_token_range!(Expression, expression01, expression_list, expression01);
563
564impl From<&FixedType> for TokenRange {
565 fn from(value: &FixedType) -> Self {
566 let beg = match value {
567 FixedType::U32(x) => x.u32.u32_token.token,
568 FixedType::U64(x) => x.u64.u64_token.token,
569 FixedType::I32(x) => x.i32.i32_token.token,
570 FixedType::I64(x) => x.i64.i64_token.token,
571 FixedType::F32(x) => x.f32.f32_token.token,
572 FixedType::F64(x) => x.f64.f64_token.token,
573 FixedType::Strin(x) => x.strin.string_token.token,
574 };
575 let end = beg;
576 TokenRange { beg, end }
577 }
578}
579
580impl From<&VariableType> for TokenRange {
581 fn from(value: &VariableType) -> Self {
582 match value {
583 VariableType::Clock(x) => {
584 let beg = x.clock.clock_token.token;
585 let end = beg;
586 TokenRange { beg, end }
587 }
588 VariableType::ClockPosedge(x) => {
589 let beg = x.clock_posedge.clock_posedge_token.token;
590 let end = beg;
591 TokenRange { beg, end }
592 }
593 VariableType::ClockNegedge(x) => {
594 let beg = x.clock_negedge.clock_negedge_token.token;
595 let end = beg;
596 TokenRange { beg, end }
597 }
598 VariableType::Reset(x) => {
599 let beg = x.reset.reset_token.token;
600 let end = beg;
601 TokenRange { beg, end }
602 }
603 VariableType::ResetAsyncHigh(x) => {
604 let beg = x.reset_async_high.reset_async_high_token.token;
605 let end = beg;
606 TokenRange { beg, end }
607 }
608 VariableType::ResetAsyncLow(x) => {
609 let beg = x.reset_async_low.reset_async_low_token.token;
610 let end = beg;
611 TokenRange { beg, end }
612 }
613 VariableType::ResetSyncHigh(x) => {
614 let beg = x.reset_sync_high.reset_sync_high_token.token;
615 let end = beg;
616 TokenRange { beg, end }
617 }
618 VariableType::ResetSyncLow(x) => {
619 let beg = x.reset_sync_low.reset_sync_low_token.token;
620 let end = beg;
621 TokenRange { beg, end }
622 }
623 VariableType::Logic(x) => {
624 let beg = x.logic.logic_token.token;
625 let end = beg;
626 TokenRange { beg, end }
627 }
628 VariableType::Bit(x) => {
629 let beg = x.bit.bit_token.token;
630 let end = beg;
631 TokenRange { beg, end }
632 }
633 }
634 }
635}
636
637impl From<&FactorType> for TokenRange {
638 fn from(value: &FactorType) -> Self {
639 match value.factor_type_group.as_ref() {
640 FactorTypeGroup::VariableTypeFactorTypeOpt(x) => {
641 let mut range: TokenRange = x.variable_type.as_ref().into();
642 if let Some(ref x) = x.factor_type_opt {
643 range.end = x.width.r_angle.r_angle_token.token;
644 }
645 range
646 }
647 FactorTypeGroup::FixedType(x) => x.fixed_type.as_ref().into(),
648 }
649 }
650}
651
652impl From<&ScalarType> for TokenRange {
653 fn from(value: &ScalarType) -> Self {
654 let mut range: TokenRange = match &*value.scalar_type_group {
655 ScalarTypeGroup::UserDefinedTypeScalarTypeOpt(x) => {
656 let mut range: TokenRange = x.user_defined_type.scoped_identifier.as_ref().into();
657 if let Some(ref x) = x.scalar_type_opt {
658 range.end = x.width.r_angle.r_angle_token.token;
659 }
660 range
661 }
662 ScalarTypeGroup::FactorType(x) => x.factor_type.as_ref().into(),
663 };
664
665 if let Some(x) = value.scalar_type_list.first() {
666 range.beg = match &*x.type_modifier {
667 TypeModifier::Tri(x) => x.tri.tri_token.token,
668 TypeModifier::Signed(x) => x.r#signed.signed_token.token,
669 };
670 }
671
672 range
673 }
674}
675
676impl From<&ArrayType> for TokenRange {
677 fn from(value: &ArrayType) -> Self {
678 let mut range: TokenRange = value.scalar_type.as_ref().into();
679
680 if let Some(ref x) = value.array_type_opt {
681 range.end = x.array.r_bracket.r_bracket_token.token;
682 }
683
684 range
685 }
686}
687
688impl From<&CastingType> for TokenRange {
689 fn from(value: &CastingType) -> Self {
690 match value {
691 CastingType::U32(x) => {
692 let beg = x.u32.u32_token.token;
693 let end = beg;
694 TokenRange { beg, end }
695 }
696 CastingType::U64(x) => {
697 let beg = x.u64.u64_token.token;
698 let end = beg;
699 TokenRange { beg, end }
700 }
701 CastingType::I32(x) => {
702 let beg = x.i32.i32_token.token;
703 let end = beg;
704 TokenRange { beg, end }
705 }
706 CastingType::I64(x) => {
707 let beg = x.i64.i64_token.token;
708 let end = beg;
709 TokenRange { beg, end }
710 }
711 CastingType::F32(x) => {
712 let beg = x.f32.f32_token.token;
713 let end = beg;
714 TokenRange { beg, end }
715 }
716 CastingType::F64(x) => {
717 let beg = x.f64.f64_token.token;
718 let end = beg;
719 TokenRange { beg, end }
720 }
721 CastingType::Clock(x) => {
722 let beg = x.clock.clock_token.token;
723 let end = beg;
724 TokenRange { beg, end }
725 }
726 CastingType::ClockPosedge(x) => {
727 let beg = x.clock_posedge.clock_posedge_token.token;
728 let end = beg;
729 TokenRange { beg, end }
730 }
731 CastingType::ClockNegedge(x) => {
732 let beg = x.clock_negedge.clock_negedge_token.token;
733 let end = beg;
734 TokenRange { beg, end }
735 }
736 CastingType::Reset(x) => {
737 let beg = x.reset.reset_token.token;
738 let end = beg;
739 TokenRange { beg, end }
740 }
741 CastingType::ResetAsyncHigh(x) => {
742 let beg = x.reset_async_high.reset_async_high_token.token;
743 let end = beg;
744 TokenRange { beg, end }
745 }
746 CastingType::ResetAsyncLow(x) => {
747 let beg = x.reset_async_low.reset_async_low_token.token;
748 let end = beg;
749 TokenRange { beg, end }
750 }
751 CastingType::ResetSyncHigh(x) => {
752 let beg = x.reset_sync_high.reset_sync_high_token.token;
753 let end = beg;
754 TokenRange { beg, end }
755 }
756 CastingType::ResetSyncLow(x) => {
757 let beg = x.reset_sync_low.reset_sync_low_token.token;
758 let end = beg;
759 TokenRange { beg, end }
760 }
761 CastingType::UserDefinedType(x) => {
762 x.user_defined_type.scoped_identifier.as_ref().into()
763 }
764 CastingType::Based(x) => {
765 let beg = x.based.based_token.token;
766 let end = beg;
767 TokenRange { beg, end }
768 }
769 CastingType::BaseLess(x) => {
770 let beg = x.base_less.base_less_token.token;
771 let end = beg;
772 TokenRange { beg, end }
773 }
774 }
775 }
776}
777
778impl From<&InstPortItem> for TokenRange {
779 fn from(value: &InstPortItem) -> Self {
780 let beg: TokenRange = value.identifier.as_ref().into();
781 let end = if let Some(x) = &value.inst_port_item_opt {
782 x.expression.as_ref().into()
783 } else {
784 beg
785 };
786
787 TokenRange {
788 beg: beg.beg,
789 end: end.end,
790 }
791 }
792}
793
794impl From<&ClockDomain> for TokenRange {
795 fn from(clock_domain: &ClockDomain) -> Self {
796 let beg = clock_domain.back_quote.back_quote_token.token;
797 let end = clock_domain.identifier.identifier_token.token;
798 TokenRange { beg, end }
799 }
800}
801
802#[derive(Debug, Clone)]
803pub struct VerylToken {
804 pub token: Token,
805 pub comments: Vec<Token>,
806}
807
808impl VerylToken {
809 pub fn new(token: Token) -> Self {
810 Self {
811 token,
812 comments: vec![],
813 }
814 }
815
816 pub fn replace(&self, text: &str) -> Self {
817 let length = text.len();
818 let text = resource_table::insert_str(text);
819 let mut ret = self.clone();
820 ret.token.text = text;
821 ret.token.length = length as u32;
822 ret
823 }
824
825 pub fn append(&self, prefix: &Option<String>, suffix: &Option<String>) -> Self {
826 let prefix_str = if let Some(x) = prefix { x.as_str() } else { "" };
827 let suffix_str = if let Some(x) = suffix { x.as_str() } else { "" };
828 let text = format!("{}{}{}", prefix_str, self.token.text, suffix_str);
829 let length = text.len();
830 let text = resource_table::insert_str(&text);
831 let mut ret = self.clone();
832 ret.token.text = text;
833 ret.token.length = length as u32;
834 ret
835 }
836
837 pub fn strip_prefix(&self, prefix: &str) -> Self {
838 let text = self.token.text.to_string();
839 if let Some(text) = text.strip_prefix(prefix) {
840 let length = text.len();
841 let text = resource_table::insert_str(text);
842 let mut ret = self.clone();
843 ret.token.text = text;
844 ret.token.length = length as u32;
845 ret
846 } else {
847 self.clone()
848 }
849 }
850}
851
852impl fmt::Display for VerylToken {
853 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
854 let text = format!("{}", self.token);
855 text.fmt(f)
856 }
857}
858
859impl ScopedIdentifier {
860 pub fn identifier(&self) -> &VerylToken {
861 match &*self.scoped_identifier_group {
862 ScopedIdentifierGroup::IdentifierScopedIdentifierOpt(x) => {
863 &x.identifier.identifier_token
864 }
865 ScopedIdentifierGroup::DollarIdentifier(x) => {
866 &x.dollar_identifier.dollar_identifier_token
867 }
868 }
869 }
870}
871
872impl ExpressionIdentifier {
873 pub fn identifier(&self) -> &VerylToken {
874 self.scoped_identifier.identifier()
875 }
876}
877
878static COMMENT_REGEX: Lazy<Regex> =
879 Lazy::new(|| Regex::new(r"((?://.*(?:\r\n|\r|\n|$))|(?:(?ms)/\u{2a}.*?\u{2a}/))").unwrap());
880
881fn split_comment_token(token: Token) -> Vec<Token> {
882 let mut line = token.line;
883 let text = resource_table::get_str_value(token.text).unwrap();
884
885 let mut prev_pos = 0;
886 let mut ret = Vec::new();
887 for cap in COMMENT_REGEX.captures_iter(&text) {
888 let cap = cap.get(0).unwrap();
889 let pos = cap.start();
890 let length = (cap.end() - pos) as u32;
891
892 line += text[prev_pos..(pos)].matches('\n').count() as u32;
893 prev_pos = pos;
894
895 let id = resource_table::new_token_id();
896 let text = &text[pos..pos + length as usize];
897 let is_doc_comment = text.starts_with("///");
898 let text = resource_table::insert_str(text);
899
900 if is_doc_comment {
901 if let TokenSource::File { path, .. } = token.source {
902 doc_comment_table::insert(path, line, text);
903 }
904 }
905
906 let token = Token {
907 id,
908 text,
909 line,
910 column: 0,
911 length,
912 pos: pos as u32 + length,
913 source: token.source,
914 };
915 ret.push(token);
916 }
917 ret
918}
919
920impl TryFrom<&StartToken> for VerylToken {
921 type Error = anyhow::Error;
922
923 fn try_from(x: &StartToken) -> Result<Self, anyhow::Error> {
924 let mut comments = Vec::new();
925 if let Some(ref x) = x.comments.comments_opt {
926 let mut tokens = split_comment_token(x.comments_term.comments_term);
927 comments.append(&mut tokens)
928 }
929 let id = resource_table::new_token_id();
930 let text = resource_table::insert_str("");
931 let source = TokenSource::Builtin;
932 let token = Token {
933 id,
934 text,
935 line: 1,
936 column: 1,
937 length: 0,
938 pos: 0,
939 source,
940 };
941 Ok(VerylToken { token, comments })
942 }
943}
944
945macro_rules! token_with_comments {
946 ($x:ident) => {
947 paste! {
948 impl TryFrom<&[<$x Token>]> for VerylToken {
949 type Error = anyhow::Error;
950
951 fn try_from(x: &[<$x Token>]) -> Result<Self, anyhow::Error> {
952 let mut comments = Vec::new();
953 if let Some(ref x) = x.comments.comments_opt {
954 let mut tokens = split_comment_token(x.comments_term.comments_term);
955 comments.append(&mut tokens)
956 }
957 Ok(VerylToken {
958 token: x.[<$x:snake _term>].clone(),
959 comments,
960 })
961 }
962 }
963 impl TryFrom<&[<$x Term>]> for Token {
964 type Error = anyhow::Error;
965
966 fn try_from(x: &[<$x Term>]) -> Result<Self, anyhow::Error> {
967 Ok(Token {
968 id: x.[<$x:snake _term>].id,
969 text: x.[<$x:snake _term>].text,
970 line: x.[<$x:snake _term>].line,
971 column: x.[<$x:snake _term>].column,
972 length: x.[<$x:snake _term>].length,
973 pos: x.[<$x:snake _term>].pos,
974 source: x.[<$x:snake _term>].source,
975 })
976 }
977 }
978 }
979 };
980}
981
982token_with_comments!(StringLiteral);
983
984token_with_comments!(FixedPoint);
985token_with_comments!(Exponent);
986token_with_comments!(Based);
987token_with_comments!(BaseLess);
988token_with_comments!(AllBit);
989
990token_with_comments!(BackQuote);
991token_with_comments!(Colon);
992token_with_comments!(ColonColon);
993token_with_comments!(ColonColonLAngle);
994token_with_comments!(Comma);
995token_with_comments!(DotDot);
996token_with_comments!(DotDotEqu);
997token_with_comments!(Dot);
998token_with_comments!(Equ);
999token_with_comments!(Hash);
1000token_with_comments!(QuoteLBrace);
1001token_with_comments!(LAngle);
1002token_with_comments!(LBrace);
1003token_with_comments!(LBracket);
1004token_with_comments!(LParen);
1005token_with_comments!(MinusColon);
1006token_with_comments!(MinusGT);
1007token_with_comments!(PlusColon);
1008token_with_comments!(RAngle);
1009token_with_comments!(RBrace);
1010token_with_comments!(RBracket);
1011token_with_comments!(RParen);
1012token_with_comments!(Semicolon);
1013token_with_comments!(Star);
1014
1015token_with_comments!(AssignmentOperator);
1016token_with_comments!(Operator01);
1017token_with_comments!(Operator02);
1018token_with_comments!(Operator03);
1019token_with_comments!(Operator04);
1020token_with_comments!(Operator05);
1021token_with_comments!(Operator06);
1022token_with_comments!(Operator07);
1023token_with_comments!(Operator08);
1024token_with_comments!(Operator09);
1025token_with_comments!(Operator10);
1026token_with_comments!(Operator11);
1027token_with_comments!(UnaryOperator);
1028
1029token_with_comments!(AlwaysComb);
1030token_with_comments!(AlwaysFf);
1031token_with_comments!(As);
1032token_with_comments!(Assign);
1033token_with_comments!(Bit);
1034token_with_comments!(Break);
1035token_with_comments!(Case);
1036token_with_comments!(Clock);
1037token_with_comments!(ClockPosedge);
1038token_with_comments!(ClockNegedge);
1039token_with_comments!(Const);
1040token_with_comments!(Converse);
1041token_with_comments!(Default);
1042token_with_comments!(Else);
1043token_with_comments!(Embed);
1044token_with_comments!(Enum);
1045token_with_comments!(Export);
1046token_with_comments!(F32);
1047token_with_comments!(F64);
1048token_with_comments!(Final);
1049token_with_comments!(For);
1050token_with_comments!(Function);
1051token_with_comments!(I32);
1052token_with_comments!(I64);
1053token_with_comments!(If);
1054token_with_comments!(IfReset);
1055token_with_comments!(Import);
1056token_with_comments!(Include);
1057token_with_comments!(Initial);
1058token_with_comments!(Inout);
1059token_with_comments!(Input);
1060token_with_comments!(Inside);
1061token_with_comments!(Inst);
1062token_with_comments!(Interface);
1063token_with_comments!(In);
1064token_with_comments!(Let);
1065token_with_comments!(Logic);
1066token_with_comments!(Lsb);
1067token_with_comments!(Modport);
1068token_with_comments!(Module);
1069token_with_comments!(Msb);
1070token_with_comments!(Output);
1071token_with_comments!(Outside);
1072token_with_comments!(Package);
1073token_with_comments!(Param);
1074token_with_comments!(Proto);
1075token_with_comments!(Pub);
1076token_with_comments!(Ref);
1077token_with_comments!(Repeat);
1078token_with_comments!(Reset);
1079token_with_comments!(ResetAsyncHigh);
1080token_with_comments!(ResetAsyncLow);
1081token_with_comments!(ResetSyncHigh);
1082token_with_comments!(ResetSyncLow);
1083token_with_comments!(Return);
1084token_with_comments!(Signed);
1085token_with_comments!(Step);
1086token_with_comments!(String);
1087token_with_comments!(Struct);
1088token_with_comments!(Switch);
1089token_with_comments!(Tri);
1090token_with_comments!(Type);
1091token_with_comments!(U32);
1092token_with_comments!(U64);
1093token_with_comments!(Union);
1094token_with_comments!(Unsafe);
1095token_with_comments!(Var);
1096
1097token_with_comments!(DollarIdentifier);
1098token_with_comments!(Identifier);
1099
1100fn embed_item_to_string(x: &EmbedItem) -> String {
1101 let mut ret = String::new();
1102 match x {
1103 EmbedItem::LBraceTermEmbedItemListRBraceTerm(x) => {
1104 ret.push_str(&x.l_brace_term.l_brace_term.to_string());
1105 for x in &x.embed_item_list {
1106 ret.push_str(&embed_item_to_string(&x.embed_item));
1107 }
1108 ret.push_str(&x.r_brace_term.r_brace_term.to_string());
1109 }
1110 EmbedItem::AnyTerm(x) => {
1111 ret.push_str(&x.any_term.any_term.to_string());
1112 }
1113 }
1114 ret
1115}
1116
1117impl TryFrom<&EmbedContentToken> for VerylToken {
1118 type Error = anyhow::Error;
1119
1120 fn try_from(x: &EmbedContentToken) -> Result<Self, anyhow::Error> {
1121 let head_token = &x.l_brace_term.l_brace_term;
1122 let line = head_token.line;
1123 let column = head_token.column;
1124 let length = head_token.length;
1125 let pos = head_token.pos;
1126 let source = head_token.source;
1127
1128 let mut text = x.l_brace_term.l_brace_term.to_string();
1129 text.push_str(&x.l_brace_term0.l_brace_term.to_string());
1130 text.push_str(&x.l_brace_term1.l_brace_term.to_string());
1131 for x in &x.embed_content_token_list {
1132 text.push_str(&embed_item_to_string(&x.embed_item));
1133 }
1134 text.push_str(&x.r_brace_term.r_brace_term.to_string());
1135 text.push_str(&x.r_brace_term0.r_brace_term.to_string());
1136 text.push_str(&x.r_brace_term1.r_brace_term.to_string());
1137
1138 let mut comments = Vec::new();
1139 if let Some(ref x) = x.comments.comments_opt {
1140 let mut tokens = split_comment_token(x.comments_term.comments_term);
1141 comments.append(&mut tokens)
1142 }
1143
1144 let token = Token::new(&text, line, column, length, pos, source);
1145 Ok(VerylToken { token, comments })
1146 }
1147}