@@ -80,8 +80,9 @@ use hir::print as pprust;
8080use lint;
8181use hir:: def:: Def ;
8282use hir:: def_id:: DefId ;
83- use infer:: { self , TypeOrigin } ;
83+ use infer;
8484use middle:: region;
85+ use traits:: { ObligationCause , ObligationCauseCode } ;
8586use ty:: { self , TyCtxt , TypeFoldable } ;
8687use ty:: { Region , ReFree } ;
8788use ty:: error:: TypeError ;
@@ -524,10 +525,10 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> {
524525
525526 fn note_error_origin ( & self ,
526527 err : & mut DiagnosticBuilder < ' tcx > ,
527- origin : & TypeOrigin )
528+ cause : & ObligationCause < ' tcx > )
528529 {
529- match origin {
530- & TypeOrigin :: MatchExpressionArm ( _ , arm_span, source) => match source {
530+ match cause . code {
531+ ObligationCauseCode :: MatchExpressionArm { arm_span, source } => match source {
531532 hir:: MatchSource :: IfLetDesugar { ..} => {
532533 err. span_note ( arm_span, "`if let` arm with an incompatible type" ) ;
533534 }
@@ -541,7 +542,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> {
541542
542543 pub fn note_type_err ( & self ,
543544 diag : & mut DiagnosticBuilder < ' tcx > ,
544- origin : TypeOrigin ,
545+ cause : & ObligationCause < ' tcx > ,
545546 secondary_span : Option < ( Span , String ) > ,
546547 values : Option < ValuePairs < ' tcx > > ,
547548 terr : & TypeError < ' tcx > )
@@ -558,7 +559,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> {
558559 }
559560 } ;
560561
561- let span = origin . span ( ) ;
562+ let span = cause . span ;
562563
563564 if let Some ( ( expected, found) ) = expected_found {
564565 let is_simple_error = if let & TypeError :: Sorts ( ref values) = terr {
@@ -588,7 +589,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> {
588589 diag. span_label ( sp, & msg) ;
589590 }
590591
591- self . note_error_origin ( diag, & origin ) ;
592+ self . note_error_origin ( diag, & cause ) ;
592593 self . check_and_note_conflicting_crates ( diag, terr, span) ;
593594 self . tcx . note_and_explain_type_err ( diag, terr, span) ;
594595 }
@@ -598,17 +599,17 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> {
598599 terr : & TypeError < ' tcx > )
599600 -> DiagnosticBuilder < ' tcx >
600601 {
601- let span = trace. origin . span ( ) ;
602- let failure_str = trace. origin . as_failure_str ( ) ;
603- let mut diag = match trace. origin {
604- TypeOrigin :: IfExpressionWithNoElse ( _ ) => {
602+ let span = trace. cause . span ;
603+ let failure_str = trace. cause . as_failure_str ( ) ;
604+ let mut diag = match trace. cause . code {
605+ ObligationCauseCode :: IfExpressionWithNoElse => {
605606 struct_span_err ! ( self . tcx. sess, span, E0317 , "{}" , failure_str)
606607 } ,
607608 _ => {
608609 struct_span_err ! ( self . tcx. sess, span, E0308 , "{}" , failure_str)
609610 } ,
610611 } ;
611- self . note_type_err ( & mut diag, trace. origin , None , Some ( trace. values ) , terr) ;
612+ self . note_type_err ( & mut diag, & trace. cause , None , Some ( trace. values ) , terr) ;
612613 diag
613614 }
614615
@@ -1695,18 +1696,18 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> {
16951696 if let Some ( ( expected, found) ) = self . values_str ( & trace. values ) {
16961697 // FIXME: do we want a "the" here?
16971698 err. span_note (
1698- trace. origin . span ( ) ,
1699+ trace. cause . span ,
16991700 & format ! ( "...so that {} (expected {}, found {})" ,
1700- trace. origin . as_requirement_str( ) , expected, found) ) ;
1701+ trace. cause . as_requirement_str( ) , expected, found) ) ;
17011702 } else {
17021703 // FIXME: this really should be handled at some earlier stage. Our
17031704 // handling of region checking when type errors are present is
17041705 // *terrible*.
17051706
17061707 err. span_note (
1707- trace. origin . span ( ) ,
1708+ trace. cause . span ,
17081709 & format ! ( "...so that {}" ,
1709- trace. origin . as_requirement_str( ) ) ) ;
1710+ trace. cause . as_requirement_str( ) ) ) ;
17101711 }
17111712 }
17121713 infer:: Reborrow ( span) => {
@@ -1961,3 +1962,45 @@ fn name_to_dummy_lifetime(name: ast::Name) -> hir::Lifetime {
19611962 span : syntax_pos:: DUMMY_SP ,
19621963 name : name }
19631964}
1965+
1966+ impl < ' tcx > ObligationCause < ' tcx > {
1967+ fn as_failure_str ( & self ) -> & ' static str {
1968+ use traits:: ObligationCauseCode :: * ;
1969+ match self . code {
1970+ CompareImplMethodObligation { .. } => "method not compatible with trait" ,
1971+ MatchExpressionArm { source, .. } => match source {
1972+ hir:: MatchSource :: IfLetDesugar { ..} => "`if let` arms have incompatible types" ,
1973+ _ => "match arms have incompatible types" ,
1974+ } ,
1975+ IfExpression => "if and else have incompatible types" ,
1976+ IfExpressionWithNoElse => "if may be missing an else clause" ,
1977+ EquatePredicate => "equality predicate not satisfied" ,
1978+ MainFunctionType => "main function has wrong type" ,
1979+ StartFunctionType => "start function has wrong type" ,
1980+ IntrinsicType => "intrinsic has wrong type" ,
1981+ MethodReceiver => "mismatched method receiver" ,
1982+ _ => "mismatched types" ,
1983+ }
1984+ }
1985+
1986+ fn as_requirement_str ( & self ) -> & ' static str {
1987+ use traits:: ObligationCauseCode :: * ;
1988+ match self . code {
1989+ CompareImplMethodObligation { .. } => "method type is compatible with trait" ,
1990+ ExprAssignable => "expression is assignable" ,
1991+ MatchExpressionArm { source, .. } => match source {
1992+ hir:: MatchSource :: IfLetDesugar { ..} => "`if let` arms have compatible types" ,
1993+ _ => "match arms have compatible types" ,
1994+ } ,
1995+ IfExpression => "if and else have compatible types" ,
1996+ IfExpressionWithNoElse => "if missing an else returns ()" ,
1997+ EquatePredicate => "equality where clause is satisfied" ,
1998+ MainFunctionType => "`main` function has the correct type" ,
1999+ StartFunctionType => "`start` function has the correct type" ,
2000+ IntrinsicType => "intrinsic has the correct type" ,
2001+ MethodReceiver => "method receiver has the correct type" ,
2002+ _ => "types are compatible" ,
2003+ }
2004+ }
2005+ }
2006+
0 commit comments