@@ -7,7 +7,6 @@ use rustc_data_structures::sync::Lrc;
7
7
use rustc_hir:: def:: { DefKind , Res } ;
8
8
use rustc_hir:: { BinOp , BinOpKind , Block , Expr , ExprKind , HirId , Item , ItemKind , Node , QPath , UnOp } ;
9
9
use rustc_lint:: LateContext ;
10
- use rustc_middle:: mir:: interpret:: Scalar ;
11
10
use rustc_middle:: ty:: subst:: { Subst , SubstsRef } ;
12
11
use rustc_middle:: ty:: { self , EarlyBinder , FloatTy , ScalarInt , Ty , TyCtxt } ;
13
12
use rustc_middle:: { bug, span_bug} ;
@@ -423,14 +422,14 @@ impl<'a, 'tcx> ConstEvalLateContext<'a, 'tcx> {
423
422
let result = self
424
423
. lcx
425
424
. tcx
426
- . const_eval_resolve (
425
+ . const_eval_resolve_for_typeck (
427
426
self . param_env ,
428
427
ty:: Unevaluated :: new ( ty:: WithOptConstParam :: unknown ( def_id) , substs) ,
429
428
None ,
430
429
)
431
430
. ok ( )
432
- . map ( |val| rustc_middle:: ty:: Const :: from_value ( self . lcx . tcx , val, ty) ) ?;
433
- let result = miri_to_const ( result) ;
431
+ . and_then ( |val| val . map ( |val| rustc_middle:: ty:: Const :: from_value ( self . lcx . tcx , val, ty) ) ) ?;
432
+ let result = miri_to_const ( self . lcx . tcx , result) ;
434
433
if result. is_some ( ) {
435
434
self . needed_resolution = true ;
436
435
}
@@ -580,80 +579,69 @@ impl<'a, 'tcx> ConstEvalLateContext<'a, 'tcx> {
580
579
}
581
580
}
582
581
583
- pub fn miri_to_const ( result : ty:: Const < ' _ > ) -> Option < Constant > {
584
- use rustc_middle:: mir:: interpret:: ConstValue ;
582
+ pub fn miri_to_const < ' tcx > ( tcx : TyCtxt < ' tcx > , result : ty:: Const < ' tcx > ) -> Option < Constant > {
585
583
match result. kind ( ) {
586
- ty:: ConstKind :: Value ( ConstValue :: Scalar ( Scalar :: Int ( int ) ) ) => {
587
- match result. ty ( ) . kind ( ) {
588
- ty:: Bool => Some ( Constant :: Bool ( int == ScalarInt :: TRUE ) ) ,
589
- ty:: Uint ( _) | ty:: Int ( _) => Some ( Constant :: Int ( int. assert_bits ( int. size ( ) ) ) ) ,
590
- ty:: Float ( FloatTy :: F32 ) => Some ( Constant :: F32 ( f32:: from_bits (
584
+ ty:: ConstKind :: Value ( valtree ) => {
585
+ match ( valtree , result. ty ( ) . kind ( ) ) {
586
+ ( ty:: ValTree :: Leaf ( int ) , ty :: Bool ) => Some ( Constant :: Bool ( int == ScalarInt :: TRUE ) ) ,
587
+ ( ty:: ValTree :: Leaf ( int ) , ty :: Uint ( _) | ty:: Int ( _) ) => Some ( Constant :: Int ( int. assert_bits ( int. size ( ) ) ) ) ,
588
+ ( ty:: ValTree :: Leaf ( int ) , ty :: Float ( FloatTy :: F32 ) ) => Some ( Constant :: F32 ( f32:: from_bits (
591
589
int. try_into ( ) . expect ( "invalid f32 bit representation" ) ,
592
590
) ) ) ,
593
- ty:: Float ( FloatTy :: F64 ) => Some ( Constant :: F64 ( f64:: from_bits (
591
+ ( ty:: ValTree :: Leaf ( int ) , ty :: Float ( FloatTy :: F64 ) ) => Some ( Constant :: F64 ( f64:: from_bits (
594
592
int. try_into ( ) . expect ( "invalid f64 bit representation" ) ,
595
593
) ) ) ,
596
- ty:: RawPtr ( type_and_mut) => {
594
+ ( ty:: ValTree :: Leaf ( int ) , ty :: RawPtr ( type_and_mut) ) => {
597
595
if let ty:: Uint ( _) = type_and_mut. ty . kind ( ) {
598
596
return Some ( Constant :: RawPtr ( int. assert_bits ( int. size ( ) ) ) ) ;
599
597
}
600
598
None
601
599
} ,
602
- // FIXME: implement other conversions.
603
- _ => None ,
604
- }
605
- } ,
606
- ty:: ConstKind :: Value ( ConstValue :: Slice { data, start, end } ) => match result. ty ( ) . kind ( ) {
607
- ty:: Ref ( _, tam, _) => match tam. kind ( ) {
608
- ty:: Str => String :: from_utf8 (
609
- data. inner ( )
610
- . inspect_with_uninit_and_ptr_outside_interpreter ( start..end)
611
- . to_owned ( ) ,
612
- )
613
- . ok ( )
614
- . map ( Constant :: Str ) ,
615
- _ => None ,
616
- } ,
617
- _ => None ,
618
- } ,
619
- ty:: ConstKind :: Value ( ConstValue :: ByRef { alloc, offset : _ } ) => match result. ty ( ) . kind ( ) {
620
- ty:: Array ( sub_type, len) => match sub_type. kind ( ) {
621
- ty:: Float ( FloatTy :: F32 ) => match miri_to_const ( * len) {
622
- Some ( Constant :: Int ( len) ) => alloc
623
- . inner ( )
624
- . inspect_with_uninit_and_ptr_outside_interpreter ( 0 ..( 4 * len as usize ) )
625
- . to_owned ( )
626
- . chunks ( 4 )
627
- . map ( |chunk| {
628
- Some ( Constant :: F32 ( f32:: from_le_bytes (
629
- chunk. try_into ( ) . expect ( "this shouldn't happen" ) ,
630
- ) ) )
631
- } )
632
- . collect :: < Option < Vec < Constant > > > ( )
633
- . map ( Constant :: Vec ) ,
634
- _ => None ,
635
- } ,
636
- ty:: Float ( FloatTy :: F64 ) => match miri_to_const ( * len) {
637
- Some ( Constant :: Int ( len) ) => alloc
638
- . inner ( )
639
- . inspect_with_uninit_and_ptr_outside_interpreter ( 0 ..( 8 * len as usize ) )
640
- . to_owned ( )
641
- . chunks ( 8 )
642
- . map ( |chunk| {
643
- Some ( Constant :: F64 ( f64:: from_le_bytes (
644
- chunk. try_into ( ) . expect ( "this shouldn't happen" ) ,
645
- ) ) )
646
- } )
647
- . collect :: < Option < Vec < Constant > > > ( )
648
- . map ( Constant :: Vec ) ,
600
+ ( ty:: ValTree :: Branch ( _) , ty:: Ref ( _, inner_ty, _) ) if * inner_ty == tcx. types . str_ => valtree
601
+ . try_to_raw_bytes ( tcx, result. ty ( ) )
602
+ . and_then ( |bytes| String :: from_utf8 ( bytes. to_owned ( ) ) . ok ( ) . map ( Constant :: Str ) ) ,
603
+ ( ty:: ValTree :: Branch ( _) , ty:: Array ( arr_ty, len) ) => match arr_ty. kind ( ) {
604
+ ty:: Float ( float_ty) => {
605
+ let chunk_size = match float_ty {
606
+ FloatTy :: F32 => 4 ,
607
+ FloatTy :: F64 => 8 ,
608
+ } ;
609
+
610
+ match miri_to_const ( tcx, * len) {
611
+ Some ( Constant :: Int ( _) ) => valtree. try_to_raw_bytes ( tcx, result. ty ( ) ) . and_then ( |bytes| {
612
+ bytes
613
+ . to_owned ( )
614
+ . chunks ( chunk_size)
615
+ . map ( |chunk| match float_ty {
616
+ FloatTy :: F32 => {
617
+ let float = f32:: from_le_bytes (
618
+ chunk
619
+ . try_into ( )
620
+ . expect ( & format ! ( "expected to construct f32 from {:?}" , chunk) ) ,
621
+ ) ;
622
+ Some ( Constant :: F32 ( float) )
623
+ } ,
624
+ FloatTy :: F64 => {
625
+ let float = f64:: from_le_bytes (
626
+ chunk
627
+ . try_into ( )
628
+ . expect ( & format ! ( "expected to construct f64 from {:?}" , chunk) ) ,
629
+ ) ;
630
+ Some ( Constant :: F64 ( float) )
631
+ } ,
632
+ } )
633
+ . collect :: < Option < Vec < Constant > > > ( )
634
+ . map ( Constant :: Vec )
635
+ } ) ,
636
+ _ => None ,
637
+ }
638
+ } ,
649
639
_ => None ,
650
640
} ,
651
- // FIXME: implement other array type conversions.
641
+ // FIXME: implement other conversions.
652
642
_ => None ,
653
- } ,
654
- _ => None ,
643
+ }
655
644
} ,
656
- // FIXME: implement other conversions.
657
645
_ => None ,
658
646
}
659
647
}
0 commit comments