Commit 95f86859 authored by Jakob Gruber's avatar Jakob Gruber Committed by Commit Bot

[snapshot] Simplify deserializer APIs

This moves deserializer setup boilerplate inside the deserializers, and
makes improper usage less likely. For instance:

  ObjectDeserializer deserializer(&scd);
  /* ... deserializer setup ... */
  MaybeHandle<HeapObject> obj = deserializer.Deserialize(isolate);
  /* ... result checks and casts ... */

has now become:

  /* All setup and casts inside deserializer, impossible to illegally
     use the same instance multiple times. */
  MaybeHandle<SharedFunctionInfo> maybe_result =
      ObjectDeserializer::DeserializeSharedFunctionInfo(
          isolate, &scd, source);

Bug: v8:6624
Change-Id: Id5a1848e024e89cf86e5292389ba7c89f31d8e6b
Reviewed-on: https://chromium-review.googlesource.com/604791
Commit-Queue: Jakob Gruber <jgruber@chromium.org>
Reviewed-by: 's avatarYang Guo <yangguo@chromium.org>
Cr-Commit-Position: refs/heads/master@{#47219}
parent d929cc75
...@@ -2807,9 +2807,7 @@ bool Isolate::Init(StartupDeserializer* des) { ...@@ -2807,9 +2807,7 @@ bool Isolate::Init(StartupDeserializer* des) {
{ {
AlwaysAllocateScope always_allocate(this); AlwaysAllocateScope always_allocate(this);
if (!create_heap_objects) { if (!create_heap_objects) des->DeserializeInto(this);
des->Deserialize(this);
}
load_stub_cache_->Initialize(); load_stub_cache_->Initialize();
store_stub_cache_->Initialize(); store_stub_cache_->Initialize();
setup_delegate_->SetupInterpreter(interpreter_, create_heap_objects); setup_delegate_->SetupInterpreter(interpreter_, create_heap_objects);
......
...@@ -194,24 +194,17 @@ MaybeHandle<SharedFunctionInfo> CodeSerializer::Deserialize( ...@@ -194,24 +194,17 @@ MaybeHandle<SharedFunctionInfo> CodeSerializer::Deserialize(
return MaybeHandle<SharedFunctionInfo>(); return MaybeHandle<SharedFunctionInfo>();
} }
ObjectDeserializer deserializer(&scd);
deserializer.AddAttachedObject(source);
Vector<const uint32_t> code_stub_keys = scd.CodeStubKeys();
for (int i = 0; i < code_stub_keys.length(); i++) {
deserializer.AddAttachedObject(
CodeStub::GetCode(isolate, code_stub_keys[i]).ToHandleChecked());
}
// Deserialize. // Deserialize.
Handle<HeapObject> as_heap_object; MaybeHandle<SharedFunctionInfo> maybe_result =
if (!deserializer.Deserialize(isolate).ToHandle(&as_heap_object)) { ObjectDeserializer::DeserializeSharedFunctionInfo(isolate, &scd, source);
Handle<SharedFunctionInfo> result;
if (!maybe_result.ToHandle(&result)) {
// Deserializing may fail if the reservations cannot be fulfilled. // Deserializing may fail if the reservations cannot be fulfilled.
if (FLAG_profile_deserialization) PrintF("[Deserializing failed]\n"); if (FLAG_profile_deserialization) PrintF("[Deserializing failed]\n");
return MaybeHandle<SharedFunctionInfo>(); return MaybeHandle<SharedFunctionInfo>();
} }
Handle<SharedFunctionInfo> result =
Handle<SharedFunctionInfo>::cast(as_heap_object);
if (FLAG_profile_deserialization) { if (FLAG_profile_deserialization) {
double ms = timer.Elapsed().InMillisecondsF(); double ms = timer.Elapsed().InMillisecondsF();
int length = cached_data->length(); int length = cached_data->length();
...@@ -265,34 +258,16 @@ MaybeHandle<FixedArray> WasmCompiledModuleSerializer::DeserializeWasmModule( ...@@ -265,34 +258,16 @@ MaybeHandle<FixedArray> WasmCompiledModuleSerializer::DeserializeWasmModule(
return nothing; return nothing;
} }
ObjectDeserializer deserializer(&scd); MaybeHandle<WasmCompiledModule> maybe_result =
deserializer.AddAttachedObject(isolate->native_context()); ObjectDeserializer::DeserializeWasmCompiledModule(isolate, &scd,
wire_bytes);
MaybeHandle<String> maybe_wire_bytes_as_string = Handle<WasmCompiledModule> result;
isolate->factory()->NewStringFromOneByte(wire_bytes, TENURED); if (!maybe_result.ToHandle(&result)) return nothing;
Handle<String> wire_bytes_as_string;
if (!maybe_wire_bytes_as_string.ToHandle(&wire_bytes_as_string)) {
return nothing;
}
deserializer.AddAttachedObject(
handle(SeqOneByteString::cast(*wire_bytes_as_string)));
Vector<const uint32_t> stub_keys = scd.CodeStubKeys(); WasmCompiledModule::ReinitializeAfterDeserialization(isolate, result);
for (int i = 0; i < stub_keys.length(); ++i) { DCHECK(WasmCompiledModule::IsWasmCompiledModule(*result));
deserializer.AddAttachedObject( return result;
CodeStub::GetCode(isolate, stub_keys[i]).ToHandleChecked());
}
MaybeHandle<HeapObject> obj = deserializer.Deserialize(isolate);
if (obj.is_null() || !obj.ToHandleChecked()->IsFixedArray()) return nothing;
// Cast without type checks, as the module wrapper is not there yet.
Handle<WasmCompiledModule> compiled_module(
static_cast<WasmCompiledModule*>(*obj.ToHandleChecked()), isolate);
WasmCompiledModule::ReinitializeAfterDeserialization(isolate,
compiled_module);
DCHECK(WasmCompiledModule::IsWasmCompiledModule(*compiled_module));
return compiled_module;
} }
void WasmCompiledModuleSerializer::SerializeCodeObject( void WasmCompiledModuleSerializer::SerializeCodeObject(
......
...@@ -5,13 +5,66 @@ ...@@ -5,13 +5,66 @@
#include "src/snapshot/object-deserializer.h" #include "src/snapshot/object-deserializer.h"
#include "src/assembler-inl.h" #include "src/assembler-inl.h"
#include "src/code-stubs.h"
#include "src/isolate.h" #include "src/isolate.h"
#include "src/objects.h" #include "src/objects.h"
#include "src/snapshot/code-serializer.h" #include "src/snapshot/code-serializer.h"
#include "src/wasm/wasm-objects.h"
namespace v8 { namespace v8 {
namespace internal { namespace internal {
MaybeHandle<SharedFunctionInfo>
ObjectDeserializer::DeserializeSharedFunctionInfo(
Isolate* isolate, const SerializedCodeData* data, Handle<String> source) {
ObjectDeserializer d(data);
d.AddAttachedObject(source);
Vector<const uint32_t> code_stub_keys = data->CodeStubKeys();
for (int i = 0; i < code_stub_keys.length(); i++) {
d.AddAttachedObject(
CodeStub::GetCode(isolate, code_stub_keys[i]).ToHandleChecked());
}
Handle<HeapObject> result;
return d.Deserialize(isolate).ToHandle(&result)
? Handle<SharedFunctionInfo>::cast(result)
: MaybeHandle<SharedFunctionInfo>();
}
MaybeHandle<WasmCompiledModule>
ObjectDeserializer::DeserializeWasmCompiledModule(
Isolate* isolate, const SerializedCodeData* data,
Vector<const byte> wire_bytes) {
ObjectDeserializer d(data);
d.AddAttachedObject(isolate->native_context());
MaybeHandle<String> maybe_wire_bytes_as_string =
isolate->factory()->NewStringFromOneByte(wire_bytes, TENURED);
Handle<String> wire_bytes_as_string;
if (!maybe_wire_bytes_as_string.ToHandle(&wire_bytes_as_string)) {
return MaybeHandle<WasmCompiledModule>();
}
d.AddAttachedObject(wire_bytes_as_string);
Vector<const uint32_t> code_stub_keys = data->CodeStubKeys();
for (int i = 0; i < code_stub_keys.length(); i++) {
d.AddAttachedObject(
CodeStub::GetCode(isolate, code_stub_keys[i]).ToHandleChecked());
}
Handle<HeapObject> result;
if (!d.Deserialize(isolate).ToHandle(&result))
return MaybeHandle<WasmCompiledModule>();
if (!result->IsFixedArray()) return MaybeHandle<WasmCompiledModule>();
// Cast without type checks, as the module wrapper is not there yet.
return handle(static_cast<WasmCompiledModule*>(*result), isolate);
}
MaybeHandle<HeapObject> ObjectDeserializer::Deserialize(Isolate* isolate) { MaybeHandle<HeapObject> ObjectDeserializer::Deserialize(Isolate* isolate) {
Initialize(isolate); Initialize(isolate);
if (!ReserveSpace()) return MaybeHandle<HeapObject>(); if (!ReserveSpace()) return MaybeHandle<HeapObject>();
......
...@@ -11,19 +11,26 @@ namespace v8 { ...@@ -11,19 +11,26 @@ namespace v8 {
namespace internal { namespace internal {
class SerializedCodeData; class SerializedCodeData;
class SharedFunctionInfo;
class WasmCompiledModule;
// Deserializes the object graph rooted at a given object. // Deserializes the object graph rooted at a given object.
// Currently, the ObjectDeserializer is only used to deserialize code objects
// and compiled wasm modules.
class ObjectDeserializer final : public Deserializer { class ObjectDeserializer final : public Deserializer {
public: public:
static MaybeHandle<SharedFunctionInfo> DeserializeSharedFunctionInfo(
Isolate* isolate, const SerializedCodeData* data, Handle<String> source);
static MaybeHandle<WasmCompiledModule> DeserializeWasmCompiledModule(
Isolate* isolate, const SerializedCodeData* data,
Vector<const byte> wire_bytes);
private:
explicit ObjectDeserializer(const SerializedCodeData* data) explicit ObjectDeserializer(const SerializedCodeData* data)
: Deserializer(data, true) {} : Deserializer(data, true) {}
// Deserialize an object graph. Fail gracefully. // Deserialize an object graph. Fail gracefully.
MaybeHandle<HeapObject> Deserialize(Isolate* isolate); MaybeHandle<HeapObject> Deserialize(Isolate* isolate);
private:
void FlushICacheForNewCodeObjectsAndRecordEmbeddedObjects(); void FlushICacheForNewCodeObjectsAndRecordEmbeddedObjects();
void CommitPostProcessedObjects(); void CommitPostProcessedObjects();
}; };
......
...@@ -10,6 +10,21 @@ ...@@ -10,6 +10,21 @@
namespace v8 { namespace v8 {
namespace internal { namespace internal {
MaybeHandle<Context> PartialDeserializer::DeserializeContext(
Isolate* isolate, const SnapshotData* data, bool can_rehash,
Handle<JSGlobalProxy> global_proxy,
v8::DeserializeEmbedderFieldsCallback embedder_fields_deserializer) {
PartialDeserializer d(data);
d.SetRehashability(can_rehash);
MaybeHandle<Object> maybe_result =
d.Deserialize(isolate, global_proxy, embedder_fields_deserializer);
Handle<Object> result;
return maybe_result.ToHandle(&result) ? Handle<Context>::cast(result)
: MaybeHandle<Context>();
}
MaybeHandle<Object> PartialDeserializer::Deserialize( MaybeHandle<Object> PartialDeserializer::Deserialize(
Isolate* isolate, Handle<JSGlobalProxy> global_proxy, Isolate* isolate, Handle<JSGlobalProxy> global_proxy,
v8::DeserializeEmbedderFieldsCallback embedder_fields_deserializer) { v8::DeserializeEmbedderFieldsCallback embedder_fields_deserializer) {
......
...@@ -11,11 +11,18 @@ ...@@ -11,11 +11,18 @@
namespace v8 { namespace v8 {
namespace internal { namespace internal {
class Context;
// Deserializes the context-dependent object graph rooted at a given object. // Deserializes the context-dependent object graph rooted at a given object.
// Currently, the only use-case is to deserialize native contexts.
// The PartialDeserializer is not expected to deserialize any code objects. // The PartialDeserializer is not expected to deserialize any code objects.
class PartialDeserializer final : public Deserializer { class PartialDeserializer final : public Deserializer {
public: public:
static MaybeHandle<Context> DeserializeContext(
Isolate* isolate, const SnapshotData* data, bool can_rehash,
Handle<JSGlobalProxy> global_proxy,
v8::DeserializeEmbedderFieldsCallback embedder_fields_deserializer);
private:
explicit PartialDeserializer(const SnapshotData* data) explicit PartialDeserializer(const SnapshotData* data)
: Deserializer(data, false) {} : Deserializer(data, false) {}
...@@ -24,7 +31,6 @@ class PartialDeserializer final : public Deserializer { ...@@ -24,7 +31,6 @@ class PartialDeserializer final : public Deserializer {
Isolate* isolate, Handle<JSGlobalProxy> global_proxy, Isolate* isolate, Handle<JSGlobalProxy> global_proxy,
v8::DeserializeEmbedderFieldsCallback embedder_fields_deserializer); v8::DeserializeEmbedderFieldsCallback embedder_fields_deserializer);
private:
void DeserializeEmbedderFields( void DeserializeEmbedderFields(
v8::DeserializeEmbedderFieldsCallback embedder_fields_deserializer); v8::DeserializeEmbedderFieldsCallback embedder_fields_deserializer);
......
...@@ -26,27 +26,25 @@ PartialSerializer::~PartialSerializer() { ...@@ -26,27 +26,25 @@ PartialSerializer::~PartialSerializer() {
} }
void PartialSerializer::Serialize(Object** o, bool include_global_proxy) { void PartialSerializer::Serialize(Object** o, bool include_global_proxy) {
if ((*o)->IsNativeContext()) { DCHECK((*o)->IsNativeContext());
Context* context = Context::cast(*o);
reference_map()->AddAttachedReference(context->global_proxy()); Context* context = Context::cast(*o);
// The bootstrap snapshot has a code-stub context. When serializing the reference_map()->AddAttachedReference(context->global_proxy());
// partial snapshot, it is chained into the weak context list on the isolate // The bootstrap snapshot has a code-stub context. When serializing the
// and it's next context pointer may point to the code-stub context. Clear // partial snapshot, it is chained into the weak context list on the isolate
// it before serializing, it will get re-added to the context list // and it's next context pointer may point to the code-stub context. Clear
// explicitly when it's loaded. // it before serializing, it will get re-added to the context list
context->set(Context::NEXT_CONTEXT_LINK, // explicitly when it's loaded.
isolate_->heap()->undefined_value()); context->set(Context::NEXT_CONTEXT_LINK,
DCHECK(!context->global_object()->IsUndefined(context->GetIsolate())); isolate_->heap()->undefined_value());
// Reset math random cache to get fresh random numbers. DCHECK(!context->global_object()->IsUndefined(context->GetIsolate()));
context->set_math_random_index(Smi::kZero); // Reset math random cache to get fresh random numbers.
context->set_math_random_cache(isolate_->heap()->undefined_value()); context->set_math_random_index(Smi::kZero);
DCHECK_NULL(rehashable_global_dictionary_); context->set_math_random_cache(isolate_->heap()->undefined_value());
rehashable_global_dictionary_ = DCHECK_NULL(rehashable_global_dictionary_);
context->global_object()->global_dictionary(); rehashable_global_dictionary_ =
} else { context->global_object()->global_dictionary();
// We only do rehashing for native contexts.
can_be_rehashed_ = false;
}
VisitRootPointer(Root::kPartialSnapshotCache, o); VisitRootPointer(Root::kPartialSnapshotCache, o);
SerializeDeferredObjects(); SerializeDeferredObjects();
SerializeEmbedderFields(); SerializeEmbedderFields();
......
...@@ -60,24 +60,25 @@ MaybeHandle<Context> Snapshot::NewContextFromSnapshot( ...@@ -60,24 +60,25 @@ MaybeHandle<Context> Snapshot::NewContextFromSnapshot(
if (FLAG_profile_deserialization) timer.Start(); if (FLAG_profile_deserialization) timer.Start();
const v8::StartupData* blob = isolate->snapshot_blob(); const v8::StartupData* blob = isolate->snapshot_blob();
bool can_rehash = ExtractRehashability(blob);
Vector<const byte> context_data = Vector<const byte> context_data =
ExtractContextData(blob, static_cast<int>(context_index)); ExtractContextData(blob, static_cast<int>(context_index));
SnapshotData snapshot_data(context_data); SnapshotData snapshot_data(context_data);
PartialDeserializer deserializer(&snapshot_data);
deserializer.SetRehashability(ExtractRehashability(blob));
MaybeHandle<Object> maybe_context = deserializer.Deserialize( MaybeHandle<Context> maybe_result = PartialDeserializer::DeserializeContext(
isolate, global_proxy, embedder_fields_deserializer); isolate, &snapshot_data, can_rehash, global_proxy,
Handle<Object> result; embedder_fields_deserializer);
if (!maybe_context.ToHandle(&result)) return MaybeHandle<Context>();
CHECK(result->IsContext()); Handle<Context> result;
if (!maybe_result.ToHandle(&result)) return MaybeHandle<Context>();
if (FLAG_profile_deserialization) { if (FLAG_profile_deserialization) {
double ms = timer.Elapsed().InMillisecondsF(); double ms = timer.Elapsed().InMillisecondsF();
int bytes = context_data.length(); int bytes = context_data.length();
PrintF("[Deserializing context #%zu (%d bytes) took %0.3f ms]\n", PrintF("[Deserializing context #%zu (%d bytes) took %0.3f ms]\n",
context_index, bytes, ms); context_index, bytes, ms);
} }
return Handle<Context>::cast(result); return result;
} }
void ProfileDeserialization(const SnapshotData* startup_snapshot, void ProfileDeserialization(const SnapshotData* startup_snapshot,
......
...@@ -11,7 +11,7 @@ ...@@ -11,7 +11,7 @@
namespace v8 { namespace v8 {
namespace internal { namespace internal {
void StartupDeserializer::Deserialize(Isolate* isolate) { void StartupDeserializer::DeserializeInto(Isolate* isolate) {
Initialize(isolate); Initialize(isolate);
if (!ReserveSpace()) V8::FatalProcessOutOfMemory("StartupDeserializer"); if (!ReserveSpace()) V8::FatalProcessOutOfMemory("StartupDeserializer");
......
...@@ -18,7 +18,7 @@ class StartupDeserializer final : public Deserializer { ...@@ -18,7 +18,7 @@ class StartupDeserializer final : public Deserializer {
: Deserializer(data, false) {} : Deserializer(data, false) {}
// Deserialize the snapshot into an empty heap. // Deserialize the snapshot into an empty heap.
void Deserialize(Isolate* isolate); void DeserializeInto(Isolate* isolate);
private: private:
void FlushICacheForNewIsolate(); void FlushICacheForNewIsolate();
......
...@@ -302,106 +302,6 @@ UNINITIALIZED_TEST(StartupSerializerTwiceRunScript) { ...@@ -302,106 +302,6 @@ UNINITIALIZED_TEST(StartupSerializerTwiceRunScript) {
isolate->Dispose(); isolate->Dispose();
} }
static void PartiallySerializeObject(Vector<const byte>* startup_blob_out,
Vector<const byte>* partial_blob_out) {
v8::Isolate* v8_isolate = TestIsolate::NewInitialized(true);
Isolate* isolate = reinterpret_cast<Isolate*>(v8_isolate);
v8_isolate->Enter();
{
Heap* heap = isolate->heap();
v8::Persistent<v8::Context> env;
{
HandleScope scope(isolate);
env.Reset(v8_isolate, v8::Context::New(v8_isolate));
}
CHECK(!env.IsEmpty());
{
v8::HandleScope handle_scope(v8_isolate);
v8::Local<v8::Context>::New(v8_isolate, env)->Enter();
}
heap->CollectAllAvailableGarbage(i::GarbageCollectionReason::kTesting);
heap->CollectAllAvailableGarbage(i::GarbageCollectionReason::kTesting);
Object* raw_foo;
{
v8::HandleScope handle_scope(v8_isolate);
v8::Local<v8::String> foo = v8_str("foo");
CHECK(!foo.IsEmpty());
raw_foo = *(v8::Utils::OpenHandle(*foo));
}
{
v8::HandleScope handle_scope(v8_isolate);
v8::Local<v8::Context>::New(v8_isolate, env)->Exit();
}
env.Reset();
StartupSerializer startup_serializer(
isolate, v8::SnapshotCreator::FunctionCodeHandling::kClear);
startup_serializer.SerializeStrongReferences();
PartialSerializer partial_serializer(isolate, &startup_serializer,
v8::SerializeInternalFieldsCallback());
partial_serializer.Serialize(&raw_foo, false);
startup_serializer.SerializeWeakReferencesAndDeferred();
SnapshotData startup_snapshot(&startup_serializer);
SnapshotData partial_snapshot(&partial_serializer);
*partial_blob_out = WritePayload(partial_snapshot.RawData());
*startup_blob_out = WritePayload(startup_snapshot.RawData());
}
v8_isolate->Exit();
v8_isolate->Dispose();
}
UNINITIALIZED_TEST(PartialSerializerObject) {
DisableAlwaysOpt();
Vector<const byte> startup_blob;
Vector<const byte> partial_blob;
PartiallySerializeObject(&startup_blob, &partial_blob);
v8::Isolate* v8_isolate = InitializeFromBlob(startup_blob);
startup_blob.Dispose();
CHECK(v8_isolate);
{
v8::Isolate::Scope isolate_scope(v8_isolate);
Isolate* isolate = reinterpret_cast<Isolate*>(v8_isolate);
HandleScope handle_scope(isolate);
Handle<Object> root;
// Intentionally empty handle. The deserializer should not come across
// any references to the global proxy in this test.
Handle<JSGlobalProxy> global_proxy = Handle<JSGlobalProxy>::null();
{
SnapshotData snapshot_data(partial_blob);
PartialDeserializer deserializer(&snapshot_data);
root = deserializer
.Deserialize(isolate, global_proxy,
v8::DeserializeInternalFieldsCallback())
.ToHandleChecked();
CHECK(root->IsString());
}
Handle<Object> root2;
{
SnapshotData snapshot_data(partial_blob);
PartialDeserializer deserializer(&snapshot_data);
root2 = deserializer
.Deserialize(isolate, global_proxy,
v8::DeserializeInternalFieldsCallback())
.ToHandleChecked();
CHECK(root2->IsString());
CHECK(root.is_identical_to(root2));
}
partial_blob.Dispose();
}
v8_isolate->Dispose();
}
static void PartiallySerializeContext(Vector<const byte>* startup_blob_out, static void PartiallySerializeContext(Vector<const byte>* startup_blob_out,
Vector<const byte>* partial_blob_out) { Vector<const byte>* partial_blob_out) {
v8::Isolate* v8_isolate = TestIsolate::NewInitialized(true); v8::Isolate* v8_isolate = TestIsolate::NewInitialized(true);
...@@ -474,10 +374,9 @@ UNINITIALIZED_TEST(PartialSerializerContext) { ...@@ -474,10 +374,9 @@ UNINITIALIZED_TEST(PartialSerializerContext) {
JSGlobalProxy::SizeWithEmbedderFields(0)); JSGlobalProxy::SizeWithEmbedderFields(0));
{ {
SnapshotData snapshot_data(partial_blob); SnapshotData snapshot_data(partial_blob);
PartialDeserializer deserializer(&snapshot_data); root = PartialDeserializer::DeserializeContext(
root = deserializer isolate, &snapshot_data, false, global_proxy,
.Deserialize(isolate, global_proxy, v8::DeserializeInternalFieldsCallback())
v8::DeserializeInternalFieldsCallback())
.ToHandleChecked(); .ToHandleChecked();
CHECK(root->IsContext()); CHECK(root->IsContext());
CHECK(Handle<Context>::cast(root)->global_proxy() == *global_proxy); CHECK(Handle<Context>::cast(root)->global_proxy() == *global_proxy);
...@@ -486,10 +385,9 @@ UNINITIALIZED_TEST(PartialSerializerContext) { ...@@ -486,10 +385,9 @@ UNINITIALIZED_TEST(PartialSerializerContext) {
Handle<Object> root2; Handle<Object> root2;
{ {
SnapshotData snapshot_data(partial_blob); SnapshotData snapshot_data(partial_blob);
PartialDeserializer deserializer(&snapshot_data); root2 = PartialDeserializer::DeserializeContext(
root2 = deserializer isolate, &snapshot_data, false, global_proxy,
.Deserialize(isolate, global_proxy, v8::DeserializeInternalFieldsCallback())
v8::DeserializeInternalFieldsCallback())
.ToHandleChecked(); .ToHandleChecked();
CHECK(root2->IsContext()); CHECK(root2->IsContext());
CHECK(!root.is_identical_to(root2)); CHECK(!root.is_identical_to(root2));
...@@ -592,10 +490,9 @@ UNINITIALIZED_TEST(PartialSerializerCustomContext) { ...@@ -592,10 +490,9 @@ UNINITIALIZED_TEST(PartialSerializerCustomContext) {
JSGlobalProxy::SizeWithEmbedderFields(0)); JSGlobalProxy::SizeWithEmbedderFields(0));
{ {
SnapshotData snapshot_data(partial_blob); SnapshotData snapshot_data(partial_blob);
PartialDeserializer deserializer(&snapshot_data); root = PartialDeserializer::DeserializeContext(
root = deserializer isolate, &snapshot_data, false, global_proxy,
.Deserialize(isolate, global_proxy, v8::DeserializeInternalFieldsCallback())
v8::DeserializeInternalFieldsCallback())
.ToHandleChecked(); .ToHandleChecked();
CHECK(root->IsContext()); CHECK(root->IsContext());
Handle<Context> context = Handle<Context>::cast(root); Handle<Context> context = Handle<Context>::cast(root);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment