Title: [240223] trunk
Revision
240223
Author
sbar...@apple.com
Date
2019-01-20 19:54:17 -0800 (Sun, 20 Jan 2019)

Log Message

JSTests:
MovHint must merge NodeBytecodeUsesAsValue for its child
https://bugs.webkit.org/show_bug.cgi?id=186916
<rdar://problem/41396612>

Reviewed by Yusuke Suzuki.

* stress/arith-abs-to-arith-negate-range-optimizaton.js:
* stress/movhint-backwards-propagation-must-merge-use-as-value.js: Added.

Source/_javascript_Core:
MovHint must merge NodeBytecodeUsesAsValue for its child in backwards propagation
https://bugs.webkit.org/show_bug.cgi?id=186916
<rdar://problem/41396612>

Reviewed by Yusuke Suzuki.

Otherwise, we may not think we care about the non-integral part in
a division (or perhaps overflow in an add, etc). Consider a program
like this:

```return a / b```

That gets compiled to:
```
a: ArithDiv // We don't check that the remainder is zero here.
b: MovHint(@a)
c: ForceOSRExit
d: Unreachable
```

If we don't inform @a that we care about its result in full number
accuracy, it will choose to ignore its non-integral remainder. This
makes sense if *everybody* that all uses of the Div only cared about
the integral part. However, OSR exit is not one of those users. OSR
exit cares about the fractional bits in such a Div.

* dfg/DFGBackwardsPropagationPhase.cpp:
(JSC::DFG::BackwardsPropagationPhase::propagate):

Modified Paths

Added Paths

Diff

Modified: trunk/JSTests/ChangeLog (240222 => 240223)


--- trunk/JSTests/ChangeLog	2019-01-21 03:33:24 UTC (rev 240222)
+++ trunk/JSTests/ChangeLog	2019-01-21 03:54:17 UTC (rev 240223)
@@ -1,3 +1,14 @@
+2019-01-20  Saam Barati  <sbar...@apple.com>
+
+        MovHint must merge NodeBytecodeUsesAsValue for its child
+        https://bugs.webkit.org/show_bug.cgi?id=186916
+        <rdar://problem/41396612>
+
+        Reviewed by Yusuke Suzuki.
+
+        * stress/arith-abs-to-arith-negate-range-optimizaton.js:
+        * stress/movhint-backwards-propagation-must-merge-use-as-value.js: Added.
+
 2019-01-20  Yusuke Suzuki  <ysuz...@apple.com>
 
         [JSC] Invalidate old scope operations using global lexical binding epoch

Modified: trunk/JSTests/stress/arith-abs-to-arith-negate-range-optimizaton.js (240222 => 240223)


--- trunk/JSTests/stress/arith-abs-to-arith-negate-range-optimizaton.js	2019-01-21 03:33:24 UTC (rev 240222)
+++ trunk/JSTests/stress/arith-abs-to-arith-negate-range-optimizaton.js	2019-01-21 03:54:17 UTC (rev 240223)
@@ -233,7 +233,7 @@
             throw "Failed testUncheckedBetweenIntMinInclusiveAndZeroExclusive() on -2147483648";
         }
     }
-    if (numberOfDFGCompiles(opaqueUncheckedBetweenIntMinInclusiveAndZeroExclusive) > 1) {
+    if (numberOfDFGCompiles(opaqueUncheckedBetweenIntMinInclusiveAndZeroExclusive) > 2) {
         throw "Failed optimizing testUncheckedBetweenIntMinInclusiveAndZeroExclusive(). None of the tested case need to OSR Exit.";
     }
 }
@@ -376,7 +376,7 @@
             throw "Failed testUncheckedLessThanOrEqualZero() on -2147483648";
         }
     }
-    if (numberOfDFGCompiles(opaqueUncheckedLessThanZero) > 1) {
+    if (numberOfDFGCompiles(opaqueUncheckedLessThanZero) > 2) {
         throw "Failed optimizing testUncheckedLessThanZero(). None of the tested case need to OSR Exit.";
     }
 
@@ -420,7 +420,7 @@
             throw "Failed testUncheckedLessThanOrEqualZero() on -2147483648";
         }
     }
-    if (numberOfDFGCompiles(opaqueUncheckedLessThanOrEqualZero) > 1) {
+    if (numberOfDFGCompiles(opaqueUncheckedLessThanOrEqualZero) > 2) {
         throw "Failed optimizing testUncheckedLessThanOrEqualZero(). None of the tested case need to OSR Exit.";
     }
 }

Added: trunk/JSTests/stress/movhint-backwards-propagation-must-merge-use-as-value-add.js (0 => 240223)


--- trunk/JSTests/stress/movhint-backwards-propagation-must-merge-use-as-value-add.js	                        (rev 0)
+++ trunk/JSTests/stress/movhint-backwards-propagation-must-merge-use-as-value-add.js	2019-01-21 03:54:17 UTC (rev 240223)
@@ -0,0 +1,16 @@
+function foo(v, a, b) {
+    if (v) {
+        let r = a + b;
+        OSRExit();
+        return r;
+    }
+}
+noInline(foo);
+
+for (let i = 0; i < 10000; ++i) {
+    let r = foo(true, 4, 4);
+    if (r !== 8)
+        throw new Error("Bad!");
+}
+if (foo(true, 2**31 - 1, 1) !== 2**31)
+    throw new Error("Bad!");

Added: trunk/JSTests/stress/movhint-backwards-propagation-must-merge-use-as-value.js (0 => 240223)


--- trunk/JSTests/stress/movhint-backwards-propagation-must-merge-use-as-value.js	                        (rev 0)
+++ trunk/JSTests/stress/movhint-backwards-propagation-must-merge-use-as-value.js	2019-01-21 03:54:17 UTC (rev 240223)
@@ -0,0 +1,16 @@
+function foo(v, a, b) {
+    if (v) {
+        let r = a / b;
+        OSRExit();
+        return r;
+    }
+}
+noInline(foo);
+
+for (let i = 0; i < 10000; ++i) {
+    let r = foo(true, 4, 4);
+    if (r !== 1)
+        throw new Error("Bad!");
+}
+if (foo(true, 1, 4) !== 0.25)
+    throw new Error("Bad!");

Modified: trunk/Source/_javascript_Core/ChangeLog (240222 => 240223)


--- trunk/Source/_javascript_Core/ChangeLog	2019-01-21 03:33:24 UTC (rev 240222)
+++ trunk/Source/_javascript_Core/ChangeLog	2019-01-21 03:54:17 UTC (rev 240223)
@@ -1,3 +1,34 @@
+2019-01-20  Saam Barati  <sbar...@apple.com>
+
+        MovHint must merge NodeBytecodeUsesAsValue for its child in backwards propagation
+        https://bugs.webkit.org/show_bug.cgi?id=186916
+        <rdar://problem/41396612>
+
+        Reviewed by Yusuke Suzuki.
+
+        Otherwise, we may not think we care about the non-integral part in
+        a division (or perhaps overflow in an add, etc). Consider a program
+        like this:
+        
+        ```return a / b```
+        
+        That gets compiled to:
+        ```
+        a: ArithDiv // We don't check that the remainder is zero here.
+        b: MovHint(@a)
+        c: ForceOSRExit
+        d: Unreachable
+        ```
+        
+        If we don't inform @a that we care about its result in full number
+        accuracy, it will choose to ignore its non-integral remainder. This
+        makes sense if *everybody* that all uses of the Div only cared about
+        the integral part. However, OSR exit is not one of those users. OSR
+        exit cares about the fractional bits in such a Div.
+
+        * dfg/DFGBackwardsPropagationPhase.cpp:
+        (JSC::DFG::BackwardsPropagationPhase::propagate):
+
 2019-01-20  Yusuke Suzuki  <ysuz...@apple.com>
 
         [JSC] Invalidate old scope operations using global lexical binding epoch

Modified: trunk/Source/_javascript_Core/dfg/DFGBackwardsPropagationPhase.cpp (240222 => 240223)


--- trunk/Source/_javascript_Core/dfg/DFGBackwardsPropagationPhase.cpp	2019-01-21 03:33:24 UTC (rev 240222)
+++ trunk/Source/_javascript_Core/dfg/DFGBackwardsPropagationPhase.cpp	2019-01-21 03:54:17 UTC (rev 240223)
@@ -205,7 +205,6 @@
             break;
         }
             
-        case MovHint:
         case Check:
         case CheckVarargs:
             break;
_______________________________________________
webkit-changes mailing list
webkit-changes@lists.webkit.org
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to