@@ -232,37 +232,46 @@ impl<'a, 'tcx> LinkCollector<'a, 'tcx> {
232232 DefKind :: Struct | DefKind :: Union | DefKind :: Enum | DefKind :: TyAlias ,
233233 did,
234234 ) => {
235- // We need item's parent to know if it's
236- // trait impl or struct/enum/etc impl
237- let item_parent = item_opt
235+ // Checks if item_name belongs to `impl SomeItem`
236+ let impl_item = cx
237+ . tcx
238+ . inherent_impls ( did)
239+ . iter ( )
240+ . flat_map ( |imp| cx. tcx . associated_items ( * imp) . in_definition_order ( ) )
241+ . find ( |item| item. ident . name == item_name) ;
242+ let trait_item = item_opt
238243 . and_then ( |item| self . cx . as_local_hir_id ( item. def_id ) )
239244 . and_then ( |item_hir| {
245+ // Checks if item_name belongs to `impl SomeTrait for SomeItem`
240246 let parent_hir = self . cx . tcx . hir ( ) . get_parent_item ( item_hir) ;
241- self . cx . tcx . hir ( ) . find ( parent_hir)
247+ let item_parent = self . cx . tcx . hir ( ) . find ( parent_hir) ;
248+ match item_parent {
249+ Some ( hir:: Node :: Item ( hir:: Item {
250+ kind : hir:: ItemKind :: Impl { of_trait : Some ( _) , self_ty, .. } ,
251+ ..
252+ } ) ) => cx
253+ . tcx
254+ . associated_item_def_ids ( self_ty. hir_id . owner )
255+ . iter ( )
256+ . map ( |child| {
257+ let associated_item = cx. tcx . associated_item ( * child) ;
258+ associated_item
259+ } )
260+ . find ( |child| child. ident . name == item_name) ,
261+ _ => None ,
262+ }
242263 } ) ;
243- let item = match item_parent {
244- Some ( hir:: Node :: Item ( hir:: Item {
245- kind : hir:: ItemKind :: Impl { of_trait : Some ( _) , self_ty, .. } ,
246- ..
247- } ) ) => {
248- // trait impl
249- cx. tcx
250- . associated_item_def_ids ( self_ty. hir_id . owner )
251- . iter ( )
252- . map ( |child| {
253- let associated_item = cx. tcx . associated_item ( * child) ;
254- associated_item
255- } )
256- . find ( |child| child. ident . name == item_name)
257- }
258- _ => {
259- // struct/enum/etc. impl
260- cx. tcx
261- . inherent_impls ( did)
262- . iter ( )
263- . flat_map ( |imp| cx. tcx . associated_items ( * imp) . in_definition_order ( ) )
264- . find ( |item| item. ident . name == item_name)
264+ let item = match ( impl_item, trait_item) {
265+ ( Some ( from_impl) , Some ( _) ) => {
266+ // Although it's ambiguous, return impl version for compat. sake.
267+ // To handle that properly resolve() would have to support
268+ // something like
269+ // [`ambi_fn`](<SomeStruct as SomeTrait>::ambi_fn)
270+ Some ( from_impl)
265271 }
272+ ( None , Some ( from_trait) ) => Some ( from_trait) ,
273+ ( Some ( from_impl) , None ) => Some ( from_impl) ,
274+ _ => None ,
266275 } ;
267276
268277 if let Some ( item) = item {
0 commit comments