1 #pragma once 2 3 #include <chrono> 4 #include <sdbusplus/bus.hpp> 5 #include <sdbusplus/server.hpp> 6 #include "event.hpp" 7 #include "timer.hpp" 8 9 namespace phosphor 10 { 11 namespace fan 12 { 13 namespace monitor 14 { 15 16 class Fan; 17 18 19 /** 20 * @class TachSensor 21 * 22 * This class represents the sensor that reads a tach value. 23 * It may also support a Target, which is the property used to 24 * set a speed. Since it doesn't necessarily have a Target, it 25 * won't for sure know if it is running too slow, so it leaves 26 * that determination to other code. 27 * 28 * This class has a parent Fan object that knows about all 29 * sensors for that fan. 30 */ 31 class TachSensor 32 { 33 public: 34 35 TachSensor() = delete; 36 TachSensor(const TachSensor&) = delete; 37 TachSensor(TachSensor&&) = default; 38 TachSensor& operator=(const TachSensor&) = delete; 39 TachSensor& operator=(TachSensor&&) = default; 40 ~TachSensor() = default; 41 42 /** 43 * @brief Constructor 44 * 45 * @param[in] bus - the dbus object 46 * @param[in] fan - the parent fan object 47 * @param[in] id - the id of the sensor 48 * @param[in] hasTarget - if the sensor supports 49 * setting the speed 50 * @param[in] timeout - Normal timeout value to use 51 * @param[in] events - sd_event pointer 52 */ 53 TachSensor(sdbusplus::bus::bus& bus, 54 Fan& fan, 55 const std::string& id, 56 bool hasTarget, 57 size_t timeout, 58 phosphor::fan::event::EventPtr& events); 59 60 /** 61 * @brief Returns the target speed value 62 */ 63 inline uint64_t getTarget() const 64 { 65 return _tachTarget; 66 } 67 68 /** 69 * @brief Returns the input speed value 70 */ 71 inline int64_t getInput() const 72 { 73 return _tachInput; 74 } 75 76 /** 77 * @brief Returns true if sensor has a target 78 */ 79 inline bool hasTarget() const 80 { 81 return _hasTarget; 82 } 83 84 /** 85 * Returns true if the hardware behind this 86 * sensor is considered working OK/functional. 87 */ 88 inline bool functional() const 89 { 90 return _functional; 91 } 92 93 /** 94 * Sets functional status 95 */ 96 inline void setFunctional(bool functional) 97 { 98 _functional = functional; 99 } 100 101 /** 102 * Returns the timer object for this sensor 103 */ 104 inline phosphor::fan::util::Timer& getTimer() 105 { 106 return _timer; 107 } 108 109 /** 110 * @brief Returns the timeout value to use for the sensor 111 */ 112 std::chrono::microseconds getTimeout(); 113 114 /** 115 * Returns the sensor name 116 */ 117 inline const std::string& name() const 118 { 119 return _name; 120 }; 121 122 private: 123 124 /** 125 * @brief Returns the service name for reading the sensor 126 */ 127 std::string getService(); 128 129 /** 130 * @brief Returns the match string to use for matching 131 * on a properties changed signal. 132 */ 133 std::string getMatchString(const std::string& interface); 134 135 /** 136 * @brief Callback function for a tach input properties 137 * changed signal 138 * 139 * @param[in] msg - the dbus message 140 * @param[in] data - user data 141 * @param[in] err - dbus error 142 */ 143 static int handleTachChangeSignal(sd_bus_message* msg, 144 void* data, 145 sd_bus_error* err); 146 147 /** 148 * @brief Callback function for a Target properties 149 * changed signal 150 * 151 * @param[in] msg - the dbus message 152 * @param[in] data - user data 153 * @param[in] err - dbus error 154 */ 155 static int handleTargetChangeSignal(sd_bus_message* msg, 156 void* data, 157 sd_bus_error* err); 158 159 /** 160 * @brief Reads the Target property and stores in _tachTarget. 161 * Also calls Fan::tachChanged(). 162 * 163 * @param[in] msg - the dbus message 164 * @param[in] err - dbus error 165 */ 166 void handleTargetChange(sdbusplus::message::message& msg, 167 sd_bus_error* err); 168 169 /** 170 * @brief Reads the Value property and stores in _tachInput. 171 * Also calls Fan::tachChanged(). 172 * 173 * @param[in] msg - the dbus message 174 * @param[in] err - dbus error 175 */ 176 void handleTachChange(sdbusplus::message::message& msg, 177 sd_bus_error* err); 178 179 180 /** 181 * @brief the dbus object 182 */ 183 sdbusplus::bus::bus& _bus; 184 185 /** 186 * @brief Reference to the parent Fan object 187 */ 188 Fan& _fan; 189 190 /** 191 * @brief The name of the sensor, including the full path 192 * 193 * For example /xyz/openbmc_project/sensors/fan_tach/fan0 194 */ 195 const std::string _name; 196 197 /** 198 * @brief If functional (not too slow). The parent 199 * fan object sets this. 200 */ 201 bool _functional = true; 202 203 /** 204 * @brief If the sensor has a Target property (can set speed) 205 */ 206 const bool _hasTarget; 207 208 /** 209 * @brief The input speed, from the Value dbus property 210 */ 211 int64_t _tachInput = 0; 212 213 /** 214 * @brief The current target speed, from the Target dbus property 215 * (if applicable) 216 */ 217 uint64_t _tachTarget = 0; 218 219 /** 220 * @brief The timeout value to use 221 */ 222 const size_t _timeout; 223 224 /** 225 * The timer object 226 */ 227 phosphor::fan::util::Timer _timer; 228 229 /** 230 * @brief The match object for the Value properties changed signal 231 */ 232 std::unique_ptr<sdbusplus::server::match::match> tachSignal; 233 234 /** 235 * @brief The match object for the Target properties changed signal 236 */ 237 std::unique_ptr<sdbusplus::server::match::match> targetSignal; 238 }; 239 240 } 241 } 242 } 243