diff options
Diffstat (limited to 'compiler')
48 files changed, 325 insertions, 376 deletions
diff --git a/compiler/rustc_ast/src/ast.rs b/compiler/rustc_ast/src/ast.rs index 93d7a597681..d3f5a37fd6e 100644 --- a/compiler/rustc_ast/src/ast.rs +++ b/compiler/rustc_ast/src/ast.rs @@ -1017,7 +1017,7 @@ pub struct Local { /// ``` #[derive(Clone, Encodable, Decodable, Debug)] pub struct Arm { - pub attrs: Vec<Attribute>, + pub attrs: AttrVec, /// Match arm pattern, e.g. `10` in `match foo { 10 => {}, _ => {} }` pub pat: P<Pat>, /// Match arm guard, e.g. `n > 10` in `match foo { n if n > 10 => {}, _ => {} }` @@ -2293,7 +2293,7 @@ pub struct EnumDef { #[derive(Clone, Encodable, Decodable, Debug)] pub struct Variant { /// Attributes of the variant. - pub attrs: Vec<Attribute>, + pub attrs: AttrVec, /// Id of the variant (not the constructor, see `VariantData::ctor_id()`). pub id: NodeId, /// Span @@ -2474,7 +2474,7 @@ impl VisibilityKind { /// E.g., `bar: usize` as in `struct Foo { bar: usize }`. #[derive(Clone, Encodable, Decodable, Debug)] pub struct FieldDef { - pub attrs: Vec<Attribute>, + pub attrs: AttrVec, pub id: NodeId, pub span: Span, pub vis: Visibility, diff --git a/compiler/rustc_ast/src/mut_visit.rs b/compiler/rustc_ast/src/mut_visit.rs index 0b6099fd330..296766f8019 100644 --- a/compiler/rustc_ast/src/mut_visit.rs +++ b/compiler/rustc_ast/src/mut_visit.rs @@ -420,7 +420,7 @@ pub fn noop_visit_use_tree<T: MutVisitor>(use_tree: &mut UseTree, vis: &mut T) { pub fn noop_flat_map_arm<T: MutVisitor>(mut arm: Arm, vis: &mut T) -> SmallVec<[Arm; 1]> { let Arm { attrs, pat, guard, body, span, id, is_placeholder: _ } = &mut arm; - visit_attrs(attrs, vis); + visit_thin_attrs(attrs, vis); vis.visit_id(id); vis.visit_pat(pat); visit_opt(guard, |guard| vis.visit_expr(guard)); @@ -504,7 +504,7 @@ pub fn noop_flat_map_variant<T: MutVisitor>( let Variant { ident, vis, attrs, id, data, disr_expr, span, is_placeholder: _ } = &mut variant; visitor.visit_ident(ident); visitor.visit_vis(vis); - visit_attrs(attrs, visitor); + visit_thin_attrs(attrs, visitor); visitor.visit_id(id); visitor.visit_variant_data(data); visit_opt(disr_expr, |disr_expr| visitor.visit_anon_const(disr_expr)); @@ -918,7 +918,7 @@ pub fn noop_flat_map_field_def<T: MutVisitor>( visitor.visit_vis(vis); visitor.visit_id(id); visitor.visit_ty(ty); - visit_attrs(attrs, visitor); + visit_thin_attrs(attrs, visitor); smallvec![fd] } diff --git a/compiler/rustc_ast_passes/src/ast_validation.rs b/compiler/rustc_ast_passes/src/ast_validation.rs index 357a2e65cf7..acc41d9f644 100644 --- a/compiler/rustc_ast_passes/src/ast_validation.rs +++ b/compiler/rustc_ast_passes/src/ast_validation.rs @@ -652,7 +652,7 @@ impl<'a> AstValidator<'a> { self.err_handler() .struct_span_err( *span, - "only foreign or `unsafe extern \"C\" functions may be C-variadic", + "only foreign or `unsafe extern \"C\"` functions may be C-variadic", ) .emit(); } diff --git a/compiler/rustc_ast_pretty/src/pprust/tests.rs b/compiler/rustc_ast_pretty/src/pprust/tests.rs index b1a73a0bf02..8abd85a5a52 100644 --- a/compiler/rustc_ast_pretty/src/pprust/tests.rs +++ b/compiler/rustc_ast_pretty/src/pprust/tests.rs @@ -49,7 +49,7 @@ fn test_variant_to_string() { kind: ast::VisibilityKind::Inherited, tokens: None, }, - attrs: Vec::new(), + attrs: ast::AttrVec::new(), id: ast::DUMMY_NODE_ID, data: ast::VariantData::Unit(ast::DUMMY_NODE_ID), disr_expr: None, diff --git a/compiler/rustc_builtin_macros/src/deriving/encodable.rs b/compiler/rustc_builtin_macros/src/deriving/encodable.rs index 01a57bea14e..c5f3a9d3379 100644 --- a/compiler/rustc_builtin_macros/src/deriving/encodable.rs +++ b/compiler/rustc_builtin_macros/src/deriving/encodable.rs @@ -124,12 +124,7 @@ pub fn expand_deriving_rustc_encodable( explicit_self: borrowed_explicit_self(), args: vec![( Ptr(Box::new(Literal(Path::new_local(typaram))), Borrowed(None, Mutability::Mut)), - // FIXME: we could use `sym::s` here, but making `s` a static - // symbol changes the symbol index ordering in a way that makes - // ui/lint/rfc-2457-non-ascii-idents/lint-confusable-idents.rs - // fail. The linting code should be fixed so that its output - // does not depend on the symbol index ordering. - Symbol::intern("s"), + sym::s, )], ret_ty: Literal(Path::new_( pathvec_std!(result::Result), diff --git a/compiler/rustc_builtin_macros/src/format.rs b/compiler/rustc_builtin_macros/src/format.rs index 7e88b58c0e2..00f2f37146d 100644 --- a/compiler/rustc_builtin_macros/src/format.rs +++ b/compiler/rustc_builtin_macros/src/format.rs @@ -939,6 +939,7 @@ pub fn expand_preparsed_format_args( let msg = "format argument must be a string literal"; let fmt_sp = efmt.span; + let efmt_kind_is_lit: bool = matches!(efmt.kind, ast::ExprKind::Lit(_)); let (fmt_str, fmt_style, fmt_span) = match expr_to_spanned_string(ecx, efmt, msg) { Ok(mut fmt) if append_newline => { fmt.0 = Symbol::intern(&format!("{}\n", fmt.0)); @@ -989,7 +990,19 @@ pub fn expand_preparsed_format_args( if !parser.errors.is_empty() { let err = parser.errors.remove(0); - let sp = fmt_span.from_inner(err.span); + let sp = if efmt_kind_is_lit { + fmt_span.from_inner(err.span) + } else { + // The format string could be another macro invocation, e.g.: + // format!(concat!("abc", "{}"), 4); + // However, `err.span` is an inner span relative to the *result* of + // the macro invocation, which is why we would get a nonsensical + // result calling `fmt_span.from_inner(err.span)` as above, and + // might even end up inside a multibyte character (issue #86085). + // Therefore, we conservatively report the error for the entire + // argument span here. + fmt_span + }; let mut e = ecx.struct_span_err(sp, &format!("invalid format string: {}", err.description)); e.span_label(sp, err.label + " in format string"); if let Some(note) = err.note { diff --git a/compiler/rustc_data_structures/src/sorted_map/index_map.rs b/compiler/rustc_data_structures/src/sorted_map/index_map.rs index 01cd1cec924..65689ab769c 100644 --- a/compiler/rustc_data_structures/src/sorted_map/index_map.rs +++ b/compiler/rustc_data_structures/src/sorted_map/index_map.rs @@ -94,13 +94,15 @@ impl<I: Idx, K: Ord, V> SortedIndexMultiMap<I, K, V> { Q: Ord + ?Sized, K: Borrow<Q>, { - // FIXME: This should be in the standard library as `equal_range`. See rust-lang/rfcs#2184. match self.binary_search_idx(key) { Err(_) => self.idxs_to_items_enumerated(&[]), Ok(idx) => { - let start = self.find_lower_bound(key, idx); - let end = self.find_upper_bound(key, idx); + let start = self.idx_sorted_by_item_key[..idx] + .partition_point(|&i| self.items[i].0.borrow() != key); + let end = idx + + self.idx_sorted_by_item_key[idx..] + .partition_point(|&i| self.items[i].0.borrow() == key); self.idxs_to_items_enumerated(&self.idx_sorted_by_item_key[start..end]) } } @@ -114,50 +116,6 @@ impl<I: Idx, K: Ord, V> SortedIndexMultiMap<I, K, V> { self.idx_sorted_by_item_key.binary_search_by(|&idx| self.items[idx].0.borrow().cmp(key)) } - /// Returns the index into the `idx_sorted_by_item_key` array of the first item equal to - /// `key`. - /// - /// `initial` must be an index into that same array for an item that is equal to `key`. - fn find_lower_bound<Q>(&self, key: &Q, initial: usize) -> usize - where - Q: Ord + ?Sized, - K: Borrow<Q>, - { - debug_assert!(self.items[self.idx_sorted_by_item_key[initial]].0.borrow() == key); - - // FIXME: At present, this uses linear search, meaning lookup is only `O(log n)` if duplicate - // entries are rare. It would be better to start with a linear search for the common case but - // fall back to an exponential search if many duplicates are found. This applies to - // `upper_bound` as well. - let mut start = initial; - while start != 0 && self.items[self.idx_sorted_by_item_key[start - 1]].0.borrow() == key { - start -= 1; - } - - start - } - - /// Returns the index into the `idx_sorted_by_item_key` array of the first item greater than - /// `key`, or `self.len()` if no such item exists. - /// - /// `initial` must be an index into that same array for an item that is equal to `key`. - fn find_upper_bound<Q>(&self, key: &Q, initial: usize) -> usize - where - Q: Ord + ?Sized, - K: Borrow<Q>, - { - debug_assert!(self.items[self.idx_sorted_by_item_key[initial]].0.borrow() == key); - - // See the FIXME for `find_lower_bound`. - let mut end = initial + 1; - let len = self.items.len(); - while end < len && self.items[self.idx_sorted_by_item_key[end]].0.borrow() == key { - end += 1; - } - - end - } - fn idxs_to_items_enumerated(&'a self, idxs: &'a [I]) -> impl 'a + Iterator<Item = (I, &'a V)> { idxs.iter().map(move |&idx| (idx, &self.items[idx].1)) } diff --git a/compiler/rustc_expand/src/build.rs b/compiler/rustc_expand/src/build.rs index ef5b97a9469..824df2757ea 100644 --- a/compiler/rustc_expand/src/build.rs +++ b/compiler/rustc_expand/src/build.rs @@ -432,7 +432,7 @@ impl<'a> ExtCtxt<'a> { pub fn arm(&self, span: Span, pat: P<ast::Pat>, expr: P<ast::Expr>) -> ast::Arm { ast::Arm { - attrs: vec![], + attrs: AttrVec::new(), pat, guard: None, body: expr, diff --git a/compiler/rustc_hir/src/hir.rs b/compiler/rustc_hir/src/hir.rs index 577d43b1c8e..bb8d6386d8a 100644 --- a/compiler/rustc_hir/src/hir.rs +++ b/compiler/rustc_hir/src/hir.rs @@ -1205,8 +1205,6 @@ pub struct ExprField<'hir> { pub enum BlockCheckMode { DefaultBlock, UnsafeBlock(UnsafeSource), - PushUnsafeBlock(UnsafeSource), - PopUnsafeBlock(UnsafeSource), } #[derive(Copy, Clone, PartialEq, Encodable, Debug, HashStable_Generic)] diff --git a/compiler/rustc_hir_pretty/src/lib.rs b/compiler/rustc_hir_pretty/src/lib.rs index 2b932b7c953..d11dca1cba4 100644 --- a/compiler/rustc_hir_pretty/src/lib.rs +++ b/compiler/rustc_hir_pretty/src/lib.rs @@ -1070,8 +1070,6 @@ impl<'a> State<'a> { ) { match blk.rules { hir::BlockCheckMode::UnsafeBlock(..) => self.word_space("unsafe"), - hir::BlockCheckMode::PushUnsafeBlock(..) => self.word_space("push_unsafe"), - hir::BlockCheckMode::PopUnsafeBlock(..) => self.word_space("pop_unsafe"), hir::BlockCheckMode::DefaultBlock => (), } self.maybe_print_comment(blk.span.lo()); diff --git a/compiler/rustc_infer/src/infer/error_reporting/nice_region_error/util.rs b/compiler/rustc_infer/src/infer/error_reporting/nice_region_error/util.rs index 17a56046a5c..8dcdd4b149e 100644 --- a/compiler/rustc_infer/src/infer/error_reporting/nice_region_error/util.rs +++ b/compiler/rustc_infer/src/infer/error_reporting/nice_region_error/util.rs @@ -56,33 +56,42 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> { let fn_decl = hir.fn_decl_by_hir_id(owner_id).unwrap(); let poly_fn_sig = self.tcx().fn_sig(id); let fn_sig = self.tcx().liberate_late_bound_regions(id, poly_fn_sig); - body.params.iter().enumerate().find_map(|(index, param)| { - // May return None; sometimes the tables are not yet populated. - let ty = fn_sig.inputs()[index]; - let mut found_anon_region = false; - let new_param_ty = self.tcx().fold_regions(ty, &mut false, |r, _| { - if *r == *anon_region { - found_anon_region = true; - replace_region + body.params + .iter() + .take(if fn_sig.c_variadic { + fn_sig.inputs().len() + } else { + assert_eq!(fn_sig.inputs().len(), body.params.len()); + body.params.len() + }) + .enumerate() + .find_map(|(index, param)| { + // May return None; sometimes the tables are not yet populated. + let ty = fn_sig.inputs()[index]; + let mut found_anon_region = false; + let new_param_ty = self.tcx().fold_regions(ty, &mut false, |r, _| { + if *r == *anon_region { + found_anon_region = true; + replace_region + } else { + r + } + }); + if found_anon_region { + let ty_hir_id = fn_decl.inputs[index].hir_id; + let param_ty_span = hir.span(ty_hir_id); + let is_first = index == 0; + Some(AnonymousParamInfo { + param, + param_ty: new_param_ty, + param_ty_span, + bound_region, + is_first, + }) } else { - r + None } - }); - if found_anon_region { - let ty_hir_id = fn_decl.inputs[index].hir_id; - let param_ty_span = hir.span(ty_hir_id); - let is_first = index == 0; - Some(AnonymousParamInfo { - param, - param_ty: new_param_ty, - param_ty_span, - bound_region, - is_first, - }) - } else { - None - } - }) + }) } pub(super) fn future_return_type( diff --git a/compiler/rustc_interface/src/tests.rs b/compiler/rustc_interface/src/tests.rs index 5d8a6084f2e..f486a82ef95 100644 --- a/compiler/rustc_interface/src/tests.rs +++ b/compiler/rustc_interface/src/tests.rs @@ -715,7 +715,6 @@ fn test_debugging_options_tracking_hash() { tracked!(no_codegen, true); tracked!(no_generate_arange_section, true); tracked!(no_link, true); - tracked!(no_profiler_runtime, true); tracked!(osx_rpath_install_name, true); tracked!(panic_abort_tests, true); tracked!(plt, Some(true)); @@ -724,6 +723,7 @@ fn test_debugging_options_tracking_hash() { tracked!(print_fuel, Some("abc".to_string())); tracked!(profile, true); tracked!(profile_emit, Some(PathBuf::from("abc"))); + tracked!(profiler_runtime, None); tracked!(relax_elf_relocations, Some(true)); tracked!(relro_level, Some(RelroLevel::Full)); tracked!(simulate_remapped_rust_src_base, Some(PathBuf::from("/rustc/abc"))); diff --git a/compiler/rustc_metadata/src/creader.rs b/compiler/rustc_metadata/src/creader.rs index d73cfe35dc4..03a46efec3c 100644 --- a/compiler/rustc_metadata/src/creader.rs +++ b/compiler/rustc_metadata/src/creader.rs @@ -769,28 +769,32 @@ impl<'a> CrateLoader<'a> { } fn inject_profiler_runtime(&mut self, krate: &ast::Crate) { - if (self.sess.instrument_coverage() - || self.sess.opts.debugging_opts.profile - || self.sess.opts.cg.profile_generate.enabled()) - && !self.sess.opts.debugging_opts.no_profiler_runtime + let profiler_runtime = &self.sess.opts.debugging_opts.profiler_runtime; + + if !(profiler_runtime.is_some() + && (self.sess.instrument_coverage() + || self.sess.opts.debugging_opts.profile + || self.sess.opts.cg.profile_generate.enabled())) { - info!("loading profiler"); + return; + } - if self.sess.contains_name(&krate.attrs, sym::no_core) { - self.sess.err( - "`profiler_builtins` crate (required by compiler options) \ - is not compatible with crate attribute `#![no_core]`", - ); - } + info!("loading profiler"); + + let name = Symbol::intern(profiler_runtime.as_ref().unwrap()); + if name == sym::profiler_builtins && self.sess.contains_name(&krate.attrs, sym::no_core) { + self.sess.err( + "`profiler_builtins` crate (required by compiler options) \ + is not compatible with crate attribute `#![no_core]`", + ); + } - let name = sym::profiler_builtins; - let cnum = self.resolve_crate(name, DUMMY_SP, CrateDepKind::Implicit, None); - let data = self.cstore.get_crate_data(cnum); + let cnum = self.resolve_crate(name, DUMMY_SP, CrateDepKind::Implicit, None); + let data = self.cstore.get_crate_data(cnum); - // Sanity check the loaded crate to ensure it is indeed a profiler runtime - if !data.is_profiler_runtime() { - self.sess.err("the crate `profiler_builtins` is not a profiler runtime"); - } + // Sanity check the loaded crate to ensure it is indeed a profiler runtime + if !data.is_profiler_runtime() { + self.sess.err(&format!("the crate `{}` is not a profiler runtime", name)); } } diff --git a/compiler/rustc_metadata/src/locator.rs b/compiler/rustc_metadata/src/locator.rs index 6e736095090..8570bf30f80 100644 --- a/compiler/rustc_metadata/src/locator.rs +++ b/compiler/rustc_metadata/src/locator.rs @@ -1100,7 +1100,9 @@ impl CrateError { if sess.is_nightly_build() && std::env::var("CARGO").is_ok() { err.help("consider building the standard library from source with `cargo build -Zbuild-std`"); } - } else if crate_name == sym::profiler_builtins { + } else if Some(crate_name) + == sess.opts.debugging_opts.profiler_runtime.as_deref().map(Symbol::intern) + { err.note(&"the compiler may have been built without the profiler runtime"); } err.span_label(span, "can't find crate"); diff --git a/compiler/rustc_metadata/src/rmeta/decoder.rs b/compiler/rustc_metadata/src/rmeta/decoder.rs index 52cb1e1996e..48900fecd3e 100644 --- a/compiler/rustc_metadata/src/rmeta/decoder.rs +++ b/compiler/rustc_metadata/src/rmeta/decoder.rs @@ -252,6 +252,10 @@ impl<'a, 'tcx> DecodeContext<'a, 'tcx> { self.cdata.expect("missing CrateMetadata in DecodeContext") } + fn map_encoded_cnum_to_current(&self, cnum: CrateNum) -> CrateNum { + if cnum == LOCAL_CRATE { self.cdata().cnum } else { self.cdata().cnum_map[cnum] } + } + fn read_lazy_with_meta<T: ?Sized + LazyMeta>( &mut self, meta: T::Meta, @@ -324,10 +328,6 @@ impl<'a, 'tcx> TyDecoder<'tcx> for DecodeContext<'a, 'tcx> { r } - fn map_encoded_cnum_to_current(&self, cnum: CrateNum) -> CrateNum { - if cnum == LOCAL_CRATE { self.cdata().cnum } else { self.cdata().cnum_map[cnum] } - } - fn decode_alloc_id(&mut self) -> Result<rustc_middle::mir::interpret::AllocId, Self::Error> { if let Some(alloc_decoding_session) = self.alloc_decoding_session { alloc_decoding_session.decode_alloc_id(self) diff --git a/compiler/rustc_middle/src/dep_graph/dep_node.rs b/compiler/rustc_middle/src/dep_graph/dep_node.rs index 8476929eaec..aa54d1ae7b9 100644 --- a/compiler/rustc_middle/src/dep_graph/dep_node.rs +++ b/compiler/rustc_middle/src/dep_graph/dep_node.rs @@ -285,7 +285,7 @@ pub type DepNode = rustc_query_system::dep_graph::DepNode<DepKind>; // required that their size stay the same, but we don't want to change // it inadvertently. This assert just ensures we're aware of any change. #[cfg(any(target_arch = "x86", target_arch = "x86_64"))] -static_assert_size!(DepNode, 18); +static_assert_size!(DepNode, 17); #[cfg(not(any(target_arch = "x86", target_arch = "x86_64")))] static_assert_size!(DepNode, 24); diff --git a/compiler/rustc_middle/src/mir/interpret/error.rs b/compiler/rustc_middle/src/mir/interpret/error.rs index 7941800c7fa..cb2a355697d 100644 --- a/compiler/rustc_middle/src/mir/interpret/error.rs +++ b/compiler/rustc_middle/src/mir/interpret/error.rs @@ -518,4 +518,15 @@ impl InterpError<'_> { _ => false, } } + + /// Should this error be reported as a hard error, preventing compilation, or a soft error, + /// causing a deny-by-default lint? + pub fn is_hard_err(&self) -> bool { + use InterpError::*; + match *self { + MachineStop(ref err) => err.is_hard_err(), + InterpError::UndefinedBehavior(_) => true, + _ => false, + } + } } diff --git a/compiler/rustc_middle/src/mir/mod.rs b/compiler/rustc_middle/src/mir/mod.rs index 7ae7eab6e5a..0daaec272fd 100644 --- a/compiler/rustc_middle/src/mir/mod.rs +++ b/compiler/rustc_middle/src/mir/mod.rs @@ -494,8 +494,6 @@ impl<'tcx> Body<'tcx> { #[derive(Copy, Clone, PartialEq, Eq, Debug, TyEncodable, TyDecodable, HashStable)] pub enum Safety { Safe, - /// Unsafe because of a PushUnsafeBlock - BuiltinUnsafe, /// Unsafe because of an unsafe fn FnUnsafe, /// Unsafe because of an `unsafe` block diff --git a/compiler/rustc_middle/src/query/mod.rs b/compiler/rustc_middle/src/query/mod.rs index a6f9a7c96f0..dda407940e3 100644 --- a/compiler/rustc_middle/src/query/mod.rs +++ b/compiler/rustc_middle/src/query/mod.rs @@ -191,10 +191,6 @@ rustc_queries! { desc { |tcx| "elaborating item bounds for `{}`", tcx.def_path_str(key) } } - query projection_ty_from_predicates(key: (DefId, DefId)) -> Option<ty::ProjectionTy<'tcx>> { - desc { |tcx| "finding projection type inside predicates of `{}`", tcx.def_path_str(key.0) } - } - query native_libraries(_: CrateNum) -> Lrc<Vec<NativeLib>> { desc { "looking up the native libraries of a linked crate" } } diff --git a/compiler/rustc_middle/src/thir.rs b/compiler/rustc_middle/src/thir.rs index a5069113702..2f107e7b96c 100644 --- a/compiler/rustc_middle/src/thir.rs +++ b/compiler/rustc_middle/src/thir.rs @@ -97,12 +97,24 @@ pub struct Block { pub safety_mode: BlockSafety, } +#[derive(Debug, HashStable)] +pub struct Adt<'tcx> { + pub adt_def: &'tcx AdtDef, + pub variant_index: VariantIdx, + pub substs: SubstsRef<'tcx>, + + /// Optional user-given substs: for something like `let x = + /// Bar::<T> { ... }`. + pub user_ty: Option<Canonical<'tcx, UserType<'tcx>>>, + + pub fields: Box<[FieldExpr]>, + pub base: Option<FruInfo<'tcx>>, +} + #[derive(Copy, Clone, Debug, HashStable)] pub enum BlockSafety { Safe, ExplicitUnsafe(hir::HirId), - PushUnsafe, - PopUnsafe, } #[derive(Debug, HashStable)] @@ -145,7 +157,7 @@ pub enum StmtKind<'tcx> { // `Expr` is used a lot. Make sure it doesn't unintentionally get bigger. #[cfg(all(target_arch = "x86_64", target_pointer_width = "64"))] -rustc_data_structures::static_assert_size!(Expr<'_>, 144); +rustc_data_structures::static_assert_size!(Expr<'_>, 104); /// The Thir trait implementor lowers their expressions (`&'tcx H::Expr`) /// into instances of this `Expr` enum. This lowering can be done @@ -304,18 +316,7 @@ pub enum ExprKind<'tcx> { Tuple { fields: Box<[ExprId]>, }, - Adt { - adt_def: &'tcx AdtDef, - variant_index: VariantIdx, - substs: SubstsRef<'tcx>, - - /// Optional user-given substs: for something like `let x = - /// Bar::<T> { ... }`. - user_ty: Option<Canonical<'tcx, UserType<'tcx>>>, - - fields: Box<[FieldExpr]>, - base: Option<FruInfo<'tcx>>, - }, + Adt(Box<Adt<'tcx>>), PlaceTypeAscription { source: ExprId, /// Type that the user gave to this expression diff --git a/compiler/rustc_middle/src/ty/codec.rs b/compiler/rustc_middle/src/ty/codec.rs index d7767dc39cb..5ec665e913c 100644 --- a/compiler/rustc_middle/src/ty/codec.rs +++ b/compiler/rustc_middle/src/ty/codec.rs @@ -15,7 +15,7 @@ use crate::mir::{ use crate::ty::subst::SubstsRef; use crate::ty::{self, List, Ty, TyCtxt}; use rustc_data_structures::fx::FxHashMap; -use rustc_hir::def_id::{CrateNum, DefId}; +use rustc_hir::def_id::DefId; use rustc_serialize::{Decodable, Decoder, Encodable, Encoder}; use rustc_span::Span; use std::hash::Hash; @@ -179,8 +179,6 @@ pub trait TyDecoder<'tcx>: Decoder { where F: FnOnce(&mut Self) -> R; - fn map_encoded_cnum_to_current(&self, cnum: CrateNum) -> CrateNum; - fn positioned_at_shorthand(&self) -> bool { (self.peek_byte() & (SHORTHAND_OFFSET as u8)) != 0 } diff --git a/compiler/rustc_middle/src/ty/context.rs b/compiler/rustc_middle/src/ty/context.rs index d13cbdd1228..73991436b7b 100644 --- a/compiler/rustc_middle/src/ty/context.rs +++ b/compiler/rustc_middle/src/ty/context.rs @@ -53,6 +53,7 @@ use rustc_serialize::opaque::{FileEncodeResult, FileEncoder}; use rustc_session::config::{BorrowckMode, CrateType, OutputFilenames}; use rustc_session::lint::{Level, Lint}; use rustc_session::Session; +use rustc_span::def_id::StableCrateId; use rustc_span::source_map::MultiSpan; use rustc_span::symbol::{kw, sym, Ident, Symbol}; use rustc_span::{Span, DUMMY_SP}; @@ -1264,6 +1265,11 @@ impl<'tcx> TyCtxt<'tcx> { } } + #[inline] + pub fn stable_crate_id(self, cnum: CrateNum) -> StableCrateId { + self.def_path_hash(cnum.as_def_id()).stable_crate_id() + } + pub fn def_path_debug_str(self, def_id: DefId) -> String { // We are explicitly not going through queries here in order to get // crate name and disambiguator since this code is called from debug!() diff --git a/compiler/rustc_middle/src/ty/layout.rs b/compiler/rustc_middle/src/ty/layout.rs index 28a44b09de2..6b1ec1b0646 100644 --- a/compiler/rustc_middle/src/ty/layout.rs +++ b/compiler/rustc_middle/src/ty/layout.rs @@ -672,6 +672,15 @@ impl<'tcx> LayoutCx<'tcx, TyCtxt<'tcx>> { // SIMD vector types. ty::Adt(def, substs) if def.repr.simd() => { + if !def.is_struct() { + // Should have yielded E0517 by now. + tcx.sess.delay_span_bug( + DUMMY_SP, + "#[repr(simd)] was applied to an ADT that is not a struct", + ); + return Err(LayoutError::Unknown(ty)); + } + // Supported SIMD vectors are homogeneous ADTs with at least one field: // // * #[repr(simd)] struct S(T, T, T, T); diff --git a/compiler/rustc_middle/src/ty/query/on_disk_cache.rs b/compiler/rustc_middle/src/ty/query/on_disk_cache.rs index 5c42625306b..ebaef347f42 100644 --- a/compiler/rustc_middle/src/ty/query/on_disk_cache.rs +++ b/compiler/rustc_middle/src/ty/query/on_disk_cache.rs @@ -9,7 +9,7 @@ use rustc_data_structures::sync::{HashMapExt, Lock, Lrc, OnceCell}; use rustc_data_structures::thin_vec::ThinVec; use rustc_data_structures::unhash::UnhashMap; use rustc_errors::Diagnostic; -use rustc_hir::def_id::{CrateNum, DefId, DefIndex, LocalDefId, LOCAL_CRATE}; +use rustc_hir::def_id::{CrateNum, DefId, DefIndex, LocalDefId, StableCrateId, LOCAL_CRATE}; use rustc_hir::definitions::DefPathHash; use rustc_index::vec::{Idx, IndexVec}; use rustc_query_system::dep_graph::DepContext; @@ -18,7 +18,7 @@ use rustc_serialize::{ opaque::{self, FileEncodeResult, FileEncoder, IntEncodedWithFixedSize}, Decodable, Decoder, Encodable, Encoder, }; -use rustc_session::{CrateDisambiguator, Session}; +use rustc_session::Session; use rustc_span::hygiene::{ ExpnDataDecodeMode, ExpnDataEncodeMode, ExpnId, HygieneDecodeContext, HygieneEncodeContext, SyntaxContext, SyntaxContextData, @@ -51,8 +51,7 @@ pub struct OnDiskCache<'sess> { // session. current_diagnostics: Lock<FxHashMap<DepNodeIndex, Vec<Diagnostic>>>, - prev_cnums: Vec<(u32, String, CrateDisambiguator)>, - cnum_map: OnceCell<IndexVec<CrateNum, Option<CrateNum>>>, + cnum_map: OnceCell<UnhashMap<StableCrateId, CrateNum>>, source_map: &'sess SourceMap, file_index_to_stable_id: FxHashMap<SourceFileIndex, StableSourceFileId>, @@ -113,7 +112,6 @@ pub struct OnDiskCache<'sess> { #[derive(Encodable, Decodable)] struct Footer { file_index_to_stable_id: FxHashMap<SourceFileIndex, StableSourceFileId>, - prev_cnums: Vec<(u32, String, CrateDisambiguator)>, query_result_index: EncodedQueryResultIndex, diagnostics_index: EncodedQueryResultIndex, // The location of all allocations. @@ -186,7 +184,6 @@ impl<'sess> OnDiskCache<'sess> { serialized_data: data, file_index_to_stable_id: footer.file_index_to_stable_id, file_index_to_file: Default::default(), - prev_cnums: footer.prev_cnums, cnum_map: OnceCell::new(), source_map: sess.source_map(), current_diagnostics: Default::default(), @@ -207,7 +204,6 @@ impl<'sess> OnDiskCache<'sess> { serialized_data: Vec::new(), file_index_to_stable_id: Default::default(), file_index_to_file: Default::default(), - prev_cnums: vec![], cnum_map: OnceCell::new(), source_map, current_diagnostics: Default::default(), @@ -327,16 +323,6 @@ impl<'sess> OnDiskCache<'sess> { interpret_alloc_index }; - let sorted_cnums = sorted_cnums_including_local_crate(tcx); - let prev_cnums: Vec<_> = sorted_cnums - .iter() - .map(|&cnum| { - let crate_name = tcx.crate_name(cnum).to_string(); - let crate_disambiguator = tcx.crate_disambiguator(cnum); - (cnum.as_u32(), crate_name, crate_disambiguator) - }) - .collect(); - let mut syntax_contexts = FxHashMap::default(); let mut expn_ids = FxHashMap::default(); @@ -368,7 +354,6 @@ impl<'sess> OnDiskCache<'sess> { TAG_FILE_FOOTER, &Footer { file_index_to_stable_id, - prev_cnums, query_result_index, diagnostics_index, interpret_alloc_index, @@ -385,16 +370,7 @@ impl<'sess> OnDiskCache<'sess> { // DO NOT WRITE ANYTHING TO THE ENCODER AFTER THIS POINT! The address // of the footer must be the last thing in the data stream. - return Ok(()); - - fn sorted_cnums_including_local_crate(tcx: TyCtxt<'_>) -> Vec<CrateNum> { - let mut cnums = vec![LOCAL_CRATE]; - cnums.extend_from_slice(tcx.crates()); - cnums.sort_unstable(); - // Just to be sure... - cnums.dedup(); - cnums - } + Ok(()) }) } @@ -429,12 +405,11 @@ impl<'sess> OnDiskCache<'sess> { self.foreign_def_path_hashes.get(hash).copied() } - fn try_remap_cnum(&self, tcx: TyCtxt<'_>, cnum: u32) -> Option<CrateNum> { - let cnum_map = - self.cnum_map.get_or_init(|| Self::compute_cnum_map(tcx, &self.prev_cnums[..])); - debug!("try_remap_cnum({}): cnum_map={:?}", cnum, cnum_map); + fn try_remap_cnum(&self, tcx: TyCtxt<'_>, stable_crate_id: StableCrateId) -> Option<CrateNum> { + let cnum_map = self.cnum_map.get_or_init(|| Self::compute_cnum_map(tcx)); + debug!("try_remap_cnum({:?}): cnum_map={:?}", stable_crate_id, cnum_map); - cnum_map[CrateNum::from_u32(cnum)] + cnum_map.get(&stable_crate_id).copied() } pub(crate) fn store_foreign_def_id_hash(&self, def_id: DefId, hash: DefPathHash) { @@ -533,8 +508,7 @@ impl<'sess> OnDiskCache<'sess> { where T: Decodable<CacheDecoder<'a, 'tcx>>, { - let cnum_map = - self.cnum_map.get_or_init(|| Self::compute_cnum_map(tcx, &self.prev_cnums[..])); + let cnum_map = self.cnum_map.get_or_init(|| Self::compute_cnum_map(tcx)); let mut decoder = CacheDecoder { tcx, @@ -555,31 +529,16 @@ impl<'sess> OnDiskCache<'sess> { // current-session-`CrateNum`. There might be `CrateNum`s from the previous // `Session` that don't occur in the current one. For these, the mapping // maps to None. - fn compute_cnum_map( - tcx: TyCtxt<'_>, - prev_cnums: &[(u32, String, CrateDisambiguator)], - ) -> IndexVec<CrateNum, Option<CrateNum>> { + fn compute_cnum_map(tcx: TyCtxt<'_>) -> UnhashMap<StableCrateId, CrateNum> { tcx.dep_graph.with_ignore(|| { - let current_cnums = tcx - .all_crate_nums(()) + tcx.all_crate_nums(()) .iter() + .chain(std::iter::once(&LOCAL_CRATE)) .map(|&cnum| { - let crate_name = tcx.crate_name(cnum).to_string(); - let crate_disambiguator = tcx.crate_disambiguator(cnum); - ((crate_name, crate_disambiguator), cnum) + let hash = tcx.def_path_hash(cnum.as_def_id()).stable_crate_id(); + (hash, cnum) }) - .collect::<FxHashMap<_, _>>(); - - let map_size = prev_cnums.iter().map(|&(cnum, ..)| cnum).max().unwrap_or(0) + 1; - let mut map = IndexVec::from_elem_n(None, map_size as usize); - - for &(prev_cnum, ref crate_name, crate_disambiguator) in prev_cnums { - let key = (crate_name.clone(), crate_disambiguator); - map[CrateNum::from_u32(prev_cnum)] = current_cnums.get(&key).cloned(); - } - - map[LOCAL_CRATE] = Some(LOCAL_CRATE); - map + .collect() }) } @@ -612,7 +571,7 @@ impl<'sess> OnDiskCache<'sess> { debug!("def_path_hash_to_def_id({:?}): raw_def_id = {:?}", hash, raw_def_id); // If the owning crate no longer exists, the corresponding definition definitely // no longer exists. - let krate = self.try_remap_cnum(tcx, raw_def_id.krate)?; + let krate = self.try_remap_cnum(tcx, hash.stable_crate_id())?; debug!("def_path_hash_to_def_id({:?}): krate = {:?}", hash, krate); // If our `DefPathHash` corresponded to a definition in the local crate, // we should have either found it in `local_def_path_hash_to_def_id`, or @@ -644,7 +603,7 @@ pub struct CacheDecoder<'a, 'tcx> { tcx: TyCtxt<'tcx>, opaque: opaque::Decoder<'a>, source_map: &'a SourceMap, - cnum_map: &'a IndexVec<CrateNum, Option<CrateNum>>, + cnum_map: &'a UnhashMap<StableCrateId, CrateNum>, file_index_to_file: &'a Lock<FxHashMap<SourceFileIndex, Lrc<SourceFile>>>, file_index_to_stable_id: &'a FxHashMap<SourceFileIndex, StableSourceFileId>, alloc_decoding_session: AllocDecodingSession<'a>, @@ -765,10 +724,6 @@ impl<'a, 'tcx> TyDecoder<'tcx> for CacheDecoder<'a, 'tcx> { r } - fn map_encoded_cnum_to_current(&self, cnum: CrateNum) -> CrateNum { - self.cnum_map[cnum].unwrap_or_else(|| bug!("could not find new `CrateNum` for {:?}", cnum)) - } - fn decode_alloc_id(&mut self) -> Result<interpret::AllocId, Self::Error> { let alloc_decoding_session = self.alloc_decoding_session; alloc_decoding_session.decode_alloc_id(self) @@ -850,8 +805,9 @@ impl<'a, 'tcx> Decodable<CacheDecoder<'a, 'tcx>> for Span { impl<'a, 'tcx> Decodable<CacheDecoder<'a, 'tcx>> for CrateNum { fn decode(d: &mut CacheDecoder<'a, 'tcx>) -> Result<Self, String> { - let cnum = CrateNum::from_u32(u32::decode(d)?); - Ok(d.map_encoded_cnum_to_current(cnum)) + let stable_id = StableCrateId::decode(d)?; + let cnum = d.cnum_map[&stable_id]; + Ok(cnum) } } @@ -1061,6 +1017,15 @@ where } } +impl<'a, 'tcx, E> Encodable<CacheEncoder<'a, 'tcx, E>> for CrateNum +where + E: 'a + OpaqueEncoder, +{ + fn encode(&self, s: &mut CacheEncoder<'a, 'tcx, E>) -> Result<(), E::Error> { + s.tcx.stable_crate_id(*self).encode(s) + } +} + impl<'a, 'tcx, E> Encodable<CacheEncoder<'a, 'tcx, E>> for DefId where E: 'a + OpaqueEncoder, diff --git a/compiler/rustc_mir/src/borrow_check/diagnostics/conflict_errors.rs b/compiler/rustc_mir/src/borrow_check/diagnostics/conflict_errors.rs index 8b0761889b8..a0c9b43d5af 100644 --- a/compiler/rustc_mir/src/borrow_check/diagnostics/conflict_errors.rs +++ b/compiler/rustc_mir/src/borrow_check/diagnostics/conflict_errors.rs @@ -453,6 +453,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { &mut err, "", Some(borrow_span), + None, ); err.buffer(&mut self.errors_buffer); } @@ -498,6 +499,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { &mut err, "", None, + None, ); err } @@ -718,6 +720,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { &mut err, first_borrow_desc, None, + Some((issued_span, span)), ); err @@ -1076,6 +1079,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { &mut err, "", None, + None, ); } } else { @@ -1093,6 +1097,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { &mut err, "", None, + None, ); } @@ -1158,6 +1163,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { &mut err, "", None, + None, ); err.buffer(&mut self.errors_buffer); @@ -1236,6 +1242,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { &mut err, "", None, + None, ); let within = if borrow_spans.for_generator() { " by generator" } else { "" }; @@ -1614,6 +1621,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { &mut err, "", None, + None, ); self.explain_deref_coercion(loan, &mut err); diff --git a/compiler/rustc_mir/src/borrow_check/diagnostics/explain_borrow.rs b/compiler/rustc_mir/src/borrow_check/diagnostics/explain_borrow.rs index e9f1ecb9bbc..76de010d139 100644 --- a/compiler/rustc_mir/src/borrow_check/diagnostics/explain_borrow.rs +++ b/compiler/rustc_mir/src/borrow_check/diagnostics/explain_borrow.rs @@ -66,6 +66,7 @@ impl BorrowExplanation { err: &mut DiagnosticBuilder<'_>, borrow_desc: &str, borrow_span: Option<Span>, + multiple_borrow_span: Option<(Span, Span)>, ) { match *self { BorrowExplanation::UsedLater(later_use_kind, var_or_use_span, path_span) => { @@ -192,14 +193,23 @@ impl BorrowExplanation { if let Some(info) = &local_decl.is_block_tail { if info.tail_result_is_ignored { - err.span_suggestion_verbose( - info.span.shrink_to_hi(), - "consider adding semicolon after the expression so its \ - temporaries are dropped sooner, before the local variables \ - declared by the block are dropped", - ";".to_string(), - Applicability::MaybeIncorrect, - ); + // #85581: If the first mutable borrow's scope contains + // the second borrow, this suggestion isn't helpful. + if !multiple_borrow_span + .map(|(old, new)| { + old.to(info.span.shrink_to_hi()).contains(new) + }) + .unwrap_or(false) + { + err.span_suggestion_verbose( + info.span.shrink_to_hi(), + "consider adding semicolon after the expression so its \ + temporaries are dropped sooner, before the local variables \ + declared by the block are dropped", + ";".to_string(), + Applicability::MaybeIncorrect, + ); + } } else { err.note( "the temporary is part of an expression at the end of a \ diff --git a/compiler/rustc_mir/src/borrow_check/region_infer/opaque_types.rs b/compiler/rustc_mir/src/borrow_check/region_infer/opaque_types.rs index 3ec24156f22..f2d69255d50 100644 --- a/compiler/rustc_mir/src/borrow_check/region_infer/opaque_types.rs +++ b/compiler/rustc_mir/src/borrow_check/region_infer/opaque_types.rs @@ -60,33 +60,17 @@ impl<'tcx> RegionInferenceContext<'tcx> { debug!(?concrete_type, ?substs); let mut subst_regions = vec![self.universal_regions.fr_static]; - let universal_substs = - infcx.tcx.fold_regions(substs, &mut false, |region, _| match *region { - ty::ReVar(vid) => { - subst_regions.push(vid); - self.definitions[vid].external_name.unwrap_or_else(|| { - infcx.tcx.sess.delay_span_bug( - span, - "opaque type with non-universal region substs", - ); - infcx.tcx.lifetimes.re_static - }) - } - // We don't fold regions in the predicates of opaque - // types to `ReVar`s. This means that in a case like - // - // fn f<'a: 'a>() -> impl Iterator<Item = impl Sized> - // - // The inner opaque type has `'static` in its substs. - ty::ReStatic => region, - _ => { - infcx.tcx.sess.delay_span_bug( - span, - &format!("unexpected concrete region in borrowck: {:?}", region), - ); - region - } - }); + let universal_substs = infcx.tcx.fold_regions(substs, &mut false, |region, _| { + let vid = self.universal_regions.to_region_vid(region); + subst_regions.push(vid); + self.definitions[vid].external_name.unwrap_or_else(|| { + infcx + .tcx + .sess + .delay_span_bug(span, "opaque type with non-universal region substs"); + infcx.tcx.lifetimes.re_static + }) + }); subst_regions.sort(); subst_regions.dedup(); diff --git a/compiler/rustc_mir/src/const_eval/error.rs b/compiler/rustc_mir/src/const_eval/error.rs index fc21047ab72..17e8ab2a4da 100644 --- a/compiler/rustc_mir/src/const_eval/error.rs +++ b/compiler/rustc_mir/src/const_eval/error.rs @@ -157,7 +157,7 @@ impl<'tcx> ConstEvalErr<'tcx> { tcx: TyCtxtAt<'tcx>, message: &str, emit: impl FnOnce(DiagnosticBuilder<'_>), - mut lint_root: Option<hir::HirId>, + lint_root: Option<hir::HirId>, ) -> ErrorHandled { let finish = |mut err: DiagnosticBuilder<'_>, span_msg: Option<String>| { trace!("reporting const eval failure at {:?}", self.span); @@ -194,12 +194,6 @@ impl<'tcx> ConstEvalErr<'tcx> { _ => {} }; - // If we have a 'hard error', then set `lint_root` to `None` so that we don't - // emit a lint. - if matches!(&self.error, InterpError::MachineStop(err) if err.is_hard_err()) { - lint_root = None; - } - let err_msg = self.error.to_string(); // Regular case - emit a lint. diff --git a/compiler/rustc_mir/src/const_eval/eval_queries.rs b/compiler/rustc_mir/src/const_eval/eval_queries.rs index 460fea37461..536dbad4f76 100644 --- a/compiler/rustc_mir/src/const_eval/eval_queries.rs +++ b/compiler/rustc_mir/src/const_eval/eval_queries.rs @@ -312,22 +312,17 @@ pub fn eval_to_allocation_raw_provider<'tcx>( let err = ConstEvalErr::new(&ecx, error, None); // Some CTFE errors raise just a lint, not a hard error; see // <https://github.com/rust-lang/rust/issues/71800>. - let emit_as_lint = if let Some(def) = def.as_local() { + let is_hard_err = if let Some(def) = def.as_local() { // (Associated) consts only emit a lint, since they might be unused. - matches!(tcx.def_kind(def.did.to_def_id()), DefKind::Const | DefKind::AssocConst) + !matches!(tcx.def_kind(def.did.to_def_id()), DefKind::Const | DefKind::AssocConst) + // check if the inner InterpError is hard + || err.error.is_hard_err() } else { // use of broken constant from other crate: always an error - false + true }; - if emit_as_lint { - let hir_id = tcx.hir().local_def_id_to_hir_id(def.as_local().unwrap().did); - Err(err.report_as_lint( - tcx.at(tcx.def_span(def.did)), - "any use of this value will cause an error", - hir_id, - Some(err.span), - )) - } else { + + if is_hard_err { let msg = if is_static { Cow::from("could not evaluate static initializer") } else { @@ -345,6 +340,14 @@ pub fn eval_to_allocation_raw_provider<'tcx>( }; Err(err.report_as_error(ecx.tcx.at(ecx.cur_span()), &msg)) + } else { + let hir_id = tcx.hir().local_def_id_to_hir_id(def.as_local().unwrap().did); + Err(err.report_as_lint( + tcx.at(tcx.def_span(def.did)), + "any use of this value will cause an error", + hir_id, + Some(err.span), + )) } } Ok(mplace) => { diff --git a/compiler/rustc_mir/src/transform/check_unsafety.rs b/compiler/rustc_mir/src/transform/check_unsafety.rs index 103ddda1a1d..324a5257f5d 100644 --- a/compiler/rustc_mir/src/transform/check_unsafety.rs +++ b/compiler/rustc_mir/src/transform/check_unsafety.rs @@ -321,7 +321,6 @@ impl<'a, 'tcx> UnsafetyChecker<'a, 'tcx> { } false } - Safety::BuiltinUnsafe => true, Safety::ExplicitUnsafe(hir_id) => { // mark unsafe block as used if there are any unsafe operations inside if !violations.is_empty() { diff --git a/compiler/rustc_mir/src/transform/const_prop.rs b/compiler/rustc_mir/src/transform/const_prop.rs index 681d63c6fc9..b56c247127c 100644 --- a/compiler/rustc_mir/src/transform/const_prop.rs +++ b/compiler/rustc_mir/src/transform/const_prop.rs @@ -528,14 +528,14 @@ impl<'mir, 'tcx> ConstPropagator<'mir, 'tcx> { source_info: SourceInfo, message: &'static str, panic: AssertKind<impl std::fmt::Debug>, - ) -> Option<()> { - let lint_root = self.lint_root(source_info)?; - self.tcx.struct_span_lint_hir(lint, lint_root, source_info.span, |lint| { - let mut err = lint.build(message); - err.span_label(source_info.span, format!("{:?}", panic)); - err.emit() - }); - None + ) { + if let Some(lint_root) = self.lint_root(source_info) { + self.tcx.struct_span_lint_hir(lint, lint_root, source_info.span, |lint| { + let mut err = lint.build(message); + err.span_label(source_info.span, format!("{:?}", panic)); + err.emit() + }); + } } fn check_unary_op( @@ -557,7 +557,8 @@ impl<'mir, 'tcx> ConstPropagator<'mir, 'tcx> { source_info, "this arithmetic operation will overflow", AssertKind::OverflowNeg(val.to_const_int()), - )?; + ); + return None; } Some(()) @@ -602,7 +603,8 @@ impl<'mir, 'tcx> ConstPropagator<'mir, 'tcx> { }, r.to_const_int(), ), - )?; + ); + return None; } } @@ -617,7 +619,8 @@ impl<'mir, 'tcx> ConstPropagator<'mir, 'tcx> { source_info, "this arithmetic operation will overflow", AssertKind::Overflow(op, l.to_const_int(), r.to_const_int()), - )?; + ); + return None; } } Some(()) @@ -1202,12 +1205,9 @@ impl<'mir, 'tcx> MutVisitor<'tcx> for ConstPropagator<'mir, 'tcx> { let mut eval_to_int = |op| { // This can be `None` if the lhs wasn't const propagated and we just // triggered the assert on the value of the rhs. - match self.eval_operand(op, source_info) { - Some(op) => DbgVal::Val( - self.ecx.read_immediate(&op).unwrap().to_const_int(), - ), - None => DbgVal::Underscore, - } + self.eval_operand(op, source_info).map_or(DbgVal::Underscore, |op| { + DbgVal::Val(self.ecx.read_immediate(&op).unwrap().to_const_int()) + }) }; let msg = match msg { AssertKind::DivisionByZero(op) => { diff --git a/compiler/rustc_mir/src/util/pretty.rs b/compiler/rustc_mir/src/util/pretty.rs index c4e1e184ac5..f8325a3646f 100644 --- a/compiler/rustc_mir/src/util/pretty.rs +++ b/compiler/rustc_mir/src/util/pretty.rs @@ -99,7 +99,10 @@ pub fn dump_enabled<'tcx>(tcx: TyCtxt<'tcx>, pass_name: &str, def_id: DefId) -> }); filters.split('|').any(|or_filter| { or_filter.split('&').all(|and_filter| { - and_filter == "all" || pass_name.contains(and_filter) || node_path.contains(and_filter) + let and_filter_trimmed = and_filter.trim(); + and_filter_trimmed == "all" + || pass_name.contains(and_filter_trimmed) + || node_path.contains(and_filter_trimmed) }) }) } diff --git a/compiler/rustc_mir_build/src/build/block.rs b/compiler/rustc_mir_build/src/build/block.rs index 8426b24270d..4e1983aca94 100644 --- a/compiler/rustc_mir_build/src/build/block.rs +++ b/compiler/rustc_mir_build/src/build/block.rs @@ -74,8 +74,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> { // First we build all the statements in the block. let mut let_scope_stack = Vec::with_capacity(8); let outer_source_scope = this.source_scope; - let outer_push_unsafe_count = this.push_unsafe_count; - let outer_unpushed_unsafe = this.unpushed_unsafe; + let outer_in_scope_unsafe = this.in_scope_unsafe; this.update_source_scope_for_safety_mode(span, safety_mode); let source_info = this.source_info(span); @@ -206,8 +205,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> { } // Restore the original source scope. this.source_scope = outer_source_scope; - this.push_unsafe_count = outer_push_unsafe_count; - this.unpushed_unsafe = outer_unpushed_unsafe; + this.in_scope_unsafe = outer_in_scope_unsafe; block.unit() } @@ -217,8 +215,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> { let new_unsafety = match safety_mode { BlockSafety::Safe => None, BlockSafety::ExplicitUnsafe(hir_id) => { - assert_eq!(self.push_unsafe_count, 0); - match self.unpushed_unsafe { + match self.in_scope_unsafe { Safety::Safe => {} // no longer treat `unsafe fn`s as `unsafe` contexts (see RFC #2585) Safety::FnUnsafe @@ -226,20 +223,9 @@ impl<'a, 'tcx> Builder<'a, 'tcx> { != Level::Allow => {} _ => return, } - self.unpushed_unsafe = Safety::ExplicitUnsafe(hir_id); + self.in_scope_unsafe = Safety::ExplicitUnsafe(hir_id); Some(Safety::ExplicitUnsafe(hir_id)) } - BlockSafety::PushUnsafe => { - self.push_unsafe_count += 1; - Some(Safety::BuiltinUnsafe) - } - BlockSafety::PopUnsafe => { - self.push_unsafe_count = self - .push_unsafe_count - .checked_sub(1) - .unwrap_or_else(|| span_bug!(span, "unsafe count underflow")); - if self.push_unsafe_count == 0 { Some(self.unpushed_unsafe) } else { None } - } }; if let Some(unsafety) = new_unsafety { diff --git a/compiler/rustc_mir_build/src/build/expr/into.rs b/compiler/rustc_mir_build/src/build/expr/into.rs index f2b00f0f6ed..d7b3a85c15d 100644 --- a/compiler/rustc_mir_build/src/build/expr/into.rs +++ b/compiler/rustc_mir_build/src/build/expr/into.rs @@ -264,7 +264,14 @@ impl<'a, 'tcx> Builder<'a, 'tcx> { this.cfg.push_assign(block, source_info, destination, address_of); block.unit() } - ExprKind::Adt { adt_def, variant_index, substs, user_ty, ref fields, ref base } => { + ExprKind::Adt(box Adt { + adt_def, + variant_index, + substs, + user_ty, + ref fields, + ref base, + }) => { // See the notes for `ExprKind::Array` in `as_rvalue` and for // `ExprKind::Borrow` above. let is_union = adt_def.is_union(); diff --git a/compiler/rustc_mir_build/src/build/mod.rs b/compiler/rustc_mir_build/src/build/mod.rs index 10d6521e7de..f5f6da3ec0b 100644 --- a/compiler/rustc_mir_build/src/build/mod.rs +++ b/compiler/rustc_mir_build/src/build/mod.rs @@ -367,12 +367,8 @@ struct Builder<'a, 'tcx> { /// `{ STMTS; EXPR1 } + EXPR2`. block_context: BlockContext, - /// The current unsafe block in scope, even if it is hidden by - /// a `PushUnsafeBlock`. - unpushed_unsafe: Safety, - - /// The number of `push_unsafe_block` levels in scope. - push_unsafe_count: usize, + /// The current unsafe block in scope + in_scope_unsafe: Safety, /// The vector of all scopes that we have created thus far; /// we track this for debuginfo later. @@ -877,8 +873,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> { source_scopes: IndexVec::new(), source_scope: OUTERMOST_SOURCE_SCOPE, guard_context: vec![], - push_unsafe_count: 0, - unpushed_unsafe: safety, + in_scope_unsafe: safety, local_decls: IndexVec::from_elem_n(LocalDecl::new(return_ty, return_span), 1), canonical_user_type_annotations: IndexVec::new(), upvar_mutbls: vec![], diff --git a/compiler/rustc_mir_build/src/check_unsafety.rs b/compiler/rustc_mir_build/src/check_unsafety.rs index 2d52577829c..e4ed5dece86 100644 --- a/compiler/rustc_mir_build/src/check_unsafety.rs +++ b/compiler/rustc_mir_build/src/check_unsafety.rs @@ -195,14 +195,14 @@ impl<'a, 'tcx> Visitor<'a, 'tcx> for UnsafetyVisitor<'a, 'tcx> { ExprKind::InlineAsm { .. } | ExprKind::LlvmInlineAsm { .. } => { self.requires_unsafe(expr.span, UseOfInlineAssembly); } - ExprKind::Adt { + ExprKind::Adt(box Adt { adt_def, variant_index: _, substs: _, user_ty: _, fields: _, base: _, - } => match self.tcx.layout_scalar_valid_range(adt_def.did) { + }) => match self.tcx.layout_scalar_valid_range(adt_def.did) { (Bound::Unbounded, Bound::Unbounded) => {} _ => self.requires_unsafe(expr.span, InitializingTypeWith), }, diff --git a/compiler/rustc_mir_build/src/thir/cx/block.rs b/compiler/rustc_mir_build/src/thir/cx/block.rs index 77235fe9ab3..4fe8cd8541a 100644 --- a/compiler/rustc_mir_build/src/thir/cx/block.rs +++ b/compiler/rustc_mir_build/src/thir/cx/block.rs @@ -27,8 +27,6 @@ impl<'tcx> Cx<'tcx> { safety_mode: match block.rules { hir::BlockCheckMode::DefaultBlock => BlockSafety::Safe, hir::BlockCheckMode::UnsafeBlock(..) => BlockSafety::ExplicitUnsafe(block.hir_id), - hir::BlockCheckMode::PushUnsafeBlock(..) => BlockSafety::PushUnsafe, - hir::BlockCheckMode::PopUnsafeBlock(..) => BlockSafety::PopUnsafe, }, } } diff --git a/compiler/rustc_mir_build/src/thir/cx/expr.rs b/compiler/rustc_mir_build/src/thir/cx/expr.rs index aa4acfab5c8..da8cd66acb1 100644 --- a/compiler/rustc_mir_build/src/thir/cx/expr.rs +++ b/compiler/rustc_mir_build/src/thir/cx/expr.rs @@ -228,14 +228,14 @@ impl<'tcx> Cx<'tcx> { expr: self.mirror_expr(e), }) .collect(); - ExprKind::Adt { + ExprKind::Adt(Box::new(Adt { adt_def, substs, variant_index: index, fields: field_refs, user_ty, base: None, - } + })) } else { ExprKind::Call { ty: self.typeck_results().node_type(fun.hir_id), @@ -362,7 +362,7 @@ impl<'tcx> Cx<'tcx> { let user_provided_types = self.typeck_results().user_provided_types(); let user_ty = user_provided_types.get(expr.hir_id).copied(); debug!("make_mirror_unadjusted: (struct/union) user_ty={:?}", user_ty); - ExprKind::Adt { + ExprKind::Adt(Box::new(Adt { adt_def: adt, variant_index: VariantIdx::new(0), substs, @@ -375,7 +375,7 @@ impl<'tcx> Cx<'tcx> { .copied() .collect(), }), - } + })) } AdtKind::Enum => { let res = self.typeck_results().qpath_res(qpath, expr.hir_id); @@ -388,14 +388,14 @@ impl<'tcx> Cx<'tcx> { self.typeck_results().user_provided_types(); let user_ty = user_provided_types.get(expr.hir_id).copied(); debug!("make_mirror_unadjusted: (variant) user_ty={:?}", user_ty); - ExprKind::Adt { + ExprKind::Adt(Box::new(Adt { adt_def: adt, variant_index: index, substs, user_ty, fields: self.field_refs(fields), base: None, - } + })) } _ => { span_bug!(expr.span, "unexpected res: {:?}", res); @@ -906,14 +906,14 @@ impl<'tcx> Cx<'tcx> { match ty.kind() { // A unit struct/variant which is used as a value. // We return a completely different ExprKind here to account for this special case. - ty::Adt(adt_def, substs) => ExprKind::Adt { + ty::Adt(adt_def, substs) => ExprKind::Adt(Box::new(Adt { adt_def, variant_index: adt_def.variant_index_with_ctor_id(def_id), substs, user_ty: user_provided_type, fields: box [], base: None, - }, + })), _ => bug!("unexpected ty: {:?}", ty), } } diff --git a/compiler/rustc_mir_build/src/thir/visit.rs b/compiler/rustc_mir_build/src/thir/visit.rs index 12c6a9c00b2..f611bb6eb43 100644 --- a/compiler/rustc_mir_build/src/thir/visit.rs +++ b/compiler/rustc_mir_build/src/thir/visit.rs @@ -1,4 +1,4 @@ -use rustc_middle::thir::*; +use rustc_middle::thir::{self, *}; use rustc_middle::ty::Const; pub trait Visitor<'a, 'tcx: 'a>: Sized { @@ -98,7 +98,14 @@ pub fn walk_expr<'a, 'tcx: 'a, V: Visitor<'a, 'tcx>>(visitor: &mut V, expr: &Exp visitor.visit_expr(&visitor.thir()[field]); } } - Adt { ref fields, ref base, adt_def: _, variant_index: _, substs: _, user_ty: _ } => { + Adt(box thir::Adt { + ref fields, + ref base, + adt_def: _, + variant_index: _, + substs: _, + user_ty: _, + }) => { for field in &**fields { visitor.visit_expr(&visitor.thir()[field.expr]); } diff --git a/compiler/rustc_parse/src/parser/expr.rs b/compiler/rustc_parse/src/parser/expr.rs index c8789abc142..88ebf4aca23 100644 --- a/compiler/rustc_parse/src/parser/expr.rs +++ b/compiler/rustc_parse/src/parser/expr.rs @@ -2116,7 +2116,7 @@ impl<'a> Parser<'a> { let span = body.span; return Ok(( ast::Arm { - attrs, + attrs: attrs.into(), pat, guard, body, @@ -2170,7 +2170,7 @@ impl<'a> Parser<'a> { Ok(( ast::Arm { - attrs, + attrs: attrs.into(), pat, guard, body: expr, diff --git a/compiler/rustc_parse/src/parser/item.rs b/compiler/rustc_parse/src/parser/item.rs index 54e6ff6272c..2daa9e2485b 100644 --- a/compiler/rustc_parse/src/parser/item.rs +++ b/compiler/rustc_parse/src/parser/item.rs @@ -1143,7 +1143,7 @@ impl<'a> Parser<'a> { ident, vis, id: DUMMY_NODE_ID, - attrs: variant_attrs, + attrs: variant_attrs.into(), data: struct_def, disr_expr, span: vlo.to(this.prev_token.span), @@ -1286,7 +1286,7 @@ impl<'a> Parser<'a> { ident: None, id: DUMMY_NODE_ID, ty, - attrs, + attrs: attrs.into(), is_placeholder: false, }, TrailingToken::MaybeComma, @@ -1460,7 +1460,7 @@ impl<'a> Parser<'a> { vis, id: DUMMY_NODE_ID, ty, - attrs, + attrs: attrs.into(), is_placeholder: false, }) } diff --git a/compiler/rustc_passes/src/check_attr.rs b/compiler/rustc_passes/src/check_attr.rs index eca84c791fb..e85392cf0bd 100644 --- a/compiler/rustc_passes/src/check_attr.rs +++ b/compiler/rustc_passes/src/check_attr.rs @@ -525,8 +525,11 @@ impl CheckAttrVisitor<'tcx> { self.doc_attr_str_error(meta, "keyword"); return false; } - match self.tcx.hir().expect_item(hir_id).kind { - ItemKind::Mod(ref module) => { + match self.tcx.hir().find(hir_id).and_then(|node| match node { + hir::Node::Item(item) => Some(&item.kind), + _ => None, + }) { + Some(ItemKind::Mod(ref module)) => { if !module.item_ids.is_empty() { self.tcx .sess diff --git a/compiler/rustc_session/src/options.rs b/compiler/rustc_session/src/options.rs index 1946bfd78cc..ebf59bb4cc6 100644 --- a/compiler/rustc_session/src/options.rs +++ b/compiler/rustc_session/src/options.rs @@ -1160,8 +1160,6 @@ options! { "compile without linking"), no_parallel_llvm: bool = (false, parse_no_flag, [UNTRACKED], "run LLVM in non-parallel mode (while keeping codegen-units and ThinLTO)"), - no_profiler_runtime: bool = (false, parse_no_flag, [TRACKED], - "prevent automatic injection of the profiler_builtins crate"), normalize_docs: bool = (false, parse_bool, [TRACKED], "normalize associated items in rustdoc when generating documentation"), osx_rpath_install_name: bool = (false, parse_bool, [TRACKED], @@ -1205,6 +1203,8 @@ options! { profile_emit: Option<PathBuf> = (None, parse_opt_pathbuf, [TRACKED], "file path to emit profiling data at runtime when using 'profile' \ (default based on relative source path)"), + profiler_runtime: Option<String> = (Some(String::from("profiler_builtins")), parse_opt_string, [TRACKED], + "name of the profiler runtime crate to automatically inject, or None to disable"), query_dep_graph: bool = (false, parse_bool, [UNTRACKED], "enable queries of the dependency graph for regression testing (default: no)"), query_stats: bool = (false, parse_bool, [UNTRACKED], diff --git a/compiler/rustc_span/src/symbol.rs b/compiler/rustc_span/src/symbol.rs index a96d37c652d..862bde3f6a3 100644 --- a/compiler/rustc_span/src/symbol.rs +++ b/compiler/rustc_span/src/symbol.rs @@ -1062,6 +1062,7 @@ symbols! { rustdoc, rustfmt, rvalue_static_promotion, + s, sanitize, sanitizer_runtime, saturating_add, diff --git a/compiler/rustc_target/src/spec/mod.rs b/compiler/rustc_target/src/spec/mod.rs index 0f2aaeb533a..437517989ab 100644 --- a/compiler/rustc_target/src/spec/mod.rs +++ b/compiler/rustc_target/src/spec/mod.rs @@ -769,6 +769,7 @@ supported_targets! { ("armv7-unknown-freebsd", armv7_unknown_freebsd), ("i686-unknown-freebsd", i686_unknown_freebsd), ("powerpc64-unknown-freebsd", powerpc64_unknown_freebsd), + ("powerpc64le-unknown-freebsd", powerpc64le_unknown_freebsd), ("x86_64-unknown-freebsd", x86_64_unknown_freebsd), ("x86_64-unknown-dragonfly", x86_64_unknown_dragonfly), diff --git a/compiler/rustc_target/src/spec/powerpc64le_unknown_freebsd.rs b/compiler/rustc_target/src/spec/powerpc64le_unknown_freebsd.rs new file mode 100644 index 00000000000..283e9f744cb --- /dev/null +++ b/compiler/rustc_target/src/spec/powerpc64le_unknown_freebsd.rs @@ -0,0 +1,16 @@ +use crate::spec::{LinkerFlavor, Target, TargetOptions}; + +pub fn target() -> Target { + let mut base = super::freebsd_base::opts(); + base.cpu = "ppc64le".to_string(); + base.pre_link_args.entry(LinkerFlavor::Gcc).or_default().push("-m64".to_string()); + base.max_atomic_width = Some(64); + + Target { + llvm_target: "powerpc64le-unknown-freebsd".to_string(), + pointer_width: 64, + data_layout: "e-m:e-i64:64-n32:64".to_string(), + arch: "powerpc64".to_string(), + options: TargetOptions { mcount: "_mcount".to_string(), ..base }, + } +} diff --git a/compiler/rustc_typeck/src/check/mod.rs b/compiler/rustc_typeck/src/check/mod.rs index ad7853b7cd0..d102896bfa6 100644 --- a/compiler/rustc_typeck/src/check/mod.rs +++ b/compiler/rustc_typeck/src/check/mod.rs @@ -174,13 +174,12 @@ impl Needs { pub struct UnsafetyState { pub def: hir::HirId, pub unsafety: hir::Unsafety, - pub unsafe_push_count: u32, from_fn: bool, } impl UnsafetyState { pub fn function(unsafety: hir::Unsafety, def: hir::HirId) -> UnsafetyState { - UnsafetyState { def, unsafety, unsafe_push_count: 0, from_fn: true } + UnsafetyState { def, unsafety, from_fn: true } } pub fn recurse(self, blk: &hir::Block<'_>) -> UnsafetyState { @@ -193,19 +192,11 @@ impl UnsafetyState { hir::Unsafety::Unsafe if self.from_fn => self, unsafety => { - let (unsafety, def, count) = match blk.rules { - BlockCheckMode::PushUnsafeBlock(..) => { - (unsafety, blk.hir_id, self.unsafe_push_count.checked_add(1).unwrap()) - } - BlockCheckMode::PopUnsafeBlock(..) => { - (unsafety, blk.hir_id, self.unsafe_push_count.checked_sub(1).unwrap()) - } - BlockCheckMode::UnsafeBlock(..) => { - (hir::Unsafety::Unsafe, blk.hir_id, self.unsafe_push_count) - } - BlockCheckMode::DefaultBlock => (unsafety, self.def, self.unsafe_push_count), + let (unsafety, def) = match blk.rules { + BlockCheckMode::UnsafeBlock(..) => (hir::Unsafety::Unsafe, blk.hir_id), + BlockCheckMode::DefaultBlock => (unsafety, self.def), }; - UnsafetyState { def, unsafety, unsafe_push_count: count, from_fn: false } + UnsafetyState { def, unsafety, from_fn: false } } } } diff --git a/compiler/rustc_typeck/src/collect.rs b/compiler/rustc_typeck/src/collect.rs index ee3ac3b62d9..248669a2c0c 100644 --- a/compiler/rustc_typeck/src/collect.rs +++ b/compiler/rustc_typeck/src/collect.rs @@ -77,7 +77,6 @@ pub fn provide(providers: &mut Providers) { generics_of, predicates_of, predicates_defined_on, - projection_ty_from_predicates, explicit_predicates_of, super_predicates_of, super_predicates_that_define_assoc_type, @@ -180,8 +179,7 @@ crate fn placeholder_type_error( // Suggest, but only if it is not a function in const or static if suggest { let mut is_fn = false; - let mut is_const = false; - let mut is_static = false; + let mut is_const_or_static = false; if let Some(hir_ty) = hir_ty { if let hir::TyKind::BareFn(_) = hir_ty.kind { @@ -191,19 +189,26 @@ crate fn placeholder_type_error( let parent_id = tcx.hir().get_parent_node(hir_ty.hir_id); let parent_node = tcx.hir().get(parent_id); - if let hir::Node::Item(item) = parent_node { - if let hir::ItemKind::Const(_, _) = item.kind { - is_const = true; - } else if let hir::ItemKind::Static(_, _, _) = item.kind { - is_static = true; - } - } + is_const_or_static = match parent_node { + Node::Item(&hir::Item { + kind: hir::ItemKind::Const(..) | hir::ItemKind::Static(..), + .. + }) + | Node::TraitItem(&hir::TraitItem { + kind: hir::TraitItemKind::Const(..), + .. + }) + | Node::ImplItem(&hir::ImplItem { + kind: hir::ImplItemKind::Const(..), .. + }) => true, + _ => false, + }; } } // if function is wrapped around a const or static, // then don't show the suggestion - if !(is_fn && (is_const || is_static)) { + if !(is_fn && is_const_or_static) { err.multipart_suggestion( "use type parameters instead", sugg, @@ -2352,29 +2357,6 @@ fn explicit_predicates_of(tcx: TyCtxt<'_>, def_id: DefId) -> ty::GenericPredicat } } -fn projection_ty_from_predicates( - tcx: TyCtxt<'tcx>, - key: ( - // ty_def_id - DefId, - // def_id of `N` in `<T as Trait>::N` - DefId, - ), -) -> Option<ty::ProjectionTy<'tcx>> { - let (ty_def_id, item_def_id) = key; - let mut projection_ty = None; - for (predicate, _) in tcx.predicates_of(ty_def_id).predicates { - if let ty::PredicateKind::Projection(projection_predicate) = predicate.kind().skip_binder() - { - if item_def_id == projection_predicate.projection_ty.item_def_id { - projection_ty = Some(projection_predicate.projection_ty); - break; - } - } - } - projection_ty -} - /// Converts a specific `GenericBound` from the AST into a set of /// predicates that apply to the self type. A vector is returned /// because this can be anywhere from zero predicates (`T: ?Sized` adds no |
