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

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

Issue 1175523002: Object pool with support for untagged entries. (Closed) Base URL: git@github.com:dart-lang/sdk.git@master
Patch Set: Created 5 years, 6 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
« no previous file with comments | « runtime/vm/assembler_arm64.h ('k') | runtime/vm/assembler_ia32.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" // NOLINT 5 #include "vm/globals.h" // NOLINT
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 17 matching lines...) Expand all
28 Assembler::Assembler(bool use_far_branches) 28 Assembler::Assembler(bool use_far_branches)
29 : buffer_(), 29 : buffer_(),
30 prologue_offset_(-1), 30 prologue_offset_(-1),
31 use_far_branches_(use_far_branches), 31 use_far_branches_(use_far_branches),
32 comments_(), 32 comments_(),
33 allow_constant_pool_(true) { 33 allow_constant_pool_(true) {
34 if (Isolate::Current() != Dart::vm_isolate()) { 34 if (Isolate::Current() != Dart::vm_isolate()) {
35 // These objects and labels need to be accessible through every pool-pointer 35 // These objects and labels need to be accessible through every pool-pointer
36 // at the same index. 36 // at the same index.
37 intptr_t index = 37 intptr_t index =
38 object_pool_.AddObject(Object::null_object(), kNotPatchable); 38 object_pool_wrapper_.AddObject(Object::null_object());
39 ASSERT(index == 0); 39 ASSERT(index == 0);
40 40
41 index = object_pool_.AddObject(Bool::True(), kNotPatchable); 41 index = object_pool_wrapper_.AddObject(Bool::True());
42 ASSERT(index == 1); 42 ASSERT(index == 1);
43 43
44 index = object_pool_.AddObject(Bool::False(), kNotPatchable); 44 index = object_pool_wrapper_.AddObject(Bool::False());
45 ASSERT(index == 2); 45 ASSERT(index == 2);
46 46
47 const Smi& vacant = Smi::Handle(Smi::New(0xfa >> kSmiTagShift)); 47 const Smi& vacant = Smi::Handle(Smi::New(0xfa >> kSmiTagShift));
48 StubCode* stub_code = Isolate::Current()->stub_code(); 48 StubCode* stub_code = Isolate::Current()->stub_code();
49 if (stub_code->UpdateStoreBuffer_entry() != NULL) { 49 if (stub_code->UpdateStoreBuffer_entry() != NULL) {
50 object_pool_.AddExternalLabel( 50 object_pool_wrapper_.AddExternalLabel(
51 &stub_code->UpdateStoreBufferLabel(), kNotPatchable); 51 &stub_code->UpdateStoreBufferLabel(), kNotPatchable);
52 } else { 52 } else {
53 object_pool_.AddObject(vacant, kNotPatchable); 53 object_pool_wrapper_.AddObject(vacant);
54 } 54 }
55 55
56 if (stub_code->CallToRuntime_entry() != NULL) { 56 if (stub_code->CallToRuntime_entry() != NULL) {
57 object_pool_.AddExternalLabel( 57 object_pool_wrapper_.AddExternalLabel(
58 &stub_code->CallToRuntimeLabel(), kNotPatchable); 58 &stub_code->CallToRuntimeLabel(), kNotPatchable);
59 } else { 59 } else {
60 object_pool_.AddObject(vacant, kNotPatchable); 60 object_pool_wrapper_.AddObject(vacant);
61 } 61 }
62 } 62 }
63 } 63 }
64 64
65 65
66 void Assembler::InitializeMemoryWithBreakpoints(uword data, intptr_t length) { 66 void Assembler::InitializeMemoryWithBreakpoints(uword data, intptr_t length) {
67 ASSERT(Utils::IsAligned(data, 4)); 67 ASSERT(Utils::IsAligned(data, 4));
68 ASSERT(Utils::IsAligned(length, 4)); 68 ASSERT(Utils::IsAligned(length, 4));
69 const uword end = data + length; 69 const uword end = data + length;
70 while (data < end) { 70 while (data < end) {
(...skipping 312 matching lines...) Expand 10 before | Expand all | Expand 10 after
383 Operand::CanHold(upper20, kXRegSizeInBits, &op); 383 Operand::CanHold(upper20, kXRegSizeInBits, &op);
384 ASSERT(ot == Operand::Immediate); 384 ASSERT(ot == Operand::Immediate);
385 ASSERT(Address::CanHoldOffset(lower12)); 385 ASSERT(Address::CanHoldOffset(lower12));
386 add(dst, pp, op); 386 add(dst, pp, op);
387 ldr(dst, Address(dst, lower12)); 387 ldr(dst, Address(dst, lower12));
388 } 388 }
389 389
390 390
391 intptr_t Assembler::FindImmediate(int64_t imm) { 391 intptr_t Assembler::FindImmediate(int64_t imm) {
392 ASSERT(Isolate::Current() != Dart::vm_isolate()); 392 ASSERT(Isolate::Current() != Dart::vm_isolate());
393 const Smi& smi = Smi::Handle(reinterpret_cast<RawSmi*>(imm)); 393 return object_pool_wrapper_.FindImmediate(imm);
394 return object_pool_.FindObject(smi, kNotPatchable);
395 } 394 }
396 395
397 396
398 // A set of VM objects that are present in every constant pool. 397 // A set of VM objects that are present in every constant pool.
399 static bool IsAlwaysInConstantPool(const Object& object) { 398 static bool IsAlwaysInConstantPool(const Object& object) {
400 // TODO(zra): Evaluate putting all VM heap objects into the pool. 399 // TODO(zra): Evaluate putting all VM heap objects into the pool.
401 return (object.raw() == Object::null()) 400 return (object.raw() == Object::null())
402 || (object.raw() == Bool::True().raw()) 401 || (object.raw() == Bool::True().raw())
403 || (object.raw() == Bool::False().raw()); 402 || (object.raw() == Bool::False().raw());
404 } 403 }
(...skipping 29 matching lines...) Expand all
434 (Isolate::Current() != Dart::vm_isolate()); 433 (Isolate::Current() != Dart::vm_isolate());
435 } 434 }
436 435
437 436
438 void Assembler::LoadExternalLabel(Register dst, 437 void Assembler::LoadExternalLabel(Register dst,
439 const ExternalLabel* label, 438 const ExternalLabel* label,
440 Patchability patchable, 439 Patchability patchable,
441 Register pp) { 440 Register pp) {
442 const int64_t target = static_cast<int64_t>(label->address()); 441 const int64_t target = static_cast<int64_t>(label->address());
443 if (CanLoadImmediateFromPool(target, pp)) { 442 if (CanLoadImmediateFromPool(target, pp)) {
444 const int32_t offset = 443 const int32_t offset = ObjectPool::element_offset(
445 Array::element_offset(object_pool_.FindExternalLabel(label, patchable)); 444 object_pool_wrapper_.FindExternalLabel(label, patchable));
446 LoadWordFromPoolOffset(dst, pp, offset); 445 LoadWordFromPoolOffset(dst, pp, offset);
447 } else { 446 } else {
448 LoadImmediate(dst, target, kNoPP); 447 LoadImmediate(dst, target, kNoPP);
449 } 448 }
450 } 449 }
451 450
452 451
453 void Assembler::LoadExternalLabelFixed(Register dst, 452 void Assembler::LoadExternalLabelFixed(Register dst,
454 const ExternalLabel* label, 453 const ExternalLabel* label,
455 Patchability patchable, 454 Patchability patchable,
456 Register pp) { 455 Register pp) {
457 const int32_t offset = 456 const int32_t offset = ObjectPool::element_offset(
458 Array::element_offset(object_pool_.FindExternalLabel(label, patchable)); 457 object_pool_wrapper_.FindExternalLabel(label, patchable));
459 LoadWordFromPoolOffsetFixed(dst, pp, offset); 458 LoadWordFromPoolOffsetFixed(dst, pp, offset);
460 } 459 }
461 460
462 461
463 void Assembler::LoadIsolate(Register dst, Register pp) { 462 void Assembler::LoadIsolate(Register dst, Register pp) {
464 ldr(dst, Address(THR, Thread::isolate_offset())); 463 ldr(dst, Address(THR, Thread::isolate_offset()));
465 } 464 }
466 465
467 466
468 void Assembler::LoadObject(Register dst, const Object& object, Register pp) { 467 void Assembler::LoadObject(Register dst, const Object& object, Register pp) {
469 if (CanLoadObjectFromPool(object)) { 468 if (CanLoadObjectFromPool(object)) {
470 const int32_t offset = 469 const int32_t offset =
471 Array::element_offset(object_pool_.FindObject(object, kNotPatchable)); 470 ObjectPool::element_offset(object_pool_wrapper_.FindObject(object));
472 LoadWordFromPoolOffset(dst, pp, offset); 471 LoadWordFromPoolOffset(dst, pp, offset);
473 } else { 472 } else {
474 ASSERT((Isolate::Current() == Dart::vm_isolate()) || 473 ASSERT((Isolate::Current() == Dart::vm_isolate()) ||
475 object.IsSmi() || 474 object.IsSmi() ||
476 object.InVMHeap()); 475 object.InVMHeap());
477 LoadDecodableImmediate(dst, reinterpret_cast<int64_t>(object.raw()), pp); 476 LoadDecodableImmediate(dst, reinterpret_cast<int64_t>(object.raw()), pp);
478 } 477 }
479 } 478 }
480 479
481 480
482 void Assembler::CompareObject(Register reg, const Object& object, Register pp) { 481 void Assembler::CompareObject(Register reg, const Object& object, Register pp) {
483 if (CanLoadObjectFromPool(object)) { 482 if (CanLoadObjectFromPool(object)) {
484 LoadObject(TMP, object, pp); 483 LoadObject(TMP, object, pp);
485 CompareRegisters(reg, TMP); 484 CompareRegisters(reg, TMP);
486 } else { 485 } else {
487 CompareImmediate(reg, reinterpret_cast<int64_t>(object.raw()), pp); 486 CompareImmediate(reg, reinterpret_cast<int64_t>(object.raw()), pp);
488 } 487 }
489 } 488 }
490 489
491 490
492 void Assembler::LoadDecodableImmediate(Register reg, int64_t imm, Register pp) { 491 void Assembler::LoadDecodableImmediate(Register reg, int64_t imm, Register pp) {
493 if ((pp != kNoPP) && 492 if ((pp != kNoPP) &&
494 (Isolate::Current() != Dart::vm_isolate()) && 493 (Isolate::Current() != Dart::vm_isolate()) &&
495 allow_constant_pool()) { 494 allow_constant_pool()) {
496 int64_t val_smi_tag = imm & kSmiTagMask; 495 int64_t val_smi_tag = imm & kSmiTagMask;
497 imm &= ~kSmiTagMask; // Mask off the tag bits. 496 imm &= ~kSmiTagMask; // Mask off the tag bits.
498 const int32_t offset = Array::element_offset(FindImmediate(imm)); 497 const int32_t offset = ObjectPool::element_offset(FindImmediate(imm));
499 LoadWordFromPoolOffset(reg, pp, offset); 498 LoadWordFromPoolOffset(reg, pp, offset);
500 if (val_smi_tag != 0) { 499 if (val_smi_tag != 0) {
501 // Add back the tag bits. 500 // Add back the tag bits.
502 orri(reg, reg, Immediate(val_smi_tag)); 501 orri(reg, reg, Immediate(val_smi_tag));
503 } 502 }
504 } else { 503 } else {
505 // TODO(zra): Since this sequence only needs to be decodable, it can be 504 // TODO(zra): Since this sequence only needs to be decodable, it can be
506 // of variable length. 505 // of variable length.
507 LoadImmediateFixed(reg, imm); 506 LoadImmediateFixed(reg, imm);
508 } 507 }
(...skipping 15 matching lines...) Expand all
524 523
525 524
526 void Assembler::LoadImmediate(Register reg, int64_t imm, Register pp) { 525 void Assembler::LoadImmediate(Register reg, int64_t imm, Register pp) {
527 Comment("LoadImmediate"); 526 Comment("LoadImmediate");
528 if (CanLoadImmediateFromPool(imm, pp)) { 527 if (CanLoadImmediateFromPool(imm, pp)) {
529 // It's a 64-bit constant and we're not in the VM isolate, so load from 528 // It's a 64-bit constant and we're not in the VM isolate, so load from
530 // object pool. 529 // object pool.
531 // Save the bits that must be masked-off for the SmiTag 530 // Save the bits that must be masked-off for the SmiTag
532 int64_t val_smi_tag = imm & kSmiTagMask; 531 int64_t val_smi_tag = imm & kSmiTagMask;
533 imm &= ~kSmiTagMask; // Mask off the tag bits. 532 imm &= ~kSmiTagMask; // Mask off the tag bits.
534 const int32_t offset = Array::element_offset(FindImmediate(imm)); 533 const int32_t offset = ObjectPool::element_offset(FindImmediate(imm));
535 LoadWordFromPoolOffset(reg, pp, offset); 534 LoadWordFromPoolOffset(reg, pp, offset);
536 if (val_smi_tag != 0) { 535 if (val_smi_tag != 0) {
537 // Add back the tag bits. 536 // Add back the tag bits.
538 orri(reg, reg, Immediate(val_smi_tag)); 537 orri(reg, reg, Immediate(val_smi_tag));
539 } 538 }
540 } else { 539 } else {
541 // 0. Is it 0? 540 // 0. Is it 0?
542 if (imm == 0) { 541 if (imm == 0) {
543 movz(reg, Immediate(0), 0); 542 movz(reg, Immediate(0), 0);
544 return; 543 return;
(...skipping 917 matching lines...) Expand 10 before | Expand all | Expand 10 after
1462 add(base, array, Operand(index, LSL, shift)); 1461 add(base, array, Operand(index, LSL, shift));
1463 } 1462 }
1464 const OperandSize size = Address::OperandSizeFor(cid); 1463 const OperandSize size = Address::OperandSizeFor(cid);
1465 ASSERT(Address::CanHoldOffset(offset, Address::Offset, size)); 1464 ASSERT(Address::CanHoldOffset(offset, Address::Offset, size));
1466 return Address(base, offset, Address::Offset, size); 1465 return Address(base, offset, Address::Offset, size);
1467 } 1466 }
1468 1467
1469 } // namespace dart 1468 } // namespace dart
1470 1469
1471 #endif // defined TARGET_ARCH_ARM64 1470 #endif // defined TARGET_ARCH_ARM64
OLDNEW
« no previous file with comments | « runtime/vm/assembler_arm64.h ('k') | runtime/vm/assembler_ia32.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698