1 #include "oem_ibm_handler.hpp"
2
3 #include "collect_slot_vpd.hpp"
4 #include "file_io_type_lid.hpp"
5 #include "libpldmresponder/file_io.hpp"
6 #include "libpldmresponder/pdr_utils.hpp"
7
8 #include <libpldm/entity.h>
9 #include <libpldm/oem/ibm/entity.h>
10 #include <libpldm/pldm.h>
11
12 #include <phosphor-logging/lg2.hpp>
13 #include <xyz/openbmc_project/State/BMC/client.hpp>
14 #include <xyz/openbmc_project/State/Host/common.hpp>
15
16 PHOSPHOR_LOG2_USING;
17
18 using namespace pldm::pdr;
19 using namespace pldm::utils;
20
21 namespace pldm
22 {
23 namespace responder
24 {
25 namespace oem_ibm_platform
26 {
27 int pldm::responder::oem_ibm_platform::Handler::
getOemStateSensorReadingsHandler(pldm::pdr::EntityType entityType,EntityInstance entityInstance,ContainerID containerId,StateSetId stateSetId,CompositeCount compSensorCnt,uint16_t,std::vector<get_sensor_state_field> & stateField)28 getOemStateSensorReadingsHandler(
29 pldm::pdr::EntityType entityType, EntityInstance entityInstance,
30 ContainerID containerId, StateSetId stateSetId,
31 CompositeCount compSensorCnt, uint16_t /*sensorId*/,
32 std::vector<get_sensor_state_field>& stateField)
33 {
34 auto& entityAssociationMap = getAssociateEntityMap();
35 int rc = PLDM_SUCCESS;
36 stateField.clear();
37
38 for (size_t i = 0; i < compSensorCnt; i++)
39 {
40 uint8_t sensorOpState{};
41 uint8_t presentState = PLDM_SENSOR_UNKNOWN;
42 if (entityType == PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE &&
43 stateSetId == PLDM_OEM_IBM_BOOT_STATE)
44 {
45 sensorOpState = fetchBootSide(entityInstance, codeUpdate);
46 }
47 else if (entityType == PLDM_ENTITY_SLOT &&
48 stateSetId == PLDM_OEM_IBM_PCIE_SLOT_SENSOR_STATE)
49 {
50 for (const auto& [key, value] : entityAssociationMap)
51 {
52 if (value.entity_type == entityType &&
53 value.entity_instance_num == entityInstance &&
54 value.entity_container_id == containerId)
55 {
56 sensorOpState = slotHandler->fetchSlotSensorState(key);
57 break;
58 }
59 }
60 }
61 else if (entityType == PLDM_OEM_IBM_ENTITY_REAL_SAI &&
62 stateSetId == PLDM_STATE_SET_OPERATIONAL_FAULT_STATUS)
63 {
64 sensorOpState = fetchRealSAIStatus();
65 presentState = PLDM_SENSOR_NORMAL;
66 }
67 else
68 {
69 rc = PLDM_PLATFORM_INVALID_STATE_VALUE;
70 break;
71 }
72 stateField.push_back({PLDM_SENSOR_ENABLED, presentState,
73 PLDM_SENSOR_UNKNOWN, sensorOpState});
74 }
75 return rc;
76 }
77
78 int pldm::responder::oem_ibm_platform::Handler::
oemSetStateEffecterStatesHandler(uint16_t entityType,uint16_t entityInstance,uint16_t stateSetId,uint8_t compEffecterCnt,std::vector<set_effecter_state_field> & stateField,uint16_t effecterId)79 oemSetStateEffecterStatesHandler(
80 uint16_t entityType, uint16_t entityInstance, uint16_t stateSetId,
81 uint8_t compEffecterCnt,
82 std::vector<set_effecter_state_field>& stateField, uint16_t effecterId)
83 {
84 int rc = PLDM_SUCCESS;
85 auto& entityAssociationMap = getAssociateEntityMap();
86
87 for (uint8_t currState = 0; currState < compEffecterCnt; ++currState)
88 {
89 if (stateField[currState].set_request == PLDM_REQUEST_SET)
90 {
91 if (entityType == PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE &&
92 stateSetId == PLDM_OEM_IBM_BOOT_STATE)
93 {
94 rc = setBootSide(entityInstance, currState, stateField,
95 codeUpdate);
96 }
97 else if (entityType == PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE &&
98 stateSetId == PLDM_OEM_IBM_FIRMWARE_UPDATE_STATE)
99 {
100 if (stateField[currState].effecter_state ==
101 uint8_t(CodeUpdateState::START))
102 {
103 codeUpdate->setCodeUpdateProgress(true);
104 startUpdateEvent =
105 std::make_unique<sdeventplus::source::Defer>(
106 event,
107 std::bind(std::mem_fn(&oem_ibm_platform::Handler::
108 _processStartUpdate),
109 this, std::placeholders::_1));
110 }
111 else if (stateField[currState].effecter_state ==
112 uint8_t(CodeUpdateState::END))
113 {
114 rc = PLDM_SUCCESS;
115 assembleImageEvent = std::make_unique<
116 sdeventplus::source::Defer>(
117 event,
118 std::bind(
119 std::mem_fn(
120 &oem_ibm_platform::Handler::_processEndUpdate),
121 this, std::placeholders::_1));
122
123 // sendCodeUpdateEvent(effecterId, END, START);
124 }
125 else if (stateField[currState].effecter_state ==
126 uint8_t(CodeUpdateState::ABORT))
127 {
128 codeUpdate->setCodeUpdateProgress(false);
129 codeUpdate->clearDirPath(LID_STAGING_DIR);
130 auto sensorId = codeUpdate->getFirmwareUpdateSensor();
131 sendStateSensorEvent(sensorId, PLDM_STATE_SENSOR_STATE, 0,
132 uint8_t(CodeUpdateState::ABORT),
133 uint8_t(CodeUpdateState::START));
134 // sendCodeUpdateEvent(effecterId, ABORT, END);
135 }
136 else if (stateField[currState].effecter_state ==
137 uint8_t(CodeUpdateState::ACCEPT))
138 {
139 auto sensorId = codeUpdate->getFirmwareUpdateSensor();
140 sendStateSensorEvent(sensorId, PLDM_STATE_SENSOR_STATE, 0,
141 uint8_t(CodeUpdateState::ACCEPT),
142 uint8_t(CodeUpdateState::END));
143 // TODO Set new Dbus property provided by code update app
144 // sendCodeUpdateEvent(effecterId, ACCEPT, END);
145 }
146 else if (stateField[currState].effecter_state ==
147 uint8_t(CodeUpdateState::REJECT))
148 {
149 auto sensorId = codeUpdate->getFirmwareUpdateSensor();
150 sendStateSensorEvent(sensorId, PLDM_STATE_SENSOR_STATE, 0,
151 uint8_t(CodeUpdateState::REJECT),
152 uint8_t(CodeUpdateState::END));
153 // TODO Set new Dbus property provided by code update app
154 // sendCodeUpdateEvent(effecterId, REJECT, END);
155 }
156 }
157 else if (entityType == PLDM_ENTITY_SYSTEM_CHASSIS &&
158 stateSetId == PLDM_OEM_IBM_SYSTEM_POWER_STATE)
159 {
160 if (stateField[currState].effecter_state == POWER_CYCLE_HARD)
161 {
162 systemRebootEvent =
163 std::make_unique<sdeventplus::source::Defer>(
164 event,
165 std::bind(std::mem_fn(&oem_ibm_platform::Handler::
166 _processSystemReboot),
167 this, std::placeholders::_1));
168 }
169 }
170 else if (stateSetId == PLDM_OEM_IBM_PCIE_SLOT_EFFECTER_STATE)
171 {
172 slotHandler->enableSlot(effecterId, entityAssociationMap,
173 stateField[currState].effecter_state);
174 }
175 else if (entityType == PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE &&
176 stateSetId == PLDM_OEM_IBM_BOOT_SIDE_RENAME)
177 {
178 if (stateField[currState].effecter_state ==
179 PLDM_OEM_IBM_BOOT_SIDE_RENAME_STATE_RENAMED)
180 {
181 codeUpdate->processRenameEvent();
182 }
183 }
184 else if (entityType == PLDM_OEM_IBM_ENTITY_REAL_SAI &&
185 stateSetId == PLDM_STATE_SET_OPERATIONAL_FAULT_STATUS)
186 {
187 turnOffRealSAIEffecter();
188 }
189 else
190 {
191 rc = PLDM_PLATFORM_SET_EFFECTER_UNSUPPORTED_SENSORSTATE;
192 }
193 }
194 if (rc != PLDM_SUCCESS)
195 {
196 break;
197 }
198 }
199 return rc;
200 }
201
buildAllCodeUpdateEffecterPDR(oem_ibm_platform::Handler * platformHandler,uint16_t entityType,uint16_t entityInstance,uint16_t stateSetID,pdr_utils::Repo & repo)202 void buildAllCodeUpdateEffecterPDR(oem_ibm_platform::Handler* platformHandler,
203 uint16_t entityType, uint16_t entityInstance,
204 uint16_t stateSetID, pdr_utils::Repo& repo)
205 {
206 size_t pdrSize = 0;
207 pdrSize = sizeof(pldm_state_effecter_pdr) +
208 sizeof(state_effecter_possible_states);
209 std::vector<uint8_t> entry{};
210 entry.resize(pdrSize);
211 pldm_state_effecter_pdr* pdr =
212 reinterpret_cast<pldm_state_effecter_pdr*>(entry.data());
213 if (!pdr)
214 {
215 error("Failed to get record by PDR type, error - {ERROR}", "ERROR",
216 lg2::hex,
217 static_cast<unsigned>(PLDM_PLATFORM_INVALID_EFFECTER_ID));
218 return;
219 }
220 pdr->hdr.record_handle = 0;
221 pdr->hdr.version = 1;
222 pdr->hdr.type = PLDM_STATE_EFFECTER_PDR;
223 pdr->hdr.record_change_num = 0;
224 pdr->hdr.length = sizeof(pldm_state_effecter_pdr) - sizeof(pldm_pdr_hdr);
225 pdr->terminus_handle = TERMINUS_HANDLE;
226 pdr->effecter_id = platformHandler->getNextEffecterId();
227 pdr->entity_type = entityType;
228 pdr->entity_instance = entityInstance;
229 pdr->container_id = 1;
230 pdr->effecter_semantic_id = 0;
231 pdr->effecter_init = PLDM_NO_INIT;
232 pdr->has_description_pdr = false;
233 pdr->composite_effecter_count = 1;
234
235 auto* possibleStatesPtr = pdr->possible_states;
236 auto possibleStates =
237 reinterpret_cast<state_effecter_possible_states*>(possibleStatesPtr);
238 possibleStates->state_set_id = stateSetID;
239 possibleStates->possible_states_size = 2;
240 auto state =
241 reinterpret_cast<state_effecter_possible_states*>(possibleStates);
242 if ((stateSetID == PLDM_OEM_IBM_BOOT_STATE) ||
243 (stateSetID == PLDM_OEM_IBM_BOOT_SIDE_RENAME))
244 state->states[0].byte = 6;
245 else if (stateSetID == PLDM_OEM_IBM_FIRMWARE_UPDATE_STATE)
246 state->states[0].byte = 126;
247 else if (stateSetID == PLDM_OEM_IBM_SYSTEM_POWER_STATE)
248 state->states[0].byte = 2;
249 pldm::responder::pdr_utils::PdrEntry pdrEntry{};
250 pdrEntry.data = entry.data();
251 pdrEntry.size = pdrSize;
252 repo.addRecord(pdrEntry);
253 }
254
buildAllSlotEnableEffecterPDR(oem_ibm_platform::Handler * platformHandler,pdr_utils::Repo & repo,const std::vector<std::string> & slotobjpaths)255 void buildAllSlotEnableEffecterPDR(oem_ibm_platform::Handler* platformHandler,
256 pdr_utils::Repo& repo,
257 const std::vector<std::string>& slotobjpaths)
258 {
259 size_t pdrSize = 0;
260 pdrSize = sizeof(pldm_state_effecter_pdr) +
261 sizeof(state_effecter_possible_states);
262 std::vector<uint8_t> entry{};
263 entry.resize(pdrSize);
264 pldm_state_effecter_pdr* pdr =
265 reinterpret_cast<pldm_state_effecter_pdr*>(entry.data());
266 if (!pdr)
267 {
268 error("Failed to get record by PDR type, ERROR:{ERR}", "ERR", lg2::hex,
269 static_cast<unsigned>(PLDM_PLATFORM_INVALID_EFFECTER_ID));
270 return;
271 }
272
273 auto& associatedEntityMap = platformHandler->getAssociateEntityMap();
274 for (const auto& entity_path : slotobjpaths)
275 {
276 pdr->hdr.record_handle = 0;
277 pdr->hdr.version = 1;
278 pdr->hdr.type = PLDM_STATE_EFFECTER_PDR;
279 pdr->hdr.record_change_num = 0;
280 pdr->hdr.length =
281 sizeof(pldm_state_effecter_pdr) - sizeof(pldm_pdr_hdr);
282 pdr->terminus_handle = TERMINUS_HANDLE;
283 pdr->effecter_id = platformHandler->getNextEffecterId();
284
285 if (entity_path != "" && associatedEntityMap.contains(entity_path))
286 {
287 pdr->entity_type = associatedEntityMap.at(entity_path).entity_type;
288 pdr->entity_instance =
289 associatedEntityMap.at(entity_path).entity_instance_num;
290 pdr->container_id =
291 associatedEntityMap.at(entity_path).entity_container_id;
292 platformHandler->effecterIdToDbusMap[pdr->effecter_id] =
293 entity_path;
294 }
295 else
296 {
297 // the slots are not present, dont create the PDR
298 continue;
299 }
300 pdr->effecter_semantic_id = 0;
301 pdr->effecter_init = PLDM_NO_INIT;
302 pdr->has_description_pdr = false;
303 pdr->composite_effecter_count = 1;
304
305 auto* possibleStatesPtr = pdr->possible_states;
306 auto possibleStates = reinterpret_cast<state_effecter_possible_states*>(
307 possibleStatesPtr);
308 possibleStates->state_set_id = PLDM_OEM_IBM_PCIE_SLOT_EFFECTER_STATE;
309 possibleStates->possible_states_size = 2;
310 auto state =
311 reinterpret_cast<state_effecter_possible_states*>(possibleStates);
312 state->states[0].byte = 14;
313 pldm::responder::pdr_utils::PdrEntry pdrEntry{};
314 pdrEntry.data = entry.data();
315 pdrEntry.size = pdrSize;
316 repo.addRecord(pdrEntry);
317 }
318 }
319
buildAllCodeUpdateSensorPDR(oem_ibm_platform::Handler * platformHandler,uint16_t entityType,uint16_t entityInstance,uint16_t stateSetID,pdr_utils::Repo & repo)320 void buildAllCodeUpdateSensorPDR(oem_ibm_platform::Handler* platformHandler,
321 uint16_t entityType, uint16_t entityInstance,
322 uint16_t stateSetID, pdr_utils::Repo& repo)
323 {
324 size_t pdrSize = 0;
325 pdrSize = sizeof(pldm_state_sensor_pdr) +
326 sizeof(state_sensor_possible_states);
327 std::vector<uint8_t> entry{};
328 entry.resize(pdrSize);
329 pldm_state_sensor_pdr* pdr =
330 reinterpret_cast<pldm_state_sensor_pdr*>(entry.data());
331 if (!pdr)
332 {
333 error("Failed to get record by PDR type, error - {ERROR}", "ERROR",
334 lg2::hex, static_cast<unsigned>(PLDM_PLATFORM_INVALID_SENSOR_ID));
335 return;
336 }
337 pdr->hdr.record_handle = 0;
338 pdr->hdr.version = 1;
339 pdr->hdr.type = PLDM_STATE_SENSOR_PDR;
340 pdr->hdr.record_change_num = 0;
341 pdr->hdr.length = sizeof(pldm_state_sensor_pdr) - sizeof(pldm_pdr_hdr);
342 pdr->terminus_handle = TERMINUS_HANDLE;
343 pdr->sensor_id = platformHandler->getNextSensorId();
344 pdr->entity_type = entityType;
345 pdr->entity_instance = entityInstance;
346 pdr->container_id = 1;
347 pdr->sensor_init = PLDM_NO_INIT;
348 pdr->sensor_auxiliary_names_pdr = false;
349 pdr->composite_sensor_count = 1;
350
351 auto* possibleStatesPtr = pdr->possible_states;
352 auto possibleStates =
353 reinterpret_cast<state_sensor_possible_states*>(possibleStatesPtr);
354 possibleStates->state_set_id = stateSetID;
355 possibleStates->possible_states_size = 2;
356 auto state =
357 reinterpret_cast<state_sensor_possible_states*>(possibleStates);
358 if ((stateSetID == PLDM_OEM_IBM_BOOT_STATE) ||
359 (stateSetID == PLDM_OEM_IBM_VERIFICATION_STATE) ||
360 (stateSetID == PLDM_OEM_IBM_BOOT_SIDE_RENAME))
361 state->states[0].byte = 6;
362 else if (stateSetID == PLDM_OEM_IBM_FIRMWARE_UPDATE_STATE)
363 state->states[0].byte = 126;
364 pldm::responder::pdr_utils::PdrEntry pdrEntry{};
365 pdrEntry.data = entry.data();
366 pdrEntry.size = pdrSize;
367 repo.addRecord(pdrEntry);
368 }
369
buildAllSlotEnableSensorPDR(oem_ibm_platform::Handler * platformHandler,pdr_utils::Repo & repo,const std::vector<std::string> & slotobjpaths)370 void buildAllSlotEnableSensorPDR(oem_ibm_platform::Handler* platformHandler,
371 pdr_utils::Repo& repo,
372 const std::vector<std::string>& slotobjpaths)
373 {
374 size_t pdrSize = 0;
375 pdrSize = sizeof(pldm_state_sensor_pdr) +
376 sizeof(state_sensor_possible_states);
377 std::vector<uint8_t> entry{};
378 entry.resize(pdrSize);
379 pldm_state_sensor_pdr* pdr =
380 reinterpret_cast<pldm_state_sensor_pdr*>(entry.data());
381 if (!pdr)
382 {
383 error("Failed to get record by PDR type, ERROR:{ERR}", "ERR", lg2::hex,
384 static_cast<unsigned>(PLDM_PLATFORM_INVALID_SENSOR_ID));
385 return;
386 }
387 auto& associatedEntityMap = platformHandler->getAssociateEntityMap();
388 for (const auto& entity_path : slotobjpaths)
389 {
390 pdr->hdr.record_handle = 0;
391 pdr->hdr.version = 1;
392 pdr->hdr.type = PLDM_STATE_SENSOR_PDR;
393 pdr->hdr.record_change_num = 0;
394 pdr->hdr.length = sizeof(pldm_state_sensor_pdr) - sizeof(pldm_pdr_hdr);
395 pdr->terminus_handle = TERMINUS_HANDLE;
396 pdr->sensor_id = platformHandler->getNextSensorId();
397 if (entity_path != "" && associatedEntityMap.contains(entity_path))
398 {
399 pdr->entity_type = associatedEntityMap.at(entity_path).entity_type;
400 pdr->entity_instance =
401 associatedEntityMap.at(entity_path).entity_instance_num;
402 pdr->container_id =
403 associatedEntityMap.at(entity_path).entity_container_id;
404 }
405 else
406 {
407 // the slots are not present, dont create the PDR
408 continue;
409 }
410
411 pdr->sensor_init = PLDM_NO_INIT;
412 pdr->sensor_auxiliary_names_pdr = false;
413 pdr->composite_sensor_count = 1;
414
415 auto* possibleStatesPtr = pdr->possible_states;
416 auto possibleStates =
417 reinterpret_cast<state_sensor_possible_states*>(possibleStatesPtr);
418 possibleStates->state_set_id = PLDM_OEM_IBM_PCIE_SLOT_SENSOR_STATE;
419 possibleStates->possible_states_size = 1;
420 auto state =
421 reinterpret_cast<state_sensor_possible_states*>(possibleStates);
422 state->states[0].byte = 15;
423 pldm::responder::pdr_utils::PdrEntry pdrEntry{};
424 pdrEntry.data = entry.data();
425 pdrEntry.size = pdrSize;
426 repo.addRecord(pdrEntry);
427 }
428 }
429
buildAllRealSAIEffecterPDR(oem_ibm_platform::Handler * platformHandler,uint16_t entityType,uint16_t entityInstance,pdr_utils::Repo & repo)430 void buildAllRealSAIEffecterPDR(oem_ibm_platform::Handler* platformHandler,
431 uint16_t entityType, uint16_t entityInstance,
432 pdr_utils::Repo& repo)
433
434 {
435 size_t pdrSize = 0;
436 pdrSize = sizeof(pldm_state_effecter_pdr) +
437 sizeof(state_effecter_possible_states);
438 std::vector<uint8_t> entry{};
439 entry.resize(pdrSize);
440 pldm_state_effecter_pdr* pdr =
441 reinterpret_cast<pldm_state_effecter_pdr*>(entry.data());
442 if (!pdr)
443 {
444 error("Failed to get Real SAI effecter PDR record due to the "
445 "error {ERR_CODE}",
446 "ERR_CODE", lg2::hex,
447 static_cast<unsigned>(PLDM_PLATFORM_INVALID_EFFECTER_ID));
448 return;
449 }
450 pdr->hdr.record_handle = 0;
451 pdr->hdr.version = 1;
452 pdr->hdr.type = PLDM_STATE_EFFECTER_PDR;
453 pdr->hdr.record_change_num = 0;
454 pdr->hdr.length = sizeof(pldm_state_effecter_pdr) - sizeof(pldm_pdr_hdr);
455 pdr->terminus_handle = TERMINUS_HANDLE;
456 pdr->effecter_id = platformHandler->getNextEffecterId();
457 pdr->entity_type = entityType;
458 pdr->entity_instance = entityInstance;
459 pdr->container_id = 1;
460 pdr->effecter_semantic_id = 0;
461 pdr->effecter_init = PLDM_NO_INIT;
462 pdr->has_description_pdr = false;
463 pdr->composite_effecter_count = 1;
464
465 auto* possibleStatesPtr = pdr->possible_states;
466 auto possibleStates =
467 reinterpret_cast<state_effecter_possible_states*>(possibleStatesPtr);
468 possibleStates->state_set_id = PLDM_STATE_SET_OPERATIONAL_FAULT_STATUS;
469 possibleStates->possible_states_size = 1;
470 auto state =
471 reinterpret_cast<state_effecter_possible_states*>(possibleStates);
472 state->states[0].byte = 2;
473 pldm::responder::pdr_utils::PdrEntry pdrEntry{};
474 pdrEntry.data = entry.data();
475 pdrEntry.size = pdrSize;
476 repo.addRecord(pdrEntry);
477 }
478
buildAllRealSAISensorPDR(oem_ibm_platform::Handler * platformHandler,uint16_t entityType,uint16_t entityInstance,pdr_utils::Repo & repo)479 void buildAllRealSAISensorPDR(oem_ibm_platform::Handler* platformHandler,
480 uint16_t entityType, uint16_t entityInstance,
481 pdr_utils::Repo& repo)
482
483 {
484 size_t pdrSize = 0;
485 pdrSize = sizeof(pldm_state_sensor_pdr) +
486 sizeof(state_sensor_possible_states);
487 std::vector<uint8_t> entry{};
488 entry.resize(pdrSize);
489 pldm_state_sensor_pdr* pdr =
490 reinterpret_cast<pldm_state_sensor_pdr*>(entry.data());
491 if (!pdr)
492 {
493 error("Failed to get Real SAI sensor PDR record due to the "
494 "error {ERR_CODE}",
495 "ERR_CODE", lg2::hex,
496 static_cast<unsigned>(PLDM_PLATFORM_INVALID_SENSOR_ID));
497 return;
498 }
499 pdr->hdr.record_handle = 0;
500 pdr->hdr.version = 1;
501 pdr->hdr.type = PLDM_STATE_SENSOR_PDR;
502 pdr->hdr.record_change_num = 0;
503 pdr->hdr.length = sizeof(pldm_state_sensor_pdr) - sizeof(pldm_pdr_hdr);
504 pdr->terminus_handle = TERMINUS_HANDLE;
505 pdr->sensor_id = platformHandler->getNextSensorId();
506 pdr->entity_type = entityType;
507 pdr->entity_instance = entityInstance;
508 pdr->container_id = 1;
509 pdr->sensor_init = PLDM_NO_INIT;
510 pdr->sensor_auxiliary_names_pdr = false;
511 pdr->composite_sensor_count = 1;
512
513 auto* possibleStatesPtr = pdr->possible_states;
514 auto possibleStates =
515 reinterpret_cast<state_sensor_possible_states*>(possibleStatesPtr);
516 possibleStates->state_set_id = PLDM_STATE_SET_OPERATIONAL_FAULT_STATUS;
517 possibleStates->possible_states_size = 2;
518 auto state =
519 reinterpret_cast<state_sensor_possible_states*>(possibleStates);
520 state->states[0].byte = 6;
521 pldm::responder::pdr_utils::PdrEntry pdrEntry{};
522 pdrEntry.data = entry.data();
523 pdrEntry.size = pdrSize;
524 repo.addRecord(pdrEntry);
525 }
526
buildOEMPDR(pdr_utils::Repo & repo)527 void pldm::responder::oem_ibm_platform::Handler::buildOEMPDR(
528 pdr_utils::Repo& repo)
529 {
530 buildAllCodeUpdateEffecterPDR(this, PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE,
531 ENTITY_INSTANCE_0, PLDM_OEM_IBM_BOOT_STATE,
532 repo);
533 buildAllCodeUpdateEffecterPDR(this, PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE,
534 ENTITY_INSTANCE_1, PLDM_OEM_IBM_BOOT_STATE,
535 repo);
536 buildAllCodeUpdateEffecterPDR(this, PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE,
537 ENTITY_INSTANCE_0,
538 PLDM_OEM_IBM_FIRMWARE_UPDATE_STATE, repo);
539 buildAllCodeUpdateEffecterPDR(this, PLDM_ENTITY_SYSTEM_CHASSIS,
540 ENTITY_INSTANCE_1,
541 PLDM_OEM_IBM_SYSTEM_POWER_STATE, repo);
542
543 static constexpr auto objectPath = "/xyz/openbmc_project/inventory/system";
544 const std::vector<std::string> slotInterface = {
545 "xyz.openbmc_project.Inventory.Item.PCIeSlot"};
546 auto slotPaths = dBusIntf->getSubTreePaths(objectPath, 0, slotInterface);
547 buildAllSlotEnableEffecterPDR(this, repo, slotPaths);
548
549 buildAllRealSAIEffecterPDR(this, PLDM_OEM_IBM_ENTITY_REAL_SAI,
550 ENTITY_INSTANCE_1, repo);
551
552 buildAllSlotEnableSensorPDR(this, repo, slotPaths);
553
554 buildAllCodeUpdateSensorPDR(this, PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE,
555 ENTITY_INSTANCE_0, PLDM_OEM_IBM_BOOT_STATE,
556 repo);
557 buildAllCodeUpdateSensorPDR(this, PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE,
558 ENTITY_INSTANCE_1, PLDM_OEM_IBM_BOOT_STATE,
559 repo);
560 buildAllCodeUpdateSensorPDR(this, PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE,
561 ENTITY_INSTANCE_0,
562 PLDM_OEM_IBM_FIRMWARE_UPDATE_STATE, repo);
563 buildAllCodeUpdateSensorPDR(this, PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE,
564 ENTITY_INSTANCE_0,
565 PLDM_OEM_IBM_VERIFICATION_STATE, repo);
566 buildAllCodeUpdateSensorPDR(this, PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE,
567 ENTITY_INSTANCE_0,
568 PLDM_OEM_IBM_BOOT_SIDE_RENAME, repo);
569 buildAllRealSAISensorPDR(this, PLDM_OEM_IBM_ENTITY_REAL_SAI,
570 ENTITY_INSTANCE_1, repo);
571
572 realSAISensorId = findStateSensorId(
573 repo.getPdr(), 0, PLDM_OEM_IBM_ENTITY_REAL_SAI, ENTITY_INSTANCE_1, 1,
574 PLDM_STATE_SET_OPERATIONAL_FAULT_STATUS);
575
576 auto sensorId = findStateSensorId(
577 repo.getPdr(), 0, PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE,
578 ENTITY_INSTANCE_0, 1, PLDM_OEM_IBM_VERIFICATION_STATE);
579 codeUpdate->setMarkerLidSensor(sensorId);
580 sensorId = findStateSensorId(
581 repo.getPdr(), 0, PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE,
582 ENTITY_INSTANCE_0, 1, PLDM_OEM_IBM_FIRMWARE_UPDATE_STATE);
583 codeUpdate->setFirmwareUpdateSensor(sensorId);
584 sensorId =
585 findStateSensorId(repo.getPdr(), 0, PLDM_OEM_IBM_ENTITY_FIRMWARE_UPDATE,
586 ENTITY_INSTANCE_0, 1, PLDM_OEM_IBM_BOOT_SIDE_RENAME);
587 codeUpdate->setBootSideRenameStateSensor(sensorId);
588 }
589
setPlatformHandler(pldm::responder::platform::Handler * handler)590 void pldm::responder::oem_ibm_platform::Handler::setPlatformHandler(
591 pldm::responder::platform::Handler* handler)
592 {
593 platformHandler = handler;
594 }
595
sendEventToHost(std::vector<uint8_t> & requestMsg,uint8_t instanceId)596 int pldm::responder::oem_ibm_platform::Handler::sendEventToHost(
597 std::vector<uint8_t>& requestMsg, uint8_t instanceId)
598 {
599 if (requestMsg.size())
600 {
601 std::ostringstream tempStream;
602 for (int byte : requestMsg)
603 {
604 tempStream << std::setfill('0') << std::setw(2) << std::hex << byte
605 << " ";
606 }
607 std::cout << tempStream.str() << std::endl;
608 }
609 auto oemPlatformEventMessageResponseHandler = [](mctp_eid_t /*eid*/,
610 const pldm_msg* response,
611 size_t respMsgLen) {
612 uint8_t completionCode{};
613 uint8_t status{};
614 auto rc = decode_platform_event_message_resp(response, respMsgLen,
615 &completionCode, &status);
616 if (rc || completionCode)
617 {
618 error(
619 "Failed to decode platform event message response for code update event with response code '{RC}' and completion code '{CC}'",
620 "RC", rc, "CC", completionCode);
621 }
622 };
623 auto rc = handler->registerRequest(
624 mctp_eid, instanceId, PLDM_PLATFORM, PLDM_PLATFORM_EVENT_MESSAGE,
625 std::move(requestMsg),
626 std::move(oemPlatformEventMessageResponseHandler));
627 if (rc)
628 {
629 error("Failed to send BIOS attribute change event message ");
630 }
631
632 return rc;
633 }
634
encodeEventMsg(uint8_t eventType,const std::vector<uint8_t> & eventDataVec,std::vector<uint8_t> & requestMsg,uint8_t instanceId)635 int encodeEventMsg(uint8_t eventType, const std::vector<uint8_t>& eventDataVec,
636 std::vector<uint8_t>& requestMsg, uint8_t instanceId)
637 {
638 auto request = reinterpret_cast<pldm_msg*>(requestMsg.data());
639
640 auto rc = encode_platform_event_message_req(
641 instanceId, 1 /*formatVersion*/, TERMINUS_ID /*tId*/, eventType,
642 eventDataVec.data(), eventDataVec.size(), request,
643 eventDataVec.size() + PLDM_PLATFORM_EVENT_MESSAGE_MIN_REQ_BYTES);
644
645 return rc;
646 }
647
sendStateSensorEvent(uint16_t sensorId,enum sensor_event_class_states sensorEventClass,uint8_t sensorOffset,uint8_t eventState,uint8_t prevEventState)648 void pldm::responder::oem_ibm_platform::Handler::sendStateSensorEvent(
649 uint16_t sensorId, enum sensor_event_class_states sensorEventClass,
650 uint8_t sensorOffset, uint8_t eventState, uint8_t prevEventState)
651 {
652 std::vector<uint8_t> sensorEventDataVec{};
653 size_t sensorEventSize = PLDM_SENSOR_EVENT_DATA_MIN_LENGTH + 1;
654 sensorEventDataVec.resize(sensorEventSize);
655 auto eventData = reinterpret_cast<struct pldm_sensor_event_data*>(
656 sensorEventDataVec.data());
657 eventData->sensor_id = sensorId;
658 eventData->sensor_event_class_type = sensorEventClass;
659 auto eventClassStart = eventData->event_class;
660 auto eventClass =
661 reinterpret_cast<struct pldm_sensor_event_state_sensor_state*>(
662 eventClassStart);
663 eventClass->sensor_offset = sensorOffset;
664 eventClass->event_state = eventState;
665 eventClass->previous_event_state = prevEventState;
666 auto instanceId = instanceIdDb.next(mctp_eid);
667 std::vector<uint8_t> requestMsg(
668 sizeof(pldm_msg_hdr) + PLDM_PLATFORM_EVENT_MESSAGE_MIN_REQ_BYTES +
669 sensorEventDataVec.size());
670 auto rc = encodeEventMsg(PLDM_SENSOR_EVENT, sensorEventDataVec, requestMsg,
671 instanceId);
672 if (rc != PLDM_SUCCESS)
673 {
674 error("Failed to encode state sensor event with response code '{RC}'",
675 "RC", rc);
676 instanceIdDb.free(mctp_eid, instanceId);
677 return;
678 }
679 rc = sendEventToHost(requestMsg, instanceId);
680 if (rc != PLDM_SUCCESS)
681 {
682 error(
683 "Failed to send event to remote terminus with response code '{RC}'",
684 "RC", rc);
685 }
686 return;
687 }
688
_processEndUpdate(sdeventplus::source::EventBase &)689 void pldm::responder::oem_ibm_platform::Handler::_processEndUpdate(
690 sdeventplus::source::EventBase& /*source */)
691 {
692 assembleImageEvent.reset();
693 int retc = codeUpdate->assembleCodeUpdateImage();
694 if (retc != PLDM_SUCCESS)
695 {
696 codeUpdate->setCodeUpdateProgress(false);
697 auto sensorId = codeUpdate->getFirmwareUpdateSensor();
698 sendStateSensorEvent(sensorId, PLDM_STATE_SENSOR_STATE, 0,
699 uint8_t(CodeUpdateState::FAIL),
700 uint8_t(CodeUpdateState::START));
701 }
702 }
703
_processStartUpdate(sdeventplus::source::EventBase &)704 void pldm::responder::oem_ibm_platform::Handler::_processStartUpdate(
705 sdeventplus::source::EventBase& /*source */)
706 {
707 codeUpdate->deleteImage();
708 CodeUpdateState state = CodeUpdateState::START;
709 auto rc = codeUpdate->setRequestedApplyTime();
710 if (rc != PLDM_SUCCESS)
711 {
712 error("setRequestedApplyTime failed");
713 state = CodeUpdateState::FAIL;
714 }
715 auto sensorId = codeUpdate->getFirmwareUpdateSensor();
716 sendStateSensorEvent(sensorId, PLDM_STATE_SENSOR_STATE, 0, uint8_t(state),
717 uint8_t(CodeUpdateState::END));
718 }
719
updateOemDbusPaths(std::string & dbusPath)720 void pldm::responder::oem_ibm_platform::Handler::updateOemDbusPaths(
721 std::string& dbusPath)
722 {
723 std::string toFind("system1/chassis1/motherboard1");
724 if (dbusPath.find(toFind) != std::string::npos)
725 {
726 size_t pos = dbusPath.find(toFind);
727 dbusPath.replace(pos, toFind.length(), "system/chassis/motherboard");
728 }
729 toFind = "system1";
730 if (dbusPath.find(toFind) != std::string::npos)
731 {
732 size_t pos = dbusPath.find(toFind);
733 dbusPath.replace(pos, toFind.length(), "system");
734 }
735 /* below logic to replace path 'motherboard/socket/chassis' to
736 'motherboard/chassis' or 'motherboard/socket123/chassis' to
737 'motherboard/chassis' */
738 toFind = "socket";
739 size_t pos1 = dbusPath.find(toFind);
740 // while loop to detect multiple substring 'socket' in the path
741 while (pos1 != std::string::npos)
742 {
743 size_t pos2 = dbusPath.substr(pos1 + 1).find('/') + 1;
744 // Replacing starting from substring to next occurrence of char '/'
745 dbusPath.replace(pos1, pos2 + 1, "");
746 pos1 = dbusPath.find(toFind);
747 }
748 }
749
_processSystemReboot(sdeventplus::source::EventBase &)750 void pldm::responder::oem_ibm_platform::Handler::_processSystemReboot(
751 sdeventplus::source::EventBase& /*source */)
752 {
753 pldm::utils::PropertyValue value =
754 "xyz.openbmc_project.State.Chassis.Transition.Off";
755 pldm::utils::DBusMapping dbusMapping{"/xyz/openbmc_project/state/chassis0",
756 "xyz.openbmc_project.State.Chassis",
757 "RequestedPowerTransition", "string"};
758 try
759 {
760 dBusIntf->setDbusProperty(dbusMapping, value);
761 }
762 catch (const std::exception& e)
763 {
764 error(
765 "Failure in chassis State transition to Off, unable to set property RequestedPowerTransition, error - {ERROR}",
766 "ERROR", e);
767 }
768
769 using namespace sdbusplus::bus::match::rules;
770 chassisOffMatch = std::make_unique<sdbusplus::bus::match_t>(
771 pldm::utils::DBusHandler::getBus(),
772 propertiesChanged("/xyz/openbmc_project/state/chassis0",
773 "xyz.openbmc_project.State.Chassis"),
774 [this](sdbusplus::message_t& msg) {
775 DbusChangedProps props{};
776 std::string intf;
777 msg.read(intf, props);
778 const auto itr = props.find("CurrentPowerState");
779 if (itr != props.end())
780 {
781 PropertyValue value = itr->second;
782 auto propVal = std::get<std::string>(value);
783 if (propVal ==
784 "xyz.openbmc_project.State.Chassis.PowerState.Off")
785 {
786 pldm::utils::DBusMapping dbusMapping{
787 "/xyz/openbmc_project/control/host0/"
788 "power_restore_policy/one_time",
789 "xyz.openbmc_project.Control.Power.RestorePolicy",
790 "PowerRestorePolicy", "string"};
791 value = "xyz.openbmc_project.Control.Power.RestorePolicy."
792 "Policy.AlwaysOn";
793 try
794 {
795 dBusIntf->setDbusProperty(dbusMapping, value);
796 }
797 catch (const std::exception& e)
798 {
799 error(
800 "Failure in setting one-time restore policy, unable to set property PowerRestorePolicy, error - {ERROR}",
801 "ERROR", e);
802 }
803 dbusMapping = pldm::utils::DBusMapping{
804 "/xyz/openbmc_project/state/bmc0",
805 "xyz.openbmc_project.State.BMC",
806 "RequestedBMCTransition", "string"};
807 value = "xyz.openbmc_project.State.BMC.Transition.Reboot";
808 try
809 {
810 dBusIntf->setDbusProperty(dbusMapping, value);
811 }
812 catch (const std::exception& e)
813 {
814 error(
815 "Failure in BMC state transition to reboot, unable to set property RequestedBMCTransition , error - {ERROR}",
816 "ERROR", e);
817 }
818 }
819 }
820 });
821 }
822
checkAndDisableWatchDog()823 void pldm::responder::oem_ibm_platform::Handler::checkAndDisableWatchDog()
824 {
825 if (!hostOff && setEventReceiverCnt == SET_EVENT_RECEIVER_SENT)
826 {
827 disableWatchDogTimer();
828 }
829
830 return;
831 }
832
watchDogRunning()833 bool pldm::responder::oem_ibm_platform::Handler::watchDogRunning()
834 {
835 static constexpr auto watchDogObjectPath =
836 "/xyz/openbmc_project/watchdog/host0";
837 static constexpr auto watchDogEnablePropName = "Enabled";
838 static constexpr auto watchDogInterface =
839 "xyz.openbmc_project.State.Watchdog";
840 bool isWatchDogRunning = false;
841 try
842 {
843 isWatchDogRunning = pldm::utils::DBusHandler().getDbusProperty<bool>(
844 watchDogObjectPath, watchDogEnablePropName, watchDogInterface);
845 }
846 catch (const std::exception&)
847 {
848 return false;
849 }
850 return isWatchDogRunning;
851 }
852
resetWatchDogTimer()853 void pldm::responder::oem_ibm_platform::Handler::resetWatchDogTimer()
854 {
855 static constexpr auto watchDogService = "xyz.openbmc_project.Watchdog";
856 static constexpr auto watchDogObjectPath =
857 "/xyz/openbmc_project/watchdog/host0";
858 static constexpr auto watchDogInterface =
859 "xyz.openbmc_project.State.Watchdog";
860 static constexpr auto watchDogResetPropName = "ResetTimeRemaining";
861
862 bool wdStatus = watchDogRunning();
863 if (wdStatus == false)
864 {
865 return;
866 }
867 try
868 {
869 auto& bus = pldm::utils::DBusHandler::getBus();
870 auto resetMethod =
871 bus.new_method_call(watchDogService, watchDogObjectPath,
872 watchDogInterface, watchDogResetPropName);
873 resetMethod.append(true);
874 bus.call_noreply(resetMethod, dbusTimeout);
875 }
876 catch (const std::exception& e)
877 {
878 error("Failed to reset watchdog timer, error - {ERROR}", "ERROR", e);
879 return;
880 }
881 }
882
disableWatchDogTimer()883 void pldm::responder::oem_ibm_platform::Handler::disableWatchDogTimer()
884 {
885 setEventReceiverCnt = 0;
886 pldm::utils::DBusMapping dbusMapping{
887 "/xyz/openbmc_project/watchdog/host0",
888 "xyz.openbmc_project.State.Watchdog", "Enabled", "bool"};
889 bool wdStatus = watchDogRunning();
890
891 if (!wdStatus)
892 {
893 return;
894 }
895 try
896 {
897 pldm::utils::DBusHandler().setDbusProperty(dbusMapping, false);
898 }
899 catch (const std::exception& e)
900 {
901 error("Failed to disable watchdog timer, error - {ERROR}", "ERROR", e);
902 }
903 }
checkBMCState()904 int pldm::responder::oem_ibm_platform::Handler::checkBMCState()
905 {
906 using BMC = sdbusplus::client::xyz::openbmc_project::state::BMC<>;
907 auto bmcPath = sdbusplus::message::object_path(BMC::namespace_path::value) /
908 BMC::namespace_path::bmc;
909 try
910 {
911 pldm::utils::PropertyValue propertyValue =
912 pldm::utils::DBusHandler().getDbusPropertyVariant(
913 bmcPath.str.c_str(), "CurrentBMCState", BMC::interface);
914
915 if (std::get<std::string>(propertyValue) !=
916 "xyz.openbmc_project.State.BMC.BMCState.Ready")
917 {
918 error("GetPDR : PLDM stack is not ready for PDR exchange");
919 return PLDM_ERROR_NOT_READY;
920 }
921 }
922 catch (const std::exception& e)
923 {
924 error("Error getting the current BMC state, error - {ERROR}", "ERROR",
925 e);
926 return PLDM_ERROR;
927 }
928 return PLDM_SUCCESS;
929 }
930
931 const pldm_pdr_record*
fetchLastBMCRecord(const pldm_pdr * repo)932 pldm::responder::oem_ibm_platform::Handler::fetchLastBMCRecord(
933 const pldm_pdr* repo)
934 {
935 return pldm_pdr_find_last_in_range(repo, BMC_PDR_START_RANGE,
936 BMC_PDR_END_RANGE);
937 }
938
checkRecordHandleInRange(const uint32_t & record_handle)939 bool pldm::responder::oem_ibm_platform::Handler::checkRecordHandleInRange(
940 const uint32_t& record_handle)
941 {
942 return record_handle >= HOST_PDR_START_RANGE &&
943 record_handle <= HOST_PDR_END_RANGE;
944 }
945
processSetEventReceiver()946 void Handler::processSetEventReceiver()
947 {
948 this->setEventReceiver();
949 }
950
startStopTimer(bool value)951 void pldm::responder::oem_ibm_platform::Handler::startStopTimer(bool value)
952 {
953 if (value)
954 {
955 timer.restart(
956 std::chrono::seconds(HEARTBEAT_TIMEOUT + HEARTBEAT_TIMEOUT_DELTA));
957 }
958 else
959 {
960 timer.setEnabled(value);
961 }
962 }
963
setSurvTimer(uint8_t tid,bool value)964 void pldm::responder::oem_ibm_platform::Handler::setSurvTimer(uint8_t tid,
965 bool value)
966 {
967 if ((hostOff || hostTransitioningToOff || (tid != HYPERVISOR_TID)) &&
968 timer.isEnabled())
969 {
970 startStopTimer(false);
971 return;
972 }
973 if (value)
974 {
975 startStopTimer(value);
976 }
977 else if (timer.isEnabled())
978 {
979 info(
980 "Failed to stop surveillance timer while remote terminus status is ‘{HOST_TRANST_OFF}’ with Terminus ID ‘{TID}’ ",
981 "HOST_TRANST_OFF", hostTransitioningToOff, "TID", tid);
982 startStopTimer(value);
983 pldm::utils::reportError(
984 "xyz.openbmc_project.PLDM.Error.setSurvTimer.RecvSurveillancePingFail");
985 }
986 }
987
handleBootTypesAtPowerOn()988 void pldm::responder::oem_ibm_platform::Handler::handleBootTypesAtPowerOn()
989 {
990 PendingAttributesList biosAttrList;
991 auto bootInitiator =
992 getBiosAttrValue<std::string>("pvm_boot_initiator_current")
993 .value_or("");
994 std::string restartCause;
995 if (((bootInitiator != "HMC") || (bootInitiator != "Host")) &&
996 !bootInitiator.empty())
997 {
998 try
999 {
1000 restartCause =
1001 pldm::utils::DBusHandler().getDbusProperty<std::string>(
1002 "/xyz/openbmc_project/state/host0",
1003 HostState::property_names::restart_cause,
1004 sdbusplus::common::xyz::openbmc_project::state::Host::
1005 interface);
1006 setBootTypesBiosAttr(restartCause);
1007 }
1008 catch (const std::exception& e)
1009 {
1010 error(
1011 "Failed to set the D-bus property for the Host restart reason ERROR={ERR}",
1012 "ERR", e);
1013 }
1014 }
1015 }
1016
setBootTypesBiosAttr(const std::string & restartCause)1017 void pldm::responder::oem_ibm_platform::Handler::setBootTypesBiosAttr(
1018 const std::string& restartCause)
1019 {
1020 PendingAttributesList biosAttrList;
1021 if (restartCause ==
1022 "xyz.openbmc_project.State.Host.RestartCause.ScheduledPowerOn")
1023 {
1024 biosAttrList.emplace_back(std::make_pair(
1025 "pvm_boot_initiator", std::make_tuple(EnumAttribute, "Host")));
1026 setBiosAttr(biosAttrList);
1027 }
1028 else if (
1029 (restartCause ==
1030 "xyz.openbmc_project.State.Host.RestartCause.PowerPolicyAlwaysOn") ||
1031 (restartCause ==
1032 "xyz.openbmc_project.State.Host.RestartCause.PowerPolicyPreviousState"))
1033 {
1034 biosAttrList.emplace_back(std::make_pair(
1035 "pvm_boot_initiator", std::make_tuple(EnumAttribute, "Auto")));
1036 setBiosAttr(biosAttrList);
1037 }
1038 else if (restartCause ==
1039 "xyz.openbmc_project.State.Host.RestartCause.HostCrash")
1040 {
1041 biosAttrList.emplace_back(std::make_pair(
1042 "pvm_boot_initiator", std::make_tuple(EnumAttribute, "Auto")));
1043 biosAttrList.emplace_back(std::make_pair(
1044 "pvm_boot_type", std::make_tuple(EnumAttribute, "ReIPL")));
1045 setBiosAttr(biosAttrList);
1046 }
1047 }
1048
handleBootTypesAtChassisOff()1049 void pldm::responder::oem_ibm_platform::Handler::handleBootTypesAtChassisOff()
1050 {
1051 PendingAttributesList biosAttrList;
1052 auto bootInitiator =
1053 getBiosAttrValue<std::string>("pvm_boot_initiator").value_or("");
1054 auto bootType = getBiosAttrValue<std::string>("pvm_boot_type").value_or("");
1055 if (bootInitiator.empty() || bootType.empty())
1056 {
1057 error(
1058 "ERROR in fetching the pvm_boot_initiator and pvm_boot_type BIOS attribute values");
1059 return;
1060 }
1061 else if (bootInitiator != "Host")
1062 {
1063 biosAttrList.emplace_back(std::make_pair(
1064 "pvm_boot_initiator", std::make_tuple(EnumAttribute, "User")));
1065 biosAttrList.emplace_back(std::make_pair(
1066 "pvm_boot_type", std::make_tuple(EnumAttribute, "IPL")));
1067 setBiosAttr(biosAttrList);
1068 }
1069 }
1070
turnOffRealSAIEffecter()1071 void pldm::responder::oem_ibm_platform::Handler::turnOffRealSAIEffecter()
1072 {
1073 try
1074 {
1075 pldm::utils::DBusMapping dbusPartitionMapping{
1076 "/xyz/openbmc_project/led/groups/partition_system_attention_indicator",
1077 "xyz.openbmc_project.Led.Group", "Asserted", "bool"};
1078 pldm::utils::DBusHandler().setDbusProperty(dbusPartitionMapping, false);
1079 }
1080 catch (const std::exception& e)
1081 {
1082 error("Turn off of partition SAI effecter failed with "
1083 "error:{ERR_EXCEP}",
1084 "ERR_EXCEP", e);
1085 }
1086 try
1087 {
1088 pldm::utils::DBusMapping dbusPlatformMapping{
1089 "/xyz/openbmc_project/led/groups/platform_system_attention_indicator",
1090 "xyz.openbmc_project.Led.Group", "Asserted", "bool"};
1091 pldm::utils::DBusHandler().setDbusProperty(dbusPlatformMapping, false);
1092 }
1093 catch (const std::exception& e)
1094 {
1095 error("Turn off of platform SAI effecter failed with "
1096 "error:{ERR_EXCEP}",
1097 "ERR_EXCEP", e);
1098 }
1099 }
1100
fetchRealSAIStatus()1101 uint8_t pldm::responder::oem_ibm_platform::Handler::fetchRealSAIStatus()
1102 {
1103 try
1104 {
1105 auto isPartitionSAIOn = pldm::utils::DBusHandler().getDbusProperty<bool>(
1106 "/xyz/openbmc_project/led/groups/partition_system_attention_indicator",
1107 "Asserted", "xyz.openbmc_project.Led.Group");
1108 auto isPlatformSAIOn = pldm::utils::DBusHandler().getDbusProperty<bool>(
1109 "/xyz/openbmc_project/led/groups/platform_system_attention_indicator",
1110 "Asserted", "xyz.openbmc_project.Led.Group");
1111
1112 if (isPartitionSAIOn || isPlatformSAIOn)
1113 {
1114 return PLDM_SENSOR_WARNING;
1115 }
1116 }
1117 catch (const std::exception& e)
1118 {
1119 error("Fetching of Real SAI sensor status failed with "
1120 "error:{ERR_EXCEP}",
1121 "ERR_EXCEP", e);
1122 }
1123 return PLDM_SENSOR_NORMAL;
1124 }
1125
processSAIUpdate()1126 void pldm::responder::oem_ibm_platform::Handler::processSAIUpdate()
1127 {
1128 auto realSAIState = fetchRealSAIStatus();
1129 sendStateSensorEvent(realSAISensorId, PLDM_STATE_SENSOR_STATE, 0,
1130 uint8_t(realSAIState), uint8_t(PLDM_SENSOR_UNKNOWN));
1131 }
1132
1133 } // namespace oem_ibm_platform
1134 } // namespace responder
1135 } // namespace pldm
1136