[snapshot] Dedicated files for snapshot data
The intent of this work is to create a clean interface header file for the snapshot component. As a first step, move SerializedData and SnapshotData into their own dedicated files. Bug: v8:10416 Change-Id: I95af08508555a2ec3c2364094b81a76e3e6bb38a Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/2144117 Commit-Queue: Jakob Gruber <jgruber@chromium.org> Reviewed-by: Dan Elphick <delphick@chromium.org> Cr-Commit-Position: refs/heads/master@{#67269}
This commit is contained in:
parent
fe60913945
commit
b39ee29d46
2
BUILD.gn
2
BUILD.gn
@ -2960,6 +2960,8 @@ v8_source_set("v8_base_without_compiler") {
|
||||
"src/snapshot/snapshot-common.cc",
|
||||
"src/snapshot/snapshot-compression.cc",
|
||||
"src/snapshot/snapshot-compression.h",
|
||||
"src/snapshot/snapshot-data.cc",
|
||||
"src/snapshot/snapshot-data.h",
|
||||
"src/snapshot/snapshot-source-sink.cc",
|
||||
"src/snapshot/snapshot-source-sink.h",
|
||||
"src/snapshot/snapshot.h",
|
||||
|
@ -10,7 +10,8 @@
|
||||
#include "src/deoptimizer/deoptimizer.h"
|
||||
#include "src/heap/heap-write-barrier-inl.h"
|
||||
#include "src/objects/code-inl.h"
|
||||
#include "src/snapshot/snapshot.h"
|
||||
#include "src/snapshot/embedded/embedded-data.h"
|
||||
#include "src/snapshot/serializer-common.h" // For ExternalReferenceEncoder.
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
|
@ -21,7 +21,7 @@
|
||||
#include "src/objects/slots.h"
|
||||
#include "src/objects/smi.h"
|
||||
#include "src/objects/visitors.h"
|
||||
#include "src/snapshot/snapshot.h"
|
||||
#include "src/snapshot/embedded/embedded-data.h"
|
||||
#include "src/strings/string-stream.h"
|
||||
#include "src/wasm/wasm-code-manager.h"
|
||||
#include "src/wasm/wasm-engine.h"
|
||||
|
@ -25,6 +25,7 @@
|
||||
#endif // ENABLE_VTUNE_TRACEMARK
|
||||
#include "src/heap/heap-inl.h"
|
||||
#include "src/logging/counters.h"
|
||||
#include "src/logging/log.h"
|
||||
#include "src/numbers/math-random.h"
|
||||
#include "src/objects/api-callbacks.h"
|
||||
#include "src/objects/arguments.h"
|
||||
|
@ -27,6 +27,7 @@
|
||||
#include "src/objects/js-promise-inl.h"
|
||||
#include "src/runtime/runtime-utils.h"
|
||||
#include "src/runtime/runtime.h"
|
||||
#include "src/snapshot/embedded/embedded-data.h"
|
||||
#include "src/snapshot/snapshot.h"
|
||||
#include "src/wasm/wasm-objects-inl.h"
|
||||
|
||||
|
@ -9,6 +9,7 @@
|
||||
#include "src/heap/heap.h"
|
||||
#include "src/objects/heap-object.h"
|
||||
#include "src/snapshot/serializer-common.h"
|
||||
#include "src/snapshot/snapshot-data.h"
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
|
@ -22,6 +22,7 @@
|
||||
#include "src/objects/smi.h"
|
||||
#include "src/objects/string.h"
|
||||
#include "src/roots/roots.h"
|
||||
#include "src/snapshot/embedded/embedded-data.h"
|
||||
#include "src/snapshot/snapshot.h"
|
||||
#include "src/tracing/trace-event.h"
|
||||
#include "src/tracing/traced-value.h"
|
||||
|
@ -6,6 +6,7 @@
|
||||
#define V8_SNAPSHOT_SERIALIZER_ALLOCATOR_H_
|
||||
|
||||
#include "src/snapshot/serializer-common.h"
|
||||
#include "src/snapshot/snapshot-data.h"
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
|
@ -96,16 +96,6 @@ const char* ExternalReferenceEncoder::NameOfAddress(Isolate* isolate,
|
||||
return isolate->external_reference_table()->name(value.index());
|
||||
}
|
||||
|
||||
void SerializedData::AllocateData(uint32_t size) {
|
||||
DCHECK(!owns_data_);
|
||||
data_ = NewArray<byte>(size);
|
||||
size_ = size;
|
||||
owns_data_ = true;
|
||||
}
|
||||
|
||||
// static
|
||||
constexpr uint32_t SerializedData::kMagicNumber;
|
||||
|
||||
// The partial snapshot cache is terminated by undefined. We visit the
|
||||
// partial snapshot...
|
||||
// - during deserialization to populate it.
|
||||
|
@ -293,70 +293,6 @@ class SerializerDeserializer : public RootVisitor {
|
||||
HotObjectsList hot_objects_;
|
||||
};
|
||||
|
||||
class SerializedData {
|
||||
public:
|
||||
class Reservation {
|
||||
public:
|
||||
Reservation() : reservation_(0) {}
|
||||
explicit Reservation(uint32_t size)
|
||||
: reservation_(ChunkSizeBits::encode(size)) {}
|
||||
|
||||
uint32_t chunk_size() const { return ChunkSizeBits::decode(reservation_); }
|
||||
bool is_last() const { return IsLastChunkBits::decode(reservation_); }
|
||||
|
||||
void mark_as_last() { reservation_ |= IsLastChunkBits::encode(true); }
|
||||
|
||||
private:
|
||||
uint32_t reservation_;
|
||||
};
|
||||
|
||||
SerializedData(byte* data, int size)
|
||||
: data_(data), size_(size), owns_data_(false) {}
|
||||
SerializedData() : data_(nullptr), size_(0), owns_data_(false) {}
|
||||
SerializedData(SerializedData&& other) V8_NOEXCEPT
|
||||
: data_(other.data_),
|
||||
size_(other.size_),
|
||||
owns_data_(other.owns_data_) {
|
||||
// Ensure |other| will not attempt to destroy our data in destructor.
|
||||
other.owns_data_ = false;
|
||||
}
|
||||
|
||||
virtual ~SerializedData() {
|
||||
if (owns_data_) DeleteArray<byte>(data_);
|
||||
}
|
||||
|
||||
uint32_t GetMagicNumber() const { return GetHeaderValue(kMagicNumberOffset); }
|
||||
|
||||
using ChunkSizeBits = base::BitField<uint32_t, 0, 31>;
|
||||
using IsLastChunkBits = base::BitField<bool, 31, 1>;
|
||||
|
||||
static constexpr uint32_t kMagicNumberOffset = 0;
|
||||
static constexpr uint32_t kMagicNumber =
|
||||
0xC0DE0000 ^ ExternalReferenceTable::kSize;
|
||||
|
||||
protected:
|
||||
void SetHeaderValue(uint32_t offset, uint32_t value) {
|
||||
base::WriteLittleEndianValue(reinterpret_cast<Address>(data_) + offset,
|
||||
value);
|
||||
}
|
||||
|
||||
uint32_t GetHeaderValue(uint32_t offset) const {
|
||||
return base::ReadLittleEndianValue<uint32_t>(
|
||||
reinterpret_cast<Address>(data_) + offset);
|
||||
}
|
||||
|
||||
void AllocateData(uint32_t size);
|
||||
|
||||
void SetMagicNumber() { SetHeaderValue(kMagicNumberOffset, kMagicNumber); }
|
||||
|
||||
byte* data_;
|
||||
uint32_t size_;
|
||||
bool owns_data_;
|
||||
|
||||
private:
|
||||
DISALLOW_COPY_AND_ASSIGN(SerializedData);
|
||||
};
|
||||
|
||||
V8_EXPORT_PRIVATE uint32_t Checksum(Vector<const byte> payload);
|
||||
|
||||
} // namespace internal
|
||||
|
@ -339,58 +339,6 @@ void Snapshot::CheckVersion(const v8::StartupData* data) {
|
||||
}
|
||||
}
|
||||
|
||||
SnapshotData::SnapshotData(const Serializer* serializer) {
|
||||
DisallowHeapAllocation no_gc;
|
||||
std::vector<Reservation> reservations = serializer->EncodeReservations();
|
||||
const std::vector<byte>* payload = serializer->Payload();
|
||||
|
||||
// Calculate sizes.
|
||||
uint32_t reservation_size =
|
||||
static_cast<uint32_t>(reservations.size()) * kUInt32Size;
|
||||
uint32_t payload_offset = kHeaderSize + reservation_size;
|
||||
uint32_t padded_payload_offset = POINTER_SIZE_ALIGN(payload_offset);
|
||||
uint32_t size =
|
||||
padded_payload_offset + static_cast<uint32_t>(payload->size());
|
||||
|
||||
// Allocate backing store and create result data.
|
||||
AllocateData(size);
|
||||
|
||||
// Zero out pre-payload data. Part of that is only used for padding.
|
||||
memset(data_, 0, padded_payload_offset);
|
||||
|
||||
// Set header values.
|
||||
SetMagicNumber();
|
||||
SetHeaderValue(kNumReservationsOffset, static_cast<int>(reservations.size()));
|
||||
SetHeaderValue(kPayloadLengthOffset, static_cast<int>(payload->size()));
|
||||
|
||||
// Copy reservation chunk sizes.
|
||||
CopyBytes(data_ + kHeaderSize, reinterpret_cast<byte*>(reservations.data()),
|
||||
reservation_size);
|
||||
|
||||
// Copy serialized data.
|
||||
CopyBytes(data_ + padded_payload_offset, payload->data(),
|
||||
static_cast<size_t>(payload->size()));
|
||||
}
|
||||
|
||||
std::vector<SerializedData::Reservation> SnapshotData::Reservations() const {
|
||||
uint32_t size = GetHeaderValue(kNumReservationsOffset);
|
||||
std::vector<SerializedData::Reservation> reservations(size);
|
||||
memcpy(reservations.data(), data_ + kHeaderSize,
|
||||
size * sizeof(SerializedData::Reservation));
|
||||
return reservations;
|
||||
}
|
||||
|
||||
Vector<const byte> SnapshotData::Payload() const {
|
||||
uint32_t reservations_size =
|
||||
GetHeaderValue(kNumReservationsOffset) * kUInt32Size;
|
||||
uint32_t padded_payload_offset =
|
||||
POINTER_SIZE_ALIGN(kHeaderSize + reservations_size);
|
||||
const byte* payload = data_ + padded_payload_offset;
|
||||
uint32_t length = GetHeaderValue(kPayloadLengthOffset);
|
||||
DCHECK_EQ(data_ + size_, payload + length);
|
||||
return Vector<const byte>(payload, length);
|
||||
}
|
||||
|
||||
namespace {
|
||||
|
||||
bool RunExtraCode(v8::Isolate* isolate, v8::Local<v8::Context> context,
|
||||
|
80
src/snapshot/snapshot-data.cc
Normal file
80
src/snapshot/snapshot-data.cc
Normal file
@ -0,0 +1,80 @@
|
||||
// Copyright 2020 the V8 project authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
#include "src/snapshot/snapshot-data.h"
|
||||
|
||||
#include "src/common/assert-scope.h"
|
||||
#include "src/snapshot/serializer.h"
|
||||
|
||||
#ifdef V8_SNAPSHOT_COMPRESSION
|
||||
#include "src/snapshot/snapshot-compression.h"
|
||||
#endif
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
|
||||
void SerializedData::AllocateData(uint32_t size) {
|
||||
DCHECK(!owns_data_);
|
||||
data_ = NewArray<byte>(size);
|
||||
size_ = size;
|
||||
owns_data_ = true;
|
||||
}
|
||||
|
||||
// static
|
||||
constexpr uint32_t SerializedData::kMagicNumber;
|
||||
|
||||
SnapshotData::SnapshotData(const Serializer* serializer) {
|
||||
DisallowHeapAllocation no_gc;
|
||||
std::vector<Reservation> reservations = serializer->EncodeReservations();
|
||||
const std::vector<byte>* payload = serializer->Payload();
|
||||
|
||||
// Calculate sizes.
|
||||
uint32_t reservation_size =
|
||||
static_cast<uint32_t>(reservations.size()) * kUInt32Size;
|
||||
uint32_t payload_offset = kHeaderSize + reservation_size;
|
||||
uint32_t padded_payload_offset = POINTER_SIZE_ALIGN(payload_offset);
|
||||
uint32_t size =
|
||||
padded_payload_offset + static_cast<uint32_t>(payload->size());
|
||||
|
||||
// Allocate backing store and create result data.
|
||||
AllocateData(size);
|
||||
|
||||
// Zero out pre-payload data. Part of that is only used for padding.
|
||||
memset(data_, 0, padded_payload_offset);
|
||||
|
||||
// Set header values.
|
||||
SetMagicNumber();
|
||||
SetHeaderValue(kNumReservationsOffset, static_cast<int>(reservations.size()));
|
||||
SetHeaderValue(kPayloadLengthOffset, static_cast<int>(payload->size()));
|
||||
|
||||
// Copy reservation chunk sizes.
|
||||
CopyBytes(data_ + kHeaderSize, reinterpret_cast<byte*>(reservations.data()),
|
||||
reservation_size);
|
||||
|
||||
// Copy serialized data.
|
||||
CopyBytes(data_ + padded_payload_offset, payload->data(),
|
||||
static_cast<size_t>(payload->size()));
|
||||
}
|
||||
|
||||
std::vector<SerializedData::Reservation> SnapshotData::Reservations() const {
|
||||
uint32_t size = GetHeaderValue(kNumReservationsOffset);
|
||||
std::vector<SerializedData::Reservation> reservations(size);
|
||||
memcpy(reservations.data(), data_ + kHeaderSize,
|
||||
size * sizeof(SerializedData::Reservation));
|
||||
return reservations;
|
||||
}
|
||||
|
||||
Vector<const byte> SnapshotData::Payload() const {
|
||||
uint32_t reservations_size =
|
||||
GetHeaderValue(kNumReservationsOffset) * kUInt32Size;
|
||||
uint32_t padded_payload_offset =
|
||||
POINTER_SIZE_ALIGN(kHeaderSize + reservations_size);
|
||||
const byte* payload = data_ + padded_payload_offset;
|
||||
uint32_t length = GetHeaderValue(kPayloadLengthOffset);
|
||||
DCHECK_EQ(data_ + size_, payload + length);
|
||||
return Vector<const byte>(payload, length);
|
||||
}
|
||||
|
||||
} // namespace internal
|
||||
} // namespace v8
|
129
src/snapshot/snapshot-data.h
Normal file
129
src/snapshot/snapshot-data.h
Normal file
@ -0,0 +1,129 @@
|
||||
// Copyright 2020 the V8 project authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
#ifndef V8_SNAPSHOT_SNAPSHOT_DATA_H_
|
||||
#define V8_SNAPSHOT_SNAPSHOT_DATA_H_
|
||||
|
||||
#include "src/base/bit-field.h"
|
||||
#include "src/base/memory.h"
|
||||
#include "src/codegen/external-reference-table.h"
|
||||
#include "src/utils/memcopy.h"
|
||||
#include "src/utils/vector.h"
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
|
||||
// Forward declarations.
|
||||
class Isolate;
|
||||
class Serializer;
|
||||
|
||||
class SerializedData {
|
||||
public:
|
||||
class Reservation {
|
||||
public:
|
||||
Reservation() : reservation_(0) {}
|
||||
explicit Reservation(uint32_t size)
|
||||
: reservation_(ChunkSizeBits::encode(size)) {}
|
||||
|
||||
uint32_t chunk_size() const { return ChunkSizeBits::decode(reservation_); }
|
||||
bool is_last() const { return IsLastChunkBits::decode(reservation_); }
|
||||
|
||||
void mark_as_last() { reservation_ |= IsLastChunkBits::encode(true); }
|
||||
|
||||
private:
|
||||
uint32_t reservation_;
|
||||
};
|
||||
|
||||
SerializedData(byte* data, int size)
|
||||
: data_(data), size_(size), owns_data_(false) {}
|
||||
SerializedData() : data_(nullptr), size_(0), owns_data_(false) {}
|
||||
SerializedData(SerializedData&& other) V8_NOEXCEPT
|
||||
: data_(other.data_),
|
||||
size_(other.size_),
|
||||
owns_data_(other.owns_data_) {
|
||||
// Ensure |other| will not attempt to destroy our data in destructor.
|
||||
other.owns_data_ = false;
|
||||
}
|
||||
|
||||
virtual ~SerializedData() {
|
||||
if (owns_data_) DeleteArray<byte>(data_);
|
||||
}
|
||||
|
||||
uint32_t GetMagicNumber() const { return GetHeaderValue(kMagicNumberOffset); }
|
||||
|
||||
using ChunkSizeBits = base::BitField<uint32_t, 0, 31>;
|
||||
using IsLastChunkBits = base::BitField<bool, 31, 1>;
|
||||
|
||||
static constexpr uint32_t kMagicNumberOffset = 0;
|
||||
static constexpr uint32_t kMagicNumber =
|
||||
0xC0DE0000 ^ ExternalReferenceTable::kSize;
|
||||
|
||||
protected:
|
||||
void SetHeaderValue(uint32_t offset, uint32_t value) {
|
||||
base::WriteLittleEndianValue(reinterpret_cast<Address>(data_) + offset,
|
||||
value);
|
||||
}
|
||||
|
||||
uint32_t GetHeaderValue(uint32_t offset) const {
|
||||
return base::ReadLittleEndianValue<uint32_t>(
|
||||
reinterpret_cast<Address>(data_) + offset);
|
||||
}
|
||||
|
||||
void AllocateData(uint32_t size);
|
||||
|
||||
void SetMagicNumber() { SetHeaderValue(kMagicNumberOffset, kMagicNumber); }
|
||||
|
||||
byte* data_;
|
||||
uint32_t size_;
|
||||
bool owns_data_;
|
||||
|
||||
private:
|
||||
DISALLOW_COPY_AND_ASSIGN(SerializedData);
|
||||
};
|
||||
|
||||
// Wrapper around reservation sizes and the serialization payload.
|
||||
class V8_EXPORT_PRIVATE SnapshotData : public SerializedData {
|
||||
public:
|
||||
// Used when producing.
|
||||
explicit SnapshotData(const Serializer* serializer);
|
||||
|
||||
// Used when consuming.
|
||||
explicit SnapshotData(const Vector<const byte> snapshot)
|
||||
: SerializedData(const_cast<byte*>(snapshot.begin()), snapshot.length()) {
|
||||
}
|
||||
|
||||
std::vector<Reservation> Reservations() const;
|
||||
virtual Vector<const byte> Payload() const;
|
||||
|
||||
Vector<const byte> RawData() const {
|
||||
return Vector<const byte>(data_, size_);
|
||||
}
|
||||
|
||||
protected:
|
||||
// Empty constructor used by SnapshotCompression so it can manually allocate
|
||||
// memory.
|
||||
SnapshotData() : SerializedData() {}
|
||||
friend class SnapshotCompression;
|
||||
|
||||
// Resize used by SnapshotCompression so it can shrink the compressed
|
||||
// SnapshotData.
|
||||
void Resize(uint32_t size) { size_ = size; }
|
||||
|
||||
// The data header consists of uint32_t-sized entries:
|
||||
// [0] magic number and (internal) external reference count
|
||||
// [1] number of reservation size entries
|
||||
// [2] payload length
|
||||
// ... reservations
|
||||
// ... serialized payload
|
||||
static const uint32_t kNumReservationsOffset =
|
||||
kMagicNumberOffset + kUInt32Size;
|
||||
static const uint32_t kPayloadLengthOffset =
|
||||
kNumReservationsOffset + kUInt32Size;
|
||||
static const uint32_t kHeaderSize = kPayloadLengthOffset + kUInt32Size;
|
||||
};
|
||||
|
||||
} // namespace internal
|
||||
} // namespace v8
|
||||
|
||||
#endif // V8_SNAPSHOT_SNAPSHOT_DATA_H_
|
@ -5,60 +5,17 @@
|
||||
#ifndef V8_SNAPSHOT_SNAPSHOT_H_
|
||||
#define V8_SNAPSHOT_SNAPSHOT_H_
|
||||
|
||||
#include "src/snapshot/partial-serializer.h"
|
||||
#include "src/snapshot/startup-serializer.h"
|
||||
#include "include/v8.h"
|
||||
|
||||
#include "src/utils/utils.h"
|
||||
#include "src/base/memory.h"
|
||||
#include "src/utils/vector.h"
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
|
||||
// Forward declarations.
|
||||
class Isolate;
|
||||
class PartialSerializer;
|
||||
class SnapshotCompression;
|
||||
class StartupSerializer;
|
||||
|
||||
// Wrapper around reservation sizes and the serialization payload.
|
||||
class V8_EXPORT_PRIVATE SnapshotData : public SerializedData {
|
||||
public:
|
||||
// Used when producing.
|
||||
explicit SnapshotData(const Serializer* serializer);
|
||||
|
||||
// Used when consuming.
|
||||
explicit SnapshotData(const Vector<const byte> snapshot)
|
||||
: SerializedData(const_cast<byte*>(snapshot.begin()), snapshot.length()) {
|
||||
}
|
||||
|
||||
std::vector<Reservation> Reservations() const;
|
||||
virtual Vector<const byte> Payload() const;
|
||||
|
||||
Vector<const byte> RawData() const {
|
||||
return Vector<const byte>(data_, size_);
|
||||
}
|
||||
|
||||
protected:
|
||||
// Empty constructor used by SnapshotCompression so it can manually allocate
|
||||
// memory.
|
||||
SnapshotData() : SerializedData() {}
|
||||
friend class SnapshotCompression;
|
||||
|
||||
// Resize used by SnapshotCompression so it can shrink the compressed
|
||||
// SnapshotData.
|
||||
void Resize(uint32_t size) { size_ = size; }
|
||||
|
||||
// The data header consists of uint32_t-sized entries:
|
||||
// [0] magic number and (internal) external reference count
|
||||
// [1] number of reservation size entries
|
||||
// [2] payload length
|
||||
// ... reservations
|
||||
// ... serialized payload
|
||||
static const uint32_t kNumReservationsOffset =
|
||||
kMagicNumberOffset + kUInt32Size;
|
||||
static const uint32_t kPayloadLengthOffset =
|
||||
kNumReservationsOffset + kUInt32Size;
|
||||
static const uint32_t kHeaderSize = kPayloadLengthOffset + kUInt32Size;
|
||||
};
|
||||
class SnapshotData;
|
||||
class JSGlobalProxy;
|
||||
|
||||
class Snapshot : public AllStatic {
|
||||
public:
|
||||
|
@ -8,6 +8,7 @@
|
||||
#include "src/codegen/assembler-inl.h"
|
||||
#include "src/execution/v8threads.h"
|
||||
#include "src/heap/heap-inl.h"
|
||||
#include "src/logging/log.h"
|
||||
#include "src/snapshot/snapshot.h"
|
||||
|
||||
namespace v8 {
|
||||
|
Loading…
Reference in New Issue
Block a user