Line data Source code
1 : // Copyright 2017 the V8 project authors. All rights reserved.
2 : // Use of this source code is governed by a BSD-style license that can be
3 : // found in the LICENSE file.
4 :
5 : #include "src/snapshot/object-deserializer.h"
6 :
7 : #include "src/assembler-inl.h"
8 : #include "src/code-stubs.h"
9 : #include "src/isolate.h"
10 : #include "src/objects.h"
11 : #include "src/snapshot/code-serializer.h"
12 : #include "src/wasm/wasm-objects.h"
13 :
14 : namespace v8 {
15 : namespace internal {
16 :
17 : MaybeHandle<SharedFunctionInfo>
18 220 : ObjectDeserializer::DeserializeSharedFunctionInfo(
19 : Isolate* isolate, const SerializedCodeData* data, Handle<String> source) {
20 : ObjectDeserializer d(data);
21 :
22 : d.AddAttachedObject(source);
23 :
24 220 : Vector<const uint32_t> code_stub_keys = data->CodeStubKeys();
25 440 : for (int i = 0; i < code_stub_keys.length(); i++) {
26 : d.AddAttachedObject(
27 0 : CodeStub::GetCode(isolate, code_stub_keys[i]).ToHandleChecked());
28 : }
29 :
30 : Handle<HeapObject> result;
31 440 : return d.Deserialize(isolate).ToHandle(&result)
32 : ? Handle<SharedFunctionInfo>::cast(result)
33 440 : : MaybeHandle<SharedFunctionInfo>();
34 : }
35 :
36 : MaybeHandle<WasmCompiledModule>
37 80 : ObjectDeserializer::DeserializeWasmCompiledModule(
38 : Isolate* isolate, const SerializedCodeData* data,
39 : Vector<const byte> wire_bytes) {
40 : ObjectDeserializer d(data);
41 :
42 80 : d.AddAttachedObject(isolate->native_context());
43 :
44 : MaybeHandle<String> maybe_wire_bytes_as_string =
45 80 : isolate->factory()->NewStringFromOneByte(wire_bytes, TENURED);
46 : Handle<String> wire_bytes_as_string;
47 80 : if (!maybe_wire_bytes_as_string.ToHandle(&wire_bytes_as_string)) {
48 0 : return MaybeHandle<WasmCompiledModule>();
49 : }
50 : d.AddAttachedObject(wire_bytes_as_string);
51 :
52 80 : Vector<const uint32_t> code_stub_keys = data->CodeStubKeys();
53 280 : for (int i = 0; i < code_stub_keys.length(); i++) {
54 : d.AddAttachedObject(
55 180 : CodeStub::GetCode(isolate, code_stub_keys[i]).ToHandleChecked());
56 : }
57 :
58 : Handle<HeapObject> result;
59 160 : if (!d.Deserialize(isolate).ToHandle(&result))
60 0 : return MaybeHandle<WasmCompiledModule>();
61 :
62 80 : if (!result->IsFixedArray()) return MaybeHandle<WasmCompiledModule>();
63 :
64 : // Cast without type checks, as the module wrapper is not there yet.
65 80 : return handle(static_cast<WasmCompiledModule*>(*result), isolate);
66 : }
67 :
68 300 : MaybeHandle<HeapObject> ObjectDeserializer::Deserialize(Isolate* isolate) {
69 300 : Initialize(isolate);
70 300 : if (!allocator()->ReserveSpace()) return MaybeHandle<HeapObject>();
71 :
72 : DCHECK(deserializing_user_code());
73 : HandleScope scope(isolate);
74 : Handle<HeapObject> result;
75 : {
76 : DisallowHeapAllocation no_gc;
77 : Object* root;
78 300 : VisitRootPointer(Root::kPartialSnapshotCache, &root);
79 300 : DeserializeDeferredObjects();
80 300 : FlushICacheForNewCodeObjectsAndRecordEmbeddedObjects();
81 600 : result = Handle<HeapObject>(HeapObject::cast(root));
82 300 : allocator()->RegisterDeserializedObjectsForBlackAllocation();
83 : }
84 300 : CommitPostProcessedObjects();
85 300 : return scope.CloseAndEscape(result);
86 : }
87 :
88 300 : void ObjectDeserializer::
89 : FlushICacheForNewCodeObjectsAndRecordEmbeddedObjects() {
90 : DCHECK(deserializing_user_code());
91 1020 : for (Code* code : new_code_objects()) {
92 : // Record all references to embedded objects in the new code object.
93 210 : isolate()->heap()->RecordWritesIntoCode(code);
94 210 : Assembler::FlushICache(isolate(), code->instruction_start(),
95 420 : code->instruction_size());
96 : }
97 300 : }
98 :
99 300 : void ObjectDeserializer::CommitPostProcessedObjects() {
100 7815 : CHECK_LE(new_internalized_strings().size(), kMaxInt);
101 : StringTable::EnsureCapacityForDeserialization(
102 600 : isolate(), static_cast<int>(new_internalized_strings().size()));
103 6915 : for (Handle<String> string : new_internalized_strings()) {
104 6315 : StringTableInsertionKey key(*string);
105 : DCHECK_NULL(StringTable::LookupKeyIfExists(isolate(), &key));
106 6315 : StringTable::LookupKey(isolate(), &key);
107 : }
108 :
109 : Heap* heap = isolate()->heap();
110 : Factory* factory = isolate()->factory();
111 900 : for (Handle<Script> script : new_scripts()) {
112 : // Assign a new script id to avoid collision.
113 : script->set_id(isolate()->heap()->NextScriptId());
114 : // Add script to list.
115 300 : Handle<Object> list = WeakFixedArray::Add(factory->script_list(), script);
116 : heap->SetRootScriptList(*list);
117 : }
118 300 : }
119 :
120 : } // namespace internal
121 : } // namespace v8
|