Created
May 17, 2024 21:12
-
-
Save markdewing/982877af92e5b852fc25daec25cc59f6 to your computer and use it in GitHub Desktop.
Collect timing information and write out a trace file in Chrome Tracing Format
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include "trace.h" | |
#include <iostream> | |
#include <unistd.h> | |
int main() | |
{ | |
Timer t1("first"); | |
t1.start(); | |
sleep(1); | |
Timer t2("second"); | |
t2.start(); | |
sleep(1); | |
t2.stop(); | |
sleep(1); | |
t1.stop(); | |
writeTrace("out1.json"); | |
return 0; | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include "trace.h" | |
#include <chrono> | |
#include <fstream> | |
#include <map> | |
#include <mutex> | |
#include <string> | |
#include <thread> | |
#include <vector> | |
// Structure to save trace event information | |
struct EventRecord { | |
double timestamp; // in seconds | |
char event_type; | |
std::string name; | |
std::thread::id tid; | |
double duration; // in seconds | |
EventRecord(double ts, char type, const std::string &name, | |
std::thread::id tid1, double dur = 0.0) | |
: timestamp(ts), event_type(type), name(name), tid(tid1), duration(dur) {} | |
}; | |
std::vector<EventRecord> events; | |
std::mutex event_mutex; // for thread safety | |
using TimePoint = std::chrono::steady_clock::time_point; | |
// Track program start time in order to compute times relative to it | |
TimePoint program_start = std::chrono::steady_clock::now(); | |
void Timer::start() { | |
start_time_ = std::chrono::steady_clock::now(); | |
} | |
void Timer::stop() { | |
TimePoint stop_time = std::chrono::steady_clock::now(); | |
std::chrono::duration<double> from_program_start = | |
start_time_ - program_start; | |
std::chrono::duration<double> dur = stop_time - start_time_; | |
std::thread::id tid = std::this_thread::get_id(); | |
event_mutex.lock(); | |
events.push_back( | |
EventRecord(from_program_start.count(), 'X', name_, tid, dur.count())); | |
event_mutex.unlock(); | |
} | |
void writeTrace(const std::string &fname) { | |
// Map thread id to a small integer | |
int small_tid = 0; | |
std::map<std::thread::id, int> tid_map; | |
std::ofstream f(fname); | |
f << "{\n"; | |
f << R"("traceEvents": [)" << "\n"; | |
for (int idx = 0; idx < events.size(); idx++) { | |
EventRecord &er = events[idx]; | |
if (tid_map.find(er.tid) == tid_map.end()) { | |
tid_map[er.tid] = small_tid++; | |
} | |
f << R"({"name":")" << er.name << R"(",)" << R"("ph":")" << er.event_type | |
<< R"(",)" << R"("pid":")" << 1 << R"(",)" << R"("tid":")" | |
<< tid_map[er.tid] << R"(",)" << R"("ts":)" << (er.timestamp * 1.0e6); | |
if (er.event_type == 'X') | |
f << R"(,"dur":)" << (er.duration * 1.0e6); | |
f << "}"; | |
// Ensure last item is not followed by a comma | |
if (idx < events.size() - 1) { | |
f << ",\n"; | |
} else { | |
f << "\n"; | |
} | |
} | |
f << "}" << std::endl; | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#ifndef TRACE_H | |
#define TRACE_H | |
#include <string> | |
#include <chrono> | |
// Collect timing information and write out a trace file in Chrome Tracing Format | |
// One possible implementation of a timer | |
class Timer { | |
public: | |
using TimePoint = std::chrono::steady_clock::time_point; | |
void start(); | |
void stop(); | |
Timer(const std::string& name) : name_(name) {} | |
private: | |
TimePoint start_time_; | |
std::string name_; | |
}; | |
// Write trace to file in JSON format | |
void writeTrace(const std::string& fname); | |
#endif |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment