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 | 5 |
6 #include "src/v8.h" | 6 #include "src/v8.h" |
7 | 7 |
8 #if V8_TARGET_ARCH_MIPS | 8 #if V8_TARGET_ARCH_MIPS |
9 | 9 |
10 #include "src/codegen.h" | 10 #include "src/codegen.h" |
(...skipping 278 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
289 } | 289 } |
290 | 290 |
291 | 291 |
292 // A register that isn't one of the parameters to the load ic. | 292 // A register that isn't one of the parameters to the load ic. |
293 static const Register LoadIC_TempRegister() { return a3; } | 293 static const Register LoadIC_TempRegister() { return a3; } |
294 | 294 |
295 | 295 |
296 static void LoadIC_PushArgs(MacroAssembler* masm) { | 296 static void LoadIC_PushArgs(MacroAssembler* masm) { |
297 Register receiver = LoadDescriptor::ReceiverRegister(); | 297 Register receiver = LoadDescriptor::ReceiverRegister(); |
298 Register name = LoadDescriptor::NameRegister(); | 298 Register name = LoadDescriptor::NameRegister(); |
299 if (FLAG_vector_ics) { | 299 Register slot = VectorLoadICDescriptor::SlotRegister(); |
300 Register slot = VectorLoadICDescriptor::SlotRegister(); | 300 Register vector = VectorLoadICDescriptor::VectorRegister(); |
301 Register vector = VectorLoadICDescriptor::VectorRegister(); | |
302 | 301 |
303 __ Push(receiver, name, slot, vector); | 302 __ Push(receiver, name, slot, vector); |
304 } else { | |
305 __ Push(receiver, name); | |
306 } | |
307 } | 303 } |
308 | 304 |
309 | 305 |
310 void LoadIC::GenerateMiss(MacroAssembler* masm) { | 306 void LoadIC::GenerateMiss(MacroAssembler* masm) { |
311 // The return address is in ra. | 307 // The return address is in ra. |
312 Isolate* isolate = masm->isolate(); | 308 Isolate* isolate = masm->isolate(); |
313 | 309 |
314 DCHECK(!FLAG_vector_ics || | 310 DCHECK(!AreAliased(t0, t1, VectorLoadICDescriptor::SlotRegister(), |
315 !AreAliased(t0, t1, VectorLoadICDescriptor::SlotRegister(), | |
316 VectorLoadICDescriptor::VectorRegister())); | 311 VectorLoadICDescriptor::VectorRegister())); |
317 __ IncrementCounter(isolate->counters()->load_miss(), 1, t0, t1); | 312 __ IncrementCounter(isolate->counters()->load_miss(), 1, t0, t1); |
318 | 313 |
319 LoadIC_PushArgs(masm); | 314 LoadIC_PushArgs(masm); |
320 | 315 |
321 // Perform tail call to the entry. | 316 // Perform tail call to the entry. |
322 ExternalReference ref = ExternalReference(IC_Utility(kLoadIC_Miss), isolate); | 317 ExternalReference ref = ExternalReference(IC_Utility(kLoadIC_Miss), isolate); |
323 int arg_count = FLAG_vector_ics ? 4 : 2; | 318 int arg_count = 4; |
324 __ TailCallExternalReference(ref, arg_count, 1); | 319 __ TailCallExternalReference(ref, arg_count, 1); |
325 } | 320 } |
326 | 321 |
327 | 322 |
328 void LoadIC::GenerateRuntimeGetProperty(MacroAssembler* masm) { | 323 void LoadIC::GenerateRuntimeGetProperty(MacroAssembler* masm) { |
329 // The return address is in ra. | 324 // The return address is in ra. |
330 | 325 |
331 __ mov(LoadIC_TempRegister(), LoadDescriptor::ReceiverRegister()); | 326 __ mov(LoadIC_TempRegister(), LoadDescriptor::ReceiverRegister()); |
332 __ Push(LoadIC_TempRegister(), LoadDescriptor::NameRegister()); | 327 __ Push(LoadIC_TempRegister(), LoadDescriptor::NameRegister()); |
333 | 328 |
(...skipping 109 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
443 __ mov(v0, a0); // (In delay slot) return the value stored in v0. | 438 __ mov(v0, a0); // (In delay slot) return the value stored in v0. |
444 __ bind(&slow); | 439 __ bind(&slow); |
445 GenerateMiss(masm); | 440 GenerateMiss(masm); |
446 } | 441 } |
447 | 442 |
448 | 443 |
449 void KeyedLoadIC::GenerateMiss(MacroAssembler* masm) { | 444 void KeyedLoadIC::GenerateMiss(MacroAssembler* masm) { |
450 // The return address is in ra. | 445 // The return address is in ra. |
451 Isolate* isolate = masm->isolate(); | 446 Isolate* isolate = masm->isolate(); |
452 | 447 |
453 DCHECK(!FLAG_vector_ics || | 448 DCHECK(!AreAliased(t0, t1, VectorLoadICDescriptor::SlotRegister(), |
454 !AreAliased(t0, t1, VectorLoadICDescriptor::SlotRegister(), | |
455 VectorLoadICDescriptor::VectorRegister())); | 449 VectorLoadICDescriptor::VectorRegister())); |
456 __ IncrementCounter(isolate->counters()->keyed_load_miss(), 1, t0, t1); | 450 __ IncrementCounter(isolate->counters()->keyed_load_miss(), 1, t0, t1); |
457 | 451 |
458 LoadIC_PushArgs(masm); | 452 LoadIC_PushArgs(masm); |
459 | 453 |
460 // Perform tail call to the entry. | 454 // Perform tail call to the entry. |
461 ExternalReference ref = | 455 ExternalReference ref = |
462 ExternalReference(IC_Utility(kKeyedLoadIC_Miss), isolate); | 456 ExternalReference(IC_Utility(kKeyedLoadIC_Miss), isolate); |
463 | 457 |
464 int arg_count = FLAG_vector_ics ? 4 : 2; | 458 int arg_count = 4; |
465 __ TailCallExternalReference(ref, arg_count, 1); | 459 __ TailCallExternalReference(ref, arg_count, 1); |
466 } | 460 } |
467 | 461 |
468 | 462 |
469 void KeyedLoadIC::GenerateRuntimeGetProperty(MacroAssembler* masm) { | 463 void KeyedLoadIC::GenerateRuntimeGetProperty(MacroAssembler* masm) { |
470 // The return address is in ra. | 464 // The return address is in ra. |
471 | 465 |
472 __ Push(LoadDescriptor::ReceiverRegister(), LoadDescriptor::NameRegister()); | 466 __ Push(LoadDescriptor::ReceiverRegister(), LoadDescriptor::NameRegister()); |
473 | 467 |
474 __ TailCallRuntime(Runtime::kKeyedGetProperty, 2, 1); | 468 __ TailCallRuntime(Runtime::kKeyedGetProperty, 2, 1); |
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
529 Map::kHasNamedInterceptor, &slow); | 523 Map::kHasNamedInterceptor, &slow); |
530 | 524 |
531 | 525 |
532 // If the receiver is a fast-case object, check the stub cache. Otherwise | 526 // If the receiver is a fast-case object, check the stub cache. Otherwise |
533 // probe the dictionary. | 527 // probe the dictionary. |
534 __ lw(a3, FieldMemOperand(receiver, JSObject::kPropertiesOffset)); | 528 __ lw(a3, FieldMemOperand(receiver, JSObject::kPropertiesOffset)); |
535 __ lw(t0, FieldMemOperand(a3, HeapObject::kMapOffset)); | 529 __ lw(t0, FieldMemOperand(a3, HeapObject::kMapOffset)); |
536 __ LoadRoot(at, Heap::kHashTableMapRootIndex); | 530 __ LoadRoot(at, Heap::kHashTableMapRootIndex); |
537 __ Branch(&probe_dictionary, eq, t0, Operand(at)); | 531 __ Branch(&probe_dictionary, eq, t0, Operand(at)); |
538 | 532 |
539 if (FLAG_vector_ics) { | 533 // The handlers in the stub cache expect a vector and slot. Since we won't |
540 // When vector ics are in use, the handlers in the stub cache expect a | 534 // change the IC from any downstream misses, a dummy vector can be used. |
541 // vector and slot. Since we won't change the IC from any downstream | 535 Register vector = VectorLoadICDescriptor::VectorRegister(); |
542 // misses, a dummy vector can be used. | 536 Register slot = VectorLoadICDescriptor::SlotRegister(); |
543 Register vector = VectorLoadICDescriptor::VectorRegister(); | 537 DCHECK(!AreAliased(vector, slot, t0, t1, t2, t5)); |
544 Register slot = VectorLoadICDescriptor::SlotRegister(); | 538 Handle<TypeFeedbackVector> dummy_vector = Handle<TypeFeedbackVector>::cast( |
545 DCHECK(!AreAliased(vector, slot, t0, t1, t2, t5)); | 539 masm->isolate()->factory()->keyed_load_dummy_vector()); |
546 Handle<TypeFeedbackVector> dummy_vector = Handle<TypeFeedbackVector>::cast( | 540 int int_slot = dummy_vector->GetIndex(FeedbackVectorICSlot(0)); |
547 masm->isolate()->factory()->keyed_load_dummy_vector()); | 541 __ LoadRoot(vector, Heap::kKeyedLoadDummyVectorRootIndex); |
548 int int_slot = dummy_vector->GetIndex(FeedbackVectorICSlot(0)); | 542 __ li(slot, Operand(Smi::FromInt(int_slot))); |
549 __ LoadRoot(vector, Heap::kKeyedLoadDummyVectorRootIndex); | |
550 __ li(slot, Operand(Smi::FromInt(int_slot))); | |
551 } | |
552 | 543 |
553 Code::Flags flags = Code::RemoveTypeAndHolderFromFlags( | 544 Code::Flags flags = Code::RemoveTypeAndHolderFromFlags( |
554 Code::ComputeHandlerFlags(Code::LOAD_IC)); | 545 Code::ComputeHandlerFlags(Code::LOAD_IC)); |
555 masm->isolate()->stub_cache()->GenerateProbe( | 546 masm->isolate()->stub_cache()->GenerateProbe( |
556 masm, Code::LOAD_IC, flags, false, receiver, key, t0, t1, t2, t5); | 547 masm, Code::LOAD_IC, flags, false, receiver, key, t0, t1, t2, t5); |
557 // Cache miss. | 548 // Cache miss. |
558 GenerateMiss(masm); | 549 GenerateMiss(masm); |
559 | 550 |
560 // Do a quick inline probe of the receiver's dictionary, if it | 551 // Do a quick inline probe of the receiver's dictionary, if it |
561 // exists. | 552 // exists. |
(...skipping 425 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
987 patcher.ChangeBranchCondition(ne); | 978 patcher.ChangeBranchCondition(ne); |
988 } else { | 979 } else { |
989 DCHECK(Assembler::IsBne(branch_instr)); | 980 DCHECK(Assembler::IsBne(branch_instr)); |
990 patcher.ChangeBranchCondition(eq); | 981 patcher.ChangeBranchCondition(eq); |
991 } | 982 } |
992 } | 983 } |
993 } | 984 } |
994 } // namespace v8::internal | 985 } // namespace v8::internal |
995 | 986 |
996 #endif // V8_TARGET_ARCH_MIPS | 987 #endif // V8_TARGET_ARCH_MIPS |
OLD | NEW |