Chromium Code Reviews| 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_DART_API_STATE_H_ | 5 #ifndef VM_DART_API_STATE_H_ |
| 6 #define VM_DART_API_STATE_H_ | 6 #define VM_DART_API_STATE_H_ |
| 7 | 7 |
| 8 #include "include/dart_api.h" | 8 #include "include/dart_api.h" |
| 9 | 9 |
| 10 #include "platform/thread.h" | 10 #include "platform/thread.h" |
| (...skipping 10 matching lines...) Expand all Loading... | |
| 21 | 21 |
| 22 namespace dart { | 22 namespace dart { |
| 23 | 23 |
| 24 // Implementation of Zone support for very fast allocation of small chunks | 24 // Implementation of Zone support for very fast allocation of small chunks |
| 25 // of memory. The chunks cannot be deallocated individually, but instead | 25 // of memory. The chunks cannot be deallocated individually, but instead |
| 26 // zones support deallocating all chunks in one fast operation when the | 26 // zones support deallocating all chunks in one fast operation when the |
| 27 // scope is exited. | 27 // scope is exited. |
| 28 class ApiZone { | 28 class ApiZone { |
| 29 public: | 29 public: |
| 30 // Create an empty zone. | 30 // Create an empty zone. |
| 31 ApiZone() : zone_() { } | 31 ApiZone() : zone_() { |
| 32 Isolate* isolate = Isolate::Current(); | |
| 33 Zone* current_zone = isolate != NULL ? isolate->current_zone() : NULL; | |
| 34 zone_.Link(current_zone); | |
| 35 if (isolate != NULL) { | |
| 36 isolate->set_current_zone(&zone_); | |
| 37 } | |
| 38 } | |
| 32 | 39 |
| 33 // Delete all memory associated with the zone. | 40 // Delete all memory associated with the zone. |
| 34 ~ApiZone() { } | 41 ~ApiZone() { |
| 42 Isolate* isolate = Isolate::Current(); | |
| 43 if (isolate != NULL && isolate->current_zone() == &zone_) { | |
| 44 isolate->set_current_zone(zone_.previous_); | |
| 45 } | |
| 46 zone_.Unlink(); | |
| 47 } | |
| 35 | 48 |
| 36 // Allocates an array sized to hold 'len' elements of type | 49 // Allocates an array sized to hold 'len' elements of type |
| 37 // 'ElementType'. Checks for integer overflow when performing the | 50 // 'ElementType'. Checks for integer overflow when performing the |
| 38 // size computation. | 51 // size computation. |
| 39 template <class ElementType> | 52 template <class ElementType> |
| 40 ElementType* Alloc(intptr_t len) { return zone_.Alloc<ElementType>(len); } | 53 ElementType* Alloc(intptr_t len) { return zone_.Alloc<ElementType>(len); } |
| 41 | 54 |
| 42 // Allocates an array sized to hold 'len' elements of type | 55 // Allocates an array sized to hold 'len' elements of type |
| 43 // 'ElementType'. The new array is initialized from the memory of | 56 // 'ElementType'. The new array is initialized from the memory of |
| 44 // 'old_array' up to 'old_len'. | 57 // 'old_array' up to 'old_len'. |
| 45 template <class ElementType> | 58 template <class ElementType> |
| 46 ElementType* Realloc(ElementType* old_array, | 59 ElementType* Realloc(ElementType* old_array, |
| 47 intptr_t old_len, | 60 intptr_t old_len, |
| 48 intptr_t new_len) { | 61 intptr_t new_len) { |
| 49 return zone_.Realloc<ElementType>(old_array, old_len, new_len); | 62 return zone_.Realloc<ElementType>(old_array, old_len, new_len); |
| 50 } | 63 } |
| 51 | 64 |
| 52 // Allocates 'size' bytes of memory in the zone; expands the zone by | 65 // Allocates 'size' bytes of memory in the zone; expands the zone by |
| 53 // allocating new segments of memory on demand using 'new'. | 66 // allocating new segments of memory on demand using 'new'. |
| 54 // | 67 // |
| 55 // It is preferred to use Alloc<T>() instead, as that function can | 68 // It is preferred to use Alloc<T>() instead, as that function can |
| 56 // check for integer overflow. If you use AllocUnsafe, you are | 69 // check for integer overflow. If you use AllocUnsafe, you are |
| 57 // responsible for avoiding integer overflow yourself. | 70 // responsible for avoiding integer overflow yourself. |
| 58 uword AllocUnsafe(intptr_t size) { return zone_.AllocUnsafe(size); } | 71 uword AllocUnsafe(intptr_t size) { return zone_.AllocUnsafe(size); } |
| 59 | 72 |
| 60 // Compute the total size of this zone. This includes wasted space that is | 73 // Compute the total size of this zone. This includes wasted space that is |
| 61 // due to internal fragmentation in the segments. | 74 // due to internal fragmentation in the segments. |
| 62 intptr_t SizeInBytes() const { return zone_.SizeInBytes(); } | 75 intptr_t SizeInBytes() const { return zone_.SizeInBytes(); } |
| 63 | 76 |
| 77 Zone* GetZone() { return &zone_; } | |
| 78 | |
| 64 private: | 79 private: |
| 65 Zone* GetBaseZone() { return &zone_; } | |
| 66 | |
| 67 Zone zone_; | 80 Zone zone_; |
| 68 | 81 |
| 69 template<typename T> friend class ApiGrowableArray; | 82 template<typename T> friend class ApiGrowableArray; |
| 70 DISALLOW_COPY_AND_ASSIGN(ApiZone); | 83 DISALLOW_COPY_AND_ASSIGN(ApiZone); |
| 71 }; | 84 }; |
| 72 | 85 |
| 73 | 86 |
| 74 // Implementation of local handles which are handed out from every | 87 // Implementation of local handles which are handed out from every |
| 75 // dart API call, these handles are valid only in the present scope | 88 // dart API call, these handles are valid only in the present scope |
| 76 // and are destroyed when a Dart_ExitScope() is called. | 89 // and are destroyed when a Dart_ExitScope() is called. |
| (...skipping 352 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 429 intptr_t num_values_; | 442 intptr_t num_values_; |
| 430 DISALLOW_COPY_AND_ASSIGN(WeakReferenceSet); | 443 DISALLOW_COPY_AND_ASSIGN(WeakReferenceSet); |
| 431 }; | 444 }; |
| 432 | 445 |
| 433 | 446 |
| 434 // Structure used for the implementation of local scopes used in dart_api. | 447 // Structure used for the implementation of local scopes used in dart_api. |
| 435 // These local scopes manage handles and memory allocated in the scope. | 448 // These local scopes manage handles and memory allocated in the scope. |
| 436 class ApiLocalScope { | 449 class ApiLocalScope { |
| 437 public: | 450 public: |
| 438 ApiLocalScope(ApiLocalScope* previous, uword stack_marker) : | 451 ApiLocalScope(ApiLocalScope* previous, uword stack_marker) : |
| 439 previous_(previous), stack_marker_(stack_marker) { } | 452 previous_(previous), stack_marker_(stack_marker) { |
|
Ivan Posva
2012/10/12 21:46:33
Emptr constructors on one line.
Tom Ball
2012/10/12 22:56:51
Done.
| |
| 453 } | |
| 440 ~ApiLocalScope() { | 454 ~ApiLocalScope() { |
| 441 previous_ = NULL; | 455 previous_ = NULL; |
| 442 } | 456 } |
| 443 | 457 |
| 444 // Accessors. | 458 // Accessors. |
| 445 ApiLocalScope* previous() const { return previous_; } | 459 ApiLocalScope* previous() const { return previous_; } |
| 446 uword stack_marker() const { return stack_marker_; } | 460 uword stack_marker() const { return stack_marker_; } |
| 447 void set_previous(ApiLocalScope* value) { previous_ = value; } | 461 void set_previous(ApiLocalScope* value) { previous_ = value; } |
| 448 LocalHandles* local_handles() { return &local_handles_; } | 462 LocalHandles* local_handles() { return &local_handles_; } |
| 449 ApiZone* zone() { return &zone_; } | 463 Zone* zone() { return zone_.GetZone(); } |
| 450 | 464 |
| 451 private: | 465 private: |
| 452 ApiLocalScope* previous_; | 466 ApiLocalScope* previous_; |
| 453 uword stack_marker_; | 467 uword stack_marker_; |
| 454 LocalHandles local_handles_; | 468 LocalHandles local_handles_; |
| 455 ApiZone zone_; | 469 ApiZone zone_; |
| 456 | 470 |
| 457 DISALLOW_COPY_AND_ASSIGN(ApiLocalScope); | 471 DISALLOW_COPY_AND_ASSIGN(ApiLocalScope); |
| 458 }; | 472 }; |
| 459 | 473 |
| (...skipping 186 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 646 ~ApiNativeScope() { | 660 ~ApiNativeScope() { |
| 647 ASSERT(Current() == this); | 661 ASSERT(Current() == this); |
| 648 Thread::SetThreadLocal(Api::api_native_key_, 0); | 662 Thread::SetThreadLocal(Api::api_native_key_, 0); |
| 649 } | 663 } |
| 650 | 664 |
| 651 static inline ApiNativeScope* Current() { | 665 static inline ApiNativeScope* Current() { |
| 652 return reinterpret_cast<ApiNativeScope*>( | 666 return reinterpret_cast<ApiNativeScope*>( |
| 653 Thread::GetThreadLocal(Api::api_native_key_)); | 667 Thread::GetThreadLocal(Api::api_native_key_)); |
| 654 } | 668 } |
| 655 | 669 |
| 656 ApiZone* zone() { return &zone_; } | 670 Zone* zone() { return zone_.GetZone(); } |
| 657 | 671 |
| 658 private: | 672 private: |
| 659 ApiZone zone_; | 673 ApiZone zone_; |
| 660 ThreadLocalKey key_; | 674 ThreadLocalKey key_; |
| 661 }; | 675 }; |
| 662 | 676 |
| 663 | 677 |
| 664 // Api growable arrays use a zone for allocation. The constructor | 678 // Api growable arrays use a zone for allocation. The constructor |
| 665 // picks the zone from the current isolate if in an isolate | 679 // picks the zone from the current isolate if in an isolate |
| 666 // environment. When outside an isolate environment it picks the zone | 680 // environment. When outside an isolate environment it picks the zone |
| 667 // from the current native scope. | 681 // from the current native scope. |
| 668 template<typename T> | 682 template<typename T> |
| 669 class ApiGrowableArray : public BaseGrowableArray<T, ValueObject> { | 683 class ApiGrowableArray : public BaseGrowableArray<T, ValueObject> { |
| 670 public: | 684 public: |
| 671 explicit ApiGrowableArray(int initial_capacity) | 685 explicit ApiGrowableArray(int initial_capacity) |
| 672 : BaseGrowableArray<T, ValueObject>( | 686 : BaseGrowableArray<T, ValueObject>( |
| 673 initial_capacity, | 687 initial_capacity, |
| 674 ApiNativeScope::Current()->zone()->GetBaseZone()) {} | 688 ApiNativeScope::Current()->zone()) {} |
| 675 ApiGrowableArray() | 689 ApiGrowableArray() |
| 676 : BaseGrowableArray<T, ValueObject>( | 690 : BaseGrowableArray<T, ValueObject>( |
| 677 ApiNativeScope::Current()->zone()->GetBaseZone()) {} | 691 ApiNativeScope::Current()->zone()) {} |
| 678 }; | 692 }; |
| 679 | 693 |
| 680 | 694 |
| 681 } // namespace dart | 695 } // namespace dart |
| 682 | 696 |
| 683 #endif // VM_DART_API_STATE_H_ | 697 #endif // VM_DART_API_STATE_H_ |
| OLD | NEW |