blob: 9132a607f66f4f9ca90c7442270107896833a42e [file] [log] [blame]
Patrick Ventureaadb30d2020-08-10 09:17:11 -07001#include "util.hpp"
2
3#include <cmath>
Patrick Venture8b4478c2020-10-06 08:30:27 -07004#include <cstdint>
Patrick Ventureaadb30d2020-08-10 09:17:11 -07005#include <iostream>
Patrick Venture8b4478c2020-10-06 08:30:27 -07006#include <map>
Patrick Venture1a7c49f2020-10-06 15:49:27 -07007#include <regex>
Patrick Ventureaadb30d2020-08-10 09:17:11 -07008#include <set>
Patrick Venture8b4478c2020-10-06 08:30:27 -07009#include <string>
Patrick Venture1a7c49f2020-10-06 15:49:27 -070010#include <unordered_map>
11#include <utility>
Patrick Ventureaadb30d2020-08-10 09:17:11 -070012#include <variant>
Patrick Venture1a7c49f2020-10-06 15:49:27 -070013#include <vector>
Patrick Ventureaadb30d2020-08-10 09:17:11 -070014
15using Property = std::string;
16using Value = std::variant<int64_t, double, std::string, bool>;
17using PropertyMap = std::map<Property, Value>;
18
19namespace pid_control
20{
21
Patrick Ventureb8cfc642020-10-07 08:30:22 -070022int64_t setZoneIndex(const std::string& name,
23 std::map<std::string, int64_t>& zones, int64_t index)
24{
25 auto it = zones.find(name);
26 if (it != zones.end())
27 {
28 // Name already allocated, make no change, return existing
29 return it->second;
30 }
31
32 // The zone name is known not to exist yet
33 for (;;)
34 {
35 bool usedIndex = false;
36
37 // See if desired index number is free
38 for (const auto& zi : zones)
39 {
40 if (index == zi.second)
41 {
42 usedIndex = true;
43 break;
44 }
45 }
46
47 // Increment until a free index number is found
48 if (usedIndex)
49 {
50 ++index;
51 continue;
52 }
53
54 break;
55 }
56
57 // Allocate and return new zone index number for this name
58 zones[name] = index;
59 return index;
60}
61
62int64_t getZoneIndex(const std::string& name,
63 std::map<std::string, int64_t>& zones)
64{
65 auto it = zones.find(name);
66 if (it != zones.end())
67 {
68 return it->second;
69 }
70
71 // Auto-assign next unused zone number, using 0-based numbering
72 return setZoneIndex(name, zones, 0);
73}
74
Patrick Venture1a7c49f2020-10-06 15:49:27 -070075bool findSensors(const std::unordered_map<std::string, std::string>& sensors,
76 const std::string& search,
77 std::vector<std::pair<std::string, std::string>>& matches)
78{
79 std::smatch match;
Jae Hyun Yoo7a8d5a12020-10-21 17:38:56 -070080 std::regex reg('/' + search + '$');
Patrick Venture1a7c49f2020-10-06 15:49:27 -070081 for (const auto& sensor : sensors)
82 {
83 if (std::regex_search(sensor.first, match, reg))
84 {
85 matches.push_back(sensor);
86 }
87 }
88 return matches.size() > 0;
89}
90
Patrick Ventureaadb30d2020-08-10 09:17:11 -070091std::string getSensorPath(const std::string& type, const std::string& id)
92{
93 std::string layer = type;
94 if (type == "fan")
95 {
96 layer = "fan_tach";
97 }
98 else if (type == "temp")
99 {
100 layer = "temperature";
101 }
Josh Lehan3e2f7582020-09-20 22:06:03 -0700102 else if (type == "margin")
103 {
104 layer = "temperature";
105 }
Patrick Ventureaadb30d2020-08-10 09:17:11 -0700106 else
107 {
108 layer = "unknown"; // TODO(venture): Need to handle.
109 }
110
111 return std::string("/xyz/openbmc_project/sensors/" + layer + "/" + id);
112}
113
114std::string getMatch(const std::string& type, const std::string& id)
115{
116 return std::string("type='signal',"
117 "interface='org.freedesktop.DBus.Properties',"
118 "member='PropertiesChanged',"
119 "path='" +
120 getSensorPath(type, id) + "'");
121}
122
123bool validType(const std::string& type)
124{
Josh Lehan3e2f7582020-09-20 22:06:03 -0700125 static std::set<std::string> valid = {"fan", "temp", "margin"};
Patrick Ventureaadb30d2020-08-10 09:17:11 -0700126 return (valid.find(type) != valid.end());
127}
128
129void scaleSensorReading(const double min, const double max, double& value)
130{
131 if (max <= 0 || max <= min)
132 {
133 return;
134 }
Josh Lehan91fe17f2020-09-20 22:50:26 -0700135 value -= min;
Patrick Ventureaadb30d2020-08-10 09:17:11 -0700136 value /= (max - min);
137}
138
139} // namespace pid_control