Skip to main content

veryl_analyzer/conv/
instance.rs

1use crate::HashMap;
2use crate::conv::context::Config;
3use crate::ir::{Component, Signature};
4use std::sync::Arc;
5
6#[derive(Clone, Default)]
7pub struct InstanceHistory {
8    pub hierarchy: Vec<Signature>,
9    /// `Arc`-wrapped so repeated `get` hands out references instead of
10    /// deep-cloning the component tree — matters on testbench-heavy designs.
11    full: HashMap<Signature, Option<Arc<Component>>>,
12}
13
14impl InstanceHistory {
15    pub fn get(&self, sig: &Signature) -> Option<Arc<Component>> {
16        self.full.get(sig).cloned().flatten()
17    }
18
19    pub fn set(&mut self, sig: &Signature, component: Arc<Component>) {
20        if let Some(x) = self.full.get_mut(sig) {
21            *x = Some(component);
22        }
23    }
24
25    pub fn get_current_signature(&self) -> Option<&Signature> {
26        self.hierarchy.last()
27    }
28
29    pub fn push(
30        &mut self,
31        mut sig: Signature,
32        config: &Config,
33    ) -> Result<bool, InstanceHistoryError> {
34        sig.normalize();
35        if self.hierarchy.len() > config.instance_depth_limit {
36            return Err(InstanceHistoryError::ExceedDepthLimit(self.hierarchy.len()));
37        }
38        if self.full.len() > config.instance_total_limit {
39            return Err(InstanceHistoryError::ExceedTotalLimit(self.full.len()));
40        }
41        if self.hierarchy.contains(&sig) {
42            return Err(InstanceHistoryError::InfiniteRecursion);
43        }
44        if self.full.contains_key(&sig) {
45            Ok(false)
46        } else {
47            self.hierarchy.push(sig.clone());
48            self.full.insert(sig, None);
49            Ok(true)
50        }
51    }
52
53    pub fn pop(&mut self) {
54        self.hierarchy.pop();
55    }
56
57    pub fn clear(&mut self) {
58        self.hierarchy.clear();
59        self.full.clear();
60    }
61}
62
63#[derive(Debug)]
64pub enum InstanceHistoryError {
65    ExceedDepthLimit(usize),
66    ExceedTotalLimit(usize),
67    InfiniteRecursion,
68}