Skip to content
This repository was archived by the owner on May 28, 2025. It is now read-only.

Commit 06947be

Browse files
committed
valtree_to_const_value: add fast-path for Scalar tuples/structs
1 parent 3aedb85 commit 06947be

File tree

1 file changed

+16
-1
lines changed

1 file changed

+16
-1
lines changed

compiler/rustc_const_eval/src/const_eval/valtrees.rs

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ use crate::interpret::{
77
intern_const_alloc_recursive, ConstValue, ImmTy, Immediate, InternKind, MemPlaceMeta,
88
MemoryKind, PlaceTy, Projectable, Scalar,
99
};
10-
use rustc_middle::ty::layout::{LayoutOf, TyAndLayout};
10+
use rustc_middle::ty::layout::{LayoutCx, LayoutOf, TyAndLayout};
1111
use rustc_middle::ty::{self, ScalarInt, Ty, TyCtxt};
1212
use rustc_span::source_map::DUMMY_SP;
1313
use rustc_target::abi::VariantIdx;
@@ -239,6 +239,21 @@ pub fn valtree_to_const_value<'tcx>(
239239
// Fast path to avoid some allocations.
240240
return ConstValue::ZeroSized;
241241
}
242+
if layout.abi.is_scalar()
243+
&& (matches!(ty.kind(), ty::Tuple(_))
244+
|| matches!(ty.kind(), ty::Adt(def, _) if def.is_struct()))
245+
{
246+
// A Scalar tuple/struct; we can avoid creating an allocation.
247+
let branches = valtree.unwrap_branch();
248+
// Find the non-ZST field. (There can be aligned ZST!)
249+
for (i, &inner_valtree) in branches.iter().enumerate() {
250+
let field = layout.field(&LayoutCx { tcx, param_env }, i);
251+
if !field.is_zst() {
252+
return valtree_to_const_value(tcx, param_env.and(field.ty), inner_valtree);
253+
}
254+
}
255+
bug!("could not find non-ZST field during in {layout:#?}");
256+
}
242257

243258
let mut ecx = mk_eval_cx(tcx, DUMMY_SP, param_env, CanAccessStatics::No);
244259

0 commit comments

Comments
 (0)