Skip to content
Merged
Show file tree
Hide file tree
Changes from 4 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions Android.bp
Original file line number Diff line number Diff line change
Expand Up @@ -14801,6 +14801,7 @@ filegroup {
"src/trace_processor/importers/proto/heap_graph_tracker.cc",
"src/trace_processor/importers/proto/jit_tracker.cc",
"src/trace_processor/importers/proto/metadata_module.cc",
"src/trace_processor/importers/proto/perf_counter_set_tracker.cc",
"src/trace_processor/importers/proto/pigweed_detokenizer.cc",
"src/trace_processor/importers/proto/pixel_modem_module.cc",
"src/trace_processor/importers/proto/pixel_modem_parser.cc",
Expand Down Expand Up @@ -15399,6 +15400,7 @@ filegroup {
"src/trace_processor/perfetto_sql/intrinsics/functions/layout_functions.cc",
"src/trace_processor/perfetto_sql/intrinsics/functions/math.cc",
"src/trace_processor/perfetto_sql/intrinsics/functions/package_lookup.cc",
"src/trace_processor/perfetto_sql/intrinsics/functions/perf_counter.cc",
"src/trace_processor/perfetto_sql/intrinsics/functions/pprof_functions.cc",
"src/trace_processor/perfetto_sql/intrinsics/functions/replace_numbers_function.cc",
"src/trace_processor/perfetto_sql/intrinsics/functions/sqlite3_str_split.cc",
Expand Down Expand Up @@ -15732,6 +15734,7 @@ genrule {
"src/trace_processor/perfetto_sql/stdlib/linux/memory/general.sql",
"src/trace_processor/perfetto_sql/stdlib/linux/memory/high_watermark.sql",
"src/trace_processor/perfetto_sql/stdlib/linux/memory/process.sql",
"src/trace_processor/perfetto_sql/stdlib/linux/perf/counters.sql",
"src/trace_processor/perfetto_sql/stdlib/linux/perf/samples.sql",
"src/trace_processor/perfetto_sql/stdlib/linux/perf/spe.sql",
"src/trace_processor/perfetto_sql/stdlib/linux/threads.sql",
Expand Down
5 changes: 5 additions & 0 deletions BUILD
Original file line number Diff line number Diff line change
Expand Up @@ -2629,6 +2629,8 @@ perfetto_filegroup(
"src/trace_processor/importers/proto/jit_tracker.h",
"src/trace_processor/importers/proto/metadata_module.cc",
"src/trace_processor/importers/proto/metadata_module.h",
"src/trace_processor/importers/proto/perf_counter_set_tracker.cc",
"src/trace_processor/importers/proto/perf_counter_set_tracker.h",
"src/trace_processor/importers/proto/pigweed_detokenizer.cc",
"src/trace_processor/importers/proto/pigweed_detokenizer.h",
"src/trace_processor/importers/proto/pixel_modem_module.cc",
Expand Down Expand Up @@ -3169,6 +3171,8 @@ perfetto_filegroup(
"src/trace_processor/perfetto_sql/intrinsics/functions/math.h",
"src/trace_processor/perfetto_sql/intrinsics/functions/package_lookup.cc",
"src/trace_processor/perfetto_sql/intrinsics/functions/package_lookup.h",
"src/trace_processor/perfetto_sql/intrinsics/functions/perf_counter.cc",
"src/trace_processor/perfetto_sql/intrinsics/functions/perf_counter.h",
"src/trace_processor/perfetto_sql/intrinsics/functions/pprof_functions.cc",
"src/trace_processor/perfetto_sql/intrinsics/functions/pprof_functions.h",
"src/trace_processor/perfetto_sql/intrinsics/functions/replace_numbers_function.cc",
Expand Down Expand Up @@ -3616,6 +3620,7 @@ perfetto_filegroup(
perfetto_filegroup(
name = "src_trace_processor_perfetto_sql_stdlib_linux_perf_perf",
srcs = [
"src/trace_processor/perfetto_sql/stdlib/linux/perf/counters.sql",
"src/trace_processor/perfetto_sql/stdlib/linux/perf/samples.sql",
"src/trace_processor/perfetto_sql/stdlib/linux/perf/spe.sql",
],
Expand Down
8 changes: 4 additions & 4 deletions src/trace_processor/importers/perf/perf_counter.cc
Original file line number Diff line number Diff line change
Expand Up @@ -23,15 +23,15 @@

namespace perfetto::trace_processor::perf_importer {

void PerfCounter::AddDelta(int64_t ts, double delta) {
CounterId PerfCounter::AddDelta(int64_t ts, double delta) {
last_count_ += delta;
counter_table_.Insert({ts, track_id_, last_count_});
return counter_table_.Insert({ts, track_id_, last_count_}).id;
}

void PerfCounter::AddCount(int64_t ts, double count) {
CounterId PerfCounter::AddCount(int64_t ts, double count) {
PERFETTO_CHECK(count >= last_count_);
last_count_ = count;
counter_table_.Insert({ts, track_id_, last_count_});
return counter_table_.Insert({ts, track_id_, last_count_}).id;
}

} // namespace perfetto::trace_processor::perf_importer
7 changes: 5 additions & 2 deletions src/trace_processor/importers/perf/perf_counter.h
Original file line number Diff line number Diff line change
Expand Up @@ -19,11 +19,14 @@

#include <cstdint>

#include "src/trace_processor/storage/trace_storage.h"
#include "src/trace_processor/tables/counter_tables_py.h"
#include "src/trace_processor/tables/track_tables_py.h"

namespace perfetto::trace_processor::perf_importer {

using trace_processor::CounterId;

// Helper class to keep track of perf counters and convert delta values found in
// perf files to absolute values needed for the perfetto counter table.
class PerfCounter {
Expand All @@ -37,8 +40,8 @@ class PerfCounter {

bool is_timebase() const { return is_timebase_; }

void AddDelta(int64_t ts, double delta);
void AddCount(int64_t ts, double count);
CounterId AddDelta(int64_t ts, double delta);
CounterId AddCount(int64_t ts, double count);

private:
tables::CounterTable& counter_table_;
Expand Down
42 changes: 32 additions & 10 deletions src/trace_processor/importers/perf/record_parser.cc
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
#include "perfetto/base/logging.h"
#include "perfetto/base/status.h"
#include "perfetto/ext/base/status_macros.h"
#include "perfetto/ext/base/status_or.h"
#include "perfetto/ext/base/string_view.h"
#include "perfetto/public/compiler.h"
#include "perfetto/trace_processor/ref_counted.h"
Expand Down Expand Up @@ -183,14 +184,29 @@ base::Status RecordParser::InternSample(Sample sample) {
std::optional<CallsiteId> callsite_id = InternCallchain(
upid, sample.callchain, sample.perf_invocation->needs_pc_adjustment());

// Update counters and create counter set.
ASSIGN_OR_RETURN(std::vector<CounterId> counter_ids, UpdateCounters(sample));

std::optional<uint32_t> counter_set_id;
if (!counter_ids.empty()) {
auto* table = context_->storage->mutable_perf_counter_set_table();
counter_set_id = static_cast<uint32_t>(table->row_count());
for (CounterId counter_id : counter_ids) {
tables::PerfCounterSetTable::Row row;
row.perf_counter_set_id = *counter_set_id;
row.counter_id = counter_id;
table->Insert(row);
}
}

auto session_id = sample.attr->perf_session_id();
context_->storage->mutable_perf_sample_table()->Insert(
{sample.trace_ts, utid, sample.cpu,
context_->storage->InternString(
ProfilePacketUtils::StringifyCpuMode(sample.cpu_mode)),
callsite_id, std::nullopt, session_id});
callsite_id, std::nullopt, session_id, counter_set_id});

return UpdateCounters(sample);
return base::OkStatus();
}

std::optional<CallsiteId> RecordParser::InternCallchain(
Expand Down Expand Up @@ -318,7 +334,8 @@ UniquePid RecordParser::GetUpid(const CommonMmapRecordFields& fields) const {
return *upid;
}

base::Status RecordParser::UpdateCounters(const Sample& sample) {
base::StatusOr<std::vector<CounterId>> RecordParser::UpdateCounters(
const Sample& sample) {
if (!sample.read_groups.empty()) {
return UpdateCountersInReadGroups(sample);
}
Expand All @@ -329,23 +346,28 @@ base::Status RecordParser::UpdateCounters(const Sample& sample) {

uint64_t period = sample.period.has_value() ? *sample.period
: *sample.attr->sample_period();
sample.attr->GetOrCreateCounter(sample.cpu)
.AddDelta(sample.trace_ts, static_cast<double>(period));
return base::OkStatus();
CounterId counter_id =
sample.attr->GetOrCreateCounter(sample.cpu)
.AddDelta(sample.trace_ts, static_cast<double>(period));
return std::vector<CounterId>{counter_id};
}

base::Status RecordParser::UpdateCountersInReadGroups(const Sample& sample) {
base::StatusOr<std::vector<CounterId>> RecordParser::UpdateCountersInReadGroups(
const Sample& sample) {
std::vector<CounterId> counter_ids;
for (const auto& entry : sample.read_groups) {
RefPtr<PerfEventAttr> attr =
sample.perf_invocation->FindAttrForEventId(*entry.event_id);
if (PERFETTO_UNLIKELY(!attr)) {
return base::ErrStatus("No perf_event_attr for id %" PRIu64,
*entry.event_id);
}
attr->GetOrCreateCounter(sample.cpu)
.AddCount(sample.trace_ts, static_cast<double>(entry.value));
CounterId counter_id =
attr->GetOrCreateCounter(sample.cpu)
.AddCount(sample.trace_ts, static_cast<double>(entry.value));
counter_ids.push_back(counter_id);
}
return base::OkStatus();
return counter_ids;
}

DummyMemoryMapping* RecordParser::GetDummyMapping(UniquePid upid) {
Expand Down
6 changes: 4 additions & 2 deletions src/trace_processor/importers/perf/record_parser.h
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@

#include "perfetto/base/status.h"
#include "perfetto/ext/base/flat_hash_map.h"
#include "perfetto/ext/base/status_or.h"
#include "src/trace_processor/importers/perf/mmap_record.h"
#include "src/trace_processor/importers/perf/perf_tracker.h"
#include "src/trace_processor/importers/perf/record.h"
Expand Down Expand Up @@ -59,8 +60,9 @@ class RecordParser : public TraceSorter::Sink<Record, RecordParser> {

base::Status InternSample(Sample sample);

base::Status UpdateCounters(const Sample& sample);
static base::Status UpdateCountersInReadGroups(const Sample& sample);
base::StatusOr<std::vector<CounterId>> UpdateCounters(const Sample& sample);
static base::StatusOr<std::vector<CounterId>> UpdateCountersInReadGroups(
const Sample& sample);

std::optional<CallsiteId> InternCallchain(
UniquePid upid,
Expand Down
46 changes: 40 additions & 6 deletions src/trace_processor/importers/proto/profile_module.cc
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,25 @@

namespace perfetto::trace_processor {

namespace {

// Adds a counter set containing the given counter IDs.
// Returns the set ID that can be stored in PerfSampleTable.
uint32_t AddCounterSet(TraceProcessorContext* context,
const std::vector<CounterId>& counter_ids) {
auto* table = context->storage->mutable_perf_counter_set_table();
uint32_t set_id = static_cast<uint32_t>(table->row_count());
for (CounterId counter_id : counter_ids) {
tables::PerfCounterSetTable::Row row;
row.perf_counter_set_id = set_id;
row.counter_id = counter_id;
table->Insert(row);
}
return set_id;
}

} // namespace

using perfetto::protos::pbzero::TracePacket;
using protozero::ConstBytes;

Expand Down Expand Up @@ -253,20 +272,35 @@ void ProfileModule::ParsePerfSample(

// Populate the |perf_sample| table with everything except the recorded
// counter values, which go to |counter|.
context_->event_tracker->PushCounter(
// Collect counter IDs for counter set association
std::vector<CounterId> counter_ids;

auto timebase_counter_id = context_->event_tracker->PushCounter(
ts, static_cast<double>(sample.timebase_count()),
sampling_stream.timebase_track_id);
if (timebase_counter_id) {
counter_ids.push_back(*timebase_counter_id);
}

if (sample.has_follower_counts()) {
auto track_it = sampling_stream.follower_track_ids.begin();
auto track_end = sampling_stream.follower_track_ids.end();
for (auto it = sample.follower_counts(); it && track_it != track_end;
++it, ++track_it) {
context_->event_tracker->PushCounter(ts, static_cast<double>(*it),
*track_it);
auto follower_counter_id = context_->event_tracker->PushCounter(
ts, static_cast<double>(*it), *track_it);
if (follower_counter_id) {
counter_ids.push_back(*follower_counter_id);
}
}
}

// Create counter set if we have any counter IDs
std::optional<uint32_t> counter_set_id;
if (!counter_ids.empty()) {
counter_set_id = AddCounterSet(context_, counter_ids);
}

const UniqueTid utid =
context_->process_tracker->UpdateThread(sample.tid(), sample.pid());
const UniquePid upid =
Expand Down Expand Up @@ -295,9 +329,9 @@ void ProfileModule::ParsePerfSample(
unwind_error_id = storage->InternString(
ProfilePacketUtils::StringifyStackUnwindError(unwind_error));
}
tables::PerfSampleTable::Row sample_row(ts, utid, sample.cpu(), cpu_mode_id,
cs_id, unwind_error_id,
sampling_stream.perf_session_id);
tables::PerfSampleTable::Row sample_row(
ts, utid, sample.cpu(), cpu_mode_id, cs_id, unwind_error_id,
sampling_stream.perf_session_id, counter_set_id);
context_->storage->mutable_perf_sample_table()->Insert(sample_row);
}

Expand Down
6 changes: 3 additions & 3 deletions src/trace_processor/perfetto_sql/engine/perfetto_sql_engine.h
Original file line number Diff line number Diff line change
Expand Up @@ -440,8 +440,8 @@ base::Status PerfettoSqlEngine::RegisterFunction(
function_count_++;
const char* name = args.name ? args.name : Function::kName;
int argc = args.argc.has_value() ? args.argc.value() : Function::kArgCount;
return engine_->RegisterFunction(name, argc, Function::Step, ctx, nullptr,
args.deterministic);
return RegisterFunctionAndAddToRegistry(name, argc, Function::Step, ctx,
nullptr, args.deterministic);
}

template <typename Function>
Expand All @@ -451,7 +451,7 @@ base::Status PerfettoSqlEngine::RegisterFunction(
function_count_++;
const char* name = args.name ? args.name : Function::kName;
int argc = args.argc.has_value() ? args.argc.value() : Function::kArgCount;
return engine_->RegisterFunction(
return RegisterFunctionAndAddToRegistry(
name, argc, Function::Step, ctx.release(),
[](void* ptr) {
std::unique_ptr<typename Function::UserData>(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,8 @@ source_set("functions") {
"math.h",
"package_lookup.cc",
"package_lookup.h",
"perf_counter.cc",
"perf_counter.h",
"pprof_functions.cc",
"pprof_functions.h",
"replace_numbers_function.cc",
Expand Down
Loading
Loading