@@ -105,7 +105,6 @@ enum CastError {
105105 NeedViaPtr ,
106106 NeedViaThinPtr ,
107107 NeedViaInt ,
108- NeedViaUsize ,
109108 NonScalar ,
110109}
111110
@@ -139,26 +138,39 @@ impl<'a, 'gcx, 'tcx> CastCheck<'tcx> {
139138
140139 fn report_cast_error ( & self , fcx : & FnCtxt < ' a , ' gcx , ' tcx > , e : CastError ) {
141140 match e {
142- CastError :: NeedViaPtr |
143141 CastError :: NeedViaThinPtr |
144- CastError :: NeedViaInt |
145- CastError :: NeedViaUsize => {
142+ CastError :: NeedViaPtr => {
143+ let mut err = fcx. type_error_struct ( self . span ,
144+ |actual| {
145+ format ! ( "casting `{}` as `{}` is invalid" ,
146+ actual,
147+ fcx. ty_to_string( self . cast_ty) )
148+ } ,
149+ self . expr_ty ) ;
150+ if self . cast_ty . is_uint ( ) {
151+ err. help ( & format ! ( "cast through {} first" ,
152+ match e {
153+ CastError :: NeedViaPtr => "a raw pointer" ,
154+ CastError :: NeedViaThinPtr => "a thin pointer" ,
155+ _ => bug!( ) ,
156+ } ) ) ;
157+ }
158+ err. emit ( ) ;
159+ }
160+ CastError :: NeedViaInt => {
146161 fcx. type_error_struct ( self . span ,
147- |actual| {
148- format ! ( "casting `{}` as `{}` is invalid" ,
149- actual,
150- fcx. ty_to_string( self . cast_ty) )
151- } ,
152- self . expr_ty )
153- . help ( & format ! ( "cast through {} first" ,
154- match e {
155- CastError :: NeedViaPtr => "a raw pointer" ,
156- CastError :: NeedViaThinPtr => "a thin pointer" ,
157- CastError :: NeedViaInt => "an integer" ,
158- CastError :: NeedViaUsize => "a usize" ,
159- _ => bug!( ) ,
160- } ) )
161- . emit ( ) ;
162+ |actual| {
163+ format ! ( "casting `{}` as `{}` is invalid" ,
164+ actual,
165+ fcx. ty_to_string( self . cast_ty) )
166+ } ,
167+ self . expr_ty )
168+ . help ( & format ! ( "cast through {} first" ,
169+ match e {
170+ CastError :: NeedViaInt => "an integer" ,
171+ _ => bug!( ) ,
172+ } ) )
173+ . emit ( ) ;
162174 }
163175 CastError :: CastToBool => {
164176 struct_span_err ! ( fcx. tcx. sess, self . span, E0054 , "cannot cast as `bool`" )
@@ -366,21 +378,23 @@ impl<'a, 'gcx, 'tcx> CastCheck<'tcx> {
366378 ( Int ( Bool ) , Float ) |
367379 ( Int ( CEnum ) , Float ) |
368380 ( Int ( Char ) , Float ) => Err ( CastError :: NeedViaInt ) ,
381+
369382 ( Int ( Bool ) , Ptr ( _) ) |
370383 ( Int ( CEnum ) , Ptr ( _) ) |
371- ( Int ( Char ) , Ptr ( _) ) => Err ( CastError :: NeedViaUsize ) ,
384+ ( Int ( Char ) , Ptr ( _) ) |
385+ ( Ptr ( _) , Float ) |
386+ ( FnPtr , Float ) |
387+ ( Float , Ptr ( _) ) => Err ( CastError :: IllegalCast ) ,
372388
373389 // ptr -> *
374390 ( Ptr ( m_e) , Ptr ( m_c) ) => self . check_ptr_ptr_cast ( fcx, m_e, m_c) , // ptr-ptr-cast
375391 ( Ptr ( m_expr) , Int ( _) ) => self . check_ptr_addr_cast ( fcx, m_expr) , // ptr-addr-cast
376- ( Ptr ( _) , Float ) | ( FnPtr , Float ) => Err ( CastError :: NeedViaUsize ) ,
377392 ( FnPtr , Int ( _) ) => Ok ( CastKind :: FnPtrAddrCast ) ,
378393 ( RPtr ( _) , Int ( _) ) |
379394 ( RPtr ( _) , Float ) => Err ( CastError :: NeedViaPtr ) ,
380395 // * -> ptr
381396 ( Int ( _) , Ptr ( mt) ) => self . check_addr_ptr_cast ( fcx, mt) , // addr-ptr-cast
382397 ( FnPtr , Ptr ( mt) ) => self . check_fptr_ptr_cast ( fcx, mt) ,
383- ( Float , Ptr ( _) ) => Err ( CastError :: NeedViaUsize ) ,
384398 ( RPtr ( rmt) , Ptr ( mt) ) => self . check_ref_cast ( fcx, rmt, mt) , // array-ptr-cast
385399
386400 // prim -> prim
@@ -391,7 +405,6 @@ impl<'a, 'gcx, 'tcx> CastCheck<'tcx> {
391405 ( Int ( _) , Int ( _) ) | ( Int ( _) , Float ) | ( Float , Int ( _) ) | ( Float , Float ) => {
392406 Ok ( CastKind :: NumericCast )
393407 }
394-
395408 }
396409 }
397410
0 commit comments