From fe0c119e7da2e9b068dd54bb88e8acb23d31bfa4 Mon Sep 17 00:00:00 2001 From: varkor Date: Thu, 8 Mar 2018 10:39:31 +0000 Subject: [PATCH 01/40] Consolidate ty::Generics --- src/librustc/hir/lowering.rs | 2 +- src/librustc/ich/impls_ty.rs | 17 ++--- src/librustc/infer/anon_types/mod.rs | 2 +- src/librustc/middle/resolve_lifetime.rs | 2 +- src/librustc/traits/error_reporting.rs | 2 +- src/librustc/traits/object_safety.rs | 2 +- src/librustc/traits/on_unimplemented.rs | 4 +- src/librustc/ty/mod.rs | 73 +++++++++++++++++--- src/librustc/ty/subst.rs | 31 +++++---- src/librustc/util/ppaux.rs | 14 ++-- src/librustc_metadata/encoder.rs | 2 +- src/librustc_mir/monomorphize/collector.rs | 4 +- src/librustc_mir/transform/check_unsafety.rs | 2 +- src/librustc_privacy/lib.rs | 4 +- src/librustc_trans/debuginfo/mod.rs | 2 +- src/librustc_typeck/astconv.rs | 8 +-- src/librustc_typeck/check/compare_method.rs | 10 +-- src/librustc_typeck/check/intrinsic.rs | 4 +- src/librustc_typeck/check/method/confirm.rs | 2 +- src/librustc_typeck/check/method/mod.rs | 3 +- src/librustc_typeck/check/method/probe.rs | 6 +- src/librustc_typeck/check/mod.rs | 26 +++---- src/librustc_typeck/check/wfcheck.rs | 10 +-- src/librustc_typeck/collect.rs | 17 +++-- src/librustc_typeck/impl_wf_check.rs | 4 +- src/librustdoc/clean/auto_trait.rs | 40 +++++------ src/librustdoc/clean/mod.rs | 19 +++-- 27 files changed, 186 insertions(+), 126 deletions(-) diff --git a/src/librustc/hir/lowering.rs b/src/librustc/hir/lowering.rs index 51f0c1d7047c9..e05c686f39fcc 100644 --- a/src/librustc/hir/lowering.rs +++ b/src/librustc/hir/lowering.rs @@ -1461,7 +1461,7 @@ impl<'a> LoweringContext<'a> { assert!(!def_id.is_local()); let n = self.cstore .item_generics_cloned_untracked(def_id, self.sess) - .regions + .lifetimes() .len(); self.type_def_lifetime_params.insert(def_id, n); n diff --git a/src/librustc/ich/impls_ty.rs b/src/librustc/ich/impls_ty.rs index 1036eae9b856b..c7f0979766cf6 100644 --- a/src/librustc/ich/impls_ty.rs +++ b/src/librustc/ich/impls_ty.rs @@ -735,10 +735,8 @@ impl<'a> HashStable> for ty::Generics { hasher: &mut StableHasher) { let ty::Generics { parent, - parent_regions, - parent_types, - ref regions, - ref types, + ref parent_parameters, + ref parameters, // Reverse map to each `TypeParameterDef`'s `index` field, from // `def_id.index` (`def_id.krate` is the same as the item's). @@ -748,15 +746,18 @@ impl<'a> HashStable> for ty::Generics { } = *self; parent.hash_stable(hcx, hasher); - parent_regions.hash_stable(hcx, hasher); - parent_types.hash_stable(hcx, hasher); - regions.hash_stable(hcx, hasher); - types.hash_stable(hcx, hasher); + parent_parameters.hash_stable(hcx, hasher); + parameters.hash_stable(hcx, hasher); has_self.hash_stable(hcx, hasher); has_late_bound_regions.hash_stable(hcx, hasher); } } +impl_stable_hash_for!(enum ty::GenericParameterDef { + Lifetime(lt), + Type(ty) +}); + impl<'a> HashStable> for ty::RegionParameterDef { fn hash_stable(&self, diff --git a/src/librustc/infer/anon_types/mod.rs b/src/librustc/infer/anon_types/mod.rs index 725ea9734abf4..9cf55e85693a4 100644 --- a/src/librustc/infer/anon_types/mod.rs +++ b/src/librustc/infer/anon_types/mod.rs @@ -313,7 +313,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { // `['a]` for the first impl trait and `'b` for the // second. let mut least_region = None; - for region_def in &abstract_type_generics.regions { + for region_def in abstract_type_generics.lifetimes() { // Find the index of this region in the list of substitutions. let index = region_def.index as usize; diff --git a/src/librustc/middle/resolve_lifetime.rs b/src/librustc/middle/resolve_lifetime.rs index 8c19a19523275..8f44507035af3 100644 --- a/src/librustc/middle/resolve_lifetime.rs +++ b/src/librustc/middle/resolve_lifetime.rs @@ -1659,7 +1659,7 @@ impl<'a, 'tcx> LifetimeContext<'a, 'tcx> { .entry(def_id) .or_insert_with(|| { tcx.generics_of(def_id) - .types + .types() .iter() .map(|def| def.object_lifetime_default) .collect() diff --git a/src/librustc/traits/error_reporting.rs b/src/librustc/traits/error_reporting.rs index 25be4a2ff5c8b..dfe0cd6900e7a 100644 --- a/src/librustc/traits/error_reporting.rs +++ b/src/librustc/traits/error_reporting.rs @@ -378,7 +378,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { flags.push(("_Self".to_string(), Some(self.tcx.type_of(def.did).to_string()))); } - for param in generics.types.iter() { + for param in generics.types().iter() { let name = param.name.to_string(); let ty = trait_ref.substs.type_for_def(param); let ty_str = ty.to_string(); diff --git a/src/librustc/traits/object_safety.rs b/src/librustc/traits/object_safety.rs index c0d5a337cee3a..10228c5783c56 100644 --- a/src/librustc/traits/object_safety.rs +++ b/src/librustc/traits/object_safety.rs @@ -284,7 +284,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { } // We can't monomorphize things like `fn foo(...)`. - if !self.generics_of(method.def_id).types.is_empty() { + if !self.generics_of(method.def_id).types().is_empty() { return Some(MethodViolationCode::Generic); } diff --git a/src/librustc/traits/on_unimplemented.rs b/src/librustc/traits/on_unimplemented.rs index 3cf7af30b3d55..b2fc2c171063f 100644 --- a/src/librustc/traits/on_unimplemented.rs +++ b/src/librustc/traits/on_unimplemented.rs @@ -243,7 +243,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let name = tcx.item_name(trait_def_id); let generics = tcx.generics_of(trait_def_id); let parser = Parser::new(&self.0); - let types = &generics.types; + let types = generics.types(); let mut result = Ok(()); for token in parser { match token { @@ -288,7 +288,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let name = tcx.item_name(trait_ref.def_id); let trait_str = tcx.item_path_str(trait_ref.def_id); let generics = tcx.generics_of(trait_ref.def_id); - let generic_map = generics.types.iter().map(|param| { + let generic_map = generics.types().iter().map(|param| { (param.name.to_string(), trait_ref.substs.type_for_def(param).to_string()) }).collect::>(); diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index eede7bd2ea619..f32316ac54723 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -757,6 +757,21 @@ impl ty::EarlyBoundRegion { } } +#[derive(Clone, Debug, RustcEncodable, RustcDecodable)] +pub enum GenericParameterDef { + Lifetime(RegionParameterDef), + Type(TypeParameterDef), +} + +impl GenericParameterDef { + pub fn index(&self) -> u32 { + match self { + GenericParameterDef::Lifetime(lt) => lt.index, + GenericParameterDef::Type(ty) => ty.index, + } + } +} + /// Information about the formal type/lifetime parameters associated /// with an item or method. Analogous to hir::Generics. /// @@ -769,10 +784,8 @@ impl ty::EarlyBoundRegion { #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] pub struct Generics { pub parent: Option, - pub parent_regions: u32, - pub parent_types: u32, - pub regions: Vec, - pub types: Vec, + pub parent_parameters: Vec, + pub parameters: Vec, /// Reverse map to each `TypeParameterDef`'s `index` field pub type_param_to_index: FxHashMap, @@ -783,24 +796,56 @@ pub struct Generics { impl<'a, 'gcx, 'tcx> Generics { pub fn parent_count(&self) -> usize { - self.parent_regions as usize + self.parent_types as usize + self.parent_parameters.iter().map(|&x| x as usize).sum() } pub fn own_count(&self) -> usize { - self.regions.len() + self.types.len() + self.parameters.len() } pub fn count(&self) -> usize { self.parent_count() + self.own_count() } + pub fn lifetimes(&self) -> Vec<&RegionParameterDef> { + self.parameters.iter().filter_map(|p| { + if let GenericParameterDef::Lifetime(lt) = p { + Some(lt) + } else { + None + } + }).collect() + } + + pub fn types(&self) -> Vec<&TypeParameterDef> { + self.parameters.iter().filter_map(|p| { + if let GenericParameterDef::Type(ty) = p { + Some(ty) + } else { + None + } + }).collect() + } + + pub fn parent_lifetimes(&self) -> u32 { + self.parent_parameters[0] + } + + pub fn parent_types(&self) -> u32 { + self.parent_parameters[1] + } + pub fn region_param(&'tcx self, param: &EarlyBoundRegion, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> &'tcx RegionParameterDef { if let Some(index) = param.index.checked_sub(self.parent_count() as u32) { - &self.regions[index as usize - self.has_self as usize] + // We're currently assuming that lifetimes precede other generic parameters. + match self.parameters[index as usize - self.has_self as usize] { + ty::GenericParameterDef::Lifetime(ref lt) => lt, + _ => bug!("expected region parameter, but found another generic parameter") + } } else { tcx.generics_of(self.parent.expect("parent_count>0 but no parent?")) .region_param(param, tcx) @@ -840,17 +885,23 @@ impl<'a, 'gcx, 'tcx> Generics { // And it can be seen that in both cases, to move from a substs // offset to a generics offset you just have to offset by the // number of regions. - let type_param_offset = self.regions.len(); + let type_param_offset = self.lifetimes().len(); let has_self = self.has_self && self.parent.is_none(); let is_separated_self = type_param_offset != 0 && idx == 0 && has_self; - if let Some(idx) = (idx as usize).checked_sub(type_param_offset) { + if let Some(_) = (idx as usize).checked_sub(type_param_offset) { assert!(!is_separated_self, "found a Self after type_param_offset"); - &self.types[idx] + match self.parameters[idx as usize] { + ty::GenericParameterDef::Type(ref ty) => ty, + _ => bug!("expected type parameter, but found another generic parameter") + } } else { assert!(is_separated_self, "non-Self param before type_param_offset"); - &self.types[0] + match self.parameters[type_param_offset] { + ty::GenericParameterDef::Type(ref ty) => ty, + _ => bug!("expected type parameter, but found another generic parameter") + } } } else { tcx.generics_of(self.parent.expect("parent_count>0 but no parent?")) diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index e7b58ae1564aa..fa2aa9720064a 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -242,24 +242,31 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, FT: FnMut(&ty::TypeParameterDef, &[Kind<'tcx>]) -> Ty<'tcx> { // Handle Self first, before all regions. - let mut types = defs.types.iter(); - if defs.parent.is_none() && defs.has_self { + let types = defs.types(); + let mut types = types.iter(); + let mut skip_self = defs.parent.is_none() && defs.has_self; + if skip_self { let def = types.next().unwrap(); let ty = mk_type(def, substs); assert_eq!(def.index as usize, substs.len()); substs.push(ty.into()); } - for def in &defs.regions { - let region = mk_region(def, substs); - assert_eq!(def.index as usize, substs.len()); - substs.push(Kind::from(region)); - } - - for def in types { - let ty = mk_type(def, substs); - assert_eq!(def.index as usize, substs.len()); - substs.push(Kind::from(ty)); + for def in &defs.parameters { + let param = match def { + ty::GenericParameterDef::Lifetime(ref lt) => { + UnpackedKind::Lifetime(mk_region(lt, substs)) + } + ty::GenericParameterDef::Type(ref ty) => { + if skip_self { + skip_self = false; + continue + } + UnpackedKind::Type(mk_type(ty, substs)) + } + }; + assert_eq!(def.index() as usize, substs.len()); + substs.push(param.pack()); } } diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index a6eb468e33836..5b287e416297b 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -310,10 +310,10 @@ impl PrintContext { if let Some(def_id) = generics.parent { // Methods. assert!(is_value_path); - child_types = generics.types.len(); + child_types = generics.types().len(); generics = tcx.generics_of(def_id); - num_regions = generics.regions.len(); - num_types = generics.types.len(); + num_regions = generics.lifetimes().len(); + num_types = generics.types().len(); if has_self { print!(f, self, write("<"), print_display(substs.type_at(0)), write(" as "))?; @@ -328,16 +328,16 @@ impl PrintContext { assert_eq!(has_self, false); } else { // Types and traits. - num_regions = generics.regions.len(); - num_types = generics.types.len(); + num_regions = generics.lifetimes().len(); + num_types = generics.types().len(); } } if !verbose { - if generics.types.last().map_or(false, |def| def.has_default) { + if generics.types().last().map_or(false, |def| def.has_default) { if let Some(substs) = tcx.lift(&substs) { let tps = substs.types().rev().skip(child_types); - for (def, actual) in generics.types.iter().rev().zip(tps) { + for (def, actual) in generics.types().iter().rev().zip(tps) { if !def.has_default { break; } diff --git a/src/librustc_metadata/encoder.rs b/src/librustc_metadata/encoder.rs index d7a06f7932fef..7e580e9333ff0 100644 --- a/src/librustc_metadata/encoder.rs +++ b/src/librustc_metadata/encoder.rs @@ -929,7 +929,7 @@ impl<'a, 'b: 'a, 'tcx: 'b> IsolatedEncoder<'a, 'b, 'tcx> { hir::ImplItemKind::Const(..) => true, hir::ImplItemKind::Method(ref sig, _) => { let generics = self.tcx.generics_of(def_id); - let types = generics.parent_types as usize + generics.types.len(); + let types = generics.parent_types() as usize + generics.types().len(); let needs_inline = (types > 0 || tcx.trans_fn_attrs(def_id).requests_inline()) && !self.metadata_output_only(); diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index e690e8ee88066..bfdf81588afdc 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -1076,7 +1076,7 @@ impl<'b, 'a, 'v> RootCollector<'b, 'a, 'v> { fn item_has_type_parameters<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> bool { let generics = tcx.generics_of(def_id); - generics.parent_types as usize + generics.types.len() > 0 + generics.parent_types() as usize + generics.types().len() > 0 } fn create_mono_items_for_default_impls<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, @@ -1108,7 +1108,7 @@ fn create_mono_items_for_default_impls<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, continue; } - if !tcx.generics_of(method.def_id).types.is_empty() { + if !tcx.generics_of(method.def_id).types().is_empty() { continue; } diff --git a/src/librustc_mir/transform/check_unsafety.rs b/src/librustc_mir/transform/check_unsafety.rs index 2bf5a49c97e8f..1e8707157f75a 100644 --- a/src/librustc_mir/transform/check_unsafety.rs +++ b/src/librustc_mir/transform/check_unsafety.rs @@ -357,7 +357,7 @@ fn unsafe_derive_on_repr_packed<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: D // FIXME: when we make this a hard error, this should have its // own error code. - let message = if !tcx.generics_of(def_id).types.is_empty() { + let message = if !tcx.generics_of(def_id).types().is_empty() { format!("#[derive] can't be used on a #[repr(packed)] struct with \ type parameters (error E0133)") } else { diff --git a/src/librustc_privacy/lib.rs b/src/librustc_privacy/lib.rs index 42031d9cc5630..445717ac60081 100644 --- a/src/librustc_privacy/lib.rs +++ b/src/librustc_privacy/lib.rs @@ -399,7 +399,7 @@ impl<'a, 'tcx> Visitor<'tcx> for EmbargoVisitor<'a, 'tcx> { impl<'b, 'a, 'tcx> ReachEverythingInTheInterfaceVisitor<'b, 'a, 'tcx> { fn generics(&mut self) -> &mut Self { - for def in &self.ev.tcx.generics_of(self.item_def_id).types { + for def in &self.ev.tcx.generics_of(self.item_def_id).types() { if def.has_default { self.ev.tcx.type_of(def.def_id).visit_with(self); } @@ -1335,7 +1335,7 @@ struct SearchInterfaceForPrivateItemsVisitor<'a, 'tcx: 'a> { impl<'a, 'tcx: 'a> SearchInterfaceForPrivateItemsVisitor<'a, 'tcx> { fn generics(&mut self) -> &mut Self { - for def in &self.tcx.generics_of(self.item_def_id).types { + for def in &self.tcx.generics_of(self.item_def_id).types() { if def.has_default { self.tcx.type_of(def.def_id).visit_with(self); } diff --git a/src/librustc_trans/debuginfo/mod.rs b/src/librustc_trans/debuginfo/mod.rs index 30676b91620a6..be9aa49c100a8 100644 --- a/src/librustc_trans/debuginfo/mod.rs +++ b/src/librustc_trans/debuginfo/mod.rs @@ -417,7 +417,7 @@ pub fn create_function_debug_context<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>, let mut names = generics.parent.map_or(vec![], |def_id| { get_type_parameter_names(cx, cx.tcx.generics_of(def_id)) }); - names.extend(generics.types.iter().map(|param| param.name)); + names.extend(generics.types().iter().map(|param| param.name)); names } diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index d307ef30044e1..4286946599a7c 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -209,7 +209,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { // whatever & would get replaced with). let decl_generics = tcx.generics_of(def_id); let num_types_provided = parameters.types.len(); - let expected_num_region_params = decl_generics.regions.len(); + let expected_num_region_params = decl_generics.lifetimes().len(); let supplied_num_region_params = parameters.lifetimes.len(); if expected_num_region_params != supplied_num_region_params { report_lifetime_number_error(tcx, span, @@ -221,7 +221,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { assert_eq!(decl_generics.has_self, self_ty.is_some()); // Check the number of type parameters supplied by the user. - let ty_param_defs = &decl_generics.types[self_ty.is_some() as usize..]; + let ty_param_defs = &decl_generics.types()[self_ty.is_some() as usize..]; if !infer_types || num_types_provided > ty_param_defs.len() { check_type_argument_count(tcx, span, num_types_provided, ty_param_defs); } @@ -254,7 +254,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { return ty; } - let i = i - self_ty.is_some() as usize - decl_generics.regions.len(); + let i = i - self_ty.is_some() as usize - decl_generics.lifetimes().len(); if i < num_types_provided { // A provided type parameter. self.ast_ty_to_ty(¶meters.types[i]) @@ -1300,7 +1300,7 @@ fn split_auto_traits<'a, 'b, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, } fn check_type_argument_count(tcx: TyCtxt, span: Span, supplied: usize, - ty_param_defs: &[ty::TypeParameterDef]) { + ty_param_defs: &[&ty::TypeParameterDef]) { let accepted = ty_param_defs.len(); let required = ty_param_defs.iter().take_while(|x| !x.has_default).count(); if supplied < required { diff --git a/src/librustc_typeck/check/compare_method.rs b/src/librustc_typeck/check/compare_method.rs index 91264849cadf8..1dce514023a59 100644 --- a/src/librustc_typeck/check/compare_method.rs +++ b/src/librustc_typeck/check/compare_method.rs @@ -357,8 +357,8 @@ fn check_region_bounds_on_impl_method<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, trait_to_skol_substs: &Substs<'tcx>) -> Result<(), ErrorReported> { let span = tcx.sess.codemap().def_span(span); - let trait_params = &trait_generics.regions[..]; - let impl_params = &impl_generics.regions[..]; + let trait_params = trait_generics.lifetimes(); + let impl_params = impl_generics.lifetimes(); debug!("check_region_bounds_on_impl_method: \ trait_generics={:?} \ @@ -574,8 +574,8 @@ fn compare_number_of_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, -> Result<(), ErrorReported> { let impl_m_generics = tcx.generics_of(impl_m.def_id); let trait_m_generics = tcx.generics_of(trait_m.def_id); - let num_impl_m_type_params = impl_m_generics.types.len(); - let num_trait_m_type_params = trait_m_generics.types.len(); + let num_impl_m_type_params = impl_m_generics.types().len(); + let num_trait_m_type_params = trait_m_generics.types().len(); if num_impl_m_type_params != num_trait_m_type_params { let impl_m_node_id = tcx.hir.as_local_node_id(impl_m.def_id).unwrap(); let impl_m_item = tcx.hir.expect_impl_item(impl_m_node_id); @@ -728,7 +728,7 @@ fn compare_synthetic_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let mut error_found = false; let impl_m_generics = tcx.generics_of(impl_m.def_id); let trait_m_generics = tcx.generics_of(trait_m.def_id); - for (impl_ty, trait_ty) in impl_m_generics.types.iter().zip(trait_m_generics.types.iter()) { + for (impl_ty, trait_ty) in impl_m_generics.types().iter().zip(trait_m_generics.types().iter()) { if impl_ty.synthetic != trait_ty.synthetic { let impl_node_id = tcx.hir.as_local_node_id(impl_ty.def_id).unwrap(); let impl_span = tcx.hir.span(impl_node_id); diff --git a/src/librustc_typeck/check/intrinsic.rs b/src/librustc_typeck/check/intrinsic.rs index fcf7541a159b0..50a3cab6d2bb0 100644 --- a/src/librustc_typeck/check/intrinsic.rs +++ b/src/librustc_typeck/check/intrinsic.rs @@ -45,7 +45,7 @@ fn equate_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } } - let i_n_tps = tcx.generics_of(def_id).types.len(); + let i_n_tps = tcx.generics_of(def_id).types().len(); if i_n_tps != n_tps { let span = match it.node { hir::ForeignItemFn(_, _, ref generics) => generics.span, @@ -346,7 +346,7 @@ pub fn check_platform_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }; let def_id = tcx.hir.local_def_id(it.id); - let i_n_tps = tcx.generics_of(def_id).types.len(); + let i_n_tps = tcx.generics_of(def_id).types().len(); let name = it.name.as_str(); let (n_tps, inputs, output) = match &*name { diff --git a/src/librustc_typeck/check/method/confirm.rs b/src/librustc_typeck/check/method/confirm.rs index 46288181037f4..3accb51f3087e 100644 --- a/src/librustc_typeck/check/method/confirm.rs +++ b/src/librustc_typeck/check/method/confirm.rs @@ -332,7 +332,7 @@ impl<'a, 'gcx, 'tcx> ConfirmContext<'a, 'gcx, 'tcx> { parent_substs.type_at(i) } else if let Some(ast_ty) = provided.as_ref().and_then(|p| { - p.types.get(i - parent_substs.len() - method_generics.regions.len()) + p.types.get(i - parent_substs.len() - method_generics.lifetimes().len()) }) { self.to_ty(ast_ty) diff --git a/src/librustc_typeck/check/method/mod.rs b/src/librustc_typeck/check/method/mod.rs index 5f904a9419b1d..8d7d8cb0f5f66 100644 --- a/src/librustc_typeck/check/method/mod.rs +++ b/src/librustc_typeck/check/method/mod.rs @@ -288,8 +288,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { let method_item = self.associated_item(trait_def_id, m_name, Namespace::Value).unwrap(); let def_id = method_item.def_id; let generics = tcx.generics_of(def_id); - assert_eq!(generics.types.len(), 0); - assert_eq!(generics.regions.len(), 0); + assert_eq!(generics.parameters.len(), 0); debug!("lookup_in_trait_adjusted: method_item={:?}", method_item); let mut obligations = vec![]; diff --git a/src/librustc_typeck/check/method/probe.rs b/src/librustc_typeck/check/method/probe.rs index e45565c2f5220..d3335fdd9807e 100644 --- a/src/librustc_typeck/check/method/probe.rs +++ b/src/librustc_typeck/check/method/probe.rs @@ -1378,14 +1378,14 @@ impl<'a, 'gcx, 'tcx> ProbeContext<'a, 'gcx, 'tcx> { // method yet. So create fresh variables here for those too, // if there are any. let generics = self.tcx.generics_of(method); - assert_eq!(substs.types().count(), generics.parent_types as usize); - assert_eq!(substs.regions().count(), generics.parent_regions as usize); + assert_eq!(substs.regions().count(), generics.parent_lifetimes() as usize); + assert_eq!(substs.types().count(), generics.parent_types() as usize); // Erase any late-bound regions from the method and substitute // in the values from the substitution. let xform_fn_sig = self.erase_late_bound_regions(&fn_sig); - if generics.types.is_empty() && generics.regions.is_empty() { + if generics.parameters.is_empty() { xform_fn_sig.subst(self.tcx, substs) } else { let substs = Substs::for_item(self.tcx, method, |def, _| { diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index b4a7de7b8443c..1faf1f7e88286 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -1239,7 +1239,7 @@ pub fn check_item_type<'a,'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, it: &'tcx hir::Item } else { for item in &m.items { let generics = tcx.generics_of(tcx.hir.local_def_id(item.id)); - if !generics.types.is_empty() { + if !generics.types().is_empty() { let mut err = struct_span_err!(tcx.sess, item.span, E0044, "foreign items may not have type parameters"); err.span_label(item.span, "can't have type parameters"); @@ -4799,7 +4799,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // Skip over the lifetimes in the same segment. if let Some((_, generics)) = segment { - i -= generics.regions.len(); + i -= generics.lifetimes().len(); } if let Some(ast_ty) = types.get(i) { @@ -4918,11 +4918,11 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { }; // Check provided type parameters. - let type_defs = segment.map_or(&[][..], |(_, generics)| { + let type_defs = segment.map_or(vec![], |(_, generics)| { if generics.parent.is_none() { - &generics.types[generics.has_self as usize..] + generics.types()[generics.has_self as usize..].to_vec() } else { - &generics.types + generics.types() } }); let required_len = type_defs.iter().take_while(|d| !d.has_default).count(); @@ -4957,7 +4957,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { } // Check provided lifetime parameters. - let lifetime_defs = segment.map_or(&[][..], |(_, generics)| &generics.regions); + let lifetime_defs = segment.map_or(vec![], |(_, generics)| generics.lifetimes()); let required_len = lifetime_defs.len(); // Prohibit explicit lifetime arguments if late bound lifetime parameters are present. @@ -5014,13 +5014,13 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { let segment = segment.map(|(path_segment, generics)| { let explicit = !path_segment.infer_types; - let impl_trait = generics.types.iter() - .any(|ty_param| { - match ty_param.synthetic { - Some(ImplTrait) => true, - _ => false, - } - }); + let impl_trait = generics.types().iter() + .any(|ty_param| { + match ty_param.synthetic { + Some(ImplTrait) => true, + _ => false, + } + }); if explicit && impl_trait { let mut err = struct_span_err! { diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index d0ff44c8e7e10..ec1f654d44b1e 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -641,12 +641,12 @@ fn report_bivariance<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, fn reject_shadowing_type_parameters(tcx: TyCtxt, def_id: DefId) { let generics = tcx.generics_of(def_id); let parent = tcx.generics_of(generics.parent.unwrap()); - let impl_params: FxHashMap<_, _> = parent.types - .iter() - .map(|tp| (tp.name, tp.def_id)) - .collect(); + let impl_params: FxHashMap<_, _> = parent.types() + .iter() + .map(|tp| (tp.name, tp.def_id)) + .collect(); - for method_param in &generics.types { + for method_param in generics.types() { if impl_params.contains_key(&method_param.name) { // Tighten up the span to focus on only the shadowing type let type_span = tcx.def_span(method_param.def_id); diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index f0f392a2458e9..bb30866886917 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -881,8 +881,8 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, assert_eq!(has_self, false); parent_has_self = generics.has_self; own_start = generics.count() as u32; - (generics.parent_regions + generics.regions.len() as u32, - generics.parent_types + generics.types.len() as u32) + (generics.parent_lifetimes() + generics.lifetimes().len() as u32, + generics.parent_types() + generics.types().len() as u32) }); let early_lifetimes = early_bound_lifetimes_from_generics(tcx, ast_generics); @@ -971,12 +971,17 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, .map(|param| (param.def_id, param.index)) .collect(); + let parent_parameters = vec![parent_regions, parent_types]; + let lifetimes: Vec = + regions.into_iter().map(|lt| ty::GenericParameterDef::Lifetime(lt)).collect(); + let types: Vec = + types.into_iter().map(|ty| ty::GenericParameterDef::Type(ty)).collect(); + let parameters = lifetimes.into_iter().chain(types.into_iter()).collect(); + tcx.alloc_generics(ty::Generics { parent: parent_def_id, - parent_regions, - parent_types, - regions, - types, + parent_parameters, + parameters, type_param_to_index, has_self: has_self || parent_has_self, has_late_bound_regions: has_late_bound_regions(tcx, node), diff --git a/src/librustc_typeck/impl_wf_check.rs b/src/librustc_typeck/impl_wf_check.rs index faf3ccb1133ad..fe51e182044c8 100644 --- a/src/librustc_typeck/impl_wf_check.rs +++ b/src/librustc_typeck/impl_wf_check.rs @@ -105,7 +105,7 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, tcx, &impl_predicates.predicates.as_slice(), impl_trait_ref, &mut input_parameters); // Disallow ANY unconstrained type parameters. - for (ty_param, param) in impl_generics.types.iter().zip(impl_hir_generics.ty_params()) { + for (ty_param, param) in impl_generics.types().iter().zip(impl_hir_generics.ty_params()) { let param_ty = ty::ParamTy::for_def(ty_param); if !input_parameters.contains(&ctp::Parameter::from(param_ty)) { report_unused_parameter(tcx, param.span, "type", ¶m_ty.to_string()); @@ -122,7 +122,7 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, .flat_map(|def_id| { ctp::parameters_for(&tcx.type_of(def_id), true) }).collect(); - for (ty_lifetime, lifetime) in impl_generics.regions.iter() + for (ty_lifetime, lifetime) in impl_generics.lifetimes().iter() .zip(impl_hir_generics.lifetimes()) { let param = ctp::Parameter::from(ty_lifetime.to_early_bound_region_data()); diff --git a/src/librustdoc/clean/auto_trait.rs b/src/librustdoc/clean/auto_trait.rs index 722dcb7fe6a73..7601bac67b066 100644 --- a/src/librustdoc/clean/auto_trait.rs +++ b/src/librustdoc/clean/auto_trait.rs @@ -225,30 +225,28 @@ impl<'a, 'tcx, 'rcx> AutoTraitFinder<'a, 'tcx, 'rcx> { fn generics_to_path_params(&self, generics: ty::Generics) -> hir::PathParameters { let lifetimes = HirVec::from_vec( - generics - .regions - .iter() - .map(|p| { - let name = if p.name == "" { - hir::LifetimeName::Static - } else { - hir::LifetimeName::Name(p.name.as_symbol()) - }; + generics.lifetimes() + .iter() + .map(|p| { + let name = if p.name == "" { + hir::LifetimeName::Static + } else { + hir::LifetimeName::Name(p.name.as_symbol()) + }; - hir::Lifetime { - id: ast::DUMMY_NODE_ID, - span: DUMMY_SP, - name, - } - }) - .collect(), + hir::Lifetime { + id: ast::DUMMY_NODE_ID, + span: DUMMY_SP, + name, + } + }) + .collect(), ); let types = HirVec::from_vec( - generics - .types - .iter() - .map(|p| P(self.ty_param_to_ty(p.clone()))) - .collect(), + generics.types() + .into_iter() + .map(|p| P(self.ty_param_to_ty(p.clone()))) + .collect(), ); hir::PathParameters { diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 7d3ba79282938..eec92184ac49d 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1800,7 +1800,7 @@ impl<'a, 'tcx> Clean for (&'a ty::Generics, // Bounds in the type_params and lifetimes fields are repeated in the // predicates field (see rustc_typeck::collect::ty_generics), so remove // them. - let stripped_typarams = gens.types.iter().filter_map(|tp| { + let stripped_typarams = gens.types().iter().filter_map(|tp| { if tp.name == keywords::SelfType.name().as_str() { assert_eq!(tp.index, 0); None @@ -1849,16 +1849,15 @@ impl<'a, 'tcx> Clean for (&'a ty::Generics, // and instead see `where T: Foo + Bar + Sized + 'a` Generics { - params: gens.regions - .clean(cx) - .into_iter() - .map(|lp| GenericParam::Lifetime(lp)) - .chain( - simplify::ty_params(stripped_typarams) + params: gens.lifetimes() .into_iter() - .map(|tp| GenericParam::Type(tp)) - ) - .collect(), + .map(|lp| GenericParam::Lifetime(lp.clean(cx))) + .chain( + simplify::ty_params(stripped_typarams) + .into_iter() + .map(|tp| GenericParam::Type(tp)) + ) + .collect(), where_predicates: simplify::where_clauses(cx, where_predicates), } } From de1c29c95e075af9d95b20860b7f2d9af1449c07 Mon Sep 17 00:00:00 2001 From: varkor Date: Sat, 24 Feb 2018 18:29:40 +0000 Subject: [PATCH 02/40] Reduce parent_params to parent_count --- src/librustc/ich/impls_ty.rs | 4 +-- src/librustc/ty/mod.rs | 28 ++++++++++----------- src/librustc/ty/sty.rs | 2 +- src/librustc_metadata/encoder.rs | 7 +++--- src/librustc_mir/monomorphize/collector.rs | 2 +- src/librustc_typeck/astconv.rs | 2 +- src/librustc_typeck/check/method/confirm.rs | 2 +- src/librustc_typeck/check/method/probe.rs | 3 +-- src/librustc_typeck/check/mod.rs | 2 +- src/librustc_typeck/collect.rs | 10 +++----- 10 files changed, 29 insertions(+), 33 deletions(-) diff --git a/src/librustc/ich/impls_ty.rs b/src/librustc/ich/impls_ty.rs index c7f0979766cf6..62da6be5b211e 100644 --- a/src/librustc/ich/impls_ty.rs +++ b/src/librustc/ich/impls_ty.rs @@ -735,7 +735,7 @@ impl<'a> HashStable> for ty::Generics { hasher: &mut StableHasher) { let ty::Generics { parent, - ref parent_parameters, + ref parent_count, ref parameters, // Reverse map to each `TypeParameterDef`'s `index` field, from @@ -746,7 +746,7 @@ impl<'a> HashStable> for ty::Generics { } = *self; parent.hash_stable(hcx, hasher); - parent_parameters.hash_stable(hcx, hasher); + parent_count.hash_stable(hcx, hasher); parameters.hash_stable(hcx, hasher); has_self.hash_stable(hcx, hasher); has_late_bound_regions.hash_stable(hcx, hasher); diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index f32316ac54723..8f5ec3aae8a35 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -784,7 +784,7 @@ impl GenericParameterDef { #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] pub struct Generics { pub parent: Option, - pub parent_parameters: Vec, + pub parent_count: usize, pub parameters: Vec, /// Reverse map to each `TypeParameterDef`'s `index` field @@ -795,16 +795,12 @@ pub struct Generics { } impl<'a, 'gcx, 'tcx> Generics { - pub fn parent_count(&self) -> usize { - self.parent_parameters.iter().map(|&x| x as usize).sum() - } - pub fn own_count(&self) -> usize { self.parameters.len() } pub fn count(&self) -> usize { - self.parent_count() + self.own_count() + self.parent_count + self.own_count() } pub fn lifetimes(&self) -> Vec<&RegionParameterDef> { @@ -827,12 +823,16 @@ impl<'a, 'gcx, 'tcx> Generics { }).collect() } - pub fn parent_lifetimes(&self) -> u32 { - self.parent_parameters[0] - } - - pub fn parent_types(&self) -> u32 { - self.parent_parameters[1] + pub fn has_type_parameters(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { + if self.types().len() != 0 { + return true; + } + if let Some(parent_def_id) = self.parent { + let parent = tcx.generics_of(parent_def_id); + parent.has_type_parameters(tcx) + } else { + false + } } pub fn region_param(&'tcx self, @@ -840,7 +840,7 @@ impl<'a, 'gcx, 'tcx> Generics { tcx: TyCtxt<'a, 'gcx, 'tcx>) -> &'tcx RegionParameterDef { - if let Some(index) = param.index.checked_sub(self.parent_count() as u32) { + if let Some(index) = param.index.checked_sub(self.parent_count as u32) { // We're currently assuming that lifetimes precede other generic parameters. match self.parameters[index as usize - self.has_self as usize] { ty::GenericParameterDef::Lifetime(ref lt) => lt, @@ -857,7 +857,7 @@ impl<'a, 'gcx, 'tcx> Generics { param: &ParamTy, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> &TypeParameterDef { - if let Some(idx) = param.idx.checked_sub(self.parent_count() as u32) { + if let Some(idx) = param.idx.checked_sub(self.parent_count as u32) { // non-Self type parameters are always offset by exactly // `self.regions.len()`. In the absence of a Self, this is obvious, // but even in the presence of a `Self` we just have to "compensate" diff --git a/src/librustc/ty/sty.rs b/src/librustc/ty/sty.rs index f0a7ce5497166..c1e3153c4618e 100644 --- a/src/librustc/ty/sty.rs +++ b/src/librustc/ty/sty.rs @@ -292,7 +292,7 @@ impl<'tcx> ClosureSubsts<'tcx> { /// ordering. fn split(self, def_id: DefId, tcx: TyCtxt<'_, '_, '_>) -> SplitClosureSubsts<'tcx> { let generics = tcx.generics_of(def_id); - let parent_len = generics.parent_count(); + let parent_len = generics.parent_count; SplitClosureSubsts { closure_kind_ty: self.substs.type_at(parent_len), closure_sig_ty: self.substs.type_at(parent_len + 1), diff --git a/src/librustc_metadata/encoder.rs b/src/librustc_metadata/encoder.rs index 7e580e9333ff0..9ebffa4c744e1 100644 --- a/src/librustc_metadata/encoder.rs +++ b/src/librustc_metadata/encoder.rs @@ -929,10 +929,9 @@ impl<'a, 'b: 'a, 'tcx: 'b> IsolatedEncoder<'a, 'b, 'tcx> { hir::ImplItemKind::Const(..) => true, hir::ImplItemKind::Method(ref sig, _) => { let generics = self.tcx.generics_of(def_id); - let types = generics.parent_types() as usize + generics.types().len(); - let needs_inline = - (types > 0 || tcx.trans_fn_attrs(def_id).requests_inline()) - && !self.metadata_output_only(); + let needs_inline = (generics.has_type_parameters(self.tcx) || + tcx.trans_fn_attrs(def_id).requests_inline()) && + !self.metadata_output_only(); let is_const_fn = sig.constness == hir::Constness::Const; let always_encode_mir = self.tcx.sess.opts.debugging_opts.always_encode_mir; needs_inline || is_const_fn || always_encode_mir diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index bfdf81588afdc..ecdd6b358cd7b 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -1076,7 +1076,7 @@ impl<'b, 'a, 'v> RootCollector<'b, 'a, 'v> { fn item_has_type_parameters<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> bool { let generics = tcx.generics_of(def_id); - generics.parent_types() as usize + generics.types().len() > 0 + generics.has_type_parameters(tcx) } fn create_mono_items_for_default_impls<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index 4286946599a7c..ef3f81cfc5c36 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -1139,7 +1139,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { } debug!("impl_trait_ty_to_ty: substs from parent = {:?}", substs); } - assert_eq!(substs.len(), generics.parent_count()); + assert_eq!(substs.len(), generics.parent_count); // Fill in our own generics with the resolved lifetimes assert_eq!(lifetimes.len(), generics.own_count()); diff --git a/src/librustc_typeck/check/method/confirm.rs b/src/librustc_typeck/check/method/confirm.rs index 3accb51f3087e..ed4fb7ba93960 100644 --- a/src/librustc_typeck/check/method/confirm.rs +++ b/src/librustc_typeck/check/method/confirm.rs @@ -314,7 +314,7 @@ impl<'a, 'gcx, 'tcx> ConfirmContext<'a, 'gcx, 'tcx> { // Create subst for early-bound lifetime parameters, combining // parameters from the type and those from the method. - assert_eq!(method_generics.parent_count(), parent_substs.len()); + assert_eq!(method_generics.parent_count, parent_substs.len()); let provided = &segment.parameters; Substs::for_item(self.tcx, pick.item.def_id, |def, _| { let i = def.index as usize; diff --git a/src/librustc_typeck/check/method/probe.rs b/src/librustc_typeck/check/method/probe.rs index d3335fdd9807e..513bc6931ecef 100644 --- a/src/librustc_typeck/check/method/probe.rs +++ b/src/librustc_typeck/check/method/probe.rs @@ -1378,8 +1378,7 @@ impl<'a, 'gcx, 'tcx> ProbeContext<'a, 'gcx, 'tcx> { // method yet. So create fresh variables here for those too, // if there are any. let generics = self.tcx.generics_of(method); - assert_eq!(substs.regions().count(), generics.parent_lifetimes() as usize); - assert_eq!(substs.types().count(), generics.parent_types() as usize); + assert_eq!(substs.len(), generics.parent_count as usize); // Erase any late-bound regions from the method and substitute // in the values from the substitution. diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 1faf1f7e88286..0c875e704c6de 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -4751,7 +4751,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { let (fn_start, has_self) = match (type_segment, fn_segment) { (_, Some((_, generics))) => { - (generics.parent_count(), generics.has_self) + (generics.parent_count, generics.has_self) } (Some((_, generics)), None) => { (generics.own_count(), generics.has_self) diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index bb30866886917..ffbbb3b1faef4 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -876,13 +876,12 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let has_self = opt_self.is_some(); let mut parent_has_self = false; let mut own_start = has_self as u32; - let (parent_regions, parent_types) = parent_def_id.map_or((0, 0), |def_id| { + let parent_count = parent_def_id.map_or(0, |def_id| { let generics = tcx.generics_of(def_id); assert_eq!(has_self, false); parent_has_self = generics.has_self; own_start = generics.count() as u32; - (generics.parent_lifetimes() + generics.lifetimes().len() as u32, - generics.parent_types() + generics.types().len() as u32) + generics.parent_count + generics.parameters.len() }); let early_lifetimes = early_bound_lifetimes_from_generics(tcx, ast_generics); @@ -971,7 +970,6 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, .map(|param| (param.def_id, param.index)) .collect(); - let parent_parameters = vec![parent_regions, parent_types]; let lifetimes: Vec = regions.into_iter().map(|lt| ty::GenericParameterDef::Lifetime(lt)).collect(); let types: Vec = @@ -980,7 +978,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, tcx.alloc_generics(ty::Generics { parent: parent_def_id, - parent_parameters, + parent_count, parameters, type_param_to_index, has_self: has_self || parent_has_self, @@ -1395,7 +1393,7 @@ pub fn explicit_predicates_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }; let generics = tcx.generics_of(def_id); - let parent_count = generics.parent_count() as u32; + let parent_count = generics.parent_count as u32; let has_own_self = generics.has_self && parent_count == 0; let mut predicates = vec![]; From 63553547e588d7a44f42ccc41efa338129898a6c Mon Sep 17 00:00:00 2001 From: varkor Date: Sat, 24 Feb 2018 02:40:40 +0000 Subject: [PATCH 03/40] Rename ty::Generics::parameters to params --- src/librustc/ich/impls_ty.rs | 4 ++-- src/librustc/ty/mod.rs | 14 +++++++------- src/librustc/ty/subst.rs | 2 +- src/librustc_typeck/check/method/mod.rs | 2 +- src/librustc_typeck/check/method/probe.rs | 2 +- src/librustc_typeck/collect.rs | 6 +++--- 6 files changed, 15 insertions(+), 15 deletions(-) diff --git a/src/librustc/ich/impls_ty.rs b/src/librustc/ich/impls_ty.rs index 62da6be5b211e..dbd7175272a36 100644 --- a/src/librustc/ich/impls_ty.rs +++ b/src/librustc/ich/impls_ty.rs @@ -736,7 +736,7 @@ impl<'a> HashStable> for ty::Generics { let ty::Generics { parent, ref parent_count, - ref parameters, + ref params, // Reverse map to each `TypeParameterDef`'s `index` field, from // `def_id.index` (`def_id.krate` is the same as the item's). @@ -747,7 +747,7 @@ impl<'a> HashStable> for ty::Generics { parent.hash_stable(hcx, hasher); parent_count.hash_stable(hcx, hasher); - parameters.hash_stable(hcx, hasher); + params.hash_stable(hcx, hasher); has_self.hash_stable(hcx, hasher); has_late_bound_regions.hash_stable(hcx, hasher); } diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 8f5ec3aae8a35..8b69ba1780ec2 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -785,7 +785,7 @@ impl GenericParameterDef { pub struct Generics { pub parent: Option, pub parent_count: usize, - pub parameters: Vec, + pub params: Vec, /// Reverse map to each `TypeParameterDef`'s `index` field pub type_param_to_index: FxHashMap, @@ -796,7 +796,7 @@ pub struct Generics { impl<'a, 'gcx, 'tcx> Generics { pub fn own_count(&self) -> usize { - self.parameters.len() + self.params.len() } pub fn count(&self) -> usize { @@ -804,7 +804,7 @@ impl<'a, 'gcx, 'tcx> Generics { } pub fn lifetimes(&self) -> Vec<&RegionParameterDef> { - self.parameters.iter().filter_map(|p| { + self.params.iter().filter_map(|p| { if let GenericParameterDef::Lifetime(lt) = p { Some(lt) } else { @@ -814,7 +814,7 @@ impl<'a, 'gcx, 'tcx> Generics { } pub fn types(&self) -> Vec<&TypeParameterDef> { - self.parameters.iter().filter_map(|p| { + self.params.iter().filter_map(|p| { if let GenericParameterDef::Type(ty) = p { Some(ty) } else { @@ -842,7 +842,7 @@ impl<'a, 'gcx, 'tcx> Generics { { if let Some(index) = param.index.checked_sub(self.parent_count as u32) { // We're currently assuming that lifetimes precede other generic parameters. - match self.parameters[index as usize - self.has_self as usize] { + match self.params[index as usize - self.has_self as usize] { ty::GenericParameterDef::Lifetime(ref lt) => lt, _ => bug!("expected region parameter, but found another generic parameter") } @@ -892,13 +892,13 @@ impl<'a, 'gcx, 'tcx> Generics { if let Some(_) = (idx as usize).checked_sub(type_param_offset) { assert!(!is_separated_self, "found a Self after type_param_offset"); - match self.parameters[idx as usize] { + match self.params[idx as usize] { ty::GenericParameterDef::Type(ref ty) => ty, _ => bug!("expected type parameter, but found another generic parameter") } } else { assert!(is_separated_self, "non-Self param before type_param_offset"); - match self.parameters[type_param_offset] { + match self.params[type_param_offset] { ty::GenericParameterDef::Type(ref ty) => ty, _ => bug!("expected type parameter, but found another generic parameter") } diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index fa2aa9720064a..a6960339fd4aa 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -252,7 +252,7 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { substs.push(ty.into()); } - for def in &defs.parameters { + for def in &defs.params { let param = match def { ty::GenericParameterDef::Lifetime(ref lt) => { UnpackedKind::Lifetime(mk_region(lt, substs)) diff --git a/src/librustc_typeck/check/method/mod.rs b/src/librustc_typeck/check/method/mod.rs index 8d7d8cb0f5f66..83f132d88691a 100644 --- a/src/librustc_typeck/check/method/mod.rs +++ b/src/librustc_typeck/check/method/mod.rs @@ -288,7 +288,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { let method_item = self.associated_item(trait_def_id, m_name, Namespace::Value).unwrap(); let def_id = method_item.def_id; let generics = tcx.generics_of(def_id); - assert_eq!(generics.parameters.len(), 0); + assert_eq!(generics.params.len(), 0); debug!("lookup_in_trait_adjusted: method_item={:?}", method_item); let mut obligations = vec![]; diff --git a/src/librustc_typeck/check/method/probe.rs b/src/librustc_typeck/check/method/probe.rs index 513bc6931ecef..9d762ca383476 100644 --- a/src/librustc_typeck/check/method/probe.rs +++ b/src/librustc_typeck/check/method/probe.rs @@ -1384,7 +1384,7 @@ impl<'a, 'gcx, 'tcx> ProbeContext<'a, 'gcx, 'tcx> { // in the values from the substitution. let xform_fn_sig = self.erase_late_bound_regions(&fn_sig); - if generics.parameters.is_empty() { + if generics.params.is_empty() { xform_fn_sig.subst(self.tcx, substs) } else { let substs = Substs::for_item(self.tcx, method, |def, _| { diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index ffbbb3b1faef4..6783f6f1987d7 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -881,7 +881,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, assert_eq!(has_self, false); parent_has_self = generics.has_self; own_start = generics.count() as u32; - generics.parent_count + generics.parameters.len() + generics.parent_count + generics.params.len() }); let early_lifetimes = early_bound_lifetimes_from_generics(tcx, ast_generics); @@ -974,12 +974,12 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, regions.into_iter().map(|lt| ty::GenericParameterDef::Lifetime(lt)).collect(); let types: Vec = types.into_iter().map(|ty| ty::GenericParameterDef::Type(ty)).collect(); - let parameters = lifetimes.into_iter().chain(types.into_iter()).collect(); + let params = lifetimes.into_iter().chain(types.into_iter()).collect(); tcx.alloc_generics(ty::Generics { parent: parent_def_id, parent_count, - parameters, + params, type_param_to_index, has_self: has_self || parent_has_self, has_late_bound_regions: has_late_bound_regions(tcx, node), From e9e3d5703b1a4ec4fc542e293fa7261e3ad79e29 Mon Sep 17 00:00:00 2001 From: varkor Date: Sun, 25 Feb 2018 00:01:05 +0000 Subject: [PATCH 04/40] Rename ty::GenericParameterDef to GenericParam --- src/librustc/ich/impls_ty.rs | 2 +- src/librustc/ty/mod.rs | 20 ++++++++++---------- src/librustc/ty/subst.rs | 4 ++-- src/librustc_typeck/collect.rs | 8 ++++---- 4 files changed, 17 insertions(+), 17 deletions(-) diff --git a/src/librustc/ich/impls_ty.rs b/src/librustc/ich/impls_ty.rs index dbd7175272a36..dd09af10bd934 100644 --- a/src/librustc/ich/impls_ty.rs +++ b/src/librustc/ich/impls_ty.rs @@ -753,7 +753,7 @@ impl<'a> HashStable> for ty::Generics { } } -impl_stable_hash_for!(enum ty::GenericParameterDef { +impl_stable_hash_for!(enum ty::GenericParam { Lifetime(lt), Type(ty) }); diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 8b69ba1780ec2..81e188649b8c3 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -758,16 +758,16 @@ impl ty::EarlyBoundRegion { } #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] -pub enum GenericParameterDef { +pub enum GenericParam { Lifetime(RegionParameterDef), Type(TypeParameterDef), } -impl GenericParameterDef { +impl GenericParam { pub fn index(&self) -> u32 { match self { - GenericParameterDef::Lifetime(lt) => lt.index, - GenericParameterDef::Type(ty) => ty.index, + GenericParam::Lifetime(lt) => lt.index, + GenericParam::Type(ty) => ty.index, } } } @@ -785,7 +785,7 @@ impl GenericParameterDef { pub struct Generics { pub parent: Option, pub parent_count: usize, - pub params: Vec, + pub params: Vec, /// Reverse map to each `TypeParameterDef`'s `index` field pub type_param_to_index: FxHashMap, @@ -805,7 +805,7 @@ impl<'a, 'gcx, 'tcx> Generics { pub fn lifetimes(&self) -> Vec<&RegionParameterDef> { self.params.iter().filter_map(|p| { - if let GenericParameterDef::Lifetime(lt) = p { + if let GenericParam::Lifetime(lt) = p { Some(lt) } else { None @@ -815,7 +815,7 @@ impl<'a, 'gcx, 'tcx> Generics { pub fn types(&self) -> Vec<&TypeParameterDef> { self.params.iter().filter_map(|p| { - if let GenericParameterDef::Type(ty) = p { + if let GenericParam::Type(ty) = p { Some(ty) } else { None @@ -843,7 +843,7 @@ impl<'a, 'gcx, 'tcx> Generics { if let Some(index) = param.index.checked_sub(self.parent_count as u32) { // We're currently assuming that lifetimes precede other generic parameters. match self.params[index as usize - self.has_self as usize] { - ty::GenericParameterDef::Lifetime(ref lt) => lt, + ty::GenericParam::Lifetime(ref lt) => lt, _ => bug!("expected region parameter, but found another generic parameter") } } else { @@ -893,13 +893,13 @@ impl<'a, 'gcx, 'tcx> Generics { if let Some(_) = (idx as usize).checked_sub(type_param_offset) { assert!(!is_separated_self, "found a Self after type_param_offset"); match self.params[idx as usize] { - ty::GenericParameterDef::Type(ref ty) => ty, + ty::GenericParam::Type(ref ty) => ty, _ => bug!("expected type parameter, but found another generic parameter") } } else { assert!(is_separated_self, "non-Self param before type_param_offset"); match self.params[type_param_offset] { - ty::GenericParameterDef::Type(ref ty) => ty, + ty::GenericParam::Type(ref ty) => ty, _ => bug!("expected type parameter, but found another generic parameter") } } diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index a6960339fd4aa..67cb2d829ff31 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -254,10 +254,10 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { for def in &defs.params { let param = match def { - ty::GenericParameterDef::Lifetime(ref lt) => { + ty::GenericParam::Lifetime(ref lt) => { UnpackedKind::Lifetime(mk_region(lt, substs)) } - ty::GenericParameterDef::Type(ref ty) => { + ty::GenericParam::Type(ref ty) => { if skip_self { skip_self = false; continue diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 6783f6f1987d7..0fc47b93f8f99 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -970,10 +970,10 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, .map(|param| (param.def_id, param.index)) .collect(); - let lifetimes: Vec = - regions.into_iter().map(|lt| ty::GenericParameterDef::Lifetime(lt)).collect(); - let types: Vec = - types.into_iter().map(|ty| ty::GenericParameterDef::Type(ty)).collect(); + let lifetimes: Vec = + regions.into_iter().map(|lt| ty::GenericParam::Lifetime(lt)).collect(); + let types: Vec = + types.into_iter().map(|ty| ty::GenericParam::Type(ty)).collect(); let params = lifetimes.into_iter().chain(types.into_iter()).collect(); tcx.alloc_generics(ty::Generics { From e5825c29c33dde7335e8fd64cd3861aa6428ea9b Mon Sep 17 00:00:00 2001 From: varkor Date: Sun, 25 Feb 2018 00:31:26 +0000 Subject: [PATCH 05/40] Prefer iterator to vec --- src/librustc/hir/lowering.rs | 7 +++--- src/librustc/middle/resolve_lifetime.rs | 1 - src/librustc/traits/error_reporting.rs | 2 +- src/librustc/traits/object_safety.rs | 2 +- src/librustc/traits/on_unimplemented.rs | 6 ++--- src/librustc/ty/mod.rs | 12 +++++----- src/librustc/ty/subst.rs | 3 +-- src/librustc/util/ppaux.rs | 12 +++++----- src/librustc_mir/monomorphize/collector.rs | 2 +- src/librustc_mir/transform/check_unsafety.rs | 2 +- src/librustc_privacy/lib.rs | 4 ++-- src/librustc_trans/debuginfo/mod.rs | 2 +- src/librustc_typeck/astconv.rs | 9 ++++---- src/librustc_typeck/check/compare_method.rs | 8 +++---- src/librustc_typeck/check/intrinsic.rs | 4 ++-- src/librustc_typeck/check/method/confirm.rs | 2 +- src/librustc_typeck/check/mod.rs | 23 ++++++++++---------- src/librustc_typeck/check/wfcheck.rs | 1 - src/librustc_typeck/impl_wf_check.rs | 14 +++++------- src/librustdoc/clean/auto_trait.rs | 1 - src/librustdoc/clean/mod.rs | 2 +- 21 files changed, 55 insertions(+), 64 deletions(-) diff --git a/src/librustc/hir/lowering.rs b/src/librustc/hir/lowering.rs index e05c686f39fcc..735598fd436c8 100644 --- a/src/librustc/hir/lowering.rs +++ b/src/librustc/hir/lowering.rs @@ -1459,10 +1459,9 @@ impl<'a> LoweringContext<'a> { return n; } assert!(!def_id.is_local()); - let n = self.cstore - .item_generics_cloned_untracked(def_id, self.sess) - .lifetimes() - .len(); + let item_generics = + self.cstore.item_generics_cloned_untracked(def_id, self.sess); + let n = item_generics.lifetimes().count(); self.type_def_lifetime_params.insert(def_id, n); n }); diff --git a/src/librustc/middle/resolve_lifetime.rs b/src/librustc/middle/resolve_lifetime.rs index 8f44507035af3..225384ed0cb47 100644 --- a/src/librustc/middle/resolve_lifetime.rs +++ b/src/librustc/middle/resolve_lifetime.rs @@ -1660,7 +1660,6 @@ impl<'a, 'tcx> LifetimeContext<'a, 'tcx> { .or_insert_with(|| { tcx.generics_of(def_id) .types() - .iter() .map(|def| def.object_lifetime_default) .collect() }) diff --git a/src/librustc/traits/error_reporting.rs b/src/librustc/traits/error_reporting.rs index dfe0cd6900e7a..00a0d4dc554d5 100644 --- a/src/librustc/traits/error_reporting.rs +++ b/src/librustc/traits/error_reporting.rs @@ -378,7 +378,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { flags.push(("_Self".to_string(), Some(self.tcx.type_of(def.did).to_string()))); } - for param in generics.types().iter() { + for param in generics.types() { let name = param.name.to_string(); let ty = trait_ref.substs.type_for_def(param); let ty_str = ty.to_string(); diff --git a/src/librustc/traits/object_safety.rs b/src/librustc/traits/object_safety.rs index 10228c5783c56..3c82dbd7ad662 100644 --- a/src/librustc/traits/object_safety.rs +++ b/src/librustc/traits/object_safety.rs @@ -284,7 +284,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { } // We can't monomorphize things like `fn foo(...)`. - if !self.generics_of(method.def_id).types().is_empty() { + if self.generics_of(method.def_id).types().count() != 0 { return Some(MethodViolationCode::Generic); } diff --git a/src/librustc/traits/on_unimplemented.rs b/src/librustc/traits/on_unimplemented.rs index b2fc2c171063f..a44dcc7c274e5 100644 --- a/src/librustc/traits/on_unimplemented.rs +++ b/src/librustc/traits/on_unimplemented.rs @@ -243,7 +243,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let name = tcx.item_name(trait_def_id); let generics = tcx.generics_of(trait_def_id); let parser = Parser::new(&self.0); - let types = generics.types(); + let mut types = generics.types(); let mut result = Ok(()); for token in parser { match token { @@ -254,7 +254,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { // `{ThisTraitsName}` is allowed Position::ArgumentNamed(s) if s == name => (), // So is `{A}` if A is a type parameter - Position::ArgumentNamed(s) => match types.iter().find(|t| { + Position::ArgumentNamed(s) => match types.find(|t| { t.name == s }) { Some(_) => (), @@ -288,7 +288,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let name = tcx.item_name(trait_ref.def_id); let trait_str = tcx.item_path_str(trait_ref.def_id); let generics = tcx.generics_of(trait_ref.def_id); - let generic_map = generics.types().iter().map(|param| { + let generic_map = generics.types().map(|param| { (param.name.to_string(), trait_ref.substs.type_for_def(param).to_string()) }).collect::>(); diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 81e188649b8c3..bf4bc9d3b3e24 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -803,28 +803,28 @@ impl<'a, 'gcx, 'tcx> Generics { self.parent_count + self.own_count() } - pub fn lifetimes(&self) -> Vec<&RegionParameterDef> { + pub fn lifetimes(&self) -> impl DoubleEndedIterator { self.params.iter().filter_map(|p| { if let GenericParam::Lifetime(lt) = p { Some(lt) } else { None } - }).collect() + }) } - pub fn types(&self) -> Vec<&TypeParameterDef> { + pub fn types(&self) -> impl DoubleEndedIterator { self.params.iter().filter_map(|p| { if let GenericParam::Type(ty) = p { Some(ty) } else { None } - }).collect() + }) } pub fn has_type_parameters(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { - if self.types().len() != 0 { + if self.types().count() != 0 { return true; } if let Some(parent_def_id) = self.parent { @@ -885,7 +885,7 @@ impl<'a, 'gcx, 'tcx> Generics { // And it can be seen that in both cases, to move from a substs // offset to a generics offset you just have to offset by the // number of regions. - let type_param_offset = self.lifetimes().len(); + let type_param_offset = self.lifetimes().count(); let has_self = self.has_self && self.parent.is_none(); let is_separated_self = type_param_offset != 0 && idx == 0 && has_self; diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index 67cb2d829ff31..2f4daf61a074c 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -242,8 +242,7 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, FT: FnMut(&ty::TypeParameterDef, &[Kind<'tcx>]) -> Ty<'tcx> { // Handle Self first, before all regions. - let types = defs.types(); - let mut types = types.iter(); + let mut types = defs.types(); let mut skip_self = defs.parent.is_none() && defs.has_self; if skip_self { let def = types.next().unwrap(); diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index 5b287e416297b..431fd59e02cb3 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -310,10 +310,10 @@ impl PrintContext { if let Some(def_id) = generics.parent { // Methods. assert!(is_value_path); - child_types = generics.types().len(); + child_types = generics.types().count(); generics = tcx.generics_of(def_id); - num_regions = generics.lifetimes().len(); - num_types = generics.types().len(); + num_regions = generics.lifetimes().count(); + num_types = generics.types().count(); if has_self { print!(f, self, write("<"), print_display(substs.type_at(0)), write(" as "))?; @@ -328,8 +328,8 @@ impl PrintContext { assert_eq!(has_self, false); } else { // Types and traits. - num_regions = generics.lifetimes().len(); - num_types = generics.types().len(); + num_regions = generics.lifetimes().count(); + num_types = generics.types().count(); } } @@ -337,7 +337,7 @@ impl PrintContext { if generics.types().last().map_or(false, |def| def.has_default) { if let Some(substs) = tcx.lift(&substs) { let tps = substs.types().rev().skip(child_types); - for (def, actual) in generics.types().iter().rev().zip(tps) { + for (def, actual) in generics.types().rev().zip(tps) { if !def.has_default { break; } diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index ecdd6b358cd7b..8646df02e5108 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -1108,7 +1108,7 @@ fn create_mono_items_for_default_impls<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, continue; } - if !tcx.generics_of(method.def_id).types().is_empty() { + if tcx.generics_of(method.def_id).types().count() != 0 { continue; } diff --git a/src/librustc_mir/transform/check_unsafety.rs b/src/librustc_mir/transform/check_unsafety.rs index 1e8707157f75a..68b8b256f290d 100644 --- a/src/librustc_mir/transform/check_unsafety.rs +++ b/src/librustc_mir/transform/check_unsafety.rs @@ -357,7 +357,7 @@ fn unsafe_derive_on_repr_packed<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: D // FIXME: when we make this a hard error, this should have its // own error code. - let message = if !tcx.generics_of(def_id).types().is_empty() { + let message = if tcx.generics_of(def_id).types().count() != 0 { format!("#[derive] can't be used on a #[repr(packed)] struct with \ type parameters (error E0133)") } else { diff --git a/src/librustc_privacy/lib.rs b/src/librustc_privacy/lib.rs index 445717ac60081..d590210925597 100644 --- a/src/librustc_privacy/lib.rs +++ b/src/librustc_privacy/lib.rs @@ -399,7 +399,7 @@ impl<'a, 'tcx> Visitor<'tcx> for EmbargoVisitor<'a, 'tcx> { impl<'b, 'a, 'tcx> ReachEverythingInTheInterfaceVisitor<'b, 'a, 'tcx> { fn generics(&mut self) -> &mut Self { - for def in &self.ev.tcx.generics_of(self.item_def_id).types() { + for def in self.ev.tcx.generics_of(self.item_def_id).types() { if def.has_default { self.ev.tcx.type_of(def.def_id).visit_with(self); } @@ -1335,7 +1335,7 @@ struct SearchInterfaceForPrivateItemsVisitor<'a, 'tcx: 'a> { impl<'a, 'tcx: 'a> SearchInterfaceForPrivateItemsVisitor<'a, 'tcx> { fn generics(&mut self) -> &mut Self { - for def in &self.tcx.generics_of(self.item_def_id).types() { + for def in self.tcx.generics_of(self.item_def_id).types() { if def.has_default { self.tcx.type_of(def.def_id).visit_with(self); } diff --git a/src/librustc_trans/debuginfo/mod.rs b/src/librustc_trans/debuginfo/mod.rs index be9aa49c100a8..1282626974df0 100644 --- a/src/librustc_trans/debuginfo/mod.rs +++ b/src/librustc_trans/debuginfo/mod.rs @@ -417,7 +417,7 @@ pub fn create_function_debug_context<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>, let mut names = generics.parent.map_or(vec![], |def_id| { get_type_parameter_names(cx, cx.tcx.generics_of(def_id)) }); - names.extend(generics.types().iter().map(|param| param.name)); + names.extend(generics.types().map(|param| param.name)); names } diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index ef3f81cfc5c36..fab8eec35f3b4 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -209,7 +209,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { // whatever & would get replaced with). let decl_generics = tcx.generics_of(def_id); let num_types_provided = parameters.types.len(); - let expected_num_region_params = decl_generics.lifetimes().len(); + let expected_num_region_params = decl_generics.lifetimes().count(); let supplied_num_region_params = parameters.lifetimes.len(); if expected_num_region_params != supplied_num_region_params { report_lifetime_number_error(tcx, span, @@ -221,9 +221,10 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { assert_eq!(decl_generics.has_self, self_ty.is_some()); // Check the number of type parameters supplied by the user. - let ty_param_defs = &decl_generics.types()[self_ty.is_some() as usize..]; + let ty_param_defs = + decl_generics.types().skip(self_ty.is_some() as usize).collect::>(); if !infer_types || num_types_provided > ty_param_defs.len() { - check_type_argument_count(tcx, span, num_types_provided, ty_param_defs); + check_type_argument_count(tcx, span, num_types_provided, &ty_param_defs); } let is_object = self_ty.map_or(false, |ty| ty.sty == TRAIT_OBJECT_DUMMY_SELF); @@ -254,7 +255,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { return ty; } - let i = i - self_ty.is_some() as usize - decl_generics.lifetimes().len(); + let i = i - self_ty.is_some() as usize - decl_generics.lifetimes().count(); if i < num_types_provided { // A provided type parameter. self.ast_ty_to_ty(¶meters.types[i]) diff --git a/src/librustc_typeck/check/compare_method.rs b/src/librustc_typeck/check/compare_method.rs index 1dce514023a59..30620caf69274 100644 --- a/src/librustc_typeck/check/compare_method.rs +++ b/src/librustc_typeck/check/compare_method.rs @@ -377,7 +377,7 @@ fn check_region_bounds_on_impl_method<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, // but found 0" it's confusing, because it looks like there // are zero. Since I don't quite know how to phrase things at // the moment, give a kind of vague error message. - if trait_params.len() != impl_params.len() { + if trait_params.count() != impl_params.count() { let mut err = struct_span_err!(tcx.sess, span, E0195, @@ -574,8 +574,8 @@ fn compare_number_of_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, -> Result<(), ErrorReported> { let impl_m_generics = tcx.generics_of(impl_m.def_id); let trait_m_generics = tcx.generics_of(trait_m.def_id); - let num_impl_m_type_params = impl_m_generics.types().len(); - let num_trait_m_type_params = trait_m_generics.types().len(); + let num_impl_m_type_params = impl_m_generics.types().count(); + let num_trait_m_type_params = trait_m_generics.types().count(); if num_impl_m_type_params != num_trait_m_type_params { let impl_m_node_id = tcx.hir.as_local_node_id(impl_m.def_id).unwrap(); let impl_m_item = tcx.hir.expect_impl_item(impl_m_node_id); @@ -728,7 +728,7 @@ fn compare_synthetic_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let mut error_found = false; let impl_m_generics = tcx.generics_of(impl_m.def_id); let trait_m_generics = tcx.generics_of(trait_m.def_id); - for (impl_ty, trait_ty) in impl_m_generics.types().iter().zip(trait_m_generics.types().iter()) { + for (impl_ty, trait_ty) in impl_m_generics.types().zip(trait_m_generics.types()) { if impl_ty.synthetic != trait_ty.synthetic { let impl_node_id = tcx.hir.as_local_node_id(impl_ty.def_id).unwrap(); let impl_span = tcx.hir.span(impl_node_id); diff --git a/src/librustc_typeck/check/intrinsic.rs b/src/librustc_typeck/check/intrinsic.rs index 50a3cab6d2bb0..e2deca38302cd 100644 --- a/src/librustc_typeck/check/intrinsic.rs +++ b/src/librustc_typeck/check/intrinsic.rs @@ -45,7 +45,7 @@ fn equate_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } } - let i_n_tps = tcx.generics_of(def_id).types().len(); + let i_n_tps = tcx.generics_of(def_id).types().count(); if i_n_tps != n_tps { let span = match it.node { hir::ForeignItemFn(_, _, ref generics) => generics.span, @@ -346,7 +346,7 @@ pub fn check_platform_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }; let def_id = tcx.hir.local_def_id(it.id); - let i_n_tps = tcx.generics_of(def_id).types().len(); + let i_n_tps = tcx.generics_of(def_id).types().count(); let name = it.name.as_str(); let (n_tps, inputs, output) = match &*name { diff --git a/src/librustc_typeck/check/method/confirm.rs b/src/librustc_typeck/check/method/confirm.rs index ed4fb7ba93960..f075cd911ad9e 100644 --- a/src/librustc_typeck/check/method/confirm.rs +++ b/src/librustc_typeck/check/method/confirm.rs @@ -332,7 +332,7 @@ impl<'a, 'gcx, 'tcx> ConfirmContext<'a, 'gcx, 'tcx> { parent_substs.type_at(i) } else if let Some(ast_ty) = provided.as_ref().and_then(|p| { - p.types.get(i - parent_substs.len() - method_generics.lifetimes().len()) + p.types.get(i - parent_substs.len() - method_generics.lifetimes().count()) }) { self.to_ty(ast_ty) diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 0c875e704c6de..b6f3d5a80d64c 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -1239,7 +1239,7 @@ pub fn check_item_type<'a,'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, it: &'tcx hir::Item } else { for item in &m.items { let generics = tcx.generics_of(tcx.hir.local_def_id(item.id)); - if !generics.types().is_empty() { + if generics.types().count() != 0 { let mut err = struct_span_err!(tcx.sess, item.span, E0044, "foreign items may not have type parameters"); err.span_label(item.span, "can't have type parameters"); @@ -4799,7 +4799,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // Skip over the lifetimes in the same segment. if let Some((_, generics)) = segment { - i -= generics.lifetimes().len(); + i -= generics.lifetimes().count(); } if let Some(ast_ty) = types.get(i) { @@ -4920,9 +4920,9 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // Check provided type parameters. let type_defs = segment.map_or(vec![], |(_, generics)| { if generics.parent.is_none() { - generics.types()[generics.has_self as usize..].to_vec() + generics.types().skip(generics.has_self as usize).collect() } else { - generics.types() + generics.types().collect() } }); let required_len = type_defs.iter().take_while(|d| !d.has_default).count(); @@ -4957,7 +4957,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { } // Check provided lifetime parameters. - let lifetime_defs = segment.map_or(vec![], |(_, generics)| generics.lifetimes()); + let lifetime_defs = segment.map_or(vec![], |(_, generics)| generics.lifetimes().collect()); let required_len = lifetime_defs.len(); // Prohibit explicit lifetime arguments if late bound lifetime parameters are present. @@ -4968,7 +4968,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { let primary_msg = "cannot specify lifetime arguments explicitly \ if late bound lifetime parameters are present"; let note_msg = "the late bound lifetime parameter is introduced here"; - if !is_method_call && (lifetimes.len() > lifetime_defs.len() || + if !is_method_call && (lifetimes.len() > required_len || lifetimes.len() < required_len && !infer_lifetimes) { let mut err = self.tcx.sess.struct_span_err(lifetimes[0].span, primary_msg); err.span_note(span_late, note_msg); @@ -4983,9 +4983,9 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { return; } - if lifetimes.len() > lifetime_defs.len() { - let span = lifetimes[lifetime_defs.len()].span; - let expected_text = count_lifetime_params(lifetime_defs.len()); + if lifetimes.len() > required_len { + let span = lifetimes[required_len].span; + let expected_text = count_lifetime_params(required_len); let actual_text = count_lifetime_params(lifetimes.len()); struct_span_err!(self.tcx.sess, span, E0088, "too many lifetime parameters provided: \ @@ -4994,7 +4994,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { .span_label(span, format!("expected {}", expected_text)) .emit(); } else if lifetimes.len() < required_len && !infer_lifetimes { - let expected_text = count_lifetime_params(lifetime_defs.len()); + let expected_text = count_lifetime_params(required_len); let actual_text = count_lifetime_params(lifetimes.len()); struct_span_err!(self.tcx.sess, span, E0090, "too few lifetime parameters provided: \ @@ -5014,8 +5014,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { let segment = segment.map(|(path_segment, generics)| { let explicit = !path_segment.infer_types; - let impl_trait = generics.types().iter() - .any(|ty_param| { + let impl_trait = generics.types().any(|ty_param| { match ty_param.synthetic { Some(ImplTrait) => true, _ => false, diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index ec1f654d44b1e..2fafee3a6582c 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -642,7 +642,6 @@ fn reject_shadowing_type_parameters(tcx: TyCtxt, def_id: DefId) { let generics = tcx.generics_of(def_id); let parent = tcx.generics_of(generics.parent.unwrap()); let impl_params: FxHashMap<_, _> = parent.types() - .iter() .map(|tp| (tp.name, tp.def_id)) .collect(); diff --git a/src/librustc_typeck/impl_wf_check.rs b/src/librustc_typeck/impl_wf_check.rs index fe51e182044c8..60a998db3594f 100644 --- a/src/librustc_typeck/impl_wf_check.rs +++ b/src/librustc_typeck/impl_wf_check.rs @@ -105,7 +105,7 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, tcx, &impl_predicates.predicates.as_slice(), impl_trait_ref, &mut input_parameters); // Disallow ANY unconstrained type parameters. - for (ty_param, param) in impl_generics.types().iter().zip(impl_hir_generics.ty_params()) { + for (ty_param, param) in impl_generics.types().zip(impl_hir_generics.ty_params()) { let param_ty = ty::ParamTy::for_def(ty_param); if !input_parameters.contains(&ctp::Parameter::from(param_ty)) { report_unused_parameter(tcx, param.span, "type", ¶m_ty.to_string()); @@ -114,7 +114,7 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, // Disallow unconstrained lifetimes, but only if they appear in assoc types. let lifetimes_in_associated_types: FxHashSet<_> = impl_item_refs.iter() - .map(|item_ref| tcx.hir.local_def_id(item_ref.id.node_id)) + .map(|item_ref| tcx.hir.local_def_id(item_ref.id.node_id)) .filter(|&def_id| { let item = tcx.associated_item(def_id); item.kind == ty::AssociatedKind::Type && item.defaultness.has_value() @@ -122,15 +122,11 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, .flat_map(|def_id| { ctp::parameters_for(&tcx.type_of(def_id), true) }).collect(); - for (ty_lifetime, lifetime) in impl_generics.lifetimes().iter() - .zip(impl_hir_generics.lifetimes()) - { + for (ty_lifetime, lifetime) in impl_generics.lifetimes().zip(impl_hir_generics.lifetimes()) { let param = ctp::Parameter::from(ty_lifetime.to_early_bound_region_data()); - if - lifetimes_in_associated_types.contains(¶m) && // (*) - !input_parameters.contains(¶m) - { + if lifetimes_in_associated_types.contains(¶m) && // (*) + !input_parameters.contains(¶m) { report_unused_parameter(tcx, lifetime.lifetime.span, "lifetime", &lifetime.lifetime.name.name().to_string()); } diff --git a/src/librustdoc/clean/auto_trait.rs b/src/librustdoc/clean/auto_trait.rs index 7601bac67b066..ea7371f064726 100644 --- a/src/librustdoc/clean/auto_trait.rs +++ b/src/librustdoc/clean/auto_trait.rs @@ -226,7 +226,6 @@ impl<'a, 'tcx, 'rcx> AutoTraitFinder<'a, 'tcx, 'rcx> { fn generics_to_path_params(&self, generics: ty::Generics) -> hir::PathParameters { let lifetimes = HirVec::from_vec( generics.lifetimes() - .iter() .map(|p| { let name = if p.name == "" { hir::LifetimeName::Static diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index eec92184ac49d..25ca42db67e45 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1800,7 +1800,7 @@ impl<'a, 'tcx> Clean for (&'a ty::Generics, // Bounds in the type_params and lifetimes fields are repeated in the // predicates field (see rustc_typeck::collect::ty_generics), so remove // them. - let stripped_typarams = gens.types().iter().filter_map(|tp| { + let stripped_typarams = gens.types().filter_map(|tp| { if tp.name == keywords::SelfType.name().as_str() { assert_eq!(tp.index, 0); None From 5b4e2b7fbc6fb97c09d61f9785a8555044df59c1 Mon Sep 17 00:00:00 2001 From: varkor Date: Thu, 8 Mar 2018 12:10:13 +0000 Subject: [PATCH 06/40] Inline Generics::own_count --- src/librustc/ty/mod.rs | 6 +----- src/librustc/ty/subst.rs | 12 ++++++------ src/librustc_typeck/astconv.rs | 2 +- src/librustc_typeck/check/mod.rs | 2 +- src/librustc_typeck/collect.rs | 6 +++--- 5 files changed, 12 insertions(+), 16 deletions(-) diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index bf4bc9d3b3e24..45005fd543d1b 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -795,12 +795,8 @@ pub struct Generics { } impl<'a, 'gcx, 'tcx> Generics { - pub fn own_count(&self) -> usize { - self.params.len() - } - pub fn count(&self) -> usize { - self.parent_count + self.own_count() + self.parent_count + self.params.len() } pub fn lifetimes(&self) -> impl DoubleEndedIterator { diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index 2f4daf61a074c..ed8549af8b4bd 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -252,20 +252,20 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { } for def in &defs.params { + assert_eq!(def.index() as usize, substs.len()); let param = match def { ty::GenericParam::Lifetime(ref lt) => { - UnpackedKind::Lifetime(mk_region(lt, substs)) + mk_region(lt, substs).into() } ty::GenericParam::Type(ref ty) => { if skip_self { skip_self = false; continue } - UnpackedKind::Type(mk_type(ty, substs)) + mk_type(ty, substs).into() } }; - assert_eq!(def.index() as usize, substs.len()); - substs.push(param.pack()); + substs.push(param); } } @@ -333,7 +333,7 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { target_substs: &Substs<'tcx>) -> &'tcx Substs<'tcx> { let defs = tcx.generics_of(source_ancestor); - tcx.mk_substs(target_substs.iter().chain(&self[defs.own_count()..]).cloned()) + tcx.mk_substs(target_substs.iter().chain(&self[defs.params.len()..]).cloned()) } pub fn truncate_to(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>, generics: &ty::Generics) @@ -586,7 +586,7 @@ impl<'a, 'gcx, 'tcx> ty::TraitRef<'tcx> { ty::TraitRef { def_id: trait_id, - substs: tcx.intern_substs(&substs[..defs.own_count()]) + substs: tcx.intern_substs(&substs[..defs.params.len()]) } } } diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index fab8eec35f3b4..0de26ba584b19 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -1143,7 +1143,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { assert_eq!(substs.len(), generics.parent_count); // Fill in our own generics with the resolved lifetimes - assert_eq!(lifetimes.len(), generics.own_count()); + assert_eq!(lifetimes.len(), generics.params.len()); substs.extend(lifetimes.iter().map(|lt| Kind::from(self.ast_region_to_region(lt, None)))); debug!("impl_trait_ty_to_ty: final substs = {:?}", substs); diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index b6f3d5a80d64c..338f5cc867629 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -4754,7 +4754,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { (generics.parent_count, generics.has_self) } (Some((_, generics)), None) => { - (generics.own_count(), generics.has_self) + (generics.params.len(), generics.has_self) } (None, None) => (0, false) }; diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 0fc47b93f8f99..ca496aed34267 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -971,10 +971,10 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, .collect(); let lifetimes: Vec = - regions.into_iter().map(|lt| ty::GenericParam::Lifetime(lt)).collect(); + regions.into_iter().map(|lt| ty::GenericParam::Lifetime(lt)); let types: Vec = - types.into_iter().map(|ty| ty::GenericParam::Type(ty)).collect(); - let params = lifetimes.into_iter().chain(types.into_iter()).collect(); + types.into_iter().map(|ty| ty::GenericParam::Type(ty)); + let params = lifetimes.chain(types).collect(); tcx.alloc_generics(ty::Generics { parent: parent_def_id, From a9622dc5c67b06c9e6bac9dae9899aed3a4da9c1 Mon Sep 17 00:00:00 2001 From: varkor Date: Mon, 12 Mar 2018 12:47:03 +0000 Subject: [PATCH 07/40] Fix generics type parameter handling in miri --- src/librustc/infer/anon_types/mod.rs | 3 +-- src/librustc/ty/subst.rs | 2 +- src/librustc_mir/transform/const_prop.rs | 7 +++---- src/librustc_traits/dropck_outlives.rs | 3 ++- src/librustc_trans/back/symbol_export.rs | 2 +- src/librustc_typeck/check/wfcheck.rs | 4 ++-- src/librustc_typeck/collect.rs | 6 ++---- 7 files changed, 12 insertions(+), 15 deletions(-) diff --git a/src/librustc/infer/anon_types/mod.rs b/src/librustc/infer/anon_types/mod.rs index 9cf55e85693a4..1da6d9e174024 100644 --- a/src/librustc/infer/anon_types/mod.rs +++ b/src/librustc/infer/anon_types/mod.rs @@ -616,10 +616,9 @@ impl<'cx, 'gcx, 'tcx> TypeFolder<'gcx, 'tcx> for ReverseMapper<'cx, 'gcx, 'tcx> // during trans. let generics = self.tcx.generics_of(def_id); - let parent_len = generics.parent_count(); let substs = self.tcx.mk_substs(substs.substs.iter().enumerate().map( |(index, &kind)| { - if index < parent_len { + if index < generics.parent_count { // Accommodate missing regions in the parent kinds... self.fold_kind_mapping_missing_regions_to_empty(kind) } else { diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index ed8549af8b4bd..8acda182b976b 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -252,7 +252,6 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { } for def in &defs.params { - assert_eq!(def.index() as usize, substs.len()); let param = match def { ty::GenericParam::Lifetime(ref lt) => { mk_region(lt, substs).into() @@ -265,6 +264,7 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { mk_type(ty, substs).into() } }; + assert_eq!(def.index() as usize, substs.len()); substs.push(param); } } diff --git a/src/librustc_mir/transform/const_prop.rs b/src/librustc_mir/transform/const_prop.rs index 6b0217c8f7cbc..111783fff7e45 100644 --- a/src/librustc_mir/transform/const_prop.rs +++ b/src/librustc_mir/transform/const_prop.rs @@ -184,7 +184,7 @@ impl<'b, 'a, 'tcx:'b> ConstPropagator<'b, 'a, 'tcx> { // evaluate the promoted and replace the constant with the evaluated result Literal::Promoted { index } => { let generics = self.tcx.generics_of(self.source.def_id); - if generics.parent_types as usize + generics.types.len() > 0 { + if generics.has_type_parameters(self.tcx) { // FIXME: can't handle code with generics return None; } @@ -295,7 +295,7 @@ impl<'b, 'a, 'tcx:'b> ConstPropagator<'b, 'a, 'tcx> { self.source.def_id }; let generics = self.tcx.generics_of(def_id); - if generics.parent_types as usize + generics.types.len() > 0 { + if generics.has_type_parameters(self.tcx) { // FIXME: can't handle code with generics return None; } @@ -317,8 +317,7 @@ impl<'b, 'a, 'tcx:'b> ConstPropagator<'b, 'a, 'tcx> { self.source.def_id }; let generics = self.tcx.generics_of(def_id); - let has_generics = generics.parent_types as usize + generics.types.len() > 0; - if has_generics { + if generics.has_type_parameters(self.tcx) { // FIXME: can't handle code with generics return None; } diff --git a/src/librustc_traits/dropck_outlives.rs b/src/librustc_traits/dropck_outlives.rs index ce5707276ee1a..39326713df2a1 100644 --- a/src/librustc_traits/dropck_outlives.rs +++ b/src/librustc_traits/dropck_outlives.rs @@ -280,7 +280,8 @@ crate fn adt_dtorck_constraint<'a, 'tcx>( if def.is_phantom_data() { let result = DtorckConstraint { outlives: vec![], - dtorck_types: vec![tcx.mk_param_from_def(&tcx.generics_of(def_id).types[0])], + dtorck_types: vec![tcx.mk_param_from_def(&tcx.generics_of(def_id).types().next() + .expect("should be at least one type parameter"))], overflows: vec![], }; debug!("dtorck_constraint: {:?} => {:?}", def, result); diff --git a/src/librustc_trans/back/symbol_export.rs b/src/librustc_trans/back/symbol_export.rs index d8520b61d9157..c4a2d1798019d 100644 --- a/src/librustc_trans/back/symbol_export.rs +++ b/src/librustc_trans/back/symbol_export.rs @@ -117,7 +117,7 @@ fn reachable_non_generics_provider<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }) => { let def_id = tcx.hir.local_def_id(node_id); let generics = tcx.generics_of(def_id); - if (generics.parent_types == 0 && generics.types.is_empty()) && + if !generics.has_type_parameters(tcx) && // Functions marked with #[inline] are only ever translated // with "internal" linkage and are never exported. !Instance::mono(tcx, def_id).def.requires_local(tcx) { diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index 2fafee3a6582c..d5c4cfc8be7a9 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -369,13 +369,13 @@ fn check_where_clauses<'a, 'gcx, 'fcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'gcx>, let generics = tcx.generics_of(def_id); let is_our_default = |def: &ty::TypeParameterDef| - def.has_default && def.index >= generics.parent_count() as u32; + def.has_default && def.index >= generics.parent_count as u32; // Check that concrete defaults are well-formed. See test `type-check-defaults.rs`. // For example this forbids the declaration: // struct Foo> { .. } // Here the default `Vec<[u32]>` is not WF because `[u32]: Sized` does not hold. - for d in generics.types.iter().cloned().filter(is_our_default).map(|p| p.def_id) { + for d in generics.types().cloned().filter(is_our_default).map(|p| p.def_id) { let ty = fcx.tcx.type_of(d); // ignore dependent defaults -- that is, where the default of one type // parameter includes another (e.g., ). In those cases, we can't diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index ca496aed34267..0a5830e5f86e9 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -970,10 +970,8 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, .map(|param| (param.def_id, param.index)) .collect(); - let lifetimes: Vec = - regions.into_iter().map(|lt| ty::GenericParam::Lifetime(lt)); - let types: Vec = - types.into_iter().map(|ty| ty::GenericParam::Type(ty)); + let lifetimes = regions.into_iter().map(|lt| ty::GenericParam::Lifetime(lt)); + let types = types.into_iter().map(|ty| ty::GenericParam::Type(ty)); let params = lifetimes.chain(types).collect(); tcx.alloc_generics(ty::Generics { From 15d2759d909ccb4b3146654a76845ef5e1d5f6cb Mon Sep 17 00:00:00 2001 From: varkor Date: Thu, 12 Apr 2018 17:51:08 +0100 Subject: [PATCH 08/40] Rename `has_type_parameters` to `requires_monomorphization` --- src/librustc/ty/mod.rs | 8 +++++--- src/librustc_metadata/encoder.rs | 2 +- src/librustc_mir/monomorphize/collector.rs | 2 +- src/librustc_mir/transform/const_prop.rs | 6 +++--- src/librustc_trans/back/symbol_export.rs | 2 +- 5 files changed, 11 insertions(+), 9 deletions(-) diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 45005fd543d1b..218be48da24d5 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -819,13 +819,15 @@ impl<'a, 'gcx, 'tcx> Generics { }) } - pub fn has_type_parameters(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { - if self.types().count() != 0 { + pub fn requires_monomorphization(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { + if self.params.iter().any(|p| { + if let GenericParam::Type(_) = p { true } else { false } + }) { return true; } if let Some(parent_def_id) = self.parent { let parent = tcx.generics_of(parent_def_id); - parent.has_type_parameters(tcx) + parent.requires_monomorphization(tcx) } else { false } diff --git a/src/librustc_metadata/encoder.rs b/src/librustc_metadata/encoder.rs index 9ebffa4c744e1..3de90abd9663f 100644 --- a/src/librustc_metadata/encoder.rs +++ b/src/librustc_metadata/encoder.rs @@ -929,7 +929,7 @@ impl<'a, 'b: 'a, 'tcx: 'b> IsolatedEncoder<'a, 'b, 'tcx> { hir::ImplItemKind::Const(..) => true, hir::ImplItemKind::Method(ref sig, _) => { let generics = self.tcx.generics_of(def_id); - let needs_inline = (generics.has_type_parameters(self.tcx) || + let needs_inline = (generics.requires_monomorphization(self.tcx) || tcx.trans_fn_attrs(def_id).requests_inline()) && !self.metadata_output_only(); let is_const_fn = sig.constness == hir::Constness::Const; diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index 8646df02e5108..2bc4e651dd357 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -1076,7 +1076,7 @@ impl<'b, 'a, 'v> RootCollector<'b, 'a, 'v> { fn item_has_type_parameters<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> bool { let generics = tcx.generics_of(def_id); - generics.has_type_parameters(tcx) + generics.requires_monomorphization(tcx) } fn create_mono_items_for_default_impls<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, diff --git a/src/librustc_mir/transform/const_prop.rs b/src/librustc_mir/transform/const_prop.rs index 111783fff7e45..80603959ec202 100644 --- a/src/librustc_mir/transform/const_prop.rs +++ b/src/librustc_mir/transform/const_prop.rs @@ -184,7 +184,7 @@ impl<'b, 'a, 'tcx:'b> ConstPropagator<'b, 'a, 'tcx> { // evaluate the promoted and replace the constant with the evaluated result Literal::Promoted { index } => { let generics = self.tcx.generics_of(self.source.def_id); - if generics.has_type_parameters(self.tcx) { + if generics.requires_monomorphization(self.tcx) { // FIXME: can't handle code with generics return None; } @@ -295,7 +295,7 @@ impl<'b, 'a, 'tcx:'b> ConstPropagator<'b, 'a, 'tcx> { self.source.def_id }; let generics = self.tcx.generics_of(def_id); - if generics.has_type_parameters(self.tcx) { + if generics.requires_monomorphization(self.tcx) { // FIXME: can't handle code with generics return None; } @@ -317,7 +317,7 @@ impl<'b, 'a, 'tcx:'b> ConstPropagator<'b, 'a, 'tcx> { self.source.def_id }; let generics = self.tcx.generics_of(def_id); - if generics.has_type_parameters(self.tcx) { + if generics.requires_monomorphization(self.tcx) { // FIXME: can't handle code with generics return None; } diff --git a/src/librustc_trans/back/symbol_export.rs b/src/librustc_trans/back/symbol_export.rs index c4a2d1798019d..d77855220691d 100644 --- a/src/librustc_trans/back/symbol_export.rs +++ b/src/librustc_trans/back/symbol_export.rs @@ -117,7 +117,7 @@ fn reachable_non_generics_provider<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }) => { let def_id = tcx.hir.local_def_id(node_id); let generics = tcx.generics_of(def_id); - if !generics.has_type_parameters(tcx) && + if !generics.requires_monomorphization(tcx) && // Functions marked with #[inline] are only ever translated // with "internal" linkage and are never exported. !Instance::mono(tcx, def_id).def.requires_local(tcx) { From 178a8f1139ddad2aa59ce0e54cf10659dc4eed30 Mon Sep 17 00:00:00 2001 From: varkor Date: Thu, 12 Apr 2018 17:53:29 +0100 Subject: [PATCH 09/40] Rename GenericParam to GenericParamDef --- src/librustc/ich/impls_ty.rs | 2 +- src/librustc/ty/mod.rs | 22 +++++++++++----------- src/librustc/ty/subst.rs | 4 ++-- src/librustc_typeck/collect.rs | 4 ++-- src/librustdoc/clean/auto_trait.rs | 6 +++--- src/librustdoc/clean/mod.rs | 30 +++++++++++++++--------------- src/librustdoc/html/format.rs | 6 +++--- src/librustdoc/html/render.rs | 2 +- 8 files changed, 38 insertions(+), 38 deletions(-) diff --git a/src/librustc/ich/impls_ty.rs b/src/librustc/ich/impls_ty.rs index dd09af10bd934..35c92dd48aa40 100644 --- a/src/librustc/ich/impls_ty.rs +++ b/src/librustc/ich/impls_ty.rs @@ -753,7 +753,7 @@ impl<'a> HashStable> for ty::Generics { } } -impl_stable_hash_for!(enum ty::GenericParam { +impl_stable_hash_for!(enum ty::GenericParamDef { Lifetime(lt), Type(ty) }); diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 218be48da24d5..3fe12e342ebab 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -758,16 +758,16 @@ impl ty::EarlyBoundRegion { } #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] -pub enum GenericParam { +pub enum GenericParamDef { Lifetime(RegionParameterDef), Type(TypeParameterDef), } -impl GenericParam { +impl GenericParamDef { pub fn index(&self) -> u32 { match self { - GenericParam::Lifetime(lt) => lt.index, - GenericParam::Type(ty) => ty.index, + GenericParamDef::Lifetime(lt) => lt.index, + GenericParamDef::Type(ty) => ty.index, } } } @@ -785,7 +785,7 @@ impl GenericParam { pub struct Generics { pub parent: Option, pub parent_count: usize, - pub params: Vec, + pub params: Vec, /// Reverse map to each `TypeParameterDef`'s `index` field pub type_param_to_index: FxHashMap, @@ -801,7 +801,7 @@ impl<'a, 'gcx, 'tcx> Generics { pub fn lifetimes(&self) -> impl DoubleEndedIterator { self.params.iter().filter_map(|p| { - if let GenericParam::Lifetime(lt) = p { + if let GenericParamDef::Lifetime(lt) = p { Some(lt) } else { None @@ -811,7 +811,7 @@ impl<'a, 'gcx, 'tcx> Generics { pub fn types(&self) -> impl DoubleEndedIterator { self.params.iter().filter_map(|p| { - if let GenericParam::Type(ty) = p { + if let GenericParamDef::Type(ty) = p { Some(ty) } else { None @@ -821,7 +821,7 @@ impl<'a, 'gcx, 'tcx> Generics { pub fn requires_monomorphization(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { if self.params.iter().any(|p| { - if let GenericParam::Type(_) = p { true } else { false } + if let GenericParamDef::Type(_) = p { true } else { false } }) { return true; } @@ -841,7 +841,7 @@ impl<'a, 'gcx, 'tcx> Generics { if let Some(index) = param.index.checked_sub(self.parent_count as u32) { // We're currently assuming that lifetimes precede other generic parameters. match self.params[index as usize - self.has_self as usize] { - ty::GenericParam::Lifetime(ref lt) => lt, + ty::GenericParamDef::Lifetime(ref lt) => lt, _ => bug!("expected region parameter, but found another generic parameter") } } else { @@ -891,13 +891,13 @@ impl<'a, 'gcx, 'tcx> Generics { if let Some(_) = (idx as usize).checked_sub(type_param_offset) { assert!(!is_separated_self, "found a Self after type_param_offset"); match self.params[idx as usize] { - ty::GenericParam::Type(ref ty) => ty, + ty::GenericParamDef::Type(ref ty) => ty, _ => bug!("expected type parameter, but found another generic parameter") } } else { assert!(is_separated_self, "non-Self param before type_param_offset"); match self.params[type_param_offset] { - ty::GenericParam::Type(ref ty) => ty, + ty::GenericParamDef::Type(ref ty) => ty, _ => bug!("expected type parameter, but found another generic parameter") } } diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index 8acda182b976b..ed342e1d37e57 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -253,10 +253,10 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { for def in &defs.params { let param = match def { - ty::GenericParam::Lifetime(ref lt) => { + ty::GenericParamDef::Lifetime(ref lt) => { mk_region(lt, substs).into() } - ty::GenericParam::Type(ref ty) => { + ty::GenericParamDef::Type(ref ty) => { if skip_self { skip_self = false; continue diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 0a5830e5f86e9..03b685c82e7c8 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -970,8 +970,8 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, .map(|param| (param.def_id, param.index)) .collect(); - let lifetimes = regions.into_iter().map(|lt| ty::GenericParam::Lifetime(lt)); - let types = types.into_iter().map(|ty| ty::GenericParam::Type(ty)); + let lifetimes = regions.into_iter().map(|lt| ty::GenericParamDef::Lifetime(lt)); + let types = types.into_iter().map(|ty| ty::GenericParamDef::Type(ty)); let params = lifetimes.chain(types).collect(); tcx.alloc_generics(ty::Generics { diff --git a/src/librustdoc/clean/auto_trait.rs b/src/librustdoc/clean/auto_trait.rs index ea7371f064726..f35a4c080e50e 100644 --- a/src/librustdoc/clean/auto_trait.rs +++ b/src/librustdoc/clean/auto_trait.rs @@ -491,7 +491,7 @@ impl<'a, 'tcx, 'rcx> AutoTraitFinder<'a, 'tcx, 'rcx> { &self, tcx: TyCtxt<'b, 'c, 'd>, pred: ty::Predicate<'d>, - ) -> FxHashSet { + ) -> FxHashSet { pred.walk_tys() .flat_map(|t| { let mut regions = FxHashSet(); @@ -502,7 +502,7 @@ impl<'a, 'tcx, 'rcx> AutoTraitFinder<'a, 'tcx, 'rcx> { // We only care about late bound regions, as we need to add them // to the 'for<>' section &ty::ReLateBound(_, ty::BoundRegion::BrNamed(_, name)) => { - Some(GenericParam::Lifetime(Lifetime(name.to_string()))) + Some(GenericParamDef::Lifetime(Lifetime(name.to_string()))) } &ty::ReVar(_) | &ty::ReEarlyBound(_) => None, _ => panic!("Unexpected region type {:?}", r), @@ -850,7 +850,7 @@ impl<'a, 'tcx, 'rcx> AutoTraitFinder<'a, 'tcx, 'rcx> { for p in generic_params.iter_mut() { match p { - &mut GenericParam::Type(ref mut ty) => { + &mut GenericParamDef::Type(ref mut ty) => { // We never want something like 'impl' ty.default.take(); diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 25ca42db67e45..4797b5a912a70 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1484,7 +1484,7 @@ impl<'a, 'tcx> Clean for (&'a ty::TraitRef<'tcx>, Vec if let &ty::RegionKind::ReLateBound(..) = *reg { debug!(" hit an ReLateBound {:?}", reg); if let Some(lt) = reg.clean(cx) { - late_bounds.push(GenericParam::Lifetime(lt)); + late_bounds.push(GenericParamDef::Lifetime(lt)); } } } @@ -1718,14 +1718,14 @@ impl<'tcx> Clean for ty::ProjectionTy<'tcx> { } #[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] -pub enum GenericParam { +pub enum GenericParamDef { Lifetime(Lifetime), Type(TyParam), } -impl GenericParam { +impl GenericParamDef { pub fn is_synthetic_type_param(&self) -> bool { - if let GenericParam::Type(ref t) = *self { + if let GenericParamDef::Type(ref t) = *self { t.synthetic.is_some() } else { false @@ -1733,11 +1733,11 @@ impl GenericParam { } } -impl Clean for hir::GenericParam { - fn clean(&self, cx: &DocContext) -> GenericParam { +impl Clean for hir::GenericParam { + fn clean(&self, cx: &DocContext) -> GenericParamDef { match *self { - hir::GenericParam::Lifetime(ref l) => GenericParam::Lifetime(l.clean(cx)), - hir::GenericParam::Type(ref t) => GenericParam::Type(t.clean(cx)), + hir::GenericParam::Lifetime(ref l) => GenericParamDef::Lifetime(l.clean(cx)), + hir::GenericParam::Type(ref t) => GenericParamDef::Type(t.clean(cx)), } } } @@ -1745,7 +1745,7 @@ impl Clean for hir::GenericParam { // maybe use a Generic enum and use Vec? #[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Default, Hash)] pub struct Generics { - pub params: Vec, + pub params: Vec, pub where_predicates: Vec, } @@ -1774,7 +1774,7 @@ impl Clean for hir::Generics { WherePredicate::BoundPredicate { ty: Generic(ref name), ref mut bounds } => { if bounds.is_empty() { for param in &mut g.params { - if let GenericParam::Type(ref mut type_param) = *param { + if let GenericParamDef::Type(ref mut type_param) = *param { if &type_param.name == name { mem::swap(bounds, &mut type_param.bounds); break @@ -1851,11 +1851,11 @@ impl<'a, 'tcx> Clean for (&'a ty::Generics, Generics { params: gens.lifetimes() .into_iter() - .map(|lp| GenericParam::Lifetime(lp.clean(cx))) + .map(|lp| GenericParamDef::Lifetime(lp.clean(cx))) .chain( simplify::ty_params(stripped_typarams) .into_iter() - .map(|tp| GenericParam::Type(tp)) + .map(|tp| GenericParamDef::Type(tp)) ) .collect(), where_predicates: simplify::where_clauses(cx, where_predicates), @@ -2348,7 +2348,7 @@ impl<'tcx> Clean for ty::AssociatedItem { #[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] pub struct PolyTrait { pub trait_: Type, - pub generic_params: Vec, + pub generic_params: Vec, } /// A representation of a Type suitable for hyperlinking purposes. Ideally one can get the original @@ -3413,7 +3413,7 @@ impl Clean for doctree::Typedef { #[derive(Clone, RustcEncodable, RustcDecodable, PartialEq, Eq, Debug, Hash)] pub struct BareFunctionDecl { pub unsafety: hir::Unsafety, - pub generic_params: Vec, + pub generic_params: Vec, pub decl: FnDecl, pub abi: Abi, } @@ -4172,7 +4172,7 @@ struct RegionDeps<'tcx> { #[derive(Eq, PartialEq, Hash, Debug)] enum SimpleBound { RegionBound(Lifetime), - TraitBound(Vec, Vec, Vec, hir::TraitBoundModifier) + TraitBound(Vec, Vec, Vec, hir::TraitBoundModifier) } enum AutoTraitResult { diff --git a/src/librustdoc/html/format.rs b/src/librustdoc/html/format.rs index a9a4c5113747e..0323e2b1f522e 100644 --- a/src/librustdoc/html/format.rs +++ b/src/librustdoc/html/format.rs @@ -117,11 +117,11 @@ impl<'a> fmt::Display for TyParamBounds<'a> { } } -impl fmt::Display for clean::GenericParam { +impl fmt::Display for clean::GenericParamDef { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { match *self { - clean::GenericParam::Lifetime(ref lp) => write!(f, "{}", lp), - clean::GenericParam::Type(ref tp) => { + clean::GenericParamDef::Lifetime(ref lp) => write!(f, "{}", lp), + clean::GenericParamDef::Type(ref tp) => { f.write_str(&tp.name)?; if !tp.bounds.is_empty() { diff --git a/src/librustdoc/html/render.rs b/src/librustdoc/html/render.rs index 32cfb05bbe49b..5be9000d2a5ce 100644 --- a/src/librustdoc/html/render.rs +++ b/src/librustdoc/html/render.rs @@ -1437,7 +1437,7 @@ impl DocFolder for Cache { impl<'a> Cache { fn generics(&mut self, generics: &clean::Generics) { for param in &generics.params { - if let clean::GenericParam::Type(ref typ) = *param { + if let clean::GenericParamDef::Type(ref typ) = *param { self.typarams.insert(typ.did, typ.name.clone()); } } From 06f0a7c89fb51934951c07820e759685c4f6c197 Mon Sep 17 00:00:00 2001 From: varkor Date: Thu, 12 Apr 2018 20:29:44 +0100 Subject: [PATCH 10/40] Rename TypeParameterDef -> TypeParamDef and RegionParameterDef -> RegionParamDef --- src/librustc/ich/impls_ty.rs | 8 ++++---- src/librustc/infer/mod.rs | 4 ++-- src/librustc/ty/context.rs | 2 +- src/librustc/ty/mod.rs | 22 +++++++++++----------- src/librustc/ty/sty.rs | 2 +- src/librustc/ty/subst.rs | 20 ++++++++++---------- src/librustc/util/ppaux.rs | 8 ++++---- src/librustc_typeck/astconv.rs | 10 +++++----- src/librustc_typeck/check/mod.rs | 4 ++-- src/librustc_typeck/check/wfcheck.rs | 2 +- src/librustc_typeck/collect.rs | 10 +++++----- src/librustdoc/clean/auto_trait.rs | 2 +- src/librustdoc/clean/mod.rs | 4 ++-- 13 files changed, 49 insertions(+), 49 deletions(-) diff --git a/src/librustc/ich/impls_ty.rs b/src/librustc/ich/impls_ty.rs index 35c92dd48aa40..d0427ef4be227 100644 --- a/src/librustc/ich/impls_ty.rs +++ b/src/librustc/ich/impls_ty.rs @@ -738,7 +738,7 @@ impl<'a> HashStable> for ty::Generics { ref parent_count, ref params, - // Reverse map to each `TypeParameterDef`'s `index` field, from + // Reverse map to each `TypeParamDef`'s `index` field, from // `def_id.index` (`def_id.krate` is the same as the item's). type_param_to_index: _, // Don't hash this has_self, @@ -759,11 +759,11 @@ impl_stable_hash_for!(enum ty::GenericParamDef { }); impl<'a> HashStable> -for ty::RegionParameterDef { +for ty::RegionParamDef { fn hash_stable(&self, hcx: &mut StableHashingContext<'a>, hasher: &mut StableHasher) { - let ty::RegionParameterDef { + let ty::RegionParamDef { name, def_id, index, @@ -777,7 +777,7 @@ for ty::RegionParameterDef { } } -impl_stable_hash_for!(struct ty::TypeParameterDef { +impl_stable_hash_for!(struct ty::TypeParamDef { name, def_id, index, diff --git a/src/librustc/infer/mod.rs b/src/librustc/infer/mod.rs index c62e7f8d9b635..a594231441a9b 100644 --- a/src/librustc/infer/mod.rs +++ b/src/librustc/infer/mod.rs @@ -909,7 +909,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { /// region parameter definition. pub fn region_var_for_def(&self, span: Span, - def: &ty::RegionParameterDef) + def: &ty::RegionParamDef) -> ty::Region<'tcx> { self.next_region_var(EarlyBoundRegion(span, def.name)) } @@ -924,7 +924,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { /// as the substitutions for the default, `(T, U)`. pub fn type_var_for_def(&self, span: Span, - def: &ty::TypeParameterDef) + def: &ty::TypeParamDef) -> Ty<'tcx> { let ty_var_id = self.type_variables .borrow_mut() diff --git a/src/librustc/ty/context.rs b/src/librustc/ty/context.rs index dcd20465fbb9a..7391d1872520d 100644 --- a/src/librustc/ty/context.rs +++ b/src/librustc/ty/context.rs @@ -2467,7 +2467,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { self.mk_param(0, keywords::SelfType.name().as_interned_str()) } - pub fn mk_param_from_def(self, def: &ty::TypeParameterDef) -> Ty<'tcx> { + pub fn mk_param_from_def(self, def: &ty::TypeParamDef) -> Ty<'tcx> { self.mk_param(def.index, def.name) } diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 3fe12e342ebab..59b88567a0d1c 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -710,7 +710,7 @@ pub enum IntVarValue { pub struct FloatVarValue(pub ast::FloatTy); #[derive(Copy, Clone, RustcEncodable, RustcDecodable)] -pub struct TypeParameterDef { +pub struct TypeParamDef { pub name: InternedString, pub def_id: DefId, pub index: u32, @@ -726,7 +726,7 @@ pub struct TypeParameterDef { } #[derive(Copy, Clone, RustcEncodable, RustcDecodable)] -pub struct RegionParameterDef { +pub struct RegionParamDef { pub name: InternedString, pub def_id: DefId, pub index: u32, @@ -737,7 +737,7 @@ pub struct RegionParameterDef { pub pure_wrt_drop: bool, } -impl RegionParameterDef { +impl RegionParamDef { pub fn to_early_bound_region_data(&self) -> ty::EarlyBoundRegion { ty::EarlyBoundRegion { def_id: self.def_id, @@ -759,8 +759,8 @@ impl ty::EarlyBoundRegion { #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] pub enum GenericParamDef { - Lifetime(RegionParameterDef), - Type(TypeParameterDef), + Lifetime(RegionParamDef), + Type(TypeParamDef), } impl GenericParamDef { @@ -787,7 +787,7 @@ pub struct Generics { pub parent_count: usize, pub params: Vec, - /// Reverse map to each `TypeParameterDef`'s `index` field + /// Reverse map to each `TypeParamDef`'s `index` field pub type_param_to_index: FxHashMap, pub has_self: bool, @@ -799,7 +799,7 @@ impl<'a, 'gcx, 'tcx> Generics { self.parent_count + self.params.len() } - pub fn lifetimes(&self) -> impl DoubleEndedIterator { + pub fn lifetimes(&self) -> impl DoubleEndedIterator { self.params.iter().filter_map(|p| { if let GenericParamDef::Lifetime(lt) = p { Some(lt) @@ -809,7 +809,7 @@ impl<'a, 'gcx, 'tcx> Generics { }) } - pub fn types(&self) -> impl DoubleEndedIterator { + pub fn types(&self) -> impl DoubleEndedIterator { self.params.iter().filter_map(|p| { if let GenericParamDef::Type(ty) = p { Some(ty) @@ -836,7 +836,7 @@ impl<'a, 'gcx, 'tcx> Generics { pub fn region_param(&'tcx self, param: &EarlyBoundRegion, tcx: TyCtxt<'a, 'gcx, 'tcx>) - -> &'tcx RegionParameterDef + -> &'tcx RegionParamDef { if let Some(index) = param.index.checked_sub(self.parent_count as u32) { // We're currently assuming that lifetimes precede other generic parameters. @@ -850,11 +850,11 @@ impl<'a, 'gcx, 'tcx> Generics { } } - /// Returns the `TypeParameterDef` associated with this `ParamTy`. + /// Returns the `TypeParamDef` associated with this `ParamTy`. pub fn type_param(&'tcx self, param: &ParamTy, tcx: TyCtxt<'a, 'gcx, 'tcx>) - -> &TypeParameterDef { + -> &TypeParamDef { if let Some(idx) = param.idx.checked_sub(self.parent_count as u32) { // non-Self type parameters are always offset by exactly // `self.regions.len()`. In the absence of a Self, this is obvious, diff --git a/src/librustc/ty/sty.rs b/src/librustc/ty/sty.rs index c1e3153c4618e..01ebf3666f9c2 100644 --- a/src/librustc/ty/sty.rs +++ b/src/librustc/ty/sty.rs @@ -928,7 +928,7 @@ impl<'a, 'gcx, 'tcx> ParamTy { ParamTy::new(0, keywords::SelfType.name().as_interned_str()) } - pub fn for_def(def: &ty::TypeParameterDef) -> ParamTy { + pub fn for_def(def: &ty::TypeParamDef) -> ParamTy { ParamTy::new(def.index, def.name) } diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index ed342e1d37e57..bec343afca82d 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -196,8 +196,8 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { mut mk_region: FR, mut mk_type: FT) -> &'tcx Substs<'tcx> - where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, - FT: FnMut(&ty::TypeParameterDef, &[Kind<'tcx>]) -> Ty<'tcx> { + where FR: FnMut(&ty::RegionParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, + FT: FnMut(&ty::TypeParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { let defs = tcx.generics_of(def_id); let mut substs = Vec::with_capacity(defs.count()); Substs::fill_item(&mut substs, tcx, defs, &mut mk_region, &mut mk_type); @@ -210,8 +210,8 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { mut mk_region: FR, mut mk_type: FT) -> &'tcx Substs<'tcx> - where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, - FT: FnMut(&ty::TypeParameterDef, &[Kind<'tcx>]) -> Ty<'tcx> + where FR: FnMut(&ty::RegionParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, + FT: FnMut(&ty::TypeParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { let defs = tcx.generics_of(def_id); let mut result = Vec::with_capacity(defs.count()); @@ -225,8 +225,8 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { defs: &ty::Generics, mk_region: &mut FR, mk_type: &mut FT) - where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, - FT: FnMut(&ty::TypeParameterDef, &[Kind<'tcx>]) -> Ty<'tcx> { + where FR: FnMut(&ty::RegionParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, + FT: FnMut(&ty::TypeParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { if let Some(def_id) = defs.parent { let parent_defs = tcx.generics_of(def_id); @@ -239,8 +239,8 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { defs: &ty::Generics, mk_region: &mut FR, mk_type: &mut FT) - where FR: FnMut(&ty::RegionParameterDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, - FT: FnMut(&ty::TypeParameterDef, &[Kind<'tcx>]) -> Ty<'tcx> { + where FR: FnMut(&ty::RegionParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, + FT: FnMut(&ty::TypeParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { // Handle Self first, before all regions. let mut types = defs.types(); let mut skip_self = defs.parent.is_none() && defs.has_self; @@ -314,12 +314,12 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { } #[inline] - pub fn type_for_def(&self, ty_param_def: &ty::TypeParameterDef) -> Ty<'tcx> { + pub fn type_for_def(&self, ty_param_def: &ty::TypeParamDef) -> Ty<'tcx> { self.type_at(ty_param_def.index as usize) } #[inline] - pub fn region_for_def(&self, def: &ty::RegionParameterDef) -> ty::Region<'tcx> { + pub fn region_for_def(&self, def: &ty::RegionParamDef) -> ty::Region<'tcx> { self.region_at(def.index as usize) } diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index 431fd59e02cb3..1a0c5f4a78a42 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -588,18 +588,18 @@ define_print! { } } -impl fmt::Debug for ty::TypeParameterDef { +impl fmt::Debug for ty::TypeParamDef { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - write!(f, "TypeParameterDef({}, {:?}, {})", + write!(f, "TypeParamDef({}, {:?}, {})", self.name, self.def_id, self.index) } } -impl fmt::Debug for ty::RegionParameterDef { +impl fmt::Debug for ty::RegionParamDef { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - write!(f, "RegionParameterDef({}, {:?}, {})", + write!(f, "RegionParamDef({}, {:?}, {})", self.name, self.def_id, self.index) diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index 0de26ba584b19..a6e24f155090d 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -43,7 +43,7 @@ pub trait AstConv<'gcx, 'tcx> { -> ty::GenericPredicates<'tcx>; /// What lifetime should we use when a lifetime is omitted (and not elided)? - fn re_infer(&self, span: Span, _def: Option<&ty::RegionParameterDef>) + fn re_infer(&self, span: Span, _def: Option<&ty::RegionParamDef>) -> Option>; /// What type should we use when a type is omitted? @@ -51,7 +51,7 @@ pub trait AstConv<'gcx, 'tcx> { /// Same as ty_infer, but with a known type parameter definition. fn ty_infer_for_def(&self, - _def: &ty::TypeParameterDef, + _def: &ty::TypeParamDef, span: Span) -> Ty<'tcx> { self.ty_infer(span) } @@ -95,7 +95,7 @@ const TRAIT_OBJECT_DUMMY_SELF: ty::TypeVariants<'static> = ty::TyInfer(ty::Fresh impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { pub fn ast_region_to_region(&self, lifetime: &hir::Lifetime, - def: Option<&ty::RegionParameterDef>) + def: Option<&ty::RegionParamDef>) -> ty::Region<'tcx> { let tcx = self.tcx(); @@ -228,7 +228,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { } let is_object = self_ty.map_or(false, |ty| ty.sty == TRAIT_OBJECT_DUMMY_SELF); - let default_needs_object_self = |p: &ty::TypeParameterDef| { + let default_needs_object_self = |p: &ty::TypeParamDef| { if is_object && p.has_default { if tcx.at(span).type_of(p.def_id).has_self_ty() { // There is no suitable inference default for a type parameter @@ -1301,7 +1301,7 @@ fn split_auto_traits<'a, 'b, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, } fn check_type_argument_count(tcx: TyCtxt, span: Span, supplied: usize, - ty_param_defs: &[&ty::TypeParameterDef]) { + ty_param_defs: &[&ty::TypeParamDef]) { let accepted = ty_param_defs.len(); let required = ty_param_defs.iter().take_while(|x| !x.has_default).count(); if supplied < required { diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 338f5cc867629..b427020908dc1 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -1730,7 +1730,7 @@ impl<'a, 'gcx, 'tcx> AstConv<'gcx, 'tcx> for FnCtxt<'a, 'gcx, 'tcx> { } } - fn re_infer(&self, span: Span, def: Option<&ty::RegionParameterDef>) + fn re_infer(&self, span: Span, def: Option<&ty::RegionParamDef>) -> Option> { let v = match def { Some(def) => infer::EarlyBoundRegion(span, def.name), @@ -1744,7 +1744,7 @@ impl<'a, 'gcx, 'tcx> AstConv<'gcx, 'tcx> for FnCtxt<'a, 'gcx, 'tcx> { } fn ty_infer_for_def(&self, - ty_param_def: &ty::TypeParameterDef, + ty_param_def: &ty::TypeParamDef, span: Span) -> Ty<'tcx> { self.type_var_for_def(span, ty_param_def) } diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index d5c4cfc8be7a9..ae77896668744 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -368,7 +368,7 @@ fn check_where_clauses<'a, 'gcx, 'fcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'gcx>, let mut substituted_predicates = Vec::new(); let generics = tcx.generics_of(def_id); - let is_our_default = |def: &ty::TypeParameterDef| + let is_our_default = |def: &ty::TypeParamDef| def.has_default && def.index >= generics.parent_count as u32; // Check that concrete defaults are well-formed. See test `type-check-defaults.rs`. diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 03b685c82e7c8..869ae779c1747 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -181,7 +181,7 @@ impl<'a, 'tcx> AstConv<'tcx, 'tcx> for ItemCtxt<'a, 'tcx> { self.tcx.at(span).type_param_predicates((self.item_def_id, def_id)) } - fn re_infer(&self, _span: Span, _def: Option<&ty::RegionParameterDef>) + fn re_infer(&self, _span: Span, _def: Option<&ty::RegionParamDef>) -> Option> { None } @@ -840,7 +840,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, // the node id for the Self type parameter. let param_id = item.id; - opt_self = Some(ty::TypeParameterDef { + opt_self = Some(ty::TypeParamDef { index: 0, name: keywords::SelfType.name().as_interned_str(), def_id: tcx.hir.local_def_id(param_id), @@ -886,7 +886,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let early_lifetimes = early_bound_lifetimes_from_generics(tcx, ast_generics); let regions = early_lifetimes.enumerate().map(|(i, l)| { - ty::RegionParameterDef { + ty::RegionParamDef { name: l.lifetime.name.name().as_interned_str(), index: own_start + i as u32, def_id: tcx.hir.local_def_id(l.lifetime.id), @@ -915,7 +915,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } } - ty::TypeParameterDef { + ty::TypeParamDef { index: type_start + i as u32, name: p.name.as_interned_str(), def_id: tcx.hir.local_def_id(p.id), @@ -940,7 +940,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }; for (i, &arg) in dummy_args.iter().enumerate() { - types.push(ty::TypeParameterDef { + types.push(ty::TypeParamDef { index: type_start + i as u32, name: Symbol::intern(arg).as_interned_str(), def_id, diff --git a/src/librustdoc/clean/auto_trait.rs b/src/librustdoc/clean/auto_trait.rs index f35a4c080e50e..11bcbc1fe7e30 100644 --- a/src/librustdoc/clean/auto_trait.rs +++ b/src/librustdoc/clean/auto_trait.rs @@ -256,7 +256,7 @@ impl<'a, 'tcx, 'rcx> AutoTraitFinder<'a, 'tcx, 'rcx> { } } - fn ty_param_to_ty(&self, param: ty::TypeParameterDef) -> hir::Ty { + fn ty_param_to_ty(&self, param: ty::TypeParamDef) -> hir::Ty { debug!("ty_param_to_ty({:?}) {:?}", param, param.def_id); hir::Ty { id: ast::DUMMY_NODE_ID, diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 4797b5a912a70..31f227373cb93 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1336,7 +1336,7 @@ impl Clean for hir::TyParam { } } -impl<'tcx> Clean for ty::TypeParameterDef { +impl<'tcx> Clean for ty::TypeParamDef { fn clean(&self, cx: &DocContext) -> TyParam { cx.renderinfo.borrow_mut().external_typarams.insert(self.def_id, self.name.clean(cx)); TyParam { @@ -1577,7 +1577,7 @@ impl Clean for hir::LifetimeDef { } } -impl Clean for ty::RegionParameterDef { +impl Clean for ty::RegionParamDef { fn clean(&self, _: &DocContext) -> Lifetime { Lifetime(self.name.to_string()) } From cadf96e8e1523ed5928fd476f34e1b34c445afbe Mon Sep 17 00:00:00 2001 From: varkor Date: Thu, 12 Apr 2018 20:36:18 +0100 Subject: [PATCH 11/40] Fix tidy errors caused by renaming --- src/librustc/hir/lowering.rs | 12 +++++++----- src/librustc/hir/print.rs | 5 ++++- src/libsyntax/visit.rs | 4 +++- src/libsyntax_ext/deriving/generic/mod.rs | 6 +++++- src/libsyntax_ext/deriving/generic/ty.rs | 9 +++++++-- 5 files changed, 26 insertions(+), 10 deletions(-) diff --git a/src/librustc/hir/lowering.rs b/src/librustc/hir/lowering.rs index 735598fd436c8..fd2a328f2fdfa 100644 --- a/src/librustc/hir/lowering.rs +++ b/src/librustc/hir/lowering.rs @@ -1895,11 +1895,13 @@ impl<'a> LoweringContext<'a> { GenericParam::Lifetime(ref lifetime_def) => { hir::GenericParam::Lifetime(self.lower_lifetime_def(lifetime_def)) } - GenericParam::Type(ref ty_param) => hir::GenericParam::Type(self.lower_ty_param( - ty_param, - add_bounds.get(&ty_param.id).map_or(&[][..], |x| &x), - itctx, - )), + GenericParam::Type(ref ty_param) => { + hir::GenericParam::Type(self.lower_ty_param( + ty_param, + add_bounds.get(&ty_param.id).map_or(&[][..], |x| &x), + itctx, + )) + } }) .collect() } diff --git a/src/librustc/hir/print.rs b/src/librustc/hir/print.rs index 3943c30127d6f..2dc46f5f69d70 100644 --- a/src/librustc/hir/print.rs +++ b/src/librustc/hir/print.rs @@ -2043,7 +2043,10 @@ impl<'a> State<'a> { Ok(()) } - pub fn print_generic_params(&mut self, generic_params: &[hir::GenericParam]) -> io::Result<()> { + pub fn print_generic_params(&mut self, + generic_params: &[hir::GenericParam]) + -> io::Result<()> + { if !generic_params.is_empty() { self.s.word("<")?; diff --git a/src/libsyntax/visit.rs b/src/libsyntax/visit.rs index 40d59d3ff8b8d..3f9e0b9fbb5d6 100644 --- a/src/libsyntax/visit.rs +++ b/src/libsyntax/visit.rs @@ -72,7 +72,9 @@ pub trait Visitor<'ast>: Sized { fn visit_expr(&mut self, ex: &'ast Expr) { walk_expr(self, ex) } fn visit_expr_post(&mut self, _ex: &'ast Expr) { } fn visit_ty(&mut self, t: &'ast Ty) { walk_ty(self, t) } - fn visit_generic_param(&mut self, param: &'ast GenericParam) { walk_generic_param(self, param) } + fn visit_generic_param(&mut self, param: &'ast GenericParam) { + walk_generic_param(self, param) + } fn visit_generics(&mut self, g: &'ast Generics) { walk_generics(self, g) } fn visit_where_predicate(&mut self, p: &'ast WherePredicate) { walk_where_predicate(self, p) diff --git a/src/libsyntax_ext/deriving/generic/mod.rs b/src/libsyntax_ext/deriving/generic/mod.rs index 80f65957c39a2..ddf3ae41faa3b 100644 --- a/src/libsyntax_ext/deriving/generic/mod.rs +++ b/src/libsyntax_ext/deriving/generic/mod.rs @@ -570,7 +570,11 @@ impl<'a> TraitDef<'a> { bounds.push((*declared_bound).clone()); } - GenericParam::Type(cx.typaram(self.span, ty_param.ident, vec![], bounds, None)) + GenericParam::Type(cx.typaram(self.span, + ty_param.ident, + vec![], + bounds, + None)) } } })); diff --git a/src/libsyntax_ext/deriving/generic/ty.rs b/src/libsyntax_ext/deriving/generic/ty.rs index 25a2969448835..76950a546cfd1 100644 --- a/src/libsyntax_ext/deriving/generic/ty.rs +++ b/src/libsyntax_ext/deriving/generic/ty.rs @@ -187,7 +187,9 @@ impl<'a> Ty<'a> { let self_params = self_generics.params .iter() .filter_map(|param| match *param { - GenericParam::Type(ref ty_param) => Some(cx.ty_ident(span, ty_param.ident)), + GenericParam::Type(ref ty_param) => { + Some(cx.ty_ident(span, ty_param.ident)) + } _ => None, }) .collect(); @@ -270,7 +272,10 @@ impl<'a> LifetimeBounds<'a> { let bounds = bounds.iter() .map(|b| cx.lifetime(span, Ident::from_str(b))) .collect(); - GenericParam::Lifetime(cx.lifetime_def(span, Ident::from_str(lt), vec![], bounds)) + GenericParam::Lifetime(cx.lifetime_def(span, + Ident::from_str(lt), + vec![], + bounds)) }) .chain(self.bounds .iter() From 4a6c9463683b5903de5e13c59b48914206754152 Mon Sep 17 00:00:00 2001 From: varkor Date: Fri, 13 Apr 2018 00:57:38 +0100 Subject: [PATCH 12/40] Generalise cases of explicit iteration of specific kinds --- src/librustc/hir/lowering.rs | 4 +- src/librustc/middle/resolve_lifetime.rs | 4 +- src/librustc/traits/error_reporting.rs | 3 +- src/librustc/traits/on_unimplemented.rs | 14 ++-- src/librustc/ty/mod.rs | 29 ++++++++ src/librustc/util/ppaux.rs | 30 ++++---- src/librustc_trans/debuginfo/mod.rs | 23 ++++-- src/librustc_typeck/check/mod.rs | 95 +++++++++++++++---------- src/librustc_typeck/check/wfcheck.rs | 38 +++++++--- src/librustdoc/clean/auto_trait.rs | 48 ++++++------- src/librustdoc/clean/mod.rs | 41 +++++++---- 11 files changed, 210 insertions(+), 119 deletions(-) diff --git a/src/librustc/hir/lowering.rs b/src/librustc/hir/lowering.rs index fd2a328f2fdfa..5b6b0284de520 100644 --- a/src/librustc/hir/lowering.rs +++ b/src/librustc/hir/lowering.rs @@ -374,8 +374,8 @@ impl<'a> LoweringContext<'a> { if item_lowered { let item_lifetimes = match self.lctx.items.get(&item.id).unwrap().node { - hir::Item_::ItemImpl(_, _, _, ref generics, ..) - | hir::Item_::ItemTrait(_, _, ref generics, ..) => { + hir::Item_::ItemImpl(_, _, _, ref generics, .. ) | + hir::Item_::ItemTrait(_, _, ref generics, .. ) => { generics.lifetimes().cloned().collect::>() } _ => Vec::new(), diff --git a/src/librustc/middle/resolve_lifetime.rs b/src/librustc/middle/resolve_lifetime.rs index 225384ed0cb47..a12506afb21f3 100644 --- a/src/librustc/middle/resolve_lifetime.rs +++ b/src/librustc/middle/resolve_lifetime.rs @@ -667,8 +667,8 @@ impl<'a, 'tcx> Visitor<'tcx> for LifetimeContext<'a, 'tcx> { for lt_def in generics.lifetimes() { let (lt_name, region) = Region::early(&self.tcx.hir, &mut index, <_def); if let hir::LifetimeName::Underscore = lt_name { - // Pick the elided lifetime "definition" if one exists and use it to make an - // elision scope. + // Pick the elided lifetime "definition" if one exists and use it to make + // an elision scope. elision = Some(region); } else { lifetimes.insert(lt_name, region); diff --git a/src/librustc/traits/error_reporting.rs b/src/librustc/traits/error_reporting.rs index 00a0d4dc554d5..0dfb4572c35af 100644 --- a/src/librustc/traits/error_reporting.rs +++ b/src/librustc/traits/error_reporting.rs @@ -382,8 +382,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { let name = param.name.to_string(); let ty = trait_ref.substs.type_for_def(param); let ty_str = ty.to_string(); - flags.push((name.clone(), - Some(ty_str.clone()))); + flags.push((name.clone(), Some(ty_str.clone()))); } if let Some(true) = self_ty.ty_to_def_id().map(|def_id| def_id.is_local()) { diff --git a/src/librustc/traits/on_unimplemented.rs b/src/librustc/traits/on_unimplemented.rs index a44dcc7c274e5..3fc95e9518fb4 100644 --- a/src/librustc/traits/on_unimplemented.rs +++ b/src/librustc/traits/on_unimplemented.rs @@ -11,7 +11,7 @@ use fmt_macros::{Parser, Piece, Position}; use hir::def_id::DefId; -use ty::{self, TyCtxt}; +use ty::{self, TyCtxt, GenericParamDef}; use util::common::ErrorReported; use util::nodemap::FxHashMap; @@ -243,7 +243,6 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let name = tcx.item_name(trait_def_id); let generics = tcx.generics_of(trait_def_id); let parser = Parser::new(&self.0); - let mut types = generics.types(); let mut result = Ok(()); for token in parser { match token { @@ -254,8 +253,12 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { // `{ThisTraitsName}` is allowed Position::ArgumentNamed(s) if s == name => (), // So is `{A}` if A is a type parameter - Position::ArgumentNamed(s) => match types.find(|t| { - t.name == s + Position::ArgumentNamed(s) => match generics.params.iter().find(|param| { + if let GenericParamDef::Type(ty) = param { + ty.name == s + } else { + false + } }) { Some(_) => (), None => { @@ -289,8 +292,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let trait_str = tcx.item_path_str(trait_ref.def_id); let generics = tcx.generics_of(trait_ref.def_id); let generic_map = generics.types().map(|param| { - (param.name.to_string(), - trait_ref.substs.type_for_def(param).to_string()) + (param.name.to_string(), trait_ref.substs.type_for_def(param).to_string()) }).collect::>(); let parser = Parser::new(&self.0); diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 59b88567a0d1c..f7d09b5070c10 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -757,6 +757,18 @@ impl ty::EarlyBoundRegion { } } +#[derive(PartialEq, Eq, Hash, Copy, Clone, Debug, RustcEncodable, RustcDecodable)] +pub enum Kind { + Lifetime, + Type, +} + +impl Kind { + pub fn iter<'a>() -> impl Iterator { + [Kind::Lifetime, Kind::Type].into_iter() + } +} + #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] pub enum GenericParamDef { Lifetime(RegionParamDef), @@ -799,6 +811,23 @@ impl<'a, 'gcx, 'tcx> Generics { self.parent_count + self.params.len() } + pub fn param_counts(&self) -> FxHashMap { + let mut param_counts: FxHashMap<_, _> = FxHashMap(); + Kind::iter().for_each(|kind| { + param_counts.insert(*kind, 0); + }); + + for param in self.params.iter() { + let key = match param { + GenericParamDef::Type(_) => Kind::Type, + GenericParamDef::Lifetime(_) => Kind::Lifetime, + }; + *param_counts.get_mut(&key).unwrap() += 1; + } + + param_counts + } + pub fn lifetimes(&self) -> impl DoubleEndedIterator { self.params.iter().filter_map(|p| { if let GenericParamDef::Lifetime(lt) = p { diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index 1a0c5f4a78a42..c6a2dccac4952 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -19,8 +19,8 @@ use ty::{TyError, TyStr, TyArray, TySlice, TyFloat, TyFnDef, TyFnPtr}; use ty::{TyParam, TyRawPtr, TyRef, TyNever, TyTuple}; use ty::{TyClosure, TyGenerator, TyGeneratorWitness, TyForeign, TyProjection, TyAnon}; use ty::{TyDynamic, TyInt, TyUint, TyInfer}; -use ty::{self, Ty, TyCtxt, TypeFoldable}; -use util::nodemap::FxHashSet; +use ty::{self, Ty, TyCtxt, TypeFoldable, Kind}; +use util::nodemap::{FxHashSet, FxHashMap}; use std::cell::Cell; use std::fmt; @@ -256,8 +256,10 @@ impl PrintContext { let verbose = self.is_verbose; let mut num_supplied_defaults = 0; let mut has_self = false; - let mut num_regions = 0; - let mut num_types = 0; + let mut param_counts = FxHashMap(); + Kind::iter().for_each(|kind| { + param_counts.insert(*kind, 0); + }); let mut is_value_path = false; let fn_trait_kind = ty::tls::with(|tcx| { // Unfortunately, some kinds of items (e.g., closures) don't have @@ -303,6 +305,7 @@ impl PrintContext { } } let mut generics = tcx.generics_of(item_def_id); + let child_param_counts = generics.param_counts(); let mut path_def_id = did; has_self = generics.has_self; @@ -310,10 +313,9 @@ impl PrintContext { if let Some(def_id) = generics.parent { // Methods. assert!(is_value_path); - child_types = generics.types().count(); + child_types = child_param_counts[&Kind::Type]; generics = tcx.generics_of(def_id); - num_regions = generics.lifetimes().count(); - num_types = generics.types().count(); + param_counts = generics.param_counts(); if has_self { print!(f, self, write("<"), print_display(substs.type_at(0)), write(" as "))?; @@ -328,8 +330,7 @@ impl PrintContext { assert_eq!(has_self, false); } else { // Types and traits. - num_regions = generics.lifetimes().count(); - num_types = generics.types().count(); + param_counts = child_param_counts; } } @@ -401,10 +402,11 @@ impl PrintContext { Ok(()) }; - print_regions(f, "<", 0, num_regions)?; + print_regions(f, "<", 0, param_counts[&Kind::Lifetime])?; - let tps = substs.types().take(num_types - num_supplied_defaults) - .skip(has_self as usize); + let tps = substs.types() + .take(param_counts[&Kind::Type] - num_supplied_defaults) + .skip(has_self as usize); for ty in tps { start_or_continue(f, "<", ", ")?; @@ -435,10 +437,10 @@ impl PrintContext { write!(f, "::{}", item_name)?; } - print_regions(f, "::<", num_regions, usize::MAX)?; + print_regions(f, "::<", param_counts[&Kind::Lifetime], usize::MAX)?; // FIXME: consider being smart with defaults here too - for ty in substs.types().skip(num_types) { + for ty in substs.types().skip(param_counts[&Kind::Type]) { start_or_continue(f, "::<", ", ")?; ty.print_display(f, self)?; } diff --git a/src/librustc_trans/debuginfo/mod.rs b/src/librustc_trans/debuginfo/mod.rs index 1282626974df0..d50c74da31302 100644 --- a/src/librustc_trans/debuginfo/mod.rs +++ b/src/librustc_trans/debuginfo/mod.rs @@ -26,6 +26,7 @@ use llvm::debuginfo::{DIFile, DIType, DIScope, DIBuilderRef, DISubprogram, DIArr use rustc::hir::TransFnAttrFlags; use rustc::hir::def_id::{DefId, CrateNum}; use rustc::ty::subst::Substs; +use rustc::ty::{Kind, GenericParamDef}; use abi::Abi; use common::CodegenCx; @@ -390,7 +391,14 @@ pub fn create_function_debug_context<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>, // Again, only create type information if full debuginfo is enabled let template_params: Vec<_> = if cx.sess().opts.debuginfo == FullDebugInfo { - let names = get_type_parameter_names(cx, generics); + let names = get_parameter_names(cx, generics); + let names = names.iter().flat_map(|(kind, param)| { + if kind == &Kind::Type { + Some(param) + } else { + None + } + }); substs.types().zip(names).map(|(ty, name)| { let actual_type = cx.tcx.normalize_erasing_regions(ParamEnv::reveal_all(), ty); let actual_type_metadata = type_metadata(cx, actual_type, syntax_pos::DUMMY_SP); @@ -413,11 +421,18 @@ pub fn create_function_debug_context<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>, return create_DIArray(DIB(cx), &template_params[..]); } - fn get_type_parameter_names(cx: &CodegenCx, generics: &ty::Generics) -> Vec { + fn get_parameter_names(cx: &CodegenCx, + generics: &ty::Generics) + -> Vec<(Kind, InternedString)> { let mut names = generics.parent.map_or(vec![], |def_id| { - get_type_parameter_names(cx, cx.tcx.generics_of(def_id)) + get_parameter_names(cx, cx.tcx.generics_of(def_id)) }); - names.extend(generics.types().map(|param| param.name)); + names.extend(generics.params.iter().map(|param| { + match param { + GenericParamDef::Lifetime(lt) => (Kind::Lifetime, lt.name.as_str()), + GenericParamDef::Type(ty) => (Kind::Type, ty.name), + } + })); names } diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index b427020908dc1..44b0ebf7f0116 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -96,7 +96,7 @@ use rustc::middle::region; use rustc::mir::interpret::{GlobalId}; use rustc::ty::subst::{Kind, Subst, Substs}; use rustc::traits::{self, ObligationCause, ObligationCauseCode, TraitEngine}; -use rustc::ty::{self, Ty, TyCtxt, Visibility, ToPredicate}; +use rustc::ty::{self, Ty, TyCtxt, Visibility, ToPredicate, GenericParamDef}; use rustc::ty::adjustment::{Adjust, Adjustment, AllowTwoPhase, AutoBorrow, AutoBorrowMutability}; use rustc::ty::fold::TypeFoldable; use rustc::ty::maps::Providers; @@ -1239,7 +1239,8 @@ pub fn check_item_type<'a,'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, it: &'tcx hir::Item } else { for item in &m.items { let generics = tcx.generics_of(tcx.hir.local_def_id(item.id)); - if generics.types().count() != 0 { + let param_counts = generics.param_counts(); + if generics.params.len() - param_counts[&ty::Kind::Lifetime] != 0 { let mut err = struct_span_err!(tcx.sess, item.span, E0044, "foreign items may not have type parameters"); err.span_label(item.span, "can't have type parameters"); @@ -4799,7 +4800,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // Skip over the lifetimes in the same segment. if let Some((_, generics)) = segment { - i -= generics.lifetimes().count(); + i -= generics.param_counts()[&ty::Kind::Lifetime]; } if let Some(ast_ty) = types.get(i) { @@ -4917,18 +4918,28 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { format!("{} type parameter{}", n, if n == 1 { "" } else { "s" }) }; - // Check provided type parameters. - let type_defs = segment.map_or(vec![], |(_, generics)| { - if generics.parent.is_none() { - generics.types().skip(generics.has_self as usize).collect() - } else { - generics.types().collect() - } - }); - let required_len = type_defs.iter().take_while(|d| !d.has_default).count(); - if types.len() > type_defs.len() { - let span = types[type_defs.len()].span; - let expected_text = count_type_params(type_defs.len()); + // Check provided parameters. + let (ty_non_def_req_len, ty_req_len, lt_req_len) = + segment.map_or((0, 0, 0), |(_, generics)| { + let params_count = generics.param_counts(); + + let offset_type_params = generics.parent.is_none() && generics.has_self; + let type_params = params_count[&ty::Kind::Type] - offset_type_params as usize; + let type_params_barring_defaults = + type_params - generics.params.iter().filter(|param| { + if let GenericParamDef::Type(ty) = param { + ty.has_default + } else { + false + } + }).count(); + + (type_params_barring_defaults, type_params, params_count[&ty::Kind::Lifetime]) + }); + + if types.len() > ty_req_len { + let span = types[ty_req_len].span; + let expected_text = count_type_params(ty_req_len); let actual_text = count_type_params(types.len()); struct_span_err!(self.tcx.sess, span, E0087, "too many type parameters provided: \ @@ -4941,8 +4952,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // type parameters, we force instantiate_value_path to // use inference variables instead of the provided types. *segment = None; - } else if types.len() < required_len && !infer_types && !supress_mismatch_error { - let expected_text = count_type_params(required_len); + } else if types.len() < ty_non_def_req_len && !infer_types && !supress_mismatch_error { + let expected_text = count_type_params(ty_non_def_req_len); let actual_text = count_type_params(types.len()); struct_span_err!(self.tcx.sess, span, E0089, "too few type parameters provided: \ @@ -4956,10 +4967,6 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { AstConv::prohibit_projection(self, bindings[0].span); } - // Check provided lifetime parameters. - let lifetime_defs = segment.map_or(vec![], |(_, generics)| generics.lifetimes().collect()); - let required_len = lifetime_defs.len(); - // Prohibit explicit lifetime arguments if late bound lifetime parameters are present. let has_late_bound_lifetime_defs = segment.map_or(None, |(_, generics)| generics.has_late_bound_regions); @@ -4968,8 +4975,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { let primary_msg = "cannot specify lifetime arguments explicitly \ if late bound lifetime parameters are present"; let note_msg = "the late bound lifetime parameter is introduced here"; - if !is_method_call && (lifetimes.len() > required_len || - lifetimes.len() < required_len && !infer_lifetimes) { + if !is_method_call && (lifetimes.len() > lt_req_len || + lifetimes.len() < lt_req_len && !infer_lifetimes) { let mut err = self.tcx.sess.struct_span_err(lifetimes[0].span, primary_msg); err.span_note(span_late, note_msg); err.emit(); @@ -4983,9 +4990,9 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { return; } - if lifetimes.len() > required_len { - let span = lifetimes[required_len].span; - let expected_text = count_lifetime_params(required_len); + if lifetimes.len() > lt_req_len { + let span = lifetimes[lt_req_len].span; + let expected_text = count_lifetime_params(lt_req_len); let actual_text = count_lifetime_params(lifetimes.len()); struct_span_err!(self.tcx.sess, span, E0088, "too many lifetime parameters provided: \ @@ -4993,8 +5000,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { expected_text, actual_text) .span_label(span, format!("expected {}", expected_text)) .emit(); - } else if lifetimes.len() < required_len && !infer_lifetimes { - let expected_text = count_lifetime_params(required_len); + } else if lifetimes.len() < lt_req_len && !infer_lifetimes { + let expected_text = count_lifetime_params(lt_req_len); let actual_text = count_lifetime_params(lifetimes.len()); struct_span_err!(self.tcx.sess, span, E0090, "too few lifetime parameters provided: \ @@ -5010,16 +5017,16 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { span: Span, segment: &mut Option<(&hir::PathSegment, &ty::Generics)>) -> bool { - use hir::SyntheticTyParamKind::*; - let segment = segment.map(|(path_segment, generics)| { let explicit = !path_segment.infer_types; - let impl_trait = generics.types().any(|ty_param| { - match ty_param.synthetic { - Some(ImplTrait) => true, - _ => false, - } - }); + let impl_trait = generics.params.iter().any(|param| { + if let ty::GenericParamDef::Type(ty) = param { + if let Some(hir::SyntheticTyParamKind::ImplTrait) = ty.synthetic { + return true; + } + } + false + }); if explicit && impl_trait { let mut err = struct_span_err! { @@ -5086,12 +5093,22 @@ pub fn check_bounds_are_used<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, if generics.ty_params().next().is_none() { return; } let mut tps_used = vec![false; generics.ty_params().count()]; - let lifetime_count = generics.lifetimes().count(); + let mut param_counts = FxHashMap(); + param_counts.insert(ty::Kind::Type, 0); + param_counts.insert(ty::Kind::Lifetime, 0); + + for param in generics.params.iter() { + let key = match param { + hir::GenericParamDef::Type(_) => ty::Kind::Type, + hir::GenericParamDef::Lifetime(_) => ty::Kind::Lifetime, + }; + *param_counts.get_mut(&key).unwrap() += 1; + } for leaf_ty in ty.walk() { - if let ty::TyParam(ty::ParamTy {idx, ..}) = leaf_ty.sty { + if let ty::TyParam(ty::ParamTy {idx, .. }) = leaf_ty.sty { debug!("Found use of ty param num {}", idx); - tps_used[idx as usize - lifetime_count] = true; + tps_used[idx as usize - param_counts[&ty::Kind::Lifetime]] = true; } else if let ty::TyError = leaf_ty.sty { // If there already another error, do not emit an error for not using a type Parameter assert!(tcx.sess.err_count() > 0); diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index ae77896668744..fa1ac49232ac0 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -11,6 +11,8 @@ use check::{Inherited, FnCtxt}; use constrained_type_params::{identify_constrained_type_params, Parameter}; +use ty::GenericParamDef; + use hir::def_id::DefId; use rustc::traits::{self, ObligationCauseCode}; use rustc::ty::{self, Lift, Ty, TyCtxt}; @@ -187,7 +189,7 @@ fn check_associated_item<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, fcx.register_wf_obligation(ty, span, code.clone()); } ty::AssociatedKind::Method => { - reject_shadowing_type_parameters(fcx.tcx, item.def_id); + reject_shadowing_parameters(fcx.tcx, item.def_id); let sig = fcx.tcx.fn_sig(item.def_id); let sig = fcx.normalize_associated_types_in(span, &sig); check_fn_or_method(tcx, fcx, span, sig, @@ -638,23 +640,37 @@ fn report_bivariance<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, err.emit(); } -fn reject_shadowing_type_parameters(tcx: TyCtxt, def_id: DefId) { +fn reject_shadowing_parameters(tcx: TyCtxt, def_id: DefId) { let generics = tcx.generics_of(def_id); let parent = tcx.generics_of(generics.parent.unwrap()); - let impl_params: FxHashMap<_, _> = parent.types() - .map(|tp| (tp.name, tp.def_id)) - .collect(); - - for method_param in generics.types() { - if impl_params.contains_key(&method_param.name) { + let impl_params: FxHashMap<_, _> = + parent.params.iter() + .flat_map(|param| { + match param { + GenericParamDef::Lifetime(_) => None, + GenericParamDef::Type(ty) => Some((ty.name, ty.def_id)), + } + }) + .collect(); + + for method_param in generics.params.iter() { + // Shadowing is currently permitted with lifetimes. + if let GenericParamDef::Lifetime(_) = method_param { + continue; + } + let (name, def_id) = match method_param { + GenericParamDef::Lifetime(_) => continue, + GenericParamDef::Type(ty) => (ty.name, ty.def_id), + }; + if impl_params.contains_key(&name) { // Tighten up the span to focus on only the shadowing type - let type_span = tcx.def_span(method_param.def_id); + let type_span = tcx.def_span(def_id); // The expectation here is that the original trait declaration is // local so it should be okay to just unwrap everything. - let trait_def_id = impl_params[&method_param.name]; + let trait_def_id = impl_params[&name]; let trait_decl_span = tcx.def_span(trait_def_id); - error_194(tcx, type_span, trait_decl_span, &method_param.name.as_str()[..]); + error_194(tcx, type_span, trait_decl_span, &name[..]); } } } diff --git a/src/librustdoc/clean/auto_trait.rs b/src/librustdoc/clean/auto_trait.rs index 11bcbc1fe7e30..b1981c0650441 100644 --- a/src/librustdoc/clean/auto_trait.rs +++ b/src/librustdoc/clean/auto_trait.rs @@ -224,33 +224,33 @@ impl<'a, 'tcx, 'rcx> AutoTraitFinder<'a, 'tcx, 'rcx> { } fn generics_to_path_params(&self, generics: ty::Generics) -> hir::PathParameters { - let lifetimes = HirVec::from_vec( - generics.lifetimes() - .map(|p| { - let name = if p.name == "" { - hir::LifetimeName::Static - } else { - hir::LifetimeName::Name(p.name.as_symbol()) - }; + let mut lifetimes = vec![]; + let mut types = vec![]; + + for param in generics.params.iter() { + match param { + ty::GenericParamDef::Lifetime(lt) => { + let name = if lt.name == "" { + hir::LifetimeName::Static + } else { + hir::LifetimeName::Name(lt.name.as_symbol()) + }; - hir::Lifetime { - id: ast::DUMMY_NODE_ID, - span: DUMMY_SP, - name, - } - }) - .collect(), - ); - let types = HirVec::from_vec( - generics.types() - .into_iter() - .map(|p| P(self.ty_param_to_ty(p.clone()))) - .collect(), - ); + lifetimes.push(hir::Lifetime { + id: ast::DUMMY_NODE_ID, + span: DUMMY_SP, + name, + }); + } + ty::GenericParamDef::Type(ty) => { + types.push(P(self.ty_param_to_ty(ty.clone()))); + } + } + } hir::PathParameters { - lifetimes: lifetimes, - types: types, + lifetimes: HirVec::from_vec(lifetimes), + types: HirVec::from_vec(types), bindings: HirVec::new(), parenthesized: false, } diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 31f227373cb93..d1db5185f194a 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -41,7 +41,7 @@ use rustc::hir::def::{self, Def, CtorKind}; use rustc::hir::def_id::{CrateNum, DefId, DefIndex, CRATE_DEF_INDEX, LOCAL_CRATE}; use rustc::hir::def_id::DefIndexAddressSpace; use rustc::ty::subst::Substs; -use rustc::ty::{self, TyCtxt, Region, RegionVid, Ty, AdtKind}; +use rustc::ty::{self, TyCtxt, Region, RegionVid, Ty, AdtKind, Kind}; use rustc::middle::stability; use rustc::util::nodemap::{FxHashMap, FxHashSet}; use rustc_typeck::hir_ty_to_ty; @@ -2675,20 +2675,31 @@ impl Clean for hir::Ty { let mut ty_substs = FxHashMap(); let mut lt_substs = FxHashMap(); provided_params.with_parameters(|provided_params| { - for (i, ty_param) in generics.ty_params().enumerate() { - let ty_param_def = Def::TyParam(cx.tcx.hir.local_def_id(ty_param.id)); - if let Some(ty) = provided_params.types.get(i).cloned() { - ty_substs.insert(ty_param_def, ty.into_inner().clean(cx)); - } else if let Some(default) = ty_param.default.clone() { - ty_substs.insert(ty_param_def, default.into_inner().clean(cx)); - } - } - - for (i, lt_param) in generics.lifetimes().enumerate() { - if let Some(lt) = provided_params.lifetimes.get(i).cloned() { - if !lt.is_elided() { - let lt_def_id = cx.tcx.hir.local_def_id(lt_param.lifetime.id); - lt_substs.insert(lt_def_id, lt.clean(cx)); + let mut indices = FxHashMap(); + for param in generics.params.iter() { + match param { + GenericParamDef::Type(ty_param) => { + let i = indices.entry(Kind::Type).or_insert(0); + let ty_param_def = + Def::TyParam(cx.tcx.hir.local_def_id(ty_param.id)); + if let Some(ty) = provided_params.types.get(*i).cloned() { + ty_substs.insert(ty_param_def, ty.into_inner().clean(cx)); + } else if let Some(default) = ty_param.default.clone() { + ty_substs.insert(ty_param_def, + default.into_inner().clean(cx)); + } + *i += 1; + } + GenericParamDef::Lifetime(lt_param) => { + let i = indices.entry(Kind::Type).or_insert(0); + if let Some(lt) = provided_params.lifetimes.get(*i).cloned() { + if !lt.is_elided() { + let lt_def_id = + cx.tcx.hir.local_def_id(lt_param.lifetime.id); + lt_substs.insert(lt_def_id, lt.clean(cx)); + } + } + *i += 1; } } } From b75f421ee912edc096c546b1fac19fd8990a180c Mon Sep 17 00:00:00 2001 From: varkor Date: Fri, 13 Apr 2018 23:12:14 +0100 Subject: [PATCH 13/40] Generalise more cases of explicit iteration of specific kinds --- src/librustc/hir/lowering.rs | 3 +- src/librustc/infer/anon_types/mod.rs | 2 +- src/librustc/lib.rs | 1 + src/librustc/middle/resolve_lifetime.rs | 2 +- src/librustc/traits/error_reporting.rs | 2 +- src/librustc/traits/object_safety.rs | 4 +-- src/librustc/traits/on_unimplemented.rs | 2 +- src/librustc/ty/mod.rs | 29 ++++++++++++++---- src/librustc/ty/subst.rs | 5 ++-- src/librustc/util/ppaux.rs | 4 +-- src/librustc_mir/monomorphize/collector.rs | 2 +- src/librustc_mir/transform/check_unsafety.rs | 4 +-- src/librustc_privacy/lib.rs | 24 ++++++++++----- src/librustc_traits/dropck_outlives.rs | 8 +++-- src/librustc_traits/lib.rs | 1 + src/librustc_typeck/astconv.rs | 31 +++++++++++++------- src/librustc_typeck/check/compare_method.rs | 14 ++++----- src/librustc_typeck/check/intrinsic.rs | 6 ++-- src/librustc_typeck/check/method/confirm.rs | 6 ++-- src/librustc_typeck/check/mod.rs | 15 ++++------ src/librustc_typeck/check/wfcheck.rs | 2 +- src/librustc_typeck/impl_wf_check.rs | 10 +++---- src/librustdoc/clean/mod.rs | 4 +-- 23 files changed, 110 insertions(+), 71 deletions(-) diff --git a/src/librustc/hir/lowering.rs b/src/librustc/hir/lowering.rs index 5b6b0284de520..c780d1b72f2a0 100644 --- a/src/librustc/hir/lowering.rs +++ b/src/librustc/hir/lowering.rs @@ -46,6 +46,7 @@ use hir::HirVec; use hir::map::{DefKey, DefPathData, Definitions}; use hir::def_id::{DefId, DefIndex, DefIndexAddressSpace, CRATE_DEF_INDEX}; use hir::def::{Def, PathResolution}; +use ty::Kind; use lint::builtin::{self, PARENTHESIZED_PARAMS_IN_TYPES_AND_MODULES}; use middle::cstore::CrateStore; use rustc_data_structures::indexed_vec::IndexVec; @@ -1461,7 +1462,7 @@ impl<'a> LoweringContext<'a> { assert!(!def_id.is_local()); let item_generics = self.cstore.item_generics_cloned_untracked(def_id, self.sess); - let n = item_generics.lifetimes().count(); + let n = item_generics.param_counts()[&Kind::Lifetime]; self.type_def_lifetime_params.insert(def_id, n); n }); diff --git a/src/librustc/infer/anon_types/mod.rs b/src/librustc/infer/anon_types/mod.rs index 1da6d9e174024..06af6d16c3006 100644 --- a/src/librustc/infer/anon_types/mod.rs +++ b/src/librustc/infer/anon_types/mod.rs @@ -313,7 +313,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { // `['a]` for the first impl trait and `'b` for the // second. let mut least_region = None; - for region_def in abstract_type_generics.lifetimes() { + for region_def in abstract_type_generics.lifetimes_depr() { // Find the index of this region in the list of substitutions. let index = region_def.index as usize; diff --git a/src/librustc/lib.rs b/src/librustc/lib.rs index 2a288ae522aac..26ac9d6ee9ea6 100644 --- a/src/librustc/lib.rs +++ b/src/librustc/lib.rs @@ -49,6 +49,7 @@ #![cfg_attr(stage0, feature(dyn_trait))] #![feature(from_ref)] #![feature(fs_read_write)] +#![feature(iterator_find_map)] #![cfg_attr(windows, feature(libc))] #![cfg_attr(stage0, feature(macro_lifetime_matcher))] #![feature(macro_vis_matcher)] diff --git a/src/librustc/middle/resolve_lifetime.rs b/src/librustc/middle/resolve_lifetime.rs index a12506afb21f3..b450ef81c9178 100644 --- a/src/librustc/middle/resolve_lifetime.rs +++ b/src/librustc/middle/resolve_lifetime.rs @@ -1659,7 +1659,7 @@ impl<'a, 'tcx> LifetimeContext<'a, 'tcx> { .entry(def_id) .or_insert_with(|| { tcx.generics_of(def_id) - .types() + .types_depr() .map(|def| def.object_lifetime_default) .collect() }) diff --git a/src/librustc/traits/error_reporting.rs b/src/librustc/traits/error_reporting.rs index 0dfb4572c35af..b7f0e6a32ea15 100644 --- a/src/librustc/traits/error_reporting.rs +++ b/src/librustc/traits/error_reporting.rs @@ -378,7 +378,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { flags.push(("_Self".to_string(), Some(self.tcx.type_of(def.did).to_string()))); } - for param in generics.types() { + for param in generics.types_depr() { let name = param.name.to_string(); let ty = trait_ref.substs.type_for_def(param); let ty_str = ty.to_string(); diff --git a/src/librustc/traits/object_safety.rs b/src/librustc/traits/object_safety.rs index 3c82dbd7ad662..cb8ff674188c4 100644 --- a/src/librustc/traits/object_safety.rs +++ b/src/librustc/traits/object_safety.rs @@ -21,7 +21,7 @@ use super::elaborate_predicates; use hir::def_id::DefId; use traits; -use ty::{self, Ty, TyCtxt, TypeFoldable}; +use ty::{self, Ty, TyCtxt, Kind, TypeFoldable}; use ty::subst::Substs; use ty::util::ExplicitSelf; use std::borrow::Cow; @@ -284,7 +284,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { } // We can't monomorphize things like `fn foo(...)`. - if self.generics_of(method.def_id).types().count() != 0 { + if self.generics_of(method.def_id).param_counts()[&Kind::Type] != 0 { return Some(MethodViolationCode::Generic); } diff --git a/src/librustc/traits/on_unimplemented.rs b/src/librustc/traits/on_unimplemented.rs index 3fc95e9518fb4..cee63e2ecc149 100644 --- a/src/librustc/traits/on_unimplemented.rs +++ b/src/librustc/traits/on_unimplemented.rs @@ -291,7 +291,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let name = tcx.item_name(trait_ref.def_id); let trait_str = tcx.item_path_str(trait_ref.def_id); let generics = tcx.generics_of(trait_ref.def_id); - let generic_map = generics.types().map(|param| { + let generic_map = generics.types_depr().map(|param| { (param.name.to_string(), trait_ref.substs.type_for_def(param).to_string()) }).collect::>(); diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index f7d09b5070c10..eabff9a912413 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -782,6 +782,13 @@ impl GenericParamDef { GenericParamDef::Type(ty) => ty.index, } } + + pub fn get_type(&self) -> Option { + match *self { + GenericParamDef::Type(ty) => Some(ty), + _ => None, + } + } } /// Information about the formal type/lifetime parameters associated @@ -828,7 +835,19 @@ impl<'a, 'gcx, 'tcx> Generics { param_counts } - pub fn lifetimes(&self) -> impl DoubleEndedIterator { + pub fn type_params_without_defaults(&self) -> usize { + let mut count = 0; + for param in self.params.iter() { + if let GenericParamDef::Type(ty) = param { + if !ty.has_default { + count += 1 + } + } + } + count + } + + pub fn lifetimes_depr(&self) -> impl DoubleEndedIterator { self.params.iter().filter_map(|p| { if let GenericParamDef::Lifetime(lt) = p { Some(lt) @@ -838,7 +857,7 @@ impl<'a, 'gcx, 'tcx> Generics { }) } - pub fn types(&self) -> impl DoubleEndedIterator { + pub fn types_depr(&self) -> impl DoubleEndedIterator { self.params.iter().filter_map(|p| { if let GenericParamDef::Type(ty) = p { Some(ty) @@ -849,9 +868,7 @@ impl<'a, 'gcx, 'tcx> Generics { } pub fn requires_monomorphization(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { - if self.params.iter().any(|p| { - if let GenericParamDef::Type(_) = p { true } else { false } - }) { + if self.params.iter().any(|p| p.get_type().is_some()) { return true; } if let Some(parent_def_id) = self.parent { @@ -912,7 +929,7 @@ impl<'a, 'gcx, 'tcx> Generics { // And it can be seen that in both cases, to move from a substs // offset to a generics offset you just have to offset by the // number of regions. - let type_param_offset = self.lifetimes().count(); + let type_param_offset = self.param_counts()[&Kind::Lifetime]; let has_self = self.has_self && self.parent.is_none(); let is_separated_self = type_param_offset != 0 && idx == 0 && has_self; diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index bec343afca82d..a9077eb193f38 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -242,11 +242,10 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { where FR: FnMut(&ty::RegionParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, FT: FnMut(&ty::TypeParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { // Handle Self first, before all regions. - let mut types = defs.types(); let mut skip_self = defs.parent.is_none() && defs.has_self; if skip_self { - let def = types.next().unwrap(); - let ty = mk_type(def, substs); + let def = defs.params.iter().find_map(|p| p.get_type()).unwrap(); + let ty = mk_type(&def, substs); assert_eq!(def.index as usize, substs.len()); substs.push(ty.into()); } diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index c6a2dccac4952..e8edf58a9db39 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -335,10 +335,10 @@ impl PrintContext { } if !verbose { - if generics.types().last().map_or(false, |def| def.has_default) { + if generics.types_depr().last().map_or(false, |def| def.has_default) { if let Some(substs) = tcx.lift(&substs) { let tps = substs.types().rev().skip(child_types); - for (def, actual) in generics.types().rev().zip(tps) { + for (def, actual) in generics.types_depr().rev().zip(tps) { if !def.has_default { break; } diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index 2bc4e651dd357..99a7e0abe1679 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -1108,7 +1108,7 @@ fn create_mono_items_for_default_impls<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, continue; } - if tcx.generics_of(method.def_id).types().count() != 0 { + if tcx.generics_of(method.def_id).param_counts()[&ty::Kind::Type] != 0 { continue; } diff --git a/src/librustc_mir/transform/check_unsafety.rs b/src/librustc_mir/transform/check_unsafety.rs index 68b8b256f290d..58e63fe6b048d 100644 --- a/src/librustc_mir/transform/check_unsafety.rs +++ b/src/librustc_mir/transform/check_unsafety.rs @@ -13,7 +13,7 @@ use rustc_data_structures::indexed_vec::IndexVec; use rustc_data_structures::sync::Lrc; use rustc::ty::maps::Providers; -use rustc::ty::{self, TyCtxt}; +use rustc::ty::{self, TyCtxt, Kind}; use rustc::hir; use rustc::hir::def_id::DefId; use rustc::lint::builtin::{SAFE_EXTERN_STATICS, SAFE_PACKED_BORROWS, UNUSED_UNSAFE}; @@ -357,7 +357,7 @@ fn unsafe_derive_on_repr_packed<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: D // FIXME: when we make this a hard error, this should have its // own error code. - let message = if tcx.generics_of(def_id).types().count() != 0 { + let message = if tcx.generics_of(def_id).param_counts()[&Kind::Type] != 0 { format!("#[derive] can't be used on a #[repr(packed)] struct with \ type parameters (error E0133)") } else { diff --git a/src/librustc_privacy/lib.rs b/src/librustc_privacy/lib.rs index d590210925597..56ffadc882a45 100644 --- a/src/librustc_privacy/lib.rs +++ b/src/librustc_privacy/lib.rs @@ -27,7 +27,7 @@ use rustc::hir::intravisit::{self, Visitor, NestedVisitorMap}; use rustc::hir::itemlikevisit::DeepVisitor; use rustc::lint; use rustc::middle::privacy::{AccessLevel, AccessLevels}; -use rustc::ty::{self, TyCtxt, Ty, TypeFoldable}; +use rustc::ty::{self, TyCtxt, Ty, TypeFoldable, GenericParamDef}; use rustc::ty::fold::TypeVisitor; use rustc::ty::maps::Providers; use rustc::ty::subst::UnpackedKind; @@ -399,9 +399,14 @@ impl<'a, 'tcx> Visitor<'tcx> for EmbargoVisitor<'a, 'tcx> { impl<'b, 'a, 'tcx> ReachEverythingInTheInterfaceVisitor<'b, 'a, 'tcx> { fn generics(&mut self) -> &mut Self { - for def in self.ev.tcx.generics_of(self.item_def_id).types() { - if def.has_default { - self.ev.tcx.type_of(def.def_id).visit_with(self); + for def in self.ev.tcx.generics_of(self.item_def_id).params.iter() { + match def { + GenericParamDef::Type(ty) => { + if ty.has_default { + self.ev.tcx.type_of(ty.def_id).visit_with(self); + } + } + GenericParamDef::Lifetime(_) => {} } } self @@ -1335,9 +1340,14 @@ struct SearchInterfaceForPrivateItemsVisitor<'a, 'tcx: 'a> { impl<'a, 'tcx: 'a> SearchInterfaceForPrivateItemsVisitor<'a, 'tcx> { fn generics(&mut self) -> &mut Self { - for def in self.tcx.generics_of(self.item_def_id).types() { - if def.has_default { - self.tcx.type_of(def.def_id).visit_with(self); + for def in self.tcx.generics_of(self.item_def_id).params.iter() { + match def { + GenericParamDef::Type(ty) => { + if ty.has_default { + self.tcx.type_of(ty.def_id).visit_with(self); + } + } + GenericParamDef::Lifetime(_) => {} } } self diff --git a/src/librustc_traits/dropck_outlives.rs b/src/librustc_traits/dropck_outlives.rs index 39326713df2a1..c9c0902940e54 100644 --- a/src/librustc_traits/dropck_outlives.rs +++ b/src/librustc_traits/dropck_outlives.rs @@ -280,8 +280,12 @@ crate fn adt_dtorck_constraint<'a, 'tcx>( if def.is_phantom_data() { let result = DtorckConstraint { outlives: vec![], - dtorck_types: vec![tcx.mk_param_from_def(&tcx.generics_of(def_id).types().next() - .expect("should be at least one type parameter"))], + dtorck_types: vec![tcx.mk_param_from_def( + &tcx.generics_of(def_id) + .params + .iter() + .find_map(|p| p.get_type()) + .expect("should be at least one type parameter"))], overflows: vec![], }; debug!("dtorck_constraint: {:?} => {:?}", def, result); diff --git a/src/librustc_traits/lib.rs b/src/librustc_traits/lib.rs index 7f18fac2db5a3..f2627f6570241 100644 --- a/src/librustc_traits/lib.rs +++ b/src/librustc_traits/lib.rs @@ -12,6 +12,7 @@ //! the guts are broken up into modules; see the comments in those modules. #![feature(crate_visibility_modifier)] +#![feature(iterator_find_map)] #[macro_use] extern crate log; diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index a6e24f155090d..d77a090de682d 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -208,8 +208,9 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { // region with the current anon region binding (in other words, // whatever & would get replaced with). let decl_generics = tcx.generics_of(def_id); + let param_counts = decl_generics.param_counts(); let num_types_provided = parameters.types.len(); - let expected_num_region_params = decl_generics.lifetimes().count(); + let expected_num_region_params = param_counts[&ty::Kind::Lifetime]; let supplied_num_region_params = parameters.lifetimes.len(); if expected_num_region_params != supplied_num_region_params { report_lifetime_number_error(tcx, span, @@ -221,10 +222,14 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { assert_eq!(decl_generics.has_self, self_ty.is_some()); // Check the number of type parameters supplied by the user. - let ty_param_defs = - decl_generics.types().skip(self_ty.is_some() as usize).collect::>(); - if !infer_types || num_types_provided > ty_param_defs.len() { - check_type_argument_count(tcx, span, num_types_provided, &ty_param_defs); + let type_params_offset = self_ty.is_some() as usize; + let ty_param_defs = param_counts[&ty::Kind::Type] - type_params_offset; + if !infer_types || num_types_provided > ty_param_defs { + check_type_argument_count(tcx, + span, + num_types_provided, + ty_param_defs, + decl_generics.type_params_without_defaults() - type_params_offset); } let is_object = self_ty.map_or(false, |ty| ty.sty == TRAIT_OBJECT_DUMMY_SELF); @@ -241,7 +246,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { }; let substs = Substs::for_item(tcx, def_id, |def, _| { - let i = def.index as usize - self_ty.is_some() as usize; + let i = def.index as usize - type_params_offset; if let Some(lifetime) = parameters.lifetimes.get(i) { self.ast_region_to_region(lifetime, Some(def)) } else { @@ -255,7 +260,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { return ty; } - let i = i - self_ty.is_some() as usize - decl_generics.lifetimes().count(); + let i = i - (param_counts[&ty::Kind::Lifetime] + type_params_offset); if i < num_types_provided { // A provided type parameter. self.ast_ty_to_ty(¶meters.types[i]) @@ -1300,10 +1305,14 @@ fn split_auto_traits<'a, 'b, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, (auto_traits, trait_bounds) } -fn check_type_argument_count(tcx: TyCtxt, span: Span, supplied: usize, - ty_param_defs: &[&ty::TypeParamDef]) { - let accepted = ty_param_defs.len(); - let required = ty_param_defs.iter().take_while(|x| !x.has_default).count(); +fn check_type_argument_count(tcx: TyCtxt, + span: Span, + supplied: usize, + ty_param_defs: usize, + ty_param_defs_without_default: usize) +{ + let accepted = ty_param_defs; + let required = ty_param_defs_without_default; if supplied < required { let expected = if required < accepted { "expected at least" diff --git a/src/librustc_typeck/check/compare_method.rs b/src/librustc_typeck/check/compare_method.rs index 30620caf69274..59728542bcda0 100644 --- a/src/librustc_typeck/check/compare_method.rs +++ b/src/librustc_typeck/check/compare_method.rs @@ -10,7 +10,7 @@ use rustc::hir::{self, ImplItemKind, TraitItemKind}; use rustc::infer::{self, InferOk}; -use rustc::ty::{self, TyCtxt}; +use rustc::ty::{self, TyCtxt, Kind}; use rustc::ty::util::ExplicitSelf; use rustc::traits::{self, ObligationCause, ObligationCauseCode, Reveal}; use rustc::ty::error::{ExpectedFound, TypeError}; @@ -357,8 +357,8 @@ fn check_region_bounds_on_impl_method<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, trait_to_skol_substs: &Substs<'tcx>) -> Result<(), ErrorReported> { let span = tcx.sess.codemap().def_span(span); - let trait_params = trait_generics.lifetimes(); - let impl_params = impl_generics.lifetimes(); + let trait_params = trait_generics.param_counts()[&Kind::Lifetime]; + let impl_params = impl_generics.param_counts()[&Kind::Lifetime]; debug!("check_region_bounds_on_impl_method: \ trait_generics={:?} \ @@ -377,7 +377,7 @@ fn check_region_bounds_on_impl_method<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, // but found 0" it's confusing, because it looks like there // are zero. Since I don't quite know how to phrase things at // the moment, give a kind of vague error message. - if trait_params.count() != impl_params.count() { + if trait_params != impl_params { let mut err = struct_span_err!(tcx.sess, span, E0195, @@ -574,8 +574,8 @@ fn compare_number_of_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, -> Result<(), ErrorReported> { let impl_m_generics = tcx.generics_of(impl_m.def_id); let trait_m_generics = tcx.generics_of(trait_m.def_id); - let num_impl_m_type_params = impl_m_generics.types().count(); - let num_trait_m_type_params = trait_m_generics.types().count(); + let num_impl_m_type_params = impl_m_generics.param_counts()[&Kind::Type]; + let num_trait_m_type_params = trait_m_generics.param_counts()[&Kind::Type]; if num_impl_m_type_params != num_trait_m_type_params { let impl_m_node_id = tcx.hir.as_local_node_id(impl_m.def_id).unwrap(); let impl_m_item = tcx.hir.expect_impl_item(impl_m_node_id); @@ -728,7 +728,7 @@ fn compare_synthetic_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let mut error_found = false; let impl_m_generics = tcx.generics_of(impl_m.def_id); let trait_m_generics = tcx.generics_of(trait_m.def_id); - for (impl_ty, trait_ty) in impl_m_generics.types().zip(trait_m_generics.types()) { + for (impl_ty, trait_ty) in impl_m_generics.types_depr().zip(trait_m_generics.types_depr()) { if impl_ty.synthetic != trait_ty.synthetic { let impl_node_id = tcx.hir.as_local_node_id(impl_ty.def_id).unwrap(); let impl_span = tcx.hir.span(impl_node_id); diff --git a/src/librustc_typeck/check/intrinsic.rs b/src/librustc_typeck/check/intrinsic.rs index e2deca38302cd..e3d7e16e15c97 100644 --- a/src/librustc_typeck/check/intrinsic.rs +++ b/src/librustc_typeck/check/intrinsic.rs @@ -13,7 +13,7 @@ use intrinsics; use rustc::traits::{ObligationCause, ObligationCauseCode}; -use rustc::ty::{self, TyCtxt, Ty}; +use rustc::ty::{self, TyCtxt, Ty, Kind}; use rustc::util::nodemap::FxHashMap; use require_same_types; @@ -45,7 +45,7 @@ fn equate_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } } - let i_n_tps = tcx.generics_of(def_id).types().count(); + let i_n_tps = tcx.generics_of(def_id).param_counts()[&Kind::Type]; if i_n_tps != n_tps { let span = match it.node { hir::ForeignItemFn(_, _, ref generics) => generics.span, @@ -346,7 +346,7 @@ pub fn check_platform_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }; let def_id = tcx.hir.local_def_id(it.id); - let i_n_tps = tcx.generics_of(def_id).types().count(); + let i_n_tps = tcx.generics_of(def_id).param_counts()[&Kind::Type]; let name = it.name.as_str(); let (n_tps, inputs, output) = match &*name { diff --git a/src/librustc_typeck/check/method/confirm.rs b/src/librustc_typeck/check/method/confirm.rs index f075cd911ad9e..038927bbac647 100644 --- a/src/librustc_typeck/check/method/confirm.rs +++ b/src/librustc_typeck/check/method/confirm.rs @@ -15,7 +15,7 @@ use check::{FnCtxt, PlaceOp, callee, Needs}; use hir::def_id::DefId; use rustc::ty::subst::Substs; use rustc::traits; -use rustc::ty::{self, Ty}; +use rustc::ty::{self, Ty, Kind}; use rustc::ty::subst::Subst; use rustc::ty::adjustment::{Adjustment, Adjust, OverloadedDeref}; use rustc::ty::adjustment::{AllowTwoPhase, AutoBorrow, AutoBorrowMutability}; @@ -332,7 +332,9 @@ impl<'a, 'gcx, 'tcx> ConfirmContext<'a, 'gcx, 'tcx> { parent_substs.type_at(i) } else if let Some(ast_ty) = provided.as_ref().and_then(|p| { - p.types.get(i - parent_substs.len() - method_generics.lifetimes().count()) + let idx = + i - parent_substs.len() - method_generics.param_counts()[&Kind::Lifetime]; + p.types.get(idx) }) { self.to_ty(ast_ty) diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 44b0ebf7f0116..6ed31a237ff5f 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -96,7 +96,7 @@ use rustc::middle::region; use rustc::mir::interpret::{GlobalId}; use rustc::ty::subst::{Kind, Subst, Substs}; use rustc::traits::{self, ObligationCause, ObligationCauseCode, TraitEngine}; -use rustc::ty::{self, Ty, TyCtxt, Visibility, ToPredicate, GenericParamDef}; +use rustc::ty::{self, Ty, TyCtxt, Visibility, ToPredicate}; use rustc::ty::adjustment::{Adjust, Adjustment, AllowTwoPhase, AutoBorrow, AutoBorrowMutability}; use rustc::ty::fold::TypeFoldable; use rustc::ty::maps::Providers; @@ -4923,16 +4923,11 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { segment.map_or((0, 0, 0), |(_, generics)| { let params_count = generics.param_counts(); - let offset_type_params = generics.parent.is_none() && generics.has_self; - let type_params = params_count[&ty::Kind::Type] - offset_type_params as usize; + let type_params_offset + = (generics.parent.is_none() && generics.has_self) as usize; + let type_params = params_count[&ty::Kind::Type] - type_params_offset; let type_params_barring_defaults = - type_params - generics.params.iter().filter(|param| { - if let GenericParamDef::Type(ty) = param { - ty.has_default - } else { - false - } - }).count(); + generics.type_params_without_defaults() - type_params_offset; (type_params_barring_defaults, type_params, params_count[&ty::Kind::Lifetime]) }); diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index fa1ac49232ac0..804fed1010546 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -377,7 +377,7 @@ fn check_where_clauses<'a, 'gcx, 'fcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'gcx>, // For example this forbids the declaration: // struct Foo> { .. } // Here the default `Vec<[u32]>` is not WF because `[u32]: Sized` does not hold. - for d in generics.types().cloned().filter(is_our_default).map(|p| p.def_id) { + for d in generics.types_depr().cloned().filter(is_our_default).map(|p| p.def_id) { let ty = fcx.tcx.type_of(d); // ignore dependent defaults -- that is, where the default of one type // parameter includes another (e.g., ). In those cases, we can't diff --git a/src/librustc_typeck/impl_wf_check.rs b/src/librustc_typeck/impl_wf_check.rs index 60a998db3594f..e0786ea8b3c6f 100644 --- a/src/librustc_typeck/impl_wf_check.rs +++ b/src/librustc_typeck/impl_wf_check.rs @@ -105,7 +105,7 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, tcx, &impl_predicates.predicates.as_slice(), impl_trait_ref, &mut input_parameters); // Disallow ANY unconstrained type parameters. - for (ty_param, param) in impl_generics.types().zip(impl_hir_generics.ty_params()) { + for (ty_param, param) in impl_generics.types_depr().zip(impl_hir_generics.ty_params()) { let param_ty = ty::ParamTy::for_def(ty_param); if !input_parameters.contains(&ctp::Parameter::from(param_ty)) { report_unused_parameter(tcx, param.span, "type", ¶m_ty.to_string()); @@ -122,13 +122,13 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, .flat_map(|def_id| { ctp::parameters_for(&tcx.type_of(def_id), true) }).collect(); - for (ty_lifetime, lifetime) in impl_generics.lifetimes().zip(impl_hir_generics.lifetimes()) { - let param = ctp::Parameter::from(ty_lifetime.to_early_bound_region_data()); + for (ty_lt, lt) in impl_generics.lifetimes_depr().zip(impl_hir_generics.lifetimes()) { + let param = ctp::Parameter::from(ty_lt.to_early_bound_region_data()); if lifetimes_in_associated_types.contains(¶m) && // (*) !input_parameters.contains(¶m) { - report_unused_parameter(tcx, lifetime.lifetime.span, - "lifetime", &lifetime.lifetime.name.name().to_string()); + report_unused_parameter(tcx, lt.lifetime.span, + "lifetime", <.lifetime.name.name().to_string()); } } diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index d1db5185f194a..7f6da5414c637 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1800,7 +1800,7 @@ impl<'a, 'tcx> Clean for (&'a ty::Generics, // Bounds in the type_params and lifetimes fields are repeated in the // predicates field (see rustc_typeck::collect::ty_generics), so remove // them. - let stripped_typarams = gens.types().filter_map(|tp| { + let stripped_typarams = gens.types_depr().filter_map(|tp| { if tp.name == keywords::SelfType.name().as_str() { assert_eq!(tp.index, 0); None @@ -1849,7 +1849,7 @@ impl<'a, 'tcx> Clean for (&'a ty::Generics, // and instead see `where T: Foo + Bar + Sized + 'a` Generics { - params: gens.lifetimes() + params: gens.lifetimes_depr() .into_iter() .map(|lp| GenericParamDef::Lifetime(lp.clean(cx))) .chain( From d557ff983f75ad21a90240dea0a80e318175b504 Mon Sep 17 00:00:00 2001 From: varkor Date: Sat, 14 Apr 2018 00:07:25 +0100 Subject: [PATCH 14/40] Eliminate ty::Generics::lifetimes() Begone lazy lifetime code! --- src/librustc/infer/anon_types/mod.rs | 10 ++++++-- src/librustc/ty/mod.rs | 10 -------- src/librustc_typeck/impl_wf_check.rs | 34 ++++++++++++++++------------ src/librustdoc/clean/mod.rs | 13 +++++++---- 4 files changed, 37 insertions(+), 30 deletions(-) diff --git a/src/librustc/infer/anon_types/mod.rs b/src/librustc/infer/anon_types/mod.rs index 06af6d16c3006..a83eb7fd354a3 100644 --- a/src/librustc/infer/anon_types/mod.rs +++ b/src/librustc/infer/anon_types/mod.rs @@ -14,7 +14,7 @@ use infer::outlives::free_region_map::FreeRegionRelations; use rustc_data_structures::fx::FxHashMap; use syntax::ast; use traits::{self, PredicateObligation}; -use ty::{self, Ty, TyCtxt}; +use ty::{self, Ty, TyCtxt, GenericParamDef}; use ty::fold::{BottomUpFolder, TypeFoldable, TypeFolder}; use ty::outlives::Component; use ty::subst::{Kind, Substs, UnpackedKind}; @@ -313,7 +313,13 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { // `['a]` for the first impl trait and `'b` for the // second. let mut least_region = None; - for region_def in abstract_type_generics.lifetimes_depr() { + for region_def in abstract_type_generics.params.iter().filter_map(|param| { + if let GenericParamDef::Lifetime(lt) = param { + Some(lt) + } else { + None + } + }) { // Find the index of this region in the list of substitutions. let index = region_def.index as usize; diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index eabff9a912413..680c03f02e1d5 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -847,16 +847,6 @@ impl<'a, 'gcx, 'tcx> Generics { count } - pub fn lifetimes_depr(&self) -> impl DoubleEndedIterator { - self.params.iter().filter_map(|p| { - if let GenericParamDef::Lifetime(lt) = p { - Some(lt) - } else { - None - } - }) - } - pub fn types_depr(&self) -> impl DoubleEndedIterator { self.params.iter().filter_map(|p| { if let GenericParamDef::Type(ty) = p { diff --git a/src/librustc_typeck/impl_wf_check.rs b/src/librustc_typeck/impl_wf_check.rs index e0786ea8b3c6f..01e2bc3137433 100644 --- a/src/librustc_typeck/impl_wf_check.rs +++ b/src/librustc_typeck/impl_wf_check.rs @@ -104,14 +104,6 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, ctp::identify_constrained_type_params( tcx, &impl_predicates.predicates.as_slice(), impl_trait_ref, &mut input_parameters); - // Disallow ANY unconstrained type parameters. - for (ty_param, param) in impl_generics.types_depr().zip(impl_hir_generics.ty_params()) { - let param_ty = ty::ParamTy::for_def(ty_param); - if !input_parameters.contains(&ctp::Parameter::from(param_ty)) { - report_unused_parameter(tcx, param.span, "type", ¶m_ty.to_string()); - } - } - // Disallow unconstrained lifetimes, but only if they appear in assoc types. let lifetimes_in_associated_types: FxHashSet<_> = impl_item_refs.iter() .map(|item_ref| tcx.hir.local_def_id(item_ref.id.node_id)) @@ -122,13 +114,27 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, .flat_map(|def_id| { ctp::parameters_for(&tcx.type_of(def_id), true) }).collect(); - for (ty_lt, lt) in impl_generics.lifetimes_depr().zip(impl_hir_generics.lifetimes()) { - let param = ctp::Parameter::from(ty_lt.to_early_bound_region_data()); - if lifetimes_in_associated_types.contains(¶m) && // (*) - !input_parameters.contains(¶m) { - report_unused_parameter(tcx, lt.lifetime.span, - "lifetime", <.lifetime.name.name().to_string()); + for (ty_param, hir_param) in impl_generics.params.iter() + .zip(impl_hir_generics.params.iter()) { + match (ty_param, hir_param) { + // Disallow ANY unconstrained type parameters. + (ty::GenericParamDef::Type(ty_ty), hir::GenericParamDef::Type(hir_ty)) => { + let param_ty = ty::ParamTy::for_def(ty_ty); + if !input_parameters.contains(&ctp::Parameter::from(param_ty)) { + report_unused_parameter(tcx, hir_ty.span, "type", ¶m_ty.to_string()); + } + } + (ty::GenericParamDef::Lifetime(ty_lt), hir::GenericParamDef::Lifetime(hir_lt)) => { + let param = ctp::Parameter::from(ty_lt.to_early_bound_region_data()); + if lifetimes_in_associated_types.contains(¶m) && // (*) + !input_parameters.contains(¶m) { + report_unused_parameter(tcx, hir_lt.lifetime.span, + "lifetime", &hir_lt.lifetime.name.name().to_string()); + } + } + (ty::GenericParamDef::Type(_), _) => continue, + (ty::GenericParamDef::Lifetime(_), _) => continue, } } diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 7f6da5414c637..6848b25097b8d 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1849,10 +1849,15 @@ impl<'a, 'tcx> Clean for (&'a ty::Generics, // and instead see `where T: Foo + Bar + Sized + 'a` Generics { - params: gens.lifetimes_depr() - .into_iter() - .map(|lp| GenericParamDef::Lifetime(lp.clean(cx))) - .chain( + params: gens.params + .iter() + .flat_map(|param| { + if let ty::GenericParamDef::Lifetime(lt) = param { + Some(GenericParamDef::Lifetime(lt.clean(cx))) + } else { + None + } + }).chain( simplify::ty_params(stripped_typarams) .into_iter() .map(|tp| GenericParamDef::Type(tp)) From 0b8b14f6f50575a515e1f9472eff410c6e140e9c Mon Sep 17 00:00:00 2001 From: varkor Date: Sat, 14 Apr 2018 19:20:51 +0100 Subject: [PATCH 15/40] Eliminate ty::Generics::types() And with one final incanation, the specific kind iterators were banished from ty::Generics, never to be seen again! --- src/librustc/middle/resolve_lifetime.rs | 7 ++++-- src/librustc/traits/error_reporting.rs | 4 ++-- src/librustc/traits/on_unimplemented.rs | 8 +++++-- src/librustc/ty/mod.rs | 10 --------- src/librustc/util/ppaux.rs | 25 ++++++++++++--------- src/librustc_trans/debuginfo/mod.rs | 2 +- src/librustc_typeck/check/compare_method.rs | 4 +++- src/librustc_typeck/check/wfcheck.rs | 14 +++++++++--- src/librustdoc/clean/mod.rs | 14 +++++++----- 9 files changed, 52 insertions(+), 36 deletions(-) diff --git a/src/librustc/middle/resolve_lifetime.rs b/src/librustc/middle/resolve_lifetime.rs index b450ef81c9178..f6d13c2a72f30 100644 --- a/src/librustc/middle/resolve_lifetime.rs +++ b/src/librustc/middle/resolve_lifetime.rs @@ -1659,8 +1659,11 @@ impl<'a, 'tcx> LifetimeContext<'a, 'tcx> { .entry(def_id) .or_insert_with(|| { tcx.generics_of(def_id) - .types_depr() - .map(|def| def.object_lifetime_default) + .params + .iter() + .filter_map(|param| { + param.get_type().and_then(|ty| Some(ty.object_lifetime_default)) + }) .collect() }) }; diff --git a/src/librustc/traits/error_reporting.rs b/src/librustc/traits/error_reporting.rs index b7f0e6a32ea15..d0166393f0184 100644 --- a/src/librustc/traits/error_reporting.rs +++ b/src/librustc/traits/error_reporting.rs @@ -378,9 +378,9 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { flags.push(("_Self".to_string(), Some(self.tcx.type_of(def.did).to_string()))); } - for param in generics.types_depr() { + for param in generics.params.iter().filter_map(|param| param.get_type()) { let name = param.name.to_string(); - let ty = trait_ref.substs.type_for_def(param); + let ty = trait_ref.substs.type_for_def(¶m); let ty_str = ty.to_string(); flags.push((name.clone(), Some(ty_str.clone()))); } diff --git a/src/librustc/traits/on_unimplemented.rs b/src/librustc/traits/on_unimplemented.rs index cee63e2ecc149..9fdbac49496cd 100644 --- a/src/librustc/traits/on_unimplemented.rs +++ b/src/librustc/traits/on_unimplemented.rs @@ -291,8 +291,12 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let name = tcx.item_name(trait_ref.def_id); let trait_str = tcx.item_path_str(trait_ref.def_id); let generics = tcx.generics_of(trait_ref.def_id); - let generic_map = generics.types_depr().map(|param| { - (param.name.to_string(), trait_ref.substs.type_for_def(param).to_string()) + let generic_map = generics.params.iter().filter_map(|param| { + if let Some(ty) = param.get_type() { + Some((ty.name.to_string(), trait_ref.substs.type_for_def(&ty).to_string())) + } else { + None + } }).collect::>(); let parser = Parser::new(&self.0); diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 680c03f02e1d5..4525bfc1baa2c 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -847,16 +847,6 @@ impl<'a, 'gcx, 'tcx> Generics { count } - pub fn types_depr(&self) -> impl DoubleEndedIterator { - self.params.iter().filter_map(|p| { - if let GenericParamDef::Type(ty) = p { - Some(ty) - } else { - None - } - }) - } - pub fn requires_monomorphization(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { if self.params.iter().any(|p| p.get_type().is_some()) { return true; diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index e8edf58a9db39..0817ededfaacc 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -25,6 +25,7 @@ use util::nodemap::{FxHashSet, FxHashMap}; use std::cell::Cell; use std::fmt; use std::usize; +use std::iter; use rustc_data_structures::indexed_vec::Idx; use rustc_target::spec::abi::Abi; @@ -335,17 +336,21 @@ impl PrintContext { } if !verbose { - if generics.types_depr().last().map_or(false, |def| def.has_default) { - if let Some(substs) = tcx.lift(&substs) { - let tps = substs.types().rev().skip(child_types); - for (def, actual) in generics.types_depr().rev().zip(tps) { - if !def.has_default { - break; - } - if tcx.type_of(def.def_id).subst(tcx, substs) != actual { - break; + let mut type_params = + generics.params.iter().rev().filter_map(|param| param.get_type()); + if let Some(last_ty) = type_params.next() { + if last_ty.has_default { + if let Some(substs) = tcx.lift(&substs) { + let mut tps = substs.types().rev().skip(child_types); + let zipped = iter::once((last_ty, tps.next().unwrap())) + .chain(type_params.zip(tps)); + for (ty, actual) in zipped { + if !ty.has_default || + tcx.type_of(ty.def_id).subst(tcx, substs) != actual { + break; + } + num_supplied_defaults += 1; } - num_supplied_defaults += 1; } } } diff --git a/src/librustc_trans/debuginfo/mod.rs b/src/librustc_trans/debuginfo/mod.rs index d50c74da31302..2463e571436e3 100644 --- a/src/librustc_trans/debuginfo/mod.rs +++ b/src/librustc_trans/debuginfo/mod.rs @@ -429,7 +429,7 @@ pub fn create_function_debug_context<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>, }); names.extend(generics.params.iter().map(|param| { match param { - GenericParamDef::Lifetime(lt) => (Kind::Lifetime, lt.name.as_str()), + GenericParamDef::Lifetime(lt) => (Kind::Lifetime, lt.name), GenericParamDef::Type(ty) => (Kind::Type, ty.name), } })); diff --git a/src/librustc_typeck/check/compare_method.rs b/src/librustc_typeck/check/compare_method.rs index 59728542bcda0..e02ba76405740 100644 --- a/src/librustc_typeck/check/compare_method.rs +++ b/src/librustc_typeck/check/compare_method.rs @@ -728,7 +728,9 @@ fn compare_synthetic_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let mut error_found = false; let impl_m_generics = tcx.generics_of(impl_m.def_id); let trait_m_generics = tcx.generics_of(trait_m.def_id); - for (impl_ty, trait_ty) in impl_m_generics.types_depr().zip(trait_m_generics.types_depr()) { + let impl_m_type_params = impl_m_generics.params.iter().filter_map(|param| param.get_type()); + let trait_m_type_params = trait_m_generics.params.iter().filter_map(|param| param.get_type()); + for (impl_ty, trait_ty) in impl_m_type_params.zip(trait_m_type_params) { if impl_ty.synthetic != trait_ty.synthetic { let impl_node_id = tcx.hir.as_local_node_id(impl_ty.def_id).unwrap(); let impl_span = tcx.hir.span(impl_node_id); diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index 804fed1010546..9eb53f2fdaecf 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -370,14 +370,22 @@ fn check_where_clauses<'a, 'gcx, 'fcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'gcx>, let mut substituted_predicates = Vec::new(); let generics = tcx.generics_of(def_id); - let is_our_default = |def: &ty::TypeParamDef| - def.has_default && def.index >= generics.parent_count as u32; + let is_our_default = |def: &ty::TypeParamDef| { + def.has_default && def.index >= generics.parent_count as u32 + }; // Check that concrete defaults are well-formed. See test `type-check-defaults.rs`. // For example this forbids the declaration: // struct Foo> { .. } // Here the default `Vec<[u32]>` is not WF because `[u32]: Sized` does not hold. - for d in generics.types_depr().cloned().filter(is_our_default).map(|p| p.def_id) { + for d in generics.params.iter().filter_map(|param| { + if let GenericParamDef::Type(ty) = *param { + if is_our_default(&ty) { + return Some(ty.def_id); + } + } + None + }) { let ty = fcx.tcx.type_of(d); // ignore dependent defaults -- that is, where the default of one type // parameter includes another (e.g., ). In those cases, we can't diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 6848b25097b8d..25766c553a5df 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1800,12 +1800,16 @@ impl<'a, 'tcx> Clean for (&'a ty::Generics, // Bounds in the type_params and lifetimes fields are repeated in the // predicates field (see rustc_typeck::collect::ty_generics), so remove // them. - let stripped_typarams = gens.types_depr().filter_map(|tp| { - if tp.name == keywords::SelfType.name().as_str() { - assert_eq!(tp.index, 0); - None + let stripped_typarams = gens.params.iter().filter_map(|param| { + if let ty::GenericParamDef::Type(ty) = param { + if ty.name == keywords::SelfType.name().as_str() { + assert_eq!(ty.index, 0); + None + } else { + Some(ty.clean(cx)) + } } else { - Some(tp.clean(cx)) + None } }).collect::>(); From 6f257bf26fb32cc72d4229b9bde6916562478165 Mon Sep 17 00:00:00 2001 From: varkor Date: Sun, 15 Apr 2018 00:22:29 +0100 Subject: [PATCH 16/40] Correct variable renaming fallout --- src/librustc_typeck/check/mod.rs | 4 ++-- src/librustc_typeck/impl_wf_check.rs | 4 ++-- src/librustdoc/clean/mod.rs | 4 ++-- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 6ed31a237ff5f..ad1e5ad799232 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -5094,8 +5094,8 @@ pub fn check_bounds_are_used<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, for param in generics.params.iter() { let key = match param { - hir::GenericParamDef::Type(_) => ty::Kind::Type, - hir::GenericParamDef::Lifetime(_) => ty::Kind::Lifetime, + hir::GenericParam::Type(_) => ty::Kind::Type, + hir::GenericParam::Lifetime(_) => ty::Kind::Lifetime, }; *param_counts.get_mut(&key).unwrap() += 1; } diff --git a/src/librustc_typeck/impl_wf_check.rs b/src/librustc_typeck/impl_wf_check.rs index 01e2bc3137433..1922a48d04a37 100644 --- a/src/librustc_typeck/impl_wf_check.rs +++ b/src/librustc_typeck/impl_wf_check.rs @@ -119,13 +119,13 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, .zip(impl_hir_generics.params.iter()) { match (ty_param, hir_param) { // Disallow ANY unconstrained type parameters. - (ty::GenericParamDef::Type(ty_ty), hir::GenericParamDef::Type(hir_ty)) => { + (ty::GenericParamDef::Type(ty_ty), hir::GenericParam::Type(hir_ty)) => { let param_ty = ty::ParamTy::for_def(ty_ty); if !input_parameters.contains(&ctp::Parameter::from(param_ty)) { report_unused_parameter(tcx, hir_ty.span, "type", ¶m_ty.to_string()); } } - (ty::GenericParamDef::Lifetime(ty_lt), hir::GenericParamDef::Lifetime(hir_lt)) => { + (ty::GenericParamDef::Lifetime(ty_lt), hir::GenericParam::Lifetime(hir_lt)) => { let param = ctp::Parameter::from(ty_lt.to_early_bound_region_data()); if lifetimes_in_associated_types.contains(¶m) && // (*) !input_parameters.contains(¶m) { diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 25766c553a5df..667d7f1e1605d 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -2687,7 +2687,7 @@ impl Clean for hir::Ty { let mut indices = FxHashMap(); for param in generics.params.iter() { match param { - GenericParamDef::Type(ty_param) => { + hir::GenericParam::Type(ty_param) => { let i = indices.entry(Kind::Type).or_insert(0); let ty_param_def = Def::TyParam(cx.tcx.hir.local_def_id(ty_param.id)); @@ -2699,7 +2699,7 @@ impl Clean for hir::Ty { } *i += 1; } - GenericParamDef::Lifetime(lt_param) => { + hir::GenericParam::Lifetime(lt_param) => { let i = indices.entry(Kind::Type).or_insert(0); if let Some(lt) = provided_params.lifetimes.get(*i).cloned() { if !lt.is_elided() { From a17896a3b69bfea821e4cf4c3c5c67d128cdbf47 Mon Sep 17 00:00:00 2001 From: varkor Date: Sun, 15 Apr 2018 01:36:31 +0100 Subject: [PATCH 17/40] Place Self at the start of ty::Generics' param lists --- src/librustc/ty/mod.rs | 19 +++++++------------ src/librustc_typeck/collect.rs | 14 +++++++++----- 2 files changed, 16 insertions(+), 17 deletions(-) diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 4525bfc1baa2c..0341078526267 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -794,12 +794,8 @@ impl GenericParamDef { /// Information about the formal type/lifetime parameters associated /// with an item or method. Analogous to hir::Generics. /// -/// Note that in the presence of a `Self` parameter, the ordering here -/// is different from the ordering in a Substs. Substs are ordered as -/// Self, *Regions, *Other Type Params, (...child generics) -/// while this struct is ordered as -/// regions = Regions -/// types = [Self, *Other Type Params] +/// The ordering of parameters is the same as in Subst (excluding child generics): +/// Self (optionally), Lifetime params..., Type params... #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] pub struct Generics { pub parent: Option, @@ -865,8 +861,7 @@ impl<'a, 'gcx, 'tcx> Generics { -> &'tcx RegionParamDef { if let Some(index) = param.index.checked_sub(self.parent_count as u32) { - // We're currently assuming that lifetimes precede other generic parameters. - match self.params[index as usize - self.has_self as usize] { + match self.params[index as usize] { ty::GenericParamDef::Lifetime(ref lt) => lt, _ => bug!("expected region parameter, but found another generic parameter") } @@ -881,7 +876,7 @@ impl<'a, 'gcx, 'tcx> Generics { param: &ParamTy, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> &TypeParamDef { - if let Some(idx) = param.idx.checked_sub(self.parent_count as u32) { + if let Some(index) = param.idx.checked_sub(self.parent_count as u32) { // non-Self type parameters are always offset by exactly // `self.regions.len()`. In the absence of a Self, this is obvious, // but even in the presence of a `Self` we just have to "compensate" @@ -912,11 +907,11 @@ impl<'a, 'gcx, 'tcx> Generics { let type_param_offset = self.param_counts()[&Kind::Lifetime]; let has_self = self.has_self && self.parent.is_none(); - let is_separated_self = type_param_offset != 0 && idx == 0 && has_self; + let is_separated_self = type_param_offset != 0 && index == 0 && has_self; - if let Some(_) = (idx as usize).checked_sub(type_param_offset) { + if let Some(_) = (index as usize).checked_sub(type_param_offset) { assert!(!is_separated_self, "found a Self after type_param_offset"); - match self.params[idx as usize] { + match self.params[index as usize] { ty::GenericParamDef::Type(ref ty) => ty, _ => bug!("expected type parameter, but found another generic parameter") } diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 869ae779c1747..1a8d4392f645e 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -927,7 +927,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } }); - let mut types: Vec<_> = opt_self.into_iter().chain(types).collect(); + let mut types: Vec<_> = types.into_iter().collect(); // provide junk type parameter defs - the only place that // cares about anything but the length is instantiation, @@ -966,13 +966,17 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }); } - let type_param_to_index = types.iter() - .map(|param| (param.def_id, param.index)) - .collect(); + let type_param_to_index = opt_self.iter() + .chain(types.iter()) + .map(|ty| (ty.def_id, ty.index)) + .collect(); + let opt_self = opt_self.into_iter().map(|ty| ty::GenericParamDef::Type(ty)); let lifetimes = regions.into_iter().map(|lt| ty::GenericParamDef::Lifetime(lt)); let types = types.into_iter().map(|ty| ty::GenericParamDef::Type(ty)); - let params = lifetimes.chain(types).collect(); + let params = opt_self.chain(lifetimes) + .chain(types) + .collect(); tcx.alloc_generics(ty::Generics { parent: parent_def_id, From 7b45a892a482f70ccb696abdcab089cce5f2d612 Mon Sep 17 00:00:00 2001 From: varkor Date: Wed, 18 Apr 2018 11:33:52 +0100 Subject: [PATCH 18/40] Use GenericParamCount instead of FxHashMap --- src/librustc/hir/lowering.rs | 3 +- src/librustc/traits/object_safety.rs | 4 +- src/librustc/ty/mod.rs | 39 +++++++++----------- src/librustc/util/ppaux.rs | 22 +++++------ src/librustc_mir/monomorphize/collector.rs | 2 +- src/librustc_mir/transform/check_unsafety.rs | 4 +- src/librustc_trans/debuginfo/mod.rs | 8 +++- src/librustc_typeck/astconv.rs | 6 +-- src/librustc_typeck/check/compare_method.rs | 10 ++--- src/librustc_typeck/check/intrinsic.rs | 6 +-- src/librustc_typeck/check/method/confirm.rs | 4 +- src/librustc_typeck/check/mod.rs | 27 ++++---------- src/librustdoc/clean/mod.rs | 35 ++++++++++-------- 13 files changed, 81 insertions(+), 89 deletions(-) diff --git a/src/librustc/hir/lowering.rs b/src/librustc/hir/lowering.rs index c780d1b72f2a0..77c2dd219c478 100644 --- a/src/librustc/hir/lowering.rs +++ b/src/librustc/hir/lowering.rs @@ -46,7 +46,6 @@ use hir::HirVec; use hir::map::{DefKey, DefPathData, Definitions}; use hir::def_id::{DefId, DefIndex, DefIndexAddressSpace, CRATE_DEF_INDEX}; use hir::def::{Def, PathResolution}; -use ty::Kind; use lint::builtin::{self, PARENTHESIZED_PARAMS_IN_TYPES_AND_MODULES}; use middle::cstore::CrateStore; use rustc_data_structures::indexed_vec::IndexVec; @@ -1462,7 +1461,7 @@ impl<'a> LoweringContext<'a> { assert!(!def_id.is_local()); let item_generics = self.cstore.item_generics_cloned_untracked(def_id, self.sess); - let n = item_generics.param_counts()[&Kind::Lifetime]; + let n = item_generics.param_counts().lifetimes; self.type_def_lifetime_params.insert(def_id, n); n }); diff --git a/src/librustc/traits/object_safety.rs b/src/librustc/traits/object_safety.rs index cb8ff674188c4..d659d235cd13a 100644 --- a/src/librustc/traits/object_safety.rs +++ b/src/librustc/traits/object_safety.rs @@ -21,7 +21,7 @@ use super::elaborate_predicates; use hir::def_id::DefId; use traits; -use ty::{self, Ty, TyCtxt, Kind, TypeFoldable}; +use ty::{self, Ty, TyCtxt, TypeFoldable}; use ty::subst::Substs; use ty::util::ExplicitSelf; use std::borrow::Cow; @@ -284,7 +284,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { } // We can't monomorphize things like `fn foo(...)`. - if self.generics_of(method.def_id).param_counts()[&Kind::Type] != 0 { + if self.generics_of(method.def_id).param_counts().types != 0 { return Some(MethodViolationCode::Generic); } diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 0341078526267..0cbee56487ff2 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -757,18 +757,6 @@ impl ty::EarlyBoundRegion { } } -#[derive(PartialEq, Eq, Hash, Copy, Clone, Debug, RustcEncodable, RustcDecodable)] -pub enum Kind { - Lifetime, - Type, -} - -impl Kind { - pub fn iter<'a>() -> impl Iterator { - [Kind::Lifetime, Kind::Type].into_iter() - } -} - #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] pub enum GenericParamDef { Lifetime(RegionParamDef), @@ -791,6 +779,11 @@ impl GenericParamDef { } } +pub struct GenericParamCount { + pub lifetimes: usize, + pub types: usize, +} + /// Information about the formal type/lifetime parameters associated /// with an item or method. Analogous to hir::Generics. /// @@ -814,18 +807,20 @@ impl<'a, 'gcx, 'tcx> Generics { self.parent_count + self.params.len() } - pub fn param_counts(&self) -> FxHashMap { - let mut param_counts: FxHashMap<_, _> = FxHashMap(); - Kind::iter().for_each(|kind| { - param_counts.insert(*kind, 0); - }); + pub fn param_counts(&self) -> GenericParamCount { + // We could cache this as a property of `GenericParamCount`, but + // the aim is to refactor this away entirely eventually and the + // presence of this method will be a constant reminder. + let mut param_counts = GenericParamCount { + lifetimes: 0, + types: 0, + }; for param in self.params.iter() { - let key = match param { - GenericParamDef::Type(_) => Kind::Type, - GenericParamDef::Lifetime(_) => Kind::Lifetime, + match param { + GenericParamDef::Lifetime(_) => param_counts.lifetimes += 1, + GenericParamDef::Type(_) => param_counts.types += 1, }; - *param_counts.get_mut(&key).unwrap() += 1; } param_counts @@ -904,7 +899,7 @@ impl<'a, 'gcx, 'tcx> Generics { // And it can be seen that in both cases, to move from a substs // offset to a generics offset you just have to offset by the // number of regions. - let type_param_offset = self.param_counts()[&Kind::Lifetime]; + let type_param_offset = self.param_counts().lifetimes; let has_self = self.has_self && self.parent.is_none(); let is_separated_self = type_param_offset != 0 && index == 0 && has_self; diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index 0817ededfaacc..ba8694602526c 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -19,8 +19,8 @@ use ty::{TyError, TyStr, TyArray, TySlice, TyFloat, TyFnDef, TyFnPtr}; use ty::{TyParam, TyRawPtr, TyRef, TyNever, TyTuple}; use ty::{TyClosure, TyGenerator, TyGeneratorWitness, TyForeign, TyProjection, TyAnon}; use ty::{TyDynamic, TyInt, TyUint, TyInfer}; -use ty::{self, Ty, TyCtxt, TypeFoldable, Kind}; -use util::nodemap::{FxHashSet, FxHashMap}; +use ty::{self, Ty, TyCtxt, TypeFoldable, GenericParamCount}; +use util::nodemap::FxHashSet; use std::cell::Cell; use std::fmt; @@ -257,10 +257,10 @@ impl PrintContext { let verbose = self.is_verbose; let mut num_supplied_defaults = 0; let mut has_self = false; - let mut param_counts = FxHashMap(); - Kind::iter().for_each(|kind| { - param_counts.insert(*kind, 0); - }); + let mut param_counts = GenericParamCount { + lifetimes: 0, + types: 0, + }; let mut is_value_path = false; let fn_trait_kind = ty::tls::with(|tcx| { // Unfortunately, some kinds of items (e.g., closures) don't have @@ -314,7 +314,7 @@ impl PrintContext { if let Some(def_id) = generics.parent { // Methods. assert!(is_value_path); - child_types = child_param_counts[&Kind::Type]; + child_types = child_param_counts.types; generics = tcx.generics_of(def_id); param_counts = generics.param_counts(); @@ -407,10 +407,10 @@ impl PrintContext { Ok(()) }; - print_regions(f, "<", 0, param_counts[&Kind::Lifetime])?; + print_regions(f, "<", 0, param_counts.lifetimes)?; let tps = substs.types() - .take(param_counts[&Kind::Type] - num_supplied_defaults) + .take(param_counts.types - num_supplied_defaults) .skip(has_self as usize); for ty in tps { @@ -442,10 +442,10 @@ impl PrintContext { write!(f, "::{}", item_name)?; } - print_regions(f, "::<", param_counts[&Kind::Lifetime], usize::MAX)?; + print_regions(f, "::<", param_counts.lifetimes, usize::MAX)?; // FIXME: consider being smart with defaults here too - for ty in substs.types().skip(param_counts[&Kind::Type]) { + for ty in substs.types().skip(param_counts.types) { start_or_continue(f, "::<", ", ")?; ty.print_display(f, self)?; } diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index 99a7e0abe1679..92b4babe8a3b2 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -1108,7 +1108,7 @@ fn create_mono_items_for_default_impls<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, continue; } - if tcx.generics_of(method.def_id).param_counts()[&ty::Kind::Type] != 0 { + if tcx.generics_of(method.def_id).param_counts().types != 0 { continue; } diff --git a/src/librustc_mir/transform/check_unsafety.rs b/src/librustc_mir/transform/check_unsafety.rs index 58e63fe6b048d..b65353e449f68 100644 --- a/src/librustc_mir/transform/check_unsafety.rs +++ b/src/librustc_mir/transform/check_unsafety.rs @@ -13,7 +13,7 @@ use rustc_data_structures::indexed_vec::IndexVec; use rustc_data_structures::sync::Lrc; use rustc::ty::maps::Providers; -use rustc::ty::{self, TyCtxt, Kind}; +use rustc::ty::{self, TyCtxt}; use rustc::hir; use rustc::hir::def_id::DefId; use rustc::lint::builtin::{SAFE_EXTERN_STATICS, SAFE_PACKED_BORROWS, UNUSED_UNSAFE}; @@ -357,7 +357,7 @@ fn unsafe_derive_on_repr_packed<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: D // FIXME: when we make this a hard error, this should have its // own error code. - let message = if tcx.generics_of(def_id).param_counts()[&Kind::Type] != 0 { + let message = if tcx.generics_of(def_id).param_counts().types != 0 { format!("#[derive] can't be used on a #[repr(packed)] struct with \ type parameters (error E0133)") } else { diff --git a/src/librustc_trans/debuginfo/mod.rs b/src/librustc_trans/debuginfo/mod.rs index 2463e571436e3..0990c1f1714c9 100644 --- a/src/librustc_trans/debuginfo/mod.rs +++ b/src/librustc_trans/debuginfo/mod.rs @@ -26,7 +26,7 @@ use llvm::debuginfo::{DIFile, DIType, DIScope, DIBuilderRef, DISubprogram, DIArr use rustc::hir::TransFnAttrFlags; use rustc::hir::def_id::{DefId, CrateNum}; use rustc::ty::subst::Substs; -use rustc::ty::{Kind, GenericParamDef}; +use rustc::ty::GenericParamDef; use abi::Abi; use common::CodegenCx; @@ -197,6 +197,12 @@ pub fn finalize(cx: &CodegenCx) { }; } +#[derive(PartialEq, Eq, Hash)] +pub enum Kind { + Lifetime, + Type, +} + /// Creates the function-specific debug context. /// /// Returns the FunctionDebugContext for the function which holds state needed diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index d77a090de682d..11003a49316ea 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -210,7 +210,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { let decl_generics = tcx.generics_of(def_id); let param_counts = decl_generics.param_counts(); let num_types_provided = parameters.types.len(); - let expected_num_region_params = param_counts[&ty::Kind::Lifetime]; + let expected_num_region_params = param_counts.lifetimes; let supplied_num_region_params = parameters.lifetimes.len(); if expected_num_region_params != supplied_num_region_params { report_lifetime_number_error(tcx, span, @@ -223,7 +223,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { // Check the number of type parameters supplied by the user. let type_params_offset = self_ty.is_some() as usize; - let ty_param_defs = param_counts[&ty::Kind::Type] - type_params_offset; + let ty_param_defs = param_counts.types - type_params_offset; if !infer_types || num_types_provided > ty_param_defs { check_type_argument_count(tcx, span, @@ -260,7 +260,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { return ty; } - let i = i - (param_counts[&ty::Kind::Lifetime] + type_params_offset); + let i = i - (param_counts.lifetimes + type_params_offset); if i < num_types_provided { // A provided type parameter. self.ast_ty_to_ty(¶meters.types[i]) diff --git a/src/librustc_typeck/check/compare_method.rs b/src/librustc_typeck/check/compare_method.rs index e02ba76405740..c2c250249ad8e 100644 --- a/src/librustc_typeck/check/compare_method.rs +++ b/src/librustc_typeck/check/compare_method.rs @@ -10,7 +10,7 @@ use rustc::hir::{self, ImplItemKind, TraitItemKind}; use rustc::infer::{self, InferOk}; -use rustc::ty::{self, TyCtxt, Kind}; +use rustc::ty::{self, TyCtxt}; use rustc::ty::util::ExplicitSelf; use rustc::traits::{self, ObligationCause, ObligationCauseCode, Reveal}; use rustc::ty::error::{ExpectedFound, TypeError}; @@ -357,8 +357,8 @@ fn check_region_bounds_on_impl_method<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, trait_to_skol_substs: &Substs<'tcx>) -> Result<(), ErrorReported> { let span = tcx.sess.codemap().def_span(span); - let trait_params = trait_generics.param_counts()[&Kind::Lifetime]; - let impl_params = impl_generics.param_counts()[&Kind::Lifetime]; + let trait_params = trait_generics.param_counts().lifetimes; + let impl_params = impl_generics.param_counts().lifetimes; debug!("check_region_bounds_on_impl_method: \ trait_generics={:?} \ @@ -574,8 +574,8 @@ fn compare_number_of_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, -> Result<(), ErrorReported> { let impl_m_generics = tcx.generics_of(impl_m.def_id); let trait_m_generics = tcx.generics_of(trait_m.def_id); - let num_impl_m_type_params = impl_m_generics.param_counts()[&Kind::Type]; - let num_trait_m_type_params = trait_m_generics.param_counts()[&Kind::Type]; + let num_impl_m_type_params = impl_m_generics.param_counts().types; + let num_trait_m_type_params = trait_m_generics.param_counts().types; if num_impl_m_type_params != num_trait_m_type_params { let impl_m_node_id = tcx.hir.as_local_node_id(impl_m.def_id).unwrap(); let impl_m_item = tcx.hir.expect_impl_item(impl_m_node_id); diff --git a/src/librustc_typeck/check/intrinsic.rs b/src/librustc_typeck/check/intrinsic.rs index e3d7e16e15c97..1817b4aba1912 100644 --- a/src/librustc_typeck/check/intrinsic.rs +++ b/src/librustc_typeck/check/intrinsic.rs @@ -13,7 +13,7 @@ use intrinsics; use rustc::traits::{ObligationCause, ObligationCauseCode}; -use rustc::ty::{self, TyCtxt, Ty, Kind}; +use rustc::ty::{self, TyCtxt, Ty}; use rustc::util::nodemap::FxHashMap; use require_same_types; @@ -45,7 +45,7 @@ fn equate_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } } - let i_n_tps = tcx.generics_of(def_id).param_counts()[&Kind::Type]; + let i_n_tps = tcx.generics_of(def_id).param_counts().types; if i_n_tps != n_tps { let span = match it.node { hir::ForeignItemFn(_, _, ref generics) => generics.span, @@ -346,7 +346,7 @@ pub fn check_platform_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }; let def_id = tcx.hir.local_def_id(it.id); - let i_n_tps = tcx.generics_of(def_id).param_counts()[&Kind::Type]; + let i_n_tps = tcx.generics_of(def_id).param_counts().types; let name = it.name.as_str(); let (n_tps, inputs, output) = match &*name { diff --git a/src/librustc_typeck/check/method/confirm.rs b/src/librustc_typeck/check/method/confirm.rs index 038927bbac647..eab26046147b5 100644 --- a/src/librustc_typeck/check/method/confirm.rs +++ b/src/librustc_typeck/check/method/confirm.rs @@ -15,7 +15,7 @@ use check::{FnCtxt, PlaceOp, callee, Needs}; use hir::def_id::DefId; use rustc::ty::subst::Substs; use rustc::traits; -use rustc::ty::{self, Ty, Kind}; +use rustc::ty::{self, Ty}; use rustc::ty::subst::Subst; use rustc::ty::adjustment::{Adjustment, Adjust, OverloadedDeref}; use rustc::ty::adjustment::{AllowTwoPhase, AutoBorrow, AutoBorrowMutability}; @@ -333,7 +333,7 @@ impl<'a, 'gcx, 'tcx> ConfirmContext<'a, 'gcx, 'tcx> { } else if let Some(ast_ty) = provided.as_ref().and_then(|p| { let idx = - i - parent_substs.len() - method_generics.param_counts()[&Kind::Lifetime]; + i - parent_substs.len() - method_generics.param_counts().lifetimes; p.types.get(idx) }) { diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index ad1e5ad799232..3df584040ad31 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -1239,8 +1239,7 @@ pub fn check_item_type<'a,'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, it: &'tcx hir::Item } else { for item in &m.items { let generics = tcx.generics_of(tcx.hir.local_def_id(item.id)); - let param_counts = generics.param_counts(); - if generics.params.len() - param_counts[&ty::Kind::Lifetime] != 0 { + if generics.params.len() - generics.param_counts().lifetimes != 0 { let mut err = struct_span_err!(tcx.sess, item.span, E0044, "foreign items may not have type parameters"); err.span_label(item.span, "can't have type parameters"); @@ -4800,7 +4799,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // Skip over the lifetimes in the same segment. if let Some((_, generics)) = segment { - i -= generics.param_counts()[&ty::Kind::Lifetime]; + i -= generics.param_counts().lifetimes; } if let Some(ast_ty) = types.get(i) { @@ -4921,15 +4920,15 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // Check provided parameters. let (ty_non_def_req_len, ty_req_len, lt_req_len) = segment.map_or((0, 0, 0), |(_, generics)| { - let params_count = generics.param_counts(); + let param_counts = generics.param_counts(); let type_params_offset = (generics.parent.is_none() && generics.has_self) as usize; - let type_params = params_count[&ty::Kind::Type] - type_params_offset; + let type_params = param_counts.types - type_params_offset; let type_params_barring_defaults = generics.type_params_without_defaults() - type_params_offset; - (type_params_barring_defaults, type_params, params_count[&ty::Kind::Lifetime]) + (type_params_barring_defaults, type_params, param_counts.lifetimes) }); if types.len() > ty_req_len { @@ -5088,22 +5087,12 @@ pub fn check_bounds_are_used<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, if generics.ty_params().next().is_none() { return; } let mut tps_used = vec![false; generics.ty_params().count()]; - let mut param_counts = FxHashMap(); - param_counts.insert(ty::Kind::Type, 0); - param_counts.insert(ty::Kind::Lifetime, 0); - - for param in generics.params.iter() { - let key = match param { - hir::GenericParam::Type(_) => ty::Kind::Type, - hir::GenericParam::Lifetime(_) => ty::Kind::Lifetime, - }; - *param_counts.get_mut(&key).unwrap() += 1; - } + let lifetime_count = generics.lifetimes().count(); for leaf_ty in ty.walk() { - if let ty::TyParam(ty::ParamTy {idx, .. }) = leaf_ty.sty { + if let ty::TyParam(ty::ParamTy {idx, ..}) = leaf_ty.sty { debug!("Found use of ty param num {}", idx); - tps_used[idx as usize - param_counts[&ty::Kind::Lifetime]] = true; + tps_used[idx as usize - lifetime_count] = true; } else if let ty::TyError = leaf_ty.sty { // If there already another error, do not emit an error for not using a type Parameter assert!(tcx.sess.err_count() > 0); diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 667d7f1e1605d..5146a29d4e371 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -41,7 +41,7 @@ use rustc::hir::def::{self, Def, CtorKind}; use rustc::hir::def_id::{CrateNum, DefId, DefIndex, CRATE_DEF_INDEX, LOCAL_CRATE}; use rustc::hir::def_id::DefIndexAddressSpace; use rustc::ty::subst::Substs; -use rustc::ty::{self, TyCtxt, Region, RegionVid, Ty, AdtKind, Kind}; +use rustc::ty::{self, TyCtxt, Region, RegionVid, Ty, AdtKind, GenericParamCount}; use rustc::middle::stability; use rustc::util::nodemap::{FxHashMap, FxHashSet}; use rustc_typeck::hir_ty_to_ty; @@ -2684,31 +2684,34 @@ impl Clean for hir::Ty { let mut ty_substs = FxHashMap(); let mut lt_substs = FxHashMap(); provided_params.with_parameters(|provided_params| { - let mut indices = FxHashMap(); + let mut indices = GenericParamCount { + lifetimes: 0, + types: 0 + }; for param in generics.params.iter() { match param { + hir::GenericParam::Lifetime(lt_param) => { + if let Some(lt) = provided_params.lifetimes + .get(indices.lifetimes).cloned() { + if !lt.is_elided() { + let lt_def_id = + cx.tcx.hir.local_def_id(lt_param.lifetime.id); + lt_substs.insert(lt_def_id, lt.clean(cx)); + } + } + indices.lifetimes += 1; + } hir::GenericParam::Type(ty_param) => { - let i = indices.entry(Kind::Type).or_insert(0); let ty_param_def = Def::TyParam(cx.tcx.hir.local_def_id(ty_param.id)); - if let Some(ty) = provided_params.types.get(*i).cloned() { + if let Some(ty) = provided_params.types + .get(indices.types).cloned() { ty_substs.insert(ty_param_def, ty.into_inner().clean(cx)); } else if let Some(default) = ty_param.default.clone() { ty_substs.insert(ty_param_def, default.into_inner().clean(cx)); } - *i += 1; - } - hir::GenericParam::Lifetime(lt_param) => { - let i = indices.entry(Kind::Type).or_insert(0); - if let Some(lt) = provided_params.lifetimes.get(*i).cloned() { - if !lt.is_elided() { - let lt_def_id = - cx.tcx.hir.local_def_id(lt_param.lifetime.id); - lt_substs.insert(lt_def_id, lt.clean(cx)); - } - } - *i += 1; + indices.types += 1; } } } From df1c256a2b1e7c68f343f40a870fa762a63a0a05 Mon Sep 17 00:00:00 2001 From: varkor Date: Wed, 18 Apr 2018 12:45:13 +0100 Subject: [PATCH 19/40] Replace type_param_to_index with param_def_id_to_index --- src/librustc/ich/impls_ty.rs | 2 +- src/librustc/ty/mod.rs | 2 +- src/librustc_typeck/astconv.rs | 2 +- src/librustc_typeck/check/mod.rs | 2 +- src/librustc_typeck/collect.rs | 25 +++++++++++++++---------- 5 files changed, 19 insertions(+), 14 deletions(-) diff --git a/src/librustc/ich/impls_ty.rs b/src/librustc/ich/impls_ty.rs index d0427ef4be227..fc0a9ac9d18f3 100644 --- a/src/librustc/ich/impls_ty.rs +++ b/src/librustc/ich/impls_ty.rs @@ -740,7 +740,7 @@ impl<'a> HashStable> for ty::Generics { // Reverse map to each `TypeParamDef`'s `index` field, from // `def_id.index` (`def_id.krate` is the same as the item's). - type_param_to_index: _, // Don't hash this + param_def_id_to_index: _, // Don't hash this has_self, has_late_bound_regions, } = *self; diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 0cbee56487ff2..35a44bcf40309 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -796,7 +796,7 @@ pub struct Generics { pub params: Vec, /// Reverse map to each `TypeParamDef`'s `index` field - pub type_param_to_index: FxHashMap, + pub param_def_id_to_index: FxHashMap, pub has_self: bool, pub has_late_bound_regions: Option, diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index 11003a49316ea..2c9995b25a1bd 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -985,7 +985,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { let item_id = tcx.hir.get_parent_node(node_id); let item_def_id = tcx.hir.local_def_id(item_id); let generics = tcx.generics_of(item_def_id); - let index = generics.type_param_to_index[&tcx.hir.local_def_id(node_id)]; + let index = generics.param_def_id_to_index[&tcx.hir.local_def_id(node_id)]; tcx.mk_param(index, tcx.hir.name(node_id).as_interned_str()) } Def::SelfTy(_, Some(def_id)) => { diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 3df584040ad31..0726650b05480 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -1716,7 +1716,7 @@ impl<'a, 'gcx, 'tcx> AstConv<'gcx, 'tcx> for FnCtxt<'a, 'gcx, 'tcx> { let item_id = tcx.hir.ty_param_owner(node_id); let item_def_id = tcx.hir.local_def_id(item_id); let generics = tcx.generics_of(item_def_id); - let index = generics.type_param_to_index[&def_id]; + let index = generics.param_def_id_to_index[&def_id]; ty::GenericPredicates { parent: None, predicates: self.param_env.caller_bounds.iter().filter(|predicate| { diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 1a8d4392f645e..452b76e1b702f 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -243,7 +243,7 @@ fn type_param_predicates<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let param_owner = tcx.hir.ty_param_owner(param_id); let param_owner_def_id = tcx.hir.local_def_id(param_owner); let generics = tcx.generics_of(param_owner_def_id); - let index = generics.type_param_to_index[&def_id]; + let index = generics.param_def_id_to_index[&def_id]; let ty = tcx.mk_param(index, tcx.hir.ty_param_name(param_id).as_interned_str()); // Don't look for bounds where the type parameter isn't in scope. @@ -966,23 +966,28 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }); } - let type_param_to_index = opt_self.iter() - .chain(types.iter()) - .map(|ty| (ty.def_id, ty.index)) - .collect(); - let opt_self = opt_self.into_iter().map(|ty| ty::GenericParamDef::Type(ty)); let lifetimes = regions.into_iter().map(|lt| ty::GenericParamDef::Lifetime(lt)); let types = types.into_iter().map(|ty| ty::GenericParamDef::Type(ty)); - let params = opt_self.chain(lifetimes) - .chain(types) - .collect(); + let params: Vec<_> = opt_self.chain(lifetimes) + .chain(types) + .collect(); + + let param_def_id_to_index = + params.iter() + .map(|param| { + match param { + ty::GenericParamDef::Lifetime(lt) => (lt.def_id, lt.index), + ty::GenericParamDef::Type(ty) => (ty.def_id, ty.index), + } + }) + .collect(); tcx.alloc_generics(ty::Generics { parent: parent_def_id, parent_count, params, - type_param_to_index, + param_def_id_to_index, has_self: has_self || parent_has_self, has_late_bound_regions: has_late_bound_regions(tcx, node), }) From d62fc236f9b87671955921ef0207c61056fe8af8 Mon Sep 17 00:00:00 2001 From: varkor Date: Wed, 18 Apr 2018 17:15:53 +0100 Subject: [PATCH 20/40] Refactor to address comments --- src/librustc/traits/object_safety.rs | 3 +- src/librustc/ty/mod.rs | 23 +++++------- src/librustc/ty/subst.rs | 13 ------- src/librustc_traits/dropck_outlives.rs | 7 +--- src/librustc_trans/debuginfo/mod.rs | 48 +++++++++++--------------- src/librustc_typeck/astconv.rs | 14 +++++++- src/librustc_typeck/check/mod.rs | 13 ++++++- src/librustc_typeck/check/wfcheck.rs | 2 +- src/librustc_typeck/collect.rs | 12 ++----- 9 files changed, 60 insertions(+), 75 deletions(-) diff --git a/src/librustc/traits/object_safety.rs b/src/librustc/traits/object_safety.rs index d659d235cd13a..7c68d5522fcc3 100644 --- a/src/librustc/traits/object_safety.rs +++ b/src/librustc/traits/object_safety.rs @@ -387,7 +387,6 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { } pub(super) fn is_object_safe_provider<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, - trait_def_id: DefId) - -> bool { + trait_def_id: DefId) -> bool { tcx.object_safety_violations(trait_def_id).is_empty() } diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 35a44bcf40309..635713a786650 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -767,7 +767,14 @@ impl GenericParamDef { pub fn index(&self) -> u32 { match self { GenericParamDef::Lifetime(lt) => lt.index, - GenericParamDef::Type(ty) => ty.index, + GenericParamDef::Type(ty) => ty.index, + } + } + + pub fn def_id(&self) -> DefId { + match self { + GenericParamDef::Lifetime(lt) => lt.def_id, + GenericParamDef::Type(ty) => ty.def_id, } } @@ -795,7 +802,7 @@ pub struct Generics { pub parent_count: usize, pub params: Vec, - /// Reverse map to each `TypeParamDef`'s `index` field + /// Reverse map to the `index` field of each `GenericParamDef`'s inner type pub param_def_id_to_index: FxHashMap, pub has_self: bool, @@ -826,18 +833,6 @@ impl<'a, 'gcx, 'tcx> Generics { param_counts } - pub fn type_params_without_defaults(&self) -> usize { - let mut count = 0; - for param in self.params.iter() { - if let GenericParamDef::Type(ty) = param { - if !ty.has_default { - count += 1 - } - } - } - count - } - pub fn requires_monomorphization(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { if self.params.iter().any(|p| p.get_type().is_some()) { return true; diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index a9077eb193f38..0808cc84bf7aa 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -241,25 +241,12 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { mk_type: &mut FT) where FR: FnMut(&ty::RegionParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, FT: FnMut(&ty::TypeParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { - // Handle Self first, before all regions. - let mut skip_self = defs.parent.is_none() && defs.has_self; - if skip_self { - let def = defs.params.iter().find_map(|p| p.get_type()).unwrap(); - let ty = mk_type(&def, substs); - assert_eq!(def.index as usize, substs.len()); - substs.push(ty.into()); - } - for def in &defs.params { let param = match def { ty::GenericParamDef::Lifetime(ref lt) => { mk_region(lt, substs).into() } ty::GenericParamDef::Type(ref ty) => { - if skip_self { - skip_self = false; - continue - } mk_type(ty, substs).into() } }; diff --git a/src/librustc_traits/dropck_outlives.rs b/src/librustc_traits/dropck_outlives.rs index c9c0902940e54..f333968829286 100644 --- a/src/librustc_traits/dropck_outlives.rs +++ b/src/librustc_traits/dropck_outlives.rs @@ -280,12 +280,7 @@ crate fn adt_dtorck_constraint<'a, 'tcx>( if def.is_phantom_data() { let result = DtorckConstraint { outlives: vec![], - dtorck_types: vec![tcx.mk_param_from_def( - &tcx.generics_of(def_id) - .params - .iter() - .find_map(|p| p.get_type()) - .expect("should be at least one type parameter"))], + dtorck_types: vec![tcx.mk_param_from_def(&tcx.generics_of(def_id).params[0].get_type().unwrap())], overflows: vec![], }; debug!("dtorck_constraint: {:?} => {:?}", def, result); diff --git a/src/librustc_trans/debuginfo/mod.rs b/src/librustc_trans/debuginfo/mod.rs index 0990c1f1714c9..31ef1eddfcbf5 100644 --- a/src/librustc_trans/debuginfo/mod.rs +++ b/src/librustc_trans/debuginfo/mod.rs @@ -25,7 +25,7 @@ use llvm::{ModuleRef, ContextRef, ValueRef}; use llvm::debuginfo::{DIFile, DIType, DIScope, DIBuilderRef, DISubprogram, DIArray, DIFlags}; use rustc::hir::TransFnAttrFlags; use rustc::hir::def_id::{DefId, CrateNum}; -use rustc::ty::subst::Substs; +use rustc::ty::subst::{Substs, UnpackedKind}; use rustc::ty::GenericParamDef; use abi::Abi; @@ -197,12 +197,6 @@ pub fn finalize(cx: &CodegenCx) { }; } -#[derive(PartialEq, Eq, Hash)] -pub enum Kind { - Lifetime, - Type, -} - /// Creates the function-specific debug context. /// /// Returns the FunctionDebugContext for the function which holds state needed @@ -398,27 +392,25 @@ pub fn create_function_debug_context<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>, // Again, only create type information if full debuginfo is enabled let template_params: Vec<_> = if cx.sess().opts.debuginfo == FullDebugInfo { let names = get_parameter_names(cx, generics); - let names = names.iter().flat_map(|(kind, param)| { - if kind == &Kind::Type { - Some(param) + substs.iter().zip(names).filter_map(|(kind, name)| { + if let UnpackedKind::Type(ty) = kind.unpack() { + let actual_type = cx.tcx.normalize_erasing_regions(ParamEnv::reveal_all(), ty); + let actual_type_metadata = + type_metadata(cx, actual_type, syntax_pos::DUMMY_SP); + let name = CString::new(name.as_str().as_bytes()).unwrap(); + Some(unsafe { + llvm::LLVMRustDIBuilderCreateTemplateTypeParameter( + DIB(cx), + ptr::null_mut(), + name.as_ptr(), + actual_type_metadata, + file_metadata, + 0, + 0) + }) } else { None } - }); - substs.types().zip(names).map(|(ty, name)| { - let actual_type = cx.tcx.normalize_erasing_regions(ParamEnv::reveal_all(), ty); - let actual_type_metadata = type_metadata(cx, actual_type, syntax_pos::DUMMY_SP); - let name = CString::new(name.as_str().as_bytes()).unwrap(); - unsafe { - llvm::LLVMRustDIBuilderCreateTemplateTypeParameter( - DIB(cx), - ptr::null_mut(), - name.as_ptr(), - actual_type_metadata, - file_metadata, - 0, - 0) - } }).collect() } else { vec![] @@ -429,14 +421,14 @@ pub fn create_function_debug_context<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>, fn get_parameter_names(cx: &CodegenCx, generics: &ty::Generics) - -> Vec<(Kind, InternedString)> { + -> Vec { let mut names = generics.parent.map_or(vec![], |def_id| { get_parameter_names(cx, cx.tcx.generics_of(def_id)) }); names.extend(generics.params.iter().map(|param| { match param { - GenericParamDef::Lifetime(lt) => (Kind::Lifetime, lt.name), - GenericParamDef::Type(ty) => (Kind::Type, ty.name), + GenericParamDef::Lifetime(lt) => lt.name, + GenericParamDef::Type(ty) => ty.name, } })); names diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index 2c9995b25a1bd..84d94539f7436 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -225,11 +225,23 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { let type_params_offset = self_ty.is_some() as usize; let ty_param_defs = param_counts.types - type_params_offset; if !infer_types || num_types_provided > ty_param_defs { + let type_params_without_defaults = { + let mut count = 0; + for param in decl_generics.params.iter() { + if let ty::GenericParamDef::Type(ty) = param { + if !ty.has_default { + count += 1 + } + } + } + count + }; + check_type_argument_count(tcx, span, num_types_provided, ty_param_defs, - decl_generics.type_params_without_defaults() - type_params_offset); + type_params_without_defaults - type_params_offset); } let is_object = self_ty.map_or(false, |ty| ty.sty == TRAIT_OBJECT_DUMMY_SELF); diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 0726650b05480..f860c1358a6da 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -4925,8 +4925,19 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { let type_params_offset = (generics.parent.is_none() && generics.has_self) as usize; let type_params = param_counts.types - type_params_offset; + let type_params_without_defaults = { + let mut count = 0; + for param in generics.params.iter() { + if let ty::GenericParamDef::Type(ty) = param { + if !ty.has_default { + count += 1 + } + } + } + count + }; let type_params_barring_defaults = - generics.type_params_without_defaults() - type_params_offset; + type_params_without_defaults - type_params_offset; (type_params_barring_defaults, type_params, param_counts.lifetimes) }); diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index 9eb53f2fdaecf..75380c685daa3 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -662,7 +662,7 @@ fn reject_shadowing_parameters(tcx: TyCtxt, def_id: DefId) { .collect(); for method_param in generics.params.iter() { - // Shadowing is currently permitted with lifetimes. + // Shadowing is checked in resolve_lifetime. if let GenericParamDef::Lifetime(_) = method_param { continue; } diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 452b76e1b702f..b8c78c7b36a5e 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -973,15 +973,9 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, .chain(types) .collect(); - let param_def_id_to_index = - params.iter() - .map(|param| { - match param { - ty::GenericParamDef::Lifetime(lt) => (lt.def_id, lt.index), - ty::GenericParamDef::Type(ty) => (ty.def_id, ty.index), - } - }) - .collect(); + let param_def_id_to_index = params.iter() + .map(|param| (param.def_id(), param.index())) + .collect(); tcx.alloc_generics(ty::Generics { parent: parent_def_id, From fc27c2eb38164f89ad06c5e9645349fa3de38903 Mon Sep 17 00:00:00 2001 From: varkor Date: Wed, 18 Apr 2018 18:32:45 +0100 Subject: [PATCH 21/40] Fix typo in late-bound region testing message --- src/librustc/ty/maps/config.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/librustc/ty/maps/config.rs b/src/librustc/ty/maps/config.rs index 4e104692d859b..ad48519e136c8 100644 --- a/src/librustc/ty/maps/config.rs +++ b/src/librustc/ty/maps/config.rs @@ -543,7 +543,7 @@ impl<'tcx> QueryDescription<'tcx> for queries::named_region_map<'tcx> { impl<'tcx> QueryDescription<'tcx> for queries::is_late_bound_map<'tcx> { fn describe(_tcx: TyCtxt, _: DefIndex) -> String { - format!("testing if a region is late boudn") + format!("testing if a region is late bound") } } From 5e89312a22993c946f462aff0d0fa0447210762d Mon Sep 17 00:00:00 2001 From: varkor Date: Wed, 18 Apr 2018 17:54:05 +0100 Subject: [PATCH 22/40] Inline get_type --- src/librustc/middle/resolve_lifetime.rs | 7 +++++-- src/librustc/traits/error_reporting.rs | 9 +++++++-- src/librustc/traits/on_unimplemented.rs | 16 ++++++++-------- src/librustc/ty/mod.rs | 14 ++++++-------- src/librustc/ty/subst.rs | 8 ++------ src/librustc/util/ppaux.rs | 9 +++++++-- src/librustc_traits/dropck_outlives.rs | 8 ++++++-- src/librustc_typeck/check/compare_method.rs | 16 +++++++++++++--- src/librustdoc/clean/auto_trait.rs | 2 +- src/librustdoc/clean/mod.rs | 7 +++---- src/librustdoc/html/render.rs | 7 +++++-- 11 files changed, 63 insertions(+), 40 deletions(-) diff --git a/src/librustc/middle/resolve_lifetime.rs b/src/librustc/middle/resolve_lifetime.rs index f6d13c2a72f30..a45e2f983102d 100644 --- a/src/librustc/middle/resolve_lifetime.rs +++ b/src/librustc/middle/resolve_lifetime.rs @@ -20,7 +20,7 @@ use hir::def_id::{CrateNum, DefId, LocalDefId, LOCAL_CRATE}; use hir::map::Map; use hir::ItemLocalId; use hir::LifetimeName; -use ty::{self, TyCtxt}; +use ty::{self, TyCtxt, GenericParamDef}; use errors::DiagnosticBuilder; use rustc::lint; @@ -1662,7 +1662,10 @@ impl<'a, 'tcx> LifetimeContext<'a, 'tcx> { .params .iter() .filter_map(|param| { - param.get_type().and_then(|ty| Some(ty.object_lifetime_default)) + match *param { + GenericParamDef::Type(ty) => Some(ty.object_lifetime_default), + GenericParamDef::Lifetime(_) => None, + } }) .collect() }) diff --git a/src/librustc/traits/error_reporting.rs b/src/librustc/traits/error_reporting.rs index d0166393f0184..ccaecdafa015a 100644 --- a/src/librustc/traits/error_reporting.rs +++ b/src/librustc/traits/error_reporting.rs @@ -35,7 +35,7 @@ use infer::type_variable::TypeVariableOrigin; use std::fmt; use syntax::ast; use session::DiagnosticMessageId; -use ty::{self, AdtKind, ToPredicate, ToPolyTraitRef, Ty, TyCtxt, TypeFoldable}; +use ty::{self, AdtKind, ToPredicate, ToPolyTraitRef, Ty, TyCtxt, TypeFoldable, GenericParamDef}; use ty::error::ExpectedFound; use ty::fast_reject; use ty::fold::TypeFolder; @@ -378,7 +378,12 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { flags.push(("_Self".to_string(), Some(self.tcx.type_of(def.did).to_string()))); } - for param in generics.params.iter().filter_map(|param| param.get_type()) { + for param in generics.params.iter().filter_map(|param| { + match *param { + GenericParamDef::Type(ty) => Some(ty), + GenericParamDef::Lifetime(_) => None, + } + }) { let name = param.name.to_string(); let ty = trait_ref.substs.type_for_def(¶m); let ty_str = ty.to_string(); diff --git a/src/librustc/traits/on_unimplemented.rs b/src/librustc/traits/on_unimplemented.rs index 9fdbac49496cd..c84e03e35f4ef 100644 --- a/src/librustc/traits/on_unimplemented.rs +++ b/src/librustc/traits/on_unimplemented.rs @@ -254,10 +254,9 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { Position::ArgumentNamed(s) if s == name => (), // So is `{A}` if A is a type parameter Position::ArgumentNamed(s) => match generics.params.iter().find(|param| { - if let GenericParamDef::Type(ty) = param { - ty.name == s - } else { - false + match *param { + GenericParamDef::Type(ty) => ty.name == s, + GenericParamDef::Lifetime(_) => false, } }) { Some(_) => (), @@ -292,10 +291,11 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let trait_str = tcx.item_path_str(trait_ref.def_id); let generics = tcx.generics_of(trait_ref.def_id); let generic_map = generics.params.iter().filter_map(|param| { - if let Some(ty) = param.get_type() { - Some((ty.name.to_string(), trait_ref.substs.type_for_def(&ty).to_string())) - } else { - None + match *param { + GenericParamDef::Type(ty) => { + Some((ty.name.to_string(), trait_ref.substs.type_for_def(&ty).to_string())) + }, + GenericParamDef::Lifetime(_) => None } }).collect::>(); diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 635713a786650..37a6533fb61c2 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -777,13 +777,6 @@ impl GenericParamDef { GenericParamDef::Type(ty) => ty.def_id, } } - - pub fn get_type(&self) -> Option { - match *self { - GenericParamDef::Type(ty) => Some(ty), - _ => None, - } - } } pub struct GenericParamCount { @@ -834,7 +827,12 @@ impl<'a, 'gcx, 'tcx> Generics { } pub fn requires_monomorphization(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { - if self.params.iter().any(|p| p.get_type().is_some()) { + if self.params.iter().any(|param| { + match *param { + GenericParamDef::Type(_) => true, + GenericParamDef::Lifetime(_) => false + } + }) { return true; } if let Some(parent_def_id) = self.parent { diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index 0808cc84bf7aa..4f69776721ee4 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -243,12 +243,8 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { FT: FnMut(&ty::TypeParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { for def in &defs.params { let param = match def { - ty::GenericParamDef::Lifetime(ref lt) => { - mk_region(lt, substs).into() - } - ty::GenericParamDef::Type(ref ty) => { - mk_type(ty, substs).into() - } + ty::GenericParamDef::Lifetime(ref lt) => mk_region(lt, substs).into(), + ty::GenericParamDef::Type(ref ty) => mk_type(ty, substs).into(), }; assert_eq!(def.index() as usize, substs.len()); substs.push(param); diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index ba8694602526c..603e6e0324652 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -19,7 +19,7 @@ use ty::{TyError, TyStr, TyArray, TySlice, TyFloat, TyFnDef, TyFnPtr}; use ty::{TyParam, TyRawPtr, TyRef, TyNever, TyTuple}; use ty::{TyClosure, TyGenerator, TyGeneratorWitness, TyForeign, TyProjection, TyAnon}; use ty::{TyDynamic, TyInt, TyUint, TyInfer}; -use ty::{self, Ty, TyCtxt, TypeFoldable, GenericParamCount}; +use ty::{self, Ty, TyCtxt, TypeFoldable, GenericParamCount, GenericParamDef}; use util::nodemap::FxHashSet; use std::cell::Cell; @@ -337,7 +337,12 @@ impl PrintContext { if !verbose { let mut type_params = - generics.params.iter().rev().filter_map(|param| param.get_type()); + generics.params.iter().rev().filter_map(|param| { + match *param { + GenericParamDef::Type(ty) => Some(ty), + GenericParamDef::Lifetime(_) => None, + } + }); if let Some(last_ty) = type_params.next() { if last_ty.has_default { if let Some(substs) = tcx.lift(&substs) { diff --git a/src/librustc_traits/dropck_outlives.rs b/src/librustc_traits/dropck_outlives.rs index f333968829286..da38081a60298 100644 --- a/src/librustc_traits/dropck_outlives.rs +++ b/src/librustc_traits/dropck_outlives.rs @@ -13,7 +13,7 @@ use rustc::hir::def_id::DefId; use rustc::traits::{FulfillmentContext, Normalized, ObligationCause}; use rustc::traits::query::{CanonicalTyGoal, NoSolution}; use rustc::traits::query::dropck_outlives::{DtorckConstraint, DropckOutlivesResult}; -use rustc::ty::{self, ParamEnvAnd, Ty, TyCtxt}; +use rustc::ty::{self, ParamEnvAnd, Ty, TyCtxt, GenericParamDef}; use rustc::ty::subst::Subst; use rustc::util::nodemap::FxHashSet; use rustc_data_structures::sync::Lrc; @@ -278,9 +278,13 @@ crate fn adt_dtorck_constraint<'a, 'tcx>( debug!("dtorck_constraint: {:?}", def); if def.is_phantom_data() { + let type_param = match tcx.generics_of(def_id).params[0] { + GenericParamDef::Type(ty) => ty, + GenericParamDef::Lifetime(_) => unreachable!(), + }; let result = DtorckConstraint { outlives: vec![], - dtorck_types: vec![tcx.mk_param_from_def(&tcx.generics_of(def_id).params[0].get_type().unwrap())], + dtorck_types: vec![tcx.mk_param_from_def(&type_param)], overflows: vec![], }; debug!("dtorck_constraint: {:?} => {:?}", def, result); diff --git a/src/librustc_typeck/check/compare_method.rs b/src/librustc_typeck/check/compare_method.rs index c2c250249ad8e..d1978ceb30bf3 100644 --- a/src/librustc_typeck/check/compare_method.rs +++ b/src/librustc_typeck/check/compare_method.rs @@ -10,7 +10,7 @@ use rustc::hir::{self, ImplItemKind, TraitItemKind}; use rustc::infer::{self, InferOk}; -use rustc::ty::{self, TyCtxt}; +use rustc::ty::{self, TyCtxt, GenericParamDef}; use rustc::ty::util::ExplicitSelf; use rustc::traits::{self, ObligationCause, ObligationCauseCode, Reveal}; use rustc::ty::error::{ExpectedFound, TypeError}; @@ -728,8 +728,18 @@ fn compare_synthetic_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let mut error_found = false; let impl_m_generics = tcx.generics_of(impl_m.def_id); let trait_m_generics = tcx.generics_of(trait_m.def_id); - let impl_m_type_params = impl_m_generics.params.iter().filter_map(|param| param.get_type()); - let trait_m_type_params = trait_m_generics.params.iter().filter_map(|param| param.get_type()); + let impl_m_type_params = impl_m_generics.params.iter().filter_map(|param| { + match *param { + GenericParamDef::Type(ty) => Some(ty), + GenericParamDef::Lifetime(_) => None, + } + }); + let trait_m_type_params = trait_m_generics.params.iter().filter_map(|param| { + match *param { + GenericParamDef::Type(ty) => Some(ty), + GenericParamDef::Lifetime(_) => None, + } + }); for (impl_ty, trait_ty) in impl_m_type_params.zip(trait_m_type_params) { if impl_ty.synthetic != trait_ty.synthetic { let impl_node_id = tcx.hir.as_local_node_id(impl_ty.def_id).unwrap(); diff --git a/src/librustdoc/clean/auto_trait.rs b/src/librustdoc/clean/auto_trait.rs index b1981c0650441..dc49cfcbc2b13 100644 --- a/src/librustdoc/clean/auto_trait.rs +++ b/src/librustdoc/clean/auto_trait.rs @@ -860,7 +860,7 @@ impl<'a, 'tcx, 'rcx> AutoTraitFinder<'a, 'tcx, 'rcx> { ty.bounds.insert(0, TyParamBound::maybe_sized(self.cx)); } } - _ => {} + GenericParamDef::Lifetime(_) => {} } } diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 5146a29d4e371..cb48d790f6070 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1725,10 +1725,9 @@ pub enum GenericParamDef { impl GenericParamDef { pub fn is_synthetic_type_param(&self) -> bool { - if let GenericParamDef::Type(ref t) = *self { - t.synthetic.is_some() - } else { - false + match self { + GenericParamDef::Type(ty) => ty.synthetic.is_some(), + GenericParamDef::Lifetime(_) => false, } } } diff --git a/src/librustdoc/html/render.rs b/src/librustdoc/html/render.rs index 5be9000d2a5ce..21851e7b9dcb1 100644 --- a/src/librustdoc/html/render.rs +++ b/src/librustdoc/html/render.rs @@ -1437,8 +1437,11 @@ impl DocFolder for Cache { impl<'a> Cache { fn generics(&mut self, generics: &clean::Generics) { for param in &generics.params { - if let clean::GenericParamDef::Type(ref typ) = *param { - self.typarams.insert(typ.did, typ.name.clone()); + match *param { + clean::GenericParamDef::Type(ref typ) => { + self.typarams.insert(typ.did, typ.name.clone()); + } + clean::GenericParamDef::Lifetime(_) => {} } } } From 4bed895cab365a9a020fcc033b83603e7d23e4e4 Mon Sep 17 00:00:00 2001 From: varkor Date: Thu, 19 Apr 2018 00:40:22 +0100 Subject: [PATCH 23/40] Pull common parameters into GenericParamDef This leads to a lot of simplifications, as most code doesn't actually need to know about the specific lifetime/type data; rather, it's concerned with properties like name, index and def_id. --- src/librustc/ich/impls_ty.rs | 31 ++---- src/librustc/infer/anon_types/mod.rs | 12 +- src/librustc/infer/mod.rs | 4 +- src/librustc/middle/resolve_lifetime.rs | 10 +- src/librustc/traits/error_reporting.rs | 11 +- src/librustc/traits/on_unimplemented.rs | 17 +-- src/librustc/traits/util.rs | 2 +- src/librustc/ty/context.rs | 8 +- src/librustc/ty/mod.rs | 104 ++++++++++-------- src/librustc/ty/sty.rs | 4 +- src/librustc/ty/subst.rs | 34 +++--- src/librustc/ty/util.rs | 4 +- src/librustc/util/ppaux.rs | 41 ++++--- src/librustc_driver/test.rs | 2 +- src/librustc_privacy/lib.rs | 22 ++-- src/librustc_traits/dropck_outlives.rs | 10 +- src/librustc_trans/debuginfo/mod.rs | 8 +- src/librustc_typeck/astconv.rs | 20 ++-- src/librustc_typeck/check/compare_method.rs | 16 +-- src/librustc_typeck/check/intrinsic.rs | 4 +- src/librustc_typeck/check/mod.rs | 10 +- src/librustc_typeck/check/wfcheck.rs | 29 +++-- src/librustc_typeck/collect.rs | 74 +++++++------ src/librustc_typeck/impl_wf_check.rs | 14 +-- .../outlives/implicit_infer.rs | 2 +- src/librustdoc/clean/auto_trait.rs | 14 +-- src/librustdoc/clean/mod.rs | 22 ++-- 27 files changed, 263 insertions(+), 266 deletions(-) diff --git a/src/librustc/ich/impls_ty.rs b/src/librustc/ich/impls_ty.rs index fc0a9ac9d18f3..eddb73e72399c 100644 --- a/src/librustc/ich/impls_ty.rs +++ b/src/librustc/ich/impls_ty.rs @@ -753,34 +753,23 @@ impl<'a> HashStable> for ty::Generics { } } -impl_stable_hash_for!(enum ty::GenericParamDef { +impl_stable_hash_for!(enum ty::GenericParamDefKind { Lifetime(lt), Type(ty) }); -impl<'a> HashStable> -for ty::RegionParamDef { - fn hash_stable(&self, - hcx: &mut StableHashingContext<'a>, - hasher: &mut StableHasher) { - let ty::RegionParamDef { - name, - def_id, - index, - pure_wrt_drop - } = *self; - - name.hash_stable(hcx, hasher); - def_id.hash_stable(hcx, hasher); - index.hash_stable(hcx, hasher); - pure_wrt_drop.hash_stable(hcx, hasher); - } -} - -impl_stable_hash_for!(struct ty::TypeParamDef { +impl_stable_hash_for!(struct ty::GenericParamDef { name, def_id, index, + kind +}); + +impl_stable_hash_for!(struct ty::RegionParamDef { + pure_wrt_drop +}); + +impl_stable_hash_for!(struct ty::TypeParamDef { has_default, object_lifetime_default, pure_wrt_drop, diff --git a/src/librustc/infer/anon_types/mod.rs b/src/librustc/infer/anon_types/mod.rs index a83eb7fd354a3..0af95a74686bf 100644 --- a/src/librustc/infer/anon_types/mod.rs +++ b/src/librustc/infer/anon_types/mod.rs @@ -14,7 +14,7 @@ use infer::outlives::free_region_map::FreeRegionRelations; use rustc_data_structures::fx::FxHashMap; use syntax::ast; use traits::{self, PredicateObligation}; -use ty::{self, Ty, TyCtxt, GenericParamDef}; +use ty::{self, Ty, TyCtxt, GenericParamDefKind}; use ty::fold::{BottomUpFolder, TypeFoldable, TypeFolder}; use ty::outlives::Component; use ty::subst::{Kind, Substs, UnpackedKind}; @@ -313,16 +313,14 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { // `['a]` for the first impl trait and `'b` for the // second. let mut least_region = None; - for region_def in abstract_type_generics.params.iter().filter_map(|param| { - if let GenericParamDef::Lifetime(lt) = param { - Some(lt) + for index in abstract_type_generics.params.iter().filter_map(|param| { + if let GenericParamDefKind::Lifetime(_) = param.kind { + // Find the index of this region in the list of substitutions. + Some(param.index as usize) } else { None } }) { - // Find the index of this region in the list of substitutions. - let index = region_def.index as usize; - // Get the value supplied for this region from the substs. let subst_arg = anon_defn.substs.region_at(index); diff --git a/src/librustc/infer/mod.rs b/src/librustc/infer/mod.rs index a594231441a9b..8dd661d04032a 100644 --- a/src/librustc/infer/mod.rs +++ b/src/librustc/infer/mod.rs @@ -909,7 +909,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { /// region parameter definition. pub fn region_var_for_def(&self, span: Span, - def: &ty::RegionParamDef) + def: &ty::GenericParamDef) -> ty::Region<'tcx> { self.next_region_var(EarlyBoundRegion(span, def.name)) } @@ -924,7 +924,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { /// as the substitutions for the default, `(T, U)`. pub fn type_var_for_def(&self, span: Span, - def: &ty::TypeParamDef) + def: &ty::GenericParamDef) -> Ty<'tcx> { let ty_var_id = self.type_variables .borrow_mut() diff --git a/src/librustc/middle/resolve_lifetime.rs b/src/librustc/middle/resolve_lifetime.rs index a45e2f983102d..bed5ee91800a6 100644 --- a/src/librustc/middle/resolve_lifetime.rs +++ b/src/librustc/middle/resolve_lifetime.rs @@ -20,7 +20,7 @@ use hir::def_id::{CrateNum, DefId, LocalDefId, LOCAL_CRATE}; use hir::map::Map; use hir::ItemLocalId; use hir::LifetimeName; -use ty::{self, TyCtxt, GenericParamDef}; +use ty::{self, TyCtxt, GenericParamDefKind}; use errors::DiagnosticBuilder; use rustc::lint; @@ -1662,9 +1662,11 @@ impl<'a, 'tcx> LifetimeContext<'a, 'tcx> { .params .iter() .filter_map(|param| { - match *param { - GenericParamDef::Type(ty) => Some(ty.object_lifetime_default), - GenericParamDef::Lifetime(_) => None, + match param.kind { + GenericParamDefKind::Type(ty) => { + Some(ty.object_lifetime_default) + } + GenericParamDefKind::Lifetime(_) => None, } }) .collect() diff --git a/src/librustc/traits/error_reporting.rs b/src/librustc/traits/error_reporting.rs index ccaecdafa015a..2f0691d241e32 100644 --- a/src/librustc/traits/error_reporting.rs +++ b/src/librustc/traits/error_reporting.rs @@ -35,7 +35,8 @@ use infer::type_variable::TypeVariableOrigin; use std::fmt; use syntax::ast; use session::DiagnosticMessageId; -use ty::{self, AdtKind, ToPredicate, ToPolyTraitRef, Ty, TyCtxt, TypeFoldable, GenericParamDef}; +use ty::{self, AdtKind, ToPredicate, ToPolyTraitRef, Ty, TyCtxt, TypeFoldable}; +use ty::GenericParamDefKind; use ty::error::ExpectedFound; use ty::fast_reject; use ty::fold::TypeFolder; @@ -378,10 +379,10 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { flags.push(("_Self".to_string(), Some(self.tcx.type_of(def.did).to_string()))); } - for param in generics.params.iter().filter_map(|param| { - match *param { - GenericParamDef::Type(ty) => Some(ty), - GenericParamDef::Lifetime(_) => None, + for param in generics.params.iter().filter(|param| { + match param.kind { + GenericParamDefKind::Type(_) => true, + GenericParamDefKind::Lifetime(_) => false, } }) { let name = param.name.to_string(); diff --git a/src/librustc/traits/on_unimplemented.rs b/src/librustc/traits/on_unimplemented.rs index c84e03e35f4ef..e15542cb2c09d 100644 --- a/src/librustc/traits/on_unimplemented.rs +++ b/src/librustc/traits/on_unimplemented.rs @@ -11,7 +11,7 @@ use fmt_macros::{Parser, Piece, Position}; use hir::def_id::DefId; -use ty::{self, TyCtxt, GenericParamDef}; +use ty::{self, TyCtxt, GenericParamDefKind}; use util::common::ErrorReported; use util::nodemap::FxHashMap; @@ -254,9 +254,9 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { Position::ArgumentNamed(s) if s == name => (), // So is `{A}` if A is a type parameter Position::ArgumentNamed(s) => match generics.params.iter().find(|param| { - match *param { - GenericParamDef::Type(ty) => ty.name == s, - GenericParamDef::Lifetime(_) => false, + match param.kind { + GenericParamDefKind::Type(_) => param.name == s, + GenericParamDefKind::Lifetime(_) => false, } }) { Some(_) => (), @@ -291,11 +291,12 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let trait_str = tcx.item_path_str(trait_ref.def_id); let generics = tcx.generics_of(trait_ref.def_id); let generic_map = generics.params.iter().filter_map(|param| { - match *param { - GenericParamDef::Type(ty) => { - Some((ty.name.to_string(), trait_ref.substs.type_for_def(&ty).to_string())) + match param.kind { + GenericParamDefKind::Type(_) => { + Some((param.name.to_string(), + trait_ref.substs.type_for_def(¶m).to_string())) }, - GenericParamDef::Lifetime(_) => None + GenericParamDefKind::Lifetime(_) => None } }).collect::>(); diff --git a/src/librustc/traits/util.rs b/src/librustc/traits/util.rs index 3c62f04afc56e..f5a9d2a7f0014 100644 --- a/src/librustc/traits/util.rs +++ b/src/librustc/traits/util.rs @@ -213,7 +213,7 @@ impl<'cx, 'gcx, 'tcx> Elaborator<'cx, 'gcx, 'tcx> { }, Component::Param(p) => { - let ty = tcx.mk_param(p.idx, p.name); + let ty = tcx.mk_ty_param(p.idx, p.name); Some(ty::Predicate::TypeOutlives( ty::Binder::dummy(ty::OutlivesPredicate(ty, r_min)))) }, diff --git a/src/librustc/ty/context.rs b/src/librustc/ty/context.rs index 7391d1872520d..6eb85cfb307fa 100644 --- a/src/librustc/ty/context.rs +++ b/src/librustc/ty/context.rs @@ -2457,18 +2457,18 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { self.mk_ty(TyInfer(it)) } - pub fn mk_param(self, + pub fn mk_ty_param(self, index: u32, name: InternedString) -> Ty<'tcx> { self.mk_ty(TyParam(ParamTy { idx: index, name: name })) } pub fn mk_self_type(self) -> Ty<'tcx> { - self.mk_param(0, keywords::SelfType.name().as_interned_str()) + self.mk_ty_param(0, keywords::SelfType.name().as_interned_str()) } - pub fn mk_param_from_def(self, def: &ty::TypeParamDef) -> Ty<'tcx> { - self.mk_param(def.index, def.name) + pub fn mk_ty_param_from_def(self, def: &ty::GenericParamDef) -> Ty<'tcx> { + self.mk_ty_param(def.index, def.name) } pub fn mk_anon(self, def_id: DefId, substs: &'tcx Substs<'tcx>) -> Ty<'tcx> { diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 37a6533fb61c2..3c4c326578a5d 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -709,11 +709,8 @@ pub enum IntVarValue { #[derive(Clone, Copy, PartialEq, Eq)] pub struct FloatVarValue(pub ast::FloatTy); -#[derive(Copy, Clone, RustcEncodable, RustcDecodable)] +#[derive(Copy, Clone, Debug, RustcEncodable, RustcDecodable)] pub struct TypeParamDef { - pub name: InternedString, - pub def_id: DefId, - pub index: u32, pub has_default: bool, pub object_lifetime_default: ObjectLifetimeDefault, @@ -725,32 +722,14 @@ pub struct TypeParamDef { pub synthetic: Option, } -#[derive(Copy, Clone, RustcEncodable, RustcDecodable)] +#[derive(Copy, Clone, Debug, RustcEncodable, RustcDecodable)] pub struct RegionParamDef { - pub name: InternedString, - pub def_id: DefId, - pub index: u32, - /// `pure_wrt_drop`, set by the (unsafe) `#[may_dangle]` attribute /// on generic parameter `'a`, asserts data of lifetime `'a` /// won't be accessed during the parent type's `Drop` impl. pub pure_wrt_drop: bool, } -impl RegionParamDef { - pub fn to_early_bound_region_data(&self) -> ty::EarlyBoundRegion { - ty::EarlyBoundRegion { - def_id: self.def_id, - index: self.index, - name: self.name, - } - } - - pub fn to_bound_region(&self) -> ty::BoundRegion { - self.to_early_bound_region_data().to_bound_region() - } -} - impl ty::EarlyBoundRegion { pub fn to_bound_region(&self) -> ty::BoundRegion { ty::BoundRegion::BrNamed(self.def_id, self.name) @@ -758,23 +737,53 @@ impl ty::EarlyBoundRegion { } #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] -pub enum GenericParamDef { +pub enum GenericParamDefKind { Lifetime(RegionParamDef), Type(TypeParamDef), } +#[derive(Clone, RustcEncodable, RustcDecodable)] +pub struct GenericParamDef { + pub name: InternedString, + pub def_id: DefId, + pub index: u32, + pub kind: GenericParamDefKind, +} + impl GenericParamDef { - pub fn index(&self) -> u32 { - match self { - GenericParamDef::Lifetime(lt) => lt.index, - GenericParamDef::Type(ty) => ty.index, + pub fn to_lifetime(&self) -> RegionParamDef { + match self.kind { + GenericParamDefKind::Lifetime(lt) => lt, + _ => bug!("cannot convert a non-lifetime to a lifetime") } } - pub fn def_id(&self) -> DefId { - match self { - GenericParamDef::Lifetime(lt) => lt.def_id, - GenericParamDef::Type(ty) => ty.def_id, + pub fn to_type(&self) -> TypeParamDef { + match self.kind { + GenericParamDefKind::Type(ty) => ty, + _ => bug!("cannot convert a non-type to a type") + } + } + + pub fn to_early_bound_region_data(&self) -> ty::EarlyBoundRegion { + match self.kind { + GenericParamDefKind::Lifetime(_) => { + ty::EarlyBoundRegion { + def_id: self.def_id, + index: self.index, + name: self.name, + } + } + _ => bug!("cannot convert a non-lifetime parameter def to an early bound region") + } + } + + pub fn to_bound_region(&self) -> ty::BoundRegion { + match self.kind { + GenericParamDefKind::Lifetime(_) => { + self.to_early_bound_region_data().to_bound_region() + } + _ => bug!("cannot convert a non-lifetime parameter def to an early bound region") } } } @@ -817,9 +826,9 @@ impl<'a, 'gcx, 'tcx> Generics { }; for param in self.params.iter() { - match param { - GenericParamDef::Lifetime(_) => param_counts.lifetimes += 1, - GenericParamDef::Type(_) => param_counts.types += 1, + match param.kind { + GenericParamDefKind::Lifetime(_) => param_counts.lifetimes += 1, + GenericParamDefKind::Type(_) => param_counts.types += 1, }; } @@ -828,9 +837,9 @@ impl<'a, 'gcx, 'tcx> Generics { pub fn requires_monomorphization(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { if self.params.iter().any(|param| { - match *param { - GenericParamDef::Type(_) => true, - GenericParamDef::Lifetime(_) => false + match param.kind { + GenericParamDefKind::Type(_) => true, + GenericParamDefKind::Lifetime(_) => false } }) { return true; @@ -846,11 +855,12 @@ impl<'a, 'gcx, 'tcx> Generics { pub fn region_param(&'tcx self, param: &EarlyBoundRegion, tcx: TyCtxt<'a, 'gcx, 'tcx>) - -> &'tcx RegionParamDef + -> &'tcx GenericParamDef { if let Some(index) = param.index.checked_sub(self.parent_count as u32) { - match self.params[index as usize] { - ty::GenericParamDef::Lifetime(ref lt) => lt, + let ref param = self.params[index as usize]; + match param.kind { + ty::GenericParamDefKind::Lifetime(_) => param, _ => bug!("expected region parameter, but found another generic parameter") } } else { @@ -863,7 +873,7 @@ impl<'a, 'gcx, 'tcx> Generics { pub fn type_param(&'tcx self, param: &ParamTy, tcx: TyCtxt<'a, 'gcx, 'tcx>) - -> &TypeParamDef { + -> &'tcx GenericParamDef { if let Some(index) = param.idx.checked_sub(self.parent_count as u32) { // non-Self type parameters are always offset by exactly // `self.regions.len()`. In the absence of a Self, this is obvious, @@ -899,14 +909,16 @@ impl<'a, 'gcx, 'tcx> Generics { if let Some(_) = (index as usize).checked_sub(type_param_offset) { assert!(!is_separated_self, "found a Self after type_param_offset"); - match self.params[index as usize] { - ty::GenericParamDef::Type(ref ty) => ty, + let ref param = self.params[index as usize]; + match param.kind { + ty::GenericParamDefKind::Type(_) => param, _ => bug!("expected type parameter, but found another generic parameter") } } else { assert!(is_separated_self, "non-Self param before type_param_offset"); - match self.params[type_param_offset] { - ty::GenericParamDef::Type(ref ty) => ty, + let ref param = self.params[type_param_offset]; + match param.kind { + ty::GenericParamDefKind::Type(_) => param, _ => bug!("expected type parameter, but found another generic parameter") } } diff --git a/src/librustc/ty/sty.rs b/src/librustc/ty/sty.rs index 01ebf3666f9c2..792a6bfaedfd4 100644 --- a/src/librustc/ty/sty.rs +++ b/src/librustc/ty/sty.rs @@ -928,12 +928,12 @@ impl<'a, 'gcx, 'tcx> ParamTy { ParamTy::new(0, keywords::SelfType.name().as_interned_str()) } - pub fn for_def(def: &ty::TypeParamDef) -> ParamTy { + pub fn for_def(def: &ty::GenericParamDef) -> ParamTy { ParamTy::new(def.index, def.name) } pub fn to_ty(self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> Ty<'tcx> { - tcx.mk_param(self.idx, self.name) + tcx.mk_ty_param(self.idx, self.name) } pub fn is_self(&self) -> bool { diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index 4f69776721ee4..a14045b43f2eb 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -183,7 +183,7 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { -> &'tcx Substs<'tcx> { Substs::for_item(tcx, def_id, |def, _| { tcx.mk_region(ty::ReEarlyBound(def.to_early_bound_region_data())) - }, |def, _| tcx.mk_param_from_def(def)) + }, |def, _| tcx.mk_ty_param_from_def(def)) } /// Creates a Substs for generic parameter definitions, @@ -196,8 +196,8 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { mut mk_region: FR, mut mk_type: FT) -> &'tcx Substs<'tcx> - where FR: FnMut(&ty::RegionParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, - FT: FnMut(&ty::TypeParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { + where FR: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, + FT: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { let defs = tcx.generics_of(def_id); let mut substs = Vec::with_capacity(defs.count()); Substs::fill_item(&mut substs, tcx, defs, &mut mk_region, &mut mk_type); @@ -210,8 +210,8 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { mut mk_region: FR, mut mk_type: FT) -> &'tcx Substs<'tcx> - where FR: FnMut(&ty::RegionParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, - FT: FnMut(&ty::TypeParamDef, &[Kind<'tcx>]) -> Ty<'tcx> + where FR: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, + FT: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { let defs = tcx.generics_of(def_id); let mut result = Vec::with_capacity(defs.count()); @@ -225,8 +225,8 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { defs: &ty::Generics, mk_region: &mut FR, mk_type: &mut FT) - where FR: FnMut(&ty::RegionParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, - FT: FnMut(&ty::TypeParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { + where FR: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, + FT: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { if let Some(def_id) = defs.parent { let parent_defs = tcx.generics_of(def_id); @@ -239,15 +239,15 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { defs: &ty::Generics, mk_region: &mut FR, mk_type: &mut FT) - where FR: FnMut(&ty::RegionParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, - FT: FnMut(&ty::TypeParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { - for def in &defs.params { - let param = match def { - ty::GenericParamDef::Lifetime(ref lt) => mk_region(lt, substs).into(), - ty::GenericParamDef::Type(ref ty) => mk_type(ty, substs).into(), + where FR: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, + FT: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { + for param in &defs.params { + let kind = match param.kind { + ty::GenericParamDefKind::Lifetime(_) => mk_region(param, substs).into(), + ty::GenericParamDefKind::Type(_) => mk_type(param, substs).into(), }; - assert_eq!(def.index() as usize, substs.len()); - substs.push(param); + assert_eq!(param.index as usize, substs.len()); + substs.push(kind); } } @@ -296,12 +296,12 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { } #[inline] - pub fn type_for_def(&self, ty_param_def: &ty::TypeParamDef) -> Ty<'tcx> { + pub fn type_for_def(&self, ty_param_def: &ty::GenericParamDef) -> Ty<'tcx> { self.type_at(ty_param_def.index as usize) } #[inline] - pub fn region_for_def(&self, def: &ty::RegionParamDef) -> ty::Region<'tcx> { + pub fn region_for_def(&self, def: &ty::GenericParamDef) -> ty::Region<'tcx> { self.region_at(def.index as usize) } diff --git a/src/librustc/ty/util.rs b/src/librustc/ty/util.rs index fdd0754730feb..db11f4659723b 100644 --- a/src/librustc/ty/util.rs +++ b/src/librustc/ty/util.rs @@ -505,12 +505,12 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { .filter(|&(_, &k)| { match k.unpack() { UnpackedKind::Lifetime(&ty::RegionKind::ReEarlyBound(ref ebr)) => { - !impl_generics.region_param(ebr, self).pure_wrt_drop + !impl_generics.region_param(ebr, self).to_lifetime().pure_wrt_drop } UnpackedKind::Type(&ty::TyS { sty: ty::TypeVariants::TyParam(ref pt), .. }) => { - !impl_generics.type_param(pt, self).pure_wrt_drop + !impl_generics.type_param(pt, self).to_type().pure_wrt_drop } UnpackedKind::Lifetime(_) | UnpackedKind::Type(_) => { // not a type or region param - this should be reported diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index 603e6e0324652..47315c7243f02 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -19,7 +19,7 @@ use ty::{TyError, TyStr, TyArray, TySlice, TyFloat, TyFnDef, TyFnPtr}; use ty::{TyParam, TyRawPtr, TyRef, TyNever, TyTuple}; use ty::{TyClosure, TyGenerator, TyGeneratorWitness, TyForeign, TyProjection, TyAnon}; use ty::{TyDynamic, TyInt, TyUint, TyInfer}; -use ty::{self, Ty, TyCtxt, TypeFoldable, GenericParamCount, GenericParamDef}; +use ty::{self, Ty, TyCtxt, TypeFoldable, GenericParamCount, GenericParamDefKind}; use util::nodemap::FxHashSet; use std::cell::Cell; @@ -338,20 +338,21 @@ impl PrintContext { if !verbose { let mut type_params = generics.params.iter().rev().filter_map(|param| { - match *param { - GenericParamDef::Type(ty) => Some(ty), - GenericParamDef::Lifetime(_) => None, + match param.kind { + GenericParamDefKind::Type(ty) => Some((param.def_id, ty.has_default)), + GenericParamDefKind::Lifetime(_) => None, } }); if let Some(last_ty) = type_params.next() { - if last_ty.has_default { + let (_, has_default) = last_ty; + if has_default { if let Some(substs) = tcx.lift(&substs) { - let mut tps = substs.types().rev().skip(child_types); - let zipped = iter::once((last_ty, tps.next().unwrap())) - .chain(type_params.zip(tps)); - for (ty, actual) in zipped { - if !ty.has_default || - tcx.type_of(ty.def_id).subst(tcx, substs) != actual { + let mut types = substs.types().rev().skip(child_types); + let zipped = iter::once((last_ty, types.next().unwrap())) + .chain(type_params.zip(types)); + for ((def_id, has_default), actual) in zipped { + if !has_default || + tcx.type_of(def_id).subst(tcx, substs) != actual { break; } num_supplied_defaults += 1; @@ -600,18 +601,14 @@ define_print! { } } -impl fmt::Debug for ty::TypeParamDef { +impl fmt::Debug for ty::GenericParamDef { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - write!(f, "TypeParamDef({}, {:?}, {})", - self.name, - self.def_id, - self.index) - } -} - -impl fmt::Debug for ty::RegionParamDef { - fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - write!(f, "RegionParamDef({}, {:?}, {})", + let type_name = match self.kind { + ty::GenericParamDefKind::Lifetime(_) => "Region", + ty::GenericParamDefKind::Type(_) => "Type", + }; + write!(f, "{}({}, {:?}, {})", + type_name, self.name, self.def_id, self.index) diff --git a/src/librustc_driver/test.rs b/src/librustc_driver/test.rs index 7ae26e9e9798e..78c95a5ce0504 100644 --- a/src/librustc_driver/test.rs +++ b/src/librustc_driver/test.rs @@ -308,7 +308,7 @@ impl<'a, 'gcx, 'tcx> Env<'a, 'gcx, 'tcx> { pub fn t_param(&self, index: u32) -> Ty<'tcx> { let name = format!("T{}", index); - self.infcx.tcx.mk_param(index, Symbol::intern(&name).as_interned_str()) + self.infcx.tcx.mk_ty_param(index, Symbol::intern(&name).as_interned_str()) } pub fn re_early_bound(&self, index: u32, name: &'static str) -> ty::Region<'tcx> { diff --git a/src/librustc_privacy/lib.rs b/src/librustc_privacy/lib.rs index 56ffadc882a45..1b2ec481a1ccc 100644 --- a/src/librustc_privacy/lib.rs +++ b/src/librustc_privacy/lib.rs @@ -27,7 +27,7 @@ use rustc::hir::intravisit::{self, Visitor, NestedVisitorMap}; use rustc::hir::itemlikevisit::DeepVisitor; use rustc::lint; use rustc::middle::privacy::{AccessLevel, AccessLevels}; -use rustc::ty::{self, TyCtxt, Ty, TypeFoldable, GenericParamDef}; +use rustc::ty::{self, TyCtxt, Ty, TypeFoldable, GenericParamDefKind}; use rustc::ty::fold::TypeVisitor; use rustc::ty::maps::Providers; use rustc::ty::subst::UnpackedKind; @@ -399,14 +399,14 @@ impl<'a, 'tcx> Visitor<'tcx> for EmbargoVisitor<'a, 'tcx> { impl<'b, 'a, 'tcx> ReachEverythingInTheInterfaceVisitor<'b, 'a, 'tcx> { fn generics(&mut self) -> &mut Self { - for def in self.ev.tcx.generics_of(self.item_def_id).params.iter() { - match def { - GenericParamDef::Type(ty) => { + for param in self.ev.tcx.generics_of(self.item_def_id).params.iter() { + match param.kind { + GenericParamDefKind::Type(ty) => { if ty.has_default { - self.ev.tcx.type_of(ty.def_id).visit_with(self); + self.ev.tcx.type_of(param.def_id).visit_with(self); } } - GenericParamDef::Lifetime(_) => {} + GenericParamDefKind::Lifetime(_) => {} } } self @@ -1340,14 +1340,14 @@ struct SearchInterfaceForPrivateItemsVisitor<'a, 'tcx: 'a> { impl<'a, 'tcx: 'a> SearchInterfaceForPrivateItemsVisitor<'a, 'tcx> { fn generics(&mut self) -> &mut Self { - for def in self.tcx.generics_of(self.item_def_id).params.iter() { - match def { - GenericParamDef::Type(ty) => { + for param in self.tcx.generics_of(self.item_def_id).params.iter() { + match param.kind { + GenericParamDefKind::Type(ty) => { if ty.has_default { - self.tcx.type_of(ty.def_id).visit_with(self); + self.tcx.type_of(param.def_id).visit_with(self); } } - GenericParamDef::Lifetime(_) => {} + GenericParamDefKind::Lifetime(_) => {} } } self diff --git a/src/librustc_traits/dropck_outlives.rs b/src/librustc_traits/dropck_outlives.rs index da38081a60298..6c2128de27217 100644 --- a/src/librustc_traits/dropck_outlives.rs +++ b/src/librustc_traits/dropck_outlives.rs @@ -13,7 +13,7 @@ use rustc::hir::def_id::DefId; use rustc::traits::{FulfillmentContext, Normalized, ObligationCause}; use rustc::traits::query::{CanonicalTyGoal, NoSolution}; use rustc::traits::query::dropck_outlives::{DtorckConstraint, DropckOutlivesResult}; -use rustc::ty::{self, ParamEnvAnd, Ty, TyCtxt, GenericParamDef}; +use rustc::ty::{self, ParamEnvAnd, Ty, TyCtxt}; use rustc::ty::subst::Subst; use rustc::util::nodemap::FxHashSet; use rustc_data_structures::sync::Lrc; @@ -278,13 +278,11 @@ crate fn adt_dtorck_constraint<'a, 'tcx>( debug!("dtorck_constraint: {:?}", def); if def.is_phantom_data() { - let type_param = match tcx.generics_of(def_id).params[0] { - GenericParamDef::Type(ty) => ty, - GenericParamDef::Lifetime(_) => unreachable!(), - }; + // The first generic parameter here is guaranteed to be a type because it's `PhantomData`. + let param = &tcx.generics_of(def_id).params[0]; let result = DtorckConstraint { outlives: vec![], - dtorck_types: vec![tcx.mk_param_from_def(&type_param)], + dtorck_types: vec![tcx.mk_ty_param_from_def(param)], overflows: vec![], }; debug!("dtorck_constraint: {:?} => {:?}", def, result); diff --git a/src/librustc_trans/debuginfo/mod.rs b/src/librustc_trans/debuginfo/mod.rs index 31ef1eddfcbf5..2039a90a043bf 100644 --- a/src/librustc_trans/debuginfo/mod.rs +++ b/src/librustc_trans/debuginfo/mod.rs @@ -26,7 +26,6 @@ use llvm::debuginfo::{DIFile, DIType, DIScope, DIBuilderRef, DISubprogram, DIArr use rustc::hir::TransFnAttrFlags; use rustc::hir::def_id::{DefId, CrateNum}; use rustc::ty::subst::{Substs, UnpackedKind}; -use rustc::ty::GenericParamDef; use abi::Abi; use common::CodegenCx; @@ -425,12 +424,7 @@ pub fn create_function_debug_context<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>, let mut names = generics.parent.map_or(vec![], |def_id| { get_parameter_names(cx, cx.tcx.generics_of(def_id)) }); - names.extend(generics.params.iter().map(|param| { - match param { - GenericParamDef::Lifetime(lt) => lt.name, - GenericParamDef::Type(ty) => ty.name, - } - })); + names.extend(generics.params.iter().map(|param| param.name)); names } diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index 84d94539f7436..3d77c9d39a5ac 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -43,7 +43,7 @@ pub trait AstConv<'gcx, 'tcx> { -> ty::GenericPredicates<'tcx>; /// What lifetime should we use when a lifetime is omitted (and not elided)? - fn re_infer(&self, span: Span, _def: Option<&ty::RegionParamDef>) + fn re_infer(&self, span: Span, _def: Option<&ty::GenericParamDef>) -> Option>; /// What type should we use when a type is omitted? @@ -51,7 +51,7 @@ pub trait AstConv<'gcx, 'tcx> { /// Same as ty_infer, but with a known type parameter definition. fn ty_infer_for_def(&self, - _def: &ty::TypeParamDef, + _def: &ty::GenericParamDef, span: Span) -> Ty<'tcx> { self.ty_infer(span) } @@ -95,7 +95,7 @@ const TRAIT_OBJECT_DUMMY_SELF: ty::TypeVariants<'static> = ty::TyInfer(ty::Fresh impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { pub fn ast_region_to_region(&self, lifetime: &hir::Lifetime, - def: Option<&ty::RegionParamDef>) + def: Option<&ty::GenericParamDef>) -> ty::Region<'tcx> { let tcx = self.tcx(); @@ -228,7 +228,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { let type_params_without_defaults = { let mut count = 0; for param in decl_generics.params.iter() { - if let ty::GenericParamDef::Type(ty) = param { + if let ty::GenericParamDefKind::Type(ty) = param.kind { if !ty.has_default { count += 1 } @@ -245,9 +245,9 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { } let is_object = self_ty.map_or(false, |ty| ty.sty == TRAIT_OBJECT_DUMMY_SELF); - let default_needs_object_self = |p: &ty::TypeParamDef| { - if is_object && p.has_default { - if tcx.at(span).type_of(p.def_id).has_self_ty() { + let default_needs_object_self = |param: &ty::GenericParamDef| { + if is_object && param.to_type().has_default { + if tcx.at(span).type_of(param.def_id).has_self_ty() { // There is no suitable inference default for a type parameter // that references self, in an object type. return true; @@ -284,7 +284,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { self.ty_infer(span) }; ty_var - } else if def.has_default { + } else if def.to_type().has_default { // No type parameter provided, but a default exists. // If we are converting an object type, then the @@ -998,7 +998,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { let item_def_id = tcx.hir.local_def_id(item_id); let generics = tcx.generics_of(item_def_id); let index = generics.param_def_id_to_index[&tcx.hir.local_def_id(node_id)]; - tcx.mk_param(index, tcx.hir.name(node_id).as_interned_str()) + tcx.mk_ty_param(index, tcx.hir.name(node_id).as_interned_str()) } Def::SelfTy(_, Some(def_id)) => { // Self in impl (we know the concrete type). @@ -1146,7 +1146,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { &mut substs, tcx, parent_generics, &mut |def, _| tcx.mk_region( ty::ReEarlyBound(def.to_early_bound_region_data())), - &mut |def, _| tcx.mk_param_from_def(def) + &mut |def, _| tcx.mk_ty_param_from_def(def) ); // Replace all lifetimes with 'static diff --git a/src/librustc_typeck/check/compare_method.rs b/src/librustc_typeck/check/compare_method.rs index d1978ceb30bf3..11f421da71474 100644 --- a/src/librustc_typeck/check/compare_method.rs +++ b/src/librustc_typeck/check/compare_method.rs @@ -10,7 +10,7 @@ use rustc::hir::{self, ImplItemKind, TraitItemKind}; use rustc::infer::{self, InferOk}; -use rustc::ty::{self, TyCtxt, GenericParamDef}; +use rustc::ty::{self, TyCtxt, GenericParamDefKind}; use rustc::ty::util::ExplicitSelf; use rustc::traits::{self, ObligationCause, ObligationCauseCode, Reveal}; use rustc::ty::error::{ExpectedFound, TypeError}; @@ -729,19 +729,19 @@ fn compare_synthetic_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let impl_m_generics = tcx.generics_of(impl_m.def_id); let trait_m_generics = tcx.generics_of(trait_m.def_id); let impl_m_type_params = impl_m_generics.params.iter().filter_map(|param| { - match *param { - GenericParamDef::Type(ty) => Some(ty), - GenericParamDef::Lifetime(_) => None, + match param.kind { + GenericParamDefKind::Type(_) => Some(param), + GenericParamDefKind::Lifetime(_) => None, } }); let trait_m_type_params = trait_m_generics.params.iter().filter_map(|param| { - match *param { - GenericParamDef::Type(ty) => Some(ty), - GenericParamDef::Lifetime(_) => None, + match param.kind { + GenericParamDefKind::Type(_) => Some(param), + GenericParamDefKind::Lifetime(_) => None, } }); for (impl_ty, trait_ty) in impl_m_type_params.zip(trait_m_type_params) { - if impl_ty.synthetic != trait_ty.synthetic { + if impl_ty.to_type().synthetic != trait_ty.to_type().synthetic { let impl_node_id = tcx.hir.as_local_node_id(impl_ty.def_id).unwrap(); let impl_span = tcx.hir.span(impl_node_id); let trait_span = tcx.def_span(trait_ty.def_id); diff --git a/src/librustc_typeck/check/intrinsic.rs b/src/librustc_typeck/check/intrinsic.rs index 1817b4aba1912..d852a865174fb 100644 --- a/src/librustc_typeck/check/intrinsic.rs +++ b/src/librustc_typeck/check/intrinsic.rs @@ -76,7 +76,7 @@ fn equate_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, /// and in libcore/intrinsics.rs pub fn check_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, it: &hir::ForeignItem) { - let param = |n| tcx.mk_param(n, Symbol::intern(&format!("P{}", n)).as_interned_str()); + let param = |n| tcx.mk_ty_param(n, Symbol::intern(&format!("P{}", n)).as_interned_str()); let name = it.name.as_str(); let (n_tps, inputs, output) = if name.starts_with("atomic_") { let split : Vec<&str> = name.split('_').collect(); @@ -342,7 +342,7 @@ pub fn check_platform_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, it: &hir::ForeignItem) { let param = |n| { let name = Symbol::intern(&format!("P{}", n)).as_interned_str(); - tcx.mk_param(n, name) + tcx.mk_ty_param(n, name) }; let def_id = tcx.hir.local_def_id(it.id); diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index f860c1358a6da..e5dffeed56017 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -1730,7 +1730,7 @@ impl<'a, 'gcx, 'tcx> AstConv<'gcx, 'tcx> for FnCtxt<'a, 'gcx, 'tcx> { } } - fn re_infer(&self, span: Span, def: Option<&ty::RegionParamDef>) + fn re_infer(&self, span: Span, def: Option<&ty::GenericParamDef>) -> Option> { let v = match def { Some(def) => infer::EarlyBoundRegion(span, def.name), @@ -1744,7 +1744,7 @@ impl<'a, 'gcx, 'tcx> AstConv<'gcx, 'tcx> for FnCtxt<'a, 'gcx, 'tcx> { } fn ty_infer_for_def(&self, - ty_param_def: &ty::TypeParamDef, + ty_param_def: &ty::GenericParamDef, span: Span) -> Ty<'tcx> { self.type_var_for_def(span, ty_param_def) } @@ -4805,7 +4805,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { if let Some(ast_ty) = types.get(i) { // A provided type parameter. self.to_ty(ast_ty) - } else if !infer_types && def.has_default { + } else if !infer_types && def.to_type().has_default { // No type parameter provided, but a default exists. let default = self.tcx.type_of(def.def_id); self.normalize_ty( @@ -4928,7 +4928,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { let type_params_without_defaults = { let mut count = 0; for param in generics.params.iter() { - if let ty::GenericParamDef::Type(ty) = param { + if let ty::GenericParamDefKind::Type(ty) = param.kind { if !ty.has_default { count += 1 } @@ -5025,7 +5025,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { let segment = segment.map(|(path_segment, generics)| { let explicit = !path_segment.infer_types; let impl_trait = generics.params.iter().any(|param| { - if let ty::GenericParamDef::Type(ty) = param { + if let ty::GenericParamDefKind::Type(ty) = param.kind { if let Some(hir::SyntheticTyParamKind::ImplTrait) = ty.synthetic { return true; } diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index 75380c685daa3..cc20a7c28d367 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -11,7 +11,7 @@ use check::{Inherited, FnCtxt}; use constrained_type_params::{identify_constrained_type_params, Parameter}; -use ty::GenericParamDef; +use ty::GenericParamDefKind; use hir::def_id::DefId; use rustc::traits::{self, ObligationCauseCode}; @@ -370,8 +370,8 @@ fn check_where_clauses<'a, 'gcx, 'fcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'gcx>, let mut substituted_predicates = Vec::new(); let generics = tcx.generics_of(def_id); - let is_our_default = |def: &ty::TypeParamDef| { - def.has_default && def.index >= generics.parent_count as u32 + let is_our_default = |def: &ty::GenericParamDef| { + def.to_type().has_default && def.index >= generics.parent_count as u32 }; // Check that concrete defaults are well-formed. See test `type-check-defaults.rs`. @@ -379,9 +379,9 @@ fn check_where_clauses<'a, 'gcx, 'fcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'gcx>, // struct Foo> { .. } // Here the default `Vec<[u32]>` is not WF because `[u32]: Sized` does not hold. for d in generics.params.iter().filter_map(|param| { - if let GenericParamDef::Type(ty) = *param { - if is_our_default(&ty) { - return Some(ty.def_id); + if let GenericParamDefKind::Type(_) = param.kind { + if is_our_default(¶m) { + return Some(param.def_id); } } None @@ -654,21 +654,18 @@ fn reject_shadowing_parameters(tcx: TyCtxt, def_id: DefId) { let impl_params: FxHashMap<_, _> = parent.params.iter() .flat_map(|param| { - match param { - GenericParamDef::Lifetime(_) => None, - GenericParamDef::Type(ty) => Some((ty.name, ty.def_id)), + match param.kind { + GenericParamDefKind::Lifetime(_) => None, + GenericParamDefKind::Type(_) => Some((param.name, param.def_id)), } }) .collect(); for method_param in generics.params.iter() { - // Shadowing is checked in resolve_lifetime. - if let GenericParamDef::Lifetime(_) = method_param { - continue; - } - let (name, def_id) = match method_param { - GenericParamDef::Lifetime(_) => continue, - GenericParamDef::Type(ty) => (ty.name, ty.def_id), + let (name, def_id) = match method_param.kind { + // Shadowing is checked in resolve_lifetime. + GenericParamDefKind::Lifetime(_) => continue, + GenericParamDefKind::Type(_) => (method_param.name, method_param.def_id), }; if impl_params.contains_key(&name) { // Tighten up the span to focus on only the shadowing type diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index b8c78c7b36a5e..d41f7e607277a 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -181,7 +181,7 @@ impl<'a, 'tcx> AstConv<'tcx, 'tcx> for ItemCtxt<'a, 'tcx> { self.tcx.at(span).type_param_predicates((self.item_def_id, def_id)) } - fn re_infer(&self, _span: Span, _def: Option<&ty::RegionParamDef>) + fn re_infer(&self, _span: Span, _def: Option<&ty::GenericParamDef>) -> Option> { None } @@ -244,7 +244,7 @@ fn type_param_predicates<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let param_owner_def_id = tcx.hir.local_def_id(param_owner); let generics = tcx.generics_of(param_owner_def_id); let index = generics.param_def_id_to_index[&def_id]; - let ty = tcx.mk_param(index, tcx.hir.ty_param_name(param_id).as_interned_str()); + let ty = tcx.mk_ty_param(index, tcx.hir.ty_param_name(param_id).as_interned_str()); // Don't look for bounds where the type parameter isn't in scope. let parent = if item_def_id == param_owner_def_id { @@ -840,14 +840,16 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, // the node id for the Self type parameter. let param_id = item.id; - opt_self = Some(ty::TypeParamDef { + opt_self = Some(ty::GenericParamDef { index: 0, name: keywords::SelfType.name().as_interned_str(), def_id: tcx.hir.local_def_id(param_id), - has_default: false, - object_lifetime_default: rl::Set1::Empty, - pure_wrt_drop: false, - synthetic: None, + kind: ty::GenericParamDefKind::Type(ty::TypeParamDef { + has_default: false, + object_lifetime_default: rl::Set1::Empty, + pure_wrt_drop: false, + synthetic: None, + }), }); allow_defaults = true; @@ -885,12 +887,14 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }); let early_lifetimes = early_bound_lifetimes_from_generics(tcx, ast_generics); - let regions = early_lifetimes.enumerate().map(|(i, l)| { - ty::RegionParamDef { + let lifetimes = early_lifetimes.enumerate().map(|(i, l)| { + ty::GenericParamDef { name: l.lifetime.name.name().as_interned_str(), index: own_start + i as u32, def_id: tcx.hir.local_def_id(l.lifetime.id), - pure_wrt_drop: l.pure_wrt_drop, + kind: ty::GenericParamDefKind::Lifetime(ty::RegionParamDef { + pure_wrt_drop: l.pure_wrt_drop, + }), } }).collect::>(); @@ -898,7 +902,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let object_lifetime_defaults = tcx.object_lifetime_defaults(hir_id); // Now create the real type parameters. - let type_start = own_start + regions.len() as u32; + let type_start = own_start + lifetimes.len() as u32; let types = ast_generics.ty_params().enumerate().map(|(i, p)| { if p.name == keywords::SelfType.name() { span_bug!(p.span, "`Self` should not be the name of a regular parameter"); @@ -915,15 +919,17 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } } - ty::TypeParamDef { + ty::GenericParamDef { index: type_start + i as u32, name: p.name.as_interned_str(), def_id: tcx.hir.local_def_id(p.id), - has_default: p.default.is_some(), - object_lifetime_default: - object_lifetime_defaults.as_ref().map_or(rl::Set1::Empty, |o| o[i]), - pure_wrt_drop: p.pure_wrt_drop, - synthetic: p.synthetic, + kind: ty::GenericParamDefKind::Type(ty::TypeParamDef { + has_default: p.default.is_some(), + object_lifetime_default: + object_lifetime_defaults.as_ref().map_or(rl::Set1::Empty, |o| o[i]), + pure_wrt_drop: p.pure_wrt_drop, + synthetic: p.synthetic, + }), } }); @@ -940,41 +946,43 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }; for (i, &arg) in dummy_args.iter().enumerate() { - types.push(ty::TypeParamDef { + types.push(ty::GenericParamDef { index: type_start + i as u32, name: Symbol::intern(arg).as_interned_str(), def_id, - has_default: false, - object_lifetime_default: rl::Set1::Empty, - pure_wrt_drop: false, - synthetic: None, + kind: ty::GenericParamDefKind::Type(ty::TypeParamDef { + has_default: false, + object_lifetime_default: rl::Set1::Empty, + pure_wrt_drop: false, + synthetic: None, + }), }); } tcx.with_freevars(node_id, |fv| { types.extend(fv.iter().zip((dummy_args.len() as u32)..).map(|(_, i)| { - ty::TypeParameterDef { + ty::GenericParamDef { index: type_start + i, name: Symbol::intern("").as_interned_str(), def_id, - has_default: false, - object_lifetime_default: rl::Set1::Empty, - pure_wrt_drop: false, - synthetic: None, + kind: ty::GenericParamDefKind::Type(ty::TypeParamDef { + has_default: false, + object_lifetime_default: rl::Set1::Empty, + pure_wrt_drop: false, + synthetic: None, + }), } })); }); } - let opt_self = opt_self.into_iter().map(|ty| ty::GenericParamDef::Type(ty)); - let lifetimes = regions.into_iter().map(|lt| ty::GenericParamDef::Lifetime(lt)); - let types = types.into_iter().map(|ty| ty::GenericParamDef::Type(ty)); - let params: Vec<_> = opt_self.chain(lifetimes) + let params: Vec<_> = opt_self.into_iter() + .chain(lifetimes) .chain(types) .collect(); let param_def_id_to_index = params.iter() - .map(|param| (param.def_id(), param.index())) + .map(|param| (param.def_id, param.index)) .collect(); tcx.alloc_generics(ty::Generics { @@ -1101,7 +1109,7 @@ fn type_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let region = def.to_early_bound_region_data(); tcx.mk_region(ty::ReEarlyBound(region)) }, - |def, _| tcx.mk_param_from_def(def) + |def, _| tcx.mk_ty_param_from_def(def) ) }; diff --git a/src/librustc_typeck/impl_wf_check.rs b/src/librustc_typeck/impl_wf_check.rs index 1922a48d04a37..f3645142e4b61 100644 --- a/src/librustc_typeck/impl_wf_check.rs +++ b/src/librustc_typeck/impl_wf_check.rs @@ -117,24 +117,24 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, for (ty_param, hir_param) in impl_generics.params.iter() .zip(impl_hir_generics.params.iter()) { - match (ty_param, hir_param) { + match (&ty_param.kind, hir_param) { // Disallow ANY unconstrained type parameters. - (ty::GenericParamDef::Type(ty_ty), hir::GenericParam::Type(hir_ty)) => { - let param_ty = ty::ParamTy::for_def(ty_ty); + (&ty::GenericParamDefKind::Type(_), hir::GenericParam::Type(hir_ty)) => { + let param_ty = ty::ParamTy::for_def(ty_param); if !input_parameters.contains(&ctp::Parameter::from(param_ty)) { report_unused_parameter(tcx, hir_ty.span, "type", ¶m_ty.to_string()); } } - (ty::GenericParamDef::Lifetime(ty_lt), hir::GenericParam::Lifetime(hir_lt)) => { - let param = ctp::Parameter::from(ty_lt.to_early_bound_region_data()); + (&ty::GenericParamDefKind::Lifetime(_), hir::GenericParam::Lifetime(hir_lt)) => { + let param = ctp::Parameter::from(ty_param.to_early_bound_region_data()); if lifetimes_in_associated_types.contains(¶m) && // (*) !input_parameters.contains(¶m) { report_unused_parameter(tcx, hir_lt.lifetime.span, "lifetime", &hir_lt.lifetime.name.name().to_string()); } } - (ty::GenericParamDef::Type(_), _) => continue, - (ty::GenericParamDef::Lifetime(_), _) => continue, + (&ty::GenericParamDefKind::Type(_), _) => continue, + (&ty::GenericParamDefKind::Lifetime(_), _) => continue, } } diff --git a/src/librustc_typeck/outlives/implicit_infer.rs b/src/librustc_typeck/outlives/implicit_infer.rs index 5a9539a8badf0..e711598c944c1 100644 --- a/src/librustc_typeck/outlives/implicit_infer.rs +++ b/src/librustc_typeck/outlives/implicit_infer.rs @@ -353,7 +353,7 @@ fn insert_outlives_predicate<'tcx>( // Vec`. Decomposing `Vec` into // components would yield `U`, and we add the // where clause that `U: 'a`. - let ty: Ty<'tcx> = tcx.mk_param(param_ty.idx, param_ty.name); + let ty: Ty<'tcx> = tcx.mk_ty_param(param_ty.idx, param_ty.name); required_predicates .insert(ty::OutlivesPredicate(ty.into(), outlived_region)); } diff --git a/src/librustdoc/clean/auto_trait.rs b/src/librustdoc/clean/auto_trait.rs index dc49cfcbc2b13..88784aab90e0e 100644 --- a/src/librustdoc/clean/auto_trait.rs +++ b/src/librustdoc/clean/auto_trait.rs @@ -228,12 +228,12 @@ impl<'a, 'tcx, 'rcx> AutoTraitFinder<'a, 'tcx, 'rcx> { let mut types = vec![]; for param in generics.params.iter() { - match param { - ty::GenericParamDef::Lifetime(lt) => { - let name = if lt.name == "" { + match param.kind { + ty::GenericParamDefKind::Lifetime(_) => { + let name = if param.name == "" { hir::LifetimeName::Static } else { - hir::LifetimeName::Name(lt.name.as_symbol()) + hir::LifetimeName::Name(param.name.as_symbol()) }; lifetimes.push(hir::Lifetime { @@ -242,8 +242,8 @@ impl<'a, 'tcx, 'rcx> AutoTraitFinder<'a, 'tcx, 'rcx> { name, }); } - ty::GenericParamDef::Type(ty) => { - types.push(P(self.ty_param_to_ty(ty.clone()))); + ty::GenericParamDefKind::Type(_) => { + types.push(P(self.ty_param_to_ty(param.clone()))); } } } @@ -256,7 +256,7 @@ impl<'a, 'tcx, 'rcx> AutoTraitFinder<'a, 'tcx, 'rcx> { } } - fn ty_param_to_ty(&self, param: ty::TypeParamDef) -> hir::Ty { + fn ty_param_to_ty(&self, param: ty::GenericParamDef) -> hir::Ty { debug!("ty_param_to_ty({:?}) {:?}", param, param.def_id); hir::Ty { id: ast::DUMMY_NODE_ID, diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index cb48d790f6070..35a7b27670ae4 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1336,14 +1336,14 @@ impl Clean for hir::TyParam { } } -impl<'tcx> Clean for ty::TypeParamDef { +impl<'tcx> Clean for ty::GenericParamDef { fn clean(&self, cx: &DocContext) -> TyParam { cx.renderinfo.borrow_mut().external_typarams.insert(self.def_id, self.name.clean(cx)); TyParam { name: self.name.clean(cx), did: self.def_id, bounds: vec![], // these are filled in from the where-clauses - default: if self.has_default { + default: if self.to_type().has_default { Some(cx.tcx.type_of(self.def_id).clean(cx)) } else { None @@ -1577,8 +1577,8 @@ impl Clean for hir::LifetimeDef { } } -impl Clean for ty::RegionParamDef { - fn clean(&self, _: &DocContext) -> Lifetime { +impl<'tcx> Clean for ty::GenericParamDef { + fn clean(&self, _cx: &DocContext) -> Lifetime { Lifetime(self.name.to_string()) } } @@ -1800,17 +1800,17 @@ impl<'a, 'tcx> Clean for (&'a ty::Generics, // predicates field (see rustc_typeck::collect::ty_generics), so remove // them. let stripped_typarams = gens.params.iter().filter_map(|param| { - if let ty::GenericParamDef::Type(ty) = param { - if ty.name == keywords::SelfType.name().as_str() { - assert_eq!(ty.index, 0); + if let ty::GenericParamDefKind::Type(_) = param.kind { + if param.name == keywords::SelfType.name().as_str() { + assert_eq!(param.index, 0); None } else { - Some(ty.clean(cx)) + Some(param.clean(cx)) } } else { None } - }).collect::>(); + }).collect::>(); let mut where_predicates = preds.predicates.to_vec().clean(cx); @@ -1855,8 +1855,8 @@ impl<'a, 'tcx> Clean for (&'a ty::Generics, params: gens.params .iter() .flat_map(|param| { - if let ty::GenericParamDef::Lifetime(lt) = param { - Some(GenericParamDef::Lifetime(lt.clean(cx))) + if let ty::GenericParamDefKind::Lifetime(_) = param.kind { + Some(GenericParamDef::Lifetime(param.clean(cx))) } else { None } From 9f9d4beda69cd350e7e73bc95e01eb9c594967b7 Mon Sep 17 00:00:00 2001 From: varkor Date: Thu, 19 Apr 2018 00:41:29 +0100 Subject: [PATCH 24/40] Rename RegionParamDef to LifetimeParamDef --- src/librustc/ich/impls_ty.rs | 2 +- src/librustc/ty/mod.rs | 6 +++--- src/librustc_typeck/collect.rs | 2 +- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/src/librustc/ich/impls_ty.rs b/src/librustc/ich/impls_ty.rs index eddb73e72399c..e06d22607b75e 100644 --- a/src/librustc/ich/impls_ty.rs +++ b/src/librustc/ich/impls_ty.rs @@ -765,7 +765,7 @@ impl_stable_hash_for!(struct ty::GenericParamDef { kind }); -impl_stable_hash_for!(struct ty::RegionParamDef { +impl_stable_hash_for!(struct ty::LifetimeParamDef { pure_wrt_drop }); diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 3c4c326578a5d..025e07942656c 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -723,7 +723,7 @@ pub struct TypeParamDef { } #[derive(Copy, Clone, Debug, RustcEncodable, RustcDecodable)] -pub struct RegionParamDef { +pub struct LifetimeParamDef { /// `pure_wrt_drop`, set by the (unsafe) `#[may_dangle]` attribute /// on generic parameter `'a`, asserts data of lifetime `'a` /// won't be accessed during the parent type's `Drop` impl. @@ -738,7 +738,7 @@ impl ty::EarlyBoundRegion { #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] pub enum GenericParamDefKind { - Lifetime(RegionParamDef), + Lifetime(LifetimeParamDef), Type(TypeParamDef), } @@ -751,7 +751,7 @@ pub struct GenericParamDef { } impl GenericParamDef { - pub fn to_lifetime(&self) -> RegionParamDef { + pub fn to_lifetime(&self) -> LifetimeParamDef { match self.kind { GenericParamDefKind::Lifetime(lt) => lt, _ => bug!("cannot convert a non-lifetime to a lifetime") diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index d41f7e607277a..6945f8f3c078a 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -892,7 +892,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, name: l.lifetime.name.name().as_interned_str(), index: own_start + i as u32, def_id: tcx.hir.local_def_id(l.lifetime.id), - kind: ty::GenericParamDefKind::Lifetime(ty::RegionParamDef { + kind: ty::GenericParamDefKind::Lifetime(ty::LifetimeParamDef { pure_wrt_drop: l.pure_wrt_drop, }), } From 18f77e25e9fa52d685f6e457853af880003484f6 Mon Sep 17 00:00:00 2001 From: varkor Date: Fri, 27 Apr 2018 23:44:25 +0100 Subject: [PATCH 25/40] Fix rebase fallout --- src/librustc/ty/context.rs | 12 +++++++++--- src/librustc_typeck/check/wfcheck.rs | 2 +- 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/src/librustc/ty/context.rs b/src/librustc/ty/context.rs index 6eb85cfb307fa..ff4afdd8b7e0f 100644 --- a/src/librustc/ty/context.rs +++ b/src/librustc/ty/context.rs @@ -35,6 +35,7 @@ use mir::{self, Mir, interpret}; use ty::subst::{Kind, Substs, Subst}; use ty::ReprOptions; use ty::Instance; +use ty::GenericParamDefKind; use traits; use traits::{Clause, Clauses, Goal, Goals}; use ty::{self, Ty, TypeAndMut}; @@ -2328,9 +2329,14 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { let generics = self.generics_of(def_id); let mut substs = vec![Kind::from(ty)]; // Add defaults for other generic params if there are some. - for def in generics.types.iter().skip(1) { - assert!(def.has_default); - let ty = self.type_of(def.def_id).subst(self, &substs); + for (def_id, has_default) in generics.params.iter().filter_map(|param| { + match param.kind { + GenericParamDefKind::Type(ty) => Some((param.def_id, ty.has_default)), + GenericParamDefKind::Lifetime(_) => None + } + }).skip(1) { + assert!(has_default); + let ty = self.type_of(def_id).subst(self, &substs); substs.push(ty.into()); } let substs = self.mk_substs(substs.into_iter()); diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index cc20a7c28d367..00a75a7d87026 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -675,7 +675,7 @@ fn reject_shadowing_parameters(tcx: TyCtxt, def_id: DefId) { // local so it should be okay to just unwrap everything. let trait_def_id = impl_params[&name]; let trait_decl_span = tcx.def_span(trait_def_id); - error_194(tcx, type_span, trait_decl_span, &name[..]); + error_194(tcx, type_span, trait_decl_span, &name.as_str()[..]); } } } From 9200bdee2699b5d846c6d0e19ee6369007f06e2e Mon Sep 17 00:00:00 2001 From: varkor Date: Thu, 10 May 2018 23:02:41 +0100 Subject: [PATCH 26/40] Refactor generic params loops --- src/librustc/hir/lowering.rs | 16 +++--- src/librustc/hir/print.rs | 5 +- src/librustc/infer/anon_types/mod.rs | 13 ++--- src/librustc/traits/auto_trait.rs | 9 +++- src/librustc/traits/error_reporting.rs | 18 +++---- src/librustc/traits/on_unimplemented.rs | 7 +-- src/librustc/ty/context.rs | 26 +++++---- src/librustc/ty/mod.rs | 60 +++------------------ src/librustc/ty/sty.rs | 2 +- src/librustc/util/ppaux.rs | 8 +-- src/librustc_privacy/lib.rs | 4 +- src/librustc_typeck/astconv.rs | 10 ++-- src/librustc_typeck/check/method/confirm.rs | 3 +- src/librustc_typeck/check/mod.rs | 19 ++++--- src/librustc_typeck/check/wfcheck.rs | 33 ++++++------ src/librustc_typeck/collect.rs | 6 +-- src/librustdoc/clean/mod.rs | 2 +- src/libsyntax/visit.rs | 4 +- src/libsyntax_ext/deriving/generic/mod.rs | 6 +-- src/libsyntax_ext/deriving/generic/ty.rs | 9 +--- 20 files changed, 95 insertions(+), 165 deletions(-) diff --git a/src/librustc/hir/lowering.rs b/src/librustc/hir/lowering.rs index 77c2dd219c478..628b871ed5135 100644 --- a/src/librustc/hir/lowering.rs +++ b/src/librustc/hir/lowering.rs @@ -374,8 +374,8 @@ impl<'a> LoweringContext<'a> { if item_lowered { let item_lifetimes = match self.lctx.items.get(&item.id).unwrap().node { - hir::Item_::ItemImpl(_, _, _, ref generics, .. ) | - hir::Item_::ItemTrait(_, _, ref generics, .. ) => { + hir::Item_::ItemImpl(_, _, _, ref generics, ..) + | hir::Item_::ItemTrait(_, _, ref generics, ..) => { generics.lifetimes().cloned().collect::>() } _ => Vec::new(), @@ -1895,13 +1895,11 @@ impl<'a> LoweringContext<'a> { GenericParam::Lifetime(ref lifetime_def) => { hir::GenericParam::Lifetime(self.lower_lifetime_def(lifetime_def)) } - GenericParam::Type(ref ty_param) => { - hir::GenericParam::Type(self.lower_ty_param( - ty_param, - add_bounds.get(&ty_param.id).map_or(&[][..], |x| &x), - itctx, - )) - } + GenericParam::Type(ref ty_param) => hir::GenericParam::Type(self.lower_ty_param( + ty_param, + add_bounds.get(&ty_param.id).map_or(&[][..], |x| &x), + itctx, + )), }) .collect() } diff --git a/src/librustc/hir/print.rs b/src/librustc/hir/print.rs index 2dc46f5f69d70..3943c30127d6f 100644 --- a/src/librustc/hir/print.rs +++ b/src/librustc/hir/print.rs @@ -2043,10 +2043,7 @@ impl<'a> State<'a> { Ok(()) } - pub fn print_generic_params(&mut self, - generic_params: &[hir::GenericParam]) - -> io::Result<()> - { + pub fn print_generic_params(&mut self, generic_params: &[hir::GenericParam]) -> io::Result<()> { if !generic_params.is_empty() { self.s.word("<")?; diff --git a/src/librustc/infer/anon_types/mod.rs b/src/librustc/infer/anon_types/mod.rs index 0af95a74686bf..95727d10b1894 100644 --- a/src/librustc/infer/anon_types/mod.rs +++ b/src/librustc/infer/anon_types/mod.rs @@ -313,16 +313,13 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { // `['a]` for the first impl trait and `'b` for the // second. let mut least_region = None; - for index in abstract_type_generics.params.iter().filter_map(|param| { - if let GenericParamDefKind::Lifetime(_) = param.kind { - // Find the index of this region in the list of substitutions. - Some(param.index as usize) - } else { - None + for param in &abstract_type_generics.params { + match param.kind { + GenericParamDefKind::Lifetime(_) => {} + _ => continue } - }) { // Get the value supplied for this region from the substs. - let subst_arg = anon_defn.substs.region_at(index); + let subst_arg = anon_defn.substs.region_at(param.index as usize); // Compute the least upper bound of it with the other regions. debug!("constrain_anon_types: least_region={:?}", least_region); diff --git a/src/librustc/traits/auto_trait.rs b/src/librustc/traits/auto_trait.rs index 5d708f60604f1..4bb5387efb352 100644 --- a/src/librustc/traits/auto_trait.rs +++ b/src/librustc/traits/auto_trait.rs @@ -222,9 +222,14 @@ impl<'a, 'tcx> AutoTraitFinder<'a, 'tcx> { }); let names_map: FxHashSet = generics - .regions + .params .iter() - .map(|l| l.name.to_string()) + .filter_map(|param| { + match param.kind { + ty::GenericParamDefKind::Lifetime(_) => Some(param.name.to_string()), + _ => None + } + }) .collect(); let body_ids: FxHashSet<_> = infcx diff --git a/src/librustc/traits/error_reporting.rs b/src/librustc/traits/error_reporting.rs index 2f0691d241e32..9d71fe6f2d736 100644 --- a/src/librustc/traits/error_reporting.rs +++ b/src/librustc/traits/error_reporting.rs @@ -379,16 +379,16 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { flags.push(("_Self".to_string(), Some(self.tcx.type_of(def.did).to_string()))); } - for param in generics.params.iter().filter(|param| { - match param.kind { - GenericParamDefKind::Type(_) => true, - GenericParamDefKind::Lifetime(_) => false, - } - }) { + for param in generics.params.iter() { let name = param.name.to_string(); - let ty = trait_ref.substs.type_for_def(¶m); - let ty_str = ty.to_string(); - flags.push((name.clone(), Some(ty_str.clone()))); + let value = match param.kind { + GenericParamDefKind::Type(_) => { + let ty = trait_ref.substs.type_for_def(¶m); + ty.to_string() + }, + GenericParamDefKind::Lifetime(_) => continue, + }; + flags.push((name.clone(), Some(value.clone()))); } if let Some(true) = self_ty.ty_to_def_id().map(|def_id| def_id.is_local()) { diff --git a/src/librustc/traits/on_unimplemented.rs b/src/librustc/traits/on_unimplemented.rs index e15542cb2c09d..1980fbbe3ed75 100644 --- a/src/librustc/traits/on_unimplemented.rs +++ b/src/librustc/traits/on_unimplemented.rs @@ -254,15 +254,12 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { Position::ArgumentNamed(s) if s == name => (), // So is `{A}` if A is a type parameter Position::ArgumentNamed(s) => match generics.params.iter().find(|param| { - match param.kind { - GenericParamDefKind::Type(_) => param.name == s, - GenericParamDefKind::Lifetime(_) => false, - } + param.name == s }) { Some(_) => (), None => { span_err!(tcx.sess, span, E0230, - "there is no type parameter \ + "there is no parameter \ {} on trait {}", s, name); result = Err(ErrorReported); diff --git a/src/librustc/ty/context.rs b/src/librustc/ty/context.rs index ff4afdd8b7e0f..995d6c5576718 100644 --- a/src/librustc/ty/context.rs +++ b/src/librustc/ty/context.rs @@ -35,7 +35,6 @@ use mir::{self, Mir, interpret}; use ty::subst::{Kind, Substs, Subst}; use ty::ReprOptions; use ty::Instance; -use ty::GenericParamDefKind; use traits; use traits::{Clause, Clauses, Goal, Goals}; use ty::{self, Ty, TypeAndMut}; @@ -2326,20 +2325,19 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { pub fn mk_box(self, ty: Ty<'tcx>) -> Ty<'tcx> { let def_id = self.require_lang_item(lang_items::OwnedBoxLangItem); let adt_def = self.adt_def(def_id); - let generics = self.generics_of(def_id); - let mut substs = vec![Kind::from(ty)]; - // Add defaults for other generic params if there are some. - for (def_id, has_default) in generics.params.iter().filter_map(|param| { - match param.kind { - GenericParamDefKind::Type(ty) => Some((param.def_id, ty.has_default)), - GenericParamDefKind::Lifetime(_) => None + let substs = Substs::for_item(self, def_id, |_, _| bug!(), |def, substs| { + if def.index == 0 { + ty + } else { + match def.kind { + ty::GenericParamDefKind::Type(ty_param) => { + assert!(ty_param.has_default); + self.type_of(def.def_id).subst(self, substs) + } + _ => unreachable!() + } } - }).skip(1) { - assert!(has_default); - let ty = self.type_of(def_id).subst(self, &substs); - substs.push(ty.into()); - } - let substs = self.mk_substs(substs.into_iter()); + }); self.mk_ty(TyAdt(adt_def, substs)) } diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 025e07942656c..c3e9ffec9a009 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -804,7 +804,7 @@ pub struct Generics { pub parent_count: usize, pub params: Vec, - /// Reverse map to the `index` field of each `GenericParamDef`'s inner type + /// Reverse map to the `index` field of each `GenericParamDef` pub param_def_id_to_index: FxHashMap, pub has_self: bool, @@ -836,13 +836,11 @@ impl<'a, 'gcx, 'tcx> Generics { } pub fn requires_monomorphization(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { - if self.params.iter().any(|param| { + for param in self.params.iter() { match param.kind { - GenericParamDefKind::Type(_) => true, - GenericParamDefKind::Lifetime(_) => false + GenericParamDefKind::Type(_) => return true, + GenericParamDefKind::Lifetime(_) => {} } - }) { - return true; } if let Some(parent_def_id) = self.parent { let parent = tcx.generics_of(parent_def_id); @@ -858,7 +856,7 @@ impl<'a, 'gcx, 'tcx> Generics { -> &'tcx GenericParamDef { if let Some(index) = param.index.checked_sub(self.parent_count as u32) { - let ref param = self.params[index as usize]; + let param = &self.params[index as usize]; match param.kind { ty::GenericParamDefKind::Lifetime(_) => param, _ => bug!("expected region parameter, but found another generic parameter") @@ -875,53 +873,7 @@ impl<'a, 'gcx, 'tcx> Generics { tcx: TyCtxt<'a, 'gcx, 'tcx>) -> &'tcx GenericParamDef { if let Some(index) = param.idx.checked_sub(self.parent_count as u32) { - // non-Self type parameters are always offset by exactly - // `self.regions.len()`. In the absence of a Self, this is obvious, - // but even in the presence of a `Self` we just have to "compensate" - // for the regions: - // - // Without a `Self` (or in a nested generics that doesn't have - // a `Self` in itself, even through it parent does), for example - // for `fn foo<'a, T1, T2>()`, the situation is: - // Substs: - // 0 1 2 - // 'a T1 T2 - // generics.types: - // 0 1 - // T1 T2 - // - // And with a `Self`, for example for `trait Foo<'a, 'b, T1, T2>`, the - // situation is: - // Substs: - // 0 1 2 3 4 - // Self 'a 'b T1 T2 - // generics.types: - // 0 1 2 - // Self T1 T2 - // - // And it can be seen that in both cases, to move from a substs - // offset to a generics offset you just have to offset by the - // number of regions. - let type_param_offset = self.param_counts().lifetimes; - - let has_self = self.has_self && self.parent.is_none(); - let is_separated_self = type_param_offset != 0 && index == 0 && has_self; - - if let Some(_) = (index as usize).checked_sub(type_param_offset) { - assert!(!is_separated_self, "found a Self after type_param_offset"); - let ref param = self.params[index as usize]; - match param.kind { - ty::GenericParamDefKind::Type(_) => param, - _ => bug!("expected type parameter, but found another generic parameter") - } - } else { - assert!(is_separated_self, "non-Self param before type_param_offset"); - let ref param = self.params[type_param_offset]; - match param.kind { - ty::GenericParamDefKind::Type(_) => param, - _ => bug!("expected type parameter, but found another generic parameter") - } - } + &self.params[index as usize] } else { tcx.generics_of(self.parent.expect("parent_count>0 but no parent?")) .type_param(param, tcx) diff --git a/src/librustc/ty/sty.rs b/src/librustc/ty/sty.rs index 792a6bfaedfd4..acc225ddf5680 100644 --- a/src/librustc/ty/sty.rs +++ b/src/librustc/ty/sty.rs @@ -366,7 +366,7 @@ struct SplitGeneratorSubsts<'tcx> { impl<'tcx> GeneratorSubsts<'tcx> { fn split(self, def_id: DefId, tcx: TyCtxt<'_, '_, '_>) -> SplitGeneratorSubsts<'tcx> { let generics = tcx.generics_of(def_id); - let parent_len = generics.parent_count(); + let parent_len = generics.parent_count; SplitGeneratorSubsts { yield_ty: self.substs.type_at(parent_len), return_ty: self.substs.type_at(parent_len + 1), diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index 47315c7243f02..ca939b161d21e 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -351,8 +351,10 @@ impl PrintContext { let zipped = iter::once((last_ty, types.next().unwrap())) .chain(type_params.zip(types)); for ((def_id, has_default), actual) in zipped { - if !has_default || - tcx.type_of(def_id).subst(tcx, substs) != actual { + if !has_default { + break; + } + if tcx.type_of(def_id).subst(tcx, substs) != actual { break; } num_supplied_defaults += 1; @@ -604,7 +606,7 @@ define_print! { impl fmt::Debug for ty::GenericParamDef { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { let type_name = match self.kind { - ty::GenericParamDefKind::Lifetime(_) => "Region", + ty::GenericParamDefKind::Lifetime(_) => "Lifetime", ty::GenericParamDefKind::Type(_) => "Type", }; write!(f, "{}({}, {:?}, {})", diff --git a/src/librustc_privacy/lib.rs b/src/librustc_privacy/lib.rs index 1b2ec481a1ccc..929030e832e94 100644 --- a/src/librustc_privacy/lib.rs +++ b/src/librustc_privacy/lib.rs @@ -399,7 +399,7 @@ impl<'a, 'tcx> Visitor<'tcx> for EmbargoVisitor<'a, 'tcx> { impl<'b, 'a, 'tcx> ReachEverythingInTheInterfaceVisitor<'b, 'a, 'tcx> { fn generics(&mut self) -> &mut Self { - for param in self.ev.tcx.generics_of(self.item_def_id).params.iter() { + for param in &self.ev.tcx.generics_of(self.item_def_id).params { match param.kind { GenericParamDefKind::Type(ty) => { if ty.has_default { @@ -1340,7 +1340,7 @@ struct SearchInterfaceForPrivateItemsVisitor<'a, 'tcx: 'a> { impl<'a, 'tcx: 'a> SearchInterfaceForPrivateItemsVisitor<'a, 'tcx> { fn generics(&mut self) -> &mut Self { - for param in self.tcx.generics_of(self.item_def_id).params.iter() { + for param in &self.tcx.generics_of(self.item_def_id).params { match param.kind { GenericParamDefKind::Type(ty) => { if ty.has_default { diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index 3d77c9d39a5ac..e4d5ce054577d 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -222,8 +222,8 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { assert_eq!(decl_generics.has_self, self_ty.is_some()); // Check the number of type parameters supplied by the user. - let type_params_offset = self_ty.is_some() as usize; - let ty_param_defs = param_counts.types - type_params_offset; + let own_self = self_ty.is_some() as usize; + let ty_param_defs = param_counts.types - own_self; if !infer_types || num_types_provided > ty_param_defs { let type_params_without_defaults = { let mut count = 0; @@ -241,7 +241,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { span, num_types_provided, ty_param_defs, - type_params_without_defaults - type_params_offset); + type_params_without_defaults - own_self); } let is_object = self_ty.map_or(false, |ty| ty.sty == TRAIT_OBJECT_DUMMY_SELF); @@ -258,7 +258,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { }; let substs = Substs::for_item(tcx, def_id, |def, _| { - let i = def.index as usize - type_params_offset; + let i = def.index as usize - own_self; if let Some(lifetime) = parameters.lifetimes.get(i) { self.ast_region_to_region(lifetime, Some(def)) } else { @@ -272,7 +272,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { return ty; } - let i = i - (param_counts.lifetimes + type_params_offset); + let i = i - (param_counts.lifetimes + own_self); if i < num_types_provided { // A provided type parameter. self.ast_ty_to_ty(¶meters.types[i]) diff --git a/src/librustc_typeck/check/method/confirm.rs b/src/librustc_typeck/check/method/confirm.rs index eab26046147b5..cfb8441231706 100644 --- a/src/librustc_typeck/check/method/confirm.rs +++ b/src/librustc_typeck/check/method/confirm.rs @@ -316,6 +316,7 @@ impl<'a, 'gcx, 'tcx> ConfirmContext<'a, 'gcx, 'tcx> { // parameters from the type and those from the method. assert_eq!(method_generics.parent_count, parent_substs.len()); let provided = &segment.parameters; + let param_counts = method_generics.param_counts(); Substs::for_item(self.tcx, pick.item.def_id, |def, _| { let i = def.index as usize; if i < parent_substs.len() { @@ -333,7 +334,7 @@ impl<'a, 'gcx, 'tcx> ConfirmContext<'a, 'gcx, 'tcx> { } else if let Some(ast_ty) = provided.as_ref().and_then(|p| { let idx = - i - parent_substs.len() - method_generics.param_counts().lifetimes; + i - parent_substs.len() - param_counts.lifetimes; p.types.get(idx) }) { diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index e5dffeed56017..256e44a2d6b02 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -4918,13 +4918,12 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { }; // Check provided parameters. - let (ty_non_def_req_len, ty_req_len, lt_req_len) = + let (ty_req_len, accepted, lt_req_len) = segment.map_or((0, 0, 0), |(_, generics)| { let param_counts = generics.param_counts(); - let type_params_offset - = (generics.parent.is_none() && generics.has_self) as usize; - let type_params = param_counts.types - type_params_offset; + let own_self = (generics.parent.is_none() && generics.has_self) as usize; + let type_params = param_counts.types - own_self; let type_params_without_defaults = { let mut count = 0; for param in generics.params.iter() { @@ -4937,14 +4936,14 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { count }; let type_params_barring_defaults = - type_params_without_defaults - type_params_offset; + type_params_without_defaults - own_self; (type_params_barring_defaults, type_params, param_counts.lifetimes) }); - if types.len() > ty_req_len { - let span = types[ty_req_len].span; - let expected_text = count_type_params(ty_req_len); + if types.len() > accepted { + let span = types[accepted].span; + let expected_text = count_type_params(accepted); let actual_text = count_type_params(types.len()); struct_span_err!(self.tcx.sess, span, E0087, "too many type parameters provided: \ @@ -4957,8 +4956,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // type parameters, we force instantiate_value_path to // use inference variables instead of the provided types. *segment = None; - } else if types.len() < ty_non_def_req_len && !infer_types && !supress_mismatch_error { - let expected_text = count_type_params(ty_non_def_req_len); + } else if types.len() < ty_req_len && !infer_types && !supress_mismatch_error { + let expected_text = count_type_params(ty_req_len); let actual_text = count_type_params(types.len()); struct_span_err!(self.tcx.sess, span, E0089, "too few type parameters provided: \ diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index 00a75a7d87026..740a3dfcac973 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -378,22 +378,19 @@ fn check_where_clauses<'a, 'gcx, 'fcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'gcx>, // For example this forbids the declaration: // struct Foo> { .. } // Here the default `Vec<[u32]>` is not WF because `[u32]: Sized` does not hold. - for d in generics.params.iter().filter_map(|param| { + for param in &generics.params { if let GenericParamDefKind::Type(_) = param.kind { if is_our_default(¶m) { - return Some(param.def_id); + let ty = fcx.tcx.type_of(param.def_id); + // ignore dependent defaults -- that is, where the default of one type + // parameter includes another (e.g., ). In those cases, we can't + // be sure if it will error or not as user might always specify the other. + if !ty.needs_subst() { + fcx.register_wf_obligation(ty, fcx.tcx.def_span(param.def_id), + ObligationCauseCode::MiscObligation); + } } } - None - }) { - let ty = fcx.tcx.type_of(d); - // ignore dependent defaults -- that is, where the default of one type - // parameter includes another (e.g., ). In those cases, we can't - // be sure if it will error or not as user might always specify the other. - if !ty.needs_subst() { - fcx.register_wf_obligation(ty, fcx.tcx.def_span(d), - ObligationCauseCode::MiscObligation); - } } // Check that trait predicates are WF when params are substituted by their defaults. @@ -662,20 +659,20 @@ fn reject_shadowing_parameters(tcx: TyCtxt, def_id: DefId) { .collect(); for method_param in generics.params.iter() { - let (name, def_id) = match method_param.kind { + match method_param.kind { // Shadowing is checked in resolve_lifetime. GenericParamDefKind::Lifetime(_) => continue, - GenericParamDefKind::Type(_) => (method_param.name, method_param.def_id), + _ => {}, }; - if impl_params.contains_key(&name) { + if impl_params.contains_key(&method_param.name) { // Tighten up the span to focus on only the shadowing type - let type_span = tcx.def_span(def_id); + let type_span = tcx.def_span(method_param.def_id); // The expectation here is that the original trait declaration is // local so it should be okay to just unwrap everything. - let trait_def_id = impl_params[&name]; + let trait_def_id = impl_params[&method_param.name]; let trait_decl_span = tcx.def_span(trait_def_id); - error_194(tcx, type_span, trait_decl_span, &name.as_str()[..]); + error_194(tcx, type_span, trait_decl_span, &method_param.name.as_str()[..]); } } } diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 6945f8f3c078a..3be702189fb69 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -903,7 +903,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, // Now create the real type parameters. let type_start = own_start + lifetimes.len() as u32; - let types = ast_generics.ty_params().enumerate().map(|(i, p)| { + let mut types: Vec<_> = ast_generics.ty_params().enumerate().map(|(i, p)| { if p.name == keywords::SelfType.name() { span_bug!(p.span, "`Self` should not be the name of a regular parameter"); } @@ -931,9 +931,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, synthetic: p.synthetic, }), } - }); - - let mut types: Vec<_> = types.into_iter().collect(); + }).collect(); // provide junk type parameter defs - the only place that // cares about anything but the length is instantiation, diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 35a7b27670ae4..69999eb69b0b2 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1753,7 +1753,7 @@ impl Clean for hir::Generics { let mut params = Vec::with_capacity(self.params.len()); for p in &self.params { let p = p.clean(cx); - if let GenericParam::Type(ref tp) = p { + if let GenericParamDef::Type(ref tp) = p { if tp.synthetic == Some(hir::SyntheticTyParamKind::ImplTrait) { cx.impl_trait_bounds.borrow_mut().insert(tp.did, tp.bounds.clone()); } diff --git a/src/libsyntax/visit.rs b/src/libsyntax/visit.rs index 3f9e0b9fbb5d6..40d59d3ff8b8d 100644 --- a/src/libsyntax/visit.rs +++ b/src/libsyntax/visit.rs @@ -72,9 +72,7 @@ pub trait Visitor<'ast>: Sized { fn visit_expr(&mut self, ex: &'ast Expr) { walk_expr(self, ex) } fn visit_expr_post(&mut self, _ex: &'ast Expr) { } fn visit_ty(&mut self, t: &'ast Ty) { walk_ty(self, t) } - fn visit_generic_param(&mut self, param: &'ast GenericParam) { - walk_generic_param(self, param) - } + fn visit_generic_param(&mut self, param: &'ast GenericParam) { walk_generic_param(self, param) } fn visit_generics(&mut self, g: &'ast Generics) { walk_generics(self, g) } fn visit_where_predicate(&mut self, p: &'ast WherePredicate) { walk_where_predicate(self, p) diff --git a/src/libsyntax_ext/deriving/generic/mod.rs b/src/libsyntax_ext/deriving/generic/mod.rs index ddf3ae41faa3b..80f65957c39a2 100644 --- a/src/libsyntax_ext/deriving/generic/mod.rs +++ b/src/libsyntax_ext/deriving/generic/mod.rs @@ -570,11 +570,7 @@ impl<'a> TraitDef<'a> { bounds.push((*declared_bound).clone()); } - GenericParam::Type(cx.typaram(self.span, - ty_param.ident, - vec![], - bounds, - None)) + GenericParam::Type(cx.typaram(self.span, ty_param.ident, vec![], bounds, None)) } } })); diff --git a/src/libsyntax_ext/deriving/generic/ty.rs b/src/libsyntax_ext/deriving/generic/ty.rs index 76950a546cfd1..25a2969448835 100644 --- a/src/libsyntax_ext/deriving/generic/ty.rs +++ b/src/libsyntax_ext/deriving/generic/ty.rs @@ -187,9 +187,7 @@ impl<'a> Ty<'a> { let self_params = self_generics.params .iter() .filter_map(|param| match *param { - GenericParam::Type(ref ty_param) => { - Some(cx.ty_ident(span, ty_param.ident)) - } + GenericParam::Type(ref ty_param) => Some(cx.ty_ident(span, ty_param.ident)), _ => None, }) .collect(); @@ -272,10 +270,7 @@ impl<'a> LifetimeBounds<'a> { let bounds = bounds.iter() .map(|b| cx.lifetime(span, Ident::from_str(b))) .collect(); - GenericParam::Lifetime(cx.lifetime_def(span, - Ident::from_str(lt), - vec![], - bounds)) + GenericParam::Lifetime(cx.lifetime_def(span, Ident::from_str(lt), vec![], bounds)) }) .chain(self.bounds .iter() From 007de2f89672559c8fd4593831c3edb93f1983a5 Mon Sep 17 00:00:00 2001 From: varkor Date: Thu, 10 May 2018 23:46:57 +0100 Subject: [PATCH 27/40] Lift pure_wrt_drop to GenericParamDef --- src/librustc/ich/impls_ty.rs | 8 ++--- src/librustc/infer/anon_types/mod.rs | 2 +- src/librustc/middle/resolve_lifetime.rs | 2 +- src/librustc/traits/auto_trait.rs | 2 +- src/librustc/traits/error_reporting.rs | 2 +- src/librustc/traits/on_unimplemented.rs | 2 +- src/librustc/ty/mod.rs | 39 +++++++-------------- src/librustc/ty/subst.rs | 2 +- src/librustc/ty/util.rs | 4 +-- src/librustc/util/ppaux.rs | 4 +-- src/librustc_privacy/lib.rs | 4 +-- src/librustc_typeck/check/compare_method.rs | 4 +-- src/librustc_typeck/check/wfcheck.rs | 4 +-- src/librustc_typeck/collect.rs | 13 ++++--- src/librustc_typeck/impl_wf_check.rs | 4 +-- src/librustdoc/clean/auto_trait.rs | 2 +- src/librustdoc/clean/mod.rs | 2 +- 17 files changed, 40 insertions(+), 60 deletions(-) diff --git a/src/librustc/ich/impls_ty.rs b/src/librustc/ich/impls_ty.rs index e06d22607b75e..31dce2a14c2b7 100644 --- a/src/librustc/ich/impls_ty.rs +++ b/src/librustc/ich/impls_ty.rs @@ -754,7 +754,7 @@ impl<'a> HashStable> for ty::Generics { } impl_stable_hash_for!(enum ty::GenericParamDefKind { - Lifetime(lt), + Lifetime, Type(ty) }); @@ -762,17 +762,13 @@ impl_stable_hash_for!(struct ty::GenericParamDef { name, def_id, index, + pure_wrt_drop, kind }); -impl_stable_hash_for!(struct ty::LifetimeParamDef { - pure_wrt_drop -}); - impl_stable_hash_for!(struct ty::TypeParamDef { has_default, object_lifetime_default, - pure_wrt_drop, synthetic }); diff --git a/src/librustc/infer/anon_types/mod.rs b/src/librustc/infer/anon_types/mod.rs index 95727d10b1894..d681e2e3d34b9 100644 --- a/src/librustc/infer/anon_types/mod.rs +++ b/src/librustc/infer/anon_types/mod.rs @@ -315,7 +315,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { let mut least_region = None; for param in &abstract_type_generics.params { match param.kind { - GenericParamDefKind::Lifetime(_) => {} + GenericParamDefKind::Lifetime => {} _ => continue } // Get the value supplied for this region from the substs. diff --git a/src/librustc/middle/resolve_lifetime.rs b/src/librustc/middle/resolve_lifetime.rs index bed5ee91800a6..900fbdfdeadb3 100644 --- a/src/librustc/middle/resolve_lifetime.rs +++ b/src/librustc/middle/resolve_lifetime.rs @@ -1666,7 +1666,7 @@ impl<'a, 'tcx> LifetimeContext<'a, 'tcx> { GenericParamDefKind::Type(ty) => { Some(ty.object_lifetime_default) } - GenericParamDefKind::Lifetime(_) => None, + GenericParamDefKind::Lifetime => None, } }) .collect() diff --git a/src/librustc/traits/auto_trait.rs b/src/librustc/traits/auto_trait.rs index 4bb5387efb352..227cba40d1463 100644 --- a/src/librustc/traits/auto_trait.rs +++ b/src/librustc/traits/auto_trait.rs @@ -226,7 +226,7 @@ impl<'a, 'tcx> AutoTraitFinder<'a, 'tcx> { .iter() .filter_map(|param| { match param.kind { - ty::GenericParamDefKind::Lifetime(_) => Some(param.name.to_string()), + ty::GenericParamDefKind::Lifetime => Some(param.name.to_string()), _ => None } }) diff --git a/src/librustc/traits/error_reporting.rs b/src/librustc/traits/error_reporting.rs index 9d71fe6f2d736..f56720328b299 100644 --- a/src/librustc/traits/error_reporting.rs +++ b/src/librustc/traits/error_reporting.rs @@ -386,7 +386,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { let ty = trait_ref.substs.type_for_def(¶m); ty.to_string() }, - GenericParamDefKind::Lifetime(_) => continue, + GenericParamDefKind::Lifetime => continue, }; flags.push((name.clone(), Some(value.clone()))); } diff --git a/src/librustc/traits/on_unimplemented.rs b/src/librustc/traits/on_unimplemented.rs index 1980fbbe3ed75..ff10c430f7be8 100644 --- a/src/librustc/traits/on_unimplemented.rs +++ b/src/librustc/traits/on_unimplemented.rs @@ -293,7 +293,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { Some((param.name.to_string(), trait_ref.substs.type_for_def(¶m).to_string())) }, - GenericParamDefKind::Lifetime(_) => None + GenericParamDefKind::Lifetime => None } }).collect::>(); diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index c3e9ffec9a009..42aed9940ad5c 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -713,23 +713,9 @@ pub struct FloatVarValue(pub ast::FloatTy); pub struct TypeParamDef { pub has_default: bool, pub object_lifetime_default: ObjectLifetimeDefault, - - /// `pure_wrt_drop`, set by the (unsafe) `#[may_dangle]` attribute - /// on generic parameter `T`, asserts data behind the parameter - /// `T` won't be accessed during the parent type's `Drop` impl. - pub pure_wrt_drop: bool, - pub synthetic: Option, } -#[derive(Copy, Clone, Debug, RustcEncodable, RustcDecodable)] -pub struct LifetimeParamDef { - /// `pure_wrt_drop`, set by the (unsafe) `#[may_dangle]` attribute - /// on generic parameter `'a`, asserts data of lifetime `'a` - /// won't be accessed during the parent type's `Drop` impl. - pub pure_wrt_drop: bool, -} - impl ty::EarlyBoundRegion { pub fn to_bound_region(&self) -> ty::BoundRegion { ty::BoundRegion::BrNamed(self.def_id, self.name) @@ -738,7 +724,7 @@ impl ty::EarlyBoundRegion { #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] pub enum GenericParamDefKind { - Lifetime(LifetimeParamDef), + Lifetime, Type(TypeParamDef), } @@ -747,17 +733,16 @@ pub struct GenericParamDef { pub name: InternedString, pub def_id: DefId, pub index: u32, + + /// `pure_wrt_drop`, set by the (unsafe) `#[may_dangle]` attribute + /// on generic parameter `'a`/`T`, asserts data behind the parameter + /// `'a`/`T` won't be accessed during the parent type's `Drop` impl. + pub pure_wrt_drop: bool, + pub kind: GenericParamDefKind, } impl GenericParamDef { - pub fn to_lifetime(&self) -> LifetimeParamDef { - match self.kind { - GenericParamDefKind::Lifetime(lt) => lt, - _ => bug!("cannot convert a non-lifetime to a lifetime") - } - } - pub fn to_type(&self) -> TypeParamDef { match self.kind { GenericParamDefKind::Type(ty) => ty, @@ -767,7 +752,7 @@ impl GenericParamDef { pub fn to_early_bound_region_data(&self) -> ty::EarlyBoundRegion { match self.kind { - GenericParamDefKind::Lifetime(_) => { + GenericParamDefKind::Lifetime => { ty::EarlyBoundRegion { def_id: self.def_id, index: self.index, @@ -780,7 +765,7 @@ impl GenericParamDef { pub fn to_bound_region(&self) -> ty::BoundRegion { match self.kind { - GenericParamDefKind::Lifetime(_) => { + GenericParamDefKind::Lifetime => { self.to_early_bound_region_data().to_bound_region() } _ => bug!("cannot convert a non-lifetime parameter def to an early bound region") @@ -827,7 +812,7 @@ impl<'a, 'gcx, 'tcx> Generics { for param in self.params.iter() { match param.kind { - GenericParamDefKind::Lifetime(_) => param_counts.lifetimes += 1, + GenericParamDefKind::Lifetime => param_counts.lifetimes += 1, GenericParamDefKind::Type(_) => param_counts.types += 1, }; } @@ -839,7 +824,7 @@ impl<'a, 'gcx, 'tcx> Generics { for param in self.params.iter() { match param.kind { GenericParamDefKind::Type(_) => return true, - GenericParamDefKind::Lifetime(_) => {} + GenericParamDefKind::Lifetime => {} } } if let Some(parent_def_id) = self.parent { @@ -858,7 +843,7 @@ impl<'a, 'gcx, 'tcx> Generics { if let Some(index) = param.index.checked_sub(self.parent_count as u32) { let param = &self.params[index as usize]; match param.kind { - ty::GenericParamDefKind::Lifetime(_) => param, + ty::GenericParamDefKind::Lifetime => param, _ => bug!("expected region parameter, but found another generic parameter") } } else { diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index a14045b43f2eb..d4db2ae481a27 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -243,7 +243,7 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { FT: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { for param in &defs.params { let kind = match param.kind { - ty::GenericParamDefKind::Lifetime(_) => mk_region(param, substs).into(), + ty::GenericParamDefKind::Lifetime => mk_region(param, substs).into(), ty::GenericParamDefKind::Type(_) => mk_type(param, substs).into(), }; assert_eq!(param.index as usize, substs.len()); diff --git a/src/librustc/ty/util.rs b/src/librustc/ty/util.rs index db11f4659723b..fdd0754730feb 100644 --- a/src/librustc/ty/util.rs +++ b/src/librustc/ty/util.rs @@ -505,12 +505,12 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { .filter(|&(_, &k)| { match k.unpack() { UnpackedKind::Lifetime(&ty::RegionKind::ReEarlyBound(ref ebr)) => { - !impl_generics.region_param(ebr, self).to_lifetime().pure_wrt_drop + !impl_generics.region_param(ebr, self).pure_wrt_drop } UnpackedKind::Type(&ty::TyS { sty: ty::TypeVariants::TyParam(ref pt), .. }) => { - !impl_generics.type_param(pt, self).to_type().pure_wrt_drop + !impl_generics.type_param(pt, self).pure_wrt_drop } UnpackedKind::Lifetime(_) | UnpackedKind::Type(_) => { // not a type or region param - this should be reported diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index ca939b161d21e..b3e840ae025dd 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -340,7 +340,7 @@ impl PrintContext { generics.params.iter().rev().filter_map(|param| { match param.kind { GenericParamDefKind::Type(ty) => Some((param.def_id, ty.has_default)), - GenericParamDefKind::Lifetime(_) => None, + GenericParamDefKind::Lifetime => None, } }); if let Some(last_ty) = type_params.next() { @@ -606,7 +606,7 @@ define_print! { impl fmt::Debug for ty::GenericParamDef { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { let type_name = match self.kind { - ty::GenericParamDefKind::Lifetime(_) => "Lifetime", + ty::GenericParamDefKind::Lifetime => "Lifetime", ty::GenericParamDefKind::Type(_) => "Type", }; write!(f, "{}({}, {:?}, {})", diff --git a/src/librustc_privacy/lib.rs b/src/librustc_privacy/lib.rs index 929030e832e94..6e9b03cd2a9c6 100644 --- a/src/librustc_privacy/lib.rs +++ b/src/librustc_privacy/lib.rs @@ -406,7 +406,7 @@ impl<'b, 'a, 'tcx> ReachEverythingInTheInterfaceVisitor<'b, 'a, 'tcx> { self.ev.tcx.type_of(param.def_id).visit_with(self); } } - GenericParamDefKind::Lifetime(_) => {} + GenericParamDefKind::Lifetime => {} } } self @@ -1347,7 +1347,7 @@ impl<'a, 'tcx: 'a> SearchInterfaceForPrivateItemsVisitor<'a, 'tcx> { self.tcx.type_of(param.def_id).visit_with(self); } } - GenericParamDefKind::Lifetime(_) => {} + GenericParamDefKind::Lifetime => {} } } self diff --git a/src/librustc_typeck/check/compare_method.rs b/src/librustc_typeck/check/compare_method.rs index 11f421da71474..86913fcadfa67 100644 --- a/src/librustc_typeck/check/compare_method.rs +++ b/src/librustc_typeck/check/compare_method.rs @@ -731,13 +731,13 @@ fn compare_synthetic_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let impl_m_type_params = impl_m_generics.params.iter().filter_map(|param| { match param.kind { GenericParamDefKind::Type(_) => Some(param), - GenericParamDefKind::Lifetime(_) => None, + GenericParamDefKind::Lifetime => None, } }); let trait_m_type_params = trait_m_generics.params.iter().filter_map(|param| { match param.kind { GenericParamDefKind::Type(_) => Some(param), - GenericParamDefKind::Lifetime(_) => None, + GenericParamDefKind::Lifetime => None, } }); for (impl_ty, trait_ty) in impl_m_type_params.zip(trait_m_type_params) { diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index 740a3dfcac973..a96652f953e99 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -652,7 +652,7 @@ fn reject_shadowing_parameters(tcx: TyCtxt, def_id: DefId) { parent.params.iter() .flat_map(|param| { match param.kind { - GenericParamDefKind::Lifetime(_) => None, + GenericParamDefKind::Lifetime => None, GenericParamDefKind::Type(_) => Some((param.name, param.def_id)), } }) @@ -661,7 +661,7 @@ fn reject_shadowing_parameters(tcx: TyCtxt, def_id: DefId) { for method_param in generics.params.iter() { match method_param.kind { // Shadowing is checked in resolve_lifetime. - GenericParamDefKind::Lifetime(_) => continue, + GenericParamDefKind::Lifetime => continue, _ => {}, }; if impl_params.contains_key(&method_param.name) { diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 3be702189fb69..1cc2730158f82 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -844,10 +844,10 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, index: 0, name: keywords::SelfType.name().as_interned_str(), def_id: tcx.hir.local_def_id(param_id), + pure_wrt_drop: false, kind: ty::GenericParamDefKind::Type(ty::TypeParamDef { has_default: false, object_lifetime_default: rl::Set1::Empty, - pure_wrt_drop: false, synthetic: None, }), }); @@ -892,9 +892,8 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, name: l.lifetime.name.name().as_interned_str(), index: own_start + i as u32, def_id: tcx.hir.local_def_id(l.lifetime.id), - kind: ty::GenericParamDefKind::Lifetime(ty::LifetimeParamDef { - pure_wrt_drop: l.pure_wrt_drop, - }), + pure_wrt_drop: l.pure_wrt_drop, + kind: ty::GenericParamDefKind::Lifetime, } }).collect::>(); @@ -923,11 +922,11 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, index: type_start + i as u32, name: p.name.as_interned_str(), def_id: tcx.hir.local_def_id(p.id), + pure_wrt_drop: p.pure_wrt_drop, kind: ty::GenericParamDefKind::Type(ty::TypeParamDef { has_default: p.default.is_some(), object_lifetime_default: object_lifetime_defaults.as_ref().map_or(rl::Set1::Empty, |o| o[i]), - pure_wrt_drop: p.pure_wrt_drop, synthetic: p.synthetic, }), } @@ -948,10 +947,10 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, index: type_start + i as u32, name: Symbol::intern(arg).as_interned_str(), def_id, + pure_wrt_drop: false, kind: ty::GenericParamDefKind::Type(ty::TypeParamDef { has_default: false, object_lifetime_default: rl::Set1::Empty, - pure_wrt_drop: false, synthetic: None, }), }); @@ -963,10 +962,10 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, index: type_start + i, name: Symbol::intern("").as_interned_str(), def_id, + pure_wrt_drop: false, kind: ty::GenericParamDefKind::Type(ty::TypeParamDef { has_default: false, object_lifetime_default: rl::Set1::Empty, - pure_wrt_drop: false, synthetic: None, }), } diff --git a/src/librustc_typeck/impl_wf_check.rs b/src/librustc_typeck/impl_wf_check.rs index f3645142e4b61..ef699b201a51a 100644 --- a/src/librustc_typeck/impl_wf_check.rs +++ b/src/librustc_typeck/impl_wf_check.rs @@ -125,7 +125,7 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, report_unused_parameter(tcx, hir_ty.span, "type", ¶m_ty.to_string()); } } - (&ty::GenericParamDefKind::Lifetime(_), hir::GenericParam::Lifetime(hir_lt)) => { + (&ty::GenericParamDefKind::Lifetime, hir::GenericParam::Lifetime(hir_lt)) => { let param = ctp::Parameter::from(ty_param.to_early_bound_region_data()); if lifetimes_in_associated_types.contains(¶m) && // (*) !input_parameters.contains(¶m) { @@ -134,7 +134,7 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } } (&ty::GenericParamDefKind::Type(_), _) => continue, - (&ty::GenericParamDefKind::Lifetime(_), _) => continue, + (&ty::GenericParamDefKind::Lifetime, _) => continue, } } diff --git a/src/librustdoc/clean/auto_trait.rs b/src/librustdoc/clean/auto_trait.rs index 88784aab90e0e..d7646ce7bfc5c 100644 --- a/src/librustdoc/clean/auto_trait.rs +++ b/src/librustdoc/clean/auto_trait.rs @@ -229,7 +229,7 @@ impl<'a, 'tcx, 'rcx> AutoTraitFinder<'a, 'tcx, 'rcx> { for param in generics.params.iter() { match param.kind { - ty::GenericParamDefKind::Lifetime(_) => { + ty::GenericParamDefKind::Lifetime => { let name = if param.name == "" { hir::LifetimeName::Static } else { diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 69999eb69b0b2..621ec641ee036 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1855,7 +1855,7 @@ impl<'a, 'tcx> Clean for (&'a ty::Generics, params: gens.params .iter() .flat_map(|param| { - if let ty::GenericParamDefKind::Lifetime(_) = param.kind { + if let ty::GenericParamDefKind::Lifetime = param.kind { Some(GenericParamDef::Lifetime(param.clean(cx))) } else { None From 365c8c3704fd65fa2dcb112c19eabec44696fea1 Mon Sep 17 00:00:00 2001 From: varkor Date: Fri, 11 May 2018 00:29:38 +0100 Subject: [PATCH 28/40] Remove GenericParamDef::to_type --- src/librustc/ty/mod.rs | 7 ------- src/librustc_typeck/astconv.rs | 21 ++++++++++++++------- src/librustc_typeck/check/compare_method.rs | 13 +++++++------ src/librustc_typeck/check/mod.rs | 9 +++++++-- src/librustc_typeck/check/wfcheck.rs | 7 ++++++- 5 files changed, 34 insertions(+), 23 deletions(-) diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 42aed9940ad5c..aef8e7f5eea75 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -743,13 +743,6 @@ pub struct GenericParamDef { } impl GenericParamDef { - pub fn to_type(&self) -> TypeParamDef { - match self.kind { - GenericParamDefKind::Type(ty) => ty, - _ => bug!("cannot convert a non-type to a type") - } - } - pub fn to_early_bound_region_data(&self) -> ty::EarlyBoundRegion { match self.kind { GenericParamDefKind::Lifetime => { diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index e4d5ce054577d..6c64d1ae02136 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -20,7 +20,7 @@ use middle::resolve_lifetime as rl; use namespace::Namespace; use rustc::ty::subst::{Kind, UnpackedKind, Subst, Substs}; use rustc::traits; -use rustc::ty::{self, RegionKind, Ty, TyCtxt, ToPredicate, TypeFoldable}; +use rustc::ty::{self, RegionKind, Ty, TyCtxt, GenericParamDefKind, ToPredicate, TypeFoldable}; use rustc::ty::wf::object_region_bounds; use rustc_target::spec::abi; use std::slice; @@ -246,11 +246,13 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { let is_object = self_ty.map_or(false, |ty| ty.sty == TRAIT_OBJECT_DUMMY_SELF); let default_needs_object_self = |param: &ty::GenericParamDef| { - if is_object && param.to_type().has_default { - if tcx.at(span).type_of(param.def_id).has_self_ty() { - // There is no suitable inference default for a type parameter - // that references self, in an object type. - return true; + if let GenericParamDefKind::Type(ty) = param.kind { + if is_object && ty.has_default { + if tcx.at(span).type_of(param.def_id).has_self_ty() { + // There is no suitable inference default for a type parameter + // that references self, in an object type. + return true; + } } } @@ -272,6 +274,11 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { return ty; } + let has_default = match def.kind { + GenericParamDefKind::Type(ty) => ty.has_default, + _ => unreachable!() + }; + let i = i - (param_counts.lifetimes + own_self); if i < num_types_provided { // A provided type parameter. @@ -284,7 +291,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { self.ty_infer(span) }; ty_var - } else if def.to_type().has_default { + } else if has_default { // No type parameter provided, but a default exists. // If we are converting an object type, then the diff --git a/src/librustc_typeck/check/compare_method.rs b/src/librustc_typeck/check/compare_method.rs index 86913fcadfa67..355440769cdf0 100644 --- a/src/librustc_typeck/check/compare_method.rs +++ b/src/librustc_typeck/check/compare_method.rs @@ -730,21 +730,22 @@ fn compare_synthetic_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let trait_m_generics = tcx.generics_of(trait_m.def_id); let impl_m_type_params = impl_m_generics.params.iter().filter_map(|param| { match param.kind { - GenericParamDefKind::Type(_) => Some(param), + GenericParamDefKind::Type(ty) => Some((param.def_id, ty.synthetic)), GenericParamDefKind::Lifetime => None, } }); let trait_m_type_params = trait_m_generics.params.iter().filter_map(|param| { match param.kind { - GenericParamDefKind::Type(_) => Some(param), + GenericParamDefKind::Type(ty) => Some((param.def_id, ty.synthetic)), GenericParamDefKind::Lifetime => None, } }); - for (impl_ty, trait_ty) in impl_m_type_params.zip(trait_m_type_params) { - if impl_ty.to_type().synthetic != trait_ty.to_type().synthetic { - let impl_node_id = tcx.hir.as_local_node_id(impl_ty.def_id).unwrap(); + for ((impl_def_id, impl_synthetic), + (trait_def_id, trait_synthetic)) in impl_m_type_params.zip(trait_m_type_params) { + if impl_synthetic != trait_synthetic { + let impl_node_id = tcx.hir.as_local_node_id(impl_def_id).unwrap(); let impl_span = tcx.hir.span(impl_node_id); - let trait_span = tcx.def_span(trait_ty.def_id); + let trait_span = tcx.def_span(trait_def_id); let mut err = struct_span_err!(tcx.sess, impl_span, E0643, diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 256e44a2d6b02..a6b072f3213d9 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -96,7 +96,7 @@ use rustc::middle::region; use rustc::mir::interpret::{GlobalId}; use rustc::ty::subst::{Kind, Subst, Substs}; use rustc::traits::{self, ObligationCause, ObligationCauseCode, TraitEngine}; -use rustc::ty::{self, Ty, TyCtxt, Visibility, ToPredicate}; +use rustc::ty::{self, Ty, TyCtxt, GenericParamDefKind, Visibility, ToPredicate}; use rustc::ty::adjustment::{Adjust, Adjustment, AllowTwoPhase, AutoBorrow, AutoBorrowMutability}; use rustc::ty::fold::TypeFoldable; use rustc::ty::maps::Providers; @@ -4802,10 +4802,15 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { i -= generics.param_counts().lifetimes; } + let has_default = match def.kind { + GenericParamDefKind::Type(ty) => ty.has_default, + _ => unreachable!() + }; + if let Some(ast_ty) = types.get(i) { // A provided type parameter. self.to_ty(ast_ty) - } else if !infer_types && def.to_type().has_default { + } else if !infer_types && has_default { // No type parameter provided, but a default exists. let default = self.tcx.type_of(def.def_id); self.normalize_ty( diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index a96652f953e99..a37137c68cb76 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -371,7 +371,12 @@ fn check_where_clauses<'a, 'gcx, 'fcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'gcx>, let generics = tcx.generics_of(def_id); let is_our_default = |def: &ty::GenericParamDef| { - def.to_type().has_default && def.index >= generics.parent_count as u32 + match def.kind { + GenericParamDefKind::Type(ty) => { + ty.has_default && def.index >= generics.parent_count as u32 + } + _ => unreachable!() + } }; // Check that concrete defaults are well-formed. See test `type-check-defaults.rs`. From fd8e284a206a35e4247a04f909a0960d89331ab0 Mon Sep 17 00:00:00 2001 From: varkor Date: Fri, 11 May 2018 00:30:34 +0100 Subject: [PATCH 29/40] Rename param_counts to own_counts --- src/librustc/hir/lowering.rs | 2 +- src/librustc/traits/object_safety.rs | 2 +- src/librustc/ty/mod.rs | 10 +++++----- src/librustc/util/ppaux.rs | 18 +++++++++--------- src/librustc_mir/monomorphize/collector.rs | 2 +- src/librustc_mir/transform/check_unsafety.rs | 2 +- src/librustc_typeck/astconv.rs | 8 ++++---- src/librustc_typeck/check/compare_method.rs | 8 ++++---- src/librustc_typeck/check/intrinsic.rs | 4 ++-- src/librustc_typeck/check/method/confirm.rs | 4 ++-- src/librustc_typeck/check/mod.rs | 10 +++++----- 11 files changed, 35 insertions(+), 35 deletions(-) diff --git a/src/librustc/hir/lowering.rs b/src/librustc/hir/lowering.rs index 628b871ed5135..be9c5d2d334ae 100644 --- a/src/librustc/hir/lowering.rs +++ b/src/librustc/hir/lowering.rs @@ -1461,7 +1461,7 @@ impl<'a> LoweringContext<'a> { assert!(!def_id.is_local()); let item_generics = self.cstore.item_generics_cloned_untracked(def_id, self.sess); - let n = item_generics.param_counts().lifetimes; + let n = item_generics.own_counts().lifetimes; self.type_def_lifetime_params.insert(def_id, n); n }); diff --git a/src/librustc/traits/object_safety.rs b/src/librustc/traits/object_safety.rs index 7c68d5522fcc3..6c67c10dc69cf 100644 --- a/src/librustc/traits/object_safety.rs +++ b/src/librustc/traits/object_safety.rs @@ -284,7 +284,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { } // We can't monomorphize things like `fn foo(...)`. - if self.generics_of(method.def_id).param_counts().types != 0 { + if self.generics_of(method.def_id).own_counts().types != 0 { return Some(MethodViolationCode::Generic); } diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index aef8e7f5eea75..fc085cbd4f844 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -794,23 +794,23 @@ impl<'a, 'gcx, 'tcx> Generics { self.parent_count + self.params.len() } - pub fn param_counts(&self) -> GenericParamCount { + pub fn own_counts(&self) -> GenericParamCount { // We could cache this as a property of `GenericParamCount`, but // the aim is to refactor this away entirely eventually and the // presence of this method will be a constant reminder. - let mut param_counts = GenericParamCount { + let mut own_counts = GenericParamCount { lifetimes: 0, types: 0, }; for param in self.params.iter() { match param.kind { - GenericParamDefKind::Lifetime => param_counts.lifetimes += 1, - GenericParamDefKind::Type(_) => param_counts.types += 1, + GenericParamDefKind::Lifetime => own_counts.lifetimes += 1, + GenericParamDefKind::Type(_) => own_counts.types += 1, }; } - param_counts + own_counts } pub fn requires_monomorphization(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index b3e840ae025dd..7044404e655b9 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -257,7 +257,7 @@ impl PrintContext { let verbose = self.is_verbose; let mut num_supplied_defaults = 0; let mut has_self = false; - let mut param_counts = GenericParamCount { + let mut own_counts = GenericParamCount { lifetimes: 0, types: 0, }; @@ -306,7 +306,7 @@ impl PrintContext { } } let mut generics = tcx.generics_of(item_def_id); - let child_param_counts = generics.param_counts(); + let child_own_counts = generics.own_counts(); let mut path_def_id = did; has_self = generics.has_self; @@ -314,9 +314,9 @@ impl PrintContext { if let Some(def_id) = generics.parent { // Methods. assert!(is_value_path); - child_types = child_param_counts.types; + child_types = child_own_counts.types; generics = tcx.generics_of(def_id); - param_counts = generics.param_counts(); + own_counts = generics.own_counts(); if has_self { print!(f, self, write("<"), print_display(substs.type_at(0)), write(" as "))?; @@ -331,7 +331,7 @@ impl PrintContext { assert_eq!(has_self, false); } else { // Types and traits. - param_counts = child_param_counts; + own_counts = child_own_counts; } } @@ -415,10 +415,10 @@ impl PrintContext { Ok(()) }; - print_regions(f, "<", 0, param_counts.lifetimes)?; + print_regions(f, "<", 0, own_counts.lifetimes)?; let tps = substs.types() - .take(param_counts.types - num_supplied_defaults) + .take(own_counts.types - num_supplied_defaults) .skip(has_self as usize); for ty in tps { @@ -450,10 +450,10 @@ impl PrintContext { write!(f, "::{}", item_name)?; } - print_regions(f, "::<", param_counts.lifetimes, usize::MAX)?; + print_regions(f, "::<", own_counts.lifetimes, usize::MAX)?; // FIXME: consider being smart with defaults here too - for ty in substs.types().skip(param_counts.types) { + for ty in substs.types().skip(own_counts.types) { start_or_continue(f, "::<", ", ")?; ty.print_display(f, self)?; } diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index 92b4babe8a3b2..f8f6bec33a2ab 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -1108,7 +1108,7 @@ fn create_mono_items_for_default_impls<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, continue; } - if tcx.generics_of(method.def_id).param_counts().types != 0 { + if tcx.generics_of(method.def_id).own_counts().types != 0 { continue; } diff --git a/src/librustc_mir/transform/check_unsafety.rs b/src/librustc_mir/transform/check_unsafety.rs index b65353e449f68..fc3764e4f49a5 100644 --- a/src/librustc_mir/transform/check_unsafety.rs +++ b/src/librustc_mir/transform/check_unsafety.rs @@ -357,7 +357,7 @@ fn unsafe_derive_on_repr_packed<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: D // FIXME: when we make this a hard error, this should have its // own error code. - let message = if tcx.generics_of(def_id).param_counts().types != 0 { + let message = if tcx.generics_of(def_id).own_counts().types != 0 { format!("#[derive] can't be used on a #[repr(packed)] struct with \ type parameters (error E0133)") } else { diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index 6c64d1ae02136..50d76d8179057 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -208,9 +208,9 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { // region with the current anon region binding (in other words, // whatever & would get replaced with). let decl_generics = tcx.generics_of(def_id); - let param_counts = decl_generics.param_counts(); + let own_counts = decl_generics.own_counts(); let num_types_provided = parameters.types.len(); - let expected_num_region_params = param_counts.lifetimes; + let expected_num_region_params = own_counts.lifetimes; let supplied_num_region_params = parameters.lifetimes.len(); if expected_num_region_params != supplied_num_region_params { report_lifetime_number_error(tcx, span, @@ -223,7 +223,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { // Check the number of type parameters supplied by the user. let own_self = self_ty.is_some() as usize; - let ty_param_defs = param_counts.types - own_self; + let ty_param_defs = own_counts.types - own_self; if !infer_types || num_types_provided > ty_param_defs { let type_params_without_defaults = { let mut count = 0; @@ -279,7 +279,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { _ => unreachable!() }; - let i = i - (param_counts.lifetimes + own_self); + let i = i - (own_counts.lifetimes + own_self); if i < num_types_provided { // A provided type parameter. self.ast_ty_to_ty(¶meters.types[i]) diff --git a/src/librustc_typeck/check/compare_method.rs b/src/librustc_typeck/check/compare_method.rs index 355440769cdf0..ba950f90d0a02 100644 --- a/src/librustc_typeck/check/compare_method.rs +++ b/src/librustc_typeck/check/compare_method.rs @@ -357,8 +357,8 @@ fn check_region_bounds_on_impl_method<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, trait_to_skol_substs: &Substs<'tcx>) -> Result<(), ErrorReported> { let span = tcx.sess.codemap().def_span(span); - let trait_params = trait_generics.param_counts().lifetimes; - let impl_params = impl_generics.param_counts().lifetimes; + let trait_params = trait_generics.own_counts().lifetimes; + let impl_params = impl_generics.own_counts().lifetimes; debug!("check_region_bounds_on_impl_method: \ trait_generics={:?} \ @@ -574,8 +574,8 @@ fn compare_number_of_generics<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, -> Result<(), ErrorReported> { let impl_m_generics = tcx.generics_of(impl_m.def_id); let trait_m_generics = tcx.generics_of(trait_m.def_id); - let num_impl_m_type_params = impl_m_generics.param_counts().types; - let num_trait_m_type_params = trait_m_generics.param_counts().types; + let num_impl_m_type_params = impl_m_generics.own_counts().types; + let num_trait_m_type_params = trait_m_generics.own_counts().types; if num_impl_m_type_params != num_trait_m_type_params { let impl_m_node_id = tcx.hir.as_local_node_id(impl_m.def_id).unwrap(); let impl_m_item = tcx.hir.expect_impl_item(impl_m_node_id); diff --git a/src/librustc_typeck/check/intrinsic.rs b/src/librustc_typeck/check/intrinsic.rs index d852a865174fb..97e4a35ea4762 100644 --- a/src/librustc_typeck/check/intrinsic.rs +++ b/src/librustc_typeck/check/intrinsic.rs @@ -45,7 +45,7 @@ fn equate_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } } - let i_n_tps = tcx.generics_of(def_id).param_counts().types; + let i_n_tps = tcx.generics_of(def_id).own_counts().types; if i_n_tps != n_tps { let span = match it.node { hir::ForeignItemFn(_, _, ref generics) => generics.span, @@ -346,7 +346,7 @@ pub fn check_platform_intrinsic_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }; let def_id = tcx.hir.local_def_id(it.id); - let i_n_tps = tcx.generics_of(def_id).param_counts().types; + let i_n_tps = tcx.generics_of(def_id).own_counts().types; let name = it.name.as_str(); let (n_tps, inputs, output) = match &*name { diff --git a/src/librustc_typeck/check/method/confirm.rs b/src/librustc_typeck/check/method/confirm.rs index cfb8441231706..9928ef549ff70 100644 --- a/src/librustc_typeck/check/method/confirm.rs +++ b/src/librustc_typeck/check/method/confirm.rs @@ -316,7 +316,7 @@ impl<'a, 'gcx, 'tcx> ConfirmContext<'a, 'gcx, 'tcx> { // parameters from the type and those from the method. assert_eq!(method_generics.parent_count, parent_substs.len()); let provided = &segment.parameters; - let param_counts = method_generics.param_counts(); + let own_counts = method_generics.own_counts(); Substs::for_item(self.tcx, pick.item.def_id, |def, _| { let i = def.index as usize; if i < parent_substs.len() { @@ -334,7 +334,7 @@ impl<'a, 'gcx, 'tcx> ConfirmContext<'a, 'gcx, 'tcx> { } else if let Some(ast_ty) = provided.as_ref().and_then(|p| { let idx = - i - parent_substs.len() - param_counts.lifetimes; + i - parent_substs.len() - own_counts.lifetimes; p.types.get(idx) }) { diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index a6b072f3213d9..2ff760726d253 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -1239,7 +1239,7 @@ pub fn check_item_type<'a,'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, it: &'tcx hir::Item } else { for item in &m.items { let generics = tcx.generics_of(tcx.hir.local_def_id(item.id)); - if generics.params.len() - generics.param_counts().lifetimes != 0 { + if generics.params.len() - generics.own_counts().lifetimes != 0 { let mut err = struct_span_err!(tcx.sess, item.span, E0044, "foreign items may not have type parameters"); err.span_label(item.span, "can't have type parameters"); @@ -4799,7 +4799,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // Skip over the lifetimes in the same segment. if let Some((_, generics)) = segment { - i -= generics.param_counts().lifetimes; + i -= generics.own_counts().lifetimes; } let has_default = match def.kind { @@ -4925,10 +4925,10 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // Check provided parameters. let (ty_req_len, accepted, lt_req_len) = segment.map_or((0, 0, 0), |(_, generics)| { - let param_counts = generics.param_counts(); + let own_counts = generics.own_counts(); let own_self = (generics.parent.is_none() && generics.has_self) as usize; - let type_params = param_counts.types - own_self; + let type_params = own_counts.types - own_self; let type_params_without_defaults = { let mut count = 0; for param in generics.params.iter() { @@ -4943,7 +4943,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { let type_params_barring_defaults = type_params_without_defaults - own_self; - (type_params_barring_defaults, type_params, param_counts.lifetimes) + (type_params_barring_defaults, type_params, own_counts.lifetimes) }); if types.len() > accepted { From fe1f651e4c28bb39da739f1433d94c6ed6caec82 Mon Sep 17 00:00:00 2001 From: varkor Date: Fri, 11 May 2018 01:56:05 +0100 Subject: [PATCH 30/40] Review refactoring --- src/librustc/traits/error_reporting.rs | 2 +- src/librustc/traits/on_unimplemented.rs | 11 ++++---- src/librustc/util/ppaux.rs | 32 +++++++++++------------ src/librustc_typeck/collect.rs | 21 +++++++-------- src/librustc_typeck/impl_wf_check.rs | 34 ++++++++++++------------- 5 files changed, 48 insertions(+), 52 deletions(-) diff --git a/src/librustc/traits/error_reporting.rs b/src/librustc/traits/error_reporting.rs index f56720328b299..18c0020a2b49b 100644 --- a/src/librustc/traits/error_reporting.rs +++ b/src/librustc/traits/error_reporting.rs @@ -380,7 +380,6 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { } for param in generics.params.iter() { - let name = param.name.to_string(); let value = match param.kind { GenericParamDefKind::Type(_) => { let ty = trait_ref.substs.type_for_def(¶m); @@ -388,6 +387,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { }, GenericParamDefKind::Lifetime => continue, }; + let name = param.name.to_string(); flags.push((name.clone(), Some(value.clone()))); } diff --git a/src/librustc/traits/on_unimplemented.rs b/src/librustc/traits/on_unimplemented.rs index ff10c430f7be8..bc558c2933cdc 100644 --- a/src/librustc/traits/on_unimplemented.rs +++ b/src/librustc/traits/on_unimplemented.rs @@ -288,13 +288,14 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let trait_str = tcx.item_path_str(trait_ref.def_id); let generics = tcx.generics_of(trait_ref.def_id); let generic_map = generics.params.iter().filter_map(|param| { - match param.kind { + let value = match param.kind { GenericParamDefKind::Type(_) => { - Some((param.name.to_string(), - trait_ref.substs.type_for_def(¶m).to_string())) + trait_ref.substs.type_for_def(¶m).to_string() }, - GenericParamDefKind::Lifetime => None - } + GenericParamDefKind::Lifetime => return None + }; + let name = param.name.to_string(); + Some((name, value)) }).collect::>(); let parser = Parser::new(&self.0); diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index 7044404e655b9..eaae874635f62 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -25,7 +25,6 @@ use util::nodemap::FxHashSet; use std::cell::Cell; use std::fmt; use std::usize; -use std::iter; use rustc_data_structures::indexed_vec::Idx; use rustc_target::spec::abi::Abi; @@ -342,23 +341,22 @@ impl PrintContext { GenericParamDefKind::Type(ty) => Some((param.def_id, ty.has_default)), GenericParamDefKind::Lifetime => None, } - }); - if let Some(last_ty) = type_params.next() { - let (_, has_default) = last_ty; - if has_default { - if let Some(substs) = tcx.lift(&substs) { - let mut types = substs.types().rev().skip(child_types); - let zipped = iter::once((last_ty, types.next().unwrap())) - .chain(type_params.zip(types)); - for ((def_id, has_default), actual) in zipped { - if !has_default { - break; - } - if tcx.type_of(def_id).subst(tcx, substs) != actual { - break; - } - num_supplied_defaults += 1; + }).peekable(); + let has_default = { + let has_default = type_params.peek().map(|(_, has_default)| has_default); + *has_default.unwrap_or(&false) + }; + if has_default { + if let Some(substs) = tcx.lift(&substs) { + let mut types = substs.types().rev().skip(child_types); + for ((def_id, has_default), actual) in type_params.zip(types) { + if !has_default { + break; + } + if tcx.type_of(def_id).subst(tcx, substs) != actual { + break; } + num_supplied_defaults += 1; } } } diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 1cc2730158f82..4ddbe58484678 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -886,8 +886,10 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, generics.parent_count + generics.params.len() }); + let mut params: Vec<_> = opt_self.into_iter().collect(); + let early_lifetimes = early_bound_lifetimes_from_generics(tcx, ast_generics); - let lifetimes = early_lifetimes.enumerate().map(|(i, l)| { + params.extend(early_lifetimes.enumerate().map(|(i, l)| { ty::GenericParamDef { name: l.lifetime.name.name().as_interned_str(), index: own_start + i as u32, @@ -895,14 +897,14 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, pure_wrt_drop: l.pure_wrt_drop, kind: ty::GenericParamDefKind::Lifetime, } - }).collect::>(); + })); let hir_id = tcx.hir.node_to_hir_id(node_id); let object_lifetime_defaults = tcx.object_lifetime_defaults(hir_id); // Now create the real type parameters. - let type_start = own_start + lifetimes.len() as u32; - let mut types: Vec<_> = ast_generics.ty_params().enumerate().map(|(i, p)| { + let type_start = params.len() as u32; + params.extend(ast_generics.ty_params().enumerate().map(|(i, p)| { if p.name == keywords::SelfType.name() { span_bug!(p.span, "`Self` should not be the name of a regular parameter"); } @@ -930,7 +932,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, synthetic: p.synthetic, }), } - }).collect(); + })); // provide junk type parameter defs - the only place that // cares about anything but the length is instantiation, @@ -943,7 +945,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }; for (i, &arg) in dummy_args.iter().enumerate() { - types.push(ty::GenericParamDef { + params.push(ty::GenericParamDef { index: type_start + i as u32, name: Symbol::intern(arg).as_interned_str(), def_id, @@ -957,7 +959,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } tcx.with_freevars(node_id, |fv| { - types.extend(fv.iter().zip((dummy_args.len() as u32)..).map(|(_, i)| { + params.extend(fv.iter().zip((dummy_args.len() as u32)..).map(|(_, i)| { ty::GenericParamDef { index: type_start + i, name: Symbol::intern("").as_interned_str(), @@ -973,11 +975,6 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }); } - let params: Vec<_> = opt_self.into_iter() - .chain(lifetimes) - .chain(types) - .collect(); - let param_def_id_to_index = params.iter() .map(|param| (param.def_id, param.index)) .collect(); diff --git a/src/librustc_typeck/impl_wf_check.rs b/src/librustc_typeck/impl_wf_check.rs index ef699b201a51a..1ba967ce4b064 100644 --- a/src/librustc_typeck/impl_wf_check.rs +++ b/src/librustc_typeck/impl_wf_check.rs @@ -72,10 +72,9 @@ struct ImplWfCheck<'a, 'tcx: 'a> { impl<'a, 'tcx> ItemLikeVisitor<'tcx> for ImplWfCheck<'a, 'tcx> { fn visit_item(&mut self, item: &'tcx hir::Item) { match item.node { - hir::ItemImpl(.., ref generics, _, _, ref impl_item_refs) => { + hir::ItemImpl(.., _, _, _, ref impl_item_refs) => { let impl_def_id = self.tcx.hir.local_def_id(item.id); enforce_impl_params_are_constrained(self.tcx, - generics, impl_def_id, impl_item_refs); enforce_impl_items_are_distinct(self.tcx, impl_item_refs); @@ -90,7 +89,6 @@ impl<'a, 'tcx> ItemLikeVisitor<'tcx> for ImplWfCheck<'a, 'tcx> { } fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, - impl_hir_generics: &hir::Generics, impl_def_id: DefId, impl_item_refs: &[hir::ImplItemRef]) { @@ -115,26 +113,28 @@ fn enforce_impl_params_are_constrained<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, ctp::parameters_for(&tcx.type_of(def_id), true) }).collect(); - for (ty_param, hir_param) in impl_generics.params.iter() - .zip(impl_hir_generics.params.iter()) { - match (&ty_param.kind, hir_param) { + for param in &impl_generics.params { + match param.kind { // Disallow ANY unconstrained type parameters. - (&ty::GenericParamDefKind::Type(_), hir::GenericParam::Type(hir_ty)) => { - let param_ty = ty::ParamTy::for_def(ty_param); + ty::GenericParamDefKind::Type(_) => { + let param_ty = ty::ParamTy::for_def(param); if !input_parameters.contains(&ctp::Parameter::from(param_ty)) { - report_unused_parameter(tcx, hir_ty.span, "type", ¶m_ty.to_string()); + report_unused_parameter(tcx, + tcx.def_span(param.def_id), + "type", + ¶m_ty.to_string()); } } - (&ty::GenericParamDefKind::Lifetime, hir::GenericParam::Lifetime(hir_lt)) => { - let param = ctp::Parameter::from(ty_param.to_early_bound_region_data()); - if lifetimes_in_associated_types.contains(¶m) && // (*) - !input_parameters.contains(¶m) { - report_unused_parameter(tcx, hir_lt.lifetime.span, - "lifetime", &hir_lt.lifetime.name.name().to_string()); + ty::GenericParamDefKind::Lifetime => { + let param_lt = ctp::Parameter::from(param.to_early_bound_region_data()); + if lifetimes_in_associated_types.contains(¶m_lt) && // (*) + !input_parameters.contains(¶m_lt) { + report_unused_parameter(tcx, + tcx.def_span(param.def_id), + "lifetime", + ¶m.name.to_string()); } } - (&ty::GenericParamDefKind::Type(_), _) => continue, - (&ty::GenericParamDefKind::Lifetime, _) => continue, } } From b575c18992394f9723ddacee49665351874c7b30 Mon Sep 17 00:00:00 2001 From: varkor Date: Fri, 11 May 2018 16:12:56 +0100 Subject: [PATCH 31/40] Refactoring generic counting loops --- src/librustc/ty/mod.rs | 4 +- src/librustc_typeck/astconv.rs | 66 ++++++++++++++++---------------- src/librustc_typeck/check/mod.rs | 60 +++++++++++++++-------------- src/librustc_typeck/collect.rs | 2 +- src/librustdoc/clean/mod.rs | 6 ++- 5 files changed, 71 insertions(+), 67 deletions(-) diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index fc085cbd4f844..4818006b9e7eb 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -803,7 +803,7 @@ impl<'a, 'gcx, 'tcx> Generics { types: 0, }; - for param in self.params.iter() { + for param in &self.params { match param.kind { GenericParamDefKind::Lifetime => own_counts.lifetimes += 1, GenericParamDefKind::Type(_) => own_counts.types += 1, @@ -814,7 +814,7 @@ impl<'a, 'gcx, 'tcx> Generics { } pub fn requires_monomorphization(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> bool { - for param in self.params.iter() { + for param in &self.params { match param.kind { GenericParamDefKind::Type(_) => return true, GenericParamDefKind::Lifetime => {} diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index 50d76d8179057..ec685dd8c4c03 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -208,40 +208,39 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { // region with the current anon region binding (in other words, // whatever & would get replaced with). let decl_generics = tcx.generics_of(def_id); - let own_counts = decl_generics.own_counts(); - let num_types_provided = parameters.types.len(); - let expected_num_region_params = own_counts.lifetimes; - let supplied_num_region_params = parameters.lifetimes.len(); - if expected_num_region_params != supplied_num_region_params { - report_lifetime_number_error(tcx, span, - supplied_num_region_params, - expected_num_region_params); + let ty_provided = parameters.types.len(); + let lt_provided = parameters.lifetimes.len(); + + let mut lt_accepted = 0; + let mut ty_range = (0, 0); + for param in &decl_generics.params { + match param.kind { + GenericParamDefKind::Lifetime => { + lt_accepted += 1; + } + GenericParamDefKind::Type(ty) => { + ty_range.1 += 1; + if !ty.has_default { + ty_range.0 += 1; + } + } + }; + } + if self_ty.is_some() { + ty_range.0 -= 1; + ty_range.1 -= 1; + } + + if lt_accepted != lt_provided { + report_lifetime_number_error(tcx, span, lt_provided, lt_accepted); } // If a self-type was declared, one should be provided. assert_eq!(decl_generics.has_self, self_ty.is_some()); // Check the number of type parameters supplied by the user. - let own_self = self_ty.is_some() as usize; - let ty_param_defs = own_counts.types - own_self; - if !infer_types || num_types_provided > ty_param_defs { - let type_params_without_defaults = { - let mut count = 0; - for param in decl_generics.params.iter() { - if let ty::GenericParamDefKind::Type(ty) = param.kind { - if !ty.has_default { - count += 1 - } - } - } - count - }; - - check_type_argument_count(tcx, - span, - num_types_provided, - ty_param_defs, - type_params_without_defaults - own_self); + if !infer_types || ty_provided > ty_range.0 { + check_type_argument_count(tcx, span, ty_provided, ty_range); } let is_object = self_ty.map_or(false, |ty| ty.sty == TRAIT_OBJECT_DUMMY_SELF); @@ -259,6 +258,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { false }; + let own_self = self_ty.is_some() as usize; let substs = Substs::for_item(tcx, def_id, |def, _| { let i = def.index as usize - own_self; if let Some(lifetime) = parameters.lifetimes.get(i) { @@ -279,8 +279,8 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { _ => unreachable!() }; - let i = i - (own_counts.lifetimes + own_self); - if i < num_types_provided { + let i = i - (lt_accepted + own_self); + if i < ty_provided { // A provided type parameter. self.ast_ty_to_ty(¶meters.types[i]) } else if infer_types { @@ -1327,11 +1327,9 @@ fn split_auto_traits<'a, 'b, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, fn check_type_argument_count(tcx: TyCtxt, span: Span, supplied: usize, - ty_param_defs: usize, - ty_param_defs_without_default: usize) + ty_range: (usize, usize)) { - let accepted = ty_param_defs; - let required = ty_param_defs_without_default; + let (required, accepted) = ty_range; if supplied < required { let expected = if required < accepted { "expected at least" diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 2ff760726d253..70d29c60a101a 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -4923,32 +4923,34 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { }; // Check provided parameters. - let (ty_req_len, accepted, lt_req_len) = - segment.map_or((0, 0, 0), |(_, generics)| { - let own_counts = generics.own_counts(); - - let own_self = (generics.parent.is_none() && generics.has_self) as usize; - let type_params = own_counts.types - own_self; - let type_params_without_defaults = { - let mut count = 0; - for param in generics.params.iter() { - if let ty::GenericParamDefKind::Type(ty) = param.kind { + let ((ty_required, ty_accepted), lt_accepted) = + segment.map_or(((0, 0), 0), |(_, generics)| { + let mut lt_accepted = 0; + let mut ty_range = (0, 0); + for param in &generics.params { + match param.kind { + GenericParamDefKind::Lifetime => { + lt_accepted += 1; + } + GenericParamDefKind::Type(ty) => { + ty_range.1 += 1; if !ty.has_default { - count += 1 + ty_range.0 += 1; } } - } - count - }; - let type_params_barring_defaults = - type_params_without_defaults - own_self; + }; + } + if generics.parent.is_none() && generics.has_self { + ty_range.0 -= 1; + ty_range.1 -= 1; + } - (type_params_barring_defaults, type_params, own_counts.lifetimes) + ((ty_range.0, ty_range.1), lt_accepted) }); - if types.len() > accepted { - let span = types[accepted].span; - let expected_text = count_type_params(accepted); + if types.len() > ty_accepted { + let span = types[ty_accepted].span; + let expected_text = count_type_params(ty_accepted); let actual_text = count_type_params(types.len()); struct_span_err!(self.tcx.sess, span, E0087, "too many type parameters provided: \ @@ -4961,8 +4963,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // type parameters, we force instantiate_value_path to // use inference variables instead of the provided types. *segment = None; - } else if types.len() < ty_req_len && !infer_types && !supress_mismatch_error { - let expected_text = count_type_params(ty_req_len); + } else if types.len() < ty_required && !infer_types && !supress_mismatch_error { + let expected_text = count_type_params(ty_required); let actual_text = count_type_params(types.len()); struct_span_err!(self.tcx.sess, span, E0089, "too few type parameters provided: \ @@ -4984,8 +4986,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { let primary_msg = "cannot specify lifetime arguments explicitly \ if late bound lifetime parameters are present"; let note_msg = "the late bound lifetime parameter is introduced here"; - if !is_method_call && (lifetimes.len() > lt_req_len || - lifetimes.len() < lt_req_len && !infer_lifetimes) { + if !is_method_call && (lifetimes.len() > lt_accepted || + lifetimes.len() < lt_accepted && !infer_lifetimes) { let mut err = self.tcx.sess.struct_span_err(lifetimes[0].span, primary_msg); err.span_note(span_late, note_msg); err.emit(); @@ -4999,9 +5001,9 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { return; } - if lifetimes.len() > lt_req_len { - let span = lifetimes[lt_req_len].span; - let expected_text = count_lifetime_params(lt_req_len); + if lifetimes.len() > lt_accepted { + let span = lifetimes[lt_accepted].span; + let expected_text = count_lifetime_params(lt_accepted); let actual_text = count_lifetime_params(lifetimes.len()); struct_span_err!(self.tcx.sess, span, E0088, "too many lifetime parameters provided: \ @@ -5009,8 +5011,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { expected_text, actual_text) .span_label(span, format!("expected {}", expected_text)) .emit(); - } else if lifetimes.len() < lt_req_len && !infer_lifetimes { - let expected_text = count_lifetime_params(lt_req_len); + } else if lifetimes.len() < lt_accepted && !infer_lifetimes { + let expected_text = count_lifetime_params(lt_accepted); let actual_text = count_lifetime_params(lifetimes.len()); struct_span_err!(self.tcx.sess, span, E0090, "too few lifetime parameters provided: \ diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 4ddbe58484678..d4f9fb948fe4f 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -903,7 +903,7 @@ fn generics_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let object_lifetime_defaults = tcx.object_lifetime_defaults(hir_id); // Now create the real type parameters. - let type_start = params.len() as u32; + let type_start = own_start - has_self as u32 + params.len() as u32; params.extend(ast_generics.ty_params().enumerate().map(|(i, p)| { if p.name == keywords::SelfType.name() { span_bug!(p.span, "`Self` should not be the name of a regular parameter"); diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 621ec641ee036..17f2c47562f74 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1339,11 +1339,15 @@ impl Clean for hir::TyParam { impl<'tcx> Clean for ty::GenericParamDef { fn clean(&self, cx: &DocContext) -> TyParam { cx.renderinfo.borrow_mut().external_typarams.insert(self.def_id, self.name.clean(cx)); + let has_default = match self.kind { + ty::GenericParamDefKind::Type(ty) => ty.has_default, + _ => panic!("tried to convert a non-type GenericParamDef as a type") + }; TyParam { name: self.name.clean(cx), did: self.def_id, bounds: vec![], // these are filled in from the where-clauses - default: if self.to_type().has_default { + default: if has_default { Some(cx.tcx.type_of(self.def_id).clean(cx)) } else { None From 25bf73d31cab64d9511e45d78efc6265e2cdd693 Mon Sep 17 00:00:00 2001 From: varkor Date: Fri, 11 May 2018 16:46:38 +0100 Subject: [PATCH 32/40] Update bad-annotation error message --- src/test/ui/on-unimplemented/bad-annotation.rs | 2 +- src/test/ui/on-unimplemented/bad-annotation.stderr | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/test/ui/on-unimplemented/bad-annotation.rs b/src/test/ui/on-unimplemented/bad-annotation.rs index e7483dbd3b546..7ef155e5f2ebe 100644 --- a/src/test/ui/on-unimplemented/bad-annotation.rs +++ b/src/test/ui/on-unimplemented/bad-annotation.rs @@ -28,7 +28,7 @@ trait BadAnnotation1 {} #[rustc_on_unimplemented = "Unimplemented trait error on `{Self}` with params `<{A},{B},{C}>`"] -//~^ ERROR there is no type parameter C on trait BadAnnotation2 +//~^ ERROR there is no parameter C on trait BadAnnotation2 trait BadAnnotation2 {} diff --git a/src/test/ui/on-unimplemented/bad-annotation.stderr b/src/test/ui/on-unimplemented/bad-annotation.stderr index c37383757384e..1c5d4d603afc6 100644 --- a/src/test/ui/on-unimplemented/bad-annotation.stderr +++ b/src/test/ui/on-unimplemented/bad-annotation.stderr @@ -6,7 +6,7 @@ LL | #[rustc_on_unimplemented] //~ ERROR `#[rustc_on_unimplemented]` requires a | = note: eg `#[rustc_on_unimplemented = "foo"]` -error[E0230]: there is no type parameter C on trait BadAnnotation2 +error[E0230]: there is no parameter C on trait BadAnnotation2 --> $DIR/bad-annotation.rs:30:1 | LL | #[rustc_on_unimplemented = "Unimplemented trait error on `{Self}` with params `<{A},{B},{C}>`"] From 030f10f752b6584e4f1974c104dd644dfffd80ad Mon Sep 17 00:00:00 2001 From: varkor Date: Mon, 14 May 2018 12:49:32 +0100 Subject: [PATCH 33/40] Clean up generic param handling --- src/librustc/traits/error_reporting.rs | 5 ++--- src/librustc/traits/on_unimplemented.rs | 2 +- src/librustc/ty/mod.rs | 8 ++++++-- src/librustc_typeck/astconv.rs | 23 ++++++++++++++--------- src/librustc_typeck/check/mod.rs | 17 +++++++++++------ src/librustc_typeck/impl_wf_check.rs | 2 +- 6 files changed, 35 insertions(+), 22 deletions(-) diff --git a/src/librustc/traits/error_reporting.rs b/src/librustc/traits/error_reporting.rs index 18c0020a2b49b..934069974beb1 100644 --- a/src/librustc/traits/error_reporting.rs +++ b/src/librustc/traits/error_reporting.rs @@ -382,13 +382,12 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { for param in generics.params.iter() { let value = match param.kind { GenericParamDefKind::Type(_) => { - let ty = trait_ref.substs.type_for_def(¶m); - ty.to_string() + trait_ref.substs[param.index as usize].to_string() }, GenericParamDefKind::Lifetime => continue, }; let name = param.name.to_string(); - flags.push((name.clone(), Some(value.clone()))); + flags.push((name, Some(value))); } if let Some(true) = self_ty.ty_to_def_id().map(|def_id| def_id.is_local()) { diff --git a/src/librustc/traits/on_unimplemented.rs b/src/librustc/traits/on_unimplemented.rs index bc558c2933cdc..539f40cf3efb5 100644 --- a/src/librustc/traits/on_unimplemented.rs +++ b/src/librustc/traits/on_unimplemented.rs @@ -290,7 +290,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedFormatString { let generic_map = generics.params.iter().filter_map(|param| { let value = match param.kind { GenericParamDefKind::Type(_) => { - trait_ref.substs.type_for_def(¶m).to_string() + trait_ref.substs[param.index as usize].to_string() }, GenericParamDefKind::Lifetime => return None }; diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 4818006b9e7eb..6861683ed1298 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -837,7 +837,7 @@ impl<'a, 'gcx, 'tcx> Generics { let param = &self.params[index as usize]; match param.kind { ty::GenericParamDefKind::Lifetime => param, - _ => bug!("expected region parameter, but found another generic parameter") + _ => bug!("expected lifetime parameter, but found another generic parameter") } } else { tcx.generics_of(self.parent.expect("parent_count>0 but no parent?")) @@ -851,7 +851,11 @@ impl<'a, 'gcx, 'tcx> Generics { tcx: TyCtxt<'a, 'gcx, 'tcx>) -> &'tcx GenericParamDef { if let Some(index) = param.idx.checked_sub(self.parent_count as u32) { - &self.params[index as usize] + let param = &self.params[index as usize]; + match param.kind { + ty::GenericParamDefKind::Type(_) => param, + _ => bug!("expected type parameter, but found another generic parameter") + } } else { tcx.generics_of(self.parent.expect("parent_count>0 but no parent?")) .type_param(param, tcx) diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index ec685dd8c4c03..12e1bfde2241c 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -87,6 +87,11 @@ struct ConvertedBinding<'tcx> { span: Span, } +struct ParamRange { + required: usize, + accepted: usize +} + /// Dummy type used for the `Self` of a `TraitRef` created for converting /// a trait object, and which gets removed in `ExistentialTraitRef`. /// This type must not appear anywhere in other converted types. @@ -212,23 +217,23 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { let lt_provided = parameters.lifetimes.len(); let mut lt_accepted = 0; - let mut ty_range = (0, 0); + let mut ty_params = ParamRange { required: 0, accepted: 0 }; for param in &decl_generics.params { match param.kind { GenericParamDefKind::Lifetime => { lt_accepted += 1; } GenericParamDefKind::Type(ty) => { - ty_range.1 += 1; + ty_params.accepted += 1; if !ty.has_default { - ty_range.0 += 1; + ty_params.required += 1; } } }; } if self_ty.is_some() { - ty_range.0 -= 1; - ty_range.1 -= 1; + ty_params.required -= 1; + ty_params.accepted -= 1; } if lt_accepted != lt_provided { @@ -239,8 +244,8 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { assert_eq!(decl_generics.has_self, self_ty.is_some()); // Check the number of type parameters supplied by the user. - if !infer_types || ty_provided > ty_range.0 { - check_type_argument_count(tcx, span, ty_provided, ty_range); + if !infer_types || ty_provided > ty_params.required { + check_type_argument_count(tcx, span, ty_provided, ty_params); } let is_object = self_ty.map_or(false, |ty| ty.sty == TRAIT_OBJECT_DUMMY_SELF); @@ -1327,9 +1332,9 @@ fn split_auto_traits<'a, 'b, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, fn check_type_argument_count(tcx: TyCtxt, span: Span, supplied: usize, - ty_range: (usize, usize)) + ty_params: ParamRange) { - let (required, accepted) = ty_range; + let (required, accepted) = (ty_params.required, ty_params.accepted); if supplied < required { let expected = if required < accepted { "expected at least" diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 70d29c60a101a..7e33bf9722f19 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -4925,27 +4925,32 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // Check provided parameters. let ((ty_required, ty_accepted), lt_accepted) = segment.map_or(((0, 0), 0), |(_, generics)| { + struct ParamRange { + required: usize, + accepted: usize + }; + let mut lt_accepted = 0; - let mut ty_range = (0, 0); + let mut ty_params = ParamRange { required: 0, accepted: 0 }; for param in &generics.params { match param.kind { GenericParamDefKind::Lifetime => { lt_accepted += 1; } GenericParamDefKind::Type(ty) => { - ty_range.1 += 1; + ty_params.accepted += 1; if !ty.has_default { - ty_range.0 += 1; + ty_params.required += 1; } } }; } if generics.parent.is_none() && generics.has_self { - ty_range.0 -= 1; - ty_range.1 -= 1; + ty_params.required -= 1; + ty_params.accepted -= 1; } - ((ty_range.0, ty_range.1), lt_accepted) + ((ty_params.required, ty_params.accepted), lt_accepted) }); if types.len() > ty_accepted { diff --git a/src/librustc_typeck/impl_wf_check.rs b/src/librustc_typeck/impl_wf_check.rs index 1ba967ce4b064..80dde814c6638 100644 --- a/src/librustc_typeck/impl_wf_check.rs +++ b/src/librustc_typeck/impl_wf_check.rs @@ -72,7 +72,7 @@ struct ImplWfCheck<'a, 'tcx: 'a> { impl<'a, 'tcx> ItemLikeVisitor<'tcx> for ImplWfCheck<'a, 'tcx> { fn visit_item(&mut self, item: &'tcx hir::Item) { match item.node { - hir::ItemImpl(.., _, _, _, ref impl_item_refs) => { + hir::ItemImpl(.., ref impl_item_refs) => { let impl_def_id = self.tcx.hir.local_def_id(item.id); enforce_impl_params_are_constrained(self.tcx, impl_def_id, From d9190da9825b729ce63becf727b2cfdad3e8561a Mon Sep 17 00:00:00 2001 From: varkor Date: Mon, 14 May 2018 18:27:13 +0100 Subject: [PATCH 34/40] Refactor Substs methods on generic parameters --- src/librustc/infer/mod.rs | 17 ++- src/librustc/traits/mod.rs | 18 ++- src/librustc/ty/context.rs | 27 ++-- src/librustc/ty/subst.rs | 82 +++++------ src/librustc/ty/util.rs | 17 ++- src/librustc_mir/monomorphize/collector.rs | 18 ++- src/librustc_mir/shim.rs | 16 +-- src/librustc_typeck/astconv.rs | 144 +++++++++++--------- src/librustc_typeck/check/closure.rs | 24 ++-- src/librustc_typeck/check/method/confirm.rs | 59 ++++---- src/librustc_typeck/check/method/mod.rs | 28 ++-- src/librustc_typeck/check/method/probe.rs | 58 +++++--- src/librustc_typeck/check/mod.rs | 129 +++++++++--------- src/librustc_typeck/check/wfcheck.rs | 39 +++--- src/librustc_typeck/collect.rs | 23 ++-- 15 files changed, 393 insertions(+), 306 deletions(-) diff --git a/src/librustc/infer/mod.rs b/src/librustc/infer/mod.rs index 8dd661d04032a..d90ba51fffc26 100644 --- a/src/librustc/infer/mod.rs +++ b/src/librustc/infer/mod.rs @@ -21,9 +21,9 @@ use hir::def_id::DefId; use middle::free_region::RegionRelations; use middle::region; use middle::lang_items; -use ty::subst::Substs; +use ty::subst::{UnpackedKind, Substs}; use ty::{TyVid, IntVid, FloatVid}; -use ty::{self, Ty, TyCtxt}; +use ty::{self, Ty, TyCtxt, GenericParamDefKind}; use ty::error::{ExpectedFound, TypeError, UnconstrainedNumeric}; use ty::fold::TypeFoldable; use ty::relate::RelateResult; @@ -941,10 +941,15 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { span: Span, def_id: DefId) -> &'tcx Substs<'tcx> { - Substs::for_item(self.tcx, def_id, |def, _| { - self.region_var_for_def(span, def) - }, |def, _| { - self.type_var_for_def(span, def) + Substs::for_item(self.tcx, def_id, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => { + UnpackedKind::Lifetime(self.region_var_for_def(span, param)) + } + GenericParamDefKind::Type(_) => { + UnpackedKind::Type(self.type_var_for_def(span, param)) + } + } }) } diff --git a/src/librustc/traits/mod.rs b/src/librustc/traits/mod.rs index a765ffe2396bf..4b5c767b03145 100644 --- a/src/librustc/traits/mod.rs +++ b/src/librustc/traits/mod.rs @@ -22,8 +22,8 @@ use hir::def_id::DefId; use infer::outlives::env::OutlivesEnvironment; use middle::region; use middle::const_val::ConstEvalErr; -use ty::subst::Substs; -use ty::{self, AdtKind, Slice, Ty, TyCtxt, TypeFoldable, ToPredicate}; +use ty::subst::{UnpackedKind, Substs}; +use ty::{self, AdtKind, Slice, Ty, TyCtxt, GenericParamDefKind, TypeFoldable, ToPredicate}; use ty::error::{ExpectedFound, TypeError}; use infer::{InferCtxt}; @@ -841,10 +841,16 @@ fn vtable_methods<'a, 'tcx>( // the method may have some early-bound lifetimes, add // regions for those let substs = trait_ref.map_bound(|trait_ref| { - Substs::for_item( - tcx, def_id, - |_, _| tcx.types.re_erased, - |def, _| trait_ref.substs.type_for_def(def)) + Substs::for_item(tcx, def_id, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => { + UnpackedKind::Lifetime(tcx.types.re_erased) + } + GenericParamDefKind::Type(_) => { + UnpackedKind::Type(trait_ref.substs.type_for_def(param)) + } + } + }) }); // the trait type may have higher-ranked lifetimes in it; diff --git a/src/librustc/ty/context.rs b/src/librustc/ty/context.rs index 995d6c5576718..924271ea3d474 100644 --- a/src/librustc/ty/context.rs +++ b/src/librustc/ty/context.rs @@ -32,7 +32,7 @@ use middle::lang_items; use middle::resolve_lifetime::{self, ObjectLifetimeDefault}; use middle::stability; use mir::{self, Mir, interpret}; -use ty::subst::{Kind, Substs, Subst}; +use ty::subst::{Kind, UnpackedKind, Substs, Subst}; use ty::ReprOptions; use ty::Instance; use traits; @@ -44,6 +44,7 @@ use ty::{PolyFnSig, InferTy, ParamTy, ProjectionTy, ExistentialPredicate, Predic use ty::RegionKind; use ty::{TyVar, TyVid, IntVar, IntVid, FloatVar, FloatVid}; use ty::TypeVariants::*; +use ty::GenericParamDefKind; use ty::layout::{LayoutDetails, TargetDataLayout}; use ty::maps; use ty::steal::Steal; @@ -2325,16 +2326,22 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { pub fn mk_box(self, ty: Ty<'tcx>) -> Ty<'tcx> { let def_id = self.require_lang_item(lang_items::OwnedBoxLangItem); let adt_def = self.adt_def(def_id); - let substs = Substs::for_item(self, def_id, |_, _| bug!(), |def, substs| { - if def.index == 0 { - ty - } else { - match def.kind { - ty::GenericParamDefKind::Type(ty_param) => { - assert!(ty_param.has_default); - self.type_of(def.def_id).subst(self, substs) + let substs = Substs::for_item(self, def_id, |param, substs| { + match param.kind { + GenericParamDefKind::Lifetime => bug!(), + GenericParamDefKind::Type(_) => { + if param.index == 0 { + UnpackedKind::Type(ty) + } else { + match param.kind { + ty::GenericParamDefKind::Type(ty_param) => { + assert!(ty_param.has_default); + UnpackedKind::Type( + self.type_of(param.def_id).subst(self, substs)) + } + _ => unreachable!() + } } - _ => unreachable!() } } }); diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index d4db2ae481a27..5c2b5c5cd4557 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -11,7 +11,7 @@ // Type substitutions. use hir::def_id::DefId; -use ty::{self, Lift, Slice, Region, Ty, TyCtxt}; +use ty::{self, Lift, Slice, Region, Ty, TyCtxt, GenericParamDefKind}; use ty::fold::{TypeFoldable, TypeFolder, TypeVisitor}; use serialize::{self, Encodable, Encoder, Decodable, Decoder}; @@ -174,80 +174,80 @@ impl<'tcx> Decodable for Kind<'tcx> { } } -/// A substitution mapping type/region parameters to new values. +/// A substitution mapping generic parameters to new values. pub type Substs<'tcx> = Slice>; impl<'a, 'gcx, 'tcx> Substs<'tcx> { /// Creates a Substs that maps each generic parameter to itself. pub fn identity_for_item(tcx: TyCtxt<'a, 'gcx, 'tcx>, def_id: DefId) -> &'tcx Substs<'tcx> { - Substs::for_item(tcx, def_id, |def, _| { - tcx.mk_region(ty::ReEarlyBound(def.to_early_bound_region_data())) - }, |def, _| tcx.mk_ty_param_from_def(def)) + Substs::for_item(tcx, def_id, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => { + UnpackedKind::Lifetime( + tcx.mk_region(ty::ReEarlyBound(param.to_early_bound_region_data()))) + } + GenericParamDefKind::Type(_) => { + UnpackedKind::Type(tcx.mk_ty_param_from_def(param)) + } + } + }) } /// Creates a Substs for generic parameter definitions, - /// by calling closures to obtain each region and type. + /// by calling closures to obtain each kind. /// The closures get to observe the Substs as they're /// being built, which can be used to correctly - /// substitute defaults of type parameters. - pub fn for_item(tcx: TyCtxt<'a, 'gcx, 'tcx>, - def_id: DefId, - mut mk_region: FR, - mut mk_type: FT) - -> &'tcx Substs<'tcx> - where FR: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, - FT: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { + /// substitute defaults of generic parameters. + pub fn for_item(tcx: TyCtxt<'a, 'gcx, 'tcx>, + def_id: DefId, + mut mk_kind: F) + -> &'tcx Substs<'tcx> + where F: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> UnpackedKind<'tcx> + { let defs = tcx.generics_of(def_id); let mut substs = Vec::with_capacity(defs.count()); - Substs::fill_item(&mut substs, tcx, defs, &mut mk_region, &mut mk_type); + Substs::fill_item(&mut substs, tcx, defs, &mut mk_kind); tcx.intern_substs(&substs) } - pub fn extend_to(&self, - tcx: TyCtxt<'a, 'gcx, 'tcx>, - def_id: DefId, - mut mk_region: FR, - mut mk_type: FT) - -> &'tcx Substs<'tcx> - where FR: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, - FT: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Ty<'tcx> + pub fn extend_to(&self, + tcx: TyCtxt<'a, 'gcx, 'tcx>, + def_id: DefId, + mut mk_kind: F) + -> &'tcx Substs<'tcx> + where F: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> UnpackedKind<'tcx> { let defs = tcx.generics_of(def_id); let mut result = Vec::with_capacity(defs.count()); result.extend(self[..].iter().cloned()); - Substs::fill_single(&mut result, defs, &mut mk_region, &mut mk_type); + Substs::fill_single(&mut result, defs, &mut mk_kind); tcx.intern_substs(&result) } - pub fn fill_item(substs: &mut Vec>, + pub fn fill_item(substs: &mut Vec>, tcx: TyCtxt<'a, 'gcx, 'tcx>, defs: &ty::Generics, - mk_region: &mut FR, - mk_type: &mut FT) - where FR: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, - FT: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { + mk_kind: &mut F) + where F: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> UnpackedKind<'tcx> + { if let Some(def_id) = defs.parent { let parent_defs = tcx.generics_of(def_id); - Substs::fill_item(substs, tcx, parent_defs, mk_region, mk_type); + Substs::fill_item(substs, tcx, parent_defs, mk_kind); } - Substs::fill_single(substs, defs, mk_region, mk_type) + Substs::fill_single(substs, defs, mk_kind) } - fn fill_single(substs: &mut Vec>, + fn fill_single(substs: &mut Vec>, defs: &ty::Generics, - mk_region: &mut FR, - mk_type: &mut FT) - where FR: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> ty::Region<'tcx>, - FT: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Ty<'tcx> { + mk_kind: &mut F) + where F: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> UnpackedKind<'tcx> + { for param in &defs.params { - let kind = match param.kind { - ty::GenericParamDefKind::Lifetime => mk_region(param, substs).into(), - ty::GenericParamDefKind::Type(_) => mk_type(param, substs).into(), - }; + let kind = mk_kind(param, substs); assert_eq!(param.index as usize, substs.len()); - substs.push(kind); + substs.push(kind.pack()); } } diff --git a/src/librustc/ty/util.rs b/src/librustc/ty/util.rs index fdd0754730feb..91280e5b8a3fd 100644 --- a/src/librustc/ty/util.rs +++ b/src/librustc/ty/util.rs @@ -17,9 +17,9 @@ use hir; use ich::NodeIdHashingMode; use middle::const_val::ConstVal; use traits::{self, ObligationCause}; -use ty::{self, Ty, TyCtxt, TypeFoldable}; +use ty::{self, Ty, TyCtxt, GenericParamDefKind, TypeFoldable}; use ty::fold::TypeVisitor; -use ty::subst::UnpackedKind; +use ty::subst::{Substs, UnpackedKind}; use ty::maps::TyCtxtAt; use ty::TypeVariants::*; use ty::layout::{Integer, IntegerExt}; @@ -573,11 +573,14 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { /// Given the def-id of some item that has no type parameters, make /// a suitable "empty substs" for it. - pub fn empty_substs_for_def_id(self, item_def_id: DefId) -> &'tcx ty::Substs<'tcx> { - ty::Substs::for_item(self, item_def_id, - |_, _| self.types.re_erased, - |_, _| { - bug!("empty_substs_for_def_id: {:?} has type parameters", item_def_id) + pub fn empty_substs_for_def_id(self, item_def_id: DefId) -> &'tcx Substs<'tcx> { + Substs::for_item(self, item_def_id, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => UnpackedKind::Lifetime(self.types.re_erased), + GenericParamDefKind::Type(_) => { + bug!("empty_substs_for_def_id: {:?} has type parameters", item_def_id) + } + } }) } diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index f8f6bec33a2ab..c8d4ccaf0bbb2 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -196,8 +196,8 @@ use rustc::hir::def_id::DefId; use rustc::middle::const_val::ConstVal; use rustc::mir::interpret::{AllocId, ConstValue}; use rustc::middle::lang_items::{ExchangeMallocFnLangItem, StartFnLangItem}; -use rustc::ty::subst::{Substs, Kind}; -use rustc::ty::{self, TypeFoldable, Ty, TyCtxt}; +use rustc::ty::subst::{Substs, Kind, UnpackedKind}; +use rustc::ty::{self, TypeFoldable, Ty, TyCtxt, GenericParamDefKind}; use rustc::ty::adjustment::CustomCoerceUnsized; use rustc::session::config; use rustc::mir::{self, Location, Promoted}; @@ -1112,10 +1112,16 @@ fn create_mono_items_for_default_impls<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, continue; } - let substs = Substs::for_item(tcx, - method.def_id, - |_, _| tcx.types.re_erased, - |def, _| trait_ref.substs.type_for_def(def)); + let substs = Substs::for_item(tcx, method.def_id, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => { + UnpackedKind::Lifetime(tcx.types.re_erased) + } + GenericParamDefKind::Type(_) => { + UnpackedKind::Type(trait_ref.substs.type_for_def(param)) + } + } + }); let instance = ty::Instance::resolve(tcx, ty::ParamEnv::reveal_all(), diff --git a/src/librustc_mir/shim.rs b/src/librustc_mir/shim.rs index 5b2f3a8b8aac7..8596d546b09a2 100644 --- a/src/librustc_mir/shim.rs +++ b/src/librustc_mir/shim.rs @@ -12,8 +12,8 @@ use rustc::hir; use rustc::hir::def_id::DefId; use rustc::infer; use rustc::mir::*; -use rustc::ty::{self, Ty, TyCtxt}; -use rustc::ty::subst::{Kind, Subst, Substs}; +use rustc::ty::{self, Ty, TyCtxt, GenericParamDefKind}; +use rustc::ty::subst::{Kind, UnpackedKind, Subst, Substs}; use rustc::ty::maps::Providers; use rustc_data_structures::indexed_vec::{IndexVec, Idx}; @@ -427,12 +427,12 @@ impl<'a, 'tcx> CloneShimBuilder<'a, 'tcx> { ) { let tcx = self.tcx; - let substs = Substs::for_item( - tcx, - self.def_id, - |_, _| tcx.types.re_erased, - |_, _| ty - ); + let substs = Substs::for_item(tcx, self.def_id, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => UnpackedKind::Lifetime(tcx.types.re_erased), + GenericParamDefKind::Type(_) => UnpackedKind::Type(ty), + } + }); // `func == Clone::clone(&ty) -> ty` let func_ty = tcx.mk_fn_def(self.def_id, substs); diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index 12e1bfde2241c..f60c78702b6f3 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -20,7 +20,8 @@ use middle::resolve_lifetime as rl; use namespace::Namespace; use rustc::ty::subst::{Kind, UnpackedKind, Subst, Substs}; use rustc::traits; -use rustc::ty::{self, RegionKind, Ty, TyCtxt, GenericParamDefKind, ToPredicate, TypeFoldable}; +use rustc::ty::{self, RegionKind, Ty, TyCtxt, ToPredicate, TypeFoldable}; +use rustc::ty::GenericParamDefKind; use rustc::ty::wf::object_region_bounds; use rustc_target::spec::abi; use std::slice; @@ -264,66 +265,76 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { }; let own_self = self_ty.is_some() as usize; - let substs = Substs::for_item(tcx, def_id, |def, _| { - let i = def.index as usize - own_self; - if let Some(lifetime) = parameters.lifetimes.get(i) { - self.ast_region_to_region(lifetime, Some(def)) - } else { - tcx.types.re_static - } - }, |def, substs| { - let i = def.index as usize; - - // Handle Self first, so we can adjust the index to match the AST. - if let (0, Some(ty)) = (i, self_ty) { - return ty; - } + let substs = Substs::for_item(tcx, def_id, |param, substs| { + match param.kind { + GenericParamDefKind::Lifetime => { + let i = param.index as usize - own_self; + let lt = if let Some(lifetime) = parameters.lifetimes.get(i) { + self.ast_region_to_region(lifetime, Some(param)) + } else { + tcx.types.re_static + }; + UnpackedKind::Lifetime(lt) + } + GenericParamDefKind::Type(_) => { + let i = param.index as usize; - let has_default = match def.kind { - GenericParamDefKind::Type(ty) => ty.has_default, - _ => unreachable!() - }; + // Handle Self first, so we can adjust the index to match the AST. + if let (0, Some(ty)) = (i, self_ty) { + return UnpackedKind::Type(ty); + } - let i = i - (lt_accepted + own_self); - if i < ty_provided { - // A provided type parameter. - self.ast_ty_to_ty(¶meters.types[i]) - } else if infer_types { - // No type parameters were provided, we can infer all. - let ty_var = if !default_needs_object_self(def) { - self.ty_infer_for_def(def, span) - } else { - self.ty_infer(span) - }; - ty_var - } else if has_default { - // No type parameter provided, but a default exists. - - // If we are converting an object type, then the - // `Self` parameter is unknown. However, some of the - // other type parameters may reference `Self` in their - // defaults. This will lead to an ICE if we are not - // careful! - if default_needs_object_self(def) { - struct_span_err!(tcx.sess, span, E0393, - "the type parameter `{}` must be explicitly specified", - def.name) - .span_label(span, format!("missing reference to `{}`", def.name)) - .note(&format!("because of the default `Self` reference, \ - type parameters must be specified on object types")) - .emit(); - tcx.types.err - } else { - // This is a default type parameter. - self.normalize_ty( - span, - tcx.at(span).type_of(def.def_id) - .subst_spanned(tcx, substs, Some(span)) - ) + let has_default = match param.kind { + GenericParamDefKind::Type(ty) => ty.has_default, + _ => unreachable!() + }; + + let i = i - (lt_accepted + own_self); + let ty = if i < ty_provided { + // A provided type parameter. + self.ast_ty_to_ty(¶meters.types[i]) + } else if infer_types { + // No type parameters were provided, we can infer all. + let ty_var = if !default_needs_object_self(param) { + self.ty_infer_for_def(param, span) + } else { + self.ty_infer(span) + }; + ty_var + } else if has_default { + // No type parameter provided, but a default exists. + + // If we are converting an object type, then the + // `Self` parameter is unknown. However, some of the + // other type parameters may reference `Self` in their + // defaults. This will lead to an ICE if we are not + // careful! + if default_needs_object_self(param) { + struct_span_err!(tcx.sess, span, E0393, + "the type parameter `{}` must be explicitly \ + specified", + param.name) + .span_label(span, + format!("missing reference to `{}`", param.name)) + .note(&format!("because of the default `Self` reference, \ + type parameters must be specified on object \ + types")) + .emit(); + tcx.types.err + } else { + // This is a default type parameter. + self.normalize_ty( + span, + tcx.at(span).type_of(param.def_id) + .subst_spanned(tcx, substs, Some(span)) + ) + } + } else { + // We've already errored above about the mismatch. + tcx.types.err + }; + UnpackedKind::Type(ty) } - } else { - // We've already errored above about the mismatch. - tcx.types.err } }); @@ -1154,12 +1165,17 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { let mut substs = Vec::with_capacity(generics.count()); if let Some(parent_id) = generics.parent { let parent_generics = tcx.generics_of(parent_id); - Substs::fill_item( - &mut substs, tcx, parent_generics, - &mut |def, _| tcx.mk_region( - ty::ReEarlyBound(def.to_early_bound_region_data())), - &mut |def, _| tcx.mk_ty_param_from_def(def) - ); + Substs::fill_item(&mut substs, tcx, parent_generics, &mut |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => { + UnpackedKind::Lifetime( + tcx.mk_region(ty::ReEarlyBound(param.to_early_bound_region_data()))) + } + GenericParamDefKind::Type(_) => { + UnpackedKind::Type(tcx.mk_ty_param_from_def(param)) + } + } + }); // Replace all lifetimes with 'static for subst in &mut substs { diff --git a/src/librustc_typeck/check/closure.rs b/src/librustc_typeck/check/closure.rs index 94ef040d80a4f..152f020c4769e 100644 --- a/src/librustc_typeck/check/closure.rs +++ b/src/librustc_typeck/check/closure.rs @@ -18,8 +18,8 @@ use rustc::infer::{InferOk, InferResult}; use rustc::infer::LateBoundRegionConversionTime; use rustc::infer::type_variable::TypeVariableOrigin; use rustc::traits::error_reporting::ArgKind; -use rustc::ty::{self, ToPolyTraitRef, Ty}; -use rustc::ty::subst::Substs; +use rustc::ty::{self, ToPolyTraitRef, Ty, GenericParamDefKind}; +use rustc::ty::subst::{UnpackedKind, Substs}; use rustc::ty::TypeFoldable; use std::cmp; use std::iter; @@ -104,15 +104,17 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // inference phase (`upvar.rs`). let base_substs = Substs::identity_for_item(self.tcx, self.tcx.closure_base_def_id(expr_def_id)); - let substs = base_substs.extend_to( - self.tcx, - expr_def_id, - |_, _| span_bug!(expr.span, "closure has region param"), - |_, _| { - self.infcx - .next_ty_var(TypeVariableOrigin::ClosureSynthetic(expr.span)) - }, - ); + let substs = base_substs.extend_to(self.tcx,expr_def_id, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => { + span_bug!(expr.span, "closure has region param") + } + GenericParamDefKind::Type(_) => { + UnpackedKind::Type(self.infcx + .next_ty_var(TypeVariableOrigin::ClosureSynthetic(expr.span))) + } + } + }); if let Some(GeneratorTypes { yield_ty, interior, movability }) = generator_types { let substs = ty::GeneratorSubsts { substs }; self.demand_eqtype( diff --git a/src/librustc_typeck/check/method/confirm.rs b/src/librustc_typeck/check/method/confirm.rs index 9928ef549ff70..c208e0fae6429 100644 --- a/src/librustc_typeck/check/method/confirm.rs +++ b/src/librustc_typeck/check/method/confirm.rs @@ -15,8 +15,8 @@ use check::{FnCtxt, PlaceOp, callee, Needs}; use hir::def_id::DefId; use rustc::ty::subst::Substs; use rustc::traits; -use rustc::ty::{self, Ty}; -use rustc::ty::subst::Subst; +use rustc::ty::{self, Ty, GenericParamDefKind}; +use rustc::ty::subst::{UnpackedKind, Subst}; use rustc::ty::adjustment::{Adjustment, Adjust, OverloadedDeref}; use rustc::ty::adjustment::{AllowTwoPhase, AutoBorrow, AutoBorrowMutability}; use rustc::ty::fold::TypeFoldable; @@ -317,30 +317,37 @@ impl<'a, 'gcx, 'tcx> ConfirmContext<'a, 'gcx, 'tcx> { assert_eq!(method_generics.parent_count, parent_substs.len()); let provided = &segment.parameters; let own_counts = method_generics.own_counts(); - Substs::for_item(self.tcx, pick.item.def_id, |def, _| { - let i = def.index as usize; - if i < parent_substs.len() { - parent_substs.region_at(i) - } else if let Some(lifetime) - = provided.as_ref().and_then(|p| p.lifetimes.get(i - parent_substs.len())) { - AstConv::ast_region_to_region(self.fcx, lifetime, Some(def)) - } else { - self.region_var_for_def(self.span, def) - } - }, |def, _cur_substs| { - let i = def.index as usize; - if i < parent_substs.len() { - parent_substs.type_at(i) - } else if let Some(ast_ty) - = provided.as_ref().and_then(|p| { - let idx = - i - parent_substs.len() - own_counts.lifetimes; - p.types.get(idx) - }) - { - self.to_ty(ast_ty) - } else { - self.type_var_for_def(self.span, def) + Substs::for_item(self.tcx, pick.item.def_id, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => { + let i = param.index as usize; + let lt = if i < parent_substs.len() { + parent_substs.region_at(i) + } else if let Some(lifetime) + = provided.as_ref().and_then(|p| p.lifetimes.get(i - parent_substs.len())) { + AstConv::ast_region_to_region(self.fcx, lifetime, Some(param)) + } else { + self.region_var_for_def(self.span, param) + }; + UnpackedKind::Lifetime(lt) + } + GenericParamDefKind::Type(_) => { + let i = param.index as usize; + let ty = if i < parent_substs.len() { + parent_substs.type_at(i) + } else if let Some(ast_ty) + = provided.as_ref().and_then(|p| { + let idx = + i - parent_substs.len() - own_counts.lifetimes; + p.types.get(idx) + }) + { + self.to_ty(ast_ty) + } else { + self.type_var_for_def(self.span, param) + }; + UnpackedKind::Type(ty) + } } }) } diff --git a/src/librustc_typeck/check/method/mod.rs b/src/librustc_typeck/check/method/mod.rs index 83f132d88691a..298b8548e36e7 100644 --- a/src/librustc_typeck/check/method/mod.rs +++ b/src/librustc_typeck/check/method/mod.rs @@ -19,7 +19,8 @@ use namespace::Namespace; use rustc::ty::subst::Substs; use rustc::traits; use rustc::ty::{self, Ty, ToPredicate, ToPolyTraitRef, TraitRef, TypeFoldable}; -use rustc::ty::subst::Subst; +use rustc::ty::GenericParamDefKind; +use rustc::ty::subst::{UnpackedKind, Subst}; use rustc::infer::{self, InferOk}; use syntax::ast; @@ -253,16 +254,21 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { trait_def_id); // Construct a trait-reference `self_ty : Trait` - let substs = Substs::for_item(self.tcx, - trait_def_id, - |def, _| self.region_var_for_def(span, def), - |def, _substs| { - if def.index == 0 { - self_ty - } else if let Some(ref input_types) = opt_input_types { - input_types[def.index as usize - 1] - } else { - self.type_var_for_def(span, def) + let substs = Substs::for_item(self.tcx, trait_def_id, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => { + UnpackedKind::Lifetime(self.region_var_for_def(span, param)) + } + GenericParamDefKind::Type(_) => { + let ty = if param.index == 0 { + self_ty + } else if let Some(ref input_types) = opt_input_types { + input_types[param.index as usize - 1] + } else { + self.type_var_for_def(span, param) + }; + UnpackedKind::Type(ty) + } } }); diff --git a/src/librustc_typeck/check/method/probe.rs b/src/librustc_typeck/check/method/probe.rs index 9d762ca383476..a96796bb148cb 100644 --- a/src/librustc_typeck/check/method/probe.rs +++ b/src/librustc_typeck/check/method/probe.rs @@ -17,9 +17,10 @@ use check::FnCtxt; use hir::def_id::DefId; use hir::def::Def; use namespace::Namespace; -use rustc::ty::subst::{Subst, Substs}; +use rustc::ty::subst::{UnpackedKind, Subst, Substs}; use rustc::traits::{self, ObligationCause}; use rustc::ty::{self, Ty, ToPolyTraitRef, ToPredicate, TraitRef, TypeFoldable}; +use rustc::ty::GenericParamDefKind; use rustc::infer::type_variable::TypeVariableOrigin; use rustc::util::nodemap::FxHashSet; use rustc::infer::{self, InferOk}; @@ -1387,21 +1388,28 @@ impl<'a, 'gcx, 'tcx> ProbeContext<'a, 'gcx, 'tcx> { if generics.params.is_empty() { xform_fn_sig.subst(self.tcx, substs) } else { - let substs = Substs::for_item(self.tcx, method, |def, _| { - let i = def.index as usize; - if i < substs.len() { - substs.region_at(i) - } else { - // In general, during probe we erase regions. See - // `impl_self_ty()` for an explanation. - self.tcx.types.re_erased - } - }, |def, _cur_substs| { - let i = def.index as usize; - if i < substs.len() { - substs.type_at(i) - } else { - self.type_var_for_def(self.span, def) + let substs = Substs::for_item(self.tcx, method, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => { + let i = param.index as usize; + let lt = if i < substs.len() { + substs.region_at(i) + } else { + // In general, during probe we erase regions. See + // `impl_self_ty()` for an explanation. + self.tcx.types.re_erased + }; + UnpackedKind::Lifetime(lt) + } + GenericParamDefKind::Type(_) => { + let i = param.index as usize; + let ty = if i < substs.len() { + substs.type_at(i) + } else { + self.type_var_for_def(self.span, param) + }; + UnpackedKind::Type(ty) + } } }); xform_fn_sig.subst(self.tcx, substs) @@ -1414,12 +1422,18 @@ impl<'a, 'gcx, 'tcx> ProbeContext<'a, 'gcx, 'tcx> { } fn fresh_item_substs(&self, def_id: DefId) -> &'tcx Substs<'tcx> { - Substs::for_item(self.tcx, - def_id, - |_, _| self.tcx.types.re_erased, - |_, _| self.next_ty_var( - TypeVariableOrigin::SubstitutionPlaceholder( - self.tcx.def_span(def_id)))) + Substs::for_item(self.tcx, def_id, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => { + UnpackedKind::Lifetime(self.tcx.types.re_erased) + } + GenericParamDefKind::Type(_) => { + UnpackedKind::Type(self.next_ty_var( + TypeVariableOrigin::SubstitutionPlaceholder( + self.tcx.def_span(def_id)))) + } + } + }) } /// Replace late-bound-regions bound by `value` with `'static` using diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 7e33bf9722f19..99e47f92daf0f 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -94,7 +94,7 @@ use rustc::infer::anon_types::AnonTypeDecl; use rustc::infer::type_variable::{TypeVariableOrigin}; use rustc::middle::region; use rustc::mir::interpret::{GlobalId}; -use rustc::ty::subst::{Kind, Subst, Substs}; +use rustc::ty::subst::{Kind, UnpackedKind, Subst, Substs}; use rustc::traits::{self, ObligationCause, ObligationCauseCode, TraitEngine}; use rustc::ty::{self, Ty, TyCtxt, GenericParamDefKind, Visibility, ToPredicate}; use rustc::ty::adjustment::{Adjust, Adjustment, AllowTwoPhase, AutoBorrow, AutoBorrowMutability}; @@ -4758,71 +4758,78 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { } (None, None) => (0, false) }; - let substs = Substs::for_item(self.tcx, def.def_id(), |def, _| { - let mut i = def.index as usize; - - let segment = if i < fn_start { - i -= has_self as usize; - type_segment - } else { - i -= fn_start; - fn_segment - }; - let lifetimes = segment.map_or(&[][..], |(s, _)| { - s.parameters.as_ref().map_or(&[][..], |p| &p.lifetimes[..]) - }); - - if let Some(lifetime) = lifetimes.get(i) { - AstConv::ast_region_to_region(self, lifetime, Some(def)) - } else { - self.re_infer(span, Some(def)).unwrap() - } - }, |def, substs| { - let mut i = def.index as usize; - - let segment = if i < fn_start { - // Handle Self first, so we can adjust the index to match the AST. - if has_self && i == 0 { - return opt_self_ty.unwrap_or_else(|| { - self.type_var_for_def(span, def) + let substs = Substs::for_item(self.tcx, def.def_id(), |param, substs| { + match param.kind { + GenericParamDefKind::Lifetime => { + let mut i = param.index as usize; + + let segment = if i < fn_start { + i -= has_self as usize; + type_segment + } else { + i -= fn_start; + fn_segment + }; + let lifetimes = segment.map_or(&[][..], |(s, _)| { + s.parameters.as_ref().map_or(&[][..], |p| &p.lifetimes[..]) }); + + let lt = if let Some(lifetime) = lifetimes.get(i) { + AstConv::ast_region_to_region(self, lifetime, Some(param)) + } else { + self.re_infer(span, Some(param)).unwrap() + }; + UnpackedKind::Lifetime(lt) } - i -= has_self as usize; - type_segment - } else { - i -= fn_start; - fn_segment - }; - let (types, infer_types) = segment.map_or((&[][..], true), |(s, _)| { - (s.parameters.as_ref().map_or(&[][..], |p| &p.types[..]), s.infer_types) - }); + GenericParamDefKind::Type(_) => { + let mut i = param.index as usize; + + let segment = if i < fn_start { + // Handle Self first, so we can adjust the index to match the AST. + if has_self && i == 0 { + return UnpackedKind::Type(opt_self_ty.unwrap_or_else(|| { + self.type_var_for_def(span, param) + })); + } + i -= has_self as usize; + type_segment + } else { + i -= fn_start; + fn_segment + }; + let (types, infer_types) = segment.map_or((&[][..], true), |(s, _)| { + (s.parameters.as_ref().map_or(&[][..], |p| &p.types[..]), s.infer_types) + }); - // Skip over the lifetimes in the same segment. - if let Some((_, generics)) = segment { - i -= generics.own_counts().lifetimes; - } + // Skip over the lifetimes in the same segment. + if let Some((_, generics)) = segment { + i -= generics.own_counts().lifetimes; + } - let has_default = match def.kind { - GenericParamDefKind::Type(ty) => ty.has_default, - _ => unreachable!() - }; + let has_default = match param.kind { + GenericParamDefKind::Type(ty) => ty.has_default, + _ => unreachable!() + }; - if let Some(ast_ty) = types.get(i) { - // A provided type parameter. - self.to_ty(ast_ty) - } else if !infer_types && has_default { - // No type parameter provided, but a default exists. - let default = self.tcx.type_of(def.def_id); - self.normalize_ty( - span, - default.subst_spanned(self.tcx, substs, Some(span)) - ) - } else { - // No type parameters were provided, we can infer all. - // This can also be reached in some error cases: - // We prefer to use inference variables instead of - // TyError to let type inference recover somewhat. - self.type_var_for_def(span, def) + let ty = if let Some(ast_ty) = types.get(i) { + // A provided type parameter. + self.to_ty(ast_ty) + } else if !infer_types && has_default { + // No type parameter provided, but a default exists. + let default = self.tcx.type_of(param.def_id); + self.normalize_ty( + span, + default.subst_spanned(self.tcx, substs, Some(span)) + ) + } else { + // No type parameters were provided, we can infer all. + // This can also be reached in some error cases: + // We prefer to use inference variables instead of + // TyError to let type inference recover somewhat. + self.type_var_for_def(span, param) + }; + UnpackedKind::Type(ty) + } } }); diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index a37137c68cb76..5c6a78de313b6 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -11,11 +11,10 @@ use check::{Inherited, FnCtxt}; use constrained_type_params::{identify_constrained_type_params, Parameter}; -use ty::GenericParamDefKind; - use hir::def_id::DefId; use rustc::traits::{self, ObligationCauseCode}; -use rustc::ty::{self, Lift, Ty, TyCtxt}; +use rustc::ty::{self, Lift, Ty, TyCtxt, GenericParamDefKind}; +use rustc::ty::subst::{UnpackedKind, Substs}; use rustc::ty::util::ExplicitSelf; use rustc::util::nodemap::{FxHashSet, FxHashMap}; use rustc::middle::lang_items; @@ -406,22 +405,28 @@ fn check_where_clauses<'a, 'gcx, 'fcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'gcx>, // For more examples see tests `defaults-well-formedness.rs` and `type-check-defaults.rs`. // // First we build the defaulted substitution. - let substs = ty::subst::Substs::for_item(fcx.tcx, def_id, |def, _| { - // All regions are identity. - fcx.tcx.mk_region(ty::ReEarlyBound(def.to_early_bound_region_data())) - }, |def, _| { - // If the param has a default, - if is_our_default(def) { - let default_ty = fcx.tcx.type_of(def.def_id); - // and it's not a dependent default - if !default_ty.needs_subst() { - // then substitute with the default. - return default_ty; + let substs = Substs::for_item(fcx.tcx, def_id, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => { + // All regions are identity. + UnpackedKind::Lifetime( + fcx.tcx.mk_region(ty::ReEarlyBound(param.to_early_bound_region_data()))) + } + GenericParamDefKind::Type(_) => { + // If the param has a default, + if is_our_default(param) { + let default_ty = fcx.tcx.type_of(param.def_id); + // and it's not a dependent default + if !default_ty.needs_subst() { + // then substitute with the default. + return UnpackedKind::Type(default_ty); + } } + // Mark unwanted params as err. + UnpackedKind::Type(fcx.tcx.types.err) } - // Mark unwanted params as err. - fcx.tcx.types.err - }); + } + }); // Now we build the substituted predicates. for &pred in predicates.predicates.iter() { struct CountParams { params: FxHashSet } diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index d4f9fb948fe4f..1a2480bf45e3b 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -30,7 +30,8 @@ use constrained_type_params as ctp; use middle::lang_items::SizedTraitLangItem; use middle::resolve_lifetime as rl; use rustc::mir::mono::Linkage; -use rustc::ty::subst::Substs; +use rustc::ty::subst::{UnpackedKind, Substs}; +use rustc::ty::GenericParamDefKind; use rustc::ty::{ToPredicate, ReprOptions}; use rustc::ty::{self, AdtKind, ToPolyTraitRef, Ty, TyCtxt}; use rustc::ty::maps::Providers; @@ -1096,15 +1097,17 @@ fn type_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } let substs = ty::ClosureSubsts { - substs: Substs::for_item( - tcx, - def_id, - |def, _| { - let region = def.to_early_bound_region_data(); - tcx.mk_region(ty::ReEarlyBound(region)) - }, - |def, _| tcx.mk_ty_param_from_def(def) - ) + substs: Substs::for_item(tcx, def_id, |param, _| { + match param.kind { + GenericParamDefKind::Lifetime => { + let region = param.to_early_bound_region_data(); + UnpackedKind::Lifetime(tcx.mk_region(ty::ReEarlyBound(region))) + } + GenericParamDefKind::Type(_) => { + UnpackedKind::Type(tcx.mk_ty_param_from_def(param)) + } + } + }) }; tcx.mk_closure(def_id, substs) From 3ae2468261dca097ecfa81a74654fed32b60f8ce Mon Sep 17 00:00:00 2001 From: varkor Date: Mon, 14 May 2018 19:57:59 +0100 Subject: [PATCH 35/40] Clean up shared subst code --- src/librustc/infer/mod.rs | 65 +++++++++------------ src/librustc/ty/context.rs | 12 +--- src/librustc_typeck/astconv.rs | 14 ++--- src/librustc_typeck/check/method/confirm.rs | 50 +++++++--------- src/librustc_typeck/check/method/mod.rs | 16 ++--- src/librustc_typeck/check/method/probe.rs | 27 +++------ src/librustc_typeck/check/mod.rs | 61 +++++++++---------- 7 files changed, 101 insertions(+), 144 deletions(-) diff --git a/src/librustc/infer/mod.rs b/src/librustc/infer/mod.rs index d90ba51fffc26..7a1e255dc5d0c 100644 --- a/src/librustc/infer/mod.rs +++ b/src/librustc/infer/mod.rs @@ -905,34 +905,34 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { self.next_region_var(RegionVariableOrigin::NLL(origin)) } - /// Create a region inference variable for the given - /// region parameter definition. - pub fn region_var_for_def(&self, - span: Span, - def: &ty::GenericParamDef) - -> ty::Region<'tcx> { - self.next_region_var(EarlyBoundRegion(span, def.name)) - } - - /// Create a type inference variable for the given - /// type parameter definition. The substitutions are - /// for actual parameters that may be referred to by - /// the default of this type parameter, if it exists. - /// E.g. `struct Foo(...);` when - /// used in a path such as `Foo::::new()` will - /// use an inference variable for `C` with `[T, U]` - /// as the substitutions for the default, `(T, U)`. - pub fn type_var_for_def(&self, - span: Span, - def: &ty::GenericParamDef) - -> Ty<'tcx> { - let ty_var_id = self.type_variables - .borrow_mut() - .new_var(self.universe(), - false, - TypeVariableOrigin::TypeParameterDefinition(span, def.name)); - - self.tcx.mk_var(ty_var_id) + pub fn var_for_def(&self, + span: Span, + param: &ty::GenericParamDef) + -> UnpackedKind<'tcx> { + match param.kind { + GenericParamDefKind::Lifetime => { + // Create a region inference variable for the given + // region parameter definition. + UnpackedKind::Lifetime(self.next_region_var(EarlyBoundRegion(span, param.name))) + } + GenericParamDefKind::Type(_) => { + // Create a type inference variable for the given + // type parameter definition. The substitutions are + // for actual parameters that may be referred to by + // the default of this type parameter, if it exists. + // E.g. `struct Foo(...);` when + // used in a path such as `Foo::::new()` will + // use an inference variable for `C` with `[T, U]` + // as the substitutions for the default, `(T, U)`. + let ty_var_id = self.type_variables + .borrow_mut() + .new_var(self.universe(), + false, + TypeVariableOrigin::TypeParameterDefinition(span, param.name)); + + UnpackedKind::Type(self.tcx.mk_var(ty_var_id)) + } + } } /// Given a set of generics defined on a type or impl, returns a substitution mapping each @@ -942,14 +942,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { def_id: DefId) -> &'tcx Substs<'tcx> { Substs::for_item(self.tcx, def_id, |param, _| { - match param.kind { - GenericParamDefKind::Lifetime => { - UnpackedKind::Lifetime(self.region_var_for_def(span, param)) - } - GenericParamDefKind::Type(_) => { - UnpackedKind::Type(self.type_var_for_def(span, param)) - } - } + self.var_for_def(span, param) }) } diff --git a/src/librustc/ty/context.rs b/src/librustc/ty/context.rs index 924271ea3d474..66c451e819310 100644 --- a/src/librustc/ty/context.rs +++ b/src/librustc/ty/context.rs @@ -2329,18 +2329,12 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { let substs = Substs::for_item(self, def_id, |param, substs| { match param.kind { GenericParamDefKind::Lifetime => bug!(), - GenericParamDefKind::Type(_) => { + GenericParamDefKind::Type(ty_param) => { if param.index == 0 { UnpackedKind::Type(ty) } else { - match param.kind { - ty::GenericParamDefKind::Type(ty_param) => { - assert!(ty_param.has_default); - UnpackedKind::Type( - self.type_of(param.def_id).subst(self, substs)) - } - _ => unreachable!() - } + assert!(ty_param.has_default); + UnpackedKind::Type(self.type_of(param.def_id).subst(self, substs)) } } } diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index f60c78702b6f3..32ea9938ff554 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -276,7 +276,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { }; UnpackedKind::Lifetime(lt) } - GenericParamDefKind::Type(_) => { + GenericParamDefKind::Type(ty) => { let i = param.index as usize; // Handle Self first, so we can adjust the index to match the AST. @@ -284,24 +284,18 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { return UnpackedKind::Type(ty); } - let has_default = match param.kind { - GenericParamDefKind::Type(ty) => ty.has_default, - _ => unreachable!() - }; - let i = i - (lt_accepted + own_self); let ty = if i < ty_provided { // A provided type parameter. self.ast_ty_to_ty(¶meters.types[i]) } else if infer_types { // No type parameters were provided, we can infer all. - let ty_var = if !default_needs_object_self(param) { + if !default_needs_object_self(param) { self.ty_infer_for_def(param, span) } else { self.ty_infer(span) - }; - ty_var - } else if has_default { + } + } else if ty.has_default { // No type parameter provided, but a default exists. // If we are converting an object type, then the diff --git a/src/librustc_typeck/check/method/confirm.rs b/src/librustc_typeck/check/method/confirm.rs index c208e0fae6429..e2b4380fda2a5 100644 --- a/src/librustc_typeck/check/method/confirm.rs +++ b/src/librustc_typeck/check/method/confirm.rs @@ -318,36 +318,28 @@ impl<'a, 'gcx, 'tcx> ConfirmContext<'a, 'gcx, 'tcx> { let provided = &segment.parameters; let own_counts = method_generics.own_counts(); Substs::for_item(self.tcx, pick.item.def_id, |param, _| { - match param.kind { - GenericParamDefKind::Lifetime => { - let i = param.index as usize; - let lt = if i < parent_substs.len() { - parent_substs.region_at(i) - } else if let Some(lifetime) - = provided.as_ref().and_then(|p| p.lifetimes.get(i - parent_substs.len())) { - AstConv::ast_region_to_region(self.fcx, lifetime, Some(param)) - } else { - self.region_var_for_def(self.span, param) - }; - UnpackedKind::Lifetime(lt) - } - GenericParamDefKind::Type(_) => { - let i = param.index as usize; - let ty = if i < parent_substs.len() { - parent_substs.type_at(i) - } else if let Some(ast_ty) - = provided.as_ref().and_then(|p| { - let idx = - i - parent_substs.len() - own_counts.lifetimes; - p.types.get(idx) - }) - { - self.to_ty(ast_ty) - } else { - self.type_var_for_def(self.span, param) - }; - UnpackedKind::Type(ty) + let i = param.index as usize; + if i < parent_substs.len() { + parent_substs[i].unpack() + } else { + match param.kind { + GenericParamDefKind::Lifetime => { + if let Some(lifetime) = provided.as_ref().and_then(|p| { + p.lifetimes.get(i - parent_substs.len()) + }) { + return UnpackedKind::Lifetime( + AstConv::ast_region_to_region(self.fcx, lifetime, Some(param))); + } + } + GenericParamDefKind::Type(_) => { + if let Some(ast_ty) = provided.as_ref().and_then(|p| { + p.types.get(i - parent_substs.len() - own_counts.lifetimes) + }) { + return UnpackedKind::Type(self.to_ty(ast_ty)); + } + } } + self.var_for_def(self.span, param) } }) } diff --git a/src/librustc_typeck/check/method/mod.rs b/src/librustc_typeck/check/method/mod.rs index 298b8548e36e7..f02f70caef9b8 100644 --- a/src/librustc_typeck/check/method/mod.rs +++ b/src/librustc_typeck/check/method/mod.rs @@ -256,20 +256,16 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // Construct a trait-reference `self_ty : Trait` let substs = Substs::for_item(self.tcx, trait_def_id, |param, _| { match param.kind { - GenericParamDefKind::Lifetime => { - UnpackedKind::Lifetime(self.region_var_for_def(span, param)) - } + GenericParamDefKind::Lifetime => {} GenericParamDefKind::Type(_) => { - let ty = if param.index == 0 { - self_ty + if param.index == 0 { + return UnpackedKind::Type(self_ty); } else if let Some(ref input_types) = opt_input_types { - input_types[param.index as usize - 1] - } else { - self.type_var_for_def(span, param) - }; - UnpackedKind::Type(ty) + return UnpackedKind::Type(input_types[param.index as usize - 1]); + } } } + self.var_for_def(span, param) }); let trait_ref = ty::TraitRef::new(trait_def_id, substs); diff --git a/src/librustc_typeck/check/method/probe.rs b/src/librustc_typeck/check/method/probe.rs index a96796bb148cb..54fea4ab00a68 100644 --- a/src/librustc_typeck/check/method/probe.rs +++ b/src/librustc_typeck/check/method/probe.rs @@ -1389,26 +1389,17 @@ impl<'a, 'gcx, 'tcx> ProbeContext<'a, 'gcx, 'tcx> { xform_fn_sig.subst(self.tcx, substs) } else { let substs = Substs::for_item(self.tcx, method, |param, _| { - match param.kind { - GenericParamDefKind::Lifetime => { - let i = param.index as usize; - let lt = if i < substs.len() { - substs.region_at(i) - } else { + let i = param.index as usize; + if i < substs.len() { + substs[i].unpack() + } else { + match param.kind { + GenericParamDefKind::Lifetime => { // In general, during probe we erase regions. See // `impl_self_ty()` for an explanation. - self.tcx.types.re_erased - }; - UnpackedKind::Lifetime(lt) - } - GenericParamDefKind::Type(_) => { - let i = param.index as usize; - let ty = if i < substs.len() { - substs.type_at(i) - } else { - self.type_var_for_def(self.span, param) - }; - UnpackedKind::Type(ty) + UnpackedKind::Lifetime(self.tcx.types.re_erased) + } + GenericParamDefKind::Type(_) => self.var_for_def(self.span, param), } } }); diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 99e47f92daf0f..0b0659729ef8b 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -1746,7 +1746,11 @@ impl<'a, 'gcx, 'tcx> AstConv<'gcx, 'tcx> for FnCtxt<'a, 'gcx, 'tcx> { fn ty_infer_for_def(&self, ty_param_def: &ty::GenericParamDef, span: Span) -> Ty<'tcx> { - self.type_var_for_def(span, ty_param_def) + if let UnpackedKind::Type(ty) = self.var_for_def(span, ty_param_def) { + ty + } else { + unreachable!() + } } fn projected_ty_from_poly_trait_ref(&self, @@ -4759,17 +4763,26 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { (None, None) => (0, false) }; let substs = Substs::for_item(self.tcx, def.def_id(), |param, substs| { + let mut i = param.index as usize; + + let segment = if i < fn_start { + if let GenericParamDefKind::Type(_) = param.kind { + // Handle Self first, so we can adjust the index to match the AST. + if has_self && i == 0 { + return opt_self_ty.map(|ty| UnpackedKind::Type(ty)).unwrap_or_else(|| { + self.var_for_def(span, param) + }); + } + } + i -= has_self as usize; + type_segment + } else { + i -= fn_start; + fn_segment + }; + match param.kind { GenericParamDefKind::Lifetime => { - let mut i = param.index as usize; - - let segment = if i < fn_start { - i -= has_self as usize; - type_segment - } else { - i -= fn_start; - fn_segment - }; let lifetimes = segment.map_or(&[][..], |(s, _)| { s.parameters.as_ref().map_or(&[][..], |p| &p.lifetimes[..]) }); @@ -4782,21 +4795,6 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { UnpackedKind::Lifetime(lt) } GenericParamDefKind::Type(_) => { - let mut i = param.index as usize; - - let segment = if i < fn_start { - // Handle Self first, so we can adjust the index to match the AST. - if has_self && i == 0 { - return UnpackedKind::Type(opt_self_ty.unwrap_or_else(|| { - self.type_var_for_def(span, param) - })); - } - i -= has_self as usize; - type_segment - } else { - i -= fn_start; - fn_segment - }; let (types, infer_types) = segment.map_or((&[][..], true), |(s, _)| { (s.parameters.as_ref().map_or(&[][..], |p| &p.types[..]), s.infer_types) }); @@ -4811,24 +4809,23 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { _ => unreachable!() }; - let ty = if let Some(ast_ty) = types.get(i) { + if let Some(ast_ty) = types.get(i) { // A provided type parameter. - self.to_ty(ast_ty) + UnpackedKind::Type(self.to_ty(ast_ty)) } else if !infer_types && has_default { // No type parameter provided, but a default exists. let default = self.tcx.type_of(param.def_id); - self.normalize_ty( + UnpackedKind::Type(self.normalize_ty( span, default.subst_spanned(self.tcx, substs, Some(span)) - ) + )) } else { // No type parameters were provided, we can infer all. // This can also be reached in some error cases: // We prefer to use inference variables instead of // TyError to let type inference recover somewhat. - self.type_var_for_def(span, param) - }; - UnpackedKind::Type(ty) + self.var_for_def(span, param) + } } } }); From e9c28b2564c26767b6cab2f95e851389b4c1b014 Mon Sep 17 00:00:00 2001 From: varkor Date: Tue, 15 May 2018 13:15:49 +0100 Subject: [PATCH 36/40] Use Kind instead of UnpackedKind in Substs methods --- src/librustc/infer/mod.rs | 8 ++--- src/librustc/traits/mod.rs | 8 ++--- src/librustc/ty/context.rs | 6 ++-- src/librustc/ty/subst.rs | 17 ++++------ src/librustc/ty/util.rs | 2 +- src/librustc_mir/monomorphize/collector.rs | 8 ++--- src/librustc_mir/shim.rs | 6 ++-- src/librustc_typeck/astconv.rs | 36 +++++++++------------ src/librustc_typeck/check/closure.rs | 6 ++-- src/librustc_typeck/check/method/confirm.rs | 10 +++--- src/librustc_typeck/check/method/mod.rs | 6 ++-- src/librustc_typeck/check/method/probe.rs | 15 ++++----- src/librustc_typeck/check/mod.rs | 24 +++++++------- src/librustc_typeck/check/wfcheck.rs | 9 +++--- src/librustc_typeck/collect.rs | 8 ++--- 15 files changed, 75 insertions(+), 94 deletions(-) diff --git a/src/librustc/infer/mod.rs b/src/librustc/infer/mod.rs index 7a1e255dc5d0c..38db58b1e0006 100644 --- a/src/librustc/infer/mod.rs +++ b/src/librustc/infer/mod.rs @@ -21,7 +21,7 @@ use hir::def_id::DefId; use middle::free_region::RegionRelations; use middle::region; use middle::lang_items; -use ty::subst::{UnpackedKind, Substs}; +use ty::subst::{Kind, Substs}; use ty::{TyVid, IntVid, FloatVid}; use ty::{self, Ty, TyCtxt, GenericParamDefKind}; use ty::error::{ExpectedFound, TypeError, UnconstrainedNumeric}; @@ -908,12 +908,12 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { pub fn var_for_def(&self, span: Span, param: &ty::GenericParamDef) - -> UnpackedKind<'tcx> { + -> Kind<'tcx> { match param.kind { GenericParamDefKind::Lifetime => { // Create a region inference variable for the given // region parameter definition. - UnpackedKind::Lifetime(self.next_region_var(EarlyBoundRegion(span, param.name))) + self.next_region_var(EarlyBoundRegion(span, param.name)).into() } GenericParamDefKind::Type(_) => { // Create a type inference variable for the given @@ -930,7 +930,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { false, TypeVariableOrigin::TypeParameterDefinition(span, param.name)); - UnpackedKind::Type(self.tcx.mk_var(ty_var_id)) + self.tcx.mk_var(ty_var_id).into() } } } diff --git a/src/librustc/traits/mod.rs b/src/librustc/traits/mod.rs index 4b5c767b03145..36fedab9e7993 100644 --- a/src/librustc/traits/mod.rs +++ b/src/librustc/traits/mod.rs @@ -22,7 +22,7 @@ use hir::def_id::DefId; use infer::outlives::env::OutlivesEnvironment; use middle::region; use middle::const_val::ConstEvalErr; -use ty::subst::{UnpackedKind, Substs}; +use ty::subst::Substs; use ty::{self, AdtKind, Slice, Ty, TyCtxt, GenericParamDefKind, TypeFoldable, ToPredicate}; use ty::error::{ExpectedFound, TypeError}; use infer::{InferCtxt}; @@ -843,11 +843,9 @@ fn vtable_methods<'a, 'tcx>( let substs = trait_ref.map_bound(|trait_ref| { Substs::for_item(tcx, def_id, |param, _| { match param.kind { - GenericParamDefKind::Lifetime => { - UnpackedKind::Lifetime(tcx.types.re_erased) - } + GenericParamDefKind::Lifetime => tcx.types.re_erased.into(), GenericParamDefKind::Type(_) => { - UnpackedKind::Type(trait_ref.substs.type_for_def(param)) + trait_ref.substs.type_for_def(param).into() } } }) diff --git a/src/librustc/ty/context.rs b/src/librustc/ty/context.rs index 66c451e819310..592f04ca9136a 100644 --- a/src/librustc/ty/context.rs +++ b/src/librustc/ty/context.rs @@ -32,7 +32,7 @@ use middle::lang_items; use middle::resolve_lifetime::{self, ObjectLifetimeDefault}; use middle::stability; use mir::{self, Mir, interpret}; -use ty::subst::{Kind, UnpackedKind, Substs, Subst}; +use ty::subst::{Kind, Substs, Subst}; use ty::ReprOptions; use ty::Instance; use traits; @@ -2331,10 +2331,10 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { GenericParamDefKind::Lifetime => bug!(), GenericParamDefKind::Type(ty_param) => { if param.index == 0 { - UnpackedKind::Type(ty) + ty.into() } else { assert!(ty_param.has_default); - UnpackedKind::Type(self.type_of(param.def_id).subst(self, substs)) + self.type_of(param.def_id).subst(self, substs).into() } } } diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index 5c2b5c5cd4557..3c016b38aff41 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -184,12 +184,9 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { Substs::for_item(tcx, def_id, |param, _| { match param.kind { GenericParamDefKind::Lifetime => { - UnpackedKind::Lifetime( - tcx.mk_region(ty::ReEarlyBound(param.to_early_bound_region_data()))) - } - GenericParamDefKind::Type(_) => { - UnpackedKind::Type(tcx.mk_ty_param_from_def(param)) + tcx.mk_region(ty::ReEarlyBound(param.to_early_bound_region_data())).into() } + GenericParamDefKind::Type(_) => tcx.mk_ty_param_from_def(param).into(), } }) } @@ -203,7 +200,7 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { def_id: DefId, mut mk_kind: F) -> &'tcx Substs<'tcx> - where F: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> UnpackedKind<'tcx> + where F: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Kind<'tcx> { let defs = tcx.generics_of(def_id); let mut substs = Vec::with_capacity(defs.count()); @@ -216,7 +213,7 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { def_id: DefId, mut mk_kind: F) -> &'tcx Substs<'tcx> - where F: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> UnpackedKind<'tcx> + where F: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Kind<'tcx> { let defs = tcx.generics_of(def_id); let mut result = Vec::with_capacity(defs.count()); @@ -229,7 +226,7 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { tcx: TyCtxt<'a, 'gcx, 'tcx>, defs: &ty::Generics, mk_kind: &mut F) - where F: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> UnpackedKind<'tcx> + where F: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Kind<'tcx> { if let Some(def_id) = defs.parent { @@ -242,12 +239,12 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { fn fill_single(substs: &mut Vec>, defs: &ty::Generics, mk_kind: &mut F) - where F: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> UnpackedKind<'tcx> + where F: FnMut(&ty::GenericParamDef, &[Kind<'tcx>]) -> Kind<'tcx> { for param in &defs.params { let kind = mk_kind(param, substs); assert_eq!(param.index as usize, substs.len()); - substs.push(kind.pack()); + substs.push(kind); } } diff --git a/src/librustc/ty/util.rs b/src/librustc/ty/util.rs index 91280e5b8a3fd..d5532f8f8355a 100644 --- a/src/librustc/ty/util.rs +++ b/src/librustc/ty/util.rs @@ -576,7 +576,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { pub fn empty_substs_for_def_id(self, item_def_id: DefId) -> &'tcx Substs<'tcx> { Substs::for_item(self, item_def_id, |param, _| { match param.kind { - GenericParamDefKind::Lifetime => UnpackedKind::Lifetime(self.types.re_erased), + GenericParamDefKind::Lifetime => self.types.re_erased.into(), GenericParamDefKind::Type(_) => { bug!("empty_substs_for_def_id: {:?} has type parameters", item_def_id) } diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index c8d4ccaf0bbb2..bff8f2246ab3f 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -196,7 +196,7 @@ use rustc::hir::def_id::DefId; use rustc::middle::const_val::ConstVal; use rustc::mir::interpret::{AllocId, ConstValue}; use rustc::middle::lang_items::{ExchangeMallocFnLangItem, StartFnLangItem}; -use rustc::ty::subst::{Substs, Kind, UnpackedKind}; +use rustc::ty::subst::{Substs, Kind}; use rustc::ty::{self, TypeFoldable, Ty, TyCtxt, GenericParamDefKind}; use rustc::ty::adjustment::CustomCoerceUnsized; use rustc::session::config; @@ -1114,11 +1114,9 @@ fn create_mono_items_for_default_impls<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let substs = Substs::for_item(tcx, method.def_id, |param, _| { match param.kind { - GenericParamDefKind::Lifetime => { - UnpackedKind::Lifetime(tcx.types.re_erased) - } + GenericParamDefKind::Lifetime => tcx.types.re_erased.into(), GenericParamDefKind::Type(_) => { - UnpackedKind::Type(trait_ref.substs.type_for_def(param)) + trait_ref.substs.type_for_def(param).into() } } }); diff --git a/src/librustc_mir/shim.rs b/src/librustc_mir/shim.rs index 8596d546b09a2..c79298d8dd2cf 100644 --- a/src/librustc_mir/shim.rs +++ b/src/librustc_mir/shim.rs @@ -13,7 +13,7 @@ use rustc::hir::def_id::DefId; use rustc::infer; use rustc::mir::*; use rustc::ty::{self, Ty, TyCtxt, GenericParamDefKind}; -use rustc::ty::subst::{Kind, UnpackedKind, Subst, Substs}; +use rustc::ty::subst::{Kind, Subst, Substs}; use rustc::ty::maps::Providers; use rustc_data_structures::indexed_vec::{IndexVec, Idx}; @@ -429,8 +429,8 @@ impl<'a, 'tcx> CloneShimBuilder<'a, 'tcx> { let substs = Substs::for_item(tcx, self.def_id, |param, _| { match param.kind { - GenericParamDefKind::Lifetime => UnpackedKind::Lifetime(tcx.types.re_erased), - GenericParamDefKind::Type(_) => UnpackedKind::Type(ty), + GenericParamDefKind::Lifetime => tcx.types.re_erased.into(), + GenericParamDefKind::Type(_) => ty.into(), } }); diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index 32ea9938ff554..dc7c8849f914e 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -269,31 +269,30 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { match param.kind { GenericParamDefKind::Lifetime => { let i = param.index as usize - own_self; - let lt = if let Some(lifetime) = parameters.lifetimes.get(i) { - self.ast_region_to_region(lifetime, Some(param)) + if let Some(lifetime) = parameters.lifetimes.get(i) { + self.ast_region_to_region(lifetime, Some(param)).into() } else { - tcx.types.re_static - }; - UnpackedKind::Lifetime(lt) + tcx.types.re_static.into() + } } GenericParamDefKind::Type(ty) => { let i = param.index as usize; // Handle Self first, so we can adjust the index to match the AST. if let (0, Some(ty)) = (i, self_ty) { - return UnpackedKind::Type(ty); + return ty.into(); } let i = i - (lt_accepted + own_self); - let ty = if i < ty_provided { + if i < ty_provided { // A provided type parameter. - self.ast_ty_to_ty(¶meters.types[i]) + self.ast_ty_to_ty(¶meters.types[i]).into() } else if infer_types { // No type parameters were provided, we can infer all. if !default_needs_object_self(param) { - self.ty_infer_for_def(param, span) + self.ty_infer_for_def(param, span).into() } else { - self.ty_infer(span) + self.ty_infer(span).into() } } else if ty.has_default { // No type parameter provided, but a default exists. @@ -314,20 +313,19 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { type parameters must be specified on object \ types")) .emit(); - tcx.types.err + tcx.types.err.into() } else { // This is a default type parameter. self.normalize_ty( span, tcx.at(span).type_of(param.def_id) .subst_spanned(tcx, substs, Some(span)) - ) + ).into() } } else { // We've already errored above about the mismatch. - tcx.types.err - }; - UnpackedKind::Type(ty) + tcx.types.err.into() + } } } }); @@ -1162,12 +1160,10 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { Substs::fill_item(&mut substs, tcx, parent_generics, &mut |param, _| { match param.kind { GenericParamDefKind::Lifetime => { - UnpackedKind::Lifetime( - tcx.mk_region(ty::ReEarlyBound(param.to_early_bound_region_data()))) - } - GenericParamDefKind::Type(_) => { - UnpackedKind::Type(tcx.mk_ty_param_from_def(param)) + tcx.mk_region( + ty::ReEarlyBound(param.to_early_bound_region_data())).into() } + GenericParamDefKind::Type(_) => tcx.mk_ty_param_from_def(param).into(), } }); diff --git a/src/librustc_typeck/check/closure.rs b/src/librustc_typeck/check/closure.rs index 152f020c4769e..c2ec6475b9c65 100644 --- a/src/librustc_typeck/check/closure.rs +++ b/src/librustc_typeck/check/closure.rs @@ -19,7 +19,7 @@ use rustc::infer::LateBoundRegionConversionTime; use rustc::infer::type_variable::TypeVariableOrigin; use rustc::traits::error_reporting::ArgKind; use rustc::ty::{self, ToPolyTraitRef, Ty, GenericParamDefKind}; -use rustc::ty::subst::{UnpackedKind, Substs}; +use rustc::ty::subst::Substs; use rustc::ty::TypeFoldable; use std::cmp; use std::iter; @@ -110,8 +110,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { span_bug!(expr.span, "closure has region param") } GenericParamDefKind::Type(_) => { - UnpackedKind::Type(self.infcx - .next_ty_var(TypeVariableOrigin::ClosureSynthetic(expr.span))) + self.infcx + .next_ty_var(TypeVariableOrigin::ClosureSynthetic(expr.span)).into() } } }); diff --git a/src/librustc_typeck/check/method/confirm.rs b/src/librustc_typeck/check/method/confirm.rs index e2b4380fda2a5..aa3a166d0656f 100644 --- a/src/librustc_typeck/check/method/confirm.rs +++ b/src/librustc_typeck/check/method/confirm.rs @@ -16,7 +16,7 @@ use hir::def_id::DefId; use rustc::ty::subst::Substs; use rustc::traits; use rustc::ty::{self, Ty, GenericParamDefKind}; -use rustc::ty::subst::{UnpackedKind, Subst}; +use rustc::ty::subst::Subst; use rustc::ty::adjustment::{Adjustment, Adjust, OverloadedDeref}; use rustc::ty::adjustment::{AllowTwoPhase, AutoBorrow, AutoBorrowMutability}; use rustc::ty::fold::TypeFoldable; @@ -320,22 +320,22 @@ impl<'a, 'gcx, 'tcx> ConfirmContext<'a, 'gcx, 'tcx> { Substs::for_item(self.tcx, pick.item.def_id, |param, _| { let i = param.index as usize; if i < parent_substs.len() { - parent_substs[i].unpack() + parent_substs[i] } else { match param.kind { GenericParamDefKind::Lifetime => { if let Some(lifetime) = provided.as_ref().and_then(|p| { p.lifetimes.get(i - parent_substs.len()) }) { - return UnpackedKind::Lifetime( - AstConv::ast_region_to_region(self.fcx, lifetime, Some(param))); + return AstConv::ast_region_to_region( + self.fcx, lifetime, Some(param)).into(); } } GenericParamDefKind::Type(_) => { if let Some(ast_ty) = provided.as_ref().and_then(|p| { p.types.get(i - parent_substs.len() - own_counts.lifetimes) }) { - return UnpackedKind::Type(self.to_ty(ast_ty)); + return self.to_ty(ast_ty).into(); } } } diff --git a/src/librustc_typeck/check/method/mod.rs b/src/librustc_typeck/check/method/mod.rs index f02f70caef9b8..15a8efd5885d7 100644 --- a/src/librustc_typeck/check/method/mod.rs +++ b/src/librustc_typeck/check/method/mod.rs @@ -20,7 +20,7 @@ use rustc::ty::subst::Substs; use rustc::traits; use rustc::ty::{self, Ty, ToPredicate, ToPolyTraitRef, TraitRef, TypeFoldable}; use rustc::ty::GenericParamDefKind; -use rustc::ty::subst::{UnpackedKind, Subst}; +use rustc::ty::subst::Subst; use rustc::infer::{self, InferOk}; use syntax::ast; @@ -259,9 +259,9 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { GenericParamDefKind::Lifetime => {} GenericParamDefKind::Type(_) => { if param.index == 0 { - return UnpackedKind::Type(self_ty); + return self_ty.into(); } else if let Some(ref input_types) = opt_input_types { - return UnpackedKind::Type(input_types[param.index as usize - 1]); + return input_types[param.index as usize - 1].into(); } } } diff --git a/src/librustc_typeck/check/method/probe.rs b/src/librustc_typeck/check/method/probe.rs index 54fea4ab00a68..6b860dbe8febb 100644 --- a/src/librustc_typeck/check/method/probe.rs +++ b/src/librustc_typeck/check/method/probe.rs @@ -17,7 +17,7 @@ use check::FnCtxt; use hir::def_id::DefId; use hir::def::Def; use namespace::Namespace; -use rustc::ty::subst::{UnpackedKind, Subst, Substs}; +use rustc::ty::subst::{Subst, Substs}; use rustc::traits::{self, ObligationCause}; use rustc::ty::{self, Ty, ToPolyTraitRef, ToPredicate, TraitRef, TypeFoldable}; use rustc::ty::GenericParamDefKind; @@ -1391,13 +1391,13 @@ impl<'a, 'gcx, 'tcx> ProbeContext<'a, 'gcx, 'tcx> { let substs = Substs::for_item(self.tcx, method, |param, _| { let i = param.index as usize; if i < substs.len() { - substs[i].unpack() + substs[i] } else { match param.kind { GenericParamDefKind::Lifetime => { // In general, during probe we erase regions. See // `impl_self_ty()` for an explanation. - UnpackedKind::Lifetime(self.tcx.types.re_erased) + self.tcx.types.re_erased.into() } GenericParamDefKind::Type(_) => self.var_for_def(self.span, param), } @@ -1415,13 +1415,10 @@ impl<'a, 'gcx, 'tcx> ProbeContext<'a, 'gcx, 'tcx> { fn fresh_item_substs(&self, def_id: DefId) -> &'tcx Substs<'tcx> { Substs::for_item(self.tcx, def_id, |param, _| { match param.kind { - GenericParamDefKind::Lifetime => { - UnpackedKind::Lifetime(self.tcx.types.re_erased) - } + GenericParamDefKind::Lifetime => self.tcx.types.re_erased.into(), GenericParamDefKind::Type(_) => { - UnpackedKind::Type(self.next_ty_var( - TypeVariableOrigin::SubstitutionPlaceholder( - self.tcx.def_span(def_id)))) + self.next_ty_var(TypeVariableOrigin::SubstitutionPlaceholder( + self.tcx.def_span(def_id))).into() } } }) diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 0b0659729ef8b..2e9f31dd15e1e 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -1746,11 +1746,10 @@ impl<'a, 'gcx, 'tcx> AstConv<'gcx, 'tcx> for FnCtxt<'a, 'gcx, 'tcx> { fn ty_infer_for_def(&self, ty_param_def: &ty::GenericParamDef, span: Span) -> Ty<'tcx> { - if let UnpackedKind::Type(ty) = self.var_for_def(span, ty_param_def) { - ty - } else { - unreachable!() + if let UnpackedKind::Type(ty) = self.var_for_def(span, ty_param_def).unpack() { + return ty; } + unreachable!() } fn projected_ty_from_poly_trait_ref(&self, @@ -4769,7 +4768,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { if let GenericParamDefKind::Type(_) = param.kind { // Handle Self first, so we can adjust the index to match the AST. if has_self && i == 0 { - return opt_self_ty.map(|ty| UnpackedKind::Type(ty)).unwrap_or_else(|| { + return opt_self_ty.map(|ty| Kind::from(ty)).unwrap_or_else(|| { self.var_for_def(span, param) }); } @@ -4787,12 +4786,11 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { s.parameters.as_ref().map_or(&[][..], |p| &p.lifetimes[..]) }); - let lt = if let Some(lifetime) = lifetimes.get(i) { - AstConv::ast_region_to_region(self, lifetime, Some(param)) + if let Some(lifetime) = lifetimes.get(i) { + AstConv::ast_region_to_region(self, lifetime, Some(param)).into() } else { - self.re_infer(span, Some(param)).unwrap() - }; - UnpackedKind::Lifetime(lt) + self.re_infer(span, Some(param)).unwrap().into() + } } GenericParamDefKind::Type(_) => { let (types, infer_types) = segment.map_or((&[][..], true), |(s, _)| { @@ -4811,14 +4809,14 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { if let Some(ast_ty) = types.get(i) { // A provided type parameter. - UnpackedKind::Type(self.to_ty(ast_ty)) + self.to_ty(ast_ty).into() } else if !infer_types && has_default { // No type parameter provided, but a default exists. let default = self.tcx.type_of(param.def_id); - UnpackedKind::Type(self.normalize_ty( + self.normalize_ty( span, default.subst_spanned(self.tcx, substs, Some(span)) - )) + ).into() } else { // No type parameters were provided, we can infer all. // This can also be reached in some error cases: diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index 5c6a78de313b6..34978c4e31bef 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -14,7 +14,7 @@ use constrained_type_params::{identify_constrained_type_params, Parameter}; use hir::def_id::DefId; use rustc::traits::{self, ObligationCauseCode}; use rustc::ty::{self, Lift, Ty, TyCtxt, GenericParamDefKind}; -use rustc::ty::subst::{UnpackedKind, Substs}; +use rustc::ty::subst::Substs; use rustc::ty::util::ExplicitSelf; use rustc::util::nodemap::{FxHashSet, FxHashMap}; use rustc::middle::lang_items; @@ -409,8 +409,7 @@ fn check_where_clauses<'a, 'gcx, 'fcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'gcx>, match param.kind { GenericParamDefKind::Lifetime => { // All regions are identity. - UnpackedKind::Lifetime( - fcx.tcx.mk_region(ty::ReEarlyBound(param.to_early_bound_region_data()))) + fcx.tcx.mk_region(ty::ReEarlyBound(param.to_early_bound_region_data())).into() } GenericParamDefKind::Type(_) => { // If the param has a default, @@ -419,11 +418,11 @@ fn check_where_clauses<'a, 'gcx, 'fcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'gcx>, // and it's not a dependent default if !default_ty.needs_subst() { // then substitute with the default. - return UnpackedKind::Type(default_ty); + return default_ty.into(); } } // Mark unwanted params as err. - UnpackedKind::Type(fcx.tcx.types.err) + fcx.tcx.types.err.into() } } }); diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 1a2480bf45e3b..8eb0507835954 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -30,7 +30,7 @@ use constrained_type_params as ctp; use middle::lang_items::SizedTraitLangItem; use middle::resolve_lifetime as rl; use rustc::mir::mono::Linkage; -use rustc::ty::subst::{UnpackedKind, Substs}; +use rustc::ty::subst::Substs; use rustc::ty::GenericParamDefKind; use rustc::ty::{ToPredicate, ReprOptions}; use rustc::ty::{self, AdtKind, ToPolyTraitRef, Ty, TyCtxt}; @@ -1101,11 +1101,9 @@ fn type_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, match param.kind { GenericParamDefKind::Lifetime => { let region = param.to_early_bound_region_data(); - UnpackedKind::Lifetime(tcx.mk_region(ty::ReEarlyBound(region))) - } - GenericParamDefKind::Type(_) => { - UnpackedKind::Type(tcx.mk_ty_param_from_def(param)) + tcx.mk_region(ty::ReEarlyBound(region)).into() } + GenericParamDefKind::Type(_) => tcx.mk_ty_param_from_def(param).into(), } }) }; From 0a9371ab7738109c41bbd9c3ae2e3bd4ce49121e Mon Sep 17 00:00:00 2001 From: varkor Date: Tue, 15 May 2018 13:35:53 +0100 Subject: [PATCH 37/40] Add mk_param_from_def --- src/librustc/traits/mod.rs | 2 +- src/librustc/ty/context.rs | 9 +++++++-- src/librustc/ty/subst.rs | 18 ++++-------------- src/librustc_mir/monomorphize/collector.rs | 2 +- src/librustc_traits/dropck_outlives.rs | 11 ++++++++--- src/librustc_typeck/astconv.rs | 8 +------- src/librustc_typeck/check/wfcheck.rs | 2 +- src/librustc_typeck/collect.rs | 9 +-------- 8 files changed, 24 insertions(+), 37 deletions(-) diff --git a/src/librustc/traits/mod.rs b/src/librustc/traits/mod.rs index 36fedab9e7993..154c6815bb666 100644 --- a/src/librustc/traits/mod.rs +++ b/src/librustc/traits/mod.rs @@ -845,7 +845,7 @@ fn vtable_methods<'a, 'tcx>( match param.kind { GenericParamDefKind::Lifetime => tcx.types.re_erased.into(), GenericParamDefKind::Type(_) => { - trait_ref.substs.type_for_def(param).into() + trait_ref.substs[param.index as usize] } } }) diff --git a/src/librustc/ty/context.rs b/src/librustc/ty/context.rs index 592f04ca9136a..3c345fcd9ee61 100644 --- a/src/librustc/ty/context.rs +++ b/src/librustc/ty/context.rs @@ -2472,8 +2472,13 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { self.mk_ty_param(0, keywords::SelfType.name().as_interned_str()) } - pub fn mk_ty_param_from_def(self, def: &ty::GenericParamDef) -> Ty<'tcx> { - self.mk_ty_param(def.index, def.name) + pub fn mk_param_from_def(self, param: &ty::GenericParamDef) -> Kind<'tcx> { + match param.kind { + GenericParamDefKind::Lifetime => { + self.mk_region(ty::ReEarlyBound(param.to_early_bound_region_data())).into() + } + GenericParamDefKind::Type(_) => self.mk_ty_param(param.index, param.name).into(), + } } pub fn mk_anon(self, def_id: DefId, substs: &'tcx Substs<'tcx>) -> Ty<'tcx> { diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index 3c016b38aff41..b94b3e17f862f 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -11,7 +11,7 @@ // Type substitutions. use hir::def_id::DefId; -use ty::{self, Lift, Slice, Region, Ty, TyCtxt, GenericParamDefKind}; +use ty::{self, Lift, Slice, Region, Ty, TyCtxt}; use ty::fold::{TypeFoldable, TypeFolder, TypeVisitor}; use serialize::{self, Encodable, Encoder, Decodable, Decoder}; @@ -182,12 +182,7 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { pub fn identity_for_item(tcx: TyCtxt<'a, 'gcx, 'tcx>, def_id: DefId) -> &'tcx Substs<'tcx> { Substs::for_item(tcx, def_id, |param, _| { - match param.kind { - GenericParamDefKind::Lifetime => { - tcx.mk_region(ty::ReEarlyBound(param.to_early_bound_region_data())).into() - } - GenericParamDefKind::Type(_) => tcx.mk_ty_param_from_def(param).into(), - } + tcx.mk_param_from_def(param) }) } @@ -293,13 +288,8 @@ impl<'a, 'gcx, 'tcx> Substs<'tcx> { } #[inline] - pub fn type_for_def(&self, ty_param_def: &ty::GenericParamDef) -> Ty<'tcx> { - self.type_at(ty_param_def.index as usize) - } - - #[inline] - pub fn region_for_def(&self, def: &ty::GenericParamDef) -> ty::Region<'tcx> { - self.region_at(def.index as usize) + pub fn type_for_def(&self, def: &ty::GenericParamDef) -> Kind<'tcx> { + self.type_at(def.index as usize).into() } /// Transform from substitutions for a child of `source_ancestor` diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index bff8f2246ab3f..dc2009a026003 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -1116,7 +1116,7 @@ fn create_mono_items_for_default_impls<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, match param.kind { GenericParamDefKind::Lifetime => tcx.types.re_erased.into(), GenericParamDefKind::Type(_) => { - trait_ref.substs.type_for_def(param).into() + trait_ref.substs[param.index as usize] } } }); diff --git a/src/librustc_traits/dropck_outlives.rs b/src/librustc_traits/dropck_outlives.rs index 6c2128de27217..7a39b46f799d2 100644 --- a/src/librustc_traits/dropck_outlives.rs +++ b/src/librustc_traits/dropck_outlives.rs @@ -14,7 +14,7 @@ use rustc::traits::{FulfillmentContext, Normalized, ObligationCause}; use rustc::traits::query::{CanonicalTyGoal, NoSolution}; use rustc::traits::query::dropck_outlives::{DtorckConstraint, DropckOutlivesResult}; use rustc::ty::{self, ParamEnvAnd, Ty, TyCtxt}; -use rustc::ty::subst::Subst; +use rustc::ty::subst::{UnpackedKind, Subst}; use rustc::util::nodemap::FxHashSet; use rustc_data_structures::sync::Lrc; use syntax::codemap::{Span, DUMMY_SP}; @@ -278,11 +278,16 @@ crate fn adt_dtorck_constraint<'a, 'tcx>( debug!("dtorck_constraint: {:?}", def); if def.is_phantom_data() { - // The first generic parameter here is guaranteed to be a type because it's `PhantomData`. + // The first generic parameter here is guaranteed to be a type because it's + // `PhantomData`. let param = &tcx.generics_of(def_id).params[0]; + let ty = match tcx.mk_param_from_def(param).unpack() { + UnpackedKind::Type(ty) => ty, + _ => unreachable!(), + }; let result = DtorckConstraint { outlives: vec![], - dtorck_types: vec![tcx.mk_ty_param_from_def(param)], + dtorck_types: vec![ty], overflows: vec![], }; debug!("dtorck_constraint: {:?} => {:?}", def, result); diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index dc7c8849f914e..c1868467503f8 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -1158,13 +1158,7 @@ impl<'o, 'gcx: 'tcx, 'tcx> AstConv<'gcx, 'tcx>+'o { if let Some(parent_id) = generics.parent { let parent_generics = tcx.generics_of(parent_id); Substs::fill_item(&mut substs, tcx, parent_generics, &mut |param, _| { - match param.kind { - GenericParamDefKind::Lifetime => { - tcx.mk_region( - ty::ReEarlyBound(param.to_early_bound_region_data())).into() - } - GenericParamDefKind::Type(_) => tcx.mk_ty_param_from_def(param).into(), - } + tcx.mk_param_from_def(param) }); // Replace all lifetimes with 'static diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index 34978c4e31bef..6b873c093c02f 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -409,7 +409,7 @@ fn check_where_clauses<'a, 'gcx, 'fcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'gcx>, match param.kind { GenericParamDefKind::Lifetime => { // All regions are identity. - fcx.tcx.mk_region(ty::ReEarlyBound(param.to_early_bound_region_data())).into() + fcx.tcx.mk_param_from_def(param) } GenericParamDefKind::Type(_) => { // If the param has a default, diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index 8eb0507835954..d659dae250337 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -31,7 +31,6 @@ use middle::lang_items::SizedTraitLangItem; use middle::resolve_lifetime as rl; use rustc::mir::mono::Linkage; use rustc::ty::subst::Substs; -use rustc::ty::GenericParamDefKind; use rustc::ty::{ToPredicate, ReprOptions}; use rustc::ty::{self, AdtKind, ToPolyTraitRef, Ty, TyCtxt}; use rustc::ty::maps::Providers; @@ -1098,13 +1097,7 @@ fn type_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let substs = ty::ClosureSubsts { substs: Substs::for_item(tcx, def_id, |param, _| { - match param.kind { - GenericParamDefKind::Lifetime => { - let region = param.to_early_bound_region_data(); - tcx.mk_region(ty::ReEarlyBound(region)).into() - } - GenericParamDefKind::Type(_) => tcx.mk_ty_param_from_def(param).into(), - } + tcx.mk_param_from_def(param) }) }; From 39a68e9069a8673be1e3a51173327f82c9daf986 Mon Sep 17 00:00:00 2001 From: varkor Date: Tue, 15 May 2018 13:48:04 +0100 Subject: [PATCH 38/40] Clean up dropck_outlives PhantomData handling --- src/librustc_traits/dropck_outlives.rs | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/src/librustc_traits/dropck_outlives.rs b/src/librustc_traits/dropck_outlives.rs index 7a39b46f799d2..219c6b9aefba5 100644 --- a/src/librustc_traits/dropck_outlives.rs +++ b/src/librustc_traits/dropck_outlives.rs @@ -14,7 +14,7 @@ use rustc::traits::{FulfillmentContext, Normalized, ObligationCause}; use rustc::traits::query::{CanonicalTyGoal, NoSolution}; use rustc::traits::query::dropck_outlives::{DtorckConstraint, DropckOutlivesResult}; use rustc::ty::{self, ParamEnvAnd, Ty, TyCtxt}; -use rustc::ty::subst::{UnpackedKind, Subst}; +use rustc::ty::subst::{Subst, Substs}; use rustc::util::nodemap::FxHashSet; use rustc_data_structures::sync::Lrc; use syntax::codemap::{Span, DUMMY_SP}; @@ -280,14 +280,11 @@ crate fn adt_dtorck_constraint<'a, 'tcx>( if def.is_phantom_data() { // The first generic parameter here is guaranteed to be a type because it's // `PhantomData`. - let param = &tcx.generics_of(def_id).params[0]; - let ty = match tcx.mk_param_from_def(param).unpack() { - UnpackedKind::Type(ty) => ty, - _ => unreachable!(), - }; + let substs = Substs::identity_for_item(tcx, def_id); + assert_eq!(substs.len(), 1); let result = DtorckConstraint { outlives: vec![], - dtorck_types: vec![ty], + dtorck_types: vec![substs.type_at(0)], overflows: vec![], }; debug!("dtorck_constraint: {:?} => {:?}", def, result); From 5ea91ac531de9e309a495538a84f84ec9653bd51 Mon Sep 17 00:00:00 2001 From: varkor Date: Tue, 15 May 2018 13:53:20 +0100 Subject: [PATCH 39/40] Collapse Substs::identity_for_item in collect --- src/librustc_typeck/collect.rs | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index d659dae250337..c2dde2d2e014b 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -1096,9 +1096,7 @@ fn type_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } let substs = ty::ClosureSubsts { - substs: Substs::for_item(tcx, def_id, |param, _| { - tcx.mk_param_from_def(param) - }) + substs: Substs::identity_for_item(tcx, def_id), }; tcx.mk_closure(def_id, substs) From 5be2bdb498249d71a4a5671f73224727784a1203 Mon Sep 17 00:00:00 2001 From: varkor Date: Tue, 15 May 2018 14:52:53 +0100 Subject: [PATCH 40/40] One must always remember to clean up after themselves --- src/librustc/infer/mod.rs | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/src/librustc/infer/mod.rs b/src/librustc/infer/mod.rs index 38db58b1e0006..1cc65dcfd1027 100644 --- a/src/librustc/infer/mod.rs +++ b/src/librustc/infer/mod.rs @@ -924,11 +924,12 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { // used in a path such as `Foo::::new()` will // use an inference variable for `C` with `[T, U]` // as the substitutions for the default, `(T, U)`. - let ty_var_id = self.type_variables - .borrow_mut() - .new_var(self.universe(), - false, - TypeVariableOrigin::TypeParameterDefinition(span, param.name)); + let ty_var_id = + self.type_variables + .borrow_mut() + .new_var(self.universe(), + false, + TypeVariableOrigin::TypeParameterDefinition(span, param.name)); self.tcx.mk_var(ty_var_id).into() }