1use super::*;
2use serde::{Deserialize, Serialize};
3
4#[derive(Debug, Serialize, Deserialize, Clone)]
5pub enum ConstrTypeDcl {
6 StructForwardDcl(StructForwardDcl),
7 StructDcl(StructDcl),
8 EnumDcl(EnumDcl),
9 UnionForwardDcl(UnionForwardDcl),
10 UnionDef(UnionDef),
11 BitsetDcl(BitsetDcl),
12 BitmaskDcl(BitmaskDcl),
13}
14
15#[derive(Debug, Serialize, Deserialize, Clone)]
16pub struct UnionForwardDcl {
17 pub annotations: Vec<Annotation>,
18 pub ident: String,
19}
20
21#[derive(Debug, Serialize, Deserialize, Clone)]
22pub struct UnionDef {
23 pub annotations: Vec<Annotation>,
24 pub ident: String,
25 pub switch_type_spec: SwitchTypeSpec,
26 pub case: Vec<Case>,
27}
28
29#[derive(Debug, Serialize, Deserialize, Clone)]
30pub struct Case {
31 pub label: Vec<CaseLabel>,
32 pub element: ElementSpec,
33}
34
35#[derive(Debug, Serialize, Deserialize, Clone)]
36pub enum CaseLabel {
37 Value(ConstExpr),
38 Default,
39}
40
41#[derive(Debug, Serialize, Deserialize, Clone)]
42pub struct ElementSpec {
43 pub annotations: Vec<Annotation>,
44 pub ty: ElementSpecTy,
45 pub value: Declarator,
46 pub field_id: Option<u32>,
47 pub recursive: bool,
48}
49
50#[derive(Debug, Serialize, Deserialize, Clone)]
51pub enum ElementSpecTy {
52 TypeSpec(TypeSpec),
53 ConstrTypeDcl(ConstrTypeDcl),
54}
55
56#[derive(Debug, Serialize, Deserialize, Clone)]
57pub enum SwitchTypeSpec {
58 IntegerType(IntegerType),
59 CharType,
60 WideCharType,
61 BooleanType,
62 ScopedName(ScopedName),
63 OctetType,
64}
65
66#[derive(Debug, Serialize, Deserialize, Clone)]
67pub struct BitsetDcl {
68 pub annotations: Vec<Annotation>,
69 pub ident: String,
70 pub parent: Option<ScopedName>,
71 pub field: Vec<BitField>,
72}
73
74#[derive(Clone, Debug, Serialize, Deserialize)]
75pub enum BitFieldType {
76 Bool,
77 Octec,
78 SignedInt,
79 UnsignedInt,
80}
81
82#[derive(Debug, Serialize, Deserialize, Clone)]
83pub struct BitField {
84 pub ident: String,
85 pub pos: PositiveIntConst,
86 pub ty: Option<BitFieldType>,
87}
88
89#[derive(Debug, Serialize, Deserialize, Clone)]
90pub struct BitmaskDcl {
91 pub annotations: Vec<Annotation>,
92 pub ident: String,
93 pub value: Vec<BitValue>,
94}
95
96#[derive(Debug, Serialize, Deserialize, Clone)]
97pub struct BitValue {
98 pub position: usize,
99 pub annotations: Vec<Annotation>,
100 pub ident: String,
101}
102
103impl From<crate::typed_ast::ConstrTypeDcl> for ConstrTypeDcl {
104 fn from(value: crate::typed_ast::ConstrTypeDcl) -> Self {
105 match value {
106 crate::typed_ast::ConstrTypeDcl::StructDcl(value) => value.into(),
107 crate::typed_ast::ConstrTypeDcl::UnionDcl(value) => value.into(),
108 crate::typed_ast::ConstrTypeDcl::EnumDcl(value) => Self::EnumDcl(value.into()),
109 crate::typed_ast::ConstrTypeDcl::BitsetDcl(value) => Self::BitsetDcl(value.into()),
110 crate::typed_ast::ConstrTypeDcl::BitmaskDcl(value) => Self::BitmaskDcl(value.into()),
111 }
112 }
113}
114
115impl From<crate::typed_ast::StructDcl> for ConstrTypeDcl {
116 fn from(value: crate::typed_ast::StructDcl) -> Self {
117 match value {
118 crate::typed_ast::StructDcl::StructForwardDcl(value) => {
119 Self::StructForwardDcl(value.into())
120 }
121 crate::typed_ast::StructDcl::StructDef(value) => Self::StructDcl(value.into()),
122 }
123 }
124}
125
126impl From<crate::typed_ast::UnionDcl> for ConstrTypeDcl {
127 fn from(value: crate::typed_ast::UnionDcl) -> Self {
128 match value {
129 crate::typed_ast::UnionDcl::UnionForwardDcl(value) => {
130 Self::UnionForwardDcl(value.into())
131 }
132 crate::typed_ast::UnionDcl::UnionDef(value) => Self::UnionDef(value.into()),
133 }
134 }
135}
136
137impl From<crate::typed_ast::UnionForwardDcl> for UnionForwardDcl {
138 fn from(value: crate::typed_ast::UnionForwardDcl) -> Self {
139 Self {
140 annotations: vec![],
141 ident: value.0.0,
142 }
143 }
144}
145
146impl From<crate::typed_ast::UnionDef> for UnionDef {
147 fn from(value: crate::typed_ast::UnionDef) -> Self {
148 let mut cases = value
149 .case
150 .into_iter()
151 .map(Case::from)
152 .collect::<Vec<Case>>();
153 let mut member_ids = std::collections::HashMap::new();
154 let mut next_field_id = 1u32;
155
156 for case in &mut cases {
157 let name = declarator_name(&case.element.value).to_string();
158 if let Some(id) = case.element.field_id {
159 let entry = member_ids.entry(name.clone()).or_insert(id);
160 case.element.field_id = Some(*entry);
161 } else if let Some(existing) = member_ids.get(&name) {
162 case.element.field_id = Some(*existing);
163 } else {
164 member_ids.insert(name, next_field_id);
165 case.element.field_id = Some(next_field_id);
166 next_field_id += 1;
167 }
168 }
169
170 Self {
171 annotations: vec![],
172 ident: value.ident.0,
173 switch_type_spec: value.switch_type_spec.into(),
174 case: cases,
175 }
176 }
177}
178
179impl From<crate::typed_ast::Case> for Case {
180 fn from(value: crate::typed_ast::Case) -> Self {
181 Self {
182 label: value.label.into_iter().map(Into::into).collect(),
183 element: value.element.into(),
184 }
185 }
186}
187
188impl From<crate::typed_ast::CaseLabel> for CaseLabel {
189 fn from(value: crate::typed_ast::CaseLabel) -> Self {
190 match value {
191 crate::typed_ast::CaseLabel::Case(value) => Self::Value(value.into()),
192 crate::typed_ast::CaseLabel::Default => Self::Default,
193 }
194 }
195}
196
197impl From<crate::typed_ast::ElementSpec> for ElementSpec {
198 fn from(value: crate::typed_ast::ElementSpec) -> Self {
199 let annotations = expand_annotations(value.annotations);
200 Self {
201 field_id: annotation_id_value(&annotations),
202 annotations,
203 ty: value.ty.into(),
204 value: value.value.into(),
205 recursive: false,
206 }
207 }
208}
209
210impl From<crate::typed_ast::ElementSpecTy> for ElementSpecTy {
211 fn from(value: crate::typed_ast::ElementSpecTy) -> Self {
212 match value {
213 crate::typed_ast::ElementSpecTy::TypeSpec(value) => Self::TypeSpec(value.into()),
214 crate::typed_ast::ElementSpecTy::ConstrTypeDcl(value) => {
215 Self::ConstrTypeDcl(value.into())
216 }
217 }
218 }
219}
220
221impl From<crate::typed_ast::SwitchTypeSpec> for SwitchTypeSpec {
222 fn from(value: crate::typed_ast::SwitchTypeSpec) -> Self {
223 match value {
224 crate::typed_ast::SwitchTypeSpec::IntegerType(value) => Self::IntegerType(value.into()),
225 crate::typed_ast::SwitchTypeSpec::CharType(_) => Self::CharType,
226 crate::typed_ast::SwitchTypeSpec::WideCharType(_) => Self::WideCharType,
227 crate::typed_ast::SwitchTypeSpec::BooleanType(_) => Self::BooleanType,
228 crate::typed_ast::SwitchTypeSpec::ScopedName(value) => Self::ScopedName(value.into()),
229 crate::typed_ast::SwitchTypeSpec::OctetType(_) => Self::OctetType,
230 }
231 }
232}
233
234impl From<crate::typed_ast::BitsetDcl> for BitsetDcl {
235 fn from(value: crate::typed_ast::BitsetDcl) -> Self {
236 let mut field = Vec::new();
237 for bitfield in value.field {
238 let pos = bitfield.spec.pos;
239 let ty = bitfield.spec.dst_ty.map(Into::into);
240 for ident in bitfield.ident {
241 field.push(BitField {
242 ident: ident.0,
243 pos: pos.clone().into(),
244 ty: ty.clone(),
245 });
246 }
247 }
248
249 Self {
250 annotations: vec![],
251 ident: value.ident.0,
252 parent: value.parent.map(Into::into),
253 field,
254 }
255 }
256}
257
258impl From<crate::typed_ast::DestinationType> for BitFieldType {
259 fn from(value: crate::typed_ast::DestinationType) -> Self {
260 match value {
261 crate::typed_ast::DestinationType::BooleanType(_) => Self::Bool,
262 crate::typed_ast::DestinationType::OctetType(_) => Self::Octec,
263 crate::typed_ast::DestinationType::IntegerType(value) => {
264 if matches!(value, crate::typed_ast::IntegerType::SignedInt(_)) {
265 Self::SignedInt
266 } else {
267 Self::UnsignedInt
268 }
269 }
270 }
271 }
272}
273
274impl From<crate::typed_ast::BitmaskDcl> for BitmaskDcl {
275 fn from(value: crate::typed_ast::BitmaskDcl) -> Self {
276 let mut bits = vec![];
277 for (idx, bitvalue) in value.value.into_iter().enumerate() {
278 let mut position = idx;
279 for annotation in &bitvalue.annotations {
280 let crate::typed_ast::AnnotationName::Builtin(name) = &annotation.name else {
281 continue;
282 };
283 if !name.eq_ignore_ascii_case("position") {
284 continue;
285 }
286
287 let Some(crate::typed_ast::AnnotationParams::Raw(v)) = &annotation.params else {
288 continue;
289 };
290
291 if let Ok(v) = v.parse::<usize>() {
292 position = v;
293 }
294 }
295 let mut bit: BitValue = bitvalue.into();
296 bit.position = position;
297 bits.push(bit);
298 }
299 Self {
300 annotations: vec![],
301 ident: value.ident.0,
302 value: bits,
303 }
304 }
305}
306
307impl From<crate::typed_ast::BitValue> for BitValue {
308 fn from(value: crate::typed_ast::BitValue) -> Self {
309 Self {
310 position: 0,
311 annotations: expand_annotations(value.annotations),
312 ident: value.ident.0,
313 }
314 }
315}
316
317fn declarator_name(value: &Declarator) -> &str {
318 match value {
319 Declarator::SimpleDeclarator(value) => &value.0,
320 Declarator::ArrayDeclarator(value) => &value.ident,
321 }
322}