@@ -518,18 +518,19 @@ impl<'mir, 'tcx> ConstPropagator<'mir, 'tcx> {
518
518
}
519
519
}
520
520
521
- fn check_unary_op ( & mut self , arg : & Operand < ' tcx > , source_info : SourceInfo ) -> Option < ( ) > {
521
+ fn check_unary_op (
522
+ & mut self ,
523
+ op : UnOp ,
524
+ arg : & Operand < ' tcx > ,
525
+ source_info : SourceInfo ,
526
+ ) -> Option < ( ) > {
522
527
self . use_ecx ( source_info, |this| {
523
- let ty = arg. ty ( & this. local_decls , this. tcx ) ;
524
-
525
- if ty. is_integral ( ) {
526
- let arg = this. ecx . eval_operand ( arg, None ) ?;
527
- let prim = this. ecx . read_immediate ( arg) ?;
528
- // Need to do overflow check here: For actual CTFE, MIR
529
- // generation emits code that does this before calling the op.
530
- if prim. to_bits ( ) ? == ( 1 << ( prim. layout . size . bits ( ) - 1 ) ) {
531
- throw_panic ! ( OverflowNeg )
532
- }
528
+ let val = this. ecx . read_immediate ( this. ecx . eval_operand ( arg, None ) ?) ?;
529
+ let ( _res, overflow, _ty) = this. ecx . overflowing_unary_op ( op, val) ?;
530
+
531
+ if overflow {
532
+ assert_eq ! ( op, UnOp :: Neg , "Neg is the only UnOp that can overflow" ) ;
533
+ throw_panic ! ( OverflowNeg ) ;
533
534
}
534
535
535
536
Ok ( ( ) )
@@ -574,11 +575,10 @@ impl<'mir, 'tcx> ConstPropagator<'mir, 'tcx> {
574
575
if !overflow_check {
575
576
self . use_ecx ( source_info, |this| {
576
577
let l = this. ecx . read_immediate ( this. ecx . eval_operand ( left, None ) ?) ?;
577
- let ( _ , overflow, _ty) = this. ecx . overflowing_binary_op ( op, l, r) ?;
578
+ let ( _res , overflow, _ty) = this. ecx . overflowing_binary_op ( op, l, r) ?;
578
579
579
580
if overflow {
580
- let err = err_panic ! ( Overflow ( op) ) . into ( ) ;
581
- return Err ( err) ;
581
+ throw_panic ! ( Overflow ( op) ) ;
582
582
}
583
583
584
584
Ok ( ( ) )
@@ -618,9 +618,9 @@ impl<'mir, 'tcx> ConstPropagator<'mir, 'tcx> {
618
618
// Additional checking: if overflow checks are disabled (which is usually the case in
619
619
// release mode), then we need to do additional checking here to give lints to the user
620
620
// if an overflow would occur.
621
- Rvalue :: UnaryOp ( UnOp :: Neg , arg) if !overflow_check => {
622
- trace ! ( "checking UnaryOp(op = Neg , arg = {:?})" , arg) ;
623
- self . check_unary_op ( arg, source_info) ?;
621
+ Rvalue :: UnaryOp ( op , arg) if !overflow_check => {
622
+ trace ! ( "checking UnaryOp(op = {:?} , arg = {:?})" , op , arg) ;
623
+ self . check_unary_op ( * op , arg, source_info) ?;
624
624
}
625
625
626
626
// Additional checking: check for overflows on integer binary operations and report
0 commit comments