diff options
Diffstat (limited to 'mcs/class/System.Numerics')
3 files changed, 28 insertions, 4 deletions
diff --git a/mcs/class/System.Numerics/System.Numerics/BigInteger.cs b/mcs/class/System.Numerics/System.Numerics/BigInteger.cs index 816ca2ffce..a05d403988 100644 --- a/mcs/class/System.Numerics/System.Numerics/BigInteger.cs +++ b/mcs/class/System.Numerics/System.Numerics/BigInteger.cs @@ -473,10 +473,20 @@ namespace System.Numerics { return (((long)high) << 32) | low; } - if (high > 0x80000000u) + /* + We cannot represent negative numbers smaller than long.MinValue. + Those values are encoded into what look negative numbers, so negating + them produces a positive value, that's why it's safe to check for that + condition. + + long.MinValue works fine since it's bigint encoding looks like a negative + number, but since long.MinValue == -long.MinValue, we're good. + */ + + long result = - ((((long)high) << 32) | (long)low); + if (result > 0) throw new OverflowException (); - - return - ((((long)high) << 32) | (long)low); + return result; } [CLSCompliantAttribute (false)] diff --git a/mcs/class/System.Numerics/System.Numerics/Complex.cs b/mcs/class/System.Numerics/System.Numerics/Complex.cs index 6c172751b3..89b6bd463a 100644 --- a/mcs/class/System.Numerics/System.Numerics/Complex.cs +++ b/mcs/class/System.Numerics/System.Numerics/Complex.cs @@ -231,7 +231,7 @@ namespace System.Numerics { public static Complex Cosh (Complex value) { return new Complex (Math.Cosh (value.real) * Math.Cos (value.imaginary), - -Math.Sinh (value.real) * Math.Sin (value.imaginary)); + Math.Sinh (value.real) * Math.Sin (value.imaginary)); } public static Complex Negate (Complex value) diff --git a/mcs/class/System.Numerics/Test/System.Numerics/BigIntegerTest.cs b/mcs/class/System.Numerics/Test/System.Numerics/BigIntegerTest.cs index 098c50854b..a5ec016bb3 100644 --- a/mcs/class/System.Numerics/Test/System.Numerics/BigIntegerTest.cs +++ b/mcs/class/System.Numerics/Test/System.Numerics/BigIntegerTest.cs @@ -1145,5 +1145,19 @@ namespace MonoTests.System.Numerics a = new BigInteger (); Assert.AreEqual (BigInteger.Zero.GetHashCode (), a.GetHashCode (), "#15"); } + + [Test] + public void Bug16526 () + { + var x = BigInteger.Pow(2, 63); + x *= -1; + x -= 1; + Assert.AreEqual ("-9223372036854775809", x.ToString (), "#1"); + try { + x = (long)x; + Assert.Fail ("#2 Must OVF"); + } catch (OverflowException) { + } + } } } |