Pass key in register for keyed load IC
The calling convention for keyed load IC is changed to have the key passed both in a register (r0) and on the stack. Next steps will be first to remove the key from the stack and then pass the receiver in a register (r1). Review URL: http://codereview.chromium.org/1937003 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@4584 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
This commit is contained in:
parent
4501cea97b
commit
a355e45e22
@ -5391,7 +5391,8 @@ void DeferredReferenceGetKeyedValue::Generate() {
|
|||||||
|
|
||||||
// The rest of the instructions in the deferred code must be together.
|
// The rest of the instructions in the deferred code must be together.
|
||||||
{ Assembler::BlockConstPoolScope block_const_pool(masm_);
|
{ Assembler::BlockConstPoolScope block_const_pool(masm_);
|
||||||
// Call keyed load IC. It has all arguments on the stack.
|
// Call keyed load IC. It has all arguments on the stack and the key in r0.
|
||||||
|
__ ldr(r0, MemOperand(sp, 0));
|
||||||
Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize));
|
Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize));
|
||||||
__ Call(ic, RelocInfo::CODE_TARGET);
|
__ Call(ic, RelocInfo::CODE_TARGET);
|
||||||
// The call must be followed by a nop instruction to indicate that the
|
// The call must be followed by a nop instruction to indicate that the
|
||||||
@ -5514,7 +5515,6 @@ void CodeGenerator::EmitNamedStore(Handle<String> name, bool is_contextual) {
|
|||||||
|
|
||||||
void CodeGenerator::EmitKeyedLoad() {
|
void CodeGenerator::EmitKeyedLoad() {
|
||||||
if (loop_nesting() == 0) {
|
if (loop_nesting() == 0) {
|
||||||
VirtualFrame::SpilledScope spilled(frame_);
|
|
||||||
Comment cmnt(masm_, "[ Load from keyed property");
|
Comment cmnt(masm_, "[ Load from keyed property");
|
||||||
frame_->CallKeyedLoadIC();
|
frame_->CallKeyedLoadIC();
|
||||||
} else {
|
} else {
|
||||||
|
@ -161,9 +161,10 @@ void Debug::GenerateStoreICDebugBreak(MacroAssembler* masm) {
|
|||||||
void Debug::GenerateKeyedLoadICDebugBreak(MacroAssembler* masm) {
|
void Debug::GenerateKeyedLoadICDebugBreak(MacroAssembler* masm) {
|
||||||
// ---------- S t a t e --------------
|
// ---------- S t a t e --------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
Generate_DebugBreakCallHelper(masm, 0);
|
Generate_DebugBreakCallHelper(masm, r0.bit());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -728,7 +728,7 @@ void FullCodeGenerator::EmitVariableLoad(Variable* var,
|
|||||||
ASSERT_NOT_NULL(object_slot);
|
ASSERT_NOT_NULL(object_slot);
|
||||||
|
|
||||||
// Load the object.
|
// Load the object.
|
||||||
Move(r2, object_slot);
|
Move(r1, object_slot);
|
||||||
|
|
||||||
// Assert that the key is a smi.
|
// Assert that the key is a smi.
|
||||||
Literal* key_literal = property->key()->AsLiteral();
|
Literal* key_literal = property->key()->AsLiteral();
|
||||||
@ -736,12 +736,12 @@ void FullCodeGenerator::EmitVariableLoad(Variable* var,
|
|||||||
ASSERT(key_literal->handle()->IsSmi());
|
ASSERT(key_literal->handle()->IsSmi());
|
||||||
|
|
||||||
// Load the key.
|
// Load the key.
|
||||||
__ mov(r1, Operand(key_literal->handle()));
|
__ mov(r0, Operand(key_literal->handle()));
|
||||||
|
|
||||||
// Push both as arguments to ic.
|
// Push both as arguments to ic.
|
||||||
__ Push(r2, r1);
|
__ Push(r1, r0);
|
||||||
|
|
||||||
// Do a keyed property load.
|
// Call keyed load IC. It has all arguments on the stack and the key in r0.
|
||||||
Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize));
|
Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize));
|
||||||
__ Call(ic, RelocInfo::CODE_TARGET);
|
__ Call(ic, RelocInfo::CODE_TARGET);
|
||||||
|
|
||||||
@ -1005,6 +1005,8 @@ void FullCodeGenerator::EmitNamedPropertyLoad(Property* prop) {
|
|||||||
|
|
||||||
void FullCodeGenerator::EmitKeyedPropertyLoad(Property* prop) {
|
void FullCodeGenerator::EmitKeyedPropertyLoad(Property* prop) {
|
||||||
SetSourcePosition(prop->position());
|
SetSourcePosition(prop->position());
|
||||||
|
// Call keyed load IC. It has all arguments on the stack and the key in r0.
|
||||||
|
__ ldr(r0, MemOperand(sp, 0));
|
||||||
Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize));
|
Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize));
|
||||||
__ Call(ic, RelocInfo::CODE_TARGET);
|
__ Call(ic, RelocInfo::CODE_TARGET);
|
||||||
}
|
}
|
||||||
@ -1247,6 +1249,9 @@ void FullCodeGenerator::VisitCall(Call* expr) {
|
|||||||
VisitForValue(prop->key(), kStack);
|
VisitForValue(prop->key(), kStack);
|
||||||
// Record source code position for IC call.
|
// Record source code position for IC call.
|
||||||
SetSourcePosition(prop->position());
|
SetSourcePosition(prop->position());
|
||||||
|
// Call keyed load IC. It has all arguments on the stack and the key in
|
||||||
|
// r0.
|
||||||
|
__ ldr(r0, MemOperand(sp, 0));
|
||||||
Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize));
|
Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize));
|
||||||
__ Call(ic, RelocInfo::CODE_TARGET);
|
__ Call(ic, RelocInfo::CODE_TARGET);
|
||||||
// Load receiver object into r1.
|
// Load receiver object into r1.
|
||||||
|
@ -682,12 +682,13 @@ Object* KeyedLoadIC_Miss(Arguments args);
|
|||||||
void KeyedLoadIC::GenerateMiss(MacroAssembler* masm) {
|
void KeyedLoadIC::GenerateMiss(MacroAssembler* masm) {
|
||||||
// ---------- S t a t e --------------
|
// ---------- S t a t e --------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
|
|
||||||
__ ldm(ia, sp, r2.bit() | r3.bit());
|
__ ldr(r1, MemOperand(sp, kPointerSize));
|
||||||
__ Push(r3, r2);
|
__ Push(r1, r0);
|
||||||
|
|
||||||
ExternalReference ref = ExternalReference(IC_Utility(kKeyedLoadIC_Miss));
|
ExternalReference ref = ExternalReference(IC_Utility(kKeyedLoadIC_Miss));
|
||||||
__ TailCallExternalReference(ref, 2, 1);
|
__ TailCallExternalReference(ref, 2, 1);
|
||||||
@ -697,12 +698,13 @@ void KeyedLoadIC::GenerateMiss(MacroAssembler* masm) {
|
|||||||
void KeyedLoadIC::GenerateRuntimeGetProperty(MacroAssembler* masm) {
|
void KeyedLoadIC::GenerateRuntimeGetProperty(MacroAssembler* masm) {
|
||||||
// ---------- S t a t e --------------
|
// ---------- S t a t e --------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
|
|
||||||
__ ldm(ia, sp, r2.bit() | r3.bit());
|
__ ldr(r1, MemOperand(sp, kPointerSize));
|
||||||
__ Push(r3, r2);
|
__ Push(r1, r0);
|
||||||
|
|
||||||
__ TailCallRuntime(Runtime::kGetProperty, 2, 1);
|
__ TailCallRuntime(Runtime::kGetProperty, 2, 1);
|
||||||
}
|
}
|
||||||
@ -711,13 +713,14 @@ void KeyedLoadIC::GenerateRuntimeGetProperty(MacroAssembler* masm) {
|
|||||||
void KeyedLoadIC::GenerateGeneric(MacroAssembler* masm) {
|
void KeyedLoadIC::GenerateGeneric(MacroAssembler* masm) {
|
||||||
// ---------- S t a t e --------------
|
// ---------- S t a t e --------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
Label slow, fast, check_pixel_array, check_number_dictionary;
|
Label slow, fast, check_pixel_array, check_number_dictionary;
|
||||||
|
|
||||||
// Get the key and receiver object from the stack.
|
// Get the object from the stack.
|
||||||
__ ldm(ia, sp, r0.bit() | r1.bit());
|
__ ldr(r1, MemOperand(sp, kPointerSize));
|
||||||
|
|
||||||
// Check that the object isn't a smi.
|
// Check that the object isn't a smi.
|
||||||
__ BranchOnSmi(r1, &slow);
|
__ BranchOnSmi(r1, &slow);
|
||||||
@ -790,6 +793,7 @@ void KeyedLoadIC::GenerateGeneric(MacroAssembler* masm) {
|
|||||||
// Slow case: Push extra copies of the arguments (2).
|
// Slow case: Push extra copies of the arguments (2).
|
||||||
__ bind(&slow);
|
__ bind(&slow);
|
||||||
__ IncrementCounter(&Counters::keyed_load_generic_slow, 1, r0, r1);
|
__ IncrementCounter(&Counters::keyed_load_generic_slow, 1, r0, r1);
|
||||||
|
__ ldr(r0, MemOperand(sp, 0));
|
||||||
GenerateRuntimeGetProperty(masm);
|
GenerateRuntimeGetProperty(masm);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -797,6 +801,7 @@ void KeyedLoadIC::GenerateGeneric(MacroAssembler* masm) {
|
|||||||
void KeyedLoadIC::GenerateString(MacroAssembler* masm) {
|
void KeyedLoadIC::GenerateString(MacroAssembler* masm) {
|
||||||
// ---------- S t a t e --------------
|
// ---------- S t a t e --------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
@ -806,8 +811,8 @@ void KeyedLoadIC::GenerateString(MacroAssembler* masm) {
|
|||||||
Label slow_char_code;
|
Label slow_char_code;
|
||||||
Label got_char_code;
|
Label got_char_code;
|
||||||
|
|
||||||
// Get the key and receiver object from the stack.
|
// Get the object from the stack.
|
||||||
__ ldm(ia, sp, r0.bit() | r1.bit());
|
__ ldr(r1, MemOperand(sp, kPointerSize));
|
||||||
|
|
||||||
Register object = r1;
|
Register object = r1;
|
||||||
Register index = r0;
|
Register index = r0;
|
||||||
@ -907,13 +912,14 @@ void KeyedLoadIC::GenerateExternalArray(MacroAssembler* masm,
|
|||||||
ExternalArrayType array_type) {
|
ExternalArrayType array_type) {
|
||||||
// ---------- S t a t e --------------
|
// ---------- S t a t e --------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
Label slow, failed_allocation;
|
Label slow, failed_allocation;
|
||||||
|
|
||||||
// Get the key and receiver object from the stack.
|
// Get the object from the stack.
|
||||||
__ ldm(ia, sp, r0.bit() | r1.bit());
|
__ ldr(r1, MemOperand(sp, kPointerSize));
|
||||||
|
|
||||||
// r0: key
|
// r0: key
|
||||||
// r1: receiver object
|
// r1: receiver object
|
||||||
@ -1143,6 +1149,7 @@ void KeyedLoadIC::GenerateExternalArray(MacroAssembler* masm,
|
|||||||
// Slow case: Load name and receiver from stack and jump to runtime.
|
// Slow case: Load name and receiver from stack and jump to runtime.
|
||||||
__ bind(&slow);
|
__ bind(&slow);
|
||||||
__ IncrementCounter(&Counters::keyed_load_external_array_slow, 1, r0, r1);
|
__ IncrementCounter(&Counters::keyed_load_external_array_slow, 1, r0, r1);
|
||||||
|
__ ldr(r0, MemOperand(sp, 0));
|
||||||
GenerateRuntimeGetProperty(masm);
|
GenerateRuntimeGetProperty(masm);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1150,13 +1157,14 @@ void KeyedLoadIC::GenerateExternalArray(MacroAssembler* masm,
|
|||||||
void KeyedLoadIC::GenerateIndexedInterceptor(MacroAssembler* masm) {
|
void KeyedLoadIC::GenerateIndexedInterceptor(MacroAssembler* masm) {
|
||||||
// ---------- S t a t e --------------
|
// ---------- S t a t e --------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
Label slow;
|
Label slow;
|
||||||
|
|
||||||
// Get the key and receiver object from the stack.
|
// Get the object from the stack.
|
||||||
__ ldm(ia, sp, r0.bit() | r1.bit());
|
__ ldr(r1, MemOperand(sp, kPointerSize));
|
||||||
|
|
||||||
// Check that the receiver isn't a smi.
|
// Check that the receiver isn't a smi.
|
||||||
__ BranchOnSmi(r1, &slow);
|
__ BranchOnSmi(r1, &slow);
|
||||||
|
@ -1824,18 +1824,18 @@ Object* KeyedLoadStubCompiler::CompileLoadField(String* name,
|
|||||||
int index) {
|
int index) {
|
||||||
// ----------- S t a t e -------------
|
// ----------- S t a t e -------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
Label miss;
|
Label miss;
|
||||||
|
|
||||||
__ ldr(r2, MemOperand(sp, 0));
|
// Check the key is the cached one.
|
||||||
__ ldr(r0, MemOperand(sp, kPointerSize));
|
__ cmp(r0, Operand(Handle<String>(name)));
|
||||||
|
|
||||||
__ cmp(r2, Operand(Handle<String>(name)));
|
|
||||||
__ b(ne, &miss);
|
__ b(ne, &miss);
|
||||||
|
|
||||||
GenerateLoadField(receiver, holder, r0, r3, r1, index, name, &miss);
|
__ ldr(r1, MemOperand(sp, kPointerSize)); // Receiver.
|
||||||
|
GenerateLoadField(receiver, holder, r1, r2, r3, index, name, &miss);
|
||||||
__ bind(&miss);
|
__ bind(&miss);
|
||||||
GenerateLoadMiss(masm(), Code::KEYED_LOAD_IC);
|
GenerateLoadMiss(masm(), Code::KEYED_LOAD_IC);
|
||||||
|
|
||||||
@ -1849,19 +1849,19 @@ Object* KeyedLoadStubCompiler::CompileLoadCallback(String* name,
|
|||||||
AccessorInfo* callback) {
|
AccessorInfo* callback) {
|
||||||
// ----------- S t a t e -------------
|
// ----------- S t a t e -------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
Label miss;
|
Label miss;
|
||||||
|
|
||||||
__ ldr(r2, MemOperand(sp, 0));
|
// Check the key is the cached one.
|
||||||
__ ldr(r0, MemOperand(sp, kPointerSize));
|
__ cmp(r0, Operand(Handle<String>(name)));
|
||||||
|
|
||||||
__ cmp(r2, Operand(Handle<String>(name)));
|
|
||||||
__ b(ne, &miss);
|
__ b(ne, &miss);
|
||||||
|
|
||||||
Failure* failure = Failure::InternalError();
|
Failure* failure = Failure::InternalError();
|
||||||
bool success = GenerateLoadCallback(receiver, holder, r0, r2, r3, r1,
|
__ ldr(r1, MemOperand(sp, kPointerSize)); // Receiver.
|
||||||
|
bool success = GenerateLoadCallback(receiver, holder, r1, r0, r2, r3,
|
||||||
callback, name, &miss, &failure);
|
callback, name, &miss, &failure);
|
||||||
if (!success) return failure;
|
if (!success) return failure;
|
||||||
|
|
||||||
@ -1878,19 +1878,18 @@ Object* KeyedLoadStubCompiler::CompileLoadConstant(String* name,
|
|||||||
Object* value) {
|
Object* value) {
|
||||||
// ----------- S t a t e -------------
|
// ----------- S t a t e -------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
Label miss;
|
Label miss;
|
||||||
|
|
||||||
// Check the key is the cached one
|
// Check the key is the cached one.
|
||||||
__ ldr(r2, MemOperand(sp, 0));
|
__ cmp(r0, Operand(Handle<String>(name)));
|
||||||
__ ldr(r0, MemOperand(sp, kPointerSize));
|
|
||||||
|
|
||||||
__ cmp(r2, Operand(Handle<String>(name)));
|
|
||||||
__ b(ne, &miss);
|
__ b(ne, &miss);
|
||||||
|
|
||||||
GenerateLoadConstant(receiver, holder, r0, r3, r1, value, name, &miss);
|
__ ldr(r1, MemOperand(sp, kPointerSize)); // Receiver.
|
||||||
|
GenerateLoadConstant(receiver, holder, r1, r2, r3, value, name, &miss);
|
||||||
__ bind(&miss);
|
__ bind(&miss);
|
||||||
GenerateLoadMiss(masm(), Code::KEYED_LOAD_IC);
|
GenerateLoadMiss(masm(), Code::KEYED_LOAD_IC);
|
||||||
|
|
||||||
@ -1904,27 +1903,26 @@ Object* KeyedLoadStubCompiler::CompileLoadInterceptor(JSObject* receiver,
|
|||||||
String* name) {
|
String* name) {
|
||||||
// ----------- S t a t e -------------
|
// ----------- S t a t e -------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
Label miss;
|
Label miss;
|
||||||
|
|
||||||
// Check the key is the cached one
|
// Check the key is the cached one.
|
||||||
__ ldr(r2, MemOperand(sp, 0));
|
__ cmp(r0, Operand(Handle<String>(name)));
|
||||||
__ ldr(r0, MemOperand(sp, kPointerSize));
|
|
||||||
|
|
||||||
__ cmp(r2, Operand(Handle<String>(name)));
|
|
||||||
__ b(ne, &miss);
|
__ b(ne, &miss);
|
||||||
|
|
||||||
LookupResult lookup;
|
LookupResult lookup;
|
||||||
LookupPostInterceptor(holder, name, &lookup);
|
LookupPostInterceptor(holder, name, &lookup);
|
||||||
|
__ ldr(r1, MemOperand(sp, kPointerSize)); // Receiver.
|
||||||
GenerateLoadInterceptor(receiver,
|
GenerateLoadInterceptor(receiver,
|
||||||
holder,
|
holder,
|
||||||
&lookup,
|
&lookup,
|
||||||
|
r1,
|
||||||
r0,
|
r0,
|
||||||
r2,
|
r2,
|
||||||
r3,
|
r3,
|
||||||
r1,
|
|
||||||
name,
|
name,
|
||||||
&miss);
|
&miss);
|
||||||
__ bind(&miss);
|
__ bind(&miss);
|
||||||
@ -1937,19 +1935,18 @@ Object* KeyedLoadStubCompiler::CompileLoadInterceptor(JSObject* receiver,
|
|||||||
Object* KeyedLoadStubCompiler::CompileLoadArrayLength(String* name) {
|
Object* KeyedLoadStubCompiler::CompileLoadArrayLength(String* name) {
|
||||||
// ----------- S t a t e -------------
|
// ----------- S t a t e -------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
Label miss;
|
Label miss;
|
||||||
|
|
||||||
// Check the key is the cached one
|
// Check the key is the cached one.
|
||||||
__ ldr(r2, MemOperand(sp, 0));
|
__ cmp(r0, Operand(Handle<String>(name)));
|
||||||
__ ldr(r0, MemOperand(sp, kPointerSize));
|
|
||||||
|
|
||||||
__ cmp(r2, Operand(Handle<String>(name)));
|
|
||||||
__ b(ne, &miss);
|
__ b(ne, &miss);
|
||||||
|
|
||||||
GenerateLoadArrayLength(masm(), r0, r3, &miss);
|
__ ldr(r1, MemOperand(sp, kPointerSize)); // Receiver.
|
||||||
|
GenerateLoadArrayLength(masm(), r1, r2, &miss);
|
||||||
__ bind(&miss);
|
__ bind(&miss);
|
||||||
GenerateLoadMiss(masm(), Code::KEYED_LOAD_IC);
|
GenerateLoadMiss(masm(), Code::KEYED_LOAD_IC);
|
||||||
|
|
||||||
@ -1960,19 +1957,19 @@ Object* KeyedLoadStubCompiler::CompileLoadArrayLength(String* name) {
|
|||||||
Object* KeyedLoadStubCompiler::CompileLoadStringLength(String* name) {
|
Object* KeyedLoadStubCompiler::CompileLoadStringLength(String* name) {
|
||||||
// ----------- S t a t e -------------
|
// ----------- S t a t e -------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
Label miss;
|
Label miss;
|
||||||
__ IncrementCounter(&Counters::keyed_load_string_length, 1, r1, r3);
|
__ IncrementCounter(&Counters::keyed_load_string_length, 1, r1, r3);
|
||||||
|
|
||||||
__ ldr(r2, MemOperand(sp));
|
// Check the key is the cached one.
|
||||||
__ ldr(r0, MemOperand(sp, kPointerSize)); // receiver
|
__ cmp(r0, Operand(Handle<String>(name)));
|
||||||
|
|
||||||
__ cmp(r2, Operand(Handle<String>(name)));
|
|
||||||
__ b(ne, &miss);
|
__ b(ne, &miss);
|
||||||
|
|
||||||
GenerateLoadStringLength(masm(), r0, r1, r3, &miss);
|
__ ldr(r1, MemOperand(sp, kPointerSize)); // Receiver.
|
||||||
|
GenerateLoadStringLength(masm(), r1, r2, r3, &miss);
|
||||||
__ bind(&miss);
|
__ bind(&miss);
|
||||||
__ DecrementCounter(&Counters::keyed_load_string_length, 1, r1, r3);
|
__ DecrementCounter(&Counters::keyed_load_string_length, 1, r1, r3);
|
||||||
|
|
||||||
@ -1986,6 +1983,7 @@ Object* KeyedLoadStubCompiler::CompileLoadStringLength(String* name) {
|
|||||||
Object* KeyedLoadStubCompiler::CompileLoadFunctionPrototype(String* name) {
|
Object* KeyedLoadStubCompiler::CompileLoadFunctionPrototype(String* name) {
|
||||||
// ----------- S t a t e -------------
|
// ----------- S t a t e -------------
|
||||||
// -- lr : return address
|
// -- lr : return address
|
||||||
|
// -- r0 : key
|
||||||
// -- sp[0] : key
|
// -- sp[0] : key
|
||||||
// -- sp[4] : receiver
|
// -- sp[4] : receiver
|
||||||
// -----------------------------------
|
// -----------------------------------
|
||||||
|
@ -321,6 +321,7 @@ void VirtualFrame::CallStoreIC(Handle<String> name, bool is_contextual) {
|
|||||||
|
|
||||||
void VirtualFrame::CallKeyedLoadIC() {
|
void VirtualFrame::CallKeyedLoadIC() {
|
||||||
Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize));
|
Handle<Code> ic(Builtins::builtin(Builtins::KeyedLoadIC_Initialize));
|
||||||
|
SpillAllButCopyTOSToR0();
|
||||||
CallCodeObject(ic, RelocInfo::CODE_TARGET, 0);
|
CallCodeObject(ic, RelocInfo::CODE_TARGET, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user