1use std::{fmt::Display, rc::Rc};
2
3use convert_case::Boundary;
4#[cfg(test)]
5use device_driver_common::identifier::IdentifierType;
6use device_driver_common::{
7 identifier::{All, Identifier, IdentifierRef, Operation, RuntimeType, Type},
8 span::{Span, SpanExt, Spanned},
9 specifiers::{
10 Access, AddressMode, AddressRange, BaseType, ByteOrder, Integer, NodeType, Repeat,
11 ResetValue, TypeConversion,
12 },
13};
14
15#[derive(Debug, Clone, Default, PartialEq)]
16pub struct Manifest {
17 pub description: String,
18 pub name: Spanned<Identifier<All>>,
19 pub default_access: Option<Access>,
20 pub config: DeviceConfig,
21 pub objects: Vec<Object>,
22
23 pub short_properties_span: Span,
24 pub properties_span: Option<Span>,
25 pub span: Span,
26}
27
28impl Manifest {
29 pub fn iter_objects_with_config_mut(&mut self) -> ObjectIterMut<'_> {
30 ObjectIterMut {
31 children: &mut self.objects,
32 parent: None,
33 collection_object_returned: false,
34 current_device_config: Rc::new(self.config.clone()),
35 }
36 }
37
38 pub fn iter_objects(&self) -> impl Iterator<Item = &Object> {
39 ObjectIter {
40 children: &self.objects,
41 parent: None,
42 collection_object_returned: false,
43 current_device_config: Rc::new(self.config.clone()),
44 }
45 .map(|(object, _)| object)
46 }
47
48 #[must_use]
49 pub fn iter_objects_with_config(&self) -> ObjectIter<'_> {
50 ObjectIter {
51 children: &self.objects,
52 parent: None,
53 collection_object_returned: false,
54 current_device_config: Rc::new(self.config.clone()),
55 }
56 }
57
58 pub fn iter_enums(&self) -> impl Iterator<Item = &'_ Enum> {
59 self.iter_objects_with_config().filter_map(|(o, _)| {
60 if let Object::Enum(e) = o {
61 Some(e)
62 } else {
63 None
64 }
65 })
66 }
67
68 pub fn iter_enums_with_config(&self) -> impl Iterator<Item = (&'_ Enum, Rc<DeviceConfig>)> {
69 self.iter_objects_with_config().filter_map(|(o, config)| {
70 if let Object::Enum(e) = o {
71 Some((e, config))
72 } else {
73 None
74 }
75 })
76 }
77
78 pub fn iter_devices_with_config(&self) -> impl Iterator<Item = (&'_ Device, Rc<DeviceConfig>)> {
79 self.iter_objects_with_config().filter_map(|(o, config)| {
80 if let Object::Device(d) = o {
81 Some((d, config))
82 } else {
83 None
84 }
85 })
86 }
87}
88
89#[derive(Default)]
90pub struct ObjectIterMut<'a> {
91 children: &'a mut [Object],
92 parent: Option<Box<ObjectIterMut<'a>>>,
93 collection_object_returned: bool,
94 current_device_config: Rc<DeviceConfig>,
95}
96
97pub trait LendingIterator {
100 type Item<'a>
101 where
102 Self: 'a;
103
104 fn next(&mut self) -> Option<Self::Item<'_>>;
105}
106
107impl LendingIterator for ObjectIterMut<'_> {
108 type Item<'b>
109 = (&'b mut Object, Rc<DeviceConfig>)
110 where
111 Self: 'b;
112
113 fn next(&mut self) -> Option<Self::Item<'_>> {
114 if self.children.is_empty() {
115 match self.parent.take() {
116 Some(parent) => {
117 *self = *parent;
119 self.next()
120 }
121 None => None,
122 }
123 } else if self.children[0].child_objects_mut().is_empty() {
124 let (first, rest) = std::mem::take(&mut self.children)
125 .split_first_mut()
126 .expect("Already checked not empty");
127 self.children = rest;
128 Some((first, self.current_device_config.clone()))
129 } else if !self.collection_object_returned {
130 self.collection_object_returned = true;
131
132 let next_device_config = if let Some(new_config) = self.children[0].device_config() {
133 Rc::new(self.current_device_config.override_with(new_config))
134 } else {
135 self.current_device_config.clone()
136 };
137
138 Some((&mut self.children[0], next_device_config))
139 } else {
140 self.collection_object_returned = false;
141
142 let next_device_config = if let Some(new_config) = self.children[0].device_config() {
143 Rc::new(self.current_device_config.override_with(new_config))
144 } else {
145 self.current_device_config.clone()
146 };
147
148 let (first, rest) = std::mem::take(&mut self.children)
149 .split_first_mut()
150 .expect("Already checked not empty");
151 self.children = rest;
152
153 *self = ObjectIterMut {
154 children: first.child_objects_mut(),
155 parent: Some(Box::new(std::mem::take(self))),
156 collection_object_returned: false,
157 current_device_config: next_device_config,
158 };
159 self.next()
160 }
161 }
162}
163
164#[derive(Default)]
165pub struct ObjectIter<'a> {
166 children: &'a [Object],
167 parent: Option<Box<ObjectIter<'a>>>,
168 collection_object_returned: bool,
169 current_device_config: Rc<DeviceConfig>,
170}
171
172impl<'a> Iterator for ObjectIter<'a> {
173 type Item = (&'a Object, Rc<DeviceConfig>);
174
175 fn next(&mut self) -> Option<Self::Item> {
176 let children = std::mem::take(&mut self.children);
177
178 match children.split_first() {
179 None => match self.parent.take() {
180 Some(parent) => {
181 *self = *parent;
183 self.next()
184 }
185 None => None,
186 },
187 Some((first, rest)) => {
188 self.children = rest;
189
190 if first.child_objects().is_empty() {
191 Some((first, self.current_device_config.clone()))
192 } else if !self.collection_object_returned {
193 self.collection_object_returned = true;
194
195 let next_device_config = if let Some(new_config) = first.device_config() {
196 Rc::new(self.current_device_config.override_with(new_config))
197 } else {
198 self.current_device_config.clone()
199 };
200
201 self.children = children;
202
203 Some((&children[0], next_device_config))
204 } else {
205 self.collection_object_returned = false;
206
207 let next_device_config = if let Some(new_config) = first.device_config() {
208 Rc::new(self.current_device_config.override_with(new_config))
209 } else {
210 self.current_device_config.clone()
211 };
212
213 *self = ObjectIter {
214 children: first.child_objects(),
215 parent: Some(Box::new(std::mem::take(self))),
216 collection_object_returned: false,
217 current_device_config: next_device_config,
218 };
219 self.next()
220 }
221 }
222 }
223 }
224}
225
226impl From<Device> for Manifest {
228 fn from(value: Device) -> Self {
229 let default_access = value.default_access;
230
231 Self {
232 description: String::new(),
233 name: value
234 .name
235 .value
236 .clone()
237 .cast_unchecked()
238 .with_span(value.name.span),
239 short_properties_span: value.short_properties_span,
240 properties_span: value.properties_span,
241 span: value.span,
242 objects: vec![Object::Device(value)],
243 default_access,
244 config: DeviceConfig::default(),
245 }
246 }
247}
248
249#[derive(Debug, Clone, Default, PartialEq)]
250pub struct Device {
251 pub description: String,
252 pub name: Spanned<Identifier<Type>>,
253 pub default_access: Option<Access>,
254 pub address_offset: Spanned<i128>,
255 pub device_config: DeviceConfig,
256 pub objects: Vec<Object>,
257
258 pub short_properties_span: Span,
259 pub properties_span: Option<Span>,
260 pub span: Span,
262}
263
264impl Device {
265 pub fn iter_objects(&self) -> impl Iterator<Item = &Object> {
266 ObjectIter {
267 children: &self.objects,
268 parent: None,
269 collection_object_returned: false,
270 current_device_config: Rc::new(DeviceConfig::default()),
272 }
273 .map(|(object, _)| object)
274 }
275}
276
277#[derive(Debug, Clone, Default, PartialEq)]
278pub struct DeviceConfig {
279 pub owner: Option<UniqueId>,
281 pub byte_order: Option<ByteOrder>,
282 pub register_address_type: Option<Spanned<Integer>>,
283 pub command_address_type: Option<Spanned<Integer>>,
284 pub buffer_address_type: Option<Spanned<Integer>>,
285 pub name_word_boundaries: Option<Vec<Boundary>>,
286 pub register_address_mode: Option<Spanned<AddressMode>>,
287}
288
289impl DeviceConfig {
290 #[must_use]
291 pub fn override_with(&self, other: &Self) -> DeviceConfig {
292 Self {
293 owner: other.owner.clone().or(self.owner.clone()),
294 byte_order: other.byte_order.or(self.byte_order),
295 register_address_type: other.register_address_type.or(self.register_address_type),
296 command_address_type: other.command_address_type.or(self.command_address_type),
297 buffer_address_type: other.buffer_address_type.or(self.buffer_address_type),
298 name_word_boundaries: other
299 .name_word_boundaries
300 .as_ref()
301 .or(self.name_word_boundaries.as_ref())
302 .cloned(),
303 register_address_mode: other.register_address_mode.or(self.register_address_mode),
304 }
305 }
306}
307
308#[derive(Debug, Clone, PartialEq)]
309pub enum Object {
310 Device(Device),
311 Block(Block),
312 Register(Register),
313 Command(Command),
314 Buffer(Buffer),
315 FieldSet(FieldSet),
316 Enum(Enum),
317 Extern(Extern),
318 Field(Field),
319}
320
321impl Object {
322 pub fn device_config(&self) -> Option<&DeviceConfig> {
323 match self {
324 Object::Device(device) => Some(&device.device_config),
325 _ => None,
326 }
327 }
328
329 pub fn child_objects_mut(&mut self) -> &mut [Object] {
330 match self {
331 Object::Device(device) => &mut device.objects,
332 Object::Block(block) => &mut block.objects,
333 _ => &mut [],
334 }
335 }
336
337 pub fn child_objects_vec(&mut self) -> Option<&mut Vec<Object>> {
338 match self {
339 Object::Device(device) => Some(&mut device.objects),
340 Object::Block(block) => Some(&mut block.objects),
341 _ => None,
342 }
343 }
344
345 pub fn child_objects(&self) -> &[Object] {
346 match self {
347 Object::Device(device) => &device.objects,
348 Object::Block(block) => &block.objects,
349 _ => &[],
350 }
351 }
352
353 pub fn name_mut(&mut self) -> &mut Identifier<RuntimeType> {
355 match self {
356 Object::Device(val) => val.name.as_runtime_type_mut(),
357 Object::Block(val) => val.name.as_runtime_type_mut(),
358 Object::Register(val) => val.name.as_runtime_type_mut(),
359 Object::Command(val) => val.name.as_runtime_type_mut(),
360 Object::Buffer(val) => val.name.as_runtime_type_mut(),
361 Object::FieldSet(val) => val.name.as_runtime_type_mut(),
362 Object::Enum(val) => val.name.as_runtime_type_mut(),
363 Object::Extern(val) => val.name.as_runtime_type_mut(),
364 Object::Field(val) => val.name.as_runtime_type_mut(),
365 }
366 }
367
368 pub fn name(&self) -> &Identifier<RuntimeType> {
370 match self {
371 Object::Device(val) => val.name.as_runtime_type(),
372 Object::Block(val) => val.name.as_runtime_type(),
373 Object::Register(val) => val.name.as_runtime_type(),
374 Object::Command(val) => val.name.as_runtime_type(),
375 Object::Buffer(val) => val.name.as_runtime_type(),
376 Object::FieldSet(val) => val.name.as_runtime_type(),
377 Object::Enum(val) => val.name.as_runtime_type(),
378 Object::Extern(val) => val.name.as_runtime_type(),
379 Object::Field(val) => val.name.as_runtime_type(),
380 }
381 }
382
383 pub fn name_span(&self) -> Span {
385 match self {
386 Object::Device(val) => val.name.span,
387 Object::Block(val) => val.name.span,
388 Object::Register(val) => val.name.span,
389 Object::Command(val) => val.name.span,
390 Object::Buffer(val) => val.name.span,
391 Object::FieldSet(val) => val.name.span,
392 Object::Enum(val) => val.name.span,
393 Object::Extern(val) => val.name.span,
394 Object::Field(val) => val.name.span,
395 }
396 }
397
398 pub fn address(&self) -> Option<Spanned<i128>> {
400 match self {
401 Object::Device(device) => Some(device.address_offset),
402 Object::Block(block) => Some(block.address_offset),
403 Object::Register(register) => Some(register.address),
404 Object::Command(command) => Some(command.address),
405 Object::Buffer(buffer) => Some(buffer.address),
406 Object::FieldSet(_) => None,
407 Object::Enum(_) => None,
408 Object::Extern(_) => None,
409 Object::Field(_) => None,
410 }
411 }
412
413 pub fn repeat(&self) -> Option<&Repeat> {
415 match self {
416 Object::Device(_) => None,
417 Object::Block(block) => block.repeat.as_ref(),
418 Object::Register(register) => register.repeat.as_ref(),
419 Object::Command(command) => command.repeat.as_ref(),
420 Object::Buffer(_) => None,
421 Object::FieldSet(_) => None,
422 Object::Enum(_) => None,
423 Object::Extern(_) => None,
424 Object::Field(field) => field.repeat.as_ref(),
425 }
426 }
427
428 pub fn repeat_mut(&mut self) -> Option<&mut Repeat> {
430 match self {
431 Object::Device(_) => None,
432 Object::Block(block) => block.repeat.as_mut(),
433 Object::Register(register) => register.repeat.as_mut(),
434 Object::Command(command) => command.repeat.as_mut(),
435 Object::Buffer(_) => None,
436 Object::FieldSet(_) => None,
437 Object::Enum(_) => None,
438 Object::Extern(_) => None,
439 Object::Field(field) => field.repeat.as_mut(),
440 }
441 }
442
443 pub fn as_field_set(&self) -> Option<&FieldSet> {
444 if let Self::FieldSet(v) = self {
445 Some(v)
446 } else {
447 None
448 }
449 }
450
451 pub fn as_field_set_mut(&mut self) -> Option<&mut FieldSet> {
452 if let Self::FieldSet(v) = self {
453 Some(v)
454 } else {
455 None
456 }
457 }
458
459 pub fn as_enum(&self) -> Option<&Enum> {
460 if let Self::Enum(v) = self {
461 Some(v)
462 } else {
463 None
464 }
465 }
466
467 pub fn allow_address_overlap(&self) -> bool {
468 match self {
469 Object::Device(_) => false,
470 Object::Block(_) => false,
471 Object::Register(register) => register.allow_address_overlap,
472 Object::Command(command) => command.allow_address_overlap,
473 Object::Buffer(_) => false,
474 Object::FieldSet(_) => false,
475 Object::Enum(_) => false,
476 Object::Extern(_) => false,
477 Object::Field(_) => false,
478 }
479 }
480
481 pub fn span(&self) -> Span {
483 match self {
484 Object::Device(val) => val.span,
485 Object::Block(val) => val.span,
486 Object::Register(val) => val.span,
487 Object::Command(val) => val.span,
488 Object::Buffer(val) => val.span,
489 Object::FieldSet(val) => val.span,
490 Object::Enum(val) => val.span,
491 Object::Extern(val) => val.span,
492 Object::Field(val) => val.span,
493 }
494 }
495
496 pub fn node_type(&self) -> NodeType {
497 match self {
498 Object::Device(_) => NodeType::Device,
499 Object::Block(_) => NodeType::Block,
500 Object::Register(_) => NodeType::Register,
501 Object::Command(_) => NodeType::Command,
502 Object::Buffer(_) => NodeType::Buffer,
503 Object::FieldSet(_) => NodeType::FieldSet,
504 Object::Enum(_) => NodeType::Enum,
505 Object::Extern(_) => NodeType::Extern,
506 Object::Field(_) => NodeType::Field,
507 }
508 }
509
510 pub fn fieldset_refs(&self) -> Vec<Spanned<IdentifierRef<Type>>> {
512 match self {
513 Object::Device(_) => Vec::new(),
514 Object::Block(_) => Vec::new(),
515 Object::Register(r) => vec![r.field_set_ref.clone()],
516 Object::Command(c) => [c.field_set_ref_in.clone(), c.field_set_ref_out.clone()]
517 .into_iter()
518 .flatten()
519 .collect(),
520 Object::Buffer(_) => Vec::new(),
521 Object::FieldSet(_) => Vec::new(),
522 Object::Enum(_) => Vec::new(),
523 Object::Extern(_) => Vec::new(),
524 Object::Field(_) => Vec::new(),
525 }
526 }
527
528 pub fn properties_span(&self) -> Option<Span> {
529 match self {
530 Object::Device(val) => val.properties_span,
531 Object::Block(val) => val.properties_span,
532 Object::Register(val) => val.properties_span,
533 Object::Command(val) => val.properties_span,
534 Object::Buffer(val) => val.properties_span,
535 Object::FieldSet(val) => val.properties_span,
536 Object::Enum(val) => val.properties_span,
537 Object::Extern(val) => val.properties_span,
538 Object::Field(val) => val.properties_span,
539 }
540 }
541}
542
543#[derive(Debug, Clone, Default, PartialEq)]
544pub struct Block {
545 pub description: String,
546 pub name: Spanned<Identifier<All>>,
547 pub address_offset: Spanned<i128>,
548 pub repeat: Option<Repeat>,
549 pub objects: Vec<Object>,
550 pub default_access: Option<Access>,
551
552 pub short_properties_span: Span,
553 pub properties_span: Option<Span>,
554 pub span: Span,
556}
557
558impl Block {
559 pub fn iter_objects(&self) -> impl Iterator<Item = &Object> {
560 ObjectIter {
561 children: &self.objects,
562 parent: None,
563 collection_object_returned: false,
564 current_device_config: Rc::new(DeviceConfig::default()),
566 }
567 .map(|(object, _)| object)
568 }
569}
570
571#[derive(Debug, Clone, Default, PartialEq)]
572pub struct Register {
573 pub description: String,
574 pub name: Spanned<Identifier<Operation>>,
575 pub access: Option<Access>,
576 pub allow_address_overlap: bool,
577 pub address: Spanned<i128>,
578 pub reset_value: Option<Spanned<ResetValue>>,
579 pub repeat: Option<Repeat>,
580 pub field_set_ref: Spanned<IdentifierRef<Type>>,
581
582 pub short_properties_span: Span,
583 pub properties_span: Option<Span>,
584 pub span: Span,
586}
587
588#[derive(Debug, Clone, Default, PartialEq)]
589pub struct FieldSet {
590 pub description: String,
591 pub name: Spanned<Identifier<Type>>,
592 pub size_bytes: Spanned<u32>,
593 pub byte_order: Option<ByteOrder>,
594 pub allow_bit_overlap: bool,
595 pub default_access: Option<Access>,
596 pub fields: Vec<Field>,
597
598 pub short_properties_span: Span,
599 pub properties_span: Option<Span>,
600 pub span: Span,
602}
603
604impl FieldSet {
605 pub fn size_bits(&self) -> u32 {
606 self.size_bytes.value * 8
607 }
608}
609
610#[derive(Debug, Clone, Default, PartialEq)]
611pub struct Field {
612 pub description: String,
613 pub name: Spanned<Identifier<All>>,
614 pub access: Option<Access>,
615 pub base_type: Spanned<BaseType>,
616 pub field_conversion: Option<TypeConversion>,
617 pub field_address: Spanned<AddressRange>,
618 pub repeat: Option<Repeat>,
619
620 pub short_properties_span: Span,
621 pub properties_span: Option<Span>,
622 pub span: Span,
624}
625
626impl Field {
627 #[must_use]
628 pub fn get_type_specifier_string(&self) -> String {
629 match &self.field_conversion {
630 Some(fc) => {
631 format!(
632 "{}:{}{}",
633 self.base_type,
634 fc.type_name.original(),
635 if fc.fallible { "?" } else { "" }
636 )
637 }
638 None => self.base_type.to_string(),
639 }
640 }
641}
642
643#[derive(Debug, Clone, Default, PartialEq)]
644pub struct Enum {
645 pub description: String,
646 pub name: Spanned<Identifier<Type>>,
647 pub variants: Vec<EnumVariant>,
648 pub base_type: Spanned<BaseType>,
649 pub size_bits: Option<u32>,
650 pub generation_style: Option<EnumGenerationStyle>,
651
652 pub short_properties_span: Span,
653 pub properties_span: Option<Span>,
654 pub span: Span,
656}
657
658impl Enum {
659 #[cfg(test)]
660 pub fn new(
661 description: String,
662 name: Spanned<Identifier<Type>>,
663 variants: Vec<EnumVariant>,
664 base_type: Spanned<BaseType>,
665 size_bits: Option<u32>,
666 span: Span,
667 ) -> Self {
668 Self {
669 description,
670 name,
671 variants,
672 base_type,
673 size_bits,
674 generation_style: None,
675 short_properties_span: Span::empty(),
676 properties_span: None,
677 span,
678 }
679 }
680
681 #[cfg(test)]
682 pub fn new_with_style(
683 description: String,
684 name: Spanned<Identifier<Type>>,
685 variants: Vec<EnumVariant>,
686 base_type: Spanned<BaseType>,
687 size_bits: Option<u32>,
688 generation_style: EnumGenerationStyle,
689 span: Span,
690 ) -> Self {
691 Self {
692 description,
693 name,
694 variants,
695 base_type,
696 size_bits,
697 generation_style: Some(generation_style),
698 short_properties_span: Span::empty(),
699 properties_span: None,
700 span,
701 }
702 }
703
704 pub fn iter_variants_with_discriminant(&self) -> impl Iterator<Item = (i128, &EnumVariant)> {
709 let mut next_discriminant = 0;
710 self.variants.iter().map(move |variant| {
711 if let Some(discriminant) = variant.value.specified_discriminant() {
712 next_discriminant = discriminant + 1;
713 (discriminant, variant)
714 } else {
715 let discriminant = next_discriminant;
716 next_discriminant += 1;
717 (discriminant, variant)
718 }
719 })
720 }
721
722 pub fn iter_variants_with_discriminant_mut(
727 &mut self,
728 ) -> impl Iterator<Item = (i128, &mut EnumVariant)> {
729 let mut next_discriminant = 0;
730 self.variants.iter_mut().map(move |variant| {
731 if let Some(discriminant) = variant.value.specified_discriminant() {
732 next_discriminant = discriminant + 1;
733 (discriminant, variant)
734 } else {
735 let discriminant = next_discriminant;
736 next_discriminant += 1;
737 (discriminant, variant)
738 }
739 })
740 }
741}
742
743#[derive(Debug, Clone, PartialEq, Eq, Hash)]
744pub enum EnumGenerationStyle {
745 Fallible,
747 InfallibleWithinRange,
750 Fallback,
752}
753
754impl EnumGenerationStyle {
755 #[must_use]
759 pub fn is_fallible(&self) -> bool {
760 matches!(self, Self::Fallible)
761 }
762}
763
764#[derive(Debug, Clone, Default, PartialEq)]
765pub struct EnumVariant {
766 pub description: String,
767 pub name: Spanned<Identifier<All>>,
768 pub value: EnumValue,
769 pub span: Span,
771}
772
773#[derive(Debug, Clone, PartialEq, Eq, Default, Hash)]
774pub enum EnumValue {
775 #[default]
776 Unspecified,
777 Specified(i128),
778 Default(i128),
779 UnspecifiedDefault,
780 CatchAll(i128),
781 UnspecifiedCatchAll,
782}
783
784impl EnumValue {
785 #[must_use]
786 pub fn is_default(&self) -> bool {
787 matches!(self, Self::Default(_) | Self::UnspecifiedDefault)
788 }
789
790 #[must_use]
791 pub fn is_catch_all(&self) -> bool {
792 matches!(self, Self::CatchAll(_) | Self::UnspecifiedCatchAll)
793 }
794
795 pub fn specified_discriminant(&self) -> Option<i128> {
796 match self {
797 Self::Unspecified | Self::UnspecifiedDefault | Self::UnspecifiedCatchAll => None,
798 Self::Specified(val) | EnumValue::Default(val) | EnumValue::CatchAll(val) => Some(*val),
799 }
800 }
801
802 pub fn specify(&mut self, num: i128) {
803 *self = match self {
804 EnumValue::Unspecified | EnumValue::Specified(_) => Self::Specified(num),
805 EnumValue::Default(_) | EnumValue::UnspecifiedDefault => Self::Default(num),
806 EnumValue::CatchAll(_) | EnumValue::UnspecifiedCatchAll => Self::CatchAll(num),
807 };
808 }
809}
810
811#[derive(Debug, Clone, Default, PartialEq)]
812pub struct Command {
813 pub description: String,
814 pub name: Spanned<Identifier<Operation>>,
815 pub address: Spanned<i128>,
816 pub allow_address_overlap: bool,
817 pub repeat: Option<Repeat>,
818
819 pub field_set_ref_in: Option<Spanned<IdentifierRef<Type>>>,
820 pub field_set_ref_out: Option<Spanned<IdentifierRef<Type>>>,
821
822 pub short_properties_span: Span,
823 pub properties_span: Option<Span>,
824 pub span: Span,
826}
827
828#[derive(Debug, Clone, Default, PartialEq)]
829pub struct Buffer {
830 pub description: String,
831 pub name: Spanned<Identifier<Operation>>,
832 pub access: Option<Access>,
833 pub address: Spanned<i128>,
834
835 pub short_properties_span: Span,
836 pub properties_span: Option<Span>,
837 pub span: Span,
839}
840
841#[derive(Debug, Clone, Default, PartialEq)]
842pub struct Extern {
843 pub description: String,
844 pub name: Spanned<Identifier<Type>>,
845 pub base_type: Spanned<BaseType>,
847 pub supports_infallible: bool,
849 pub size_bits: Option<Spanned<u64>>,
851
852 pub short_properties_span: Span,
853 pub properties_span: Option<Span>,
854 pub span: Span,
856}
857
858#[derive(Debug, Clone, Hash, PartialEq, Eq)]
859pub enum UniqueId {
860 Object {
861 object_name: Spanned<Identifier<RuntimeType>>,
862 },
863 Field {
864 parent_id: Box<UniqueId>,
865 field_name: Spanned<Identifier<RuntimeType>>,
866 },
867 Variant {
868 parent_id: Box<UniqueId>,
869 variant_name: Spanned<Identifier<RuntimeType>>,
870 },
871}
872
873impl UniqueId {
874 #[must_use]
875 pub fn span(&self) -> Span {
876 match self {
877 UniqueId::Object { object_name } => object_name.span,
878 UniqueId::Field { field_name, .. } => field_name.span,
879 UniqueId::Variant { variant_name, .. } => variant_name.span,
880 }
881 }
882
883 pub fn identifier(&self) -> &Identifier<RuntimeType> {
884 match self {
885 UniqueId::Object { object_name } => object_name,
886 UniqueId::Field { field_name, .. } => field_name,
887 UniqueId::Variant { variant_name, .. } => variant_name,
888 }
889 }
890
891 #[cfg(test)]
893 pub fn new_test<T: IdentifierType>(identifier: Identifier<T>) -> Self {
894 use device_driver_common::span::SpanExt;
895
896 Self::Object {
897 object_name: identifier.to_runtime_type().with_dummy_span(),
898 }
899 }
900}
901
902impl Display for UniqueId {
903 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
904 match self {
905 UniqueId::Object { object_name } => write!(f, "{}", object_name.original()),
906 UniqueId::Field {
907 parent_id,
908 field_name,
909 } => write!(f, "{parent_id} {{ {} }}", field_name.original()),
910 UniqueId::Variant {
911 parent_id,
912 variant_name,
913 } => write!(f, "{parent_id} {{ {} }}", variant_name.original()),
914 }
915 }
916}
917
918pub trait Unique {
919 type Metadata;
920
921 fn id(&self) -> UniqueId
922 where
923 Self::Metadata: Empty;
924 fn id_with(&self, meta: Self::Metadata) -> UniqueId;
925
926 fn has_id(&self, id: &UniqueId) -> bool
927 where
928 Self::Metadata: Empty;
929 fn has_id_with(&self, meta: Self::Metadata, id: &UniqueId) -> bool {
930 self.id_with(meta) == *id
931 }
932}
933
934pub trait Empty {}
935impl Empty for () {}
936
937macro_rules! impl_unique_object {
938 ($t:ty) => {
939 impl Unique for $t {
940 type Metadata = ();
941
942 fn id(&self) -> UniqueId {
943 UniqueId::Object {
944 object_name: self
945 .name
946 .value
947 .clone()
948 .to_runtime_type()
949 .with_span(self.name.span),
950 }
951 }
952
953 fn id_with(&self, _: Self::Metadata) -> UniqueId {
954 self.id()
955 }
956
957 fn has_id(&self, id: &UniqueId) -> bool {
958 match id {
959 UniqueId::Object { object_name } => {
960 self.name.as_runtime_type() == &object_name.value
961 }
962 _ => false,
963 }
964 }
965 }
966 };
967}
968
969impl_unique_object!(Device);
970impl_unique_object!(Register);
971impl_unique_object!(Command);
972impl_unique_object!(Buffer);
973impl_unique_object!(Block);
974impl_unique_object!(Enum);
975impl_unique_object!(FieldSet);
976impl_unique_object!(Extern);
977
978impl Unique for Field {
979 type Metadata = UniqueId;
980
981 fn id(&self) -> UniqueId {
982 unreachable!()
983 }
984
985 fn id_with(&self, parent: Self::Metadata) -> UniqueId {
986 UniqueId::Field {
987 parent_id: Box::new(parent),
988 field_name: self
989 .name
990 .value
991 .clone()
992 .to_runtime_type()
993 .with_span(self.name.span),
994 }
995 }
996
997 fn has_id(&self, _id: &UniqueId) -> bool {
998 unreachable!()
999 }
1000}
1001
1002impl Unique for EnumVariant {
1003 type Metadata = UniqueId;
1004
1005 fn id(&self) -> UniqueId {
1006 unreachable!()
1007 }
1008
1009 fn id_with(&self, parent: Self::Metadata) -> UniqueId {
1010 UniqueId::Variant {
1011 parent_id: Box::new(parent),
1012 variant_name: self
1013 .name
1014 .value
1015 .clone()
1016 .to_runtime_type()
1017 .with_span(self.name.span),
1018 }
1019 }
1020
1021 fn has_id(&self, _id: &UniqueId) -> bool {
1022 unreachable!()
1023 }
1024}
1025
1026impl Unique for Object {
1027 type Metadata = ();
1028
1029 fn id(&self) -> UniqueId {
1030 match self {
1031 Object::Device(val) => val.id(),
1032 Object::Block(val) => val.id(),
1033 Object::Register(val) => val.id(),
1034 Object::Command(val) => val.id(),
1035 Object::Buffer(val) => val.id(),
1036 Object::FieldSet(val) => val.id(),
1037 Object::Enum(val) => val.id(),
1038 Object::Extern(val) => val.id(),
1039 Object::Field(_) => unimplemented!(),
1041 }
1042 }
1043
1044 fn id_with(&self, (): Self::Metadata) -> UniqueId {
1045 self.id()
1046 }
1047
1048 fn has_id(&self, id: &UniqueId) -> bool {
1049 match self {
1050 Object::Device(val) => val.has_id(id),
1051 Object::Block(val) => val.has_id(id),
1052 Object::Register(val) => val.has_id(id),
1053 Object::Command(val) => val.has_id(id),
1054 Object::Buffer(val) => val.has_id(id),
1055 Object::FieldSet(val) => val.has_id(id),
1056 Object::Enum(val) => val.has_id(id),
1057 Object::Extern(val) => val.has_id(id),
1058 Object::Field(_) => unimplemented!(),
1060 }
1061 }
1062}
1063
1064#[cfg(test)]
1065mod tests {
1066 use device_driver_common::span::SpanExt;
1067
1068 use super::*;
1069
1070 #[test]
1071 fn iter_works() {
1072 const NAME_ORDER: &[&str] = &["a", "b", "c", "d"];
1073
1074 let mut manifest = Manifest {
1075 description: Default::default(),
1076 name: Default::default(),
1077 objects: vec![
1078 Object::Device(Device {
1079 description: String::new(),
1080 name: Identifier::try_parse("a").unwrap().with_dummy_span(),
1081 objects: vec![
1082 Object::Extern(Extern {
1083 name: Identifier::try_parse("b").unwrap().with_dummy_span(),
1084 ..Default::default()
1085 }),
1086 Object::Extern(Extern {
1087 name: Identifier::try_parse("c").unwrap().with_dummy_span(),
1088 ..Default::default()
1089 }),
1090 ],
1091 ..Default::default()
1092 }),
1093 Object::Extern(Extern {
1094 name: Identifier::try_parse("d").unwrap().with_dummy_span(),
1095 ..Default::default()
1096 }),
1097 ],
1098 ..Default::default()
1099 };
1100
1101 let names: Vec<_> = manifest
1102 .iter_objects()
1103 .map(|o| o.name().original())
1104 .collect();
1105 assert_eq!(&names, NAME_ORDER);
1106
1107 let mut names = Vec::new();
1108 let mut lender = manifest.iter_objects_with_config_mut();
1109 while let Some((object, _)) = lender.next() {
1110 names.push(object.name().original().to_string());
1111 }
1112 assert_eq!(&names, NAME_ORDER);
1113 }
1114
1115 #[test]
1116 fn correct_integer_size_bits() {
1117 assert_eq!(Integer::U8.bits_required(0, 0), 0);
1118 assert_eq!(Integer::U8.bits_required(0, 1), 1);
1119 assert_eq!(Integer::U8.bits_required(0, 2), 2);
1120 assert_eq!(Integer::U8.bits_required(0, 3), 2);
1121 assert_eq!(Integer::U8.bits_required(0, 4), 3);
1122
1123 assert_eq!(Integer::I8.bits_required(0, 0), 0);
1124 assert_eq!(Integer::I8.bits_required(-1, 0), 1);
1125 assert_eq!(Integer::I8.bits_required(-1, 1), 2);
1126 assert_eq!(Integer::I8.bits_required(0, 1), 2);
1127 assert_eq!(Integer::I8.bits_required(-2, 1), 2);
1128 assert_eq!(Integer::I8.bits_required(0, 2), 3);
1129 assert_eq!(Integer::I8.bits_required(-128, 0), 8);
1130 assert_eq!(Integer::I8.bits_required(-129, 0), 9);
1131 assert_eq!(Integer::I8.bits_required(0, 127), 8);
1132 assert_eq!(Integer::I8.bits_required(0, 128), 9);
1133 assert_eq!(Integer::I8.bits_required(-16, 15), 5);
1134 assert_eq!(Integer::I8.bits_required(-16, 16), 6);
1135 assert_eq!(Integer::I8.bits_required(-17, 15), 6);
1136 }
1137}