Index: src/mips/full-codegen-mips.cc |
diff --git a/src/mips/full-codegen-mips.cc b/src/mips/full-codegen-mips.cc |
index 6947ca8781e48f9632952e4e5bef742b6178cdf8..caa7352eae8bb60b771e6c475ecb2727d568f8b7 100644 |
--- a/src/mips/full-codegen-mips.cc |
+++ b/src/mips/full-codegen-mips.cc |
@@ -4442,15 +4442,48 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) { |
PrepareForBailoutForId(prop->LoadId(), TOS_REG); |
} |
- // Call ToNumber only if operand is not a smi. |
- Label no_conversion; |
+ // Inline smi case if we are in a loop. |
+ Label stub_call, done; |
+ JumpPatchSite patch_site(masm_); |
+ |
+ int count_value = expr->op() == Token::INC ? 1 : -1; |
+ __ mov(a0, v0); |
if (ShouldInlineSmiCase(expr->op())) { |
- __ JumpIfSmi(v0, &no_conversion); |
+ Label slow; |
+ patch_site.EmitJumpIfNotSmi(v0, &slow); |
+ |
+ // Save result for postfix expressions. |
+ if (expr->is_postfix()) { |
+ if (!context()->IsEffect()) { |
+ // Save the result on the stack. If we have a named or keyed property |
+ // we store the result under the receiver that is currently on top |
+ // of the stack. |
+ switch (assign_type) { |
+ case VARIABLE: |
+ __ push(v0); |
+ break; |
+ case NAMED_PROPERTY: |
+ __ sw(v0, MemOperand(sp, kPointerSize)); |
+ break; |
+ case KEYED_PROPERTY: |
+ __ sw(v0, MemOperand(sp, 2 * kPointerSize)); |
+ break; |
+ } |
+ } |
+ } |
+ |
+ Register scratch1 = a1; |
+ Register scratch2 = t0; |
+ __ li(scratch1, Operand(Smi::FromInt(count_value))); |
+ __ AdduAndCheckForOverflow(v0, v0, scratch1, scratch2); |
+ __ BranchOnNoOverflow(&done, scratch2); |
+ // Call stub. Undo operation first. |
+ __ Move(v0, a0); |
+ __ jmp(&stub_call); |
+ __ bind(&slow); |
} |
- __ mov(a0, v0); |
ToNumberStub convert_stub; |
__ CallStub(&convert_stub); |
- __ bind(&no_conversion); |
// Save result for postfix expressions. |
if (expr->is_postfix()) { |
@@ -4471,24 +4504,9 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) { |
} |
} |
} |
- __ mov(a0, result_register()); |
- |
- // Inline smi case if we are in a loop. |
- Label stub_call, done; |
- JumpPatchSite patch_site(masm_); |
- int count_value = expr->op() == Token::INC ? 1 : -1; |
- if (ShouldInlineSmiCase(expr->op())) { |
- __ li(a1, Operand(Smi::FromInt(count_value))); |
- __ AdduAndCheckForOverflow(v0, a0, a1, t0); |
- __ BranchOnOverflow(&stub_call, t0); // Do stub on overflow. |
- |
- // We could eliminate this smi check if we split the code at |
- // the first smi check before calling ToNumber. |
- patch_site.EmitJumpIfSmi(v0, &done); |
- __ bind(&stub_call); |
- } |
- __ mov(a1, a0); |
+ __ bind(&stub_call); |
+ __ mov(a1, v0); |
__ li(a0, Operand(Smi::FromInt(count_value))); |
// Record position before stub call. |