| OLD | NEW |
| 1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #ifndef V8_SERIALIZE_H_ | 5 #ifndef V8_SERIALIZE_H_ |
| 6 #define V8_SERIALIZE_H_ | 6 #define V8_SERIALIZE_H_ |
| 7 | 7 |
| 8 #include "src/compiler.h" | 8 #include "src/compiler.h" |
| 9 #include "src/hashmap.h" | 9 #include "src/hashmap.h" |
| 10 #include "src/heap-profiler.h" | 10 #include "src/heap-profiler.h" |
| (...skipping 431 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 442 // A bitmask for getting the space out of an instruction. | 442 // A bitmask for getting the space out of an instruction. |
| 443 static const int kSpaceMask = 7; | 443 static const int kSpaceMask = 7; |
| 444 STATIC_ASSERT(kNumberOfSpaces <= kSpaceMask + 1); | 444 STATIC_ASSERT(kNumberOfSpaces <= kSpaceMask + 1); |
| 445 | 445 |
| 446 // Sentinel after a new object to indicate that double alignment is needed. | 446 // Sentinel after a new object to indicate that double alignment is needed. |
| 447 static const int kDoubleAlignmentSentinel = 0; | 447 static const int kDoubleAlignmentSentinel = 0; |
| 448 | 448 |
| 449 // Used as index for the attached reference representing the source object. | 449 // Used as index for the attached reference representing the source object. |
| 450 static const int kSourceObjectReference = 0; | 450 static const int kSourceObjectReference = 0; |
| 451 | 451 |
| 452 // Used as index for the attached reference representing the global proxy. |
| 453 static const int kGlobalProxyReference = 0; |
| 454 |
| 452 HotObjectsList hot_objects_; | 455 HotObjectsList hot_objects_; |
| 453 }; | 456 }; |
| 454 | 457 |
| 455 | 458 |
| 456 class SerializedData { | 459 class SerializedData { |
| 457 public: | 460 public: |
| 458 class Reservation { | 461 class Reservation { |
| 459 public: | 462 public: |
| 460 explicit Reservation(uint32_t size) | 463 explicit Reservation(uint32_t size) |
| 461 : reservation_(ChunkSizeBits::encode(size)) {} | 464 : reservation_(ChunkSizeBits::encode(size)) {} |
| (...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 499 }; | 502 }; |
| 500 | 503 |
| 501 | 504 |
| 502 // A Deserializer reads a snapshot and reconstructs the Object graph it defines. | 505 // A Deserializer reads a snapshot and reconstructs the Object graph it defines. |
| 503 class Deserializer: public SerializerDeserializer { | 506 class Deserializer: public SerializerDeserializer { |
| 504 public: | 507 public: |
| 505 // Create a deserializer from a snapshot byte source. | 508 // Create a deserializer from a snapshot byte source. |
| 506 template <class Data> | 509 template <class Data> |
| 507 explicit Deserializer(Data* data) | 510 explicit Deserializer(Data* data) |
| 508 : isolate_(NULL), | 511 : isolate_(NULL), |
| 509 attached_objects_(NULL), | |
| 510 source_(data->Payload()), | 512 source_(data->Payload()), |
| 511 external_reference_decoder_(NULL), | 513 external_reference_decoder_(NULL), |
| 512 deserialized_large_objects_(0) { | 514 deserialized_large_objects_(0), |
| 515 deserializing_user_code_(false) { |
| 513 DecodeReservation(data->Reservations()); | 516 DecodeReservation(data->Reservations()); |
| 514 } | 517 } |
| 515 | 518 |
| 516 virtual ~Deserializer(); | 519 virtual ~Deserializer(); |
| 517 | 520 |
| 518 // Deserialize the snapshot into an empty heap. | 521 // Deserialize the snapshot into an empty heap. |
| 519 void Deserialize(Isolate* isolate); | 522 void Deserialize(Isolate* isolate); |
| 520 | 523 |
| 521 // Deserialize a single object and the objects reachable from it. | 524 // Deserialize a single object and the objects reachable from it. |
| 522 // We may want to abort gracefully even if deserialization fails. | |
| 523 MaybeHandle<Object> DeserializePartial( | 525 MaybeHandle<Object> DeserializePartial( |
| 524 Isolate* isolate, Handle<FixedArray>* outdated_contexts_out); | 526 Isolate* isolate, Handle<JSGlobalProxy> global_proxy, |
| 527 Handle<FixedArray>* outdated_contexts_out); |
| 525 | 528 |
| 529 // Deserialize a shared function info. Fail gracefully. |
| 526 MaybeHandle<SharedFunctionInfo> DeserializeCode(Isolate* isolate); | 530 MaybeHandle<SharedFunctionInfo> DeserializeCode(Isolate* isolate); |
| 527 | 531 |
| 528 void FlushICacheForNewCodeObjects(); | 532 void FlushICacheForNewCodeObjects(); |
| 529 | 533 |
| 530 // Serialized user code reference certain objects that are provided in a list | 534 // Pass a vector of externally-provided objects referenced by the snapshot. |
| 531 // By calling this method, we assume that we are deserializing user code. | 535 // The ownership to its backing store is handed over as well. |
| 532 void SetAttachedObjects(Vector<Handle<Object> >* attached_objects) { | 536 void SetAttachedObjects(Vector<Handle<Object> > attached_objects) { |
| 533 attached_objects_ = attached_objects; | 537 attached_objects_ = attached_objects; |
| 534 } | 538 } |
| 535 | 539 |
| 536 bool deserializing_user_code() { return attached_objects_ != NULL; } | |
| 537 | |
| 538 private: | 540 private: |
| 539 virtual void VisitPointers(Object** start, Object** end); | 541 virtual void VisitPointers(Object** start, Object** end); |
| 540 | 542 |
| 541 virtual void VisitRuntimeEntry(RelocInfo* rinfo) { | 543 virtual void VisitRuntimeEntry(RelocInfo* rinfo) { |
| 542 UNREACHABLE(); | 544 UNREACHABLE(); |
| 543 } | 545 } |
| 544 | 546 |
| 545 void Initialize(Isolate* isolate); | 547 void Initialize(Isolate* isolate); |
| 546 | 548 |
| 549 bool deserializing_user_code() { return deserializing_user_code_; } |
| 550 |
| 547 void DecodeReservation(Vector<const SerializedData::Reservation> res); | 551 void DecodeReservation(Vector<const SerializedData::Reservation> res); |
| 548 | 552 |
| 549 bool ReserveSpace(); | 553 bool ReserveSpace(); |
| 550 | 554 |
| 551 void UnalignedCopy(Object** dest, Object** src) { | 555 void UnalignedCopy(Object** dest, Object** src) { |
| 552 memcpy(dest, src, sizeof(*src)); | 556 memcpy(dest, src, sizeof(*src)); |
| 553 } | 557 } |
| 554 | 558 |
| 555 // Allocation sites are present in the snapshot, and must be linked into | 559 // Allocation sites are present in the snapshot, and must be linked into |
| 556 // a list at deserialization time. | 560 // a list at deserialization time. |
| (...skipping 13 matching lines...) Expand all Loading... |
| 570 HeapObject* ProcessNewObjectFromSerializedCode(HeapObject* obj); | 574 HeapObject* ProcessNewObjectFromSerializedCode(HeapObject* obj); |
| 571 | 575 |
| 572 // This returns the address of an object that has been described in the | 576 // This returns the address of an object that has been described in the |
| 573 // snapshot by chunk index and offset. | 577 // snapshot by chunk index and offset. |
| 574 HeapObject* GetBackReferencedObject(int space); | 578 HeapObject* GetBackReferencedObject(int space); |
| 575 | 579 |
| 576 // Cached current isolate. | 580 // Cached current isolate. |
| 577 Isolate* isolate_; | 581 Isolate* isolate_; |
| 578 | 582 |
| 579 // Objects from the attached object descriptions in the serialized user code. | 583 // Objects from the attached object descriptions in the serialized user code. |
| 580 Vector<Handle<Object> >* attached_objects_; | 584 Vector<Handle<Object> > attached_objects_; |
| 581 | 585 |
| 582 SnapshotByteSource source_; | 586 SnapshotByteSource source_; |
| 583 // The address of the next object that will be allocated in each space. | 587 // The address of the next object that will be allocated in each space. |
| 584 // Each space has a number of chunks reserved by the GC, with each chunk | 588 // Each space has a number of chunks reserved by the GC, with each chunk |
| 585 // fitting into a page. Deserialized objects are allocated into the | 589 // fitting into a page. Deserialized objects are allocated into the |
| 586 // current chunk of the target space by bumping up high water mark. | 590 // current chunk of the target space by bumping up high water mark. |
| 587 Heap::Reservation reservations_[kNumberOfSpaces]; | 591 Heap::Reservation reservations_[kNumberOfSpaces]; |
| 588 uint32_t current_chunk_[kNumberOfPreallocatedSpaces]; | 592 uint32_t current_chunk_[kNumberOfPreallocatedSpaces]; |
| 589 Address high_water_[kNumberOfPreallocatedSpaces]; | 593 Address high_water_[kNumberOfPreallocatedSpaces]; |
| 590 | 594 |
| 591 ExternalReferenceDecoder* external_reference_decoder_; | 595 ExternalReferenceDecoder* external_reference_decoder_; |
| 592 | 596 |
| 593 List<HeapObject*> deserialized_large_objects_; | 597 List<HeapObject*> deserialized_large_objects_; |
| 594 | 598 |
| 599 bool deserializing_user_code_; |
| 600 |
| 595 DISALLOW_COPY_AND_ASSIGN(Deserializer); | 601 DISALLOW_COPY_AND_ASSIGN(Deserializer); |
| 596 }; | 602 }; |
| 597 | 603 |
| 598 | 604 |
| 599 class CodeAddressMap; | 605 class CodeAddressMap; |
| 600 | 606 |
| 601 // There can be only one serializer per V8 process. | 607 // There can be only one serializer per V8 process. |
| 602 class Serializer : public SerializerDeserializer { | 608 class Serializer : public SerializerDeserializer { |
| 603 public: | 609 public: |
| 604 Serializer(Isolate* isolate, SnapshotByteSink* sink); | 610 Serializer(Isolate* isolate, SnapshotByteSink* sink); |
| (...skipping 133 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 738 }; | 744 }; |
| 739 | 745 |
| 740 | 746 |
| 741 class PartialSerializer : public Serializer { | 747 class PartialSerializer : public Serializer { |
| 742 public: | 748 public: |
| 743 PartialSerializer(Isolate* isolate, Serializer* startup_snapshot_serializer, | 749 PartialSerializer(Isolate* isolate, Serializer* startup_snapshot_serializer, |
| 744 SnapshotByteSink* sink) | 750 SnapshotByteSink* sink) |
| 745 : Serializer(isolate, sink), | 751 : Serializer(isolate, sink), |
| 746 startup_serializer_(startup_snapshot_serializer), | 752 startup_serializer_(startup_snapshot_serializer), |
| 747 outdated_contexts_(0), | 753 outdated_contexts_(0), |
| 748 global_object_(NULL) { | 754 global_object_(NULL), |
| 755 global_proxy_(NULL) { |
| 749 InitializeCodeAddressMap(); | 756 InitializeCodeAddressMap(); |
| 750 } | 757 } |
| 751 | 758 |
| 752 // Serialize the objects reachable from a single object pointer. | 759 // Serialize the objects reachable from a single object pointer. |
| 753 void Serialize(Object** o); | 760 void Serialize(Object** o); |
| 754 virtual void SerializeObject(HeapObject* o, HowToCode how_to_code, | 761 virtual void SerializeObject(HeapObject* o, HowToCode how_to_code, |
| 755 WhereToPoint where_to_point, int skip) OVERRIDE; | 762 WhereToPoint where_to_point, int skip) OVERRIDE; |
| 756 | 763 |
| 757 private: | 764 private: |
| 758 int PartialSnapshotCacheIndex(HeapObject* o); | 765 int PartialSnapshotCacheIndex(HeapObject* o); |
| 759 bool ShouldBeInThePartialSnapshotCache(HeapObject* o) { | 766 bool ShouldBeInThePartialSnapshotCache(HeapObject* o) { |
| 760 // Scripts should be referred only through shared function infos. We can't | 767 // Scripts should be referred only through shared function infos. We can't |
| 761 // allow them to be part of the partial snapshot because they contain a | 768 // allow them to be part of the partial snapshot because they contain a |
| 762 // unique ID, and deserializing several partial snapshots containing script | 769 // unique ID, and deserializing several partial snapshots containing script |
| 763 // would cause dupes. | 770 // would cause dupes. |
| 764 DCHECK(!o->IsScript()); | 771 DCHECK(!o->IsScript()); |
| 765 return o->IsName() || o->IsSharedFunctionInfo() || | 772 return o->IsName() || o->IsSharedFunctionInfo() || |
| 766 o->IsHeapNumber() || o->IsCode() || | 773 o->IsHeapNumber() || o->IsCode() || |
| 767 o->IsScopeInfo() || | 774 o->IsScopeInfo() || |
| 768 o->map() == | 775 o->map() == |
| 769 startup_serializer_->isolate()->heap()->fixed_cow_array_map(); | 776 startup_serializer_->isolate()->heap()->fixed_cow_array_map(); |
| 770 } | 777 } |
| 771 | 778 |
| 772 void SerializeOutdatedContextsAsFixedArray(); | 779 void SerializeOutdatedContextsAsFixedArray(); |
| 773 | 780 |
| 774 Serializer* startup_serializer_; | 781 Serializer* startup_serializer_; |
| 775 List<BackReference> outdated_contexts_; | 782 List<BackReference> outdated_contexts_; |
| 776 Object* global_object_; | 783 Object* global_object_; |
| 784 Object* global_proxy_; |
| 777 DISALLOW_COPY_AND_ASSIGN(PartialSerializer); | 785 DISALLOW_COPY_AND_ASSIGN(PartialSerializer); |
| 778 }; | 786 }; |
| 779 | 787 |
| 780 | 788 |
| 781 class StartupSerializer : public Serializer { | 789 class StartupSerializer : public Serializer { |
| 782 public: | 790 public: |
| 783 StartupSerializer(Isolate* isolate, SnapshotByteSink* sink) | 791 StartupSerializer(Isolate* isolate, SnapshotByteSink* sink) |
| 784 : Serializer(isolate, sink), root_index_wave_front_(0) { | 792 : Serializer(isolate, sink), root_index_wave_front_(0) { |
| 785 // Clear the cache of objects used by the partial snapshot. After the | 793 // Clear the cache of objects used by the partial snapshot. After the |
| 786 // strong roots have been serialized we can create a partial snapshot | 794 // strong roots have been serialized we can create a partial snapshot |
| (...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 848 | 856 |
| 849 virtual void SerializeObject(HeapObject* o, HowToCode how_to_code, | 857 virtual void SerializeObject(HeapObject* o, HowToCode how_to_code, |
| 850 WhereToPoint where_to_point, int skip) OVERRIDE; | 858 WhereToPoint where_to_point, int skip) OVERRIDE; |
| 851 | 859 |
| 852 void SerializeBuiltin(int builtin_index, HowToCode how_to_code, | 860 void SerializeBuiltin(int builtin_index, HowToCode how_to_code, |
| 853 WhereToPoint where_to_point); | 861 WhereToPoint where_to_point); |
| 854 void SerializeIC(Code* ic, HowToCode how_to_code, | 862 void SerializeIC(Code* ic, HowToCode how_to_code, |
| 855 WhereToPoint where_to_point); | 863 WhereToPoint where_to_point); |
| 856 void SerializeCodeStub(uint32_t stub_key, HowToCode how_to_code, | 864 void SerializeCodeStub(uint32_t stub_key, HowToCode how_to_code, |
| 857 WhereToPoint where_to_point); | 865 WhereToPoint where_to_point); |
| 858 void SerializeSourceObject(HowToCode how_to_code, | |
| 859 WhereToPoint where_to_point); | |
| 860 void SerializeGeneric(HeapObject* heap_object, HowToCode how_to_code, | 866 void SerializeGeneric(HeapObject* heap_object, HowToCode how_to_code, |
| 861 WhereToPoint where_to_point); | 867 WhereToPoint where_to_point); |
| 862 int AddCodeStubKey(uint32_t stub_key); | 868 int AddCodeStubKey(uint32_t stub_key); |
| 863 | 869 |
| 864 DisallowHeapAllocation no_gc_; | 870 DisallowHeapAllocation no_gc_; |
| 865 String* source_; | 871 String* source_; |
| 866 Code* main_code_; | 872 Code* main_code_; |
| 867 int num_internalized_strings_; | 873 int num_internalized_strings_; |
| 868 List<uint32_t> stub_keys_; | 874 List<uint32_t> stub_keys_; |
| 869 DISALLOW_COPY_AND_ASSIGN(CodeSerializer); | 875 DISALLOW_COPY_AND_ASSIGN(CodeSerializer); |
| (...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 945 static const int kCheckSumOffset = 0; | 951 static const int kCheckSumOffset = 0; |
| 946 static const int kNumInternalizedStringsOffset = 1; | 952 static const int kNumInternalizedStringsOffset = 1; |
| 947 static const int kReservationsOffset = 2; | 953 static const int kReservationsOffset = 2; |
| 948 static const int kNumCodeStubKeysOffset = 3; | 954 static const int kNumCodeStubKeysOffset = 3; |
| 949 static const int kPayloadLengthOffset = 4; | 955 static const int kPayloadLengthOffset = 4; |
| 950 static const int kHeaderSize = (kPayloadLengthOffset + 1) * kIntSize; | 956 static const int kHeaderSize = (kPayloadLengthOffset + 1) * kIntSize; |
| 951 }; | 957 }; |
| 952 } } // namespace v8::internal | 958 } } // namespace v8::internal |
| 953 | 959 |
| 954 #endif // V8_SERIALIZE_H_ | 960 #endif // V8_SERIALIZE_H_ |
| OLD | NEW |