blob: 50951cdd50126b4f540498b5941cb69db1d806b7 [file] [log] [blame]
Matt Spinlerabf8da32017-04-27 14:08:45 -05001#pragma once
2
3#include <chrono>
4#include <sdbusplus/bus.hpp>
5#include <sdbusplus/server.hpp>
Matt Spinlere824f982017-05-11 10:07:55 -05006#include "event.hpp"
Matt Spinlera9406a72017-04-27 14:29:24 -05007#include "timer.hpp"
Matt Spinlerabf8da32017-04-27 14:08:45 -05008
9namespace phosphor
10{
11namespace fan
12{
13namespace monitor
14{
15
16class Fan;
17
Matt Spinler78689dd2017-09-28 10:12:07 -050018constexpr auto FAN_SENSOR_PATH = "/xyz/openbmc_project/sensors/fan_tach/";
Matt Spinlerabf8da32017-04-27 14:08:45 -050019
20/**
Matthew Barth0a9fe162018-01-26 12:53:15 -060021 * The mode fan monitor will run in:
22 * - init - only do the initialization steps
23 * - monitor - run normal monitoring algorithm
24 */
25enum class Mode
26{
27 init,
28 monitor
29};
30
31/**
Matt Spinlerabf8da32017-04-27 14:08:45 -050032 * @class TachSensor
33 *
34 * This class represents the sensor that reads a tach value.
35 * It may also support a Target, which is the property used to
36 * set a speed. Since it doesn't necessarily have a Target, it
37 * won't for sure know if it is running too slow, so it leaves
38 * that determination to other code.
39 *
40 * This class has a parent Fan object that knows about all
41 * sensors for that fan.
42 */
43class TachSensor
44{
45 public:
46
47 TachSensor() = delete;
48 TachSensor(const TachSensor&) = delete;
Brad Bishopfa0766e2017-07-30 15:42:10 -040049 // TachSensor is not moveable since the this pointer is used as systemd
50 // callback context.
51 TachSensor(TachSensor&&) = delete;
Matt Spinlerabf8da32017-04-27 14:08:45 -050052 TachSensor& operator=(const TachSensor&) = delete;
Brad Bishopfa0766e2017-07-30 15:42:10 -040053 TachSensor& operator=(TachSensor&&) = delete;
Matt Spinlerabf8da32017-04-27 14:08:45 -050054 ~TachSensor() = default;
55
56 /**
57 * @brief Constructor
58 *
Matthew Barth0a9fe162018-01-26 12:53:15 -060059 * @param[in] mode - mode of fan monitor
Matt Spinlerabf8da32017-04-27 14:08:45 -050060 * @param[in] bus - the dbus object
61 * @param[in] fan - the parent fan object
62 * @param[in] id - the id of the sensor
63 * @param[in] hasTarget - if the sensor supports
64 * setting the speed
Lei YU8e5d1972018-01-26 17:14:00 +080065 * @param[in] factor - the factor of the sensor target
66 * @param[in] offset - the offset of the sensor target
Matt Spinlerabf8da32017-04-27 14:08:45 -050067 * @param[in] timeout - Normal timeout value to use
Matt Spinlera9406a72017-04-27 14:29:24 -050068 * @param[in] events - sd_event pointer
Matt Spinlerabf8da32017-04-27 14:08:45 -050069 */
Matthew Barth0a9fe162018-01-26 12:53:15 -060070 TachSensor(Mode mode,
71 sdbusplus::bus::bus& bus,
Matt Spinlerabf8da32017-04-27 14:08:45 -050072 Fan& fan,
73 const std::string& id,
74 bool hasTarget,
Lei YU8e5d1972018-01-26 17:14:00 +080075 size_t factor,
76 size_t offset,
Matt Spinlera9406a72017-04-27 14:29:24 -050077 size_t timeout,
Matt Spinlere824f982017-05-11 10:07:55 -050078 phosphor::fan::event::EventPtr& events);
Matt Spinlerabf8da32017-04-27 14:08:45 -050079
80 /**
81 * @brief Returns the target speed value
82 */
Matthew Barthf552ea52018-01-15 16:22:04 -060083 uint64_t getTarget() const;
Matt Spinlerabf8da32017-04-27 14:08:45 -050084
85 /**
86 * @brief Returns the input speed value
87 */
88 inline int64_t getInput() const
89 {
90 return _tachInput;
91 }
92
93 /**
94 * @brief Returns true if sensor has a target
95 */
96 inline bool hasTarget() const
97 {
98 return _hasTarget;
99 }
100
101 /**
Lei YU8e5d1972018-01-26 17:14:00 +0800102 * @brief Returns the factor of the sensor target
103 */
104 inline size_t getFactor() const
105 {
106 return _factor;
107 }
108
109 /**
110 * @brief Returns the offset of the sensor target
111 */
112 inline size_t getOffset() const
113 {
114 return _offset;
115 }
116
117 /**
Matt Spinlerabf8da32017-04-27 14:08:45 -0500118 * Returns true if the hardware behind this
119 * sensor is considered working OK/functional.
120 */
121 inline bool functional() const
122 {
123 return _functional;
124 }
125
126 /**
Matthew Barthd199dcd2017-11-20 10:36:41 -0600127 * Set the functional status and update inventory to match
Matt Spinlerabf8da32017-04-27 14:08:45 -0500128 */
Matthew Barthd199dcd2017-11-20 10:36:41 -0600129 void setFunctional(bool functional);
Matt Spinlerabf8da32017-04-27 14:08:45 -0500130
Matt Spinlera9406a72017-04-27 14:29:24 -0500131 /**
Matt Spinler6fa181c2017-09-27 16:24:45 -0500132 * @brief Says if the timer is running or not
133 *
134 * @return bool - if timer is currently running
Matt Spinlera9406a72017-04-27 14:29:24 -0500135 */
Matt Spinler6fa181c2017-09-27 16:24:45 -0500136 inline bool timerRunning()
Matt Spinlera9406a72017-04-27 14:29:24 -0500137 {
Matt Spinler6fa181c2017-09-27 16:24:45 -0500138 return _timer.running();
139 }
140
141 /**
142 * @brief Starts the timer for the amount of time
143 * specified in the constructor
144 */
145 inline void startTimer()
146 {
147 _timer.start(
148 getTimeout(),
149 phosphor::fan::util::Timer::TimerType::oneshot);
150 }
151
152 /**
153 * @brief Stops the timer
154 */
155 inline void stopTimer()
156 {
157 _timer.stop();
Matt Spinlera9406a72017-04-27 14:29:24 -0500158 }
159
160 /**
161 * @brief Returns the timeout value to use for the sensor
162 */
163 std::chrono::microseconds getTimeout();
164
Matt Spinlerce75b512017-07-26 15:10:48 -0500165 /**
166 * Returns the sensor name
167 */
168 inline const std::string& name() const
169 {
170 return _name;
171 };
172
Matt Spinlerabf8da32017-04-27 14:08:45 -0500173 private:
174
175 /**
Matt Spinlerebaae612017-04-27 14:21:48 -0500176 * @brief Returns the match string to use for matching
177 * on a properties changed signal.
178 */
179 std::string getMatchString(const std::string& interface);
180
181 /**
Matt Spinlerebaae612017-04-27 14:21:48 -0500182 * @brief Reads the Target property and stores in _tachTarget.
183 * Also calls Fan::tachChanged().
184 *
185 * @param[in] msg - the dbus message
Matt Spinlerebaae612017-04-27 14:21:48 -0500186 */
Brad Bishop771659f2017-07-30 19:52:21 -0400187 void handleTargetChange(sdbusplus::message::message& msg);
Matt Spinlerebaae612017-04-27 14:21:48 -0500188
189 /**
190 * @brief Reads the Value property and stores in _tachInput.
191 * Also calls Fan::tachChanged().
192 *
193 * @param[in] msg - the dbus message
Matt Spinlerebaae612017-04-27 14:21:48 -0500194 */
Brad Bishop771659f2017-07-30 19:52:21 -0400195 void handleTachChange(sdbusplus::message::message& msg);
Matt Spinlerebaae612017-04-27 14:21:48 -0500196
Matthew Barth4d982852017-11-17 09:37:13 -0600197 /**
198 * @brief Updates the Functional property in the inventory
199 * for this tach sensor based on the value passed in.
200 *
201 * @param[in] functional - If the Functional property should
202 * be set to true or false.
203 */
204 void updateInventory(bool functional);
Matt Spinlerebaae612017-04-27 14:21:48 -0500205
206 /**
Matt Spinlerabf8da32017-04-27 14:08:45 -0500207 * @brief the dbus object
208 */
209 sdbusplus::bus::bus& _bus;
210
211 /**
212 * @brief Reference to the parent Fan object
213 */
214 Fan& _fan;
215
216 /**
217 * @brief The name of the sensor, including the full path
218 *
219 * For example /xyz/openbmc_project/sensors/fan_tach/fan0
220 */
221 const std::string _name;
222
223 /**
Matthew Barth4d982852017-11-17 09:37:13 -0600224 * @brief The inventory name of the sensor, including the full path
225 */
226 const std::string _invName;
227
228 /**
Matt Spinlerabf8da32017-04-27 14:08:45 -0500229 * @brief If functional (not too slow). The parent
230 * fan object sets this.
231 */
Matthew Barthd199dcd2017-11-20 10:36:41 -0600232 bool _functional;
Matt Spinlerabf8da32017-04-27 14:08:45 -0500233
234 /**
235 * @brief If the sensor has a Target property (can set speed)
236 */
237 const bool _hasTarget;
238
239 /**
Lei YU8e5d1972018-01-26 17:14:00 +0800240 * @brief The factor of target to get fan rpm
241 */
242 const size_t _factor;
243
244 /**
245 * @brief The offset of target to get fan rpm
246 */
247 const size_t _offset;
248
249 /**
Matt Spinlerabf8da32017-04-27 14:08:45 -0500250 * @brief The input speed, from the Value dbus property
251 */
252 int64_t _tachInput = 0;
253
254 /**
255 * @brief The current target speed, from the Target dbus property
256 * (if applicable)
257 */
258 uint64_t _tachTarget = 0;
259
260 /**
261 * @brief The timeout value to use
262 */
263 const size_t _timeout;
Matt Spinlerebaae612017-04-27 14:21:48 -0500264
265 /**
Matt Spinlera9406a72017-04-27 14:29:24 -0500266 * The timer object
267 */
268 phosphor::fan::util::Timer _timer;
269
270 /**
Matt Spinlerebaae612017-04-27 14:21:48 -0500271 * @brief The match object for the Value properties changed signal
272 */
273 std::unique_ptr<sdbusplus::server::match::match> tachSignal;
274
275 /**
276 * @brief The match object for the Target properties changed signal
277 */
278 std::unique_ptr<sdbusplus::server::match::match> targetSignal;
Matt Spinlerabf8da32017-04-27 14:08:45 -0500279};
280
281}
282}
283}