Skip to content

Commit c514904

Browse files
committed
Wrap more state into AssignmentResult.
1 parent d953583 commit c514904

File tree

1 file changed

+62
-52
lines changed

1 file changed

+62
-52
lines changed

compiler/rustc_mir_transform/src/liveness.rs

Lines changed: 62 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -134,14 +134,17 @@ pub(crate) fn check_liveness<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Den
134134
.iterate_to_fixpoint(tcx, body, None)
135135
.into_results_cursor(body);
136136

137-
let mut assignments = AssignmentResult::find_dead_assignments(&checked_places, &mut live, body);
137+
let typing_env = ty::TypingEnv::post_analysis(tcx, body.source.def_id());
138138

139-
assignments.merge_guards(&checked_places, body);
139+
let mut assignments =
140+
AssignmentResult::find_dead_assignments(tcx, typing_env, &checked_places, &mut live, body);
140141

141-
let dead_captures = assignments.compute_dead_captures(&checked_places, num_captures);
142+
assignments.merge_guards();
142143

143-
assignments.report_fully_unused(tcx, &checked_places, body);
144-
assignments.report_unused_assignments(tcx, def_id, &checked_places, body);
144+
let dead_captures = assignments.compute_dead_captures(num_captures);
145+
146+
assignments.report_fully_unused();
147+
assignments.report_unused_assignments();
145148

146149
dead_captures
147150
}
@@ -550,6 +553,7 @@ impl<'tcx> PlaceSet<'tcx> {
550553
}
551554
}
552555

