Commit 14732265 authored by mvstanton's avatar mvstanton Committed by Commit bot

Machine-readable TurboFan compiler statistics

We'd like to track performance metrics in an automated way. This CL introduces
--turbo-stats-nvp which exposes --turbo-stats information in {"name"=value} pair
format.

BUG=

Review-Url: https://codereview.chromium.org/2053383002
Cr-Commit-Position: refs/heads/master@{#36919}
parent 3400ee9f
......@@ -54,8 +54,7 @@ void CompilationStatistics::BasicStats::Accumulate(const BasicStats& stats) {
}
}
static void WriteLine(std::ostream& os, const char* name,
static void WriteLine(std::ostream& os, bool machine_format, const char* name,
const CompilationStatistics::BasicStats& stats,
const CompilationStatistics::BasicStats& total_stats) {
const size_t kBufferSize = 128;
......@@ -66,17 +65,24 @@ static void WriteLine(std::ostream& os, const char* name,
double size_percent =
static_cast<double>(stats.total_allocated_bytes_ * 100) /
static_cast<double>(total_stats.total_allocated_bytes_);
base::OS::SNPrintF(buffer, kBufferSize, "%28s %10.3f (%5.1f%%) %10" PRIuS
" (%5.1f%%) %10" PRIuS " %10" PRIuS,
name, ms, percent, stats.total_allocated_bytes_,
size_percent, stats.max_allocated_bytes_,
stats.absolute_max_allocated_bytes_);
os << buffer;
if (stats.function_name_.size() > 0) {
os << " " << stats.function_name_.c_str();
if (machine_format) {
base::OS::SNPrintF(buffer, kBufferSize,
"\"%s_time\"=%.3f\n\"%s_space\"=%" PRIuS, name, ms, name,
stats.total_allocated_bytes_);
os << buffer;
} else {
base::OS::SNPrintF(buffer, kBufferSize, "%28s %10.3f (%5.1f%%) %10" PRIuS
" (%5.1f%%) %10" PRIuS " %10" PRIuS,
name, ms, percent, stats.total_allocated_bytes_,
size_percent, stats.max_allocated_bytes_,
stats.absolute_max_allocated_bytes_);
os << buffer;
if (stats.function_name_.size() > 0) {
os << " " << stats.function_name_.c_str();
}
os << std::endl;
}
os << std::endl;
}
......@@ -101,10 +107,10 @@ static void WritePhaseKindBreak(std::ostream& os) {
"--------------------------------------------------------\n";
}
std::ostream& operator<<(std::ostream& os, const CompilationStatistics& s) {
std::ostream& operator<<(std::ostream& os, const AsPrintableStatistics& ps) {
// phase_kind_map_ and phase_map_ don't get mutated, so store a bunch of
// pointers into them.
const CompilationStatistics& s = ps.s;
typedef std::vector<CompilationStatistics::PhaseKindMap::const_iterator>
SortedPhaseKinds;
......@@ -121,22 +127,27 @@ std::ostream& operator<<(std::ostream& os, const CompilationStatistics& s) {
sorted_phases[it->second.insert_order_] = it;
}
WriteHeader(os);
if (!ps.machine_output) WriteHeader(os);
for (auto phase_kind_it : sorted_phase_kinds) {
const auto& phase_kind_name = phase_kind_it->first;
for (auto phase_it : sorted_phases) {
const auto& phase_stats = phase_it->second;
if (phase_stats.phase_kind_name_ != phase_kind_name) continue;
const auto& phase_name = phase_it->first;
WriteLine(os, phase_name.c_str(), phase_stats, s.total_stats_);
if (!ps.machine_output) {
for (auto phase_it : sorted_phases) {
const auto& phase_stats = phase_it->second;
if (phase_stats.phase_kind_name_ != phase_kind_name) continue;
const auto& phase_name = phase_it->first;
WriteLine(os, ps.machine_output, phase_name.c_str(), phase_stats,
s.total_stats_);
}
WritePhaseKindBreak(os);
}
WritePhaseKindBreak(os);
const auto& phase_kind_stats = phase_kind_it->second;
WriteLine(os, phase_kind_name.c_str(), phase_kind_stats, s.total_stats_);
WriteLine(os, ps.machine_output, phase_kind_name.c_str(), phase_kind_stats,
s.total_stats_);
os << std::endl;
}
WriteFullLine(os);
WriteLine(os, "totals", s.total_stats_, s.total_stats_);
if (!ps.machine_output) WriteFullLine(os);
WriteLine(os, ps.machine_output, "totals", s.total_stats_, s.total_stats_);
return os;
}
......
......@@ -15,6 +15,12 @@ namespace v8 {
namespace internal {
class CompilationInfo;
class CompilationStatistics;
struct AsPrintableStatistics {
const CompilationStatistics& s;
const bool machine_output;
};
class CompilationStatistics final : public Malloced {
public:
......@@ -65,7 +71,7 @@ class CompilationStatistics final : public Malloced {
};
friend std::ostream& operator<<(std::ostream& os,
const CompilationStatistics& s);
const AsPrintableStatistics& s);
typedef OrderedStats PhaseKindStats;
typedef std::map<std::string, PhaseKindStats> PhaseKindMap;
......@@ -78,7 +84,7 @@ class CompilationStatistics final : public Malloced {
DISALLOW_COPY_AND_ASSIGN(CompilationStatistics);
};
std::ostream& operator<<(std::ostream& os, const CompilationStatistics& s);
std::ostream& operator<<(std::ostream& os, const AsPrintableStatistics& s);
} // namespace internal
} // namespace v8
......
......@@ -521,7 +521,7 @@ PipelineStatistics* CreatePipelineStatistics(CompilationInfo* info,
ZonePool* zone_pool) {
PipelineStatistics* pipeline_statistics = nullptr;
if (FLAG_turbo_stats) {
if (FLAG_turbo_stats || FLAG_turbo_stats_nvp) {
pipeline_statistics = new PipelineStatistics(info, zone_pool);
pipeline_statistics->BeginPhaseKind("initializing");
}
......@@ -1503,7 +1503,7 @@ Handle<Code> Pipeline::GenerateCodeForCodeStub(Isolate* isolate,
ZonePool zone_pool(isolate->allocator());
PipelineData data(&zone_pool, &info, graph, schedule);
base::SmartPointer<PipelineStatistics> pipeline_statistics;
if (FLAG_turbo_stats) {
if (FLAG_turbo_stats || FLAG_turbo_stats_nvp) {
pipeline_statistics.Reset(new PipelineStatistics(&info, &zone_pool));
pipeline_statistics->BeginPhaseKind("stub codegen");
}
......@@ -1557,7 +1557,7 @@ Handle<Code> Pipeline::GenerateCodeForTesting(CompilationInfo* info,
ZonePool zone_pool(info->isolate()->allocator());
PipelineData data(&zone_pool, info, graph, schedule);
base::SmartPointer<PipelineStatistics> pipeline_statistics;
if (FLAG_turbo_stats) {
if (FLAG_turbo_stats || FLAG_turbo_stats_nvp) {
pipeline_statistics.Reset(new PipelineStatistics(info, &zone_pool));
pipeline_statistics->BeginPhaseKind("test codegen");
}
......
......@@ -449,6 +449,8 @@ DEFINE_BOOL(turbo_asm_deoptimization, false,
"enable deoptimization in TurboFan for asm.js code")
DEFINE_BOOL(turbo_verify, DEBUG_BOOL, "verify TurboFan graphs at each phase")
DEFINE_BOOL(turbo_stats, false, "print TurboFan statistics")
DEFINE_BOOL(turbo_stats_nvp, false,
"print TurboFan statistics in machine-readable format")
DEFINE_BOOL(turbo_splitting, true, "split nodes during scheduling in TurboFan")
DEFINE_BOOL(turbo_type_feedback, false,
"use typed feedback for representation inference in Turbofan")
......
......@@ -2450,8 +2450,17 @@ void Isolate::UnlinkDeferredHandles(DeferredHandles* deferred) {
void Isolate::DumpAndResetCompilationStats() {
if (turbo_statistics() != nullptr) {
DCHECK(FLAG_turbo_stats || FLAG_turbo_stats_nvp);
OFStream os(stdout);
os << *turbo_statistics() << std::endl;
if (FLAG_turbo_stats) {
AsPrintableStatistics ps = {*turbo_statistics(), false};
os << ps << std::endl;
}
if (FLAG_turbo_stats_nvp) {
AsPrintableStatistics ps = {*turbo_statistics(), true};
os << ps << std::endl;
}
}
if (hstatistics() != nullptr) hstatistics()->Print();
delete turbo_statistics_;
......
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