rustc_codegen_llvm/coverageinfo/
ffi.rs1use rustc_middle::mir::coverage::{CounterId, CovTerm, ExpressionId};
2
3#[derive(Copy, Clone, Debug)]
5#[repr(C)]
6pub(crate) enum CounterKind {
7 Zero = 0,
8 CounterValueReference = 1,
9 Expression = 2,
10}
11
12#[derive(Copy, Clone, Debug)]
25#[repr(C)]
26pub(crate) struct Counter {
27 pub(crate) kind: CounterKind,
29 id: u32,
30}
31
32impl Counter {
33 pub(crate) const ZERO: Self = Self { kind: CounterKind::Zero, id: 0 };
35
36 pub(crate) fn counter_value_reference(counter_id: CounterId) -> Self {
38 Self { kind: CounterKind::CounterValueReference, id: counter_id.as_u32() }
39 }
40
41 pub(crate) fn expression(expression_id: ExpressionId) -> Self {
43 Self { kind: CounterKind::Expression, id: expression_id.as_u32() }
44 }
45
46 pub(crate) fn from_term(term: CovTerm) -> Self {
47 match term {
48 CovTerm::Zero => Self::ZERO,
49 CovTerm::Counter(id) => Self::counter_value_reference(id),
50 CovTerm::Expression(id) => Self::expression(id),
51 }
52 }
53}
54
55#[derive(Copy, Clone, Debug)]
59#[repr(C)]
60pub(crate) enum ExprKind {
61 Subtract = 0,
62 Add = 1,
63}
64
65#[derive(Copy, Clone, Debug)]
69#[repr(C)]
70pub(crate) struct CounterExpression {
71 pub(crate) kind: ExprKind,
72 pub(crate) lhs: Counter,
73 pub(crate) rhs: Counter,
74}
75
76pub(crate) mod mcdc {
77 use rustc_middle::mir::coverage::{ConditionId, ConditionInfo, DecisionInfo};
78
79 #[repr(C)]
81 #[derive(Clone, Copy, Debug, Default)]
82 pub(crate) struct DecisionParameters {
83 bitmap_idx: u32,
84 num_conditions: u16,
85 }
86
87 type LLVMConditionId = i16;
88
89 #[repr(C)]
91 #[derive(Clone, Copy, Debug, Default)]
92 pub(crate) struct BranchParameters {
93 condition_id: LLVMConditionId,
94 condition_ids: [LLVMConditionId; 2],
95 }
96
97 impl From<ConditionInfo> for BranchParameters {
98 fn from(value: ConditionInfo) -> Self {
99 let to_llvm_cond_id = |cond_id: Option<ConditionId>| {
100 cond_id.and_then(|id| LLVMConditionId::try_from(id.as_usize()).ok()).unwrap_or(-1)
101 };
102 let ConditionInfo { condition_id, true_next_id, false_next_id } = value;
103 Self {
104 condition_id: to_llvm_cond_id(Some(condition_id)),
105 condition_ids: [to_llvm_cond_id(false_next_id), to_llvm_cond_id(true_next_id)],
106 }
107 }
108 }
109
110 impl From<DecisionInfo> for DecisionParameters {
111 fn from(info: DecisionInfo) -> Self {
112 let DecisionInfo { bitmap_idx, num_conditions } = info;
113 Self { bitmap_idx, num_conditions }
114 }
115 }
116}
117
118#[derive(Clone, Debug)]
122#[repr(C)]
123pub(crate) struct CoverageSpan {
124 pub(crate) file_id: u32,
128
129 pub(crate) start_line: u32,
131 pub(crate) start_col: u32,
133 pub(crate) end_line: u32,
135 pub(crate) end_col: u32,
137}
138
139#[derive(Clone, Debug, Default)]
147pub(crate) struct Regions {
148 pub(crate) code_regions: Vec<CodeRegion>,
149 pub(crate) expansion_regions: Vec<ExpansionRegion>,
150 pub(crate) branch_regions: Vec<BranchRegion>,
151 pub(crate) mcdc_branch_regions: Vec<MCDCBranchRegion>,
152 pub(crate) mcdc_decision_regions: Vec<MCDCDecisionRegion>,
153}
154
155impl Regions {
156 pub(crate) fn has_no_regions(&self) -> bool {
158 let Self {
159 code_regions,
160 expansion_regions,
161 branch_regions,
162 mcdc_branch_regions,
163 mcdc_decision_regions,
164 } = self;
165
166 code_regions.is_empty()
167 && expansion_regions.is_empty()
168 && branch_regions.is_empty()
169 && mcdc_branch_regions.is_empty()
170 && mcdc_decision_regions.is_empty()
171 }
172}
173
174#[derive(Clone, Debug)]
176#[repr(C)]
177pub(crate) struct CodeRegion {
178 pub(crate) cov_span: CoverageSpan,
179 pub(crate) counter: Counter,
180}
181
182#[derive(Clone, Debug)]
184#[repr(C)]
185pub(crate) struct ExpansionRegion {
186 pub(crate) cov_span: CoverageSpan,
187 pub(crate) expanded_file_id: u32,
188}
189
190#[derive(Clone, Debug)]
192#[repr(C)]
193pub(crate) struct BranchRegion {
194 pub(crate) cov_span: CoverageSpan,
195 pub(crate) true_counter: Counter,
196 pub(crate) false_counter: Counter,
197}
198
199#[derive(Clone, Debug)]
201#[repr(C)]
202pub(crate) struct MCDCBranchRegion {
203 pub(crate) cov_span: CoverageSpan,
204 pub(crate) true_counter: Counter,
205 pub(crate) false_counter: Counter,
206 pub(crate) mcdc_branch_params: mcdc::BranchParameters,
207}
208
209#[derive(Clone, Debug)]
211#[repr(C)]
212pub(crate) struct MCDCDecisionRegion {
213 pub(crate) cov_span: CoverageSpan,
214 pub(crate) mcdc_decision_params: mcdc::DecisionParameters,
215}