@@ -15,6 +15,7 @@ use crate::solve::{GenerateProofTree, InferCtxtEvalExt, UseGlobalCache};
1515use crate :: traits:: query:: evaluate_obligation:: InferCtxtExt as _;
1616use crate :: traits:: specialize:: to_pretty_impl_header;
1717use crate :: traits:: NormalizeExt ;
18+ use ambiguity:: Ambiguity :: * ;
1819use on_unimplemented:: { AppendConstMessage , OnUnimplementedNote , TypeErrCtxtExt as _} ;
1920use rustc_data_structures:: fx:: { FxHashMap , FxIndexMap } ;
2021use rustc_errors:: {
@@ -2283,14 +2284,28 @@ impl<'tcx> InferCtxtPrivExt<'tcx> for TypeErrCtxt<'_, 'tcx> {
22832284 )
22842285 } ;
22852286
2286- let ambiguities = ambiguity:: recompute_applicable_impls (
2287+ let mut ambiguities = ambiguity:: recompute_applicable_impls (
22872288 self . infcx ,
22882289 & obligation. with ( self . tcx , trait_ref) ,
22892290 ) ;
22902291 let has_non_region_infer =
22912292 trait_ref. skip_binder ( ) . args . types ( ) . any ( |t| !t. is_ty_or_numeric_infer ( ) ) ;
2292- // It doesn't make sense to talk about applicable impls if there are more
2293- // than a handful of them.
2293+ // It doesn't make sense to talk about applicable impls if there are more than a
2294+ // handful of them. If there are a lot of them, but only a few of them have no type
2295+ // params, we only show those, as they are more likely to be useful/intended.
2296+ if ambiguities. len ( ) > 20 {
2297+ let infcx = self . infcx ;
2298+ if !ambiguities. iter ( ) . all ( |option| match option {
2299+ DefId ( did) => infcx. fresh_args_for_item ( DUMMY_SP , * did) . is_empty ( ) ,
2300+ ParamEnv ( _) => true ,
2301+ } ) {
2302+ // If not all are blanket impls, we filter blanked impls out.
2303+ ambiguities. retain ( |option| match option {
2304+ DefId ( did) => infcx. fresh_args_for_item ( DUMMY_SP , * did) . is_empty ( ) ,
2305+ ParamEnv ( _) => true ,
2306+ } ) ;
2307+ }
2308+ }
22942309 if ambiguities. len ( ) > 1 && ambiguities. len ( ) < 10 && has_non_region_infer {
22952310 if self . tainted_by_errors ( ) . is_some ( ) && subst. is_none ( ) {
22962311 // If `subst.is_none()`, then this is probably two param-env
@@ -2309,7 +2324,7 @@ impl<'tcx> InferCtxtPrivExt<'tcx> for TypeErrCtxt<'_, 'tcx> {
23092324 err. note ( format ! ( "cannot satisfy `{predicate}`" ) ) ;
23102325 let impl_candidates = self
23112326 . find_similar_impl_candidates ( predicate. to_opt_poly_trait_pred ( ) . unwrap ( ) ) ;
2312- if impl_candidates. len ( ) < 10 {
2327+ if impl_candidates. len ( ) < 40 {
23132328 self . report_similar_impl_candidates (
23142329 impl_candidates. as_slice ( ) ,
23152330 trait_ref,
0 commit comments