Skip to main content

luaur_analysis/methods/
cfg_builder_read_variable.rs

1//! Source: `Analysis/src/ControlFlowGraph.cpp:464-486` (hand-ported)
2//! C++ `DefId CFGBuilder::readVariable(BlockId block, Symbol sym)`.
3use crate::records::cfg_builder::CfgBuilder;
4use crate::records::symbol::Symbol;
5use crate::type_aliases::block_id::BlockId;
6use crate::type_aliases::def_id_control_flow_graph::DefId;
7
8impl CfgBuilder {
9    pub fn read_variable(&mut self, block: BlockId, sym: Symbol) -> DefId {
10        unsafe {
11            // C++:
12            //   if (auto v = block->getReachingDefinition(sym); v != nullptr)
13            //       return NotNull{v};
14            let v = (*block).get_reaching_definition(sym.clone());
15            if !v.is_null() {
16                return v;
17            }
18
19            // if (!isSealed(block)) { Join* j = emitJoin(block, sym); return j->definition; }
20            if !self.is_sealed(block) {
21                let j = self.emit_join(block, sym);
22                return (*j).definition;
23            }
24            // else if (block->getPredecessors().size() == 1) {
25            //     auto def = readVariable(block->getPredecessors()[0], sym);
26            //     block->setReachingDefinition(sym, def);
27            //     return def;
28            // }
29            else if (*block).get_predecessors().len() == 1 {
30                let pred = (*block).get_predecessors()[0];
31                let def = self.read_variable(pred, sym.clone());
32                (*block).set_reaching_definition(sym, def);
33                def
34            }
35            // else { Join* j = emitJoin(block, sym); fillJoinOperands(block, j); return j->definition; }
36            else {
37                let j = self.emit_join(block, sym);
38                self.fill_join_operands(block, j);
39                (*j).definition
40            }
41        }
42    }
43}