Intern valtree field vector

This commit is contained in:
Oli Scherer 2021-02-22 14:34:23 +00:00
parent a4fbac163e
commit 0fe4f38769
4 changed files with 23 additions and 9 deletions

View File

@ -789,7 +789,7 @@ rustc_queries! {
/// return `None` if that is not possible. /// return `None` if that is not possible.
query const_to_valtree( query const_to_valtree(
key: ty::ParamEnvAnd<'tcx, ConstAlloc<'tcx>> key: ty::ParamEnvAnd<'tcx, ConstAlloc<'tcx>>
) -> Option<ty::ValTree> { ) -> Option<ty::ValTree<'tcx>> {
desc { "destructure constant" } desc { "destructure constant" }
} }

View File

@ -333,6 +333,16 @@ impl<'tcx, D: TyDecoder<'tcx>> RefDecodable<'tcx, D> for ty::Const<'tcx> {
} }
} }
impl<'tcx, D: TyDecoder<'tcx>> RefDecodable<'tcx, D> for [ty::ValTree<'tcx>] {
fn decode(decoder: &mut D) -> Result<&'tcx Self, D::Error> {
Ok(decoder.tcx().arena.alloc_from_iter(
(0..decoder.read_usize()?)
.map(|_| Decodable::decode(decoder))
.collect::<Result<Vec<_>, _>>()?,
))
}
}
impl<'tcx, D: TyDecoder<'tcx>> RefDecodable<'tcx, D> for Allocation { impl<'tcx, D: TyDecoder<'tcx>> RefDecodable<'tcx, D> for Allocation {
fn decode(decoder: &mut D) -> Result<&'tcx Self, D::Error> { fn decode(decoder: &mut D) -> Result<&'tcx Self, D::Error> {
Ok(decoder.tcx().intern_const_alloc(Decodable::decode(decoder)?)) Ok(decoder.tcx().intern_const_alloc(Decodable::decode(decoder)?))

View File

@ -1,15 +1,15 @@
use super::ScalarInt; use super::ScalarInt;
use rustc_macros::HashStable; use rustc_macros::HashStable;
#[derive(Clone, Debug, Hash, TyEncodable, TyDecodable, Eq, PartialEq, Ord, PartialOrd)] #[derive(Copy, Clone, Debug, Hash, TyEncodable, TyDecodable, Eq, PartialEq, Ord, PartialOrd)]
#[derive(HashStable)] #[derive(HashStable)]
pub enum ValTree { pub enum ValTree<'tcx> {
Leaf(ScalarInt), Leaf(ScalarInt),
Branch(Vec<ValTree>), Branch(&'tcx [ValTree<'tcx>]),
} }
impl ValTree { impl ValTree<'tcx> {
pub fn zst() -> Self { pub fn zst() -> Self {
Self::Branch(Vec::new()) Self::Branch(&[])
} }
} }

View File

@ -43,7 +43,7 @@ pub(crate) fn const_to_valtree<'tcx>(
tcx: TyCtxt<'tcx>, tcx: TyCtxt<'tcx>,
param_env: ty::ParamEnv<'tcx>, param_env: ty::ParamEnv<'tcx>,
raw: ConstAlloc<'tcx>, raw: ConstAlloc<'tcx>,
) -> Option<ty::ValTree> { ) -> Option<ty::ValTree<'tcx>> {
let ecx = mk_eval_cx(tcx, DUMMY_SP, param_env, false); let ecx = mk_eval_cx(tcx, DUMMY_SP, param_env, false);
let place = ecx.raw_const_to_mplace(raw).unwrap(); let place = ecx.raw_const_to_mplace(raw).unwrap();
const_to_valtree_inner(&ecx, &place) const_to_valtree_inner(&ecx, &place)
@ -52,7 +52,7 @@ pub(crate) fn const_to_valtree<'tcx>(
fn const_to_valtree_inner<'tcx>( fn const_to_valtree_inner<'tcx>(
ecx: &CompileTimeEvalContext<'tcx, 'tcx>, ecx: &CompileTimeEvalContext<'tcx, 'tcx>,
place: &MPlaceTy<'tcx>, place: &MPlaceTy<'tcx>,
) -> Option<ty::ValTree> { ) -> Option<ty::ValTree<'tcx>> {
let branches = |n, variant| { let branches = |n, variant| {
let place = match variant { let place = match variant {
Some(variant) => ecx.mplace_downcast(&place, variant).unwrap(), Some(variant) => ecx.mplace_downcast(&place, variant).unwrap(),
@ -64,7 +64,11 @@ fn const_to_valtree_inner<'tcx>(
let field = ecx.mplace_field(&place, i).unwrap(); let field = ecx.mplace_field(&place, i).unwrap();
const_to_valtree_inner(ecx, &field) const_to_valtree_inner(ecx, &field)
}); });
Some(ty::ValTree::Branch(variant.into_iter().chain(fields).collect::<Option<_>>()?)) Some(ty::ValTree::Branch(
ecx.tcx
.arena
.alloc_from_iter(variant.into_iter().chain(fields).collect::<Option<Vec<_>>>()?),
))
}; };
match place.layout.ty.kind() { match place.layout.ty.kind() {
ty::FnDef(..) => Some(ty::ValTree::zst()), ty::FnDef(..) => Some(ty::ValTree::zst()),