blob: 9d874f75c6c0570809f16b6a3734d49e421c0798 [file] [log] [blame]
#pragma once
#include "boottime_api/boottime_api.h"
#include <boost/asio/steady_timer.hpp>
#include <sdbusplus/asio/connection.hpp>
#include <sdbusplus/asio/object_server.hpp>
#include <sdbusplus/bus.hpp>
#include <sdbusplus/bus/match.hpp>
#include <functional>
#include <optional>
#include <vector>
namespace boot_time_monitor
{
/**
* @brief Contains functionality related to interacting with systemd for boot
* time information.
*/
namespace systemd
{
namespace btm = boot_time_monitor;
/**
* @brief Handles monitoring of systemd boot timestamps for BMC nodes.
*
* This class periodically queries systemd's D-Bus interface
* (`org.freedesktop.systemd1.Manager`) to retrieve various monotonic
* timestamps related to the boot process (Firmware, Loader, Kernel, InitRD,
* Userspace, Finish). It waits until the `FinishTimestampMonotonic` is
* available, indicating the userspace boot is complete. Once available, it
* calculates the duration of each stage and records these durations using the
* provided `IApi` instance, specifically targeting nodes tagged with
* `kBootTimeTagBMC`.
*/
class Handler
{
public:
/**
* @brief Constructs the systemd Handler.
*
* Initializes the handler and starts a timer (`m_bmc_finish_timer`) to
* periodically check for systemd boot completion.
*
* @param conn Shared pointer to the sdbusplus ASIO connection.
* @param api Shared pointer to the central boot time monitoring API.
*/
Handler(std::shared_ptr<sdbusplus::asio::connection> conn,
std::shared_ptr<btm::api::IBoottimeApi> api);
private:
/** @brief Interval for polling systemd properties until boot is finished.
*/
const std::chrono::seconds kCheckBmcFinishInterval =
std::chrono::seconds(10);
/**
* @brief Timer callback function to check systemd boot timestamps.
*
* Queries systemd D-Bus properties for boot timestamps. If the finish
* timestamp is available, calculates stage durations and records them via
* `mApi`. Otherwise, reschedules the timer.
*
* @param ec Boost error code from the timer operation.
* @param conn Shared pointer to the sdbusplus ASIO connection.
*/
void CheckBmcFinish(const boost::system::error_code& ec,
std::shared_ptr<sdbusplus::asio::connection>& conn);
#ifdef NPCM7XX_OR_NEWER
/**
* The below 2 functions are to support the (Firmware + Loader) time
* logging for NPCM7XX or newer Nuvoton BMCs.
*/
/**
* @brief Read 4 byte value from given memory address.
*
* @param target Memory address to read from.
* @return The value from the memory address. Return nullopt if failed.
*/
std::optional<uint32_t> readMem4Bytes(uint32_t target);
/**
* @brief Get system uptime from /proc/uptime.
*
* @return System uptime in milliseconds. Return nullopt if failed.
*/
std::optional<int64_t> getUpTimeInMs();
#endif
/** @brief Shared pointer to the central boot time monitoring API. */
std::shared_ptr<btm::api::IBoottimeApi> mApi;
/** @brief ASIO timer used to periodically check for systemd boot
* completion. */
boost::asio::steady_timer mBMCFinishTimer;
};
} // namespace systemd
} // namespace boot_time_monitor