WebKit Bugzilla
Attachment 339080 Details for
Bug 185115
: Math.round() produces wrong result for value prior to 0.5
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
Remember
[x]
|
Forgot Password
Login:
[x]
[patch]
Patch
bug-185115-20180428163317.patch (text/plain), 3.91 KB, created by
corydoras
on 2018-04-28 16:33:18 PDT
(
hide
)
Description:
Patch
Filename:
MIME Type:
Creator:
corydoras
Created:
2018-04-28 16:33:18 PDT
Size:
3.91 KB
patch
obsolete
>Subversion Revision: 231131 >diff --git a/Source/JavaScriptCore/ChangeLog b/Source/JavaScriptCore/ChangeLog >index b3474d05e20bd694553fe621a56875a0a578b3f4..52b1e5b91733e2d7768c9c3793f7bd7ca5f6de2e 100644 >--- a/Source/JavaScriptCore/ChangeLog >+++ b/Source/JavaScriptCore/ChangeLog >@@ -1,3 +1,30 @@ >+2018-04-28 Peter Ammon <corydoras@ridiculousfish.com> >+ >+ [JSC] Correct Math.round for largest value below 0.5 >+ https://bugs.webkit.org/show_bug.cgi?id=185115 >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ Prior to this fix, Math.round would ceil() the input, compute the delta, >+ and then correct it if the delta exceeded 0.5. However if the input is the >+ largest representable value below 0.5, the delta suffers precision loss and >+ is gets rounded down to 0.5 instead of being slightly larger. Therefore >+ Math.round() of this input would be 1.0 instead of the correct 0.0. >+ >+ Switch to an implementation (suggested by Stephen Canon) of using floor() >+ and incrementing if the delta is *at least* 0.5. This corrects the handling >+ of the before-0.5 input, because the delta becomes equal to the input and >+ so there is no precision loss. >+ >+ For the negated input (i.e. nextafter(-0.5, +inf)) we still suffer precision >+ loss and compute a delta of 0.5, but the >= test means we will still increment >+ in this case, rounding to 0. >+ >+ Unfortunately we must do a sign fixup afterwards, because incrementing -1 >+ produces +0. >+ >+ * runtime/MathCommon.cpp: >+ > 2018-04-27 Caio Lima <ticaiolima@gmail.com> > > [ESNext][BigInt] Implement support for "*" operation >diff --git a/Source/JavaScriptCore/runtime/MathCommon.cpp b/Source/JavaScriptCore/runtime/MathCommon.cpp >index bdf1487ec1ee79dab553f353ba515f623c5a959d..c0d7bcc9f293047ae0f90284e44870c383b6fcd4 100644 >--- a/Source/JavaScriptCore/runtime/MathCommon.cpp >+++ b/Source/JavaScriptCore/runtime/MathCommon.cpp >@@ -490,8 +490,8 @@ static inline bool isStrictInt32(double value) > extern "C" { > double jsRound(double value) > { >- double integer = ceil(value); >- return integer - (integer - value > 0.5); >+ double integer = floor(value); >+ return copysign(integer + (value - integer >= 0.5), value); > } > > #if CALLING_CONVENTION_IS_STDCALL || CPU(ARM_THUMB2) >diff --git a/JSTests/ChangeLog b/JSTests/ChangeLog >index 1bdb91c71ce44cf7de60a8f7960ae5392fcc3a33..262954c909ad8df05400dbf88b762a767cf8564d 100644 >--- a/JSTests/ChangeLog >+++ b/JSTests/ChangeLog >@@ -1,3 +1,14 @@ >+2018-04-28 Peter Ammon <corydoras@ridiculousfish.com> >+ >+ [JSC] Correct Math.round for largest value below 0.5 >+ https://bugs.webkit.org/show_bug.cgi?id=185115 >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ Math.round() tests for value preceding 0.5 >+ >+ * stress/math-round-basics.js: >+ > 2018-04-27 Caio Lima <ticaiolima@gmail.com> > > [ESNext][BigInt] Implement support for "*" operation >diff --git a/JSTests/stress/math-round-basics.js b/JSTests/stress/math-round-basics.js >index f61a6d4f4769585fe5b9f56ff0eabc402302413c..f301eae96946c2e0b856c5d4d4e49b86df430a72 100644 >--- a/JSTests/stress/math-round-basics.js >+++ b/JSTests/stress/math-round-basics.js >@@ -69,6 +69,14 @@ for (var i = 0; i < 1e4; ++i) { > if (!(roundedValue === 0 && (1/roundedValue) === -Infinity)) > throw "mathRoundOnDoubles(-0) = " + roundedValue; > >+ var roundedValue = mathRoundOnDoubles(0.499999999999999944); >+ if (!(roundedValue === 0 && (1/roundedValue) === Infinity)) >+ throw "mathRoundOnDoubles(0.499999999999999944) = " + roundedValue; >+ >+ var roundedValue = mathRoundOnDoubles(-0.499999999999999944); >+ if (!(roundedValue === 0 && (1/roundedValue) === -Infinity)) >+ throw "mathRoundOnDoubles(-0.499999999999999944) = " + roundedValue; >+ > var roundedValue = mathRoundOnDoubles(NaN); > if (roundedValue === roundedValue) > throw "mathRoundOnDoubles(NaN) = " + roundedValue;
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Formatted Diff
|
Diff
Attachments on
bug 185115
:
339079
|
339080
|
378145
|
378241