[cpu-profiler] Remove name_prefix field from CodeEntry

We can save a pointer of space for each CodeEntry by removing this
field which we don't really need. Instead of concatenating the name
string on demand, concatenate the prefix eagerly.

Reduces sizeof(CodeEntry) from 136 to 128 on 64-bit.

Bug: v8:7719

Cq-Include-Trybots: luci.chromium.try:linux_chromium_rel_ng
Change-Id: Id346a8f36794e337e8c886f8d1969431424539b0
Reviewed-on: https://chromium-review.googlesource.com/1039825
Reviewed-by: Yang Guo <yangguo@chromium.org>
Reviewed-by: Alexei Filippov <alph@chromium.org>
Commit-Queue: Peter Marshall <petermarshall@chromium.org>
Cr-Commit-Position: refs/heads/master@{#53014}
This commit is contained in:
Peter Marshall 2018-05-02 16:53:56 +02:00 committed by Commit Bot
parent 633910e6e5
commit 6f72af25fe
9 changed files with 61 additions and 62 deletions

View File

@ -9836,15 +9836,7 @@ Local<String> CpuProfileNode::GetFunctionName() const {
const i::CodeEntry* entry = node->entry();
i::Handle<i::String> name =
isolate->factory()->InternalizeUtf8String(entry->name());
if (!entry->has_name_prefix()) {
return ToApiHandle<String>(name);
} else {
// We do not expect this to fail. Change this if it does.
i::Handle<i::String> cons = isolate->factory()->NewConsString(
isolate->factory()->InternalizeUtf8String(entry->name_prefix()),
name).ToHandleChecked();
return ToApiHandle<String>(cons);
}
return ToApiHandle<String>(name);
}
int debug::Coverage::BlockData::StartOffset() const { return block_->start; }

View File

@ -328,9 +328,8 @@ void CpuProfiler::CreateEntriesForRuntimeCallStats() {
for (int i = 0; i < RuntimeCallStats::kNumberOfCounters; ++i) {
RuntimeCallCounter* counter = rcs->GetCounter(i);
DCHECK(counter->name());
std::unique_ptr<CodeEntry> entry(
new CodeEntry(CodeEventListener::FUNCTION_TAG, counter->name(),
CodeEntry::kEmptyNamePrefix, "native V8Runtime"));
std::unique_ptr<CodeEntry> entry(new CodeEntry(
CodeEventListener::FUNCTION_TAG, counter->name(), "native V8Runtime"));
code_map->AddCode(reinterpret_cast<Address>(counter), entry.get(), 1);
static_entries_.push_back(std::move(entry));
}

View File

@ -11,13 +11,12 @@ namespace v8 {
namespace internal {
CodeEntry::CodeEntry(CodeEventListener::LogEventsAndTags tag, const char* name,
const char* name_prefix, const char* resource_name,
int line_number, int column_number,
const char* resource_name, int line_number,
int column_number,
std::unique_ptr<SourcePositionTable> line_info,
Address instruction_start)
: bit_field_(TagField::encode(tag) |
BuiltinIdField::encode(Builtins::builtin_count)),
name_prefix_(name_prefix),
name_(name),
resource_name_(resource_name),
line_number_(line_number),

View File

@ -39,8 +39,6 @@ int SourcePositionTable::GetSourceLineNumber(int pc_offset) const {
return it->second;
}
const char* const CodeEntry::kEmptyNamePrefix = "";
const char* const CodeEntry::kEmptyResourceName = "";
const char* const CodeEntry::kEmptyBailoutReason = "";
const char* const CodeEntry::kNoDeoptReason = "";
@ -87,8 +85,6 @@ uint32_t CodeEntry::GetHash() const {
hash ^= ComputeIntegerHash(static_cast<uint32_t>(script_id_));
hash ^= ComputeIntegerHash(static_cast<uint32_t>(position_));
} else {
hash ^= ComputeIntegerHash(
static_cast<uint32_t>(reinterpret_cast<uintptr_t>(name_prefix_)));
hash ^= ComputeIntegerHash(
static_cast<uint32_t>(reinterpret_cast<uintptr_t>(name_)));
hash ^= ComputeIntegerHash(
@ -103,8 +99,7 @@ bool CodeEntry::IsSameFunctionAs(const CodeEntry* entry) const {
if (script_id_ != v8::UnboundScript::kNoScriptId) {
return script_id_ == entry->script_id_ && position_ == entry->position_;
}
return name_prefix_ == entry->name_prefix_ && name_ == entry->name_ &&
resource_name_ == entry->resource_name_ &&
return name_ == entry->name_ && resource_name_ == entry->resource_name_ &&
line_number_ == entry->line_number_;
}
@ -224,9 +219,8 @@ bool ProfileNode::GetLineTicks(v8::CpuProfileNode::LineTick* entries,
void ProfileNode::Print(int indent) {
base::OS::Print("%5u %*s %s%s %d #%d", self_ticks_, indent, "",
entry_->name_prefix(), entry_->name(), entry_->script_id(),
id());
base::OS::Print("%5u %*s %s %d #%d", self_ticks_, indent, "", entry_->name(),
entry_->script_id(), id());
if (entry_->resource_name()[0] != '\0')
base::OS::Print(" %s:%d", entry_->resource_name(), entry_->line_number());
base::OS::Print("\n");

View File

@ -42,15 +42,12 @@ class CodeEntry {
public:
// CodeEntry doesn't own name strings, just references them.
inline CodeEntry(CodeEventListener::LogEventsAndTags tag, const char* name,
const char* name_prefix = CodeEntry::kEmptyNamePrefix,
const char* resource_name = CodeEntry::kEmptyResourceName,
int line_number = v8::CpuProfileNode::kNoLineNumberInfo,
int column_number = v8::CpuProfileNode::kNoColumnNumberInfo,
std::unique_ptr<SourcePositionTable> line_info = nullptr,
Address instruction_start = kNullAddress);
const char* name_prefix() const { return name_prefix_; }
bool has_name_prefix() const { return name_prefix_[0] != '\0'; }
const char* name() const { return name_; }
const char* resource_name() const { return resource_name_; }
int line_number() const { return line_number_; }
@ -102,7 +99,6 @@ class CodeEntry {
return TagField::decode(bit_field_);
}
static const char* const kEmptyNamePrefix;
static const char* const kEmptyResourceName;
static const char* const kEmptyBailoutReason;
static const char* const kNoDeoptReason;
@ -150,7 +146,6 @@ class CodeEntry {
class BuiltinIdField : public BitField<Builtins::Name, 8, 24> {};
uint32_t bit_field_;
const char* name_prefix_;
const char* name_;
const char* resource_name_;
int line_number_;

View File

@ -37,9 +37,9 @@ void ProfilerListener::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag,
CodeCreateEventRecord* rec = &evt_rec.CodeCreateEventRecord_;
rec->start = code->address();
rec->entry = NewCodeEntry(
tag, GetFunctionName(name), CodeEntry::kEmptyNamePrefix,
CodeEntry::kEmptyResourceName, CpuProfileNode::kNoLineNumberInfo,
CpuProfileNode::kNoColumnNumberInfo, nullptr, code->InstructionStart());
tag, GetFunctionName(name), CodeEntry::kEmptyResourceName,
CpuProfileNode::kNoLineNumberInfo, CpuProfileNode::kNoColumnNumberInfo,
nullptr, code->InstructionStart());
RecordInliningInfo(rec->entry, code);
rec->size = code->ExecutableSize();
DispatchCodeEvent(evt_rec);
@ -51,9 +51,9 @@ void ProfilerListener::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag,
CodeCreateEventRecord* rec = &evt_rec.CodeCreateEventRecord_;
rec->start = code->address();
rec->entry = NewCodeEntry(
tag, GetFunctionName(name), CodeEntry::kEmptyNamePrefix,
CodeEntry::kEmptyResourceName, CpuProfileNode::kNoLineNumberInfo,
CpuProfileNode::kNoColumnNumberInfo, nullptr, code->InstructionStart());
tag, GetFunctionName(name), CodeEntry::kEmptyResourceName,
CpuProfileNode::kNoLineNumberInfo, CpuProfileNode::kNoColumnNumberInfo,
nullptr, code->InstructionStart());
RecordInliningInfo(rec->entry, code);
rec->size = code->ExecutableSize();
DispatchCodeEvent(evt_rec);
@ -66,11 +66,11 @@ void ProfilerListener::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag,
CodeEventsContainer evt_rec(CodeEventRecord::CODE_CREATION);
CodeCreateEventRecord* rec = &evt_rec.CodeCreateEventRecord_;
rec->start = code->address();
rec->entry = NewCodeEntry(
tag, GetFunctionName(shared->DebugName()), CodeEntry::kEmptyNamePrefix,
GetName(InferScriptName(script_name, shared)),
CpuProfileNode::kNoLineNumberInfo, CpuProfileNode::kNoColumnNumberInfo,
nullptr, code->InstructionStart());
rec->entry = NewCodeEntry(tag, GetFunctionName(shared->DebugName()),
GetName(InferScriptName(script_name, shared)),
CpuProfileNode::kNoLineNumberInfo,
CpuProfileNode::kNoColumnNumberInfo, nullptr,
code->InstructionStart());
RecordInliningInfo(rec->entry, code);
rec->entry->FillFunctionInfo(shared);
rec->size = code->ExecutableSize();
@ -100,10 +100,10 @@ void ProfilerListener::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag,
line_table->SetPosition(it.code_offset(), line_number);
}
}
rec->entry = NewCodeEntry(
tag, GetFunctionName(shared->DebugName()), CodeEntry::kEmptyNamePrefix,
GetName(InferScriptName(script_name, shared)), line, column,
std::move(line_table), abstract_code->InstructionStart());
rec->entry =
NewCodeEntry(tag, GetFunctionName(shared->DebugName()),
GetName(InferScriptName(script_name, shared)), line, column,
std::move(line_table), abstract_code->InstructionStart());
RecordInliningInfo(rec->entry, abstract_code);
RecordDeoptInlinedFrames(rec->entry, abstract_code);
rec->entry->FillFunctionInfo(shared);
@ -121,10 +121,10 @@ void ProfilerListener::CodeCreateEvent(CodeEventListener::LogEventsAndTags tag,
// have names.
const char* name_ptr =
name.start() == nullptr ? "<anonymous>" : GetFunctionName(name.start());
rec->entry = NewCodeEntry(
tag, name_ptr, CodeEntry::kEmptyNamePrefix, CodeEntry::kEmptyResourceName,
CpuProfileNode::kNoLineNumberInfo, CpuProfileNode::kNoColumnNumberInfo,
nullptr, code->instruction_start());
rec->entry = NewCodeEntry(tag, name_ptr, CodeEntry::kEmptyResourceName,
CpuProfileNode::kNoLineNumberInfo,
CpuProfileNode::kNoColumnNumberInfo, nullptr,
code->instruction_start());
rec->size = code->instructions().length();
DispatchCodeEvent(evt_rec);
}
@ -164,7 +164,7 @@ void ProfilerListener::GetterCallbackEvent(Name* name, Address entry_point) {
CodeCreateEventRecord* rec = &evt_rec.CodeCreateEventRecord_;
rec->start = entry_point;
rec->entry =
NewCodeEntry(CodeEventListener::CALLBACK_TAG, GetName(name), "get ");
NewCodeEntry(CodeEventListener::CALLBACK_TAG, GetConsName("get ", name));
rec->size = 1;
DispatchCodeEvent(evt_rec);
}
@ -174,11 +174,11 @@ void ProfilerListener::RegExpCodeCreateEvent(AbstractCode* code,
CodeEventsContainer evt_rec(CodeEventRecord::CODE_CREATION);
CodeCreateEventRecord* rec = &evt_rec.CodeCreateEventRecord_;
rec->start = code->address();
rec->entry = NewCodeEntry(CodeEventListener::REG_EXP_TAG, GetName(source),
"RegExp: ", CodeEntry::kEmptyResourceName,
CpuProfileNode::kNoLineNumberInfo,
CpuProfileNode::kNoColumnNumberInfo, nullptr,
code->raw_instruction_start());
rec->entry = NewCodeEntry(
CodeEventListener::REG_EXP_TAG, GetConsName("RegExp: ", source),
CodeEntry::kEmptyResourceName, CpuProfileNode::kNoLineNumberInfo,
CpuProfileNode::kNoColumnNumberInfo, nullptr,
code->raw_instruction_start());
rec->size = code->ExecutableSize();
DispatchCodeEvent(evt_rec);
}
@ -188,7 +188,7 @@ void ProfilerListener::SetterCallbackEvent(Name* name, Address entry_point) {
CodeCreateEventRecord* rec = &evt_rec.CodeCreateEventRecord_;
rec->start = entry_point;
rec->entry =
NewCodeEntry(CodeEventListener::CALLBACK_TAG, GetName(name), "set ");
NewCodeEntry(CodeEventListener::CALLBACK_TAG, GetConsName("set ", name));
rec->size = 1;
DispatchCodeEvent(evt_rec);
}
@ -241,8 +241,7 @@ void ProfilerListener::RecordInliningInfo(CodeEntry* entry,
CodeEntry* inline_entry =
new CodeEntry(entry->tag(), GetFunctionName(shared_info->DebugName()),
CodeEntry::kEmptyNamePrefix, resource_name,
CpuProfileNode::kNoLineNumberInfo,
resource_name, CpuProfileNode::kNoLineNumberInfo,
CpuProfileNode::kNoColumnNumberInfo, nullptr,
code->InstructionStart());
inline_entry->FillFunctionInfo(shared_info);
@ -294,11 +293,10 @@ void ProfilerListener::RecordDeoptInlinedFrames(CodeEntry* entry,
CodeEntry* ProfilerListener::NewCodeEntry(
CodeEventListener::LogEventsAndTags tag, const char* name,
const char* name_prefix, const char* resource_name, int line_number,
int column_number, std::unique_ptr<SourcePositionTable> line_info,
Address instruction_start) {
const char* resource_name, int line_number, int column_number,
std::unique_ptr<SourcePositionTable> line_info, Address instruction_start) {
std::unique_ptr<CodeEntry> code_entry = base::make_unique<CodeEntry>(
tag, name, name_prefix, resource_name, line_number, column_number,
tag, name, resource_name, line_number, column_number,
std::move(line_info), instruction_start);
CodeEntry* raw_code_entry = code_entry.get();
code_entries_.push_back(std::move(code_entry));

View File

@ -54,7 +54,6 @@ class ProfilerListener : public CodeEventListener {
CodeEntry* NewCodeEntry(
CodeEventListener::LogEventsAndTags tag, const char* name,
const char* name_prefix = CodeEntry::kEmptyNamePrefix,
const char* resource_name = CodeEntry::kEmptyResourceName,
int line_number = v8::CpuProfileNode::kNoLineNumberInfo,
int column_number = v8::CpuProfileNode::kNoColumnNumberInfo,
@ -67,6 +66,9 @@ class ProfilerListener : public CodeEventListener {
const char* GetName(int args_count) {
return function_and_resource_names_.GetName(args_count);
}
const char* GetConsName(const char* prefix, Name* name) {
return function_and_resource_names_.GetConsName(prefix, name);
}
const char* GetFunctionName(Name* name) {
return function_and_resource_names_.GetFunctionName(name);
}

View File

@ -88,6 +88,25 @@ const char* StringsStorage::GetName(int index) {
return GetFormatted("%d", index);
}
const char* StringsStorage::GetConsName(const char* prefix, Name* name) {
if (name->IsString()) {
String* str = String::cast(name);
int length = Min(FLAG_heap_snapshot_string_limit, str->length());
int actual_length = 0;
std::unique_ptr<char[]> data = str->ToCString(
DISALLOW_NULLS, ROBUST_STRING_TRAVERSAL, 0, length, &actual_length);
int cons_length = actual_length + static_cast<int>(strlen(prefix)) + 1;
char* cons_result = NewArray<char>(cons_length);
snprintf(cons_result, cons_length, "%s%s", prefix, data.get());
return AddOrDisposeString(cons_result, cons_length);
} else if (name->IsSymbol()) {
return "<symbol>";
}
return "";
}
const char* StringsStorage::GetFunctionName(Name* name) {
return GetName(name);
}

View File

@ -28,6 +28,7 @@ class StringsStorage {
const char* GetVFormatted(const char* format, va_list args);
const char* GetName(Name* name);
const char* GetName(int index);
const char* GetConsName(const char* prefix, Name* name);
const char* GetFunctionName(Name* name);
const char* GetFunctionName(const char* name);