| #pragma once |
| |
| #include "config.h" |
| |
| #include <cstdint> |
| #include <fstream> |
| #include <memory> |
| #include <optional> |
| #include <string> |
| #include <string_view> |
| #include <vector> |
| |
| namespace boot_time_monitor |
| { |
| |
| const std::string kBTMonitorDir = bootTimeDataDir; |
| const std::string kCheckpointFile = "checkpoints.csv"; |
| const std::string kDurationFile = "durations.csv"; |
| const std::string kCompletedSuffix = ".completed"; |
| |
| struct Checkpoint |
| { |
| std::string name; |
| int64_t wallTime; |
| int64_t monoTime; |
| |
| Checkpoint(std::string name, int64_t wallTime, int64_t monoTime) : |
| name(std::move(name)), wallTime(wallTime), monoTime(monoTime) |
| {} |
| }; |
| |
| struct Duration |
| { |
| std::string name; |
| int64_t duration; |
| |
| Duration(std::string name, int64_t duration) : |
| name(std::move(name)), duration(duration) |
| {} |
| }; |
| |
| /** |
| * An interface class for the Util APIs |
| */ |
| class UtilIface |
| { |
| public: |
| virtual ~UtilIface() = default; |
| |
| /** |
| * Read uptime from `/proc/uptime` |
| * |
| * @return Current uptime in milliseconds |
| */ |
| virtual std::optional<int64_t> getUpTimeInMs() = 0; |
| |
| /** |
| * Get system time and covert it to the epoch time in milliseconds |
| * |
| * @return Current epoch time in milliseconds |
| */ |
| virtual int64_t getWallTimeInMs() = 0; |
| |
| /** |
| * Check if the input name is valid. This can be used to check both |
| * checkpoint name and duration name |
| * |
| * @return true if the input name is valid |
| */ |
| virtual bool isValidName(std::string_view name) = 0; |
| |
| /** |
| * Get full file path of checkpoint record for a specific node |
| * |
| * @param[in] nodeName - Node name |
| * @param[in] wantCompleted - Want `kCompletedSuffix` in the file path or |
| * not |
| * @return Full file path |
| */ |
| virtual std::string getCPPath(std::string_view nodeName, |
| bool wantCompleted) = 0; |
| |
| /** |
| * Get full file path of duration record for a specific node |
| * |
| * @param[in] nodeName - Node name |
| * @param[in] wantCompleted - Want `kCompletedSuffix` in the file path or |
| * not |
| * @return Full file path |
| */ |
| virtual std::string getDurPath(std::string_view nodeName, |
| bool wantCompleted) = 0; |
| |
| /** |
| * Read 4 bytes data from target address |
| * |
| * @param[in] target - Target address |
| * @return 4 bytes data from the target address or std::nullopt if any error |
| * happens during `readMem4Bytes` |
| */ |
| virtual std::optional<uint32_t> readMem4Bytes(uint32_t target) = 0; |
| }; |
| |
| /** |
| * Utility implementation class |
| */ |
| class Util : public UtilIface |
| { |
| public: |
| std::optional<int64_t> getUpTimeInMs() override; |
| int64_t getWallTimeInMs() override; |
| bool isValidName(std::string_view name) override; |
| std::string getCPPath(std::string_view nodeName, |
| bool wantCompleted) override; |
| std::string getDurPath(std::string_view nodeName, |
| bool wantCompleted) override; |
| std::optional<uint32_t> readMem4Bytes(uint32_t target) override; |
| }; |
| |
| /** |
| * An interface class for the FileUtil APIs |
| */ |
| class FileUtilIface |
| { |
| public: |
| virtual ~FileUtilIface() = default; |
| |
| /** |
| * Add a new checkpoint record in file |
| * |
| * @param[in] name - Checkpoint name |
| * @param[in] wallTimeInMs - Current epoch time in milliseconds |
| * @param[in] monoTimeInMs - Current monotonic time in milliseconds |
| * (Typically it's from `/proc/uptime`) |
| */ |
| virtual void addCheckpoint(std::string_view name, int64_t wallTimeInMs, |
| int64_t monoTimeInMs) = 0; |
| |
| /** |
| * Add a new duration record in file |
| * |
| * @param[in] name - Duration name |
| * @param[in] durationInMs - Duration in milliseconds |
| */ |
| virtual void addDuration(std::string_view name, int64_t durationInMs) = 0; |
| |
| /** |
| * Close current file and rename it with suffix `kCompletedSuffix` |
| */ |
| virtual void completeCurrent() = 0; |
| |
| /** |
| * Load checkpoints from file |
| * |
| * @param[in] loadCompleted - Load file with `kCompletedSuffix` or not |
| * @return Smart pointer of vector of checkpoints |
| */ |
| virtual std::unique_ptr<std::vector<Checkpoint>> |
| loadCheckpoints(bool loadCompleted) = 0; |
| |
| /** |
| * Load durations from file |
| * |
| * @param[in] loadCompleted - Load file with `kCompletedSuffix` or not |
| * @return Smart pointer of vector of durations |
| */ |
| virtual std::unique_ptr<std::vector<Duration>> |
| loadDurations(bool loadCompleted) = 0; |
| |
| /** |
| * Is current file empty |
| * |
| * @return true if file is empty |
| */ |
| virtual bool isEmpty() = 0; |
| }; |
| |
| /** |
| * FileUtil implementation class |
| */ |
| class FileUtil : public FileUtilIface |
| { |
| public: |
| explicit FileUtil(std::string_view filename); |
| void addCheckpoint(std::string_view name, int64_t wallTimeInMs, |
| int64_t monoTimeInMs) override; |
| void addDuration(std::string_view name, int64_t durationInMs) override; |
| void completeCurrent() override; |
| std::unique_ptr<std::vector<Checkpoint>> |
| loadCheckpoints(bool loadCompleted) override; |
| std::unique_ptr<std::vector<Duration>> |
| loadDurations(bool loadCompleted) override; |
| bool isEmpty() override; |
| |
| protected: |
| std::string filename; |
| std::unique_ptr<std::ofstream> ofs; |
| }; |
| |
| } // namespace boot_time_monitor |