Commit d7934bd4 authored by yangguo@chromium.org's avatar yangguo@chromium.org

MIPS: Convert fast smi-only to fast object in generated code for array push.

Port r10648 (818a1aa).

BUG=
TEST=

Review URL: https://chromiumcodereview.appspot.com/9372022
Patch from Daniel Kalmar <kalmard@homejinni.com>.

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@10661 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
parent de510c3a
...@@ -1468,7 +1468,10 @@ Handle<Code> CallStubCompiler::CompileArrayPushCall( ...@@ -1468,7 +1468,10 @@ Handle<Code> CallStubCompiler::CompileArrayPushCall(
__ Ret(); __ Ret();
} else { } else {
Label call_builtin; Label call_builtin;
Register elements = a3; if (argc == 1) { // Otherwise fall through to call the builtin.
Label attempt_to_grow_elements;
Register elements = t2;
Register end_elements = t1; Register end_elements = t1;
// Get the elements array of the object. // Get the elements array of the object.
__ lw(elements, FieldMemOperand(receiver, JSArray::kElementsOffset)); __ lw(elements, FieldMemOperand(receiver, JSArray::kElementsOffset));
...@@ -1480,16 +1483,13 @@ Handle<Code> CallStubCompiler::CompileArrayPushCall( ...@@ -1480,16 +1483,13 @@ Handle<Code> CallStubCompiler::CompileArrayPushCall(
&call_builtin, &call_builtin,
DONT_DO_SMI_CHECK); DONT_DO_SMI_CHECK);
if (argc == 1) { // Otherwise fall through to call the builtin.
Label attempt_to_grow_elements;
// Get the array's length into v0 and calculate new length. // Get the array's length into v0 and calculate new length.
__ lw(v0, FieldMemOperand(receiver, JSArray::kLengthOffset)); __ lw(v0, FieldMemOperand(receiver, JSArray::kLengthOffset));
STATIC_ASSERT(kSmiTagSize == 1); STATIC_ASSERT(kSmiTagSize == 1);
STATIC_ASSERT(kSmiTag == 0); STATIC_ASSERT(kSmiTag == 0);
__ Addu(v0, v0, Operand(Smi::FromInt(argc))); __ Addu(v0, v0, Operand(Smi::FromInt(argc)));
// Get the element's length. // Get the elements' length.
__ lw(t0, FieldMemOperand(elements, FixedArray::kLengthOffset)); __ lw(t0, FieldMemOperand(elements, FixedArray::kLengthOffset));
// Check if we could survive without allocation. // Check if we could survive without allocation.
...@@ -1503,7 +1503,7 @@ Handle<Code> CallStubCompiler::CompileArrayPushCall( ...@@ -1503,7 +1503,7 @@ Handle<Code> CallStubCompiler::CompileArrayPushCall(
// Save new length. // Save new length.
__ sw(v0, FieldMemOperand(receiver, JSArray::kLengthOffset)); __ sw(v0, FieldMemOperand(receiver, JSArray::kLengthOffset));
// Push the element. // Store the value.
// We may need a register containing the address end_elements below, // We may need a register containing the address end_elements below,
// so write back the value in end_elements. // so write back the value in end_elements.
__ sll(end_elements, v0, kPointerSizeLog2 - kSmiTagSize); __ sll(end_elements, v0, kPointerSizeLog2 - kSmiTagSize);
...@@ -1519,13 +1519,33 @@ Handle<Code> CallStubCompiler::CompileArrayPushCall( ...@@ -1519,13 +1519,33 @@ Handle<Code> CallStubCompiler::CompileArrayPushCall(
__ bind(&with_write_barrier); __ bind(&with_write_barrier);
__ lw(t2, FieldMemOperand(receiver, HeapObject::kMapOffset)); __ lw(a3, FieldMemOperand(receiver, HeapObject::kMapOffset));
__ CheckFastObjectElements(t2, t2, &call_builtin);
if (FLAG_smi_only_arrays && !FLAG_trace_elements_transitions) {
Label fast_object, not_fast_object;
__ CheckFastObjectElements(a3, t3, &not_fast_object);
__ jmp(&fast_object);
// In case of fast smi-only, convert to fast object, otherwise bail out.
__ bind(&not_fast_object);
__ CheckFastSmiOnlyElements(a3, t3, &call_builtin);
// edx: receiver
// r3: map
__ LoadTransitionedArrayMapConditional(FAST_SMI_ONLY_ELEMENTS,
FAST_ELEMENTS,
a3,
t3,
&call_builtin);
__ mov(a2, receiver);
ElementsTransitionGenerator::GenerateSmiOnlyToObject(masm());
__ bind(&fast_object);
} else {
__ CheckFastObjectElements(a3, a3, &call_builtin);
}
// Save new length. // Save new length.
__ sw(v0, FieldMemOperand(receiver, JSArray::kLengthOffset)); __ sw(v0, FieldMemOperand(receiver, JSArray::kLengthOffset));
// Push the element. // Store the value.
// We may need a register containing the address end_elements below, // We may need a register containing the address end_elements below,
// so write back the value in end_elements. // so write back the value in end_elements.
__ sll(end_elements, v0, kPointerSizeLog2 - kSmiTagSize); __ sll(end_elements, v0, kPointerSizeLog2 - kSmiTagSize);
...@@ -1573,23 +1593,23 @@ Handle<Code> CallStubCompiler::CompileArrayPushCall( ...@@ -1573,23 +1593,23 @@ Handle<Code> CallStubCompiler::CompileArrayPushCall(
__ Addu(end_elements, elements, end_elements); __ Addu(end_elements, elements, end_elements);
__ Addu(end_elements, end_elements, Operand(kEndElementsOffset)); __ Addu(end_elements, end_elements, Operand(kEndElementsOffset));
__ li(t3, Operand(new_space_allocation_top)); __ li(t3, Operand(new_space_allocation_top));
__ lw(t2, MemOperand(t3)); __ lw(a3, MemOperand(t3));
__ Branch(&call_builtin, ne, end_elements, Operand(t2)); __ Branch(&call_builtin, ne, end_elements, Operand(a3));
__ li(t5, Operand(new_space_allocation_limit)); __ li(t5, Operand(new_space_allocation_limit));
__ lw(t5, MemOperand(t5)); __ lw(t5, MemOperand(t5));
__ Addu(t2, t2, Operand(kAllocationDelta * kPointerSize)); __ Addu(a3, a3, Operand(kAllocationDelta * kPointerSize));
__ Branch(&call_builtin, hi, t2, Operand(t5)); __ Branch(&call_builtin, hi, a3, Operand(t5));
// We fit and could grow elements. // We fit and could grow elements.
// Update new_space_allocation_top. // Update new_space_allocation_top.
__ sw(t2, MemOperand(t3)); __ sw(a3, MemOperand(t3));
// Push the argument. // Push the argument.
__ sw(a2, MemOperand(end_elements)); __ sw(a2, MemOperand(end_elements));
// Fill the rest with holes. // Fill the rest with holes.
__ LoadRoot(t2, Heap::kTheHoleValueRootIndex); __ LoadRoot(a3, Heap::kTheHoleValueRootIndex);
for (int i = 1; i < kAllocationDelta; i++) { for (int i = 1; i < kAllocationDelta; i++) {
__ sw(t2, MemOperand(end_elements, i * kPointerSize)); __ sw(a3, MemOperand(end_elements, i * kPointerSize));
} }
// Update elements' and array's sizes. // Update elements' and array's sizes.
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment