-
Notifications
You must be signed in to change notification settings - Fork 1.7k
VM number optimizations occasionally give wrong numerical result. #18143
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
The bug isn't new. It seems to have existed at least since v1.0. cc @whesse. |
Srdjan has investigated issues with this test in the past. Set owner to @sgmitrovic. |
Please specify what release you are running. I cannot reproduce failures neither on Mac nor on Linux. Added NeedsInfo label. |
Added CannotReproduce label. |
Added Accepted label. |
Updated status with co19 issue #679: Rectangle equality may not work with double coordinates. Maybe this should be a library bug? expected: <Rectangle (0, 99.99999999999999) 0.9999999999999999 x 4503599627370495.0>, actual: <Rectangle (0, 99.99999999999999) 0.9999999999999999 x 4503599627370496.0> |
Exhaustively search through all possible combinations /* const List<num> values = const [ num randomVal() { var failed = false; verify(i, x, y, z, w) { main() { An interesting fact is the following (and this only happens on Linux): The occasional rounding error is only reported when we go through the initial loop. It is never reported in the exhaustive search. I am starting to wonder whether the rounding mode in C (!) is inconsistent on Linux? |
Running VM on Linux (ReleaseIA32) of tip of bleeding_edge (as of ~20 hours ago). Also tried running it with archived versions of the 1.0, 1.2 and 1.2 releases, and it exhibited the same behavior. When the test fails, it prints the values used for x,y,z,w. Running simple code with just those values again does not fail, so the problem is not in Rectangle. Disabling optimization removes the problem too, so the problem does seem to be in the VM optimization code. It seems all failing cases mismatch on a 4503599627370495.0 / 4503599627370496.0 pair. That is the least significant bit of an integer, but I'm not sure it's rounding. Equality of Rectangle is defined by equality of its left/right/top/bottom edges - the rectangles are geometrically closed, so different edge values means they differ on which points they contain. The boundingBox operation only does +/- (to get the right edge from left edge+width, get width from new left and right edge) and min/max to find the new edges. Those operations should be exactly defined - I see no reason for rounding differently in some cases. Is it hitting x87 FP (80-bit precission) code because it's going to runtime? Or, as you say, not using the same rounding mode all the time? |
Lasse, I have seen other mismatches in my testing. Srdjan, Here is the minimal non-Random code causing this: <SNIP> verify(i, r1, r2, expected) { main() { // Use values that will trigger bad rounding on Linux. Running it with ./out/ReleaseIA32/dart --no-use-osr --optimization-filter=boundingBox --trace-compiler --trace-deoptimization --print-inlining-tree BoundingBox.dart we see the following: On iteration 1248 RectangleBase.boundingBox is optimized a second time. This time we do not deoptimize, but we fail the comparison afterwards. Looking at it in more details with Srdjan we realized that the optimized code calls out to C++ for the first time ever during execution to execute a Double subtraction (all other calls to the double operator - were intrinsified), leading us to strongly suspect that the subtraction from C++ is different ever so slightly. Added Accepted label. |
Thank you Ivan for the test case. While DartVM code uses SSE 64-bit precision operations, the Linux C++ code uses x87 80-bit precision doubles. The discrepancy occurs when we subtract once in 64-bit and once in 80-bit precision. There are no issues on Mac OS X (C++ code uses SSE) and on Linux64 (C++ uses SSE as well). |
The fix is to use -mfpmath=sse in 32-bit mode for Linux. CL pending. |
Fixed in r35001 |
Added Fixed label. |
While running the co19 test for Rectangle.boundingBox, the VM occasionally gives a failure that isn't reproducible when plugging the same values into a separate test. The problem goes away when optimizations are disabled.
Example:
while ( out/ReleaseIA32/dart tests/co19/src/LibTest/math/Rectangle/boundingBox_A01_t01.dart ) ; do echo -n .; done
This usually errs after a few dozen tests run. Changing it to:
while ( out/ReleaseIA32/dart --optimization-filter=xxx tests/co19/src/LibTest/math/Rectangle/boundingBox_A01_t01.dart ) ; do echo -n .; done
makes it not fail (at least for a couple of hundred rounds).
The text was updated successfully, but these errors were encountered: