diff options
author | Alon Zakai <alonzakai@gmail.com> | 2014-05-23 13:08:26 -0700 |
---|---|---|
committer | Alon Zakai <alonzakai@gmail.com> | 2014-05-23 13:08:40 -0700 |
commit | 693ece30e2c49431357c428fa835dc51d8526f98 (patch) | |
tree | 093b606de08c0329e9de4aeac2e588fd6f00b657 | |
parent | df4afcdf000553b76574594465fa4013deff7aad (diff) |
leave bool&1 as is if not going straight into a bitwise operator, to work around v8 issue 2513
-rw-r--r-- | tools/js-optimizer.js | 21 | ||||
-rw-r--r-- | tools/test-js-optimizer-asm-pre-output.js | 14 | ||||
-rw-r--r-- | tools/test-js-optimizer-asm-pre.js | 13 |
3 files changed, 22 insertions, 26 deletions
diff --git a/tools/js-optimizer.js b/tools/js-optimizer.js index 2004efda..5b01dae0 100644 --- a/tools/js-optimizer.js +++ b/tools/js-optimizer.js @@ -136,6 +136,7 @@ var CONTROL_FLOW = set('do', 'while', 'for', 'if', 'switch'); var NAME_OR_NUM = set('name', 'num'); var ASSOCIATIVE_BINARIES = set('+', '*', '|', '&', '^'); var ALTER_FLOW = set('break', 'continue', 'return'); +var BITWISE = set('|', '&', '^'); var BREAK_CAPTURERS = set('do', 'while', 'for', 'switch'); var CONTINUE_CAPTURERS = LOOP; @@ -387,14 +388,18 @@ function simplifyExpressions(ast) { return innerNode; } } - } else if (type === 'binary' && node[1] === '&' && node[3][0] === 'num') { - // Rewrite (X < Y) & 1 to (X < Y)|0. (Subsequent passes will eliminate - // the |0 if possible.) - var input = node[2]; - var amount = node[3][1]; - if (input[0] === 'binary' && (input[1] in COMPARE_OPS) && amount == 1) { - node[1] = '|'; - node[3][1] = 0; + } else if (type === 'binary' && (node[1] in BITWISE)) { + for (var i = 2; i <= 3; i++) { + var subNode = node[i]; + if (subNode[0] === 'binary' && subNode[1] === '&' && subNode[3][0] === 'num' && subNode[3][1] == 1) { + // Rewrite (X < Y) & 1 to X < Y , when it is going into a bitwise operator. We could + // remove even more (just replace &1 with |0, then subsequent passes could remove the |0) + // but v8 issue #2513 means the code would then run very slowly in chrome. + var input = subNode[2]; + if (input[0] === 'binary' && (input[1] in COMPARE_OPS)) { + node[i] = input; + } + } } } }); diff --git a/tools/test-js-optimizer-asm-pre-output.js b/tools/test-js-optimizer-asm-pre-output.js index 5281b87c..da3ebb4f 100644 --- a/tools/test-js-optimizer-asm-pre-output.js +++ b/tools/test-js-optimizer-asm-pre-output.js @@ -106,15 +106,11 @@ function sign_extension_simplification() { } } function compare_result_simplification() { - HEAP32[$4] = HEAP32[$5] < HEAP32[$6]; - HEAP32[$4] = HEAP32[$5] > HEAP32[$6]; - HEAP32[$4] = HEAP32[$5] <= HEAP32[$6]; - HEAP32[$4] = HEAP32[$5] <= HEAP32[$6]; - HEAP32[$4] = HEAP32[$5] == HEAP32[$6]; - HEAP32[$4] = HEAP32[$5] === HEAP32[$6]; - HEAP32[$4] = HEAP32[$5] != HEAP32[$6]; - HEAP32[$4] = HEAP32[$5] !== HEAP32[$6]; - var x = HEAP32[$5] != HEAP32[$6] | 0; + f((a > b & 1) + 1 | 0); + f(a > b | z); + f(a > b | c > d); + HEAP32[$4] = HEAP32[$5] < HEAP32[$6] & 1; + var x = HEAP32[$5] != HEAP32[$6] & 1; } function tempDoublePtr($45, $14, $28, $42) { $45 = $45 | 0; diff --git a/tools/test-js-optimizer-asm-pre.js b/tools/test-js-optimizer-asm-pre.js index d48d736e..08d8c2d4 100644 --- a/tools/test-js-optimizer-asm-pre.js +++ b/tools/test-js-optimizer-asm-pre.js @@ -113,16 +113,11 @@ function sign_extension_simplification() { } } function compare_result_simplification() { - // Eliminate these '&1's. + f(((a > b)&1) + 1 | 0); + f(((a > b)&1) | z); + f(((a > b)&1) | (c > d & 1)); + // Don't eliminate these '&1's. HEAP32[$4] = (HEAP32[$5] < HEAP32[$6]) & 1; - HEAP32[$4] = (HEAP32[$5] > HEAP32[$6]) & 1; - HEAP32[$4] = (HEAP32[$5] <= HEAP32[$6]) & 1; - HEAP32[$4] = (HEAP32[$5] <= HEAP32[$6]) & 1; - HEAP32[$4] = (HEAP32[$5] == HEAP32[$6]) & 1; - HEAP32[$4] = (HEAP32[$5] === HEAP32[$6]) & 1; - HEAP32[$4] = (HEAP32[$5] != HEAP32[$6]) & 1; - HEAP32[$4] = (HEAP32[$5] !== HEAP32[$6]) & 1; - // Convert the &1 to |0 here, since we don't get an implicit coersion. var x = (HEAP32[$5] != HEAP32[$6]) & 1; } function tempDoublePtr($45, $14, $28, $42) { |