1use std;
7use std::fmt;
8
9use crate::lexer::token::Literal;
10use moore_common::name::Name;
11use moore_common::source::{Span, Spanned};
12use moore_common::util::{HasDesc, HasSpan};
13
14pub use self::ExprData::*;
15pub use self::StmtData::*;
16pub use self::TypeData::*;
17
18#[derive(Clone, Copy, PartialEq, PartialOrd, Eq, Ord, Hash, Debug)]
22pub struct NodeId(u32);
23
24impl NodeId {
25 pub fn new(x: usize) -> NodeId {
26 use std::u32;
27 assert!(x < (u32::MAX as usize));
28 NodeId(x as u32)
29 }
30
31 pub fn from_u32(x: u32) -> NodeId {
32 NodeId(x)
33 }
34
35 pub fn as_usize(&self) -> usize {
36 self.0 as usize
37 }
38
39 pub fn as_u32(&self) -> u32 {
40 self.0
41 }
42}
43
44impl std::fmt::Display for NodeId {
45 fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
46 write!(f, "{}", self.0)
47 }
48}
49
50impl Default for NodeId {
51 fn default() -> NodeId {
52 DUMMY_NODE_ID
53 }
54}
55
56pub const DUMMY_NODE_ID: NodeId = NodeId(0);
60
61#[derive(Clone, Debug, PartialEq, Eq)]
65pub struct DesignUnit {
66 pub id: NodeId,
67 pub ctx: Vec<CtxItem>,
68 pub data: DesignUnitData,
69}
70
71#[derive(Clone, Debug, PartialEq, Eq)]
72pub enum DesignUnitData {
73 EntityDecl(EntityDecl),
74 CfgDecl(CfgDecl),
75 PkgDecl(PkgDecl),
76 PkgInst(PkgInst),
77 CtxDecl(CtxDecl),
78 ArchBody(ArchBody),
79 PkgBody(PkgBody),
80}
81
82#[derive(Clone, Debug, PartialEq, Eq)]
84pub enum CtxItem {
85 LibClause(Spanned<Vec<Ident>>),
86 UseClause(Spanned<Vec<CompoundName>>),
87 CtxRef(Spanned<Vec<CompoundName>>),
88}
89
90#[derive(Copy, Clone, Debug, PartialEq, Eq)]
92pub struct Ident {
94 pub id: NodeId,
95 pub span: Span,
96 pub name: Name,
97}
98
99impl From<Spanned<Name>> for Ident {
100 fn from(n: Spanned<Name>) -> Ident {
101 Ident {
102 id: Default::default(),
103 span: n.span,
104 name: n.value,
105 }
106 }
107}
108
109impl Into<Spanned<Name>> for Ident {
110 fn into(self) -> Spanned<Name> {
111 Spanned::new(self.name, self.span)
112 }
113}
114
115#[derive(Clone, Debug, PartialEq, Eq)]
132pub struct CompoundName {
133 pub id: NodeId,
134 pub span: Span,
135 pub primary: PrimaryName,
136 pub parts: Vec<NamePart>,
137}
138
139impl HasSpan for CompoundName {
140 fn span(&self) -> Span {
141 self.span
142 }
143}
144
145impl HasDesc for CompoundName {
146 fn desc(&self) -> &'static str {
147 "name"
148 }
149}
150
151#[derive(Copy, Clone, Debug, PartialEq, Eq)]
152pub struct PrimaryName {
153 pub id: NodeId,
154 pub span: Span,
155 pub kind: PrimaryNameKind,
156}
157
158#[derive(Copy, Clone, Debug, PartialEq, Eq)]
159pub enum PrimaryNameKind {
160 Ident(Name),
161 Char(char),
162 String(Name),
163}
164
165#[derive(Clone, Debug, PartialEq, Eq)]
166pub enum NamePart {
167 Select(PrimaryName),
168 SelectAll(Span),
169 Signature(Signature),
170 Attribute(Ident),
171 Call(ParenElems),
172 Range(Box<Expr>),
173}
174
175#[derive(Clone, Debug, PartialEq, Eq)]
177pub struct CtxDecl {
178 pub id: NodeId,
179 pub span: Span,
180 pub name: Spanned<Name>,
181 pub items: Vec<CtxItem>,
182}
183
184#[derive(Clone, Debug, PartialEq, Eq)]
186pub struct EntityDecl {
187 pub id: NodeId,
188 pub span: Span,
189 pub name: Spanned<Name>,
190 pub decls: Vec<DeclItem>,
191 pub stmts: Option<Vec<Stmt>>,
192}
193
194#[derive(Clone, Debug, PartialEq, Eq)]
196pub struct CfgDecl {
197 pub id: NodeId,
198 pub span: Span,
199 pub name: Spanned<Name>,
200 pub target: CompoundName,
201 pub decls: Vec<DeclItem>,
202}
203
204#[derive(Clone, Debug, PartialEq, Eq)]
206pub struct ArchBody {
207 pub id: NodeId,
208 pub span: Span,
209 pub name: Spanned<Name>,
210 pub target: CompoundName,
211 pub decls: Vec<DeclItem>,
212 pub stmts: Vec<Stmt>,
213}
214
215#[derive(Clone, Debug, PartialEq, Eq)]
217pub struct PkgDecl {
218 pub id: NodeId,
219 pub span: Span,
220 pub name: Spanned<Name>,
221 pub decls: Vec<DeclItem>,
222}
223
224#[derive(Clone, Debug, PartialEq, Eq)]
226pub struct PkgBody {
227 pub id: NodeId,
228 pub span: Span,
229 pub name: Spanned<Name>,
230 pub decls: Vec<DeclItem>,
231}
232
233#[derive(Clone, Debug, PartialEq, Eq)]
235pub struct PkgInst {
236 pub id: NodeId,
237 pub span: Span,
238 pub name: Spanned<Name>,
239 pub target: CompoundName,
240 pub generics: Option<ParenElems>,
241}
242
243#[derive(Clone, Debug, PartialEq, Eq)]
245pub enum IntfDecl {
246 TypeDecl(TypeDecl),
247 SubprogSpec(IntfSubprogDecl),
248 PkgInst(PkgInst),
249 ObjDecl(IntfObjDecl),
250}
251
252impl HasSpan for IntfDecl {
253 fn span(&self) -> Span {
254 match *self {
255 IntfDecl::TypeDecl(ref n) => n.span,
256 IntfDecl::SubprogSpec(ref n) => n.span,
257 IntfDecl::PkgInst(ref n) => n.span,
258 IntfDecl::ObjDecl(ref n) => n.span,
259 }
260 }
261
262 fn human_span(&self) -> Span {
263 match *self {
264 IntfDecl::TypeDecl(ref n) => n.name.span,
265 IntfDecl::PkgInst(ref n) => n.name.span,
266 _ => self.span(),
267 }
268 }
269}
270
271impl HasDesc for IntfDecl {
272 fn desc(&self) -> &'static str {
273 match *self {
274 IntfDecl::TypeDecl(_) => "interface type declaration",
275 IntfDecl::SubprogSpec(_) => "interface subprogram declaration",
276 IntfDecl::PkgInst(_) => "interface package declaration",
277 IntfDecl::ObjDecl(ref n) => n.desc(),
278 }
279 }
280}
281
282#[derive(Clone, Debug, PartialEq, Eq)]
283pub struct IntfSubprogDecl {
284 pub id: NodeId,
285 pub span: Span,
286 pub spec: SubprogSpec,
287 pub default: Option<SubprogDefault>,
288}
289
290#[derive(Clone, Debug, PartialEq, Eq)]
291pub enum SubprogDefault {
292 Any,
293 Name(CompoundName),
294}
295
296#[derive(Clone, Debug, PartialEq, Eq)]
298pub struct IntfObjDecl {
299 pub kind: IntfObjKind,
300 pub span: Span,
301 pub names: Vec<Ident>,
302 pub mode: Option<IntfMode>,
303 pub ty: SubtypeInd,
304 pub bus: bool,
305 pub default: Option<Expr>,
306}
307
308impl HasDesc for IntfObjDecl {
309 fn desc(&self) -> &'static str {
310 match self.kind {
311 IntfObjKind::Const => "interface constant declaration",
312 IntfObjKind::Signal => "interface signal declaration",
313 IntfObjKind::Var => "interface variable declaration",
314 IntfObjKind::File => "interface file declaration",
315 }
316 }
317}
318
319#[derive(Clone, Copy, Debug, PartialEq, Eq)]
320pub enum IntfObjKind {
321 Const,
322 Signal,
323 Var,
324 File,
325}
326
327#[derive(Clone, Copy, Debug, PartialEq, Eq)]
328pub enum IntfMode {
329 In,
330 Out,
331 Inout,
332 Buffer,
333 Linkage,
334}
335
336#[derive(Clone, Debug, PartialEq, Eq)]
338pub enum DeclItem {
339 PkgBody(PkgBody),
340 PkgInst(PkgInst),
341 PkgDecl(PkgDecl),
342 TypeDecl(TypeDecl),
343 SubtypeDecl(SubtypeDecl),
344 ObjDecl(ObjDecl),
345 AliasDecl(AliasDecl),
346 UseClause(Span, Spanned<Vec<CompoundName>>),
347 SubprogDecl(Subprog),
348 CompDecl(CompDecl),
349 DisconDecl(DisconSpec),
350 CfgSpec(CfgSpec),
351 AttrDecl(AttrDecl),
352 PortgenMap(Span, Spanned<PortgenKind>, ParenElems),
353 PortgenClause(Span, Spanned<PortgenKind>, Spanned<Vec<IntfDecl>>),
354 GroupDecl(GroupDecl),
355 VunitBindInd(()),
356 BlockCompCfg(BlockCompCfg),
357}
358
359impl HasSpan for DeclItem {
360 fn span(&self) -> Span {
361 match *self {
362 DeclItem::PkgBody(ref n) => n.span,
363 DeclItem::PkgInst(ref n) => n.span,
364 DeclItem::PkgDecl(ref n) => n.span,
365 DeclItem::TypeDecl(ref n) => n.span,
366 DeclItem::SubtypeDecl(ref n) => n.span,
367 DeclItem::ObjDecl(ref n) => n.span,
368 DeclItem::AliasDecl(ref n) => n.span,
369 DeclItem::UseClause(sp, ref n) => Span::union(sp, n.span),
370 DeclItem::SubprogDecl(ref n) => n.span(),
371 DeclItem::CompDecl(ref n) => n.span,
372 DeclItem::DisconDecl(ref n) => n.span,
373 DeclItem::CfgSpec(ref n) => n.span,
374 DeclItem::AttrDecl(ref n) => n.span,
375 DeclItem::PortgenMap(sp, _, _) => sp,
376 DeclItem::PortgenClause(sp, _, _) => sp,
377 DeclItem::GroupDecl(ref n) => n.span,
378 DeclItem::VunitBindInd(_) => unimplemented!(),
379 DeclItem::BlockCompCfg(ref n) => n.span,
380 }
381 }
382
383 fn human_span(&self) -> Span {
384 match *self {
385 DeclItem::PkgBody(ref n) => n.name.span,
386 DeclItem::PkgInst(ref n) => n.name.span,
387 DeclItem::PkgDecl(ref n) => n.name.span,
388 DeclItem::TypeDecl(ref n) => n.name.span,
389 DeclItem::SubtypeDecl(ref n) => n.name.span,
390 DeclItem::AliasDecl(ref n) => n.name.span,
391 DeclItem::UseClause(sp, _) => sp,
392 DeclItem::SubprogDecl(ref n) => n.human_span(),
393 DeclItem::PortgenMap(_, Spanned { span, .. }, _) => span,
394 DeclItem::PortgenClause(_, Spanned { span, .. }, _) => span,
395 _ => self.span(),
396 }
397 }
398}
399
400impl HasDesc for DeclItem {
401 fn desc(&self) -> &'static str {
402 match *self {
403 DeclItem::PkgBody(..) => "package body",
404 DeclItem::PkgInst(..) => "package instance",
405 DeclItem::PkgDecl(..) => "package declaration",
406 DeclItem::TypeDecl(..) => "type declaration",
407 DeclItem::SubtypeDecl(..) => "subtype declaration",
408 DeclItem::ObjDecl(..) => "object declaration",
409 DeclItem::AliasDecl(..) => "alias declaration",
410 DeclItem::UseClause(..) => "use clause",
411 DeclItem::SubprogDecl(ref n) => n.desc(),
412 DeclItem::CompDecl(..) => "component declaration",
413 DeclItem::DisconDecl(..) => "disconnection declaration",
414 DeclItem::CfgSpec(..) => "configuration specification",
415 DeclItem::AttrDecl(..) => "attribute declaration",
416 DeclItem::PortgenMap(
417 _,
418 Spanned {
419 value: PortgenKind::Port,
420 ..
421 },
422 ..,
423 ) => "port map",
424 DeclItem::PortgenMap(
425 _,
426 Spanned {
427 value: PortgenKind::Generic,
428 ..
429 },
430 ..,
431 ) => "generic map",
432 DeclItem::PortgenClause(
433 _,
434 Spanned {
435 value: PortgenKind::Port,
436 ..
437 },
438 ..,
439 ) => "port clause",
440 DeclItem::PortgenClause(
441 _,
442 Spanned {
443 value: PortgenKind::Generic,
444 ..
445 },
446 ..,
447 ) => "generic clause",
448 DeclItem::GroupDecl(..) => "group declaration",
449 DeclItem::VunitBindInd(..) => "vunit binding indication",
450 DeclItem::BlockCompCfg(..) => "block component configuration",
451 }
452 }
453}
454
455#[derive(Copy, Clone, Debug, PartialEq, Eq)]
456pub enum PortgenKind {
457 Port,
458 Generic,
459}
460
461#[derive(Clone, Debug, PartialEq, Eq)]
462pub struct Subprog {
463 pub id: NodeId,
464 pub span: Span,
465 pub spec: SubprogSpec,
466 pub data: SubprogData,
467}
468
469impl HasSpan for Subprog {
470 fn span(&self) -> Span {
471 self.span
472 }
473
474 fn human_span(&self) -> Span {
475 self.spec.name.span
476 }
477}
478
479impl HasDesc for Subprog {
480 fn desc(&self) -> &'static str {
481 self.data.desc()
482 }
483}
484
485#[derive(Clone, Debug, PartialEq, Eq)]
486pub enum SubprogData {
487 Decl,
488 Inst {
489 name: CompoundName,
490 generics: Option<ParenElems>,
491 },
492 Body {
493 decls: Vec<DeclItem>,
494 stmts: Vec<Stmt>,
495 },
496}
497
498impl HasDesc for SubprogData {
499 fn desc(&self) -> &'static str {
500 match *self {
501 SubprogData::Decl => "subprogram declaration",
502 SubprogData::Inst { .. } => "subprogram instantiation",
503 SubprogData::Body { .. } => "subprogram body",
504 }
505 }
506}
507
508#[derive(Clone, Debug, PartialEq, Eq)]
509pub struct SubprogSpec {
510 pub span: Span,
511 pub name: PrimaryName,
512 pub kind: SubprogKind,
513 pub purity: Option<SubprogPurity>,
514 pub generic_clause: Option<Vec<IntfDecl>>,
515 pub generic_map: Option<ParenElems>,
516 pub params: Option<Vec<IntfDecl>>,
517 pub retty: Option<CompoundName>,
518}
519
520#[derive(Copy, Clone, Debug, PartialEq, Eq)]
521pub enum SubprogPurity {
522 Pure,
523 Impure,
524}
525
526#[derive(Copy, Clone, Debug, PartialEq, Eq)]
527pub enum SubprogKind {
528 Proc,
529 Func,
530}
531
532#[derive(Clone, Debug, PartialEq, Eq)]
533pub struct SubtypeInd {
534 pub span: Span,
535 pub res: Option<ResolInd>,
536 pub name: CompoundName,
537}
538
539impl HasSpan for SubtypeInd {
540 fn span(&self) -> Span {
541 self.span
542 }
543}
544
545impl HasDesc for SubtypeInd {
546 fn desc(&self) -> &'static str {
547 "subtype indication"
548 }
549}
550
551#[derive(Clone, Debug, PartialEq, Eq)]
552pub struct SubtypeDecl {
553 pub id: NodeId,
554 pub span: Span,
555 pub name: Spanned<Name>,
556 pub subtype: SubtypeInd,
557}
558
559#[derive(Clone, Debug, PartialEq, Eq)]
560pub enum ResolInd {
561 Exprs(ParenElems),
562 Name(CompoundName),
563}
564
565#[derive(Clone, Debug, PartialEq, Eq)]
567pub struct AliasDecl {
568 pub id: NodeId,
569 pub span: Span,
570 pub name: PrimaryName,
571 pub subtype: Option<SubtypeInd>,
572 pub target: CompoundName,
573}
574
575#[derive(Clone, Debug, PartialEq, Eq)]
576pub struct ObjDecl {
577 pub span: Span,
578 pub kind: ObjKind,
579 pub names: Vec<Ident>,
580 pub subtype: SubtypeInd,
581 pub detail: Option<Spanned<ObjDetail>>,
582 pub init: Option<Expr>,
583}
584
585#[derive(Copy, Clone, Debug, PartialEq, Eq)]
586pub enum ObjKind {
587 Const,
588 Signal,
589 File,
590 Var,
591 SharedVar,
592}
593
594#[derive(Clone, Debug, PartialEq, Eq)]
597pub enum ObjDetail {
598 Register,
599 Bus,
600 Open(Option<Expr>, Expr),
602}
603
604impl HasSpan for ObjDecl {
605 fn span(&self) -> Span {
606 self.span
607 }
608
609 fn human_span(&self) -> Span {
610 self.names
611 .iter()
612 .map(|n| n.span)
613 .fold(self.names[0].span, Span::union)
614 }
615}
616
617impl HasDesc for ObjDecl {
618 fn desc(&self) -> &'static str {
619 match self.kind {
620 ObjKind::Const => "constant declaration",
621 ObjKind::Signal => "signal declaration",
622 ObjKind::File => "file declaration",
623 ObjKind::Var => "variable declaration",
624 ObjKind::SharedVar => "shared variable declaration",
625 }
626 }
627}
628
629#[derive(Clone, Debug, PartialEq, Eq)]
631pub struct CompDecl {
632 pub id: NodeId,
633 pub span: Span,
634 pub name: Spanned<Name>,
635 pub generics: Option<Spanned<Vec<IntfDecl>>>,
636 pub ports: Option<Spanned<Vec<IntfDecl>>>,
637}
638
639#[derive(Clone, Debug, PartialEq, Eq)]
640pub struct DisconSpec {
641 pub span: Span,
642 pub target: DisconTarget,
643 pub ty: CompoundName,
644 pub after: Expr,
645}
646
647#[derive(Clone, Debug, PartialEq, Eq)]
648pub enum DisconTarget {
649 Others,
650 All,
651 Signals(Vec<CompoundName>),
652}
653
654#[derive(Clone, Debug, PartialEq, Eq)]
655pub struct BlockCompCfg {
656 pub span: Span,
657 pub spec: Spanned<BlockCompSpec>,
658 pub bind: BindingInd,
659 pub decls: Vec<DeclItem>,
660}
661
662#[derive(Clone, Debug, PartialEq, Eq)]
663pub enum BlockCompSpec {
664 CompOthers(CompoundName),
665 CompAll(CompoundName),
666 CompNames(Vec<Ident>, CompoundName),
667 Block(CompoundName),
668}
669
670#[derive(Clone, Debug, PartialEq, Eq)]
671pub struct BindingInd {
672 pub span: Span,
673 pub entity: Option<EntityAspect>,
674 pub generics: Option<ParenElems>,
675 pub ports: Option<ParenElems>,
676}
677
678#[derive(Clone, Debug, PartialEq, Eq)]
679pub enum EntityAspect {
680 Entity(CompoundName),
681 Cfg(CompoundName),
682 Open,
683}
684
685#[derive(Clone, Debug, PartialEq, Eq)]
686pub struct CfgSpec {
687 pub span: Span,
688 pub spec: Spanned<BlockCompSpec>,
689 pub bind: BindingInd,
690 pub vunits: Vec<()>,
691}
692
693#[derive(Clone, Debug, PartialEq, Eq)]
694pub struct AttrDecl {
695 pub id: NodeId,
696 pub span: Span,
697 pub name: Spanned<Name>,
698 pub data: AttrData,
699}
700
701#[derive(Clone, Debug, PartialEq, Eq)]
702pub enum AttrData {
703 Decl(CompoundName),
704 Spec {
705 target: AttrTarget,
706 cls: EntityClass,
707 expr: Expr,
708 },
709}
710
711#[derive(Clone, Debug, PartialEq, Eq)]
712pub enum AttrTarget {
713 Others,
714 All,
715 List(Vec<(CompoundName, Option<Signature>)>),
716}
717
718#[derive(Copy, Clone, Debug, PartialEq, Eq)]
719pub enum EntityClass {
720 Arch,
721 Comp,
722 Cfg,
723 Const,
724 Entity,
725 File,
726 Func,
727 Group,
728 Label,
729 Literal,
730 Pkg,
731 Proc,
732 Prop,
733 Seq,
734 Signal,
735 Subtype,
736 Type,
737 Units,
738 Var,
739}
740
741#[derive(Clone, Debug, PartialEq, Eq)]
742pub struct GroupDecl {
743 pub id: NodeId,
744 pub span: Span,
745 pub name: Spanned<Name>,
746 pub data: GroupData,
747}
748
749#[derive(Clone, Debug, PartialEq, Eq)]
750pub enum GroupData {
751 Decl(CompoundName),
753 Temp(Vec<(EntityClass, bool)>),
756}
757
758#[derive(Clone, Debug, PartialEq, Eq)]
762pub struct ParenElem {
763 pub span: Span,
764 pub choices: Choices,
765 pub expr: Expr,
766}
767
768pub type ParenElems = Spanned<Vec<ParenElem>>;
771
772#[derive(Clone, Debug, PartialEq, Eq)]
774pub struct Expr {
775 pub span: Span,
776 pub data: ExprData,
777}
778
779impl HasSpan for Expr {
780 fn span(&self) -> Span {
781 self.span
782 }
783}
784
785impl HasDesc for Expr {
786 fn desc(&self) -> &'static str {
787 self.data.desc()
788 }
789}
790
791#[derive(Clone, Debug, PartialEq, Eq)]
793pub enum ExprData {
794 NullExpr,
795 OpenExpr,
796 OthersExpr,
797 DefaultExpr,
798 BoxExpr,
799 NewExpr(Box<Expr>),
800 LitExpr(Literal, Option<Spanned<Name>>),
801 ResolExpr(ParenElems, CompoundName),
802 ParenExpr(ParenElems),
803 DoubleNameExpr(CompoundName, CompoundName),
804 QualExpr(CompoundName, ParenElems),
805 NameExpr(CompoundName),
806 UnaryExpr(Spanned<UnaryOp>, Box<Expr>),
807 BinaryExpr(Spanned<BinaryOp>, Box<Expr>, Box<Expr>),
808}
809
810impl HasDesc for ExprData {
811 fn desc(&self) -> &'static str {
812 match *self {
813 NullExpr => "null expression",
814 UnaryExpr(..) => "unary expression",
815 BinaryExpr(..) => "binary expression",
816 _ => "expression",
817 }
818 }
819}
820
821#[derive(Copy, Clone, Debug, PartialEq, Eq)]
822pub enum UnaryOp {
823 Not,
824 Abs,
825 Sign(Sign),
826 Logical(LogicalOp),
827 Inertial,
828 Condition,
829}
830
831#[derive(Copy, Clone, Debug, PartialEq, Eq)]
832pub enum BinaryOp {
833 Dir(Dir),
834 Logical(LogicalOp),
835 Rel(RelationalOp),
836 Match(RelationalOp),
837 Shift(ShiftOp),
838 Add,
839 Sub,
840 Concat,
841 Mul,
842 Div,
843 Mod,
844 Rem,
845 Pow,
846}
847
848#[derive(Copy, Clone, Debug, PartialEq, Eq)]
849pub enum Dir {
850 To,
851 Downto,
852}
853
854impl std::fmt::Display for Dir {
855 fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
856 match *self {
857 Dir::To => write!(f, "to"),
858 Dir::Downto => write!(f, "downto"),
859 }
860 }
861}
862
863#[derive(Copy, Clone, Debug, PartialEq, Eq)]
864pub enum Sign {
865 Pos,
866 Neg,
867}
868
869#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
870pub enum LogicalOp {
871 And,
872 Or,
873 Nand,
874 Nor,
875 Xor,
876 Xnor,
877}
878
879impl fmt::Display for LogicalOp {
880 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
881 match *self {
882 LogicalOp::And => write!(f, "and"),
883 LogicalOp::Or => write!(f, "or"),
884 LogicalOp::Nand => write!(f, "nand"),
885 LogicalOp::Nor => write!(f, "nor"),
886 LogicalOp::Xor => write!(f, "xor"),
887 LogicalOp::Xnor => write!(f, "xnor"),
888 }
889 }
890}
891
892#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
893pub enum RelationalOp {
894 Eq,
895 Neq,
896 Lt,
897 Leq,
898 Gt,
899 Geq,
900}
901
902impl fmt::Display for RelationalOp {
903 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
904 match *self {
905 RelationalOp::Eq => write!(f, "="),
906 RelationalOp::Neq => write!(f, "/="),
907 RelationalOp::Lt => write!(f, "<"),
908 RelationalOp::Leq => write!(f, "<="),
909 RelationalOp::Gt => write!(f, ">"),
910 RelationalOp::Geq => write!(f, ">="),
911 }
912 }
913}
914
915#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
916pub enum ShiftOp {
917 Sll,
918 Srl,
919 Sla,
920 Sra,
921 Rol,
922 Ror,
923}
924
925impl fmt::Display for ShiftOp {
926 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
927 match *self {
928 ShiftOp::Sll => write!(f, "sll"),
929 ShiftOp::Srl => write!(f, "srl"),
930 ShiftOp::Sla => write!(f, "sla"),
931 ShiftOp::Sra => write!(f, "sra"),
932 ShiftOp::Rol => write!(f, "rol"),
933 ShiftOp::Ror => write!(f, "ror"),
934 }
935 }
936}
937
938#[derive(Clone, Debug, PartialEq, Eq)]
941pub struct TypeDecl {
942 pub id: NodeId,
943 pub span: Span,
944 pub name: Spanned<Name>,
945 pub data: Option<Spanned<TypeData>>,
946}
947
948impl HasSpan for TypeDecl {
949 fn span(&self) -> Span {
950 self.span
951 }
952
953 fn human_span(&self) -> Span {
954 self.name.span
955 }
956}
957
958impl HasDesc for TypeDecl {
959 fn desc(&self) -> &'static str {
960 match self.data {
961 Some(ref d) => d.desc(),
962 None => "incomplete type declaration",
963 }
964 }
965}
966
967#[derive(Clone, Debug, PartialEq, Eq)]
968pub enum TypeData {
969 EnumType(ParenElems),
970 RangeType(Box<Expr>, Option<Vec<(Ident, Option<Box<Expr>>)>>),
971 ArrayType(ParenElems, SubtypeInd),
972 RecordType(Vec<(Vec<Ident>, SubtypeInd)>),
973 AccessType(SubtypeInd),
974 FileType(CompoundName),
975 ProtectedType(Vec<DeclItem>),
976}
977
978impl HasDesc for TypeData {
979 fn desc(&self) -> &'static str {
980 match *self {
981 TypeData::EnumType(..) => "enumeration type declaration",
982 TypeData::RangeType(..) => "range type declaration",
983 TypeData::ArrayType(..) => "array type declaration",
984 TypeData::RecordType(..) => "record type declaration",
985 TypeData::AccessType(..) => "access type declaration",
986 TypeData::FileType(..) => "file type declaration",
987 TypeData::ProtectedType(..) => "protected type declaration",
988 }
989 }
990}
991
992#[derive(Clone, Debug, PartialEq, Eq)]
993pub struct Stmt {
994 pub id: NodeId,
995 pub span: Span,
996 pub label: Option<Spanned<Name>>,
997 pub data: StmtData,
998}
999
1000impl HasSpan for Stmt {
1001 fn span(&self) -> Span {
1002 self.span
1003 }
1004
1005 fn human_span(&self) -> Span {
1006 match self.label {
1007 Some(Spanned { span, .. }) => span,
1008 _ => self.span(),
1009 }
1010 }
1011}
1012
1013impl HasDesc for Stmt {
1014 fn desc(&self) -> &'static str {
1015 self.data.desc()
1016 }
1017}
1018
1019#[derive(Clone, Debug, PartialEq, Eq)]
1020pub enum StmtData {
1021 WaitStmt {
1022 on: Option<Spanned<Vec<CompoundName>>>,
1023 until: Option<Expr>,
1024 time: Option<Expr>,
1025 },
1026 AssertStmt {
1027 cond: Expr,
1028 report: Option<Expr>,
1029 severity: Option<Expr>,
1030 },
1031 ReportStmt {
1032 msg: Expr,
1033 severity: Option<Expr>,
1034 },
1035 IfStmt {
1036 conds: Vec<(Expr, StmtBody)>,
1037 alt: Option<StmtBody>,
1038 },
1039 CaseStmt {
1040 qm: bool,
1041 switch: Expr,
1042 cases: Vec<(Choices, StmtBody)>,
1043 },
1044 LoopStmt {
1045 scheme: LoopScheme,
1046 body: StmtBody,
1047 },
1048 NexitStmt {
1049 mode: NexitMode,
1050 target: Option<Spanned<Name>>,
1051 cond: Option<Expr>,
1052 },
1053 ReturnStmt(Option<Expr>),
1054 NullStmt,
1055 IfGenStmt {
1056 conds: Vec<(Expr, GenBody)>,
1057 alt: Option<GenBody>,
1058 },
1059 CaseGenStmt {
1060 switch: Expr,
1061 cases: Vec<(Choices, GenBody)>,
1062 },
1063 ForGenStmt {
1064 param: Spanned<Name>,
1065 range: Expr,
1066 body: GenBody,
1067 },
1068 BlockStmt {
1069 guard: Option<Expr>,
1070 decls: Vec<DeclItem>,
1071 stmts: Vec<Stmt>,
1072 },
1073 ProcStmt {
1074 sensitivity: Option<Sensitivity>,
1075 decls: Vec<DeclItem>,
1076 stmts: Vec<Stmt>,
1077 postponed: bool,
1078 },
1079 AssignStmt {
1080 target: Spanned<AssignTarget>,
1081 kind: AssignKind,
1082 guarded: bool,
1083 mode: Spanned<AssignMode>,
1084 },
1085 SelectAssignStmt {
1086 select: Expr,
1087 qm: bool,
1088 target: Spanned<AssignTarget>,
1089 kind: AssignKind,
1090 guarded: bool,
1091 mode: SelectAssignMode,
1092 waves: Vec<SelectWave>,
1093 },
1094 InstOrCallStmt {
1095 target: Option<InstTarget>,
1096 name: CompoundName,
1097 generics: Option<ParenElems>,
1098 ports: Option<ParenElems>,
1099 },
1100}
1101
1102impl HasDesc for StmtData {
1103 fn desc(&self) -> &'static str {
1104 match *self {
1105 StmtData::WaitStmt { .. } => "wait statement",
1106 StmtData::AssertStmt { .. } => "assertion statement",
1107 StmtData::ReportStmt { .. } => "report statement",
1108 StmtData::IfStmt { .. } => "if statement",
1109 StmtData::CaseStmt { .. } => "case statement",
1110 StmtData::LoopStmt { .. } => "loop statement",
1111 StmtData::NexitStmt {
1112 mode: NexitMode::Next,
1113 ..
1114 } => "next statement",
1115 StmtData::NexitStmt {
1116 mode: NexitMode::Exit,
1117 ..
1118 } => "exit statement",
1119 StmtData::ReturnStmt(..) => "return statement",
1120 StmtData::NullStmt => "null statement",
1121 StmtData::IfGenStmt { .. } => "if-generate statement",
1122 StmtData::CaseGenStmt { .. } => "case-generate statement",
1123 StmtData::ForGenStmt { .. } => "for-generate statement",
1124 StmtData::BlockStmt { .. } => "block statement",
1125 StmtData::ProcStmt { .. } => "process statement",
1126 StmtData::AssignStmt { .. } => "assign statement",
1127 StmtData::SelectAssignStmt { .. } => "assign statement",
1128 StmtData::InstOrCallStmt { .. } => "instantiation or call statement",
1129 }
1130 }
1131}
1132
1133#[derive(Clone, Debug, PartialEq, Eq)]
1135pub struct StmtBody {
1136 pub id: NodeId,
1137 pub stmts: Vec<Stmt>,
1138}
1139
1140#[derive(Clone, Debug, PartialEq, Eq)]
1141pub enum LoopScheme {
1142 While(Expr),
1143 For(Spanned<Name>, Expr),
1144 Loop,
1145}
1146
1147#[derive(Copy, Clone, Debug, PartialEq, Eq)]
1148pub enum NexitMode {
1149 Next,
1150 Exit,
1151}
1152
1153#[derive(Clone, Debug, PartialEq, Eq)]
1154pub struct GenBody {
1155 pub id: NodeId,
1156 pub label: Option<Spanned<Name>>,
1157 pub span: Span,
1158 pub decls: Vec<DeclItem>,
1159 pub stmts: Vec<Stmt>,
1160}
1161
1162#[derive(Clone, Debug, PartialEq, Eq)]
1163pub enum Sensitivity {
1164 All,
1165 List(Vec<CompoundName>),
1166}
1167
1168#[derive(Clone, Debug, PartialEq, Eq)]
1169pub enum AssignTarget {
1170 Name(CompoundName),
1171 Aggregate(ParenElems),
1172}
1173
1174#[derive(Copy, Clone, Debug, PartialEq, Eq)]
1175pub enum InstTarget {
1176 Comp,
1177 Entity,
1178 Cfg,
1179}
1180
1181#[derive(Copy, Clone, Debug, PartialEq, Eq)]
1182pub enum AssignKind {
1183 Signal,
1184 Var,
1185}
1186
1187#[derive(Clone, Debug, PartialEq, Eq)]
1188pub enum AssignMode {
1189 Release(Option<Spanned<ForceMode>>),
1190 Force(Option<Spanned<ForceMode>>, Vec<CondWave>),
1191 Normal(Option<Spanned<DelayMech>>, Vec<CondWave>),
1192}
1193
1194#[derive(Clone, Debug, PartialEq, Eq)]
1195pub enum SelectAssignMode {
1196 Force(Option<Spanned<ForceMode>>),
1197 Normal(Option<Spanned<DelayMech>>),
1198}
1199
1200#[derive(Copy, Clone, Debug, PartialEq, Eq)]
1201pub enum ForceMode {
1202 In,
1203 Out,
1204}
1205
1206#[derive(Clone, Debug, PartialEq, Eq)]
1207pub enum DelayMech {
1208 Transport,
1209 Inertial,
1210 InertialReject(Expr),
1211}
1212
1213#[derive(Clone, Debug, PartialEq, Eq)]
1214pub struct Wave {
1215 pub span: Span,
1216 pub elems: Option<Vec<(Expr, Option<Expr>)>>,
1217}
1218
1219#[derive(Clone, Debug, PartialEq, Eq)]
1221pub struct CondWave(pub Wave, pub Option<Expr>);
1222
1223#[derive(Clone, Debug, PartialEq, Eq)]
1226pub struct SelectWave(pub Wave, pub Choices);
1227
1228#[derive(Clone, Debug, PartialEq, Eq)]
1229pub struct Signature {
1230 pub span: Span,
1231 pub args: Vec<CompoundName>,
1232 pub retty: Option<CompoundName>,
1233}
1234
1235pub type Choices = Spanned<Vec<Expr>>;