@@ -93,7 +93,7 @@ pub enum Reveal {
93
93
/// }
94
94
NotSpecializable ,
95
95
96
- /// At trans time, all projections will succeed.
96
+ /// At trans time, all monomorphic projections will succeed.
97
97
All ,
98
98
}
99
99
@@ -878,7 +878,7 @@ fn assemble_candidates_from_impls<'cx, 'gcx, 'tcx>(
878
878
879
879
candidate_set. vec . push ( ProjectionTyCandidate :: Select ) ;
880
880
}
881
- super :: VtableImpl ( ref impl_data) if selcx . projection_mode ( ) != Reveal :: All => {
881
+ super :: VtableImpl ( ref impl_data) => {
882
882
// We have to be careful when projecting out of an
883
883
// impl because of specialization. If we are not in
884
884
// trans (i.e., projection mode is not "any"), and the
@@ -902,37 +902,43 @@ fn assemble_candidates_from_impls<'cx, 'gcx, 'tcx>(
902
902
impl_data. impl_def_id ,
903
903
obligation. predicate . item_name ) ;
904
904
let new_candidate = if let Some ( node_item) = opt_node_item {
905
- if node_item. node . is_from_trait ( ) {
906
- if node_item. item . ty . is_some ( ) {
907
- // The impl inherited a `type Foo =
908
- // Bar` given in the trait, which is
909
- // implicitly default. No candidate.
910
- None
911
- } else {
912
- // The impl did not specify `type` and neither
913
- // did the trait:
914
- //
915
- // ```rust
916
- // trait Foo { type T; }
917
- // impl Foo for Bar { }
918
- // ```
919
- //
920
- // This is an error, but it will be
921
- // reported in `check_impl_items_against_trait`.
922
- // We accept it here but will flag it as
923
- // an error when we confirm the candidate
924
- // (which will ultimately lead to `normalize_to_error`
925
- // being invoked).
905
+ let is_default = if node_item. node . is_from_trait ( ) {
906
+ // If true, the impl inherited a `type Foo = Bar`
907
+ // given in the trait, which is implicitly default.
908
+ // Otherwise, the impl did not specify `type` and
909
+ // neither did the trait:
910
+ //
911
+ // ```rust
912
+ // trait Foo { type T; }
913
+ // impl Foo for Bar { }
914
+ // ```
915
+ //
916
+ // This is an error, but it will be
917
+ // reported in `check_impl_items_against_trait`.
918
+ // We accept it here but will flag it as
919
+ // an error when we confirm the candidate
920
+ // (which will ultimately lead to `normalize_to_error`
921
+ // being invoked).
922
+ node_item. item . ty . is_some ( )
923
+ } else {
924
+ node_item. item . defaultness . is_default ( )
925
+ } ;
926
+
927
+ // Only reveal a specializable default if we're past type-checking
928
+ // and the obligations is monomorphic, otherwise passes such as
929
+ // transmute checking and polymorphic MIR optimizations could
930
+ // get a result which isn't correct for all monomorphizations.
931
+ if !is_default {
932
+ Some ( ProjectionTyCandidate :: Select )
933
+ } else if selcx. projection_mode ( ) == Reveal :: All {
934
+ assert ! ( !poly_trait_ref. needs_infer( ) ) ;
935
+ if !poly_trait_ref. needs_subst ( ) {
926
936
Some ( ProjectionTyCandidate :: Select )
937
+ } else {
938
+ None
927
939
}
928
- } else if node_item. item . defaultness . is_default ( ) {
929
- // The impl specified `default type Foo =
930
- // Bar`. No candidate.
931
- None
932
940
} else {
933
- // The impl specified `type Foo = Bar`
934
- // with no default. Add a candidate.
935
- Some ( ProjectionTyCandidate :: Select )
941
+ None
936
942
}
937
943
} else {
938
944
// This is saying that neither the trait nor
@@ -982,11 +988,6 @@ fn assemble_candidates_from_impls<'cx, 'gcx, 'tcx>(
982
988
} ;
983
989
candidate_set. vec . extend ( new_candidate) ;
984
990
}
985
- super :: VtableImpl ( _) => {
986
- // In trans mode, we can just project out of impls, no prob.
987
- assert ! ( selcx. projection_mode( ) == Reveal :: All ) ;
988
- candidate_set. vec . push ( ProjectionTyCandidate :: Select ) ;
989
- }
990
991
super :: VtableParam ( ..) => {
991
992
// This case tell us nothing about the value of an
992
993
// associated type. Consider:
0 commit comments