[heap] Fix --code-stats with code cache
During deserialization all allocated objects are preinitialized with Smi 0. During code cache deserialization GCs may happen. When --code-stats is enabled as well, code stats are collected during GC. In such situations crashes may happen because of fields in BytecodeArray objects not being deserialized at the time of GC. This CL introduces new raw_* getters for --code-stats which allows accessing these fields while they still contain 0. Bug: v8:13704 Change-Id: I767714ca1c936a031d71f3eb53d6401030ccce7e Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/4212406 Reviewed-by: Jakob Linke <jgruber@chromium.org> Commit-Queue: Dominik Inführ <dinfuehr@chromium.org> Cr-Commit-Position: refs/heads/main@{#85632}
This commit is contained in:
parent
de4e49260f
commit
31654be902
@ -1416,15 +1416,50 @@ DEF_GETTER(BytecodeArray, SourcePositionTable, ByteArray) {
|
||||
return roots.empty_byte_array();
|
||||
}
|
||||
|
||||
DEF_GETTER(BytecodeArray, raw_constant_pool, Object) {
|
||||
Object value =
|
||||
TaggedField<Object>::load(cage_base, *this, kConstantPoolOffset);
|
||||
// This field might be 0 during deserialization.
|
||||
DCHECK(value == Smi::zero() || value.IsFixedArray());
|
||||
return value;
|
||||
}
|
||||
|
||||
DEF_GETTER(BytecodeArray, raw_handler_table, Object) {
|
||||
Object value =
|
||||
TaggedField<Object>::load(cage_base, *this, kHandlerTableOffset);
|
||||
// This field might be 0 during deserialization.
|
||||
DCHECK(value == Smi::zero() || value.IsByteArray());
|
||||
return value;
|
||||
}
|
||||
|
||||
DEF_GETTER(BytecodeArray, raw_source_position_table, Object) {
|
||||
Object value =
|
||||
TaggedField<Object>::load(cage_base, *this, kSourcePositionTableOffset);
|
||||
// This field might be 0 during deserialization.
|
||||
DCHECK(value == Smi::zero() || value.IsByteArray() || value.IsUndefined() ||
|
||||
value.IsException());
|
||||
return value;
|
||||
}
|
||||
|
||||
int BytecodeArray::BytecodeArraySize() const { return SizeFor(this->length()); }
|
||||
|
||||
DEF_GETTER(BytecodeArray, SizeIncludingMetadata, int) {
|
||||
int size = BytecodeArraySize();
|
||||
size += constant_pool(cage_base).Size(cage_base);
|
||||
size += handler_table(cage_base).Size();
|
||||
ByteArray table = SourcePositionTable(cage_base);
|
||||
if (table.length() != 0) {
|
||||
size += table.Size();
|
||||
Object maybe_constant_pool = raw_constant_pool(cage_base);
|
||||
if (maybe_constant_pool.IsFixedArray()) {
|
||||
size += FixedArray::cast(maybe_constant_pool).Size(cage_base);
|
||||
} else {
|
||||
DCHECK_EQ(maybe_constant_pool, Smi::zero());
|
||||
}
|
||||
Object maybe_handler_table = raw_handler_table(cage_base);
|
||||
if (maybe_handler_table.IsByteArray()) {
|
||||
size += ByteArray::cast(maybe_handler_table).Size();
|
||||
} else {
|
||||
DCHECK_EQ(maybe_handler_table, Smi::zero());
|
||||
}
|
||||
Object maybe_table = raw_source_position_table(cage_base);
|
||||
if (maybe_table.IsByteArray()) {
|
||||
size += ByteArray::cast(maybe_table).Size();
|
||||
}
|
||||
return size;
|
||||
}
|
||||
|
@ -1068,6 +1068,11 @@ class BytecodeArray
|
||||
// this will return empty_byte_array.
|
||||
DECL_GETTER(SourcePositionTable, ByteArray)
|
||||
|
||||
// Raw accessors to access these fields during code cache deserialization.
|
||||
DECL_GETTER(raw_constant_pool, Object)
|
||||
DECL_GETTER(raw_handler_table, Object)
|
||||
DECL_GETTER(raw_source_position_table, Object)
|
||||
|
||||
// Indicates that an attempt was made to collect source positions, but that it
|
||||
// failed most likely due to stack exhaustion. When in this state
|
||||
// |SourcePositionTable| will return an empty byte array rather than crashing
|
||||
|
Loading…
Reference in New Issue
Block a user