From 11de4b71bd8970c9b5491cc1bb13266ce7d05af8 Mon Sep 17 00:00:00 2001 From: Mads Marquart Date: Fri, 24 Jan 2025 14:40:12 +0100 Subject: Cross-link documentation for adding a new target Both the target tier policy and the rustc-dev-guide has documentation on this, let's make sure people see both. --- src/doc/rustc-dev-guide/src/building/new-target.md | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'src/doc/rustc-dev-guide') diff --git a/src/doc/rustc-dev-guide/src/building/new-target.md b/src/doc/rustc-dev-guide/src/building/new-target.md index 1d9fa1b52d5..cd215277e69 100644 --- a/src/doc/rustc-dev-guide/src/building/new-target.md +++ b/src/doc/rustc-dev-guide/src/building/new-target.md @@ -4,8 +4,13 @@ These are a set of steps to add support for a new target. There are numerous end states and paths to get there, so not all sections may be relevant to your desired goal. +See also the associated documentation in the +[target tier policy][target_tier_policy_add]. + +[target_tier_policy_add]: https://doc.rust-lang.org/rustc/target-tier-policy.html#adding-a-new-target + ## Specifying a new LLVM For very new targets, you may need to use a different fork of LLVM -- cgit 1.4.1-3-g733a5 From 48b7e38c0607e856dbbb932e60ecc85e45a1427d Mon Sep 17 00:00:00 2001 From: Michael Goulet Date: Sat, 25 Jan 2025 04:26:32 +0000 Subject: Move outlives env computation into methods --- .../src/region_infer/opaque_types.rs | 16 ++++---- compiler/rustc_hir_analysis/src/check/wfcheck.rs | 17 ++++---- compiler/rustc_infer/src/infer/outlives/env.rs | 6 --- compiler/rustc_lint/src/impl_trait_overcaptures.rs | 6 +-- compiler/rustc_trait_selection/src/regions.rs | 46 +++++++++++++++++++++- .../rustc_trait_selection/src/traits/auto_trait.rs | 4 +- .../src/traits/outlives_bounds.rs | 21 ++-------- .../rustc-dev-guide/src/traits/implied-bounds.md | 4 +- 8 files changed, 71 insertions(+), 49 deletions(-) (limited to 'src/doc/rustc-dev-guide') diff --git a/compiler/rustc_borrowck/src/region_infer/opaque_types.rs b/compiler/rustc_borrowck/src/region_infer/opaque_types.rs index 1e7451a16af..5440d451ec8 100644 --- a/compiler/rustc_borrowck/src/region_infer/opaque_types.rs +++ b/compiler/rustc_borrowck/src/region_infer/opaque_types.rs @@ -1,6 +1,8 @@ use rustc_data_structures::fx::FxIndexMap; use rustc_errors::ErrorGuaranteed; +use rustc_hir::OpaqueTyOrigin; use rustc_hir::def_id::LocalDefId; +use rustc_infer::infer::outlives::env::OutlivesEnvironment; use rustc_infer::infer::{InferCtxt, NllRegionVariableOrigin, TyCtxtInferExt as _}; use rustc_macros::extension; use rustc_middle::ty::fold::fold_regions; @@ -10,6 +12,7 @@ use rustc_middle::ty::{ TypingMode, }; use rustc_span::Span; +use rustc_trait_selection::regions::OutlivesEnvironmentBuildExt; use rustc_trait_selection::traits::ObligationCtxt; use tracing::{debug, instrument}; @@ -406,10 +409,6 @@ impl<'tcx> LazyOpaqueTyEnv<'tcx> { } fn get_canonical_args(&self) -> ty::GenericArgsRef<'tcx> { - use rustc_hir as hir; - use rustc_infer::infer::outlives::env::OutlivesEnvironment; - use rustc_trait_selection::traits::outlives_bounds::InferCtxtExt as _; - if let Some(&canonical_args) = self.canonical_args.get() { return canonical_args; } @@ -417,9 +416,9 @@ impl<'tcx> LazyOpaqueTyEnv<'tcx> { let &Self { tcx, def_id, .. } = self; let origin = tcx.local_opaque_ty_origin(def_id); let parent = match origin { - hir::OpaqueTyOrigin::FnReturn { parent, .. } - | hir::OpaqueTyOrigin::AsyncFn { parent, .. } - | hir::OpaqueTyOrigin::TyAlias { parent, .. } => parent, + OpaqueTyOrigin::FnReturn { parent, .. } + | OpaqueTyOrigin::AsyncFn { parent, .. } + | OpaqueTyOrigin::TyAlias { parent, .. } => parent, }; let param_env = tcx.param_env(parent); let args = GenericArgs::identity_for_item(tcx, parent).extend_to( @@ -439,8 +438,7 @@ impl<'tcx> LazyOpaqueTyEnv<'tcx> { tcx.dcx().span_delayed_bug(tcx.def_span(def_id), "error getting implied bounds"); Default::default() }); - let implied_bounds = infcx.implied_bounds_tys(parent, param_env, wf_tys); - let outlives_env = OutlivesEnvironment::with_bounds(param_env, implied_bounds); + let outlives_env = OutlivesEnvironment::new(&infcx, parent, param_env, wf_tys); let mut seen = vec![tcx.lifetimes.re_static]; let canonical_args = fold_regions(tcx, args, |r1, _| { diff --git a/compiler/rustc_hir_analysis/src/check/wfcheck.rs b/compiler/rustc_hir_analysis/src/check/wfcheck.rs index 5023a09e2f3..83bb8c0dfaf 100644 --- a/compiler/rustc_hir_analysis/src/check/wfcheck.rs +++ b/compiler/rustc_hir_analysis/src/check/wfcheck.rs @@ -25,11 +25,10 @@ use rustc_middle::{bug, span_bug}; use rustc_session::parse::feature_err; use rustc_span::{DUMMY_SP, Ident, Span, sym}; use rustc_trait_selection::error_reporting::InferCtxtErrorExt; -use rustc_trait_selection::regions::InferCtxtRegionExt; +use rustc_trait_selection::regions::{InferCtxtRegionExt, OutlivesEnvironmentBuildExt}; use rustc_trait_selection::traits::misc::{ ConstParamTyImplementationError, type_allowed_to_implement_const_param_ty, }; -use rustc_trait_selection::traits::outlives_bounds::InferCtxtExt as _; use rustc_trait_selection::traits::query::evaluate_obligation::InferCtxtExt as _; use rustc_trait_selection::traits::{ self, FulfillmentError, Obligation, ObligationCause, ObligationCauseCode, ObligationCtxt, @@ -128,13 +127,13 @@ where let infcx_compat = infcx.fork(); // We specifically want to call the non-compat version of `implied_bounds_tys`; we do this always. - let implied_bounds = infcx.implied_bounds_tys_compat( + let outlives_env = OutlivesEnvironment::new_with_implied_bounds_compat( + &infcx, body_def_id, param_env, assumed_wf_types.iter().copied(), false, ); - let outlives_env = OutlivesEnvironment::with_bounds(param_env, implied_bounds); lint_redundant_lifetimes(tcx, body_def_id, &outlives_env); @@ -176,9 +175,13 @@ where // but that does result in slightly more work when this option is set and // just obscures what we mean here anyways. Let's just be explicit. if is_bevy && !infcx.tcx.sess.opts.unstable_opts.no_implied_bounds_compat { - let implied_bounds = - infcx_compat.implied_bounds_tys_compat(body_def_id, param_env, assumed_wf_types, true); - let outlives_env = OutlivesEnvironment::with_bounds(param_env, implied_bounds); + let outlives_env = OutlivesEnvironment::new_with_implied_bounds_compat( + &infcx, + body_def_id, + param_env, + assumed_wf_types, + true, + ); let errors_compat = infcx_compat.resolve_regions_with_outlives_env(&outlives_env); if errors_compat.is_empty() { Ok(()) diff --git a/compiler/rustc_infer/src/infer/outlives/env.rs b/compiler/rustc_infer/src/infer/outlives/env.rs index 9300fc574dc..f8ab0b53a00 100644 --- a/compiler/rustc_infer/src/infer/outlives/env.rs +++ b/compiler/rustc_infer/src/infer/outlives/env.rs @@ -59,12 +59,6 @@ pub struct OutlivesEnvironment<'tcx> { pub type RegionBoundPairs<'tcx> = FxIndexSet>>; impl<'tcx> OutlivesEnvironment<'tcx> { - /// Create a new `OutlivesEnvironment` without extra outlives bounds. - #[inline] - pub fn new(param_env: ty::ParamEnv<'tcx>) -> Self { - Self::with_bounds(param_env, vec![]) - } - /// Create a new `OutlivesEnvironment` with extra outlives bounds. pub fn with_bounds( param_env: ty::ParamEnv<'tcx>, diff --git a/compiler/rustc_lint/src/impl_trait_overcaptures.rs b/compiler/rustc_lint/src/impl_trait_overcaptures.rs index d6546066d86..d251b4b7459 100644 --- a/compiler/rustc_lint/src/impl_trait_overcaptures.rs +++ b/compiler/rustc_lint/src/impl_trait_overcaptures.rs @@ -25,8 +25,8 @@ use rustc_span::{Span, Symbol}; use rustc_trait_selection::errors::{ AddPreciseCapturingForOvercapture, impl_trait_overcapture_suggestion, }; +use rustc_trait_selection::regions::OutlivesEnvironmentBuildExt; use rustc_trait_selection::traits::ObligationCtxt; -use rustc_trait_selection::traits::outlives_bounds::InferCtxtExt; use crate::{LateContext, LateLintPass, fluent_generated as fluent}; @@ -190,9 +190,7 @@ fn check_fn(tcx: TyCtxt<'_>, parent_def_id: LocalDefId) { let (infcx, param_env) = tcx.infer_ctxt().build_with_typing_env(typing_env); let ocx = ObligationCtxt::new(&infcx); let assumed_wf_tys = ocx.assumed_wf_types(param_env, parent_def_id).unwrap_or_default(); - let implied_bounds = - infcx.implied_bounds_tys_compat(parent_def_id, param_env, assumed_wf_tys, false); - OutlivesEnvironment::with_bounds(param_env, implied_bounds) + OutlivesEnvironment::new(&infcx, parent_def_id, param_env, assumed_wf_tys) }), }); } diff --git a/compiler/rustc_trait_selection/src/regions.rs b/compiler/rustc_trait_selection/src/regions.rs index 1bae6c80cfa..fc9fa44b4c6 100644 --- a/compiler/rustc_trait_selection/src/regions.rs +++ b/compiler/rustc_trait_selection/src/regions.rs @@ -9,6 +9,46 @@ use rustc_middle::ty::{self, Ty}; use crate::traits::ScrubbedTraitError; use crate::traits::outlives_bounds::InferCtxtExt; +#[extension(pub trait OutlivesEnvironmentBuildExt<'tcx>)] +impl<'tcx> OutlivesEnvironment<'tcx> { + fn new( + infcx: &InferCtxt<'tcx>, + body_id: LocalDefId, + param_env: ty::ParamEnv<'tcx>, + assumed_wf_tys: impl IntoIterator>, + ) -> Self { + Self::new_with_implied_bounds_compat( + infcx, + body_id, + param_env, + assumed_wf_tys, + !infcx.tcx.sess.opts.unstable_opts.no_implied_bounds_compat, + ) + } + + fn new_with_implied_bounds_compat( + infcx: &InferCtxt<'tcx>, + body_id: LocalDefId, + param_env: ty::ParamEnv<'tcx>, + assumed_wf_tys: impl IntoIterator>, + implied_bounds_compat: bool, + ) -> Self { + // FIXME: This needs to be modified so that we normalize the known type + // outlives obligations then elaborate them into their region/type components. + // Otherwise, ` as Mirror>::Assoc: 'b` will not imply `'a: 'b` even + // if we can normalize `'a`. + OutlivesEnvironment::with_bounds( + param_env, + infcx.implied_bounds_tys_with_compat( + body_id, + param_env, + assumed_wf_tys, + implied_bounds_compat, + ), + ) + } +} + #[extension(pub trait InferCtxtRegionExt<'tcx>)] impl<'tcx> InferCtxt<'tcx> { /// Resolve regions, using the deep normalizer to normalize any type-outlives @@ -23,9 +63,11 @@ impl<'tcx> InferCtxt<'tcx> { param_env: ty::ParamEnv<'tcx>, assumed_wf_tys: impl IntoIterator>, ) -> Vec> { - self.resolve_regions_with_outlives_env(&OutlivesEnvironment::with_bounds( + self.resolve_regions_with_outlives_env(&OutlivesEnvironment::new( + self, + body_id, param_env, - self.implied_bounds_tys(body_id, param_env, assumed_wf_tys), + assumed_wf_tys, )) } diff --git a/compiler/rustc_trait_selection/src/traits/auto_trait.rs b/compiler/rustc_trait_selection/src/traits/auto_trait.rs index 9a53e8a5d51..1fca2f4da7e 100644 --- a/compiler/rustc_trait_selection/src/traits/auto_trait.rs +++ b/compiler/rustc_trait_selection/src/traits/auto_trait.rs @@ -6,6 +6,7 @@ use std::iter; use rustc_data_structures::fx::{FxIndexMap, FxIndexSet, IndexEntry}; use rustc_data_structures::unord::UnordSet; +use rustc_hir::def_id::CRATE_DEF_ID; use rustc_infer::infer::DefineOpaqueTypes; use rustc_middle::ty::{Region, RegionVid}; use tracing::debug; @@ -13,6 +14,7 @@ use tracing::debug; use super::*; use crate::errors::UnableToConstructConstantValue; use crate::infer::region_constraints::{Constraint, RegionConstraintData}; +use crate::regions::OutlivesEnvironmentBuildExt; use crate::traits::project::ProjectAndUnifyResult; // FIXME(twk): this is obviously not nice to duplicate like that @@ -158,7 +160,7 @@ impl<'tcx> AutoTraitFinder<'tcx> { panic!("Unable to fulfill trait {trait_did:?} for '{ty:?}': {errors:?}"); } - let outlives_env = OutlivesEnvironment::new(full_env); + let outlives_env = OutlivesEnvironment::new(&infcx, CRATE_DEF_ID, full_env, []); let _ = infcx.process_registered_region_obligations(&outlives_env, |ty, _| Ok(ty)); let region_data = infcx.inner.borrow_mut().unwrap_region_constraints().data().clone(); diff --git a/compiler/rustc_trait_selection/src/traits/outlives_bounds.rs b/compiler/rustc_trait_selection/src/traits/outlives_bounds.rs index eecc499f384..18932695807 100644 --- a/compiler/rustc_trait_selection/src/traits/outlives_bounds.rs +++ b/compiler/rustc_trait_selection/src/traits/outlives_bounds.rs @@ -108,8 +108,9 @@ fn implied_outlives_bounds<'a, 'tcx>( #[extension(pub trait InferCtxtExt<'tcx>)] impl<'tcx> InferCtxt<'tcx> { - /// Do *NOT* call this directly. - fn implied_bounds_tys_compat>>( + /// Do *NOT* call this directly. You probably want to construct a `OutlivesEnvironment` + /// instead if you're interested in the implied bounds for a given signature. + fn implied_bounds_tys_with_compat>>( &self, body_id: LocalDefId, param_env: ParamEnv<'tcx>, @@ -119,20 +120,4 @@ impl<'tcx> InferCtxt<'tcx> { tys.into_iter() .flat_map(move |ty| implied_outlives_bounds(self, param_env, body_id, ty, compat)) } - - /// If `-Z no-implied-bounds-compat` is set, calls `implied_bounds_tys_compat` - /// with `compat` set to `true`, otherwise `false`. - fn implied_bounds_tys( - &self, - body_id: LocalDefId, - param_env: ParamEnv<'tcx>, - tys: impl IntoIterator>, - ) -> impl Iterator> { - self.implied_bounds_tys_compat( - body_id, - param_env, - tys, - !self.tcx.sess.opts.unstable_opts.no_implied_bounds_compat, - ) - } } diff --git a/src/doc/rustc-dev-guide/src/traits/implied-bounds.md b/src/doc/rustc-dev-guide/src/traits/implied-bounds.md index 63b09a43f47..05693dcd5a1 100644 --- a/src/doc/rustc-dev-guide/src/traits/implied-bounds.md +++ b/src/doc/rustc-dev-guide/src/traits/implied-bounds.md @@ -40,7 +40,7 @@ requirements of impls and functions as explicit predicates. ### using implicit implied bounds as assumptions These bounds are not added to the `ParamEnv` of the affected item itself. For lexical -region resolution they are added using [`fn OutlivesEnvironment::with_bounds`]. +region resolution they are added using [`fn OutlivesEnvironment::new`]. Similarly, during MIR borrowck we add them using [`fn UniversalRegionRelationsBuilder::add_implied_bounds`]. @@ -55,7 +55,7 @@ The assumed outlives constraints for implicit bounds are computed using the MIR borrowck adds the outlives constraints for both the normalized and unnormalized types, lexical region resolution [only uses the unnormalized types][notnorm]. -[`fn OutlivesEnvironment::with_bounds`]: https://github.com/rust-lang/rust/blob/5b8bc568d28b2e922290c9a966b3231d0ce9398b/compiler/rustc_infer/src/infer/outlives/env.rs#L90-L97 +[`fn OutlivesEnvironment::new`]: TODO [`fn UniversalRegionRelationsBuilder::add_implied_bounds`]: https://github.com/rust-lang/rust/blob/5b8bc568d28b2e922290c9a966b3231d0ce9398b/compiler/rustc_borrowck/src/type_check/free_region_relations.rs#L316 [mir]: https://github.com/rust-lang/rust/blob/91cae1dcdcf1a31bd8a92e4a63793d65cfe289bb/compiler/rustc_borrowck/src/type_check/free_region_relations.rs#L258-L332 [`fn assumed_wf_types`]: https://github.com/rust-lang/rust/blob/5b8bc568d28b2e922290c9a966b3231d0ce9398b/compiler/rustc_ty_utils/src/implied_bounds.rs#L21 -- cgit 1.4.1-3-g733a5 From 5dfe0f8cf49110491ec0391c4b94b56834d65aef Mon Sep 17 00:00:00 2001 From: Mohammad Omidvar Date: Tue, 28 Jan 2025 19:45:20 +0000 Subject: Make crate AST mutation accessible for driver callback --- compiler/rustc_driver_impl/src/lib.rs | 6 +++--- src/doc/rustc-dev-guide/examples/rustc-driver-example.rs | 2 +- .../examples/rustc-driver-interacting-with-the-ast.rs | 2 +- 3 files changed, 5 insertions(+), 5 deletions(-) (limited to 'src/doc/rustc-dev-guide') diff --git a/compiler/rustc_driver_impl/src/lib.rs b/compiler/rustc_driver_impl/src/lib.rs index 20be2144609..c9d38a0f932 100644 --- a/compiler/rustc_driver_impl/src/lib.rs +++ b/compiler/rustc_driver_impl/src/lib.rs @@ -160,7 +160,7 @@ pub trait Callbacks { fn after_crate_root_parsing( &mut self, _compiler: &interface::Compiler, - _queries: &ast::Crate, + _krate: &mut ast::Crate, ) -> Compilation { Compilation::Continue } @@ -311,7 +311,7 @@ pub fn run_compiler(at_args: &[String], callbacks: &mut (dyn Callbacks + Send)) // Parse the crate root source code (doesn't parse submodules yet) // Everything else is parsed during macro expansion. - let krate = passes::parse(sess); + let mut krate = passes::parse(sess); // If pretty printing is requested: Figure out the representation, print it and exit if let Some(pp_mode) = sess.opts.pretty { @@ -328,7 +328,7 @@ pub fn run_compiler(at_args: &[String], callbacks: &mut (dyn Callbacks + Send)) return early_exit(); } - if callbacks.after_crate_root_parsing(compiler, &krate) == Compilation::Stop { + if callbacks.after_crate_root_parsing(compiler, &mut krate) == Compilation::Stop { return early_exit(); } diff --git a/src/doc/rustc-dev-guide/examples/rustc-driver-example.rs b/src/doc/rustc-dev-guide/examples/rustc-driver-example.rs index 8983915d78a..b0f9af1b8d1 100644 --- a/src/doc/rustc-dev-guide/examples/rustc-driver-example.rs +++ b/src/doc/rustc-dev-guide/examples/rustc-driver-example.rs @@ -58,7 +58,7 @@ impl rustc_driver::Callbacks for MyCallbacks { fn after_crate_root_parsing( &mut self, _compiler: &Compiler, - krate: &rustc_ast::Crate, + krate: &mut rustc_ast::Crate, ) -> Compilation { for item in &krate.items { println!("{}", item_to_string(&item)); diff --git a/src/doc/rustc-dev-guide/examples/rustc-driver-interacting-with-the-ast.rs b/src/doc/rustc-dev-guide/examples/rustc-driver-interacting-with-the-ast.rs index c894b60444a..8766a817344 100644 --- a/src/doc/rustc-dev-guide/examples/rustc-driver-interacting-with-the-ast.rs +++ b/src/doc/rustc-dev-guide/examples/rustc-driver-interacting-with-the-ast.rs @@ -58,7 +58,7 @@ impl rustc_driver::Callbacks for MyCallbacks { fn after_crate_root_parsing( &mut self, _compiler: &Compiler, - krate: &rustc_ast::Crate, + krate: &mut rustc_ast::Crate, ) -> Compilation { for item in &krate.items { println!("{}", item_to_string(&item)); -- cgit 1.4.1-3-g733a5 From 08d7e9dfe510196c3437662aaf1c5e6915941f94 Mon Sep 17 00:00:00 2001 From: Michael Goulet Date: Fri, 10 Jan 2025 20:09:10 +0000 Subject: Rework rustc_dump_vtable --- compiler/rustc_feature/src/builtin_attrs.rs | 2 +- compiler/rustc_hir_analysis/src/collect/dump.rs | 82 ++++++++- compiler/rustc_hir_analysis/src/lib.rs | 13 +- compiler/rustc_trait_selection/messages.ftl | 2 - compiler/rustc_trait_selection/src/errors.rs | 11 +- .../rustc_trait_selection/src/traits/vtable.rs | 17 +- src/doc/rustc-dev-guide/src/compiler-debugging.md | 2 +- .../multiple-supertraits-modulo-binder-vtable.rs | 25 +++ ...ultiple-supertraits-modulo-binder-vtable.stderr | 28 +++ ...iple-supertraits-modulo-normalization-vtable.rs | 36 ++++ ...-supertraits-modulo-normalization-vtable.stderr | 28 +++ tests/ui/traits/vtable/multiple-markers.rs | 33 ++-- tests/ui/traits/vtable/multiple-markers.stderr | 32 ++-- tests/ui/traits/vtable/vtable-diamond.rs | 31 ++-- tests/ui/traits/vtable/vtable-diamond.stderr | 45 +++-- tests/ui/traits/vtable/vtable-dyn-incompatible.rs | 7 +- .../traits/vtable/vtable-dyn-incompatible.stderr | 16 +- tests/ui/traits/vtable/vtable-multi-level.rs | 99 +++++------ tests/ui/traits/vtable/vtable-multi-level.stderr | 197 ++++++++++++--------- tests/ui/traits/vtable/vtable-multiple.rs | 22 +-- tests/ui/traits/vtable/vtable-multiple.stderr | 33 ++-- tests/ui/traits/vtable/vtable-vacant.rs | 15 +- tests/ui/traits/vtable/vtable-vacant.stderr | 22 ++- 23 files changed, 510 insertions(+), 288 deletions(-) create mode 100644 tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-binder-vtable.rs create mode 100644 tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-binder-vtable.stderr create mode 100644 tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-normalization-vtable.rs create mode 100644 tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-normalization-vtable.stderr (limited to 'src/doc/rustc-dev-guide') diff --git a/compiler/rustc_feature/src/builtin_attrs.rs b/compiler/rustc_feature/src/builtin_attrs.rs index 17433eed9e7..684fc5e37e0 100644 --- a/compiler/rustc_feature/src/builtin_attrs.rs +++ b/compiler/rustc_feature/src/builtin_attrs.rs @@ -1136,7 +1136,7 @@ pub const BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ ), rustc_attr!( TEST, rustc_dump_vtable, Normal, template!(Word), - WarnFollowing, EncodeCrossCrate::Yes + WarnFollowing, EncodeCrossCrate::No ), rustc_attr!( TEST, rustc_dummy, Normal, template!(Word /* doesn't matter*/), diff --git a/compiler/rustc_hir_analysis/src/collect/dump.rs b/compiler/rustc_hir_analysis/src/collect/dump.rs index f1022d95753..d990d824200 100644 --- a/compiler/rustc_hir_analysis/src/collect/dump.rs +++ b/compiler/rustc_hir_analysis/src/collect/dump.rs @@ -1,7 +1,8 @@ +use rustc_hir as hir; use rustc_hir::def_id::{CRATE_DEF_ID, LocalDefId}; use rustc_hir::intravisit; use rustc_middle::hir::nested_filter; -use rustc_middle::ty::TyCtxt; +use rustc_middle::ty::{self, TyCtxt, TypeVisitableExt}; use rustc_span::sym; pub(crate) fn opaque_hidden_types(tcx: TyCtxt<'_>) { @@ -87,3 +88,82 @@ pub(crate) fn def_parents(tcx: TyCtxt<'_>) { } } } + +pub(crate) fn vtables<'tcx>(tcx: TyCtxt<'tcx>) { + for id in tcx.hir().items() { + let def_id = id.owner_id.def_id; + + let Some(attr) = tcx.get_attr(def_id, sym::rustc_dump_vtable) else { + continue; + }; + + let vtable_entries = match tcx.hir().item(id).kind { + hir::ItemKind::Impl(hir::Impl { of_trait: Some(_), .. }) => { + let trait_ref = tcx.impl_trait_ref(def_id).unwrap().instantiate_identity(); + if trait_ref.has_non_region_param() { + tcx.dcx().span_err( + attr.span, + "`rustc_dump_vtable` must be applied to non-generic impl", + ); + continue; + } + if !tcx.is_dyn_compatible(trait_ref.def_id) { + tcx.dcx().span_err( + attr.span, + "`rustc_dump_vtable` must be applied to dyn-compatible trait", + ); + continue; + } + let Ok(trait_ref) = tcx + .try_normalize_erasing_regions(ty::TypingEnv::fully_monomorphized(), trait_ref) + else { + tcx.dcx().span_err( + attr.span, + "`rustc_dump_vtable` applied to impl header that cannot be normalized", + ); + continue; + }; + tcx.vtable_entries(ty::Binder::dummy(trait_ref)) + } + hir::ItemKind::TyAlias(_, _) => { + let ty = tcx.type_of(def_id).instantiate_identity(); + if ty.has_non_region_param() { + tcx.dcx().span_err( + attr.span, + "`rustc_dump_vtable` must be applied to non-generic type", + ); + continue; + } + let Ok(ty) = + tcx.try_normalize_erasing_regions(ty::TypingEnv::fully_monomorphized(), ty) + else { + tcx.dcx().span_err( + attr.span, + "`rustc_dump_vtable` applied to type alias that cannot be normalized", + ); + continue; + }; + let ty::Dynamic(data, _, _) = *ty.kind() else { + tcx.dcx().span_err(attr.span, "`rustc_dump_vtable` to type alias of dyn type"); + continue; + }; + if let Some(principal) = data.principal() { + tcx.vtable_entries( + principal.map_bound(|principal| principal.with_self_ty(tcx, ty)), + ) + } else { + TyCtxt::COMMON_VTABLE_ENTRIES + } + } + _ => { + tcx.dcx().span_err( + attr.span, + "`rustc_dump_vtable` only applies to impl, or type alias of dyn type", + ); + continue; + } + }; + + tcx.dcx().span_err(tcx.def_span(def_id), format!("vtable entries: {vtable_entries:#?}")); + } +} diff --git a/compiler/rustc_hir_analysis/src/lib.rs b/compiler/rustc_hir_analysis/src/lib.rs index bc7d4365eee..03dd0cccf75 100644 --- a/compiler/rustc_hir_analysis/src/lib.rs +++ b/compiler/rustc_hir_analysis/src/lib.rs @@ -152,11 +152,14 @@ pub fn check_crate(tcx: TyCtxt<'_>) { }); if tcx.features().rustc_attrs() { - tcx.sess.time("outlives_dumping", || outlives::dump::inferred_outlives(tcx)); - tcx.sess.time("variance_dumping", || variance::dump::variances(tcx)); - collect::dump::opaque_hidden_types(tcx); - collect::dump::predicates_and_item_bounds(tcx); - collect::dump::def_parents(tcx); + tcx.sess.time("dumping_rustc_attr_data", || { + outlives::dump::inferred_outlives(tcx); + variance::dump::variances(tcx); + collect::dump::opaque_hidden_types(tcx); + collect::dump::predicates_and_item_bounds(tcx); + collect::dump::def_parents(tcx); + collect::dump::vtables(tcx); + }); } // Make sure we evaluate all static and (non-associated) const items, even if unused. diff --git a/compiler/rustc_trait_selection/messages.ftl b/compiler/rustc_trait_selection/messages.ftl index 7c72318b4d7..055a3edcc32 100644 --- a/compiler/rustc_trait_selection/messages.ftl +++ b/compiler/rustc_trait_selection/messages.ftl @@ -148,8 +148,6 @@ trait_selection_dtcs_has_req_note = the used `impl` has a `'static` requirement trait_selection_dtcs_introduces_requirement = calling this method introduces the `impl`'s `'static` requirement trait_selection_dtcs_suggestion = consider relaxing the implicit `'static` requirement -trait_selection_dump_vtable_entries = vtable entries for `{$trait_ref}`: {$entries} - trait_selection_empty_on_clause_in_rustc_on_unimplemented = empty `on`-clause in `#[rustc_on_unimplemented]` .label = empty on-clause here diff --git a/compiler/rustc_trait_selection/src/errors.rs b/compiler/rustc_trait_selection/src/errors.rs index c8672b9dbd2..c5ab8a71c78 100644 --- a/compiler/rustc_trait_selection/src/errors.rs +++ b/compiler/rustc_trait_selection/src/errors.rs @@ -12,7 +12,7 @@ use rustc_hir::intravisit::{Visitor, VisitorExt, walk_ty}; use rustc_hir::{self as hir, AmbigArg, FnRetTy, GenericParamKind, Node}; use rustc_macros::{Diagnostic, Subdiagnostic}; use rustc_middle::ty::print::{PrintTraitRefExt as _, TraitRefPrintOnlyTraitPath}; -use rustc_middle::ty::{self, Binder, ClosureKind, FnSig, PolyTraitRef, Region, Ty, TyCtxt}; +use rustc_middle::ty::{self, Binder, ClosureKind, FnSig, Region, Ty, TyCtxt}; use rustc_span::{BytePos, Ident, Span, Symbol, kw}; use crate::error_reporting::infer::ObligationCauseAsDiagArg; @@ -22,15 +22,6 @@ use crate::fluent_generated as fluent; pub mod note_and_explain; -#[derive(Diagnostic)] -#[diag(trait_selection_dump_vtable_entries)] -pub struct DumpVTableEntries<'a> { - #[primary_span] - pub span: Span, - pub trait_ref: PolyTraitRef<'a>, - pub entries: String, -} - #[derive(Diagnostic)] #[diag(trait_selection_unable_to_construct_constant_value)] pub struct UnableToConstructConstantValue<'a> { diff --git a/compiler/rustc_trait_selection/src/traits/vtable.rs b/compiler/rustc_trait_selection/src/traits/vtable.rs index b5bc8364c7b..72ddf01c791 100644 --- a/compiler/rustc_trait_selection/src/traits/vtable.rs +++ b/compiler/rustc_trait_selection/src/traits/vtable.rs @@ -11,11 +11,10 @@ use rustc_middle::query::Providers; use rustc_middle::ty::{ self, GenericArgs, GenericParamDefKind, Ty, TyCtxt, TypeVisitableExt, Upcast, VtblEntry, }; -use rustc_span::{DUMMY_SP, Span, sym}; +use rustc_span::DUMMY_SP; use smallvec::{SmallVec, smallvec}; use tracing::debug; -use crate::errors::DumpVTableEntries; use crate::traits::{ObligationCtxt, impossible_predicates, is_vtable_safe_method}; #[derive(Clone, Debug)] @@ -192,15 +191,6 @@ fn maybe_iter(i: Option) -> impl Iterator { i.into_iter().flatten() } -fn dump_vtable_entries<'tcx>( - tcx: TyCtxt<'tcx>, - sp: Span, - trait_ref: ty::PolyTraitRef<'tcx>, - entries: &[VtblEntry<'tcx>], -) { - tcx.dcx().emit_err(DumpVTableEntries { span: sp, trait_ref, entries: format!("{entries:#?}") }); -} - fn has_own_existential_vtable_entries(tcx: TyCtxt<'_>, trait_def_id: DefId) -> bool { own_existential_vtable_entries_iter(tcx, trait_def_id).next().is_some() } @@ -317,11 +307,6 @@ fn vtable_entries<'tcx>( let _ = prepare_vtable_segments(tcx, trait_ref, vtable_segment_callback); - if tcx.has_attr(trait_ref.def_id(), sym::rustc_dump_vtable) { - let sp = tcx.def_span(trait_ref.def_id()); - dump_vtable_entries(tcx, sp, trait_ref, &entries); - } - tcx.arena.alloc_from_iter(entries) } diff --git a/src/doc/rustc-dev-guide/src/compiler-debugging.md b/src/doc/rustc-dev-guide/src/compiler-debugging.md index a2a6c8085df..e2097b26e5c 100644 --- a/src/doc/rustc-dev-guide/src/compiler-debugging.md +++ b/src/doc/rustc-dev-guide/src/compiler-debugging.md @@ -275,7 +275,7 @@ Here are some notable ones: | `rustc_dump_def_parents` | Dumps the chain of `DefId` parents of certain definitions. | | `rustc_dump_item_bounds` | Dumps the [`item_bounds`] of an item. | | `rustc_dump_predicates` | Dumps the [`predicates_of`] an item. | -| `rustc_dump_vtable` | | +| `rustc_dump_vtable` | Dumps the vtable layout of an impl, or a type alias of a dyn type. | | `rustc_hidden_type_of_opaques` | Dumps the [hidden type of each opaque types][opaq] in the crate. | | `rustc_layout` | [See this section](#debugging-type-layouts). | | `rustc_object_lifetime_default` | Dumps the [object lifetime defaults] of an item. | diff --git a/tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-binder-vtable.rs b/tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-binder-vtable.rs new file mode 100644 index 00000000000..b41cf2e9f26 --- /dev/null +++ b/tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-binder-vtable.rs @@ -0,0 +1,25 @@ +#![feature(rustc_attrs)] + +trait Supertrait { + fn _print_numbers(&self, mem: &[usize; 100]) { + } +} +impl Supertrait for () {} + +trait Trait: Supertrait + Supertrait { + fn say_hello(&self, _: &usize) { + } +} +impl Trait for () {} + +// We should observe compatibility between these two vtables. + +#[rustc_dump_vtable] +type First = dyn for<'a> Trait<&'static (), &'a ()>; +//~^ ERROR vtable entries + +#[rustc_dump_vtable] +type Second = dyn Trait<&'static (), &'static ()>; +//~^ ERROR vtable entries + +fn main() {} diff --git a/tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-binder-vtable.stderr b/tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-binder-vtable.stderr new file mode 100644 index 00000000000..1b99be4ab88 --- /dev/null +++ b/tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-binder-vtable.stderr @@ -0,0 +1,28 @@ +error: vtable entries: [ + MetadataDropInPlace, + MetadataSize, + MetadataAlign, + Method( Trait<&(), &'a ()> as Supertrait<&()>>::_print_numbers - shim(reify)), + Method( Trait<&(), &'a ()> as Supertrait<&()>>::_print_numbers - shim(reify)), + TraitVPtr(for<'a> Trait<&(), &'a ()> as Supertrait<&'a ()>>), + Method( Trait<&(), &'a ()> as Trait<&(), &()>>::say_hello - shim(reify)), + ] + --> $DIR/multiple-supertraits-modulo-binder-vtable.rs:18:1 + | +LL | type First = dyn for<'a> Trait<&'static (), &'a ()>; + | ^^^^^^^^^^ + +error: vtable entries: [ + MetadataDropInPlace, + MetadataSize, + MetadataAlign, + Method( as Supertrait<&()>>::_print_numbers - shim(reify)), + Method( as Trait<&(), &()>>::say_hello - shim(reify)), + ] + --> $DIR/multiple-supertraits-modulo-binder-vtable.rs:22:1 + | +LL | type Second = dyn Trait<&'static (), &'static ()>; + | ^^^^^^^^^^^ + +error: aborting due to 2 previous errors + diff --git a/tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-normalization-vtable.rs b/tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-normalization-vtable.rs new file mode 100644 index 00000000000..22d6bf94d87 --- /dev/null +++ b/tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-normalization-vtable.rs @@ -0,0 +1,36 @@ +#![feature(rustc_attrs)] + +#![feature(trait_upcasting)] + +trait Supertrait { + fn _print_numbers(&self, mem: &[usize; 100]) { + println!("{mem:?}"); + } +} +impl Supertrait for () {} + +trait Identity { + type Selff; +} +impl Identity for Selff { + type Selff = Selff; +} + +trait Middle: Supertrait<()> + Supertrait { + fn say_hello(&self, _: &usize) { + println!("Hello!"); + } +} +impl Middle for () {} + +trait Trait: Middle<<() as Identity>::Selff> {} + +#[rustc_dump_vtable] +impl Trait for () {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] +type Virtual = dyn Middle<()>; +//~^ ERROR vtable entries + +fn main() {} diff --git a/tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-normalization-vtable.stderr b/tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-normalization-vtable.stderr new file mode 100644 index 00000000000..9e93e1c48c9 --- /dev/null +++ b/tests/ui/traits/trait-upcasting/multiple-supertraits-modulo-normalization-vtable.stderr @@ -0,0 +1,28 @@ +error: vtable entries: [ + MetadataDropInPlace, + MetadataSize, + MetadataAlign, + Method(<() as Supertrait<()>>::_print_numbers), + Method(<() as Supertrait<()>>::_print_numbers), + TraitVPtr(<() as Supertrait<<() as Identity>::Selff>>), + Method(<() as Middle<()>>::say_hello), + ] + --> $DIR/multiple-supertraits-modulo-normalization-vtable.rs:29:1 + | +LL | impl Trait for () {} + | ^^^^^^^^^^^^^^^^^ + +error: vtable entries: [ + MetadataDropInPlace, + MetadataSize, + MetadataAlign, + Method( as Supertrait<()>>::_print_numbers - shim(reify)), + Method( as Middle<()>>::say_hello - shim(reify)), + ] + --> $DIR/multiple-supertraits-modulo-normalization-vtable.rs:33:1 + | +LL | type Virtual = dyn Middle<()>; + | ^^^^^^^^^^^^ + +error: aborting due to 2 previous errors + diff --git a/tests/ui/traits/vtable/multiple-markers.rs b/tests/ui/traits/vtable/multiple-markers.rs index 8a9e7a006cf..8eba5135582 100644 --- a/tests/ui/traits/vtable/multiple-markers.rs +++ b/tests/ui/traits/vtable/multiple-markers.rs @@ -2,8 +2,7 @@ // // This test makes sure that multiple marker (method-less) traits can reuse the // same pointer for upcasting. -// -//@ build-fail + #![crate_type = "lib"] #![feature(rustc_attrs)] @@ -17,17 +16,13 @@ trait T { fn method(&self) {} } -#[rustc_dump_vtable] -trait A: M0 + M1 + M2 + T {} //~ error: vtable entries for ``: +trait A: M0 + M1 + M2 + T {} -#[rustc_dump_vtable] -trait B: M0 + M1 + T + M2 {} //~ error: vtable entries for ``: +trait B: M0 + M1 + T + M2 {} -#[rustc_dump_vtable] -trait C: M0 + T + M1 + M2 {} //~ error: vtable entries for ``: +trait C: M0 + T + M1 + M2 {} -#[rustc_dump_vtable] -trait D: T + M0 + M1 + M2 {} //~ error: vtable entries for ``: +trait D: T + M0 + M1 + M2 {} struct S; @@ -35,13 +30,21 @@ impl M0 for S {} impl M1 for S {} impl M2 for S {} impl T for S {} + +#[rustc_dump_vtable] impl A for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl B for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl C for S {} -impl D for S {} +//~^ ERROR vtable entries -pub fn require_vtables() { - fn require_vtables(_: &dyn A, _: &dyn B, _: &dyn C, _: &dyn D) {} +#[rustc_dump_vtable] +impl D for S {} +//~^ ERROR vtable entries - require_vtables(&S, &S, &S, &S) -} +fn main() {} diff --git a/tests/ui/traits/vtable/multiple-markers.stderr b/tests/ui/traits/vtable/multiple-markers.stderr index 36ac8b24eb5..35dd3c2516d 100644 --- a/tests/ui/traits/vtable/multiple-markers.stderr +++ b/tests/ui/traits/vtable/multiple-markers.stderr @@ -1,46 +1,46 @@ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, Method(::method), ] - --> $DIR/multiple-markers.rs:21:1 + --> $DIR/multiple-markers.rs:35:1 | -LL | trait A: M0 + M1 + M2 + T {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^ +LL | impl A for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, Method(::method), ] - --> $DIR/multiple-markers.rs:24:1 + --> $DIR/multiple-markers.rs:39:1 | -LL | trait B: M0 + M1 + T + M2 {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^ +LL | impl B for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, Method(::method), ] - --> $DIR/multiple-markers.rs:27:1 + --> $DIR/multiple-markers.rs:43:1 | -LL | trait C: M0 + T + M1 + M2 {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^ +LL | impl C for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, Method(::method), ] - --> $DIR/multiple-markers.rs:30:1 + --> $DIR/multiple-markers.rs:47:1 | -LL | trait D: T + M0 + M1 + M2 {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^ +LL | impl D for S {} + | ^^^^^^^^^^^^ error: aborting due to 4 previous errors diff --git a/tests/ui/traits/vtable/vtable-diamond.rs b/tests/ui/traits/vtable/vtable-diamond.rs index 2cfa86c526d..56053f6d026 100644 --- a/tests/ui/traits/vtable/vtable-diamond.rs +++ b/tests/ui/traits/vtable/vtable-diamond.rs @@ -1,44 +1,37 @@ -//@ build-fail #![feature(rustc_attrs)] -#[rustc_dump_vtable] trait A { fn foo_a(&self) {} } -#[rustc_dump_vtable] trait B: A { fn foo_b(&self) {} } -#[rustc_dump_vtable] trait C: A { - //~^ error vtable fn foo_c(&self) {} } -#[rustc_dump_vtable] trait D: B + C { - //~^ error vtable fn foo_d(&self) {} } struct S; +#[rustc_dump_vtable] impl A for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl B for S {} -impl C for S {} -impl D for S {} +//~^ ERROR vtable entries -fn foo(d: &dyn D) { - d.foo_d(); -} +#[rustc_dump_vtable] +impl C for S {} +//~^ ERROR vtable entries -fn bar(d: &dyn C) { - d.foo_c(); -} +#[rustc_dump_vtable] +impl D for S {} +//~^ ERROR vtable entries -fn main() { - foo(&S); - bar(&S); -} +fn main() {} diff --git a/tests/ui/traits/vtable/vtable-diamond.stderr b/tests/ui/traits/vtable/vtable-diamond.stderr index f3718c5d852..4644bf339b1 100644 --- a/tests/ui/traits/vtable/vtable-diamond.stderr +++ b/tests/ui/traits/vtable/vtable-diamond.stderr @@ -1,29 +1,52 @@ -error: vtable entries for ``: [ +error: vtable entries: [ + MetadataDropInPlace, + MetadataSize, + MetadataAlign, + Method(::foo_a), + ] + --> $DIR/vtable-diamond.rs:22:1 + | +LL | impl A for S {} + | ^^^^^^^^^^^^ + +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, Method(::foo_a), Method(::foo_b), + ] + --> $DIR/vtable-diamond.rs:26:1 + | +LL | impl B for S {} + | ^^^^^^^^^^^^ + +error: vtable entries: [ + MetadataDropInPlace, + MetadataSize, + MetadataAlign, + Method(::foo_a), Method(::foo_c), - TraitVPtr(), - Method(::foo_d), ] - --> $DIR/vtable-diamond.rs:21:1 + --> $DIR/vtable-diamond.rs:30:1 | -LL | trait D: B + C { - | ^^^^^^^^^^^^^^ +LL | impl C for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, Method(::foo_a), + Method(::foo_b), Method(::foo_c), + TraitVPtr(), + Method(::foo_d), ] - --> $DIR/vtable-diamond.rs:15:1 + --> $DIR/vtable-diamond.rs:34:1 | -LL | trait C: A { - | ^^^^^^^^^^ +LL | impl D for S {} + | ^^^^^^^^^^^^ -error: aborting due to 2 previous errors +error: aborting due to 4 previous errors diff --git a/tests/ui/traits/vtable/vtable-dyn-incompatible.rs b/tests/ui/traits/vtable/vtable-dyn-incompatible.rs index 64a8138bdcf..fb19dec4ace 100644 --- a/tests/ui/traits/vtable/vtable-dyn-incompatible.rs +++ b/tests/ui/traits/vtable/vtable-dyn-incompatible.rs @@ -1,15 +1,16 @@ -//@ build-fail #![feature(rustc_attrs)] // Ensure that dyn-incompatible methods in Iterator does not generate // vtable entries. -#[rustc_dump_vtable] trait A: Iterator {} -//~^ error vtable impl A for T where T: Iterator {} +#[rustc_dump_vtable] +type Test = dyn A; +//~^ error vtable + fn foo(_a: &mut dyn A) { } diff --git a/tests/ui/traits/vtable/vtable-dyn-incompatible.stderr b/tests/ui/traits/vtable/vtable-dyn-incompatible.stderr index e442c3eac00..c80a763998b 100644 --- a/tests/ui/traits/vtable/vtable-dyn-incompatible.stderr +++ b/tests/ui/traits/vtable/vtable-dyn-incompatible.stderr @@ -1,16 +1,16 @@ -error: vtable entries for ` as A>`: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, - Method( as Iterator>::next), - Method( as Iterator>::size_hint), - Method( as Iterator>::advance_by), - Method( as Iterator>::nth), + Method( as Iterator>::next - shim(reify)), + Method( as Iterator>::size_hint - shim(reify)), + Method( as Iterator>::advance_by - shim(reify)), + Method( as Iterator>::nth - shim(reify)), ] - --> $DIR/vtable-dyn-incompatible.rs:8:1 + --> $DIR/vtable-dyn-incompatible.rs:11:1 | -LL | trait A: Iterator {} - | ^^^^^^^^^^^^^^^^^ +LL | type Test = dyn A; + | ^^^^^^^^^ error: aborting due to 1 previous error diff --git a/tests/ui/traits/vtable/vtable-multi-level.rs b/tests/ui/traits/vtable/vtable-multi-level.rs index bedbf84d303..67bac49f9f6 100644 --- a/tests/ui/traits/vtable/vtable-multi-level.rs +++ b/tests/ui/traits/vtable/vtable-multi-level.rs @@ -1,4 +1,3 @@ -//@ build-fail #![feature(rustc_attrs)] // O --> G --> C --> A @@ -10,134 +9,126 @@ // |-> M --> K // \-> L -#[rustc_dump_vtable] trait A { - //~^ error vtable fn foo_a(&self) {} } -#[rustc_dump_vtable] trait B { - //~^ error vtable fn foo_b(&self) {} } -#[rustc_dump_vtable] trait C: A + B { - //~^ error vtable fn foo_c(&self) {} } -#[rustc_dump_vtable] trait D { - //~^ error vtable fn foo_d(&self) {} } -#[rustc_dump_vtable] trait E { - //~^ error vtable fn foo_e(&self) {} } -#[rustc_dump_vtable] trait F: D + E { - //~^ error vtable fn foo_f(&self) {} } -#[rustc_dump_vtable] trait G: C + F { fn foo_g(&self) {} } -#[rustc_dump_vtable] trait H { - //~^ error vtable fn foo_h(&self) {} } -#[rustc_dump_vtable] trait I { - //~^ error vtable fn foo_i(&self) {} } -#[rustc_dump_vtable] trait J: H + I { - //~^ error vtable fn foo_j(&self) {} } -#[rustc_dump_vtable] trait K { - //~^ error vtable fn foo_k(&self) {} } -#[rustc_dump_vtable] trait L { - //~^ error vtable fn foo_l(&self) {} } -#[rustc_dump_vtable] trait M: K + L { - //~^ error vtable fn foo_m(&self) {} } -#[rustc_dump_vtable] trait N: J + M { - //~^ error vtable fn foo_n(&self) {} } -#[rustc_dump_vtable] trait O: G + N { - //~^ error vtable fn foo_o(&self) {} } struct S; +#[rustc_dump_vtable] impl A for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl B for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl C for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl D for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl E for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl F for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl G for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl H for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl I for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl J for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl K for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl L for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl M for S {} +//~^ ERROR vtable entries + +#[rustc_dump_vtable] impl N for S {} -impl O for S {} +//~^ ERROR vtable entries -macro_rules! monomorphize_vtable { - ($trait:ident) => {{ - fn foo(_ : &dyn $trait) {} - foo(&S); - }} -} +#[rustc_dump_vtable] +impl O for S {} +//~^ ERROR vtable entries -fn main() { - monomorphize_vtable!(O); - - monomorphize_vtable!(A); - monomorphize_vtable!(B); - monomorphize_vtable!(C); - monomorphize_vtable!(D); - monomorphize_vtable!(E); - monomorphize_vtable!(F); - monomorphize_vtable!(H); - monomorphize_vtable!(I); - monomorphize_vtable!(J); - monomorphize_vtable!(K); - monomorphize_vtable!(L); - monomorphize_vtable!(M); - monomorphize_vtable!(N); -} +fn main() {} diff --git a/tests/ui/traits/vtable/vtable-multi-level.stderr b/tests/ui/traits/vtable/vtable-multi-level.stderr index c4389e23fc1..961900aa3d2 100644 --- a/tests/ui/traits/vtable/vtable-multi-level.stderr +++ b/tests/ui/traits/vtable/vtable-multi-level.stderr @@ -1,134 +1,119 @@ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, Method(::foo_a), - Method(::foo_b), - TraitVPtr(), - Method(::foo_c), - Method(::foo_d), - TraitVPtr(), - Method(::foo_e), - TraitVPtr(), - Method(::foo_f), - TraitVPtr(), - Method(::foo_g), - Method(::foo_h), - TraitVPtr(), - Method(::foo_i), - TraitVPtr(), - Method(::foo_j), - TraitVPtr(), - Method(::foo_k), - TraitVPtr(), - Method(::foo_l), - TraitVPtr(), - Method(::foo_m), - TraitVPtr(), - Method(::foo_n), - TraitVPtr(), - Method(::foo_o), ] - --> $DIR/vtable-multi-level.rs:97:1 + --> $DIR/vtable-multi-level.rs:75:1 | -LL | trait O: G + N { - | ^^^^^^^^^^^^^^ +LL | impl A for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, - Method(::foo_a), + Method(::foo_b), ] - --> $DIR/vtable-multi-level.rs:14:1 + --> $DIR/vtable-multi-level.rs:79:1 | -LL | trait A { - | ^^^^^^^ +LL | impl B for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, + Method(::foo_a), Method(::foo_b), + TraitVPtr(), + Method(::foo_c), ] - --> $DIR/vtable-multi-level.rs:20:1 + --> $DIR/vtable-multi-level.rs:83:1 | -LL | trait B { - | ^^^^^^^ +LL | impl C for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, - Method(::foo_a), - Method(::foo_b), - TraitVPtr(), - Method(::foo_c), + Method(::foo_d), ] - --> $DIR/vtable-multi-level.rs:26:1 + --> $DIR/vtable-multi-level.rs:87:1 | -LL | trait C: A + B { - | ^^^^^^^^^^^^^^ +LL | impl D for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, - Method(::foo_d), + Method(::foo_e), ] - --> $DIR/vtable-multi-level.rs:32:1 + --> $DIR/vtable-multi-level.rs:91:1 | -LL | trait D { - | ^^^^^^^ +LL | impl E for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, + Method(::foo_d), Method(::foo_e), + TraitVPtr(), + Method(::foo_f), ] - --> $DIR/vtable-multi-level.rs:38:1 + --> $DIR/vtable-multi-level.rs:95:1 | -LL | trait E { - | ^^^^^^^ +LL | impl F for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, + Method(::foo_a), + Method(::foo_b), + TraitVPtr(), + Method(::foo_c), Method(::foo_d), + TraitVPtr(), Method(::foo_e), TraitVPtr(), Method(::foo_f), + TraitVPtr(), + Method(::foo_g), ] - --> $DIR/vtable-multi-level.rs:44:1 + --> $DIR/vtable-multi-level.rs:99:1 | -LL | trait F: D + E { - | ^^^^^^^^^^^^^^ +LL | impl G for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, Method(::foo_h), ] - --> $DIR/vtable-multi-level.rs:55:1 + --> $DIR/vtable-multi-level.rs:103:1 | -LL | trait H { - | ^^^^^^^ +LL | impl H for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, Method(::foo_i), ] - --> $DIR/vtable-multi-level.rs:61:1 + --> $DIR/vtable-multi-level.rs:107:1 | -LL | trait I { - | ^^^^^^^ +LL | impl I for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, @@ -137,34 +122,34 @@ error: vtable entries for ``: [ TraitVPtr(), Method(::foo_j), ] - --> $DIR/vtable-multi-level.rs:67:1 + --> $DIR/vtable-multi-level.rs:111:1 | -LL | trait J: H + I { - | ^^^^^^^^^^^^^^ +LL | impl J for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, Method(::foo_k), ] - --> $DIR/vtable-multi-level.rs:73:1 + --> $DIR/vtable-multi-level.rs:115:1 | -LL | trait K { - | ^^^^^^^ +LL | impl K for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, Method(::foo_l), ] - --> $DIR/vtable-multi-level.rs:79:1 + --> $DIR/vtable-multi-level.rs:119:1 | -LL | trait L { - | ^^^^^^^ +LL | impl L for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, @@ -173,12 +158,12 @@ error: vtable entries for ``: [ TraitVPtr(), Method(::foo_m), ] - --> $DIR/vtable-multi-level.rs:85:1 + --> $DIR/vtable-multi-level.rs:123:1 | -LL | trait M: K + L { - | ^^^^^^^^^^^^^^ +LL | impl M for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, @@ -194,10 +179,46 @@ error: vtable entries for ``: [ TraitVPtr(), Method(::foo_n), ] - --> $DIR/vtable-multi-level.rs:91:1 + --> $DIR/vtable-multi-level.rs:127:1 + | +LL | impl N for S {} + | ^^^^^^^^^^^^ + +error: vtable entries: [ + MetadataDropInPlace, + MetadataSize, + MetadataAlign, + Method(::foo_a), + Method(::foo_b), + TraitVPtr(), + Method(::foo_c), + Method(::foo_d), + TraitVPtr(), + Method(::foo_e), + TraitVPtr(), + Method(::foo_f), + TraitVPtr(), + Method(::foo_g), + Method(::foo_h), + TraitVPtr(), + Method(::foo_i), + TraitVPtr(), + Method(::foo_j), + TraitVPtr(), + Method(::foo_k), + TraitVPtr(), + Method(::foo_l), + TraitVPtr(), + Method(::foo_m), + TraitVPtr(), + Method(::foo_n), + TraitVPtr(), + Method(::foo_o), + ] + --> $DIR/vtable-multi-level.rs:131:1 | -LL | trait N: J + M { - | ^^^^^^^^^^^^^^ +LL | impl O for S {} + | ^^^^^^^^^^^^ -error: aborting due to 14 previous errors +error: aborting due to 15 previous errors diff --git a/tests/ui/traits/vtable/vtable-multiple.rs b/tests/ui/traits/vtable/vtable-multiple.rs index beaaf4db6b1..51e20ee20c9 100644 --- a/tests/ui/traits/vtable/vtable-multiple.rs +++ b/tests/ui/traits/vtable/vtable-multiple.rs @@ -1,33 +1,29 @@ -//@ build-fail #![feature(rustc_attrs)] -#[rustc_dump_vtable] trait A { fn foo_a(&self) {} } -#[rustc_dump_vtable] trait B { - //~^ error vtable fn foo_b(&self) {} } -#[rustc_dump_vtable] trait C: A + B { - //~^ error vtable fn foo_c(&self) {} } struct S; +#[rustc_dump_vtable] impl A for S {} +//~^ error vtable + +#[rustc_dump_vtable] impl B for S {} -impl C for S {} +//~^ error vtable -fn foo(c: &dyn C) {} -fn bar(c: &dyn B) {} +#[rustc_dump_vtable] +impl C for S {} +//~^ error vtable -fn main() { - foo(&S); - bar(&S); -} +fn main() {} diff --git a/tests/ui/traits/vtable/vtable-multiple.stderr b/tests/ui/traits/vtable/vtable-multiple.stderr index 0dcd8443309..bae44148baa 100644 --- a/tests/ui/traits/vtable/vtable-multiple.stderr +++ b/tests/ui/traits/vtable/vtable-multiple.stderr @@ -1,27 +1,38 @@ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, Method(::foo_a), + ] + --> $DIR/vtable-multiple.rs:18:1 + | +LL | impl A for S {} + | ^^^^^^^^^^^^ + +error: vtable entries: [ + MetadataDropInPlace, + MetadataSize, + MetadataAlign, Method(::foo_b), - TraitVPtr(), - Method(::foo_c), ] - --> $DIR/vtable-multiple.rs:16:1 + --> $DIR/vtable-multiple.rs:22:1 | -LL | trait C: A + B { - | ^^^^^^^^^^^^^^ +LL | impl B for S {} + | ^^^^^^^^^^^^ -error: vtable entries for ``: [ +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, + Method(::foo_a), Method(::foo_b), + TraitVPtr(), + Method(::foo_c), ] - --> $DIR/vtable-multiple.rs:10:1 + --> $DIR/vtable-multiple.rs:26:1 | -LL | trait B { - | ^^^^^^^ +LL | impl C for S {} + | ^^^^^^^^^^^^ -error: aborting due to 2 previous errors +error: aborting due to 3 previous errors diff --git a/tests/ui/traits/vtable/vtable-vacant.rs b/tests/ui/traits/vtable/vtable-vacant.rs index b3c76815703..b023565c56e 100644 --- a/tests/ui/traits/vtable/vtable-vacant.rs +++ b/tests/ui/traits/vtable/vtable-vacant.rs @@ -1,18 +1,14 @@ -//@ build-fail #![feature(rustc_attrs)] #![feature(negative_impls)] // B --> A -#[rustc_dump_vtable] trait A { fn foo_a1(&self) {} fn foo_a2(&self) where Self: Send {} } -#[rustc_dump_vtable] trait B: A { - //~^ error vtable fn foo_b1(&self) {} fn foo_b2(&self) where Self: Send {} } @@ -20,11 +16,12 @@ trait B: A { struct S; impl !Send for S {} +#[rustc_dump_vtable] impl A for S {} -impl B for S {} +//~^ error vtable -fn foo(_: &dyn B) {} +#[rustc_dump_vtable] +impl B for S {} +//~^ error vtable -fn main() { - foo(&S); -} +fn main() {} diff --git a/tests/ui/traits/vtable/vtable-vacant.stderr b/tests/ui/traits/vtable/vtable-vacant.stderr index f6961ca010e..ed8466f7f2e 100644 --- a/tests/ui/traits/vtable/vtable-vacant.stderr +++ b/tests/ui/traits/vtable/vtable-vacant.stderr @@ -1,4 +1,16 @@ -error: vtable entries for ``: [ +error: vtable entries: [ + MetadataDropInPlace, + MetadataSize, + MetadataAlign, + Method(::foo_a1), + Vacant, + ] + --> $DIR/vtable-vacant.rs:20:1 + | +LL | impl A for S {} + | ^^^^^^^^^^^^ + +error: vtable entries: [ MetadataDropInPlace, MetadataSize, MetadataAlign, @@ -7,10 +19,10 @@ error: vtable entries for ``: [ Method(::foo_b1), Vacant, ] - --> $DIR/vtable-vacant.rs:14:1 + --> $DIR/vtable-vacant.rs:24:1 | -LL | trait B: A { - | ^^^^^^^^^^ +LL | impl B for S {} + | ^^^^^^^^^^^^ -error: aborting due to 1 previous error +error: aborting due to 2 previous errors -- cgit 1.4.1-3-g733a5 From ba5386aeed08ed4d2a305b8f14c34de800e48167 Mon Sep 17 00:00:00 2001 From: Ryan Cumming Date: Fri, 31 Jan 2025 10:23:46 +1100 Subject: Fix a typo in conventions.md Introduced in #135950 --- src/doc/rustc-dev-guide/src/conventions.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/doc/rustc-dev-guide') diff --git a/src/doc/rustc-dev-guide/src/conventions.md b/src/doc/rustc-dev-guide/src/conventions.md index 4010e90821f..0e624a4566d 100644 --- a/src/doc/rustc-dev-guide/src/conventions.md +++ b/src/doc/rustc-dev-guide/src/conventions.md @@ -43,7 +43,7 @@ environment. ## Formatting and linting Python code -The Rust repository contains quite a lof of Python code. We try to keep +The Rust repository contains quite a lot of Python code. We try to keep it both linted and formatted by the [ruff][ruff] tool. When modifying Python code, use this command to format it: -- cgit 1.4.1-3-g733a5 From f09de673565b88dd0c9f416e171f5c099073270e Mon Sep 17 00:00:00 2001 From: The rustc-dev-guide Cronjob Bot Date: Sun, 2 Feb 2025 04:02:19 +0000 Subject: Preparing for merge from rustc --- src/doc/rustc-dev-guide/rust-version | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/doc/rustc-dev-guide') diff --git a/src/doc/rustc-dev-guide/rust-version b/src/doc/rustc-dev-guide/rust-version index 183d26b2938..fa65931bdc5 100644 --- a/src/doc/rustc-dev-guide/rust-version +++ b/src/doc/rustc-dev-guide/rust-version @@ -1 +1 @@ -66d6064f9eb888018775e08f84747ee6f39ba28e +8239a37f9c0951a037cfc51763ea52a20e71e6bd -- cgit 1.4.1-3-g733a5 From 3827ff028971a6ec6ef18fd80f44c1cc05c898bb Mon Sep 17 00:00:00 2001 From: Yuki Okushi Date: Sun, 2 Feb 2025 17:30:30 +0900 Subject: Apply suggestions from code review --- src/doc/rustc-dev-guide/src/traits/implied-bounds.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src/doc/rustc-dev-guide') diff --git a/src/doc/rustc-dev-guide/src/traits/implied-bounds.md b/src/doc/rustc-dev-guide/src/traits/implied-bounds.md index 05693dcd5a1..cdcb90d3e2e 100644 --- a/src/doc/rustc-dev-guide/src/traits/implied-bounds.md +++ b/src/doc/rustc-dev-guide/src/traits/implied-bounds.md @@ -40,7 +40,7 @@ requirements of impls and functions as explicit predicates. ### using implicit implied bounds as assumptions These bounds are not added to the `ParamEnv` of the affected item itself. For lexical -region resolution they are added using [`fn OutlivesEnvironment::new`]. +region resolution they are added using [`fn OutlivesEnvironment::from_normalized_bounds`]. Similarly, during MIR borrowck we add them using [`fn UniversalRegionRelationsBuilder::add_implied_bounds`]. @@ -55,7 +55,7 @@ The assumed outlives constraints for implicit bounds are computed using the MIR borrowck adds the outlives constraints for both the normalized and unnormalized types, lexical region resolution [only uses the unnormalized types][notnorm]. -[`fn OutlivesEnvironment::new`]: TODO +[`fn OutlivesEnvironment::from_normalized_bounds`]: https://github.com/rust-lang/rust/blob/8239a37f9c0951a037cfc51763ea52a20e71e6bd/compiler/rustc_infer/src/infer/outlives/env.rs#L50-L55 [`fn UniversalRegionRelationsBuilder::add_implied_bounds`]: https://github.com/rust-lang/rust/blob/5b8bc568d28b2e922290c9a966b3231d0ce9398b/compiler/rustc_borrowck/src/type_check/free_region_relations.rs#L316 [mir]: https://github.com/rust-lang/rust/blob/91cae1dcdcf1a31bd8a92e4a63793d65cfe289bb/compiler/rustc_borrowck/src/type_check/free_region_relations.rs#L258-L332 [`fn assumed_wf_types`]: https://github.com/rust-lang/rust/blob/5b8bc568d28b2e922290c9a966b3231d0ce9398b/compiler/rustc_ty_utils/src/implied_bounds.rs#L21 -- cgit 1.4.1-3-g733a5