blob: db988ff325ceec1dcf721170795b392dc1d539e0 [file] [log] [blame]
Wludzik, Jozef76833cb2020-12-21 14:42:41 +01001#include "trigger.hpp"
2
Szymon Dompkee28aa532021-10-27 12:33:12 +02003#include "trigger_manager.hpp"
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +00004#include "types/report_types.hpp"
5#include "types/trigger_types.hpp"
Cezary Zwolak4416fce2021-03-17 03:21:06 +01006#include "utils/conversion_trigger.hpp"
Cezary Zwolaka4e67612021-02-18 13:16:16 +01007#include "utils/transform.hpp"
8
9#include <phosphor-logging/log.hpp>
10
Wludzik, Jozef76833cb2020-12-21 14:42:41 +010011Trigger::Trigger(
12 boost::asio::io_context& ioc,
13 const std::shared_ptr<sdbusplus::asio::object_server>& objServer,
Szymon Dompkee28aa532021-10-27 12:33:12 +020014 const std::string& idIn, const std::string& nameIn,
Szymon Dompke94f71c52021-12-10 07:16:33 +010015 const std::vector<TriggerAction>& triggerActionsIn,
16 const std::shared_ptr<std::vector<std::string>> reportIdsIn,
Wludzik, Jozef1477fe62021-01-02 11:56:10 +010017 std::vector<std::shared_ptr<interfaces::Threshold>>&& thresholdsIn,
Cezary Zwolaka4e67612021-02-18 13:16:16 +010018 interfaces::TriggerManager& triggerManager,
Szymon Dompke94f71c52021-12-10 07:16:33 +010019 interfaces::JsonStorage& triggerStorageIn,
20 const interfaces::TriggerFactory& triggerFactory, Sensors sensorsIn) :
Szymon Dompkee28aa532021-10-27 12:33:12 +020021 id(idIn),
22 name(nameIn), triggerActions(std::move(triggerActionsIn)),
Szymon Dompke94f71c52021-12-10 07:16:33 +010023 path(triggerDir + id), reportIds(std::move(reportIdsIn)),
Cezary Zwolak4416fce2021-03-17 03:21:06 +010024 thresholds(std::move(thresholdsIn)),
Szymon Dompkee28aa532021-10-27 12:33:12 +020025 fileName(std::to_string(std::hash<std::string>{}(id))),
Szymon Dompke94f71c52021-12-10 07:16:33 +010026 triggerStorage(triggerStorageIn), sensors(std::move(sensorsIn))
Wludzik, Jozef76833cb2020-12-21 14:42:41 +010027{
28 deleteIface = objServer->add_unique_interface(
29 path, deleteIfaceName, [this, &ioc, &triggerManager](auto& dbusIface) {
30 dbusIface.register_method("Delete", [this, &ioc, &triggerManager] {
Cezary Zwolaka4e67612021-02-18 13:16:16 +010031 if (persistent)
32 {
33 triggerStorage.remove(fileName);
34 }
Wludzik, Jozef76833cb2020-12-21 14:42:41 +010035 boost::asio::post(ioc, [this, &triggerManager] {
36 triggerManager.removeTrigger(this);
37 });
38 });
39 });
40
41 triggerIface = objServer->add_unique_interface(
Szymon Dompke94f71c52021-12-10 07:16:33 +010042 path, triggerIfaceName, [this, &triggerFactory](auto& dbusIface) {
Cezary Zwolaka4e67612021-02-18 13:16:16 +010043 persistent = storeConfiguration();
44 dbusIface.register_property_rw(
Wludzik, Jozef76833cb2020-12-21 14:42:41 +010045 "Persistent", persistent,
46 sdbusplus::vtable::property_::emits_change,
Cezary Zwolaka4e67612021-02-18 13:16:16 +010047 [this](bool newVal, const auto&) {
48 if (newVal == persistent)
49 {
Szymon Dompke3e2cc9d2021-12-14 12:00:52 +010050 return 1;
Cezary Zwolaka4e67612021-02-18 13:16:16 +010051 }
52 if (newVal)
53 {
54 persistent = storeConfiguration();
55 }
56 else
57 {
58 triggerStorage.remove(fileName);
59 persistent = false;
60 }
Szymon Dompke3e2cc9d2021-12-14 12:00:52 +010061 return 1;
Cezary Zwolaka4e67612021-02-18 13:16:16 +010062 },
63 [this](const auto&) { return persistent; });
64
Szymon Dompke94f71c52021-12-10 07:16:33 +010065 dbusIface.register_property_rw(
Cezary Zwolak4416fce2021-03-17 03:21:06 +010066 "Thresholds", TriggerThresholdParams{},
Wludzik, Jozef76833cb2020-12-21 14:42:41 +010067 sdbusplus::vtable::property_::emits_change,
Szymon Dompke94f71c52021-12-10 07:16:33 +010068 [this, &triggerFactory](auto newVal, auto& oldVal) {
69 auto newThresholdParams = std::visit(
70 utils::ToLabeledThresholdParamConversion(), newVal);
71 triggerFactory.updateThresholds(thresholds, triggerActions,
72 reportIds, sensors,
73 newThresholdParams);
74 oldVal = std::move(newVal);
75 return 1;
76 },
Cezary Zwolak4416fce2021-03-17 03:21:06 +010077 [this](const auto&) {
Szymon Dompke94f71c52021-12-10 07:16:33 +010078 return fromLabeledThresholdParam(
79 utils::transform(thresholds, [](const auto& threshold) {
80 return threshold->getThresholdParam();
81 }));
Cezary Zwolak4416fce2021-03-17 03:21:06 +010082 });
83
Szymon Dompke94f71c52021-12-10 07:16:33 +010084 dbusIface.register_property_rw(
Cezary Zwolak4416fce2021-03-17 03:21:06 +010085 "Sensors", SensorsInfo{},
86 sdbusplus::vtable::property_::emits_change,
Szymon Dompke94f71c52021-12-10 07:16:33 +010087 [this, &triggerFactory](auto newVal, auto& oldVal) {
88 auto labeledSensorInfo =
89 triggerFactory.getLabeledSensorsInfo(newVal);
90 triggerFactory.updateSensors(sensors, labeledSensorInfo);
91 for (const auto& threshold : thresholds)
92 {
93 threshold->updateSensors(sensors);
94 }
95 oldVal = std::move(newVal);
96 return 1;
97 },
Cezary Zwolak4416fce2021-03-17 03:21:06 +010098 [this](const auto&) {
Szymon Dompke94f71c52021-12-10 07:16:33 +010099 return utils::fromLabeledSensorsInfo(
100 utils::transform(sensors, [](const auto& sensor) {
101 return sensor->getLabeledSensorInfo();
102 }));
Cezary Zwolak4416fce2021-03-17 03:21:06 +0100103 });
104
Szymon Dompke94f71c52021-12-10 07:16:33 +0100105 dbusIface.register_property_rw(
106 "ReportNames", std::vector<std::string>{},
Wludzik, Jozef76833cb2020-12-21 14:42:41 +0100107 sdbusplus::vtable::property_::emits_change,
Szymon Dompke94f71c52021-12-10 07:16:33 +0100108 [this](auto newVal, auto& oldVal) {
109 reportIds->clear();
110 std::copy(newVal.begin(), newVal.end(),
111 std::back_inserter(*reportIds));
112 oldVal = std::move(newVal);
113 return 1;
114 },
115 [this](const auto&) { return *reportIds; });
Szymon Dompke20013012021-07-23 09:54:20 +0200116
117 dbusIface.register_property_r(
118 "Discrete", false, sdbusplus::vtable::property_::const_,
119 [this](const auto& x) {
Szymon Dompke94f71c52021-12-10 07:16:33 +0100120 return !std::holds_alternative<
121 numeric::LabeledThresholdParam>(
122 thresholds.back()->getThresholdParam());
Szymon Dompke20013012021-07-23 09:54:20 +0200123 });
124
Szymon Dompkee28aa532021-10-27 12:33:12 +0200125 dbusIface.register_property_rw(
126 "Name", std::string(),
127 sdbusplus::vtable::property_::emits_change,
128 [this](auto newVal, auto& oldVal) {
129 name = oldVal = newVal;
Szymon Dompke3e2cc9d2021-12-14 12:00:52 +0100130 return 1;
Szymon Dompkee28aa532021-10-27 12:33:12 +0200131 },
132 [this](const auto&) { return name; });
133
Szymon Dompke94f71c52021-12-10 07:16:33 +0100134 dbusIface.register_property_r(
135 "TriggerActions", std::vector<std::string>(),
136 sdbusplus::vtable::property_::const_, [this](const auto&) {
137 return utils::transform(triggerActions,
138 [](const auto& action) {
139 return actionToString(action);
140 });
141 });
Wludzik, Jozef76833cb2020-12-21 14:42:41 +0100142 });
Wludzik, Jozef1477fe62021-01-02 11:56:10 +0100143
144 for (const auto& threshold : thresholds)
145 {
146 threshold->initialize();
147 }
Wludzik, Jozef76833cb2020-12-21 14:42:41 +0100148}
Cezary Zwolaka4e67612021-02-18 13:16:16 +0100149
150bool Trigger::storeConfiguration() const
151{
152 try
153 {
154 nlohmann::json data;
155
Szymon Dompke94f71c52021-12-10 07:16:33 +0100156 auto labeledThresholdParams =
157 std::visit(utils::ToLabeledThresholdParamConversion(),
158 fromLabeledThresholdParam(utils::transform(
159 thresholds, [](const auto& threshold) {
160 return threshold->getThresholdParam();
161 })));
162
Cezary Zwolaka4e67612021-02-18 13:16:16 +0100163 data["Version"] = triggerVersion;
Szymon Dompkee28aa532021-10-27 12:33:12 +0200164 data["Id"] = id;
Cezary Zwolaka4e67612021-02-18 13:16:16 +0100165 data["Name"] = name;
Cezary Zwolak4416fce2021-03-17 03:21:06 +0100166 data["ThresholdParamsDiscriminator"] = labeledThresholdParams.index();
Szymon Dompke94f71c52021-12-10 07:16:33 +0100167 data["TriggerActions"] =
168 utils::transform(triggerActions, [](const auto& action) {
169 return actionToString(action);
170 });
Cezary Zwolak4416fce2021-03-17 03:21:06 +0100171 data["ThresholdParams"] =
172 utils::labeledThresholdParamsToJson(labeledThresholdParams);
Szymon Dompke94f71c52021-12-10 07:16:33 +0100173 data["ReportIds"] = *reportIds;
174 data["Sensors"] = utils::transform(sensors, [](const auto& sensor) {
175 return sensor->getLabeledSensorInfo();
176 });
Cezary Zwolaka4e67612021-02-18 13:16:16 +0100177
178 triggerStorage.store(fileName, data);
179 }
180 catch (const std::exception& e)
181 {
182 phosphor::logging::log<phosphor::logging::level::ERR>(
183 "Failed to store a trigger in storage",
184 phosphor::logging::entry("EXCEPTION_MSG=%s", e.what()));
185 return false;
186 }
187 return true;
Cezary Zwolak4416fce2021-03-17 03:21:06 +0100188}