rapx/analysis/alias/default/
mop.rs1use rustc_hir::def_id::DefId;
2
3use std::collections::HashSet;
4
5use crate::analysis::alias::observer::NoopAliasObserver;
6use crate::analysis::path::{PathNode, PathTree};
7use crate::limit::ALIAS_VISIT_LIMIT;
8
9use super::alias::ensure_fn_aliases_cached;
10use super::{graph::*, *};
11
12impl<'tcx> AliasGraph<'tcx> {
13 pub fn process_function_paths(
14 &mut self,
15 fn_map: &mut MopFnAliasMap,
16 recursion_set: &mut HashSet<DefId>,
17 ) {
18 self.process_function_paths_opt(None, fn_map, recursion_set)
19 }
20
21 pub fn process_function_paths_opt(
22 &mut self,
23 precomputed_paths: Option<PathTree>,
24 fn_map: &mut MopFnAliasMap,
25 recursion_set: &mut HashSet<DefId>,
26 ) {
27 self.init_pts_graph();
28
29 let paths = precomputed_paths.unwrap_or_else(|| self.enumerate_paths());
30 let Some(root) = paths.root() else {
31 return;
32 };
33
34 let mut path = Vec::new();
35 let _ = self.dfs_mop(root, &mut path, fn_map, recursion_set);
36 }
37
38 fn dfs_mop(
39 &mut self,
40 node: &PathNode,
41 path: &mut Vec<usize>,
42 fn_map: &mut MopFnAliasMap,
43 rec_set: &mut HashSet<DefId>,
44 ) -> Result<(), ()> {
45 path.push(node.block);
46 let mut obs = NoopAliasObserver;
47
48 self.alias_bb(node.block, &mut obs);
49 if let Some(target_id) = self.call_target_of(node.block) {
50 ensure_fn_aliases_cached(self.tcx(), target_id, fn_map, rec_set);
51 }
52 self.alias_bbcall(node.block, fn_map, &mut obs);
53
54 let saved_pts_graph = self.pts_graph.clone();
55 let saved_rec = rec_set.clone();
56
57 if node.is_path_end {
58 self.increment_visit_times();
59 if self.visit_times() > ALIAS_VISIT_LIMIT {
60 path.pop();
61 return Err(());
62 }
63 self.merge_results_pts();
64 }
65
66 for child in &node.children {
67 self.pts_graph = saved_pts_graph.clone();
68 *rec_set = saved_rec.clone();
69 self.dfs_mop(child, path, fn_map, rec_set)?;
70 }
71
72 path.pop();
73 Ok(())
74 }
75}