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

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

Issue 262793006: Uses double load/store on arm64, enables tests. (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 6 years, 7 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
« no previous file with comments | « runtime/vm/guard_field_test.cc ('k') | runtime/vm/stack_frame_arm64.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
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" // Needed here to get TARGET_ARCH_ARM64. 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_ARM64.
6 #if defined(TARGET_ARCH_ARM64) 6 #if defined(TARGET_ARCH_ARM64)
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 592 matching lines...) Expand 10 before | Expand all | Expand 10 after
603 case kTypedDataUint16ArrayCid: 603 case kTypedDataUint16ArrayCid:
604 locs->set_in(2, Location::WritableRegister()); 604 locs->set_in(2, Location::WritableRegister());
605 break; 605 break;
606 case kTypedDataInt32ArrayCid: 606 case kTypedDataInt32ArrayCid:
607 case kTypedDataUint32ArrayCid: 607 case kTypedDataUint32ArrayCid:
608 // Mints are stored in Q registers. For smis, use a writable register 608 // Mints are stored in Q registers. For smis, use a writable register
609 // because the value must be untagged before storing. 609 // because the value must be untagged before storing.
610 if (value()->IsSmiValue()) { 610 if (value()->IsSmiValue()) {
611 locs->set_in(2, Location::WritableRegister()); 611 locs->set_in(2, Location::WritableRegister());
612 } else { 612 } else {
613 // TODO(zra): Implement when we add fpu loads and stores. 613 // TODO(zra): Implement when we add simd loads and stores.
614 UNIMPLEMENTED(); 614 UNIMPLEMENTED();
615 } 615 }
616 break; 616 break;
617 case kTypedDataFloat32ArrayCid: 617 case kTypedDataFloat32ArrayCid:
618 // TODO(zra): Implement when we add float store.
619 UNIMPLEMENTED();
620 break;
618 case kTypedDataFloat64ArrayCid: // TODO(srdjan): Support Float64 constants. 621 case kTypedDataFloat64ArrayCid: // TODO(srdjan): Support Float64 constants.
622 locs->set_in(2, Location::RequiresFpuRegister());
623 break;
619 case kTypedDataInt32x4ArrayCid: 624 case kTypedDataInt32x4ArrayCid:
620 case kTypedDataFloat32x4ArrayCid: 625 case kTypedDataFloat32x4ArrayCid:
621 case kTypedDataFloat64x2ArrayCid: 626 case kTypedDataFloat64x2ArrayCid:
622 // TODO(zra): Implement when we add fpu loads and stores. 627 // TODO(zra): Implement when we add simd loads and stores.
623 UNIMPLEMENTED(); 628 UNIMPLEMENTED();
624 break; 629 break;
625 default: 630 default:
626 UNREACHABLE(); 631 UNREACHABLE();
627 return NULL; 632 return NULL;
628 } 633 }
629 return locs; 634 return locs;
630 } 635 }
631 636
632 637
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after
735 break; 740 break;
736 } 741 }
737 case kTypedDataInt32ArrayCid: 742 case kTypedDataInt32ArrayCid:
738 case kTypedDataUint32ArrayCid: { 743 case kTypedDataUint32ArrayCid: {
739 if (value()->IsSmiValue()) { 744 if (value()->IsSmiValue()) {
740 ASSERT(RequiredInputRepresentation(2) == kTagged); 745 ASSERT(RequiredInputRepresentation(2) == kTagged);
741 Register value = locs()->in(2).reg(); 746 Register value = locs()->in(2).reg();
742 __ SmiUntag(value); 747 __ SmiUntag(value);
743 __ str(value, element_address); 748 __ str(value, element_address);
744 } else { 749 } else {
745 // TODO(zra): Implement when we add fpu loads and stores. 750 // TODO(zra): Implement when we add simd loads and stores.
746 UNIMPLEMENTED(); 751 UNIMPLEMENTED();
747 } 752 }
748 break; 753 break;
749 } 754 }
750 case kTypedDataFloat32ArrayCid: 755 case kTypedDataFloat32ArrayCid:
751 case kTypedDataFloat64ArrayCid: 756 // TODO(zra): Implement when we add float store.
757 UNIMPLEMENTED();
758 break;
759 case kTypedDataFloat64ArrayCid: {
760 VRegister in2 = locs()->in(2).fpu_reg();
761 __ add(index.reg(), index.reg(), Operand(array));
762 __ StoreDFieldToOffset(in2, index.reg(), 0);
763 break;
764 }
752 case kTypedDataFloat64x2ArrayCid: 765 case kTypedDataFloat64x2ArrayCid:
753 case kTypedDataInt32x4ArrayCid: 766 case kTypedDataInt32x4ArrayCid:
754 case kTypedDataFloat32x4ArrayCid: { 767 case kTypedDataFloat32x4ArrayCid: {
755 // TODO(zra): Implement when we add fpu loads and stores. 768 // TODO(zra): Implement when we add simd loads and stores.
756 UNIMPLEMENTED(); 769 UNIMPLEMENTED();
757 break; 770 break;
758 } 771 }
759 default: 772 default:
760 UNREACHABLE(); 773 UNREACHABLE();
761 } 774 }
762 } 775 }
763 776
764 777
765 static void LoadValueCid(FlowGraphCompiler* compiler, 778 static void LoadValueCid(FlowGraphCompiler* compiler,
(...skipping 120 matching lines...) Expand 10 before | Expand all | Expand 10 after
886 __ CompareImmediate(TMP, 0, PP); 899 __ CompareImmediate(TMP, 0, PP);
887 __ b(&skip_length_check, LT); 900 __ b(&skip_length_check, LT);
888 __ CompareImmediate(value_cid_reg, kNullCid, PP); 901 __ CompareImmediate(value_cid_reg, kNullCid, PP);
889 __ b(&no_fixed_length, EQ); 902 __ b(&no_fixed_length, EQ);
890 // Check for typed data array. 903 // Check for typed data array.
891 __ CompareImmediate(value_cid_reg, kTypedDataInt32x4ArrayCid, PP); 904 __ CompareImmediate(value_cid_reg, kTypedDataInt32x4ArrayCid, PP);
892 __ b(&no_fixed_length, GT); 905 __ b(&no_fixed_length, GT);
893 __ CompareImmediate(value_cid_reg, kTypedDataInt8ArrayCid, PP); 906 __ CompareImmediate(value_cid_reg, kTypedDataInt8ArrayCid, PP);
894 // Could still be a regular array. 907 // Could still be a regular array.
895 __ b(&check_array, LT); 908 __ b(&check_array, LT);
896 __ LoadFromOffset(temp_reg, value_reg, TypedData::length_offset()); 909 __ LoadFieldFromOffset(
910 temp_reg, value_reg, TypedData::length_offset());
897 __ ldr(TMP, field_length_operand); 911 __ ldr(TMP, field_length_operand);
898 __ CompareRegisters(temp_reg, TMP); 912 __ CompareRegisters(temp_reg, TMP);
899 __ b(&length_compared); 913 __ b(&length_compared);
900 // Check for regular array. 914 // Check for regular array.
901 __ Bind(&check_array); 915 __ Bind(&check_array);
902 __ CompareImmediate(value_cid_reg, kImmutableArrayCid, PP); 916 __ CompareImmediate(value_cid_reg, kImmutableArrayCid, PP);
903 __ b(&no_fixed_length, GT); 917 __ b(&no_fixed_length, GT);
904 __ CompareImmediate(value_cid_reg, kArrayCid, PP); 918 __ CompareImmediate(value_cid_reg, kArrayCid, PP);
905 __ b(&no_fixed_length, LT); 919 __ b(&no_fixed_length, LT);
906 __ LoadFieldFromOffset(temp_reg, value_reg, Array::length_offset()); 920 __ LoadFieldFromOffset(temp_reg, value_reg, Array::length_offset());
(...skipping 228 matching lines...) Expand 10 before | Expand all | Expand 10 after
1135 const intptr_t kNumTemps = 0; 1149 const intptr_t kNumTemps = 0;
1136 LocationSummary* summary = 1150 LocationSummary* summary =
1137 new LocationSummary(kNumInputs, kNumTemps, 1151 new LocationSummary(kNumInputs, kNumTemps,
1138 !field().IsNull() && 1152 !field().IsNull() &&
1139 ((field().guarded_cid() == kIllegalCid) || is_initialization_) 1153 ((field().guarded_cid() == kIllegalCid) || is_initialization_)
1140 ? LocationSummary::kCallOnSlowPath 1154 ? LocationSummary::kCallOnSlowPath
1141 : LocationSummary::kNoCall); 1155 : LocationSummary::kNoCall);
1142 1156
1143 summary->set_in(0, Location::RequiresRegister()); 1157 summary->set_in(0, Location::RequiresRegister());
1144 if (IsUnboxedStore() && opt) { 1158 if (IsUnboxedStore() && opt) {
1145 // TODO(zra): Implement when we add fpu loads and stores. 1159 summary->set_in(1, Location::RequiresFpuRegister());
1146 UNIMPLEMENTED(); 1160 summary->AddTemp(Location::RequiresRegister());
1161 summary->AddTemp(Location::RequiresRegister());
1147 } else if (IsPotentialUnboxedStore()) { 1162 } else if (IsPotentialUnboxedStore()) {
1148 summary->set_in(1, ShouldEmitStoreBarrier() 1163 summary->set_in(1, ShouldEmitStoreBarrier()
1149 ? Location::WritableRegister() 1164 ? Location::WritableRegister()
1150 : Location::RequiresRegister()); 1165 : Location::RequiresRegister());
1151 summary->AddTemp(Location::RequiresRegister()); 1166 summary->AddTemp(Location::RequiresRegister());
1152 summary->AddTemp(Location::RequiresRegister()); 1167 summary->AddTemp(Location::RequiresRegister());
1168 summary->AddTemp(opt ? Location::RequiresFpuRegister()
1169 : Location::FpuRegisterLocation(V1));
1153 } else { 1170 } else {
1154 summary->set_in(1, ShouldEmitStoreBarrier() 1171 summary->set_in(1, ShouldEmitStoreBarrier()
1155 ? Location::WritableRegister() 1172 ? Location::WritableRegister()
1156 : Location::RegisterOrConstant(value())); 1173 : Location::RegisterOrConstant(value()));
1157 } 1174 }
1158 return summary; 1175 return summary;
1159 } 1176 }
1160 1177
1161 1178
1162 void StoreInstanceFieldInstr::EmitNativeCode(FlowGraphCompiler* compiler) { 1179 void StoreInstanceFieldInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
1163 Label skip_store; 1180 Label skip_store;
1164 1181
1165 Register instance_reg = locs()->in(0).reg(); 1182 Register instance_reg = locs()->in(0).reg();
1166 1183
1167 if (IsUnboxedStore() && compiler->is_optimizing()) { 1184 if (IsUnboxedStore() && compiler->is_optimizing()) {
1168 UNIMPLEMENTED(); 1185 const VRegister value = locs()->in(1).fpu_reg();
1186 const Register temp = locs()->temp(0).reg();
1187 const Register temp2 = locs()->temp(1).reg();
1188 const intptr_t cid = field().UnboxedFieldCid();
1189
1190 if (is_initialization_) {
1191 const Class* cls = NULL;
1192 switch (cid) {
1193 case kDoubleCid:
1194 cls = &compiler->double_class();
1195 break;
1196 // TODO(zra): Implement these when we add fpu loads and stores.
1197 case kFloat32x4Cid:
1198 case kFloat64x2Cid:
1199 UNIMPLEMENTED();
1200 break;
1201 default:
1202 UNREACHABLE();
1203 }
1204
1205 StoreInstanceFieldSlowPath* slow_path =
1206 new StoreInstanceFieldSlowPath(this, *cls);
1207 compiler->AddSlowPathCode(slow_path);
1208
1209 __ TryAllocate(*cls,
1210 slow_path->entry_label(),
1211 temp,
1212 temp2,
1213 PP);
1214 __ Bind(slow_path->exit_label());
1215 __ mov(temp2, temp);
1216 __ StoreIntoObject(instance_reg,
1217 FieldAddress(instance_reg, offset_in_bytes_),
1218 temp2);
1219 } else {
1220 __ LoadFieldFromOffset(temp, instance_reg, offset_in_bytes_);
1221 }
1222 switch (cid) {
1223 case kDoubleCid:
1224 __ Comment("UnboxedDoubleStoreInstanceFieldInstr");
1225 __ StoreDFieldToOffset(value, temp, Double::value_offset());
1226 break;
1227 case kFloat32x4Cid:
1228 case kFloat64x2Cid:
1229 UNIMPLEMENTED();
1230 break;
1231 default:
1232 UNREACHABLE();
1233 }
1234
1235 return;
1169 } 1236 }
1170 1237
1171 if (IsPotentialUnboxedStore()) { 1238 if (IsPotentialUnboxedStore()) {
1239 const Register value_reg = locs()->in(1).reg();
1172 const Register temp = locs()->temp(0).reg(); 1240 const Register temp = locs()->temp(0).reg();
1173 const Register temp2 = locs()->temp(1).reg(); 1241 const Register temp2 = locs()->temp(1).reg();
1242 const VRegister fpu_temp = locs()->temp(2).fpu_reg();
1174 1243
1175 Label store_pointer; 1244 Label store_pointer;
1176 Label store_double; 1245 Label store_double;
1177 Label store_float32x4; 1246 Label store_float32x4;
1178 Label store_float64x2; 1247 Label store_float64x2;
1179 1248
1180 __ LoadObject(temp, Field::ZoneHandle(field().raw()), PP); 1249 __ LoadObject(temp, Field::ZoneHandle(field().raw()), PP);
1181 1250
1182 __ LoadFieldFromOffset(temp2, temp, Field::is_nullable_offset()); 1251 __ LoadFieldFromOffset(temp2, temp, Field::is_nullable_offset());
1183 __ CompareImmediate(temp2, kNullCid, PP); 1252 __ CompareImmediate(temp2, kNullCid, PP);
(...skipping 17 matching lines...) Expand all
1201 __ b(&store_float64x2, EQ); 1270 __ b(&store_float64x2, EQ);
1202 1271
1203 // Fall through. 1272 // Fall through.
1204 __ b(&store_pointer); 1273 __ b(&store_pointer);
1205 1274
1206 if (!compiler->is_optimizing()) { 1275 if (!compiler->is_optimizing()) {
1207 locs()->live_registers()->Add(locs()->in(0)); 1276 locs()->live_registers()->Add(locs()->in(0));
1208 locs()->live_registers()->Add(locs()->in(1)); 1277 locs()->live_registers()->Add(locs()->in(1));
1209 } 1278 }
1210 1279
1211 // TODO(zra): Implement these when we add fpu loads and stores.
1212 { 1280 {
1213 __ Bind(&store_double); 1281 __ Bind(&store_double);
1214 __ hlt(0); // Unimplemented. 1282 Label copy_double;
1283 StoreInstanceFieldSlowPath* slow_path =
1284 new StoreInstanceFieldSlowPath(this, compiler->double_class());
1285 compiler->AddSlowPathCode(slow_path);
1286
1287 __ LoadFieldFromOffset(temp, instance_reg, offset_in_bytes_);
1288 __ CompareObject(temp, Object::null_object(), PP);
1289 __ b(&copy_double, NE);
1290
1291 __ TryAllocate(compiler->double_class(),
1292 slow_path->entry_label(),
1293 temp,
1294 temp2,
1295 PP);
1296 __ Bind(slow_path->exit_label());
1297 __ mov(temp2, temp);
1298 __ StoreIntoObject(instance_reg,
1299 FieldAddress(instance_reg, offset_in_bytes_),
1300 temp2);
1301 __ Bind(&copy_double);
1302 __ LoadDFieldFromOffset(fpu_temp, value_reg, Double::value_offset());
1303 __ StoreDFieldToOffset(fpu_temp, temp, Double::value_offset());
1304 __ b(&skip_store);
1215 } 1305 }
1216 1306
1307 // TODO(zra): Implement these when we add simd loads and stores.
1217 { 1308 {
1218 __ Bind(&store_float32x4); 1309 __ Bind(&store_float32x4);
1219 __ hlt(0); // Unimplemented. 1310 __ hlt(0); // Unimplemented.
1220 } 1311 }
1221 1312
1222 { 1313 {
1223 __ Bind(&store_float64x2); 1314 __ Bind(&store_float64x2);
1224 __ hlt(0); // Unimplemented. 1315 __ hlt(0); // Unimplemented.
1225 } 1316 }
1226 1317
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after
1324 ASSERT(locs()->in(kElementTypePos).reg() == R1); 1415 ASSERT(locs()->in(kElementTypePos).reg() == R1);
1325 ASSERT(locs()->in(kLengthPos).reg() == R2); 1416 ASSERT(locs()->in(kLengthPos).reg() == R2);
1326 compiler->GenerateCall(token_pos(), 1417 compiler->GenerateCall(token_pos(),
1327 &StubCode::AllocateArrayLabel(), 1418 &StubCode::AllocateArrayLabel(),
1328 PcDescriptors::kOther, 1419 PcDescriptors::kOther,
1329 locs()); 1420 locs());
1330 ASSERT(locs()->out(0).reg() == R0); 1421 ASSERT(locs()->out(0).reg() == R0);
1331 } 1422 }
1332 1423
1333 1424
1425 class BoxDoubleSlowPath : public SlowPathCode {
1426 public:
1427 explicit BoxDoubleSlowPath(Instruction* instruction)
1428 : instruction_(instruction) { }
1429
1430 virtual void EmitNativeCode(FlowGraphCompiler* compiler) {
1431 __ Comment("BoxDoubleSlowPath");
1432 __ Bind(entry_label());
1433 const Class& double_class = compiler->double_class();
1434 const Code& stub =
1435 Code::Handle(StubCode::GetAllocationStubForClass(double_class));
1436 const ExternalLabel label(double_class.ToCString(), stub.EntryPoint());
1437
1438 LocationSummary* locs = instruction_->locs();
1439 locs->live_registers()->Remove(locs->out(0));
1440
1441 compiler->SaveLiveRegisters(locs);
1442 compiler->GenerateCall(Scanner::kNoSourcePos, // No token position.
1443 &label,
1444 PcDescriptors::kOther,
1445 locs);
1446 __ mov(locs->out(0).reg(), R0);
1447 compiler->RestoreLiveRegisters(locs);
1448
1449 __ b(exit_label());
1450 }
1451
1452 private:
1453 Instruction* instruction_;
1454 };
1455
1456
1334 LocationSummary* LoadFieldInstr::MakeLocationSummary(bool opt) const { 1457 LocationSummary* LoadFieldInstr::MakeLocationSummary(bool opt) const {
1335 const intptr_t kNumInputs = 1; 1458 const intptr_t kNumInputs = 1;
1336 const intptr_t kNumTemps = 0; 1459 const intptr_t kNumTemps = 0;
1337 LocationSummary* locs = 1460 LocationSummary* locs =
1338 new LocationSummary( 1461 new LocationSummary(
1339 kNumInputs, kNumTemps, 1462 kNumInputs, kNumTemps,
1340 (opt && !IsPotentialUnboxedLoad()) 1463 (opt && !IsPotentialUnboxedLoad())
1341 ? LocationSummary::kNoCall 1464 ? LocationSummary::kNoCall
1342 : LocationSummary::kCallOnSlowPath); 1465 : LocationSummary::kCallOnSlowPath);
1343 1466
1344 locs->set_in(0, Location::RequiresRegister()); 1467 locs->set_in(0, Location::RequiresRegister());
1345 1468
1346 if (IsUnboxedLoad() && opt) { 1469 if (IsUnboxedLoad() && opt) {
1347 // TODO(zra): Implement when we add fpu loads and stores. 1470 locs->AddTemp(Location::RequiresRegister());
1348 UNIMPLEMENTED();
1349 } else if (IsPotentialUnboxedLoad()) { 1471 } else if (IsPotentialUnboxedLoad()) {
1472 locs->AddTemp(opt ? Location::RequiresFpuRegister()
1473 : Location::FpuRegisterLocation(V1));
1350 locs->AddTemp(Location::RequiresRegister()); 1474 locs->AddTemp(Location::RequiresRegister());
1351 } 1475 }
1352 locs->set_out(0, Location::RequiresRegister()); 1476 locs->set_out(0, Location::RequiresRegister());
1353 return locs; 1477 return locs;
1354 } 1478 }
1355 1479
1356 1480
1357 void LoadFieldInstr::EmitNativeCode(FlowGraphCompiler* compiler) { 1481 void LoadFieldInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
1358 Register instance_reg = locs()->in(0).reg(); 1482 Register instance_reg = locs()->in(0).reg();
1359 if (IsUnboxedLoad() && compiler->is_optimizing()) { 1483 if (IsUnboxedLoad() && compiler->is_optimizing()) {
1360 UNIMPLEMENTED(); 1484 const VRegister result = locs()->out(0).fpu_reg();
1485 const Register temp = locs()->temp(0).reg();
1486 __ LoadFieldFromOffset(temp, instance_reg, offset_in_bytes());
1487 const intptr_t cid = field()->UnboxedFieldCid();
1488 switch (cid) {
1489 case kDoubleCid:
1490 __ Comment("UnboxedDoubleLoadFieldInstr");
1491 __ LoadDFieldFromOffset(result, temp, Double::value_offset());
1492 break;
1493 case kFloat32x4Cid:
1494 case kFloat64x2Cid:
1495 UNIMPLEMENTED();
1496 break;
1497 default:
1498 UNREACHABLE();
1499 }
1500 return;
1361 } 1501 }
1362 1502
1363 Label done; 1503 Label done;
1364 Register result_reg = locs()->out(0).reg(); 1504 Register result_reg = locs()->out(0).reg();
1365 if (IsPotentialUnboxedLoad()) { 1505 if (IsPotentialUnboxedLoad()) {
1366 const Register temp = locs()->temp(0).reg(); 1506 const Register temp = locs()->temp(1).reg();
1507 const VRegister value = locs()->temp(0).fpu_reg();
1367 1508
1368 Label load_pointer; 1509 Label load_pointer;
1369 Label load_double; 1510 Label load_double;
1370 Label load_float32x4; 1511 Label load_float32x4;
1371 Label load_float64x2; 1512 Label load_float64x2;
1372 1513
1373 __ LoadObject(result_reg, Field::ZoneHandle(field()->raw()), PP); 1514 __ LoadObject(result_reg, Field::ZoneHandle(field()->raw()), PP);
1374 1515
1375 FieldAddress field_cid_operand(result_reg, Field::guarded_cid_offset()); 1516 FieldAddress field_cid_operand(result_reg, Field::guarded_cid_offset());
1376 FieldAddress field_nullability_operand(result_reg, 1517 FieldAddress field_nullability_operand(result_reg,
(...skipping 15 matching lines...) Expand all
1392 __ CompareImmediate(temp, kFloat64x2Cid, PP); 1533 __ CompareImmediate(temp, kFloat64x2Cid, PP);
1393 __ b(&load_float64x2, EQ); 1534 __ b(&load_float64x2, EQ);
1394 1535
1395 // Fall through. 1536 // Fall through.
1396 __ b(&load_pointer); 1537 __ b(&load_pointer);
1397 1538
1398 if (!compiler->is_optimizing()) { 1539 if (!compiler->is_optimizing()) {
1399 locs()->live_registers()->Add(locs()->in(0)); 1540 locs()->live_registers()->Add(locs()->in(0));
1400 } 1541 }
1401 1542
1402 // TODO(zra): Implement these when we add fpu loads and stores.
1403 { 1543 {
1404 __ Bind(&load_double); 1544 __ Bind(&load_double);
1405 __ hlt(0); // Unimplemented. 1545 BoxDoubleSlowPath* slow_path = new BoxDoubleSlowPath(this);
1546 compiler->AddSlowPathCode(slow_path);
1547
1548 __ TryAllocate(compiler->double_class(),
1549 slow_path->entry_label(),
1550 result_reg,
1551 temp,
1552 PP);
1553 __ Bind(slow_path->exit_label());
1554 __ LoadFieldFromOffset(temp, instance_reg, offset_in_bytes());
1555 __ LoadDFieldFromOffset(value, temp, Double::value_offset());
1556 __ StoreDFieldToOffset(value, result_reg, Double::value_offset());
1557 __ b(&done);
1406 } 1558 }
1407 1559
1560 // TODO(zra): Implement these when we add simd loads and stores.
1408 { 1561 {
1409 __ Bind(&load_float32x4); 1562 __ Bind(&load_float32x4);
1410 __ hlt(0); // Unimplemented. 1563 __ hlt(0); // Unimplemented.
1411 } 1564 }
1412 1565
1413 { 1566 {
1414 __ Bind(&load_float64x2); 1567 __ Bind(&load_float64x2);
1415 __ hlt(0); // Unimplemented. 1568 __ hlt(0); // Unimplemented.
1416 } 1569 }
1417 1570
1418 __ Bind(&load_pointer); 1571 __ Bind(&load_pointer);
1419 } 1572 }
1420 __ LoadFromOffset( 1573 __ LoadFieldFromOffset(result_reg, instance_reg, offset_in_bytes());
1421 result_reg, instance_reg, offset_in_bytes() - kHeapObjectTag);
1422 __ Bind(&done); 1574 __ Bind(&done);
1423 } 1575 }
1424 1576
1425 1577
1426 LocationSummary* InstantiateTypeInstr::MakeLocationSummary(bool opt) const { 1578 LocationSummary* InstantiateTypeInstr::MakeLocationSummary(bool opt) const {
1427 UNIMPLEMENTED(); 1579 UNIMPLEMENTED();
1428 return NULL; 1580 return NULL;
1429 } 1581 }
1430 1582
1431 1583
(...skipping 1205 matching lines...) Expand 10 before | Expand all | Expand 10 after
2637 compiler->GenerateCall(token_pos(), 2789 compiler->GenerateCall(token_pos(),
2638 &label, 2790 &label,
2639 PcDescriptors::kOther, 2791 PcDescriptors::kOther,
2640 locs()); 2792 locs());
2641 __ Drop(ArgumentCount()); // Discard arguments. 2793 __ Drop(ArgumentCount()); // Discard arguments.
2642 } 2794 }
2643 2795
2644 } // namespace dart 2796 } // namespace dart
2645 2797
2646 #endif // defined TARGET_ARCH_ARM64 2798 #endif // defined TARGET_ARCH_ARM64
OLDNEW
« no previous file with comments | « runtime/vm/guard_field_test.cc ('k') | runtime/vm/stack_frame_arm64.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698