Skip to main content

nichlink/registry_core/mir/
model.rs

1//! Shared MIR vocabulary: parsed candidates, evidence-aware relations, errors.
2//! 共享 MIR 词汇:已解析候选、带证据等级的关系、错误。
3//!
4//! The parsers live beside this page: `super::text` reads rustc
5//! `-Zunpretty=mir` text, `super::jsonl` reads the compact JSONL artifact,
6//! `super::render` writes both artifacts back, and `super::merge` merges
7//! static candidates with live edges.
8//! 解析器位于本页旁边:`super::text` 读取 rustc `-Zunpretty=mir` 文本,
9//! `super::jsonl` 读取紧凑 JSONL artifact,`super::render` 把两种 artifact 写回,
10//! `super::merge` 将静态候选与 live 边归并。
11
12use std::collections::BTreeSet;
13use std::fmt;
14
15use crate::registry_core::declaration::{EvidenceKind, SourceLocation};
16
17/// One direct call sighting extracted from a MIR artifact.
18/// 从 MIR artifact 中提取到的一条直接调用观测。
19#[derive(Clone, Debug, PartialEq, Eq)]
20pub struct MirCall {
21    /// Function symbol the call appears in.
22    /// 调用所在的函数符号。
23    pub caller: String,
24    /// Function symbol being called.
25    /// 被调用的函数符号。
26    pub callee: String,
27    /// 1-based position of this record within the parsed MIR, not a source line.
28    /// 该记录在已解析 MIR 内以 1 起始的位置,不是源码行号。
29    pub mir_line: usize,
30}
31
32/// One local binding sighting extracted from a MIR artifact.
33/// 从 MIR artifact 中提取到的一条局部绑定观测。
34#[derive(Clone, Debug, PartialEq, Eq)]
35pub struct MirLocal {
36    /// Function symbol owning the local.
37    /// 拥有该局部变量的函数符号。
38    pub function: String,
39    /// Local binding name as written in MIR, such as `_1`.
40    /// MIR 中书写的局部绑定名,例如 `_1`。
41    pub name: String,
42    /// Declared type text of the binding.
43    /// 该绑定的声明类型文本。
44    pub type_name: String,
45    /// 1-based position of this record within the parsed MIR, not a source line.
46    /// 该记录在已解析 MIR 内以 1 起始的位置,不是源码行号。
47    pub mir_line: usize,
48}
49
50/// Unified evidence attached to one logical call relation.
51/// 一条逻辑调用关系携带的统一证据等级。
52pub type CallEvidence = EvidenceKind;
53
54/// One call edge normalized across runtime, MIR, and source evidence.
55/// 跨运行时、MIR、源码证据统一表示的一条调用边。
56#[derive(Clone, Debug, PartialEq, Eq)]
57pub struct CallRelation {
58    /// Function symbol making the call.
59    /// 发起调用的函数符号。
60    pub caller: String,
61    /// Function symbol being called.
62    /// 被调用的函数符号。
63    pub callee: String,
64    /// Strongest evidence supporting this relation: live over MIR.
65    /// 支持该关系的最高证据等级:Live 优先于 MIR。
66    pub evidence: EvidenceKind,
67    /// Source location of the callee, when known.
68    /// 已知时,被调用方的源码位置。
69    pub source: Option<SourceLocation>,
70    /// MIR record position for a MIR-only relation; `None` for a live edge.
71    /// 仅由 MIR 支持时为 MIR 记录位置;live 边为 `None`。
72    pub mir_line: Option<usize>,
73    /// Runtime frame id of the caller; `None` for a static-only relation.
74    /// 调用方的运行期帧 id;仅静态关系为 `None`。
75    pub caller_frame: Option<u64>,
76    /// Runtime frame id of the callee; `None` for a static-only relation.
77    /// 被调用方的运行期帧 id;仅静态关系为 `None`。
78    pub callee_frame: Option<u64>,
79}
80
81impl CallRelation {
82    /// A relation whose two ends are known but whose provenance is only the text
83    /// of the call site: no MIR record, no runtime frame.
84    /// 两端已知、但来源只是调用点文本的关系:没有 MIR 记录,也没有运行期帧。
85    ///
86    /// Studio's source scan produces these, which is why the type has to be
87    /// constructible without inventing a MIR line or a frame id.
88    /// Studio 的源码扫描产生的正是它们,因此该类型必须能在不编造 MIR 行号或帧 id 的情况下构造。
89    pub fn from_symbols(
90        caller: impl Into<String>,
91        callee: impl Into<String>,
92        evidence: EvidenceKind,
93    ) -> Self {
94        Self {
95            caller: caller.into(),
96            callee: callee.into(),
97            evidence,
98            source: None,
99            mir_line: None,
100            caller_frame: None,
101            callee_frame: None,
102        }
103    }
104}
105
106/// Every candidate one MIR artifact offered, before any merge.
107/// 一份 MIR artifact 提供的全部候选,尚未归并。
108#[derive(Clone, Debug, Default, PartialEq, Eq)]
109pub struct MirGraph {
110    /// Function symbols the artifact declared.
111    /// artifact 声明过的函数符号。
112    pub functions: BTreeSet<String>,
113    /// Direct call sightings, in artifact order.
114    /// 直接调用观测,按 artifact 顺序。
115    pub calls: Vec<MirCall>,
116    /// Local binding sightings, in artifact order.
117    /// 局部绑定观测,按 artifact 顺序。
118    pub locals: Vec<MirLocal>,
119}
120
121/// Why one line of a MIR artifact could not be read.
122/// MIR artifact 某一行无法读取的原因。
123#[derive(Clone, Debug, PartialEq, Eq)]
124pub struct MirParseError {
125    /// 1-based line of the offending input.
126    /// 出错输入以 1 起始的行号。
127    pub line: usize,
128    /// Description of what the line got wrong.
129    /// 对该行错误之处的描述。
130    pub message: String,
131}
132
133impl fmt::Display for MirParseError {
134    fn fmt(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result {
135        write!(formatter, "MIR graph line {}: {}", self.line, self.message)
136    }
137}
138
139impl std::error::Error for MirParseError {}