diff --git a/src/librustc/hir/lowering.rs b/src/librustc/hir/lowering.rs index 536d682566a72..5cc517a4afd1b 100644 --- a/src/librustc/hir/lowering.rs +++ b/src/librustc/hir/lowering.rs @@ -780,8 +780,9 @@ impl<'a> LoweringContext<'a> { _ => None, }), |this| { + let itctx = ImplTraitContext::Universal(parent_id); this.collect_in_band_defs(parent_id, anonymous_lifetime_mode, |this| { - (this.lower_generics(generics), f(this)) + (this.lower_generics(generics, itctx), f(this)) }) }, ); @@ -1043,7 +1044,11 @@ impl<'a> LoweringContext<'a> { }), |this| { hir::TyBareFn(P(hir::BareFnTy { - generic_params: this.lower_generic_params(&f.generic_params, &NodeMap()), + generic_params: this.lower_generic_params( + &f.generic_params, + &NodeMap(), + ImplTraitContext::Disallowed, + ), unsafety: this.lower_unsafety(f.unsafety), abi: f.abi, decl: this.lower_fn_decl(&f.decl, None, false), @@ -1784,7 +1789,12 @@ impl<'a> LoweringContext<'a> { } } - fn lower_ty_param(&mut self, tp: &TyParam, add_bounds: &[TyParamBound]) -> hir::TyParam { + fn lower_ty_param( + &mut self, + tp: &TyParam, + add_bounds: &[TyParamBound], + itctx: ImplTraitContext, + ) -> hir::TyParam { let mut name = self.lower_ident(tp.ident); // Don't expose `Self` (recovered "keyword used as ident" parse error). @@ -1794,7 +1804,6 @@ impl<'a> LoweringContext<'a> { name = Symbol::gensym("Self"); } - let itctx = ImplTraitContext::Universal(self.resolver.definitions().local_def_id(tp.id)); let mut bounds = self.lower_bounds(&tp.bounds, itctx); if !add_bounds.is_empty() { bounds = bounds @@ -1878,6 +1887,7 @@ impl<'a> LoweringContext<'a> { &mut self, params: &Vec, add_bounds: &NodeMap>, + itctx: ImplTraitContext, ) -> hir::HirVec { params .iter() @@ -1888,12 +1898,13 @@ impl<'a> LoweringContext<'a> { 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() } - fn lower_generics(&mut self, g: &Generics) -> hir::Generics { + fn lower_generics(&mut self, g: &Generics, itctx: ImplTraitContext) -> hir::Generics { // Collect `?Trait` bounds in where clause and move them to parameter definitions. // FIXME: This could probably be done with less rightward drift. Also looks like two control // paths where report_error is called are also the only paths that advance to after @@ -1946,7 +1957,7 @@ impl<'a> LoweringContext<'a> { } hir::Generics { - params: self.lower_generic_params(&g.params, &add_bounds), + params: self.lower_generic_params(&g.params, &add_bounds, itctx), where_clause: self.lower_where_clause(&g.where_clause), span: g.span, } @@ -1980,6 +1991,7 @@ impl<'a> LoweringContext<'a> { bound_generic_params: this.lower_generic_params( bound_generic_params, &NodeMap(), + ImplTraitContext::Disallowed, ), bounded_ty: this.lower_ty(bounded_ty, ImplTraitContext::Disallowed), bounds: bounds @@ -2063,7 +2075,8 @@ impl<'a> LoweringContext<'a> { p: &PolyTraitRef, itctx: ImplTraitContext, ) -> hir::PolyTraitRef { - let bound_generic_params = self.lower_generic_params(&p.bound_generic_params, &NodeMap()); + let bound_generic_params = + self.lower_generic_params(&p.bound_generic_params, &NodeMap(), itctx); let trait_ref = self.with_parent_impl_lifetime_defs( &bound_generic_params .iter() @@ -2218,7 +2231,7 @@ impl<'a> LoweringContext<'a> { ItemKind::GlobalAsm(ref ga) => hir::ItemGlobalAsm(self.lower_global_asm(ga)), ItemKind::Ty(ref t, ref generics) => hir::ItemTy( self.lower_ty(t, ImplTraitContext::Disallowed), - self.lower_generics(generics), + self.lower_generics(generics, ImplTraitContext::Disallowed), ), ItemKind::Enum(ref enum_definition, ref generics) => hir::ItemEnum( hir::EnumDef { @@ -2228,15 +2241,21 @@ impl<'a> LoweringContext<'a> { .map(|x| self.lower_variant(x)) .collect(), }, - self.lower_generics(generics), + self.lower_generics(generics, ImplTraitContext::Disallowed), ), ItemKind::Struct(ref struct_def, ref generics) => { let struct_def = self.lower_variant_data(struct_def); - hir::ItemStruct(struct_def, self.lower_generics(generics)) + hir::ItemStruct( + struct_def, + self.lower_generics(generics, ImplTraitContext::Disallowed), + ) } ItemKind::Union(ref vdata, ref generics) => { let vdata = self.lower_variant_data(vdata); - hir::ItemUnion(vdata, self.lower_generics(generics)) + hir::ItemUnion( + vdata, + self.lower_generics(generics, ImplTraitContext::Disallowed), + ) } ItemKind::Impl( unsafety, @@ -2315,13 +2334,13 @@ impl<'a> LoweringContext<'a> { hir::ItemTrait( self.lower_is_auto(is_auto), self.lower_unsafety(unsafety), - self.lower_generics(generics), + self.lower_generics(generics, ImplTraitContext::Disallowed), bounds, items, ) } ItemKind::TraitAlias(ref generics, ref bounds) => hir::ItemTraitAlias( - self.lower_generics(generics), + self.lower_generics(generics, ImplTraitContext::Disallowed), self.lower_bounds(bounds, ImplTraitContext::Disallowed), ), ItemKind::MacroDef(..) | ItemKind::Mac(..) => panic!("Shouldn't still be around"), @@ -2456,7 +2475,7 @@ impl<'a> LoweringContext<'a> { let (generics, node) = match i.node { TraitItemKind::Const(ref ty, ref default) => ( - this.lower_generics(&i.generics), + this.lower_generics(&i.generics, ImplTraitContext::Disallowed), hir::TraitItemKind::Const( this.lower_ty(ty, ImplTraitContext::Disallowed), default @@ -2497,7 +2516,7 @@ impl<'a> LoweringContext<'a> { ) } TraitItemKind::Type(ref bounds, ref default) => ( - this.lower_generics(&i.generics), + this.lower_generics(&i.generics, ImplTraitContext::Disallowed), hir::TraitItemKind::Type( this.lower_bounds(bounds, ImplTraitContext::Disallowed), default @@ -2554,7 +2573,7 @@ impl<'a> LoweringContext<'a> { ImplItemKind::Const(ref ty, ref expr) => { let body_id = this.lower_body(None, |this| this.lower_expr(expr)); ( - this.lower_generics(&i.generics), + this.lower_generics(&i.generics, ImplTraitContext::Disallowed), hir::ImplItemKind::Const( this.lower_ty(ty, ImplTraitContext::Disallowed), body_id, @@ -2585,7 +2604,7 @@ impl<'a> LoweringContext<'a> { ) } ImplItemKind::Type(ref ty) => ( - this.lower_generics(&i.generics), + this.lower_generics(&i.generics, ImplTraitContext::Disallowed), hir::ImplItemKind::Type(this.lower_ty(ty, ImplTraitContext::Disallowed)), ), ImplItemKind::Macro(..) => panic!("Shouldn't exist any more"), diff --git a/src/librustc/infer/anon_types/mod.rs b/src/librustc/infer/anon_types/mod.rs index eb5df697216a3..725ea9734abf4 100644 --- a/src/librustc/infer/anon_types/mod.rs +++ b/src/librustc/infer/anon_types/mod.rs @@ -533,10 +533,14 @@ impl<'cx, 'gcx, 'tcx> TypeFolder<'gcx, 'tcx> for ReverseMapper<'cx, 'gcx, 'tcx> match r { // ignore bound regions that appear in the type (e.g., this // would ignore `'r` in a type like `for<'r> fn(&'r u32)`. - ty::ReLateBound(..) => return r, + ty::ReLateBound(..) | // ignore `'static`, as that can appear anywhere - ty::ReStatic => return r, + ty::ReStatic | + + // ignore `ReScope`, as that can appear anywhere + // See `src/test/run-pass/issue-49556.rs` for example. + ty::ReScope(..) => return r, _ => { } } diff --git a/src/librustc/infer/error_reporting/mod.rs b/src/librustc/infer/error_reporting/mod.rs index 96c2309882108..8d314e251972d 100644 --- a/src/librustc/infer/error_reporting/mod.rs +++ b/src/librustc/infer/error_reporting/mod.rs @@ -181,7 +181,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { self.msg_span_from_early_bound_and_free_regions(region) }, ty::ReStatic => ("the static lifetime".to_owned(), None), - _ => bug!(), + _ => bug!("{:?}", region), } } diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index 446ef6bd32876..ebe918ed26c15 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -212,8 +212,6 @@ use monomorphize::item::{MonoItemExt, DefPathBasedNames, InstantiationMode}; use rustc_data_structures::bitvec::BitVector; -use std::iter; - #[derive(PartialEq, Eq, Hash, Clone, Copy, Debug)] pub enum MonoItemCollectionMode { Eager, @@ -1030,13 +1028,15 @@ impl<'b, 'a, 'v> RootCollector<'b, 'a, 'v> { // late-bound regions, since late-bound // regions must appear in the argument // listing. - let main_ret_ty = main_ret_ty.no_late_bound_regions().unwrap(); + let main_ret_ty = self.tcx.erase_regions( + &main_ret_ty.no_late_bound_regions().unwrap(), + ); let start_instance = Instance::resolve( self.tcx, ty::ParamEnv::reveal_all(), start_def_id, - self.tcx.mk_substs(iter::once(Kind::from(main_ret_ty))) + self.tcx.intern_substs(&[Kind::from(main_ret_ty)]) ).unwrap(); self.output.push(create_fn_mono_item(start_instance)); diff --git a/src/librustc_trans/base.rs b/src/librustc_trans/base.rs index 7ab3499ead369..a513ebbf6c7f4 100644 --- a/src/librustc_trans/base.rs +++ b/src/librustc_trans/base.rs @@ -82,7 +82,6 @@ use std::str; use std::sync::Arc; use std::time::{Instant, Duration}; use std::{i32, usize}; -use std::iter; use std::sync::mpsc; use syntax_pos::Span; use syntax_pos::symbol::InternedString; @@ -553,7 +552,9 @@ fn maybe_create_entry_wrapper(cx: &CodegenCx) { // late-bound regions, since late-bound // regions must appear in the argument // listing. - let main_ret_ty = main_ret_ty.no_late_bound_regions().unwrap(); + let main_ret_ty = cx.tcx.erase_regions( + &main_ret_ty.no_late_bound_regions().unwrap(), + ); if declare::get_defined_value(cx, "main").is_some() { // FIXME: We should be smart and show a better diagnostic here. @@ -580,8 +581,11 @@ fn maybe_create_entry_wrapper(cx: &CodegenCx) { let (start_fn, args) = if use_start_lang_item { let start_def_id = cx.tcx.require_lang_item(StartFnLangItem); - let start_fn = callee::resolve_and_get_fn(cx, start_def_id, cx.tcx.mk_substs( - iter::once(Kind::from(main_ret_ty)))); + let start_fn = callee::resolve_and_get_fn( + cx, + start_def_id, + cx.tcx.intern_substs(&[Kind::from(main_ret_ty)]), + ); (start_fn, vec![bx.pointercast(rust_main, Type::i8p(cx).ptr_to()), arg_argc, arg_argv]) } else { diff --git a/src/test/compile-fail/issue-47715.rs b/src/test/compile-fail/issue-47715.rs new file mode 100644 index 0000000000000..b6b720f088aee --- /dev/null +++ b/src/test/compile-fail/issue-47715.rs @@ -0,0 +1,38 @@ +// Copyright 2018 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +trait Foo {} + +trait Bar {} + +trait Iterable { + type Item; +} + +struct Container> { + //~^ ERROR `impl Trait` not allowed + field: T +} + +enum Enum> { + //~^ ERROR `impl Trait` not allowed + A(T), +} + +union Union + Copy> { + //~^ ERROR `impl Trait` not allowed + x: T, +} + +type Type> = T; +//~^ ERROR `impl Trait` not allowed + +fn main() { +} diff --git a/src/test/run-fail/rfc-1937-termination-trait/termination-trait-for-box-dyn-error.rs b/src/test/run-fail/rfc-1937-termination-trait/termination-trait-for-box-dyn-error.rs new file mode 100644 index 0000000000000..bd6bcf88a0caf --- /dev/null +++ b/src/test/run-fail/rfc-1937-termination-trait/termination-trait-for-box-dyn-error.rs @@ -0,0 +1,21 @@ +// Copyright 2018 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +// must-compile-successfully +// failure-status: 1 + +#![feature(dyn_trait)] + +use std::error::Error; +use std::io; + +fn main() -> Result<(), Box> { + Err(Box::new(io::Error::new(io::ErrorKind::Other, "returned Box from main()"))) +} diff --git a/src/test/run-fail/rfc-1937-termination-trait/termination-trait-for-str.rs b/src/test/run-fail/rfc-1937-termination-trait/termination-trait-for-str.rs new file mode 100644 index 0000000000000..9f01b0bff8955 --- /dev/null +++ b/src/test/run-fail/rfc-1937-termination-trait/termination-trait-for-str.rs @@ -0,0 +1,16 @@ +// Copyright 2018 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +// error-pattern: An error message for you +// failure-status: 1 + +fn main() -> Result<(), &'static str> { + Err("An error message for you") +} diff --git a/src/test/run-pass/issue-49556.rs b/src/test/run-pass/issue-49556.rs new file mode 100644 index 0000000000000..70ccee99f664d --- /dev/null +++ b/src/test/run-pass/issue-49556.rs @@ -0,0 +1,22 @@ +// Copyright 2018 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +fn iter<'a>(data: &'a [usize]) -> impl Iterator + 'a { + data.iter() + .map( + |x| x // fn(&'a usize) -> &'(ReScope) usize + ) + .map( + |x| *x // fn(&'(ReScope) usize) -> usize + ) +} + +fn main() { +} diff --git a/src/test/run-pass/rfc-1937-termination-trait/termination-trait-for-box-dyn-error.rs b/src/test/run-pass/rfc-1937-termination-trait/termination-trait-for-box-dyn-error.rs new file mode 100644 index 0000000000000..24c30a5abc22a --- /dev/null +++ b/src/test/run-pass/rfc-1937-termination-trait/termination-trait-for-box-dyn-error.rs @@ -0,0 +1,17 @@ +// Copyright 2018 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +#![feature(dyn_trait)] + +use std::error::Error; + +fn main() -> Result<(), Box> { + Ok(()) +} diff --git a/src/test/run-pass/rfc-1937-termination-trait/termination-trait-for-str.rs b/src/test/run-pass/rfc-1937-termination-trait/termination-trait-for-str.rs new file mode 100644 index 0000000000000..2023ff75564f7 --- /dev/null +++ b/src/test/run-pass/rfc-1937-termination-trait/termination-trait-for-str.rs @@ -0,0 +1,13 @@ +// Copyright 2018 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +fn main() -> Result<(), &'static str> { + Ok(()) +}