| Index: src/mips/lithium-codegen-mips.cc
|
| diff --git a/src/mips/lithium-codegen-mips.cc b/src/mips/lithium-codegen-mips.cc
|
| index 292ce13f24cc9d4b39de3bbbac953f91cef33032..0f562fb899eeb4b2e68b37a2e79afe6b97bc56fc 100644
|
| --- a/src/mips/lithium-codegen-mips.cc
|
| +++ b/src/mips/lithium-codegen-mips.cc
|
| @@ -1195,39 +1195,48 @@ void LCodeGen::DoMultiplyAddD(LMultiplyAddD* instr) {
|
|
|
| void LCodeGen::DoFlooringDivByPowerOf2I(LFlooringDivByPowerOf2I* instr) {
|
| Register dividend = ToRegister(instr->dividend());
|
| + Register result = ToRegister(instr->result());
|
| int32_t divisor = instr->divisor();
|
| - ASSERT(dividend.is(ToRegister(instr->result())));
|
| Register scratch = scratch0();
|
| + ASSERT(!scratch.is(dividend));
|
|
|
| // If the divisor is positive, things are easy: There can be no deopts and we
|
| // can simply do an arithmetic right shift.
|
| if (divisor == 1) return;
|
| uint16_t shift = WhichPowerOf2Abs(divisor);
|
| if (divisor > 1) {
|
| - __ sra(dividend, dividend, shift);
|
| + __ sra(result, dividend, shift);
|
| return;
|
| }
|
|
|
| // If the divisor is negative, we have to negate and handle edge cases.
|
| - Label not_kmin_int, done;
|
| - __ Subu(scratch, zero_reg, dividend);
|
| + if (instr->hydrogen()->CheckFlag(HValue::kLeftCanBeMinInt)) {
|
| + __ Move(scratch, dividend);
|
| + }
|
| + __ Subu(result, zero_reg, dividend);
|
| if (instr->hydrogen()->CheckFlag(HValue::kBailoutOnMinusZero)) {
|
| - DeoptimizeIf(eq, instr->environment(), scratch, Operand(zero_reg));
|
| + DeoptimizeIf(eq, instr->environment(), result, Operand(zero_reg));
|
| }
|
| - if (instr->hydrogen()->left()->RangeCanInclude(kMinInt)) {
|
| + if (instr->hydrogen()->CheckFlag(HValue::kLeftCanBeMinInt)) {
|
| // Note that we could emit branch-free code, but that would need one more
|
| // register.
|
| - __ Branch(¬_kmin_int, ne, dividend, Operand(kMinInt));
|
| +
|
| + __ Xor(at, scratch, result);
|
| if (divisor == -1) {
|
| - DeoptimizeIf(al, instr->environment());
|
| + DeoptimizeIf(ge, instr->environment(), at, Operand(zero_reg));
|
| + __ sra(result, dividend, shift);
|
| } else {
|
| - __ li(dividend, Operand(kMinInt / divisor));
|
| + Label no_overflow, done;
|
| + __ Branch(&no_overflow, lt, at, Operand(zero_reg));
|
| + __ li(result, Operand(kMinInt / divisor));
|
| __ Branch(&done);
|
| + __ bind(&no_overflow);
|
| + __ sra(result, dividend, shift);
|
| + __ bind(&done);
|
| }
|
| + } else {
|
| + __ sra(result, dividend, shift);
|
| }
|
| - __ bind(¬_kmin_int);
|
| - __ sra(dividend, scratch, shift);
|
| - __ bind(&done);
|
| }
|
|
|
|
|
|
|