Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(18)

Side by Side Diff: runtime/vm/assembler_arm64.cc

Issue 593363003: Expands the use of Immediate and Operand wrappers. (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 6 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2014, 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 #include "vm/globals.h" 5 #include "vm/globals.h"
6 #if defined(TARGET_ARCH_ARM64) 6 #if defined(TARGET_ARCH_ARM64)
7 7
8 #include "vm/assembler.h" 8 #include "vm/assembler.h"
9 #include "vm/cpu.h" 9 #include "vm/cpu.h"
10 #include "vm/longjump.h" 10 #include "vm/longjump.h"
(...skipping 383 matching lines...) Expand 10 before | Expand all | Expand 10 after
394 ldr(dst, Address(pp, offset)); 394 ldr(dst, Address(pp, offset));
395 } else if (Operand::CanHold(upper20, kXRegSizeInBits, &op) == 395 } else if (Operand::CanHold(upper20, kXRegSizeInBits, &op) ==
396 Operand::Immediate) { 396 Operand::Immediate) {
397 const uint32_t lower12 = offset & 0x00000fff; 397 const uint32_t lower12 = offset & 0x00000fff;
398 ASSERT(Address::CanHoldOffset(lower12)); 398 ASSERT(Address::CanHoldOffset(lower12));
399 add(dst, pp, op); 399 add(dst, pp, op);
400 ldr(dst, Address(dst, lower12)); 400 ldr(dst, Address(dst, lower12));
401 } else { 401 } else {
402 const uint16_t offset_low = Utils::Low16Bits(offset); 402 const uint16_t offset_low = Utils::Low16Bits(offset);
403 const uint16_t offset_high = Utils::High16Bits(offset); 403 const uint16_t offset_high = Utils::High16Bits(offset);
404 movz(dst, offset_low, 0); 404 movz(dst, Immediate(offset_low), 0);
405 if (offset_high != 0) { 405 if (offset_high != 0) {
406 movk(dst, offset_high, 1); 406 movk(dst, Immediate(offset_high), 1);
407 } 407 }
408 ldr(dst, Address(pp, dst)); 408 ldr(dst, Address(pp, dst));
409 } 409 }
410 } 410 }
411 411
412 412
413 void Assembler::LoadWordFromPoolOffsetFixed(Register dst, Register pp, 413 void Assembler::LoadWordFromPoolOffsetFixed(Register dst, Register pp,
414 uint32_t offset) { 414 uint32_t offset) {
415 ASSERT(dst != pp); 415 ASSERT(dst != pp);
416 Operand op; 416 Operand op;
(...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after
583 void Assembler::LoadDecodableImmediate(Register reg, int64_t imm, Register pp) { 583 void Assembler::LoadDecodableImmediate(Register reg, int64_t imm, Register pp) {
584 if ((pp != kNoPP) && 584 if ((pp != kNoPP) &&
585 (Isolate::Current() != Dart::vm_isolate()) && 585 (Isolate::Current() != Dart::vm_isolate()) &&
586 allow_constant_pool()) { 586 allow_constant_pool()) {
587 int64_t val_smi_tag = imm & kSmiTagMask; 587 int64_t val_smi_tag = imm & kSmiTagMask;
588 imm &= ~kSmiTagMask; // Mask off the tag bits. 588 imm &= ~kSmiTagMask; // Mask off the tag bits.
589 const int32_t offset = Array::element_offset(FindImmediate(imm)); 589 const int32_t offset = Array::element_offset(FindImmediate(imm));
590 LoadWordFromPoolOffset(reg, pp, offset); 590 LoadWordFromPoolOffset(reg, pp, offset);
591 if (val_smi_tag != 0) { 591 if (val_smi_tag != 0) {
592 // Add back the tag bits. 592 // Add back the tag bits.
593 orri(reg, reg, val_smi_tag); 593 orri(reg, reg, Immediate(val_smi_tag));
594 } 594 }
595 } else { 595 } else {
596 // TODO(zra): Since this sequence only needs to be decodable, it can be 596 // TODO(zra): Since this sequence only needs to be decodable, it can be
597 // of variable length. 597 // of variable length.
598 LoadImmediateFixed(reg, imm); 598 LoadImmediateFixed(reg, imm);
599 } 599 }
600 } 600 }
601 601
602 602
603 void Assembler::LoadImmediateFixed(Register reg, int64_t imm) { 603 void Assembler::LoadImmediateFixed(Register reg, int64_t imm) {
604 const uint32_t w0 = Utils::Low32Bits(imm); 604 const uint32_t w0 = Utils::Low32Bits(imm);
605 const uint32_t w1 = Utils::High32Bits(imm); 605 const uint32_t w1 = Utils::High32Bits(imm);
606 const uint16_t h0 = Utils::Low16Bits(w0); 606 const uint16_t h0 = Utils::Low16Bits(w0);
607 const uint16_t h1 = Utils::High16Bits(w0); 607 const uint16_t h1 = Utils::High16Bits(w0);
608 const uint16_t h2 = Utils::Low16Bits(w1); 608 const uint16_t h2 = Utils::Low16Bits(w1);
609 const uint16_t h3 = Utils::High16Bits(w1); 609 const uint16_t h3 = Utils::High16Bits(w1);
610 movz(reg, h0, 0); 610 movz(reg, Immediate(h0), 0);
611 movk(reg, h1, 1); 611 movk(reg, Immediate(h1), 1);
612 movk(reg, h2, 2); 612 movk(reg, Immediate(h2), 2);
613 movk(reg, h3, 3); 613 movk(reg, Immediate(h3), 3);
614 } 614 }
615 615
616 616
617 void Assembler::LoadImmediate(Register reg, int64_t imm, Register pp) { 617 void Assembler::LoadImmediate(Register reg, int64_t imm, Register pp) {
618 Comment("LoadImmediate"); 618 Comment("LoadImmediate");
619 if (CanLoadImmediateFromPool(imm, pp)) { 619 if (CanLoadImmediateFromPool(imm, pp)) {
620 // It's a 64-bit constant and we're not in the VM isolate, so load from 620 // It's a 64-bit constant and we're not in the VM isolate, so load from
621 // object pool. 621 // object pool.
622 // Save the bits that must be masked-off for the SmiTag 622 // Save the bits that must be masked-off for the SmiTag
623 int64_t val_smi_tag = imm & kSmiTagMask; 623 int64_t val_smi_tag = imm & kSmiTagMask;
624 imm &= ~kSmiTagMask; // Mask off the tag bits. 624 imm &= ~kSmiTagMask; // Mask off the tag bits.
625 const int32_t offset = Array::element_offset(FindImmediate(imm)); 625 const int32_t offset = Array::element_offset(FindImmediate(imm));
626 LoadWordFromPoolOffset(reg, pp, offset); 626 LoadWordFromPoolOffset(reg, pp, offset);
627 if (val_smi_tag != 0) { 627 if (val_smi_tag != 0) {
628 // Add back the tag bits. 628 // Add back the tag bits.
629 orri(reg, reg, val_smi_tag); 629 orri(reg, reg, Immediate(val_smi_tag));
630 } 630 }
631 } else { 631 } else {
632 // 0. Is it 0? 632 // 0. Is it 0?
633 if (imm == 0) { 633 if (imm == 0) {
634 movz(reg, 0, 0); 634 movz(reg, Immediate(0), 0);
635 return; 635 return;
636 } 636 }
637 637
638 // 1. Can we use one orri operation? 638 // 1. Can we use one orri operation?
639 Operand op; 639 Operand op;
640 Operand::OperandType ot; 640 Operand::OperandType ot;
641 ot = Operand::CanHold(imm, kXRegSizeInBits, &op); 641 ot = Operand::CanHold(imm, kXRegSizeInBits, &op);
642 if (ot == Operand::BitfieldImm) { 642 if (ot == Operand::BitfieldImm) {
643 orri(reg, ZR, imm); 643 orri(reg, ZR, Immediate(imm));
644 return; 644 return;
645 } 645 }
646 646
647 // 2. Fall back on movz, movk, movn. 647 // 2. Fall back on movz, movk, movn.
648 const uint32_t w0 = Utils::Low32Bits(imm); 648 const uint32_t w0 = Utils::Low32Bits(imm);
649 const uint32_t w1 = Utils::High32Bits(imm); 649 const uint32_t w1 = Utils::High32Bits(imm);
650 const uint16_t h0 = Utils::Low16Bits(w0); 650 const uint16_t h0 = Utils::Low16Bits(w0);
651 const uint16_t h1 = Utils::High16Bits(w0); 651 const uint16_t h1 = Utils::High16Bits(w0);
652 const uint16_t h2 = Utils::Low16Bits(w1); 652 const uint16_t h2 = Utils::Low16Bits(w1);
653 const uint16_t h3 = Utils::High16Bits(w1); 653 const uint16_t h3 = Utils::High16Bits(w1);
654 654
655 // Special case for w1 == 0xffffffff 655 // Special case for w1 == 0xffffffff
656 if (w1 == 0xffffffff) { 656 if (w1 == 0xffffffff) {
657 if (h1 == 0xffff) { 657 if (h1 == 0xffff) {
658 movn(reg, ~h0, 0); 658 movn(reg, Immediate(~h0), 0);
659 } else { 659 } else {
660 movn(reg, ~h1, 1); 660 movn(reg, Immediate(~h1), 1);
661 movk(reg, h0, 0); 661 movk(reg, Immediate(h0), 0);
662 } 662 }
663 return; 663 return;
664 } 664 }
665 665
666 // Special case for h3 == 0xffff 666 // Special case for h3 == 0xffff
667 if (h3 == 0xffff) { 667 if (h3 == 0xffff) {
668 // We know h2 != 0xffff. 668 // We know h2 != 0xffff.
669 movn(reg, ~h2, 2); 669 movn(reg, Immediate(~h2), 2);
670 if (h1 != 0xffff) { 670 if (h1 != 0xffff) {
671 movk(reg, h1, 1); 671 movk(reg, Immediate(h1), 1);
672 } 672 }
673 if (h0 != 0xffff) { 673 if (h0 != 0xffff) {
674 movk(reg, h0, 0); 674 movk(reg, Immediate(h0), 0);
675 } 675 }
676 return; 676 return;
677 } 677 }
678 678
679 bool initialized = false; 679 bool initialized = false;
680 if (h0 != 0) { 680 if (h0 != 0) {
681 movz(reg, h0, 0); 681 movz(reg, Immediate(h0), 0);
682 initialized = true; 682 initialized = true;
683 } 683 }
684 if (h1 != 0) { 684 if (h1 != 0) {
685 if (initialized) { 685 if (initialized) {
686 movk(reg, h1, 1); 686 movk(reg, Immediate(h1), 1);
687 } else { 687 } else {
688 movz(reg, h1, 1); 688 movz(reg, Immediate(h1), 1);
689 initialized = true; 689 initialized = true;
690 } 690 }
691 } 691 }
692 if (h2 != 0) { 692 if (h2 != 0) {
693 if (initialized) { 693 if (initialized) {
694 movk(reg, h2, 2); 694 movk(reg, Immediate(h2), 2);
695 } else { 695 } else {
696 movz(reg, h2, 2); 696 movz(reg, Immediate(h2), 2);
697 initialized = true; 697 initialized = true;
698 } 698 }
699 } 699 }
700 if (h3 != 0) { 700 if (h3 != 0) {
701 if (initialized) { 701 if (initialized) {
702 movk(reg, h3, 3); 702 movk(reg, Immediate(h3), 3);
703 } else { 703 } else {
704 movz(reg, h3, 3); 704 movz(reg, Immediate(h3), 3);
705 } 705 }
706 } 706 }
707 } 707 }
708 } 708 }
709 709
710 710
711 void Assembler::LoadDImmediate(VRegister vd, double immd, Register pp) { 711 void Assembler::LoadDImmediate(VRegister vd, double immd, Register pp) {
712 if (!fmovdi(vd, immd)) { 712 if (!fmovdi(vd, immd)) {
713 int64_t imm = bit_cast<int64_t, double>(immd); 713 int64_t imm = bit_cast<int64_t, double>(immd);
714 LoadImmediate(TMP, imm, pp); 714 LoadImmediate(TMP, imm, pp);
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after
775 LoadImmediate(TMP2, imm, pp); 775 LoadImmediate(TMP2, imm, pp);
776 subs(dest, rn, Operand(TMP2)); 776 subs(dest, rn, Operand(TMP2));
777 } 777 }
778 } 778 }
779 779
780 780
781 void Assembler::AndImmediate( 781 void Assembler::AndImmediate(
782 Register rd, Register rn, int64_t imm, Register pp) { 782 Register rd, Register rn, int64_t imm, Register pp) {
783 Operand imm_op; 783 Operand imm_op;
784 if (Operand::IsImmLogical(imm, kXRegSizeInBits, &imm_op)) { 784 if (Operand::IsImmLogical(imm, kXRegSizeInBits, &imm_op)) {
785 andi(rd, rn, imm); 785 andi(rd, rn, Immediate(imm));
786 } else { 786 } else {
787 LoadImmediate(TMP, imm, pp); 787 LoadImmediate(TMP, imm, pp);
788 and_(rd, rn, Operand(TMP)); 788 and_(rd, rn, Operand(TMP));
789 } 789 }
790 } 790 }
791 791
792 792
793 void Assembler::OrImmediate( 793 void Assembler::OrImmediate(
794 Register rd, Register rn, int64_t imm, Register pp) { 794 Register rd, Register rn, int64_t imm, Register pp) {
795 Operand imm_op; 795 Operand imm_op;
796 if (Operand::IsImmLogical(imm, kXRegSizeInBits, &imm_op)) { 796 if (Operand::IsImmLogical(imm, kXRegSizeInBits, &imm_op)) {
797 orri(rd, rn, imm); 797 orri(rd, rn, Immediate(imm));
798 } else { 798 } else {
799 LoadImmediate(TMP, imm, pp); 799 LoadImmediate(TMP, imm, pp);
800 orr(rd, rn, Operand(TMP)); 800 orr(rd, rn, Operand(TMP));
801 } 801 }
802 } 802 }
803 803
804 804
805 void Assembler::XorImmediate( 805 void Assembler::XorImmediate(
806 Register rd, Register rn, int64_t imm, Register pp) { 806 Register rd, Register rn, int64_t imm, Register pp) {
807 Operand imm_op; 807 Operand imm_op;
808 if (Operand::IsImmLogical(imm, kXRegSizeInBits, &imm_op)) { 808 if (Operand::IsImmLogical(imm, kXRegSizeInBits, &imm_op)) {
809 eori(rd, rn, imm); 809 eori(rd, rn, Immediate(imm));
810 } else { 810 } else {
811 LoadImmediate(TMP, imm, pp); 811 LoadImmediate(TMP, imm, pp);
812 eor(rd, rn, Operand(TMP)); 812 eor(rd, rn, Operand(TMP));
813 } 813 }
814 } 814 }
815 815
816 816
817 void Assembler::TestImmediate(Register rn, int64_t imm, Register pp) { 817 void Assembler::TestImmediate(Register rn, int64_t imm, Register pp) {
818 Operand imm_op; 818 Operand imm_op;
819 if (Operand::IsImmLogical(imm, kXRegSizeInBits, &imm_op)) { 819 if (Operand::IsImmLogical(imm, kXRegSizeInBits, &imm_op)) {
820 tsti(rn, imm); 820 tsti(rn, Immediate(imm));
821 } else { 821 } else {
822 LoadImmediate(TMP, imm, pp); 822 LoadImmediate(TMP, imm, pp);
823 tst(rn, Operand(TMP)); 823 tst(rn, Operand(TMP));
824 } 824 }
825 } 825 }
826 826
827 827
828 void Assembler::CompareImmediate(Register rn, int64_t imm, Register pp) { 828 void Assembler::CompareImmediate(Register rn, int64_t imm, Register pp) {
829 Operand op; 829 Operand op;
830 if (Operand::CanHold(imm, kXRegSizeInBits, &op) == Operand::Immediate) { 830 if (Operand::CanHold(imm, kXRegSizeInBits, &op) == Operand::Immediate) {
(...skipping 121 matching lines...) Expand 10 before | Expand all | Expand 10 after
952 Register value, 952 Register value,
953 Label* no_update) { 953 Label* no_update) {
954 COMPILE_ASSERT((kNewObjectAlignmentOffset == kWordSize) && 954 COMPILE_ASSERT((kNewObjectAlignmentOffset == kWordSize) &&
955 (kOldObjectAlignmentOffset == 0)); 955 (kOldObjectAlignmentOffset == 0));
956 956
957 // Write-barrier triggers if the value is in the new space (has bit set) and 957 // Write-barrier triggers if the value is in the new space (has bit set) and
958 // the object is in the old space (has bit cleared). 958 // the object is in the old space (has bit cleared).
959 // To check that, we compute value & ~object and skip the write barrier 959 // To check that, we compute value & ~object and skip the write barrier
960 // if the bit is not set. We can't destroy the object. 960 // if the bit is not set. We can't destroy the object.
961 bic(TMP, value, Operand(object)); 961 bic(TMP, value, Operand(object));
962 tsti(TMP, kNewObjectAlignmentOffset); 962 tsti(TMP, Immediate(kNewObjectAlignmentOffset));
963 b(no_update, EQ); 963 b(no_update, EQ);
964 } 964 }
965 965
966 966
967 // Preserves object and value registers. 967 // Preserves object and value registers.
968 void Assembler::StoreIntoObjectFilter(Register object, 968 void Assembler::StoreIntoObjectFilter(Register object,
969 Register value, 969 Register value,
970 Label* no_update) { 970 Label* no_update) {
971 // For the value we are only interested in the new/old bit and the tag bit. 971 // For the value we are only interested in the new/old bit and the tag bit.
972 // And the new bit with the tag bit. The resulting bit will be 0 for a Smi. 972 // And the new bit with the tag bit. The resulting bit will be 0 for a Smi.
973 and_(TMP, value, Operand(value, LSL, kObjectAlignmentLog2 - 1)); 973 and_(TMP, value, Operand(value, LSL, kObjectAlignmentLog2 - 1));
974 // And the result with the negated space bit of the object. 974 // And the result with the negated space bit of the object.
975 bic(TMP, TMP, Operand(object)); 975 bic(TMP, TMP, Operand(object));
976 tsti(TMP, kNewObjectAlignmentOffset); 976 tsti(TMP, Immediate(kNewObjectAlignmentOffset));
977 b(no_update, EQ); 977 b(no_update, EQ);
978 } 978 }
979 979
980 980
981 void Assembler::StoreIntoObjectOffset(Register object, 981 void Assembler::StoreIntoObjectOffset(Register object,
982 int32_t offset, 982 int32_t offset,
983 Register value, 983 Register value,
984 Register pp, 984 Register pp,
985 bool can_value_be_smi) { 985 bool can_value_be_smi) {
986 if (Address::CanHoldOffset(offset - kHeapObjectTag)) { 986 if (Address::CanHoldOffset(offset - kHeapObjectTag)) {
(...skipping 121 matching lines...) Expand 10 before | Expand all | Expand 10 after
1108 LoadClassId(TMP, object, pp); 1108 LoadClassId(TMP, object, pp);
1109 CompareImmediate(TMP, class_id, pp); 1109 CompareImmediate(TMP, class_id, pp);
1110 } 1110 }
1111 1111
1112 1112
1113 void Assembler::LoadTaggedClassIdMayBeSmi(Register result, Register object) { 1113 void Assembler::LoadTaggedClassIdMayBeSmi(Register result, Register object) {
1114 // Load up a null object. We only need it so we can use LoadClassId on it in 1114 // Load up a null object. We only need it so we can use LoadClassId on it in
1115 // the case that object is a Smi.. 1115 // the case that object is a Smi..
1116 LoadObject(TMP, Object::null_object(), PP); 1116 LoadObject(TMP, Object::null_object(), PP);
1117 // Check if the object is a Smi. 1117 // Check if the object is a Smi.
1118 tsti(object, kSmiTagMask); 1118 tsti(object, Immediate(kSmiTagMask));
1119 // If the object *is* a Smi, use the null object instead. o/w leave alone. 1119 // If the object *is* a Smi, use the null object instead. o/w leave alone.
1120 csel(TMP, TMP, object, EQ); 1120 csel(TMP, TMP, object, EQ);
1121 // Loads either the cid of the object if it isn't a Smi, or the cid of null 1121 // Loads either the cid of the object if it isn't a Smi, or the cid of null
1122 // if it is a Smi, which will be ignored. 1122 // if it is a Smi, which will be ignored.
1123 LoadClassId(result, TMP, PP); 1123 LoadClassId(result, TMP, PP);
1124 1124
1125 LoadImmediate(TMP, kSmiCid, PP); 1125 LoadImmediate(TMP, kSmiCid, PP);
1126 // If object is a Smi, move the Smi cid into result. o/w leave alone. 1126 // If object is a Smi, move the Smi cid into result. o/w leave alone.
1127 csel(result, TMP, result, EQ); 1127 csel(result, TMP, result, EQ);
1128 // Finally, tag the result. 1128 // Finally, tag the result.
1129 SmiTag(result); 1129 SmiTag(result);
1130 } 1130 }
1131 1131
1132 1132
1133 // Frame entry and exit. 1133 // Frame entry and exit.
1134 void Assembler::ReserveAlignedFrameSpace(intptr_t frame_space) { 1134 void Assembler::ReserveAlignedFrameSpace(intptr_t frame_space) {
1135 // Reserve space for arguments and align frame before entering 1135 // Reserve space for arguments and align frame before entering
1136 // the C++ world. 1136 // the C++ world.
1137 if (frame_space != 0) { 1137 if (frame_space != 0) {
1138 AddImmediate(SP, SP, -frame_space, kNoPP); 1138 AddImmediate(SP, SP, -frame_space, kNoPP);
1139 } 1139 }
1140 if (OS::ActivationFrameAlignment() > 1) { 1140 if (OS::ActivationFrameAlignment() > 1) {
1141 andi(SP, SP, ~(OS::ActivationFrameAlignment() - 1)); 1141 andi(SP, SP, Immediate(~(OS::ActivationFrameAlignment() - 1)));
1142 } 1142 }
1143 } 1143 }
1144 1144
1145 1145
1146 void Assembler::EnterFrame(intptr_t frame_size) { 1146 void Assembler::EnterFrame(intptr_t frame_size) {
1147 Push(LR); 1147 Push(LR);
1148 Push(FP); 1148 Push(FP);
1149 mov(FP, SP); 1149 mov(FP, SP);
1150 1150
1151 if (frame_size > 0) { 1151 if (frame_size > 0) {
1152 sub(SP, SP, Operand(frame_size)); 1152 sub(SP, SP, Operand(frame_size));
1153 } 1153 }
1154 } 1154 }
1155 1155
1156 1156
1157 void Assembler::LeaveFrame() { 1157 void Assembler::LeaveFrame() {
1158 mov(SP, FP); 1158 mov(SP, FP);
1159 Pop(FP); 1159 Pop(FP);
1160 Pop(LR); 1160 Pop(LR);
1161 } 1161 }
1162 1162
1163 1163
1164 void Assembler::EnterDartFrame(intptr_t frame_size) { 1164 void Assembler::EnterDartFrame(intptr_t frame_size) {
1165 // Setup the frame. 1165 // Setup the frame.
1166 adr(TMP, -CodeSize()); // TMP gets PC marker. 1166 adr(TMP, Immediate(-CodeSize())); // TMP gets PC marker.
1167 EnterFrame(0); 1167 EnterFrame(0);
1168 Push(TMP); // Save PC Marker. 1168 Push(TMP); // Save PC Marker.
1169 TagAndPushPP(); // Save PP. 1169 TagAndPushPP(); // Save PP.
1170 1170
1171 // Load the pool pointer. 1171 // Load the pool pointer.
1172 LoadPoolPointer(PP); 1172 LoadPoolPointer(PP);
1173 1173
1174 // Reserve space. 1174 // Reserve space.
1175 if (frame_size > 0) { 1175 if (frame_size > 0) {
1176 AddImmediate(SP, SP, -frame_size, PP); 1176 AddImmediate(SP, SP, -frame_size, PP);
1177 } 1177 }
1178 } 1178 }
1179 1179
1180 1180
1181 void Assembler::EnterDartFrameWithInfo(intptr_t frame_size, Register new_pp) { 1181 void Assembler::EnterDartFrameWithInfo(intptr_t frame_size, Register new_pp) {
1182 // Setup the frame. 1182 // Setup the frame.
1183 adr(TMP, -CodeSize()); // TMP gets PC marker. 1183 adr(TMP, Immediate(-CodeSize())); // TMP gets PC marker.
1184 EnterFrame(0); 1184 EnterFrame(0);
1185 Push(TMP); // Save PC Marker. 1185 Push(TMP); // Save PC Marker.
1186 TagAndPushPP(); // Save PP. 1186 TagAndPushPP(); // Save PP.
1187 1187
1188 // Load the pool pointer. 1188 // Load the pool pointer.
1189 if (new_pp == kNoPP) { 1189 if (new_pp == kNoPP) {
1190 LoadPoolPointer(PP); 1190 LoadPoolPointer(PP);
1191 } else { 1191 } else {
1192 mov(PP, new_pp); 1192 mov(PP, new_pp);
1193 } 1193 }
1194 1194
1195 // Reserve space. 1195 // Reserve space.
1196 if (frame_size > 0) { 1196 if (frame_size > 0) {
1197 AddImmediate(SP, SP, -frame_size, PP); 1197 AddImmediate(SP, SP, -frame_size, PP);
1198 } 1198 }
1199 } 1199 }
1200 1200
1201 1201
1202 // On entry to a function compiled for OSR, the caller's frame pointer, the 1202 // On entry to a function compiled for OSR, the caller's frame pointer, the
1203 // stack locals, and any copied parameters are already in place. The frame 1203 // stack locals, and any copied parameters are already in place. The frame
1204 // pointer is already set up. The PC marker is not correct for the 1204 // pointer is already set up. The PC marker is not correct for the
1205 // optimized function and there may be extra space for spill slots to 1205 // optimized function and there may be extra space for spill slots to
1206 // allocate. We must also set up the pool pointer for the function. 1206 // allocate. We must also set up the pool pointer for the function.
1207 void Assembler::EnterOsrFrame(intptr_t extra_size, Register new_pp) { 1207 void Assembler::EnterOsrFrame(intptr_t extra_size, Register new_pp) {
1208 Comment("EnterOsrFrame"); 1208 Comment("EnterOsrFrame");
1209 adr(TMP, -CodeSize()); 1209 adr(TMP, Immediate(-CodeSize()));
1210 1210
1211 StoreToOffset(TMP, FP, kPcMarkerSlotFromFp * kWordSize, kNoPP); 1211 StoreToOffset(TMP, FP, kPcMarkerSlotFromFp * kWordSize, kNoPP);
1212 1212
1213 // Setup pool pointer for this dart function. 1213 // Setup pool pointer for this dart function.
1214 if (new_pp == kNoPP) { 1214 if (new_pp == kNoPP) {
1215 LoadPoolPointer(PP); 1215 LoadPoolPointer(PP);
1216 } else { 1216 } else {
1217 mov(PP, new_pp); 1217 mov(PP, new_pp);
1218 } 1218 }
1219 1219
(...skipping 294 matching lines...) Expand 10 before | Expand all | Expand 10 after
1514 add(base, array, Operand(index, LSL, shift)); 1514 add(base, array, Operand(index, LSL, shift));
1515 } 1515 }
1516 const OperandSize size = Address::OperandSizeFor(cid); 1516 const OperandSize size = Address::OperandSizeFor(cid);
1517 ASSERT(Address::CanHoldOffset(offset, Address::Offset, size)); 1517 ASSERT(Address::CanHoldOffset(offset, Address::Offset, size));
1518 return Address(base, offset, Address::Offset, size); 1518 return Address(base, offset, Address::Offset, size);
1519 } 1519 }
1520 1520
1521 } // namespace dart 1521 } // namespace dart
1522 1522
1523 #endif // defined TARGET_ARCH_ARM64 1523 #endif // defined TARGET_ARCH_ARM64
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698