blob: f0a60e92f876274b922032b1d82c7e05b81035ab [file] [log] [blame]
Jayanth Othayothda9b5832021-11-05 04:19:43 -05001#include "phal_service_actions.hpp"
2
3#include <attributes_info.H>
Jayanth Othayoth3ef7b602021-11-09 06:40:38 -06004#include <libphal.H>
Jayanth Othayothda9b5832021-11-05 04:19:43 -05005
Deepa Karthikeyanff35be32024-10-15 09:10:49 -05006#include <libguard/guard_interface.hpp>
7#include <libguard/include/guard_record.hpp>
Arya K Padman5bc26532024-04-10 06:19:25 -05008#include <phosphor-logging/lg2.hpp>
Jayanth Othayothda9b5832021-11-05 04:19:43 -05009
Jayanth Othayoth1aa90d42023-09-13 04:25:45 -050010#include <format>
11
Deepa Karthikeyanff35be32024-10-15 09:10:49 -050012using GardType = openpower::guard::GardType;
13
Jayanth Othayothda9b5832021-11-05 04:19:43 -050014namespace openpower
15{
16namespace pels
17{
18namespace phal
19{
Jayanth Othayothda9b5832021-11-05 04:19:43 -050020
21/**
Deepa Karthikeyanff35be32024-10-15 09:10:49 -050022 * @brief Helper function to get gard type based on
23 * the given GardType string
Jayanth Othayothda9b5832021-11-05 04:19:43 -050024 *
Deepa Karthikeyanff35be32024-10-15 09:10:49 -050025 * @param[in] guardTypeStr guard type enum value as a string
Jayanth Othayothda9b5832021-11-05 04:19:43 -050026 *
Deepa Karthikeyanff35be32024-10-15 09:10:49 -050027 * @return GardType on success
Jayanth Othayothda9b5832021-11-05 04:19:43 -050028 * Empty optional on failure
29 */
Deepa Karthikeyanff35be32024-10-15 09:10:49 -050030std::optional<GardType> getGardType(const std::string& guardTypeStr)
Jayanth Othayothda9b5832021-11-05 04:19:43 -050031{
Deepa Karthikeyanff35be32024-10-15 09:10:49 -050032 const std::unordered_map<std::string, GardType> gardTypeMap = {
33 {"GARD_Fatal", GardType::GARD_Fatal},
34 {"GARD_User_Manual", GardType::GARD_User_Manual},
35 {"GARD_Predictive", GardType::GARD_Predictive},
36 {"GARD_Spare", GardType::GARD_Spare},
37 {"GARD_Unrecoverable", GardType::GARD_Unrecoverable},
38 };
39
40 auto it = gardTypeMap.find(guardTypeStr);
41 if (it != gardTypeMap.end())
Jayanth Othayothda9b5832021-11-05 04:19:43 -050042 {
Deepa Karthikeyanff35be32024-10-15 09:10:49 -050043 return it->second;
Jayanth Othayothda9b5832021-11-05 04:19:43 -050044 }
45 else
46 {
Deepa Karthikeyanff35be32024-10-15 09:10:49 -050047 lg2::error("Invalid GardType ({GUARDTYPE})", "GUARDTYPE", guardTypeStr);
Jayanth Othayothda9b5832021-11-05 04:19:43 -050048 }
49 return std::nullopt;
50}
51
52/**
53 * @brief Helper function to create guard records.
54 *
55 * User need to fill the JSON callouts array with below keywords/data
56 * "Entitypath": entity path of the hardware from the PHAL device tree.
57 * "Guardtype": The hardware isolation severity which is defined in
58 * xyz.openbmc_project.HardwareIsolation.Entry
59 * "Guarded": boolean, true to create gurad records.
60 *
61 * @param[in] jsonCallouts - The array of JSON callouts, or an empty object.
Deepa Karthikeyanff35be32024-10-15 09:10:49 -050062 * @param[in] plid - The PEL ID to be associated with the guard
Jayanth Othayothda9b5832021-11-05 04:19:43 -050063 * @param[in] dataIface - The DataInterface object
64 */
Deepa Karthikeyanff35be32024-10-15 09:10:49 -050065void createGuardRecords(const nlohmann::json& jsonCallouts, uint32_t plid,
Jayanth Othayothda9b5832021-11-05 04:19:43 -050066 const DataInterfaceBase& dataIface)
67{
68 if (jsonCallouts.empty())
69 {
70 return;
71 }
72
73 if (!jsonCallouts.is_array())
74 {
Arya K Padman5bc26532024-04-10 06:19:25 -050075 lg2::error("GUARD: Callout JSON isn't an array");
Jayanth Othayothda9b5832021-11-05 04:19:43 -050076 return;
77 }
78 for (const auto& _callout : jsonCallouts)
79 {
80 try
81 {
82 // Check Callout data conatains Guarded requests.
83 if (!_callout.contains("Guarded"))
84 {
85 continue;
86 }
87 if (!_callout.at("Guarded").get<bool>())
88 {
89 continue;
90 }
91 // Get Entity path required for guard D-bus method
92 // "CreateWithEntityPath"
93 if (!_callout.contains("EntityPath"))
94 {
Arya K Padman5bc26532024-04-10 06:19:25 -050095 lg2::error(
Jayanth Othayothda9b5832021-11-05 04:19:43 -050096 "GUARD: Callout data, missing EntityPath information");
97 continue;
98 }
99 using EntityPath = std::vector<uint8_t>;
100
101 auto entityPath = _callout.at("EntityPath").get<EntityPath>();
102
103 std::stringstream ss;
Deepa Karthikeyanff35be32024-10-15 09:10:49 -0500104 std::ranges::for_each(entityPath, [&ss](const auto& ele) {
105 ss << std::format("{:02x} ", ele);
106 });
107
Jayanth Othayothda9b5832021-11-05 04:19:43 -0500108 std::string s = ss.str();
Arya K Padman5bc26532024-04-10 06:19:25 -0500109 lg2::info("GUARD: ({GUARD_TARGET})", "GUARD_TARGET", s);
Jayanth Othayothda9b5832021-11-05 04:19:43 -0500110
111 // Get Guard type
Deepa Karthikeyanff35be32024-10-15 09:10:49 -0500112 std::string guardTypeStr = "GARD_Predictive";
Jayanth Othayothda9b5832021-11-05 04:19:43 -0500113 if (!_callout.contains("GuardType"))
114 {
Deepa Karthikeyanff35be32024-10-15 09:10:49 -0500115 lg2::error(
116 "GUARD: doesn't have Severity, setting to GARD_Predictive");
Jayanth Othayothda9b5832021-11-05 04:19:43 -0500117 }
118 else
119 {
Deepa Karthikeyanff35be32024-10-15 09:10:49 -0500120 guardTypeStr = _callout.at("GuardType").get<std::string>();
Jayanth Othayothda9b5832021-11-05 04:19:43 -0500121 }
Deepa Karthikeyanff35be32024-10-15 09:10:49 -0500122
123 GardType eGuardType =
124 getGardType(guardTypeStr).value_or(GardType::GARD_Predictive);
125 dataIface.createGuardRecord(entityPath, eGuardType, plid);
Jayanth Othayothda9b5832021-11-05 04:19:43 -0500126 }
127 catch (const std::exception& e)
128 {
Arya K Padman5bc26532024-04-10 06:19:25 -0500129 lg2::info("GUARD: Failed entry creation exception:({EXCEPTION})",
130 "EXCEPTION", e);
Jayanth Othayothda9b5832021-11-05 04:19:43 -0500131 }
132 }
133}
134
Jayanth Othayoth3ef7b602021-11-09 06:40:38 -0600135/**
136 * @brief Helper function to create deconfig records.
137 *
138 * User need to fill the JSON callouts array with below keywords/data
139 * "EntityPath": entity path of the hardware from the PHAL device tree.
140 * "Deconfigured": boolean, true to create deconfigure records.
141 *
142 * libphal api is used for creating deconfigure records, which includes
143 * update HWAS_STATE attribute to non functional with PLID information.
144 *
145 * @param[in] jsonCallouts - The array of JSON callouts, or an empty object.
146 * @param[in] plid - PLID value
147 */
Deepa Karthikeyanff35be32024-10-15 09:10:49 -0500148void createDeconfigRecords(const nlohmann::json& jsonCallouts, uint32_t plid)
Jayanth Othayoth3ef7b602021-11-09 06:40:38 -0600149{
150 using namespace openpower::phal::pdbg;
151
152 if (jsonCallouts.empty())
153 {
154 return;
155 }
156
157 if (!jsonCallouts.is_array())
158 {
Arya K Padman5bc26532024-04-10 06:19:25 -0500159 lg2::error("Deconfig: Callout JSON isn't an array");
Jayanth Othayoth3ef7b602021-11-09 06:40:38 -0600160 return;
161 }
162 for (const auto& _callout : jsonCallouts)
163 {
164 try
165 {
166 // Check Callout data conatains Guarded requests.
167 if (!_callout.contains("Deconfigured"))
168 {
169 continue;
170 }
171
172 if (!_callout.at("Deconfigured").get<bool>())
173 {
174 continue;
175 }
176
177 if (!_callout.contains("EntityPath"))
178 {
Arya K Padman5bc26532024-04-10 06:19:25 -0500179 lg2::error(
Jayanth Othayoth3ef7b602021-11-09 06:40:38 -0600180 "Deconfig: Callout data missing EntityPath information");
181 continue;
182 }
183 using EntityPath = std::vector<uint8_t>;
184 auto entityPath = _callout.at("EntityPath").get<EntityPath>();
Arya K Padman5bc26532024-04-10 06:19:25 -0500185 lg2::info("Deconfig: adding deconfigure record");
Jayanth Othayoth3ef7b602021-11-09 06:40:38 -0600186 // convert to libphal required format.
187 ATTR_PHYS_BIN_PATH_Type physBinPath;
188 std::copy(entityPath.begin(), entityPath.end(), physBinPath);
189 // libphal api to deconfigure the target
Jayanth Othayoth3ef7b602021-11-09 06:40:38 -0600190 openpower::phal::pdbg::deconfigureTgt(physBinPath, plid);
191 }
192 catch (const std::exception& e)
193 {
Arya K Padman5bc26532024-04-10 06:19:25 -0500194 lg2::info(
195 "Deconfig: Failed to create records, exception:({EXCEPTION})",
196 "EXCEPTION", e);
Jayanth Othayoth3ef7b602021-11-09 06:40:38 -0600197 }
198 }
199}
200
Jayanth Othayothda9b5832021-11-05 04:19:43 -0500201void createServiceActions(const nlohmann::json& jsonCallouts,
Deepa Karthikeyanff35be32024-10-15 09:10:49 -0500202 const DataInterfaceBase& dataIface, uint32_t plid)
Jayanth Othayothda9b5832021-11-05 04:19:43 -0500203{
204 // Create Guard records.
Deepa Karthikeyanff35be32024-10-15 09:10:49 -0500205 createGuardRecords(jsonCallouts, plid, dataIface);
Jayanth Othayoth3ef7b602021-11-09 06:40:38 -0600206 // Create Deconfigure records.
207 createDeconfigRecords(jsonCallouts, plid);
Jayanth Othayothda9b5832021-11-05 04:19:43 -0500208}
Jayanth Othayoth3ef7b602021-11-09 06:40:38 -0600209
Jayanth Othayothda9b5832021-11-05 04:19:43 -0500210} // namespace phal
211} // namespace pels
212} // namespace openpower