Skip to content

Commit 86723e2

Browse files
committed
better example
1 parent 7922f33 commit 86723e2

File tree

1 file changed

+51
-28
lines changed

1 file changed

+51
-28
lines changed

examples/cxx/profiling.cpp

Lines changed: 51 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -22,44 +22,67 @@ int main() {
2222
auto profile = Profile::create({wall_time}, period);
2323
std::cout << "✅ Profile created" << std::endl;
2424

25-
// Add samples
25+
// Add samples with realistic stack traces
2626
std::cout << "Adding samples..." << std::endl;
2727
for (int i = 0; i < 100; i++) {
28-
// Create mapping
29-
CxxMapping mapping{
30-
0x10000000, // memory_start
31-
0x20000000, // memory_limit
32-
0, // file_offset
33-
"/usr/lib/libexample.so", // filename
34-
"abc123def456" // build_id
35-
};
28+
// Keep dynamically generated strings alive for the duration of add_sample()
29+
// The profile will intern them, so they can be freed after that call
30+
std::vector<std::string> string_storage;
31+
32+
CxxMapping mapping{0x10000000, 0x20000000, 0, "/usr/lib/libexample.so", "abc123"};
3633

37-
// Create function
38-
auto func_name = "my_function_" + std::to_string(i % 10);
39-
auto sys_name = "_Z11my_function" + std::to_string(i % 10) + "v";
40-
CxxFunction function{func_name.c_str(), sys_name.c_str(), "/path/to/source.cpp"};
34+
// Leaf frame - where the CPU was actually spending time
35+
string_storage.push_back("hot_function_" + std::to_string(i % 3));
36+
string_storage.push_back("_Z12hot_function" + std::to_string(i % 3) + "v");
37+
CxxFunction leaf_func{string_storage[0].c_str(), string_storage[1].c_str(), "/src/hot_path.cpp"};
38+
CxxLocation leaf_frame{
39+
mapping, leaf_func,
40+
static_cast<uint64_t>(0x10003000 + (i % 3) * 0x100),
41+
100 + (i % 3) * 10
42+
};
4143

42-
// Create location
43-
CxxLocation location{
44-
mapping,
45-
function,
46-
static_cast<uint64_t>(0x12345678 + i * 0x100), // address
47-
42 + i // line
44+
// Middle frame - intermediate call
45+
string_storage.push_back("process_request_" + std::to_string(i % 5));
46+
string_storage.push_back("_Z15process_request" + std::to_string(i % 5) + "v");
47+
CxxFunction mid_func{string_storage[2].c_str(), string_storage[3].c_str(), "/src/handler.cpp"};
48+
CxxLocation mid_frame{
49+
mapping, mid_func,
50+
static_cast<uint64_t>(0x10002000 + (i % 5) * 0x80),
51+
50 + (i % 5) * 5
4852
};
4953

54+
// Root frame - entry point
55+
CxxFunction root_func{"main", "main", "/src/main.cpp"};
56+
CxxLocation root_frame{mapping, root_func, 0x10001000, 42};
57+
5058
// Create labels
5159
CxxLabel thread_label{"thread_id", "", static_cast<int64_t>(i % 4), ""};
52-
CxxLabel counter_label{"unique_counter", "", static_cast<int64_t>(i), ""};
60+
CxxLabel counter_label{"sample_id", "", static_cast<int64_t>(i), ""};
5361

54-
// Create sample using initializer lists
55-
int64_t wall_time_value = 1000000; // 1ms
56-
CxxSample sample{
57-
{location}, // locations
58-
{wall_time_value}, // values
59-
{thread_label, counter_label} // labels
60-
};
62+
// Create sample with stack trace (3-4 frames depending on sample)
63+
int64_t wall_time_value = 1000000 + (i % 1000) * 1000; // 1-2ms
6164

62-
profile->add_sample(sample);
65+
if (i % 7 == 0) {
66+
// Deeper stack (4 frames)
67+
CxxFunction worker_func{"worker_loop", "_Z11worker_loopv", "/src/worker.cpp"};
68+
CxxLocation worker_frame{mapping, worker_func, 0x10000500, 25};
69+
70+
CxxSample sample{
71+
{leaf_frame, mid_frame, root_frame, worker_frame}, // 4-frame stack
72+
{wall_time_value},
73+
{thread_label, counter_label}
74+
};
75+
profile->add_sample(sample);
76+
} else {
77+
// Normal stack (3 frames)
78+
CxxSample sample{
79+
{leaf_frame, mid_frame, root_frame}, // 3-frame stack
80+
{wall_time_value},
81+
{thread_label, counter_label}
82+
};
83+
profile->add_sample(sample);
84+
}
85+
// string_storage vector destroyed here, but profile has already interned the strings
6386
}
6487

6588
std::cout << "✅ Added 100 samples" << std::endl;

0 commit comments

Comments
 (0)