diff options
Diffstat (limited to 'src/runtime.js')
-rw-r--r-- | src/runtime.js | 27 |
1 files changed, 14 insertions, 13 deletions
diff --git a/src/runtime.js b/src/runtime.js index b5663045..852d08d8 100644 --- a/src/runtime.js +++ b/src/runtime.js @@ -79,9 +79,10 @@ var RuntimeGenerator = { // Rounding is inevitable if the number is large. This is a particular problem for small negative numbers // (-1 will be rounded!), so handle negatives separately and carefully makeBigInt: function(low, high, unsigned) { - return '(' + unsigned + - ' ? (' + makeSignOp(low, 'i32', 'un', 1, 1) + '+(' + makeSignOp(high, 'i32', 'un', 1, 1) + '*4294967296))' + - ' : (' + makeSignOp(low, 'i32', 'un', 1, 1) + '+(' + makeSignOp(high, 'i32', 're', 1, 1) + '*4294967296)))'; + var unsignedRet = '(' + makeSignOp(low, 'i32', 'un', 1, 1) + '+(' + makeSignOp(high, 'i32', 'un', 1, 1) + '*4294967296))'; + var signedRet = '(' + makeSignOp(low, 'i32', 'un', 1, 1) + '+(' + makeSignOp(high, 'i32', 're', 1, 1) + '*4294967296))'; + if (typeof unsigned === 'string') return '(' + unsigned + ' ? ' + unsignedRet + ' : ' + signedRet + ')'; + return unsigned ? unsignedRet : signedRet; } }; @@ -122,34 +123,34 @@ var Runtime = { FLOAT_TYPES: set('float', 'double'), // Mirrors processMathop's treatment of constants (which we optimize directly) - bitshift64: function(value, op, bits) { + bitshift64: function(low, high, op, bits) { var ander = Math.pow(2, bits)-1; if (bits < 32) { switch (op) { case 'shl': - return [value[0] << bits, (value[1] << bits) | ((value[0]&(ander << (32 - bits))) >>> (32 - bits))]; + return [low << bits, (high << bits) | ((low&(ander << (32 - bits))) >>> (32 - bits))]; case 'ashr': - return [(((value[0] >>> bits ) | ((value[1]&ander) << (32 - bits))) >> 0) >>> 0, (value[1] >> bits) >>> 0]; + return [(((low >>> bits ) | ((high&ander) << (32 - bits))) >> 0) >>> 0, (high >> bits) >>> 0]; case 'lshr': - return [((value[0] >>> bits) | ((value[1]&ander) << (32 - bits))) >>> 0, value[1] >>> bits]; + return [((low >>> bits) | ((high&ander) << (32 - bits))) >>> 0, high >>> bits]; } } else if (bits == 32) { switch (op) { case 'shl': - return [0, value[0]]; + return [0, low]; case 'ashr': - return [value[1], (value[1]|0) < 0 ? ander : 0]; + return [high, (high|0) < 0 ? ander : 0]; case 'lshr': - return [value[1], 0]; + return [high, 0]; } } else { // bits > 32 switch (op) { case 'shl': - return [0, value[0] << (bits - 32)]; + return [0, low << (bits - 32)]; case 'ashr': - return [(value[1] >> (bits - 32)) >>> 0, (value[1]|0) < 0 ? ander : 0]; + return [(high >> (bits - 32)) >>> 0, (high|0) < 0 ? ander : 0]; case 'lshr': - return [value[1] >>> (bits - 32) , 0]; + return [high >>> (bits - 32) , 0]; } } abort('unknown bitshift64 op: ' + [value, op, bits]); |