xref: /openbmc/phosphor-hwmon/mainloop.hpp (revision d3e8794e)
1 #pragma once
2 
3 #include "average.hpp"
4 #include "hwmonio.hpp"
5 #include "interface.hpp"
6 #include "sensor.hpp"
7 #include "sensorset.hpp"
8 #include "sysfs.hpp"
9 #include "types.hpp"
10 
11 #include <any>
12 #include <memory>
13 #include <optional>
14 #include <sdbusplus/server.hpp>
15 #include <sdeventplus/clock.hpp>
16 #include <sdeventplus/event.hpp>
17 #include <sdeventplus/utility/timer.hpp>
18 #include <string>
19 #include <vector>
20 
21 static constexpr auto default_interval = 1000000;
22 
23 static constexpr auto sensorID = 0;
24 static constexpr auto sensorLabel = 1;
25 using SensorIdentifiers = std::tuple<std::string, std::string>;
26 
27 /** @class MainLoop
28  *  @brief hwmon-readd main application loop.
29  */
30 class MainLoop
31 {
32   public:
33     MainLoop() = delete;
34     MainLoop(const MainLoop&) = delete;
35     MainLoop& operator=(const MainLoop&) = delete;
36     MainLoop(MainLoop&&) = delete;
37     MainLoop& operator=(MainLoop&&) = delete;
38     ~MainLoop() = default;
39 
40     /** @brief Constructor
41      *
42      *  @param[in] bus - sdbusplus bus client connection.
43      *  @param[in] param - the path parameter provided
44      *  @param[in] path - hwmon sysfs instance to manage
45      *  @param[in] devPath - physical device sysfs path.
46      *  @param[in] prefix - DBus busname prefix.
47      *  @param[in] root - DBus sensors namespace root.
48      *
49      *  Any DBus objects are created relative to the DBus
50      *  sensors namespace root.
51      *
52      *  At startup, the application will own a busname with
53      *  the format <prefix>.hwmon<n>.
54      */
55     MainLoop(sdbusplus::bus::bus&& bus, const std::string& param,
56              const std::string& path, const std::string& devPath,
57              const char* prefix, const char* root,
58              const hwmonio::HwmonIOInterface* ioIntf);
59 
60     /** @brief Setup polling timer in a sd event loop and attach to D-Bus
61      *         event loop.
62      */
63     void run();
64 
65     /** @brief Stop polling timer event loop from another thread.
66      *
67      *  Typically only used by testcases.
68      */
69     void shutdown() noexcept;
70 
71     /** @brief Remove sensors slated for removal.
72      */
73     void removeSensors();
74 
75     /** @brief Attempt to add sensors back that had been removed.
76      */
77     void addDroppedSensors();
78 
79   private:
80     using mapped_type =
81         std::tuple<SensorSet::mapped_type, std::string, ObjectInfo>;
82     using SensorState = std::map<SensorSet::key_type, mapped_type>;
83 
84     /** @brief Read hwmon sysfs entries */
85     void read();
86 
87     /** @brief Set up D-Bus object state */
88     void init();
89 
90     /** @brief sdbusplus bus client connection. */
91     sdbusplus::bus::bus _bus;
92     /** @brief sdbusplus freedesktop.ObjectManager storage. */
93     sdbusplus::server::manager::manager _manager;
94     /** @brief the parameter path used. */
95     std::string _pathParam;
96     /** @brief hwmon sysfs class path. */
97     std::string _hwmonRoot;
98     /** @brief hwmon sysfs instance. */
99     std::string _instance;
100     /** @brief physical device sysfs path. */
101     std::string _devPath;
102     /** @brief DBus busname prefix. */
103     const char* _prefix;
104     /** @brief DBus sensors namespace root. */
105     const char* _root;
106     /** @brief DBus object state. */
107     SensorState _state;
108     /** @brief Sleep interval in microseconds. */
109     uint64_t _interval = default_interval;
110     /** @brief Hwmon sysfs access. */
111     const hwmonio::HwmonIOInterface* _ioAccess;
112     /** @brief the Event Loop structure */
113     sdeventplus::Event _event;
114     /** @brief Read Timer */
115     sdeventplus::utility::Timer<sdeventplus::ClockId::Monotonic> _timer;
116     /** @brief Store the specifications of sensor objects */
117     std::map<SensorSet::key_type, std::unique_ptr<sensor::Sensor>>
118         _sensorObjects;
119 
120     /**
121      * @brief Map of removed sensors
122      */
123     std::map<SensorSet::key_type, SensorSet::mapped_type> _rmSensors;
124 
125     /** @brief Object of class Average, to handle with average related process
126      */
127     Average _average;
128 
129     /**
130      * @brief Get the ID of the sensor
131      *
132      * @param[in] sensor - Sensor to get the ID of
133      */
134     std::string getID(SensorSet::container_t::const_reference sensor);
135 
136     /**
137      * @brief Get the sensor identifiers
138      *
139      * @param[in] sensor - Sensor to get the identifiers of
140      */
141     SensorIdentifiers
142         getIdentifiers(SensorSet::container_t::const_reference sensor);
143 
144     /**
145      * @brief Used to create and add sensor objects
146      *
147      * @param[in] sensor - Sensor to create/add object for
148      *
149      * @return - Optional
150      *     Object state data on success, nothing on failure
151      */
152     std::optional<ObjectStateData>
153         getObject(SensorSet::container_t::const_reference sensor);
154 };
155 
156 /** @brief Given a value and map of interfaces, update values and check
157  * thresholds.
158  */
159 void updateSensorInterfaces(InterfaceMap& ifaces, SensorValueType value);
160