OLD | NEW |
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #ifndef VM_ASSEMBLER_MIPS_H_ | 5 #ifndef VM_ASSEMBLER_MIPS_H_ |
6 #define VM_ASSEMBLER_MIPS_H_ | 6 #define VM_ASSEMBLER_MIPS_H_ |
7 | 7 |
8 #ifndef VM_ASSEMBLER_H_ | 8 #ifndef VM_ASSEMBLER_H_ |
9 #error Do not include assembler_mips.h directly; use assembler.h instead. | 9 #error Do not include assembler_mips.h directly; use assembler.h instead. |
10 #endif | 10 #endif |
(...skipping 144 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
155 int CodeSize() const { return buffer_.Size(); } | 155 int CodeSize() const { return buffer_.Size(); } |
156 int prologue_offset() const { return -1; } | 156 int prologue_offset() const { return -1; } |
157 const ZoneGrowableArray<int>& GetPointerOffsets() const { | 157 const ZoneGrowableArray<int>& GetPointerOffsets() const { |
158 return buffer_.pointer_offsets(); | 158 return buffer_.pointer_offsets(); |
159 } | 159 } |
160 const GrowableObjectArray& object_pool() const { return object_pool_; } | 160 const GrowableObjectArray& object_pool() const { return object_pool_; } |
161 void FinalizeInstructions(const MemoryRegion& region) { | 161 void FinalizeInstructions(const MemoryRegion& region) { |
162 buffer_.FinalizeInstructions(region); | 162 buffer_.FinalizeInstructions(region); |
163 } | 163 } |
164 | 164 |
165 // Set up a Dart frame on entry with a frame pointer and PC information to | |
166 // enable easy access to the RawInstruction object of code corresponding | |
167 // to this frame. | |
168 void EnterDartFrame(intptr_t frame_size) { | |
169 UNIMPLEMENTED(); | |
170 } | |
171 | |
172 // Set up a stub frame so that the stack traversal code can easily identify | 165 // Set up a stub frame so that the stack traversal code can easily identify |
173 // a stub frame. | 166 // a stub frame. |
174 void EnterStubFrame() { | 167 void EnterStubFrame(); |
175 UNIMPLEMENTED(); | 168 void LeaveStubFrame(); |
176 } | |
177 | 169 |
178 // Instruction pattern from entrypoint is used in dart frame prologs | 170 // Instruction pattern from entrypoint is used in dart frame prologs |
179 // to set up the frame and save a PC which can be used to figure out the | 171 // to set up the frame and save a PC which can be used to figure out the |
180 // RawInstruction object corresponding to the code running in the frame. | 172 // RawInstruction object corresponding to the code running in the frame. |
181 static const intptr_t kOffsetOfSavedPCfromEntrypoint = -1; // UNIMPLEMENTED. | 173 static const intptr_t kOffsetOfSavedPCfromEntrypoint = -1; // UNIMPLEMENTED. |
182 | 174 |
183 // Inlined allocation of an instance of class 'cls', code has no runtime | 175 // Inlined allocation of an instance of class 'cls', code has no runtime |
184 // calls. Jump to 'failure' if the instance cannot be allocated here. | 176 // calls. Jump to 'failure' if the instance cannot be allocated here. |
185 // Allocated instance is returned in 'instance_reg'. | 177 // Allocated instance is returned in 'instance_reg'. |
186 // Only the tags field of the object is initialized. | 178 // Only the tags field of the object is initialized. |
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
243 ASSERT(Utils::IsUint(16, imm.value())); | 235 ASSERT(Utils::IsUint(16, imm.value())); |
244 const uint16_t imm_value = static_cast<uint16_t>(imm.value()); | 236 const uint16_t imm_value = static_cast<uint16_t>(imm.value()); |
245 EmitIType(ANDI, rs, rt, imm_value); | 237 EmitIType(ANDI, rs, rt, imm_value); |
246 } | 238 } |
247 | 239 |
248 // Unconditional branch. | 240 // Unconditional branch. |
249 void b(Label* l) { | 241 void b(Label* l) { |
250 beq(R0, R0, l); | 242 beq(R0, R0, l); |
251 } | 243 } |
252 | 244 |
| 245 void bal(Label *l) { |
| 246 ASSERT(!in_delay_slot_); |
| 247 EmitRegImmBranch(BGEZAL, R0, l); |
| 248 EmitBranchDelayNop(); |
| 249 } |
| 250 |
253 // Branch if equal. | 251 // Branch if equal. |
254 void beq(Register rs, Register rt, Label* l) { | 252 void beq(Register rs, Register rt, Label* l) { |
255 ASSERT(!in_delay_slot_); | 253 ASSERT(!in_delay_slot_); |
256 EmitBranch(BEQ, rs, rt, l); | 254 EmitBranch(BEQ, rs, rt, l); |
257 EmitBranchDelayNop(); | 255 EmitBranchDelayNop(); |
258 } | 256 } |
259 | 257 |
260 // Branch if equal, likely taken. | 258 // Branch if equal, likely taken. |
261 // Delay slot executed only when branch taken. | 259 // Delay slot executed only when branch taken. |
262 void beql(Register rs, Register rt, Label* l) { | 260 void beql(Register rs, Register rt, Label* l) { |
(...skipping 276 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
539 Array::data_offset() + 4*AddExternalLabel(label) - kHeapObjectTag; | 537 Array::data_offset() + 4*AddExternalLabel(label) - kHeapObjectTag; |
540 LoadWordFromPoolOffset(TMP, offset); | 538 LoadWordFromPoolOffset(TMP, offset); |
541 jalr(TMP); | 539 jalr(TMP); |
542 } | 540 } |
543 | 541 |
544 void BranchPatchable(const ExternalLabel* label) { | 542 void BranchPatchable(const ExternalLabel* label) { |
545 LoadImmediate(TMP, label->address()); | 543 LoadImmediate(TMP, label->address()); |
546 jr(TMP); | 544 jr(TMP); |
547 } | 545 } |
548 | 546 |
| 547 // If the signed value in rs is less than value, rd is 1, and 0 otherwise. |
| 548 void LessThanSImmediate(Register rd, Register rs, int32_t value) { |
| 549 LoadImmediate(TMP, value); |
| 550 slt(rd, rs, TMP); |
| 551 } |
| 552 |
| 553 // If the unsigned value in rs is less than value, rd is 1, and 0 otherwise. |
| 554 void LessThanUImmediate(Register rd, Register rs, uint32_t value) { |
| 555 LoadImmediate(TMP, value); |
| 556 sltu(rd, rs, TMP); |
| 557 } |
| 558 |
549 void Drop(intptr_t stack_elements) { | 559 void Drop(intptr_t stack_elements) { |
550 ASSERT(stack_elements >= 0); | 560 ASSERT(stack_elements >= 0); |
551 if (stack_elements > 0) { | 561 if (stack_elements > 0) { |
552 addiu(SP, SP, Immediate(stack_elements * kWordSize)); | 562 addiu(SP, SP, Immediate(stack_elements * kWordSize)); |
553 } | 563 } |
554 } | 564 } |
555 | 565 |
556 void LoadImmediate(Register rd, int32_t value) { | 566 void LoadImmediate(Register rd, int32_t value) { |
557 if (Utils::IsInt(16, value)) { | 567 if (Utils::IsInt(16, value)) { |
558 addiu(rd, ZR, Immediate(value)); | 568 addiu(rd, ZR, Immediate(value)); |
(...skipping 12 matching lines...) Expand all Loading... |
571 | 581 |
572 void Pop(Register rt) { | 582 void Pop(Register rt) { |
573 lw(rt, Address(SP)); | 583 lw(rt, Address(SP)); |
574 addiu(SP, SP, Immediate(kWordSize)); | 584 addiu(SP, SP, Immediate(kWordSize)); |
575 } | 585 } |
576 | 586 |
577 void Ret() { | 587 void Ret() { |
578 jr(RA); | 588 jr(RA); |
579 } | 589 } |
580 | 590 |
| 591 void SmiTag(Register reg) { |
| 592 sll(reg, reg, kSmiTagSize); |
| 593 } |
| 594 |
| 595 void SmiUntag(Register reg) { |
| 596 sra(reg, reg, kSmiTagSize); |
| 597 } |
| 598 |
581 void LoadWordFromPoolOffset(Register rd, int32_t offset); | 599 void LoadWordFromPoolOffset(Register rd, int32_t offset); |
582 void LoadObject(Register rd, const Object& object); | 600 void LoadObject(Register rd, const Object& object); |
583 void PushObject(const Object& object); | 601 void PushObject(const Object& object); |
584 | 602 |
585 // Sets register rd to zero if the object is equal to register rn, | 603 // Sets register rd to zero if the object is equal to register rn, |
586 // set to non-zero otherwise. | 604 // set to non-zero otherwise. |
587 void CompareObject(Register rd, Register rn, const Object& object); | 605 void CompareObject(Register rd, Register rn, const Object& object); |
588 | 606 |
| 607 // Set up a Dart frame on entry with a frame pointer and PC information to |
| 608 // enable easy access to the RawInstruction object of code corresponding |
| 609 // to this frame. |
| 610 void EnterDartFrame(intptr_t frame_size); |
| 611 void LeaveDartFrame(); |
| 612 |
589 private: | 613 private: |
590 AssemblerBuffer buffer_; | 614 AssemblerBuffer buffer_; |
591 GrowableObjectArray& object_pool_; // Objects and patchable jump targets. | 615 GrowableObjectArray& object_pool_; // Objects and patchable jump targets. |
592 int prologue_offset_; | 616 int prologue_offset_; |
593 | 617 |
594 bool delay_slot_available_; | 618 bool delay_slot_available_; |
595 bool in_delay_slot_; | 619 bool in_delay_slot_; |
596 | 620 |
597 int32_t AddObject(const Object& obj); | 621 int32_t AddObject(const Object& obj); |
598 int32_t AddExternalLabel(const ExternalLabel* label); | 622 int32_t AddExternalLabel(const ExternalLabel* label); |
(...skipping 107 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
706 delay_slot_available_ = true; | 730 delay_slot_available_ = true; |
707 } | 731 } |
708 | 732 |
709 DISALLOW_ALLOCATION(); | 733 DISALLOW_ALLOCATION(); |
710 DISALLOW_COPY_AND_ASSIGN(Assembler); | 734 DISALLOW_COPY_AND_ASSIGN(Assembler); |
711 }; | 735 }; |
712 | 736 |
713 } // namespace dart | 737 } // namespace dart |
714 | 738 |
715 #endif // VM_ASSEMBLER_MIPS_H_ | 739 #endif // VM_ASSEMBLER_MIPS_H_ |
OLD | NEW |