@@ -2668,6 +2668,49 @@ impl<'cx, 'gcx, 'tcx> SelectionContext<'cx, 'gcx, 'tcx> {
2668
2668
}
2669
2669
}
2670
2670
2671
+ fn match_impl_fastpath ( & mut self ,
2672
+ impl_def_id : DefId ,
2673
+ impl_trait_ref : ty:: TraitRef < ' tcx > ,
2674
+ obligation : & TraitObligation < ' tcx > )
2675
+ -> Option < Result < & ' tcx Substs < ' tcx > , ( ) > >
2676
+ {
2677
+ debug ! ( "match_impl_fastpath({:?}={:?}, {:?}) entry" ,
2678
+ impl_def_id, impl_trait_ref, obligation) ;
2679
+
2680
+ if impl_trait_ref. has_projection_types ( ) {
2681
+ return None ;
2682
+ }
2683
+
2684
+ let obligation_predicate = self . tcx ( ) . no_late_bound_regions ( & obligation. predicate ) ;
2685
+ let obligation_trait_ref = match obligation_predicate {
2686
+ Some ( predicate) => predicate. trait_ref ,
2687
+ _ => return None
2688
+ } ;
2689
+
2690
+ let impl_substs = self . infcx . fresh_substs_for_item ( obligation. cause . span ,
2691
+ impl_def_id) ;
2692
+ let impl_trait_ref = impl_trait_ref. subst ( self . tcx ( ) , impl_substs) ;
2693
+
2694
+ debug ! ( "match_impl(impl_def_id={:?}, obligation={:?}, \
2695
+ impl_trait_ref={:?}, skol_obligation_trait_ref={:?}) fastpath",
2696
+ impl_def_id,
2697
+ obligation,
2698
+ impl_trait_ref,
2699
+ obligation_trait_ref) ;
2700
+
2701
+ let origin = TypeOrigin :: RelateOutputImplTypes ( obligation. cause . span ) ;
2702
+ match self . infcx . eq_trait_refs ( false , origin, impl_trait_ref, obligation_trait_ref) {
2703
+ Ok ( InferOk { obligations, .. } ) => {
2704
+ self . inferred_obligations . extend ( obligations) ;
2705
+ Some ( Ok ( impl_substs) )
2706
+ }
2707
+ Err ( e) => {
2708
+ debug ! ( "match_impl_fastpath: failed eq_trait_refs due to `{}`" , e) ;
2709
+ Some ( Err ( ( ) ) )
2710
+ }
2711
+ }
2712
+ }
2713
+
2671
2714
fn match_impl ( & mut self ,
2672
2715
impl_def_id : DefId ,
2673
2716
obligation : & TraitObligation < ' tcx > ,
@@ -2684,6 +2727,13 @@ impl<'cx, 'gcx, 'tcx> SelectionContext<'cx, 'gcx, 'tcx> {
2684
2727
return Err ( ( ) ) ;
2685
2728
}
2686
2729
2730
+ if let Some ( result) = self . match_impl_fastpath ( impl_def_id, impl_trait_ref, obligation) {
2731
+ return result. map ( |substs| (
2732
+ Normalized { value : substs, obligations : vec ! [ ] } ,
2733
+ FnvHashMap ( )
2734
+ ) ) ;
2735
+ }
2736
+
2687
2737
let ( skol_obligation, skol_map) = self . infcx ( ) . skolemize_late_bound_regions (
2688
2738
& obligation. predicate ,
2689
2739
snapshot) ;
@@ -2702,7 +2752,7 @@ impl<'cx, 'gcx, 'tcx> SelectionContext<'cx, 'gcx, 'tcx> {
2702
2752
& impl_trait_ref) ;
2703
2753
2704
2754
debug ! ( "match_impl(impl_def_id={:?}, obligation={:?}, \
2705
- impl_trait_ref={:?}, skol_obligation_trait_ref={:?})",
2755
+ impl_trait_ref={:?}, skol_obligation_trait_ref={:?}) slowpath ",
2706
2756
impl_def_id,
2707
2757
obligation,
2708
2758
impl_trait_ref,
0 commit comments