about summary refs log tree commit diff
path: root/compiler/rustc_ty_utils/src
diff options
context:
space:
mode:
authorMatthias Krüger <476013+matthiaskrgr@users.noreply.github.com>2025-07-06 10:03:23 +0200
committerGitHub <noreply@github.com>2025-07-06 10:03:23 +0200
commit534c09a779e8b0d7bdd289a7a4af128eb2bdd30b (patch)
tree40d1a283d83431e56bcf8e0932526b481fb0a4ec /compiler/rustc_ty_utils/src
parent6fb00b1514174f215b09afbc574f15f196eb556a (diff)
parent5bbab8967d08362a36ceb5622dd7daac0c5692f4 (diff)
downloadrust-534c09a779e8b0d7bdd289a7a4af128eb2bdd30b.tar.gz
rust-534c09a779e8b0d7bdd289a7a4af128eb2bdd30b.zip
Rollup merge of #143484 - bvanjoi:issue-140796, r=compiler-errors
distinguish the duplicate item of rpitit

Fixes rust-lang/rust#140796

r? compiler

cc `@Zoxc`
Diffstat (limited to 'compiler/rustc_ty_utils/src')
-rw-r--r--compiler/rustc_ty_utils/src/assoc.rs31
1 files changed, 29 insertions, 2 deletions
diff --git a/compiler/rustc_ty_utils/src/assoc.rs b/compiler/rustc_ty_utils/src/assoc.rs
index a65f9b347dc..2fb3c5ff945 100644
--- a/compiler/rustc_ty_utils/src/assoc.rs
+++ b/compiler/rustc_ty_utils/src/assoc.rs
@@ -195,12 +195,39 @@ fn associated_types_for_impl_traits_in_associated_fn(
     match tcx.def_kind(parent_def_id) {
         DefKind::Trait => {
             if let Some(output) = tcx.hir_get_fn_output(fn_def_id) {
-                let data = DefPathData::AnonAssocTy(tcx.item_name(fn_def_id.to_def_id()));
+                let def_path_id = |def_id: LocalDefId| tcx.item_name(def_id.to_def_id());
+                let def_path_data = def_path_id(fn_def_id);
+
+                let (.., trait_item_refs) = tcx.hir_expect_item(parent_def_id).expect_trait();
+                // The purpose of `disambiguator_idx` is to ensure there are
+                // no duplicate `def_id` in certain cases, such as:
+                // ```
+                // trait Foo {
+                //     fn bar() -> impl Trait;
+                //     fn bar() -> impl Trait;
+                //              // ~~~~~~~~~~ It will generate the same ID if we don’t disambiguate it.
+                // }
+                // ```
+                let disambiguator_idx = trait_item_refs
+                    .iter()
+                    .take_while(|item| item.id.owner_id.def_id != fn_def_id)
+                    .fold(0, |acc, item| {
+                        if !matches!(item.kind, hir::AssocItemKind::Fn { .. }) {
+                            acc
+                        } else if def_path_id(item.id.owner_id.def_id) == def_path_data {
+                            tcx.def_key(item.id.owner_id.def_id).disambiguated_data.disambiguator
+                                + 1
+                        } else {
+                            acc
+                        }
+                    });
+
+                let data = DefPathData::AnonAssocTy(def_path_data);
                 let mut visitor = RPITVisitor {
                     tcx,
                     synthetics: vec![],
                     data,
-                    disambiguator: DisambiguatorState::with(parent_def_id, data, 0),
+                    disambiguator: DisambiguatorState::with(parent_def_id, data, disambiguator_idx),
                 };
                 visitor.visit_fn_ret_ty(output);
                 tcx.arena.alloc_from_iter(