From 53958b12901d38393d89fd67d9ffe752353c409f Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Wed, 12 Aug 2026 10:17:41 +0300 Subject: [PATCH 01/22] Initial support for delegations to inherent functions --- Cargo.lock | 1 + compiler/rustc_ast_lowering/Cargo.toml | 1 + .../src/delegation/generics.rs | 25 +- .../rustc_ast_lowering/src/delegation/mod.rs | 94 ++++- .../src/delegation/resolution.rs | 236 +++++++++--- .../rustc_ast_lowering/src/diagnostics.rs | 16 + compiler/rustc_ast_lowering/src/lib.rs | 4 + compiler/rustc_hir_analysis/src/delegation.rs | 125 +++++-- compiler/rustc_hir_typeck/src/method/probe.rs | 25 +- compiler/rustc_middle/src/queries.rs | 5 + compiler/rustc_middle/src/ty/context.rs | 4 + compiler/rustc_middle/src/ty/generic_args.rs | 23 +- compiler/rustc_middle/src/ty/mod.rs | 17 +- compiler/rustc_middle/src/ty/sty.rs | 28 +- compiler/rustc_resolve/src/late.rs | 62 +++- compiler/rustc_resolve/src/lib.rs | 7 +- tests/ui/delegation/bad-resolve.rs | 7 +- tests/ui/delegation/bad-resolve.stderr | 86 +++-- tests/ui/delegation/explicit-paths.rs | 5 +- tests/ui/delegation/explicit-paths.stderr | 69 +--- tests/ui/delegation/glob-non-fn.rs | 4 +- tests/ui/delegation/glob-non-fn.stderr | 51 ++- .../delegation/impl-reuse-non-reuse-items.rs | 6 +- .../impl-reuse-non-reuse-items.stderr | 50 ++- .../inherent-impl-non-local-crate.rs | 23 ++ .../inherent-impl-non-local-crate.stderr | 49 +++ tests/ui/delegation/inherent-impls-ambig.rs | 22 +- .../ui/delegation/inherent-impls-ambig.stderr | 170 +++++---- tests/ui/delegation/inherent-impls-enums.rs | 74 ++-- .../ui/delegation/inherent-impls-enums.stderr | 342 ++++++++++++------ .../inherent-impls-glob-list.stderr | 15 +- .../inherent-impls-mixed-generics.stderr | 24 +- .../inherent-impls-non-local-crate.stderr | 40 +- .../inherent-impls-receiver-mapping.stderr | 305 +++++----------- .../inherent-impls-recursive-cycle.rs | 20 +- .../inherent-impls-recursive-cycle.stderr | 118 ++++-- .../ui/delegation/inherent-impls-recursive.rs | 11 +- .../inherent-impls-recursive.stderr | 61 ---- .../inherent-impls-self-mapping.stderr | 25 +- .../inherent-impls-self-replacement.rs | 23 +- .../inherent-impls-self-replacement.stderr | 201 +++++++--- tests/ui/delegation/inherent-impls-structs.rs | 72 ++-- .../delegation/inherent-impls-structs.stderr | 335 ++++++++++------- .../inherent-impls-wrong-header-args-ice.rs | 6 +- ...nherent-impls-wrong-header-args-ice.stderr | 30 +- ...ult-trait-shadow-cycle-issue-151358.stderr | 2 + .../query-cycle-printing-issue-151358.stderr | 2 + .../resolve/query-cycle-issue-124901.stderr | 2 + 48 files changed, 1878 insertions(+), 1045 deletions(-) create mode 100644 tests/ui/delegation/inherent-impl-non-local-crate.rs create mode 100644 tests/ui/delegation/inherent-impl-non-local-crate.stderr delete mode 100644 tests/ui/delegation/inherent-impls-recursive.stderr diff --git a/Cargo.lock b/Cargo.lock index 598ea312408f3..6d06797b7f8a1 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -3634,6 +3634,7 @@ dependencies = [ name = "rustc_ast_lowering" version = "0.0.0" dependencies = [ + "itertools", "rustc_abi", "rustc_ast", "rustc_attr_ir", diff --git a/compiler/rustc_ast_lowering/Cargo.toml b/compiler/rustc_ast_lowering/Cargo.toml index 9dc5f81581e87..f1abbc3acd820 100644 --- a/compiler/rustc_ast_lowering/Cargo.toml +++ b/compiler/rustc_ast_lowering/Cargo.toml @@ -8,6 +8,7 @@ doctest = false [dependencies] # tidy-alphabetical-start +itertools = "0.15" rustc_abi = { path = "../rustc_abi" } rustc_ast = { path = "../rustc_ast" } rustc_attr_ir = { path = "../rustc_attr_ir" } diff --git a/compiler/rustc_ast_lowering/src/delegation/generics.rs b/compiler/rustc_ast_lowering/src/delegation/generics.rs index 911ec5956006d..f40d66b2476b1 100644 --- a/compiler/rustc_ast_lowering/src/delegation/generics.rs +++ b/compiler/rustc_ast_lowering/src/delegation/generics.rs @@ -25,6 +25,7 @@ pub(super) enum GenericArgSlot { Generate(T, Option /* Infer arg index from AST */), } +#[derive(Debug)] pub(super) struct DelegationGenerics { data: T, pos: GenericsPosition, @@ -57,11 +58,13 @@ impl<'hir> DelegationGenerics> { /// meaning we did not propagate them and thus we do not need to generate generic params /// (i.e., method call scenarios), in such a case this approach helps /// a lot as if `into_hir_generics` will not be called then uplifting will not happen. +#[derive(Debug)] pub(super) enum HirOrTyGenerics<'hir> { Ty(DelegationGenerics>), Hir(DelegationGenerics<&'hir hir::Generics<'hir>>), } +#[derive(Debug)] pub(super) struct GenericsGenerationResult<'hir> { pub(super) generics: HirOrTyGenerics<'hir>, pub(super) args_segment_id: HirId, @@ -80,6 +83,7 @@ pub(super) struct GenericsGenerationResults<'hir> { pub(super) self_ty_propagation_kind: Option, } +#[derive(Debug)] pub(super) struct DelegationGenericArgsIterator<'hir> { index: usize = Default::default(), params: &'hir [hir::GenericParam<'hir>], @@ -143,9 +147,12 @@ impl<'hir> DelegationGenericArgsIterator<'hir> { pub(super) fn consume_all( mut self, ctx: &mut LoweringContext<'_, 'hir>, + ids_to_reuse: Vec, ) -> Vec> { let mut args = vec![]; - while let Some(arg) = self.next(ctx, |ctx| ctx.next_id()) { + let mut ids_iter = ids_to_reuse.into_iter(); + while let Some(arg) = self.next(ctx, |ctx| ids_iter.next().unwrap_or_else(|| ctx.next_id())) + { args.push(arg); } @@ -238,6 +245,7 @@ impl<'hir> GenericsGenerationResult<'hir> { } } +#[derive(Debug)] enum ParentSegmentArgs<'a> { /// Parent segment is valid and generic args are specified: /// `reuse Trait::<'static, ()>::foo;`. @@ -288,8 +296,7 @@ impl<'hir> DelegationResolver<'_, 'hir> { let delegation_in_free_ctx = !matches!(delegation_parent_kind, DefKind::Trait | DefKind::Impl { .. }); - let sig_parent = tcx.parent(sig_id); - let sig_in_trait = matches!(tcx.def_kind(sig_parent), DefKind::Trait); + let sig_in_trait = matches!(tcx.def_kind(tcx.parent(sig_id)), DefKind::Trait); let free_to_trait_delegation = delegation_in_free_ctx && sig_in_trait; let mut sig_parent_params: &[ty::GenericParamDef] = &[]; @@ -301,8 +308,11 @@ impl<'hir> DelegationResolver<'_, 'hir> { let parent_args = if let [.., parent_segment, _] = &delegation.path.segments[..] { let res = self.get_resolution_id(parent_segment.id)?; - if matches!(tcx.def_kind(res), DefKind::Trait | DefKind::TraitAlias) { - sig_parent_params = &tcx.generics_of(sig_parent).own_params; + if matches!( + tcx.def_kind(res), + DefKind::Trait | DefKind::Struct | DefKind::Enum | DefKind::TraitAlias + ) { + sig_parent_params = &tcx.generics_of(res).own_params; self.get_user_args(parent_segment) .map(|args| ParentSegmentArgs::Specified(args)) .unwrap_or(ParentSegmentArgs::NotSpecified) @@ -377,19 +387,20 @@ impl<'hir> DelegationResolver<'_, 'hir> { } let tcx = self.tcx(); + let skip_self = !generate_self && tcx.def_kind(tcx.parent(sig_id)) == DefKind::Trait; let parent_generics = match res.parent_args { ParentSegmentArgs::Specified(args) => DelegationGenerics { data: Self::create_slots_from_args( tcx, args, - &sig_parent_params[usize::from(!generate_self)..], + &sig_parent_params[usize::from(skip_self)..], generate_self, ), pos: GenericsPosition::Parent, trait_impl, }, ParentSegmentArgs::NotSpecified => DelegationGenerics::generate_all( - &sig_parent_params[usize::from(!generate_self)..], + &sig_parent_params[usize::from(skip_self)..], GenericsPosition::Parent, trait_impl, ), diff --git a/compiler/rustc_ast_lowering/src/delegation/mod.rs b/compiler/rustc_ast_lowering/src/delegation/mod.rs index 3b9074e67bdd2..065aaa02dbe33 100644 --- a/compiler/rustc_ast_lowering/src/delegation/mod.rs +++ b/compiler/rustc_ast_lowering/src/delegation/mod.rs @@ -47,7 +47,7 @@ use rustc_ast as ast; use rustc_ast::*; use rustc_hir::attrs::lang_items::LangItem; use rustc_hir::def::DefKind; -use rustc_hir::{self as hir, FnDeclFlags}; +use rustc_hir::{self as hir, FnDeclFlags, QPath}; use rustc_middle::ty::Asyncness; use rustc_span::def_id::DefId; use rustc_span::symbol::kw; @@ -62,7 +62,7 @@ use crate::{ mod attributes; mod generics; -mod resolution; +pub(crate) mod resolution; pub(crate) struct DelegationResults<'hir> { pub body_id: hir::BodyId, @@ -414,7 +414,35 @@ impl<'hir> LoweringContext<'_, 'hir> { hir::QPath::Resolved(ty, self.arena.alloc(new_path)) } - hir::QPath::TypeRelative(..) => unreachable!("until inherent methods are supported"), + hir::QPath::TypeRelative(mut ty, segment) => { + let mut segment = self.process_segment(span, segment, &mut generics.child); + segment.res = Res::Def(self.tcx.def_kind(res.call_path_res), res.call_path_res); + + let ty_hir_id = ty.hir_id; + ty = if let hir::TyKind::Path(QPath::Resolved(ty, path)) = ty.kind { + let mut new_path = path.clone(); + + new_path.segments = self.arena.alloc_from_iter( + new_path.segments.iter().enumerate().map(|(idx, segment)| { + if idx + 1 == new_path.segments.len() { + self.process_segment(span, segment, &mut generics.parent) + } else { + segment.clone() + } + }), + ); + + self.arena.alloc(hir::Ty { + hir_id: ty_hir_id, + span, + kind: hir::TyKind::Path(QPath::Resolved(ty, self.arena.alloc(new_path))), + }) + } else { + ty + }; + + hir::QPath::TypeRelative(ty, self.arena.alloc(segment)) + } }; if let Some(hir::DelegationSelfTyPropagationKind::SelfTy(id)) = @@ -489,21 +517,63 @@ impl<'hir> LoweringContext<'_, 'hir> { result.generics.into_hir_generics(self, span); let mut segment = segment.clone(); - let mut args_iter = result.generics.create_args_iterator(); - let new_args = segment - .args - .filter(|args| !args.is_empty()) - .map(|args| { - self.arena.alloc_from_iter(args.args.iter().enumerate().map(|(idx, arg)| { + #[derive(Debug)] + enum NewArgsCreationKind { + Propagate(Vec /* first `N` HIR ids to reuse */), + ExistingWithInfers, + } + + impl NewArgsCreationKind { + fn new(segment: &hir::PathSegment<'_>) -> NewArgsCreationKind { + let Some(args) = segment.args else { + return NewArgsCreationKind::Propagate(vec![]); + }; + + if args.is_empty() { + return NewArgsCreationKind::Propagate(vec![]); + } + + let ids_to_reuse = args + .args + .iter() + .copied() + .take_while(NewArgsCreationKind::should_reuse_id) + .map(|a| a.hir_id()) + .collect::>(); + + if ids_to_reuse.len() == args.args.len() { + NewArgsCreationKind::Propagate(ids_to_reuse) + } else { + NewArgsCreationKind::ExistingWithInfers + } + } + + fn should_reuse_id(a: &hir::GenericArg<'_>) -> bool { + let hir::GenericArg::Lifetime(lt) = a else { return false }; + lt.kind == hir::LifetimeKind::Infer && lt.syntax == hir::LifetimeSyntax::Implicit + } + } + + let mut args_iter = result.generics.create_args_iterator(); + let new_args = match NewArgsCreationKind::new(&segment) { + NewArgsCreationKind::Propagate(ids_to_reuse) => { + let consumed_args = args_iter.consume_all(self, ids_to_reuse); + match consumed_args.is_empty() { + true => segment.args.map(|args| args.args).unwrap_or_default(), + false => self.arena.alloc_from_iter(consumed_args), + } + } + NewArgsCreationKind::ExistingWithInfers => self.arena.alloc_from_iter( + segment.args.expect("must be Some").args.iter().enumerate().map(|(idx, arg)| { if infer_indices.contains(&idx) { args_iter.next(self, |_| arg.hir_id()).expect("arg must exist for infer") } else { *arg } - })) - }) - .unwrap_or_else(|| self.arena.alloc_from_iter(args_iter.consume_all(self))); + }), + ), + }; // Do not omit constraints as there might be some and they must be present in HIR (#158812). let has_constraints = segment.args.is_some_and(|a| !a.constraints.is_empty()); diff --git a/compiler/rustc_ast_lowering/src/delegation/resolution.rs b/compiler/rustc_ast_lowering/src/delegation/resolution.rs index dd1b9518e6d7f..70603c7863f19 100644 --- a/compiler/rustc_ast_lowering/src/delegation/resolution.rs +++ b/compiler/rustc_ast_lowering/src/delegation/resolution.rs @@ -2,22 +2,111 @@ use std::ops::ControlFlow; use ast::visit::Visitor; use hir::def::DefKind; -use rustc_ast::{self as ast, Delegation, DelegationSource, NodeId}; -use rustc_data_structures::fx::{FxHashSet, FxIndexSet}; +use rustc_ast::{ + self as ast, AssocItemKind, AstOwner, Delegation, DelegationSource, Item, ItemKind, NodeId, +}; +use rustc_data_structures::fx::{FxHashSet, FxIndexMap, FxIndexSet}; +use rustc_data_structures::steal::Steal; use rustc_hir as hir; -use rustc_middle::ty::{Ty, TyCtxt, TypeSuperVisitable, TypeVisitable, TypeVisitor}; -use rustc_middle::{span_bug, ty}; +use rustc_middle::ty::{ + self, AssocKind, DelegationInhFuncKind, Ty, TyCtxt, TypeRelativeDelegationRes, + TypeSuperVisitable, TypeVisitable, TypeVisitor, +}; use rustc_span::def_id::{DefId, LocalDefId}; use rustc_span::{ErrorGuaranteed, Span}; use crate::delegation::generics::GenericsGenerationResults; use crate::delegation::resolution::resolver::DelegationResolver; use crate::diagnostics::{ - CycleInDelegationSignatureResolution, DelegationAttemptedBlockWithDefsDeletion, - DelegationAttemptedBlockWithDefsRelowering, DelegationBlockSpecifiedWhenNoParams, + AmbiguousDelegationToInherentImpl, CycleInDelegationSignatureResolution, + DelegationAttemptedBlockWithDefsDeletion, DelegationAttemptedBlockWithDefsRelowering, + DelegationBlockSpecifiedWhenNoParams, DelegationGenericsMismatchInInherentImpl, UnresolvedDelegationCallee, }; +pub(crate) fn resolve_type_relative_delegations( + tcx: TyCtxt<'_>, + _: (), +) -> FxIndexMap { + let ast_index = tcx.index_ast(()); + let resolutions = tcx.resolutions(()); + + let infos = &resolutions.delegation_infos; + let inh_methods = &resolutions.delegation_inh_functions_map; + + let mut type_relative_resolutions: FxIndexMap = + Default::default(); + + for (&def_id, res) in infos { + if res.resolution_id.is_some() { + continue; + } + + let Some(r_and_owner) = ast_index.get(def_id).map(Steal::borrow) else { + unreachable!("ast index must contain delegations"); + }; + + let (r, owner) = &*r_and_owner; + + let delegation = match owner { + AstOwner::Item(Item { kind: ItemKind::Delegation(d), .. }) + | AstOwner::TraitItem(Item { kind: AssocItemKind::Delegation(d), .. }) + | AstOwner::ImplItem(Item { kind: AssocItemKind::Delegation(d), .. }) => d, + _ => unreachable!("we are processing only delegations"), + }; + + let res = r.partial_res_map.get(&delegation.id); + let res = res.and_then(|res| res.base_res().opt_def_id()); + let ident = delegation.path.segments.last().map(|s| s.ident); + + let res = if let Some(res) = res + && let Some(ident) = ident + { + match res.as_local() { + Some(local_def_id) => { + let res = inh_methods.get(&local_def_id).and_then(|map| map.get(&ident)); + + match res { + Some(res) => match res { + DelegationInhFuncKind::Ambig => TypeRelativeDelegationRes::Ambig, + DelegationInhFuncKind::Single(res) => { + TypeRelativeDelegationRes::Ok(res.to_def_id()) + } + }, + _ => TypeRelativeDelegationRes::Error, + } + } + None => { + let mut sig_res = None; + 'inh_loop: for inh_impl_id in tcx.inherent_impls(res) { + let assoc_items = tcx.associated_items(*inh_impl_id); + let mut candidates = assoc_items + .filter_by_name_unhygienic(ident.name) + .filter(|it| matches!(it.kind, AssocKind::Fn { .. })); + + while let Some(candidate) = candidates.next() { + if sig_res.is_some() { + sig_res = Some(TypeRelativeDelegationRes::Ambig); + break 'inh_loop; + } else { + sig_res = Some(TypeRelativeDelegationRes::Ok(candidate.def_id)); + } + } + } + + sig_res.unwrap_or(TypeRelativeDelegationRes::Error) + } + } + } else { + TypeRelativeDelegationRes::Error + }; + + type_relative_resolutions.insert(def_id, res); + } + + type_relative_resolutions +} + /// Summary info about function parameters. #[derive(Debug, Clone, Copy, Eq, PartialEq)] pub(super) struct ParamInfo { @@ -100,6 +189,10 @@ pub(super) mod resolver { || self.tcx().dcx().delayed_bug(format!("failed to resolve node {id:?}")), ) } + + pub(crate) fn opt_resolution_id(&self, id: NodeId) -> Option { + self.0.get_partial_res(id).and_then(|r| r.full_res()).and_then(|r| r.opt_def_id()) + } } } @@ -114,26 +207,12 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { // Delegation can be missing from the `delegations_resolutions` table // in illegal places such as function bodies in extern blocks (see #151356). - let sig_id = tcx - .resolutions(()) - .delegation_infos - .get(&def_id) - .map(|info| { - info.resolution_id.and_then(|id| self.check_for_cycles(id, span).map(|_| id)) - }) - .unwrap_or_else(|| { - Err(tcx.dcx().span_delayed_bug( - span, - format!("delegation resolution record was not found for {:?}", def_id), - )) - })?; - - let is_method = match tcx.def_kind(sig_id) { - DefKind::Fn => false, - DefKind::AssocFn => tcx.associated_item(sig_id).is_method(), - _ => span_bug!(span, "unexpected DefKind for delegation item"), - }; + let sig_id = self.resolve_delegation_sig(def_id, span)?; + + self.check_inherent_impl_generic_args(sig_id, span)?; + self.check_for_cycles(sig_id, span)?; + let is_method = tcx.is_method(sig_id); let sig = tcx.fn_sig(sig_id).skip_binder().skip_binder(); let param_count = sig.inputs().len() + usize::from(sig.c_variadic()); let parent = tcx.local_parent(def_id); @@ -149,7 +228,7 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { // FIXME(splat): use `sig.splatted()` once FnSig has it param_info: ParamInfo { param_count, c_variadic: sig.c_variadic(), splatted: None }, source: delegation.source, - call_path_res: self.get_resolution_id(delegation.id)?, + call_path_res: self.get_call_path_res(delegation, span)?, sig_mapping: self.create_sig_mapping( delegation, span, @@ -163,9 +242,83 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { Ok((res, self.resolve_and_generate_generics(delegation, sig_id)?)) } + fn check_inherent_impl_generic_args( + &self, + sig_id: DefId, + span: Span, + ) -> Result<(), ErrorGuaranteed> { + let tcx = self.tcx(); + if !matches!(tcx.def_kind(tcx.parent(sig_id)), DefKind::Impl { of_trait: false }) { + return Ok(()); + } + + let ty::Adt(def, args) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { + unreachable!("parent of inherent function can be only struct or enum") + }; + + let adt_params = &tcx.generics_of(def.did()).own_params; + let adt_params_types = adt_params.iter().map(|p| p.kind.is_ty_or_const()); + + let actual_args = args.iter().flat_map(|a| a.opt_param_info().map(|a| a.1)); + + itertools::equal(actual_args, adt_params_types) + .ok_or_else(|| tcx.dcx().emit_err(DelegationGenericsMismatchInInherentImpl { span })) + } + + fn get_call_path_res( + &self, + delegation: &Delegation, + span: Span, + ) -> Result { + self.opt_resolution_id(delegation.id) + .map(|id| Ok(id)) + .unwrap_or_else(|| self.resolve_delegation_sig(self.owner_id(), span)) + } + + fn resolve_delegation_sig( + &self, + def_id: LocalDefId, + span: Span, + ) -> Result { + self.tcx() + .resolutions(()) + .delegation_infos + .get(&def_id) + .and_then(|info| info.resolution_id) + .map(|id| Ok(id)) + .unwrap_or_else(|| self.resolve_type_relative_delegation_sig(def_id, span)) + } + + fn resolve_type_relative_delegation_sig( + &self, + def_id: LocalDefId, + span: Span, + ) -> Result { + let tcx = self.tcx(); + + let unresolved_error = + || Err(tcx.dcx().span_delayed_bug(span, format!("unresolved delegation {def_id:?}"))); + + if matches!(tcx.def_kind(tcx.local_parent(def_id)), DefKind::Impl { of_trait: true }) { + return unresolved_error(); + } + + match tcx.resolve_type_relative_delegations(()).get(&def_id) { + Some(res) => match res { + TypeRelativeDelegationRes::Ok(sig_id) => Ok(*sig_id), + TypeRelativeDelegationRes::Error => unresolved_error(), + TypeRelativeDelegationRes::Ambig => { + Err(tcx.dcx().emit_err(AmbiguousDelegationToInherentImpl { span })) + } + }, + None => unresolved_error(), + } + } + fn check_for_cycles(&self, mut def_id: DefId, span: Span) -> Result<(), ErrorGuaranteed> { let tcx = self.tcx(); let mut visited: FxHashSet = Default::default(); + let delegation_infos = &tcx.resolutions(()).delegation_infos; loop { visited.insert(def_id); @@ -174,8 +327,8 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { // it means that we refer to another delegation as a callee, so in order to obtain // a signature DefId we obtain NodeId of the callee delegation and try to get signature from it. if let Some(local_id) = def_id.as_local() - && let Some(info) = tcx.resolutions(()).delegation_infos.get(&local_id) - && let Ok(id) = info.resolution_id + && delegation_infos.contains_key(&local_id) + && let Ok(id) = self.resolve_delegation_sig(local_id, span) { def_id = id; if visited.contains(&def_id) { @@ -253,7 +406,7 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { mapping.arguments_to_map.insert(0); } - if self.can_perform_self_mapping(delegation, parent)? { + if self.can_perform_self_mapping(delegation, parent) { /// Finds `Self` generic param only in ADT or references, so we avoid cases like /// `Self::Item` which will return true if `output.contains(...)` will be used. struct SelfFinder; @@ -307,23 +460,18 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { // We can't yet map more than one argument if there are definitions inside. // FIXME(fn_delegation): support relowering with defs inside if contains_defs && mapping.arguments_to_map.len() > 1 { - return Err(self - .tcx() - .dcx() - .emit_err(DelegationAttemptedBlockWithDefsRelowering { span })); + let err = DelegationAttemptedBlockWithDefsRelowering { span }; + let err = self.tcx().dcx().emit_err(err); + return Err(err); } Ok(mapping) } - fn can_perform_self_mapping( - &self, - delegation: &Delegation, - parent: LocalDefId, - ) -> Result { + fn can_perform_self_mapping(&self, delegation: &Delegation, parent: LocalDefId) -> bool { // Heuristic: don't do wrapping if there is no target expression. if delegation.body.is_none() { - return Ok(false); + return false; } let tcx = self.tcx(); @@ -339,13 +487,17 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { // 2) Inherent methods when delegating to trait, as we change the type of // `Self` to type of struct or enum we delegate from. if !matches!(tcx.def_kind(parent), DefKind::Impl { .. }) { - return Ok(false); + return false; } // Check that delegation path resolves to a trait AssocFn, not to a free method. // After previous check we are sure that `sig_id` and `delegation.id` // point to the same function. - let id = self.get_resolution_id(delegation.id)?; - Ok(tcx.def_kind(id) == DefKind::AssocFn && tcx.def_kind(tcx.parent(id)) == DefKind::Trait) + self.opt_resolution_id(delegation.id) + .map(|id| { + tcx.def_kind(id) == DefKind::AssocFn + && tcx.def_kind(tcx.parent(id)) == DefKind::Trait + }) + .unwrap_or(false) } } diff --git a/compiler/rustc_ast_lowering/src/diagnostics.rs b/compiler/rustc_ast_lowering/src/diagnostics.rs index b0fada9d3cd9e..230c3c9a4e7b3 100644 --- a/compiler/rustc_ast_lowering/src/diagnostics.rs +++ b/compiler/rustc_ast_lowering/src/diagnostics.rs @@ -609,3 +609,19 @@ pub(crate) struct RestrictionAncestorOnly { pub(crate) span: Span, pub(crate) kind: ResolvingRestrictionKind, } + +#[derive(Diagnostic)] +#[diag("ambiguous delegation to inherent impl function")] +pub(crate) struct AmbiguousDelegationToInherentImpl { + #[primary_span] + pub span: Span, +} + +#[derive(Diagnostic)] +#[diag( + "failed to generate delegation: mismatch between provided generic args in inherent impl and declared generics" +)] +pub(crate) struct DelegationGenericsMismatchInInherentImpl { + #[primary_span] + pub span: Span, +} diff --git a/compiler/rustc_ast_lowering/src/lib.rs b/compiler/rustc_ast_lowering/src/lib.rs index def0934214ef2..e9946341c38ae 100644 --- a/compiler/rustc_ast_lowering/src/lib.rs +++ b/compiler/rustc_ast_lowering/src/lib.rs @@ -99,6 +99,8 @@ pub mod stability; pub fn provide(providers: &mut Providers) { providers.index_ast = index_ast; providers.lower_to_hir = lower_to_hir; + providers.resolve_type_relative_delegations = + delegation::resolution::resolve_type_relative_delegations; } #[cfg(debug_assertions)] @@ -657,6 +659,8 @@ fn index_ast<'tcx>( #[instrument(level = "trace", skip(tcx))] fn lower_to_hir(tcx: TyCtxt<'_>, def_id: LocalDefId) -> hir::MaybeOwner<'_> { + tcx.ensure_done().resolve_type_relative_delegations(()); + let ast_index = tcx.index_ast(()); let resolver_and_node = ast_index.get(def_id).map(Steal::steal); diff --git a/compiler/rustc_hir_analysis/src/delegation.rs b/compiler/rustc_hir_analysis/src/delegation.rs index 5324b4d3552c6..28c8d843642cf 100644 --- a/compiler/rustc_hir_analysis/src/delegation.rs +++ b/compiler/rustc_hir_analysis/src/delegation.rs @@ -122,8 +122,6 @@ fn fn_kinds(tcx: TyCtxt<'_>, def_id: LocalDefId, sig_id: DefId) -> (FnKind, FnKi // For trait impl's `sig_id` is always equal to the corresponding trait method. assert!(!matches!(kinds, (_, FnKind::AssocTraitImpl))); - // Delegation to inherent impls is not yet supported. - assert!(!matches!(kinds, (_, FnKind::AssocInherentImpl))); kinds } @@ -177,20 +175,44 @@ fn create_mapping<'tcx>( args_index += is_self_at_zero as usize; args_index += get_delegation_parent_args_count_without_self(tcx, def_id, sig_id); - let sig_generics = tcx.generics_of(sig_id); - let process_sig_parent_generics = matches!(fn_kind(tcx, sig_id), FnKind::AssocTrait); + let parent_kind = fn_kind(tcx, sig_id); + let process_parent = matches!(parent_kind, FnKind::AssocTrait | FnKind::AssocInherentImpl); + let parent_generics = process_parent.then(|| tcx.generics_of(tcx.parent(sig_id))); - if process_sig_parent_generics { - for i in (sig_generics.has_self as usize)..sig_generics.parent_count { - let param = sig_generics.param_at(i, tcx); - if !param.kind.is_ty_or_const() { - mapping.insert(param.index, args_index as u32); + let parent_params = match parent_kind { + FnKind::AssocInherentImpl => { + let ty::Adt(_, args) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { + unreachable!("parent of inherent function in delegation can be only struct or enum") + }; + + args.iter().flat_map(|a| a.opt_param_info()).collect::>() + } + FnKind::AssocTrait => parent_generics + .expect("trait must have generics") + .own_params + .iter() + .map(|p| (p.index as u32, p.kind.is_ty_or_const())) + .collect::>(), + _ => vec![], + }; + + let has_self = match parent_kind { + FnKind::AssocTrait => parent_generics.expect("trait must have generics").has_self, + _ => false, + }; + + if process_parent { + for i in (has_self as usize)..parent_params.len() { + let (index, is_ty_or_const) = parent_params[i]; + if !is_ty_or_const { + mapping.insert(index, args_index as u32); args_index += 1; } } } - for param in &sig_generics.own_params { + let child_generics = tcx.generics_of(sig_id); + for param in &child_generics.own_params { if !param.kind.is_ty_or_const() { mapping.insert(param.index, args_index as u32); args_index += 1; @@ -205,17 +227,17 @@ fn create_mapping<'tcx>( args_index += 1; } - if process_sig_parent_generics { - for i in (sig_generics.has_self as usize)..sig_generics.parent_count { - let param = sig_generics.param_at(i, tcx); - if param.kind.is_ty_or_const() { - mapping.insert(param.index, args_index as u32); + if process_parent { + for i in (has_self as usize)..parent_params.len() { + let (index, is_ty_or_const) = parent_params[i]; + if is_ty_or_const { + mapping.insert(index, args_index as u32); args_index += 1; } } } - for param in &sig_generics.own_params { + for param in &child_generics.own_params { if param.kind.is_ty_or_const() { mapping.insert(param.index, args_index as u32); args_index += 1; @@ -340,7 +362,7 @@ fn create_generic_args<'tcx>( let delegation_args = &delegation_args[delegation_generics.parent_count..]; - let kinds = fn_kinds(tcx, def_id, sig_id); + let kinds @ (_, parent_kind) = fn_kinds(tcx, def_id, sig_id); if matches!(kinds, (FnKind::AssocTraitImpl, FnKind::AssocTrait)) { // Special case, as user specifies Trait args in trait impl header, we want to treat // them as parent args. We always generate a function whose generics match @@ -358,10 +380,14 @@ fn create_generic_args<'tcx>( let self_type = get_delegation_self_ty(tcx, def_id).map(ty::GenericArg::from); - // Remove `Self` from parent args (it is always at the `0th` index) as it is - // added manually. if self_type.is_some() && !parent_args.is_empty() { - parent_args = &parent_args[1..]; + parent_args = match parent_kind { + FnKind::AssocInherentImpl => parent_args, + // Remove `Self` from parent args (it is always at the `0th` index) as it is + // added manually. + FnKind::AssocTrait => &parent_args[1..], + _ => unreachable!("if parent args are non-empty then the parent must exist"), + } } let (zero_self, after_lifetimes_self) = @@ -583,8 +609,42 @@ pub(crate) fn inherit_sig_for_delegation_item<'tcx>( let caller_sig = EarlyBinder::bind(tcx, caller_sig.skip_binder().fold_with(&mut folder)); let sig = caller_sig.instantiate(tcx, args.as_slice()).skip_binder(); - let sig_iter = sig.inputs().iter().cloned().chain(std::iter::once(sig.output())); - tcx.arena.alloc_from_iter(sig_iter) + let output = std::iter::once(sig.output()); + let mut sig = sig.inputs().iter().cloned().chain(output).collect::>(); + + adjust_sig_in_inherent_impl_cases(tcx, sig_id, def_id, parent_args, &mut sig); + + tcx.arena.alloc_from_iter(sig) +} + +fn adjust_sig_in_inherent_impl_cases<'tcx>( + tcx: TyCtxt<'tcx>, + sig_id: DefId, + def_id: LocalDefId, + parent_args: &[ty::GenericArg<'tcx>], + sig: &mut [Ty<'tcx>], +) { + if !tcx.is_method(sig_id) { + return; + } + + let self_input = sig[0]; + + sig[0] = match fn_kinds(tcx, def_id, sig_id) { + (FnKind::AssocInherentImpl, FnKind::AssocInherentImpl) => { + tcx.type_of(tcx.parent(def_id.to_def_id())).skip_binder() + } + (FnKind::AssocTrait, FnKind::AssocInherentImpl) => { + let ty::Adt(def, _) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { + unreachable!("delegation is supported only to struct or enums") + }; + + let sig_self_type = Ty::new_adt(tcx, *def, tcx.mk_args(parent_args)); + let self_param = Ty::new_param(tcx, 0, kw::SelfUpper); + self_input.replace_inside(tcx, sig_self_type, self_param) + } + _ => self_input, + }; } // Creates user-specified generic arguments from delegation path, @@ -607,7 +667,9 @@ pub(crate) fn delegation_user_specified_args<'tcx>( let parent_args = info .parent_seg_id_for_sig .and_then(get_segment) - .filter(|(_, def_id)| matches!(tcx.def_kind(*def_id), DefKind::Trait)) + .filter(|(_, def_id)| { + matches!(tcx.def_kind(*def_id), DefKind::Trait | DefKind::Struct | DefKind::Enum) + }) .map(|(segment, def_id)| { let self_ty = (tcx.def_kind(def_id) == DefKind::Trait) .then(|| Ty::new_param(tcx, 0, kw::SelfUpper)); @@ -623,14 +685,19 @@ pub(crate) fn delegation_user_specified_args<'tcx>( .and_then(get_segment) .filter(|(_, def_id)| matches!(tcx.def_kind(*def_id), DefKind::Fn | DefKind::AssocFn)) .map(|(segment, def_id)| { - let parent_args = if let Some(parent_args) = parent_args { - parent_args + let parent = tcx.parent(def_id); + + let parent_args = if matches!(tcx.def_kind(parent), DefKind::Impl { of_trait: false }) { + ty::GenericArgs::identity_for_item(tcx, parent).as_slice() } else { - let parent = tcx.parent(def_id); - if matches!(tcx.def_kind(parent), DefKind::Trait) { - ty::GenericArgs::identity_for_item(tcx, parent).as_slice() + if let Some(parent_args) = parent_args { + parent_args } else { - &[] + if matches!(tcx.def_kind(parent), DefKind::Trait) { + ty::GenericArgs::identity_for_item(tcx, parent).as_slice() + } else { + &[] + } } }; diff --git a/compiler/rustc_hir_typeck/src/method/probe.rs b/compiler/rustc_hir_typeck/src/method/probe.rs index f5b8b9d6a1e6f..15916db330381 100644 --- a/compiler/rustc_hir_typeck/src/method/probe.rs +++ b/compiler/rustc_hir_typeck/src/method/probe.rs @@ -1,7 +1,7 @@ use std::cell::{Cell, RefCell}; use std::cmp::max; -use std::debug_assert_matches; use std::ops::Deref; +use std::{assert_matches, debug_assert_matches}; use rustc_data_structures::fx::FxHashSet; use rustc_data_structures::sso::SsoHashSet; @@ -595,8 +595,10 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { } ProbeScope::Single(def_id, self_ty_override) => { let item = self.tcx.associated_item(def_id); - // FIXME(fn_delegation): Delegation to inherent methods is not yet supported. - assert_eq!(item.container, AssocContainer::Trait); + assert_matches!( + item.container, + AssocContainer::Trait | AssocContainer::InherentImpl + ); let trait_def_id = self.tcx.parent(def_id); let trait_span = self.tcx.def_span(trait_def_id); @@ -608,10 +610,19 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { probe_cx.push_candidate( Candidate { item, - kind: CandidateKind::TraitCandidate( - ty::Binder::dummy(trait_ref), - false, - ), + kind: match item.container { + AssocContainer::Trait => CandidateKind::TraitCandidate( + ty::Binder::dummy(trait_ref), + false, + ), + AssocContainer::InherentImpl => { + CandidateKind::InherentImplCandidate { + impl_def_id: self.tcx.parent(def_id), + receiver_steps: 0, + } + } + _ => unreachable!(), + }, import_ids: &[], }, false, diff --git a/compiler/rustc_middle/src/queries.rs b/compiler/rustc_middle/src/queries.rs index 5794a6533bd1d..389eb7a984c97 100644 --- a/compiler/rustc_middle/src/queries.rs +++ b/compiler/rustc_middle/src/queries.rs @@ -226,6 +226,11 @@ rustc_queries! { desc { "getting the source span" } } + query resolve_type_relative_delegations(_: ()) -> &'tcx FxIndexMap { + arena_cache + desc { "resolving type relative delegations" } + } + query lower_to_hir(def_id: LocalDefId) -> hir::MaybeOwner<'tcx> { eval_always desc { "lowering HIR for `{}`", tcx.def_path_str(def_id) } diff --git a/compiler/rustc_middle/src/ty/context.rs b/compiler/rustc_middle/src/ty/context.rs index 924dc7552e59b..3962af0ec3586 100644 --- a/compiler/rustc_middle/src/ty/context.rs +++ b/compiler/rustc_middle/src/ty/context.rs @@ -1268,6 +1268,10 @@ impl<'tcx> TyCtxt<'tcx> { None => Err(VarError::NotPresent), } } + + pub fn is_method(self, id: DefId) -> bool { + self.opt_associated_item(id).is_some_and(|item| item.is_method()) + } } impl<'tcx> TyCtxtAt<'tcx> { diff --git a/compiler/rustc_middle/src/ty/generic_args.rs b/compiler/rustc_middle/src/ty/generic_args.rs index 96e59c22c0d8d..18deada559e40 100644 --- a/compiler/rustc_middle/src/ty/generic_args.rs +++ b/compiler/rustc_middle/src/ty/generic_args.rs @@ -16,9 +16,9 @@ use smallvec::SmallVec; use crate::ty::codec::{TyDecoder, TyEncoder}; use crate::ty::{ - self, ClosureArgs, CoroutineArgs, CoroutineClosureArgs, FallibleTypeFolder, InlineConstArgs, - Lift, List, Ty, TyCtxt, TypeFoldable, TypeFolder, TypeVisitable, TypeVisitor, VisitorResult, - walk_visitable_list, + self, ClosureArgs, ConstKind, CoroutineArgs, CoroutineClosureArgs, FallibleTypeFolder, + InlineConstArgs, Lift, List, RegionKind, Ty, TyCtxt, TypeFoldable, TypeFolder, TypeVisitable, + TypeVisitor, VisitorResult, walk_visitable_list, }; pub type GenericArgKind<'tcx> = rustc_type_ir::GenericArgKind>; @@ -316,6 +316,23 @@ impl<'tcx> GenericArg<'tcx> { pub fn walk(self) -> TypeWalker> { TypeWalker::new(self) } + + pub fn opt_param_info(self) -> Option<(u32 /* index */, bool /* is ty or const */)> { + match self.kind() { + GenericArgKind::Lifetime(r) => match r.kind() { + RegionKind::ReEarlyParam(p) => Some((p.index, false)), + _ => None, + }, + GenericArgKind::Type(t) => match t.kind() { + ty::Param(p) => Some((p.index, true)), + _ => None, + }, + GenericArgKind::Const(c) => match c.kind() { + ConstKind::Param(p) => Some((p.index, true)), + _ => None, + }, + } + } } impl<'a, 'tcx> Lift> for GenericArg<'a> { diff --git a/compiler/rustc_middle/src/ty/mod.rs b/compiler/rustc_middle/src/ty/mod.rs index 0ced7d1ea2bc5..19fd3f0d06fb8 100644 --- a/compiler/rustc_middle/src/ty/mod.rs +++ b/compiler/rustc_middle/src/ty/mod.rs @@ -203,6 +203,8 @@ pub struct ResolverGlobalCtxt { // Information about delegations which is used when handling recursive delegations // and ensures easy access to delegation-only `LocalDefId`s. pub delegation_infos: FxIndexMap, + pub delegation_inh_functions_map: + FxIndexMap>, } #[derive(Debug)] @@ -283,7 +285,20 @@ pub struct DelegationInfo { /// Refers to the next element in a delegation resolution chain. /// Usually points to the final resolution, as most "chains" are just /// one step to a trait or an impl. - pub resolution_id: Result, + pub resolution_id: Option, +} + +#[derive(Debug, StableHash)] +pub enum TypeRelativeDelegationRes { + Ok(DefId), + Ambig, + Error, +} + +#[derive(Debug, StableHash)] +pub enum DelegationInhFuncKind { + Single(LocalDefId), + Ambig, } #[derive(Clone, Copy, Debug, StableHash)] diff --git a/compiler/rustc_middle/src/ty/sty.rs b/compiler/rustc_middle/src/ty/sty.rs index 013064b5cec4b..e9782a942de6f 100644 --- a/compiler/rustc_middle/src/ty/sty.rs +++ b/compiler/rustc_middle/src/ty/sty.rs @@ -18,7 +18,8 @@ use rustc_type_ir::TyKind::*; use rustc_type_ir::solve::SizedTraitKind; use rustc_type_ir::walk::TypeWalker; use rustc_type_ir::{ - self as ir, BoundVar, CollectAndApply, MayBeErased, TypeVisitableExt, elaborate, + self as ir, BoundVar, CollectAndApply, MayBeErased, TypeFoldable, TypeFolder, + TypeSuperFoldable, TypeVisitableExt, elaborate, }; use tracing::instrument; use ty::util::IntTypeExt; @@ -1551,6 +1552,31 @@ impl<'tcx> Ty<'tcx> { cf.is_break() } + pub fn replace_inside( + self, + tcx: TyCtxt<'tcx>, + to_replace: Ty<'tcx>, + replacement: Ty<'tcx>, + ) -> Ty<'tcx> { + struct Replacer<'tcx> { + tcx: TyCtxt<'tcx>, + to_replace: Ty<'tcx>, + replacement: Ty<'tcx>, + } + + impl<'tcx> TypeFolder> for Replacer<'tcx> { + fn fold_ty(&mut self, t: Ty<'tcx>) -> Ty<'tcx> { + if t == self.to_replace { self.replacement } else { t.super_fold_with(self) } + } + + fn cx(&self) -> TyCtxt<'tcx> { + self.tcx + } + } + + self.fold_with(&mut Replacer { tcx, to_replace, replacement }) + } + /// Checks whether a type recursively contains any closure /// /// Example: `Option<{closure@file.rs:4:20}>` returns true diff --git a/compiler/rustc_resolve/src/late.rs b/compiler/rustc_resolve/src/late.rs index 396db754f7c96..b6507f94973c7 100644 --- a/compiler/rustc_resolve/src/late.rs +++ b/compiler/rustc_resolve/src/late.rs @@ -30,7 +30,7 @@ use rustc_hir::def_id::{CRATE_DEF_ID, DefId, LOCAL_CRATE, LocalDefId}; use rustc_hir::{MissingLifetimeKind, PrimTy}; use rustc_lint_defs::builtin::{ELIDED_LIFETIMES_IN_PATHS, UNUSED_LABELS}; use rustc_middle::middle::resolve_bound_vars::Set1; -use rustc_middle::ty::{AssocTag, DelegationInfo, Visibility}; +use rustc_middle::ty::{AssocTag, DelegationInfo, DelegationInhFuncKind, Visibility}; use rustc_middle::{bug, span_bug}; use rustc_session::config::ResolveDocLinks; use rustc_session::diagnostics::feature_err; @@ -490,11 +490,11 @@ impl PathSource<'_, '_, '_> { | PathSource::Pat | PathSource::Struct(_) | PathSource::TupleStruct(..) + | PathSource::Delegation | PathSource::ReturnTypeNotation => true, PathSource::Trait(_) | PathSource::TraitItem(..) | PathSource::DefineOpaques - | PathSource::Delegation | PathSource::ExternItemImpl | PathSource::PreciseCapturingArg(..) | PathSource::Macro @@ -3561,6 +3561,17 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { // Resolve the generic parameters. this.visit_generics(generics); + let self_type_def_id = of_trait + .is_none() + .then(|| { + this.r.partial_res_map.get(&self_type.id).and_then(|res| { + res.full_res() + .and_then(|r| r.opt_def_id()) + .and_then(|id| id.as_local()) + }) + }) + .flatten(); + // Resolve the items within the impl. this.with_current_self_type(self_type, |this| { this.with_self_rib_ns(ValueNS, Res::SelfCtor(item_def_id), |this| { @@ -3568,7 +3579,13 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { let mut seen_trait_items = Default::default(); for item in impl_items { with_owner(this, item.id, |this| { - this.resolve_impl_item(&**item, &mut seen_trait_items, trait_id, of_trait.is_some()); + this.resolve_impl_item( + &**item, + &mut seen_trait_items, + trait_id, + of_trait.is_some(), + self_type_def_id + ); }) } }); @@ -3611,6 +3628,7 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { seen_trait_items: &mut FxHashMap, trait_id: Option, is_in_trait_impl: bool, + self_type_def_id: Option, ) { use crate::ResolutionError::*; self.resolve_doc_links(&item.attrs, MaybeExported::ImplItem(trait_id.ok_or(&item.vis))); @@ -3712,6 +3730,10 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { }, ); + if let Some(self_type_def_id) = self_type_def_id { + self.fill_delegation_inh_functions_map(self_type_def_id, ident); + } + self.resolve_define_opaques(define_opaque); } AssocItemKind::Type(TyAlias { ident, generics, .. }) => { @@ -3754,6 +3776,13 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { LifetimeBinderKind::Function, delegation.path.segments.last().unwrap().ident.span, |this| { + if let Some(self_type_def_id) = self_type_def_id { + this.fill_delegation_inh_functions_map( + self_type_def_id, + &delegation.ident, + ); + } + this.check_trait_item( item.id, delegation.ident, @@ -3778,6 +3807,20 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { self.diag_metadata.current_impl_item = prev; } + fn fill_delegation_inh_functions_map(&mut self, self_type_def_id: LocalDefId, ident: &Ident) { + let map = self.r.delegation_inh_functions_map.entry(self_type_def_id).or_default(); + + match map.get(ident) { + None => { + map.insert(*ident, DelegationInhFuncKind::Single(self.r.current_owner.def_id)); + } + Some(DelegationInhFuncKind::Single(..)) => { + map.insert(*ident, DelegationInhFuncKind::Ambig); + } + _ => {} + }; + } + fn check_trait_item( &mut self, id: NodeId, @@ -3942,20 +3985,11 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { }); let resolution_node_id = if is_in_trait_impl { item_id } else { delegation.id }; - let def_id = self + let resolution_id = self .r .partial_res_map .get(&resolution_node_id) - .and_then(|r| r.expect_full_res().opt_def_id()); - - let resolution_id = def_id.ok_or_else(|| { - self.r.tcx.dcx().span_delayed_bug( - delegation.path.span, - format!( - "LateResolutionVisitor: couldn't resolve node {resolution_node_id:?} in delegation item", - ), - ) - }); + .and_then(|r| r.full_res().and_then(|res| res.opt_def_id())); let info = DelegationInfo { resolution_id }; self.r.delegation_infos.insert(self.r.current_owner.def_id, info); diff --git a/compiler/rustc_resolve/src/lib.rs b/compiler/rustc_resolve/src/lib.rs index f5e684cb81631..9aa3c79191651 100644 --- a/compiler/rustc_resolve/src/lib.rs +++ b/compiler/rustc_resolve/src/lib.rs @@ -66,8 +66,8 @@ use rustc_middle::metadata::{AmbigModChild, ModChild, Reexport}; use rustc_middle::middle::privacy::EffectiveVisibilities; use rustc_middle::query::Providers; use rustc_middle::ty::{ - self, DelegationInfo, MainDefinition, PerOwnerResolverData, RegisteredTools, - ResolverAstLowering, ResolverGlobalCtxt, TyCtxt, TyCtxtFeed, Visibility, + self, DelegationInfo, DelegationInhFuncKind, MainDefinition, PerOwnerResolverData, + RegisteredTools, ResolverAstLowering, ResolverGlobalCtxt, TyCtxt, TyCtxtFeed, Visibility, }; use rustc_middle::{bug, span_bug}; use rustc_span::def_id::{LocalModId, ModId}; @@ -1516,6 +1516,7 @@ pub struct Resolver<'ra, 'tcx> { item_required_generic_args_suggestions: FxHashMap = default::fx_hash_map(), delegation_fn_sigs: LocalDefIdMap = Default::default(), delegation_infos: FxIndexMap, + delegation_inh_functions_map: FxIndexMap>, main_def: Option = None, trait_impls: FxIndexMap>, @@ -1888,6 +1889,7 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> { current_crate_outer_attr_insert_span, disambiguators: Default::default(), delegation_infos: Default::default(), + delegation_inh_functions_map: Default::default(), features: tcx.features(), .. }; @@ -1992,6 +1994,7 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> { all_macro_rules: self.all_macro_rules, stripped_cfg_items, delegation_infos: self.delegation_infos, + delegation_inh_functions_map: self.delegation_inh_functions_map, }; let ast_lowering = ty::ResolverAstLowering { partial_res_map: self.partial_res_map, diff --git a/tests/ui/delegation/bad-resolve.rs b/tests/ui/delegation/bad-resolve.rs index eb31c20081461..caf4b6f4ac211 100644 --- a/tests/ui/delegation/bad-resolve.rs +++ b/tests/ui/delegation/bad-resolve.rs @@ -33,10 +33,11 @@ impl Trait for S { reuse foo { &self.0 } //~^ ERROR cannot find function `foo` in this scope - //~| ERROR: method `foo` has a `&self` declaration in the trait, but not in the impl reuse Trait::foo2 { self.0 } - //~^ ERROR cannot find function `foo2` in trait `Trait` - //~| ERROR method `foo2` is not a member of trait `Trait` + //~^ ERROR: method `foo2` is not a member of trait `Trait` + //~| WARN: trait objects without an explicit `dyn` are deprecated [bare_trait_objects] + //~| WARN: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! + //~| ERROR: the trait `Trait` is not dyn compatible [E0038] } mod prefix {} diff --git a/tests/ui/delegation/bad-resolve.stderr b/tests/ui/delegation/bad-resolve.stderr index 44cf5149d08dd..0cf25e0ecbb10 100644 --- a/tests/ui/delegation/bad-resolve.stderr +++ b/tests/ui/delegation/bad-resolve.stderr @@ -26,7 +26,7 @@ LL | reuse ::baz; | not a member of trait `Trait` error[E0407]: method `foo2` is not a member of trait `Trait` - --> $DIR/bad-resolve.rs:37:5 + --> $DIR/bad-resolve.rs:36:5 | LL | reuse Trait::foo2 { self.0 } | ^^^^^^^^^^^^^----^^^^^^^^^^^ @@ -71,40 +71,14 @@ error[E0425]: cannot find function `foo` in this scope LL | reuse foo { &self.0 } | ^^^ not found in this scope -error[E0425]: cannot find function `foo2` in trait `Trait` - --> $DIR/bad-resolve.rs:37:18 - | -LL | reuse Trait::foo2 { self.0 } - | ^^^^ not found in `Trait` - | -note: similarly named associated function `foo` defined here - --> $DIR/bad-resolve.rs:7:5 - | -LL | fn foo(&self, x: i32) -> i32 { x } - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -help: an associated function with a similar name exists - | -LL - reuse Trait::foo2 { self.0 } -LL + reuse Trait::foo { self.0 } - | - error[E0423]: cannot find function `self` in module `prefix` - --> $DIR/bad-resolve.rs:44:16 + --> $DIR/bad-resolve.rs:45:16 | LL | reuse prefix::{self, super, crate}; | ^^^^ not found in `prefix` | = note: a module named `prefix::self` exists in another namespace -error[E0186]: method `foo` has a `&self` declaration in the trait, but not in the impl - --> $DIR/bad-resolve.rs:34:11 - | -LL | fn foo(&self, x: i32) -> i32 { x } - | ---------------------------- `&self` used in trait -... -LL | reuse foo { &self.0 } - | ^^^ expected `&self` in impl - error[E0046]: not all trait items implemented, missing: `Type` --> $DIR/bad-resolve.rs:21:1 | @@ -114,8 +88,54 @@ LL | type Type; LL | impl Trait for S { | ^^^^^^^^^^^^^^^^ missing `Type` in implementation +warning: trait objects without an explicit `dyn` are deprecated + --> $DIR/bad-resolve.rs:36:11 + | +LL | reuse Trait::foo2 { self.0 } + | ^^^^^ + | + = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! + = note: for more information, see + = note: `#[warn(bare_trait_objects)]` (part of `#[warn(rust_2021_compatibility)]`) on by default +help: if this is a dyn-compatible trait, use `dyn` + | +LL | reuse ::foo2 { self.0 } + | ++++ + + +error[E0038]: the trait `Trait` is not dyn compatible + --> $DIR/bad-resolve.rs:36:11 + | +LL | reuse Trait::foo2 { self.0 } + | ^^^^^ `Trait` is not dyn compatible + | +note: for a trait to be dyn compatible it needs to allow building a vtable + for more information, visit + --> $DIR/bad-resolve.rs:4:11 + | +LL | trait Trait { + | ----- this trait is not dyn compatible... +LL | const C: u32 = 0; + | ^ ...because it contains associated const `C` +LL | type Type; +LL | fn bar() {} + | ^^^ ...because associated function `bar` has no `self` parameter + = help: consider moving `C` to another trait + = help: the following types implement `Trait`: + F + S + consider defining an enum where each variant holds one of these types, + implementing `Trait` for this new enum and using it instead +help: consider turning `bar` into a method by giving it a `&self` argument, so that it is accessible through the trait object's vtable + | +LL | fn bar(&self) {} + | +++++ +help: alternatively, consider constraining `bar` so it is explicitly marked as not applying to trait objects + | +LL | fn bar() where Self: Sized {} + | +++++++++++++++++ + error[E0433]: cannot find module or crate `unresolved_prefix` in this scope - --> $DIR/bad-resolve.rs:43:7 + --> $DIR/bad-resolve.rs:44:7 | LL | reuse unresolved_prefix::{a, b, c}; | ^^^^^^^^^^^^^^^^^ use of unresolved module or unlinked crate `unresolved_prefix` @@ -123,12 +143,12 @@ LL | reuse unresolved_prefix::{a, b, c}; = help: you might be missing a crate named `unresolved_prefix` error[E0433]: `crate` in paths can only be used in start position - --> $DIR/bad-resolve.rs:44:29 + --> $DIR/bad-resolve.rs:45:29 | LL | reuse prefix::{self, super, crate}; | ^^^^^ can only be used in path start position -error: aborting due to 14 previous errors +error: aborting due to 13 previous errors; 1 warning emitted -Some errors have detailed explanations: E0046, E0186, E0324, E0407, E0423, E0425, E0433, E0575, E0576. -For more information about an error, try `rustc --explain E0046`. +Some errors have detailed explanations: E0038, E0046, E0324, E0407, E0423, E0425, E0433, E0575, E0576. +For more information about an error, try `rustc --explain E0038`. diff --git a/tests/ui/delegation/explicit-paths.rs b/tests/ui/delegation/explicit-paths.rs index 2592d3d2698fc..e9530ec9d2314 100644 --- a/tests/ui/delegation/explicit-paths.rs +++ b/tests/ui/delegation/explicit-paths.rs @@ -25,7 +25,7 @@ mod fn_to_other { reuse ::foo2; reuse to_reuse::foo3; reuse S::foo4; - //~^ ERROR cannot find function `foo4` in `S` + //~^ ERROR: method `foo4` is private } mod inherent_impl_assoc_fn_to_other { @@ -36,7 +36,6 @@ mod inherent_impl_assoc_fn_to_other { reuse ::foo2; reuse to_reuse::foo3; reuse F::foo4 { &self.0 } - //~^ ERROR cannot find function `foo4` in `F` } } @@ -50,7 +49,6 @@ mod trait_impl_assoc_fn_to_other { //~^ ERROR method `foo3` is not a member of trait `Trait` reuse F::foo4 { &self.0 } //~^ ERROR method `foo4` is not a member of trait `Trait` - //~| ERROR cannot find function `foo4` in `F` } } @@ -63,7 +61,6 @@ mod trait_assoc_fn_to_other { reuse ::foo2; reuse to_reuse::foo3; reuse F::foo4 { &F } - //~^ ERROR cannot find function `foo4` in `F` } } diff --git a/tests/ui/delegation/explicit-paths.stderr b/tests/ui/delegation/explicit-paths.stderr index 30239f3648a53..f92bfd73266c3 100644 --- a/tests/ui/delegation/explicit-paths.stderr +++ b/tests/ui/delegation/explicit-paths.stderr @@ -1,5 +1,5 @@ error[E0407]: method `foo3` is not a member of trait `Trait` - --> $DIR/explicit-paths.rs:49:9 + --> $DIR/explicit-paths.rs:48:9 | LL | reuse to_reuse::foo3; | ^^^^^^^^^^^^^^^^----^ @@ -8,7 +8,7 @@ LL | reuse to_reuse::foo3; | not a member of trait `Trait` error[E0407]: method `foo4` is not a member of trait `Trait` - --> $DIR/explicit-paths.rs:51:9 + --> $DIR/explicit-paths.rs:50:9 | LL | reuse F::foo4 { &self.0 } | ^^^^^^^^^----^^^^^^^^^^^^ @@ -16,50 +16,8 @@ LL | reuse F::foo4 { &self.0 } | | help: there is an associated function with a similar name: `foo1` | not a member of trait `Trait` -error[E0425]: cannot find function `foo4` in `S` - --> $DIR/explicit-paths.rs:27:14 - | -LL | reuse S::foo4; - | ^^^^ not found in `S` - -error[E0425]: cannot find function `foo4` in `F` - --> $DIR/explicit-paths.rs:38:18 - | -LL | reuse F::foo4 { &self.0 } - | ^^^^ not found in `F` - | -note: function `fn_to_other::foo4` exists but is inaccessible - --> $DIR/explicit-paths.rs:27:5 - | -LL | reuse S::foo4; - | ^^^^^^^^^^^^^^ not accessible - -error[E0425]: cannot find function `foo4` in `F` - --> $DIR/explicit-paths.rs:51:18 - | -LL | reuse F::foo4 { &self.0 } - | ^^^^ not found in `F` - | -note: function `fn_to_other::foo4` exists but is inaccessible - --> $DIR/explicit-paths.rs:27:5 - | -LL | reuse S::foo4; - | ^^^^^^^^^^^^^^ not accessible - -error[E0425]: cannot find function `foo4` in `F` - --> $DIR/explicit-paths.rs:65:18 - | -LL | reuse F::foo4 { &F } - | ^^^^ not found in `F` - | -note: function `fn_to_other::foo4` exists but is inaccessible - --> $DIR/explicit-paths.rs:27:5 - | -LL | reuse S::foo4; - | ^^^^^^^^^^^^^^ not accessible - error[E0119]: conflicting implementations of trait `Trait` for type `S` - --> $DIR/explicit-paths.rs:74:5 + --> $DIR/explicit-paths.rs:71:5 | LL | impl Trait for S { | ---------------- first implementation here @@ -67,8 +25,17 @@ LL | impl Trait for S { LL | impl Trait for S { | ^^^^^^^^^^^^^^^^ conflicting implementation for `S` +error[E0624]: method `foo4` is private + --> $DIR/explicit-paths.rs:27:14 + | +LL | reuse S::foo4; + | ^^^^ private method +... +LL | reuse F::foo4 { &self.0 } + | ---- private method defined here + error[E0308]: mismatched types - --> $DIR/explicit-paths.rs:61:36 + --> $DIR/explicit-paths.rs:59:36 | LL | trait Trait2 : Trait { | -------------------- found this type parameter @@ -86,13 +53,13 @@ LL | fn foo1(&self, x: i32) -> i32 { x } | ^^^^ ----- error[E0277]: the trait bound `S2: Trait` is not satisfied - --> $DIR/explicit-paths.rs:76:16 + --> $DIR/explicit-paths.rs:73:16 | LL | reuse ::foo1; | ^^ unsatisfied trait bound | help: the trait `Trait` is not implemented for `S2` - --> $DIR/explicit-paths.rs:73:5 + --> $DIR/explicit-paths.rs:70:5 | LL | struct S2; | ^^^^^^^^^ @@ -109,7 +76,7 @@ LL | impl Trait for S { | ^^^^^^^^^^^^^^^^ `S` error[E0308]: mismatched types - --> $DIR/explicit-paths.rs:76:30 + --> $DIR/explicit-paths.rs:73:30 | LL | reuse ::foo1; | ^^^^ @@ -125,7 +92,7 @@ note: method defined here LL | fn foo1(&self, x: i32) -> i32 { x } | ^^^^ ----- -error: aborting due to 10 previous errors +error: aborting due to 7 previous errors -Some errors have detailed explanations: E0119, E0277, E0308, E0407, E0425. +Some errors have detailed explanations: E0119, E0277, E0308, E0407, E0624. For more information about an error, try `rustc --explain E0119`. diff --git a/tests/ui/delegation/glob-non-fn.rs b/tests/ui/delegation/glob-non-fn.rs index 939c5db6a0e8f..72111fc81d7f0 100644 --- a/tests/ui/delegation/glob-non-fn.rs +++ b/tests/ui/delegation/glob-non-fn.rs @@ -31,7 +31,9 @@ impl Trait for Bad { //~ ERROR not all trait items implemented, missing: `CONST` //~| ERROR item `Type` is an associated method, which doesn't match its trait `Trait` //~| ERROR duplicate definitions with name `method` //~| ERROR expected function, found associated constant `Trait::CONST` - //~| ERROR cannot find function `Type` in trait `Trait` + //~| ERROR the trait `Trait` is not dyn compatible + //~| WARN trait objects without an explicit `dyn` are deprecated [bare_trait_objects] + //~| WARN this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! } fn main() {} diff --git a/tests/ui/delegation/glob-non-fn.stderr b/tests/ui/delegation/glob-non-fn.stderr index 6f7010d43d8ae..e1a4ffce5ac17 100644 --- a/tests/ui/delegation/glob-non-fn.stderr +++ b/tests/ui/delegation/glob-non-fn.stderr @@ -34,14 +34,6 @@ error[E0423]: expected function, found associated constant `Trait::CONST` LL | reuse Trait::* { &self.0 } | ^^^^^ not a function -error[E0423]: cannot find function `Type` in trait `Trait` - --> $DIR/glob-non-fn.rs:29:18 - | -LL | reuse Trait::* { &self.0 } - | ^ not found in `Trait` - | - = note: an associated type named `Trait::Type` exists in another namespace - error[E0046]: not all trait items implemented, missing: `CONST`, `Type`, `method` --> $DIR/glob-non-fn.rs:28:1 | @@ -56,7 +48,44 @@ LL | type method; LL | impl Trait for Bad { | ^^^^^^^^^^^^^^^^^^ missing `CONST`, `Type`, `method` in implementation -error: aborting due to 6 previous errors +warning: trait objects without an explicit `dyn` are deprecated + --> $DIR/glob-non-fn.rs:29:11 + | +LL | reuse Trait::* { &self.0 } + | ^^^^^ + | + = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! + = note: for more information, see + = note: `#[warn(bare_trait_objects)]` (part of `#[warn(rust_2021_compatibility)]`) on by default +help: if this is a dyn-compatible trait, use `dyn` + | +LL | reuse ::* { &self.0 } + | ++++ + + +error[E0038]: the trait `Trait` is not dyn compatible + --> $DIR/glob-non-fn.rs:29:11 + | +LL | reuse Trait::* { &self.0 } + | ^^^^^ `Trait` is not dyn compatible + | +note: for a trait to be dyn compatible it needs to allow building a vtable + for more information, visit + --> $DIR/glob-non-fn.rs:5:11 + | +LL | trait Trait { + | ----- this trait is not dyn compatible... +LL | fn method(&self); +LL | const CONST: u8; + | ^^^^^ ...because it contains associated const `CONST` + = help: consider moving `CONST` to another trait + = help: the following types implement `Trait`: + u8 + Good + Bad + consider defining an enum where each variant holds one of these types, + implementing `Trait` for this new enum and using it instead + +error: aborting due to 6 previous errors; 1 warning emitted -Some errors have detailed explanations: E0046, E0201, E0324, E0423. -For more information about an error, try `rustc --explain E0046`. +Some errors have detailed explanations: E0038, E0046, E0201, E0324, E0423. +For more information about an error, try `rustc --explain E0038`. diff --git a/tests/ui/delegation/impl-reuse-non-reuse-items.rs b/tests/ui/delegation/impl-reuse-non-reuse-items.rs index 23c22a61cbb0a..517e2b26a36f9 100644 --- a/tests/ui/delegation/impl-reuse-non-reuse-items.rs +++ b/tests/ui/delegation/impl-reuse-non-reuse-items.rs @@ -23,9 +23,11 @@ mod non_delegatable_items { //~^ ERROR item `CONST` is an associated method, which doesn't match its trait `Trait` //~| ERROR item `Type` is an associated method, which doesn't match its trait `Trait` //~| ERROR duplicate definitions with name `method` - //~| ERROR expected function, found associated constant `Trait::CONST` - //~| ERROR cannot find function `Type` in trait `Trait` //~| ERROR not all trait items implemented, missing: `CONST`, `Type`, `method` + //~| ERROR expected function, found associated constant `Trait::CONST` + //~| WARN trait objects without an explicit `dyn` are deprecated [bare_trait_objects] + //~| WARN this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! + //~| ERROR the trait `non_delegatable_items::Trait` is not dyn compatible } fn main() {} diff --git a/tests/ui/delegation/impl-reuse-non-reuse-items.stderr b/tests/ui/delegation/impl-reuse-non-reuse-items.stderr index 2bd488e9fb3d8..2a33982cc6730 100644 --- a/tests/ui/delegation/impl-reuse-non-reuse-items.stderr +++ b/tests/ui/delegation/impl-reuse-non-reuse-items.stderr @@ -34,14 +34,6 @@ error[E0423]: expected function, found associated constant `Trait::CONST` LL | reuse impl Trait for S { &self.0 } | ^^^^^ not a function -error[E0423]: cannot find function `Type` in trait `Trait` - --> $DIR/impl-reuse-non-reuse-items.rs:22:5 - | -LL | reuse impl Trait for S { &self.0 } - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not found in `Trait` - | - = note: an associated type named `Trait::Type` exists in another namespace - error[E0046]: not all trait items implemented, missing: `CONST`, `Type`, `method` --> $DIR/impl-reuse-non-reuse-items.rs:22:5 | @@ -56,7 +48,43 @@ LL | type method; LL | reuse impl Trait for S { &self.0 } | ^^^^^^^^^^^^^^^^^^^^^^ missing `CONST`, `Type`, `method` in implementation -error: aborting due to 6 previous errors +warning: trait objects without an explicit `dyn` are deprecated + --> $DIR/impl-reuse-non-reuse-items.rs:22:16 + | +LL | reuse impl Trait for S { &self.0 } + | ^^^^^ + | + = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! + = note: for more information, see + = note: `#[warn(bare_trait_objects)]` (part of `#[warn(rust_2021_compatibility)]`) on by default +help: if this is a dyn-compatible trait, use `dyn` + | +LL | reuse impl for S { &self.0 } + | ++++ + + +error[E0038]: the trait `non_delegatable_items::Trait` is not dyn compatible + --> $DIR/impl-reuse-non-reuse-items.rs:22:16 + | +LL | reuse impl Trait for S { &self.0 } + | ^^^^^ `non_delegatable_items::Trait` is not dyn compatible + | +note: for a trait to be dyn compatible it needs to allow building a vtable + for more information, visit + --> $DIR/impl-reuse-non-reuse-items.rs:6:15 + | +LL | trait Trait { + | ----- this trait is not dyn compatible... +LL | fn method(&self); +LL | const CONST: u8; + | ^^^^^ ...because it contains associated const `CONST` + = help: consider moving `CONST` to another trait + = help: the following types implement `non_delegatable_items::Trait`: + non_delegatable_items::F + non_delegatable_items::S + consider defining an enum where each variant holds one of these types, + implementing `non_delegatable_items::Trait` for this new enum and using it instead + +error: aborting due to 6 previous errors; 1 warning emitted -Some errors have detailed explanations: E0046, E0201, E0324, E0423. -For more information about an error, try `rustc --explain E0046`. +Some errors have detailed explanations: E0038, E0046, E0201, E0324, E0423. +For more information about an error, try `rustc --explain E0038`. diff --git a/tests/ui/delegation/inherent-impl-non-local-crate.rs b/tests/ui/delegation/inherent-impl-non-local-crate.rs new file mode 100644 index 0000000000000..27b8d387a7e63 --- /dev/null +++ b/tests/ui/delegation/inherent-impl-non-local-crate.rs @@ -0,0 +1,23 @@ +//@ aux-crate:inherent_impl=inherent-impl.rs + +#![feature(fn_delegation)] + +reuse inherent_impl::S::foo; + +reuse inherent_impl::S::not_existing; +//~^ ERROR: no associated function or constant named `not_existing` found for struct `S` in the current scope +reuse inherent_impl::S::TYPE; +//~^ ERROR: no associated function or constant named `TYPE` found for struct `S` in the current scope +reuse inherent_impl::S::CONST; +//~^ ERROR: expected function, found `usize` [E0618] + +reuse inherent_impl::S::bar; +//~^ ERROR: no associated function or constant named `bar` found for struct `S` in the current scope + +reuse ::bar as trait_bar; + +reuse inherent_impl::X::foo as x_foo; +//~^ ERROR: ambiguous delegation to inherent impl function +//~| ERROR: multiple applicable items in scope + +fn main() {} diff --git a/tests/ui/delegation/inherent-impl-non-local-crate.stderr b/tests/ui/delegation/inherent-impl-non-local-crate.stderr new file mode 100644 index 0000000000000..e763a132baa08 --- /dev/null +++ b/tests/ui/delegation/inherent-impl-non-local-crate.stderr @@ -0,0 +1,49 @@ +error: ambiguous delegation to inherent impl function + --> $DIR/inherent-impl-non-local-crate.rs:19:25 + | +LL | reuse inherent_impl::X::foo as x_foo; + | ^^^ + +error[E0599]: no associated function or constant named `not_existing` found for struct `S` in the current scope + --> $DIR/inherent-impl-non-local-crate.rs:7:25 + | +LL | reuse inherent_impl::S::not_existing; + | ^^^^^^^^^^^^ associated function or constant not found in `S` + +error[E0599]: no associated function or constant named `TYPE` found for struct `S` in the current scope + --> $DIR/inherent-impl-non-local-crate.rs:9:25 + | +LL | reuse inherent_impl::S::TYPE; + | ^^^^ associated function or constant not found in `S` + +error[E0618]: expected function, found `usize` + --> $DIR/inherent-impl-non-local-crate.rs:11:25 + | +LL | reuse inherent_impl::S::CONST; + | ^^^^^ call expression requires function + +error[E0599]: no associated function or constant named `bar` found for struct `S` in the current scope + --> $DIR/inherent-impl-non-local-crate.rs:14:25 + | +LL | reuse inherent_impl::S::bar; + | ^^^ associated function or constant not found in `S` + | + = help: items from traits can only be used if the trait is in scope +help: trait `Trait` which provides `bar` is implemented but not in scope; perhaps you want to import it + | +LL + use inherent_impl::Trait; + | + +error[E0034]: multiple applicable items in scope + --> $DIR/inherent-impl-non-local-crate.rs:19:25 + | +LL | reuse inherent_impl::X::foo as x_foo; + | ^^^ multiple `foo` found + | + = note: candidate #1 is defined in an impl for the type `X` + = note: candidate #2 is defined in an impl for the type `X` + +error: aborting due to 6 previous errors + +Some errors have detailed explanations: E0034, E0599, E0618. +For more information about an error, try `rustc --explain E0034`. diff --git a/tests/ui/delegation/inherent-impls-ambig.rs b/tests/ui/delegation/inherent-impls-ambig.rs index 1c419034d2446..1b7c9a6fcef0f 100644 --- a/tests/ui/delegation/inherent-impls-ambig.rs +++ b/tests/ui/delegation/inherent-impls-ambig.rs @@ -14,16 +14,19 @@ mod test_1 { } reuse X::foo; - //~^ ERROR: cannot find function `foo` in `X` + //~^ ERROR: ambiguous delegation to inherent impl function + //~| ERROR: multiple applicable items in scope [E0034] reuse X::foo_self; - //~^ ERROR: cannot find function `foo_self` in `X` + //~^ ERROR: ambiguous delegation to inherent impl function + //~| ERROR: multiple applicable items in scope [E0034] reuse X::<()>::foo as foo1; - //~^ ERROR: cannot find function `foo` in `X` + //~^ ERROR: ambiguous delegation to inherent impl function reuse X::::foo_self as foo_self1; - //~^ ERROR: cannot find function `foo_self` in `X` + //~^ ERROR: ambiguous delegation to inherent impl function + //~| ERROR: this function takes 1 argument but 0 arguments were supplied } mod test_2 { @@ -47,16 +50,19 @@ mod test_2 { impl Marker2 for M2 {} reuse X::foo; - //~^ ERROR: cannot find function `foo` in `X` + //~^ ERROR: ambiguous delegation to inherent impl function + //~| ERROR: multiple applicable items in scope [E0034] reuse X::foo_self; - //~^ ERROR: cannot find function `foo_self` in `X` + //~^ ERROR: ambiguous delegation to inherent impl function + //~| ERROR: multiple applicable items in scope [E0034] reuse X::::foo as foo1; - //~^ ERROR: cannot find function `foo` in `X` + //~^ ERROR: ambiguous delegation to inherent impl function reuse X::::foo_self as foo_self1; - //~^ ERROR: cannot find function `foo_self` in `X` + //~^ ERROR: ambiguous delegation to inherent impl function + //~| ERROR: no associated function or constant named `foo_self` found for struct `test_2::X` in the current scope } fn main() {} diff --git a/tests/ui/delegation/inherent-impls-ambig.stderr b/tests/ui/delegation/inherent-impls-ambig.stderr index 0be82bcdd6f74..a15fc0f2af268 100644 --- a/tests/ui/delegation/inherent-impls-ambig.stderr +++ b/tests/ui/delegation/inherent-impls-ambig.stderr @@ -1,99 +1,145 @@ -error[E0425]: cannot find function `foo` in `X` +error: ambiguous delegation to inherent impl function --> $DIR/inherent-impls-ambig.rs:16:14 | LL | reuse X::foo; - | ^^^ not found in `X` - | -note: function `test_2::foo` exists but is inaccessible - --> $DIR/inherent-impls-ambig.rs:49:5 - | -LL | reuse X::foo; - | ^^^^^^^^^^^^^ not accessible + | ^^^ -error[E0425]: cannot find function `foo_self` in `X` - --> $DIR/inherent-impls-ambig.rs:19:14 - | -LL | reuse X::foo_self; - | ^^^^^^^^ not found in `X` - | -note: function `test_2::foo_self` exists but is inaccessible - --> $DIR/inherent-impls-ambig.rs:52:5 +error: ambiguous delegation to inherent impl function + --> $DIR/inherent-impls-ambig.rs:20:14 | LL | reuse X::foo_self; - | ^^^^^^^^^^^^^^^^^^ not accessible + | ^^^^^^^^ -error[E0425]: cannot find function `foo` in `X` - --> $DIR/inherent-impls-ambig.rs:22:20 +error: ambiguous delegation to inherent impl function + --> $DIR/inherent-impls-ambig.rs:24:20 | LL | reuse X::<()>::foo as foo1; - | ^^^ not found in `X` + | ^^^ + +error: ambiguous delegation to inherent impl function + --> $DIR/inherent-impls-ambig.rs:27:23 | -note: function `test_2::foo` exists but is inaccessible - --> $DIR/inherent-impls-ambig.rs:49:5 +LL | reuse X::::foo_self as foo_self1; + | ^^^^^^^^ + +error: ambiguous delegation to inherent impl function + --> $DIR/inherent-impls-ambig.rs:52:14 | LL | reuse X::foo; - | ^^^^^^^^^^^^^ not accessible + | ^^^ -error[E0425]: cannot find function `foo_self` in `X` - --> $DIR/inherent-impls-ambig.rs:25:23 +error: ambiguous delegation to inherent impl function + --> $DIR/inherent-impls-ambig.rs:56:14 | -LL | reuse X::::foo_self as foo_self1; - | ^^^^^^^^ not found in `X` +LL | reuse X::foo_self; + | ^^^^^^^^ + +error: ambiguous delegation to inherent impl function + --> $DIR/inherent-impls-ambig.rs:60:27 | -note: function `test_2::foo_self` exists but is inaccessible - --> $DIR/inherent-impls-ambig.rs:52:5 +LL | reuse X::::foo as foo1; + | ^^^ + +error: ambiguous delegation to inherent impl function + --> $DIR/inherent-impls-ambig.rs:63:28 | -LL | reuse X::foo_self; - | ^^^^^^^^^^^^^^^^^^ not accessible +LL | reuse X::::foo_self as foo_self1; + | ^^^^^^^^ -error[E0425]: cannot find function `foo` in `X` - --> $DIR/inherent-impls-ambig.rs:49:14 +error[E0034]: multiple applicable items in scope + --> $DIR/inherent-impls-ambig.rs:16:14 | LL | reuse X::foo; - | ^^^ not found in `X` + | ^^^ multiple `foo` found | -note: function `test_1::foo` exists but is inaccessible - --> $DIR/inherent-impls-ambig.rs:16:5 +note: candidate #1 is defined in an impl for the type `test_1::X<()>` + --> $DIR/inherent-impls-ambig.rs:7:9 | -LL | reuse X::foo; - | ^^^^^^^^^^^^^ not accessible +LL | fn foo() {} + | ^^^^^^^^ +note: candidate #2 is defined in an impl for the type `test_1::X` + --> $DIR/inherent-impls-ambig.rs:12:9 + | +LL | fn foo() {} + | ^^^^^^^^ -error[E0425]: cannot find function `foo_self` in `X` - --> $DIR/inherent-impls-ambig.rs:52:14 +error[E0034]: multiple applicable items in scope + --> $DIR/inherent-impls-ambig.rs:20:14 | LL | reuse X::foo_self; - | ^^^^^^^^ not found in `X` + | ^^^^^^^^ multiple `foo_self` found | -note: function `test_1::foo_self` exists but is inaccessible - --> $DIR/inherent-impls-ambig.rs:19:5 +note: candidate #1 is defined in an impl for the type `test_1::X<()>` + --> $DIR/inherent-impls-ambig.rs:8:9 | -LL | reuse X::foo_self; - | ^^^^^^^^^^^^^^^^^^ not accessible +LL | fn foo_self(self) {} + | ^^^^^^^^^^^^^^^^^ +note: candidate #2 is defined in an impl for the type `test_1::X` + --> $DIR/inherent-impls-ambig.rs:13:9 + | +LL | fn foo_self(self) {} + | ^^^^^^^^^^^^^^^^^ -error[E0425]: cannot find function `foo` in `X` - --> $DIR/inherent-impls-ambig.rs:55:27 +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-ambig.rs:27:23 | -LL | reuse X::::foo as foo1; - | ^^^ not found in `X` +LL | reuse X::::foo_self as foo_self1; + | ^^^^^^^^ argument #1 of type `test_1::X` is missing | -note: function `test_1::foo` exists but is inaccessible - --> $DIR/inherent-impls-ambig.rs:16:5 +note: method defined here + --> $DIR/inherent-impls-ambig.rs:13:12 | -LL | reuse X::foo; - | ^^^^^^^^^^^^^ not accessible +LL | fn foo_self(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse X::::foo_self(/* X */) as foo_self1; + | ++++++++++++++++ -error[E0425]: cannot find function `foo_self` in `X` - --> $DIR/inherent-impls-ambig.rs:58:28 +error[E0034]: multiple applicable items in scope + --> $DIR/inherent-impls-ambig.rs:52:14 | -LL | reuse X::::foo_self as foo_self1; - | ^^^^^^^^ not found in `X` +LL | reuse X::foo; + | ^^^ multiple `foo` found | -note: function `test_1::foo_self` exists but is inaccessible - --> $DIR/inherent-impls-ambig.rs:19:5 +note: candidate #1 is defined in an impl for the type `test_2::X` + --> $DIR/inherent-impls-ambig.rs:43:9 + | +LL | fn foo() {} + | ^^^^^^^^ +note: candidate #2 is defined in an impl for the type `test_2::X` + --> $DIR/inherent-impls-ambig.rs:38:9 + | +LL | fn foo() {} + | ^^^^^^^^ + +error[E0034]: multiple applicable items in scope + --> $DIR/inherent-impls-ambig.rs:56:14 | LL | reuse X::foo_self; - | ^^^^^^^^^^^^^^^^^^ not accessible + | ^^^^^^^^ multiple `foo_self` found + | +note: candidate #1 is defined in an impl for the type `test_2::X` + --> $DIR/inherent-impls-ambig.rs:44:9 + | +LL | fn foo_self(self) {} + | ^^^^^^^^^^^^^^^^^ +note: candidate #2 is defined in an impl for the type `test_2::X` + --> $DIR/inherent-impls-ambig.rs:39:9 + | +LL | fn foo_self(self) {} + | ^^^^^^^^^^^^^^^^^ + +error[E0599]: no associated function or constant named `foo_self` found for struct `test_2::X` in the current scope + --> $DIR/inherent-impls-ambig.rs:63:28 + | +LL | struct X(T, U); + | -------------- associated function or constant `foo_self` not found for this struct +... +LL | reuse X::::foo_self as foo_self1; + | ^^^^^^^^ associated function or constant not found in `test_2::X` -error: aborting due to 8 previous errors +error: aborting due to 14 previous errors -For more information about this error, try `rustc --explain E0425`. +Some errors have detailed explanations: E0034, E0061, E0599. +For more information about an error, try `rustc --explain E0034`. diff --git a/tests/ui/delegation/inherent-impls-enums.rs b/tests/ui/delegation/inherent-impls-enums.rs index 301cbe32b6f88..320a7d6fea6db 100644 --- a/tests/ui/delegation/inherent-impls-enums.rs +++ b/tests/ui/delegation/inherent-impls-enums.rs @@ -10,81 +10,87 @@ impl<'a, 'b, 'c, A: 'a, const C: usize> S<'a, A, C> { fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} } +reuse S::foo_static; reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; -//~^ ERROR: cannot find function `foo_static` in enum `S` +reuse S::foo_static::<'static, (), true> as foo_static_2; reuse S::<'static, (), 1>::foo_static as foo_static_3; -//~^ ERROR: cannot find function `foo_static` in enum `S` -reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; -//~^ ERROR: cannot find function `foo_static` in enum `S` +reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; +reuse S::foo_self; reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1; -//~^ ERROR: cannot find function `foo_self` in enum `S` +reuse S::foo_self::<'static, (), true> as foo_self_2; reuse S::<'static, (), 1>::foo_self as foo_self_3; -//~^ ERROR: cannot find function `foo_self` in enum `S` -reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; -//~^ ERROR: cannot find function `foo_self` in enum `S` +reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; trait Trait<'a, AA, BB> where Self: Sized, { + reuse S::foo_static; reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; - //~^ ERROR: cannot find function `foo_static` in enum `S` + reuse S::foo_static::<'static, (), true> as foo_static_2; reuse S::<'static, (), 1>::foo_static as foo_static_3; - //~^ ERROR: cannot find function `foo_static` in enum `S` - reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; - //~^ ERROR: cannot find function `foo_static` in enum `S` + reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; fn get_s(self) -> S<'static, (), 1> { panic!(); } + reuse S::foo_self; + //~^ ERROR: mismatched types [E0308] reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - //~^ ERROR: cannot find function `foo_self` in enum `S` + reuse S::foo_self::<'static, (), true> as foo_self_2; + //~^ ERROR: mismatched types [E0308] reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } - //~^ ERROR: cannot find function `foo_self` in enum `S` - reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; - //~^ ERROR: cannot find function `foo_self` in enum `S` + reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; + //~^ ERROR: mismatched types [E0308] } struct X; impl<'a, A, B> Trait<'a, A, B> for X { + reuse S::foo_static; + //~^ ERROR: associated function takes at most 2 generic arguments but 4 generic arguments were supplied [E0107] + //~| ERROR: associated function takes 1 lifetime argument but 2 lifetime arguments were supplied reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; - //~^ ERROR: cannot find function `foo_static` in enum `S` + reuse S::foo_static::<'static, (), true> as foo_static_2; + //~^ ERROR: type annotations needed [E0284] + //~| ERROR: type annotations needed [E0284] reuse S::<'static, (), 1>::foo_static as foo_static_3; - //~^ ERROR: cannot find function `foo_static` in enum `S` - reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; - //~^ ERROR: cannot find function `foo_static` in enum `S` + reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; + //~^ ERROR: type annotations needed [E0284] + reuse S::foo_self; + //~^ ERROR: mismatched types [E0308] + //~| ERROR: method takes at most 2 generic arguments but 4 generic arguments were supplied + //~| ERROR: method takes 1 lifetime argument but 2 lifetime arguments were supplied reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - //~^ ERROR: cannot find function `foo_self` in enum `S` - //~| ERROR: delegation's target expression is specified for function with no params + reuse S::foo_self::<'static, (), true> as foo_self_2; + //~^ ERROR: mismatched types [E0308] reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } - //~^ ERROR: cannot find function `foo_self` in enum `S` - //~| ERROR: delegation's target expression is specified for function with no params - reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; - //~^ ERROR: cannot find function `foo_self` in enum `S` + reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; + //~^ ERROR: mismatched types [E0308] } impl X { + reuse S::foo_static; reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; - //~^ ERROR: cannot find function `foo_static` in enum `S` + reuse S::foo_static::<'static, (), true> as foo_static_2; reuse S::<'static, (), 1>::foo_static as foo_static_3; - //~^ ERROR: cannot find function `foo_static` in enum `S` - reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; - //~^ ERROR: cannot find function `foo_static` in enum `S` + reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; fn get_s(self) -> S<'static, (), 1> { panic!(); } + reuse S::foo_self; + //~^ ERROR: mismatched types [E0308] reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - //~^ ERROR: cannot find function `foo_self` in enum `S` + reuse S::foo_self::<'static, (), true> as foo_self_2; + //~^ ERROR: mismatched types [E0308] reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } - //~^ ERROR: cannot find function `foo_self` in enum `S` - reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; - //~^ ERROR: cannot find function `foo_self` in enum `S` + reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; + //~^ ERROR: mismatched types [E0308] } fn main() {} diff --git a/tests/ui/delegation/inherent-impls-enums.stderr b/tests/ui/delegation/inherent-impls-enums.stderr index 0016488386017..ac783ac70ac82 100644 --- a/tests/ui/delegation/inherent-impls-enums.stderr +++ b/tests/ui/delegation/inherent-impls-enums.stderr @@ -1,159 +1,267 @@ -error[E0425]: cannot find function `foo_static` in enum `S` - --> $DIR/inherent-impls-enums.rs:13:28 +error[E0308]: mismatched types + --> $DIR/inherent-impls-enums.rs:39:14 | -LL | reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in enum `S` - --> $DIR/inherent-impls-enums.rs:15:28 +LL | trait Trait<'a, AA, BB> + | ----------------------- found this type parameter +... +LL | reuse S::foo_self; + | ^^^^^^^^ + | | + | expected `S<'_, A, C>`, found type parameter `Self` + | arguments to this function are incorrect | -LL | reuse S::<'static, (), 1>::foo_static as foo_static_3; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in enum `S` - --> $DIR/inherent-impls-enums.rs:17:28 + = note: expected enum `S<'_, A, C>` + found type parameter `Self` +note: method defined here + --> $DIR/inherent-impls-enums.rs:10:8 | -LL | reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; - | ^^^^^^^^^^ not found in `S` +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- -error[E0425]: cannot find function `foo_self` in enum `S` - --> $DIR/inherent-impls-enums.rs:20:28 +error[E0308]: mismatched types + --> $DIR/inherent-impls-enums.rs:42:14 | -LL | reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1; - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in enum `S` - --> $DIR/inherent-impls-enums.rs:22:28 +LL | trait Trait<'a, AA, BB> + | ----------------------- found this type parameter +... +LL | reuse S::foo_self::<'static, (), true> as foo_self_2; + | ^^^^^^^^ + | | + | expected `S<'_, A, C>`, found type parameter `Self` + | arguments to this function are incorrect | -LL | reuse S::<'static, (), 1>::foo_self as foo_self_3; - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in enum `S` - --> $DIR/inherent-impls-enums.rs:24:28 + = note: expected enum `S<'_, A, C>` + found type parameter `Self` +note: method defined here + --> $DIR/inherent-impls-enums.rs:10:8 | -LL | reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ not found in `S` +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- -error[E0425]: cannot find function `foo_static` in enum `S` - --> $DIR/inherent-impls-enums.rs:31:32 +error[E0308]: mismatched types + --> $DIR/inherent-impls-enums.rs:45:26 | -LL | reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in enum `S` - --> $DIR/inherent-impls-enums.rs:33:32 +LL | trait Trait<'a, AA, BB> + | ----------------------- found this type parameter +... +LL | reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; + | ^^^^^^^^ + | | + | expected `S<'_, A, 1>`, found type parameter `Self` + | arguments to this function are incorrect | -LL | reuse S::<'static, (), 1>::foo_static as foo_static_3; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in enum `S` - --> $DIR/inherent-impls-enums.rs:35:32 + = note: expected enum `S<'_, A, 1>` + found type parameter `Self` +note: method defined here + --> $DIR/inherent-impls-enums.rs:10:8 | -LL | reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; - | ^^^^^^^^^^ not found in `S` +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- -error[E0425]: cannot find function `foo_self` in enum `S` - --> $DIR/inherent-impls-enums.rs:42:32 +error[E0107]: associated function takes 1 lifetime argument but 2 lifetime arguments were supplied + --> $DIR/inherent-impls-enums.rs:52:14 | -LL | reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in enum `S` - --> $DIR/inherent-impls-enums.rs:44:32 +LL | reuse S::foo_static; + | ^^^^^^^^^^ + | | + | expected 1 lifetime argument + | help: remove the lifetime argument | -LL | reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in enum `S` - --> $DIR/inherent-impls-enums.rs:46:32 +note: associated function defined here, with 1 lifetime parameter: `'d` + --> $DIR/inherent-impls-enums.rs:9:8 | -LL | reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ not found in `S` +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ^^^^^^^^^^ -- -error[E0425]: cannot find function `foo_static` in enum `S` - --> $DIR/inherent-impls-enums.rs:53:32 +error[E0107]: associated function takes at most 2 generic arguments but 4 generic arguments were supplied + --> $DIR/inherent-impls-enums.rs:52:14 | -LL | reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in enum `S` - --> $DIR/inherent-impls-enums.rs:55:32 +LL | reuse S::foo_static; + | ^^^^^^^^^^ + | | + | expected at most 2 generic arguments + | help: remove the unnecessary generic arguments | -LL | reuse S::<'static, (), 1>::foo_static as foo_static_3; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in enum `S` - --> $DIR/inherent-impls-enums.rs:57:32 +note: associated function defined here, with at most 2 generic parameters: `T`, `B` + --> $DIR/inherent-impls-enums.rs:9:8 | -LL | reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; - | ^^^^^^^^^^ not found in `S` +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ^^^^^^^^^^ - ------------- -error[E0425]: cannot find function `foo_self` in enum `S` - --> $DIR/inherent-impls-enums.rs:60:32 +error[E0284]: type annotations needed + --> $DIR/inherent-impls-enums.rs:56:14 | -LL | reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in enum `S` - --> $DIR/inherent-impls-enums.rs:63:32 +LL | reuse S::foo_static::<'static, (), true> as foo_static_2; + | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `S` + | +note: required by a const generic parameter in `S` + --> $DIR/inherent-impls-enums.rs:3:23 + | +LL | enum S<'a: 'a, A: 'a, const C: usize> { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` +help: consider specifying the generic arguments + | +LL - reuse S::foo_static::<'static, (), true> as foo_static_2; +LL + reuse S:: as foo_static_2; | -LL | reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } - | ^^^^^^^^ not found in `S` -error[E0425]: cannot find function `foo_self` in enum `S` - --> $DIR/inherent-impls-enums.rs:66:32 +error[E0284]: type annotations needed + --> $DIR/inherent-impls-enums.rs:60:26 | -LL | reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ not found in `S` +LL | reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; + | ^^^^^^^^^^ cannot infer the value of const parameter `B` declared on the associated function `foo_static` + | +note: required by a const generic parameter in `S::<'a, A, C>::foo_static` + --> $DIR/inherent-impls-enums.rs:9:34 + | +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ^^^^^^^^^^^^^ required by this const generic parameter in `S::<'a, A, C>::foo_static` -error[E0425]: cannot find function `foo_static` in enum `S` - --> $DIR/inherent-impls-enums.rs:71:32 +error[E0107]: method takes 1 lifetime argument but 2 lifetime arguments were supplied + --> $DIR/inherent-impls-enums.rs:63:14 + | +LL | reuse S::foo_self; + | ^^^^^^^^ + | | + | expected 1 lifetime argument + | help: remove the lifetime argument + | +note: method defined here, with 1 lifetime parameter: `'d` + --> $DIR/inherent-impls-enums.rs:10:8 | -LL | reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; - | ^^^^^^^^^^ not found in `S` +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ -- -error[E0425]: cannot find function `foo_static` in enum `S` - --> $DIR/inherent-impls-enums.rs:73:32 +error[E0107]: method takes at most 2 generic arguments but 4 generic arguments were supplied + --> $DIR/inherent-impls-enums.rs:63:14 | -LL | reuse S::<'static, (), 1>::foo_static as foo_static_3; - | ^^^^^^^^^^ not found in `S` +LL | reuse S::foo_self; + | ^^^^^^^^ + | | + | expected at most 2 generic arguments + | help: remove the unnecessary generic arguments + | +note: method defined here, with at most 2 generic parameters: `T`, `B` + --> $DIR/inherent-impls-enums.rs:10:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ - ------------- -error[E0425]: cannot find function `foo_static` in enum `S` - --> $DIR/inherent-impls-enums.rs:75:32 +error[E0308]: mismatched types + --> $DIR/inherent-impls-enums.rs:63:14 + | +LL | reuse S::foo_self; + | ^^^^^^^^ + | | + | expected `S<'_, _, _>`, found `X` + | arguments to this function are incorrect + | + = note: expected enum `S<'_, _, _>` + found struct `X` +note: method defined here + --> $DIR/inherent-impls-enums.rs:10:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: try wrapping the expression in `S::A` | -LL | reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; - | ^^^^^^^^^^ not found in `S` +LL | reuse S::S::A(foo_self); + | +++++ + -error[E0425]: cannot find function `foo_self` in enum `S` - --> $DIR/inherent-impls-enums.rs:82:32 +error[E0308]: mismatched types + --> $DIR/inherent-impls-enums.rs:68:14 | -LL | reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - | ^^^^^^^^ not found in `S` +LL | reuse S::foo_self::<'static, (), true> as foo_self_2; + | ^^^^^^^^ + | | + | expected `S<'_, _, _>`, found `X` + | arguments to this function are incorrect + | + = note: expected enum `S<'_, _, _>` + found struct `X` +note: method defined here + --> $DIR/inherent-impls-enums.rs:10:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: try wrapping the expression in `S::A` + | +LL | reuse S::S::A(foo_self)::<'static, (), true> as foo_self_2; + | +++++ + -error[E0425]: cannot find function `foo_self` in enum `S` - --> $DIR/inherent-impls-enums.rs:84:32 +error[E0308]: mismatched types + --> $DIR/inherent-impls-enums.rs:71:26 + | +LL | reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; + | ^^^^^^^^ + | | + | expected `S<'_, _, 1>`, found `X` + | arguments to this function are incorrect | -LL | reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } - | ^^^^^^^^ not found in `S` + = note: expected enum `S<'_, _, 1>` + found struct `X` +note: method defined here + --> $DIR/inherent-impls-enums.rs:10:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: try wrapping the expression in `S::A` + | +LL | reuse S::<'_, _, 1>::S::A(foo_self)::<'static, _, _> as foo_self_4; + | +++++ + -error[E0425]: cannot find function `foo_self` in enum `S` - --> $DIR/inherent-impls-enums.rs:86:32 +error[E0308]: mismatched types + --> $DIR/inherent-impls-enums.rs:86:14 + | +LL | reuse S::foo_self; + | ^^^^^^^^ + | | + | expected `S<'_, A, C>`, found `X` + | arguments to this function are incorrect + | + = note: expected enum `S<'_, A, C>` + found struct `X` +note: method defined here + --> $DIR/inherent-impls-enums.rs:10:8 | -LL | reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ not found in `S` +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- -error: delegation's target expression is specified for function with no params - --> $DIR/inherent-impls-enums.rs:60:76 +error[E0308]: mismatched types + --> $DIR/inherent-impls-enums.rs:89:14 | -LL | reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - | ^^^^^^^^^^^^^^^^ +LL | reuse S::foo_self::<'static, (), true> as foo_self_2; + | ^^^^^^^^ + | | + | expected `S<'_, A, C>`, found `X` + | arguments to this function are incorrect + | + = note: expected enum `S<'_, A, C>` + found struct `X` +note: method defined here + --> $DIR/inherent-impls-enums.rs:10:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- -error: delegation's target expression is specified for function with no params - --> $DIR/inherent-impls-enums.rs:63:55 +error[E0308]: mismatched types + --> $DIR/inherent-impls-enums.rs:92:26 + | +LL | reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; + | ^^^^^^^^ + | | + | expected `S<'_, A, 1>`, found `X` + | arguments to this function are incorrect + | + = note: expected enum `S<'_, A, 1>` + found struct `X` +note: method defined here + --> $DIR/inherent-impls-enums.rs:10:8 | -LL | reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } - | ^^^^^^^^^^^^^^^^ +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- -error: aborting due to 26 previous errors +error: aborting due to 15 previous errors -For more information about this error, try `rustc --explain E0425`. +Some errors have detailed explanations: E0107, E0284, E0308. +For more information about an error, try `rustc --explain E0107`. diff --git a/tests/ui/delegation/inherent-impls-glob-list.stderr b/tests/ui/delegation/inherent-impls-glob-list.stderr index d2dfce86f860a..c15c53194a50b 100644 --- a/tests/ui/delegation/inherent-impls-glob-list.stderr +++ b/tests/ui/delegation/inherent-impls-glob-list.stderr @@ -4,18 +4,5 @@ error: expected trait, found struct `X` LL | reuse X::*; | ^ not a trait -error[E0425]: cannot find function `foo` in `X` - --> $DIR/inherent-impls-glob-list.rs:13:15 - | -LL | reuse X::{foo, foo2} { X } - | ^^^ not found in `X` - -error[E0425]: cannot find function `foo2` in `X` - --> $DIR/inherent-impls-glob-list.rs:13:20 - | -LL | reuse X::{foo, foo2} { X } - | ^^^^ not found in `X` - -error: aborting due to 3 previous errors +error: aborting due to 1 previous error -For more information about this error, try `rustc --explain E0425`. diff --git a/tests/ui/delegation/inherent-impls-mixed-generics.stderr b/tests/ui/delegation/inherent-impls-mixed-generics.stderr index f515b52ca45ab..e2550242284da 100644 --- a/tests/ui/delegation/inherent-impls-mixed-generics.stderr +++ b/tests/ui/delegation/inherent-impls-mixed-generics.stderr @@ -1,9 +1,25 @@ -error[E0425]: cannot find function `foo_self` in `S` +error: failed to generate delegation: mismatch between provided generic args in inherent impl and declared generics --> $DIR/inherent-impls-mixed-generics.rs:12:14 | LL | reuse S::foo_self; - | ^^^^^^^^ not found in `S` + | ^^^^^^^^ -error: aborting due to 1 previous error +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-mixed-generics.rs:12:14 + | +LL | reuse S::foo_self; + | ^^^^^^^^ argument #1 of type `S<'static, _, usize, _>` is missing + | +note: method defined here + --> $DIR/inherent-impls-mixed-generics.rs:8:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse S::foo_self(/* value */); + | +++++++++++++ + +error: aborting due to 2 previous errors -For more information about this error, try `rustc --explain E0425`. +For more information about this error, try `rustc --explain E0061`. diff --git a/tests/ui/delegation/inherent-impls-non-local-crate.stderr b/tests/ui/delegation/inherent-impls-non-local-crate.stderr index 983c8b8f3cb9b..870194eedd5ca 100644 --- a/tests/ui/delegation/inherent-impls-non-local-crate.stderr +++ b/tests/ui/delegation/inherent-impls-non-local-crate.stderr @@ -1,39 +1,49 @@ -error[E0425]: cannot find function `foo` in `inherent_impl::S` - --> $DIR/inherent-impls-non-local-crate.rs:5:25 +error: ambiguous delegation to inherent impl function + --> $DIR/inherent-impls-non-local-crate.rs:22:25 | -LL | reuse inherent_impl::S::foo; - | ^^^ not found in `inherent_impl::S` +LL | reuse inherent_impl::X::foo as x_foo; + | ^^^ -error[E0425]: cannot find function `not_existing` in `inherent_impl::S` +error[E0599]: no associated function or constant named `not_existing` found for struct `S` in the current scope --> $DIR/inherent-impls-non-local-crate.rs:8:25 | LL | reuse inherent_impl::S::not_existing; - | ^^^^^^^^^^^^ not found in `inherent_impl::S` + | ^^^^^^^^^^^^ associated function or constant not found in `S` -error[E0425]: cannot find function `TYPE` in `inherent_impl::S` +error[E0599]: no associated function or constant named `TYPE` found for struct `S` in the current scope --> $DIR/inherent-impls-non-local-crate.rs:11:25 | LL | reuse inherent_impl::S::TYPE; - | ^^^^ not found in `inherent_impl::S` + | ^^^^ associated function or constant not found in `S` -error[E0425]: cannot find function `CONST` in `inherent_impl::S` +error[E0618]: expected function, found `usize` --> $DIR/inherent-impls-non-local-crate.rs:14:25 | LL | reuse inherent_impl::S::CONST; - | ^^^^^ not found in `inherent_impl::S` + | ^^^^^ call expression requires function -error[E0425]: cannot find function `bar` in `inherent_impl::S` +error[E0599]: no associated function or constant named `bar` found for struct `S` in the current scope --> $DIR/inherent-impls-non-local-crate.rs:17:25 | LL | reuse inherent_impl::S::bar; - | ^^^ not found in `inherent_impl::S` + | ^^^ associated function or constant not found in `S` + | + = help: items from traits can only be used if the trait is in scope +help: trait `Trait` which provides `bar` is implemented but not in scope; perhaps you want to import it + | +LL + use inherent_impl::Trait; + | -error[E0425]: cannot find function `foo` in `inherent_impl::X` +error[E0034]: multiple applicable items in scope --> $DIR/inherent-impls-non-local-crate.rs:22:25 | LL | reuse inherent_impl::X::foo as x_foo; - | ^^^ not found in `inherent_impl::X` + | ^^^ multiple `foo` found + | + = note: candidate #1 is defined in an impl for the type `X` + = note: candidate #2 is defined in an impl for the type `X` error: aborting due to 6 previous errors -For more information about this error, try `rustc --explain E0425`. +Some errors have detailed explanations: E0034, E0599, E0618. +For more information about an error, try `rustc --explain E0034`. diff --git a/tests/ui/delegation/inherent-impls-receiver-mapping.stderr b/tests/ui/delegation/inherent-impls-receiver-mapping.stderr index 92baa5ff53ed0..e98169c9c8c65 100644 --- a/tests/ui/delegation/inherent-impls-receiver-mapping.stderr +++ b/tests/ui/delegation/inherent-impls-receiver-mapping.stderr @@ -1,256 +1,145 @@ -error[E0425]: cannot find function `static_f` in `X` - --> $DIR/inherent-impls-receiver-mapping.rs:17:19 +error[E0308]: mismatched types + --> $DIR/inherent-impls-receiver-mapping.rs:66:18 | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^^^ not found in `X` - -error[E0425]: cannot find function `by_value` in `X` - --> $DIR/inherent-impls-receiver-mapping.rs:17:29 - | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^^^ not found in `X` - -error[E0425]: cannot find function `by_ref` in `X` - --> $DIR/inherent-impls-receiver-mapping.rs:17:39 - | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^ not found in `X` - -error[E0425]: cannot find function `by_mut_ref` in `X` - --> $DIR/inherent-impls-receiver-mapping.rs:17:47 +LL | W(X).add(W(X)); + | --- ^^^^ expected `X`, found `W` + | | + | arguments to this method are incorrect | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^^^^^ not found in `X` - -error[E0425]: cannot find function `add` in `X` +note: method defined here --> $DIR/inherent-impls-receiver-mapping.rs:61:18 | LL | reuse X::add { self.0 } - | ^^^ not found in `X` + | ^^^ -error[E0599]: no method named `by_ref` found for struct `Y` in the current scope - --> $DIR/inherent-impls-receiver-mapping.rs:26:11 +error[E0382]: use of moved value: `y` + --> $DIR/inherent-impls-receiver-mapping.rs:28:9 | -LL | struct Y; - | -------- method `by_ref` not found for this struct -... +LL | let y = Y; + | - move occurs because `y` has type `Y`, which does not implement the `Copy` trait LL | y.by_ref(); - | ^^^^^^ this is an associated function, not a method - | - = note: found the following associated functions; to be used as methods, functions must have a `self` parameter -note: the candidate is defined in an impl for the type `Y` - --> $DIR/inherent-impls-receiver-mapping.rs:17:39 - | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^ - = help: items from traits can only be used if the trait is implemented and in scope - = note: the following traits define an item `by_ref`, perhaps you need to implement one of them: - candidate #1: `Iterator` - candidate #2: `std::io::Read` - candidate #3: `std::io::Write` -help: use associated function syntax instead - | -LL - y.by_ref(); -LL + Y::by_ref(); - | - -error[E0599]: no method named `by_mut_ref` found for struct `Y` in the current scope - --> $DIR/inherent-impls-receiver-mapping.rs:28:11 - | -LL | struct Y; - | -------- method `by_mut_ref` not found for this struct -... + | -------- `y` moved due to this method call +LL | LL | y.by_mut_ref(); - | ^^^^^^^^^^ this is an associated function, not a method - | - = note: found the following associated functions; to be used as methods, functions must have a `self` parameter -note: the candidate is defined in an impl for the type `Y` - --> $DIR/inherent-impls-receiver-mapping.rs:17:47 - | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^^^^^ -help: use associated function syntax instead - | -LL - y.by_mut_ref(); -LL + Y::by_mut_ref(); + | ^ value used here after move | + = note: `receiver_mapping::Y::by_ref` takes ownership of the receiver `self`, which moves `y` -error[E0599]: no method named `by_value` found for struct `Y` in the current scope - --> $DIR/inherent-impls-receiver-mapping.rs:30:11 +error[E0382]: use of moved value: `y` + --> $DIR/inherent-impls-receiver-mapping.rs:30:9 | -LL | struct Y; - | -------- method `by_value` not found for this struct +LL | let y = Y; + | - move occurs because `y` has type `Y`, which does not implement the `Copy` trait ... +LL | y.by_mut_ref(); + | ------------ `y` moved due to this method call +LL | LL | y.by_value(); - | ^^^^^^^^ this is an associated function, not a method - | - = note: found the following associated functions; to be used as methods, functions must have a `self` parameter -note: the candidate is defined in an impl for the type `Y` - --> $DIR/inherent-impls-receiver-mapping.rs:17:29 - | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^^^ -help: use associated function syntax instead - | -LL - y.by_value(); -LL + Y::by_value(); - | + | ^ value used here after move -error[E0599]: no method named `by_value` found for reference `&Y` in the current scope - --> $DIR/inherent-impls-receiver-mapping.rs:34:11 +error[E0507]: cannot move out of `*y` which is behind a shared reference + --> $DIR/inherent-impls-receiver-mapping.rs:34:9 | LL | y.by_value(); - | ^^^^^^^^ this is an associated function, not a method - | - = note: found the following associated functions; to be used as methods, functions must have a `self` parameter -note: the candidate is defined in an impl for the type `Y` - --> $DIR/inherent-impls-receiver-mapping.rs:17:29 + | ^ ---------- `*y` moved due to this method call + | | + | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^^^ -help: use associated function syntax instead - | -LL - y.by_value(); -LL + Y::by_value(); +note: if `Y` implemented `Clone`, you could clone the value + --> $DIR/inherent-impls-receiver-mapping.rs:13:5 | +LL | struct Y; + | ^^^^^^^^ consider implementing `Clone` for this type +... +LL | y.by_value(); + | - you could clone this value -error[E0599]: no method named `by_ref` found for reference `&Y` in the current scope - --> $DIR/inherent-impls-receiver-mapping.rs:36:11 +error[E0507]: cannot move out of `*y` which is behind a shared reference + --> $DIR/inherent-impls-receiver-mapping.rs:36:9 | LL | y.by_ref(); - | ^^^^^^ this is an associated function, not a method - | - = note: found the following associated functions; to be used as methods, functions must have a `self` parameter -note: the candidate is defined in an impl for the type `Y` - --> $DIR/inherent-impls-receiver-mapping.rs:17:39 - | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^ - = help: items from traits can only be used if the trait is implemented and in scope - = note: the following traits define an item `by_ref`, perhaps you need to implement one of them: - candidate #1: `std::io::Read` - candidate #2: `std::io::Write` - = note: the trait `Iterator` defines an item `by_ref`, but is explicitly unimplemented -help: use associated function syntax instead + | ^ -------- `*y` moved due to this method call + | | + | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait | -LL - y.by_ref(); -LL + Y::by_ref(); +note: if `Y` implemented `Clone`, you could clone the value + --> $DIR/inherent-impls-receiver-mapping.rs:13:5 | +LL | struct Y; + | ^^^^^^^^ consider implementing `Clone` for this type +... +LL | y.by_ref(); + | - you could clone this value -error[E0599]: no method named `by_mut_ref` found for reference `&Y` in the current scope - --> $DIR/inherent-impls-receiver-mapping.rs:38:11 +error[E0507]: cannot move out of `*y` which is behind a shared reference + --> $DIR/inherent-impls-receiver-mapping.rs:38:9 | LL | y.by_mut_ref(); - | ^^^^^^^^^^ this is an associated function, not a method - | - = note: found the following associated functions; to be used as methods, functions must have a `self` parameter -note: the candidate is defined in an impl for the type `Y` - --> $DIR/inherent-impls-receiver-mapping.rs:17:47 - | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^^^^^ -help: use associated function syntax instead + | ^ ------------ `*y` moved due to this method call + | | + | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait | -LL - y.by_mut_ref(); -LL + Y::by_mut_ref(); +note: if `Y` implemented `Clone`, you could clone the value + --> $DIR/inherent-impls-receiver-mapping.rs:13:5 | +LL | struct Y; + | ^^^^^^^^ consider implementing `Clone` for this type +... +LL | y.by_mut_ref(); + | - you could clone this value -error[E0599]: no method named `by_value` found for mutable reference `&mut Y` in the current scope - --> $DIR/inherent-impls-receiver-mapping.rs:42:11 +error[E0507]: cannot move out of `*y` which is behind a mutable reference + --> $DIR/inherent-impls-receiver-mapping.rs:42:9 | LL | y.by_value(); - | ^^^^^^^^ this is an associated function, not a method + | ^ ---------- `*y` moved due to this method call + | | + | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait | - = note: found the following associated functions; to be used as methods, functions must have a `self` parameter -note: the candidate is defined in an impl for the type `Y` - --> $DIR/inherent-impls-receiver-mapping.rs:17:29 +note: if `Y` implemented `Clone`, you could clone the value + --> $DIR/inherent-impls-receiver-mapping.rs:13:5 | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^^^ -help: use associated function syntax instead +LL | struct Y; + | ^^^^^^^^ consider implementing `Clone` for this type +... +LL | y.by_value(); + | - you could clone this value + +error[E0507]: cannot move out of `*y` which is behind a mutable reference + --> $DIR/inherent-impls-receiver-mapping.rs:44:9 | -LL - y.by_value(); -LL + Y::by_value(); +LL | y.by_ref(); + | ^ -------- `*y` moved due to this method call + | | + | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait | - -error[E0599]: the method `by_ref` exists for mutable reference `&mut Y`, but its trait bounds were not satisfied - --> $DIR/inherent-impls-receiver-mapping.rs:44:11 +note: if `Y` implemented `Clone`, you could clone the value + --> $DIR/inherent-impls-receiver-mapping.rs:13:5 | LL | struct Y; - | -------- doesn't satisfy `Y: Iterator` + | ^^^^^^^^ consider implementing `Clone` for this type ... LL | y.by_ref(); - | ^^^^^^ this is an associated function, not a method - | - = note: found the following associated functions; to be used as methods, functions must have a `self` parameter -note: the candidate is defined in an impl for the type `Y` - --> $DIR/inherent-impls-receiver-mapping.rs:17:39 - | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^ - = note: the following trait bounds were not satisfied: - `Y: Iterator` - which is required by `&mut Y: Iterator` -note: the trait `Iterator` must be implemented - --> $SRC_DIR/core/src/iter/traits/iterator.rs:LL:COL - = help: items from traits can only be used if the trait is implemented and in scope - = note: the following traits define an item `by_ref`, perhaps you need to implement one of them: - candidate #1: `std::io::Read` - candidate #2: `std::io::Write` - = note: the trait `Iterator` defines an item `by_ref`, but is explicitly unimplemented -help: use associated function syntax instead - | -LL - y.by_ref(); -LL + Y::by_ref(); - | + | - you could clone this value -error[E0599]: no method named `by_mut_ref` found for mutable reference `&mut Y` in the current scope - --> $DIR/inherent-impls-receiver-mapping.rs:46:11 +error[E0507]: cannot move out of `*y` which is behind a mutable reference + --> $DIR/inherent-impls-receiver-mapping.rs:46:9 | LL | y.by_mut_ref(); - | ^^^^^^^^^^ this is an associated function, not a method - | - = note: found the following associated functions; to be used as methods, functions must have a `self` parameter -note: the candidate is defined in an impl for the type `Y` - --> $DIR/inherent-impls-receiver-mapping.rs:17:47 - | -LL | reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - | ^^^^^^^^^^ -help: use associated function syntax instead - | -LL - y.by_mut_ref(); -LL + Y::by_mut_ref(); + | ^ ------------ `*y` moved due to this method call + | | + | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait | - -error[E0599]: no method named `add` found for struct `W` in the current scope - --> $DIR/inherent-impls-receiver-mapping.rs:66:14 +note: if `Y` implemented `Clone`, you could clone the value + --> $DIR/inherent-impls-receiver-mapping.rs:13:5 | -LL | struct W(X); - | -------- method `add` not found for this struct +LL | struct Y; + | ^^^^^^^^ consider implementing `Clone` for this type ... -LL | W(X).add(W(X)); - | ^^^ this is an associated function, not a method - | - = note: found the following associated functions; to be used as methods, functions must have a `self` parameter -note: the candidate is defined in an impl for the type `W` - --> $DIR/inherent-impls-receiver-mapping.rs:61:18 - | -LL | reuse X::add { self.0 } - | ^^^ - = help: items from traits can only be used if the trait is implemented and in scope - = note: the following trait defines an item `add`, perhaps you need to implement it: - candidate #1: `Add` -help: use associated function syntax instead - | -LL - W(X).add(W(X)); -LL + W::add(W(X)); - | -help: one of the expressions' fields has a method of the same name - | -LL | W(X).0.add(W(X)); - | ++ +LL | y.by_mut_ref(); + | - you could clone this value -error: aborting due to 15 previous errors +error: aborting due to 9 previous errors -Some errors have detailed explanations: E0425, E0599. -For more information about an error, try `rustc --explain E0425`. +Some errors have detailed explanations: E0308, E0382, E0507. +For more information about an error, try `rustc --explain E0308`. diff --git a/tests/ui/delegation/inherent-impls-recursive-cycle.rs b/tests/ui/delegation/inherent-impls-recursive-cycle.rs index 0860ff39f51ee..81a59b63874fb 100644 --- a/tests/ui/delegation/inherent-impls-recursive-cycle.rs +++ b/tests/ui/delegation/inherent-impls-recursive-cycle.rs @@ -2,6 +2,7 @@ trait Trait1 { reuse trait_foo_reused as foo; + //~^ ERROR: encountered a cycle during delegation signature resolution } impl Trait1 for () {} @@ -9,44 +10,49 @@ impl Trait1 for () {} struct S1(T); impl S1 { reuse Trait1::foo { self.0 } - //~^ ERROR: delegation's target expression is specified for function with no params + //~^ ERROR: encountered a cycle during delegation signature resolution //~| ERROR: this function takes 0 arguments but 1 argument was supplied } struct S2(S1<()>); impl S2 { reuse S1::<()>::foo { self.0 } - //~^ ERROR: cannot find function `foo` in `S1` + //~^ ERROR: encountered a cycle during delegation signature resolution + //~| ERROR: this function takes 0 arguments but 1 argument was supplied } reuse S2::foo; -//~^ ERROR: cannot find function `foo` in `S2` +//~^ ERROR: encountered a cycle during delegation signature resolution struct S3; impl S3 { reuse foo; + //~^ ERROR: encountered a cycle during delegation signature resolution } impl Trait1 for S3 { reuse S2::foo { S2(S1(())) } - //~^ ERROR: delegation's target expression is specified for function with no params - //~| ERROR: cannot find function `foo` in `S2` + //~^ ERROR: encountered a cycle during delegation signature resolution + //~| ERROR: this function takes 0 arguments but 1 argument was supplied } trait Trait2 { reuse ::foo { S3 } - //~^ ERROR: delegation's target expression is specified for function with no params + //~^ ERROR: encountered a cycle during delegation signature resolution //~| ERROR: this function takes 0 arguments but 1 argument was supplied } reuse Trait2::foo as trait_foo; +//~^ ERROR: encountered a cycle during delegation signature resolution +//~| ERROR: type annotations needed struct S4; impl S4 { reuse trait_foo; + //~^ ERROR: encountered a cycle during delegation signature resolution } reuse S4::trait_foo as trait_foo_reused; -//~^ ERROR: cannot find function `trait_foo` in `S4` +//~^ ERROR: encountered a cycle during delegation signature resolution fn main() {} diff --git a/tests/ui/delegation/inherent-impls-recursive-cycle.stderr b/tests/ui/delegation/inherent-impls-recursive-cycle.stderr index a68931f8abce7..9c88b8e7cacc4 100644 --- a/tests/ui/delegation/inherent-impls-recursive-cycle.stderr +++ b/tests/ui/delegation/inherent-impls-recursive-cycle.stderr @@ -1,47 +1,65 @@ -error[E0425]: cannot find function `foo` in `S1` - --> $DIR/inherent-impls-recursive-cycle.rs:18:21 +error: encountered a cycle during delegation signature resolution + --> $DIR/inherent-impls-recursive-cycle.rs:4:11 + | +LL | reuse trait_foo_reused as foo; + | ^^^^^^^^^^^^^^^^ + +error: encountered a cycle during delegation signature resolution + --> $DIR/inherent-impls-recursive-cycle.rs:12:19 + | +LL | reuse Trait1::foo { self.0 } + | ^^^ + +error: encountered a cycle during delegation signature resolution + --> $DIR/inherent-impls-recursive-cycle.rs:19:21 | LL | reuse S1::<()>::foo { self.0 } - | ^^^ not found in `S1` + | ^^^ -error[E0425]: cannot find function `foo` in `S2` - --> $DIR/inherent-impls-recursive-cycle.rs:22:11 +error: encountered a cycle during delegation signature resolution + --> $DIR/inherent-impls-recursive-cycle.rs:24:11 | LL | reuse S2::foo; - | ^^^ not found in `S2` + | ^^^ + +error: encountered a cycle during delegation signature resolution + --> $DIR/inherent-impls-recursive-cycle.rs:29:11 + | +LL | reuse foo; + | ^^^ -error[E0425]: cannot find function `foo` in `S2` - --> $DIR/inherent-impls-recursive-cycle.rs:31:15 +error: encountered a cycle during delegation signature resolution + --> $DIR/inherent-impls-recursive-cycle.rs:34:15 | LL | reuse S2::foo { S2(S1(())) } - | ^^^ not found in `S2` + | ^^^ -error[E0425]: cannot find function `trait_foo` in `S4` - --> $DIR/inherent-impls-recursive-cycle.rs:49:11 +error: encountered a cycle during delegation signature resolution + --> $DIR/inherent-impls-recursive-cycle.rs:40:27 | -LL | reuse S4::trait_foo as trait_foo_reused; - | ^^^^^^^^^ not found in `S4` +LL | reuse ::foo { S3 } + | ^^^ -error: delegation's target expression is specified for function with no params - --> $DIR/inherent-impls-recursive-cycle.rs:11:23 +error: encountered a cycle during delegation signature resolution + --> $DIR/inherent-impls-recursive-cycle.rs:45:15 | -LL | reuse Trait1::foo { self.0 } - | ^^^^^^^^^^ +LL | reuse Trait2::foo as trait_foo; + | ^^^ -error: delegation's target expression is specified for function with no params - --> $DIR/inherent-impls-recursive-cycle.rs:31:19 +error: encountered a cycle during delegation signature resolution + --> $DIR/inherent-impls-recursive-cycle.rs:51:11 | -LL | reuse S2::foo { S2(S1(())) } - | ^^^^^^^^^^^^^^ +LL | reuse trait_foo; + | ^^^^^^^^^ -error: delegation's target expression is specified for function with no params - --> $DIR/inherent-impls-recursive-cycle.rs:37:31 +error: encountered a cycle during delegation signature resolution + --> $DIR/inherent-impls-recursive-cycle.rs:55:11 | -LL | reuse ::foo { S3 } - | ^^^^^^ +LL | reuse S4::trait_foo as trait_foo_reused; + | ^^^^^^^^^ error[E0061]: this function takes 0 arguments but 1 argument was supplied - --> $DIR/inherent-impls-recursive-cycle.rs:11:19 + --> $DIR/inherent-impls-recursive-cycle.rs:12:19 | LL | reuse Trait1::foo { self.0 } | ^^^ ---------- unexpected argument @@ -58,7 +76,41 @@ LL + reuse Trait1::fo{ self.0 } | error[E0061]: this function takes 0 arguments but 1 argument was supplied - --> $DIR/inherent-impls-recursive-cycle.rs:37:27 + --> $DIR/inherent-impls-recursive-cycle.rs:19:21 + | +LL | reuse S1::<()>::foo { self.0 } + | ^^^ ---------- unexpected argument + | +note: associated function defined here + --> $DIR/inherent-impls-recursive-cycle.rs:12:19 + | +LL | reuse Trait1::foo { self.0 } + | ^^^ +help: remove the extra argument + | +LL - reuse S1::<()>::foo { self.0 } +LL + reuse S1::<()>::fo{ self.0 } + | + +error[E0061]: this function takes 0 arguments but 1 argument was supplied + --> $DIR/inherent-impls-recursive-cycle.rs:34:15 + | +LL | reuse S2::foo { S2(S1(())) } + | ^^^ -------------- unexpected argument of type `S2` + | +note: associated function defined here + --> $DIR/inherent-impls-recursive-cycle.rs:19:21 + | +LL | reuse S1::<()>::foo { self.0 } + | ^^^ +help: remove the extra argument + | +LL - reuse S2::foo { S2(S1(())) } +LL + reuse S2::fo{ S2(S1(())) } + | + +error[E0061]: this function takes 0 arguments but 1 argument was supplied + --> $DIR/inherent-impls-recursive-cycle.rs:40:27 | LL | reuse ::foo { S3 } | ^^^ ------ unexpected argument of type `S3` @@ -74,7 +126,15 @@ LL - reuse ::foo { S3 } LL + reuse ::fo{ S3 } | -error: aborting due to 9 previous errors +error[E0283]: type annotations needed + --> $DIR/inherent-impls-recursive-cycle.rs:45:15 + | +LL | reuse Trait2::foo as trait_foo; + | ^^^ cannot infer type + | + = note: the type must implement `Trait2` + +error: aborting due to 15 previous errors -Some errors have detailed explanations: E0061, E0425. +Some errors have detailed explanations: E0061, E0283. For more information about an error, try `rustc --explain E0061`. diff --git a/tests/ui/delegation/inherent-impls-recursive.rs b/tests/ui/delegation/inherent-impls-recursive.rs index c57ef40642346..b8a0ac314f559 100644 --- a/tests/ui/delegation/inherent-impls-recursive.rs +++ b/tests/ui/delegation/inherent-impls-recursive.rs @@ -1,3 +1,5 @@ +//@ check-pass + #![feature(fn_delegation)] mod test_1 { @@ -9,13 +11,11 @@ mod test_1 { struct S2; impl S2 { reuse S1::foo; - //~^ ERROR: cannot find function `foo` in `S1` } struct S3; impl S3 { reuse S2::foo; - //~^ ERROR: cannot find function `foo` in `S2` } } @@ -34,11 +34,9 @@ mod test_2 { struct S2(S1<()>); impl S2 { reuse S1::<()>::foo { self.0 } - //~^ ERROR: cannot find function `foo` in `S1` } reuse S2::foo; - //~^ ERROR: cannot find function `foo` in `S2` struct S3; impl S3 { @@ -46,9 +44,7 @@ mod test_2 { } impl Trait1 for S3 { - reuse S2::foo { &S2(S1(())) } - //~^ ERROR: method `foo` has a `&self` declaration in the trait, but not in the impl - //~| ERROR: cannot find function `foo` in `S2` + reuse S2::foo { S2(S1(())) } } trait Trait2 { @@ -63,7 +59,6 @@ mod test_2 { } reuse S4::trait_foo as trait_foo_reused; - //~^ ERROR: cannot find function `trait_foo` in `S4` } fn main() {} diff --git a/tests/ui/delegation/inherent-impls-recursive.stderr b/tests/ui/delegation/inherent-impls-recursive.stderr deleted file mode 100644 index f80d9d3b84097..0000000000000 --- a/tests/ui/delegation/inherent-impls-recursive.stderr +++ /dev/null @@ -1,61 +0,0 @@ -error[E0425]: cannot find function `foo` in `S1` - --> $DIR/inherent-impls-recursive.rs:11:19 - | -LL | reuse S1::foo; - | ^^^ not found in `S1` - | -note: function `test_2::foo` exists but is inaccessible - --> $DIR/inherent-impls-recursive.rs:40:5 - | -LL | reuse S2::foo; - | ^^^^^^^^^^^^^^ not accessible - -error[E0425]: cannot find function `foo` in `S2` - --> $DIR/inherent-impls-recursive.rs:17:19 - | -LL | reuse S2::foo; - | ^^^ not found in `S2` - | -note: function `test_2::foo` exists but is inaccessible - --> $DIR/inherent-impls-recursive.rs:40:5 - | -LL | reuse S2::foo; - | ^^^^^^^^^^^^^^ not accessible - -error[E0425]: cannot find function `foo` in `S1` - --> $DIR/inherent-impls-recursive.rs:36:25 - | -LL | reuse S1::<()>::foo { self.0 } - | ^^^ not found in `S1` - -error[E0425]: cannot find function `foo` in `S2` - --> $DIR/inherent-impls-recursive.rs:40:15 - | -LL | reuse S2::foo; - | ^^^ not found in `S2` - -error[E0425]: cannot find function `foo` in `S2` - --> $DIR/inherent-impls-recursive.rs:49:19 - | -LL | reuse S2::foo { &S2(S1(())) } - | ^^^ not found in `S2` - -error[E0425]: cannot find function `trait_foo` in `S4` - --> $DIR/inherent-impls-recursive.rs:65:15 - | -LL | reuse S4::trait_foo as trait_foo_reused; - | ^^^^^^^^^ not found in `S4` - -error[E0186]: method `foo` has a `&self` declaration in the trait, but not in the impl - --> $DIR/inherent-impls-recursive.rs:49:19 - | -LL | fn foo(&self) {} - | ------------- `&self` used in trait -... -LL | reuse S2::foo { &S2(S1(())) } - | ^^^ expected `&self` in impl - -error: aborting due to 7 previous errors - -Some errors have detailed explanations: E0186, E0425. -For more information about an error, try `rustc --explain E0186`. diff --git a/tests/ui/delegation/inherent-impls-self-mapping.stderr b/tests/ui/delegation/inherent-impls-self-mapping.stderr index 9ecf04626d29c..d372383d8e344 100644 --- a/tests/ui/delegation/inherent-impls-self-mapping.stderr +++ b/tests/ui/delegation/inherent-impls-self-mapping.stderr @@ -1,15 +1,22 @@ -error[E0425]: cannot find function `foo` in `X` +error[E0308]: mismatched types --> $DIR/inherent-impls-self-mapping.rs:13:14 | +LL | trait Trait { + | ----------- found this type parameter LL | reuse X::foo; - | ^^^ not found in `X` - -error[E0425]: cannot find function `foo` in `X` - --> $DIR/inherent-impls-self-mapping.rs:17:10 + | ^^^ + | | + | expected `Rc>`, found `Rc>` + | arguments to this function are incorrect + | + = note: expected struct `Rc>` + found struct `Rc>` +note: method defined here + --> $DIR/inherent-impls-self-mapping.rs:7:8 | -LL | reuse X::foo; - | ^^^ not found in `X` +LL | fn foo(self: Rc>, other: Box>) -> Option> { + | ^^^ ---- -error: aborting due to 2 previous errors +error: aborting due to 1 previous error -For more information about this error, try `rustc --explain E0425`. +For more information about this error, try `rustc --explain E0308`. diff --git a/tests/ui/delegation/inherent-impls-self-replacement.rs b/tests/ui/delegation/inherent-impls-self-replacement.rs index e6aa7458993fd..65ecccf766719 100644 --- a/tests/ui/delegation/inherent-impls-self-replacement.rs +++ b/tests/ui/delegation/inherent-impls-self-replacement.rs @@ -20,37 +20,36 @@ trait Trait: Sized { fn get_s(self) -> S<(), 123>; reuse S::<(), 123>::by_value { self.get_s() } - //~^ ERROR: cannot find function `by_value` in `S` reuse S::<(), 123>::by_ref { self.get_s() } - //~^ ERROR: cannot find function `by_ref` in `S` + //~^ ERROR: cannot move out of `*self` which is behind a shared reference reuse S::<(), 123>::by_mut_ref { self.get_s() } - //~^ ERROR: cannot find function `by_mut_ref` in `S` + //~^ ERROR: cannot move out of `*self` which is behind a mutable reference reuse S::<(), 123>::by_box { self.get_s() } - //~^ ERROR: cannot find function `by_box` in `S` + //~^ ERROR: mismatched types reuse S::<(), 123>::by_rc { self.get_s() } - //~^ ERROR: cannot find function `by_rc` in `S` + //~^ ERROR: mismatched types reuse S::<(), 123>::by_pin { self.get_s() } - //~^ ERROR: cannot find function `by_pin` in `S` + //~^ ERROR: mismatched types } trait Trait2: Sized { reuse S::<(), 123>::by_value { self.get_s() } - //~^ ERROR: cannot find function `by_value` in `S` + //~^ ERROR: no method named `get_s` found for type parameter `Self` in the current scope reuse S::<(), 123>::by_ref { self.get_s() } - //~^ ERROR: cannot find function `by_ref` in `S` + //~^ ERROR: no method named `get_s` found for reference `&Self` in the current scope reuse S::<(), 123>::by_mut_ref { self.get_s() } - //~^ ERROR: cannot find function `by_mut_ref` in `S` + //~^ ERROR: no method named `get_s` found for mutable reference `&mut Self` in the current scope reuse S::<(), 123>::by_box { self.get_s() } - //~^ ERROR: cannot find function `by_box` in `S` + //~^ ERROR: no method named `get_s` found for struct `Box` in the current scope reuse S::<(), 123>::by_rc { self.get_s() } - //~^ ERROR: cannot find function `by_rc` in `S` + //~^ ERROR: no method named `get_s` found for struct `Rc` in the current scope reuse S::<(), 123>::by_pin { self.get_s() } - //~^ ERROR: cannot find function `by_pin` in `S` + //~^ ERROR: no method named `get_s` found for struct `Pin>` in the current scope } fn main() {} diff --git a/tests/ui/delegation/inherent-impls-self-replacement.stderr b/tests/ui/delegation/inherent-impls-self-replacement.stderr index e293635e4a1ea..e017bee8af540 100644 --- a/tests/ui/delegation/inherent-impls-self-replacement.stderr +++ b/tests/ui/delegation/inherent-impls-self-replacement.stderr @@ -1,75 +1,186 @@ -error[E0425]: cannot find function `by_value` in `S` - --> $DIR/inherent-impls-self-replacement.rs:22:25 +error[E0308]: mismatched types + --> $DIR/inherent-impls-self-replacement.rs:30:34 | -LL | reuse S::<(), 123>::by_value { self.get_s() } - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `by_ref` in `S` - --> $DIR/inherent-impls-self-replacement.rs:25:25 +LL | reuse S::<(), 123>::by_box { self.get_s() } + | ------ ^^^^^^^^^^^^ expected `Box>`, found `S<(), 123>` + | | + | arguments to this function are incorrect | -LL | reuse S::<(), 123>::by_ref { self.get_s() } - | ^^^^^^ not found in `S` - -error[E0425]: cannot find function `by_mut_ref` in `S` - --> $DIR/inherent-impls-self-replacement.rs:28:25 + = note: expected struct `Box>` + found struct `S<_, _>` + = note: for more on the distinction between the stack and the heap, read https://doc.rust-lang.org/book/ch15-01-box.html, https://doc.rust-lang.org/rust-by-example/std/box.html, and https://doc.rust-lang.org/std/boxed/index.html +note: method defined here + --> $DIR/inherent-impls-self-replacement.rs:14:8 | -LL | reuse S::<(), 123>::by_mut_ref { self.get_s() } - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `by_box` in `S` - --> $DIR/inherent-impls-self-replacement.rs:31:25 +LL | fn by_box<'d: 'd, 'e, T, const B: bool>(self: Box) {} + | ^^^^^^ ---- +help: store this in the heap by calling `Box::new` | -LL | reuse S::<(), 123>::by_box { self.get_s() } - | ^^^^^^ not found in `S` +LL | reuse S::<(), 123>::by_box { Box::new(self.get_s()) } + | +++++++++ + -error[E0425]: cannot find function `by_rc` in `S` - --> $DIR/inherent-impls-self-replacement.rs:34:25 +error[E0308]: mismatched types + --> $DIR/inherent-impls-self-replacement.rs:33:33 | LL | reuse S::<(), 123>::by_rc { self.get_s() } - | ^^^^^ not found in `S` + | ----- ^^^^^^^^^^^^ expected `Rc>`, found `S<(), 123>` + | | + | arguments to this function are incorrect + | + = note: expected struct `Rc>` + found struct `S<_, _>` +note: method defined here + --> $DIR/inherent-impls-self-replacement.rs:15:8 + | +LL | fn by_rc<'d: 'd, 'e, T, const B: bool>(self: Rc) {} + | ^^^^^ ---- +help: call `Into::into` on this expression to convert `S<(), 123>` into `Rc>` + | +LL | reuse S::<(), 123>::by_rc { self.get_s().into() } + | +++++++ -error[E0425]: cannot find function `by_pin` in `S` - --> $DIR/inherent-impls-self-replacement.rs:37:25 +error[E0308]: mismatched types + --> $DIR/inherent-impls-self-replacement.rs:36:34 | LL | reuse S::<(), 123>::by_pin { self.get_s() } - | ^^^^^^ not found in `S` + | ------ ^^^^^^^^^^^^ expected `Pin>>`, found `S<(), 123>` + | | + | arguments to this function are incorrect + | + = note: expected struct `Pin>>` + found struct `S<(), 123>` +note: method defined here + --> $DIR/inherent-impls-self-replacement.rs:16:8 + | +LL | fn by_pin<'d: 'd, 'e, T, const B: bool>(self: Pin>) {} + | ^^^^^^ ---- +help: you need to pin and box this expression + | +LL | reuse S::<(), 123>::by_pin { Box::pin(self.get_s()) } + | +++++++++ + -error[E0425]: cannot find function `by_value` in `S` - --> $DIR/inherent-impls-self-replacement.rs:42:25 +error[E0599]: no method named `get_s` found for type parameter `Self` in the current scope + --> $DIR/inherent-impls-self-replacement.rs:41:41 | +LL | trait Trait2: Sized { + | ------------------- method `get_s` not found for this type parameter LL | reuse S::<(), 123>::by_value { self.get_s() } - | ^^^^^^^^ not found in `S` + | ^^^^^ method not found in `Self` + | + = help: items from traits can only be used if the type parameter is bounded by the trait +help: the following trait defines an item `get_s`, perhaps you need to add another supertrait for it: + | +LL | trait Trait2: Sized + Trait { + | +++++++ -error[E0425]: cannot find function `by_ref` in `S` - --> $DIR/inherent-impls-self-replacement.rs:44:25 +error[E0599]: no method named `get_s` found for reference `&Self` in the current scope + --> $DIR/inherent-impls-self-replacement.rs:43:39 | LL | reuse S::<(), 123>::by_ref { self.get_s() } - | ^^^^^^ not found in `S` + | ^^^^^ method not found in `&Self` + | + = help: items from traits can only be used if the type parameter is bounded by the trait +help: the following trait defines an item `get_s`, perhaps you need to add another supertrait for it: + | +LL | trait Trait2: Sized + Trait { + | +++++++ -error[E0425]: cannot find function `by_mut_ref` in `S` - --> $DIR/inherent-impls-self-replacement.rs:46:25 +error[E0599]: no method named `get_s` found for mutable reference `&mut Self` in the current scope + --> $DIR/inherent-impls-self-replacement.rs:45:43 | LL | reuse S::<(), 123>::by_mut_ref { self.get_s() } - | ^^^^^^^^^^ not found in `S` + | ^^^^^ method not found in `&mut Self` + | + = help: items from traits can only be used if the type parameter is bounded by the trait +help: the following trait defines an item `get_s`, perhaps you need to add another supertrait for it: + | +LL | trait Trait2: Sized + Trait { + | +++++++ -error[E0425]: cannot find function `by_box` in `S` - --> $DIR/inherent-impls-self-replacement.rs:48:25 +error[E0599]: no method named `get_s` found for struct `Box` in the current scope + --> $DIR/inherent-impls-self-replacement.rs:47:39 | LL | reuse S::<(), 123>::by_box { self.get_s() } - | ^^^^^^ not found in `S` + | ^^^^^ method not found in `Box` + | + = help: items from traits can only be used if the trait is implemented and in scope +note: `Trait` defines an item `get_s`, perhaps you need to implement it + --> $DIR/inherent-impls-self-replacement.rs:19:1 + | +LL | trait Trait: Sized { + | ^^^^^^^^^^^^^^^^^^ -error[E0425]: cannot find function `by_rc` in `S` - --> $DIR/inherent-impls-self-replacement.rs:50:25 +error[E0599]: no method named `get_s` found for struct `Rc` in the current scope + --> $DIR/inherent-impls-self-replacement.rs:49:38 | LL | reuse S::<(), 123>::by_rc { self.get_s() } - | ^^^^^ not found in `S` + | ^^^^^ method not found in `Rc` + | + = help: items from traits can only be used if the trait is implemented and in scope +note: `Trait` defines an item `get_s`, perhaps you need to implement it + --> $DIR/inherent-impls-self-replacement.rs:19:1 + | +LL | trait Trait: Sized { + | ^^^^^^^^^^^^^^^^^^ -error[E0425]: cannot find function `by_pin` in `S` - --> $DIR/inherent-impls-self-replacement.rs:52:25 +error[E0599]: no method named `get_s` found for struct `Pin>` in the current scope + --> $DIR/inherent-impls-self-replacement.rs:51:39 | LL | reuse S::<(), 123>::by_pin { self.get_s() } - | ^^^^^^ not found in `S` + | ^^^^^ method not found in `Pin>` + | + = help: items from traits can only be used if the trait is implemented and in scope +note: `Trait` defines an item `get_s`, perhaps you need to implement it + --> $DIR/inherent-impls-self-replacement.rs:19:1 + | +LL | trait Trait: Sized { + | ^^^^^^^^^^^^^^^^^^ + +error[E0507]: cannot move out of `*self` which is behind a shared reference + --> $DIR/inherent-impls-self-replacement.rs:24:34 + | +LL | reuse S::<(), 123>::by_ref { self.get_s() } + | ^^^^ ------- `*self` moved due to this method call + | | + | move occurs because `*self` has type `Self`, which does not implement the `Copy` trait + | +note: `Trait::get_s` takes ownership of the receiver `self`, which moves `*self` + --> $DIR/inherent-impls-self-replacement.rs:20:14 + | +LL | fn get_s(self) -> S<(), 123>; + | ^^^^ +help: if `Self` implemented `Clone`, you could clone the value + --> $DIR/inherent-impls-self-replacement.rs:19:1 + | +LL | trait Trait: Sized { + | ^^^^^^^^^^^^^^^^^^ consider constraining this type parameter with `Clone` +... +LL | reuse S::<(), 123>::by_ref { self.get_s() } + | ---- you could clone this value + +error[E0507]: cannot move out of `*self` which is behind a mutable reference + --> $DIR/inherent-impls-self-replacement.rs:27:38 + | +LL | reuse S::<(), 123>::by_mut_ref { self.get_s() } + | ^^^^ ------- `*self` moved due to this method call + | | + | move occurs because `*self` has type `Self`, which does not implement the `Copy` trait + | +note: `Trait::get_s` takes ownership of the receiver `self`, which moves `*self` + --> $DIR/inherent-impls-self-replacement.rs:20:14 + | +LL | fn get_s(self) -> S<(), 123>; + | ^^^^ +help: if `Self` implemented `Clone`, you could clone the value + --> $DIR/inherent-impls-self-replacement.rs:19:1 + | +LL | trait Trait: Sized { + | ^^^^^^^^^^^^^^^^^^ consider constraining this type parameter with `Clone` +... +LL | reuse S::<(), 123>::by_mut_ref { self.get_s() } + | ---- you could clone this value -error: aborting due to 12 previous errors +error: aborting due to 11 previous errors -For more information about this error, try `rustc --explain E0425`. +Some errors have detailed explanations: E0308, E0507, E0599. +For more information about an error, try `rustc --explain E0308`. diff --git a/tests/ui/delegation/inherent-impls-structs.rs b/tests/ui/delegation/inherent-impls-structs.rs index a5950185b6dad..5f0b43d9660ba 100644 --- a/tests/ui/delegation/inherent-impls-structs.rs +++ b/tests/ui/delegation/inherent-impls-structs.rs @@ -9,78 +9,82 @@ impl<'a, 'b, 'c, A, const C: usize> S { fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} } +reuse S::foo_static; reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; -//~^ ERROR: cannot find function `foo_static` in `S` +reuse S::foo_static::<'static, (), true> as foo_static_2; reuse S::<(), 1>::foo_static as foo_static_3; -//~^ ERROR: cannot find function `foo_static` in `S` -reuse S::::foo_static::<'static, _, _> as foo_static_4; -//~^ ERROR: cannot find function `foo_static` in `S` +reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; +reuse S::foo_self; reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1; -//~^ ERROR: cannot find function `foo_self` in `S` +reuse S::foo_self::<'static, (), true> as foo_self_2; reuse S::<(), 1>::foo_self as foo_self_3; -//~^ ERROR: cannot find function `foo_self` in `S` -reuse S::::foo_self::<'static, _, _> as foo_self_4; -//~^ ERROR: cannot find function `foo_self` in `S` +reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; trait Trait<'a, AA, BB> where Self: Sized { + reuse S::foo_static; reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; - //~^ ERROR: cannot find function `foo_static` in `S` + reuse S::foo_static::<'static, (), true> as foo_static_2; reuse S::<(), 1>::foo_static as foo_static_3; - //~^ ERROR: cannot find function `foo_static` in `S` - reuse S::<(), 1>::foo_static::<'static, _, _> as foo_static_4; - //~^ ERROR: cannot find function `foo_static` in `S` + reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; fn get_s(self) -> S<(), 1> { panic!(); } + reuse S::foo_self; + //~^ ERROR: mismatched types [E0308] reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - //~^ ERROR: cannot find function `foo_self` in `S` + reuse S::foo_self::<'static, (), true> as foo_self_2; + //~^ ERROR: mismatched types [E0308] reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } - //~^ ERROR: cannot find function `foo_self` in `S` - reuse S::<(), 1>::foo_self::<'static, _, _> as foo_self_4; - //~^ ERROR: cannot find function `foo_self` in `S` + reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; + //~^ ERROR: mismatched types [E0308] } struct X; impl<'a, A, B> Trait<'a, A, B> for X { + reuse S::foo_static; + //~^ ERROR: associated function takes at most 2 generic arguments but 4 generic arguments were supplied [E0107] reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; - //~^ ERROR: cannot find function `foo_static` in `S` + reuse S::foo_static::<'static, (), true> as foo_static_2; + //~^ ERROR: type annotations needed [E0284] + //~| ERROR: type annotations needed [E0284] reuse S::<(), 1>::foo_static as foo_static_3; - //~^ ERROR: cannot find function `foo_static` in `S` - reuse S::<(), 1>::foo_static::<'static, _, _> as foo_static_4; - //~^ ERROR: cannot find function `foo_static` in `S` + reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; + //~^ ERROR: type annotations needed [E0284] + reuse S::foo_self; + //~^ ERROR: mismatched types [E0308] + //~| ERROR: method takes at most 2 generic arguments but 4 generic arguments were supplied [E0107] reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - //~^ ERROR: cannot find function `foo_self` in `S` - //~| ERROR: delegation's target expression is specified for function with no params + reuse S::foo_self::<'static, (), true> as foo_self_2; + //~^ ERROR: mismatched types [E0308] reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } - //~^ ERROR: cannot find function `foo_self` in `S` - //~| ERROR: delegation's target expression is specified for function with no params - reuse S::<(), 1>::foo_self::<'static, _, _> as foo_self_4; - //~^ ERROR: cannot find function `foo_self` in `S` + reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; + //~^ ERROR: mismatched types [E0308] } impl X { + reuse S::foo_static; reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; - //~^ ERROR: cannot find function `foo_static` in `S` + reuse S::foo_static::<'static, (), true> as foo_static_2; reuse S::<(), 1>::foo_static as foo_static_3; - //~^ ERROR: cannot find function `foo_static` in `S` - reuse S::<(), 1>::foo_static::<'static, _, _> as foo_static_4; - //~^ ERROR: cannot find function `foo_static` in `S` + reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; fn get_s(self) -> S<(), 1> { panic!(); } + reuse S::foo_self; + //~^ ERROR: mismatched types [E0308] reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - //~^ ERROR: cannot find function `foo_self` in `S` + reuse S::foo_self::<'static, (), true> as foo_self_2; + //~^ ERROR: mismatched types [E0308] reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } - //~^ ERROR: cannot find function `foo_self` in `S` - reuse S::<(), 1>::foo_self::<'static, _, _> as foo_self_4; - //~^ ERROR: cannot find function `foo_self` in `S` + reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; + //~^ ERROR: mismatched types [E0308] } fn main() {} diff --git a/tests/ui/delegation/inherent-impls-structs.stderr b/tests/ui/delegation/inherent-impls-structs.stderr index 6a426564a6e3a..a92d9061d3dbd 100644 --- a/tests/ui/delegation/inherent-impls-structs.stderr +++ b/tests/ui/delegation/inherent-impls-structs.stderr @@ -1,159 +1,224 @@ -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-structs.rs:12:19 +error[E0308]: mismatched types + --> $DIR/inherent-impls-structs.rs:35:14 | -LL | reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-structs.rs:14:19 +LL | trait Trait<'a, AA, BB> where Self: Sized { + | ----------------------- found this type parameter +... +LL | reuse S::foo_self; + | ^^^^^^^^ + | | + | expected `S`, found type parameter `Self` + | arguments to this function are incorrect + | + = note: expected struct `S` + found type parameter `Self` +note: method defined here + --> $DIR/inherent-impls-structs.rs:9:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- + +error[E0308]: mismatched types + --> $DIR/inherent-impls-structs.rs:38:14 | -LL | reuse S::<(), 1>::foo_static as foo_static_3; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-structs.rs:16:22 +LL | trait Trait<'a, AA, BB> where Self: Sized { + | ----------------------- found this type parameter +... +LL | reuse S::foo_self::<'static, (), true> as foo_self_2; + | ^^^^^^^^ + | | + | expected `S`, found type parameter `Self` + | arguments to this function are incorrect + | + = note: expected struct `S` + found type parameter `Self` +note: method defined here + --> $DIR/inherent-impls-structs.rs:9:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- + +error[E0308]: mismatched types + --> $DIR/inherent-impls-structs.rs:41:22 + | +LL | trait Trait<'a, AA, BB> where Self: Sized { + | ----------------------- found this type parameter +... +LL | reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; + | ^^^^^^^^ + | | + | expected `S`, found type parameter `Self` + | arguments to this function are incorrect + | + = note: expected struct `S` + found type parameter `Self` +note: method defined here + --> $DIR/inherent-impls-structs.rs:9:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- + +error[E0107]: associated function takes at most 2 generic arguments but 4 generic arguments were supplied + --> $DIR/inherent-impls-structs.rs:48:14 + | +LL | reuse S::foo_static; + | ^^^^^^^^^^ + | | + | expected at most 2 generic arguments + | help: remove the unnecessary generic arguments + | +note: associated function defined here, with at most 2 generic parameters: `T`, `B` + --> $DIR/inherent-impls-structs.rs:8:8 + | +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ^^^^^^^^^^ - ------------- + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-structs.rs:51:14 + | +LL | reuse S::foo_static::<'static, (), true> as foo_static_2; + | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` + | +note: required by a const generic parameter in `S` + --> $DIR/inherent-impls-structs.rs:3:13 + | +LL | struct S { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` +help: consider specifying the generic arguments + | +LL | reuse S::::foo_static::<'static, (), true> as foo_static_2; + | ++++++++ + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-structs.rs:55:22 + | +LL | reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; + | ^^^^^^^^^^ cannot infer the value of const parameter `B` declared on the associated function `foo_static` + | +note: required by a const generic parameter in `S::::foo_static` + --> $DIR/inherent-impls-structs.rs:8:34 + | +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` + +error[E0107]: method takes at most 2 generic arguments but 4 generic arguments were supplied + --> $DIR/inherent-impls-structs.rs:58:14 + | +LL | reuse S::foo_self; + | ^^^^^^^^ + | | + | expected at most 2 generic arguments + | help: remove the unnecessary generic arguments | -LL | reuse S::::foo_static::<'static, _, _> as foo_static_4; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-structs.rs:19:19 +note: method defined here, with at most 2 generic parameters: `T`, `B` + --> $DIR/inherent-impls-structs.rs:9:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ - ------------- + +error[E0308]: mismatched types + --> $DIR/inherent-impls-structs.rs:58:14 + | +LL | reuse S::foo_self; + | ^^^^^^^^ + | | + | expected `S<_, _>`, found `X` + | arguments to this function are incorrect | -LL | reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1; - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-structs.rs:21:19 + = note: expected struct `S<_, _>` + found struct `X` +note: method defined here + --> $DIR/inherent-impls-structs.rs:9:8 | -LL | reuse S::<(), 1>::foo_self as foo_self_3; - | ^^^^^^^^ not found in `S` +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-structs.rs:23:23 +error[E0308]: mismatched types + --> $DIR/inherent-impls-structs.rs:62:14 | -LL | reuse S::::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-structs.rs:27:23 +LL | reuse S::foo_self::<'static, (), true> as foo_self_2; + | ^^^^^^^^ + | | + | expected `S<_, _>`, found `X` + | arguments to this function are incorrect | -LL | reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-structs.rs:29:23 + = note: expected struct `S<_, _>` + found struct `X` +note: method defined here + --> $DIR/inherent-impls-structs.rs:9:8 | -LL | reuse S::<(), 1>::foo_static as foo_static_3; - | ^^^^^^^^^^ not found in `S` +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-structs.rs:31:23 +error[E0308]: mismatched types + --> $DIR/inherent-impls-structs.rs:65:22 | -LL | reuse S::<(), 1>::foo_static::<'static, _, _> as foo_static_4; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-structs.rs:38:23 +LL | reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; + | ^^^^^^^^ + | | + | expected `S<_, 1>`, found `X` + | arguments to this function are incorrect | -LL | reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-structs.rs:40:23 + = note: expected struct `S<_, 1>` + found struct `X` +note: method defined here + --> $DIR/inherent-impls-structs.rs:9:8 | -LL | reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } - | ^^^^^^^^ not found in `S` +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-structs.rs:42:23 +error[E0308]: mismatched types + --> $DIR/inherent-impls-structs.rs:80:14 | -LL | reuse S::<(), 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-structs.rs:49:23 +LL | reuse S::foo_self; + | ^^^^^^^^ + | | + | expected `S`, found `X` + | arguments to this function are incorrect | -LL | reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-structs.rs:51:23 + = note: expected struct `S` + found struct `X` +note: method defined here + --> $DIR/inherent-impls-structs.rs:9:8 | -LL | reuse S::<(), 1>::foo_static as foo_static_3; - | ^^^^^^^^^^ not found in `S` +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-structs.rs:53:23 +error[E0308]: mismatched types + --> $DIR/inherent-impls-structs.rs:83:14 | -LL | reuse S::<(), 1>::foo_static::<'static, _, _> as foo_static_4; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-structs.rs:56:23 +LL | reuse S::foo_self::<'static, (), true> as foo_self_2; + | ^^^^^^^^ + | | + | expected `S`, found `X` + | arguments to this function are incorrect | -LL | reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-structs.rs:59:23 + = note: expected struct `S` + found struct `X` +note: method defined here + --> $DIR/inherent-impls-structs.rs:9:8 | -LL | reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } - | ^^^^^^^^ not found in `S` +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-structs.rs:62:23 +error[E0308]: mismatched types + --> $DIR/inherent-impls-structs.rs:86:22 | -LL | reuse S::<(), 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-structs.rs:67:23 - | -LL | reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-structs.rs:69:23 +LL | reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; + | ^^^^^^^^ + | | + | expected `S`, found `X` + | arguments to this function are incorrect | -LL | reuse S::<(), 1>::foo_static as foo_static_3; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-structs.rs:71:23 - | -LL | reuse S::<(), 1>::foo_static::<'static, _, _> as foo_static_4; - | ^^^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-structs.rs:78:23 - | -LL | reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-structs.rs:80:23 - | -LL | reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } - | ^^^^^^^^ not found in `S` - -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-structs.rs:82:23 - | -LL | reuse S::<(), 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ not found in `S` - -error: delegation's target expression is specified for function with no params - --> $DIR/inherent-impls-structs.rs:56:67 - | -LL | reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - | ^^^^^^^^^^^^^^^^ - -error: delegation's target expression is specified for function with no params - --> $DIR/inherent-impls-structs.rs:59:46 - | -LL | reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } - | ^^^^^^^^^^^^^^^^ - -error: aborting due to 26 previous errors - -For more information about this error, try `rustc --explain E0425`. + = note: expected struct `S` + found struct `X` +note: method defined here + --> $DIR/inherent-impls-structs.rs:9:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- + +error: aborting due to 13 previous errors + +Some errors have detailed explanations: E0107, E0284, E0308. +For more information about an error, try `rustc --explain E0107`. diff --git a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs index 8375df5f26587..d38cf95133b60 100644 --- a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs +++ b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs @@ -6,12 +6,14 @@ struct S<'a, A, const C: usize> { impl<'a, 'b, 'c, A, const C: usize> S { //~^ ERROR: implicit elided lifetime not allowed here + fn foo_static<'d: 'd, 'e, T, const B: bool>() {} fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} } trait Trait<'a, AA, BB> where Self: Sized { - reuse S::<(), ()>::foo_self; - //~^ ERROR: cannot find function `foo_self` in `S` + reuse S::foo_self; + //~^ ERROR: failed to generate delegation: mismatch between provided generic args in inherent impl and declared generics + //~| ERROR: this function takes 1 argument but 0 arguments were supplied } fn main() {} diff --git a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr index bfa377dcc2db6..1919688299a40 100644 --- a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr +++ b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr @@ -9,13 +9,29 @@ help: indicate the anonymous lifetime LL | impl<'a, 'b, 'c, A, const C: usize> S<'_, A, C> { | +++ -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-wrong-header-args-ice.rs:13:24 +error: failed to generate delegation: mismatch between provided generic args in inherent impl and declared generics + --> $DIR/inherent-impls-wrong-header-args-ice.rs:14:14 | -LL | reuse S::<(), ()>::foo_self; - | ^^^^^^^^ not found in `S` +LL | reuse S::foo_self; + | ^^^^^^^^ -error: aborting due to 2 previous errors +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-wrong-header-args-ice.rs:14:14 + | +LL | reuse S::foo_self; + | ^^^^^^^^ argument #1 is missing + | +note: method defined here + --> $DIR/inherent-impls-wrong-header-args-ice.rs:10:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse S::foo_self(/* value */); + | +++++++++++++ + +error: aborting due to 3 previous errors -Some errors have detailed explanations: E0425, E0726. -For more information about an error, try `rustc --explain E0425`. +Some errors have detailed explanations: E0061, E0726. +For more information about an error, try `rustc --explain E0061`. diff --git a/tests/ui/parallel-rustc/default-trait-shadow-cycle-issue-151358.stderr b/tests/ui/parallel-rustc/default-trait-shadow-cycle-issue-151358.stderr index 594f6cc66690e..da16e49a777eb 100644 --- a/tests/ui/parallel-rustc/default-trait-shadow-cycle-issue-151358.stderr +++ b/tests/ui/parallel-rustc/default-trait-shadow-cycle-issue-151358.stderr @@ -2,6 +2,7 @@ error: internal compiler error: query cycle when printing cycle detected | = note: ...when getting owner for `Default` = note: ...which requires lowering HIR for `Default`... + = note: ...which requires resolving type relative delegations... = note: ...which requires getting the AST for lowering... = note: ...which requires perform lints prior to AST lowering... = note: ...which requires looking up span for `Default`... @@ -13,6 +14,7 @@ error[E0391]: cycle detected when getting the resolver for lowering | = note: ...which requires getting owner for `Default`... = note: ...which requires lowering HIR for `Default`... + = note: ...which requires resolving type relative delegations... = note: ...which requires getting the AST for lowering... = note: ...which requires perform lints prior to AST lowering... = note: ...which again requires getting the resolver for lowering, completing the cycle diff --git a/tests/ui/query-system/query-cycle-printing-issue-151358.stderr b/tests/ui/query-system/query-cycle-printing-issue-151358.stderr index 594f6cc66690e..da16e49a777eb 100644 --- a/tests/ui/query-system/query-cycle-printing-issue-151358.stderr +++ b/tests/ui/query-system/query-cycle-printing-issue-151358.stderr @@ -2,6 +2,7 @@ error: internal compiler error: query cycle when printing cycle detected | = note: ...when getting owner for `Default` = note: ...which requires lowering HIR for `Default`... + = note: ...which requires resolving type relative delegations... = note: ...which requires getting the AST for lowering... = note: ...which requires perform lints prior to AST lowering... = note: ...which requires looking up span for `Default`... @@ -13,6 +14,7 @@ error[E0391]: cycle detected when getting the resolver for lowering | = note: ...which requires getting owner for `Default`... = note: ...which requires lowering HIR for `Default`... + = note: ...which requires resolving type relative delegations... = note: ...which requires getting the AST for lowering... = note: ...which requires perform lints prior to AST lowering... = note: ...which again requires getting the resolver for lowering, completing the cycle diff --git a/tests/ui/resolve/query-cycle-issue-124901.stderr b/tests/ui/resolve/query-cycle-issue-124901.stderr index 594f6cc66690e..da16e49a777eb 100644 --- a/tests/ui/resolve/query-cycle-issue-124901.stderr +++ b/tests/ui/resolve/query-cycle-issue-124901.stderr @@ -2,6 +2,7 @@ error: internal compiler error: query cycle when printing cycle detected | = note: ...when getting owner for `Default` = note: ...which requires lowering HIR for `Default`... + = note: ...which requires resolving type relative delegations... = note: ...which requires getting the AST for lowering... = note: ...which requires perform lints prior to AST lowering... = note: ...which requires looking up span for `Default`... @@ -13,6 +14,7 @@ error[E0391]: cycle detected when getting the resolver for lowering | = note: ...which requires getting owner for `Default`... = note: ...which requires lowering HIR for `Default`... + = note: ...which requires resolving type relative delegations... = note: ...which requires getting the AST for lowering... = note: ...which requires perform lints prior to AST lowering... = note: ...which again requires getting the resolver for lowering, completing the cycle From 274997f1db52b3afa9882130b8e68ee0f453d263 Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Wed, 12 Aug 2026 10:28:18 +0300 Subject: [PATCH 02/22] Fix tests --- tests/ui/delegation/inherent-impls-enums.rs | 1 - .../ui/delegation/inherent-impls-enums.stderr | 18 +++++++++--------- tests/ui/delegation/inherent-impls-structs.rs | 1 - .../delegation/inherent-impls-structs.stderr | 16 ++++++++-------- 4 files changed, 17 insertions(+), 19 deletions(-) diff --git a/tests/ui/delegation/inherent-impls-enums.rs b/tests/ui/delegation/inherent-impls-enums.rs index 320a7d6fea6db..66ad148dc5acc 100644 --- a/tests/ui/delegation/inherent-impls-enums.rs +++ b/tests/ui/delegation/inherent-impls-enums.rs @@ -55,7 +55,6 @@ impl<'a, A, B> Trait<'a, A, B> for X { reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; reuse S::foo_static::<'static, (), true> as foo_static_2; //~^ ERROR: type annotations needed [E0284] - //~| ERROR: type annotations needed [E0284] reuse S::<'static, (), 1>::foo_static as foo_static_3; reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; //~^ ERROR: type annotations needed [E0284] diff --git a/tests/ui/delegation/inherent-impls-enums.stderr b/tests/ui/delegation/inherent-impls-enums.stderr index ac783ac70ac82..23315e99c5f07 100644 --- a/tests/ui/delegation/inherent-impls-enums.stderr +++ b/tests/ui/delegation/inherent-impls-enums.stderr @@ -106,7 +106,7 @@ LL + reuse S:: as foo_static_2; | error[E0284]: type annotations needed - --> $DIR/inherent-impls-enums.rs:60:26 + --> $DIR/inherent-impls-enums.rs:59:26 | LL | reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; | ^^^^^^^^^^ cannot infer the value of const parameter `B` declared on the associated function `foo_static` @@ -118,7 +118,7 @@ LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} | ^^^^^^^^^^^^^ required by this const generic parameter in `S::<'a, A, C>::foo_static` error[E0107]: method takes 1 lifetime argument but 2 lifetime arguments were supplied - --> $DIR/inherent-impls-enums.rs:63:14 + --> $DIR/inherent-impls-enums.rs:62:14 | LL | reuse S::foo_self; | ^^^^^^^^ @@ -133,7 +133,7 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ -- error[E0107]: method takes at most 2 generic arguments but 4 generic arguments were supplied - --> $DIR/inherent-impls-enums.rs:63:14 + --> $DIR/inherent-impls-enums.rs:62:14 | LL | reuse S::foo_self; | ^^^^^^^^ @@ -148,7 +148,7 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ - ------------- error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:63:14 + --> $DIR/inherent-impls-enums.rs:62:14 | LL | reuse S::foo_self; | ^^^^^^^^ @@ -169,7 +169,7 @@ LL | reuse S::S::A(foo_self); | +++++ + error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:68:14 + --> $DIR/inherent-impls-enums.rs:67:14 | LL | reuse S::foo_self::<'static, (), true> as foo_self_2; | ^^^^^^^^ @@ -190,7 +190,7 @@ LL | reuse S::S::A(foo_self)::<'static, (), true> as foo_self_2; | +++++ + error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:71:26 + --> $DIR/inherent-impls-enums.rs:70:26 | LL | reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; | ^^^^^^^^ @@ -211,7 +211,7 @@ LL | reuse S::<'_, _, 1>::S::A(foo_self)::<'static, _, _> as foo_self_4; | +++++ + error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:86:14 + --> $DIR/inherent-impls-enums.rs:85:14 | LL | reuse S::foo_self; | ^^^^^^^^ @@ -228,7 +228,7 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:89:14 + --> $DIR/inherent-impls-enums.rs:88:14 | LL | reuse S::foo_self::<'static, (), true> as foo_self_2; | ^^^^^^^^ @@ -245,7 +245,7 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:92:26 + --> $DIR/inherent-impls-enums.rs:91:26 | LL | reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; | ^^^^^^^^ diff --git a/tests/ui/delegation/inherent-impls-structs.rs b/tests/ui/delegation/inherent-impls-structs.rs index 5f0b43d9660ba..26c61726a9eda 100644 --- a/tests/ui/delegation/inherent-impls-structs.rs +++ b/tests/ui/delegation/inherent-impls-structs.rs @@ -50,7 +50,6 @@ impl<'a, A, B> Trait<'a, A, B> for X { reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; reuse S::foo_static::<'static, (), true> as foo_static_2; //~^ ERROR: type annotations needed [E0284] - //~| ERROR: type annotations needed [E0284] reuse S::<(), 1>::foo_static as foo_static_3; reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; //~^ ERROR: type annotations needed [E0284] diff --git a/tests/ui/delegation/inherent-impls-structs.stderr b/tests/ui/delegation/inherent-impls-structs.stderr index a92d9061d3dbd..450f01357ee6b 100644 --- a/tests/ui/delegation/inherent-impls-structs.stderr +++ b/tests/ui/delegation/inherent-impls-structs.stderr @@ -90,7 +90,7 @@ LL | reuse S::::foo_static::<'static, (), true> as foo_static_2; | ++++++++ error[E0284]: type annotations needed - --> $DIR/inherent-impls-structs.rs:55:22 + --> $DIR/inherent-impls-structs.rs:54:22 | LL | reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; | ^^^^^^^^^^ cannot infer the value of const parameter `B` declared on the associated function `foo_static` @@ -102,7 +102,7 @@ LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} | ^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` error[E0107]: method takes at most 2 generic arguments but 4 generic arguments were supplied - --> $DIR/inherent-impls-structs.rs:58:14 + --> $DIR/inherent-impls-structs.rs:57:14 | LL | reuse S::foo_self; | ^^^^^^^^ @@ -117,7 +117,7 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ - ------------- error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:58:14 + --> $DIR/inherent-impls-structs.rs:57:14 | LL | reuse S::foo_self; | ^^^^^^^^ @@ -134,7 +134,7 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:62:14 + --> $DIR/inherent-impls-structs.rs:61:14 | LL | reuse S::foo_self::<'static, (), true> as foo_self_2; | ^^^^^^^^ @@ -151,7 +151,7 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:65:22 + --> $DIR/inherent-impls-structs.rs:64:22 | LL | reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; | ^^^^^^^^ @@ -168,7 +168,7 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:80:14 + --> $DIR/inherent-impls-structs.rs:79:14 | LL | reuse S::foo_self; | ^^^^^^^^ @@ -185,7 +185,7 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:83:14 + --> $DIR/inherent-impls-structs.rs:82:14 | LL | reuse S::foo_self::<'static, (), true> as foo_self_2; | ^^^^^^^^ @@ -202,7 +202,7 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:86:22 + --> $DIR/inherent-impls-structs.rs:85:22 | LL | reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; | ^^^^^^^^ From f8727552f273814871ec7665b25fb1d9afcda59b Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Wed, 12 Aug 2026 11:47:00 +0300 Subject: [PATCH 03/22] Better handling of wrong args in inherent impl --- Cargo.lock | 1 - compiler/rustc_ast_lowering/Cargo.toml | 1 - .../src/delegation/resolution.rs | 22 +++++++++---------- .../rustc_ast_lowering/src/diagnostics.rs | 9 -------- .../inherent-impls-wrong-header-args-ice.rs | 3 +-- ...nherent-impls-wrong-header-args-ice.stderr | 8 +------ 6 files changed, 13 insertions(+), 31 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 6d06797b7f8a1..598ea312408f3 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -3634,7 +3634,6 @@ dependencies = [ name = "rustc_ast_lowering" version = "0.0.0" dependencies = [ - "itertools", "rustc_abi", "rustc_ast", "rustc_attr_ir", diff --git a/compiler/rustc_ast_lowering/Cargo.toml b/compiler/rustc_ast_lowering/Cargo.toml index f1abbc3acd820..9dc5f81581e87 100644 --- a/compiler/rustc_ast_lowering/Cargo.toml +++ b/compiler/rustc_ast_lowering/Cargo.toml @@ -8,7 +8,6 @@ doctest = false [dependencies] # tidy-alphabetical-start -itertools = "0.15" rustc_abi = { path = "../rustc_abi" } rustc_ast = { path = "../rustc_ast" } rustc_attr_ir = { path = "../rustc_attr_ir" } diff --git a/compiler/rustc_ast_lowering/src/delegation/resolution.rs b/compiler/rustc_ast_lowering/src/delegation/resolution.rs index 70603c7863f19..58f74aa9f9c98 100644 --- a/compiler/rustc_ast_lowering/src/delegation/resolution.rs +++ b/compiler/rustc_ast_lowering/src/delegation/resolution.rs @@ -10,7 +10,7 @@ use rustc_data_structures::steal::Steal; use rustc_hir as hir; use rustc_middle::ty::{ self, AssocKind, DelegationInhFuncKind, Ty, TyCtxt, TypeRelativeDelegationRes, - TypeSuperVisitable, TypeVisitable, TypeVisitor, + TypeSuperVisitable, TypeVisitable, TypeVisitableExt, TypeVisitor, }; use rustc_span::def_id::{DefId, LocalDefId}; use rustc_span::{ErrorGuaranteed, Span}; @@ -20,8 +20,7 @@ use crate::delegation::resolution::resolver::DelegationResolver; use crate::diagnostics::{ AmbiguousDelegationToInherentImpl, CycleInDelegationSignatureResolution, DelegationAttemptedBlockWithDefsDeletion, DelegationAttemptedBlockWithDefsRelowering, - DelegationBlockSpecifiedWhenNoParams, DelegationGenericsMismatchInInherentImpl, - UnresolvedDelegationCallee, + DelegationBlockSpecifiedWhenNoParams, UnresolvedDelegationCallee, }; pub(crate) fn resolve_type_relative_delegations( @@ -242,6 +241,11 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { Ok((res, self.resolve_and_generate_generics(delegation, sig_id)?)) } + /// See tests\ui\delegation\inherent-impls-wrong-header-args-ice.rs, + /// there might be situations when not all generic args are supplied + /// to a struct/enum in an impl, in this case there will be ICEs when + /// trying to instantiate signature or predicates, so we would emit delayed + /// bug here and will not process this delegation further. fn check_inherent_impl_generic_args( &self, sig_id: DefId, @@ -252,17 +256,13 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { return Ok(()); } - let ty::Adt(def, args) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { + let ty::Adt(_, args) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { unreachable!("parent of inherent function can be only struct or enum") }; - let adt_params = &tcx.generics_of(def.did()).own_params; - let adt_params_types = adt_params.iter().map(|p| p.kind.is_ty_or_const()); - - let actual_args = args.iter().flat_map(|a| a.opt_param_info().map(|a| a.1)); - - itertools::equal(actual_args, adt_params_types) - .ok_or_else(|| tcx.dcx().emit_err(DelegationGenericsMismatchInInherentImpl { span })) + (!args.iter().any(|a| a.references_error())).ok_or_else(|| { + tcx.dcx().span_delayed_bug(span, "incorrect generic args in inherent impl") + }) } fn get_call_path_res( diff --git a/compiler/rustc_ast_lowering/src/diagnostics.rs b/compiler/rustc_ast_lowering/src/diagnostics.rs index 230c3c9a4e7b3..52f9a79307c1c 100644 --- a/compiler/rustc_ast_lowering/src/diagnostics.rs +++ b/compiler/rustc_ast_lowering/src/diagnostics.rs @@ -616,12 +616,3 @@ pub(crate) struct AmbiguousDelegationToInherentImpl { #[primary_span] pub span: Span, } - -#[derive(Diagnostic)] -#[diag( - "failed to generate delegation: mismatch between provided generic args in inherent impl and declared generics" -)] -pub(crate) struct DelegationGenericsMismatchInInherentImpl { - #[primary_span] - pub span: Span, -} diff --git a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs index d38cf95133b60..a618babb16f59 100644 --- a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs +++ b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs @@ -12,8 +12,7 @@ impl<'a, 'b, 'c, A, const C: usize> S { trait Trait<'a, AA, BB> where Self: Sized { reuse S::foo_self; - //~^ ERROR: failed to generate delegation: mismatch between provided generic args in inherent impl and declared generics - //~| ERROR: this function takes 1 argument but 0 arguments were supplied + //~^ ERROR: this function takes 1 argument but 0 arguments were supplied } fn main() {} diff --git a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr index 1919688299a40..cfb9c3e9e1a29 100644 --- a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr +++ b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr @@ -9,12 +9,6 @@ help: indicate the anonymous lifetime LL | impl<'a, 'b, 'c, A, const C: usize> S<'_, A, C> { | +++ -error: failed to generate delegation: mismatch between provided generic args in inherent impl and declared generics - --> $DIR/inherent-impls-wrong-header-args-ice.rs:14:14 - | -LL | reuse S::foo_self; - | ^^^^^^^^ - error[E0061]: this function takes 1 argument but 0 arguments were supplied --> $DIR/inherent-impls-wrong-header-args-ice.rs:14:14 | @@ -31,7 +25,7 @@ help: provide the argument LL | reuse S::foo_self(/* value */); | +++++++++++++ -error: aborting due to 3 previous errors +error: aborting due to 2 previous errors Some errors have detailed explanations: E0061, E0726. For more information about an error, try `rustc --explain E0061`. From ab0e2e18c6d4b2cc0e4aa9f6e95aa27c6606016f Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Wed, 12 Aug 2026 13:08:22 +0300 Subject: [PATCH 04/22] Fix incorrect signature update --- compiler/rustc_hir_analysis/src/delegation.rs | 23 ++++--- .../ui/delegation/inherent-impl-glob-list.rs | 21 +++++++ .../delegation/inherent-impl-glob-list.stderr | 8 +++ .../inherent-impl-receiver-mapping.rs | 38 ++++++++++++ .../inherent-impl-receiver-mapping.stderr | 61 +++++++++++++++++++ .../ui/delegation/inherent-impls-recursive.rs | 2 +- 6 files changed, 144 insertions(+), 9 deletions(-) create mode 100644 tests/ui/delegation/inherent-impl-glob-list.rs create mode 100644 tests/ui/delegation/inherent-impl-glob-list.stderr create mode 100644 tests/ui/delegation/inherent-impl-receiver-mapping.rs create mode 100644 tests/ui/delegation/inherent-impl-receiver-mapping.stderr diff --git a/compiler/rustc_hir_analysis/src/delegation.rs b/compiler/rustc_hir_analysis/src/delegation.rs index 28c8d843642cf..e71c7c098966d 100644 --- a/compiler/rustc_hir_analysis/src/delegation.rs +++ b/compiler/rustc_hir_analysis/src/delegation.rs @@ -630,20 +630,27 @@ fn adjust_sig_in_inherent_impl_cases<'tcx>( let self_input = sig[0]; - sig[0] = match fn_kinds(tcx, def_id, sig_id) { - (FnKind::AssocInherentImpl, FnKind::AssocInherentImpl) => { - tcx.type_of(tcx.parent(def_id.to_def_id())).skip_binder() - } - (FnKind::AssocTrait, FnKind::AssocInherentImpl) => { + let kinds @ (def_kind, _) = fn_kinds(tcx, def_id, sig_id); + + sig[0] = match kinds { + (_, FnKind::AssocInherentImpl) => { let ty::Adt(def, _) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { unreachable!("delegation is supported only to struct or enums") }; let sig_self_type = Ty::new_adt(tcx, *def, tcx.mk_args(parent_args)); - let self_param = Ty::new_param(tcx, 0, kw::SelfUpper); - self_input.replace_inside(tcx, sig_self_type, self_param) + let replacement = match def_kind { + FnKind::AssocTrait => Ty::new_param(tcx, 0, kw::SelfUpper), + FnKind::Free => sig_self_type, + _ => tcx + .type_of(tcx.parent(def_id.to_def_id())) + .instantiate_identity() + .skip_norm_wip(), + }; + + self_input.replace_inside(tcx, sig_self_type, replacement) } - _ => self_input, + _ => sig[0], }; } diff --git a/tests/ui/delegation/inherent-impl-glob-list.rs b/tests/ui/delegation/inherent-impl-glob-list.rs new file mode 100644 index 0000000000000..d983711102dde --- /dev/null +++ b/tests/ui/delegation/inherent-impl-glob-list.rs @@ -0,0 +1,21 @@ +#![feature(fn_delegation)] + +struct X; + +impl X { + fn foo(&self) {} + fn foo2(&self) {} +} + +struct Y; + +impl Y { + reuse X::{foo, foo2} { X } +} + +impl Y { + reuse X::*; + //~^ ERROR: expected trait, found struct `X` +} + +fn main() {} diff --git a/tests/ui/delegation/inherent-impl-glob-list.stderr b/tests/ui/delegation/inherent-impl-glob-list.stderr new file mode 100644 index 0000000000000..f0ecc659d2fba --- /dev/null +++ b/tests/ui/delegation/inherent-impl-glob-list.stderr @@ -0,0 +1,8 @@ +error: expected trait, found struct `X` + --> $DIR/inherent-impl-glob-list.rs:17:11 + | +LL | reuse X::*; + | ^ not a trait + +error: aborting due to 1 previous error + diff --git a/tests/ui/delegation/inherent-impl-receiver-mapping.rs b/tests/ui/delegation/inherent-impl-receiver-mapping.rs new file mode 100644 index 0000000000000..3870a0cd8bb7f --- /dev/null +++ b/tests/ui/delegation/inherent-impl-receiver-mapping.rs @@ -0,0 +1,38 @@ +#![feature(fn_delegation)] + +struct X; + +impl X { + fn static_f() {} + fn by_value(self) {} + fn by_ref(&self) {} + fn by_mut_ref(&mut self) {} +} + +struct Y; + +impl Y { + fn get_x(&self) -> X { X } + reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } +} + +fn main() { + let y = Y; + y.by_ref(); + y.by_mut_ref(); + //~^ ERROR: cannot borrow `y` as mutable, as it is not declared as mutable + y.by_value(); + + let y = &Y; + y.by_value(); + //~^ ERROR: cannot move out of `*y` which is behind a shared reference + y.by_ref(); + y.by_mut_ref(); + //~^ ERROR: cannot borrow `*y` as mutable, as it is behind a `&` reference + + let y = &mut Y; + y.by_value(); + //~^ ERROR: cannot move out of `*y` which is behind a mutable reference + y.by_ref(); + y.by_mut_ref(); +} diff --git a/tests/ui/delegation/inherent-impl-receiver-mapping.stderr b/tests/ui/delegation/inherent-impl-receiver-mapping.stderr new file mode 100644 index 0000000000000..74899d9fb6e8a --- /dev/null +++ b/tests/ui/delegation/inherent-impl-receiver-mapping.stderr @@ -0,0 +1,61 @@ +error[E0596]: cannot borrow `y` as mutable, as it is not declared as mutable + --> $DIR/inherent-impl-receiver-mapping.rs:22:5 + | +LL | y.by_mut_ref(); + | ^ cannot borrow as mutable + | +help: consider changing this to be mutable + | +LL | let mut y = Y; + | +++ + +error[E0507]: cannot move out of `*y` which is behind a shared reference + --> $DIR/inherent-impl-receiver-mapping.rs:27:5 + | +LL | y.by_value(); + | ^ ---------- `*y` moved due to this method call + | | + | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait + | + = note: `Y::by_value` takes ownership of the receiver `self`, which moves `*y` +note: if `Y` implemented `Clone`, you could clone the value + --> $DIR/inherent-impl-receiver-mapping.rs:12:1 + | +LL | struct Y; + | ^^^^^^^^ consider implementing `Clone` for this type +... +LL | y.by_value(); + | - you could clone this value + +error[E0596]: cannot borrow `*y` as mutable, as it is behind a `&` reference + --> $DIR/inherent-impl-receiver-mapping.rs:30:5 + | +LL | y.by_mut_ref(); + | ^ `y` is a `&` reference, so it cannot be borrowed as mutable + | +help: consider changing this to be a mutable reference + | +LL | let y = &mut Y; + | +++ + +error[E0507]: cannot move out of `*y` which is behind a mutable reference + --> $DIR/inherent-impl-receiver-mapping.rs:34:5 + | +LL | y.by_value(); + | ^ ---------- `*y` moved due to this method call + | | + | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait + | +note: if `Y` implemented `Clone`, you could clone the value + --> $DIR/inherent-impl-receiver-mapping.rs:12:1 + | +LL | struct Y; + | ^^^^^^^^ consider implementing `Clone` for this type +... +LL | y.by_value(); + | - you could clone this value + +error: aborting due to 4 previous errors + +Some errors have detailed explanations: E0507, E0596. +For more information about an error, try `rustc --explain E0507`. diff --git a/tests/ui/delegation/inherent-impls-recursive.rs b/tests/ui/delegation/inherent-impls-recursive.rs index b8a0ac314f559..7d86cf93a4660 100644 --- a/tests/ui/delegation/inherent-impls-recursive.rs +++ b/tests/ui/delegation/inherent-impls-recursive.rs @@ -44,7 +44,7 @@ mod test_2 { } impl Trait1 for S3 { - reuse S2::foo { S2(S1(())) } + reuse S2::foo { &S2(S1(())) } } trait Trait2 { From d2f4ce2118dcc4cd446c0b95e8dcb0543f1892cd Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Wed, 12 Aug 2026 13:39:37 +0300 Subject: [PATCH 05/22] Cleanups + add test for self type mapping in inherent impls --- compiler/rustc_hir_analysis/src/delegation.rs | 2 +- compiler/rustc_middle/src/ty/sty.rs | 2 +- .../inherent-impl-receiver-mapping.rs | 83 ++++++++++++------- .../inherent-impl-receiver-mapping.stderr | 82 ++++++++++-------- 4 files changed, 103 insertions(+), 66 deletions(-) diff --git a/compiler/rustc_hir_analysis/src/delegation.rs b/compiler/rustc_hir_analysis/src/delegation.rs index e71c7c098966d..7d78d947573cc 100644 --- a/compiler/rustc_hir_analysis/src/delegation.rs +++ b/compiler/rustc_hir_analysis/src/delegation.rs @@ -648,7 +648,7 @@ fn adjust_sig_in_inherent_impl_cases<'tcx>( .skip_norm_wip(), }; - self_input.replace_inside(tcx, sig_self_type, replacement) + self_input.replace(tcx, sig_self_type, replacement) } _ => sig[0], }; diff --git a/compiler/rustc_middle/src/ty/sty.rs b/compiler/rustc_middle/src/ty/sty.rs index e9782a942de6f..b2a84acc2fdfa 100644 --- a/compiler/rustc_middle/src/ty/sty.rs +++ b/compiler/rustc_middle/src/ty/sty.rs @@ -1552,7 +1552,7 @@ impl<'tcx> Ty<'tcx> { cf.is_break() } - pub fn replace_inside( + pub fn replace( self, tcx: TyCtxt<'tcx>, to_replace: Ty<'tcx>, diff --git a/tests/ui/delegation/inherent-impl-receiver-mapping.rs b/tests/ui/delegation/inherent-impl-receiver-mapping.rs index 3870a0cd8bb7f..476fb2075d280 100644 --- a/tests/ui/delegation/inherent-impl-receiver-mapping.rs +++ b/tests/ui/delegation/inherent-impl-receiver-mapping.rs @@ -1,38 +1,61 @@ #![feature(fn_delegation)] -struct X; +mod receiver_mapping { + struct X; -impl X { - fn static_f() {} - fn by_value(self) {} - fn by_ref(&self) {} - fn by_mut_ref(&mut self) {} -} + impl X { + fn static_f() {} + fn by_value(self) {} + fn by_ref(&self) {} + fn by_mut_ref(&mut self) {} + } + + struct Y; + + impl Y { + fn get_x(&self) -> X { X } + reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } + } + + fn check() { + let y = Y; + y.by_ref(); + y.by_mut_ref(); + //~^ ERROR: cannot borrow `y` as mutable, as it is not declared as mutable + y.by_value(); -struct Y; + let y = &Y; + y.by_value(); + //~^ ERROR: cannot move out of `*y` which is behind a shared reference + y.by_ref(); + y.by_mut_ref(); + //~^ ERROR: cannot borrow `*y` as mutable, as it is behind a `&` reference -impl Y { - fn get_x(&self) -> X { X } - reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } + let y = &mut Y; + y.by_value(); + //~^ ERROR: cannot move out of `*y` which is behind a mutable reference + y.by_ref(); + y.by_mut_ref(); + } } -fn main() { - let y = Y; - y.by_ref(); - y.by_mut_ref(); - //~^ ERROR: cannot borrow `y` as mutable, as it is not declared as mutable - y.by_value(); - - let y = &Y; - y.by_value(); - //~^ ERROR: cannot move out of `*y` which is behind a shared reference - y.by_ref(); - y.by_mut_ref(); - //~^ ERROR: cannot borrow `*y` as mutable, as it is behind a `&` reference - - let y = &mut Y; - y.by_value(); - //~^ ERROR: cannot move out of `*y` which is behind a mutable reference - y.by_ref(); - y.by_mut_ref(); +mod self_type_mapping { + struct X; + impl X { + fn add(self, other: Self) -> Self { + Self + } + } + + struct W(X); + impl W { + reuse X::add { self.0 } + } + + fn check() { + W(X).add(W(X)); + //~^ ERROR: mismatched types + } } + +fn main() {} diff --git a/tests/ui/delegation/inherent-impl-receiver-mapping.stderr b/tests/ui/delegation/inherent-impl-receiver-mapping.stderr index 74899d9fb6e8a..7c17f62321040 100644 --- a/tests/ui/delegation/inherent-impl-receiver-mapping.stderr +++ b/tests/ui/delegation/inherent-impl-receiver-mapping.stderr @@ -1,61 +1,75 @@ +error[E0308]: mismatched types + --> $DIR/inherent-impl-receiver-mapping.rs:56:18 + | +LL | W(X).add(W(X)); + | --- ^^^^ expected `X`, found `W` + | | + | arguments to this method are incorrect + | +note: method defined here + --> $DIR/inherent-impl-receiver-mapping.rs:52:18 + | +LL | reuse X::add { self.0 } + | ^^^ + error[E0596]: cannot borrow `y` as mutable, as it is not declared as mutable - --> $DIR/inherent-impl-receiver-mapping.rs:22:5 + --> $DIR/inherent-impl-receiver-mapping.rs:23:9 | -LL | y.by_mut_ref(); - | ^ cannot borrow as mutable +LL | y.by_mut_ref(); + | ^ cannot borrow as mutable | help: consider changing this to be mutable | -LL | let mut y = Y; - | +++ +LL | let mut y = Y; + | +++ error[E0507]: cannot move out of `*y` which is behind a shared reference - --> $DIR/inherent-impl-receiver-mapping.rs:27:5 + --> $DIR/inherent-impl-receiver-mapping.rs:28:9 | -LL | y.by_value(); - | ^ ---------- `*y` moved due to this method call - | | - | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait +LL | y.by_value(); + | ^ ---------- `*y` moved due to this method call + | | + | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait | - = note: `Y::by_value` takes ownership of the receiver `self`, which moves `*y` + = note: `receiver_mapping::Y::by_value` takes ownership of the receiver `self`, which moves `*y` note: if `Y` implemented `Clone`, you could clone the value - --> $DIR/inherent-impl-receiver-mapping.rs:12:1 + --> $DIR/inherent-impl-receiver-mapping.rs:13:5 | -LL | struct Y; - | ^^^^^^^^ consider implementing `Clone` for this type +LL | struct Y; + | ^^^^^^^^ consider implementing `Clone` for this type ... -LL | y.by_value(); - | - you could clone this value +LL | y.by_value(); + | - you could clone this value error[E0596]: cannot borrow `*y` as mutable, as it is behind a `&` reference - --> $DIR/inherent-impl-receiver-mapping.rs:30:5 + --> $DIR/inherent-impl-receiver-mapping.rs:31:9 | -LL | y.by_mut_ref(); - | ^ `y` is a `&` reference, so it cannot be borrowed as mutable +LL | y.by_mut_ref(); + | ^ `y` is a `&` reference, so it cannot be borrowed as mutable | help: consider changing this to be a mutable reference | -LL | let y = &mut Y; - | +++ +LL | let y = &mut Y; + | +++ error[E0507]: cannot move out of `*y` which is behind a mutable reference - --> $DIR/inherent-impl-receiver-mapping.rs:34:5 + --> $DIR/inherent-impl-receiver-mapping.rs:35:9 | -LL | y.by_value(); - | ^ ---------- `*y` moved due to this method call - | | - | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait +LL | y.by_value(); + | ^ ---------- `*y` moved due to this method call + | | + | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait | note: if `Y` implemented `Clone`, you could clone the value - --> $DIR/inherent-impl-receiver-mapping.rs:12:1 + --> $DIR/inherent-impl-receiver-mapping.rs:13:5 | -LL | struct Y; - | ^^^^^^^^ consider implementing `Clone` for this type +LL | struct Y; + | ^^^^^^^^ consider implementing `Clone` for this type ... -LL | y.by_value(); - | - you could clone this value +LL | y.by_value(); + | - you could clone this value -error: aborting due to 4 previous errors +error: aborting due to 5 previous errors -Some errors have detailed explanations: E0507, E0596. -For more information about an error, try `rustc --explain E0507`. +Some errors have detailed explanations: E0308, E0507, E0596. +For more information about an error, try `rustc --explain E0308`. From 64cac60e19070ee41408d8d5a4c479dc0937fa74 Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Thu, 13 Aug 2026 08:58:41 +0300 Subject: [PATCH 06/22] Force specification of parent generics in inherent impls --- .../src/delegation/generics.rs | 35 +- .../src/delegation/resolution.rs | 32 +- .../rustc_ast_lowering/src/diagnostics.rs | 7 + .../inherent-impl-mixed-generics.rs | 17 + .../inherent-impl-mixed-generics.stderr | 25 ++ tests/ui/delegation/inherent-impls-enums.rs | 27 -- .../ui/delegation/inherent-impls-enums.stderr | 207 +---------- .../delegation/inherent-impls-generics.stderr | 296 ++++++++++++++++ .../inherent-impls-parent-generics.rs | 55 ++- .../inherent-impls-parent-generics.stderr | 327 +++++++++++++----- tests/ui/delegation/inherent-impls-structs.rs | 25 -- .../delegation/inherent-impls-structs.stderr | 168 +-------- .../inherent-impls-wrong-header-args-ice.rs | 1 - ...nherent-impls-wrong-header-args-ice.stderr | 4 +- 14 files changed, 692 insertions(+), 534 deletions(-) create mode 100644 tests/ui/delegation/inherent-impl-mixed-generics.rs create mode 100644 tests/ui/delegation/inherent-impl-mixed-generics.stderr create mode 100644 tests/ui/delegation/inherent-impls-generics.stderr diff --git a/compiler/rustc_ast_lowering/src/delegation/generics.rs b/compiler/rustc_ast_lowering/src/delegation/generics.rs index f40d66b2476b1..05cedfb9badd1 100644 --- a/compiler/rustc_ast_lowering/src/delegation/generics.rs +++ b/compiler/rustc_ast_lowering/src/delegation/generics.rs @@ -11,7 +11,9 @@ use rustc_span::{ErrorGuaranteed, Ident, Span, sym}; use crate::LoweringContext; use crate::delegation::resolution::resolver::DelegationResolver; -use crate::diagnostics::DelegationInfersMismatch; +use crate::diagnostics::{ + DelegationInfersMismatch, DelegationToInherentImplMustContainParentGenerics, +}; #[derive(Debug, Clone, Copy, Eq, PartialEq)] pub(super) enum GenericsPosition { @@ -359,6 +361,7 @@ impl<'hir> DelegationResolver<'_, 'hir> { &self, delegation: &Delegation, sig_id: DefId, + span: Span, ) -> Result, ErrorGuaranteed> { let res @ GenericsResolution { trait_impl, @@ -386,6 +389,8 @@ impl<'hir> DelegationResolver<'_, 'hir> { return Ok(GenericsGenerationResults { parent, child, self_ty_propagation_kind: None }); } + self.check_delegation_to_inherent_impl(&res.parent_args, sig_id, span)?; + let tcx = self.tcx(); let skip_self = !generate_self && tcx.def_kind(tcx.parent(sig_id)) == DefKind::Trait; let parent_generics = match res.parent_args { @@ -448,6 +453,34 @@ impl<'hir> DelegationResolver<'_, 'hir> { }) } + fn check_delegation_to_inherent_impl( + &self, + parent_args: &ParentSegmentArgs<'_>, + sig_id: DefId, + span: Span, + ) -> Result<(), ErrorGuaranteed> { + if !self.is_delegation_to_inherent_impl(sig_id) { + return Ok(()); + } + + let tcx = self.tcx(); + match parent_args { + ParentSegmentArgs::Specified(..) => Ok(()), + ParentSegmentArgs::Invalid => unreachable!(), + ParentSegmentArgs::NotSpecified => { + let Some((did, _)) = self.opt_inherent_impl_adt(sig_id) else { unreachable!() }; + + match tcx.generics_of(did).own_params.len() { + 0 => Ok(()), + _ => Err(self + .tcx() + .dcx() + .emit_err(DelegationToInherentImplMustContainParentGenerics { span })), + } + } + } + } + /// Generates generic argument slots for user-specified `args` and /// generic `params` of the signature function. This function checks whether /// there are infers (`kw::UnderscoreLifetime` or `kw::Underscore`) in diff --git a/compiler/rustc_ast_lowering/src/delegation/resolution.rs b/compiler/rustc_ast_lowering/src/delegation/resolution.rs index 58f74aa9f9c98..f953079f0f90f 100644 --- a/compiler/rustc_ast_lowering/src/delegation/resolution.rs +++ b/compiler/rustc_ast_lowering/src/delegation/resolution.rs @@ -238,7 +238,7 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { )?, }; - Ok((res, self.resolve_and_generate_generics(delegation, sig_id)?)) + Ok((res, self.resolve_and_generate_generics(delegation, sig_id, span)?)) } /// See tests\ui\delegation\inherent-impls-wrong-header-args-ice.rs, @@ -251,18 +251,36 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { sig_id: DefId, span: Span, ) -> Result<(), ErrorGuaranteed> { + self.opt_inherent_impl_adt(sig_id) + .map(|(_, args)| { + (!args.iter().any(|a| a.references_error())).ok_or_else(|| { + self.tcx() + .dcx() + .span_delayed_bug(span, "incorrect generic args in inherent impl") + }) + }) + .unwrap_or(Ok(())) + } + + pub(super) fn opt_inherent_impl_adt( + &self, + sig_id: DefId, + ) -> Option<(DefId, ty::GenericArgsRef<'tcx>)> { let tcx = self.tcx(); - if !matches!(tcx.def_kind(tcx.parent(sig_id)), DefKind::Impl { of_trait: false }) { - return Ok(()); + if !self.is_delegation_to_inherent_impl(sig_id) { + return None; } - let ty::Adt(_, args) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { + let ty::Adt(def, args) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { unreachable!("parent of inherent function can be only struct or enum") }; - (!args.iter().any(|a| a.references_error())).ok_or_else(|| { - tcx.dcx().span_delayed_bug(span, "incorrect generic args in inherent impl") - }) + Some((def.did(), args)) + } + + pub(super) fn is_delegation_to_inherent_impl(&self, sig_id: DefId) -> bool { + let tcx = self.tcx(); + matches!(tcx.def_kind(tcx.parent(sig_id)), DefKind::Impl { of_trait: false }) } fn get_call_path_res( diff --git a/compiler/rustc_ast_lowering/src/diagnostics.rs b/compiler/rustc_ast_lowering/src/diagnostics.rs index 52f9a79307c1c..b5fa908d1483b 100644 --- a/compiler/rustc_ast_lowering/src/diagnostics.rs +++ b/compiler/rustc_ast_lowering/src/diagnostics.rs @@ -616,3 +616,10 @@ pub(crate) struct AmbiguousDelegationToInherentImpl { #[primary_span] pub span: Span, } + +#[derive(Diagnostic)] +#[diag("delegation to inherent impl must contain parent generics")] +pub(crate) struct DelegationToInherentImplMustContainParentGenerics { + #[primary_span] + pub span: Span, +} diff --git a/tests/ui/delegation/inherent-impl-mixed-generics.rs b/tests/ui/delegation/inherent-impl-mixed-generics.rs new file mode 100644 index 0000000000000..b24acff6187eb --- /dev/null +++ b/tests/ui/delegation/inherent-impl-mixed-generics.rs @@ -0,0 +1,17 @@ +#![feature(fn_delegation)] + +struct S<'a, A, B, const C: usize> { + xd: &'a [(A, B); C], +} + +impl<'a, 'b, 'c, A, const C: usize> S<'static, A, usize, C> { + fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} +} + +trait Trait<'a, AA, BB> where Self: Sized { + reuse S::foo_self; + //~^ ERROR: delegation to inherent impl must contain parent generics + //~| ERROR: this function takes 1 argument but 0 arguments were supplied +} + +fn main() {} diff --git a/tests/ui/delegation/inherent-impl-mixed-generics.stderr b/tests/ui/delegation/inherent-impl-mixed-generics.stderr new file mode 100644 index 0000000000000..33e63e606f00f --- /dev/null +++ b/tests/ui/delegation/inherent-impl-mixed-generics.stderr @@ -0,0 +1,25 @@ +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impl-mixed-generics.rs:12:14 + | +LL | reuse S::foo_self; + | ^^^^^^^^ + +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impl-mixed-generics.rs:12:14 + | +LL | reuse S::foo_self; + | ^^^^^^^^ argument #1 of type `S<'static, _, usize, _>` is missing + | +note: method defined here + --> $DIR/inherent-impl-mixed-generics.rs:8:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse S::foo_self(/* value */); + | +++++++++++++ + +error: aborting due to 2 previous errors + +For more information about this error, try `rustc --explain E0061`. diff --git a/tests/ui/delegation/inherent-impls-enums.rs b/tests/ui/delegation/inherent-impls-enums.rs index 66ad148dc5acc..0e32a9aa2e44d 100644 --- a/tests/ui/delegation/inherent-impls-enums.rs +++ b/tests/ui/delegation/inherent-impls-enums.rs @@ -10,15 +10,11 @@ impl<'a, 'b, 'c, A: 'a, const C: usize> S<'a, A, C> { fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} } -reuse S::foo_static; reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; -reuse S::foo_static::<'static, (), true> as foo_static_2; reuse S::<'static, (), 1>::foo_static as foo_static_3; reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; -reuse S::foo_self; reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1; -reuse S::foo_self::<'static, (), true> as foo_self_2; reuse S::<'static, (), 1>::foo_self as foo_self_3; reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; @@ -26,9 +22,7 @@ trait Trait<'a, AA, BB> where Self: Sized, { - reuse S::foo_static; reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; - reuse S::foo_static::<'static, (), true> as foo_static_2; reuse S::<'static, (), 1>::foo_static as foo_static_3; reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; @@ -36,11 +30,7 @@ where panic!(); } - reuse S::foo_self; - //~^ ERROR: mismatched types [E0308] reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - reuse S::foo_self::<'static, (), true> as foo_self_2; - //~^ ERROR: mismatched types [E0308] reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; //~^ ERROR: mismatched types [E0308] @@ -49,32 +39,19 @@ where struct X; impl<'a, A, B> Trait<'a, A, B> for X { - reuse S::foo_static; - //~^ ERROR: associated function takes at most 2 generic arguments but 4 generic arguments were supplied [E0107] - //~| ERROR: associated function takes 1 lifetime argument but 2 lifetime arguments were supplied reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; - reuse S::foo_static::<'static, (), true> as foo_static_2; - //~^ ERROR: type annotations needed [E0284] reuse S::<'static, (), 1>::foo_static as foo_static_3; reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; //~^ ERROR: type annotations needed [E0284] - reuse S::foo_self; - //~^ ERROR: mismatched types [E0308] - //~| ERROR: method takes at most 2 generic arguments but 4 generic arguments were supplied - //~| ERROR: method takes 1 lifetime argument but 2 lifetime arguments were supplied reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - reuse S::foo_self::<'static, (), true> as foo_self_2; - //~^ ERROR: mismatched types [E0308] reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; //~^ ERROR: mismatched types [E0308] } impl X { - reuse S::foo_static; reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; - reuse S::foo_static::<'static, (), true> as foo_static_2; reuse S::<'static, (), 1>::foo_static as foo_static_3; reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; @@ -82,11 +59,7 @@ impl X { panic!(); } - reuse S::foo_self; - //~^ ERROR: mismatched types [E0308] reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - reuse S::foo_self::<'static, (), true> as foo_self_2; - //~^ ERROR: mismatched types [E0308] reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; //~^ ERROR: mismatched types [E0308] diff --git a/tests/ui/delegation/inherent-impls-enums.stderr b/tests/ui/delegation/inherent-impls-enums.stderr index 23315e99c5f07..b0de16aab5db7 100644 --- a/tests/ui/delegation/inherent-impls-enums.stderr +++ b/tests/ui/delegation/inherent-impls-enums.stderr @@ -1,45 +1,5 @@ error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:39:14 - | -LL | trait Trait<'a, AA, BB> - | ----------------------- found this type parameter -... -LL | reuse S::foo_self; - | ^^^^^^^^ - | | - | expected `S<'_, A, C>`, found type parameter `Self` - | arguments to this function are incorrect - | - = note: expected enum `S<'_, A, C>` - found type parameter `Self` -note: method defined here - --> $DIR/inherent-impls-enums.rs:10:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- - -error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:42:14 - | -LL | trait Trait<'a, AA, BB> - | ----------------------- found this type parameter -... -LL | reuse S::foo_self::<'static, (), true> as foo_self_2; - | ^^^^^^^^ - | | - | expected `S<'_, A, C>`, found type parameter `Self` - | arguments to this function are incorrect - | - = note: expected enum `S<'_, A, C>` - found type parameter `Self` -note: method defined here - --> $DIR/inherent-impls-enums.rs:10:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- - -error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:45:26 + --> $DIR/inherent-impls-enums.rs:35:26 | LL | trait Trait<'a, AA, BB> | ----------------------- found this type parameter @@ -58,55 +18,8 @@ note: method defined here LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- -error[E0107]: associated function takes 1 lifetime argument but 2 lifetime arguments were supplied - --> $DIR/inherent-impls-enums.rs:52:14 - | -LL | reuse S::foo_static; - | ^^^^^^^^^^ - | | - | expected 1 lifetime argument - | help: remove the lifetime argument - | -note: associated function defined here, with 1 lifetime parameter: `'d` - --> $DIR/inherent-impls-enums.rs:9:8 - | -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ^^^^^^^^^^ -- - -error[E0107]: associated function takes at most 2 generic arguments but 4 generic arguments were supplied - --> $DIR/inherent-impls-enums.rs:52:14 - | -LL | reuse S::foo_static; - | ^^^^^^^^^^ - | | - | expected at most 2 generic arguments - | help: remove the unnecessary generic arguments - | -note: associated function defined here, with at most 2 generic parameters: `T`, `B` - --> $DIR/inherent-impls-enums.rs:9:8 - | -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ^^^^^^^^^^ - ------------- - error[E0284]: type annotations needed - --> $DIR/inherent-impls-enums.rs:56:14 - | -LL | reuse S::foo_static::<'static, (), true> as foo_static_2; - | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `S` - | -note: required by a const generic parameter in `S` - --> $DIR/inherent-impls-enums.rs:3:23 - | -LL | enum S<'a: 'a, A: 'a, const C: usize> { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` -help: consider specifying the generic arguments - | -LL - reuse S::foo_static::<'static, (), true> as foo_static_2; -LL + reuse S:: as foo_static_2; - | - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-enums.rs:59:26 + --> $DIR/inherent-impls-enums.rs:44:26 | LL | reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; | ^^^^^^^^^^ cannot infer the value of const parameter `B` declared on the associated function `foo_static` @@ -117,80 +30,8 @@ note: required by a const generic parameter in `S::<'a, A, C>::foo_static` LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} | ^^^^^^^^^^^^^ required by this const generic parameter in `S::<'a, A, C>::foo_static` -error[E0107]: method takes 1 lifetime argument but 2 lifetime arguments were supplied - --> $DIR/inherent-impls-enums.rs:62:14 - | -LL | reuse S::foo_self; - | ^^^^^^^^ - | | - | expected 1 lifetime argument - | help: remove the lifetime argument - | -note: method defined here, with 1 lifetime parameter: `'d` - --> $DIR/inherent-impls-enums.rs:10:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ -- - -error[E0107]: method takes at most 2 generic arguments but 4 generic arguments were supplied - --> $DIR/inherent-impls-enums.rs:62:14 - | -LL | reuse S::foo_self; - | ^^^^^^^^ - | | - | expected at most 2 generic arguments - | help: remove the unnecessary generic arguments - | -note: method defined here, with at most 2 generic parameters: `T`, `B` - --> $DIR/inherent-impls-enums.rs:10:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ - ------------- - error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:62:14 - | -LL | reuse S::foo_self; - | ^^^^^^^^ - | | - | expected `S<'_, _, _>`, found `X` - | arguments to this function are incorrect - | - = note: expected enum `S<'_, _, _>` - found struct `X` -note: method defined here - --> $DIR/inherent-impls-enums.rs:10:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- -help: try wrapping the expression in `S::A` - | -LL | reuse S::S::A(foo_self); - | +++++ + - -error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:67:14 - | -LL | reuse S::foo_self::<'static, (), true> as foo_self_2; - | ^^^^^^^^ - | | - | expected `S<'_, _, _>`, found `X` - | arguments to this function are incorrect - | - = note: expected enum `S<'_, _, _>` - found struct `X` -note: method defined here - --> $DIR/inherent-impls-enums.rs:10:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- -help: try wrapping the expression in `S::A` - | -LL | reuse S::S::A(foo_self)::<'static, (), true> as foo_self_2; - | +++++ + - -error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:70:26 + --> $DIR/inherent-impls-enums.rs:49:26 | LL | reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; | ^^^^^^^^ @@ -211,41 +52,7 @@ LL | reuse S::<'_, _, 1>::S::A(foo_self)::<'static, _, _> as foo_self_4; | +++++ + error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:85:14 - | -LL | reuse S::foo_self; - | ^^^^^^^^ - | | - | expected `S<'_, A, C>`, found `X` - | arguments to this function are incorrect - | - = note: expected enum `S<'_, A, C>` - found struct `X` -note: method defined here - --> $DIR/inherent-impls-enums.rs:10:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- - -error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:88:14 - | -LL | reuse S::foo_self::<'static, (), true> as foo_self_2; - | ^^^^^^^^ - | | - | expected `S<'_, A, C>`, found `X` - | arguments to this function are incorrect - | - = note: expected enum `S<'_, A, C>` - found struct `X` -note: method defined here - --> $DIR/inherent-impls-enums.rs:10:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- - -error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:91:26 + --> $DIR/inherent-impls-enums.rs:64:26 | LL | reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; | ^^^^^^^^ @@ -261,7 +68,7 @@ note: method defined here LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- -error: aborting due to 15 previous errors +error: aborting due to 4 previous errors -Some errors have detailed explanations: E0107, E0284, E0308. -For more information about an error, try `rustc --explain E0107`. +Some errors have detailed explanations: E0284, E0308. +For more information about an error, try `rustc --explain E0284`. diff --git a/tests/ui/delegation/inherent-impls-generics.stderr b/tests/ui/delegation/inherent-impls-generics.stderr new file mode 100644 index 0000000000000..f9a14310ec52e --- /dev/null +++ b/tests/ui/delegation/inherent-impls-generics.stderr @@ -0,0 +1,296 @@ +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-generics.rs:16:10 + | +LL | reuse E::foo_static as e; + | ^^^^^^^^^^ + +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-generics.rs:21:10 + | +LL | reuse E::foo_self as e1; + | ^^^^^^^^ + +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-generics.rs:25:10 + | +LL | reuse E::foo_static::<'static, (), true> as e2; + | ^^^^^^^^^^ + +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-generics.rs:29:10 + | +LL | reuse E::foo_self::<'static, (), true> as e3; + | ^^^^^^^^ + +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-generics.rs:48:10 + | +LL | reuse S::foo_static as s; + | ^^^^^^^^^^ + +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-generics.rs:53:10 + | +LL | reuse S::foo_self as s1; + | ^^^^^^^^ + +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-generics.rs:57:10 + | +LL | reuse S::foo_static::<'static, (), true> as s2; + | ^^^^^^^^^^ + +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-generics.rs:61:10 + | +LL | reuse S::foo_self::<'static, (), true> as s3; + | ^^^^^^^^ + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-generics.rs:16:10 + | +LL | reuse E::foo_static as e; + | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` + | | + | type must be known at this point + | +note: required by a const generic parameter in `E` + --> $DIR/inherent-impls-generics.rs:6:23 + | +LL | enum E<'a: 'a, A: 'a, const C: usize> { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `E` +help: consider specifying the generic arguments + | +LL - reuse E::foo_static as e; +LL + reuse E:: as e; + | + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-generics.rs:16:10 + | +LL | reuse E::foo_static as e; + | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` + | +note: required by a const generic parameter in `E::<'a, A, C>::foo_static` + --> $DIR/inherent-impls-generics.rs:11:25 + | +LL | impl<'a, 'b, 'c, A: 'a, const C: usize> E<'a, A, C> { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ---------- required by a bound in this associated function +help: consider specifying the generic arguments + | +LL - reuse E::foo_static as e; +LL + reuse E:: as e; + | + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-generics.rs:16:10 + | +LL | reuse E::foo_static as e; + | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` + | +note: required by a const generic parameter in `E::<'a, A, C>::foo_static` + --> $DIR/inherent-impls-generics.rs:12:34 + | +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` +help: consider specifying the generic arguments + | +LL | reuse E::foo_static:: as e; + | ++++++++ + +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-generics.rs:21:10 + | +LL | reuse E::foo_self as e1; + | ^^^^^^^^ argument #1 of type `E<'_, _, _>` is missing + | +note: method defined here + --> $DIR/inherent-impls-generics.rs:13:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse E::foo_self(/* value */) as e1; + | +++++++++++++ + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-generics.rs:25:10 + | +LL | reuse E::foo_static::<'static, (), true> as e2; + | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` + | | + | type must be known at this point + | +note: required by a const generic parameter in `E` + --> $DIR/inherent-impls-generics.rs:6:23 + | +LL | enum E<'a: 'a, A: 'a, const C: usize> { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `E` +help: consider specifying the generic arguments + | +LL - reuse E::foo_static::<'static, (), true> as e2; +LL + reuse E:: as e2; + | + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-generics.rs:25:10 + | +LL | reuse E::foo_static::<'static, (), true> as e2; + | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` + | +note: required by a const generic parameter in `E::<'a, A, C>::foo_static` + --> $DIR/inherent-impls-generics.rs:11:25 + | +LL | impl<'a, 'b, 'c, A: 'a, const C: usize> E<'a, A, C> { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ---------- required by a bound in this associated function +help: consider specifying the generic arguments + | +LL - reuse E::foo_static::<'static, (), true> as e2; +LL + reuse E:: as e2; + | + +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-generics.rs:29:10 + | +LL | reuse E::foo_self::<'static, (), true> as e3; + | ^^^^^^^^ argument #1 of type `E<'_, _, _>` is missing + | +note: method defined here + --> $DIR/inherent-impls-generics.rs:13:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse E::foo_self(/* value */)::<'static, (), true> as e3; + | +++++++++++++ + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-generics.rs:48:10 + | +LL | reuse S::foo_static as s; + | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` + | | + | type must be known at this point + | +note: required by a const generic parameter in `S` + --> $DIR/inherent-impls-generics.rs:39:13 + | +LL | struct S { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` +help: consider specifying the generic arguments + | +LL | reuse S::::foo_static as s; + | ++++++++ + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-generics.rs:48:10 + | +LL | reuse S::foo_static as s; + | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` + | +note: required by a const generic parameter in `S::::foo_static` + --> $DIR/inherent-impls-generics.rs:43:21 + | +LL | impl<'a, 'b, 'c, A, const C: usize> S { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ---------- required by a bound in this associated function +help: consider specifying the generic arguments + | +LL | reuse S::::foo_static as s; + | ++++++++ + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-generics.rs:48:10 + | +LL | reuse S::foo_static as s; + | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` + | +note: required by a const generic parameter in `S::::foo_static` + --> $DIR/inherent-impls-generics.rs:44:34 + | +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` +help: consider specifying the generic arguments + | +LL | reuse S::foo_static:: as s; + | ++++++++ + +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-generics.rs:53:10 + | +LL | reuse S::foo_self as s1; + | ^^^^^^^^ argument #1 of type `S<_, _>` is missing + | +note: method defined here + --> $DIR/inherent-impls-generics.rs:45:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse S::foo_self(/* value */) as s1; + | +++++++++++++ + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-generics.rs:57:10 + | +LL | reuse S::foo_static::<'static, (), true> as s2; + | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` + | | + | type must be known at this point + | +note: required by a const generic parameter in `S` + --> $DIR/inherent-impls-generics.rs:39:13 + | +LL | struct S { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` +help: consider specifying the generic arguments + | +LL | reuse S::::foo_static::<'static, (), true> as s2; + | ++++++++ + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-generics.rs:57:10 + | +LL | reuse S::foo_static::<'static, (), true> as s2; + | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` + | +note: required by a const generic parameter in `S::::foo_static` + --> $DIR/inherent-impls-generics.rs:43:21 + | +LL | impl<'a, 'b, 'c, A, const C: usize> S { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ---------- required by a bound in this associated function +help: consider specifying the generic arguments + | +LL | reuse S::::foo_static::<'static, (), true> as s2; + | ++++++++ + +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-generics.rs:61:10 + | +LL | reuse S::foo_self::<'static, (), true> as s3; + | ^^^^^^^^ argument #1 of type `S<_, _>` is missing + | +note: method defined here + --> $DIR/inherent-impls-generics.rs:45:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse S::foo_self(/* value */)::<'static, (), true> as s3; + | +++++++++++++ + +error: aborting due to 22 previous errors + +Some errors have detailed explanations: E0061, E0284. +For more information about an error, try `rustc --explain E0061`. diff --git a/tests/ui/delegation/inherent-impls-parent-generics.rs b/tests/ui/delegation/inherent-impls-parent-generics.rs index 0f95540643bd7..ca65495695975 100644 --- a/tests/ui/delegation/inherent-impls-parent-generics.rs +++ b/tests/ui/delegation/inherent-impls-parent-generics.rs @@ -12,32 +12,27 @@ impl<'a, 'b, 'c, A: 'a, const C: usize> E<'a, A, C> { } reuse E::foo_static as e; -//~^ ERROR: cannot find function `foo_static` in enum `E` - +//~^ ERROR: delegation to inherent impl must contain parent generics +//~| ERROR: type annotations needed +//~| ERROR: type annotations needed +//~| ERROR: type annotations needed reuse E::foo_self as e1; -//~^ ERROR: cannot find function `foo_self` in enum `E` +//~^ ERROR: delegation to inherent impl must contain parent generics +//~| ERROR: this function takes 1 argument but 0 arguments were supplied reuse E::foo_static::<'static, (), true> as e2; -//~^ ERROR: cannot find function `foo_static` in enum `E` - +//~^ ERROR: delegation to inherent impl must contain parent generics +//~| ERROR: type annotations needed +//~| ERROR: type annotations needed reuse E::foo_self::<'static, (), true> as e3; -//~^ ERROR: cannot find function `foo_self` in enum `E` +//~^ ERROR: delegation to inherent impl must contain parent generics +//~| ERROR: this function takes 1 argument but 0 arguments were supplied reuse E::<'static, (), 123>::foo_static as e4; -//~^ ERROR: cannot find function `foo_static` in enum `E` reuse E::<'static, (), 123>::foo_self as e5; -//~^ ERROR: cannot find function `foo_self` in enum `E` reuse E::<'static, (), 123>::foo_static::<'static, (), true> as e6; -//~^ ERROR: cannot find function `foo_static` in enum `E` reuse E::<'static, (), 123>::foo_self::<'static, (), true> as e7; -//~^ ERROR: cannot find function `foo_self` in enum `E` - -reuse E::<'_, (), _>::foo_static as e8; -//~^ ERROR: cannot find function `foo_static` in enum `E` - -reuse E::<'_, _, _>::foo_self as e9; -//~^ ERROR: cannot find function `foo_self` in enum `E` struct S { xd: [A; C], @@ -49,32 +44,26 @@ impl<'a, 'b, 'c, A, const C: usize> S { } reuse S::foo_static as s; -//~^ ERROR: cannot find function `foo_static` in `S` - +//~^ ERROR: delegation to inherent impl must contain parent generics +//~| ERROR: type annotations needed +//~| ERROR: type annotations needed +//~| ERROR: type annotations needed reuse S::foo_self as s1; -//~^ ERROR: cannot find function `foo_self` in `S` +//~^ ERROR: delegation to inherent impl must contain parent generics +//~| ERROR: this function takes 1 argument but 0 arguments were supplied reuse S::foo_static::<'static, (), true> as s2; -//~^ ERROR: cannot find function `foo_static` in `S` - +//~^ ERROR: delegation to inherent impl must contain parent generics +//~| ERROR: type annotations needed +//~| ERROR: type annotations needed reuse S::foo_self::<'static, (), true> as s3; -//~^ ERROR: cannot find function `foo_self` in `S` +//~^ ERROR: delegation to inherent impl must contain parent generics +//~| ERROR: this function takes 1 argument but 0 arguments were supplied reuse S::<(), 123>::foo_static as s4; -//~^ ERROR: cannot find function `foo_static` in `S` reuse S::<(), 123>::foo_self as s5; -//~^ ERROR: cannot find function `foo_self` in `S` reuse S::<(), 123>::foo_static::<'static, (), true> as s6; -//~^ ERROR: cannot find function `foo_static` in `S` reuse S::<(), 123>::foo_self::<'static, (), true> as s7; -//~^ ERROR: cannot find function `foo_self` in `S` - -reuse S::<(), _>::foo_static as s8; -//~^ ERROR: cannot find function `foo_static` in `S` - -reuse S::<_, 123>::foo_self as s9; -//~^ ERROR: cannot find function `foo_self` in `S` - fn main() {} diff --git a/tests/ui/delegation/inherent-impls-parent-generics.stderr b/tests/ui/delegation/inherent-impls-parent-generics.stderr index 508ca65316457..a99e5f69a7af3 100644 --- a/tests/ui/delegation/inherent-impls-parent-generics.stderr +++ b/tests/ui/delegation/inherent-impls-parent-generics.stderr @@ -1,123 +1,296 @@ -error[E0425]: cannot find function `foo_static` in enum `E` +error: delegation to inherent impl must contain parent generics --> $DIR/inherent-impls-parent-generics.rs:14:10 | LL | reuse E::foo_static as e; - | ^^^^^^^^^^ not found in `E` + | ^^^^^^^^^^ -error[E0425]: cannot find function `foo_self` in enum `E` - --> $DIR/inherent-impls-parent-generics.rs:17:10 +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-parent-generics.rs:19:10 | LL | reuse E::foo_self as e1; - | ^^^^^^^^ not found in `E` + | ^^^^^^^^ -error[E0425]: cannot find function `foo_static` in enum `E` - --> $DIR/inherent-impls-parent-generics.rs:20:10 +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-parent-generics.rs:23:10 | LL | reuse E::foo_static::<'static, (), true> as e2; - | ^^^^^^^^^^ not found in `E` + | ^^^^^^^^^^ -error[E0425]: cannot find function `foo_self` in enum `E` - --> $DIR/inherent-impls-parent-generics.rs:23:10 +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-parent-generics.rs:27:10 | LL | reuse E::foo_self::<'static, (), true> as e3; - | ^^^^^^^^ not found in `E` + | ^^^^^^^^ -error[E0425]: cannot find function `foo_static` in enum `E` - --> $DIR/inherent-impls-parent-generics.rs:26:30 +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-parent-generics.rs:46:10 | -LL | reuse E::<'static, (), 123>::foo_static as e4; - | ^^^^^^^^^^ not found in `E` +LL | reuse S::foo_static as s; + | ^^^^^^^^^^ -error[E0425]: cannot find function `foo_self` in enum `E` - --> $DIR/inherent-impls-parent-generics.rs:28:30 +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-parent-generics.rs:51:10 | -LL | reuse E::<'static, (), 123>::foo_self as e5; - | ^^^^^^^^ not found in `E` +LL | reuse S::foo_self as s1; + | ^^^^^^^^ -error[E0425]: cannot find function `foo_static` in enum `E` - --> $DIR/inherent-impls-parent-generics.rs:31:30 +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-parent-generics.rs:55:10 | -LL | reuse E::<'static, (), 123>::foo_static::<'static, (), true> as e6; - | ^^^^^^^^^^ not found in `E` +LL | reuse S::foo_static::<'static, (), true> as s2; + | ^^^^^^^^^^ -error[E0425]: cannot find function `foo_self` in enum `E` - --> $DIR/inherent-impls-parent-generics.rs:33:30 +error: delegation to inherent impl must contain parent generics + --> $DIR/inherent-impls-parent-generics.rs:59:10 | -LL | reuse E::<'static, (), 123>::foo_self::<'static, (), true> as e7; - | ^^^^^^^^ not found in `E` +LL | reuse S::foo_self::<'static, (), true> as s3; + | ^^^^^^^^ -error[E0425]: cannot find function `foo_static` in enum `E` - --> $DIR/inherent-impls-parent-generics.rs:36:23 +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:14:10 + | +LL | reuse E::foo_static as e; + | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` + | | + | type must be known at this point + | +note: required by a const generic parameter in `E` + --> $DIR/inherent-impls-parent-generics.rs:4:23 + | +LL | enum E<'a: 'a, A: 'a, const C: usize> { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `E` +help: consider specifying the generic arguments + | +LL - reuse E::foo_static as e; +LL + reuse E:: as e; | -LL | reuse E::<'_, (), _>::foo_static as e8; - | ^^^^^^^^^^ not found in `E` -error[E0425]: cannot find function `foo_self` in enum `E` - --> $DIR/inherent-impls-parent-generics.rs:39:22 +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:14:10 + | +LL | reuse E::foo_static as e; + | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` + | +note: required by a const generic parameter in `E::<'a, A, C>::foo_static` + --> $DIR/inherent-impls-parent-generics.rs:9:25 + | +LL | impl<'a, 'b, 'c, A: 'a, const C: usize> E<'a, A, C> { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ---------- required by a bound in this associated function +help: consider specifying the generic arguments + | +LL - reuse E::foo_static as e; +LL + reuse E:: as e; | -LL | reuse E::<'_, _, _>::foo_self as e9; - | ^^^^^^^^ not found in `E` -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-parent-generics.rs:51:10 +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:14:10 | -LL | reuse S::foo_static as s; - | ^^^^^^^^^^ not found in `S` +LL | reuse E::foo_static as e; + | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` + | +note: required by a const generic parameter in `E::<'a, A, C>::foo_static` + --> $DIR/inherent-impls-parent-generics.rs:10:34 + | +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` +help: consider specifying the generic arguments + | +LL | reuse E::foo_static:: as e; + | ++++++++ -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-parent-generics.rs:54:10 +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-parent-generics.rs:19:10 | -LL | reuse S::foo_self as s1; - | ^^^^^^^^ not found in `S` +LL | reuse E::foo_self as e1; + | ^^^^^^^^ argument #1 of type `E<'_, _, _>` is missing + | +note: method defined here + --> $DIR/inherent-impls-parent-generics.rs:11:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse E::foo_self(/* value */) as e1; + | +++++++++++++ -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-parent-generics.rs:57:10 +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:23:10 + | +LL | reuse E::foo_static::<'static, (), true> as e2; + | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` + | | + | type must be known at this point + | +note: required by a const generic parameter in `E` + --> $DIR/inherent-impls-parent-generics.rs:4:23 + | +LL | enum E<'a: 'a, A: 'a, const C: usize> { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `E` +help: consider specifying the generic arguments + | +LL - reuse E::foo_static::<'static, (), true> as e2; +LL + reuse E:: as e2; | -LL | reuse S::foo_static::<'static, (), true> as s2; - | ^^^^^^^^^^ not found in `S` -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-parent-generics.rs:60:10 +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:23:10 + | +LL | reuse E::foo_static::<'static, (), true> as e2; + | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` + | +note: required by a const generic parameter in `E::<'a, A, C>::foo_static` + --> $DIR/inherent-impls-parent-generics.rs:9:25 + | +LL | impl<'a, 'b, 'c, A: 'a, const C: usize> E<'a, A, C> { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ---------- required by a bound in this associated function +help: consider specifying the generic arguments + | +LL - reuse E::foo_static::<'static, (), true> as e2; +LL + reuse E:: as e2; | -LL | reuse S::foo_self::<'static, (), true> as s3; - | ^^^^^^^^ not found in `S` -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-parent-generics.rs:63:21 +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-parent-generics.rs:27:10 + | +LL | reuse E::foo_self::<'static, (), true> as e3; + | ^^^^^^^^ argument #1 of type `E<'_, _, _>` is missing | -LL | reuse S::<(), 123>::foo_static as s4; - | ^^^^^^^^^^ not found in `S` +note: method defined here + --> $DIR/inherent-impls-parent-generics.rs:11:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse E::foo_self(/* value */)::<'static, (), true> as e3; + | +++++++++++++ -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-parent-generics.rs:65:21 +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:46:10 + | +LL | reuse S::foo_static as s; + | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` + | | + | type must be known at this point + | +note: required by a const generic parameter in `S` + --> $DIR/inherent-impls-parent-generics.rs:37:13 | -LL | reuse S::<(), 123>::foo_self as s5; - | ^^^^^^^^ not found in `S` +LL | struct S { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` +help: consider specifying the generic arguments + | +LL | reuse S::::foo_static as s; + | ++++++++ -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-parent-generics.rs:68:21 +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:46:10 + | +LL | reuse S::foo_static as s; + | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` + | +note: required by a const generic parameter in `S::::foo_static` + --> $DIR/inherent-impls-parent-generics.rs:41:21 + | +LL | impl<'a, 'b, 'c, A, const C: usize> S { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ---------- required by a bound in this associated function +help: consider specifying the generic arguments | -LL | reuse S::<(), 123>::foo_static::<'static, (), true> as s6; - | ^^^^^^^^^^ not found in `S` +LL | reuse S::::foo_static as s; + | ++++++++ -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-parent-generics.rs:70:21 +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:46:10 | -LL | reuse S::<(), 123>::foo_self::<'static, (), true> as s7; - | ^^^^^^^^ not found in `S` +LL | reuse S::foo_static as s; + | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` + | +note: required by a const generic parameter in `S::::foo_static` + --> $DIR/inherent-impls-parent-generics.rs:42:34 + | +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` +help: consider specifying the generic arguments + | +LL | reuse S::foo_static:: as s; + | ++++++++ -error[E0425]: cannot find function `foo_static` in `S` - --> $DIR/inherent-impls-parent-generics.rs:73:19 +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-parent-generics.rs:51:10 | -LL | reuse S::<(), _>::foo_static as s8; - | ^^^^^^^^^^ not found in `S` +LL | reuse S::foo_self as s1; + | ^^^^^^^^ argument #1 of type `S<_, _>` is missing + | +note: method defined here + --> $DIR/inherent-impls-parent-generics.rs:43:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse S::foo_self(/* value */) as s1; + | +++++++++++++ + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:55:10 + | +LL | reuse S::foo_static::<'static, (), true> as s2; + | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` + | | + | type must be known at this point + | +note: required by a const generic parameter in `S` + --> $DIR/inherent-impls-parent-generics.rs:37:13 + | +LL | struct S { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` +help: consider specifying the generic arguments + | +LL | reuse S::::foo_static::<'static, (), true> as s2; + | ++++++++ -error[E0425]: cannot find function `foo_self` in `S` - --> $DIR/inherent-impls-parent-generics.rs:76:20 +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:55:10 + | +LL | reuse S::foo_static::<'static, (), true> as s2; + | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` + | +note: required by a const generic parameter in `S::::foo_static` + --> $DIR/inherent-impls-parent-generics.rs:41:21 + | +LL | impl<'a, 'b, 'c, A, const C: usize> S { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ---------- required by a bound in this associated function +help: consider specifying the generic arguments + | +LL | reuse S::::foo_static::<'static, (), true> as s2; + | ++++++++ + +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-parent-generics.rs:59:10 + | +LL | reuse S::foo_self::<'static, (), true> as s3; + | ^^^^^^^^ argument #1 of type `S<_, _>` is missing + | +note: method defined here + --> $DIR/inherent-impls-parent-generics.rs:43:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument | -LL | reuse S::<_, 123>::foo_self as s9; - | ^^^^^^^^ not found in `S` +LL | reuse S::foo_self(/* value */)::<'static, (), true> as s3; + | +++++++++++++ -error: aborting due to 20 previous errors +error: aborting due to 22 previous errors -For more information about this error, try `rustc --explain E0425`. +Some errors have detailed explanations: E0061, E0284. +For more information about an error, try `rustc --explain E0061`. diff --git a/tests/ui/delegation/inherent-impls-structs.rs b/tests/ui/delegation/inherent-impls-structs.rs index 26c61726a9eda..86557cbe6362c 100644 --- a/tests/ui/delegation/inherent-impls-structs.rs +++ b/tests/ui/delegation/inherent-impls-structs.rs @@ -9,22 +9,16 @@ impl<'a, 'b, 'c, A, const C: usize> S { fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} } -reuse S::foo_static; reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; -reuse S::foo_static::<'static, (), true> as foo_static_2; reuse S::<(), 1>::foo_static as foo_static_3; reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; -reuse S::foo_self; reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1; -reuse S::foo_self::<'static, (), true> as foo_self_2; reuse S::<(), 1>::foo_self as foo_self_3; reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; trait Trait<'a, AA, BB> where Self: Sized { - reuse S::foo_static; reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; - reuse S::foo_static::<'static, (), true> as foo_static_2; reuse S::<(), 1>::foo_static as foo_static_3; reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; @@ -32,11 +26,7 @@ trait Trait<'a, AA, BB> where Self: Sized { panic!(); } - reuse S::foo_self; - //~^ ERROR: mismatched types [E0308] reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - reuse S::foo_self::<'static, (), true> as foo_self_2; - //~^ ERROR: mismatched types [E0308] reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; //~^ ERROR: mismatched types [E0308] @@ -45,30 +35,19 @@ trait Trait<'a, AA, BB> where Self: Sized { struct X; impl<'a, A, B> Trait<'a, A, B> for X { - reuse S::foo_static; - //~^ ERROR: associated function takes at most 2 generic arguments but 4 generic arguments were supplied [E0107] reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; - reuse S::foo_static::<'static, (), true> as foo_static_2; - //~^ ERROR: type annotations needed [E0284] reuse S::<(), 1>::foo_static as foo_static_3; reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; //~^ ERROR: type annotations needed [E0284] - reuse S::foo_self; - //~^ ERROR: mismatched types [E0308] - //~| ERROR: method takes at most 2 generic arguments but 4 generic arguments were supplied [E0107] reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - reuse S::foo_self::<'static, (), true> as foo_self_2; - //~^ ERROR: mismatched types [E0308] reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; //~^ ERROR: mismatched types [E0308] } impl X { - reuse S::foo_static; reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; - reuse S::foo_static::<'static, (), true> as foo_static_2; reuse S::<(), 1>::foo_static as foo_static_3; reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; @@ -76,11 +55,7 @@ impl X { panic!(); } - reuse S::foo_self; - //~^ ERROR: mismatched types [E0308] reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } - reuse S::foo_self::<'static, (), true> as foo_self_2; - //~^ ERROR: mismatched types [E0308] reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; //~^ ERROR: mismatched types [E0308] diff --git a/tests/ui/delegation/inherent-impls-structs.stderr b/tests/ui/delegation/inherent-impls-structs.stderr index 450f01357ee6b..1956b5655fe25 100644 --- a/tests/ui/delegation/inherent-impls-structs.stderr +++ b/tests/ui/delegation/inherent-impls-structs.stderr @@ -1,45 +1,5 @@ error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:35:14 - | -LL | trait Trait<'a, AA, BB> where Self: Sized { - | ----------------------- found this type parameter -... -LL | reuse S::foo_self; - | ^^^^^^^^ - | | - | expected `S`, found type parameter `Self` - | arguments to this function are incorrect - | - = note: expected struct `S` - found type parameter `Self` -note: method defined here - --> $DIR/inherent-impls-structs.rs:9:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- - -error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:38:14 - | -LL | trait Trait<'a, AA, BB> where Self: Sized { - | ----------------------- found this type parameter -... -LL | reuse S::foo_self::<'static, (), true> as foo_self_2; - | ^^^^^^^^ - | | - | expected `S`, found type parameter `Self` - | arguments to this function are incorrect - | - = note: expected struct `S` - found type parameter `Self` -note: method defined here - --> $DIR/inherent-impls-structs.rs:9:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- - -error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:41:22 + --> $DIR/inherent-impls-structs.rs:31:22 | LL | trait Trait<'a, AA, BB> where Self: Sized { | ----------------------- found this type parameter @@ -58,39 +18,8 @@ note: method defined here LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- -error[E0107]: associated function takes at most 2 generic arguments but 4 generic arguments were supplied - --> $DIR/inherent-impls-structs.rs:48:14 - | -LL | reuse S::foo_static; - | ^^^^^^^^^^ - | | - | expected at most 2 generic arguments - | help: remove the unnecessary generic arguments - | -note: associated function defined here, with at most 2 generic parameters: `T`, `B` - --> $DIR/inherent-impls-structs.rs:8:8 - | -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ^^^^^^^^^^ - ------------- - error[E0284]: type annotations needed - --> $DIR/inherent-impls-structs.rs:51:14 - | -LL | reuse S::foo_static::<'static, (), true> as foo_static_2; - | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` - | -note: required by a const generic parameter in `S` - --> $DIR/inherent-impls-structs.rs:3:13 - | -LL | struct S { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` -help: consider specifying the generic arguments - | -LL | reuse S::::foo_static::<'static, (), true> as foo_static_2; - | ++++++++ - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-structs.rs:54:22 + --> $DIR/inherent-impls-structs.rs:40:22 | LL | reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; | ^^^^^^^^^^ cannot infer the value of const parameter `B` declared on the associated function `foo_static` @@ -101,57 +30,8 @@ note: required by a const generic parameter in `S::::foo_static` LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} | ^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` -error[E0107]: method takes at most 2 generic arguments but 4 generic arguments were supplied - --> $DIR/inherent-impls-structs.rs:57:14 - | -LL | reuse S::foo_self; - | ^^^^^^^^ - | | - | expected at most 2 generic arguments - | help: remove the unnecessary generic arguments - | -note: method defined here, with at most 2 generic parameters: `T`, `B` - --> $DIR/inherent-impls-structs.rs:9:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ - ------------- - -error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:57:14 - | -LL | reuse S::foo_self; - | ^^^^^^^^ - | | - | expected `S<_, _>`, found `X` - | arguments to this function are incorrect - | - = note: expected struct `S<_, _>` - found struct `X` -note: method defined here - --> $DIR/inherent-impls-structs.rs:9:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- - -error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:61:14 - | -LL | reuse S::foo_self::<'static, (), true> as foo_self_2; - | ^^^^^^^^ - | | - | expected `S<_, _>`, found `X` - | arguments to this function are incorrect - | - = note: expected struct `S<_, _>` - found struct `X` -note: method defined here - --> $DIR/inherent-impls-structs.rs:9:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- - error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:64:22 + --> $DIR/inherent-impls-structs.rs:45:22 | LL | reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; | ^^^^^^^^ @@ -168,41 +48,7 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:79:14 - | -LL | reuse S::foo_self; - | ^^^^^^^^ - | | - | expected `S`, found `X` - | arguments to this function are incorrect - | - = note: expected struct `S` - found struct `X` -note: method defined here - --> $DIR/inherent-impls-structs.rs:9:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- - -error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:82:14 - | -LL | reuse S::foo_self::<'static, (), true> as foo_self_2; - | ^^^^^^^^ - | | - | expected `S`, found `X` - | arguments to this function are incorrect - | - = note: expected struct `S` - found struct `X` -note: method defined here - --> $DIR/inherent-impls-structs.rs:9:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- - -error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:85:22 + --> $DIR/inherent-impls-structs.rs:60:22 | LL | reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; | ^^^^^^^^ @@ -218,7 +64,7 @@ note: method defined here LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- -error: aborting due to 13 previous errors +error: aborting due to 4 previous errors -Some errors have detailed explanations: E0107, E0284, E0308. -For more information about an error, try `rustc --explain E0107`. +Some errors have detailed explanations: E0284, E0308. +For more information about an error, try `rustc --explain E0284`. diff --git a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs index a618babb16f59..d17c387547e98 100644 --- a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs +++ b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs @@ -6,7 +6,6 @@ struct S<'a, A, const C: usize> { impl<'a, 'b, 'c, A, const C: usize> S { //~^ ERROR: implicit elided lifetime not allowed here - fn foo_static<'d: 'd, 'e, T, const B: bool>() {} fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} } diff --git a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr index cfb9c3e9e1a29..c2005837b47e4 100644 --- a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr +++ b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr @@ -10,13 +10,13 @@ LL | impl<'a, 'b, 'c, A, const C: usize> S<'_, A, C> { | +++ error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-wrong-header-args-ice.rs:14:14 + --> $DIR/inherent-impls-wrong-header-args-ice.rs:13:14 | LL | reuse S::foo_self; | ^^^^^^^^ argument #1 is missing | note: method defined here - --> $DIR/inherent-impls-wrong-header-args-ice.rs:10:8 + --> $DIR/inherent-impls-wrong-header-args-ice.rs:9:8 | LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- From 5791b536c3a0e30b301a91ecb4af47e1ffd18abc Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Thu, 13 Aug 2026 09:01:21 +0300 Subject: [PATCH 07/22] Cleanup tests --- .../ui/delegation/inherent-impl-glob-list.rs | 21 -- .../delegation/inherent-impl-glob-list.stderr | 8 - .../inherent-impl-mixed-generics.rs | 17 - .../inherent-impl-mixed-generics.stderr | 25 -- .../inherent-impl-non-local-crate.rs | 23 -- .../inherent-impl-non-local-crate.stderr | 49 --- .../inherent-impl-receiver-mapping.rs | 61 ---- .../inherent-impl-receiver-mapping.stderr | 75 ----- .../delegation/inherent-impls-generics.stderr | 296 ------------------ .../ui/delegation/inherent-impls-glob-list.rs | 2 - .../inherent-impls-glob-list.stderr | 2 +- .../inherent-impls-mixed-generics.rs | 3 +- .../inherent-impls-mixed-generics.stderr | 2 +- .../inherent-impls-non-local-crate.rs | 14 +- .../inherent-impls-non-local-crate.stderr | 12 +- .../inherent-impls-receiver-mapping.rs | 20 +- .../inherent-impls-receiver-mapping.stderr | 108 ++----- 17 files changed, 40 insertions(+), 698 deletions(-) delete mode 100644 tests/ui/delegation/inherent-impl-glob-list.rs delete mode 100644 tests/ui/delegation/inherent-impl-glob-list.stderr delete mode 100644 tests/ui/delegation/inherent-impl-mixed-generics.rs delete mode 100644 tests/ui/delegation/inherent-impl-mixed-generics.stderr delete mode 100644 tests/ui/delegation/inherent-impl-non-local-crate.rs delete mode 100644 tests/ui/delegation/inherent-impl-non-local-crate.stderr delete mode 100644 tests/ui/delegation/inherent-impl-receiver-mapping.rs delete mode 100644 tests/ui/delegation/inherent-impl-receiver-mapping.stderr delete mode 100644 tests/ui/delegation/inherent-impls-generics.stderr diff --git a/tests/ui/delegation/inherent-impl-glob-list.rs b/tests/ui/delegation/inherent-impl-glob-list.rs deleted file mode 100644 index d983711102dde..0000000000000 --- a/tests/ui/delegation/inherent-impl-glob-list.rs +++ /dev/null @@ -1,21 +0,0 @@ -#![feature(fn_delegation)] - -struct X; - -impl X { - fn foo(&self) {} - fn foo2(&self) {} -} - -struct Y; - -impl Y { - reuse X::{foo, foo2} { X } -} - -impl Y { - reuse X::*; - //~^ ERROR: expected trait, found struct `X` -} - -fn main() {} diff --git a/tests/ui/delegation/inherent-impl-glob-list.stderr b/tests/ui/delegation/inherent-impl-glob-list.stderr deleted file mode 100644 index f0ecc659d2fba..0000000000000 --- a/tests/ui/delegation/inherent-impl-glob-list.stderr +++ /dev/null @@ -1,8 +0,0 @@ -error: expected trait, found struct `X` - --> $DIR/inherent-impl-glob-list.rs:17:11 - | -LL | reuse X::*; - | ^ not a trait - -error: aborting due to 1 previous error - diff --git a/tests/ui/delegation/inherent-impl-mixed-generics.rs b/tests/ui/delegation/inherent-impl-mixed-generics.rs deleted file mode 100644 index b24acff6187eb..0000000000000 --- a/tests/ui/delegation/inherent-impl-mixed-generics.rs +++ /dev/null @@ -1,17 +0,0 @@ -#![feature(fn_delegation)] - -struct S<'a, A, B, const C: usize> { - xd: &'a [(A, B); C], -} - -impl<'a, 'b, 'c, A, const C: usize> S<'static, A, usize, C> { - fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} -} - -trait Trait<'a, AA, BB> where Self: Sized { - reuse S::foo_self; - //~^ ERROR: delegation to inherent impl must contain parent generics - //~| ERROR: this function takes 1 argument but 0 arguments were supplied -} - -fn main() {} diff --git a/tests/ui/delegation/inherent-impl-mixed-generics.stderr b/tests/ui/delegation/inherent-impl-mixed-generics.stderr deleted file mode 100644 index 33e63e606f00f..0000000000000 --- a/tests/ui/delegation/inherent-impl-mixed-generics.stderr +++ /dev/null @@ -1,25 +0,0 @@ -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impl-mixed-generics.rs:12:14 - | -LL | reuse S::foo_self; - | ^^^^^^^^ - -error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impl-mixed-generics.rs:12:14 - | -LL | reuse S::foo_self; - | ^^^^^^^^ argument #1 of type `S<'static, _, usize, _>` is missing - | -note: method defined here - --> $DIR/inherent-impl-mixed-generics.rs:8:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- -help: provide the argument - | -LL | reuse S::foo_self(/* value */); - | +++++++++++++ - -error: aborting due to 2 previous errors - -For more information about this error, try `rustc --explain E0061`. diff --git a/tests/ui/delegation/inherent-impl-non-local-crate.rs b/tests/ui/delegation/inherent-impl-non-local-crate.rs deleted file mode 100644 index 27b8d387a7e63..0000000000000 --- a/tests/ui/delegation/inherent-impl-non-local-crate.rs +++ /dev/null @@ -1,23 +0,0 @@ -//@ aux-crate:inherent_impl=inherent-impl.rs - -#![feature(fn_delegation)] - -reuse inherent_impl::S::foo; - -reuse inherent_impl::S::not_existing; -//~^ ERROR: no associated function or constant named `not_existing` found for struct `S` in the current scope -reuse inherent_impl::S::TYPE; -//~^ ERROR: no associated function or constant named `TYPE` found for struct `S` in the current scope -reuse inherent_impl::S::CONST; -//~^ ERROR: expected function, found `usize` [E0618] - -reuse inherent_impl::S::bar; -//~^ ERROR: no associated function or constant named `bar` found for struct `S` in the current scope - -reuse ::bar as trait_bar; - -reuse inherent_impl::X::foo as x_foo; -//~^ ERROR: ambiguous delegation to inherent impl function -//~| ERROR: multiple applicable items in scope - -fn main() {} diff --git a/tests/ui/delegation/inherent-impl-non-local-crate.stderr b/tests/ui/delegation/inherent-impl-non-local-crate.stderr deleted file mode 100644 index e763a132baa08..0000000000000 --- a/tests/ui/delegation/inherent-impl-non-local-crate.stderr +++ /dev/null @@ -1,49 +0,0 @@ -error: ambiguous delegation to inherent impl function - --> $DIR/inherent-impl-non-local-crate.rs:19:25 - | -LL | reuse inherent_impl::X::foo as x_foo; - | ^^^ - -error[E0599]: no associated function or constant named `not_existing` found for struct `S` in the current scope - --> $DIR/inherent-impl-non-local-crate.rs:7:25 - | -LL | reuse inherent_impl::S::not_existing; - | ^^^^^^^^^^^^ associated function or constant not found in `S` - -error[E0599]: no associated function or constant named `TYPE` found for struct `S` in the current scope - --> $DIR/inherent-impl-non-local-crate.rs:9:25 - | -LL | reuse inherent_impl::S::TYPE; - | ^^^^ associated function or constant not found in `S` - -error[E0618]: expected function, found `usize` - --> $DIR/inherent-impl-non-local-crate.rs:11:25 - | -LL | reuse inherent_impl::S::CONST; - | ^^^^^ call expression requires function - -error[E0599]: no associated function or constant named `bar` found for struct `S` in the current scope - --> $DIR/inherent-impl-non-local-crate.rs:14:25 - | -LL | reuse inherent_impl::S::bar; - | ^^^ associated function or constant not found in `S` - | - = help: items from traits can only be used if the trait is in scope -help: trait `Trait` which provides `bar` is implemented but not in scope; perhaps you want to import it - | -LL + use inherent_impl::Trait; - | - -error[E0034]: multiple applicable items in scope - --> $DIR/inherent-impl-non-local-crate.rs:19:25 - | -LL | reuse inherent_impl::X::foo as x_foo; - | ^^^ multiple `foo` found - | - = note: candidate #1 is defined in an impl for the type `X` - = note: candidate #2 is defined in an impl for the type `X` - -error: aborting due to 6 previous errors - -Some errors have detailed explanations: E0034, E0599, E0618. -For more information about an error, try `rustc --explain E0034`. diff --git a/tests/ui/delegation/inherent-impl-receiver-mapping.rs b/tests/ui/delegation/inherent-impl-receiver-mapping.rs deleted file mode 100644 index 476fb2075d280..0000000000000 --- a/tests/ui/delegation/inherent-impl-receiver-mapping.rs +++ /dev/null @@ -1,61 +0,0 @@ -#![feature(fn_delegation)] - -mod receiver_mapping { - struct X; - - impl X { - fn static_f() {} - fn by_value(self) {} - fn by_ref(&self) {} - fn by_mut_ref(&mut self) {} - } - - struct Y; - - impl Y { - fn get_x(&self) -> X { X } - reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - } - - fn check() { - let y = Y; - y.by_ref(); - y.by_mut_ref(); - //~^ ERROR: cannot borrow `y` as mutable, as it is not declared as mutable - y.by_value(); - - let y = &Y; - y.by_value(); - //~^ ERROR: cannot move out of `*y` which is behind a shared reference - y.by_ref(); - y.by_mut_ref(); - //~^ ERROR: cannot borrow `*y` as mutable, as it is behind a `&` reference - - let y = &mut Y; - y.by_value(); - //~^ ERROR: cannot move out of `*y` which is behind a mutable reference - y.by_ref(); - y.by_mut_ref(); - } -} - -mod self_type_mapping { - struct X; - impl X { - fn add(self, other: Self) -> Self { - Self - } - } - - struct W(X); - impl W { - reuse X::add { self.0 } - } - - fn check() { - W(X).add(W(X)); - //~^ ERROR: mismatched types - } -} - -fn main() {} diff --git a/tests/ui/delegation/inherent-impl-receiver-mapping.stderr b/tests/ui/delegation/inherent-impl-receiver-mapping.stderr deleted file mode 100644 index 7c17f62321040..0000000000000 --- a/tests/ui/delegation/inherent-impl-receiver-mapping.stderr +++ /dev/null @@ -1,75 +0,0 @@ -error[E0308]: mismatched types - --> $DIR/inherent-impl-receiver-mapping.rs:56:18 - | -LL | W(X).add(W(X)); - | --- ^^^^ expected `X`, found `W` - | | - | arguments to this method are incorrect - | -note: method defined here - --> $DIR/inherent-impl-receiver-mapping.rs:52:18 - | -LL | reuse X::add { self.0 } - | ^^^ - -error[E0596]: cannot borrow `y` as mutable, as it is not declared as mutable - --> $DIR/inherent-impl-receiver-mapping.rs:23:9 - | -LL | y.by_mut_ref(); - | ^ cannot borrow as mutable - | -help: consider changing this to be mutable - | -LL | let mut y = Y; - | +++ - -error[E0507]: cannot move out of `*y` which is behind a shared reference - --> $DIR/inherent-impl-receiver-mapping.rs:28:9 - | -LL | y.by_value(); - | ^ ---------- `*y` moved due to this method call - | | - | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait - | - = note: `receiver_mapping::Y::by_value` takes ownership of the receiver `self`, which moves `*y` -note: if `Y` implemented `Clone`, you could clone the value - --> $DIR/inherent-impl-receiver-mapping.rs:13:5 - | -LL | struct Y; - | ^^^^^^^^ consider implementing `Clone` for this type -... -LL | y.by_value(); - | - you could clone this value - -error[E0596]: cannot borrow `*y` as mutable, as it is behind a `&` reference - --> $DIR/inherent-impl-receiver-mapping.rs:31:9 - | -LL | y.by_mut_ref(); - | ^ `y` is a `&` reference, so it cannot be borrowed as mutable - | -help: consider changing this to be a mutable reference - | -LL | let y = &mut Y; - | +++ - -error[E0507]: cannot move out of `*y` which is behind a mutable reference - --> $DIR/inherent-impl-receiver-mapping.rs:35:9 - | -LL | y.by_value(); - | ^ ---------- `*y` moved due to this method call - | | - | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait - | -note: if `Y` implemented `Clone`, you could clone the value - --> $DIR/inherent-impl-receiver-mapping.rs:13:5 - | -LL | struct Y; - | ^^^^^^^^ consider implementing `Clone` for this type -... -LL | y.by_value(); - | - you could clone this value - -error: aborting due to 5 previous errors - -Some errors have detailed explanations: E0308, E0507, E0596. -For more information about an error, try `rustc --explain E0308`. diff --git a/tests/ui/delegation/inherent-impls-generics.stderr b/tests/ui/delegation/inherent-impls-generics.stderr deleted file mode 100644 index f9a14310ec52e..0000000000000 --- a/tests/ui/delegation/inherent-impls-generics.stderr +++ /dev/null @@ -1,296 +0,0 @@ -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-generics.rs:16:10 - | -LL | reuse E::foo_static as e; - | ^^^^^^^^^^ - -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-generics.rs:21:10 - | -LL | reuse E::foo_self as e1; - | ^^^^^^^^ - -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-generics.rs:25:10 - | -LL | reuse E::foo_static::<'static, (), true> as e2; - | ^^^^^^^^^^ - -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-generics.rs:29:10 - | -LL | reuse E::foo_self::<'static, (), true> as e3; - | ^^^^^^^^ - -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-generics.rs:48:10 - | -LL | reuse S::foo_static as s; - | ^^^^^^^^^^ - -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-generics.rs:53:10 - | -LL | reuse S::foo_self as s1; - | ^^^^^^^^ - -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-generics.rs:57:10 - | -LL | reuse S::foo_static::<'static, (), true> as s2; - | ^^^^^^^^^^ - -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-generics.rs:61:10 - | -LL | reuse S::foo_self::<'static, (), true> as s3; - | ^^^^^^^^ - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-generics.rs:16:10 - | -LL | reuse E::foo_static as e; - | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` - | | - | type must be known at this point - | -note: required by a const generic parameter in `E` - --> $DIR/inherent-impls-generics.rs:6:23 - | -LL | enum E<'a: 'a, A: 'a, const C: usize> { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `E` -help: consider specifying the generic arguments - | -LL - reuse E::foo_static as e; -LL + reuse E:: as e; - | - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-generics.rs:16:10 - | -LL | reuse E::foo_static as e; - | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` - | -note: required by a const generic parameter in `E::<'a, A, C>::foo_static` - --> $DIR/inherent-impls-generics.rs:11:25 - | -LL | impl<'a, 'b, 'c, A: 'a, const C: usize> E<'a, A, C> { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ---------- required by a bound in this associated function -help: consider specifying the generic arguments - | -LL - reuse E::foo_static as e; -LL + reuse E:: as e; - | - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-generics.rs:16:10 - | -LL | reuse E::foo_static as e; - | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` - | -note: required by a const generic parameter in `E::<'a, A, C>::foo_static` - --> $DIR/inherent-impls-generics.rs:12:34 - | -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` -help: consider specifying the generic arguments - | -LL | reuse E::foo_static:: as e; - | ++++++++ - -error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-generics.rs:21:10 - | -LL | reuse E::foo_self as e1; - | ^^^^^^^^ argument #1 of type `E<'_, _, _>` is missing - | -note: method defined here - --> $DIR/inherent-impls-generics.rs:13:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- -help: provide the argument - | -LL | reuse E::foo_self(/* value */) as e1; - | +++++++++++++ - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-generics.rs:25:10 - | -LL | reuse E::foo_static::<'static, (), true> as e2; - | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` - | | - | type must be known at this point - | -note: required by a const generic parameter in `E` - --> $DIR/inherent-impls-generics.rs:6:23 - | -LL | enum E<'a: 'a, A: 'a, const C: usize> { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `E` -help: consider specifying the generic arguments - | -LL - reuse E::foo_static::<'static, (), true> as e2; -LL + reuse E:: as e2; - | - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-generics.rs:25:10 - | -LL | reuse E::foo_static::<'static, (), true> as e2; - | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` - | -note: required by a const generic parameter in `E::<'a, A, C>::foo_static` - --> $DIR/inherent-impls-generics.rs:11:25 - | -LL | impl<'a, 'b, 'c, A: 'a, const C: usize> E<'a, A, C> { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ---------- required by a bound in this associated function -help: consider specifying the generic arguments - | -LL - reuse E::foo_static::<'static, (), true> as e2; -LL + reuse E:: as e2; - | - -error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-generics.rs:29:10 - | -LL | reuse E::foo_self::<'static, (), true> as e3; - | ^^^^^^^^ argument #1 of type `E<'_, _, _>` is missing - | -note: method defined here - --> $DIR/inherent-impls-generics.rs:13:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- -help: provide the argument - | -LL | reuse E::foo_self(/* value */)::<'static, (), true> as e3; - | +++++++++++++ - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-generics.rs:48:10 - | -LL | reuse S::foo_static as s; - | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` - | | - | type must be known at this point - | -note: required by a const generic parameter in `S` - --> $DIR/inherent-impls-generics.rs:39:13 - | -LL | struct S { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` -help: consider specifying the generic arguments - | -LL | reuse S::::foo_static as s; - | ++++++++ - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-generics.rs:48:10 - | -LL | reuse S::foo_static as s; - | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` - | -note: required by a const generic parameter in `S::::foo_static` - --> $DIR/inherent-impls-generics.rs:43:21 - | -LL | impl<'a, 'b, 'c, A, const C: usize> S { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ---------- required by a bound in this associated function -help: consider specifying the generic arguments - | -LL | reuse S::::foo_static as s; - | ++++++++ - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-generics.rs:48:10 - | -LL | reuse S::foo_static as s; - | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` - | -note: required by a const generic parameter in `S::::foo_static` - --> $DIR/inherent-impls-generics.rs:44:34 - | -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` -help: consider specifying the generic arguments - | -LL | reuse S::foo_static:: as s; - | ++++++++ - -error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-generics.rs:53:10 - | -LL | reuse S::foo_self as s1; - | ^^^^^^^^ argument #1 of type `S<_, _>` is missing - | -note: method defined here - --> $DIR/inherent-impls-generics.rs:45:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- -help: provide the argument - | -LL | reuse S::foo_self(/* value */) as s1; - | +++++++++++++ - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-generics.rs:57:10 - | -LL | reuse S::foo_static::<'static, (), true> as s2; - | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` - | | - | type must be known at this point - | -note: required by a const generic parameter in `S` - --> $DIR/inherent-impls-generics.rs:39:13 - | -LL | struct S { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` -help: consider specifying the generic arguments - | -LL | reuse S::::foo_static::<'static, (), true> as s2; - | ++++++++ - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-generics.rs:57:10 - | -LL | reuse S::foo_static::<'static, (), true> as s2; - | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` - | -note: required by a const generic parameter in `S::::foo_static` - --> $DIR/inherent-impls-generics.rs:43:21 - | -LL | impl<'a, 'b, 'c, A, const C: usize> S { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ---------- required by a bound in this associated function -help: consider specifying the generic arguments - | -LL | reuse S::::foo_static::<'static, (), true> as s2; - | ++++++++ - -error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-generics.rs:61:10 - | -LL | reuse S::foo_self::<'static, (), true> as s3; - | ^^^^^^^^ argument #1 of type `S<_, _>` is missing - | -note: method defined here - --> $DIR/inherent-impls-generics.rs:45:8 - | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- -help: provide the argument - | -LL | reuse S::foo_self(/* value */)::<'static, (), true> as s3; - | +++++++++++++ - -error: aborting due to 22 previous errors - -Some errors have detailed explanations: E0061, E0284. -For more information about an error, try `rustc --explain E0061`. diff --git a/tests/ui/delegation/inherent-impls-glob-list.rs b/tests/ui/delegation/inherent-impls-glob-list.rs index 51d24e6838df0..d983711102dde 100644 --- a/tests/ui/delegation/inherent-impls-glob-list.rs +++ b/tests/ui/delegation/inherent-impls-glob-list.rs @@ -11,8 +11,6 @@ struct Y; impl Y { reuse X::{foo, foo2} { X } - //~^ ERROR: cannot find function `foo` in `X` - //~| ERROR: cannot find function `foo2` in `X` } impl Y { diff --git a/tests/ui/delegation/inherent-impls-glob-list.stderr b/tests/ui/delegation/inherent-impls-glob-list.stderr index c15c53194a50b..7972e598e1853 100644 --- a/tests/ui/delegation/inherent-impls-glob-list.stderr +++ b/tests/ui/delegation/inherent-impls-glob-list.stderr @@ -1,5 +1,5 @@ error: expected trait, found struct `X` - --> $DIR/inherent-impls-glob-list.rs:19:11 + --> $DIR/inherent-impls-glob-list.rs:17:11 | LL | reuse X::*; | ^ not a trait diff --git a/tests/ui/delegation/inherent-impls-mixed-generics.rs b/tests/ui/delegation/inherent-impls-mixed-generics.rs index 027dcace3ab0d..b24acff6187eb 100644 --- a/tests/ui/delegation/inherent-impls-mixed-generics.rs +++ b/tests/ui/delegation/inherent-impls-mixed-generics.rs @@ -10,7 +10,8 @@ impl<'a, 'b, 'c, A, const C: usize> S<'static, A, usize, C> { trait Trait<'a, AA, BB> where Self: Sized { reuse S::foo_self; - //~^ ERROR: cannot find function `foo_self` in `S` + //~^ ERROR: delegation to inherent impl must contain parent generics + //~| ERROR: this function takes 1 argument but 0 arguments were supplied } fn main() {} diff --git a/tests/ui/delegation/inherent-impls-mixed-generics.stderr b/tests/ui/delegation/inherent-impls-mixed-generics.stderr index e2550242284da..f730d5360eef7 100644 --- a/tests/ui/delegation/inherent-impls-mixed-generics.stderr +++ b/tests/ui/delegation/inherent-impls-mixed-generics.stderr @@ -1,4 +1,4 @@ -error: failed to generate delegation: mismatch between provided generic args in inherent impl and declared generics +error: delegation to inherent impl must contain parent generics --> $DIR/inherent-impls-mixed-generics.rs:12:14 | LL | reuse S::foo_self; diff --git a/tests/ui/delegation/inherent-impls-non-local-crate.rs b/tests/ui/delegation/inherent-impls-non-local-crate.rs index c2f07fd8e7ae7..27b8d387a7e63 100644 --- a/tests/ui/delegation/inherent-impls-non-local-crate.rs +++ b/tests/ui/delegation/inherent-impls-non-local-crate.rs @@ -3,23 +3,21 @@ #![feature(fn_delegation)] reuse inherent_impl::S::foo; -//~^ ERROR: cannot find function `foo` in `inherent_impl::S` reuse inherent_impl::S::not_existing; -//~^ ERROR: cannot find function `not_existing` in `inherent_impl::S` - +//~^ ERROR: no associated function or constant named `not_existing` found for struct `S` in the current scope reuse inherent_impl::S::TYPE; -//~^ ERROR: cannot find function `TYPE` in `inherent_impl::S` - +//~^ ERROR: no associated function or constant named `TYPE` found for struct `S` in the current scope reuse inherent_impl::S::CONST; -//~^ ERROR: cannot find function `CONST` in `inherent_impl::S` +//~^ ERROR: expected function, found `usize` [E0618] reuse inherent_impl::S::bar; -//~^ ERROR: cannot find function `bar` in `inherent_impl::S` +//~^ ERROR: no associated function or constant named `bar` found for struct `S` in the current scope reuse ::bar as trait_bar; reuse inherent_impl::X::foo as x_foo; -//~^ ERROR: cannot find function `foo` in `inherent_impl::X` +//~^ ERROR: ambiguous delegation to inherent impl function +//~| ERROR: multiple applicable items in scope fn main() {} diff --git a/tests/ui/delegation/inherent-impls-non-local-crate.stderr b/tests/ui/delegation/inherent-impls-non-local-crate.stderr index 870194eedd5ca..31358b1d7144e 100644 --- a/tests/ui/delegation/inherent-impls-non-local-crate.stderr +++ b/tests/ui/delegation/inherent-impls-non-local-crate.stderr @@ -1,29 +1,29 @@ error: ambiguous delegation to inherent impl function - --> $DIR/inherent-impls-non-local-crate.rs:22:25 + --> $DIR/inherent-impls-non-local-crate.rs:19:25 | LL | reuse inherent_impl::X::foo as x_foo; | ^^^ error[E0599]: no associated function or constant named `not_existing` found for struct `S` in the current scope - --> $DIR/inherent-impls-non-local-crate.rs:8:25 + --> $DIR/inherent-impls-non-local-crate.rs:7:25 | LL | reuse inherent_impl::S::not_existing; | ^^^^^^^^^^^^ associated function or constant not found in `S` error[E0599]: no associated function or constant named `TYPE` found for struct `S` in the current scope - --> $DIR/inherent-impls-non-local-crate.rs:11:25 + --> $DIR/inherent-impls-non-local-crate.rs:9:25 | LL | reuse inherent_impl::S::TYPE; | ^^^^ associated function or constant not found in `S` error[E0618]: expected function, found `usize` - --> $DIR/inherent-impls-non-local-crate.rs:14:25 + --> $DIR/inherent-impls-non-local-crate.rs:11:25 | LL | reuse inherent_impl::S::CONST; | ^^^^^ call expression requires function error[E0599]: no associated function or constant named `bar` found for struct `S` in the current scope - --> $DIR/inherent-impls-non-local-crate.rs:17:25 + --> $DIR/inherent-impls-non-local-crate.rs:14:25 | LL | reuse inherent_impl::S::bar; | ^^^ associated function or constant not found in `S` @@ -35,7 +35,7 @@ LL + use inherent_impl::Trait; | error[E0034]: multiple applicable items in scope - --> $DIR/inherent-impls-non-local-crate.rs:22:25 + --> $DIR/inherent-impls-non-local-crate.rs:19:25 | LL | reuse inherent_impl::X::foo as x_foo; | ^^^ multiple `foo` found diff --git a/tests/ui/delegation/inherent-impls-receiver-mapping.rs b/tests/ui/delegation/inherent-impls-receiver-mapping.rs index 05a9c350af746..476fb2075d280 100644 --- a/tests/ui/delegation/inherent-impls-receiver-mapping.rs +++ b/tests/ui/delegation/inherent-impls-receiver-mapping.rs @@ -15,36 +15,27 @@ mod receiver_mapping { impl Y { fn get_x(&self) -> X { X } reuse X::{static_f, by_value, by_ref, by_mut_ref} { self.get_x() } - //~^ ERROR: cannot find function `by_mut_ref` in `X` - //~| ERROR: cannot find function `by_ref` in `X` - //~| ERROR: cannot find function `by_value` in `X` - //~| ERROR: cannot find function `static_f` in `X` } fn check() { let y = Y; y.by_ref(); - //~^ ERROR: no method named `by_ref` found for struct `Y` in the current scope y.by_mut_ref(); - //~^ ERROR: no method named `by_mut_ref` found for struct `Y` in the current scope + //~^ ERROR: cannot borrow `y` as mutable, as it is not declared as mutable y.by_value(); - //~^ ERROR: no method named `by_value` found for struct `Y` in the current scope let y = &Y; y.by_value(); - //~^ ERROR: no method named `by_value` found for reference `&Y` in the current scope + //~^ ERROR: cannot move out of `*y` which is behind a shared reference y.by_ref(); - //~^ ERROR: no method named `by_ref` found for reference `&Y` in the current scope y.by_mut_ref(); - //~^ ERROR: no method named `by_mut_ref` found for reference `&Y` in the current scope + //~^ ERROR: cannot borrow `*y` as mutable, as it is behind a `&` reference let y = &mut Y; y.by_value(); - //~^ ERROR: no method named `by_value` found for mutable reference `&mut Y` in the current scope + //~^ ERROR: cannot move out of `*y` which is behind a mutable reference y.by_ref(); - //~^ ERROR: the method `by_ref` exists for mutable reference `&mut Y`, but its trait bounds were not satisfied y.by_mut_ref(); - //~^ ERROR: no method named `by_mut_ref` found for mutable reference `&mut Y` in the current scope } } @@ -59,12 +50,11 @@ mod self_type_mapping { struct W(X); impl W { reuse X::add { self.0 } - //~^ ERROR: cannot find function `add` in `X` } fn check() { W(X).add(W(X)); - //~^ ERROR: no method named `add` found for struct `W` in the current scope + //~^ ERROR: mismatched types } } diff --git a/tests/ui/delegation/inherent-impls-receiver-mapping.stderr b/tests/ui/delegation/inherent-impls-receiver-mapping.stderr index e98169c9c8c65..0c7263ffa43cb 100644 --- a/tests/ui/delegation/inherent-impls-receiver-mapping.stderr +++ b/tests/ui/delegation/inherent-impls-receiver-mapping.stderr @@ -1,5 +1,5 @@ error[E0308]: mismatched types - --> $DIR/inherent-impls-receiver-mapping.rs:66:18 + --> $DIR/inherent-impls-receiver-mapping.rs:56:18 | LL | W(X).add(W(X)); | --- ^^^^ expected `X`, found `W` @@ -7,44 +7,31 @@ LL | W(X).add(W(X)); | arguments to this method are incorrect | note: method defined here - --> $DIR/inherent-impls-receiver-mapping.rs:61:18 + --> $DIR/inherent-impls-receiver-mapping.rs:52:18 | LL | reuse X::add { self.0 } | ^^^ -error[E0382]: use of moved value: `y` - --> $DIR/inherent-impls-receiver-mapping.rs:28:9 +error[E0596]: cannot borrow `y` as mutable, as it is not declared as mutable + --> $DIR/inherent-impls-receiver-mapping.rs:23:9 | -LL | let y = Y; - | - move occurs because `y` has type `Y`, which does not implement the `Copy` trait -LL | y.by_ref(); - | -------- `y` moved due to this method call -LL | LL | y.by_mut_ref(); - | ^ value used here after move + | ^ cannot borrow as mutable | - = note: `receiver_mapping::Y::by_ref` takes ownership of the receiver `self`, which moves `y` - -error[E0382]: use of moved value: `y` - --> $DIR/inherent-impls-receiver-mapping.rs:30:9 +help: consider changing this to be mutable | -LL | let y = Y; - | - move occurs because `y` has type `Y`, which does not implement the `Copy` trait -... -LL | y.by_mut_ref(); - | ------------ `y` moved due to this method call -LL | -LL | y.by_value(); - | ^ value used here after move +LL | let mut y = Y; + | +++ error[E0507]: cannot move out of `*y` which is behind a shared reference - --> $DIR/inherent-impls-receiver-mapping.rs:34:9 + --> $DIR/inherent-impls-receiver-mapping.rs:28:9 | LL | y.by_value(); | ^ ---------- `*y` moved due to this method call | | | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait | + = note: `receiver_mapping::Y::by_value` takes ownership of the receiver `self`, which moves `*y` note: if `Y` implemented `Clone`, you could clone the value --> $DIR/inherent-impls-receiver-mapping.rs:13:5 | @@ -54,42 +41,19 @@ LL | struct Y; LL | y.by_value(); | - you could clone this value -error[E0507]: cannot move out of `*y` which is behind a shared reference - --> $DIR/inherent-impls-receiver-mapping.rs:36:9 - | -LL | y.by_ref(); - | ^ -------- `*y` moved due to this method call - | | - | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait - | -note: if `Y` implemented `Clone`, you could clone the value - --> $DIR/inherent-impls-receiver-mapping.rs:13:5 - | -LL | struct Y; - | ^^^^^^^^ consider implementing `Clone` for this type -... -LL | y.by_ref(); - | - you could clone this value - -error[E0507]: cannot move out of `*y` which is behind a shared reference - --> $DIR/inherent-impls-receiver-mapping.rs:38:9 +error[E0596]: cannot borrow `*y` as mutable, as it is behind a `&` reference + --> $DIR/inherent-impls-receiver-mapping.rs:31:9 | LL | y.by_mut_ref(); - | ^ ------------ `*y` moved due to this method call - | | - | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait + | ^ `y` is a `&` reference, so it cannot be borrowed as mutable | -note: if `Y` implemented `Clone`, you could clone the value - --> $DIR/inherent-impls-receiver-mapping.rs:13:5 +help: consider changing this to be a mutable reference | -LL | struct Y; - | ^^^^^^^^ consider implementing `Clone` for this type -... -LL | y.by_mut_ref(); - | - you could clone this value +LL | let y = &mut Y; + | +++ error[E0507]: cannot move out of `*y` which is behind a mutable reference - --> $DIR/inherent-impls-receiver-mapping.rs:42:9 + --> $DIR/inherent-impls-receiver-mapping.rs:35:9 | LL | y.by_value(); | ^ ---------- `*y` moved due to this method call @@ -105,41 +69,7 @@ LL | struct Y; LL | y.by_value(); | - you could clone this value -error[E0507]: cannot move out of `*y` which is behind a mutable reference - --> $DIR/inherent-impls-receiver-mapping.rs:44:9 - | -LL | y.by_ref(); - | ^ -------- `*y` moved due to this method call - | | - | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait - | -note: if `Y` implemented `Clone`, you could clone the value - --> $DIR/inherent-impls-receiver-mapping.rs:13:5 - | -LL | struct Y; - | ^^^^^^^^ consider implementing `Clone` for this type -... -LL | y.by_ref(); - | - you could clone this value - -error[E0507]: cannot move out of `*y` which is behind a mutable reference - --> $DIR/inherent-impls-receiver-mapping.rs:46:9 - | -LL | y.by_mut_ref(); - | ^ ------------ `*y` moved due to this method call - | | - | move occurs because `*y` has type `Y`, which does not implement the `Copy` trait - | -note: if `Y` implemented `Clone`, you could clone the value - --> $DIR/inherent-impls-receiver-mapping.rs:13:5 - | -LL | struct Y; - | ^^^^^^^^ consider implementing `Clone` for this type -... -LL | y.by_mut_ref(); - | - you could clone this value - -error: aborting due to 9 previous errors +error: aborting due to 5 previous errors -Some errors have detailed explanations: E0308, E0382, E0507. +Some errors have detailed explanations: E0308, E0507, E0596. For more information about an error, try `rustc --explain E0308`. From bdc9c7a6c298d0029df035a79bbc21d952c8e367 Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Thu, 13 Aug 2026 09:30:04 +0300 Subject: [PATCH 08/22] Ban infers in parent segments of delegations to inherent impls --- compiler/rustc_ast/src/ast.rs | 8 + .../src/delegation/generics.rs | 19 +- .../rustc_ast_lowering/src/diagnostics.rs | 7 + tests/ui/delegation/inherent-impls-enums.rs | 16 +- .../ui/delegation/inherent-impls-enums.stderr | 52 +++-- .../inherent-impls-parent-generics.rs | 18 ++ .../inherent-impls-parent-generics.stderr | 182 ++++++++++++++++-- tests/ui/delegation/inherent-impls-structs.rs | 16 +- .../delegation/inherent-impls-structs.stderr | 48 ++--- 9 files changed, 272 insertions(+), 94 deletions(-) diff --git a/compiler/rustc_ast/src/ast.rs b/compiler/rustc_ast/src/ast.rs index 426fc4e7be228..73b187bcf61e1 100644 --- a/compiler/rustc_ast/src/ast.rs +++ b/compiler/rustc_ast/src/ast.rs @@ -295,6 +295,14 @@ impl GenericArg { GenericArg::Const(ct) => ct.value.span, } } + + pub fn is_infer(&self) -> bool { + match self { + GenericArg::Lifetime(lt) => lt.ident.name == kw::UnderscoreLifetime, + GenericArg::Type(ty) => ty.is_maybe_parenthesised_infer(), + GenericArg::Const(_) => false, + } + } } /// A path like `Foo<'a, T>`. diff --git a/compiler/rustc_ast_lowering/src/delegation/generics.rs b/compiler/rustc_ast_lowering/src/delegation/generics.rs index 05cedfb9badd1..c1e98c364c8b8 100644 --- a/compiler/rustc_ast_lowering/src/delegation/generics.rs +++ b/compiler/rustc_ast_lowering/src/delegation/generics.rs @@ -13,6 +13,7 @@ use crate::LoweringContext; use crate::delegation::resolution::resolver::DelegationResolver; use crate::diagnostics::{ DelegationInfersMismatch, DelegationToInherentImplMustContainParentGenerics, + DelegationToInherentImplParentContainsInfer, }; #[derive(Debug, Clone, Copy, Eq, PartialEq)] @@ -465,8 +466,17 @@ impl<'hir> DelegationResolver<'_, 'hir> { let tcx = self.tcx(); match parent_args { - ParentSegmentArgs::Specified(..) => Ok(()), ParentSegmentArgs::Invalid => unreachable!(), + ParentSegmentArgs::Specified(args) => args + .args + .iter() + .all(|arg| { + let AngleBracketedArg::Arg(arg) = arg else { return false }; + !arg.is_infer() + }) + .ok_or_else(|| { + self.tcx().dcx().emit_err(DelegationToInherentImplParentContainsInfer { span }) + }), ParentSegmentArgs::NotSpecified => { let Some((did, _)) = self.opt_inherent_impl_adt(sig_id) else { unreachable!() }; @@ -503,12 +513,7 @@ impl<'hir> DelegationResolver<'_, 'hir> { let params = ¶ms[usize::from(add_first_self)..]; for (idx, (arg, param)) in args.args.iter().zip(params).enumerate() { let AngleBracketedArg::Arg(arg) = arg else { continue }; - - let is_infer = match arg { - GenericArg::Lifetime(lt) => lt.ident.name == kw::UnderscoreLifetime, - GenericArg::Type(ty) => ty.is_maybe_parenthesised_infer(), - GenericArg::Const(_) => false, - }; + let is_infer = arg.is_infer(); // If `'_` is used instead of `_` (or vice versa) we emit a meaningful // error instead of processing this infer or leaving it as is for signature diff --git a/compiler/rustc_ast_lowering/src/diagnostics.rs b/compiler/rustc_ast_lowering/src/diagnostics.rs index b5fa908d1483b..2542268712f98 100644 --- a/compiler/rustc_ast_lowering/src/diagnostics.rs +++ b/compiler/rustc_ast_lowering/src/diagnostics.rs @@ -623,3 +623,10 @@ pub(crate) struct DelegationToInherentImplMustContainParentGenerics { #[primary_span] pub span: Span, } + +#[derive(Diagnostic)] +#[diag("parent segment of delegation to inherent impl can not contain infers")] +pub(crate) struct DelegationToInherentImplParentContainsInfer { + #[primary_span] + pub span: Span, +} diff --git a/tests/ui/delegation/inherent-impls-enums.rs b/tests/ui/delegation/inherent-impls-enums.rs index 0e32a9aa2e44d..e8c7ba891b5ef 100644 --- a/tests/ui/delegation/inherent-impls-enums.rs +++ b/tests/ui/delegation/inherent-impls-enums.rs @@ -12,11 +12,11 @@ impl<'a, 'b, 'c, A: 'a, const C: usize> S<'a, A, C> { reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; reuse S::<'static, (), 1>::foo_static as foo_static_3; -reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; +reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1; reuse S::<'static, (), 1>::foo_self as foo_self_3; -reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; +reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; trait Trait<'a, AA, BB> where @@ -24,7 +24,7 @@ where { reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; reuse S::<'static, (), 1>::foo_static as foo_static_3; - reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; + reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; fn get_s(self) -> S<'static, (), 1> { panic!(); @@ -32,7 +32,7 @@ where reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } - reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; + reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; //~^ ERROR: mismatched types [E0308] } @@ -41,19 +41,19 @@ struct X; impl<'a, A, B> Trait<'a, A, B> for X { reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; reuse S::<'static, (), 1>::foo_static as foo_static_3; - reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; + reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; //~^ ERROR: type annotations needed [E0284] reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } - reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; + reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; //~^ ERROR: mismatched types [E0308] } impl X { reuse S::<'static, (), 1>::foo_static::<'static, (), true> as foo_static_1; reuse S::<'static, (), 1>::foo_static as foo_static_3; - reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; + reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; fn get_s(self) -> S<'static, (), 1> { panic!(); @@ -61,7 +61,7 @@ impl X { reuse S::<'static, (), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } reuse S::<'static, (), 1>::foo_self as foo_self_3 { self.get_s() } - reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; + reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; //~^ ERROR: mismatched types [E0308] } diff --git a/tests/ui/delegation/inherent-impls-enums.stderr b/tests/ui/delegation/inherent-impls-enums.stderr index b0de16aab5db7..d76aba9517ee4 100644 --- a/tests/ui/delegation/inherent-impls-enums.stderr +++ b/tests/ui/delegation/inherent-impls-enums.stderr @@ -1,16 +1,16 @@ error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:35:26 + --> $DIR/inherent-impls-enums.rs:35:32 | LL | trait Trait<'a, AA, BB> | ----------------------- found this type parameter ... -LL | reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ - | | - | expected `S<'_, A, 1>`, found type parameter `Self` - | arguments to this function are incorrect +LL | reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; + | ^^^^^^^^ + | | + | expected `S<'_, (), 1>`, found type parameter `Self` + | arguments to this function are incorrect | - = note: expected enum `S<'_, A, 1>` + = note: expected enum `S<'_, (), 1>` found type parameter `Self` note: method defined here --> $DIR/inherent-impls-enums.rs:10:8 @@ -19,10 +19,10 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- error[E0284]: type annotations needed - --> $DIR/inherent-impls-enums.rs:44:26 + --> $DIR/inherent-impls-enums.rs:44:32 | -LL | reuse S::<'_, _, 1>::foo_static::<'static, _, _> as foo_static_4; - | ^^^^^^^^^^ cannot infer the value of const parameter `B` declared on the associated function `foo_static` +LL | reuse S::<'static, (), 1>::foo_static::<'static, _, _> as foo_static_4; + | ^^^^^^^^^^ cannot infer the value of const parameter `B` declared on the associated function `foo_static` | note: required by a const generic parameter in `S::<'a, A, C>::foo_static` --> $DIR/inherent-impls-enums.rs:9:34 @@ -31,36 +31,32 @@ LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} | ^^^^^^^^^^^^^ required by this const generic parameter in `S::<'a, A, C>::foo_static` error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:49:26 + --> $DIR/inherent-impls-enums.rs:49:32 | -LL | reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ - | | - | expected `S<'_, _, 1>`, found `X` - | arguments to this function are incorrect +LL | reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; + | ^^^^^^^^ + | | + | expected `S<'_, (), 1>`, found `X` + | arguments to this function are incorrect | - = note: expected enum `S<'_, _, 1>` + = note: expected enum `S<'_, (), 1>` found struct `X` note: method defined here --> $DIR/inherent-impls-enums.rs:10:8 | LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- -help: try wrapping the expression in `S::A` - | -LL | reuse S::<'_, _, 1>::S::A(foo_self)::<'static, _, _> as foo_self_4; - | +++++ + error[E0308]: mismatched types - --> $DIR/inherent-impls-enums.rs:64:26 + --> $DIR/inherent-impls-enums.rs:64:32 | -LL | reuse S::<'_, _, 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ - | | - | expected `S<'_, A, 1>`, found `X` - | arguments to this function are incorrect +LL | reuse S::<'static, (), 1>::foo_self::<'static, _, _> as foo_self_4; + | ^^^^^^^^ + | | + | expected `S<'_, (), 1>`, found `X` + | arguments to this function are incorrect | - = note: expected enum `S<'_, A, 1>` + = note: expected enum `S<'_, (), 1>` found struct `X` note: method defined here --> $DIR/inherent-impls-enums.rs:10:8 diff --git a/tests/ui/delegation/inherent-impls-parent-generics.rs b/tests/ui/delegation/inherent-impls-parent-generics.rs index ca65495695975..1c303e16a0272 100644 --- a/tests/ui/delegation/inherent-impls-parent-generics.rs +++ b/tests/ui/delegation/inherent-impls-parent-generics.rs @@ -34,6 +34,15 @@ reuse E::<'static, (), 123>::foo_self as e5; reuse E::<'static, (), 123>::foo_static::<'static, (), true> as e6; reuse E::<'static, (), 123>::foo_self::<'static, (), true> as e7; +reuse E::<'_, (), _>::foo_static as e8; +//~^ ERROR: parent segment of delegation to inherent impl can not contain infers +//~| ERROR: type annotations needed +//~| ERROR: type annotations needed +//~| ERROR: type annotations needed +reuse E::<'_, _, _>::foo_self as e9; +//~^ ERROR: parent segment of delegation to inherent impl can not contain infers +//~| ERROR: this function takes 1 argument but 0 arguments were supplied + struct S { xd: [A; C], } @@ -66,4 +75,13 @@ reuse S::<(), 123>::foo_self as s5; reuse S::<(), 123>::foo_static::<'static, (), true> as s6; reuse S::<(), 123>::foo_self::<'static, (), true> as s7; +reuse S::<(), _>::foo_static as s8; +//~^ ERROR: parent segment of delegation to inherent impl can not contain infers +//~| ERROR: type annotations needed +//~| ERROR: type annotations needed +//~| ERROR: type annotations needed +reuse S::<_, 123>::foo_self as s9; +//~^ ERROR: parent segment of delegation to inherent impl can not contain infers +//~| ERROR: this function takes 1 argument but 0 arguments were supplied + fn main() {} diff --git a/tests/ui/delegation/inherent-impls-parent-generics.stderr b/tests/ui/delegation/inherent-impls-parent-generics.stderr index a99e5f69a7af3..b1001e193a9cd 100644 --- a/tests/ui/delegation/inherent-impls-parent-generics.stderr +++ b/tests/ui/delegation/inherent-impls-parent-generics.stderr @@ -22,30 +22,54 @@ error: delegation to inherent impl must contain parent generics LL | reuse E::foo_self::<'static, (), true> as e3; | ^^^^^^^^ +error: parent segment of delegation to inherent impl can not contain infers + --> $DIR/inherent-impls-parent-generics.rs:37:23 + | +LL | reuse E::<'_, (), _>::foo_static as e8; + | ^^^^^^^^^^ + +error: parent segment of delegation to inherent impl can not contain infers + --> $DIR/inherent-impls-parent-generics.rs:42:22 + | +LL | reuse E::<'_, _, _>::foo_self as e9; + | ^^^^^^^^ + error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-parent-generics.rs:46:10 + --> $DIR/inherent-impls-parent-generics.rs:55:10 | LL | reuse S::foo_static as s; | ^^^^^^^^^^ error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-parent-generics.rs:51:10 + --> $DIR/inherent-impls-parent-generics.rs:60:10 | LL | reuse S::foo_self as s1; | ^^^^^^^^ error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-parent-generics.rs:55:10 + --> $DIR/inherent-impls-parent-generics.rs:64:10 | LL | reuse S::foo_static::<'static, (), true> as s2; | ^^^^^^^^^^ error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-parent-generics.rs:59:10 + --> $DIR/inherent-impls-parent-generics.rs:68:10 | LL | reuse S::foo_self::<'static, (), true> as s3; | ^^^^^^^^ +error: parent segment of delegation to inherent impl can not contain infers + --> $DIR/inherent-impls-parent-generics.rs:78:19 + | +LL | reuse S::<(), _>::foo_static as s8; + | ^^^^^^^^^^ + +error: parent segment of delegation to inherent impl can not contain infers + --> $DIR/inherent-impls-parent-generics.rs:83:20 + | +LL | reuse S::<_, 123>::foo_self as s9; + | ^^^^^^^^ + error[E0284]: type annotations needed --> $DIR/inherent-impls-parent-generics.rs:14:10 | @@ -171,7 +195,67 @@ LL | reuse E::foo_self(/* value */)::<'static, (), true> as e3; | +++++++++++++ error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:46:10 + --> $DIR/inherent-impls-parent-generics.rs:37:23 + | +LL | reuse E::<'_, (), _>::foo_static as e8; + | -------------- ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` + | | + | type must be known at this point + | +note: required by a const generic parameter in `E` + --> $DIR/inherent-impls-parent-generics.rs:4:23 + | +LL | enum E<'a: 'a, A: 'a, const C: usize> { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `E` + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:37:23 + | +LL | reuse E::<'_, (), _>::foo_static as e8; + | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` + | +note: required by a const generic parameter in `E::<'a, A, C>::foo_static` + --> $DIR/inherent-impls-parent-generics.rs:9:25 + | +LL | impl<'a, 'b, 'c, A: 'a, const C: usize> E<'a, A, C> { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ---------- required by a bound in this associated function + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:37:23 + | +LL | reuse E::<'_, (), _>::foo_static as e8; + | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` + | +note: required by a const generic parameter in `E::<'a, A, C>::foo_static` + --> $DIR/inherent-impls-parent-generics.rs:10:34 + | +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` +help: consider specifying the generic arguments + | +LL | reuse E::<'_, (), _>::foo_static:: as e8; + | ++++++++ + +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-parent-generics.rs:42:22 + | +LL | reuse E::<'_, _, _>::foo_self as e9; + | ^^^^^^^^ argument #1 of type `E<'_, _, _>` is missing + | +note: method defined here + --> $DIR/inherent-impls-parent-generics.rs:11:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse E::<'_, _, _>::foo_self(/* value */) as e9; + | +++++++++++++ + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:55:10 | LL | reuse S::foo_static as s; | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` @@ -179,7 +263,7 @@ LL | reuse S::foo_static as s; | type must be known at this point | note: required by a const generic parameter in `S` - --> $DIR/inherent-impls-parent-generics.rs:37:13 + --> $DIR/inherent-impls-parent-generics.rs:46:13 | LL | struct S { | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` @@ -189,13 +273,13 @@ LL | reuse S::::foo_static as s; | ++++++++ error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:46:10 + --> $DIR/inherent-impls-parent-generics.rs:55:10 | LL | reuse S::foo_static as s; | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` | note: required by a const generic parameter in `S::::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:41:21 + --> $DIR/inherent-impls-parent-generics.rs:50:21 | LL | impl<'a, 'b, 'c, A, const C: usize> S { | ^^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` @@ -207,13 +291,13 @@ LL | reuse S::::foo_static as s; | ++++++++ error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:46:10 + --> $DIR/inherent-impls-parent-generics.rs:55:10 | LL | reuse S::foo_static as s; | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` | note: required by a const generic parameter in `S::::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:42:34 + --> $DIR/inherent-impls-parent-generics.rs:51:34 | LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} | ^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` @@ -223,13 +307,13 @@ LL | reuse S::foo_static:: as s; | ++++++++ error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-parent-generics.rs:51:10 + --> $DIR/inherent-impls-parent-generics.rs:60:10 | LL | reuse S::foo_self as s1; | ^^^^^^^^ argument #1 of type `S<_, _>` is missing | note: method defined here - --> $DIR/inherent-impls-parent-generics.rs:43:8 + --> $DIR/inherent-impls-parent-generics.rs:52:8 | LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- @@ -239,7 +323,7 @@ LL | reuse S::foo_self(/* value */) as s1; | +++++++++++++ error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:55:10 + --> $DIR/inherent-impls-parent-generics.rs:64:10 | LL | reuse S::foo_static::<'static, (), true> as s2; | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` @@ -247,7 +331,7 @@ LL | reuse S::foo_static::<'static, (), true> as s2; | type must be known at this point | note: required by a const generic parameter in `S` - --> $DIR/inherent-impls-parent-generics.rs:37:13 + --> $DIR/inherent-impls-parent-generics.rs:46:13 | LL | struct S { | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` @@ -257,13 +341,13 @@ LL | reuse S::::foo_static::<'static, (), true> as s2; | ++++++++ error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:55:10 + --> $DIR/inherent-impls-parent-generics.rs:64:10 | LL | reuse S::foo_static::<'static, (), true> as s2; | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` | note: required by a const generic parameter in `S::::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:41:21 + --> $DIR/inherent-impls-parent-generics.rs:50:21 | LL | impl<'a, 'b, 'c, A, const C: usize> S { | ^^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` @@ -275,13 +359,13 @@ LL | reuse S::::foo_static::<'static, (), true> as s2; | ++++++++ error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-parent-generics.rs:59:10 + --> $DIR/inherent-impls-parent-generics.rs:68:10 | LL | reuse S::foo_self::<'static, (), true> as s3; | ^^^^^^^^ argument #1 of type `S<_, _>` is missing | note: method defined here - --> $DIR/inherent-impls-parent-generics.rs:43:8 + --> $DIR/inherent-impls-parent-generics.rs:52:8 | LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- @@ -290,7 +374,67 @@ help: provide the argument LL | reuse S::foo_self(/* value */)::<'static, (), true> as s3; | +++++++++++++ -error: aborting due to 22 previous errors +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:78:19 + | +LL | reuse S::<(), _>::foo_static as s8; + | ---------- ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` + | | + | type must be known at this point + | +note: required by a const generic parameter in `S` + --> $DIR/inherent-impls-parent-generics.rs:46:13 + | +LL | struct S { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:78:19 + | +LL | reuse S::<(), _>::foo_static as s8; + | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` + | +note: required by a const generic parameter in `S::::foo_static` + --> $DIR/inherent-impls-parent-generics.rs:50:21 + | +LL | impl<'a, 'b, 'c, A, const C: usize> S { + | ^^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ---------- required by a bound in this associated function + +error[E0284]: type annotations needed + --> $DIR/inherent-impls-parent-generics.rs:78:19 + | +LL | reuse S::<(), _>::foo_static as s8; + | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` + | +note: required by a const generic parameter in `S::::foo_static` + --> $DIR/inherent-impls-parent-generics.rs:51:34 + | +LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + | ^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` +help: consider specifying the generic arguments + | +LL | reuse S::<(), _>::foo_static:: as s8; + | ++++++++ + +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/inherent-impls-parent-generics.rs:83:20 + | +LL | reuse S::<_, 123>::foo_self as s9; + | ^^^^^^^^ argument #1 of type `S<_, 123>` is missing + | +note: method defined here + --> $DIR/inherent-impls-parent-generics.rs:52:8 + | +LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + | ^^^^^^^^ ---- +help: provide the argument + | +LL | reuse S::<_, 123>::foo_self(/* value */) as s9; + | +++++++++++++ + +error: aborting due to 34 previous errors Some errors have detailed explanations: E0061, E0284. For more information about an error, try `rustc --explain E0061`. diff --git a/tests/ui/delegation/inherent-impls-structs.rs b/tests/ui/delegation/inherent-impls-structs.rs index 86557cbe6362c..f7a9d362dd9ca 100644 --- a/tests/ui/delegation/inherent-impls-structs.rs +++ b/tests/ui/delegation/inherent-impls-structs.rs @@ -11,16 +11,16 @@ impl<'a, 'b, 'c, A, const C: usize> S { reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; reuse S::<(), 1>::foo_static as foo_static_3; -reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; +reuse S::::foo_static::<'static, _, _> as foo_static_4; reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1; reuse S::<(), 1>::foo_self as foo_self_3; -reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; +reuse S::::foo_self::<'static, _, _> as foo_self_4; trait Trait<'a, AA, BB> where Self: Sized { reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; reuse S::<(), 1>::foo_static as foo_static_3; - reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; + reuse S::<(), 1>::foo_static::<'static, _, _> as foo_static_4; fn get_s(self) -> S<(), 1> { panic!(); @@ -28,7 +28,7 @@ trait Trait<'a, AA, BB> where Self: Sized { reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } - reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; + reuse S::<(), 1>::foo_self::<'static, _, _> as foo_self_4; //~^ ERROR: mismatched types [E0308] } @@ -37,19 +37,19 @@ struct X; impl<'a, A, B> Trait<'a, A, B> for X { reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; reuse S::<(), 1>::foo_static as foo_static_3; - reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; + reuse S::<(), 1>::foo_static::<'static, _, _> as foo_static_4; //~^ ERROR: type annotations needed [E0284] reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } - reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; + reuse S::<(), 1>::foo_self::<'static, _, _> as foo_self_4; //~^ ERROR: mismatched types [E0308] } impl X { reuse S::<(), 1>::foo_static::<'static, (), true> as foo_static_1; reuse S::<(), 1>::foo_static as foo_static_3; - reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; + reuse S::<(), 1>::foo_static::<'static, _, _> as foo_static_4; fn get_s(self) -> S<(), 1> { panic!(); @@ -57,7 +57,7 @@ impl X { reuse S::<(), 1>::foo_self::<'static, (), true> as foo_self_1 { self.get_s() } reuse S::<(), 1>::foo_self as foo_self_3 { self.get_s() } - reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; + reuse S::<(), 1>::foo_self::<'static, _, _> as foo_self_4; //~^ ERROR: mismatched types [E0308] } diff --git a/tests/ui/delegation/inherent-impls-structs.stderr b/tests/ui/delegation/inherent-impls-structs.stderr index 1956b5655fe25..29963431b1451 100644 --- a/tests/ui/delegation/inherent-impls-structs.stderr +++ b/tests/ui/delegation/inherent-impls-structs.stderr @@ -1,16 +1,16 @@ error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:31:22 + --> $DIR/inherent-impls-structs.rs:31:23 | LL | trait Trait<'a, AA, BB> where Self: Sized { | ----------------------- found this type parameter ... -LL | reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ - | | - | expected `S`, found type parameter `Self` - | arguments to this function are incorrect +LL | reuse S::<(), 1>::foo_self::<'static, _, _> as foo_self_4; + | ^^^^^^^^ + | | + | expected `S<(), 1>`, found type parameter `Self` + | arguments to this function are incorrect | - = note: expected struct `S` + = note: expected struct `S<(), 1>` found type parameter `Self` note: method defined here --> $DIR/inherent-impls-structs.rs:9:8 @@ -19,10 +19,10 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- error[E0284]: type annotations needed - --> $DIR/inherent-impls-structs.rs:40:22 + --> $DIR/inherent-impls-structs.rs:40:23 | -LL | reuse S::<_, 1>::foo_static::<'static, _, _> as foo_static_4; - | ^^^^^^^^^^ cannot infer the value of const parameter `B` declared on the associated function `foo_static` +LL | reuse S::<(), 1>::foo_static::<'static, _, _> as foo_static_4; + | ^^^^^^^^^^ cannot infer the value of const parameter `B` declared on the associated function `foo_static` | note: required by a const generic parameter in `S::::foo_static` --> $DIR/inherent-impls-structs.rs:8:34 @@ -31,15 +31,15 @@ LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} | ^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:45:22 + --> $DIR/inherent-impls-structs.rs:45:23 | -LL | reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ - | | - | expected `S<_, 1>`, found `X` - | arguments to this function are incorrect +LL | reuse S::<(), 1>::foo_self::<'static, _, _> as foo_self_4; + | ^^^^^^^^ + | | + | expected `S<(), 1>`, found `X` + | arguments to this function are incorrect | - = note: expected struct `S<_, 1>` + = note: expected struct `S<(), 1>` found struct `X` note: method defined here --> $DIR/inherent-impls-structs.rs:9:8 @@ -48,15 +48,15 @@ LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- error[E0308]: mismatched types - --> $DIR/inherent-impls-structs.rs:60:22 + --> $DIR/inherent-impls-structs.rs:60:23 | -LL | reuse S::<_, 1>::foo_self::<'static, _, _> as foo_self_4; - | ^^^^^^^^ - | | - | expected `S`, found `X` - | arguments to this function are incorrect +LL | reuse S::<(), 1>::foo_self::<'static, _, _> as foo_self_4; + | ^^^^^^^^ + | | + | expected `S<(), 1>`, found `X` + | arguments to this function are incorrect | - = note: expected struct `S` + = note: expected struct `S<(), 1>` found struct `X` note: method defined here --> $DIR/inherent-impls-structs.rs:9:8 From 64aab4f5660870e5b1abb5ace5d1c89f66de3a7d Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Thu, 13 Aug 2026 10:22:44 +0300 Subject: [PATCH 09/22] Fix arguments mapping, remove not needed check --- .../src/delegation/resolution.rs | 24 +------------ compiler/rustc_hir_analysis/src/delegation.rs | 14 +++++--- compiler/rustc_middle/src/ty/generic_args.rs | 35 ++++++++++++------- .../inherent-impls-wrong-header-args-ice.rs | 6 ++-- ...nherent-impls-wrong-header-args-ice.stderr | 32 +++++++++-------- 5 files changed, 55 insertions(+), 56 deletions(-) diff --git a/compiler/rustc_ast_lowering/src/delegation/resolution.rs b/compiler/rustc_ast_lowering/src/delegation/resolution.rs index f953079f0f90f..b784c1e02f952 100644 --- a/compiler/rustc_ast_lowering/src/delegation/resolution.rs +++ b/compiler/rustc_ast_lowering/src/delegation/resolution.rs @@ -10,7 +10,7 @@ use rustc_data_structures::steal::Steal; use rustc_hir as hir; use rustc_middle::ty::{ self, AssocKind, DelegationInhFuncKind, Ty, TyCtxt, TypeRelativeDelegationRes, - TypeSuperVisitable, TypeVisitable, TypeVisitableExt, TypeVisitor, + TypeSuperVisitable, TypeVisitable, TypeVisitor, }; use rustc_span::def_id::{DefId, LocalDefId}; use rustc_span::{ErrorGuaranteed, Span}; @@ -208,7 +208,6 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { // in illegal places such as function bodies in extern blocks (see #151356). let sig_id = self.resolve_delegation_sig(def_id, span)?; - self.check_inherent_impl_generic_args(sig_id, span)?; self.check_for_cycles(sig_id, span)?; let is_method = tcx.is_method(sig_id); @@ -241,27 +240,6 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { Ok((res, self.resolve_and_generate_generics(delegation, sig_id, span)?)) } - /// See tests\ui\delegation\inherent-impls-wrong-header-args-ice.rs, - /// there might be situations when not all generic args are supplied - /// to a struct/enum in an impl, in this case there will be ICEs when - /// trying to instantiate signature or predicates, so we would emit delayed - /// bug here and will not process this delegation further. - fn check_inherent_impl_generic_args( - &self, - sig_id: DefId, - span: Span, - ) -> Result<(), ErrorGuaranteed> { - self.opt_inherent_impl_adt(sig_id) - .map(|(_, args)| { - (!args.iter().any(|a| a.references_error())).ok_or_else(|| { - self.tcx() - .dcx() - .span_delayed_bug(span, "incorrect generic args in inherent impl") - }) - }) - .unwrap_or(Ok(())) - } - pub(super) fn opt_inherent_impl_adt( &self, sig_id: DefId, diff --git a/compiler/rustc_hir_analysis/src/delegation.rs b/compiler/rustc_hir_analysis/src/delegation.rs index 7d78d947573cc..2e392730e80f7 100644 --- a/compiler/rustc_hir_analysis/src/delegation.rs +++ b/compiler/rustc_hir_analysis/src/delegation.rs @@ -185,13 +185,13 @@ fn create_mapping<'tcx>( unreachable!("parent of inherent function in delegation can be only struct or enum") }; - args.iter().flat_map(|a| a.opt_param_info()).collect::>() + args.iter().map(|a| a.opt_param_info()).collect::>() } FnKind::AssocTrait => parent_generics .expect("trait must have generics") .own_params .iter() - .map(|p| (p.index as u32, p.kind.is_ty_or_const())) + .map(|p| (Some(p.index as u32), p.kind.is_ty_or_const())) .collect::>(), _ => vec![], }; @@ -205,7 +205,10 @@ fn create_mapping<'tcx>( for i in (has_self as usize)..parent_params.len() { let (index, is_ty_or_const) = parent_params[i]; if !is_ty_or_const { - mapping.insert(index, args_index as u32); + if let Some(index) = index { + mapping.insert(index, args_index as u32); + } + args_index += 1; } } @@ -231,7 +234,10 @@ fn create_mapping<'tcx>( for i in (has_self as usize)..parent_params.len() { let (index, is_ty_or_const) = parent_params[i]; if is_ty_or_const { - mapping.insert(index, args_index as u32); + if let Some(index) = index { + mapping.insert(index, args_index as u32); + } + args_index += 1; } } diff --git a/compiler/rustc_middle/src/ty/generic_args.rs b/compiler/rustc_middle/src/ty/generic_args.rs index 18deada559e40..cf65e3f9443bf 100644 --- a/compiler/rustc_middle/src/ty/generic_args.rs +++ b/compiler/rustc_middle/src/ty/generic_args.rs @@ -317,20 +317,29 @@ impl<'tcx> GenericArg<'tcx> { TypeWalker::new(self) } - pub fn opt_param_info(self) -> Option<(u32 /* index */, bool /* is ty or const */)> { + pub fn opt_param_info(self) -> (Option /* index */, bool /* is ty or const */) { match self.kind() { - GenericArgKind::Lifetime(r) => match r.kind() { - RegionKind::ReEarlyParam(p) => Some((p.index, false)), - _ => None, - }, - GenericArgKind::Type(t) => match t.kind() { - ty::Param(p) => Some((p.index, true)), - _ => None, - }, - GenericArgKind::Const(c) => match c.kind() { - ConstKind::Param(p) => Some((p.index, true)), - _ => None, - }, + GenericArgKind::Lifetime(r) => ( + match r.kind() { + RegionKind::ReEarlyParam(p) => Some(p.index), + _ => None, + }, + false, + ), + GenericArgKind::Type(t) => ( + match t.kind() { + ty::Param(p) => Some(p.index), + _ => None, + }, + true, + ), + GenericArgKind::Const(c) => ( + match c.kind() { + ConstKind::Param(p) => Some(p.index), + _ => None, + }, + true, + ), } } } diff --git a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs index d17c387547e98..90c329ea6a69c 100644 --- a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs +++ b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.rs @@ -10,8 +10,10 @@ impl<'a, 'b, 'c, A, const C: usize> S { } trait Trait<'a, AA, BB> where Self: Sized { - reuse S::foo_self; - //~^ ERROR: this function takes 1 argument but 0 arguments were supplied + reuse S::<(), ()>::foo_self; + //~^ ERROR: inferred lifetimes are not allowed in delegations as we need to inherit signature + //~| ERROR: type provided when a constant was expected + //~| ERROR: type provided when a constant was expected } fn main() {} diff --git a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr index c2005837b47e4..bda4c7ceab9e8 100644 --- a/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr +++ b/tests/ui/delegation/inherent-impls-wrong-header-args-ice.stderr @@ -9,23 +9,27 @@ help: indicate the anonymous lifetime LL | impl<'a, 'b, 'c, A, const C: usize> S<'_, A, C> { | +++ -error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-wrong-header-args-ice.rs:13:14 +error: inferred lifetimes are not allowed in delegations as we need to inherit signature + --> $DIR/inherent-impls-wrong-header-args-ice.rs:13:15 | -LL | reuse S::foo_self; - | ^^^^^^^^ argument #1 is missing +LL | reuse S::<(), ()>::foo_self; + | ^ + +error[E0747]: type provided when a constant was expected + --> $DIR/inherent-impls-wrong-header-args-ice.rs:13:19 | -note: method defined here - --> $DIR/inherent-impls-wrong-header-args-ice.rs:9:8 +LL | reuse S::<(), ()>::foo_self; + | ^^ + +error[E0747]: type provided when a constant was expected + --> $DIR/inherent-impls-wrong-header-args-ice.rs:13:19 | -LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} - | ^^^^^^^^ ---- -help: provide the argument +LL | reuse S::<(), ()>::foo_self; + | ^^ | -LL | reuse S::foo_self(/* value */); - | +++++++++++++ + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` -error: aborting due to 2 previous errors +error: aborting due to 4 previous errors -Some errors have detailed explanations: E0061, E0726. -For more information about an error, try `rustc --explain E0061`. +Some errors have detailed explanations: E0726, E0747. +For more information about an error, try `rustc --explain E0726`. From a2a1393136ed64943e704fe6e0fe6835a08f9e1f Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Mon, 17 Aug 2026 10:43:49 +0300 Subject: [PATCH 10/22] Fix not adjusting all signature when delegating to inherent impl --- compiler/rustc_hir_analysis/src/delegation.rs | 23 ++++++++------- .../inherent-impls-receiver-mapping.rs | 3 +- .../inherent-impls-receiver-mapping.stderr | 27 +++++++++++++---- .../delegation/inherent-impls-self-mapping.rs | 4 +-- .../inherent-impls-self-mapping.stderr | 29 +++++++++++++++---- 5 files changed, 61 insertions(+), 25 deletions(-) diff --git a/compiler/rustc_hir_analysis/src/delegation.rs b/compiler/rustc_hir_analysis/src/delegation.rs index 2e392730e80f7..1bf9d3b63d6d9 100644 --- a/compiler/rustc_hir_analysis/src/delegation.rs +++ b/compiler/rustc_hir_analysis/src/delegation.rs @@ -634,30 +634,31 @@ fn adjust_sig_in_inherent_impl_cases<'tcx>( return; } - let self_input = sig[0]; - let kinds @ (def_kind, _) = fn_kinds(tcx, def_id, sig_id); + if def_kind == FnKind::Free { + return; + } - sig[0] = match kinds { - (_, FnKind::AssocInherentImpl) => { - let ty::Adt(def, _) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { - unreachable!("delegation is supported only to struct or enums") - }; + if matches!(kinds, (_, FnKind::AssocInherentImpl)) { + let ty::Adt(def, _) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { + unreachable!("delegation is supported only to struct or enums") + }; + for i in 0..sig.len() { let sig_self_type = Ty::new_adt(tcx, *def, tcx.mk_args(parent_args)); let replacement = match def_kind { + FnKind::Free => unreachable!(), + FnKind::AssocTrait => Ty::new_param(tcx, 0, kw::SelfUpper), - FnKind::Free => sig_self_type, _ => tcx .type_of(tcx.parent(def_id.to_def_id())) .instantiate_identity() .skip_norm_wip(), }; - self_input.replace(tcx, sig_self_type, replacement) + sig[i] = sig[i].replace(tcx, sig_self_type, replacement); } - _ => sig[0], - }; + } } // Creates user-specified generic arguments from delegation path, diff --git a/tests/ui/delegation/inherent-impls-receiver-mapping.rs b/tests/ui/delegation/inherent-impls-receiver-mapping.rs index 476fb2075d280..d4678134e5de1 100644 --- a/tests/ui/delegation/inherent-impls-receiver-mapping.rs +++ b/tests/ui/delegation/inherent-impls-receiver-mapping.rs @@ -50,11 +50,12 @@ mod self_type_mapping { struct W(X); impl W { reuse X::add { self.0 } + //~^ ERROR: mismatched types + //~| ERROR: mismatched types } fn check() { W(X).add(W(X)); - //~^ ERROR: mismatched types } } diff --git a/tests/ui/delegation/inherent-impls-receiver-mapping.stderr b/tests/ui/delegation/inherent-impls-receiver-mapping.stderr index 0c7263ffa43cb..60982076f4acd 100644 --- a/tests/ui/delegation/inherent-impls-receiver-mapping.stderr +++ b/tests/ui/delegation/inherent-impls-receiver-mapping.stderr @@ -1,16 +1,31 @@ error[E0308]: mismatched types - --> $DIR/inherent-impls-receiver-mapping.rs:56:18 + --> $DIR/inherent-impls-receiver-mapping.rs:52:18 | -LL | W(X).add(W(X)); - | --- ^^^^ expected `X`, found `W` - | | - | arguments to this method are incorrect +LL | reuse X::add { self.0 } + | ^^^ + | | + | expected `X`, found `W` + | arguments to this function are incorrect | note: method defined here + --> $DIR/inherent-impls-receiver-mapping.rs:45:12 + | +LL | fn add(self, other: Self) -> Self { + | ^^^ ----------- + +error[E0308]: mismatched types --> $DIR/inherent-impls-receiver-mapping.rs:52:18 | LL | reuse X::add { self.0 } | ^^^ + | | + | expected `W`, found `X` + | expected `W` because of return type + | +help: try wrapping the expression in `self_type_mapping::W` + | +LL | reuse X::self_type_mapping::W(add) { self.0 } + | +++++++++++++++++++++ + error[E0596]: cannot borrow `y` as mutable, as it is not declared as mutable --> $DIR/inherent-impls-receiver-mapping.rs:23:9 @@ -69,7 +84,7 @@ LL | struct Y; LL | y.by_value(); | - you could clone this value -error: aborting due to 5 previous errors +error: aborting due to 6 previous errors Some errors have detailed explanations: E0308, E0507, E0596. For more information about an error, try `rustc --explain E0308`. diff --git a/tests/ui/delegation/inherent-impls-self-mapping.rs b/tests/ui/delegation/inherent-impls-self-mapping.rs index 36aef3a7bc7d8..9c13c13786fa7 100644 --- a/tests/ui/delegation/inherent-impls-self-mapping.rs +++ b/tests/ui/delegation/inherent-impls-self-mapping.rs @@ -11,10 +11,10 @@ impl X { trait Trait { reuse X::foo; - //~^ ERROR: cannot find function `foo` in `X` + //~^ ERROR: arguments to this function are incorrect + //~| ERROR: mismatched types } reuse X::foo; -//~^ ERROR: cannot find function `foo` in `X` fn main() {} diff --git a/tests/ui/delegation/inherent-impls-self-mapping.stderr b/tests/ui/delegation/inherent-impls-self-mapping.stderr index d372383d8e344..82ea263a8513b 100644 --- a/tests/ui/delegation/inherent-impls-self-mapping.stderr +++ b/tests/ui/delegation/inherent-impls-self-mapping.stderr @@ -1,22 +1,41 @@ -error[E0308]: mismatched types +error[E0308]: arguments to this function are incorrect --> $DIR/inherent-impls-self-mapping.rs:13:14 | LL | trait Trait { - | ----------- found this type parameter + | ----------- + | | + | found this type parameter + | found this type parameter LL | reuse X::foo; | ^^^ | | | expected `Rc>`, found `Rc>` - | arguments to this function are incorrect + | expected `Box>`, found `Box>` | = note: expected struct `Rc>` found struct `Rc>` + = note: expected struct `Box>` + found struct `Box>` note: method defined here --> $DIR/inherent-impls-self-mapping.rs:7:8 | LL | fn foo(self: Rc>, other: Box>) -> Option> { - | ^^^ ---- + | ^^^ ---- -------------------- + +error[E0308]: mismatched types + --> $DIR/inherent-impls-self-mapping.rs:13:14 + | +LL | trait Trait { + | ----------- expected this type parameter +LL | reuse X::foo; + | ^^^ + | | + | expected `Option>`, found `Option>` + | expected `Option>` because of return type + | + = note: expected enum `Option>` + found enum `Option>` -error: aborting due to 1 previous error +error: aborting due to 2 previous errors For more information about this error, try `rustc --explain E0308`. From d07ebcd9a30b985cb0f50d1e589ccb804636dae6 Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Mon, 17 Aug 2026 15:28:55 +0300 Subject: [PATCH 11/22] Cleanups --- compiler/rustc_hir_analysis/src/delegation.rs | 43 ++++++++----------- 1 file changed, 17 insertions(+), 26 deletions(-) diff --git a/compiler/rustc_hir_analysis/src/delegation.rs b/compiler/rustc_hir_analysis/src/delegation.rs index 1bf9d3b63d6d9..8ae9d79d85149 100644 --- a/compiler/rustc_hir_analysis/src/delegation.rs +++ b/compiler/rustc_hir_analysis/src/delegation.rs @@ -635,29 +635,24 @@ fn adjust_sig_in_inherent_impl_cases<'tcx>( } let kinds @ (def_kind, _) = fn_kinds(tcx, def_id, sig_id); - if def_kind == FnKind::Free { + if def_kind == FnKind::Free || !matches!(kinds, (_, FnKind::AssocInherentImpl)) { return; } - if matches!(kinds, (_, FnKind::AssocInherentImpl)) { - let ty::Adt(def, _) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { - unreachable!("delegation is supported only to struct or enums") - }; + let ty::Adt(def, _) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { + unreachable!("delegation is supported only to struct or enums") + }; - for i in 0..sig.len() { - let sig_self_type = Ty::new_adt(tcx, *def, tcx.mk_args(parent_args)); - let replacement = match def_kind { - FnKind::Free => unreachable!(), + for i in 0..sig.len() { + let sig_self_type = Ty::new_adt(tcx, *def, tcx.mk_args(parent_args)); + let replacement = match def_kind { + FnKind::Free => unreachable!(), - FnKind::AssocTrait => Ty::new_param(tcx, 0, kw::SelfUpper), - _ => tcx - .type_of(tcx.parent(def_id.to_def_id())) - .instantiate_identity() - .skip_norm_wip(), - }; + FnKind::AssocTrait => Ty::new_param(tcx, 0, kw::SelfUpper), + _ => tcx.type_of(tcx.parent(def_id.to_def_id())).instantiate_identity().skip_norm_wip(), + }; - sig[i] = sig[i].replace(tcx, sig_self_type, replacement); - } + sig[i] = sig[i].replace(tcx, sig_self_type, replacement); } } @@ -703,16 +698,12 @@ pub(crate) fn delegation_user_specified_args<'tcx>( let parent_args = if matches!(tcx.def_kind(parent), DefKind::Impl { of_trait: false }) { ty::GenericArgs::identity_for_item(tcx, parent).as_slice() + } else if let Some(parent_args) = parent_args { + parent_args + } else if matches!(tcx.def_kind(parent), DefKind::Trait) { + ty::GenericArgs::identity_for_item(tcx, parent).as_slice() } else { - if let Some(parent_args) = parent_args { - parent_args - } else { - if matches!(tcx.def_kind(parent), DefKind::Trait) { - ty::GenericArgs::identity_for_item(tcx, parent).as_slice() - } else { - &[] - } - } + &[] }; let args = lowerer From 32a7a40f40e81a58dc0613b195d504c7f03194f0 Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Mon, 17 Aug 2026 15:33:43 +0300 Subject: [PATCH 12/22] Cleanups --- compiler/rustc_hir_analysis/src/delegation.rs | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/compiler/rustc_hir_analysis/src/delegation.rs b/compiler/rustc_hir_analysis/src/delegation.rs index 8ae9d79d85149..cf628bbd874d6 100644 --- a/compiler/rustc_hir_analysis/src/delegation.rs +++ b/compiler/rustc_hir_analysis/src/delegation.rs @@ -696,12 +696,13 @@ pub(crate) fn delegation_user_specified_args<'tcx>( .map(|(segment, def_id)| { let parent = tcx.parent(def_id); - let parent_args = if matches!(tcx.def_kind(parent), DefKind::Impl { of_trait: false }) { + let parent_args = if matches!( + tcx.def_kind(parent), + DefKind::Impl { of_trait: false } | DefKind::Trait + ) { ty::GenericArgs::identity_for_item(tcx, parent).as_slice() } else if let Some(parent_args) = parent_args { parent_args - } else if matches!(tcx.def_kind(parent), DefKind::Trait) { - ty::GenericArgs::identity_for_item(tcx, parent).as_slice() } else { &[] }; From c483069fc164fc13d0f89cd73065cb142864ca5d Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Mon, 24 Aug 2026 13:53:15 +0300 Subject: [PATCH 13/22] Comment + add test for rename --- compiler/rustc_resolve/src/late.rs | 1 + tests/ui/delegation/inherent-impls-rename.rs | 3 ++- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/compiler/rustc_resolve/src/late.rs b/compiler/rustc_resolve/src/late.rs index b6507f94973c7..95586ced9a975 100644 --- a/compiler/rustc_resolve/src/late.rs +++ b/compiler/rustc_resolve/src/late.rs @@ -3779,6 +3779,7 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { if let Some(self_type_def_id) = self_type_def_id { this.fill_delegation_inh_functions_map( self_type_def_id, + // If rename is specified then ident equals rename. &delegation.ident, ); } diff --git a/tests/ui/delegation/inherent-impls-rename.rs b/tests/ui/delegation/inherent-impls-rename.rs index 7b6e1e4b7cddc..6a0fd672cf8e5 100644 --- a/tests/ui/delegation/inherent-impls-rename.rs +++ b/tests/ui/delegation/inherent-impls-rename.rs @@ -1,3 +1,5 @@ +//@ check-pass + #![feature(fn_delegation)] struct X; @@ -9,6 +11,5 @@ impl X { } reuse X::bar; -//~^ ERROR: cannot find function `bar` in `X` fn main() {} From e8f3a356f53e89c994eae9e6d4b58e13c351102b Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Tue, 25 Aug 2026 11:03:42 +0300 Subject: [PATCH 14/22] Fix tests --- tests/ui/delegation/inherent-impls-rename.stderr | 9 --------- 1 file changed, 9 deletions(-) delete mode 100644 tests/ui/delegation/inherent-impls-rename.stderr diff --git a/tests/ui/delegation/inherent-impls-rename.stderr b/tests/ui/delegation/inherent-impls-rename.stderr deleted file mode 100644 index e2e8946412e93..0000000000000 --- a/tests/ui/delegation/inherent-impls-rename.stderr +++ /dev/null @@ -1,9 +0,0 @@ -error[E0425]: cannot find function `bar` in `X` - --> $DIR/inherent-impls-rename.rs:11:10 - | -LL | reuse X::bar; - | ^^^ not found in `X` - -error: aborting due to 1 previous error - -For more information about this error, try `rustc --explain E0425`. From 508cfc9034a667a15d3157a8f5ee3d8a1bdeb9de Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Tue, 25 Aug 2026 12:12:13 +0300 Subject: [PATCH 15/22] Cleanups and comments --- .../rustc_ast_lowering/src/delegation/generics.rs | 3 +++ compiler/rustc_ast_lowering/src/delegation/mod.rs | 12 +++++++----- .../rustc_ast_lowering/src/delegation/resolution.rs | 9 ++++++--- compiler/rustc_hir_analysis/src/delegation.rs | 9 +++++++++ 4 files changed, 25 insertions(+), 8 deletions(-) diff --git a/compiler/rustc_ast_lowering/src/delegation/generics.rs b/compiler/rustc_ast_lowering/src/delegation/generics.rs index c1e98c364c8b8..be678edab071b 100644 --- a/compiler/rustc_ast_lowering/src/delegation/generics.rs +++ b/compiler/rustc_ast_lowering/src/delegation/generics.rs @@ -153,6 +153,9 @@ impl<'hir> DelegationGenericArgsIterator<'hir> { ids_to_reuse: Vec, ) -> Vec> { let mut args = vec![]; + + // If there were already generic args in HIR that should be replaced by our args, + // reuse their HIR ids in order not to trigger an assert for an unused HIR. let mut ids_iter = ids_to_reuse.into_iter(); while let Some(arg) = self.next(ctx, |ctx| ids_iter.next().unwrap_or_else(|| ctx.next_id())) { diff --git a/compiler/rustc_ast_lowering/src/delegation/mod.rs b/compiler/rustc_ast_lowering/src/delegation/mod.rs index 065aaa02dbe33..c385922115f38 100644 --- a/compiler/rustc_ast_lowering/src/delegation/mod.rs +++ b/compiler/rustc_ast_lowering/src/delegation/mod.rs @@ -525,15 +525,17 @@ impl<'hir> LoweringContext<'_, 'hir> { } impl NewArgsCreationKind { + /// There may be cases with delegations to inherent impls where + /// while lowering path segment through default AST -> HIR + /// lowering routine infer lifetimes are inserted. This means + /// that HIR ids were allocated and if we will just replace them + /// with our generated args we will trigger assert that there are + /// unused HIR ids, so we need to reuse those HIR ids. fn new(segment: &hir::PathSegment<'_>) -> NewArgsCreationKind { - let Some(args) = segment.args else { + let Some(args) = segment.args.filter(|args| !args.is_empty()) else { return NewArgsCreationKind::Propagate(vec![]); }; - if args.is_empty() { - return NewArgsCreationKind::Propagate(vec![]); - } - let ids_to_reuse = args .args .iter() diff --git a/compiler/rustc_ast_lowering/src/delegation/resolution.rs b/compiler/rustc_ast_lowering/src/delegation/resolution.rs index b784c1e02f952..951ea44861a87 100644 --- a/compiler/rustc_ast_lowering/src/delegation/resolution.rs +++ b/compiler/rustc_ast_lowering/src/delegation/resolution.rs @@ -27,11 +27,12 @@ pub(crate) fn resolve_type_relative_delegations( tcx: TyCtxt<'_>, _: (), ) -> FxIndexMap { + // FIXME(fn_delegation): fair resolution through `ProbeContext` engine. let ast_index = tcx.index_ast(()); let resolutions = tcx.resolutions(()); let infos = &resolutions.delegation_infos; - let inh_methods = &resolutions.delegation_inh_functions_map; + let inh_fns = &resolutions.delegation_inh_functions_map; let mut type_relative_resolutions: FxIndexMap = Default::default(); @@ -63,7 +64,7 @@ pub(crate) fn resolve_type_relative_delegations( { match res.as_local() { Some(local_def_id) => { - let res = inh_methods.get(&local_def_id).and_then(|map| map.get(&ident)); + let res = inh_fns.get(&local_def_id).and_then(|map| map.get(&ident)); match res { Some(res) => match res { @@ -258,7 +259,9 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { pub(super) fn is_delegation_to_inherent_impl(&self, sig_id: DefId) -> bool { let tcx = self.tcx(); - matches!(tcx.def_kind(tcx.parent(sig_id)), DefKind::Impl { of_trait: false }) + + tcx.def_kind(sig_id) == DefKind::AssocFn + && matches!(tcx.def_kind(tcx.parent(sig_id)), DefKind::Impl { of_trait: false }) } fn get_call_path_res( diff --git a/compiler/rustc_hir_analysis/src/delegation.rs b/compiler/rustc_hir_analysis/src/delegation.rs index cf628bbd874d6..66c36709ad684 100644 --- a/compiler/rustc_hir_analysis/src/delegation.rs +++ b/compiler/rustc_hir_analysis/src/delegation.rs @@ -179,6 +179,15 @@ fn create_mapping<'tcx>( let process_parent = matches!(parent_kind, FnKind::AssocTrait | FnKind::AssocInherentImpl); let parent_generics = process_parent.then(|| tcx.generics_of(tcx.parent(sig_id))); + // In case of delegations to inherent impls indices of generic params which are passed + // to ADT can be random numbers not from range 0..parent_params_count, so we need to + // use original indices in mapping: + // impl<'a, 'b, 'c, A: 'a, const C: usize> S<'a, A, C> { + // fn foo_static<'d: 'd, 'e, T, const B: bool>() {} + // fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} + // }, + // 'a has index 0, A index 3, C index 4. If we encounter not a generic param as generic arg, + // then we do not need to map it (i.e. consts like `1`, `2`, `3`; `'static`, etc.). let parent_params = match parent_kind { FnKind::AssocInherentImpl => { let ty::Adt(_, args) = tcx.type_of(tcx.parent(sig_id)).skip_binder().kind() else { From 70929e431c1953256168ac8891e9416f67cac5e4 Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Tue, 1 Sep 2026 17:10:50 +0300 Subject: [PATCH 16/22] wip --- .../rustc_ast_lowering/src/delegation/mod.rs | 37 +- .../src/delegation/resolution.rs | 170 +++---- compiler/rustc_ast_lowering/src/item.rs | 9 +- compiler/rustc_ast_lowering/src/lib.rs | 51 +- compiler/rustc_hir/src/hir.rs | 11 + compiler/rustc_hir_analysis/src/collect.rs | 24 +- .../src/collect/resolve_bound_vars.rs | 18 + compiler/rustc_hir_analysis/src/delegation.rs | 2 +- .../src/hir_ty_lowering/mod.rs | 19 +- compiler/rustc_hir_analysis/src/lib.rs | 2 +- compiler/rustc_hir_typeck/src/lib.rs | 51 +- compiler/rustc_hir_typeck/src/method/probe.rs | 23 +- .../rustc_hir_typeck/src/typeck_root_ctxt.rs | 17 +- compiler/rustc_interface/src/passes.rs | 4 +- compiler/rustc_middle/src/hir/map.rs | 4 +- compiler/rustc_middle/src/hooks.rs | 4 +- compiler/rustc_middle/src/queries.rs | 9 + compiler/rustc_middle/src/ty/mod.rs | 1 + compiler/rustc_query_impl/src/execution.rs | 2 +- .../src/handle_cycle_error.rs | 44 +- compiler/rustc_resolve/src/late.rs | 4 + compiler/rustc_resolve/src/lib.rs | 3 + tests/ui/delegation/explicit-paths.rs | 1 + tests/ui/delegation/explicit-paths.stderr | 36 +- tests/ui/delegation/inherent-impls-ambig.rs | 17 +- .../ui/delegation/inherent-impls-ambig.stderr | 94 ++-- .../inherent-impls-mixed-generics.rs | 5 +- .../inherent-impls-mixed-generics.stderr | 33 +- .../inherent-impls-non-local-crate.rs | 2 +- .../inherent-impls-non-local-crate.stderr | 8 +- .../inherent-impls-parent-generics.rs | 59 +-- .../inherent-impls-parent-generics.stderr | 452 ++++++------------ .../inherent-impls-recursive-cycle.stderr | 142 +----- tests/ui/delegation/inherent-impls-rename.rs | 6 +- .../ui/delegation/unsupported.current.stderr | 16 +- tests/ui/delegation/unsupported.next.stderr | 16 +- 36 files changed, 650 insertions(+), 746 deletions(-) diff --git a/compiler/rustc_ast_lowering/src/delegation/mod.rs b/compiler/rustc_ast_lowering/src/delegation/mod.rs index c385922115f38..fb77d444eaa47 100644 --- a/compiler/rustc_ast_lowering/src/delegation/mod.rs +++ b/compiler/rustc_ast_lowering/src/delegation/mod.rs @@ -75,6 +75,10 @@ impl<'hir> LoweringContext<'_, 'hir> { pub(crate) fn lower_delegation(&mut self, delegation: &Delegation) -> DelegationResults<'hir> { let span = self.lower_span(delegation.last_segment_span()); + if self.generate_error_delegation { + return self.generate_delegation_error(span, delegation); + } + let resolver = DelegationResolver::new(self); let Ok((res, mut generics)) = resolver.resolve_delegation(delegation, span) else { return self.generate_delegation_error(span, delegation); @@ -598,18 +602,13 @@ impl<'hir> LoweringContext<'_, 'hir> { segment } - fn generate_delegation_error( + pub(crate) fn generate_delegation_error( &mut self, span: Span, delegation: &Delegation, ) -> DelegationResults<'hir> { let decl = self.arena.alloc(hir::FnDecl::dummy(span)); - let header = self.generate_header_error(); - let sig = hir::FnSig { decl, header, span }; - - let ident = self.lower_ident(delegation.ident); - let body_id = self.lower_body(|this| { let path = this.lower_qpath( delegation.id, @@ -621,6 +620,28 @@ impl<'hir> LoweringContext<'_, 'hir> { None, ); + let ty_id = match path { + QPath::Resolved(_, _) => HirId::INVALID, + QPath::TypeRelative(ty, _) => ty.hir_id, + }; + + if let [.., parent, child] = &delegation.path.segments[..] + && this.get_partial_res(parent.id).is_some_and(|res| res.full_res().is_some()) + && this.get_partial_res(child.id).is_none() + { + decl.output = rustc_hir::FnRetTy::Return(this.arena.alloc(hir::Ty { + hir_id: this.next_id(), + kind: hir::TyKind::InferDelegation(rustc_hir::InferDelegation::Err( + this.arena.alloc(( + ty_id, + span, + delegation.path.segments.last().unwrap().ident, + )), + )), + span, + })); + } + let callee_path = this.arena.alloc(this.mk_expr(hir::ExprKind::Path(path), span)); let args = if let Some(block) = &delegation.body { this.arena.alloc_slice(&[this.lower_block_expr(block)]) @@ -642,7 +663,11 @@ impl<'hir> LoweringContext<'_, 'hir> { (&[], this.mk_expr(hir::ExprKind::Block(block, None), span)) }); + let header = self.generate_header_error(); + let sig = hir::FnSig { decl, header, span }; + let ident = self.lower_ident(delegation.ident); let generics = hir::Generics::empty(); + DelegationResults { ident, generics, body_id, sig } } diff --git a/compiler/rustc_ast_lowering/src/delegation/resolution.rs b/compiler/rustc_ast_lowering/src/delegation/resolution.rs index 951ea44861a87..a4c38b4d83106 100644 --- a/compiler/rustc_ast_lowering/src/delegation/resolution.rs +++ b/compiler/rustc_ast_lowering/src/delegation/resolution.rs @@ -2,15 +2,11 @@ use std::ops::ControlFlow; use ast::visit::Visitor; use hir::def::DefKind; -use rustc_ast::{ - self as ast, AssocItemKind, AstOwner, Delegation, DelegationSource, Item, ItemKind, NodeId, -}; -use rustc_data_structures::fx::{FxHashSet, FxIndexMap, FxIndexSet}; -use rustc_data_structures::steal::Steal; +use rustc_ast::{self as ast, Delegation, DelegationSource, NodeId}; +use rustc_data_structures::fx::{FxHashSet, FxIndexSet}; use rustc_hir as hir; use rustc_middle::ty::{ - self, AssocKind, DelegationInhFuncKind, Ty, TyCtxt, TypeRelativeDelegationRes, - TypeSuperVisitable, TypeVisitable, TypeVisitor, + self, Ty, TyCtxt, TypeRelativeDelegationRes, TypeSuperVisitable, TypeVisitable, TypeVisitor, }; use rustc_span::def_id::{DefId, LocalDefId}; use rustc_span::{ErrorGuaranteed, Span}; @@ -23,90 +19,6 @@ use crate::diagnostics::{ DelegationBlockSpecifiedWhenNoParams, UnresolvedDelegationCallee, }; -pub(crate) fn resolve_type_relative_delegations( - tcx: TyCtxt<'_>, - _: (), -) -> FxIndexMap { - // FIXME(fn_delegation): fair resolution through `ProbeContext` engine. - let ast_index = tcx.index_ast(()); - let resolutions = tcx.resolutions(()); - - let infos = &resolutions.delegation_infos; - let inh_fns = &resolutions.delegation_inh_functions_map; - - let mut type_relative_resolutions: FxIndexMap = - Default::default(); - - for (&def_id, res) in infos { - if res.resolution_id.is_some() { - continue; - } - - let Some(r_and_owner) = ast_index.get(def_id).map(Steal::borrow) else { - unreachable!("ast index must contain delegations"); - }; - - let (r, owner) = &*r_and_owner; - - let delegation = match owner { - AstOwner::Item(Item { kind: ItemKind::Delegation(d), .. }) - | AstOwner::TraitItem(Item { kind: AssocItemKind::Delegation(d), .. }) - | AstOwner::ImplItem(Item { kind: AssocItemKind::Delegation(d), .. }) => d, - _ => unreachable!("we are processing only delegations"), - }; - - let res = r.partial_res_map.get(&delegation.id); - let res = res.and_then(|res| res.base_res().opt_def_id()); - let ident = delegation.path.segments.last().map(|s| s.ident); - - let res = if let Some(res) = res - && let Some(ident) = ident - { - match res.as_local() { - Some(local_def_id) => { - let res = inh_fns.get(&local_def_id).and_then(|map| map.get(&ident)); - - match res { - Some(res) => match res { - DelegationInhFuncKind::Ambig => TypeRelativeDelegationRes::Ambig, - DelegationInhFuncKind::Single(res) => { - TypeRelativeDelegationRes::Ok(res.to_def_id()) - } - }, - _ => TypeRelativeDelegationRes::Error, - } - } - None => { - let mut sig_res = None; - 'inh_loop: for inh_impl_id in tcx.inherent_impls(res) { - let assoc_items = tcx.associated_items(*inh_impl_id); - let mut candidates = assoc_items - .filter_by_name_unhygienic(ident.name) - .filter(|it| matches!(it.kind, AssocKind::Fn { .. })); - - while let Some(candidate) = candidates.next() { - if sig_res.is_some() { - sig_res = Some(TypeRelativeDelegationRes::Ambig); - break 'inh_loop; - } else { - sig_res = Some(TypeRelativeDelegationRes::Ok(candidate.def_id)); - } - } - } - - sig_res.unwrap_or(TypeRelativeDelegationRes::Error) - } - } - } else { - TypeRelativeDelegationRes::Error - }; - - type_relative_resolutions.insert(def_id, res); - } - - type_relative_resolutions -} - /// Summary info about function parameters. #[derive(Debug, Clone, Copy, Eq, PartialEq)] pub(super) struct ParamInfo { @@ -139,8 +51,9 @@ pub(super) struct DelegationResolution { pub(super) mod resolver { use rustc_ast::NodeId; + use rustc_hir::HirId; use rustc_hir::def_id::{DefId, LocalDefId}; - use rustc_middle::ty::TyCtxt; + use rustc_middle::ty::{TyCtxt, TypeRelativeDelegationRes}; use rustc_span::ErrorGuaranteed; use crate::LoweringContext; @@ -193,6 +106,60 @@ pub(super) mod resolver { pub(crate) fn opt_resolution_id(&self, id: NodeId) -> Option { self.0.get_partial_res(id).and_then(|r| r.full_res()).and_then(|r| r.opt_def_id()) } + + pub(crate) fn resolve_type_relative_delegation( + &self, + def_id: LocalDefId, + ) -> TypeRelativeDelegationRes { + let tcx = self.tcx(); + + // let resolver_and_node = tcx.index_ast(()).get(def_id).map(Steal::borrow); + // let Some(resolver_and_node) = resolver_and_node else { unreachable!() }; + // let (r, node) = &*resolver_and_node; + + // let (delegation, id) = match node { + // AstOwner::Item(Item { kind: ItemKind::Delegation(d), id, .. }) + // | AstOwner::TraitItem(Item { kind: AssocItemKind::Delegation(d), id, .. }) + // | AstOwner::ImplItem(Item { kind: AssocItemKind::Delegation(d), id, .. }) => { + // (d, id) + // } + // _ => unreachable!("we are processing only delegations"), + // }; + + // let mut ctxt = LoweringContext::new(self.tcx(), r, *id, true, false); + + // let path = ctxt.lower_qpath( + // delegation.id, + // &delegation.qself, + // &delegation.path, + // ParamMode::Optional, + // AllowReturnTypeNotation::No, + // ImplTraitContext::Disallowed(ImplTraitPosition::Path), + // None, + // ); + + let nodes = &self.tcx().lower_to_hir(def_id).unwrap().nodes; + + if let Some((ty_hir_id, span, ident)) = + nodes.node().fn_decl().unwrap().opt_error_delegation_ty_id() + { + if ty_hir_id == HirId::INVALID { + TypeRelativeDelegationRes::Error + } else { + let ty = nodes.nodes.get(ty_hir_id.local_id).unwrap().node.expect_ty(); + + if let Some(sig_id) = tcx.resolve_delegation_sig(span, def_id, ty, ident) { + TypeRelativeDelegationRes::Ok(sig_id) + } else { + TypeRelativeDelegationRes::Error + } + } + } else { + tcx.hir_opt_delegation_sig_id(def_id) + .map(|sig_id| TypeRelativeDelegationRes::Ok(sig_id)) + .unwrap_or(TypeRelativeDelegationRes::Error) + } + } } } @@ -302,15 +269,12 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { return unresolved_error(); } - match tcx.resolve_type_relative_delegations(()).get(&def_id) { - Some(res) => match res { - TypeRelativeDelegationRes::Ok(sig_id) => Ok(*sig_id), - TypeRelativeDelegationRes::Error => unresolved_error(), - TypeRelativeDelegationRes::Ambig => { - Err(tcx.dcx().emit_err(AmbiguousDelegationToInherentImpl { span })) - } - }, - None => unresolved_error(), + match self.resolve_type_relative_delegation(def_id) { + TypeRelativeDelegationRes::Ok(sig_id) => Ok(sig_id), + TypeRelativeDelegationRes::Error => unresolved_error(), + TypeRelativeDelegationRes::Ambig => { + Err(tcx.dcx().emit_err(AmbiguousDelegationToInherentImpl { span })) + } } } @@ -327,9 +291,9 @@ impl<'tcx> DelegationResolver<'_, 'tcx> { // a signature DefId we obtain NodeId of the callee delegation and try to get signature from it. if let Some(local_id) = def_id.as_local() && delegation_infos.contains_key(&local_id) - && let Ok(id) = self.resolve_delegation_sig(local_id, span) { - def_id = id; + def_id = self.resolve_delegation_sig(local_id, span)?; + if visited.contains(&def_id) { return Err(match visited.len() { 1 => tcx.dcx().emit_err(UnresolvedDelegationCallee { span }), diff --git a/compiler/rustc_ast_lowering/src/item.rs b/compiler/rustc_ast_lowering/src/item.rs index 1ad96d1057042..ef88368c9c596 100644 --- a/compiler/rustc_ast_lowering/src/item.rs +++ b/compiler/rustc_ast_lowering/src/item.rs @@ -31,6 +31,7 @@ use crate::diagnostics::{ConstComptimeFn, ResolvingRestrictionKind, RestrictionA pub(super) struct ItemLowerer<'a, 'hir> { pub(super) tcx: TyCtxt<'hir>, pub(super) resolver: &'a ResolverAstLowering<'hir>, + pub(super) generate_error_delegation: bool, } /// When we have a ty alias we *may* have two where clauses. To give the best diagnostics, we set the span @@ -58,7 +59,13 @@ impl<'hir> ItemLowerer<'_, 'hir> { owner: NodeId, f: impl FnOnce(&mut LoweringContext<'_, 'hir>) -> hir::OwnerNode<'hir>, ) -> hir::MaybeOwner<'hir> { - let mut lctx = LoweringContext::new(self.tcx, self.resolver, owner); + let mut lctx = LoweringContext::new( + self.tcx, + self.resolver, + owner, + false, + self.generate_error_delegation, + ); let item = f(&mut lctx); debug_assert_eq!(lctx.current_hir_id_owner, item.def_id()); diff --git a/compiler/rustc_ast_lowering/src/lib.rs b/compiler/rustc_ast_lowering/src/lib.rs index e9946341c38ae..1ed1392f7b52b 100644 --- a/compiler/rustc_ast_lowering/src/lib.rs +++ b/compiler/rustc_ast_lowering/src/lib.rs @@ -65,9 +65,9 @@ use rustc_hir::{ }; use rustc_index::{Idx, IndexVec}; use rustc_macros::extension; -use rustc_middle::queries::Providers; use rustc_middle::span_bug; use rustc_middle::ty::{PerOwnerResolverData, ResolverAstLowering, TyCtxt}; +use rustc_middle::util::Providers; use rustc_session::diagnostics::add_feature_diagnostics; use rustc_span::symbol::{Ident, Symbol, kw, sym}; use rustc_span::{DUMMY_SP, DesugaringKind, Span}; @@ -97,10 +97,9 @@ mod path; pub mod stability; pub fn provide(providers: &mut Providers) { - providers.index_ast = index_ast; - providers.lower_to_hir = lower_to_hir; - providers.resolve_type_relative_delegations = - delegation::resolution::resolve_type_relative_delegations; + providers.queries.index_ast = index_ast; + providers.queries.lower_to_hir = lower_to_hir; + providers.queries.delegation_error = |tcx, def_id| lower_to_hir_internal(tcx, def_id, true); } #[cfg(debug_assertions)] @@ -150,6 +149,7 @@ struct LoweringContext<'a, 'hir> { tcx: TyCtxt<'hir>, resolver: &'a ResolverAstLowering<'hir>, current_disambiguator: PerParentDisambiguatorState, + generate_error_delegation: bool, /// Used to allocate HIR nodes. arena: &'hir hir::Arena<'hir>, @@ -224,19 +224,26 @@ struct LoweringContext<'a, 'hir> { } impl<'a, 'hir> LoweringContext<'a, 'hir> { - fn new(tcx: TyCtxt<'hir>, resolver: &'a ResolverAstLowering<'hir>, owner: NodeId) -> Self { + fn new( + tcx: TyCtxt<'hir>, + resolver: &'a ResolverAstLowering<'hir>, + owner: NodeId, + _clone_disambig: bool, + generate_error_delegation: bool, + ) -> Self { let current_ast_owner = &resolver.owners[&owner]; let current_hir_id_owner = hir::OwnerId { def_id: current_ast_owner.def_id }; let current_disambiguator = resolver .disambiguators .get(¤t_hir_id_owner.def_id) - .map(|s| s.steal()) + .map(|s| s.borrow().clone()) .unwrap_or_else(|| PerParentDisambiguatorState::new(current_hir_id_owner.def_id)); Self { tcx, resolver, current_disambiguator, + generate_error_delegation, owner: current_ast_owner, arena: tcx.hir_arena, @@ -659,10 +666,20 @@ fn index_ast<'tcx>( #[instrument(level = "trace", skip(tcx))] fn lower_to_hir(tcx: TyCtxt<'_>, def_id: LocalDefId) -> hir::MaybeOwner<'_> { - tcx.ensure_done().resolve_type_relative_delegations(()); + let maybe_owner = lower_to_hir_internal(tcx, def_id, false); + if let Some((_, node)) = tcx.index_ast(()).get(def_id).map(Steal::steal) { + tcx.sess.time("drop_ast", || mem::drop(node)); + } + maybe_owner +} + +fn lower_to_hir_internal( + tcx: TyCtxt<'_>, + def_id: LocalDefId, + generate_error_delegation: bool, +) -> hir::MaybeOwner<'_> { let ast_index = tcx.index_ast(()); - let resolver_and_node = ast_index.get(def_id).map(Steal::steal); let fallback_to_ancestor = |parent_id| { // The item did not exist in the AST, it was created while lowering another item. @@ -688,16 +705,20 @@ fn lower_to_hir(tcx: TyCtxt<'_>, def_id: LocalDefId) -> hir::MaybeOwner<'_> { }) }; - let Some((resolver, node)) = resolver_and_node else { + let resolver_and_node = ast_index.get(def_id).map(Steal::borrow); + let Some(resolver_and_node) = resolver_and_node else { // `ast_index` does not contain all definitions, only up-to the highest // `LocalDefId` which has a non-trivial `AstOwner`. Gracefully handle // other definitions, in particular those nested inside this highest definition. return fallback_to_ancestor(tcx.local_parent(def_id)); }; - let mut item_lowerer = item::ItemLowerer { tcx, resolver: &*resolver }; + let (resolver, node) = &*resolver_and_node; - let item = match &node { + let mut item_lowerer = + item::ItemLowerer { tcx, resolver: &*resolver, generate_error_delegation }; + + match &node { // The item existed in the AST. AstOwner::Crate(c) => item_lowerer.lower_crate(&c), AstOwner::Item(item) => item_lowerer.lower_item(&item), @@ -708,11 +729,7 @@ fn lower_to_hir(tcx: TyCtxt<'_>, def_id: LocalDefId) -> hir::MaybeOwner<'_> { // The item existed in the AST, but is not a HIR owner. // Fetch the correct information from its parent. AstOwner::NonOwner => fallback_to_ancestor(tcx.local_parent(def_id)), - }; - - tcx.sess.time("drop_ast", || mem::drop(node)); - - item + } } #[derive(Copy, Clone, PartialEq, Debug)] diff --git a/compiler/rustc_hir/src/hir.rs b/compiler/rustc_hir/src/hir.rs index fb4b61e9f4875..3b10daa0e8a43 100644 --- a/compiler/rustc_hir/src/hir.rs +++ b/compiler/rustc_hir/src/hir.rs @@ -3550,6 +3550,7 @@ pub enum InferDelegation<'hir> { DefId(DefId), /// Used during signature inheritance, `DefId` corresponds to the signature function. Sig(DefId, InferDelegationSig<'hir>), + Err(&'hir (HirId, Span, Ident)), } /// The various kinds of types recognized by the compiler. @@ -3907,6 +3908,16 @@ impl<'hir> FnDecl<'hir> { None } + pub fn opt_error_delegation_ty_id(&self) -> Option<(HirId, Span, Ident)> { + if let FnRetTy::Return(ty) = self.output + && let TyKind::InferDelegation(InferDelegation::Err(data)) = ty.kind + { + return Some(*data); + } + + None + } + pub fn implicit_self(&self) -> ImplicitSelfKind { self.fn_decl_kind.implicit_self() } diff --git a/compiler/rustc_hir_analysis/src/collect.rs b/compiler/rustc_hir_analysis/src/collect.rs index 65fd562a4ebf6..12ff928e2bffa 100644 --- a/compiler/rustc_hir_analysis/src/collect.rs +++ b/compiler/rustc_hir_analysis/src/collect.rs @@ -31,6 +31,7 @@ use rustc_hir::{self as hir, GenericParamKind, HirId, Node, PreciseCapturingArgK use rustc_infer::infer::{InferCtxt, SolverRegionConstraint, TyCtxtInferExt}; use rustc_infer::traits::{DynCompatibilityViolation, ObligationCause}; use rustc_lint_defs::builtin::REPR_C_ENUMS_LARGER_THAN_INT; +use rustc_middle::middle::resolve_bound_vars::ResolveBoundVars; use rustc_middle::query::Providers; use rustc_middle::ty::util::{Discr, IntTypeExt}; use rustc_middle::ty::{ @@ -54,7 +55,7 @@ mod clauses_of; pub(crate) mod dump; mod generics_of; mod item_bounds; -mod resolve_bound_vars; +pub mod resolve_bound_vars; mod type_of; /////////////////////////////////////////////////////////////////////////// @@ -129,11 +130,12 @@ pub(crate) fn provide(providers: &mut Providers) { /// `ItemCtxt` is parameterized by a `DefId` that it uses to satisfy /// `probe_ty_param_bounds` requests, drawing the information from /// the HIR (`hir::Generics`), recursively. -pub(crate) struct ItemCtxt<'tcx> { +pub struct ItemCtxt<'tcx> { tcx: TyCtxt<'tcx>, item_def_id: LocalDefId, tainted_by_errors: Cell>, lowering_delegation_segment: bool, + rbv: Option>, } /////////////////////////////////////////////////////////////////////////// @@ -243,25 +245,31 @@ fn bad_placeholder<'cx, 'tcx>( } impl<'tcx> ItemCtxt<'tcx> { - pub(crate) fn new(tcx: TyCtxt<'tcx>, item_def_id: LocalDefId) -> ItemCtxt<'tcx> { - ItemCtxt::new_internal(tcx, item_def_id, false) + pub fn new(tcx: TyCtxt<'tcx>, item_def_id: LocalDefId) -> ItemCtxt<'tcx> { + ItemCtxt::new_internal(tcx, item_def_id, false, None) } fn new_internal( tcx: TyCtxt<'tcx>, item_def_id: LocalDefId, delegation: bool, + rbv: Option>, ) -> ItemCtxt<'tcx> { ItemCtxt { tcx, item_def_id, tainted_by_errors: Cell::new(None), lowering_delegation_segment: delegation, + rbv, } } - pub(crate) fn new_for_delegation(tcx: TyCtxt<'tcx>, item_def_id: LocalDefId) -> ItemCtxt<'tcx> { - ItemCtxt::new_internal(tcx, item_def_id, true) + pub fn new_for_delegation( + tcx: TyCtxt<'tcx>, + item_def_id: LocalDefId, + rbv: Option>, + ) -> ItemCtxt<'tcx> { + ItemCtxt::new_internal(tcx, item_def_id, true, rbv) } pub(crate) fn lower_ty(&self, hir_ty: &hir::Ty<'_>) -> Ty<'tcx> { @@ -472,6 +480,10 @@ impl<'tcx> HirTyLowerer<'tcx> for ItemCtxt<'tcx> { self.item_def_id } + fn opt_preset_rbv(&self) -> Option<&ResolveBoundVars<'tcx>> { + self.rbv.as_ref() + } + fn re_infer(&self, span: Span, reason: RegionInferReason<'_>) -> ty::Region<'tcx> { if let RegionInferReason::ObjectLifetimeDefault(sugg_sp) = reason { // FIXME: Account for trailing plus `dyn Trait+`, the need of parens in diff --git a/compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs b/compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs index dbd210e08ea50..4619c2d32bd7b 100644 --- a/compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs +++ b/compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs @@ -289,6 +289,24 @@ fn resolve_bound_vars(tcx: TyCtxt<'_>, local_def_id: hir::OwnerId) -> ResolveBou rbv } +pub fn resolve_delegation_bound_vars<'tcx>( + tcx: TyCtxt<'tcx>, + ty: &'tcx hir::Ty<'tcx, AmbigArg>, +) -> ResolveBoundVars<'tcx> { + let mut rbv = ResolveBoundVars::default(); + let mut visitor = BoundVarContext { + tcx, + rbv: &mut rbv, + scope: &Scope::Root { opt_parent_item: None }, + disambiguators: &mut Default::default(), + opaque_capture_errors: RefCell::new(None), + }; + + visitor.visit_ty(ty); + + rbv +} + fn late_arg_as_bound_arg<'tcx>(param: &GenericParam<'tcx>) -> ty::BoundVariableKind<'tcx> { let def_id = param.def_id.to_def_id(); match param.kind { diff --git a/compiler/rustc_hir_analysis/src/delegation.rs b/compiler/rustc_hir_analysis/src/delegation.rs index 66c36709ad684..2e983636fa035 100644 --- a/compiler/rustc_hir_analysis/src/delegation.rs +++ b/compiler/rustc_hir_analysis/src/delegation.rs @@ -680,7 +680,7 @@ pub(crate) fn delegation_user_specified_args<'tcx>( segment.res.opt_def_id().map(|def_id| (segment, def_id)) }; - let ctx = ItemCtxt::new_for_delegation(tcx, def_id); + let ctx = ItemCtxt::new_for_delegation(tcx, def_id, None); let lowerer = ctx.lowerer(); let parent_args = info .parent_seg_id_for_sig diff --git a/compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs b/compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs index cfff8d1768f0e..24a1de89e8306 100644 --- a/compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs +++ b/compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs @@ -41,6 +41,7 @@ use rustc_infer::infer::{InferCtxt, TyCtxtInferExt}; use rustc_infer::traits::DynCompatibilityViolation; use rustc_lint_defs::builtin::AMBIGUOUS_ASSOCIATED_ITEMS; use rustc_macros::{TypeFoldable, TypeVisitable}; +use rustc_middle::middle::resolve_bound_vars::ResolveBoundVars; use rustc_middle::middle::stability::AllowUnstable; use rustc_middle::ty::{ self, Const, FnSigKind, GenericArgKind, GenericArgsRef, GenericParamDefKind, LitToConstInput, @@ -240,6 +241,10 @@ pub trait HirTyLowerer<'tcx> { self } + fn opt_preset_rbv(&self) -> Option<&ResolveBoundVars<'tcx>> { + None + } + /// Performs minimalistic dyn compat checks outside of bodies, but full within bodies. /// Outside of bodies we could end up in cycles, so we delay most checks to later phases. fn dyn_compatibility_violations(&self, trait_def_id: DefId) -> Vec; @@ -579,7 +584,12 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ { lifetime: &hir::Lifetime, reason: RegionInferReason<'_>, ) -> ty::Region<'tcx> { - if let Some(resolved) = self.tcx().named_bound_var(lifetime.hir_id) { + let resolved = self + .opt_preset_rbv() + .map(|rbv| rbv.defs.get(&lifetime.hir_id.local_id).cloned()) + .unwrap_or_else(|| self.tcx().named_bound_var(lifetime.hir_id)); + + if let Some(resolved) = resolved { let region = self.lower_resolved_lifetime(resolved); self.check_param_uses_if_mcg(region, lifetime.ident.span, false) } else { @@ -2187,7 +2197,6 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ { } /// Lower a [resolved][hir::QPath::Resolved] path to a type. - #[instrument(level = "debug", skip_all)] pub fn lower_resolved_ty_path( &self, opt_self_ty: Option>, @@ -3201,11 +3210,15 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ { hir::InferDelegationSig::Output { .. } => *delegation_sig.last().unwrap(), } } + rustc_hir::InferDelegation::Err(_) => Ty::new_error_with_message( + self.tcx(), + DUMMY_SP, + "accessing type of an error delegation", + ), } } /// Lower a type from the HIR to our internal notion of a type. - #[instrument(level = "debug", skip(self), ret)] pub fn lower_ty(&self, hir_ty: &hir::Ty<'_>) -> Ty<'tcx> { let tcx = self.tcx(); diff --git a/compiler/rustc_hir_analysis/src/lib.rs b/compiler/rustc_hir_analysis/src/lib.rs index 41f98e2fb40c0..547ca0c11eba8 100644 --- a/compiler/rustc_hir_analysis/src/lib.rs +++ b/compiler/rustc_hir_analysis/src/lib.rs @@ -71,7 +71,7 @@ pub mod check; pub mod autoderef; mod check_unused; mod coherence; -mod collect; +pub mod collect; mod constrained_generic_params; pub mod delegation; pub mod diagnostics; diff --git a/compiler/rustc_hir_typeck/src/lib.rs b/compiler/rustc_hir_typeck/src/lib.rs index 0f977710fbe09..3648d27a94cca 100644 --- a/compiler/rustc_hir_typeck/src/lib.rs +++ b/compiler/rustc_hir_typeck/src/lib.rs @@ -44,19 +44,21 @@ use fn_ctxt::FnCtxt; use rustc_data_structures::unord::UnordSet; use rustc_errors::codes::*; use rustc_errors::{Applicability, Diag, ErrorGuaranteed, struct_span_code_err}; -use rustc_hir as hir; use rustc_hir::def::{DefKind, Res}; -use rustc_hir::{HirId, HirIdMap, Node}; +use rustc_hir::def_id::DefId; +use rustc_hir::{self as hir, HirId, HirIdMap, Node}; use rustc_hir_analysis::check::check_abi; +use rustc_hir_analysis::collect::ItemCtxt; +use rustc_hir_analysis::collect::resolve_bound_vars::resolve_delegation_bound_vars; use rustc_hir_analysis::hir_ty_lowering::HirTyLowerer; use rustc_infer::traits::{ObligationCauseCode, ObligationInspector, TraitEngine, WellFormedLoc}; use rustc_middle::middle::codegen_fn_attrs::CodegenFnAttrFlags; -use rustc_middle::query::Providers; -use rustc_middle::ty::{self, FnSigKind, Ty, TyCtxt, Unnormalized}; +use rustc_middle::ty::{self, FnSigKind, ParamEnv, Ty, TyCtxt, Unnormalized}; +use rustc_middle::util::Providers; use rustc_middle::{bug, span_bug}; use rustc_session::config; -use rustc_span::Span; use rustc_span::def_id::LocalDefId; +use rustc_span::{Ident, Span}; use tracing::{debug, instrument}; use typeck_root_ctxt::TypeckRootCtxt; @@ -66,6 +68,7 @@ use crate::diverges::Diverges; use crate::expectation::Expectation; use crate::fn_ctxt::LoweredTy; use crate::gather_locals::GatherLocalsVisitor; +use crate::method::probe::{IsSuggestion, Mode}; #[macro_export] macro_rules! type_error_struct { @@ -718,14 +721,48 @@ fn fatally_break_rust(tcx: TyCtxt<'_>, span: Span) -> ! { diag.emit() } +pub(crate) fn resolve_delegation_sig<'tcx>( + tcx: TyCtxt<'tcx>, + span: Span, + parent_id: LocalDefId, + ty: &'tcx hir::Ty<'tcx>, + ident: Ident, +) -> Option { + let param_env = ParamEnv::empty(); + let root_ctxt = TypeckRootCtxt::new_delegation(tcx, parent_id); + let fn_ctxt = FnCtxt::new(&root_ctxt, param_env, parent_id); + let rbv = resolve_delegation_bound_vars(tcx, ty.try_as_ambig_ty().unwrap()); + let p_ty = ItemCtxt::new_for_delegation(tcx, parent_id, Some(rbv)).lowerer().lower_ty(ty); + let ty::Adt(def, _) = p_ty.kind() else { unreachable!() }; + + let pick = fn_ctxt.probe_op( + span, + Mode::Path, + Some(ident), + None, + IsSuggestion(false), + p_ty, + HirId::INVALID, + method::probe::ProbeScope::InherentImplsOnly(def.did()), + |probe_cx| probe_cx.pick_core(&mut vec![]).ok_or(method::MethodError::BadReturnType), + ); + + pick.ok() + .map(|p| p.ok().map(|p| p.item.def_id)) + .flatten() + .filter(|def_id| tcx.def_kind(*def_id) == DefKind::AssocFn) +} + /// Adds query implementations to the [Providers] vtable, see [`rustc_middle::query`] pub fn provide(providers: &mut Providers) { - *providers = Providers { + providers.queries = rustc_middle::query::Providers { method_autoderef_steps: method::probe::method_autoderef_steps, typeck_root, used_trait_imports, check_transmutes: intrinsicck::check_transmutes, check_offloads: intrinsicck::check_offloads, - ..*providers + ..providers.queries }; + + providers.hooks.resolve_delegation_sig = resolve_delegation_sig; } diff --git a/compiler/rustc_hir_typeck/src/method/probe.rs b/compiler/rustc_hir_typeck/src/method/probe.rs index 15916db330381..c37509ad2eeb4 100644 --- a/compiler/rustc_hir_typeck/src/method/probe.rs +++ b/compiler/rustc_hir_typeck/src/method/probe.rs @@ -273,6 +273,8 @@ pub(crate) enum Mode { #[derive(PartialEq, Eq, Debug)] pub(crate) enum ProbeScope<'tcx> { + InherentImplsOnly(DefId), + // Single candidate coming from pre-resolved delegation method. Single(DefId, Option> /* self_ty override */), @@ -628,7 +630,26 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { false, ); } + ProbeScope::InherentImplsOnly(def_id) => { + if let Some(def_id) = def_id.as_local() { + let impls = self + .tcx + .resolutions(()) + .delegation_types_to_inh_impls + .get(&def_id) + .map(|impls| impls.as_slice()) + .unwrap_or(&[]); + + for impl_def_id in impls { + probe_cx.assemble_inherent_impl_probe(impl_def_id.to_def_id(), 0); + } + } else { + probe_cx.assemble_inherent_candidates(); + probe_cx.assemble_extension_candidates_for_traits_in_scope(); + } + } }; + op(probe_cx) }) } @@ -1298,7 +1319,7 @@ impl<'a, 'tcx> ProbeContext<'a, 'tcx> { })) } - fn pick_core( + pub(crate) fn pick_core( &self, unsatisfied_predicates: &mut UnsatisfiedPredicates<'tcx>, ) -> Option> { diff --git a/compiler/rustc_hir_typeck/src/typeck_root_ctxt.rs b/compiler/rustc_hir_typeck/src/typeck_root_ctxt.rs index 945e14b3d98fa..2c7b6a8e0a47e 100644 --- a/compiler/rustc_hir_typeck/src/typeck_root_ctxt.rs +++ b/compiler/rustc_hir_typeck/src/typeck_root_ctxt.rs @@ -2,7 +2,7 @@ use std::cell::{Cell, RefCell}; use std::ops::Deref; use rustc_hir::def_id::LocalDefId; -use rustc_hir::{self as hir, HirId, HirIdMap}; +use rustc_hir::{self as hir, HirId, HirIdMap, OwnerId}; use rustc_infer::infer::{InferCtxt, InferOk, OpaqueTypeStorageEntries, TyCtxtInferExt}; use rustc_middle::span_bug; use rustc_middle::ty::{self, Ty, TyCtxt, TyVid, TypeVisitableExt, TypingMode}; @@ -80,13 +80,12 @@ impl<'tcx> Deref for TypeckRootCtxt<'tcx> { impl<'tcx> TypeckRootCtxt<'tcx> { pub(crate) fn new(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Self { let hir_owner = tcx.local_def_id_to_hir_id(def_id).owner; + Self::new_internal(tcx, hir_owner, TypingMode::typeck_for_body(tcx, def_id)) + } - let infcx = tcx - .infer_ctxt() - .ignoring_regions() - .in_hir_typeck() - .build(TypingMode::typeck_for_body(tcx, def_id)); - let typeck_results = RefCell::new(ty::TypeckResults::new(hir_owner)); + fn new_internal(tcx: TyCtxt<'tcx>, owner: OwnerId, mode: TypingMode<'tcx>) -> Self { + let infcx = tcx.infer_ctxt().ignoring_regions().in_hir_typeck().build(mode); + let typeck_results = RefCell::new(ty::TypeckResults::new(owner)); let fulfillment_cx = RefCell::new(FulfillmentEngine::new(&infcx)); TypeckRootCtxt { @@ -106,6 +105,10 @@ impl<'tcx> TypeckRootCtxt<'tcx> { } } + pub(crate) fn new_delegation(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Self { + Self::new_internal(tcx, OwnerId { def_id }, TypingMode::non_body_analysis()) + } + #[instrument(level = "debug", skip(self))] pub(super) fn register_predicate(&self, obligation: traits::PredicateObligation<'tcx>) { if obligation.has_escaping_bound_vars() { diff --git a/compiler/rustc_interface/src/passes.rs b/compiler/rustc_interface/src/passes.rs index c829864b02288..9a80527ae80d8 100644 --- a/compiler/rustc_interface/src/passes.rs +++ b/compiler/rustc_interface/src/passes.rs @@ -905,7 +905,7 @@ pub static DEFAULT_QUERY_PROVIDERS: LazyLock = LazyLock::new(|| { providers.queries.early_lint_checks = early_lint_checks; providers.queries.env_var_os = env_var_os; providers.queries.proc_macro_decls_static = |tcx, _| tcx.hir_crate_items(()).proc_macro_decls(); - rustc_ast_lowering::provide(&mut providers.queries); + rustc_ast_lowering::provide(providers); limits::provide(&mut providers.queries); rustc_expand::provide(&mut providers.queries); rustc_const_eval::provide(providers); @@ -919,7 +919,7 @@ pub static DEFAULT_QUERY_PROVIDERS: LazyLock = LazyLock::new(|| { rustc_query_impl::provide(providers); rustc_resolve::provide(&mut providers.queries); rustc_hir_analysis::provide(&mut providers.queries); - rustc_hir_typeck::provide(&mut providers.queries); + rustc_hir_typeck::provide(providers); ty::provide(&mut providers.queries); traits::provide(&mut providers.queries); solve::provide(&mut providers.queries); diff --git a/compiler/rustc_middle/src/hir/map.rs b/compiler/rustc_middle/src/hir/map.rs index b384a7a16e54f..1e5c0f7cb838f 100644 --- a/compiler/rustc_middle/src/hir/map.rs +++ b/compiler/rustc_middle/src/hir/map.rs @@ -871,8 +871,8 @@ impl<'tcx> TyCtxt<'tcx> { self.opt_hir_owner_node(def_id)?.fn_decl()?.opt_delegation_info() } - pub fn hir_delegation_info(self, delegation_id: LocalDefId) -> &'tcx DelegationInfo { - self.hir_opt_delegation_info(delegation_id).expect("processing delegation") + pub fn hir_delegation_info(self, def_id: LocalDefId) -> &'tcx DelegationInfo { + self.hir_opt_delegation_info(def_id).expect("processing delegation") } #[inline] diff --git a/compiler/rustc_middle/src/hooks.rs b/compiler/rustc_middle/src/hooks.rs index 7a69f58d52fae..d6da356fb916b 100644 --- a/compiler/rustc_middle/src/hooks.rs +++ b/compiler/rustc_middle/src/hooks.rs @@ -6,7 +6,7 @@ use rustc_hir::def_id::{DefId, DefPathHash}; use rustc_session::StableCrateId; use rustc_span::def_id::{CrateNum, LocalDefId}; -use rustc_span::{ExpnHash, ExpnId}; +use rustc_span::{ExpnHash, ExpnId, Span}; use crate::mir; use crate::query::on_disk_cache::CacheEncoder; @@ -107,6 +107,8 @@ declare_hooks! { /// Serializes all eligible query return values into the on-disk cache. hook encode_query_values(encoder: &mut CacheEncoder<'_, 'tcx>) -> (); + + hook resolve_delegation_sig(span: Span, parent_id: LocalDefId, ty: &'tcx rustc_hir::Ty<'tcx>, ident: rustc_span::Ident) -> Option; } #[cold] diff --git a/compiler/rustc_middle/src/queries.rs b/compiler/rustc_middle/src/queries.rs index 389eb7a984c97..af43d587215bf 100644 --- a/compiler/rustc_middle/src/queries.rs +++ b/compiler/rustc_middle/src/queries.rs @@ -215,6 +215,11 @@ rustc_queries! { desc { "getting the AST for lowering" } } + query delegation_error(def_id: LocalDefId) -> hir::MaybeOwner<'tcx> { + eval_always + desc { "getting error delegation for `{}`", tcx.def_path_str(def_id) } + } + /// Return the span for a definition. /// /// Contrary to `def_span` below, this query returns the full absolute span of the definition. @@ -233,11 +238,13 @@ rustc_queries! { query lower_to_hir(def_id: LocalDefId) -> hir::MaybeOwner<'tcx> { eval_always + handle_cycle_error desc { "lowering HIR for `{}`", tcx.def_path_str(def_id) } } query hir_owner(def_id: LocalDefId) -> rustc_middle::hir::ProjectedMaybeOwner<'tcx> { desc { "getting owner for `{}`", tcx.def_path_str(def_id) } + handle_cycle_error feedable } @@ -437,6 +444,7 @@ rustc_queries! { /// **Tip**: You can use `#[rustc_dump_clauses]` on an item to basically print /// the result of this query for use in UI tests or for debugging purposes. query clauses_of(key: DefId) -> ty::GenericClauses<'tcx> { + handle_cycle_error desc { "computing clauses of `{}`", tcx.def_path_str(key) } } @@ -820,6 +828,7 @@ rustc_queries! { desc { "computing explicit predicates of `{}`", tcx.def_path_str(key) } cache_on_disk separate_provide_extern + handle_cycle_error feedable } diff --git a/compiler/rustc_middle/src/ty/mod.rs b/compiler/rustc_middle/src/ty/mod.rs index 19fd3f0d06fb8..adff8b616b6ed 100644 --- a/compiler/rustc_middle/src/ty/mod.rs +++ b/compiler/rustc_middle/src/ty/mod.rs @@ -205,6 +205,7 @@ pub struct ResolverGlobalCtxt { pub delegation_infos: FxIndexMap, pub delegation_inh_functions_map: FxIndexMap>, + pub delegation_types_to_inh_impls: FxIndexMap>, } #[derive(Debug)] diff --git a/compiler/rustc_query_impl/src/execution.rs b/compiler/rustc_query_impl/src/execution.rs index d220826670729..13a9927c3375b 100644 --- a/compiler/rustc_query_impl/src/execution.rs +++ b/compiler/rustc_query_impl/src/execution.rs @@ -58,7 +58,7 @@ fn handle_cycle<'tcx, C: QueryCache>( if nested { // Avoid custom handlers and only use the robust `create_cycle_error` for nested cycle errors - handle_cycle_error::default(error) + (query.handle_cycle_error_fn)(tcx, key, cycle, error) } else { (query.handle_cycle_error_fn)(tcx, key, cycle, error) } diff --git a/compiler/rustc_query_impl/src/handle_cycle_error.rs b/compiler/rustc_query_impl/src/handle_cycle_error.rs index 8d0d671406468..db40ef3acc092 100644 --- a/compiler/rustc_query_impl/src/handle_cycle_error.rs +++ b/compiler/rustc_query_impl/src/handle_cycle_error.rs @@ -15,6 +15,46 @@ use rustc_middle::ty::{self, Ty, TyCtxt}; use rustc_span::def_id::{DefId, LocalDefId}; use rustc_span::{DUMMY_SP, ErrorGuaranteed, Span}; +pub(crate) fn hir_owner<'tcx>( + tcx: TyCtxt<'tcx>, + def_id: LocalDefId, + _: Cycle<'tcx>, + err: Diag<'_>, +) -> rustc_middle::hir::ProjectedMaybeOwner<'tcx> { + err.cancel(); + rustc_middle::hir::ProjectedMaybeOwner::new(tcx.delegation_error(def_id)) +} + +pub(crate) fn lower_to_hir<'tcx>( + tcx: TyCtxt<'tcx>, + def_id: LocalDefId, + _: Cycle<'tcx>, + err: Diag<'_>, +) -> rustc_hir::MaybeOwner<'tcx> { + err.cancel(); + tcx.delegation_error(def_id) +} + +pub(crate) fn clauses_of<'tcx>( + _: TyCtxt<'_>, + _: DefId, + _: Cycle<'tcx>, + err: Diag<'_>, +) -> rustc_middle::ty::GenericClauses<'tcx> { + err.cancel(); + Default::default() +} + +pub(crate) fn explicit_clauses_of<'tcx>( + _: TyCtxt<'_>, + _: DefId, + _: Cycle<'tcx>, + err: Diag<'_>, +) -> rustc_middle::ty::GenericClauses<'tcx> { + err.cancel(); + Default::default() +} + // Default cycle handler used for all queries that don't use the `handle_cycle_error` query // modifier. pub(crate) fn default(err: Diag<'_>) -> ! { @@ -351,7 +391,7 @@ pub(crate) fn create_cycle_error<'tcx>( ) -> Diag<'tcx> { assert!(!frames.is_empty()); - let span = frames[0].tagged_key.catch_default_span(tcx, frames[1 % frames.len()].span); + let span = DUMMY_SP; let mut cycle_stack = Vec::new(); @@ -366,7 +406,7 @@ pub(crate) fn create_cycle_error<'tcx>( let mut prev = span; for i in 1..frames.len() { let frame = &frames[i]; - let span = frame.tagged_key.catch_default_span(tcx, frames[(i + 1) % frames.len()].span); + let span = DUMMY_SP; cycle_stack.push(crate::diagnostics::CycleStack { span: if span == prev { DUMMY_SP } else { span }, desc: frame.tagged_key.catch_description(tcx), diff --git a/compiler/rustc_resolve/src/late.rs b/compiler/rustc_resolve/src/late.rs index 95586ced9a975..b3b6e78b736d1 100644 --- a/compiler/rustc_resolve/src/late.rs +++ b/compiler/rustc_resolve/src/late.rs @@ -3572,6 +3572,10 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { }) .flatten(); + if let Some(id) = self_type_def_id { + this.r.delegation_types_to_inh_impls.entry(id).or_default().push(this.r.current_owner.def_id); + } + // Resolve the items within the impl. this.with_current_self_type(self_type, |this| { this.with_self_rib_ns(ValueNS, Res::SelfCtor(item_def_id), |this| { diff --git a/compiler/rustc_resolve/src/lib.rs b/compiler/rustc_resolve/src/lib.rs index 9aa3c79191651..58fa7c80d4525 100644 --- a/compiler/rustc_resolve/src/lib.rs +++ b/compiler/rustc_resolve/src/lib.rs @@ -1517,6 +1517,7 @@ pub struct Resolver<'ra, 'tcx> { delegation_fn_sigs: LocalDefIdMap = Default::default(), delegation_infos: FxIndexMap, delegation_inh_functions_map: FxIndexMap>, + delegation_types_to_inh_impls: FxIndexMap>, main_def: Option = None, trait_impls: FxIndexMap>, @@ -1890,6 +1891,7 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> { disambiguators: Default::default(), delegation_infos: Default::default(), delegation_inh_functions_map: Default::default(), + delegation_types_to_inh_impls: Default::default(), features: tcx.features(), .. }; @@ -1995,6 +1997,7 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> { stripped_cfg_items, delegation_infos: self.delegation_infos, delegation_inh_functions_map: self.delegation_inh_functions_map, + delegation_types_to_inh_impls: self.delegation_types_to_inh_impls, }; let ast_lowering = ty::ResolverAstLowering { partial_res_map: self.partial_res_map, diff --git a/tests/ui/delegation/explicit-paths.rs b/tests/ui/delegation/explicit-paths.rs index e9530ec9d2314..a0d380fdb75e1 100644 --- a/tests/ui/delegation/explicit-paths.rs +++ b/tests/ui/delegation/explicit-paths.rs @@ -26,6 +26,7 @@ mod fn_to_other { reuse to_reuse::foo3; reuse S::foo4; //~^ ERROR: method `foo4` is private + //~| ERROR: this function takes 1 argument but 0 arguments were supplied } mod inherent_impl_assoc_fn_to_other { diff --git a/tests/ui/delegation/explicit-paths.stderr b/tests/ui/delegation/explicit-paths.stderr index f92bfd73266c3..684de8cc0a141 100644 --- a/tests/ui/delegation/explicit-paths.stderr +++ b/tests/ui/delegation/explicit-paths.stderr @@ -1,5 +1,5 @@ error[E0407]: method `foo3` is not a member of trait `Trait` - --> $DIR/explicit-paths.rs:48:9 + --> $DIR/explicit-paths.rs:49:9 | LL | reuse to_reuse::foo3; | ^^^^^^^^^^^^^^^^----^ @@ -8,7 +8,7 @@ LL | reuse to_reuse::foo3; | not a member of trait `Trait` error[E0407]: method `foo4` is not a member of trait `Trait` - --> $DIR/explicit-paths.rs:50:9 + --> $DIR/explicit-paths.rs:51:9 | LL | reuse F::foo4 { &self.0 } | ^^^^^^^^^----^^^^^^^^^^^^ @@ -17,7 +17,7 @@ LL | reuse F::foo4 { &self.0 } | not a member of trait `Trait` error[E0119]: conflicting implementations of trait `Trait` for type `S` - --> $DIR/explicit-paths.rs:71:5 + --> $DIR/explicit-paths.rs:72:5 | LL | impl Trait for S { | ---------------- first implementation here @@ -34,8 +34,24 @@ LL | reuse S::foo4; LL | reuse F::foo4 { &self.0 } | ---- private method defined here +error[E0061]: this function takes 1 argument but 0 arguments were supplied + --> $DIR/explicit-paths.rs:27:14 + | +LL | reuse S::foo4; + | ^^^^ argument #1 of type `&S` is missing + | +note: method defined here + --> $DIR/explicit-paths.rs:39:18 + | +LL | reuse F::foo4 { &self.0 } + | ^^^^ +help: provide the argument + | +LL | reuse S::foo4(/* &S */); + | ++++++++++ + error[E0308]: mismatched types - --> $DIR/explicit-paths.rs:59:36 + --> $DIR/explicit-paths.rs:60:36 | LL | trait Trait2 : Trait { | -------------------- found this type parameter @@ -53,13 +69,13 @@ LL | fn foo1(&self, x: i32) -> i32 { x } | ^^^^ ----- error[E0277]: the trait bound `S2: Trait` is not satisfied - --> $DIR/explicit-paths.rs:73:16 + --> $DIR/explicit-paths.rs:74:16 | LL | reuse ::foo1; | ^^ unsatisfied trait bound | help: the trait `Trait` is not implemented for `S2` - --> $DIR/explicit-paths.rs:70:5 + --> $DIR/explicit-paths.rs:71:5 | LL | struct S2; | ^^^^^^^^^ @@ -76,7 +92,7 @@ LL | impl Trait for S { | ^^^^^^^^^^^^^^^^ `S` error[E0308]: mismatched types - --> $DIR/explicit-paths.rs:73:30 + --> $DIR/explicit-paths.rs:74:30 | LL | reuse ::foo1; | ^^^^ @@ -92,7 +108,7 @@ note: method defined here LL | fn foo1(&self, x: i32) -> i32 { x } | ^^^^ ----- -error: aborting due to 7 previous errors +error: aborting due to 8 previous errors -Some errors have detailed explanations: E0119, E0277, E0308, E0407, E0624. -For more information about an error, try `rustc --explain E0119`. +Some errors have detailed explanations: E0061, E0119, E0277, E0308, E0407, E0624. +For more information about an error, try `rustc --explain E0061`. diff --git a/tests/ui/delegation/inherent-impls-ambig.rs b/tests/ui/delegation/inherent-impls-ambig.rs index 1b7c9a6fcef0f..6ca629cb2db7b 100644 --- a/tests/ui/delegation/inherent-impls-ambig.rs +++ b/tests/ui/delegation/inherent-impls-ambig.rs @@ -1,3 +1,5 @@ +//@compile-flags: -Z deduplicate-diagnostics=yes + #![feature(fn_delegation)] mod test_1 { @@ -14,19 +16,16 @@ mod test_1 { } reuse X::foo; - //~^ ERROR: ambiguous delegation to inherent impl function + //~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions //~| ERROR: multiple applicable items in scope [E0034] reuse X::foo_self; - //~^ ERROR: ambiguous delegation to inherent impl function + //~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions //~| ERROR: multiple applicable items in scope [E0034] reuse X::<()>::foo as foo1; - //~^ ERROR: ambiguous delegation to inherent impl function reuse X::::foo_self as foo_self1; - //~^ ERROR: ambiguous delegation to inherent impl function - //~| ERROR: this function takes 1 argument but 0 arguments were supplied } mod test_2 { @@ -50,19 +49,17 @@ mod test_2 { impl Marker2 for M2 {} reuse X::foo; - //~^ ERROR: ambiguous delegation to inherent impl function + //~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions //~| ERROR: multiple applicable items in scope [E0034] reuse X::foo_self; - //~^ ERROR: ambiguous delegation to inherent impl function + //~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions //~| ERROR: multiple applicable items in scope [E0034] reuse X::::foo as foo1; - //~^ ERROR: ambiguous delegation to inherent impl function reuse X::::foo_self as foo_self1; - //~^ ERROR: ambiguous delegation to inherent impl function - //~| ERROR: no associated function or constant named `foo_self` found for struct `test_2::X` in the current scope + //~^ ERROR: no associated function or constant named `foo_self` found for struct `test_2::X` in the current scope } fn main() {} diff --git a/tests/ui/delegation/inherent-impls-ambig.stderr b/tests/ui/delegation/inherent-impls-ambig.stderr index a15fc0f2af268..7708a6d61f161 100644 --- a/tests/ui/delegation/inherent-impls-ambig.stderr +++ b/tests/ui/delegation/inherent-impls-ambig.stderr @@ -1,137 +1,97 @@ -error: ambiguous delegation to inherent impl function - --> $DIR/inherent-impls-ambig.rs:16:14 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-ambig.rs:18:11 | LL | reuse X::foo; - | ^^^ + | ^ not allowed in type signatures -error: ambiguous delegation to inherent impl function - --> $DIR/inherent-impls-ambig.rs:20:14 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-ambig.rs:22:11 | LL | reuse X::foo_self; - | ^^^^^^^^ + | ^ not allowed in type signatures -error: ambiguous delegation to inherent impl function - --> $DIR/inherent-impls-ambig.rs:24:20 - | -LL | reuse X::<()>::foo as foo1; - | ^^^ - -error: ambiguous delegation to inherent impl function - --> $DIR/inherent-impls-ambig.rs:27:23 - | -LL | reuse X::::foo_self as foo_self1; - | ^^^^^^^^ - -error: ambiguous delegation to inherent impl function - --> $DIR/inherent-impls-ambig.rs:52:14 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-ambig.rs:51:11 | LL | reuse X::foo; - | ^^^ + | ^ not allowed in type signatures -error: ambiguous delegation to inherent impl function - --> $DIR/inherent-impls-ambig.rs:56:14 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-ambig.rs:55:11 | LL | reuse X::foo_self; - | ^^^^^^^^ - -error: ambiguous delegation to inherent impl function - --> $DIR/inherent-impls-ambig.rs:60:27 - | -LL | reuse X::::foo as foo1; - | ^^^ - -error: ambiguous delegation to inherent impl function - --> $DIR/inherent-impls-ambig.rs:63:28 - | -LL | reuse X::::foo_self as foo_self1; - | ^^^^^^^^ + | ^ not allowed in type signatures error[E0034]: multiple applicable items in scope - --> $DIR/inherent-impls-ambig.rs:16:14 + --> $DIR/inherent-impls-ambig.rs:18:14 | LL | reuse X::foo; | ^^^ multiple `foo` found | note: candidate #1 is defined in an impl for the type `test_1::X<()>` - --> $DIR/inherent-impls-ambig.rs:7:9 + --> $DIR/inherent-impls-ambig.rs:9:9 | LL | fn foo() {} | ^^^^^^^^ note: candidate #2 is defined in an impl for the type `test_1::X` - --> $DIR/inherent-impls-ambig.rs:12:9 + --> $DIR/inherent-impls-ambig.rs:14:9 | LL | fn foo() {} | ^^^^^^^^ error[E0034]: multiple applicable items in scope - --> $DIR/inherent-impls-ambig.rs:20:14 + --> $DIR/inherent-impls-ambig.rs:22:14 | LL | reuse X::foo_self; | ^^^^^^^^ multiple `foo_self` found | note: candidate #1 is defined in an impl for the type `test_1::X<()>` - --> $DIR/inherent-impls-ambig.rs:8:9 + --> $DIR/inherent-impls-ambig.rs:10:9 | LL | fn foo_self(self) {} | ^^^^^^^^^^^^^^^^^ note: candidate #2 is defined in an impl for the type `test_1::X` - --> $DIR/inherent-impls-ambig.rs:13:9 + --> $DIR/inherent-impls-ambig.rs:15:9 | LL | fn foo_self(self) {} | ^^^^^^^^^^^^^^^^^ -error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-ambig.rs:27:23 - | -LL | reuse X::::foo_self as foo_self1; - | ^^^^^^^^ argument #1 of type `test_1::X` is missing - | -note: method defined here - --> $DIR/inherent-impls-ambig.rs:13:12 - | -LL | fn foo_self(self) {} - | ^^^^^^^^ ---- -help: provide the argument - | -LL | reuse X::::foo_self(/* X */) as foo_self1; - | ++++++++++++++++ - error[E0034]: multiple applicable items in scope - --> $DIR/inherent-impls-ambig.rs:52:14 + --> $DIR/inherent-impls-ambig.rs:51:14 | LL | reuse X::foo; | ^^^ multiple `foo` found | note: candidate #1 is defined in an impl for the type `test_2::X` - --> $DIR/inherent-impls-ambig.rs:43:9 + --> $DIR/inherent-impls-ambig.rs:42:9 | LL | fn foo() {} | ^^^^^^^^ note: candidate #2 is defined in an impl for the type `test_2::X` - --> $DIR/inherent-impls-ambig.rs:38:9 + --> $DIR/inherent-impls-ambig.rs:37:9 | LL | fn foo() {} | ^^^^^^^^ error[E0034]: multiple applicable items in scope - --> $DIR/inherent-impls-ambig.rs:56:14 + --> $DIR/inherent-impls-ambig.rs:55:14 | LL | reuse X::foo_self; | ^^^^^^^^ multiple `foo_self` found | note: candidate #1 is defined in an impl for the type `test_2::X` - --> $DIR/inherent-impls-ambig.rs:44:9 + --> $DIR/inherent-impls-ambig.rs:43:9 | LL | fn foo_self(self) {} | ^^^^^^^^^^^^^^^^^ note: candidate #2 is defined in an impl for the type `test_2::X` - --> $DIR/inherent-impls-ambig.rs:39:9 + --> $DIR/inherent-impls-ambig.rs:38:9 | LL | fn foo_self(self) {} | ^^^^^^^^^^^^^^^^^ error[E0599]: no associated function or constant named `foo_self` found for struct `test_2::X` in the current scope - --> $DIR/inherent-impls-ambig.rs:63:28 + --> $DIR/inherent-impls-ambig.rs:61:28 | LL | struct X(T, U); | -------------- associated function or constant `foo_self` not found for this struct @@ -139,7 +99,7 @@ LL | struct X(T, U); LL | reuse X::::foo_self as foo_self1; | ^^^^^^^^ associated function or constant not found in `test_2::X` -error: aborting due to 14 previous errors +error: aborting due to 9 previous errors -Some errors have detailed explanations: E0034, E0061, E0599. +Some errors have detailed explanations: E0034, E0121, E0599. For more information about an error, try `rustc --explain E0034`. diff --git a/tests/ui/delegation/inherent-impls-mixed-generics.rs b/tests/ui/delegation/inherent-impls-mixed-generics.rs index b24acff6187eb..9e1a2b7b1ff1d 100644 --- a/tests/ui/delegation/inherent-impls-mixed-generics.rs +++ b/tests/ui/delegation/inherent-impls-mixed-generics.rs @@ -10,7 +10,10 @@ impl<'a, 'b, 'c, A, const C: usize> S<'static, A, usize, C> { trait Trait<'a, AA, BB> where Self: Sized { reuse S::foo_self; - //~^ ERROR: delegation to inherent impl must contain parent generics + //~^ ERROR: inferred lifetimes are not allowed in delegations as we need to inherit signature + //~| ERROR: the placeholder `_` is not allowed within types on item signatures for associated functions + //~| ERROR: the placeholder `_` is not allowed within types on item signatures for associated functions + //~| ERROR: the placeholder `_` is not allowed within types on item signatures for associated functions //~| ERROR: this function takes 1 argument but 0 arguments were supplied } diff --git a/tests/ui/delegation/inherent-impls-mixed-generics.stderr b/tests/ui/delegation/inherent-impls-mixed-generics.stderr index f730d5360eef7..5816217cbfa65 100644 --- a/tests/ui/delegation/inherent-impls-mixed-generics.stderr +++ b/tests/ui/delegation/inherent-impls-mixed-generics.stderr @@ -1,8 +1,30 @@ -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-mixed-generics.rs:12:14 +error: inferred lifetimes are not allowed in delegations as we need to inherit signature + --> $DIR/inherent-impls-mixed-generics.rs:12:11 + | +LL | reuse S::foo_self; + | ^ + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for associated functions + --> $DIR/inherent-impls-mixed-generics.rs:12:11 + | +LL | reuse S::foo_self; + | ^ not allowed in type signatures + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for associated functions + --> $DIR/inherent-impls-mixed-generics.rs:12:11 + | +LL | reuse S::foo_self; + | ^ not allowed in type signatures + | + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for associated functions + --> $DIR/inherent-impls-mixed-generics.rs:12:11 | LL | reuse S::foo_self; - | ^^^^^^^^ + | ^ not allowed in type signatures + | + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` error[E0061]: this function takes 1 argument but 0 arguments were supplied --> $DIR/inherent-impls-mixed-generics.rs:12:14 @@ -20,6 +42,7 @@ help: provide the argument LL | reuse S::foo_self(/* value */); | +++++++++++++ -error: aborting due to 2 previous errors +error: aborting due to 5 previous errors -For more information about this error, try `rustc --explain E0061`. +Some errors have detailed explanations: E0061, E0121. +For more information about an error, try `rustc --explain E0061`. diff --git a/tests/ui/delegation/inherent-impls-non-local-crate.rs b/tests/ui/delegation/inherent-impls-non-local-crate.rs index 27b8d387a7e63..22d94ef382846 100644 --- a/tests/ui/delegation/inherent-impls-non-local-crate.rs +++ b/tests/ui/delegation/inherent-impls-non-local-crate.rs @@ -17,7 +17,7 @@ reuse inherent_impl::S::bar; reuse ::bar as trait_bar; reuse inherent_impl::X::foo as x_foo; -//~^ ERROR: ambiguous delegation to inherent impl function +//~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions //~| ERROR: multiple applicable items in scope fn main() {} diff --git a/tests/ui/delegation/inherent-impls-non-local-crate.stderr b/tests/ui/delegation/inherent-impls-non-local-crate.stderr index 31358b1d7144e..c131f0a0919ab 100644 --- a/tests/ui/delegation/inherent-impls-non-local-crate.stderr +++ b/tests/ui/delegation/inherent-impls-non-local-crate.stderr @@ -1,8 +1,8 @@ -error: ambiguous delegation to inherent impl function - --> $DIR/inherent-impls-non-local-crate.rs:19:25 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-non-local-crate.rs:19:7 | LL | reuse inherent_impl::X::foo as x_foo; - | ^^^ + | ^^^^^^^^^^^^^^^^ not allowed in type signatures error[E0599]: no associated function or constant named `not_existing` found for struct `S` in the current scope --> $DIR/inherent-impls-non-local-crate.rs:7:25 @@ -45,5 +45,5 @@ LL | reuse inherent_impl::X::foo as x_foo; error: aborting due to 6 previous errors -Some errors have detailed explanations: E0034, E0599, E0618. +Some errors have detailed explanations: E0034, E0121, E0599, E0618. For more information about an error, try `rustc --explain E0034`. diff --git a/tests/ui/delegation/inherent-impls-parent-generics.rs b/tests/ui/delegation/inherent-impls-parent-generics.rs index 1c303e16a0272..8afe41b174970 100644 --- a/tests/ui/delegation/inherent-impls-parent-generics.rs +++ b/tests/ui/delegation/inherent-impls-parent-generics.rs @@ -12,20 +12,23 @@ impl<'a, 'b, 'c, A: 'a, const C: usize> E<'a, A, C> { } reuse E::foo_static as e; -//~^ ERROR: delegation to inherent impl must contain parent generics -//~| ERROR: type annotations needed -//~| ERROR: type annotations needed -//~| ERROR: type annotations needed +//~^ ERROR: inferred lifetimes are not allowed in delegations as we need to inherit signature +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions reuse E::foo_self as e1; -//~^ ERROR: delegation to inherent impl must contain parent generics +//~^ ERROR: inferred lifetimes are not allowed in delegations as we need to inherit signature +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions //~| ERROR: this function takes 1 argument but 0 arguments were supplied reuse E::foo_static::<'static, (), true> as e2; -//~^ ERROR: delegation to inherent impl must contain parent generics -//~| ERROR: type annotations needed -//~| ERROR: type annotations needed +//~^ ERROR: inferred lifetimes are not allowed in delegations as we need to inherit signature +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions reuse E::foo_self::<'static, (), true> as e3; -//~^ ERROR: delegation to inherent impl must contain parent generics +//~^ ERROR: inferred lifetimes are not allowed in delegations as we need to inherit signature +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions //~| ERROR: this function takes 1 argument but 0 arguments were supplied reuse E::<'static, (), 123>::foo_static as e4; @@ -35,12 +38,13 @@ reuse E::<'static, (), 123>::foo_static::<'static, (), true> as e6; reuse E::<'static, (), 123>::foo_self::<'static, (), true> as e7; reuse E::<'_, (), _>::foo_static as e8; -//~^ ERROR: parent segment of delegation to inherent impl can not contain infers -//~| ERROR: type annotations needed -//~| ERROR: type annotations needed -//~| ERROR: type annotations needed +//~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions +//~| ERROR: inferred lifetimes are not allowed in delegations as we need to inherit signature + reuse E::<'_, _, _>::foo_self as e9; -//~^ ERROR: parent segment of delegation to inherent impl can not contain infers +//~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions +//~| ERROR: inferred lifetimes are not allowed in delegations as we need to inherit signature //~| ERROR: this function takes 1 argument but 0 arguments were supplied struct S { @@ -53,20 +57,21 @@ impl<'a, 'b, 'c, A, const C: usize> S { } reuse S::foo_static as s; -//~^ ERROR: delegation to inherent impl must contain parent generics -//~| ERROR: type annotations needed -//~| ERROR: type annotations needed -//~| ERROR: type annotations needed +//~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions + reuse S::foo_self as s1; -//~^ ERROR: delegation to inherent impl must contain parent generics +//~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions //~| ERROR: this function takes 1 argument but 0 arguments were supplied reuse S::foo_static::<'static, (), true> as s2; -//~^ ERROR: delegation to inherent impl must contain parent generics -//~| ERROR: type annotations needed -//~| ERROR: type annotations needed +//~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions + reuse S::foo_self::<'static, (), true> as s3; -//~^ ERROR: delegation to inherent impl must contain parent generics +//~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions +//~| ERROR: the placeholder `_` is not allowed within types on item signatures for functions //~| ERROR: this function takes 1 argument but 0 arguments were supplied reuse S::<(), 123>::foo_static as s4; @@ -76,12 +81,10 @@ reuse S::<(), 123>::foo_static::<'static, (), true> as s6; reuse S::<(), 123>::foo_self::<'static, (), true> as s7; reuse S::<(), _>::foo_static as s8; -//~^ ERROR: parent segment of delegation to inherent impl can not contain infers -//~| ERROR: type annotations needed -//~| ERROR: type annotations needed -//~| ERROR: type annotations needed +//~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions + reuse S::<_, 123>::foo_self as s9; -//~^ ERROR: parent segment of delegation to inherent impl can not contain infers +//~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions //~| ERROR: this function takes 1 argument but 0 arguments were supplied fn main() {} diff --git a/tests/ui/delegation/inherent-impls-parent-generics.stderr b/tests/ui/delegation/inherent-impls-parent-generics.stderr index b1001e193a9cd..d950be77b4ff0 100644 --- a/tests/ui/delegation/inherent-impls-parent-generics.stderr +++ b/tests/ui/delegation/inherent-impls-parent-generics.stderr @@ -1,131 +1,183 @@ -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-parent-generics.rs:14:10 +error: inferred lifetimes are not allowed in delegations as we need to inherit signature + --> $DIR/inherent-impls-parent-generics.rs:14:7 | LL | reuse E::foo_static as e; - | ^^^^^^^^^^ + | ^ -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-parent-generics.rs:19:10 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:14:7 + | +LL | reuse E::foo_static as e; + | ^ not allowed in type signatures + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:14:7 + | +LL | reuse E::foo_static as e; + | ^ not allowed in type signatures + | + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` + +error: inferred lifetimes are not allowed in delegations as we need to inherit signature + --> $DIR/inherent-impls-parent-generics.rs:18:7 | LL | reuse E::foo_self as e1; - | ^^^^^^^^ + | ^ -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-parent-generics.rs:23:10 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:18:7 + | +LL | reuse E::foo_self as e1; + | ^ not allowed in type signatures + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:18:7 + | +LL | reuse E::foo_self as e1; + | ^ not allowed in type signatures + | + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` + +error: inferred lifetimes are not allowed in delegations as we need to inherit signature + --> $DIR/inherent-impls-parent-generics.rs:24:7 | LL | reuse E::foo_static::<'static, (), true> as e2; - | ^^^^^^^^^^ + | ^ -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-parent-generics.rs:27:10 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:24:7 | -LL | reuse E::foo_self::<'static, (), true> as e3; - | ^^^^^^^^ +LL | reuse E::foo_static::<'static, (), true> as e2; + | ^ not allowed in type signatures -error: parent segment of delegation to inherent impl can not contain infers - --> $DIR/inherent-impls-parent-generics.rs:37:23 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:24:7 | -LL | reuse E::<'_, (), _>::foo_static as e8; - | ^^^^^^^^^^ +LL | reuse E::foo_static::<'static, (), true> as e2; + | ^ not allowed in type signatures + | + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` -error: parent segment of delegation to inherent impl can not contain infers - --> $DIR/inherent-impls-parent-generics.rs:42:22 +error: inferred lifetimes are not allowed in delegations as we need to inherit signature + --> $DIR/inherent-impls-parent-generics.rs:28:7 | -LL | reuse E::<'_, _, _>::foo_self as e9; - | ^^^^^^^^ +LL | reuse E::foo_self::<'static, (), true> as e3; + | ^ -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-parent-generics.rs:55:10 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:28:7 | -LL | reuse S::foo_static as s; - | ^^^^^^^^^^ +LL | reuse E::foo_self::<'static, (), true> as e3; + | ^ not allowed in type signatures -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-parent-generics.rs:60:10 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:28:7 | -LL | reuse S::foo_self as s1; - | ^^^^^^^^ +LL | reuse E::foo_self::<'static, (), true> as e3; + | ^ not allowed in type signatures + | + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-parent-generics.rs:64:10 +error: inferred lifetimes are not allowed in delegations as we need to inherit signature + --> $DIR/inherent-impls-parent-generics.rs:40:11 | -LL | reuse S::foo_static::<'static, (), true> as s2; - | ^^^^^^^^^^ +LL | reuse E::<'_, (), _>::foo_static as e8; + | ^^ -error: delegation to inherent impl must contain parent generics - --> $DIR/inherent-impls-parent-generics.rs:68:10 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:40:19 | -LL | reuse S::foo_self::<'static, (), true> as s3; - | ^^^^^^^^ +LL | reuse E::<'_, (), _>::foo_static as e8; + | ^ not allowed in type signatures -error: parent segment of delegation to inherent impl can not contain infers - --> $DIR/inherent-impls-parent-generics.rs:78:19 +error: inferred lifetimes are not allowed in delegations as we need to inherit signature + --> $DIR/inherent-impls-parent-generics.rs:44:11 | -LL | reuse S::<(), _>::foo_static as s8; - | ^^^^^^^^^^ +LL | reuse E::<'_, _, _>::foo_self as e9; + | ^^ -error: parent segment of delegation to inherent impl can not contain infers - --> $DIR/inherent-impls-parent-generics.rs:83:20 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:44:15 | -LL | reuse S::<_, 123>::foo_self as s9; - | ^^^^^^^^ +LL | reuse E::<'_, _, _>::foo_self as e9; + | ^ not allowed in type signatures -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:14:10 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:44:18 | -LL | reuse E::foo_static as e; - | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` - | | - | type must be known at this point +LL | reuse E::<'_, _, _>::foo_self as e9; + | ^ not allowed in type signatures + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:59:7 | -note: required by a const generic parameter in `E` - --> $DIR/inherent-impls-parent-generics.rs:4:23 +LL | reuse S::foo_static as s; + | ^ not allowed in type signatures + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:59:7 | -LL | enum E<'a: 'a, A: 'a, const C: usize> { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `E` -help: consider specifying the generic arguments +LL | reuse S::foo_static as s; + | ^ not allowed in type signatures | -LL - reuse E::foo_static as e; -LL + reuse E:: as e; + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:63:7 | +LL | reuse S::foo_self as s1; + | ^ not allowed in type signatures -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:14:10 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:63:7 | -LL | reuse E::foo_static as e; - | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` +LL | reuse S::foo_self as s1; + | ^ not allowed in type signatures | -note: required by a const generic parameter in `E::<'a, A, C>::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:9:25 + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:68:7 | -LL | impl<'a, 'b, 'c, A: 'a, const C: usize> E<'a, A, C> { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ---------- required by a bound in this associated function -help: consider specifying the generic arguments +LL | reuse S::foo_static::<'static, (), true> as s2; + | ^ not allowed in type signatures + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:68:7 | -LL - reuse E::foo_static as e; -LL + reuse E:: as e; +LL | reuse S::foo_static::<'static, (), true> as s2; + | ^ not allowed in type signatures | + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:14:10 +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:72:7 | -LL | reuse E::foo_static as e; - | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` +LL | reuse S::foo_self::<'static, (), true> as s3; + | ^ not allowed in type signatures + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:72:7 | -note: required by a const generic parameter in `E::<'a, A, C>::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:10:34 +LL | reuse S::foo_self::<'static, (), true> as s3; + | ^ not allowed in type signatures + | + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:83:15 | -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` -help: consider specifying the generic arguments +LL | reuse S::<(), _>::foo_static as s8; + | ^ not allowed in type signatures + +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-parent-generics.rs:86:11 | -LL | reuse E::foo_static:: as e; - | ++++++++ +LL | reuse S::<_, 123>::foo_self as s9; + | ^ not allowed in type signatures error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-parent-generics.rs:19:10 + --> $DIR/inherent-impls-parent-generics.rs:18:10 | LL | reuse E::foo_self as e1; | ^^^^^^^^ argument #1 of type `E<'_, _, _>` is missing @@ -140,46 +192,8 @@ help: provide the argument LL | reuse E::foo_self(/* value */) as e1; | +++++++++++++ -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:23:10 - | -LL | reuse E::foo_static::<'static, (), true> as e2; - | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` - | | - | type must be known at this point - | -note: required by a const generic parameter in `E` - --> $DIR/inherent-impls-parent-generics.rs:4:23 - | -LL | enum E<'a: 'a, A: 'a, const C: usize> { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `E` -help: consider specifying the generic arguments - | -LL - reuse E::foo_static::<'static, (), true> as e2; -LL + reuse E:: as e2; - | - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:23:10 - | -LL | reuse E::foo_static::<'static, (), true> as e2; - | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` - | -note: required by a const generic parameter in `E::<'a, A, C>::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:9:25 - | -LL | impl<'a, 'b, 'c, A: 'a, const C: usize> E<'a, A, C> { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ---------- required by a bound in this associated function -help: consider specifying the generic arguments - | -LL - reuse E::foo_static::<'static, (), true> as e2; -LL + reuse E:: as e2; - | - error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-parent-generics.rs:27:10 + --> $DIR/inherent-impls-parent-generics.rs:28:10 | LL | reuse E::foo_self::<'static, (), true> as e3; | ^^^^^^^^ argument #1 of type `E<'_, _, _>` is missing @@ -194,52 +208,8 @@ help: provide the argument LL | reuse E::foo_self(/* value */)::<'static, (), true> as e3; | +++++++++++++ -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:37:23 - | -LL | reuse E::<'_, (), _>::foo_static as e8; - | -------------- ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` - | | - | type must be known at this point - | -note: required by a const generic parameter in `E` - --> $DIR/inherent-impls-parent-generics.rs:4:23 - | -LL | enum E<'a: 'a, A: 'a, const C: usize> { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `E` - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:37:23 - | -LL | reuse E::<'_, (), _>::foo_static as e8; - | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the enum `E` - | -note: required by a const generic parameter in `E::<'a, A, C>::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:9:25 - | -LL | impl<'a, 'b, 'c, A: 'a, const C: usize> E<'a, A, C> { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ---------- required by a bound in this associated function - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:37:23 - | -LL | reuse E::<'_, (), _>::foo_static as e8; - | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` - | -note: required by a const generic parameter in `E::<'a, A, C>::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:10:34 - | -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ^^^^^^^^^^^^^ required by this const generic parameter in `E::<'a, A, C>::foo_static` -help: consider specifying the generic arguments - | -LL | reuse E::<'_, (), _>::foo_static:: as e8; - | ++++++++ - error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-parent-generics.rs:42:22 + --> $DIR/inherent-impls-parent-generics.rs:44:22 | LL | reuse E::<'_, _, _>::foo_self as e9; | ^^^^^^^^ argument #1 of type `E<'_, _, _>` is missing @@ -254,66 +224,14 @@ help: provide the argument LL | reuse E::<'_, _, _>::foo_self(/* value */) as e9; | +++++++++++++ -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:55:10 - | -LL | reuse S::foo_static as s; - | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` - | | - | type must be known at this point - | -note: required by a const generic parameter in `S` - --> $DIR/inherent-impls-parent-generics.rs:46:13 - | -LL | struct S { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` -help: consider specifying the generic arguments - | -LL | reuse S::::foo_static as s; - | ++++++++ - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:55:10 - | -LL | reuse S::foo_static as s; - | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` - | -note: required by a const generic parameter in `S::::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:50:21 - | -LL | impl<'a, 'b, 'c, A, const C: usize> S { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ---------- required by a bound in this associated function -help: consider specifying the generic arguments - | -LL | reuse S::::foo_static as s; - | ++++++++ - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:55:10 - | -LL | reuse S::foo_static as s; - | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` - | -note: required by a const generic parameter in `S::::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:51:34 - | -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` -help: consider specifying the generic arguments - | -LL | reuse S::foo_static:: as s; - | ++++++++ - error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-parent-generics.rs:60:10 + --> $DIR/inherent-impls-parent-generics.rs:63:10 | LL | reuse S::foo_self as s1; | ^^^^^^^^ argument #1 of type `S<_, _>` is missing | note: method defined here - --> $DIR/inherent-impls-parent-generics.rs:52:8 + --> $DIR/inherent-impls-parent-generics.rs:56:8 | LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- @@ -322,50 +240,14 @@ help: provide the argument LL | reuse S::foo_self(/* value */) as s1; | +++++++++++++ -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:64:10 - | -LL | reuse S::foo_static::<'static, (), true> as s2; - | - ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` - | | - | type must be known at this point - | -note: required by a const generic parameter in `S` - --> $DIR/inherent-impls-parent-generics.rs:46:13 - | -LL | struct S { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` -help: consider specifying the generic arguments - | -LL | reuse S::::foo_static::<'static, (), true> as s2; - | ++++++++ - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:64:10 - | -LL | reuse S::foo_static::<'static, (), true> as s2; - | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` - | -note: required by a const generic parameter in `S::::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:50:21 - | -LL | impl<'a, 'b, 'c, A, const C: usize> S { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ---------- required by a bound in this associated function -help: consider specifying the generic arguments - | -LL | reuse S::::foo_static::<'static, (), true> as s2; - | ++++++++ - error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-parent-generics.rs:68:10 + --> $DIR/inherent-impls-parent-generics.rs:72:10 | LL | reuse S::foo_self::<'static, (), true> as s3; | ^^^^^^^^ argument #1 of type `S<_, _>` is missing | note: method defined here - --> $DIR/inherent-impls-parent-generics.rs:52:8 + --> $DIR/inherent-impls-parent-generics.rs:56:8 | LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- @@ -374,58 +256,14 @@ help: provide the argument LL | reuse S::foo_self(/* value */)::<'static, (), true> as s3; | +++++++++++++ -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:78:19 - | -LL | reuse S::<(), _>::foo_static as s8; - | ---------- ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` - | | - | type must be known at this point - | -note: required by a const generic parameter in `S` - --> $DIR/inherent-impls-parent-generics.rs:46:13 - | -LL | struct S { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `S` - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:78:19 - | -LL | reuse S::<(), _>::foo_static as s8; - | ^^^^^^^^^^ cannot infer the value of the const parameter `C` declared on the struct `S` - | -note: required by a const generic parameter in `S::::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:50:21 - | -LL | impl<'a, 'b, 'c, A, const C: usize> S { - | ^^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ---------- required by a bound in this associated function - -error[E0284]: type annotations needed - --> $DIR/inherent-impls-parent-generics.rs:78:19 - | -LL | reuse S::<(), _>::foo_static as s8; - | ^^^^^^^^^^ cannot infer the value of the const parameter `B` declared on the associated function `foo_static` - | -note: required by a const generic parameter in `S::::foo_static` - --> $DIR/inherent-impls-parent-generics.rs:51:34 - | -LL | fn foo_static<'d: 'd, 'e, T, const B: bool>() {} - | ^^^^^^^^^^^^^ required by this const generic parameter in `S::::foo_static` -help: consider specifying the generic arguments - | -LL | reuse S::<(), _>::foo_static:: as s8; - | ++++++++ - error[E0061]: this function takes 1 argument but 0 arguments were supplied - --> $DIR/inherent-impls-parent-generics.rs:83:20 + --> $DIR/inherent-impls-parent-generics.rs:86:20 | LL | reuse S::<_, 123>::foo_self as s9; | ^^^^^^^^ argument #1 of type `S<_, 123>` is missing | note: method defined here - --> $DIR/inherent-impls-parent-generics.rs:52:8 + --> $DIR/inherent-impls-parent-generics.rs:56:8 | LL | fn foo_self<'d: 'd, 'e, T, const B: bool>(self) {} | ^^^^^^^^ ---- @@ -434,7 +272,7 @@ help: provide the argument LL | reuse S::<_, 123>::foo_self(/* value */) as s9; | +++++++++++++ -error: aborting due to 34 previous errors +error: aborting due to 33 previous errors -Some errors have detailed explanations: E0061, E0284. +Some errors have detailed explanations: E0061, E0121. For more information about an error, try `rustc --explain E0061`. diff --git a/tests/ui/delegation/inherent-impls-recursive-cycle.stderr b/tests/ui/delegation/inherent-impls-recursive-cycle.stderr index 9c88b8e7cacc4..3584420ec58c2 100644 --- a/tests/ui/delegation/inherent-impls-recursive-cycle.stderr +++ b/tests/ui/delegation/inherent-impls-recursive-cycle.stderr @@ -1,140 +1,16 @@ -error: encountered a cycle during delegation signature resolution - --> $DIR/inherent-impls-recursive-cycle.rs:4:11 +error[E0391]: cycle detected when collecting associated items of `` | -LL | reuse trait_foo_reused as foo; - | ^^^^^^^^^^^^^^^^ - -error: encountered a cycle during delegation signature resolution - --> $DIR/inherent-impls-recursive-cycle.rs:12:19 - | -LL | reuse Trait1::foo { self.0 } - | ^^^ - -error: encountered a cycle during delegation signature resolution - --> $DIR/inherent-impls-recursive-cycle.rs:19:21 - | -LL | reuse S1::<()>::foo { self.0 } - | ^^^ - -error: encountered a cycle during delegation signature resolution - --> $DIR/inherent-impls-recursive-cycle.rs:24:11 - | -LL | reuse S2::foo; - | ^^^ - -error: encountered a cycle during delegation signature resolution - --> $DIR/inherent-impls-recursive-cycle.rs:29:11 - | -LL | reuse foo; - | ^^^ - -error: encountered a cycle during delegation signature resolution - --> $DIR/inherent-impls-recursive-cycle.rs:34:15 - | -LL | reuse S2::foo { S2(S1(())) } - | ^^^ - -error: encountered a cycle during delegation signature resolution - --> $DIR/inherent-impls-recursive-cycle.rs:40:27 - | -LL | reuse ::foo { S3 } - | ^^^ - -error: encountered a cycle during delegation signature resolution - --> $DIR/inherent-impls-recursive-cycle.rs:45:15 - | -LL | reuse Trait2::foo as trait_foo; - | ^^^ - -error: encountered a cycle during delegation signature resolution - --> $DIR/inherent-impls-recursive-cycle.rs:51:11 - | -LL | reuse trait_foo; - | ^^^^^^^^^ - -error: encountered a cycle during delegation signature resolution + = note: ...which requires computing associated item data for `::trait_foo`... + = note: ...which requires getting owner for `::trait_foo`... + = note: ...which requires lowering HIR for `::trait_foo`... + = note: ...which again requires collecting associated items of ``, completing the cycle +note: cycle used when lowering HIR for `trait_foo_reused` --> $DIR/inherent-impls-recursive-cycle.rs:55:11 | LL | reuse S4::trait_foo as trait_foo_reused; | ^^^^^^^^^ + = note: for more information, see and -error[E0061]: this function takes 0 arguments but 1 argument was supplied - --> $DIR/inherent-impls-recursive-cycle.rs:12:19 - | -LL | reuse Trait1::foo { self.0 } - | ^^^ ---------- unexpected argument - | -note: associated function defined here - --> $DIR/inherent-impls-recursive-cycle.rs:4:31 - | -LL | reuse trait_foo_reused as foo; - | ^^^ -help: remove the extra argument - | -LL - reuse Trait1::foo { self.0 } -LL + reuse Trait1::fo{ self.0 } - | - -error[E0061]: this function takes 0 arguments but 1 argument was supplied - --> $DIR/inherent-impls-recursive-cycle.rs:19:21 - | -LL | reuse S1::<()>::foo { self.0 } - | ^^^ ---------- unexpected argument - | -note: associated function defined here - --> $DIR/inherent-impls-recursive-cycle.rs:12:19 - | -LL | reuse Trait1::foo { self.0 } - | ^^^ -help: remove the extra argument - | -LL - reuse S1::<()>::foo { self.0 } -LL + reuse S1::<()>::fo{ self.0 } - | - -error[E0061]: this function takes 0 arguments but 1 argument was supplied - --> $DIR/inherent-impls-recursive-cycle.rs:34:15 - | -LL | reuse S2::foo { S2(S1(())) } - | ^^^ -------------- unexpected argument of type `S2` - | -note: associated function defined here - --> $DIR/inherent-impls-recursive-cycle.rs:19:21 - | -LL | reuse S1::<()>::foo { self.0 } - | ^^^ -help: remove the extra argument - | -LL - reuse S2::foo { S2(S1(())) } -LL + reuse S2::fo{ S2(S1(())) } - | - -error[E0061]: this function takes 0 arguments but 1 argument was supplied - --> $DIR/inherent-impls-recursive-cycle.rs:40:27 - | -LL | reuse ::foo { S3 } - | ^^^ ------ unexpected argument of type `S3` - | -note: associated function defined here - --> $DIR/inherent-impls-recursive-cycle.rs:4:31 - | -LL | reuse trait_foo_reused as foo; - | ^^^ -help: remove the extra argument - | -LL - reuse ::foo { S3 } -LL + reuse ::fo{ S3 } - | - -error[E0283]: type annotations needed - --> $DIR/inherent-impls-recursive-cycle.rs:45:15 - | -LL | reuse Trait2::foo as trait_foo; - | ^^^ cannot infer type - | - = note: the type must implement `Trait2` - -error: aborting due to 15 previous errors +error: aborting due to 1 previous error -Some errors have detailed explanations: E0061, E0283. -For more information about an error, try `rustc --explain E0061`. +For more information about this error, try `rustc --explain E0391`. diff --git a/tests/ui/delegation/inherent-impls-rename.rs b/tests/ui/delegation/inherent-impls-rename.rs index 6a0fd672cf8e5..47515c8234f2c 100644 --- a/tests/ui/delegation/inherent-impls-rename.rs +++ b/tests/ui/delegation/inherent-impls-rename.rs @@ -2,14 +2,14 @@ #![feature(fn_delegation)] -struct X; +struct X<'a, T>(&'a T); fn foo() {} -impl X { +impl X<'_, String> { reuse foo as bar; } -reuse X::bar; +reuse X::<'static, String>::bar; fn main() {} diff --git a/tests/ui/delegation/unsupported.current.stderr b/tests/ui/delegation/unsupported.current.stderr index 075dfbe7622fe..ab5283574b39c 100644 --- a/tests/ui/delegation/unsupported.current.stderr +++ b/tests/ui/delegation/unsupported.current.stderr @@ -1,23 +1,23 @@ error[E0391]: cycle detected when computing type of `opaque::::opaque_ret::{anon_assoc#0}` + | + = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... + = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle +note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition --> $DIR/unsupported.rs:29:25 | LL | reuse to_reuse::opaque_ret; | ^^^^^^^^^^ - | - = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... - = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle - = note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition = note: for more information, see and error[E0391]: cycle detected when computing type of `opaque::::opaque_ret::{anon_assoc#0}` + | + = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... + = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle +note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition --> $DIR/unsupported.rs:32:24 | LL | reuse ToReuse::opaque_ret; | ^^^^^^^^^^ - | - = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... - = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle - = note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition = note: for more information, see and error: aborting due to 2 previous errors diff --git a/tests/ui/delegation/unsupported.next.stderr b/tests/ui/delegation/unsupported.next.stderr index 075dfbe7622fe..ab5283574b39c 100644 --- a/tests/ui/delegation/unsupported.next.stderr +++ b/tests/ui/delegation/unsupported.next.stderr @@ -1,23 +1,23 @@ error[E0391]: cycle detected when computing type of `opaque::::opaque_ret::{anon_assoc#0}` + | + = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... + = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle +note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition --> $DIR/unsupported.rs:29:25 | LL | reuse to_reuse::opaque_ret; | ^^^^^^^^^^ - | - = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... - = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle - = note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition = note: for more information, see and error[E0391]: cycle detected when computing type of `opaque::::opaque_ret::{anon_assoc#0}` + | + = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... + = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle +note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition --> $DIR/unsupported.rs:32:24 | LL | reuse ToReuse::opaque_ret; | ^^^^^^^^^^ - | - = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... - = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle - = note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition = note: for more information, see and error: aborting due to 2 previous errors From 904cb0cc156c0c8334ebbd680168dcbd8101649f Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Tue, 1 Sep 2026 17:47:50 +0300 Subject: [PATCH 17/22] wip --- compiler/rustc_ast_lowering/src/item.rs | 9 ++------- compiler/rustc_ast_lowering/src/lib.rs | 15 ++++++++++++--- 2 files changed, 14 insertions(+), 10 deletions(-) diff --git a/compiler/rustc_ast_lowering/src/item.rs b/compiler/rustc_ast_lowering/src/item.rs index ef88368c9c596..91071ef84f376 100644 --- a/compiler/rustc_ast_lowering/src/item.rs +++ b/compiler/rustc_ast_lowering/src/item.rs @@ -59,13 +59,8 @@ impl<'hir> ItemLowerer<'_, 'hir> { owner: NodeId, f: impl FnOnce(&mut LoweringContext<'_, 'hir>) -> hir::OwnerNode<'hir>, ) -> hir::MaybeOwner<'hir> { - let mut lctx = LoweringContext::new( - self.tcx, - self.resolver, - owner, - false, - self.generate_error_delegation, - ); + let mut lctx = + LoweringContext::new(self.tcx, self.resolver, owner, self.generate_error_delegation); let item = f(&mut lctx); debug_assert_eq!(lctx.current_hir_id_owner, item.def_id()); diff --git a/compiler/rustc_ast_lowering/src/lib.rs b/compiler/rustc_ast_lowering/src/lib.rs index 1ed1392f7b52b..a45ce7281dc7a 100644 --- a/compiler/rustc_ast_lowering/src/lib.rs +++ b/compiler/rustc_ast_lowering/src/lib.rs @@ -228,7 +228,6 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { tcx: TyCtxt<'hir>, resolver: &'a ResolverAstLowering<'hir>, owner: NodeId, - _clone_disambig: bool, generate_error_delegation: bool, ) -> Self { let current_ast_owner = &resolver.owners[&owner]; @@ -236,7 +235,13 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { let current_disambiguator = resolver .disambiguators .get(¤t_hir_id_owner.def_id) - .map(|s| s.borrow().clone()) + .map(|s| { + if tcx.resolutions(()).delegation_infos.contains_key(¤t_ast_owner.def_id) { + s.borrow().clone() + } else { + s.steal() + } + }) .unwrap_or_else(|| PerParentDisambiguatorState::new(current_hir_id_owner.def_id)); Self { @@ -667,8 +672,12 @@ fn index_ast<'tcx>( #[instrument(level = "trace", skip(tcx))] fn lower_to_hir(tcx: TyCtxt<'_>, def_id: LocalDefId) -> hir::MaybeOwner<'_> { let maybe_owner = lower_to_hir_internal(tcx, def_id, false); - if let Some((_, node)) = tcx.index_ast(()).get(def_id).map(Steal::steal) { + + if tcx.resolutions(()).delegation_infos.contains_key(&def_id) { + let (r, node) = tcx.index_ast(()).get(def_id).map(Steal::steal).expect("must be"); + tcx.sess.time("drop_ast", || mem::drop(node)); + let _ = r.disambiguators.get(&def_id).map(Steal::steal); } maybe_owner From 35f455e5c49988008d603a4820c9f2833c9f6a3e Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Wed, 2 Sep 2026 13:06:12 +0300 Subject: [PATCH 18/22] wip --- .../src/delegation/resolution.rs | 35 +++--------------- compiler/rustc_middle/src/ty/context.rs | 4 +++ compiler/rustc_query_impl/src/diagnostics.rs | 7 ++++ compiler/rustc_query_impl/src/execution.rs | 28 +++++++++++---- .../src/handle_cycle_error.rs | 36 +++++++++++++------ .../inherent-impls-recursive-cycle.rs | 16 +-------- .../inherent-impls-recursive-cycle.stderr | 20 +++++++---- .../ui/delegation/unsupported.current.stderr | 16 ++++----- tests/ui/delegation/unsupported.next.stderr | 16 ++++----- ...default-trait-shadow-cycle-issue-151358.rs | 3 +- ...ult-trait-shadow-cycle-issue-151358.stderr | 15 +------- .../query-cycle-printing-issue-151358.rs | 3 +- .../query-cycle-printing-issue-151358.stderr | 15 +------- tests/ui/resolve/query-cycle-issue-124901.rs | 3 +- .../resolve/query-cycle-issue-124901.stderr | 15 +------- 15 files changed, 99 insertions(+), 133 deletions(-) diff --git a/compiler/rustc_ast_lowering/src/delegation/resolution.rs b/compiler/rustc_ast_lowering/src/delegation/resolution.rs index a4c38b4d83106..e97cc1b7ad3e7 100644 --- a/compiler/rustc_ast_lowering/src/delegation/resolution.rs +++ b/compiler/rustc_ast_lowering/src/delegation/resolution.rs @@ -113,31 +113,6 @@ pub(super) mod resolver { ) -> TypeRelativeDelegationRes { let tcx = self.tcx(); - // let resolver_and_node = tcx.index_ast(()).get(def_id).map(Steal::borrow); - // let Some(resolver_and_node) = resolver_and_node else { unreachable!() }; - // let (r, node) = &*resolver_and_node; - - // let (delegation, id) = match node { - // AstOwner::Item(Item { kind: ItemKind::Delegation(d), id, .. }) - // | AstOwner::TraitItem(Item { kind: AssocItemKind::Delegation(d), id, .. }) - // | AstOwner::ImplItem(Item { kind: AssocItemKind::Delegation(d), id, .. }) => { - // (d, id) - // } - // _ => unreachable!("we are processing only delegations"), - // }; - - // let mut ctxt = LoweringContext::new(self.tcx(), r, *id, true, false); - - // let path = ctxt.lower_qpath( - // delegation.id, - // &delegation.qself, - // &delegation.path, - // ParamMode::Optional, - // AllowReturnTypeNotation::No, - // ImplTraitContext::Disallowed(ImplTraitPosition::Path), - // None, - // ); - let nodes = &self.tcx().lower_to_hir(def_id).unwrap().nodes; if let Some((ty_hir_id, span, ident)) = @@ -146,13 +121,11 @@ pub(super) mod resolver { if ty_hir_id == HirId::INVALID { TypeRelativeDelegationRes::Error } else { - let ty = nodes.nodes.get(ty_hir_id.local_id).unwrap().node.expect_ty(); + let ty = nodes.nodes[ty_hir_id.local_id].node.expect_ty(); - if let Some(sig_id) = tcx.resolve_delegation_sig(span, def_id, ty, ident) { - TypeRelativeDelegationRes::Ok(sig_id) - } else { - TypeRelativeDelegationRes::Error - } + tcx.resolve_delegation_sig(span, def_id, ty, ident) + .map(|sig_id| TypeRelativeDelegationRes::Ok(sig_id)) + .unwrap_or(TypeRelativeDelegationRes::Error) } } else { tcx.hir_opt_delegation_sig_id(def_id) diff --git a/compiler/rustc_middle/src/ty/context.rs b/compiler/rustc_middle/src/ty/context.rs index 3962af0ec3586..2b623cd36dde0 100644 --- a/compiler/rustc_middle/src/ty/context.rs +++ b/compiler/rustc_middle/src/ty/context.rs @@ -1020,6 +1020,10 @@ impl<'tcx> TyCtxt<'tcx> { self.coroutine_kind(def_id).is_some() } + pub fn is_delegation(self, def_id: LocalDefId) -> bool { + self.resolutions(()).delegation_infos.contains_key(&def_id) + } + pub fn is_async_drop_in_place_coroutine(self, def_id: DefId) -> bool { self.is_lang_item(self.parent(def_id), LangItem::AsyncDropInPlace) } diff --git a/compiler/rustc_query_impl/src/diagnostics.rs b/compiler/rustc_query_impl/src/diagnostics.rs index dd33d4c7bbf57..d46f1a08d3e4c 100644 --- a/compiler/rustc_query_impl/src/diagnostics.rs +++ b/compiler/rustc_query_impl/src/diagnostics.rs @@ -105,3 +105,10 @@ pub(crate) struct NestedCycle { )] pub note_span: (), } + +#[derive(Diagnostic)] +#[diag("query cycle while lowering delegation")] +pub(crate) struct QueryCycleWhileLoweringDelegation { + #[primary_span] + pub span: Span, +} diff --git a/compiler/rustc_query_impl/src/execution.rs b/compiler/rustc_query_impl/src/execution.rs index 13a9927c3375b..6b3b21b112f4b 100644 --- a/compiler/rustc_query_impl/src/execution.rs +++ b/compiler/rustc_query_impl/src/execution.rs @@ -8,6 +8,7 @@ use rustc_errors::FatalError; use rustc_middle::dep_graph::{ DepGraphData, DepNode, DepNodeIndex, DepNodeKey, SerializedDepNodeIndex, }; +use rustc_middle::queries::TaggedQueryKey; use rustc_middle::query::{ ActiveKeyStatus, QueryCache, QueryCycle, QueryJob, QueryJobId, QueryLatch, QueryMode, QueryState, QueryVTable, @@ -19,7 +20,7 @@ use rustc_span::def_id::LOCAL_CRATE; use rustc_span::{DUMMY_SP, Span}; use rustc_structures::Limit; -use crate::diagnostics::{QueryOverflow, QueryOverflowNote}; +use crate::diagnostics::{QueryCycleWhileLoweringDelegation, QueryOverflow, QueryOverflowNote}; use crate::handle_cycle_error; use crate::incremental::should_verify_loaded_value; use crate::job::{ @@ -54,13 +55,26 @@ fn handle_cycle<'tcx, C: QueryCache>( } let _guard = defer(|| *tcx.query_system.cycle_handler_nesting.lock() -= 1); - let error = handle_cycle_error::create_cycle_error(tcx, &cycle, nested); + match (query.create_tagged_key)(key) { + TaggedQueryKey::lower_to_hir(def_id) | TaggedQueryKey::hir_owner(def_id) + if tcx.is_delegation(def_id) => + { + let error = tcx.dcx().create_err(QueryCycleWhileLoweringDelegation { + span: tcx.untracked().source_span.get(def_id).unwrap_or(DUMMY_SP), + }); - if nested { - // Avoid custom handlers and only use the robust `create_cycle_error` for nested cycle errors - (query.handle_cycle_error_fn)(tcx, key, cycle, error) - } else { - (query.handle_cycle_error_fn)(tcx, key, cycle, error) + (query.handle_cycle_error_fn)(tcx, key, cycle, error) + } + _ => { + let error = handle_cycle_error::create_cycle_error(tcx, &cycle, nested); + + if nested { + // Avoid custom handlers and only use the robust `create_cycle_error` for nested cycle errors + handle_cycle_error::default(error) + } else { + (query.handle_cycle_error_fn)(tcx, key, cycle, error) + } + } } } diff --git a/compiler/rustc_query_impl/src/handle_cycle_error.rs b/compiler/rustc_query_impl/src/handle_cycle_error.rs index db40ef3acc092..375f8442758eb 100644 --- a/compiler/rustc_query_impl/src/handle_cycle_error.rs +++ b/compiler/rustc_query_impl/src/handle_cycle_error.rs @@ -18,9 +18,13 @@ use rustc_span::{DUMMY_SP, ErrorGuaranteed, Span}; pub(crate) fn hir_owner<'tcx>( tcx: TyCtxt<'tcx>, def_id: LocalDefId, - _: Cycle<'tcx>, + _: QueryCycle<'tcx>, err: Diag<'_>, ) -> rustc_middle::hir::ProjectedMaybeOwner<'tcx> { + if !tcx.is_delegation(def_id) { + err.emit().raise_fatal(); + } + err.cancel(); rustc_middle::hir::ProjectedMaybeOwner::new(tcx.delegation_error(def_id)) } @@ -28,29 +32,41 @@ pub(crate) fn hir_owner<'tcx>( pub(crate) fn lower_to_hir<'tcx>( tcx: TyCtxt<'tcx>, def_id: LocalDefId, - _: Cycle<'tcx>, + _: QueryCycle<'tcx>, err: Diag<'_>, ) -> rustc_hir::MaybeOwner<'tcx> { + if !tcx.is_delegation(def_id) { + err.emit().raise_fatal(); + } + err.cancel(); tcx.delegation_error(def_id) } pub(crate) fn clauses_of<'tcx>( - _: TyCtxt<'_>, - _: DefId, - _: Cycle<'tcx>, + tcx: TyCtxt<'_>, + def_id: DefId, + _: QueryCycle<'tcx>, err: Diag<'_>, ) -> rustc_middle::ty::GenericClauses<'tcx> { + if def_id.as_local().is_some_and(|def_id| !tcx.is_delegation(def_id)) { + err.emit().raise_fatal(); + } + err.cancel(); Default::default() } pub(crate) fn explicit_clauses_of<'tcx>( - _: TyCtxt<'_>, - _: DefId, - _: Cycle<'tcx>, + tcx: TyCtxt<'_>, + def_id: DefId, + _: QueryCycle<'tcx>, err: Diag<'_>, ) -> rustc_middle::ty::GenericClauses<'tcx> { + if def_id.as_local().is_some_and(|def_id| !tcx.is_delegation(def_id)) { + err.emit().raise_fatal(); + } + err.cancel(); Default::default() } @@ -391,7 +407,7 @@ pub(crate) fn create_cycle_error<'tcx>( ) -> Diag<'tcx> { assert!(!frames.is_empty()); - let span = DUMMY_SP; + let span = frames[0].tagged_key.catch_default_span(tcx, frames[1 % frames.len()].span); let mut cycle_stack = Vec::new(); @@ -406,7 +422,7 @@ pub(crate) fn create_cycle_error<'tcx>( let mut prev = span; for i in 1..frames.len() { let frame = &frames[i]; - let span = DUMMY_SP; + let span = frame.tagged_key.catch_default_span(tcx, frames[(i + 1) % frames.len()].span); cycle_stack.push(crate::diagnostics::CycleStack { span: if span == prev { DUMMY_SP } else { span }, desc: frame.tagged_key.catch_description(tcx), diff --git a/tests/ui/delegation/inherent-impls-recursive-cycle.rs b/tests/ui/delegation/inherent-impls-recursive-cycle.rs index 81a59b63874fb..72c41926ff63f 100644 --- a/tests/ui/delegation/inherent-impls-recursive-cycle.rs +++ b/tests/ui/delegation/inherent-impls-recursive-cycle.rs @@ -2,7 +2,6 @@ trait Trait1 { reuse trait_foo_reused as foo; - //~^ ERROR: encountered a cycle during delegation signature resolution } impl Trait1 for () {} @@ -10,49 +9,36 @@ impl Trait1 for () {} struct S1(T); impl S1 { reuse Trait1::foo { self.0 } - //~^ ERROR: encountered a cycle during delegation signature resolution - //~| ERROR: this function takes 0 arguments but 1 argument was supplied } struct S2(S1<()>); impl S2 { reuse S1::<()>::foo { self.0 } - //~^ ERROR: encountered a cycle during delegation signature resolution - //~| ERROR: this function takes 0 arguments but 1 argument was supplied } reuse S2::foo; -//~^ ERROR: encountered a cycle during delegation signature resolution struct S3; impl S3 { reuse foo; - //~^ ERROR: encountered a cycle during delegation signature resolution } impl Trait1 for S3 { reuse S2::foo { S2(S1(())) } - //~^ ERROR: encountered a cycle during delegation signature resolution - //~| ERROR: this function takes 0 arguments but 1 argument was supplied } trait Trait2 { reuse ::foo { S3 } - //~^ ERROR: encountered a cycle during delegation signature resolution - //~| ERROR: this function takes 0 arguments but 1 argument was supplied } reuse Trait2::foo as trait_foo; -//~^ ERROR: encountered a cycle during delegation signature resolution -//~| ERROR: type annotations needed struct S4; impl S4 { +//~^ ERROR: cycle detected when collecting associated items of `` [E0391] reuse trait_foo; - //~^ ERROR: encountered a cycle during delegation signature resolution } reuse S4::trait_foo as trait_foo_reused; -//~^ ERROR: encountered a cycle during delegation signature resolution fn main() {} diff --git a/tests/ui/delegation/inherent-impls-recursive-cycle.stderr b/tests/ui/delegation/inherent-impls-recursive-cycle.stderr index 3584420ec58c2..f14e3dcc07729 100644 --- a/tests/ui/delegation/inherent-impls-recursive-cycle.stderr +++ b/tests/ui/delegation/inherent-impls-recursive-cycle.stderr @@ -1,11 +1,19 @@ -error[E0391]: cycle detected when collecting associated items of `` +error[E0391]: cycle detected when collecting associated items of `` + --> $DIR/inherent-impls-recursive-cycle.rs:37:1 | - = note: ...which requires computing associated item data for `::trait_foo`... - = note: ...which requires getting owner for `::trait_foo`... - = note: ...which requires lowering HIR for `::trait_foo`... - = note: ...which again requires collecting associated items of ``, completing the cycle +LL | impl S4 { + | ^^^^^^^ + | +note: ...which requires computing associated item data for `::trait_foo`... + --> $DIR/inherent-impls-recursive-cycle.rs:39:11 + | +LL | reuse trait_foo; + | ^^^^^^^^^ + = note: ...which requires getting owner for `::trait_foo`... + = note: ...which requires lowering HIR for `::trait_foo`... + = note: ...which again requires collecting associated items of ``, completing the cycle note: cycle used when lowering HIR for `trait_foo_reused` - --> $DIR/inherent-impls-recursive-cycle.rs:55:11 + --> $DIR/inherent-impls-recursive-cycle.rs:42:11 | LL | reuse S4::trait_foo as trait_foo_reused; | ^^^^^^^^^ diff --git a/tests/ui/delegation/unsupported.current.stderr b/tests/ui/delegation/unsupported.current.stderr index ab5283574b39c..075dfbe7622fe 100644 --- a/tests/ui/delegation/unsupported.current.stderr +++ b/tests/ui/delegation/unsupported.current.stderr @@ -1,23 +1,23 @@ error[E0391]: cycle detected when computing type of `opaque::::opaque_ret::{anon_assoc#0}` - | - = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... - = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle -note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition --> $DIR/unsupported.rs:29:25 | LL | reuse to_reuse::opaque_ret; | ^^^^^^^^^^ + | + = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... + = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle + = note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition = note: for more information, see and error[E0391]: cycle detected when computing type of `opaque::::opaque_ret::{anon_assoc#0}` - | - = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... - = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle -note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition --> $DIR/unsupported.rs:32:24 | LL | reuse ToReuse::opaque_ret; | ^^^^^^^^^^ + | + = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... + = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle + = note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition = note: for more information, see and error: aborting due to 2 previous errors diff --git a/tests/ui/delegation/unsupported.next.stderr b/tests/ui/delegation/unsupported.next.stderr index ab5283574b39c..075dfbe7622fe 100644 --- a/tests/ui/delegation/unsupported.next.stderr +++ b/tests/ui/delegation/unsupported.next.stderr @@ -1,23 +1,23 @@ error[E0391]: cycle detected when computing type of `opaque::::opaque_ret::{anon_assoc#0}` - | - = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... - = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle -note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition --> $DIR/unsupported.rs:29:25 | LL | reuse to_reuse::opaque_ret; | ^^^^^^^^^^ + | + = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... + = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle + = note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition = note: for more information, see and error[E0391]: cycle detected when computing type of `opaque::::opaque_ret::{anon_assoc#0}` - | - = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... - = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle -note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition --> $DIR/unsupported.rs:32:24 | LL | reuse ToReuse::opaque_ret; | ^^^^^^^^^^ + | + = note: ...which requires comparing an impl and trait method signature, inferring any hidden `impl Trait` types in the process... + = note: ...which again requires computing type of `opaque::::opaque_ret::{anon_assoc#0}`, completing the cycle + = note: cycle used when checking assoc item `opaque::::opaque_ret` is compatible with trait definition = note: for more information, see and error: aborting due to 2 previous errors diff --git a/tests/ui/parallel-rustc/default-trait-shadow-cycle-issue-151358.rs b/tests/ui/parallel-rustc/default-trait-shadow-cycle-issue-151358.rs index 21ec2f6b2af29..4e5f9d2c7a86c 100644 --- a/tests/ui/parallel-rustc/default-trait-shadow-cycle-issue-151358.rs +++ b/tests/ui/parallel-rustc/default-trait-shadow-cycle-issue-151358.rs @@ -1,6 +1,5 @@ // Test for #151358, assertion failed: !worker_thread.is_null() -//~^ ERROR internal compiler error: query cycle when printing cycle detected -//~^^ ERROR cycle detected when getting the resolver for lowering +//~^ ERROR cycle detected when getting the resolver for lowering trait Default {} use std::num::NonZero; diff --git a/tests/ui/parallel-rustc/default-trait-shadow-cycle-issue-151358.stderr b/tests/ui/parallel-rustc/default-trait-shadow-cycle-issue-151358.stderr index da16e49a777eb..66ecc68c0909b 100644 --- a/tests/ui/parallel-rustc/default-trait-shadow-cycle-issue-151358.stderr +++ b/tests/ui/parallel-rustc/default-trait-shadow-cycle-issue-151358.stderr @@ -1,25 +1,12 @@ -error: internal compiler error: query cycle when printing cycle detected - | - = note: ...when getting owner for `Default` - = note: ...which requires lowering HIR for `Default`... - = note: ...which requires resolving type relative delegations... - = note: ...which requires getting the AST for lowering... - = note: ...which requires perform lints prior to AST lowering... - = note: ...which requires looking up span for `Default`... - = note: ...which again requires getting owner for `Default`, completing the cycle - = note: cycle used when getting the resolver for lowering - = note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information - error[E0391]: cycle detected when getting the resolver for lowering | = note: ...which requires getting owner for `Default`... = note: ...which requires lowering HIR for `Default`... - = note: ...which requires resolving type relative delegations... = note: ...which requires getting the AST for lowering... = note: ...which requires perform lints prior to AST lowering... = note: ...which again requires getting the resolver for lowering, completing the cycle = note: for more information, see and -error: aborting due to 2 previous errors +error: aborting due to 1 previous error For more information about this error, try `rustc --explain E0391`. diff --git a/tests/ui/query-system/query-cycle-printing-issue-151358.rs b/tests/ui/query-system/query-cycle-printing-issue-151358.rs index e71d83bc7b786..62d30f031ab32 100644 --- a/tests/ui/query-system/query-cycle-printing-issue-151358.rs +++ b/tests/ui/query-system/query-cycle-printing-issue-151358.rs @@ -1,5 +1,4 @@ -//~ ERROR: cycle when printing cycle detected -//~^ ERROR: cycle detected +//~ ERROR: cycle detected trait Default {} use std::num::NonZero; fn main() { diff --git a/tests/ui/query-system/query-cycle-printing-issue-151358.stderr b/tests/ui/query-system/query-cycle-printing-issue-151358.stderr index da16e49a777eb..66ecc68c0909b 100644 --- a/tests/ui/query-system/query-cycle-printing-issue-151358.stderr +++ b/tests/ui/query-system/query-cycle-printing-issue-151358.stderr @@ -1,25 +1,12 @@ -error: internal compiler error: query cycle when printing cycle detected - | - = note: ...when getting owner for `Default` - = note: ...which requires lowering HIR for `Default`... - = note: ...which requires resolving type relative delegations... - = note: ...which requires getting the AST for lowering... - = note: ...which requires perform lints prior to AST lowering... - = note: ...which requires looking up span for `Default`... - = note: ...which again requires getting owner for `Default`, completing the cycle - = note: cycle used when getting the resolver for lowering - = note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information - error[E0391]: cycle detected when getting the resolver for lowering | = note: ...which requires getting owner for `Default`... = note: ...which requires lowering HIR for `Default`... - = note: ...which requires resolving type relative delegations... = note: ...which requires getting the AST for lowering... = note: ...which requires perform lints prior to AST lowering... = note: ...which again requires getting the resolver for lowering, completing the cycle = note: for more information, see and -error: aborting due to 2 previous errors +error: aborting due to 1 previous error For more information about this error, try `rustc --explain E0391`. diff --git a/tests/ui/resolve/query-cycle-issue-124901.rs b/tests/ui/resolve/query-cycle-issue-124901.rs index eacbf73755744..0575f168c372f 100644 --- a/tests/ui/resolve/query-cycle-issue-124901.rs +++ b/tests/ui/resolve/query-cycle-issue-124901.rs @@ -1,5 +1,4 @@ -//~ ERROR: cycle when printing cycle detected -//~^ ERROR: cycle detected +//~ ERROR: cycle detected when getting the resolver for lowering trait Default { type Id; diff --git a/tests/ui/resolve/query-cycle-issue-124901.stderr b/tests/ui/resolve/query-cycle-issue-124901.stderr index da16e49a777eb..66ecc68c0909b 100644 --- a/tests/ui/resolve/query-cycle-issue-124901.stderr +++ b/tests/ui/resolve/query-cycle-issue-124901.stderr @@ -1,25 +1,12 @@ -error: internal compiler error: query cycle when printing cycle detected - | - = note: ...when getting owner for `Default` - = note: ...which requires lowering HIR for `Default`... - = note: ...which requires resolving type relative delegations... - = note: ...which requires getting the AST for lowering... - = note: ...which requires perform lints prior to AST lowering... - = note: ...which requires looking up span for `Default`... - = note: ...which again requires getting owner for `Default`, completing the cycle - = note: cycle used when getting the resolver for lowering - = note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information - error[E0391]: cycle detected when getting the resolver for lowering | = note: ...which requires getting owner for `Default`... = note: ...which requires lowering HIR for `Default`... - = note: ...which requires resolving type relative delegations... = note: ...which requires getting the AST for lowering... = note: ...which requires perform lints prior to AST lowering... = note: ...which again requires getting the resolver for lowering, completing the cycle = note: for more information, see and -error: aborting due to 2 previous errors +error: aborting due to 1 previous error For more information about this error, try `rustc --explain E0391`. From 84008f59ddeb15e63d1ffa0f092e89608748a8ce Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Wed, 2 Sep 2026 14:22:16 +0300 Subject: [PATCH 19/22] wip --- .../src/hir_ty_lowering/mod.rs | 20 +++++++------- .../src/handle_cycle_error.rs | 5 ++-- .../inherent-impls-non-local-crate.rs | 11 ++++++++ .../inherent-impls-non-local-crate.stderr | 27 ++++++++++++++++++- 4 files changed, 51 insertions(+), 12 deletions(-) diff --git a/compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs b/compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs index 24a1de89e8306..d2c377d81b43c 100644 --- a/compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs +++ b/compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs @@ -41,7 +41,7 @@ use rustc_infer::infer::{InferCtxt, TyCtxtInferExt}; use rustc_infer::traits::DynCompatibilityViolation; use rustc_lint_defs::builtin::AMBIGUOUS_ASSOCIATED_ITEMS; use rustc_macros::{TypeFoldable, TypeVisitable}; -use rustc_middle::middle::resolve_bound_vars::ResolveBoundVars; +use rustc_middle::middle::resolve_bound_vars::{ResolveBoundVars, ResolvedArg}; use rustc_middle::middle::stability::AllowUnstable; use rustc_middle::ty::{ self, Const, FnSigKind, GenericArgKind, GenericArgsRef, GenericParamDefKind, LitToConstInput, @@ -584,12 +584,7 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ { lifetime: &hir::Lifetime, reason: RegionInferReason<'_>, ) -> ty::Region<'tcx> { - let resolved = self - .opt_preset_rbv() - .map(|rbv| rbv.defs.get(&lifetime.hir_id.local_id).cloned()) - .unwrap_or_else(|| self.tcx().named_bound_var(lifetime.hir_id)); - - if let Some(resolved) = resolved { + if let Some(resolved) = self.resolve_bound_var(lifetime.hir_id) { let region = self.lower_resolved_lifetime(resolved); self.check_param_uses_if_mcg(region, lifetime.ident.span, false) } else { @@ -597,6 +592,13 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ { } } + #[inline] + fn resolve_bound_var(&self, hir_id: HirId) -> Option { + self.opt_preset_rbv() + .map(|rbv| rbv.defs.get(&hir_id.local_id).cloned()) + .unwrap_or_else(|| self.tcx().named_bound_var(hir_id)) + } + /// Lower a lifetime from the HIR to our internal notion of a lifetime called a *region*. #[instrument(level = "debug", skip(self), ret)] fn lower_resolved_lifetime(&self, resolved: rbv::ResolvedArg) -> ty::Region<'tcx> { @@ -2348,7 +2350,7 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ { pub(crate) fn lower_ty_param(&self, hir_id: HirId) -> Ty<'tcx> { let tcx = self.tcx(); - let ty = match tcx.named_bound_var(hir_id) { + let ty = match self.resolve_bound_var(hir_id) { Some(rbv::ResolvedArg::LateBound(debruijn, index, def_id)) => { let br = ty::BoundTy { var: ty::BoundVar::from_u32(index), @@ -2375,7 +2377,7 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ { pub(crate) fn lower_const_param(&self, param_def_id: DefId, path_hir_id: HirId) -> Const<'tcx> { let tcx = self.tcx(); - let ct = match tcx.named_bound_var(path_hir_id) { + let ct = match self.resolve_bound_var(path_hir_id) { Some(rbv::ResolvedArg::EarlyBound(_)) => { // Find the name and index of the const parameter by indexing the generics of // the parent item and construct a `ParamConst`. diff --git a/compiler/rustc_query_impl/src/handle_cycle_error.rs b/compiler/rustc_query_impl/src/handle_cycle_error.rs index 375f8442758eb..4bbc2b3ebf785 100644 --- a/compiler/rustc_query_impl/src/handle_cycle_error.rs +++ b/compiler/rustc_query_impl/src/handle_cycle_error.rs @@ -9,6 +9,7 @@ use rustc_errors::{Applicability, Diag, MultiSpan, pluralize, struct_span_code_e use rustc_hir as hir; use rustc_hir::def::{DefKind, Res}; use rustc_middle::bug; +use rustc_middle::hir::ProjectedMaybeOwner; use rustc_middle::queries::TaggedQueryKey; use rustc_middle::query::QueryCycle; use rustc_middle::ty::{self, Ty, TyCtxt}; @@ -20,13 +21,13 @@ pub(crate) fn hir_owner<'tcx>( def_id: LocalDefId, _: QueryCycle<'tcx>, err: Diag<'_>, -) -> rustc_middle::hir::ProjectedMaybeOwner<'tcx> { +) -> ProjectedMaybeOwner<'tcx> { if !tcx.is_delegation(def_id) { err.emit().raise_fatal(); } err.cancel(); - rustc_middle::hir::ProjectedMaybeOwner::new(tcx.delegation_error(def_id)) + ProjectedMaybeOwner::new(tcx.delegation_error(def_id)) } pub(crate) fn lower_to_hir<'tcx>( diff --git a/tests/ui/delegation/inherent-impls-non-local-crate.rs b/tests/ui/delegation/inherent-impls-non-local-crate.rs index 22d94ef382846..55397f742a28b 100644 --- a/tests/ui/delegation/inherent-impls-non-local-crate.rs +++ b/tests/ui/delegation/inherent-impls-non-local-crate.rs @@ -20,4 +20,15 @@ reuse inherent_impl::X::foo as x_foo; //~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions //~| ERROR: multiple applicable items in scope +reuse inherent_impl::X::::foo as x_foo_1; +reuse inherent_impl::X::::foo as x_foo_2; + +reuse inherent_impl::X::<_>::foo as x_foo_3; +//~^ ERROR: the placeholder `_` is not allowed within types on item signatures for functions +//~| ERROR: multiple applicable items in scope [E0034] + +reuse inherent_impl::X::<()>::foo as x_foo_4; +//~^ ERROR: no associated function or constant named `foo` found for struct `X<()>` in the current scope + + fn main() {} diff --git a/tests/ui/delegation/inherent-impls-non-local-crate.stderr b/tests/ui/delegation/inherent-impls-non-local-crate.stderr index c131f0a0919ab..f0806133d286c 100644 --- a/tests/ui/delegation/inherent-impls-non-local-crate.stderr +++ b/tests/ui/delegation/inherent-impls-non-local-crate.stderr @@ -4,6 +4,12 @@ error[E0121]: the placeholder `_` is not allowed within types on item signatures LL | reuse inherent_impl::X::foo as x_foo; | ^^^^^^^^^^^^^^^^ not allowed in type signatures +error[E0121]: the placeholder `_` is not allowed within types on item signatures for functions + --> $DIR/inherent-impls-non-local-crate.rs:26:26 + | +LL | reuse inherent_impl::X::<_>::foo as x_foo_3; + | ^ not allowed in type signatures + error[E0599]: no associated function or constant named `not_existing` found for struct `S` in the current scope --> $DIR/inherent-impls-non-local-crate.rs:7:25 | @@ -43,7 +49,26 @@ LL | reuse inherent_impl::X::foo as x_foo; = note: candidate #1 is defined in an impl for the type `X` = note: candidate #2 is defined in an impl for the type `X` -error: aborting due to 6 previous errors +error[E0034]: multiple applicable items in scope + --> $DIR/inherent-impls-non-local-crate.rs:26:30 + | +LL | reuse inherent_impl::X::<_>::foo as x_foo_3; + | ^^^ multiple `foo` found + | + = note: candidate #1 is defined in an impl for the type `X` + = note: candidate #2 is defined in an impl for the type `X` + +error[E0599]: no associated function or constant named `foo` found for struct `X<()>` in the current scope + --> $DIR/inherent-impls-non-local-crate.rs:30:31 + | +LL | reuse inherent_impl::X::<()>::foo as x_foo_4; + | ^^^ associated function or constant not found in `X<()>` + | + = note: the associated function or constant was found for + - `X` + - `X` + +error: aborting due to 9 previous errors Some errors have detailed explanations: E0034, E0121, E0599, E0618. For more information about an error, try `rustc --explain E0034`. From 6fb44662a07f4a9834a4350455775193714ed110 Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Wed, 2 Sep 2026 15:27:31 +0300 Subject: [PATCH 20/22] wip --- .../rustc_ast_lowering/src/delegation/mod.rs | 4 +- .../src/delegation/resolution.rs | 22 ++++---- compiler/rustc_hir/src/hir.rs | 4 +- compiler/rustc_middle/src/ty/mod.rs | 8 --- compiler/rustc_resolve/src/late.rs | 55 ++++++------------- compiler/rustc_resolve/src/lib.rs | 5 +- tests/ui/delegation/inherent-impls-ambig.rs | 7 ++- .../ui/delegation/inherent-impls-ambig.stderr | 19 ++++++- .../delegation/inherent-impls-trait-impls.rs | 17 ++++++ .../inherent-impls-trait-impls.stderr | 18 ++++++ 10 files changed, 92 insertions(+), 67 deletions(-) create mode 100644 tests/ui/delegation/inherent-impls-trait-impls.rs create mode 100644 tests/ui/delegation/inherent-impls-trait-impls.stderr diff --git a/compiler/rustc_ast_lowering/src/delegation/mod.rs b/compiler/rustc_ast_lowering/src/delegation/mod.rs index fb77d444eaa47..c47c9179ff82a 100644 --- a/compiler/rustc_ast_lowering/src/delegation/mod.rs +++ b/compiler/rustc_ast_lowering/src/delegation/mod.rs @@ -621,8 +621,8 @@ impl<'hir> LoweringContext<'_, 'hir> { ); let ty_id = match path { - QPath::Resolved(_, _) => HirId::INVALID, - QPath::TypeRelative(ty, _) => ty.hir_id, + QPath::Resolved(_, _) => None, + QPath::TypeRelative(ty, _) => Some(ty.hir_id), }; if let [.., parent, child] = &delegation.path.segments[..] diff --git a/compiler/rustc_ast_lowering/src/delegation/resolution.rs b/compiler/rustc_ast_lowering/src/delegation/resolution.rs index e97cc1b7ad3e7..c3dd2d2f73b46 100644 --- a/compiler/rustc_ast_lowering/src/delegation/resolution.rs +++ b/compiler/rustc_ast_lowering/src/delegation/resolution.rs @@ -51,7 +51,6 @@ pub(super) struct DelegationResolution { pub(super) mod resolver { use rustc_ast::NodeId; - use rustc_hir::HirId; use rustc_hir::def_id::{DefId, LocalDefId}; use rustc_middle::ty::{TyCtxt, TypeRelativeDelegationRes}; use rustc_span::ErrorGuaranteed; @@ -113,19 +112,22 @@ pub(super) mod resolver { ) -> TypeRelativeDelegationRes { let tcx = self.tcx(); - let nodes = &self.tcx().lower_to_hir(def_id).unwrap().nodes; + let Some(nodes) = &self.tcx().lower_to_hir(def_id).as_owner().map(|o| &o.nodes) else { + return TypeRelativeDelegationRes::Error; + }; if let Some((ty_hir_id, span, ident)) = nodes.node().fn_decl().unwrap().opt_error_delegation_ty_id() { - if ty_hir_id == HirId::INVALID { - TypeRelativeDelegationRes::Error - } else { - let ty = nodes.nodes[ty_hir_id.local_id].node.expect_ty(); - - tcx.resolve_delegation_sig(span, def_id, ty, ident) - .map(|sig_id| TypeRelativeDelegationRes::Ok(sig_id)) - .unwrap_or(TypeRelativeDelegationRes::Error) + match ty_hir_id { + None => TypeRelativeDelegationRes::Error, + Some(ty_hir_id) => { + let ty = nodes.nodes[ty_hir_id.local_id].node.expect_ty(); + + tcx.resolve_delegation_sig(span, def_id, ty, ident) + .map(|sig_id| TypeRelativeDelegationRes::Ok(sig_id)) + .unwrap_or(TypeRelativeDelegationRes::Error) + } } } else { tcx.hir_opt_delegation_sig_id(def_id) diff --git a/compiler/rustc_hir/src/hir.rs b/compiler/rustc_hir/src/hir.rs index 3b10daa0e8a43..4abfb1ad6d2a2 100644 --- a/compiler/rustc_hir/src/hir.rs +++ b/compiler/rustc_hir/src/hir.rs @@ -3550,7 +3550,7 @@ pub enum InferDelegation<'hir> { DefId(DefId), /// Used during signature inheritance, `DefId` corresponds to the signature function. Sig(DefId, InferDelegationSig<'hir>), - Err(&'hir (HirId, Span, Ident)), + Err(&'hir (Option, Span, Ident)), } /// The various kinds of types recognized by the compiler. @@ -3908,7 +3908,7 @@ impl<'hir> FnDecl<'hir> { None } - pub fn opt_error_delegation_ty_id(&self) -> Option<(HirId, Span, Ident)> { + pub fn opt_error_delegation_ty_id(&self) -> Option<(Option, Span, Ident)> { if let FnRetTy::Return(ty) = self.output && let TyKind::InferDelegation(InferDelegation::Err(data)) = ty.kind { diff --git a/compiler/rustc_middle/src/ty/mod.rs b/compiler/rustc_middle/src/ty/mod.rs index adff8b616b6ed..701c1a42a862d 100644 --- a/compiler/rustc_middle/src/ty/mod.rs +++ b/compiler/rustc_middle/src/ty/mod.rs @@ -203,8 +203,6 @@ pub struct ResolverGlobalCtxt { // Information about delegations which is used when handling recursive delegations // and ensures easy access to delegation-only `LocalDefId`s. pub delegation_infos: FxIndexMap, - pub delegation_inh_functions_map: - FxIndexMap>, pub delegation_types_to_inh_impls: FxIndexMap>, } @@ -296,12 +294,6 @@ pub enum TypeRelativeDelegationRes { Error, } -#[derive(Debug, StableHash)] -pub enum DelegationInhFuncKind { - Single(LocalDefId), - Ambig, -} - #[derive(Clone, Copy, Debug, StableHash)] pub struct MainDefinition { pub res: Res, diff --git a/compiler/rustc_resolve/src/late.rs b/compiler/rustc_resolve/src/late.rs index b3b6e78b736d1..9c76160792c71 100644 --- a/compiler/rustc_resolve/src/late.rs +++ b/compiler/rustc_resolve/src/late.rs @@ -30,7 +30,7 @@ use rustc_hir::def_id::{CRATE_DEF_ID, DefId, LOCAL_CRATE, LocalDefId}; use rustc_hir::{MissingLifetimeKind, PrimTy}; use rustc_lint_defs::builtin::{ELIDED_LIFETIMES_IN_PATHS, UNUSED_LABELS}; use rustc_middle::middle::resolve_bound_vars::Set1; -use rustc_middle::ty::{AssocTag, DelegationInfo, DelegationInhFuncKind, Visibility}; +use rustc_middle::ty::{AssocTag, DelegationInfo, Visibility}; use rustc_middle::{bug, span_bug}; use rustc_session::config::ResolveDocLinks; use rustc_session::diagnostics::feature_err; @@ -3515,7 +3515,10 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { // If applicable, create a rib for the type parameters. self.with_generic_param_rib( &generics.params, - RibKind::Item(HasGenericParams::Yes(generics.span), self.r.tcx.def_kind(self.r.current_owner.def_id)), + RibKind::Item( + HasGenericParams::Yes(generics.span), + self.r.tcx.def_kind(self.r.current_owner.def_id), + ), item_id, LifetimeBinderKind::ImplBlock, generics.span, @@ -3525,7 +3528,7 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { this.with_lifetime_rib( LifetimeRibKind::AnonymousCreateParameter { binder: item_id, - report_in_path: true + report_in_path: true, }, |this| { // Resolve the trait reference, if necessary. @@ -3564,16 +3567,22 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { let self_type_def_id = of_trait .is_none() .then(|| { - this.r.partial_res_map.get(&self_type.id).and_then(|res| { - res.full_res() - .and_then(|r| r.opt_def_id()) - .and_then(|id| id.as_local()) - }) + this.r.partial_res_map.get(&self_type.id).and_then( + |res| { + res.full_res() + .and_then(|r| r.opt_def_id()) + .and_then(|id| id.as_local()) + }, + ) }) .flatten(); if let Some(id) = self_type_def_id { - this.r.delegation_types_to_inh_impls.entry(id).or_default().push(this.r.current_owner.def_id); + this.r + .delegation_types_to_inh_impls + .entry(id) + .or_default() + .push(this.r.current_owner.def_id); } // Resolve the items within the impl. @@ -3588,7 +3597,6 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { &mut seen_trait_items, trait_id, of_trait.is_some(), - self_type_def_id ); }) } @@ -3632,7 +3640,6 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { seen_trait_items: &mut FxHashMap, trait_id: Option, is_in_trait_impl: bool, - self_type_def_id: Option, ) { use crate::ResolutionError::*; self.resolve_doc_links(&item.attrs, MaybeExported::ImplItem(trait_id.ok_or(&item.vis))); @@ -3734,10 +3741,6 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { }, ); - if let Some(self_type_def_id) = self_type_def_id { - self.fill_delegation_inh_functions_map(self_type_def_id, ident); - } - self.resolve_define_opaques(define_opaque); } AssocItemKind::Type(TyAlias { ident, generics, .. }) => { @@ -3780,14 +3783,6 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { LifetimeBinderKind::Function, delegation.path.segments.last().unwrap().ident.span, |this| { - if let Some(self_type_def_id) = self_type_def_id { - this.fill_delegation_inh_functions_map( - self_type_def_id, - // If rename is specified then ident equals rename. - &delegation.ident, - ); - } - this.check_trait_item( item.id, delegation.ident, @@ -3812,20 +3807,6 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> { self.diag_metadata.current_impl_item = prev; } - fn fill_delegation_inh_functions_map(&mut self, self_type_def_id: LocalDefId, ident: &Ident) { - let map = self.r.delegation_inh_functions_map.entry(self_type_def_id).or_default(); - - match map.get(ident) { - None => { - map.insert(*ident, DelegationInhFuncKind::Single(self.r.current_owner.def_id)); - } - Some(DelegationInhFuncKind::Single(..)) => { - map.insert(*ident, DelegationInhFuncKind::Ambig); - } - _ => {} - }; - } - fn check_trait_item( &mut self, id: NodeId, diff --git a/compiler/rustc_resolve/src/lib.rs b/compiler/rustc_resolve/src/lib.rs index 58fa7c80d4525..0d2e68be8fde1 100644 --- a/compiler/rustc_resolve/src/lib.rs +++ b/compiler/rustc_resolve/src/lib.rs @@ -66,7 +66,7 @@ use rustc_middle::metadata::{AmbigModChild, ModChild, Reexport}; use rustc_middle::middle::privacy::EffectiveVisibilities; use rustc_middle::query::Providers; use rustc_middle::ty::{ - self, DelegationInfo, DelegationInhFuncKind, MainDefinition, PerOwnerResolverData, + self, DelegationInfo, MainDefinition, PerOwnerResolverData, RegisteredTools, ResolverAstLowering, ResolverGlobalCtxt, TyCtxt, TyCtxtFeed, Visibility, }; use rustc_middle::{bug, span_bug}; @@ -1516,7 +1516,6 @@ pub struct Resolver<'ra, 'tcx> { item_required_generic_args_suggestions: FxHashMap = default::fx_hash_map(), delegation_fn_sigs: LocalDefIdMap = Default::default(), delegation_infos: FxIndexMap, - delegation_inh_functions_map: FxIndexMap>, delegation_types_to_inh_impls: FxIndexMap>, main_def: Option = None, @@ -1890,7 +1889,6 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> { current_crate_outer_attr_insert_span, disambiguators: Default::default(), delegation_infos: Default::default(), - delegation_inh_functions_map: Default::default(), delegation_types_to_inh_impls: Default::default(), features: tcx.features(), .. @@ -1996,7 +1994,6 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> { all_macro_rules: self.all_macro_rules, stripped_cfg_items, delegation_infos: self.delegation_infos, - delegation_inh_functions_map: self.delegation_inh_functions_map, delegation_types_to_inh_impls: self.delegation_types_to_inh_impls, }; let ast_lowering = ty::ResolverAstLowering { diff --git a/tests/ui/delegation/inherent-impls-ambig.rs b/tests/ui/delegation/inherent-impls-ambig.rs index 6ca629cb2db7b..e52511cf2872b 100644 --- a/tests/ui/delegation/inherent-impls-ambig.rs +++ b/tests/ui/delegation/inherent-impls-ambig.rs @@ -57,8 +57,13 @@ mod test_2 { //~| ERROR: multiple applicable items in scope [E0034] reuse X::::foo as foo1; + reuse X::::foo_self as foo_self1; + reuse X::::foo as foo2; + reuse X::::foo_self as foo_self2; - reuse X::::foo_self as foo_self1; + reuse X::::foo as foo3; + //~^ ERROR: no associated function or constant named `foo` found for struct `test_2::X` in the current scope + reuse X::::foo_self as foo_self3; //~^ ERROR: no associated function or constant named `foo_self` found for struct `test_2::X` in the current scope } diff --git a/tests/ui/delegation/inherent-impls-ambig.stderr b/tests/ui/delegation/inherent-impls-ambig.stderr index 7708a6d61f161..0a69044abda19 100644 --- a/tests/ui/delegation/inherent-impls-ambig.stderr +++ b/tests/ui/delegation/inherent-impls-ambig.stderr @@ -90,16 +90,29 @@ note: candidate #2 is defined in an impl for the type `test_2::X` LL | fn foo_self(self) {} | ^^^^^^^^^^^^^^^^^ +error[E0599]: no associated function or constant named `foo` found for struct `test_2::X` in the current scope + --> $DIR/inherent-impls-ambig.rs:64:28 + | +LL | struct X(T, U); + | -------------- associated function or constant `foo` not found for this struct +... +LL | reuse X::::foo as foo3; + | ^^^ associated function or constant not found in `test_2::X` + | + = note: the associated function or constant was found for + - `test_2::X` + - `test_2::X` + error[E0599]: no associated function or constant named `foo_self` found for struct `test_2::X` in the current scope - --> $DIR/inherent-impls-ambig.rs:61:28 + --> $DIR/inherent-impls-ambig.rs:66:28 | LL | struct X(T, U); | -------------- associated function or constant `foo_self` not found for this struct ... -LL | reuse X::::foo_self as foo_self1; +LL | reuse X::::foo_self as foo_self3; | ^^^^^^^^ associated function or constant not found in `test_2::X` -error: aborting due to 9 previous errors +error: aborting due to 10 previous errors Some errors have detailed explanations: E0034, E0121, E0599. For more information about an error, try `rustc --explain E0034`. diff --git a/tests/ui/delegation/inherent-impls-trait-impls.rs b/tests/ui/delegation/inherent-impls-trait-impls.rs new file mode 100644 index 0000000000000..127ed44cfa19c --- /dev/null +++ b/tests/ui/delegation/inherent-impls-trait-impls.rs @@ -0,0 +1,17 @@ +#![feature(fn_delegation)] + +trait Trait { + fn foo(&self) {} +} + +struct X; +impl Trait for X { + fn foo(&self) {} +} + +reuse X::foo; +//~^ ERROR: no associated function or constant named `foo` found for struct `X` in the current scope + +fn main() { + foo(); +} diff --git a/tests/ui/delegation/inherent-impls-trait-impls.stderr b/tests/ui/delegation/inherent-impls-trait-impls.stderr new file mode 100644 index 0000000000000..e46ade5fbfdd6 --- /dev/null +++ b/tests/ui/delegation/inherent-impls-trait-impls.stderr @@ -0,0 +1,18 @@ +error[E0599]: no associated function or constant named `foo` found for struct `X` in the current scope + --> $DIR/inherent-impls-trait-impls.rs:12:10 + | +LL | struct X; + | -------- associated function or constant `foo` not found for this struct +... +LL | reuse X::foo; + | ^^^ associated function or constant not found in `X` + | + = help: items from traits can only be used if the trait is in scope +help: trait `Trait` which provides `foo` is implemented but not in scope; perhaps you want to import it + | +LL + use Trait; + | + +error: aborting due to 1 previous error + +For more information about this error, try `rustc --explain E0599`. From 8202a8fe9b348e6e222355349d600bc6b07d3ca0 Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Wed, 2 Sep 2026 16:01:59 +0300 Subject: [PATCH 21/22] Cleanups --- compiler/rustc_middle/src/queries.rs | 5 ----- compiler/rustc_resolve/src/lib.rs | 4 ++-- 2 files changed, 2 insertions(+), 7 deletions(-) diff --git a/compiler/rustc_middle/src/queries.rs b/compiler/rustc_middle/src/queries.rs index af43d587215bf..6e542ee0cacff 100644 --- a/compiler/rustc_middle/src/queries.rs +++ b/compiler/rustc_middle/src/queries.rs @@ -231,11 +231,6 @@ rustc_queries! { desc { "getting the source span" } } - query resolve_type_relative_delegations(_: ()) -> &'tcx FxIndexMap { - arena_cache - desc { "resolving type relative delegations" } - } - query lower_to_hir(def_id: LocalDefId) -> hir::MaybeOwner<'tcx> { eval_always handle_cycle_error diff --git a/compiler/rustc_resolve/src/lib.rs b/compiler/rustc_resolve/src/lib.rs index 0d2e68be8fde1..71746fdf70aaf 100644 --- a/compiler/rustc_resolve/src/lib.rs +++ b/compiler/rustc_resolve/src/lib.rs @@ -66,8 +66,8 @@ use rustc_middle::metadata::{AmbigModChild, ModChild, Reexport}; use rustc_middle::middle::privacy::EffectiveVisibilities; use rustc_middle::query::Providers; use rustc_middle::ty::{ - self, DelegationInfo, MainDefinition, PerOwnerResolverData, - RegisteredTools, ResolverAstLowering, ResolverGlobalCtxt, TyCtxt, TyCtxtFeed, Visibility, + self, DelegationInfo, MainDefinition, PerOwnerResolverData, RegisteredTools, + ResolverAstLowering, ResolverGlobalCtxt, TyCtxt, TyCtxtFeed, Visibility, }; use rustc_middle::{bug, span_bug}; use rustc_span::def_id::{LocalModId, ModId}; From 193c5b5deaf620332e3d370395815044ec42aa05 Mon Sep 17 00:00:00 2001 From: aerooneqq Date: Wed, 2 Sep 2026 16:08:17 +0300 Subject: [PATCH 22/22] Fix checks --- compiler/rustc_query_impl/src/handle_cycle_error.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/compiler/rustc_query_impl/src/handle_cycle_error.rs b/compiler/rustc_query_impl/src/handle_cycle_error.rs index 4bbc2b3ebf785..00f2190c59982 100644 --- a/compiler/rustc_query_impl/src/handle_cycle_error.rs +++ b/compiler/rustc_query_impl/src/handle_cycle_error.rs @@ -50,7 +50,7 @@ pub(crate) fn clauses_of<'tcx>( _: QueryCycle<'tcx>, err: Diag<'_>, ) -> rustc_middle::ty::GenericClauses<'tcx> { - if def_id.as_local().is_some_and(|def_id| !tcx.is_delegation(def_id)) { + if def_id.as_local().is_none_or(|def_id| !tcx.is_delegation(def_id)) { err.emit().raise_fatal(); } @@ -64,7 +64,7 @@ pub(crate) fn explicit_clauses_of<'tcx>( _: QueryCycle<'tcx>, err: Diag<'_>, ) -> rustc_middle::ty::GenericClauses<'tcx> { - if def_id.as_local().is_some_and(|def_id| !tcx.is_delegation(def_id)) { + if def_id.as_local().is_none_or(|def_id| !tcx.is_delegation(def_id)) { err.emit().raise_fatal(); }