Skip to content

Commit b10a86d

Browse files
committed
Merge the AggregateEq and StringEq test arms into a single case
1 parent d48c130 commit b10a86d

1 file changed

Lines changed: 16 additions & 54 deletions

File tree

  • compiler/rustc_mir_build/src/builder/matches

compiler/rustc_mir_build/src/builder/matches/test.rs

Lines changed: 16 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -140,85 +140,47 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
140140
self.cfg.terminate(block, self.source_info(match_start_span), terminator);
141141
}
142142

143-
TestKind::StringEq { value } => {
143+
TestKind::StringEq { value } | TestKind::AggregateEq { value } => {
144144
let tcx = self.tcx;
145145
let success_block = target_block(TestBranch::Success);
146146
let fail_block = target_block(TestBranch::Failure);
147147

148-
let ref_str_ty = Ty::new_imm_ref(tcx, tcx.lifetimes.re_erased, tcx.types.str_);
149-
assert!(ref_str_ty.is_imm_ref_str(), "{ref_str_ty:?}");
148+
let inner_ty = value.ty;
149+
let ref_ty = Ty::new_imm_ref(tcx, tcx.lifetimes.re_erased, inner_ty);
150150

151-
// The string constant we're testing against has type `str`, but
152-
// calling `<str as PartialEq>::eq` requires `&str` operands.
153-
//
154-
// Because `str` and `&str` have the same valtree representation,
155-
// we can "cast" to the desired type by just replacing the type.
156-
assert!(value.ty.is_str(), "unexpected value type for StringEq test: {value:?}");
157-
let expected_value = ty::Value { ty: ref_str_ty, valtree: value.valtree };
151+
// The constant we're testing against has type `str`, `[T; N]`, or `[T]`,
152+
// but calling `<T as PartialEq>::eq` requires a reference operand
153+
// (`&str`, `&[T; N]`, or `&[T]`). Valtree representations are the same
154+
// with or without the reference wrapper, so we can "cast" to the
155+
// desired type by just replacing the type.
156+
let expected_value = ty::Value { ty: ref_ty, valtree: value.valtree };
158157
let expected_value_operand =
159158
self.literal_operand(test.span, Const::from_ty_value(tcx, expected_value));
160159

161-
// Similarly, the scrutinized place has type `str`, but we need `&str`.
162-
// Get a reference by doing `let actual_value_ref_place: &str = &place`.
163-
let actual_value_ref_place = self.temp(ref_str_ty, test.span);
160+
// Similarly, the scrutinised place has the inner type, but we need a
161+
// reference. Get one by doing `let actual_value_ref_place = &place`.
162+
let actual_value_ref_place = self.temp(ref_ty, test.span);
164163
self.cfg.push_assign(
165164
block,
166165
self.source_info(test.span),
167166
actual_value_ref_place,
168167
Rvalue::Ref(tcx.lifetimes.re_erased, BorrowKind::Shared, place),
169168
);
170169

171-
// Compare two strings using `<str as std::cmp::PartialEq>::eq`.
172-
// (Interestingly this means that exhaustiveness analysis relies, for soundness,
173-
// on the `PartialEq` impl for `str` to be correct!)
170+
// Compare the two values using `<T as std::cmp::PartialEq>::eq`.
171+
// (Interestingly this means that, for `str`, exhaustiveness analysis
172+
// relies for soundness on the `PartialEq` impl for `str` to be correct!)
174173
self.non_scalar_compare(
175174
block,
176175
success_block,
177176
fail_block,
178177
source_info,
179-
tcx.types.str_,
178+
inner_ty,
180179
expected_value_operand,
181180
Operand::Copy(actual_value_ref_place),
182181
);
183182
}
184183

185-
TestKind::AggregateEq { value } => {
186-
let tcx = self.tcx;
187-
let success_block = target_block(TestBranch::Success);
188-
let fail_block = target_block(TestBranch::Failure);
189-
190-
let aggregate_ty = value.ty;
191-
let ref_ty = Ty::new_imm_ref(tcx, tcx.lifetimes.re_erased, aggregate_ty);
192-
193-
// The constant has type `[T; N]` (or `[T]`), but calling
194-
// `PartialEq::eq` requires `&[T; N]` (or `&[T]`) operands.
195-
// Valtree representations are the same with or without the
196-
// reference wrapper, so we can reinterpret by replacing the type.
197-
let expected_value = ty::Value { ty: ref_ty, valtree: value.valtree };
198-
let expected_operand =
199-
self.literal_operand(test.span, Const::from_ty_value(tcx, expected_value));
200-
201-
// Create a reference to the scrutinee place.
202-
let actual_ref_place = self.temp(ref_ty, test.span);
203-
self.cfg.push_assign(
204-
block,
205-
self.source_info(test.span),
206-
actual_ref_place,
207-
Rvalue::Ref(tcx.lifetimes.re_erased, BorrowKind::Shared, place),
208-
);
209-
210-
// Compare using `<T as PartialEq>::eq` where `T` is the array or slice type.
211-
self.non_scalar_compare(
212-
block,
213-
success_block,
214-
fail_block,
215-
source_info,
216-
aggregate_ty,
217-
expected_operand,
218-
Operand::Copy(actual_ref_place),
219-
);
220-
}
221-
222184
TestKind::ScalarEq { value } => {
223185
let tcx = self.tcx;
224186
let success_block = target_block(TestBranch::Success);

0 commit comments

Comments
 (0)