Commit ab34189c authored by sgjesse@chromium.org's avatar sgjesse@chromium.org

Handle array construction in native code (x64 version).

Ported the handle array construction in native code to x64. See http://codereview.chromium.org/193125 for details.

Please take a closer look of my use of the macro assembler Smi abstractions.
Review URL: http://codereview.chromium.org/209048

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@2960 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
parent 98390928
......@@ -674,18 +674,18 @@ static const int kPreallocatedArrayElements = 4;
// Allocate an empty JSArray. The allocated array is put into the result
// register. If the parameter holes is larger than zero an elements backing
// store is allocated with this size and filled with the hole values. Otherwise
// the elements backing store is set to the empty FixedArray.
// register. If the parameter initial_capacity is larger than zero an elements
// backing store is allocated with this size and filled with the hole values.
// Otherwise the elements backing store is set to the empty FixedArray.
static void AllocateEmptyJSArray(MacroAssembler* masm,
Register array_function,
Register result,
Register scratch1,
Register scratch2,
Register scratch3,
int holes,
int initial_capacity,
Label* gc_required) {
ASSERT(holes >= 0);
ASSERT(initial_capacity >= 0);
// Load the initial map from the array function.
__ mov(scratch1, FieldOperand(array_function,
......@@ -694,8 +694,8 @@ static void AllocateEmptyJSArray(MacroAssembler* masm,
// Allocate the JSArray object together with space for a fixed array with the
// requested elements.
int size = JSArray::kSize;
if (holes > 0) {
size += FixedArray::SizeFor(holes);
if (initial_capacity > 0) {
size += FixedArray::SizeFor(initial_capacity);
}
__ AllocateObjectInNewSpace(size,
result,
......@@ -717,7 +717,7 @@ static void AllocateEmptyJSArray(MacroAssembler* masm,
// If no storage is requested for the elements array just set the empty
// fixed array.
if (holes == 0) {
if (initial_capacity == 0) {
__ mov(FieldOperand(result, JSArray::kElementsOffset),
Factory::empty_fixed_array());
return;
......@@ -737,17 +737,18 @@ static void AllocateEmptyJSArray(MacroAssembler* masm,
// scratch2: start of next object
__ mov(FieldOperand(scratch1, JSObject::kMapOffset),
Factory::fixed_array_map());
__ mov(FieldOperand(scratch1, Array::kLengthOffset), Immediate(holes));
__ mov(FieldOperand(scratch1, Array::kLengthOffset),
Immediate(initial_capacity));
// Fill the FixedArray with the hole value. Inline the code if short.
// Reconsider loop unfolding if kPreallocatedArrayElements gets changed.
static const int kLoopUnfoldLimit = 4;
ASSERT(kPreallocatedArrayElements <= kLoopUnfoldLimit);
if (holes <= kLoopUnfoldLimit) {
if (initial_capacity <= kLoopUnfoldLimit) {
// Use a scratch register here to have only one reloc info when unfolding
// the loop.
__ mov(scratch3, Factory::the_hole_value());
for (int i = 0; i < holes; i++) {
for (int i = 0; i < initial_capacity; i++) {
__ mov(FieldOperand(scratch1,
FixedArray::kHeaderSize + i * kPointerSize),
scratch3);
......
......@@ -687,6 +687,10 @@ class Assembler : public Malloced {
immediate_arithmetic_op(0x4, dst, src);
}
void andl(Register dst, Immediate src) {
immediate_arithmetic_op_32(0x4, dst, src);
}
void decq(Register dst);
void decq(const Operand& dst);
void decl(Register dst);
......
This diff is collapsed.
......@@ -519,6 +519,18 @@ void MacroAssembler::JumpIfSmiEqualsConstant(Register src,
}
void MacroAssembler::JumpIfSmiGreaterEqualsConstant(Register src,
int constant,
Label* on_greater_equals) {
if (Smi::IsValid(constant)) {
Condition are_greater_equal = CheckSmiGreaterEqualsConstant(src, constant);
j(are_greater_equal, on_greater_equals);
} else if (constant < Smi::kMinValue){
jmp(on_greater_equals);
}
}
void MacroAssembler::JumpIfNotValidSmiValue(Register src, Label* on_invalid) {
Condition is_valid = CheckInteger32ValidSmiValue(src);
j(ReverseCondition(is_valid), on_invalid);
......@@ -602,6 +614,22 @@ Condition MacroAssembler::CheckSmiEqualsConstant(Register src, int constant) {
}
Condition MacroAssembler::CheckSmiGreaterEqualsConstant(Register src,
int constant) {
if (constant == 0) {
testl(src, Immediate(static_cast<uint32_t>(0x80000000u)));
return positive;
}
if (Smi::IsValid(constant)) {
cmpl(src, Immediate(Smi::FromInt(constant)));
return greater_equal;
}
// Can't be equal.
UNREACHABLE();
return no_condition;
}
Condition MacroAssembler::CheckInteger32ValidSmiValue(Register src) {
// A 32-bit integer value can be converted to a smi if it is in the
// range [-2^30 .. 2^30-1]. That is equivalent to having its 32-bit
......
......@@ -193,6 +193,9 @@ class MacroAssembler: public Assembler {
// Check whether a tagged smi is equal to a constant.
Condition CheckSmiEqualsConstant(Register src, int constant);
// Check whether a tagged smi is greater than or equal to a constant.
Condition CheckSmiGreaterEqualsConstant(Register src, int constant);
// Checks whether an 32-bit integer value is a valid for conversion
// to a smi.
Condition CheckInteger32ValidSmiValue(Register src);
......@@ -216,6 +219,12 @@ class MacroAssembler: public Assembler {
// to the constant.
void JumpIfSmiEqualsConstant(Register src, int constant, Label* on_equals);
// Jump to label if the value is a tagged smi with value greater than or equal
// to the constant.
void JumpIfSmiGreaterEqualsConstant(Register src,
int constant,
Label* on_equals);
// Jump if either or both register are not smi values.
void JumpIfNotBothSmi(Register src1, Register src2, Label* on_not_both_smi);
......
......@@ -1751,6 +1751,7 @@ Object* ConstructStubCompiler::CompileConstructStub(
// Load the initial map and verify that it is in fact a map.
__ movq(rbx, FieldOperand(rdi, JSFunction::kPrototypeOrInitialMapOffset));
// Will both indicate a NULL and a Smi.
ASSERT(kSmiTag == 0);
__ JumpIfSmi(rbx, &generic_stub_call);
__ CmpObjectType(rbx, MAP_TYPE, rcx);
__ j(not_equal, &generic_stub_call);
......
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