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

Side by Side Diff: src/snapshot/serialize.cc

Issue 1204863006: Serializer: commit new internalized strings after deserialization. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.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 | « src/snapshot/serialize.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 #include "src/v8.h" 5 #include "src/v8.h"
6 6
7 #include "src/accessors.h" 7 #include "src/accessors.h"
8 #include "src/api.h" 8 #include "src/api.h"
9 #include "src/base/platform/platform.h" 9 #include "src/base/platform/platform.h"
10 #include "src/bootstrapper.h" 10 #include "src/bootstrapper.h"
(...skipping 624 matching lines...) Expand 10 before | Expand all | Expand 10 after
635 } 635 }
636 636
637 637
638 MaybeHandle<SharedFunctionInfo> Deserializer::DeserializeCode( 638 MaybeHandle<SharedFunctionInfo> Deserializer::DeserializeCode(
639 Isolate* isolate) { 639 Isolate* isolate) {
640 Initialize(isolate); 640 Initialize(isolate);
641 if (!ReserveSpace()) { 641 if (!ReserveSpace()) {
642 return Handle<SharedFunctionInfo>(); 642 return Handle<SharedFunctionInfo>();
643 } else { 643 } else {
644 deserializing_user_code_ = true; 644 deserializing_user_code_ = true;
645 DisallowHeapAllocation no_gc; 645 HandleScope scope(isolate);
646 Object* root; 646 Handle<SharedFunctionInfo> result;
647 VisitPointer(&root); 647 {
648 DeserializeDeferredObjects(); 648 DisallowHeapAllocation no_gc;
649 return Handle<SharedFunctionInfo>(SharedFunctionInfo::cast(root)); 649 Object* root;
650 VisitPointer(&root);
651 DeserializeDeferredObjects();
652 result = Handle<SharedFunctionInfo>(SharedFunctionInfo::cast(root));
653 }
654 CommitNewInternalizedStrings(isolate);
655 return scope.CloseAndEscape(result);
650 } 656 }
651 } 657 }
652 658
653 659
654 Deserializer::~Deserializer() { 660 Deserializer::~Deserializer() {
655 // TODO(svenpanne) Re-enable this assertion when v8 initialization is fixed. 661 // TODO(svenpanne) Re-enable this assertion when v8 initialization is fixed.
656 // DCHECK(source_.AtEOF()); 662 // DCHECK(source_.AtEOF());
657 attached_objects_.Dispose(); 663 attached_objects_.Dispose();
658 } 664 }
659 665
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
704 uint32_t Hash() override { return hash_; } 710 uint32_t Hash() override { return hash_; }
705 711
706 uint32_t HashForObject(Object* key) override { 712 uint32_t HashForObject(Object* key) override {
707 return String::cast(key)->Hash(); 713 return String::cast(key)->Hash();
708 } 714 }
709 715
710 MUST_USE_RESULT virtual Handle<Object> AsHandle(Isolate* isolate) override { 716 MUST_USE_RESULT virtual Handle<Object> AsHandle(Isolate* isolate) override {
711 return handle(string_, isolate); 717 return handle(string_, isolate);
712 } 718 }
713 719
720 private:
714 String* string_; 721 String* string_;
715 uint32_t hash_; 722 uint32_t hash_;
723 DisallowHeapAllocation no_gc;
716 }; 724 };
717 725
718 726
719 HeapObject* Deserializer::PostProcessNewObject(HeapObject* obj, int space) { 727 HeapObject* Deserializer::PostProcessNewObject(HeapObject* obj, int space) {
720 if (deserializing_user_code()) { 728 if (deserializing_user_code()) {
721 if (obj->IsString()) { 729 if (obj->IsString()) {
722 String* string = String::cast(obj); 730 String* string = String::cast(obj);
723 // Uninitialize hash field as the hash seed may have changed. 731 // Uninitialize hash field as the hash seed may have changed.
724 string->set_hash_field(String::kEmptyHashField); 732 string->set_hash_field(String::kEmptyHashField);
725 if (string->IsInternalizedString()) { 733 if (string->IsInternalizedString()) {
726 // Canonicalize the internalized string. If it already exists in the 734 // Canonicalize the internalized string. If it already exists in the
727 // string table, set it to forward to the existing one. 735 // string table, set it to forward to the existing one.
728 DisallowHeapAllocation no_gc;
729 HandleScope scope(isolate_);
730 StringTableInsertionKey key(string); 736 StringTableInsertionKey key(string);
731 String* canonical = *StringTable::LookupKey(isolate_, &key); 737 String* canonical = StringTable::LookupKeyIfExists(isolate_, &key);
732 string->SetForwardedInternalizedString(canonical); 738 if (canonical == NULL) {
733 return canonical; 739 new_internalized_strings_.Add(handle(string));
740 return string;
741 } else {
742 string->SetForwardedInternalizedString(canonical);
743 return canonical;
744 }
734 } 745 }
735 } else if (obj->IsScript()) { 746 } else if (obj->IsScript()) {
736 // Assign a new script id to avoid collision. 747 // Assign a new script id to avoid collision.
737 Script::cast(obj)->set_id(isolate_->heap()->NextScriptId()); 748 Script::cast(obj)->set_id(isolate_->heap()->NextScriptId());
738 } else { 749 } else {
739 DCHECK(CanBeDeferred(obj)); 750 DCHECK(CanBeDeferred(obj));
740 } 751 }
741 } 752 }
742 if (obj->IsAllocationSite()) { 753 if (obj->IsAllocationSite()) {
743 DCHECK(obj->IsAllocationSite()); 754 DCHECK(obj->IsAllocationSite());
(...skipping 16 matching lines...) Expand all
760 if (deserializing_user_code() || space == LO_SPACE) { 771 if (deserializing_user_code() || space == LO_SPACE) {
761 new_code_objects_.Add(Code::cast(obj)); 772 new_code_objects_.Add(Code::cast(obj));
762 } 773 }
763 } 774 }
764 // Check alignment. 775 // Check alignment.
765 DCHECK_EQ(0, Heap::GetFillToAlign(obj->address(), obj->RequiredAlignment())); 776 DCHECK_EQ(0, Heap::GetFillToAlign(obj->address(), obj->RequiredAlignment()));
766 return obj; 777 return obj;
767 } 778 }
768 779
769 780
781 void Deserializer::CommitNewInternalizedStrings(Isolate* isolate) {
782 StringTable::EnsureCapacityForDeserialization(
783 isolate, new_internalized_strings_.length());
784 for (Handle<String> string : new_internalized_strings_) {
785 StringTableInsertionKey key(*string);
786 DCHECK_NULL(StringTable::LookupKeyIfExists(isolate, &key));
787 StringTable::LookupKey(isolate, &key);
788 }
789 }
790
791
770 HeapObject* Deserializer::GetBackReferencedObject(int space) { 792 HeapObject* Deserializer::GetBackReferencedObject(int space) {
771 HeapObject* obj; 793 HeapObject* obj;
772 BackReference back_reference(source_.GetInt()); 794 BackReference back_reference(source_.GetInt());
773 if (space == LO_SPACE) { 795 if (space == LO_SPACE) {
774 CHECK(back_reference.chunk_index() == 0); 796 CHECK(back_reference.chunk_index() == 0);
775 uint32_t index = back_reference.large_object_index(); 797 uint32_t index = back_reference.large_object_index();
776 obj = deserialized_large_objects_[index]; 798 obj = deserialized_large_objects_[index];
777 } else { 799 } else {
778 DCHECK(space < kNumberOfPreallocatedSpaces); 800 DCHECK(space < kNumberOfPreallocatedSpaces);
779 uint32_t chunk_index = back_reference.chunk_index(); 801 uint32_t chunk_index = back_reference.chunk_index();
(...skipping 1561 matching lines...) Expand 10 before | Expand all | Expand 10 after
2341 // We expect no instantiated function objects or contexts. 2363 // We expect no instantiated function objects or contexts.
2342 CHECK(!obj->IsJSFunction() && !obj->IsContext()); 2364 CHECK(!obj->IsJSFunction() && !obj->IsContext());
2343 2365
2344 SerializeGeneric(obj, how_to_code, where_to_point); 2366 SerializeGeneric(obj, how_to_code, where_to_point);
2345 } 2367 }
2346 2368
2347 2369
2348 void CodeSerializer::SerializeGeneric(HeapObject* heap_object, 2370 void CodeSerializer::SerializeGeneric(HeapObject* heap_object,
2349 HowToCode how_to_code, 2371 HowToCode how_to_code,
2350 WhereToPoint where_to_point) { 2372 WhereToPoint where_to_point) {
2351 if (heap_object->IsInternalizedString()) num_internalized_strings_++;
2352
2353 // Object has not yet been serialized. Serialize it here. 2373 // Object has not yet been serialized. Serialize it here.
2354 ObjectSerializer serializer(this, heap_object, sink_, how_to_code, 2374 ObjectSerializer serializer(this, heap_object, sink_, how_to_code,
2355 where_to_point); 2375 where_to_point);
2356 serializer.Serialize(); 2376 serializer.Serialize();
2357 } 2377 }
2358 2378
2359 2379
2360 void CodeSerializer::SerializeBuiltin(int builtin_index, HowToCode how_to_code, 2380 void CodeSerializer::SerializeBuiltin(int builtin_index, HowToCode how_to_code,
2361 WhereToPoint where_to_point) { 2381 WhereToPoint where_to_point) {
2362 DCHECK((how_to_code == kPlain && where_to_point == kStartOfObject) || 2382 DCHECK((how_to_code == kPlain && where_to_point == kStartOfObject) ||
(...skipping 101 matching lines...) Expand 10 before | Expand all | Expand 10 after
2464 // Prepare and register list of attached objects. 2484 // Prepare and register list of attached objects.
2465 Vector<const uint32_t> code_stub_keys = scd->CodeStubKeys(); 2485 Vector<const uint32_t> code_stub_keys = scd->CodeStubKeys();
2466 Vector<Handle<Object> > attached_objects = Vector<Handle<Object> >::New( 2486 Vector<Handle<Object> > attached_objects = Vector<Handle<Object> >::New(
2467 code_stub_keys.length() + kCodeStubsBaseIndex); 2487 code_stub_keys.length() + kCodeStubsBaseIndex);
2468 attached_objects[kSourceObjectIndex] = source; 2488 attached_objects[kSourceObjectIndex] = source;
2469 for (int i = 0; i < code_stub_keys.length(); i++) { 2489 for (int i = 0; i < code_stub_keys.length(); i++) {
2470 attached_objects[i + kCodeStubsBaseIndex] = 2490 attached_objects[i + kCodeStubsBaseIndex] =
2471 CodeStub::GetCode(isolate, code_stub_keys[i]).ToHandleChecked(); 2491 CodeStub::GetCode(isolate, code_stub_keys[i]).ToHandleChecked();
2472 } 2492 }
2473 2493
2474 // Eagerly expand string table to avoid allocations during deserialization.
2475 StringTable::EnsureCapacityForDeserialization(isolate,
2476 scd->NumInternalizedStrings());
2477
2478 Deserializer deserializer(scd.get()); 2494 Deserializer deserializer(scd.get());
2479 deserializer.SetAttachedObjects(attached_objects); 2495 deserializer.SetAttachedObjects(attached_objects);
2480 2496
2481 // Deserialize. 2497 // Deserialize.
2482 Handle<SharedFunctionInfo> result; 2498 Handle<SharedFunctionInfo> result;
2483 if (!deserializer.DeserializeCode(isolate).ToHandle(&result)) { 2499 if (!deserializer.DeserializeCode(isolate).ToHandle(&result)) {
2484 // Deserializing may fail if the reservations cannot be fulfilled. 2500 // Deserializing may fail if the reservations cannot be fulfilled.
2485 if (FLAG_profile_deserialization) PrintF("[Deserializing failed]\n"); 2501 if (FLAG_profile_deserialization) PrintF("[Deserializing failed]\n");
2486 return MaybeHandle<SharedFunctionInfo>(); 2502 return MaybeHandle<SharedFunctionInfo>();
2487 } 2503 }
(...skipping 138 matching lines...) Expand 10 before | Expand all | Expand 10 after
2626 // Allocate backing store and create result data. 2642 // Allocate backing store and create result data.
2627 AllocateData(size); 2643 AllocateData(size);
2628 2644
2629 // Set header values. 2645 // Set header values.
2630 SetMagicNumber(cs.isolate()); 2646 SetMagicNumber(cs.isolate());
2631 SetHeaderValue(kVersionHashOffset, Version::Hash()); 2647 SetHeaderValue(kVersionHashOffset, Version::Hash());
2632 SetHeaderValue(kSourceHashOffset, SourceHash(cs.source())); 2648 SetHeaderValue(kSourceHashOffset, SourceHash(cs.source()));
2633 SetHeaderValue(kCpuFeaturesOffset, 2649 SetHeaderValue(kCpuFeaturesOffset,
2634 static_cast<uint32_t>(CpuFeatures::SupportedFeatures())); 2650 static_cast<uint32_t>(CpuFeatures::SupportedFeatures()));
2635 SetHeaderValue(kFlagHashOffset, FlagList::Hash()); 2651 SetHeaderValue(kFlagHashOffset, FlagList::Hash());
2636 SetHeaderValue(kNumInternalizedStringsOffset, cs.num_internalized_strings());
2637 SetHeaderValue(kNumReservationsOffset, reservations.length()); 2652 SetHeaderValue(kNumReservationsOffset, reservations.length());
2638 SetHeaderValue(kNumCodeStubKeysOffset, num_stub_keys); 2653 SetHeaderValue(kNumCodeStubKeysOffset, num_stub_keys);
2639 SetHeaderValue(kPayloadLengthOffset, payload.length()); 2654 SetHeaderValue(kPayloadLengthOffset, payload.length());
2640 2655
2641 Checksum checksum(payload.ToConstVector()); 2656 Checksum checksum(payload.ToConstVector());
2642 SetHeaderValue(kChecksum1Offset, checksum.a()); 2657 SetHeaderValue(kChecksum1Offset, checksum.a());
2643 SetHeaderValue(kChecksum2Offset, checksum.b()); 2658 SetHeaderValue(kChecksum2Offset, checksum.b());
2644 2659
2645 // Copy reservation chunk sizes. 2660 // Copy reservation chunk sizes.
2646 CopyBytes(data_ + kHeaderSize, reinterpret_cast<byte*>(reservations.begin()), 2661 CopyBytes(data_ + kHeaderSize, reinterpret_cast<byte*>(reservations.begin()),
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
2704 int payload_offset = kHeaderSize + reservations_size + code_stubs_size; 2719 int payload_offset = kHeaderSize + reservations_size + code_stubs_size;
2705 int padded_payload_offset = POINTER_SIZE_ALIGN(payload_offset); 2720 int padded_payload_offset = POINTER_SIZE_ALIGN(payload_offset);
2706 const byte* payload = data_ + padded_payload_offset; 2721 const byte* payload = data_ + padded_payload_offset;
2707 DCHECK(IsAligned(reinterpret_cast<intptr_t>(payload), kPointerAlignment)); 2722 DCHECK(IsAligned(reinterpret_cast<intptr_t>(payload), kPointerAlignment));
2708 int length = GetHeaderValue(kPayloadLengthOffset); 2723 int length = GetHeaderValue(kPayloadLengthOffset);
2709 DCHECK_EQ(data_ + size_, payload + length); 2724 DCHECK_EQ(data_ + size_, payload + length);
2710 return Vector<const byte>(payload, length); 2725 return Vector<const byte>(payload, length);
2711 } 2726 }
2712 2727
2713 2728
2714 int SerializedCodeData::NumInternalizedStrings() const {
2715 return GetHeaderValue(kNumInternalizedStringsOffset);
2716 }
2717
2718 Vector<const uint32_t> SerializedCodeData::CodeStubKeys() const { 2729 Vector<const uint32_t> SerializedCodeData::CodeStubKeys() const {
2719 int reservations_size = GetHeaderValue(kNumReservationsOffset) * kInt32Size; 2730 int reservations_size = GetHeaderValue(kNumReservationsOffset) * kInt32Size;
2720 const byte* start = data_ + kHeaderSize + reservations_size; 2731 const byte* start = data_ + kHeaderSize + reservations_size;
2721 return Vector<const uint32_t>(reinterpret_cast<const uint32_t*>(start), 2732 return Vector<const uint32_t>(reinterpret_cast<const uint32_t*>(start),
2722 GetHeaderValue(kNumCodeStubKeysOffset)); 2733 GetHeaderValue(kNumCodeStubKeysOffset));
2723 } 2734 }
2724 2735
2725 2736
2726 SerializedCodeData::SerializedCodeData(ScriptData* data) 2737 SerializedCodeData::SerializedCodeData(ScriptData* data)
2727 : SerializedData(const_cast<byte*>(data->data()), data->length()) {} 2738 : SerializedData(const_cast<byte*>(data->data()), data->length()) {}
2728 2739
2729 2740
2730 SerializedCodeData* SerializedCodeData::FromCachedData(Isolate* isolate, 2741 SerializedCodeData* SerializedCodeData::FromCachedData(Isolate* isolate,
2731 ScriptData* cached_data, 2742 ScriptData* cached_data,
2732 String* source) { 2743 String* source) {
2733 DisallowHeapAllocation no_gc; 2744 DisallowHeapAllocation no_gc;
2734 SerializedCodeData* scd = new SerializedCodeData(cached_data); 2745 SerializedCodeData* scd = new SerializedCodeData(cached_data);
2735 SanityCheckResult r = scd->SanityCheck(isolate, source); 2746 SanityCheckResult r = scd->SanityCheck(isolate, source);
2736 if (r == CHECK_SUCCESS) return scd; 2747 if (r == CHECK_SUCCESS) return scd;
2737 cached_data->Reject(); 2748 cached_data->Reject();
2738 source->GetIsolate()->counters()->code_cache_reject_reason()->AddSample(r); 2749 source->GetIsolate()->counters()->code_cache_reject_reason()->AddSample(r);
2739 delete scd; 2750 delete scd;
2740 return NULL; 2751 return NULL;
2741 } 2752 }
2742 } // namespace internal 2753 } // namespace internal
2743 } // namespace v8 2754 } // namespace v8
OLDNEW
« no previous file with comments | « src/snapshot/serialize.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698