OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #if V8_TARGET_ARCH_IA32 | 5 #if V8_TARGET_ARCH_IA32 |
6 | 6 |
7 #include "src/code-stubs.h" | 7 #include "src/code-stubs.h" |
8 #include "src/api-arguments.h" | 8 #include "src/api-arguments.h" |
9 #include "src/base/bits.h" | 9 #include "src/base/bits.h" |
10 #include "src/bootstrapper.h" | 10 #include "src/bootstrapper.h" |
(...skipping 3177 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3188 // If the name comparison succeeded, we know we have a fixed array with | 3188 // If the name comparison succeeded, we know we have a fixed array with |
3189 // at least one map/handler pair. | 3189 // at least one map/handler pair. |
3190 __ mov(feedback, FieldOperand(vector, slot, times_half_pointer_size, | 3190 __ mov(feedback, FieldOperand(vector, slot, times_half_pointer_size, |
3191 FixedArray::kHeaderSize + kPointerSize)); | 3191 FixedArray::kHeaderSize + kPointerSize)); |
3192 HandleArrayCases(masm, receiver, key, vector, slot, feedback, false, &miss); | 3192 HandleArrayCases(masm, receiver, key, vector, slot, feedback, false, &miss); |
3193 | 3193 |
3194 __ bind(&miss); | 3194 __ bind(&miss); |
3195 KeyedLoadIC::GenerateMiss(masm); | 3195 KeyedLoadIC::GenerateMiss(masm); |
3196 } | 3196 } |
3197 | 3197 |
3198 void StoreICTrampolineStub::Generate(MacroAssembler* masm) { | |
3199 __ EmitLoadTypeFeedbackVector(StoreWithVectorDescriptor::VectorRegister()); | |
3200 StoreICStub stub(isolate(), state()); | |
3201 stub.GenerateForTrampoline(masm); | |
3202 } | |
3203 | |
3204 void KeyedStoreICTrampolineStub::Generate(MacroAssembler* masm) { | 3198 void KeyedStoreICTrampolineStub::Generate(MacroAssembler* masm) { |
3205 __ EmitLoadTypeFeedbackVector(StoreWithVectorDescriptor::VectorRegister()); | 3199 __ EmitLoadTypeFeedbackVector(StoreWithVectorDescriptor::VectorRegister()); |
3206 KeyedStoreICStub stub(isolate(), state()); | 3200 KeyedStoreICStub stub(isolate(), state()); |
3207 stub.GenerateForTrampoline(masm); | 3201 stub.GenerateForTrampoline(masm); |
3208 } | 3202 } |
3209 | 3203 |
3210 void StoreICStub::Generate(MacroAssembler* masm) { GenerateImpl(masm, false); } | |
3211 | |
3212 void StoreICStub::GenerateForTrampoline(MacroAssembler* masm) { | |
3213 GenerateImpl(masm, true); | |
3214 } | |
3215 | |
3216 | |
3217 // value is on the stack already. | 3204 // value is on the stack already. |
3218 static void HandlePolymorphicStoreCase(MacroAssembler* masm, Register receiver, | 3205 static void HandlePolymorphicStoreCase(MacroAssembler* masm, Register receiver, |
3219 Register key, Register vector, | 3206 Register key, Register vector, |
3220 Register slot, Register feedback, | 3207 Register slot, Register feedback, |
3221 bool is_polymorphic, Label* miss) { | 3208 bool is_polymorphic, Label* miss) { |
3222 // feedback initially contains the feedback array | 3209 // feedback initially contains the feedback array |
3223 Label next, next_loop, prepare_next; | 3210 Label next, next_loop, prepare_next; |
3224 Label load_smi_map, compare_map; | 3211 Label load_smi_map, compare_map; |
3225 Label start_polymorphic; | 3212 Label start_polymorphic; |
3226 Label pop_and_miss; | 3213 Label pop_and_miss; |
(...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3323 __ bind(&compare_smi_map); | 3310 __ bind(&compare_smi_map); |
3324 __ CompareRoot(ic_map, Heap::kHeapNumberMapRootIndex); | 3311 __ CompareRoot(ic_map, Heap::kHeapNumberMapRootIndex); |
3325 __ j(not_equal, miss); | 3312 __ j(not_equal, miss); |
3326 __ mov(weak_cell, FieldOperand(vector, slot, times_half_pointer_size, | 3313 __ mov(weak_cell, FieldOperand(vector, slot, times_half_pointer_size, |
3327 FixedArray::kHeaderSize + kPointerSize)); | 3314 FixedArray::kHeaderSize + kPointerSize)); |
3328 __ lea(weak_cell, FieldOperand(weak_cell, Code::kHeaderSize)); | 3315 __ lea(weak_cell, FieldOperand(weak_cell, Code::kHeaderSize)); |
3329 // jump to the handler. | 3316 // jump to the handler. |
3330 __ jmp(weak_cell); | 3317 __ jmp(weak_cell); |
3331 } | 3318 } |
3332 | 3319 |
3333 void StoreICStub::GenerateImpl(MacroAssembler* masm, bool in_frame) { | |
3334 Register receiver = StoreWithVectorDescriptor::ReceiverRegister(); // edx | |
3335 Register key = StoreWithVectorDescriptor::NameRegister(); // ecx | |
3336 Register value = StoreWithVectorDescriptor::ValueRegister(); // eax | |
3337 Register vector = StoreWithVectorDescriptor::VectorRegister(); // ebx | |
3338 Register slot = StoreWithVectorDescriptor::SlotRegister(); // edi | |
3339 Label miss; | |
3340 | |
3341 if (StoreWithVectorDescriptor::kPassLastArgsOnStack) { | |
3342 // Current stack layout: | |
3343 // - esp[8] -- value | |
3344 // - esp[4] -- slot | |
3345 // - esp[0] -- return address | |
3346 STATIC_ASSERT(StoreDescriptor::kStackArgumentsCount == 2); | |
3347 STATIC_ASSERT(StoreWithVectorDescriptor::kStackArgumentsCount == 3); | |
3348 if (in_frame) { | |
3349 __ RecordComment("[ StoreDescriptor -> StoreWithVectorDescriptor"); | |
3350 // If the vector is not on the stack, then insert the vector beneath | |
3351 // return address in order to prepare for calling handler with | |
3352 // StoreWithVector calling convention. | |
3353 __ push(Operand(esp, 0)); | |
3354 __ mov(Operand(esp, 4), StoreWithVectorDescriptor::VectorRegister()); | |
3355 __ RecordComment("]"); | |
3356 } else { | |
3357 __ mov(vector, Operand(esp, 1 * kPointerSize)); | |
3358 } | |
3359 __ mov(slot, Operand(esp, 2 * kPointerSize)); | |
3360 } | |
3361 | |
3362 Register scratch = value; | |
3363 __ mov(scratch, FieldOperand(vector, slot, times_half_pointer_size, | |
3364 FixedArray::kHeaderSize)); | |
3365 | |
3366 // Is it a weak cell? | |
3367 Label try_array; | |
3368 Label not_array, smi_key, key_okay; | |
3369 __ CompareRoot(FieldOperand(scratch, 0), Heap::kWeakCellMapRootIndex); | |
3370 __ j(not_equal, &try_array); | |
3371 HandleMonomorphicStoreCase(masm, receiver, key, vector, slot, scratch, &miss); | |
3372 | |
3373 // Is it a fixed array? | |
3374 __ bind(&try_array); | |
3375 __ CompareRoot(FieldOperand(scratch, 0), Heap::kFixedArrayMapRootIndex); | |
3376 __ j(not_equal, ¬_array); | |
3377 HandlePolymorphicStoreCase(masm, receiver, key, vector, slot, scratch, true, | |
3378 &miss); | |
3379 | |
3380 __ bind(¬_array); | |
3381 __ CompareRoot(scratch, Heap::kmegamorphic_symbolRootIndex); | |
3382 __ j(not_equal, &miss); | |
3383 | |
3384 masm->isolate()->store_stub_cache()->GenerateProbe(masm, receiver, key, slot, | |
3385 no_reg); | |
3386 __ bind(&miss); | |
3387 StoreIC::GenerateMiss(masm); | |
3388 } | |
3389 | |
3390 void KeyedStoreICStub::Generate(MacroAssembler* masm) { | 3320 void KeyedStoreICStub::Generate(MacroAssembler* masm) { |
3391 GenerateImpl(masm, false); | 3321 GenerateImpl(masm, false); |
3392 } | 3322 } |
3393 | 3323 |
3394 void KeyedStoreICStub::GenerateForTrampoline(MacroAssembler* masm) { | 3324 void KeyedStoreICStub::GenerateForTrampoline(MacroAssembler* masm) { |
3395 GenerateImpl(masm, true); | 3325 GenerateImpl(masm, true); |
3396 } | 3326 } |
3397 | 3327 |
3398 | 3328 |
3399 static void HandlePolymorphicKeyedStoreCase(MacroAssembler* masm, | 3329 static void HandlePolymorphicKeyedStoreCase(MacroAssembler* masm, |
(...skipping 1751 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5151 kStackUnwindSpace, nullptr, return_value_operand, | 5081 kStackUnwindSpace, nullptr, return_value_operand, |
5152 NULL); | 5082 NULL); |
5153 } | 5083 } |
5154 | 5084 |
5155 #undef __ | 5085 #undef __ |
5156 | 5086 |
5157 } // namespace internal | 5087 } // namespace internal |
5158 } // namespace v8 | 5088 } // namespace v8 |
5159 | 5089 |
5160 #endif // V8_TARGET_ARCH_IA32 | 5090 #endif // V8_TARGET_ARCH_IA32 |
OLD | NEW |