summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorJoyee Cheung <joyeec9h3@gmail.com>2023-04-07 02:17:47 +0200
committerJoyee Cheung <joyeec9h3@gmail.com>2023-04-26 00:34:49 +0200
commit2e44a14cfb84a0665fb4bac06b2fca76e8da06a7 (patch)
tree613dddb805deec2e3b5a50977c22dceb1388980a /src
parentab3a54f2eed465f730f55fc9efa972ab465e374d (diff)
downloadnode-new-2e44a14cfb84a0665fb4bac06b2fca76e8da06a7.tar.gz
src: split BlobSerializer/BlobDeserializer
This patch splits BlobSerializer and BlobDeserializer out of SnapshotSerializer and SnapshotDeserializer. The child classes can implement serialization methods for custom types on top of BlobSerializer/BlobDeserializer for conversions between native types and binary blobs. This allows us to reuse the classes for other cases (e.g. SEA blobs). PR-URL: https://github.com/nodejs/node/pull/47458 Reviewed-By: Darshan Sen <raisinten@gmail.com>
Diffstat (limited to 'src')
-rw-r--r--src/env.h1
-rw-r--r--src/node_snapshotable.cc268
2 files changed, 169 insertions, 100 deletions
diff --git a/src/env.h b/src/env.h
index a50e2a83e3..5359436be3 100644
--- a/src/env.h
+++ b/src/env.h
@@ -534,6 +534,7 @@ struct SnapshotData {
bool Check() const;
static bool FromFile(SnapshotData* out, FILE* in);
static bool FromBlob(SnapshotData* out, const std::vector<char>& in);
+ static bool FromBlob(SnapshotData* out, std::string_view in);
static const SnapshotData* FromEmbedderWrapper(
const EmbedderSnapshotData* data);
EmbedderSnapshotData::Pointer AsEmbedderWrapper() const;
diff --git a/src/node_snapshotable.cc b/src/node_snapshotable.cc
index 0c842a8631..6302fa04c4 100644
--- a/src/node_snapshotable.cc
+++ b/src/node_snapshotable.cc
@@ -140,16 +140,15 @@ std::ostream& operator<<(std::ostream& output, const EnvSerializeInfo& i) {
return output;
}
-class SnapshotSerializerDeserializer {
+class BlobSerializerDeserializer {
public:
- SnapshotSerializerDeserializer()
- : is_debug(per_process::enabled_debug_list.enabled(
- DebugCategory::MKSNAPSHOT)) {}
+ explicit BlobSerializerDeserializer(bool is_debug_v) : is_debug(is_debug_v) {}
template <typename... Args>
void Debug(const char* format, Args&&... args) const {
- per_process::Debug(
- DebugCategory::MKSNAPSHOT, format, std::forward<Args>(args)...);
+ if (is_debug) {
+ FPrintF(stderr, format, std::forward<Args>(args)...);
+ }
}
template <typename T>
@@ -185,18 +184,28 @@ class SnapshotSerializerDeserializer {
bool is_debug = false;
};
-class SnapshotDeserializer : public SnapshotSerializerDeserializer {
+// TODO(joyeecheung): move it to the separate header file.
+// Child classes are expected to implement T Read<T>() where
+// !std::is_arithmetic_v<T> && !std::is_same_v<T, std::string>
+template <typename Impl>
+class BlobDeserializer : public BlobSerializerDeserializer {
public:
- explicit SnapshotDeserializer(const std::vector<char>& s)
- : SnapshotSerializerDeserializer(), sink(s) {}
- ~SnapshotDeserializer() {}
+ explicit BlobDeserializer(bool is_debug_v, std::string_view s)
+ : BlobSerializerDeserializer(is_debug_v), sink(s) {}
+ ~BlobDeserializer() {}
+
+ size_t read_total = 0;
+ std::string_view sink;
+
+ Impl* impl() { return static_cast<Impl*>(this); }
+ const Impl* impl() const { return static_cast<const Impl*>(this); }
// Helper for reading numeric types.
template <typename T>
- T Read() {
+ T ReadArithmetic() {
static_assert(std::is_arithmetic_v<T>, "Not an arithmetic type");
T result;
- Read(&result, 1);
+ ReadArithmetic(&result, 1);
return result;
}
@@ -209,14 +218,19 @@ class SnapshotDeserializer : public SnapshotSerializerDeserializer {
std::string name = GetName<T>();
Debug("\nReadVector<%s>()(%d-byte)\n", name.c_str(), sizeof(T));
}
- size_t count = static_cast<size_t>(Read<size_t>());
+ size_t count = static_cast<size_t>(ReadArithmetic<size_t>());
if (count == 0) {
return std::vector<T>();
}
if (is_debug) {
Debug("Reading %d vector elements...\n", count);
}
- std::vector<T> result = ReadVector<T>(count, std::is_arithmetic<T>{});
+ std::vector<T> result;
+ if constexpr (std::is_arithmetic_v<T>) {
+ result = ReadArithmeticVector<T>(count);
+ } else {
+ result = ReadNonArithmeticVector<T>(count);
+ }
if (is_debug) {
std::string str = std::is_arithmetic_v<T> ? "" : ToStr(result);
std::string name = GetName<T>();
@@ -226,7 +240,7 @@ class SnapshotDeserializer : public SnapshotSerializerDeserializer {
}
std::string ReadString() {
- size_t length = Read<size_t>();
+ size_t length = ReadArithmetic<size_t>();
if (is_debug) {
Debug("ReadString(), length=%d: ", length);
@@ -245,13 +259,9 @@ class SnapshotDeserializer : public SnapshotSerializerDeserializer {
return result;
}
- size_t read_total = 0;
- const std::vector<char>& sink;
-
- private:
// Helper for reading an array of numeric types.
template <typename T>
- void Read(T* out, size_t count) {
+ void ReadArithmetic(T* out, size_t count) {
static_assert(std::is_arithmetic_v<T>, "Not an arithmetic type");
DCHECK_GT(count, 0); // Should not read contents for vectors of size 0.
if (is_debug) {
@@ -272,17 +282,18 @@ class SnapshotDeserializer : public SnapshotSerializerDeserializer {
// Helper for reading numeric vectors.
template <typename Number>
- std::vector<Number> ReadVector(size_t count, std::true_type) {
+ std::vector<Number> ReadArithmeticVector(size_t count) {
static_assert(std::is_arithmetic_v<Number>, "Not an arithmetic type");
DCHECK_GT(count, 0); // Should not read contents for vectors of size 0.
std::vector<Number> result(count);
- Read(result.data(), count);
+ ReadArithmetic(result.data(), count);
return result;
}
+ private:
// Helper for reading non-numeric vectors.
template <typename T>
- std::vector<T> ReadVector(size_t count, std::false_type) {
+ std::vector<T> ReadNonArithmeticVector(size_t count) {
static_assert(!std::is_arithmetic_v<T>, "Arithmetic type");
DCHECK_GT(count, 0); // Should not read contents for vectors of size 0.
std::vector<T> result;
@@ -293,29 +304,49 @@ class SnapshotDeserializer : public SnapshotSerializerDeserializer {
if (is_debug) {
Debug("\n[%d] ", i);
}
- result.push_back(Read<T>());
+ result.push_back(ReadElement<T>());
}
is_debug = original_is_debug;
return result;
}
+
+ template <typename T>
+ T ReadElement() {
+ if constexpr (std::is_arithmetic_v<T>) {
+ return ReadArithmetic<T>();
+ } else if constexpr (std::is_same_v<T, std::string>) {
+ return ReadString();
+ } else {
+ return impl()->template Read<T>();
+ }
+ }
};
-class SnapshotSerializer : public SnapshotSerializerDeserializer {
+// TODO(joyeecheung): move it to the separate header file.
+// Child classes are expected to implement size_t Write<T>(const T&) where
+// !std::is_arithmetic_v<T> && !std::is_same_v<T, std::string>
+template <typename Impl>
+class BlobSerializer : public BlobSerializerDeserializer {
public:
- SnapshotSerializer() : SnapshotSerializerDeserializer() {
+ explicit BlobSerializer(bool is_debug_v)
+ : BlobSerializerDeserializer(is_debug_v) {
// Currently the snapshot blob built with an empty script is around 4MB.
// So use that as the default sink size.
sink.reserve(4 * 1024 * 1024);
}
- ~SnapshotSerializer() {}
+ ~BlobSerializer() {}
+
+ Impl* impl() { return static_cast<Impl*>(this); }
+ const Impl* impl() const { return static_cast<const Impl*>(this); }
+
std::vector<char> sink;
// Helper for writing numeric types.
template <typename T>
- size_t Write(const T& data) {
+ size_t WriteArithmetic(const T& data) {
static_assert(std::is_arithmetic_v<T>, "Not an arithmetic type");
- return Write(&data, 1);
+ return WriteArithmetic(&data, 1);
}
// Layout of vectors:
@@ -333,11 +364,16 @@ class SnapshotSerializer : public SnapshotSerializerDeserializer {
str.c_str());
}
- size_t written_total = Write<size_t>(data.size());
+ size_t written_total = WriteArithmetic<size_t>(data.size());
if (data.size() == 0) {
return written_total;
}
- written_total += WriteVector<T>(data, std::is_arithmetic<T>{});
+
+ if constexpr (std::is_arithmetic_v<T>) {
+ written_total += WriteArithmeticVector<T>(data);
+ } else {
+ written_total += WriteNonArithmeticVector<T>(data);
+ }
if (is_debug) {
std::string name = GetName<T>();
@@ -352,7 +388,7 @@ class SnapshotSerializer : public SnapshotSerializerDeserializer {
// [ |length| bytes ] contents
size_t WriteString(const std::string& data) {
CHECK_GT(data.size(), 0); // No empty strings should be written.
- size_t written_total = Write<size_t>(data.size());
+ size_t written_total = WriteArithmetic<size_t>(data.size());
if (is_debug) {
std::string str = ToStr(data);
Debug("WriteString(), length=%zu: \"%s\"\n", data.size(), data.c_str());
@@ -370,10 +406,10 @@ class SnapshotSerializer : public SnapshotSerializerDeserializer {
return written_total;
}
- private:
// Helper for writing an array of numeric types.
template <typename T>
- size_t Write(const T* data, size_t count) {
+ size_t WriteArithmetic(const T* data, size_t count) {
+ static_assert(std::is_arithmetic_v<T>, "Arithmetic type");
DCHECK_GT(count, 0); // Should not write contents for vectors of size 0.
if (is_debug) {
std::string str =
@@ -398,13 +434,16 @@ class SnapshotSerializer : public SnapshotSerializerDeserializer {
// Helper for writing numeric vectors.
template <typename Number>
- size_t WriteVector(const std::vector<Number>& data, std::true_type) {
- return Write(data.data(), data.size());
+ size_t WriteArithmeticVector(const std::vector<Number>& data) {
+ static_assert(std::is_arithmetic_v<Number>, "Arithmetic type");
+ return WriteArithmetic(data.data(), data.size());
}
+ private:
// Helper for writing non-numeric vectors.
template <typename T>
- size_t WriteVector(const std::vector<T>& data, std::false_type) {
+ size_t WriteNonArithmeticVector(const std::vector<T>& data) {
+ static_assert(!std::is_arithmetic_v<T>, "Arithmetic type");
DCHECK_GT(data.size(),
0); // Should not write contents for vectors of size 0.
size_t written_total = 0;
@@ -414,25 +453,50 @@ class SnapshotSerializer : public SnapshotSerializerDeserializer {
if (is_debug) {
Debug("\n[%d] ", i);
}
- written_total += Write<T>(data[i]);
+ written_total += WriteElement<T>(data[i]);
}
is_debug = original_is_debug;
return written_total;
}
+
+ template <typename T>
+ size_t WriteElement(const T& data) {
+ if constexpr (std::is_arithmetic_v<T>) {
+ return WriteArithmetic<T>(data);
+ } else if constexpr (std::is_same_v<T, std::string>) {
+ return WriteString(data);
+ } else {
+ return impl()->template Write<T>(data);
+ }
+ }
};
-// Layout of serialized std::string:
-// [ 4/8 bytes ] length
-// [ |length| bytes ] contents
-template <>
-std::string SnapshotDeserializer::Read() {
- return ReadString();
-}
-template <>
-size_t SnapshotSerializer::Write(const std::string& data) {
- return WriteString(data);
-}
+class SnapshotDeserializer : public BlobDeserializer<SnapshotDeserializer> {
+ public:
+ explicit SnapshotDeserializer(std::string_view v)
+ : BlobDeserializer<SnapshotDeserializer>(
+ per_process::enabled_debug_list.enabled(DebugCategory::MKSNAPSHOT),
+ v) {}
+
+ template <typename T,
+ std::enable_if_t<!std::is_same<T, std::string>::value>* = nullptr,
+ std::enable_if_t<!std::is_arithmetic<T>::value>* = nullptr>
+ T Read();
+};
+
+class SnapshotSerializer : public BlobSerializer<SnapshotSerializer> {
+ public:
+ SnapshotSerializer()
+ : BlobSerializer<SnapshotSerializer>(
+ per_process::enabled_debug_list.enabled(
+ DebugCategory::MKSNAPSHOT)) {}
+
+ template <typename T,
+ std::enable_if_t<!std::is_same<T, std::string>::value>* = nullptr,
+ std::enable_if_t<!std::is_arithmetic<T>::value>* = nullptr>
+ size_t Write(const T& data);
+};
// Layout of v8::StartupData
// [ 4/8 bytes ] raw_size
@@ -441,13 +505,13 @@ template <>
v8::StartupData SnapshotDeserializer::Read() {
Debug("Read<v8::StartupData>()\n");
- int raw_size = Read<int>();
+ int raw_size = ReadArithmetic<int>();
Debug("size=%d\n", raw_size);
CHECK_GT(raw_size, 0); // There should be no startup data of size 0.
// The data pointer of v8::StartupData would be deleted so it must be new'ed.
std::unique_ptr<char> buf = std::unique_ptr<char>(new char[raw_size]);
- Read<char>(buf.get(), raw_size);
+ ReadArithmetic<char>(buf.get(), raw_size);
return v8::StartupData{buf.release(), raw_size};
}
@@ -457,8 +521,9 @@ size_t SnapshotSerializer::Write(const v8::StartupData& data) {
Debug("\nWrite<v8::StartupData>() size=%d\n", data.raw_size);
CHECK_GT(data.raw_size, 0); // There should be no startup data of size 0.
- size_t written_total = Write<int>(data.raw_size);
- written_total += Write<char>(data.data, static_cast<size_t>(data.raw_size));
+ size_t written_total = WriteArithmetic<int>(data.raw_size);
+ written_total +=
+ WriteArithmetic<char>(data.data, static_cast<size_t>(data.raw_size));
Debug("Write<v8::StartupData>() wrote %d bytes\n\n", written_total);
return written_total;
@@ -508,8 +573,8 @@ PropInfo SnapshotDeserializer::Read() {
PropInfo result;
result.name = ReadString();
- result.id = Read<uint32_t>();
- result.index = Read<SnapshotIndex>();
+ result.id = ReadArithmetic<uint32_t>();
+ result.index = ReadArithmetic<SnapshotIndex>();
if (is_debug) {
std::string str = ToStr(result);
@@ -527,8 +592,8 @@ size_t SnapshotSerializer::Write(const PropInfo& data) {
}
size_t written_total = WriteString(data.name);
- written_total += Write<uint32_t>(data.id);
- written_total += Write<SnapshotIndex>(data.index);
+ written_total += WriteArithmetic<uint32_t>(data.id);
+ written_total += WriteArithmetic<SnapshotIndex>(data.index);
Debug("Write<PropInfo>() wrote %d bytes\n", written_total);
return written_total;
@@ -547,10 +612,10 @@ AsyncHooks::SerializeInfo SnapshotDeserializer::Read() {
Debug("Read<AsyncHooks::SerializeInfo>()\n");
AsyncHooks::SerializeInfo result;
- result.async_ids_stack = Read<AliasedBufferIndex>();
- result.fields = Read<AliasedBufferIndex>();
- result.async_id_fields = Read<AliasedBufferIndex>();
- result.js_execution_async_resources = Read<SnapshotIndex>();
+ result.async_ids_stack = ReadArithmetic<AliasedBufferIndex>();
+ result.fields = ReadArithmetic<AliasedBufferIndex>();
+ result.async_id_fields = ReadArithmetic<AliasedBufferIndex>();
+ result.js_execution_async_resources = ReadArithmetic<SnapshotIndex>();
result.native_execution_async_resources = ReadVector<SnapshotIndex>();
if (is_debug) {
@@ -567,10 +632,12 @@ size_t SnapshotSerializer::Write(const AsyncHooks::SerializeInfo& data) {
Debug("Write<AsyncHooks::SerializeInfo>() %s\n", str.c_str());
}
- size_t written_total = Write<AliasedBufferIndex>(data.async_ids_stack);
- written_total += Write<AliasedBufferIndex>(data.fields);
- written_total += Write<AliasedBufferIndex>(data.async_id_fields);
- written_total += Write<SnapshotIndex>(data.js_execution_async_resources);
+ size_t written_total =
+ WriteArithmetic<AliasedBufferIndex>(data.async_ids_stack);
+ written_total += WriteArithmetic<AliasedBufferIndex>(data.fields);
+ written_total += WriteArithmetic<AliasedBufferIndex>(data.async_id_fields);
+ written_total +=
+ WriteArithmetic<SnapshotIndex>(data.js_execution_async_resources);
written_total +=
WriteVector<SnapshotIndex>(data.native_execution_async_resources);
@@ -585,7 +652,7 @@ TickInfo::SerializeInfo SnapshotDeserializer::Read() {
Debug("Read<TickInfo::SerializeInfo>()\n");
TickInfo::SerializeInfo result;
- result.fields = Read<AliasedBufferIndex>();
+ result.fields = ReadArithmetic<AliasedBufferIndex>();
if (is_debug) {
std::string str = ToStr(result);
@@ -602,7 +669,7 @@ size_t SnapshotSerializer::Write(const TickInfo::SerializeInfo& data) {
Debug("Write<TickInfo::SerializeInfo>() %s\n", str.c_str());
}
- size_t written_total = Write<AliasedBufferIndex>(data.fields);
+ size_t written_total = WriteArithmetic<AliasedBufferIndex>(data.fields);
Debug("Write<TickInfo::SerializeInfo>() wrote %d bytes\n", written_total);
return written_total;
@@ -612,11 +679,10 @@ size_t SnapshotSerializer::Write(const TickInfo::SerializeInfo& data) {
// [ 4/8 bytes ] snapshot index of fields
template <>
ImmediateInfo::SerializeInfo SnapshotDeserializer::Read() {
- per_process::Debug(DebugCategory::MKSNAPSHOT,
- "Read<ImmediateInfo::SerializeInfo>()\n");
+ Debug("Read<ImmediateInfo::SerializeInfo>()\n");
ImmediateInfo::SerializeInfo result;
- result.fields = Read<AliasedBufferIndex>();
+ result.fields = ReadArithmetic<AliasedBufferIndex>();
if (is_debug) {
std::string str = ToStr(result);
Debug("Read<ImmediateInfo::SerializeInfo>() %s\n", str.c_str());
@@ -631,7 +697,7 @@ size_t SnapshotSerializer::Write(const ImmediateInfo::SerializeInfo& data) {
Debug("Write<ImmediateInfo::SerializeInfo>() %s\n", str.c_str());
}
- size_t written_total = Write<AliasedBufferIndex>(data.fields);
+ size_t written_total = WriteArithmetic<AliasedBufferIndex>(data.fields);
Debug("Write<ImmediateInfo::SerializeInfo>() wrote %d bytes\n",
written_total);
@@ -644,13 +710,12 @@ size_t SnapshotSerializer::Write(const ImmediateInfo::SerializeInfo& data) {
// [ 4/8 bytes ] snapshot index of observers
template <>
performance::PerformanceState::SerializeInfo SnapshotDeserializer::Read() {
- per_process::Debug(DebugCategory::MKSNAPSHOT,
- "Read<PerformanceState::SerializeInfo>()\n");
+ Debug("Read<PerformanceState::SerializeInfo>()\n");
performance::PerformanceState::SerializeInfo result;
- result.root = Read<AliasedBufferIndex>();
- result.milestones = Read<AliasedBufferIndex>();
- result.observers = Read<AliasedBufferIndex>();
+ result.root = ReadArithmetic<AliasedBufferIndex>();
+ result.milestones = ReadArithmetic<AliasedBufferIndex>();
+ result.observers = ReadArithmetic<AliasedBufferIndex>();
if (is_debug) {
std::string str = ToStr(result);
Debug("Read<PerformanceState::SerializeInfo>() %s\n", str.c_str());
@@ -666,9 +731,9 @@ size_t SnapshotSerializer::Write(
Debug("Write<PerformanceState::SerializeInfo>() %s\n", str.c_str());
}
- size_t written_total = Write<AliasedBufferIndex>(data.root);
- written_total += Write<AliasedBufferIndex>(data.milestones);
- written_total += Write<AliasedBufferIndex>(data.observers);
+ size_t written_total = WriteArithmetic<AliasedBufferIndex>(data.root);
+ written_total += WriteArithmetic<AliasedBufferIndex>(data.milestones);
+ written_total += WriteArithmetic<AliasedBufferIndex>(data.observers);
Debug("Write<PerformanceState::SerializeInfo>() wrote %d bytes\n",
written_total);
@@ -682,8 +747,7 @@ size_t SnapshotSerializer::Write(
// [ ... ] |length| of PropInfo data
template <>
IsolateDataSerializeInfo SnapshotDeserializer::Read() {
- per_process::Debug(DebugCategory::MKSNAPSHOT,
- "Read<IsolateDataSerializeInfo>()\n");
+ Debug("Read<IsolateDataSerializeInfo>()\n");
IsolateDataSerializeInfo result;
result.primitive_values = ReadVector<SnapshotIndex>();
@@ -711,12 +775,12 @@ size_t SnapshotSerializer::Write(const IsolateDataSerializeInfo& data) {
template <>
RealmSerializeInfo SnapshotDeserializer::Read() {
- per_process::Debug(DebugCategory::MKSNAPSHOT, "Read<RealmSerializeInfo>()\n");
+ Debug("Read<RealmSerializeInfo>()\n");
RealmSerializeInfo result;
result.builtins = ReadVector<std::string>();
result.persistent_values = ReadVector<PropInfo>();
result.native_objects = ReadVector<PropInfo>();
- result.context = Read<SnapshotIndex>();
+ result.context = ReadArithmetic<SnapshotIndex>();
return result;
}
@@ -731,7 +795,7 @@ size_t SnapshotSerializer::Write(const RealmSerializeInfo& data) {
size_t written_total = WriteVector<std::string>(data.builtins);
written_total += WriteVector<PropInfo>(data.persistent_values);
written_total += WriteVector<PropInfo>(data.native_objects);
- written_total += Write<SnapshotIndex>(data.context);
+ written_total += WriteArithmetic<SnapshotIndex>(data.context);
Debug("Write<RealmSerializeInfo>() wrote %d bytes\n", written_total);
return written_total;
@@ -739,17 +803,17 @@ size_t SnapshotSerializer::Write(const RealmSerializeInfo& data) {
template <>
EnvSerializeInfo SnapshotDeserializer::Read() {
- per_process::Debug(DebugCategory::MKSNAPSHOT, "Read<EnvSerializeInfo>()\n");
+ Debug("Read<EnvSerializeInfo>()\n");
EnvSerializeInfo result;
result.async_hooks = Read<AsyncHooks::SerializeInfo>();
result.tick_info = Read<TickInfo::SerializeInfo>();
result.immediate_info = Read<ImmediateInfo::SerializeInfo>();
- result.timeout_info = Read<AliasedBufferIndex>();
+ result.timeout_info = ReadArithmetic<AliasedBufferIndex>();
result.performance_state =
Read<performance::PerformanceState::SerializeInfo>();
- result.exit_info = Read<AliasedBufferIndex>();
- result.stream_base_state = Read<AliasedBufferIndex>();
- result.should_abort_on_uncaught_toggle = Read<AliasedBufferIndex>();
+ result.exit_info = ReadArithmetic<AliasedBufferIndex>();
+ result.stream_base_state = ReadArithmetic<AliasedBufferIndex>();
+ result.should_abort_on_uncaught_toggle = ReadArithmetic<AliasedBufferIndex>();
result.principal_realm = Read<RealmSerializeInfo>();
return result;
}
@@ -765,13 +829,13 @@ size_t SnapshotSerializer::Write(const EnvSerializeInfo& data) {
size_t written_total = Write<AsyncHooks::SerializeInfo>(data.async_hooks);
written_total += Write<TickInfo::SerializeInfo>(data.tick_info);
written_total += Write<ImmediateInfo::SerializeInfo>(data.immediate_info);
- written_total += Write<AliasedBufferIndex>(data.timeout_info);
+ written_total += WriteArithmetic<AliasedBufferIndex>(data.timeout_info);
written_total += Write<performance::PerformanceState::SerializeInfo>(
data.performance_state);
- written_total += Write<AliasedBufferIndex>(data.exit_info);
- written_total += Write<AliasedBufferIndex>(data.stream_base_state);
+ written_total += WriteArithmetic<AliasedBufferIndex>(data.exit_info);
+ written_total += WriteArithmetic<AliasedBufferIndex>(data.stream_base_state);
written_total +=
- Write<AliasedBufferIndex>(data.should_abort_on_uncaught_toggle);
+ WriteArithmetic<AliasedBufferIndex>(data.should_abort_on_uncaught_toggle);
written_total += Write<RealmSerializeInfo>(data.principal_realm);
Debug("Write<EnvSerializeInfo>() wrote %d bytes\n", written_total);
@@ -789,14 +853,14 @@ size_t SnapshotSerializer::Write(const EnvSerializeInfo& data) {
// [ 4 bytes ] v8 cache version tag
template <>
SnapshotMetadata SnapshotDeserializer::Read() {
- per_process::Debug(DebugCategory::MKSNAPSHOT, "Read<SnapshotMetadata>()\n");
+ Debug("Read<SnapshotMetadata>()\n");
SnapshotMetadata result;
- result.type = static_cast<SnapshotMetadata::Type>(Read<uint8_t>());
+ result.type = static_cast<SnapshotMetadata::Type>(ReadArithmetic<uint8_t>());
result.node_version = ReadString();
result.node_arch = ReadString();
result.node_platform = ReadString();
- result.v8_cache_version_tag = Read<uint32_t>();
+ result.v8_cache_version_tag = ReadArithmetic<uint32_t>();
if (is_debug) {
std::string str = ToStr(result);
@@ -816,7 +880,7 @@ size_t SnapshotSerializer::Write(const SnapshotMetadata& data) {
// Node.js may perform synchronizations that are platform-specific and they
// can be changed in semver-patches.
Debug("Write snapshot type %" PRIu8 "\n", static_cast<uint8_t>(data.type));
- written_total += Write<uint8_t>(static_cast<uint8_t>(data.type));
+ written_total += WriteArithmetic<uint8_t>(static_cast<uint8_t>(data.type));
Debug("Write Node.js version %s\n", data.node_version.c_str());
written_total += WriteString(data.node_version);
Debug("Write Node.js arch %s\n", data.node_arch);
@@ -825,7 +889,7 @@ size_t SnapshotSerializer::Write(const SnapshotMetadata& data) {
written_total += WriteString(data.node_platform);
Debug("Write V8 cached data version tag %" PRIx32 "\n",
data.v8_cache_version_tag);
- written_total += Write<uint32_t>(data.v8_cache_version_tag);
+ written_total += WriteArithmetic<uint32_t>(data.v8_cache_version_tag);
return written_total;
}
@@ -848,7 +912,7 @@ std::vector<char> SnapshotData::ToBlob() const {
// Metadata
w.Debug("Write magic %" PRIx32 "\n", kMagic);
- written_total += w.Write<uint32_t>(kMagic);
+ written_total += w.WriteArithmetic<uint32_t>(kMagic);
w.Debug("Write metadata\n");
written_total += w.Write<SnapshotMetadata>(metadata);
@@ -883,13 +947,17 @@ bool SnapshotData::FromFile(SnapshotData* out, FILE* in) {
}
bool SnapshotData::FromBlob(SnapshotData* out, const std::vector<char>& in) {
+ return FromBlob(out, std::string_view(in.data(), in.size()));
+}
+
+bool SnapshotData::FromBlob(SnapshotData* out, std::string_view in) {
SnapshotDeserializer r(in);
r.Debug("SnapshotData::FromBlob()\n");
DCHECK_EQ(out->data_ownership, SnapshotData::DataOwnership::kOwned);
// Metadata
- uint32_t magic = r.Read<uint32_t>();
+ uint32_t magic = r.ReadArithmetic<uint32_t>();
r.Debug("Read magic %" PRIx32 "\n", magic);
CHECK_EQ(magic, kMagic);
out->metadata = r.Read<SnapshotMetadata>();