@@ -552,8 +552,18 @@ pub fn from_str_bytes_common<T:NumCast+Zero+One+Eq+Ord+Div<T,T>+
552
552
// Detect overflow by comparing to last value, except
553
553
// if we've not seen any non-zero digits.
554
554
if last_accum != _0 {
555
- if accum_positive && accum <= last_accum { return None ; }
556
- if !accum_positive && accum >= last_accum { return None ; }
555
+ if accum_positive && accum <= last_accum { return NumStrConv :: inf ( ) ; }
556
+ if !accum_positive && accum >= last_accum { return NumStrConv :: neg_inf ( ) ; }
557
+
558
+ // Detect overflow by reversing the shift-and-add proccess
559
+ if accum_positive &&
560
+ ( last_accum != ( ( accum - cast ( digit as int ) ) /radix_gen. clone ( ) ) ) {
561
+ return NumStrConv :: inf ( ) ;
562
+ }
563
+ if !accum_positive &&
564
+ ( last_accum != ( ( accum + cast ( digit as int ) ) /radix_gen. clone ( ) ) ) {
565
+ return NumStrConv :: neg_inf ( ) ;
566
+ }
557
567
}
558
568
last_accum = accum. clone ( ) ;
559
569
}
@@ -597,8 +607,8 @@ pub fn from_str_bytes_common<T:NumCast+Zero+One+Eq+Ord+Div<T,T>+
597
607
}
598
608
599
609
// Detect overflow by comparing to last value
600
- if accum_positive && accum < last_accum { return None ; }
601
- if !accum_positive && accum > last_accum { return None ; }
610
+ if accum_positive && accum < last_accum { return NumStrConv :: inf ( ) ; }
611
+ if !accum_positive && accum > last_accum { return NumStrConv :: neg_inf ( ) ; }
602
612
last_accum = accum. clone ( ) ;
603
613
}
604
614
None => match c {
@@ -702,6 +712,23 @@ mod test {
702
712
ExpNone , false , false ) ;
703
713
assert_eq ! ( n, None ) ;
704
714
}
715
+
716
+ #[ test]
717
+ fn from_str_issue7588 ( ) {
718
+ let u : Option < u8 > = from_str_common ( "1000" , 10 , false , false , false ,
719
+ ExpNone , false , false ) ;
720
+ assert_eq ! ( u, None ) ;
721
+ let s : Option < i16 > = from_str_common ( "80000" , 10 , false , false , false ,
722
+ ExpNone , false , false ) ;
723
+ assert_eq ! ( s, None ) ;
724
+ let f : Option < f32 > = from_str_common (
725
+ "10000000000000000000000000000000000000000" , 10 , false , false , false ,
726
+ ExpNone , false , false ) ;
727
+ assert_eq ! ( f, NumStrConv :: inf( ) )
728
+ let fe : Option < f32 > = from_str_common ( "1e40" , 10 , false , false , false ,
729
+ ExpDec , false , false ) ;
730
+ assert_eq ! ( fe, NumStrConv :: inf( ) )
731
+ }
705
732
}
706
733
707
734
#[ cfg( test) ]
0 commit comments