xref: /openbmc/pldm/oem/meta/event/oem_event_manager.cpp (revision c86cd0427d889484440912722a7e5ec861673378)
1*c86cd042SSora Su #include "oem_event_manager.hpp"
2*c86cd042SSora Su 
3*c86cd042SSora Su #include <com/meta/IPMI/UnifiedSEL/event.hpp>
4*c86cd042SSora Su #include <oem/meta/utils.hpp>
5*c86cd042SSora Su #include <phosphor-logging/commit.hpp>
6*c86cd042SSora Su #include <phosphor-logging/lg2.hpp>
7*c86cd042SSora Su #include <xyz/openbmc_project/Inventory/Decorator/Slot/client.hpp>
8*c86cd042SSora Su 
9*c86cd042SSora Su #include <cstdint>
10*c86cd042SSora Su #include <iostream>
11*c86cd042SSora Su #include <sstream>
12*c86cd042SSora Su 
13*c86cd042SSora Su namespace pldm
14*c86cd042SSora Su {
15*c86cd042SSora Su namespace oem_meta
16*c86cd042SSora Su {
17*c86cd042SSora Su 
18*c86cd042SSora Su int OemEventManager::processOemMetaEvent(
19*c86cd042SSora Su     pldm_tid_t tid, const uint8_t* eventData, size_t eventDataSize) const
20*c86cd042SSora Su {
21*c86cd042SSora Su     RecordType recordType = static_cast<RecordType>(eventData[0]);
22*c86cd042SSora Su     std::string errorLog;
23*c86cd042SSora Su     switch (recordType)
24*c86cd042SSora Su     {
25*c86cd042SSora Su         case RecordType::SYSTEM_EVENT_RECORD:
26*c86cd042SSora Su         {
27*c86cd042SSora Su             handleSystemEvent(eventData, errorLog);
28*c86cd042SSora Su             break;
29*c86cd042SSora Su         }
30*c86cd042SSora Su         case RecordType::UNIFIED_BIOS_SEL:
31*c86cd042SSora Su         {
32*c86cd042SSora Su             handleUnifiedBIOSEvent(eventData, errorLog);
33*c86cd042SSora Su             break;
34*c86cd042SSora Su         }
35*c86cd042SSora Su         default:
36*c86cd042SSora Su         {
37*c86cd042SSora Su             return PLDM_ERROR;
38*c86cd042SSora Su         }
39*c86cd042SSora Su     }
40*c86cd042SSora Su 
41*c86cd042SSora Su     std::string slotNumber = getSlotNumberStringByTID(tid);
42*c86cd042SSora Su     std::string message =
43*c86cd042SSora Su         "SEL Entry: Host: " + slotNumber + ", Record: " + errorLog;
44*c86cd042SSora Su     lg2::error("{ERROR}", "ERROR", message); // Create log in journal
45*c86cd042SSora Su 
46*c86cd042SSora Su     std::string rawLog = [eventData, eventDataSize]() {
47*c86cd042SSora Su         std::stringstream stream;
48*c86cd042SSora Su         stream << std::hex << std::uppercase << std::setfill('0');
49*c86cd042SSora Su         for (int i = 0; i < static_cast<int>(eventDataSize); ++i)
50*c86cd042SSora Su         {
51*c86cd042SSora Su             stream << std::setw(2) << static_cast<int>(eventData[i]);
52*c86cd042SSora Su         }
53*c86cd042SSora Su         return stream.str();
54*c86cd042SSora Su     }();
55*c86cd042SSora Su 
56*c86cd042SSora Su     std::string source = "/xyz/openbmc_project/state/host" + slotNumber;
57*c86cd042SSora Su     {
58*c86cd042SSora Su         namespace Errors = sdbusplus::error::com::meta::ipmi::UnifiedSEL;
59*c86cd042SSora Su         lg2::commit(Errors::UnifiedSELEvent("SOURCE", source, "EVENT", errorLog,
60*c86cd042SSora Su                                             "RAW_EVENT", rawLog));
61*c86cd042SSora Su     }
62*c86cd042SSora Su 
63*c86cd042SSora Su     return 0;
64*c86cd042SSora Su }
65*c86cd042SSora Su 
66*c86cd042SSora Su int OemEventManager::handleOemEvent(
67*c86cd042SSora Su     const pldm_msg* request, size_t payloadLength, uint8_t /* formatVersion */,
68*c86cd042SSora Su     pldm_tid_t tid, size_t eventDataOffset) const
69*c86cd042SSora Su {
70*c86cd042SSora Su     auto eventData =
71*c86cd042SSora Su         reinterpret_cast<const uint8_t*>(request->payload) + eventDataOffset;
72*c86cd042SSora Su     auto eventDataSize = payloadLength - eventDataOffset;
73*c86cd042SSora Su     if (!pldm::oem_meta::checkMetaIana(tid))
74*c86cd042SSora Su     {
75*c86cd042SSora Su         lg2::error("Recieve OEM Meta event from not Meta specific device");
76*c86cd042SSora Su         return PLDM_ERROR;
77*c86cd042SSora Su     }
78*c86cd042SSora Su     if (!processOemMetaEvent(tid, eventData, eventDataSize))
79*c86cd042SSora Su     {
80*c86cd042SSora Su         return PLDM_ERROR;
81*c86cd042SSora Su     }
82*c86cd042SSora Su 
83*c86cd042SSora Su     return PLDM_SUCCESS;
84*c86cd042SSora Su }
85*c86cd042SSora Su 
86*c86cd042SSora Su void OemEventManager::handleSystemEvent(const uint8_t* eventData,
87*c86cd042SSora Su                                         std::string& errorLog) const
88*c86cd042SSora Su {
89*c86cd042SSora Su     errorLog = "Standard (0x02), ";
90*c86cd042SSora Su     switch (auto se = static_cast<SystemError>(eventData[8]); se)
91*c86cd042SSora Su     {
92*c86cd042SSora Su         case SystemError::SYSTEM_PROCESSOR_ERR:
93*c86cd042SSora Su         {
94*c86cd042SSora Su             switch (auto pe = static_cast<ProcessorError>(eventData[9]); pe)
95*c86cd042SSora Su             {
96*c86cd042SSora Su                 case ProcessorError::MACHINE_CHK_ERR:
97*c86cd042SSora Su                 {
98*c86cd042SSora Su                     errorLog += "MACHINE_CHK_ERR (" +
99*c86cd042SSora Su                                 to_hex_string(eventData[9]) + "), ";
100*c86cd042SSora Su                     errorLog += "Event Data: (" + to_hex_string(eventData[11]) +
101*c86cd042SSora Su                                 to_hex_string(eventData[12]) +
102*c86cd042SSora Su                                 to_hex_string(eventData[13]) + ") ";
103*c86cd042SSora Su 
104*c86cd042SSora Su                     switch (auto ps = static_cast<ProcessorSeverity>(
105*c86cd042SSora Su                                 eventData[11] & 0x0F);
106*c86cd042SSora Su                             ps)
107*c86cd042SSora Su                     {
108*c86cd042SSora Su                         case ProcessorSeverity::UNCORRECT_SYSTEM_FATAL_ERR:
109*c86cd042SSora Su                             errorLog += "Uncorrected System Fatal Error, ";
110*c86cd042SSora Su                             break;
111*c86cd042SSora Su                         case ProcessorSeverity::CORRECTABLE_SYSTEM_ERR:
112*c86cd042SSora Su                             errorLog += "Correctable System Error, ";
113*c86cd042SSora Su                             break;
114*c86cd042SSora Su                         default:
115*c86cd042SSora Su                             errorLog += "Unknown Error, ";
116*c86cd042SSora Su                             break;
117*c86cd042SSora Su                     }
118*c86cd042SSora Su 
119*c86cd042SSora Su                     if (eventData[12] == 0x1D)
120*c86cd042SSora Su                     {
121*c86cd042SSora Su                         errorLog += "Bank Number " +
122*c86cd042SSora Su                                     std::to_string(eventData[12]) +
123*c86cd042SSora Su                                     " (SMU/MPDMA), ";
124*c86cd042SSora Su                     }
125*c86cd042SSora Su 
126*c86cd042SSora Su                     errorLog += "CPU " + std::to_string(eventData[13] >> 5) +
127*c86cd042SSora Su                                 ", CCD " + std::to_string(eventData[13] & 0x1F);
128*c86cd042SSora Su                     break;
129*c86cd042SSora Su                 }
130*c86cd042SSora Su             }
131*c86cd042SSora Su             break;
132*c86cd042SSora Su         }
133*c86cd042SSora Su         case SystemError::SYSTEM_POST_ERR:
134*c86cd042SSora Su         {
135*c86cd042SSora Su             errorLog += "POST_ERROR:";
136*c86cd042SSora Su             if ((eventData[11] & 0x0F) == 0x0)
137*c86cd042SSora Su                 errorLog += ", System Firmware Error";
138*c86cd042SSora Su 
139*c86cd042SSora Su             if (((eventData[11] >> 6) & 0x03) == 0x2)
140*c86cd042SSora Su             {
141*c86cd042SSora Su                 errorLog += ", OEM Post Code 0x" +
142*c86cd042SSora Su                             to_hex_string(eventData[13]) +
143*c86cd042SSora Su                             to_hex_string(eventData[12]);
144*c86cd042SSora Su             }
145*c86cd042SSora Su 
146*c86cd042SSora Su             if (((eventData[13] << 8) | eventData[12]) == 0xD9)
147*c86cd042SSora Su             {
148*c86cd042SSora Su                 errorLog +=
149*c86cd042SSora Su                     ", Error loading Boot Option (Load image returned error)";
150*c86cd042SSora Su             }
151*c86cd042SSora Su             break;
152*c86cd042SSora Su         }
153*c86cd042SSora Su         case SystemError::SYSTEM_CXL_ERR:
154*c86cd042SSora Su         {
155*c86cd042SSora Su             errorLog += "CXL 1.1 Error, ";
156*c86cd042SSora Su             switch (auto ce = static_cast<CxlError>(eventData[9]); ce)
157*c86cd042SSora Su             {
158*c86cd042SSora Su                 case CxlError::PROTOCOL_ERR:
159*c86cd042SSora Su                 {
160*c86cd042SSora Su                     errorLog += ", Protocol Error(0x1), ";
161*c86cd042SSora Su                     break;
162*c86cd042SSora Su                 }
163*c86cd042SSora Su                 case CxlError::COMPONENT_ERR:
164*c86cd042SSora Su                 {
165*c86cd042SSora Su                     errorLog += ", Component Error(0x2), ";
166*c86cd042SSora Su                     break;
167*c86cd042SSora Su                 }
168*c86cd042SSora Su             }
169*c86cd042SSora Su 
170*c86cd042SSora Su             errorLog += "Severity: ";
171*c86cd042SSora Su             errorLog +=
172*c86cd042SSora Su                 (eventData[11] & 0x01) ? "Uncorrectable" : "Correctable";
173*c86cd042SSora Su             errorLog += ", Detected By: ";
174*c86cd042SSora Su             errorLog += (eventData[11] & 0x02) ? "CXL 1.1 Host Downstream Port"
175*c86cd042SSora Su                                                : "CXL 1.1 Device";
176*c86cd042SSora Su 
177*c86cd042SSora Su             uint8_t errorType = (eventData[11] >> 2) & 0x03;
178*c86cd042SSora Su 
179*c86cd042SSora Su             errorLog += ", Error Type: " + std::string(cxlError[errorType]) +
180*c86cd042SSora Su                         ", Bus " + to_hex_string(eventData[12]) + "/Dev " +
181*c86cd042SSora Su                         to_hex_string(eventData[13] >> 3) + "/Fun " +
182*c86cd042SSora Su                         to_hex_string(eventData[13] & 0x7);
183*c86cd042SSora Su             break;
184*c86cd042SSora Su         }
185*c86cd042SSora Su         case SystemError::SYSTEM_CXL_ERR_2_0:
186*c86cd042SSora Su         {
187*c86cd042SSora Su             errorLog += "CXL 2.0 Error, ";
188*c86cd042SSora Su             switch (auto ce = static_cast<CxlError2>(eventData[9]); ce)
189*c86cd042SSora Su             {
190*c86cd042SSora Su                 case CxlError2::PROTOCOL_ERR:
191*c86cd042SSora Su                 {
192*c86cd042SSora Su                     errorLog += ", Protocol Error(0x1), ";
193*c86cd042SSora Su                     break;
194*c86cd042SSora Su                 }
195*c86cd042SSora Su                 case CxlError2::COMPONENT_ERR:
196*c86cd042SSora Su                 {
197*c86cd042SSora Su                     errorLog += ", Component Error(0x2), ";
198*c86cd042SSora Su                     break;
199*c86cd042SSora Su                 }
200*c86cd042SSora Su             }
201*c86cd042SSora Su 
202*c86cd042SSora Su             errorLog += "Severity: ";
203*c86cd042SSora Su             errorLog +=
204*c86cd042SSora Su                 (eventData[11] & 0x01) ? "Uncorrectable" : "Correctable";
205*c86cd042SSora Su             // root port only
206*c86cd042SSora Su             errorLog += ", Detected By: CXL Root Port";
207*c86cd042SSora Su 
208*c86cd042SSora Su             uint8_t errorType = (eventData[11] >> 2) & 0x03;
209*c86cd042SSora Su 
210*c86cd042SSora Su             errorLog += ", Error Type: " + std::string(cxlError[errorType]) +
211*c86cd042SSora Su                         ", Bus " + to_hex_string(eventData[12]) + "/Dev " +
212*c86cd042SSora Su                         to_hex_string(eventData[13] >> 3) + "/Fun " +
213*c86cd042SSora Su                         to_hex_string(eventData[13] & 0x7);
214*c86cd042SSora Su             break;
215*c86cd042SSora Su         }
216*c86cd042SSora Su         default:
217*c86cd042SSora Su         { // Not supported
218*c86cd042SSora Su             errorLog +=
219*c86cd042SSora Su                 "Raw: " + to_hex_string(eventData[1]) +
220*c86cd042SSora Su                 to_hex_string(eventData[2]) + to_hex_string(eventData[3]) +
221*c86cd042SSora Su                 to_hex_string(eventData[4]) + to_hex_string(eventData[5]) +
222*c86cd042SSora Su                 to_hex_string(eventData[6]) + to_hex_string(eventData[7]) +
223*c86cd042SSora Su                 to_hex_string(eventData[8]) + to_hex_string(eventData[9]) +
224*c86cd042SSora Su                 to_hex_string(eventData[10]) + to_hex_string(eventData[11]) +
225*c86cd042SSora Su                 to_hex_string(eventData[12]) + to_hex_string(eventData[13]);
226*c86cd042SSora Su         }
227*c86cd042SSora Su     }
228*c86cd042SSora Su }
229*c86cd042SSora Su 
230*c86cd042SSora Su void OemEventManager::handleUnifiedBIOSEvent(const uint8_t* eventData,
231*c86cd042SSora Su                                              std::string& errorLog) const
232*c86cd042SSora Su {
233*c86cd042SSora Su     errorLog = "Meta Unified SEL (0xFB), ";
234*c86cd042SSora Su 
235*c86cd042SSora Su     DimmInfo dimmInfo = {
236*c86cd042SSora Su         static_cast<uint8_t>((eventData[6] >> 4) & 0x03), // Sled
237*c86cd042SSora Su         static_cast<uint8_t>(eventData[6] & 0x0F),        // Socket
238*c86cd042SSora Su         static_cast<uint8_t>(eventData[7]),               // Channel
239*c86cd042SSora Su         static_cast<uint8_t>(eventData[8])                // Slot
240*c86cd042SSora Su     };
241*c86cd042SSora Su 
242*c86cd042SSora Su     uint8_t generalInfo = eventData[1];
243*c86cd042SSora Su     UnifiedError errorType = static_cast<UnifiedError>(generalInfo & 0xF);
244*c86cd042SSora Su     switch (errorType)
245*c86cd042SSora Su     {
246*c86cd042SSora Su         case UnifiedError::UNIFIED_PCIE_ERR:
247*c86cd042SSora Su         {
248*c86cd042SSora Su             uint8_t plat = (generalInfo & 0x10) >> 4;
249*c86cd042SSora Su             if (plat == 0)
250*c86cd042SSora Su             { // x86
251*c86cd042SSora Su                 errorLog +=
252*c86cd042SSora Su                     "GeneralInfo: x86/PCIeErr(0x" + to_hex_string(generalInfo) +
253*c86cd042SSora Su                     "), Bus " + to_hex_string(eventData[9]) + "/Dev " +
254*c86cd042SSora Su                     to_hex_string(eventData[8] >> 3) + "/Fun " +
255*c86cd042SSora Su                     to_hex_string(eventData[8] & 0x7) + ", ErrID2: 0x" +
256*c86cd042SSora Su                     to_hex_string(eventData[12]) + ", ErrID1: 0x" +
257*c86cd042SSora Su                     to_hex_string(eventData[13]);
258*c86cd042SSora Su             }
259*c86cd042SSora Su             else
260*c86cd042SSora Su             {
261*c86cd042SSora Su                 errorLog +=
262*c86cd042SSora Su                     "GeneralInfo: ARM/PCIeErr(0x" + to_hex_string(generalInfo) +
263*c86cd042SSora Su                     "), Aux. Info: 0x" +
264*c86cd042SSora Su                     to_hex_string((eventData[7] << 8) | eventData[6], 4) +
265*c86cd042SSora Su                     ", Bus " + to_hex_string(eventData[9]) + "/Dev " +
266*c86cd042SSora Su                     to_hex_string(eventData[8] >> 3) + "/Fun " +
267*c86cd042SSora Su                     to_hex_string(eventData[8] & 0x7) + ", ErrID2: 0x" +
268*c86cd042SSora Su                     to_hex_string(eventData[12]) + ", ErrID1: 0x" +
269*c86cd042SSora Su                     to_hex_string(eventData[13]);
270*c86cd042SSora Su             }
271*c86cd042SSora Su             break;
272*c86cd042SSora Su         }
273*c86cd042SSora Su         case UnifiedError::UNIFIED_MEM_ERR:
274*c86cd042SSora Su         {
275*c86cd042SSora Su             handleMemoryError(eventData, errorLog, dimmInfo, generalInfo);
276*c86cd042SSora Su             break;
277*c86cd042SSora Su         }
278*c86cd042SSora Su         case UnifiedError::UNIFIED_UPI_ERR:
279*c86cd042SSora Su         {
280*c86cd042SSora Su             UpiError eventType = static_cast<UpiError>(eventData[10] & 0xF);
281*c86cd042SSora Su             uint8_t estrIdx =
282*c86cd042SSora Su                 (static_cast<uint8_t>(eventType) < upiError.size())
283*c86cd042SSora Su                     ? static_cast<uint8_t>(eventType)
284*c86cd042SSora Su                     : (upiError.size() - 1);
285*c86cd042SSora Su 
286*c86cd042SSora Su             switch (eventType)
287*c86cd042SSora Su             {
288*c86cd042SSora Su                 case UpiError::UPI_INIT_ERR:
289*c86cd042SSora Su                 {
290*c86cd042SSora Su                     errorLog +=
291*c86cd042SSora Su                         "GeneralInfo: UPIErr(0x" + to_hex_string(generalInfo) +
292*c86cd042SSora Su                         "), UPI Port Location: Sled " +
293*c86cd042SSora Su                         std::to_string(dimmInfo.sled) + "/Socket " +
294*c86cd042SSora Su                         std::to_string(dimmInfo.socket) + ", Port " +
295*c86cd042SSora Su                         std::to_string(eventData[4] & 0xF) +
296*c86cd042SSora Su                         ", UPI Failure Event: " + upiError[estrIdx] +
297*c86cd042SSora Su                         ", Major Code: 0x" + to_hex_string(eventData[8]) +
298*c86cd042SSora Su                         ", Minor Code: 0x" + to_hex_string(eventData[9]);
299*c86cd042SSora Su                     break;
300*c86cd042SSora Su                 }
301*c86cd042SSora Su                 default:
302*c86cd042SSora Su                 {
303*c86cd042SSora Su                     errorLog +=
304*c86cd042SSora Su                         "GeneralInfo: UPIErr(0x" + to_hex_string(generalInfo) +
305*c86cd042SSora Su                         "), UPI Port Location: Sled " +
306*c86cd042SSora Su                         std::to_string(dimmInfo.sled) + "/Socket " +
307*c86cd042SSora Su                         std::to_string(dimmInfo.socket) + ", Port " +
308*c86cd042SSora Su                         std::to_string(eventData[4] & 0xF) +
309*c86cd042SSora Su                         ", UPI Failure Event: " + upiError[estrIdx];
310*c86cd042SSora Su                     break;
311*c86cd042SSora Su                 }
312*c86cd042SSora Su             }
313*c86cd042SSora Su             break;
314*c86cd042SSora Su         }
315*c86cd042SSora Su         case UnifiedError::UNIFIED_IIO_ERR:
316*c86cd042SSora Su         {
317*c86cd042SSora Su             uint8_t stack = eventData[7];
318*c86cd042SSora Su             uint8_t selErrorType = eventData[11];
319*c86cd042SSora Su             uint8_t selErrorSeverity = eventData[12];
320*c86cd042SSora Su             uint8_t selErrorId = eventData[13];
321*c86cd042SSora Su 
322*c86cd042SSora Su             errorLog +=
323*c86cd042SSora Su                 "GeneralInfo: IIOErr(0x" + to_hex_string(generalInfo) +
324*c86cd042SSora Su                 "), IIO Port Location: Sled " + std::to_string(dimmInfo.sled) +
325*c86cd042SSora Su                 "/Socket " + std::to_string(dimmInfo.socket) + ", Stack 0x" +
326*c86cd042SSora Su                 to_hex_string(stack) + ", Error Type: 0x" +
327*c86cd042SSora Su                 to_hex_string(selErrorType) + ", Error Severity: 0x" +
328*c86cd042SSora Su                 to_hex_string(selErrorSeverity) + ", Error ID: 0x" +
329*c86cd042SSora Su                 to_hex_string(selErrorId);
330*c86cd042SSora Su             break;
331*c86cd042SSora Su         }
332*c86cd042SSora Su         case UnifiedError::UNIFIED_MCA_ERR:
333*c86cd042SSora Su         {
334*c86cd042SSora Su             uint8_t mcaSeverity = ((eventData[6] >> 4) & 0x07);
335*c86cd042SSora Su             uint8_t cpuNumber = (eventData[7] >> 5) & 0x07;
336*c86cd042SSora Su             uint8_t coreNumber = eventData[7] & 0x1F;
337*c86cd042SSora Su             uint8_t machineCheckBankNumber = eventData[8];
338*c86cd042SSora Su             uint32_t errorInfo = (static_cast<uint32_t>(eventData[9]) << 16) |
339*c86cd042SSora Su                                  (static_cast<uint32_t>(eventData[10]) << 8) |
340*c86cd042SSora Su                                  static_cast<uint32_t>(eventData[11]);
341*c86cd042SSora Su             uint8_t errorCode = eventData[12];
342*c86cd042SSora Su             uint8_t errorStatus = eventData[13];
343*c86cd042SSora Su 
344*c86cd042SSora Su             errorLog +=
345*c86cd042SSora Su                 "GeneralInfo: MCAErr(0x" + to_hex_string(generalInfo) +
346*c86cd042SSora Su                 "), MCA Severity: " + errorSeverityDetail[mcaSeverity] +
347*c86cd042SSora Su                 ", CPU Number: " + std::to_string(cpuNumber) +
348*c86cd042SSora Su                 ", Core Number: " + std::to_string(coreNumber) +
349*c86cd042SSora Su                 ", Machine Check Bank: " +
350*c86cd042SSora Su                 machineCheckBank[machineCheckBankNumber] + ", Error Info: 0x" +
351*c86cd042SSora Su                 to_hex_string(errorInfo, 6) + ", Error Code: 0x" +
352*c86cd042SSora Su                 to_hex_string(errorCode) + ", Error Status: 0x" +
353*c86cd042SSora Su                 to_hex_string(errorStatus);
354*c86cd042SSora Su             break;
355*c86cd042SSora Su         }
356*c86cd042SSora Su         case UnifiedError::UNIFIED_MCA_ERR_EXT:
357*c86cd042SSora Su         {
358*c86cd042SSora Su             uint8_t mcaSeverity = ((eventData[6] >> 4) & 0x07);
359*c86cd042SSora Su             uint8_t cpuNumber = (eventData[7] >> 5) & 0x07;
360*c86cd042SSora Su             uint8_t coreNumber = eventData[7] & 0x1F;
361*c86cd042SSora Su             uint8_t machineCheckBankNumber = eventData[8];
362*c86cd042SSora Su             uint16_t errorCode = (eventData[9] << 8) | eventData[10];
363*c86cd042SSora Su 
364*c86cd042SSora Su             errorLog +=
365*c86cd042SSora Su                 "GeneralInfo: MCAErrExt(0x" + to_hex_string(generalInfo) +
366*c86cd042SSora Su                 "), MCA Severity: " + errorSeverityDetail[mcaSeverity] +
367*c86cd042SSora Su                 ", CPU Number: " + std::to_string(cpuNumber) +
368*c86cd042SSora Su                 ", Core Number: " + std::to_string(coreNumber) +
369*c86cd042SSora Su                 ", Machine Check Bank: " +
370*c86cd042SSora Su                 machineCheckBank[machineCheckBankNumber] + ", Error Code: 0x" +
371*c86cd042SSora Su                 to_hex_string(errorCode, 4);
372*c86cd042SSora Su             break;
373*c86cd042SSora Su         }
374*c86cd042SSora Su         case UnifiedError::UNIFIED_RP_PIO_1st:
375*c86cd042SSora Su         case UnifiedError::UNIFIED_RP_PIO_2nd:
376*c86cd042SSora Su         {
377*c86cd042SSora Su             auto offset =
378*c86cd042SSora Su                 static_cast<uint8_t>(errorType) -
379*c86cd042SSora Su                 static_cast<uint8_t>(UnifiedError::UNIFIED_RP_PIO_1st);
380*c86cd042SSora Su             errorLog +=
381*c86cd042SSora Su                 "GeneralInfo: RP_PIOEvent(0x" + to_hex_string(generalInfo) +
382*c86cd042SSora Su                 "), RP_PIO Header Log" + std::to_string(1 + offset * 2) +
383*c86cd042SSora Su                 ": 0x" + to_hex_string(eventData[9]) +
384*c86cd042SSora Su                 to_hex_string(eventData[8]) + to_hex_string(eventData[7]) +
385*c86cd042SSora Su                 to_hex_string(eventData[6]) + ", RP_PIO Header Log" +
386*c86cd042SSora Su                 std::to_string(2 + offset * 2) + ": 0x" +
387*c86cd042SSora Su                 to_hex_string(eventData[13]) + to_hex_string(eventData[12]) +
388*c86cd042SSora Su                 to_hex_string(eventData[11]) + to_hex_string(eventData[10]);
389*c86cd042SSora Su             break;
390*c86cd042SSora Su         }
391*c86cd042SSora Su         case UnifiedError::UNIFIED_POST_EVENT:
392*c86cd042SSora Su         {
393*c86cd042SSora Su             handleSystemPostEvent(eventData, errorLog, generalInfo);
394*c86cd042SSora Su             break;
395*c86cd042SSora Su         }
396*c86cd042SSora Su         case UnifiedError::UNIFIED_PCIE_EVENT:
397*c86cd042SSora Su         {
398*c86cd042SSora Su             PcieEvent eventType = static_cast<PcieEvent>(eventData[6] & 0xF);
399*c86cd042SSora Su             uint8_t estrIdx =
400*c86cd042SSora Su                 (static_cast<uint8_t>(eventType) < pcieEvent.size())
401*c86cd042SSora Su                     ? static_cast<uint8_t>(eventType)
402*c86cd042SSora Su                     : (pcieEvent.size() - 1);
403*c86cd042SSora Su             switch (eventType)
404*c86cd042SSora Su             {
405*c86cd042SSora Su                 case PcieEvent::PCIE_DPC:
406*c86cd042SSora Su                 {
407*c86cd042SSora Su                     errorLog +=
408*c86cd042SSora Su                         "GeneralInfo: PCIeEvent(0x" +
409*c86cd042SSora Su                         to_hex_string(generalInfo) +
410*c86cd042SSora Su                         "), PCIe Failure Event: " + pcieEvent[estrIdx] +
411*c86cd042SSora Su                         ", Status: 0x" +
412*c86cd042SSora Su                         to_hex_string((eventData[9] << 8) | eventData[8], 4) +
413*c86cd042SSora Su                         ", Source ID: 0x" +
414*c86cd042SSora Su                         to_hex_string((eventData[11] << 8) | eventData[10], 4);
415*c86cd042SSora Su                     break;
416*c86cd042SSora Su                 }
417*c86cd042SSora Su                 default:
418*c86cd042SSora Su                 {
419*c86cd042SSora Su                     errorLog += "GeneralInfo: PCIeEvent(0x" +
420*c86cd042SSora Su                                 to_hex_string(generalInfo) +
421*c86cd042SSora Su                                 "), PCIe Failure Event: " + pcieEvent[estrIdx];
422*c86cd042SSora Su                     break;
423*c86cd042SSora Su                 }
424*c86cd042SSora Su             }
425*c86cd042SSora Su             break;
426*c86cd042SSora Su         }
427*c86cd042SSora Su         case UnifiedError::UNIFIED_MEM_EVENT:
428*c86cd042SSora Su         {
429*c86cd042SSora Su             // get dimm location data string.
430*c86cd042SSora Su             std::string dimmLocation, dimm;
431*c86cd042SSora Su             getCommonDimmLocation(dimmInfo, dimmLocation, dimm);
432*c86cd042SSora Su 
433*c86cd042SSora Su             // Event-Type Bit[3:0]
434*c86cd042SSora Su             MemoryEvent eventType =
435*c86cd042SSora Su                 static_cast<MemoryEvent>(eventData[10] & 0x0F);
436*c86cd042SSora Su             switch (eventType)
437*c86cd042SSora Su             {
438*c86cd042SSora Su                 case MemoryEvent::MEM_PPR:
439*c86cd042SSora Su                 {
440*c86cd042SSora Su                     errorLog += "GeneralInfo: MemEvent(0x" +
441*c86cd042SSora Su                                 to_hex_string(generalInfo) + "), " +
442*c86cd042SSora Su                                 dimmLocation + ", DIMM Failure Event: " +
443*c86cd042SSora Su                                 memoryPprRepairTime[eventData[11] >> 2 & 0x03] +
444*c86cd042SSora Su                                 ", " + memoryPprEvent[eventData[11] & 0x03];
445*c86cd042SSora Su                     break;
446*c86cd042SSora Su                 }
447*c86cd042SSora Su                 case MemoryEvent::MEM_ADDDC:
448*c86cd042SSora Su                 {
449*c86cd042SSora Su                     uint8_t estrIdx = eventData[12] & 0x03;
450*c86cd042SSora Su                     if (estrIdx >= memoryAdddcEvent.size())
451*c86cd042SSora Su                         estrIdx = memoryAdddcEvent.size() - 1;
452*c86cd042SSora Su                     errorLog += "GeneralInfo: MemEvent(0x" +
453*c86cd042SSora Su                                 to_hex_string(generalInfo) + "), " +
454*c86cd042SSora Su                                 dimmLocation + ", DIMM Failure Event: " +
455*c86cd042SSora Su                                 memoryEvent[static_cast<uint8_t>(eventType)] +
456*c86cd042SSora Su                                 " " + memoryAdddcEvent[estrIdx];
457*c86cd042SSora Su                     break;
458*c86cd042SSora Su                 }
459*c86cd042SSora Su                 case MemoryEvent::MEM_NO_DIMM:
460*c86cd042SSora Su                 {
461*c86cd042SSora Su                     errorLog += "GeneralInfo: MemEvent(0x" +
462*c86cd042SSora Su                                 to_hex_string(generalInfo) +
463*c86cd042SSora Su                                 "), DIMM Failure Event: " +
464*c86cd042SSora Su                                 memoryEvent[static_cast<uint8_t>(eventType)];
465*c86cd042SSora Su                     break;
466*c86cd042SSora Su                 }
467*c86cd042SSora Su                 case MemoryEvent::MEM_CXL_POST_PPR:
468*c86cd042SSora Su                 {
469*c86cd042SSora Su                     errorLog +=
470*c86cd042SSora Su                         "GeneralInfo: MemEvent(0x" +
471*c86cd042SSora Su                         to_hex_string(generalInfo) + "), Bus " +
472*c86cd042SSora Su                         to_hex_string(eventData[12]) + "/Dev " +
473*c86cd042SSora Su                         to_hex_string(eventData[13] >> 3) + "/Fun " +
474*c86cd042SSora Su                         to_hex_string(eventData[13] & 0x7) +
475*c86cd042SSora Su                         ", DIMM Failure Event: " +
476*c86cd042SSora Su                         memoryEvent[static_cast<uint8_t>(eventType)] + ", " +
477*c86cd042SSora Su                         memoryCXLPostPprEvent[eventData[11] >> 7 & 0x1] + ", " +
478*c86cd042SSora Su                         getDimmDeviceName(eventData, 12) +
479*c86cd042SSora Su                         memoryCxlEvent[eventData[11] & 0x3];
480*c86cd042SSora Su                     break;
481*c86cd042SSora Su                 }
482*c86cd042SSora Su                 default:
483*c86cd042SSora Su                 {
484*c86cd042SSora Su                     uint8_t estrIdx =
485*c86cd042SSora Su                         (static_cast<uint8_t>(eventType) < memoryEvent.size())
486*c86cd042SSora Su                             ? static_cast<uint8_t>(eventType)
487*c86cd042SSora Su                             : (memoryEvent.size() - 1);
488*c86cd042SSora Su                     errorLog += "GeneralInfo: MemEvent(0x" +
489*c86cd042SSora Su                                 to_hex_string(generalInfo) + "), " +
490*c86cd042SSora Su                                 dimmLocation +
491*c86cd042SSora Su                                 ", DIMM Failure Event: " + memoryEvent[estrIdx];
492*c86cd042SSora Su                     break;
493*c86cd042SSora Su                 }
494*c86cd042SSora Su             }
495*c86cd042SSora Su             break;
496*c86cd042SSora Su         }
497*c86cd042SSora Su         case UnifiedError::UNIFIED_UPI_EVENT:
498*c86cd042SSora Su         {
499*c86cd042SSora Su             uint8_t eventType = eventData[10] & 0x0F;
500*c86cd042SSora Su             uint8_t estrIdx = (eventType < upiEvent.size())
501*c86cd042SSora Su                                   ? eventType
502*c86cd042SSora Su                                   : (upiEvent.size() - 1);
503*c86cd042SSora Su             errorLog +=
504*c86cd042SSora Su                 "GeneralInfo: UPIEvent(0x" + to_hex_string(generalInfo) +
505*c86cd042SSora Su                 "), UPI Port Location: Sled " + std::to_string(dimmInfo.sled) +
506*c86cd042SSora Su                 "/Socket " + std::to_string(dimmInfo.socket) + ", Port " +
507*c86cd042SSora Su                 std::to_string(eventData[7] & 0xF) +
508*c86cd042SSora Su                 ", UPI Failure Event: " + upiEvent[estrIdx];
509*c86cd042SSora Su             break;
510*c86cd042SSora Su         }
511*c86cd042SSora Su         case UnifiedError::UNIFIED_BOOT_GUARD:
512*c86cd042SSora Su         {
513*c86cd042SSora Su             errorLog +=
514*c86cd042SSora Su                 "GeneralInfo: Boot Guard ACM Failure Events(0x" +
515*c86cd042SSora Su                 to_hex_string(generalInfo) + "), Error Class(0x" +
516*c86cd042SSora Su                 to_hex_string(eventData[10]) + "), Major Error Code(0x" +
517*c86cd042SSora Su                 to_hex_string(eventData[11]) + "), Minor Error Code(0x" +
518*c86cd042SSora Su                 to_hex_string(eventData[12]) + ")";
519*c86cd042SSora Su             break;
520*c86cd042SSora Su         }
521*c86cd042SSora Su         case UnifiedError::UNIFIED_PPR_EVENT:
522*c86cd042SSora Su         {
523*c86cd042SSora Su             uint8_t eventType = eventData[6] & 0x0F;
524*c86cd042SSora Su             errorLog +=
525*c86cd042SSora Su                 "GeneralInfo: PPR Events(0x" + to_hex_string(generalInfo) +
526*c86cd042SSora Su                 "), " + pprEvent[eventType] + ". DIMM Info: (" +
527*c86cd042SSora Su                 to_hex_string(eventData[7]) + to_hex_string(eventData[8]) +
528*c86cd042SSora Su                 to_hex_string(eventData[9]) + to_hex_string(eventData[10]) +
529*c86cd042SSora Su                 to_hex_string(eventData[11]) + to_hex_string(eventData[12]) +
530*c86cd042SSora Su                 to_hex_string(eventData[13]) + ")";
531*c86cd042SSora Su             break;
532*c86cd042SSora Su         }
533*c86cd042SSora Su         case UnifiedError::UNIFIED_CXL_MEM_ERR:
534*c86cd042SSora Su         {
535*c86cd042SSora Su             uint8_t eventType = eventData[10] & 0xF;
536*c86cd042SSora Su 
537*c86cd042SSora Su             errorLog += "GeneralInfo: CXL Memory Error(0x" +
538*c86cd042SSora Su                         to_hex_string(generalInfo) + "), Bus " +
539*c86cd042SSora Su                         to_hex_string(eventData[7]) + "/Dev " +
540*c86cd042SSora Su                         to_hex_string(eventData[8] >> 3) + "/Fun " +
541*c86cd042SSora Su                         to_hex_string(eventData[8] & 0x7) +
542*c86cd042SSora Su                         ", DIMM Failure Event: " + memoryError[eventType] +
543*c86cd042SSora Su                         ", " + getDimmDeviceName(eventData, 7) +
544*c86cd042SSora Su                         memoryCxlEvent[eventData[11] & 0x7];
545*c86cd042SSora Su             break;
546*c86cd042SSora Su         }
547*c86cd042SSora Su         default:
548*c86cd042SSora Su         {
549*c86cd042SSora Su             errorLog +=
550*c86cd042SSora Su                 "Undefined Error Type(0x" +
551*c86cd042SSora Su                 to_hex_string(static_cast<uint8_t>(errorType)) +
552*c86cd042SSora Su                 "), Raw: " + to_hex_string(eventData[1]) +
553*c86cd042SSora Su                 to_hex_string(eventData[2]) + to_hex_string(eventData[3]) +
554*c86cd042SSora Su                 to_hex_string(eventData[4]) + to_hex_string(eventData[5]) +
555*c86cd042SSora Su                 to_hex_string(eventData[6]) + to_hex_string(eventData[7]) +
556*c86cd042SSora Su                 to_hex_string(eventData[8]) + to_hex_string(eventData[9]) +
557*c86cd042SSora Su                 to_hex_string(eventData[10]) + to_hex_string(eventData[11]) +
558*c86cd042SSora Su                 to_hex_string(eventData[12]) + to_hex_string(eventData[13]);
559*c86cd042SSora Su             break;
560*c86cd042SSora Su         }
561*c86cd042SSora Su     }
562*c86cd042SSora Su }
563*c86cd042SSora Su 
564*c86cd042SSora Su void OemEventManager::handleMemoryError(
565*c86cd042SSora Su     const uint8_t* eventData, std::string& errorLog, const DimmInfo& dimmInfo,
566*c86cd042SSora Su     uint8_t generalInfo) const
567*c86cd042SSora Su {
568*c86cd042SSora Su     std::string dimmLocation, dimm;
569*c86cd042SSora Su     getCommonDimmLocation(dimmInfo, dimmLocation, dimm);
570*c86cd042SSora Su     uint8_t plat = (eventData[10] & 0x80) >> 7;
571*c86cd042SSora Su     MemoryError eventType = static_cast<MemoryError>(eventData[10] & 0xF);
572*c86cd042SSora Su     switch (eventType)
573*c86cd042SSora Su     {
574*c86cd042SSora Su         case MemoryError::MEMORY_TRAINING_ERR:
575*c86cd042SSora Su         case MemoryError::MEMORY_PMIC_ERR:
576*c86cd042SSora Su         {
577*c86cd042SSora Su             if (plat == 0)
578*c86cd042SSora Su             { // Intel
579*c86cd042SSora Su                 errorLog += "GeneralInfo: MEMORY_ECC_ERR(0x" +
580*c86cd042SSora Su                             to_hex_string(generalInfo) + "), " + dimmLocation +
581*c86cd042SSora Su                             ", DIMM Failure Event: " +
582*c86cd042SSora Su                             memoryError[static_cast<uint8_t>(eventType)] +
583*c86cd042SSora Su                             ", Major Code: 0x" + to_hex_string(eventData[11]) +
584*c86cd042SSora Su                             ", Minor Code: 0x" + to_hex_string(eventData[12]);
585*c86cd042SSora Su             }
586*c86cd042SSora Su             else
587*c86cd042SSora Su             { // AMD
588*c86cd042SSora Su                 errorLog +=
589*c86cd042SSora Su                     "GeneralInfo: MEMORY_ECC_ERR(0x" +
590*c86cd042SSora Su                     to_hex_string(generalInfo) + "), " + dimmLocation +
591*c86cd042SSora Su                     ", DIMM Failure Event: " +
592*c86cd042SSora Su                     memoryError[static_cast<uint8_t>(eventType)] +
593*c86cd042SSora Su                     ", Major Code: 0x" + to_hex_string(eventData[11]) +
594*c86cd042SSora Su                     ", Minor Code: 0x" +
595*c86cd042SSora Su                     to_hex_string((eventData[13] << 8) | eventData[12], 4);
596*c86cd042SSora Su             }
597*c86cd042SSora Su             break;
598*c86cd042SSora Su         }
599*c86cd042SSora Su         default:
600*c86cd042SSora Su             convertToDimmString(dimmInfo.socket, dimmInfo.channel,
601*c86cd042SSora Su                                 dimmInfo.slot, dimm);
602*c86cd042SSora Su             uint8_t estrIdx =
603*c86cd042SSora Su                 (static_cast<uint8_t>(eventType) < memoryError.size())
604*c86cd042SSora Su                     ? static_cast<uint8_t>(eventType)
605*c86cd042SSora Su                     : (memoryError.size() - 1);
606*c86cd042SSora Su             errorLog += "GeneralInfo: MEMORY_ECC_ERR(0x" +
607*c86cd042SSora Su                         to_hex_string(generalInfo) + "), " + dimmLocation +
608*c86cd042SSora Su                         ", DIMM Failure Event: " + memoryError[estrIdx];
609*c86cd042SSora Su             break;
610*c86cd042SSora Su     }
611*c86cd042SSora Su }
612*c86cd042SSora Su 
613*c86cd042SSora Su void OemEventManager::handleSystemPostEvent(
614*c86cd042SSora Su     const uint8_t* eventData, std::string& errorLog, uint8_t generalInfo) const
615*c86cd042SSora Su {
616*c86cd042SSora Su     uint8_t certEventIdx = (eventData[10] < certEvent.size())
617*c86cd042SSora Su                                ? eventData[10]
618*c86cd042SSora Su                                : (certEvent.size() - 1);
619*c86cd042SSora Su     uint8_t failType = eventData[11] & 0xF;
620*c86cd042SSora Su     uint8_t errCode = eventData[12];
621*c86cd042SSora Su     PostError eventType = static_cast<PostError>(eventData[6] & 0xF);
622*c86cd042SSora Su     uint8_t estrIdx = (static_cast<uint8_t>(eventType) < postError.size())
623*c86cd042SSora Su                           ? static_cast<uint8_t>(eventType)
624*c86cd042SSora Su                           : (postError.size() - 1);
625*c86cd042SSora Su 
626*c86cd042SSora Su     switch (eventType)
627*c86cd042SSora Su     {
628*c86cd042SSora Su         case PostError::POST_PXE_BOOT_FAIL:
629*c86cd042SSora Su         case PostError::POST_HTTP_BOOT_FAIL:
630*c86cd042SSora Su         {
631*c86cd042SSora Su             std::string tempLog;
632*c86cd042SSora Su             if (failType == 4 || failType == 6)
633*c86cd042SSora Su             {
634*c86cd042SSora Su                 tempLog = "IPv" + std::to_string(failType) + " fail";
635*c86cd042SSora Su             }
636*c86cd042SSora Su             else
637*c86cd042SSora Su             {
638*c86cd042SSora Su                 tempLog = "0x" + to_hex_string(eventData[11]);
639*c86cd042SSora Su             }
640*c86cd042SSora Su             errorLog += "GeneralInfo: POST(0x" + to_hex_string(generalInfo) +
641*c86cd042SSora Su                         "), POST Failure Event: " + postError[estrIdx] +
642*c86cd042SSora Su                         ", Fail Type: " + tempLog + ", Error Code: 0x" +
643*c86cd042SSora Su                         to_hex_string(errCode);
644*c86cd042SSora Su             break;
645*c86cd042SSora Su         }
646*c86cd042SSora Su         case PostError::POST_GET_CERT_FAIL:
647*c86cd042SSora Su         {
648*c86cd042SSora Su             errorLog += "GeneralInfo: POST(0x" + to_hex_string(generalInfo) +
649*c86cd042SSora Su                         "), POST Failure Event: " + postError[estrIdx] +
650*c86cd042SSora Su                         ", Failure Detail: " + certEvent[certEventIdx];
651*c86cd042SSora Su             break;
652*c86cd042SSora Su         }
653*c86cd042SSora Su         case PostError::POST_AMD_ABL_FAIL:
654*c86cd042SSora Su         {
655*c86cd042SSora Su             uint16_t ablErrCode = (eventData[13] << 8) | eventData[12];
656*c86cd042SSora Su             errorLog += "GeneralInfo: POST(0x" + to_hex_string(generalInfo) +
657*c86cd042SSora Su                         "), POST Failure Event: " + postError[estrIdx] +
658*c86cd042SSora Su                         ", ABL Error Code: 0x" + to_hex_string(ablErrCode, 4);
659*c86cd042SSora Su             break;
660*c86cd042SSora Su         }
661*c86cd042SSora Su         case PostError::POST_BOOT_DRIVE_FAIL:
662*c86cd042SSora Su         case PostError::POST_DATA_DRIVE_FAIL:
663*c86cd042SSora Su         case PostError::POST_CXL_NOT_READY:
664*c86cd042SSora Su         case PostError::POST_CXL_ERR_RECORD_CLEARED_BY_BIOS:
665*c86cd042SSora Su         {
666*c86cd042SSora Su             errorLog += "GeneralInfo: POST(0x" + to_hex_string(generalInfo) +
667*c86cd042SSora Su                         "), Bus " + to_hex_string(eventData[7]) + "/Dev " +
668*c86cd042SSora Su                         to_hex_string(eventData[8] >> 3) + "/Fun " +
669*c86cd042SSora Su                         to_hex_string(eventData[8] & 0x7) +
670*c86cd042SSora Su                         ", POST Failure Event: " + postError[estrIdx];
671*c86cd042SSora Su             break;
672*c86cd042SSora Su         }
673*c86cd042SSora Su         default:
674*c86cd042SSora Su         {
675*c86cd042SSora Su             errorLog += "GeneralInfo: POST(0x" + to_hex_string(generalInfo) +
676*c86cd042SSora Su                         "), POST Failure Event: " + postError[estrIdx];
677*c86cd042SSora Su             break;
678*c86cd042SSora Su         }
679*c86cd042SSora Su     }
680*c86cd042SSora Su }
681*c86cd042SSora Su 
682*c86cd042SSora Su } // namespace oem_meta
683*c86cd042SSora Su } // namespace pldm
684