1
Fork 0

rustc: slightly optimize make_mono_id to not clone lots of vectors.

This commit is contained in:
Eduard Burtescu 2014-04-20 19:09:11 +03:00
parent c709c1efc6
commit 5fa7be659c
3 changed files with 65 additions and 69 deletions

View file

@ -690,6 +690,7 @@ pub fn is_null(val: ValueRef) -> bool {
#[deriving(Eq, TotalEq, Hash)] #[deriving(Eq, TotalEq, Hash)]
pub struct MonoParamId { pub struct MonoParamId {
pub subst: ty::t, pub subst: ty::t,
// Do we really need the vtables to be hashed? Isn't the type enough?
pub vtables: Vec<mono_id> pub vtables: Vec<mono_id>
} }

View file

@ -427,29 +427,6 @@ pub fn trans_trait_callee_from_llval<'a>(bcx: &'a Block<'a>,
}; };
} }
pub fn vtable_id(ccx: &CrateContext,
origin: &typeck::vtable_origin)
-> mono_id {
match origin {
&typeck::vtable_static(impl_id, ref substs, ref sub_vtables) => {
let psubsts = param_substs {
tys: (*substs).clone(),
vtables: Some(sub_vtables.clone()),
self_ty: None,
self_vtables: None
};
monomorphize::make_mono_id(
ccx,
impl_id,
&psubsts)
}
// can't this be checked at the callee?
_ => fail!("vtable_id")
}
}
/// Creates a returns a dynamic vtable for the given type and vtable origin. /// Creates a returns a dynamic vtable for the given type and vtable origin.
/// This is used only for objects. /// This is used only for objects.
fn get_vtable(bcx: &Block, fn get_vtable(bcx: &Block,
@ -460,7 +437,7 @@ fn get_vtable(bcx: &Block,
let _icx = push_ctxt("meth::get_vtable"); let _icx = push_ctxt("meth::get_vtable");
// Check the cache. // Check the cache.
let hash_id = (self_ty, vtable_id(ccx, origins.get(0))); let hash_id = (self_ty, monomorphize::make_vtable_id(ccx, origins.get(0)));
match ccx.vtables.borrow().find(&hash_id) { match ccx.vtables.borrow().find(&hash_id) {
Some(&val) => { return val } Some(&val) => { return val }
None => { } None => { }

View file

@ -47,28 +47,34 @@ pub fn monomorphic_fn(ccx: &CrateContext,
self_vtables.repr(ccx.tcx()), self_vtables.repr(ccx.tcx()),
ref_id); ref_id);
assert!(real_substs.tps.iter().all(|t| !ty::type_needs_infer(*t))); assert!(real_substs.tps.iter().all(|t| {
!ty::type_needs_infer(*t) && !ty::type_has_params(*t)
}));
let _icx = push_ctxt("monomorphic_fn"); let _icx = push_ctxt("monomorphic_fn");
let psubsts = @param_substs { let substs_iter = real_substs.self_ty.iter().chain(real_substs.tps.iter());
tys: real_substs.tps.clone(), let param_ids: Vec<MonoParamId> = match vtables {
vtables: vtables, Some(ref vts) => {
self_ty: real_substs.self_ty.clone(), debug!("make_mono_id vtables={} psubsts={}",
self_vtables: self_vtables vts.repr(ccx.tcx()), real_substs.tps.repr(ccx.tcx()));
let vts_iter = self_vtables.iter().chain(vts.iter());
vts_iter.zip(substs_iter).map(|(vtable, subst)| MonoParamId {
subst: *subst,
// Do we really need the vtables to be hashed? Isn't the type enough?
vtables: vtable.iter().map(|vt| make_vtable_id(ccx, vt)).collect()
}).collect()
}
None => substs_iter.map(|subst| MonoParamId {
subst: *subst,
vtables: Vec::new()
}).collect()
}; };
for s in real_substs.tps.iter() { assert!(!ty::type_has_params(*s)); } let hash_id = @mono_id_ {
for s in psubsts.tys.iter() { assert!(!ty::type_has_params(*s)); } def: fn_id,
params: param_ids
let hash_id = make_mono_id(ccx, fn_id, &*psubsts); };
debug!("monomorphic_fn(\
fn_id={}, \
psubsts={}, \
hash_id={:?})",
fn_id.repr(ccx.tcx()),
psubsts.repr(ccx.tcx()),
hash_id);
match ccx.monomorphized.borrow().find(&hash_id) { match ccx.monomorphized.borrow().find(&hash_id) {
Some(&val) => { Some(&val) => {
@ -79,6 +85,21 @@ pub fn monomorphic_fn(ccx: &CrateContext,
None => () None => ()
} }
let psubsts = @param_substs {
tys: real_substs.tps.clone(),
vtables: vtables,
self_ty: real_substs.self_ty.clone(),
self_vtables: self_vtables
};
debug!("monomorphic_fn(\
fn_id={}, \
psubsts={}, \
hash_id={:?})",
fn_id.repr(ccx.tcx()),
psubsts.repr(ccx.tcx()),
hash_id);
let tpt = ty::lookup_item_type(ccx.tcx(), fn_id); let tpt = ty::lookup_item_type(ccx.tcx(), fn_id);
let llitem_ty = tpt.ty; let llitem_ty = tpt.ty;
@ -117,8 +138,8 @@ pub fn monomorphic_fn(ccx: &CrateContext,
debug!("monomorphic_fn about to subst into {}", llitem_ty.repr(ccx.tcx())); debug!("monomorphic_fn about to subst into {}", llitem_ty.repr(ccx.tcx()));
let mono_ty = match is_static_provided { let mono_ty = match is_static_provided {
None => ty::subst_tps(ccx.tcx(), psubsts.tys.as_slice(), None => ty::subst_tps(ccx.tcx(), real_substs.tps.as_slice(),
psubsts.self_ty, llitem_ty), real_substs.self_ty, llitem_ty),
Some(num_method_ty_params) => { Some(num_method_ty_params) => {
// Static default methods are a little unfortunate, in // Static default methods are a little unfortunate, in
// that the "internal" and "external" type of them differ. // that the "internal" and "external" type of them differ.
@ -134,9 +155,9 @@ pub fn monomorphic_fn(ccx: &CrateContext,
// stick a substitution for the self type in. // stick a substitution for the self type in.
// This is a bit unfortunate. // This is a bit unfortunate.
let idx = psubsts.tys.len() - num_method_ty_params; let idx = real_substs.tps.len() - num_method_ty_params;
let substs = psubsts.tys.slice(0, idx) + let substs = real_substs.tps.slice(0, idx) +
&[psubsts.self_ty.unwrap()] + psubsts.tys.tailn(idx); &[real_substs.self_ty.unwrap()] + real_substs.tps.tailn(idx);
debug!("static default: changed substitution to {}", debug!("static default: changed substitution to {}",
substs.repr(ccx.tcx())); substs.repr(ccx.tcx()));
@ -284,28 +305,25 @@ pub fn monomorphic_fn(ccx: &CrateContext,
(lldecl, false) (lldecl, false)
} }
pub fn make_mono_id(ccx: &CrateContext, pub fn make_vtable_id(ccx: &CrateContext,
item: ast::DefId, origin: &typeck::vtable_origin)
substs: &param_substs) -> mono_id { -> mono_id {
let substs_iter = substs.self_ty.iter().chain(substs.tys.iter()); match origin {
let param_ids: Vec<MonoParamId> = match substs.vtables { &typeck::vtable_static(impl_id, ref substs, ref sub_vtables) => {
Some(ref vts) => { let param_ids = sub_vtables.iter().zip(substs.iter()).map(|(vtable, subst)| {
debug!("make_mono_id vtables={} substs={}", MonoParamId {
vts.repr(ccx.tcx()), substs.tys.repr(ccx.tcx())); subst: *subst,
let vts_iter = substs.self_vtables.iter().chain(vts.iter()); vtables: vtable.iter().map(|vt| make_vtable_id(ccx, vt)).collect()
vts_iter.zip(substs_iter).map(|(vtable, subst)| MonoParamId { }
subst: *subst, }).collect();
vtables: vtable.iter().map(|vt| meth::vtable_id(ccx, vt)).collect()
}).collect()
}
None => substs_iter.map(|subst| MonoParamId {
subst: *subst,
vtables: Vec::new()
}).collect()
};
@mono_id_ { @mono_id_ {
def: item, def: impl_id,
params: param_ids params: param_ids
}
}
// can't this be checked at the callee?
_ => fail!("make_vtable_id needs vtable_static")
} }
} }