Skip to main content

xidl_parser/typed_ast/
mod.rs

1mod base_types;
2pub use base_types::*;
3use serde::{Deserialize, Serialize};
4
5mod expr;
6pub use expr::*;
7use xidl_parser_derive::Parser;
8
9mod annotation;
10pub use annotation::*;
11
12mod annotation_builtin;
13pub use annotation_builtin::*;
14
15mod preproc;
16pub use preproc::*;
17
18mod bitmask;
19pub use bitmask::*;
20
21mod interface;
22pub use interface::*;
23
24mod union;
25pub use union::*;
26
27mod typedef_dcl_imp;
28pub use typedef_dcl_imp::*;
29
30mod module_dcl;
31pub use module_dcl::*;
32
33mod exception_dcl;
34pub use exception_dcl::*;
35
36mod template_module;
37pub use template_module::*;
38
39#[derive(Debug, Parser, Serialize, Deserialize)]
40pub struct Specification(pub Vec<Definition>);
41
42#[derive(Debug, Parser, Serialize, Deserialize)]
43pub enum Definition {
44    ModuleDcl(ModuleDcl),
45    TypeDcl(TypeDcl),
46    ConstDcl(ConstDcl),
47    ExceptDcl(ExceptDcl),
48    InterfaceDcl(InterfaceDcl),
49    TemplateModuleDcl(TemplateModuleDcl),
50    TemplateModuleInst(TemplateModuleInst),
51    PreprocInclude(PreprocInclude),
52    PreprocCall(PreprocCall),
53    PreprocDefine(PreprocDefine),
54}
55
56#[derive(Debug, Serialize, Deserialize)]
57pub struct TypeDcl {
58    pub annotations: Vec<AnnotationAppl>,
59    pub decl: TypeDclInner,
60}
61
62#[derive(Debug, Parser, Serialize, Deserialize)]
63#[ts(transparent)]
64#[allow(clippy::large_enum_variant)]
65pub enum TypeDclInner {
66    ConstrTypeDcl(ConstrTypeDcl),
67    NativeDcl(NativeDcl),
68    TypedefDcl(TypedefDcl),
69}
70
71impl<'a> crate::parser::FromTreeSitter<'a> for TypeDcl {
72    fn from_node(
73        node: tree_sitter::Node<'a>,
74        ctx: &mut crate::parser::ParseContext<'a>,
75    ) -> crate::error::ParserResult<Self> {
76        assert_eq!(node.kind_id(), xidl_parser_derive::node_id!("type_dcl"));
77        let mut annotations = Vec::new();
78        let mut decl = None;
79        for ch in node.children(&mut node.walk()) {
80            match ch.kind_id() {
81                xidl_parser_derive::node_id!("annotation_appl")
82                | xidl_parser_derive::node_id!("extend_annotation_appl") => {
83                    annotations.push(AnnotationAppl::from_node(ch, ctx)?);
84                }
85                xidl_parser_derive::node_id!("constr_type_dcl")
86                | xidl_parser_derive::node_id!("native_dcl")
87                | xidl_parser_derive::node_id!("typedef_dcl") => {
88                    decl = Some(TypeDclInner::from_node(ch, ctx)?);
89                }
90                _ => {}
91            }
92        }
93        if let Some(doc) = ctx.take_doc_comment(&node) {
94            annotations.insert(0, AnnotationAppl::doc(doc));
95        }
96        Ok(Self {
97            annotations,
98            decl: decl.ok_or_else(|| {
99                crate::error::ParseError::UnexpectedNode(format!(
100                    "parent: {}, got: missing type decl",
101                    node.kind()
102                ))
103            })?,
104        })
105    }
106}
107
108#[derive(Debug, Parser, Serialize, Deserialize)]
109pub struct NativeDcl {
110    pub decl: SimpleDeclarator,
111}
112
113#[derive(Debug, Parser, Serialize, Deserialize)]
114pub enum ConstrTypeDcl {
115    StructDcl(StructDcl),
116    UnionDcl(UnionDcl),
117    EnumDcl(EnumDcl),
118    BitsetDcl(BitsetDcl),
119    BitmaskDcl(BitmaskDcl),
120}
121
122#[derive(Debug, Parser, Serialize, Deserialize)]
123pub enum StructDcl {
124    StructForwardDcl(StructForwardDcl),
125    StructDef(StructDef),
126}
127
128#[derive(Debug, Parser, Serialize, Deserialize)]
129pub struct StructForwardDcl {
130    pub ident: Identifier,
131}
132
133#[derive(Debug, Parser, Serialize, Deserialize)]
134pub struct StructDef {
135    pub ident: Identifier,
136    pub parent: Vec<ScopedName>,
137    pub member: Vec<Member>,
138}
139
140#[derive(Debug, Serialize, Deserialize)]
141pub struct Member {
142    pub annotations: Vec<AnnotationAppl>,
143    pub ty: TypeSpec,
144    pub ident: Declarators,
145    pub default: Option<Default>,
146}
147
148impl<'a> crate::parser::FromTreeSitter<'a> for Member {
149    fn from_node(
150        node: tree_sitter::Node<'a>,
151        ctx: &mut crate::parser::ParseContext<'a>,
152    ) -> crate::error::ParserResult<Self> {
153        assert_eq!(node.kind_id(), xidl_parser_derive::node_id!("member"));
154        let mut annotations = Vec::new();
155        let mut ty = None;
156        let mut ident = None;
157        let mut default = None;
158        for ch in node.children(&mut node.walk()) {
159            match ch.kind_id() {
160                xidl_parser_derive::node_id!("annotation_appl")
161                | xidl_parser_derive::node_id!("extend_annotation_appl") => {
162                    annotations.push(AnnotationAppl::from_node(ch, ctx)?);
163                }
164                xidl_parser_derive::node_id!("type_spec") => {
165                    ty = Some(TypeSpec::from_node(ch, ctx)?);
166                }
167                xidl_parser_derive::node_id!("declarators") => {
168                    ident = Some(Declarators::from_node(ch, ctx)?);
169                }
170                xidl_parser_derive::node_id!("default") => {
171                    default = Some(Default::from_node(ch, ctx)?);
172                }
173                _ => {}
174            }
175        }
176        if let Some(doc) = ctx.take_doc_comment(&node) {
177            annotations.insert(0, AnnotationAppl::doc(doc));
178        }
179        Ok(Self {
180            annotations,
181            ty: ty.ok_or_else(|| {
182                crate::error::ParseError::UnexpectedNode(format!(
183                    "parent: {}, got: missing type",
184                    node.kind()
185                ))
186            })?,
187            ident: ident.ok_or_else(|| {
188                crate::error::ParseError::UnexpectedNode(format!(
189                    "parent: {}, got: missing declarators",
190                    node.kind()
191                ))
192            })?,
193            default,
194        })
195    }
196}
197
198#[derive(Debug, Parser, Serialize, Deserialize)]
199pub struct Default(pub ConstExpr);
200
201#[derive(Debug, Serialize, Deserialize)]
202pub struct ConstDcl {
203    pub annotations: Vec<AnnotationAppl>,
204    pub ty: ConstType,
205    pub ident: Identifier,
206    pub value: ConstExpr,
207}
208
209impl<'a> crate::parser::FromTreeSitter<'a> for ConstDcl {
210    fn from_node(
211        node: tree_sitter::Node<'a>,
212        ctx: &mut crate::parser::ParseContext<'a>,
213    ) -> crate::error::ParserResult<Self> {
214        assert_eq!(node.kind_id(), xidl_parser_derive::node_id!("const_dcl"));
215        let mut annotations = Vec::new();
216        let mut ty = None;
217        let mut ident = None;
218        let mut value = None;
219        for ch in node.children(&mut node.walk()) {
220            match ch.kind_id() {
221                xidl_parser_derive::node_id!("annotation_appl")
222                | xidl_parser_derive::node_id!("extend_annotation_appl") => {
223                    annotations.push(AnnotationAppl::from_node(ch, ctx)?);
224                }
225                xidl_parser_derive::node_id!("const_type") => {
226                    ty = Some(ConstType::from_node(ch, ctx)?);
227                }
228                xidl_parser_derive::node_id!("identifier") => {
229                    ident = Some(Identifier::from_node(ch, ctx)?);
230                }
231                xidl_parser_derive::node_id!("const_expr") => {
232                    value = Some(ConstExpr::from_node(ch, ctx)?);
233                }
234                _ => {}
235            }
236        }
237        if let Some(doc) = ctx.take_doc_comment(&node) {
238            annotations.insert(0, AnnotationAppl::doc(doc));
239        }
240        Ok(Self {
241            annotations,
242            ty: ty.ok_or_else(|| {
243                crate::error::ParseError::UnexpectedNode(format!(
244                    "parent: {}, got: missing const type",
245                    node.kind()
246                ))
247            })?,
248            ident: ident.ok_or_else(|| {
249                crate::error::ParseError::UnexpectedNode(format!(
250                    "parent: {}, got: missing identifier",
251                    node.kind()
252                ))
253            })?,
254            value: value.ok_or_else(|| {
255                crate::error::ParseError::UnexpectedNode(format!(
256                    "parent: {}, got: missing const value",
257                    node.kind()
258                ))
259            })?,
260        })
261    }
262}
263
264#[derive(Debug, Parser, Serialize, Deserialize)]
265pub enum ConstType {
266    IntegerType(IntegerType),
267    FloatingPtType(FloatingPtType),
268    FixedPtConstType(FixedPtConstType),
269    CharType(CharType),
270    WideCharType(WideCharType),
271    BooleanType(BooleanType),
272    OctetType(OctetType),
273    StringType(StringType),
274    WideStringType(WideStringType),
275    ScopedName(ScopedName),
276    SequenceType(SequenceType),
277}
278
279#[derive(Debug, Clone, PartialEq, Parser, Serialize, Deserialize)]
280#[ts(transparent)]
281pub struct Identifier(pub String);
282
283#[derive(Debug, Clone, Parser, Serialize, Deserialize)]
284pub struct PositiveIntConst(pub ConstExpr);