| OLD | NEW |
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, 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_OBJECT_H_ | 5 #ifndef VM_OBJECT_H_ |
| 6 #define VM_OBJECT_H_ | 6 #define VM_OBJECT_H_ |
| 7 | 7 |
| 8 #include "include/dart_api.h" | 8 #include "include/dart_api.h" |
| 9 #include "platform/assert.h" | 9 #include "platform/assert.h" |
| 10 #include "platform/utils.h" | 10 #include "platform/utils.h" |
| (...skipping 571 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 582 void set_vtable(cpp_vtable value) { *vtable_address() = value; } | 582 void set_vtable(cpp_vtable value) { *vtable_address() = value; } |
| 583 | 583 |
| 584 static RawObject* Allocate(intptr_t cls_id, | 584 static RawObject* Allocate(intptr_t cls_id, |
| 585 intptr_t size, | 585 intptr_t size, |
| 586 Heap::Space space); | 586 Heap::Space space); |
| 587 | 587 |
| 588 static intptr_t RoundedAllocationSize(intptr_t size) { | 588 static intptr_t RoundedAllocationSize(intptr_t size) { |
| 589 return Utils::RoundUp(size, kObjectAlignment); | 589 return Utils::RoundUp(size, kObjectAlignment); |
| 590 } | 590 } |
| 591 | 591 |
| 592 bool Contains(uword addr) const { | 592 bool Contains(uword addr) const { return raw()->Contains(addr); } |
| 593 intptr_t this_size = raw()->Size(); | |
| 594 uword this_addr = RawObject::ToAddr(raw()); | |
| 595 return (addr >= this_addr) && (addr < (this_addr + this_size)); | |
| 596 } | |
| 597 | 593 |
| 598 // Start of field mutator guards. | 594 // Start of field mutator guards. |
| 599 // | 595 // |
| 600 // All writes to heap objects should ultimately pass through one of the | 596 // All writes to heap objects should ultimately pass through one of the |
| 601 // methods below, to ensure that the write barrier is correctly applied. | 597 // methods below or their counterparts in RawObject, to ensure that the |
| 598 // write barrier is correctly applied. |
| 602 | 599 |
| 603 template<typename type> | 600 template<typename type> |
| 604 void StorePointer(type const* addr, type value) const { | 601 void StorePointer(type const* addr, type value) const { |
| 605 // Ensure that this object contains the addr. | 602 raw()->StorePointer(addr, value); |
| 606 ASSERT(Contains(reinterpret_cast<uword>(addr))); | |
| 607 *const_cast<type*>(addr) = value; | |
| 608 // Filter stores based on source and target. | |
| 609 if (!value->IsHeapObject()) return; | |
| 610 if (value->IsNewObject() && raw()->IsOldObject() && | |
| 611 !raw()->IsRemembered()) { | |
| 612 raw()->SetRememberedBit(); | |
| 613 Isolate::Current()->store_buffer()->AddObject(raw()); | |
| 614 } | |
| 615 } | 603 } |
| 616 | 604 |
| 617 // Store a range of pointers [from, from + count) into [to, to + count). | 605 // Store a range of pointers [from, from + count) into [to, to + count). |
| 618 // TODO(koda): Use this to fix Object::Clone's broken store buffer logic. | 606 // TODO(koda): Use this to fix Object::Clone's broken store buffer logic. |
| 619 void StorePointers(RawObject* const* to, | 607 void StorePointers(RawObject* const* to, |
| 620 RawObject* const* from, | 608 RawObject* const* from, |
| 621 intptr_t count) { | 609 intptr_t count) { |
| 622 ASSERT(Contains(reinterpret_cast<uword>(to))); | 610 ASSERT(Contains(reinterpret_cast<uword>(to))); |
| 623 if (raw()->IsNewObject()) { | 611 if (raw()->IsNewObject()) { |
| 624 memmove(const_cast<RawObject**>(to), from, count * kWordSize); | 612 memmove(const_cast<RawObject**>(to), from, count * kWordSize); |
| 625 } else { | 613 } else { |
| 626 for (intptr_t i = 0; i < count; ++i) { | 614 for (intptr_t i = 0; i < count; ++i) { |
| 627 StorePointer(&to[i], from[i]); | 615 StorePointer(&to[i], from[i]); |
| 628 } | 616 } |
| 629 } | 617 } |
| 630 } | 618 } |
| 631 | 619 |
| 632 // Use for storing into an explicitly Smi-typed field of an object | 620 // Use for storing into an explicitly Smi-typed field of an object |
| 633 // (i.e., both the previous and new value are Smis). | 621 // (i.e., both the previous and new value are Smis). |
| 634 void StoreSmi(RawSmi* const* addr, RawSmi* value) const { | 622 void StoreSmi(RawSmi* const* addr, RawSmi* value) const { |
| 635 // Can't use Contains, as array length is initialized through this method. | 623 raw()->StoreSmi(addr, value); |
| 636 ASSERT(reinterpret_cast<uword>(addr) >= RawObject::ToAddr(raw())); | |
| 637 *const_cast<RawSmi**>(addr) = value; | |
| 638 } | 624 } |
| 639 | 625 |
| 640 template<typename FieldType> | 626 template<typename FieldType> |
| 641 void StoreSimd128(const FieldType* addr, simd128_value_t value) const { | 627 void StoreSimd128(const FieldType* addr, simd128_value_t value) const { |
| 642 ASSERT(Contains(reinterpret_cast<uword>(addr))); | 628 ASSERT(Contains(reinterpret_cast<uword>(addr))); |
| 643 value.writeTo(const_cast<FieldType*>(addr)); | 629 value.writeTo(const_cast<FieldType*>(addr)); |
| 644 } | 630 } |
| 645 | 631 |
| 646 // Needs two template arguments to allow assigning enums to fixed-size ints. | 632 // Needs two template arguments to allow assigning enums to fixed-size ints. |
| 647 template<typename FieldType, typename ValueType> | 633 template<typename FieldType, typename ValueType> |
| (...skipping 5830 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6478 Heap::Space space = Heap::kNew); | 6464 Heap::Space space = Heap::kNew); |
| 6479 static RawGrowableObjectArray* New(const Array& array, | 6465 static RawGrowableObjectArray* New(const Array& array, |
| 6480 Heap::Space space = Heap::kNew); | 6466 Heap::Space space = Heap::kNew); |
| 6481 | 6467 |
| 6482 private: | 6468 private: |
| 6483 RawArray* DataArray() const { return data()->ptr(); } | 6469 RawArray* DataArray() const { return data()->ptr(); } |
| 6484 RawObject** ObjectAddr(intptr_t index) const { | 6470 RawObject** ObjectAddr(intptr_t index) const { |
| 6485 ASSERT((index >= 0) && (index < Length())); | 6471 ASSERT((index >= 0) && (index < Length())); |
| 6486 return &(DataArray()->data()[index]); | 6472 return &(DataArray()->data()[index]); |
| 6487 } | 6473 } |
| 6488 bool DataContains(uword addr) const { | |
| 6489 intptr_t data_size = data()->Size(); | |
| 6490 uword data_addr = RawObject::ToAddr(data()); | |
| 6491 return (addr >= data_addr) && (addr < (data_addr + data_size)); | |
| 6492 } | |
| 6493 void DataStorePointer(RawObject** addr, RawObject* value) const { | 6474 void DataStorePointer(RawObject** addr, RawObject* value) const { |
| 6494 // Ensure that the backing array object contains the addr. | 6475 data()->StorePointer(addr, value); |
| 6495 ASSERT(DataContains(reinterpret_cast<uword>(addr))); | |
| 6496 *addr = value; | |
| 6497 // Filter stores based on source and target. | |
| 6498 if (!value->IsHeapObject()) return; | |
| 6499 if (value->IsNewObject() && data()->IsOldObject() && | |
| 6500 !data()->IsRemembered()) { | |
| 6501 data()->SetRememberedBit(); | |
| 6502 Isolate::Current()->store_buffer()->AddObject(data()); | |
| 6503 } | |
| 6504 } | 6476 } |
| 6505 | 6477 |
| 6506 static const int kDefaultInitialCapacity = 4; | 6478 static const int kDefaultInitialCapacity = 4; |
| 6507 | 6479 |
| 6508 FINAL_HEAP_OBJECT_IMPLEMENTATION(GrowableObjectArray, Instance); | 6480 FINAL_HEAP_OBJECT_IMPLEMENTATION(GrowableObjectArray, Instance); |
| 6509 friend class Array; | 6481 friend class Array; |
| 6510 friend class Class; | 6482 friend class Class; |
| 6511 }; | 6483 }; |
| 6512 | 6484 |
| 6513 | 6485 |
| (...skipping 804 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 7318 StorePointer(&raw_ptr()->value_, value.raw()); | 7290 StorePointer(&raw_ptr()->value_, value.raw()); |
| 7319 } | 7291 } |
| 7320 | 7292 |
| 7321 static RawWeakProperty* New(Heap::Space space = Heap::kNew); | 7293 static RawWeakProperty* New(Heap::Space space = Heap::kNew); |
| 7322 | 7294 |
| 7323 static intptr_t InstanceSize() { | 7295 static intptr_t InstanceSize() { |
| 7324 return RoundedAllocationSize(sizeof(RawWeakProperty)); | 7296 return RoundedAllocationSize(sizeof(RawWeakProperty)); |
| 7325 } | 7297 } |
| 7326 | 7298 |
| 7327 static void Clear(RawWeakProperty* raw_weak) { | 7299 static void Clear(RawWeakProperty* raw_weak) { |
| 7328 raw_weak->ptr()->key_ = Object::null(); | 7300 raw_weak->StorePointer(&(raw_weak->ptr()->key_), Object::null()); |
| 7329 raw_weak->ptr()->value_ = Object::null(); | 7301 raw_weak->StorePointer(&(raw_weak->ptr()->value_), Object::null()); |
| 7330 } | 7302 } |
| 7331 | 7303 |
| 7332 private: | 7304 private: |
| 7333 FINAL_HEAP_OBJECT_IMPLEMENTATION(WeakProperty, Instance); | 7305 FINAL_HEAP_OBJECT_IMPLEMENTATION(WeakProperty, Instance); |
| 7334 friend class Class; | 7306 friend class Class; |
| 7335 }; | 7307 }; |
| 7336 | 7308 |
| 7337 | 7309 |
| 7338 class MirrorReference : public Instance { | 7310 class MirrorReference : public Instance { |
| 7339 public: | 7311 public: |
| (...skipping 211 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 7551 | 7523 |
| 7552 | 7524 |
| 7553 RawObject* MegamorphicCache::GetTargetFunction(const Array& array, | 7525 RawObject* MegamorphicCache::GetTargetFunction(const Array& array, |
| 7554 intptr_t index) { | 7526 intptr_t index) { |
| 7555 return array.At((index * kEntryLength) + kTargetFunctionIndex); | 7527 return array.At((index * kEntryLength) + kTargetFunctionIndex); |
| 7556 } | 7528 } |
| 7557 | 7529 |
| 7558 } // namespace dart | 7530 } // namespace dart |
| 7559 | 7531 |
| 7560 #endif // VM_OBJECT_H_ | 7532 #endif // VM_OBJECT_H_ |
| OLD | NEW |