blob: 015f524930392c4f188bd8aed4cfcd1e073ab958 [file] [log] [blame]
Lei YU01539e72019-07-31 10:57:38 +08001#pragma once
2
3#include "config.h"
4
Lei YUffb36532019-10-15 13:55:24 +08005#include "activation_listener.hpp"
Lei YU7f2a2152019-09-16 16:50:18 +08006#include "association_interface.hpp"
Lei YU91029442019-08-01 15:57:31 +08007#include "types.hpp"
Lei YU9edb7332019-09-19 14:46:19 +08008#include "version.hpp"
Lei YU91029442019-08-01 15:57:31 +08009
Lei YU01539e72019-07-31 10:57:38 +080010#include <sdbusplus/server.hpp>
Lei YU91029442019-08-01 15:57:31 +080011#include <xyz/openbmc_project/Association/Definitions/server.hpp>
Lei YU99301372019-09-29 16:27:12 +080012#include <xyz/openbmc_project/Common/FilePath/server.hpp>
Lei YU01539e72019-07-31 10:57:38 +080013#include <xyz/openbmc_project/Software/Activation/server.hpp>
Lei YU81c67722019-09-11 16:47:29 +080014#include <xyz/openbmc_project/Software/ActivationBlocksTransition/server.hpp>
Lei YU90c8a8b2019-09-11 17:20:03 +080015#include <xyz/openbmc_project/Software/ActivationProgress/server.hpp>
Lei YU01539e72019-07-31 10:57:38 +080016#include <xyz/openbmc_project/Software/ExtendedVersion/server.hpp>
17
Patrick Williams5670b182023-05-10 07:50:50 -050018#include <queue>
Shawn McCarney487e2e12024-11-25 17:19:46 -060019#include <string>
Patrick Williams5670b182023-05-10 07:50:50 -050020
Lei YUff83c2a2019-09-12 13:55:18 +080021class TestActivation;
22
Lei YU01539e72019-07-31 10:57:38 +080023namespace phosphor
24{
25namespace software
26{
27namespace updater
28{
29
Lei YU12c9f4c2019-09-11 15:08:15 +080030namespace sdbusRule = sdbusplus::bus::match::rules;
31
Patrick Williams374fae52022-07-22 19:26:55 -050032using ActivationBlocksTransitionInherit =
33 sdbusplus::server::object_t<sdbusplus::xyz::openbmc_project::Software::
34 server::ActivationBlocksTransition>;
Lei YU81c67722019-09-11 16:47:29 +080035
36/** @class ActivationBlocksTransition
37 * @brief OpenBMC ActivationBlocksTransition implementation.
38 * @details A concrete implementation for
39 * xyz.openbmc_project.Software.ActivationBlocksTransition DBus API.
40 */
41class ActivationBlocksTransition : public ActivationBlocksTransitionInherit
42{
43 public:
George Liu66a54ad2024-08-23 13:53:39 +080044 ActivationBlocksTransition() = delete;
45 ActivationBlocksTransition(const ActivationBlocksTransition&) = delete;
46 ActivationBlocksTransition&
47 operator=(const ActivationBlocksTransition&) = delete;
48 ActivationBlocksTransition(ActivationBlocksTransition&&) = delete;
49 ActivationBlocksTransition&
50 operator=(ActivationBlocksTransition&&) = delete;
51
Lei YU81c67722019-09-11 16:47:29 +080052 /** @brief Constructs ActivationBlocksTransition.
53 *
54 * @param[in] bus - The Dbus bus object
55 * @param[in] path - The Dbus object path
56 */
Patrick Williams374fae52022-07-22 19:26:55 -050057 ActivationBlocksTransition(sdbusplus::bus_t& bus, const std::string& path) :
Albert Zhangf356fdc2020-03-02 09:24:17 +080058 ActivationBlocksTransitionInherit(bus, path.c_str(),
59 action::emit_interface_added),
60 bus(bus)
Lei YU81c67722019-09-11 16:47:29 +080061 {
Lei YU8afeee52019-10-21 15:25:35 +080062 enableRebootGuard();
Lei YU81c67722019-09-11 16:47:29 +080063 }
64
George Liu047d9942024-08-23 13:44:31 +080065 ~ActivationBlocksTransition() override
Lei YU81c67722019-09-11 16:47:29 +080066 {
Lei YU8afeee52019-10-21 15:25:35 +080067 disableRebootGuard();
Lei YU81c67722019-09-11 16:47:29 +080068 }
69
70 private:
Patrick Williams374fae52022-07-22 19:26:55 -050071 sdbusplus::bus_t& bus;
Lei YU8afeee52019-10-21 15:25:35 +080072
73 /** @brief Enables a Guard that blocks any BMC reboot commands */
74 void enableRebootGuard();
75
76 /** @brief Disables any guard that was blocking the BMC reboot */
77 void disableRebootGuard();
Lei YU81c67722019-09-11 16:47:29 +080078};
79
Patrick Williams374fae52022-07-22 19:26:55 -050080using ActivationProgressInherit = sdbusplus::server::object_t<
Lei YU90c8a8b2019-09-11 17:20:03 +080081 sdbusplus::xyz::openbmc_project::Software::server::ActivationProgress>;
82
83class ActivationProgress : public ActivationProgressInherit
84{
85 public:
86 /** @brief Constructs ActivationProgress.
87 *
88 * @param[in] bus - The Dbus bus object
89 * @param[in] path - The Dbus object path
90 */
Patrick Williams374fae52022-07-22 19:26:55 -050091 ActivationProgress(sdbusplus::bus_t& bus, const std::string& path) :
Albert Zhangf356fdc2020-03-02 09:24:17 +080092 ActivationProgressInherit(bus, path.c_str(),
93 action::emit_interface_added)
Lei YU90c8a8b2019-09-11 17:20:03 +080094 {
95 progress(0);
Lei YU90c8a8b2019-09-11 17:20:03 +080096 }
Lei YU90c8a8b2019-09-11 17:20:03 +080097};
98
Patrick Williams374fae52022-07-22 19:26:55 -050099using ActivationInherit = sdbusplus::server::object_t<
Lei YU01539e72019-07-31 10:57:38 +0800100 sdbusplus::xyz::openbmc_project::Software::server::ExtendedVersion,
Lei YU91029442019-08-01 15:57:31 +0800101 sdbusplus::xyz::openbmc_project::Software::server::Activation,
Lei YU99301372019-09-29 16:27:12 +0800102 sdbusplus::xyz::openbmc_project::Association::server::Definitions,
103 sdbusplus::xyz::openbmc_project::Common::server::FilePath>;
Lei YU01539e72019-07-31 10:57:38 +0800104
105/** @class Activation
106 * @brief OpenBMC activation software management implementation.
107 * @details A concrete implementation for
108 * xyz.openbmc_project.Software.Activation DBus API.
109 */
110class Activation : public ActivationInherit
111{
112 public:
Lei YUff83c2a2019-09-12 13:55:18 +0800113 friend class ::TestActivation;
Lei YU12c9f4c2019-09-11 15:08:15 +0800114 using Status = Activations;
Lei YUff83c2a2019-09-12 13:55:18 +0800115
Lei YU01539e72019-07-31 10:57:38 +0800116 /** @brief Constructs Activation Software Manager
117 *
118 * @param[in] bus - The Dbus bus object
119 * @param[in] path - The Dbus object path
120 * @param[in] versionId - The software version id
121 * @param[in] extVersion - The extended version
122 * @param[in] activationStatus - The status of Activation
Lei YU91029442019-08-01 15:57:31 +0800123 * @param[in] assocs - Association objects
Lei YU99301372019-09-29 16:27:12 +0800124 * @param[in] filePath - The image filesystem path
Lei YU01539e72019-07-31 10:57:38 +0800125 */
Patrick Williams374fae52022-07-22 19:26:55 -0500126 Activation(sdbusplus::bus_t& bus, const std::string& objPath,
Lei YU01539e72019-07-31 10:57:38 +0800127 const std::string& versionId, const std::string& extVersion,
Lei YU7f2a2152019-09-16 16:50:18 +0800128 Status activationStatus, const AssociationList& assocs,
Lei YUffb36532019-10-15 13:55:24 +0800129 const std::string& filePath,
Lei YU99301372019-09-29 16:27:12 +0800130 AssociationInterface* associationInterface,
Lei YUffb36532019-10-15 13:55:24 +0800131 ActivationListener* activationListener) :
Tang Yiwei434ae482022-04-16 13:55:21 +0800132 ActivationInherit(bus, objPath.c_str(),
133 ActivationInherit::action::defer_emit),
Lei YU99301372019-09-29 16:27:12 +0800134 bus(bus), objPath(objPath), versionId(versionId),
Lei YU12c9f4c2019-09-11 15:08:15 +0800135 systemdSignals(
136 bus,
137 sdbusRule::type::signal() + sdbusRule::member("JobRemoved") +
138 sdbusRule::path("/org/freedesktop/systemd1") +
139 sdbusRule::interface("org.freedesktop.systemd1.Manager"),
140 std::bind(&Activation::unitStateChange, this,
Lei YU7f2a2152019-09-16 16:50:18 +0800141 std::placeholders::_1)),
Lei YUffb36532019-10-15 13:55:24 +0800142 associationInterface(associationInterface),
143 activationListener(activationListener)
Lei YU01539e72019-07-31 10:57:38 +0800144 {
145 // Set Properties.
146 extendedVersion(extVersion);
147 activation(activationStatus);
Lei YU91029442019-08-01 15:57:31 +0800148 associations(assocs);
Lei YU99301372019-09-29 16:27:12 +0800149 path(filePath);
Lei YU01539e72019-07-31 10:57:38 +0800150
Lei YU9edb7332019-09-19 14:46:19 +0800151 auto info = Version::getExtVersionInfo(extVersion);
152 manufacturer = info["manufacturer"];
153 model = info["model"];
154
Lei YU01539e72019-07-31 10:57:38 +0800155 // Emit deferred signal.
156 emit_object_added();
157 }
158
159 /** @brief Overloaded Activation property setter function
160 *
161 * @param[in] value - One of Activation::Activations
162 *
163 * @return Success or exception thrown
164 */
Lei YUff83c2a2019-09-12 13:55:18 +0800165 Status activation(Status value) override;
Lei YU01539e72019-07-31 10:57:38 +0800166
167 /** @brief Activation */
168 using ActivationInherit::activation;
169
170 /** @brief Overloaded requestedActivation property setter function
171 *
172 * @param[in] value - One of Activation::RequestedActivations
173 *
174 * @return Success or exception thrown
175 */
176 RequestedActivations
177 requestedActivation(RequestedActivations value) override;
178
Lei YU63f9e712019-10-12 15:16:55 +0800179 /** @brief Get the object path */
180 const std::string& getObjectPath() const
181 {
182 return objPath;
183 }
184
Lei YUa5c47bb2019-09-29 11:28:53 +0800185 /** @brief Get the version ID */
186 const std::string& getVersionId() const
187 {
188 return versionId;
189 }
Lei YU12c9f4c2019-09-11 15:08:15 +0800190
191 private:
192 /** @brief Check if systemd state change is relevant to this object
193 *
194 * Instance specific interface to handle the detected systemd state
195 * change
196 *
197 * @param[in] msg - Data associated with subscribed signal
198 *
199 */
Patrick Williams374fae52022-07-22 19:26:55 -0500200 void unitStateChange(sdbusplus::message_t& msg);
Lei YU12c9f4c2019-09-11 15:08:15 +0800201
Lei YUd0bbfa92019-09-11 16:10:54 +0800202 /**
203 * @brief Delete the version from Image Manager and the
204 * untar image from image upload dir.
205 */
206 void deleteImageManagerObject();
207
Lei YUff83c2a2019-09-12 13:55:18 +0800208 /** @brief Invoke the update service for the PSU
209 *
210 * @param[in] psuInventoryPath - The PSU inventory to be updated.
211 *
212 * @return true if the update starts, and false if it fails.
213 */
214 bool doUpdate(const std::string& psuInventoryPath);
215
216 /** @brief Do PSU update one-by-one
217 *
218 * @return true if the update starts, and false if it fails.
219 */
220 bool doUpdate();
221
222 /** @brief Handle an update done event */
223 void onUpdateDone();
224
225 /** @brief Handle an update failure event */
226 void onUpdateFailed();
227
Lei YU12c9f4c2019-09-11 15:08:15 +0800228 /** @brief Start PSU update */
Lei YUff83c2a2019-09-12 13:55:18 +0800229 Status startActivation();
Lei YU12c9f4c2019-09-11 15:08:15 +0800230
231 /** @brief Finish PSU update */
232 void finishActivation();
233
Manojkiran Eda33cf9f02024-06-17 14:40:44 +0530234 /** @brief Check if the PSU is compatible with this software*/
Lei YU9edb7332019-09-19 14:46:19 +0800235 bool isCompatible(const std::string& psuInventoryPath);
236
Lei YU2e0e2de2019-09-26 16:42:23 +0800237 /** @brief Store the updated PSU image to persistent dir */
238 void storeImage();
239
Lei YUe8945ea2019-09-29 17:25:31 +0800240 /** @brief Construct the systemd service name
241 *
Shawn McCarney487e2e12024-11-25 17:19:46 -0600242 * @details Throws an exception if an error occurs
243 *
Lei YUe8945ea2019-09-29 17:25:31 +0800244 * @param[in] psuInventoryPath - The PSU inventory to be updated.
245 *
246 * @return The escaped string of systemd unit to do the PSU update.
247 */
248 std::string getUpdateService(const std::string& psuInventoryPath);
249
Lei YU01539e72019-07-31 10:57:38 +0800250 /** @brief Persistent sdbusplus DBus bus connection */
Patrick Williams374fae52022-07-22 19:26:55 -0500251 sdbusplus::bus_t& bus;
Lei YU01539e72019-07-31 10:57:38 +0800252
253 /** @brief Persistent DBus object path */
Lei YU99301372019-09-29 16:27:12 +0800254 std::string objPath;
Lei YU01539e72019-07-31 10:57:38 +0800255
Lei YUa5c47bb2019-09-29 11:28:53 +0800256 /** @brief Version id */
257 std::string versionId;
258
Lei YU12c9f4c2019-09-11 15:08:15 +0800259 /** @brief Used to subscribe to dbus systemd signals */
260 sdbusplus::bus::match_t systemdSignals;
261
Lei YUff83c2a2019-09-12 13:55:18 +0800262 /** @brief The queue of psu objects to be updated */
263 std::queue<std::string> psuQueue;
264
265 /** @brief The progress step for each PSU update is done */
266 uint32_t progressStep;
267
Lei YU12c9f4c2019-09-11 15:08:15 +0800268 /** @brief The PSU update systemd unit */
269 std::string psuUpdateUnit;
Lei YU81c67722019-09-11 16:47:29 +0800270
Lei YU7f2a2152019-09-16 16:50:18 +0800271 /** @brief The PSU Inventory path of the current updating PSU */
272 std::string currentUpdatingPsu;
273
Lei YU81c67722019-09-11 16:47:29 +0800274 /** @brief Persistent ActivationBlocksTransition dbus object */
275 std::unique_ptr<ActivationBlocksTransition> activationBlocksTransition;
Lei YU90c8a8b2019-09-11 17:20:03 +0800276
277 /** @brief Persistent ActivationProgress dbus object */
278 std::unique_ptr<ActivationProgress> activationProgress;
Lei YU7f2a2152019-09-16 16:50:18 +0800279
280 /** @brief The AssociationInterface pointer */
281 AssociationInterface* associationInterface;
Lei YU9edb7332019-09-19 14:46:19 +0800282
Lei YUffb36532019-10-15 13:55:24 +0800283 /** @brief The activationListener pointer */
284 ActivationListener* activationListener;
285
Lei YU9edb7332019-09-19 14:46:19 +0800286 /** @brief The PSU manufacturer of the software */
287 std::string manufacturer;
288
289 /** @brief The PSU model of the software */
290 std::string model;
Lei YU01539e72019-07-31 10:57:38 +0800291};
292
293} // namespace updater
294} // namespace software
295} // namespace phosphor