blob: 521037cbf28a981b248a1c9e70fd0112b84a76e0 [file] [log] [blame]
Sunny Srivastavafa5e4d32023-03-12 11:59:49 -05001#include "gpio_monitor.hpp"
2
3#include "constants.hpp"
4#include "logger.hpp"
5#include "types.hpp"
6#include "utility/dbus_utility.hpp"
7#include "utility/json_utility.hpp"
8
9#include <boost/asio.hpp>
10#include <boost/bind/bind.hpp>
11#include <gpiod.hpp>
12
13namespace vpd
14{
15void GpioEventHandler::handleChangeInGpioPin(const bool& i_isFruPresent)
16{
17 try
18 {
19 if (i_isFruPresent)
20 {
21 types::VPDMapVariant l_parsedVpd =
22 m_worker->parseVpdFile(m_fruPath);
23
24 if (std::holds_alternative<std::monostate>(l_parsedVpd))
25 {
26 throw std::runtime_error(
27 "VPD parsing failed for " + std::string(m_fruPath));
28 }
29
30 types::ObjectMap l_dbusObjectMap;
31 m_worker->populateDbus(l_parsedVpd, l_dbusObjectMap, m_fruPath);
32
33 if (l_dbusObjectMap.empty())
34 {
35 throw std::runtime_error("Failed to create D-bus object map.");
36 }
37
38 if (!dbusUtility::callPIM(move(l_dbusObjectMap)))
39 {
40 throw std::runtime_error("call PIM failed");
41 }
42 }
43 else
44 {
45 // TODO -- Add implementation to Delete FRU if FRU is not present.
46 }
47 }
48 catch (std::exception& l_ex)
49 {
50 logging::logMessage(std::string(l_ex.what()));
51 }
52}
53
54void GpioEventHandler::handleTimerExpiry(
55 const boost::system::error_code& i_errorCode,
56 const std::shared_ptr<boost::asio::steady_timer>& i_timerObj)
57{
58 if (i_errorCode == boost::asio::error::operation_aborted)
59 {
60 logging::logMessage("Timer aborted for GPIO pin");
61 return;
62 }
63
64 if (i_errorCode)
65 {
66 logging::logMessage("Timer wait failed for gpio pin" +
67 std::string(i_errorCode.message()));
68 return;
69 }
70
71 bool l_currentPresencePinValue = jsonUtility::processGpioPresenceTag(
72 m_worker->getSysCfgJsonObj(), m_fruPath, "pollingRequired",
73 "hotPlugging");
74
75 if (m_prevPresencePinValue != l_currentPresencePinValue)
76 {
77 m_prevPresencePinValue = l_currentPresencePinValue;
78 handleChangeInGpioPin(l_currentPresencePinValue);
79 }
80
81 i_timerObj->expires_at(std::chrono::steady_clock::now() +
82 std::chrono::seconds(constants::VALUE_5));
83 i_timerObj->async_wait(
84 boost::bind(&GpioEventHandler::handleTimerExpiry, this,
85 boost::asio::placeholders::error, i_timerObj));
86}
87
88void GpioEventHandler::setEventHandlerForGpioPresence(
89 const std::shared_ptr<boost::asio::io_context>& i_ioContext)
90{
91 m_prevPresencePinValue = jsonUtility::processGpioPresenceTag(
92 m_worker->getSysCfgJsonObj(), m_fruPath, "pollingRequired",
93 "hotPlugging");
94
95 static std::vector<std::shared_ptr<boost::asio::steady_timer>> l_timers;
96
97 auto l_timerObj = make_shared<boost::asio::steady_timer>(
98 *i_ioContext, std::chrono::seconds(constants::VALUE_5));
99
100 l_timerObj->async_wait(
101 boost::bind(&GpioEventHandler::handleTimerExpiry, this,
102 boost::asio::placeholders::error, l_timerObj));
103
104 l_timers.push_back(l_timerObj);
105}
106
107void GpioMonitor::initHandlerForGpio(
108 const std::shared_ptr<boost::asio::io_context>& i_ioContext,
109 const std::shared_ptr<Worker>& i_worker)
110{
111 try
112 {
113 std::vector<std::string> l_gpioPollingRequiredFrusList =
114 jsonUtility::getListOfGpioPollingFrus(m_sysCfgJsonObj);
115
116 for (const auto& l_fruPath : l_gpioPollingRequiredFrusList)
117 {
118 std::shared_ptr<GpioEventHandler> l_gpioEventHandlerObj =
119 std::make_shared<GpioEventHandler>(l_fruPath, i_worker,
120 i_ioContext);
121
122 m_gpioEventHandlerObjects.push_back(l_gpioEventHandlerObj);
123 }
124 }
125 catch (std::exception& l_ex)
126 {
127 // TODO log PEL for exception.
128 logging::logMessage(l_ex.what());
129 }
130}
131} // namespace vpd