@@ -511,7 +511,7 @@ impl f64 {
511
511
#[ stable( feature = "rust1" , since = "1.0.0" ) ]
512
512
#[ inline]
513
513
pub fn ln ( self ) -> f64 {
514
- unsafe { intrinsics:: logf64 ( self ) }
514
+ self . log_wrapper ( |n| { unsafe { intrinsics:: logf64 ( n ) } } )
515
515
}
516
516
517
517
/// Returns the logarithm of the number with respect to an arbitrary base.
@@ -546,7 +546,7 @@ impl f64 {
546
546
#[ stable( feature = "rust1" , since = "1.0.0" ) ]
547
547
#[ inline]
548
548
pub fn log2 ( self ) -> f64 {
549
- unsafe { intrinsics:: log2f64 ( self ) }
549
+ self . log_wrapper ( |n| { unsafe { intrinsics:: log2f64 ( n ) } } )
550
550
}
551
551
552
552
/// Returns the base 10 logarithm of the number.
@@ -562,7 +562,7 @@ impl f64 {
562
562
#[ stable( feature = "rust1" , since = "1.0.0" ) ]
563
563
#[ inline]
564
564
pub fn log10 ( self ) -> f64 {
565
- unsafe { intrinsics:: log10f64 ( self ) }
565
+ self . log_wrapper ( |n| { unsafe { intrinsics:: log10f64 ( n ) } } )
566
566
}
567
567
568
568
/// Converts radians to degrees.
@@ -1065,6 +1065,31 @@ impl f64 {
1065
1065
pub fn atanh ( self ) -> f64 {
1066
1066
0.5 * ( ( 2.0 * self ) / ( 1.0 - self ) ) . ln_1p ( )
1067
1067
}
1068
+
1069
+ // Solaris/Illumos requires a wrapper around log, log2, and log10 functions
1070
+ // because of their non-standard behavior (e.g. log(-n) returns -Inf instead
1071
+ // of expected NaN).
1072
+ fn log_wrapper < F : Fn ( f64 ) -> f64 > ( self , log_fn : F ) -> f64 {
1073
+ if !cfg ! ( target_os = "solaris" ) {
1074
+ log_fn ( self )
1075
+ } else {
1076
+ if self . is_finite ( ) {
1077
+ if self > 0.0 {
1078
+ log_fn ( self )
1079
+ } else if self == 0.0 {
1080
+ NEG_INFINITY // log(0) = -Inf
1081
+ } else {
1082
+ NAN // log(-n) = NaN
1083
+ }
1084
+ } else if self . is_nan ( ) {
1085
+ self // log(NaN) = NaN
1086
+ } else if self > 0.0 {
1087
+ self // log(Inf) = Inf
1088
+ } else {
1089
+ NAN // log(-Inf) = NaN
1090
+ }
1091
+ }
1092
+ }
1068
1093
}
1069
1094
1070
1095
#[ cfg( test) ]
0 commit comments