blob: 8937e43416865bfee79b845f4f928fca8e2bec75 [file] [log] [blame]
#pragma once
#include <ipmid-host/cmd-utils.hpp>
#include <sdbusplus/bus.hpp>
#include <sdbusplus/bus/match.hpp>
#include <sdbusplus/timer.hpp>
#include <queue>
#include <tuple>
namespace phosphor
{
namespace host
{
namespace command
{
/** @class
* @brief Manages commands that are to be sent to Host
*/
class Manager
{
public:
Manager() = delete;
~Manager() = default;
Manager(const Manager&) = delete;
Manager& operator=(const Manager&) = delete;
Manager(Manager&&) = delete;
Manager& operator=(Manager&&) = delete;
/** @brief Constructs Manager object
*
* @param[in] bus - dbus handler
* @param[in] event - pointer to sd_event
*/
explicit Manager(sdbusplus::bus_t& bus);
/** @brief Extracts the next entry in the queue and returns
* Command and data part of it.
*
* @detail Also calls into the registered handlers so that they can now
* send the CommandComplete signal since the interface contract
* is that we emit this signal once the message has been
* passed to the host (which is required when calling this)
*
* Also, if the queue has more commands, then it will alert the
* host
*/
IpmiCmdData getNextCommand();
/** @brief Pushes the command onto the queue.
*
* @detail If the queue is empty, then it alerts the Host. If not,
* then it returns and the API documented above will handle
* the commands in Queue.
*
* @param[in] command - tuple of <IPMI command, data, callback>
*/
void execute(CommandHandler command);
private:
/** @brief Check if anything in queue and alert host if so */
void checkQueueAndAlertHost();
/** @brief Call back interface on message timeouts to host.
*
* @detail When this happens, a failure message would be sent
* to all the commands that are in the Queue and queue
* will be purged
*/
void hostTimeout();
/** @brief Clears the command queue
*
* @detail Clears the command queue and calls all callbacks
* specifying the command wasn't successful.
*/
void clearQueue();
/** @brief Clears the command queue on a power on
*
* @detail The properties changed handler for the
* RequestedHostTransition property. When this property
* changes to 'On', this function will purge the command
* queue.
*
* This is done to avoid having commands that were issued
* before the host powers on from getting sent to the host,
* either due to race conditions around state transitions
* or from a user doing something like requesting an already
* powered off system to power off again and then immediately
* requesting a power on.
*
* @param[in] msg - the sdbusplus message containing the property
*/
void clearQueueOnPowerOn(sdbusplus::message_t& msg);
/** @brief Reference to the dbus handler */
sdbusplus::bus_t& bus;
/** @brief Queue to store the requested commands */
std::queue<CommandHandler> workQueue{};
/** @brief Timer for commands to host */
sdbusplus::Timer timer;
/** @brief Match handler for the requested host state */
sdbusplus::bus::match_t hostTransitionMatch;
};
} // namespace command
} // namespace host
} // namespace phosphor