| 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 #include "vm/globals.h" // Needed here to get TARGET_ARCH_X64. | 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_X64. |
| 6 #if defined(TARGET_ARCH_X64) | 6 #if defined(TARGET_ARCH_X64) |
| 7 | 7 |
| 8 #include "vm/intermediate_language.h" | 8 #include "vm/intermediate_language.h" |
| 9 | 9 |
| 10 #include "vm/dart_entry.h" | 10 #include "vm/dart_entry.h" |
| (...skipping 1113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1124 __ SmiTag(result); | 1124 __ SmiTag(result); |
| 1125 break; | 1125 break; |
| 1126 default: | 1126 default: |
| 1127 ASSERT((class_id() == kArrayCid) || (class_id() == kImmutableArrayCid)); | 1127 ASSERT((class_id() == kArrayCid) || (class_id() == kImmutableArrayCid)); |
| 1128 __ movq(result, element_address); | 1128 __ movq(result, element_address); |
| 1129 break; | 1129 break; |
| 1130 } | 1130 } |
| 1131 } | 1131 } |
| 1132 | 1132 |
| 1133 | 1133 |
| 1134 LocationSummary* LoadCodeUnitsInstr::MakeLocationSummary(Isolate* isolate, | |
| 1135 bool opt) const { | |
| 1136 const intptr_t kNumInputs = 2; | |
| 1137 const intptr_t kNumTemps = 0; | |
| 1138 LocationSummary* summary = new(isolate) LocationSummary( | |
| 1139 isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); | |
| 1140 summary->set_in(0, Location::RequiresRegister()); | |
| 1141 // The smi index is either untagged (element size == 1), or it is left smi | |
| 1142 // tagged (for all element sizes > 1). | |
| 1143 summary->set_in(1, index_scale() == 1 ? Location::WritableRegister() | |
| 1144 : Location::RequiresRegister()); | |
| 1145 summary->set_out(0, Location::RequiresRegister()); | |
| 1146 return summary; | |
| 1147 } | |
| 1148 | |
| 1149 | |
| 1150 void LoadCodeUnitsInstr::EmitNativeCode(FlowGraphCompiler* compiler) { | |
| 1151 const Register array = locs()->in(0).reg(); | |
| 1152 const Location index = locs()->in(1); | |
| 1153 | |
| 1154 Address element_address = Assembler::ElementAddressForRegIndex( | |
| 1155 IsExternal(), class_id(), index_scale(), array, index.reg()); | |
| 1156 | |
| 1157 if ((index_scale() == 1)) { | |
| 1158 __ SmiUntag(index.reg()); | |
| 1159 } | |
| 1160 Register result = locs()->out(0).reg(); | |
| 1161 switch (class_id()) { | |
| 1162 case kOneByteStringCid: | |
| 1163 case kExternalOneByteStringCid: | |
| 1164 switch (element_count()) { | |
| 1165 case 1: __ movzxb(result, element_address); break; | |
| 1166 case 2: __ movzxw(result, element_address); break; | |
| 1167 case 4: __ movl(result, element_address); break; | |
| 1168 default: UNREACHABLE(); | |
| 1169 } | |
| 1170 __ SmiTag(result); | |
| 1171 break; | |
| 1172 case kTwoByteStringCid: | |
| 1173 case kExternalTwoByteStringCid: | |
| 1174 switch (element_count()) { | |
| 1175 case 1: __ movzxw(result, element_address); break; | |
| 1176 case 2: __ movl(result, element_address); break; | |
| 1177 default: UNREACHABLE(); | |
| 1178 } | |
| 1179 __ SmiTag(result); | |
| 1180 break; | |
| 1181 default: | |
| 1182 UNREACHABLE(); | |
| 1183 break; | |
| 1184 } | |
| 1185 } | |
| 1186 | |
| 1187 | |
| 1188 Representation StoreIndexedInstr::RequiredInputRepresentation( | 1134 Representation StoreIndexedInstr::RequiredInputRepresentation( |
| 1189 intptr_t idx) const { | 1135 intptr_t idx) const { |
| 1190 if (idx == 0) return kNoRepresentation; | 1136 if (idx == 0) return kNoRepresentation; |
| 1191 if (idx == 1) return kTagged; | 1137 if (idx == 1) return kTagged; |
| 1192 ASSERT(idx == 2); | 1138 ASSERT(idx == 2); |
| 1193 switch (class_id_) { | 1139 switch (class_id_) { |
| 1194 case kArrayCid: | 1140 case kArrayCid: |
| 1195 case kOneByteStringCid: | 1141 case kOneByteStringCid: |
| 1196 case kTypedDataInt8ArrayCid: | 1142 case kTypedDataInt8ArrayCid: |
| 1197 case kTypedDataUint8ArrayCid: | 1143 case kTypedDataUint8ArrayCid: |
| (...skipping 3411 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4609 __ ReserveAlignedFrameSpace(0); | 4555 __ ReserveAlignedFrameSpace(0); |
| 4610 __ movaps(XMM0, locs()->in(0).fpu_reg()); | 4556 __ movaps(XMM0, locs()->in(0).fpu_reg()); |
| 4611 __ CallRuntime(TargetFunction(), InputCount()); | 4557 __ CallRuntime(TargetFunction(), InputCount()); |
| 4612 __ movaps(locs()->out(0).fpu_reg(), XMM0); | 4558 __ movaps(locs()->out(0).fpu_reg(), XMM0); |
| 4613 // Restore RSP. | 4559 // Restore RSP. |
| 4614 __ movq(RSP, locs()->temp(0).reg()); | 4560 __ movq(RSP, locs()->temp(0).reg()); |
| 4615 } | 4561 } |
| 4616 } | 4562 } |
| 4617 | 4563 |
| 4618 | 4564 |
| 4619 LocationSummary* CaseInsensitiveCompareUC16Instr::MakeLocationSummary( | |
| 4620 Isolate* isolate, bool opt) const { | |
| 4621 const intptr_t kNumTemps = 0; | |
| 4622 LocationSummary* summary = new(isolate) LocationSummary( | |
| 4623 isolate, InputCount(), kNumTemps, LocationSummary::kCall); | |
| 4624 summary->set_in(0, Location::RegisterLocation(CallingConventions::kArg1Reg)); | |
| 4625 summary->set_in(1, Location::RegisterLocation(CallingConventions::kArg2Reg)); | |
| 4626 summary->set_in(2, Location::RegisterLocation(CallingConventions::kArg3Reg)); | |
| 4627 summary->set_in(3, Location::RegisterLocation(CallingConventions::kArg4Reg)); | |
| 4628 summary->set_out(0, Location::RegisterLocation(RAX)); | |
| 4629 return summary; | |
| 4630 } | |
| 4631 | |
| 4632 | |
| 4633 void CaseInsensitiveCompareUC16Instr::EmitNativeCode( | |
| 4634 FlowGraphCompiler* compiler) { | |
| 4635 | |
| 4636 // Save RSP. R13 is chosen because it is callee saved so we do not need to | |
| 4637 // back it up before calling into the runtime. | |
| 4638 static const Register kSavedSPReg = R13; | |
| 4639 __ movq(kSavedSPReg, RSP); | |
| 4640 __ ReserveAlignedFrameSpace(0); | |
| 4641 | |
| 4642 // Call the function. Parameters are already in their correct spots. | |
| 4643 __ CallRuntime(TargetFunction(), TargetFunction().argument_count()); | |
| 4644 | |
| 4645 // Restore RSP. | |
| 4646 __ movq(RSP, kSavedSPReg); | |
| 4647 } | |
| 4648 | |
| 4649 | |
| 4650 LocationSummary* UnarySmiOpInstr::MakeLocationSummary(Isolate* isolate, | 4565 LocationSummary* UnarySmiOpInstr::MakeLocationSummary(Isolate* isolate, |
| 4651 bool opt) const { | 4566 bool opt) const { |
| 4652 const intptr_t kNumInputs = 1; | 4567 const intptr_t kNumInputs = 1; |
| 4653 return LocationSummary::Make(isolate, | 4568 return LocationSummary::Make(isolate, |
| 4654 kNumInputs, | 4569 kNumInputs, |
| 4655 Location::SameAsFirstInput(), | 4570 Location::SameAsFirstInput(), |
| 4656 LocationSummary::kNoCall); | 4571 LocationSummary::kNoCall); |
| 4657 } | 4572 } |
| 4658 | 4573 |
| 4659 | 4574 |
| (...skipping 1503 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6163 } | 6078 } |
| 6164 | 6079 |
| 6165 // We can fall through if the successor is the next block in the list. | 6080 // We can fall through if the successor is the next block in the list. |
| 6166 // Otherwise, we need a jump. | 6081 // Otherwise, we need a jump. |
| 6167 if (!compiler->CanFallThroughTo(successor())) { | 6082 if (!compiler->CanFallThroughTo(successor())) { |
| 6168 __ jmp(compiler->GetJumpLabel(successor())); | 6083 __ jmp(compiler->GetJumpLabel(successor())); |
| 6169 } | 6084 } |
| 6170 } | 6085 } |
| 6171 | 6086 |
| 6172 | 6087 |
| 6173 LocationSummary* IndirectGotoInstr::MakeLocationSummary(Isolate* isolate, | |
| 6174 bool opt) const { | |
| 6175 const intptr_t kNumInputs = 1; | |
| 6176 const intptr_t kNumTemps = 1; | |
| 6177 | |
| 6178 LocationSummary* summary = new(isolate) LocationSummary( | |
| 6179 isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); | |
| 6180 | |
| 6181 summary->set_in(0, Location::RequiresRegister()); | |
| 6182 summary->set_temp(0, Location::RequiresRegister()); | |
| 6183 | |
| 6184 return summary; | |
| 6185 } | |
| 6186 | |
| 6187 | |
| 6188 void IndirectGotoInstr::EmitNativeCode(FlowGraphCompiler* compiler) { | |
| 6189 Register offset_reg = locs()->in(0).reg(); | |
| 6190 Register target_address_reg = locs()->temp_slot(0)->reg(); | |
| 6191 | |
| 6192 // Load from [current frame pointer] + kPcMarkerSlotFromFp. | |
| 6193 __ movq(target_address_reg, Address(RBP, kPcMarkerSlotFromFp * kWordSize)); | |
| 6194 | |
| 6195 // Calculate the final absolute address. | |
| 6196 __ SmiUntag(offset_reg); | |
| 6197 __ addq(target_address_reg, offset_reg); | |
| 6198 | |
| 6199 // Jump to the absolute address. | |
| 6200 __ jmp(target_address_reg); | |
| 6201 } | |
| 6202 | |
| 6203 LocationSummary* StrictCompareInstr::MakeLocationSummary(Isolate* isolate, | 6088 LocationSummary* StrictCompareInstr::MakeLocationSummary(Isolate* isolate, |
| 6204 bool opt) const { | 6089 bool opt) const { |
| 6205 const intptr_t kNumInputs = 2; | 6090 const intptr_t kNumInputs = 2; |
| 6206 const intptr_t kNumTemps = 0; | 6091 const intptr_t kNumTemps = 0; |
| 6207 if (needs_number_check()) { | 6092 if (needs_number_check()) { |
| 6208 LocationSummary* locs = new(isolate) LocationSummary( | 6093 LocationSummary* locs = new(isolate) LocationSummary( |
| 6209 isolate, kNumInputs, kNumTemps, LocationSummary::kCall); | 6094 isolate, kNumInputs, kNumTemps, LocationSummary::kCall); |
| 6210 locs->set_in(0, Location::RegisterLocation(RAX)); | 6095 locs->set_in(0, Location::RegisterLocation(RAX)); |
| 6211 locs->set_in(1, Location::RegisterLocation(RCX)); | 6096 locs->set_in(1, Location::RegisterLocation(RCX)); |
| 6212 locs->set_out(0, Location::RegisterLocation(RAX)); | 6097 locs->set_out(0, Location::RegisterLocation(RAX)); |
| (...skipping 171 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6384 __ movq(R10, Immediate(kInvalidObjectPointer)); | 6269 __ movq(R10, Immediate(kInvalidObjectPointer)); |
| 6385 __ movq(RBX, Immediate(kInvalidObjectPointer)); | 6270 __ movq(RBX, Immediate(kInvalidObjectPointer)); |
| 6386 #endif | 6271 #endif |
| 6387 } | 6272 } |
| 6388 | 6273 |
| 6389 } // namespace dart | 6274 } // namespace dart |
| 6390 | 6275 |
| 6391 #undef __ | 6276 #undef __ |
| 6392 | 6277 |
| 6393 #endif // defined TARGET_ARCH_X64 | 6278 #endif // defined TARGET_ARCH_X64 |
| OLD | NEW |