Skip to main content

litex/execute/
exec_have_exist_obj_stmt.rs

1use crate::prelude::*;
2
3impl Runtime {
4    pub fn exec_have_exist_obj_stmt(
5        &mut self,
6        have_exist_obj_stmt: &HaveByExistStmt,
7    ) -> Result<StmtResult, RuntimeError> {
8        let exist_fact_in_have_obj_stmt = &have_exist_obj_stmt.exist_fact_in_have_obj_st;
9        let verify_state = VerifyState::new(0, false);
10
11        let result = self
12            .verify_exist_fact(exist_fact_in_have_obj_stmt, &verify_state)
13            .map_err(|verify_error| {
14                short_exec_error(
15                    have_exist_obj_stmt.clone().into(),
16                    "",
17                    Some(verify_error),
18                    vec![],
19                )
20            })?;
21        if result.is_unknown() {
22            return Err(short_exec_error(
23                have_exist_obj_stmt.clone().into(),
24                "have_exist_obj_stmt: exist fact is not verified".to_string(),
25                None,
26                vec![],
27            ));
28        }
29
30        if exist_fact_in_have_obj_stmt
31            .params_def_with_type()
32            .number_of_params()
33            != have_exist_obj_stmt.equal_tos.len()
34        {
35            return Err(short_exec_error(
36 have_exist_obj_stmt.clone().into(),
37                    "have_exist_obj_stmt: number of params in exist does not match number of given objs".to_string(),
38                    None,
39                    vec![],
40                ));
41        }
42
43        for obj in have_exist_obj_stmt.equal_tos.iter() {
44            self.store_free_param_or_identifier_name(obj, ParamObjType::Exist)?;
45        }
46
47        let new_obj_names_as_identifier_objs = have_exist_obj_stmt
48            .equal_tos
49            .iter()
50            .map(|s| Identifier::new(s.clone()).into())
51            .collect();
52
53        let mut infer_result = self
54            .store_args_satisfy_param_type_when_not_defining_new_identifiers(
55                exist_fact_in_have_obj_stmt.params_def_with_type(),
56                &new_obj_names_as_identifier_objs,
57                have_exist_obj_stmt.line_file.clone(),
58                ParamObjType::Exist,
59            )
60            .map_err(|e| {
61                short_exec_error(have_exist_obj_stmt.clone().into(), "", Some(e), vec![])
62            })?;
63
64        let param_to_obj_map = exist_fact_in_have_obj_stmt
65            .params_def_with_type()
66            .param_defs_and_args_to_param_to_arg_map(new_obj_names_as_identifier_objs.as_slice());
67
68        for fact in exist_fact_in_have_obj_stmt.facts().iter() {
69            let instantiated_fact = self
70                .inst_exist_body_fact(fact, &param_to_obj_map, ParamObjType::Exist, None)
71                .map_err(|runtime_error| {
72                    short_exec_error(
73                        have_exist_obj_stmt.clone().into(),
74                        "",
75                        Some(runtime_error),
76                        vec![],
77                    )
78                })?
79                .to_fact();
80            let fact_infer_result = self
81                .verify_well_defined_and_store_and_infer_with_default_verify_state(
82                    instantiated_fact,
83                )
84                .map_err(|store_fact_error| {
85                    short_exec_error(
86                        have_exist_obj_stmt.clone().into(),
87                        "",
88                        Some(store_fact_error),
89                        vec![],
90                    )
91                })?;
92            infer_result.new_infer_result_inside(fact_infer_result);
93        }
94
95        Ok((NonFactualStmtSuccess::new(
96            have_exist_obj_stmt.clone().into(),
97            infer_result,
98            vec![result],
99        ))
100        .into())
101    }
102}