blob: cc059592d1e33b2ca6bb28649c340d99666ca48c [file] [log] [blame]
Matt Spinler7f88fe62017-04-10 14:39:02 -05001#pragma once
2#include <vector>
Matthew Barthe0ca13e2017-06-13 16:29:09 -05003#include <algorithm>
Matt Spinler7f88fe62017-04-10 14:39:02 -05004#include <sdbusplus/bus.hpp>
Matthew Barth38a93a82017-05-11 14:12:27 -05005#include <sdbusplus/server.hpp>
Matt Spinler7f88fe62017-04-10 14:39:02 -05006#include "fan.hpp"
7#include "types.hpp"
8
9namespace phosphor
10{
11namespace fan
12{
13namespace control
14{
15
16/**
Matthew Barth14184132017-05-19 14:37:30 -050017 * The mode fan control will run in:
18 * - init - only do the initialization steps
19 * - control - run normal control algorithms
20 */
21enum class Mode
22{
23 init,
24 control
25};
26
27/**
Matt Spinler7f88fe62017-04-10 14:39:02 -050028 * @class Represents a fan control zone, which is a group of fans
29 * that behave the same.
30 */
31class Zone
32{
33 public:
34
35 Zone() = delete;
36 Zone(const Zone&) = delete;
37 Zone(Zone&&) = default;
38 Zone& operator=(const Zone&) = delete;
39 Zone& operator=(Zone&&) = delete;
40 ~Zone() = default;
41
42 /**
43 * Constructor
44 * Creates the appropriate fan objects based on
45 * the zone definition data passed in.
46 *
Matthew Barth14184132017-05-19 14:37:30 -050047 * @param[in] mode - mode of fan control
Matt Spinler7f88fe62017-04-10 14:39:02 -050048 * @param[in] bus - the dbus object
49 * @param[in] def - the fan zone definition data
50 */
Matthew Barth14184132017-05-19 14:37:30 -050051 Zone(Mode mode,
52 sdbusplus::bus::bus& bus,
Matt Spinler7f88fe62017-04-10 14:39:02 -050053 const ZoneDefinition& def);
54
55 /**
56 * Sets all fans in the zone to the speed
57 * passed in
58 *
59 * @param[in] speed - the fan speed
60 */
61 void setSpeed(uint64_t speed);
62
63 /**
64 * Sets the zone to full speed
65 */
66 inline void setFullSpeed()
67 {
68 if (_fullSpeed != 0)
69 {
70 setSpeed(_fullSpeed);
71 }
72 }
73
Matthew Barth38a93a82017-05-11 14:12:27 -050074 /**
Matthew Barth861d77c2017-05-22 14:18:25 -050075 * @brief Sets the automatic fan control allowed active state
76 *
77 * @param[in] group - A group that affects the active state
78 * @param[in] isActiveAllow - Active state according to group
79 */
80 void setActiveAllow(const Group* group, bool isActiveAllow);
81
82 /**
Matthew Barth38a93a82017-05-11 14:12:27 -050083 * @brief Sets a given object's property value
84 *
85 * @param[in] object - Name of the object containing the property
Matthew Barthcec5ab72017-06-02 15:20:56 -050086 * @param[in] interface - Interface name containing the property
Matthew Barth38a93a82017-05-11 14:12:27 -050087 * @param[in] property - Property name
88 * @param[in] value - Property value
89 */
Matthew Barth9e741ed2017-06-02 16:29:09 -050090 template <typename T>
Matthew Barth38a93a82017-05-11 14:12:27 -050091 void setPropertyValue(const char* object,
Matthew Barthcec5ab72017-06-02 15:20:56 -050092 const char* interface,
Matthew Barth38a93a82017-05-11 14:12:27 -050093 const char* property,
Matthew Barth9e741ed2017-06-02 16:29:09 -050094 T value)
Matthew Barth38a93a82017-05-11 14:12:27 -050095 {
Matthew Barthcec5ab72017-06-02 15:20:56 -050096 _properties[object][interface][property] = value;
Matthew Barth38a93a82017-05-11 14:12:27 -050097 };
98
Matthew Barth17d1fe22017-05-11 15:00:36 -050099 /**
100 * @brief Get the value of an object's property
101 *
102 * @param[in] object - Name of the object containing the property
Matthew Barthcec5ab72017-06-02 15:20:56 -0500103 * @param[in] interface - Interface name containing the property
Matthew Barth17d1fe22017-05-11 15:00:36 -0500104 * @param[in] property - Property name
105 *
106 * @return - The property value
107 */
Matthew Barth9e741ed2017-06-02 16:29:09 -0500108 template <typename T>
Matthew Barth17d1fe22017-05-11 15:00:36 -0500109 inline auto getPropertyValue(const std::string& object,
Matthew Barthcec5ab72017-06-02 15:20:56 -0500110 const std::string& interface,
Matthew Barth17d1fe22017-05-11 15:00:36 -0500111 const std::string& property)
112 {
Matthew Barth9e741ed2017-06-02 16:29:09 -0500113 return sdbusplus::message::variant_ns::get<T>(
114 _properties[object][interface][property]);
Matthew Barth17d1fe22017-05-11 15:00:36 -0500115 };
116
Matthew Barth1de66622017-06-12 13:13:02 -0500117 /**
118 * @brief Get the default floor speed
119 *
120 * @return - The defined default floor speed
121 */
122 inline auto getDefFloor()
123 {
124 return _defFloorSpeed;
125 };
126
Matthew Barth4af419c2017-06-12 13:39:31 -0500127 /**
128 * @brief Set the floor speed to the given speed
129 *
130 * @param[in] speed - Speed to set the floor to
131 */
132 inline void setFloor(uint64_t speed)
133 {
134 _floorSpeed = speed;
135 };
136
Matthew Barthe0ca13e2017-06-13 16:29:09 -0500137 /**
138 * @brief Get the ceiling speed
139 *
140 * @return - The current ceiling speed
141 */
142 inline auto& getCeiling() const
143 {
144 return _ceilingSpeed;
145 };
146
147 /**
148 * @brief Set the ceiling speed to the given speed
149 *
150 * @param[in] speed - Speed to set the ceiling to
151 */
152 inline void setCeiling(uint64_t speed)
153 {
154 _ceilingSpeed = speed;
155 };
156
157 /**
158 * @brief Swaps the ceiling key value with what's given and
159 * returns the value that was swapped.
160 *
161 * @param[in] keyValue - New ceiling key value
162 *
163 * @return - Ceiling key value prior to swapping
164 */
165 inline auto swapCeilingKeyValue(int64_t keyValue)
166 {
167 std::swap(_ceilingKeyValue, keyValue);
168 return keyValue;
169 };
170
Matthew Barth24623522017-06-21 14:09:57 -0500171 /**
172 * @brief Get the increase speed delta
173 *
174 * @return - The current increase speed delta
175 */
176 inline auto& getIncSpeedDelta() const
177 {
178 return _incSpeedDelta;
179 };
180
Matthew Barth240397b2017-06-22 11:23:30 -0500181 /**
182 * @brief Calculate the requested target speed from the given delta
183 * and increase the fan speeds, not going above the ceiling.
184 *
185 * @param[in] targetDelta - The delta to increase the target speed by
186 */
187 void requestSpeedIncrease(uint64_t targetDelta);
188
Matt Spinler7f88fe62017-04-10 14:39:02 -0500189 private:
190
191 /**
192 * The dbus object
193 */
194 sdbusplus::bus::bus& _bus;
195
196 /**
197 * Full speed for the zone
198 */
199 const uint64_t _fullSpeed;
200
201 /**
202 * The zone number
203 */
204 const size_t _zoneNum;
205
206 /**
Matthew Barth1de66622017-06-12 13:13:02 -0500207 * The default floor speed for the zone
208 */
209 const uint64_t _defFloorSpeed;
210
211 /**
Matthew Barthe0ca13e2017-06-13 16:29:09 -0500212 * The default ceiling speed for the zone
213 */
214 const uint64_t _defCeilingSpeed;
215
216 /**
Matthew Barth4af419c2017-06-12 13:39:31 -0500217 * The floor speed to not go below
218 */
219 uint64_t _floorSpeed = _defFloorSpeed;
220
221 /**
Matthew Barthe0ca13e2017-06-13 16:29:09 -0500222 * The ceiling speed to not go above
223 */
224 uint64_t _ceilingSpeed = _defCeilingSpeed;
225
226 /**
227 * The previous sensor value for calculating the ceiling
228 */
229 int64_t _ceilingKeyValue = 0;
230
231 /**
Matthew Barth861d77c2017-05-22 14:18:25 -0500232 * Automatic fan control active state
233 */
234 bool _isActive = true;
235
236 /**
Matthew Barth240397b2017-06-22 11:23:30 -0500237 * Target speed for this zone
238 */
239 uint64_t _targetSpeed = _fullSpeed;
240
241 /**
Matthew Barth24623522017-06-21 14:09:57 -0500242 * Speed increase delta
243 */
244 uint64_t _incSpeedDelta = 0;
245
246 /**
Matt Spinler7f88fe62017-04-10 14:39:02 -0500247 * The vector of fans in this zone
248 */
249 std::vector<std::unique_ptr<Fan>> _fans;
Matthew Barth38a93a82017-05-11 14:12:27 -0500250
251 /**
252 * @brief Map of object property values
253 */
Matthew Barthcec5ab72017-06-02 15:20:56 -0500254 std::map<std::string,
255 std::map<std::string,
256 std::map<std::string,
Matthew Barth9e741ed2017-06-02 16:29:09 -0500257 PropertyVariantType>>> _properties;
Matthew Barth38a93a82017-05-11 14:12:27 -0500258
259 /**
Matthew Barth861d77c2017-05-22 14:18:25 -0500260 * @brief Map of active fan control allowed by groups
261 */
262 std::map<const Group*, bool> _active;
263
264 /**
Matthew Barth38a93a82017-05-11 14:12:27 -0500265 * @brief List of signal event arguments
266 */
Matthew Barth34f1bda2017-05-31 13:45:36 -0500267 std::vector<std::unique_ptr<EventData>> _signalEvents;
Matthew Barth38a93a82017-05-11 14:12:27 -0500268
269 /**
270 * @brief list of Dbus matches for callbacks
271 */
272 std::vector<sdbusplus::server::match::match> _matches;
273
274 /**
Matthew Barthdf3e8d62017-05-31 11:07:24 -0500275 * @brief Get a property value from the path/interface given
276 *
277 * @param[in] bus - the bus to use
278 * @param[in] path - the dbus path name
279 * @param[in] iface - the dbus interface name
280 * @param[in] prop - the property name
281 * @param[out] value - the value of the property
282 */
Matthew Barthdf3e8d62017-05-31 11:07:24 -0500283 static void getProperty(sdbusplus::bus::bus& bus,
284 const std::string& path,
285 const std::string& iface,
286 const std::string& prop,
Matthew Barth9e741ed2017-06-02 16:29:09 -0500287 PropertyVariantType& value);
Matthew Barthdf3e8d62017-05-31 11:07:24 -0500288
289 /**
Matthew Barth34f1bda2017-05-31 13:45:36 -0500290 * @brief Dbus signal change callback handler
Matthew Barth38a93a82017-05-11 14:12:27 -0500291 *
Matthew Barth34f1bda2017-05-31 13:45:36 -0500292 * @param[in] msg - Expanded sdbusplus message data
293 * @param[in] eventData - The single event's data
Matthew Barth38a93a82017-05-11 14:12:27 -0500294 */
Matthew Barth34f1bda2017-05-31 13:45:36 -0500295 void handleEvent(sdbusplus::message::message& msg,
296 const EventData* eventData);
Matt Spinler7f88fe62017-04-10 14:39:02 -0500297};
298
299}
300}
301}