556+
#[inline]
553557
fn get(&self, place: PlaceRef<'tcx>) -> Option<(PlaceIndex, &'tcx [PlaceElem<'tcx>])> {
554558
if let Some(index) = self.locals[place.local] {
555559
return Some((index, place.projection));
@@ -583,7 +587,11 @@ impl<'tcx> PlaceSet<'tcx> {
583587
}
584588
}
585589

586-
struct AssignmentResult {
590+
struct AssignmentResult<'a, 'tcx> {
591+
tcx: TyCtxt<'tcx>,
592+
typing_env: ty::TypingEnv<'tcx>,
593+
checked_places: &'a PlaceSet<'tcx>,
594+
body: &'a Body<'tcx>,
587595
/// Set of locals that are live at least once. This is used to report fully unused locals.
588596
ever_live: DenseBitSet<PlaceIndex>,
589597
/// Set of locals that have a non-trivial drop. This is used to skip reporting unused
@@ -598,16 +606,18 @@ struct AssignmentResult {
598606
assignments: IndexVec<PlaceIndex, FxIndexMap<SourceInfo, Access>>,
599607
}
600608

601-
impl AssignmentResult {
609+
impl<'a, 'tcx> AssignmentResult<'a, 'tcx> {
602610
/// Collect all assignments to checked locals.
603611
///
604612
/// Assignments are collected, even if they are live. Dead assignments are reported, and live
605613
/// assignments are used to make diagnostics correct for match guards.
606-
fn find_dead_assignments<'tcx>(
607-
checked_places: &PlaceSet<'tcx>,
614+
fn find_dead_assignments(
615+
tcx: TyCtxt<'tcx>,
616+
typing_env: ty::TypingEnv<'tcx>,
617+
checked_places: &'a PlaceSet<'tcx>,
608618
cursor: &mut ResultsCursor<'_, 'tcx, MaybeLivePlaces<'_, 'tcx>>,
609-
body: &Body<'tcx>,
610-
) -> AssignmentResult {
619+
body: &'a Body<'tcx>,
620+
) -> AssignmentResult<'a, 'tcx> {
611621
let mut ever_live = DenseBitSet::new_empty(checked_places.len());
612622
let mut ever_dropped = DenseBitSet::new_empty(checked_places.len());
613623
let mut assignments = IndexVec::<PlaceIndex, FxIndexMap<_, _>>::from_elem(
@@ -717,7 +727,15 @@ impl AssignmentResult {
717727
}
718728
}
719729

720-
AssignmentResult { ever_live, ever_dropped, assignments }
730+
AssignmentResult {
731+
tcx,
732+
typing_env,
733+
checked_places,
734+
ever_live,
735+
ever_dropped,
736+
assignments,
737+
body,
738+
}
721739
}
722740

723741
/// Match guards introduce a different local to freeze the guarded value as immutable.
@@ -731,16 +749,16 @@ impl AssignmentResult {
731749
/// _ => {}
732750
/// }
733751
///
734-
fn merge_guards<'tcx>(&mut self, checked_places: &PlaceSet<'tcx>, body: &Body<'_>) {
735-
for (index, place) in checked_places.iter() {
752+
fn merge_guards(&mut self) {
753+
for (index, place) in self.checked_places.iter() {
736754
let local = place.local;
737755
if let &LocalInfo::User(BindingForm::RefForGuard(arm_local)) =
738-
body.local_decls[local].local_info()
756+
self.body.local_decls[local].local_info()
739757
{
740758
debug_assert!(place.projection.is_empty());
741759

742760
// Local to use in the arm.
743-
let Some((arm_index, _proj)) = checked_places.get(arm_local.into()) else {
761+
let Some((arm_index, _proj)) = self.checked_places.get(arm_local.into()) else {
744762
continue;
745763
};
746764
debug_assert_ne!(index, arm_index);
@@ -775,14 +793,10 @@ impl AssignmentResult {
775793
}
776794

777795
/// Compute captures that are fully dead.
778-
fn compute_dead_captures<'tcx>(
779-
&self,
780-
checked_places: &PlaceSet<'tcx>,
781-
num_captures: usize,
782-
) -> DenseBitSet<FieldIdx> {
796+
fn compute_dead_captures(&self, num_captures: usize) -> DenseBitSet<FieldIdx> {
783797
// Report to caller the set of dead captures.
784798
let mut dead_captures = DenseBitSet::new_empty(num_captures);
785-
for (index, place) in checked_places.iter() {
799+
for (index, place) in self.checked_places.iter() {
786800
if self.ever_live.contains(index) {
787801
continue;
788802
}
@@ -803,16 +817,11 @@ impl AssignmentResult {
803817
}
804818

805819
/// Report fully unused locals, and forget the corresponding assignments.
806-
fn report_fully_unused<'tcx>(
807-
&mut self,
808-
tcx: TyCtxt<'tcx>,
809-
checked_places: &PlaceSet<'tcx>,
810-
body: &Body<'tcx>,
811-
) {
812-
let typing_env = ty::TypingEnv::post_analysis(tcx, body.source.def_id());
820+
fn report_fully_unused(&mut self) {
821+
let tcx = self.tcx;
813822

814823
// First, report fully unused locals.
815-
for (index, place) in checked_places.iter() {
824+
for (index, place) in self.checked_places.iter() {
816825
if self.ever_live.contains(index) {
817826
continue;
818827
}
@@ -823,21 +832,21 @@ impl AssignmentResult {
823832
}
824833

825834
let local = place.local;
826-
let decl = &body.local_decls[local];
835+
let decl = &self.body.local_decls[local];
827836

828837
if decl.from_compiler_desugaring() {
829838
continue;
830839
}
831840

832841
// Only report actual user-defined binding from now on.
833842
let LocalInfo::User(BindingForm::Var(binding)) = decl.local_info() else { continue };
834-
let Some(hir_id) = decl.source_info.scope.lint_root(&body.source_scopes) else {
843+
let Some(hir_id) = decl.source_info.scope.lint_root(&self.body.source_scopes) else {
835844
continue;
836845
};
837846

838847
let introductions = &binding.introductions;
839848

840-
let Some((name, def_span)) = checked_places.names[index] else { continue };
849+
let Some((name, def_span)) = self.checked_places.names[index] else { continue };
841850

842851
// #117284, when `ident_span` and `def_span` have different contexts
843852
// we can't provide a good suggestion, instead we pointed out the spans from macro
@@ -857,7 +866,7 @@ impl AssignmentResult {
857866
def_span,
858867
errors::UnusedVariable {
859868
name,
860-
string_interp: maybe_suggest_literal_matching_name(body, name),
869+
string_interp: maybe_suggest_literal_matching_name(self.body, name),
861870
sugg,
862871
},
863872
);
@@ -888,11 +897,11 @@ impl AssignmentResult {
888897
// This is probably a drop-guard, so we do not issue a warning there.
889898
if maybe_drop_guard(
890899
tcx,
891-
typing_env,
900+
self.typing_env,
892901
index,
893902
&self.ever_dropped,
894-
checked_places,
895-
body,
903+
self.checked_places,
904+
self.body,
896905
) {
897906
statements.clear();
898907
continue;
@@ -944,7 +953,7 @@ impl AssignmentResult {
944953
spans,
945954
errors::UnusedVariable {
946955
name,
947-
string_interp: maybe_suggest_literal_matching_name(body, name),
956+
string_interp: maybe_suggest_literal_matching_name(self.body, name),
948957
sugg,
949958
},
950959
);
@@ -953,25 +962,26 @@ impl AssignmentResult {
953962

954963
/// Second, report unused assignments that do not correspond to initialization.
955964
/// Initializations have been removed in the previous loop reporting unused variables.
956-
fn report_unused_assignments<'tcx>(
957-
self,
958-
tcx: TyCtxt<'tcx>,
959-
body_def_id: LocalDefId,
960-
checked_places: &PlaceSet<'tcx>,
961-
body: &Body<'tcx>,
962-
) {
963-
let typing_env = ty::TypingEnv::post_analysis(tcx, body.source.def_id());
965+
fn report_unused_assignments(self) {
966+
let tcx = self.tcx;
964967

965968
for (index, statements) in self.assignments.into_iter_enumerated() {
966969
if statements.is_empty() {
967970
continue;
968971
}
969972

970-
let Some((name, decl_span)) = checked_places.names[index] else { continue };
973+
let Some((name, decl_span)) = self.checked_places.names[index] else { continue };
971974

972975
// We have outstanding assignments and with non-trivial drop.
973976
// This is probably a drop-guard, so we do not issue a warning there.
974-
if maybe_drop_guard(tcx, typing_env, index, &self.ever_dropped, checked_places, body) {
977+
if maybe_drop_guard(
978+
tcx,
979+
self.typing_env,
980+
index,
981+
&self.ever_dropped,
982+
self.checked_places,
983+
self.body,
984+
) {
975985
continue;
976986
}
977987

@@ -983,18 +993,18 @@ impl AssignmentResult {
983993
}
984994

985995
// Report the dead assignment.
986-
let Some(hir_id) = source_info.scope.lint_root(&body.source_scopes) else {
996+
let Some(hir_id) = source_info.scope.lint_root(&self.body.source_scopes) else {
987997
continue;
988998
};
989999

9901000
match kind {
9911001
AccessKind::Assign => {
9921002
let suggestion = annotate_mut_binding_to_immutable_binding(
9931003
tcx,
994-
checked_places.places[index],
995-
body_def_id,
1004+
self.checked_places.places[index],
1005+
self.body.source.def_id().expect_local(),
9961006
source_info.span,
997-
body,
1007+
self.body,
9981008
);
9991009
tcx.emit_node_span_lint(
10001010
lint::builtin::UNUSED_ASSIGNMENTS,

0 commit comments

Comments
 (0)