blob: b58bf8228a540b6957acb22935f3e08c24a09b0a [file] [log] [blame]
Lawrence Tang7f21db62022-07-06 11:09:39 +01001/**
2 * Describes functions for converting memory error CPER sections from binary and JSON format
3 * into an intermediate format.
Ed Tanousfedd4572024-07-12 13:56:00 -07004 *
Lawrence Tang7f21db62022-07-06 11:09:39 +01005 * Author: Lawrence.Tang@arm.com
6 **/
7#include <stdio.h>
Lawrence Tang5202bbb2022-08-12 14:54:36 +01008#include <json.h>
Thu Nguyene42fb482024-10-15 14:43:11 +00009#include <libcper/Cper.h>
10#include <libcper/cper-utils.h>
11#include <libcper/sections/cper-section-memory.h>
Lawrence Tang7f21db62022-07-06 11:09:39 +010012
13//Converts a single memory error CPER section into JSON IR.
Ed Tanous12dbd4f2025-03-08 19:05:01 -080014json_object *cper_section_platform_memory_to_ir(const UINT8 *section,
15 UINT32 size)
Lawrence Tang7f21db62022-07-06 11:09:39 +010016{
Ed Tanous12dbd4f2025-03-08 19:05:01 -080017 if (size < sizeof(EFI_PLATFORM_MEMORY_ERROR_DATA)) {
18 return NULL;
19 }
20
Lawrence Tange407b4c2022-07-21 13:54:01 +010021 EFI_PLATFORM_MEMORY_ERROR_DATA *memory_error =
22 (EFI_PLATFORM_MEMORY_ERROR_DATA *)section;
23 json_object *section_ir = json_object_new_object();
Lawrence Tang7f21db62022-07-06 11:09:39 +010024
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -080025 ValidationTypes ui64Type = { UINT_64T,
26 .value.ui64 = memory_error->ValidFields };
Lawrence Tang7f21db62022-07-06 11:09:39 +010027
Lawrence Tange407b4c2022-07-21 13:54:01 +010028 //Error status.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -080029 if (isvalid_prop_to_ir(&ui64Type, 0)) {
30 json_object *error_status = cper_generic_error_status_to_ir(
31 &memory_error->ErrorStatus);
32 json_object_object_add(section_ir, "errorStatus", error_status);
33 }
Lawrence Tanga0865e32022-07-06 11:59:52 +010034
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -080035 //Bank
Lawrence Tange407b4c2022-07-21 13:54:01 +010036 json_object *bank = json_object_new_object();
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -080037 if (isvalid_prop_to_ir(&ui64Type, 6)) {
Lawrence Tange407b4c2022-07-21 13:54:01 +010038 //Entire bank address mode.
39 json_object_object_add(
40 bank, "value",
41 json_object_new_uint64(memory_error->Bank));
42 } else {
43 //Address/group address mode.
44 json_object_object_add(
45 bank, "address",
46 json_object_new_uint64(memory_error->Bank & 0xFF));
47 json_object_object_add(
48 bank, "group",
49 json_object_new_uint64(memory_error->Bank >> 8));
50 }
51 json_object_object_add(section_ir, "bank", bank);
Lawrence Tanga0865e32022-07-06 11:59:52 +010052
Lawrence Tange407b4c2022-07-21 13:54:01 +010053 //Memory error type.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -080054 if (isvalid_prop_to_ir(&ui64Type, 14)) {
55 json_object *memory_error_type = integer_to_readable_pair(
56 memory_error->ErrorType, 16, MEMORY_ERROR_TYPES_KEYS,
57 MEMORY_ERROR_TYPES_VALUES, "Unknown (Reserved)");
58 json_object_object_add(section_ir, "memoryErrorType",
59 memory_error_type);
60 }
Lawrence Tanga0865e32022-07-06 11:59:52 +010061
Lawrence Tange407b4c2022-07-21 13:54:01 +010062 //"Extended" row/column indication field + misc.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -080063 // Review this
64 if (isvalid_prop_to_ir(&ui64Type, 18)) {
65 json_object *extended = json_object_new_object();
66 json_object_object_add(
67 extended, "rowBit16",
68 json_object_new_boolean(memory_error->Extended & 0x1));
69 json_object_object_add(
70 extended, "rowBit17",
71 json_object_new_boolean((memory_error->Extended >> 1) &
72 0x1));
73 if (isvalid_prop_to_ir(&ui64Type, 21)) {
74 json_object_object_add(
75 extended, "chipIdentification",
76 json_object_new_int(memory_error->Extended >>
77 5));
78 }
79 json_object_object_add(section_ir, "extended", extended);
80
81 //bit 16 and 17 are valid only if extended is valid
82 if (isvalid_prop_to_ir(&ui64Type, 16)) {
83 json_object_object_add(
84 section_ir, "cardSmbiosHandle",
85 json_object_new_uint64(
86 memory_error->CardHandle));
87 }
88 if (isvalid_prop_to_ir(&ui64Type, 17)) {
89 json_object_object_add(
90 section_ir, "moduleSmbiosHandle",
91 json_object_new_uint64(
92 memory_error->ModuleHandle));
93 }
94 }
Lawrence Tanga0865e32022-07-06 11:59:52 +010095
Lawrence Tange407b4c2022-07-21 13:54:01 +010096 //Miscellaneous numeric fields.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -080097 if (isvalid_prop_to_ir(&ui64Type, 1)) {
98 json_object_object_add(
99 section_ir, "physicalAddress",
100 json_object_new_uint64(memory_error->PhysicalAddress));
Aushim Nagarkatticc367012024-12-05 18:17:27 -0800101
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800102 char hexstring_buf[EFI_UINT64_HEX_STRING_LEN];
103 snprintf(hexstring_buf, EFI_UINT64_HEX_STRING_LEN, "0x%016llX",
104 memory_error->PhysicalAddress);
105 json_object_object_add(section_ir, "physicalAddressHex",
106 json_object_new_string(hexstring_buf));
107 }
108 if (isvalid_prop_to_ir(&ui64Type, 2)) {
109 json_object_object_add(
110 section_ir, "physicalAddressMask",
111 json_object_new_uint64(
112 memory_error->PhysicalAddressMask));
113 }
114 if (isvalid_prop_to_ir(&ui64Type, 3)) {
115 json_object_object_add(
116 section_ir, "node",
117 json_object_new_uint64(memory_error->Node));
118 }
119 if (isvalid_prop_to_ir(&ui64Type, 4)) {
120 json_object_object_add(
121 section_ir, "card",
122 json_object_new_uint64(memory_error->Card));
123 }
124 if (isvalid_prop_to_ir(&ui64Type, 5)) {
125 json_object_object_add(
126 section_ir, "moduleRank",
127 json_object_new_uint64(memory_error->ModuleRank));
128 }
129 if (isvalid_prop_to_ir(&ui64Type, 7)) {
130 json_object_object_add(
131 section_ir, "device",
132 json_object_new_uint64(memory_error->Device));
133 }
134 if (isvalid_prop_to_ir(&ui64Type, 8)) {
135 json_object_object_add(
136 section_ir, "row",
137 json_object_new_uint64(memory_error->Row));
138 }
139 if (isvalid_prop_to_ir(&ui64Type, 9)) {
140 json_object_object_add(
141 section_ir, "column",
142 json_object_new_uint64(memory_error->Column));
143 }
144 if (isvalid_prop_to_ir(&ui64Type, 10)) {
145 json_object_object_add(
146 section_ir, "bitPosition",
147 json_object_new_uint64(memory_error->BitPosition));
148 }
149 if (isvalid_prop_to_ir(&ui64Type, 11)) {
150 json_object_object_add(
151 section_ir, "requestorID",
152 json_object_new_uint64(memory_error->RequestorId));
153 }
154 if (isvalid_prop_to_ir(&ui64Type, 12)) {
155 json_object_object_add(
156 section_ir, "responderID",
157 json_object_new_uint64(memory_error->ResponderId));
158 }
159 if (isvalid_prop_to_ir(&ui64Type, 13)) {
160 json_object_object_add(
161 section_ir, "targetID",
162 json_object_new_uint64(memory_error->TargetId));
163 }
164 if (isvalid_prop_to_ir(&ui64Type, 15)) {
165 json_object_object_add(
166 section_ir, "rankNumber",
167 json_object_new_uint64(memory_error->RankNum));
168 }
Lawrence Tang54da4412022-07-06 13:14:58 +0100169
Lawrence Tange407b4c2022-07-21 13:54:01 +0100170 return section_ir;
Lawrence Tanga0865e32022-07-06 11:59:52 +0100171}
172
173//Converts a single memory error 2 CPER section into JSON IR.
Ed Tanous12dbd4f2025-03-08 19:05:01 -0800174json_object *cper_section_platform_memory2_to_ir(const UINT8 *section,
175 UINT32 size)
Lawrence Tanga0865e32022-07-06 11:59:52 +0100176{
Ed Tanous12dbd4f2025-03-08 19:05:01 -0800177 if (size < sizeof(EFI_PLATFORM_MEMORY2_ERROR_DATA)) {
178 return NULL;
179 }
180
Lawrence Tange407b4c2022-07-21 13:54:01 +0100181 EFI_PLATFORM_MEMORY2_ERROR_DATA *memory_error =
182 (EFI_PLATFORM_MEMORY2_ERROR_DATA *)section;
183 json_object *section_ir = json_object_new_object();
Lawrence Tanga0865e32022-07-06 11:59:52 +0100184
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800185 ValidationTypes ui64Type = { UINT_64T,
186 .value.ui64 = memory_error->ValidFields };
Lawrence Tanga0865e32022-07-06 11:59:52 +0100187
Lawrence Tange407b4c2022-07-21 13:54:01 +0100188 //Error status.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800189 if (isvalid_prop_to_ir(&ui64Type, 0)) {
190 json_object *error_status = cper_generic_error_status_to_ir(
191 &memory_error->ErrorStatus);
192 json_object_object_add(section_ir, "errorStatus", error_status);
193 }
Lawrence Tang54da4412022-07-06 13:14:58 +0100194
Lawrence Tange407b4c2022-07-21 13:54:01 +0100195 //Bank.
196 json_object *bank = json_object_new_object();
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800197 if (isvalid_prop_to_ir(&ui64Type, 6)) {
Lawrence Tange407b4c2022-07-21 13:54:01 +0100198 //Entire bank address mode.
199 json_object_object_add(
200 bank, "value",
201 json_object_new_uint64(memory_error->Bank));
202 } else {
203 //Address/group address mode.
204 json_object_object_add(
205 bank, "address",
206 json_object_new_uint64(memory_error->Bank & 0xFF));
207 json_object_object_add(
208 bank, "group",
209 json_object_new_uint64(memory_error->Bank >> 8));
210 }
211 json_object_object_add(section_ir, "bank", bank);
Lawrence Tang54da4412022-07-06 13:14:58 +0100212
Lawrence Tange407b4c2022-07-21 13:54:01 +0100213 //Memory error type.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800214 if (isvalid_prop_to_ir(&ui64Type, 13)) {
215 json_object *memory_error_type = integer_to_readable_pair(
216 memory_error->MemErrorType, 16, MEMORY_ERROR_TYPES_KEYS,
217 MEMORY_ERROR_TYPES_VALUES, "Unknown (Reserved)");
218 json_object_object_add(section_ir, "memoryErrorType",
219 memory_error_type);
220 }
Lawrence Tang54da4412022-07-06 13:14:58 +0100221
Lawrence Tange407b4c2022-07-21 13:54:01 +0100222 //Status.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800223 if (isvalid_prop_to_ir(&ui64Type, 14)) {
224 json_object *status = json_object_new_object();
225 json_object_object_add(
226 status, "value",
227 json_object_new_int(memory_error->Status));
228 json_object_object_add(
229 status, "state",
230 json_object_new_string((memory_error->Status & 0x1) ==
231 0 ?
232 "Corrected" :
233 "Uncorrected"));
234 json_object_object_add(section_ir, "status", status);
235 }
Lawrence Tang54da4412022-07-06 13:14:58 +0100236
Lawrence Tange407b4c2022-07-21 13:54:01 +0100237 //Miscellaneous numeric fields.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800238 if (isvalid_prop_to_ir(&ui64Type, 0)) {
239 json_object_object_add(
240 section_ir, "physicalAddress",
241 json_object_new_uint64(memory_error->PhysicalAddress));
242 }
Aushim Nagarkatticc367012024-12-05 18:17:27 -0800243
244 char hexstring_buf[EFI_UINT64_HEX_STRING_LEN];
245 snprintf(hexstring_buf, EFI_UINT64_HEX_STRING_LEN, "0x%016llX",
246 memory_error->PhysicalAddress);
247 json_object_object_add(section_ir, "physicalAddressHex",
248 json_object_new_string(hexstring_buf));
249
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800250 if (isvalid_prop_to_ir(&ui64Type, 2)) {
251 json_object_object_add(
252 section_ir, "physicalAddressMask",
253 json_object_new_uint64(
254 memory_error->PhysicalAddressMask));
255 }
256 if (isvalid_prop_to_ir(&ui64Type, 3)) {
257 json_object_object_add(
258 section_ir, "node",
259 json_object_new_uint64(memory_error->Node));
260 }
261 if (isvalid_prop_to_ir(&ui64Type, 4)) {
262 json_object_object_add(
263 section_ir, "card",
264 json_object_new_uint64(memory_error->Card));
265 }
266 if (isvalid_prop_to_ir(&ui64Type, 5)) {
267 json_object_object_add(
268 section_ir, "module",
269 json_object_new_uint64(memory_error->Module));
270 }
271 if (isvalid_prop_to_ir(&ui64Type, 7)) {
272 json_object_object_add(
273 section_ir, "device",
274 json_object_new_uint64(memory_error->Device));
275 }
276 if (isvalid_prop_to_ir(&ui64Type, 8)) {
277 json_object_object_add(
278 section_ir, "row",
279 json_object_new_uint64(memory_error->Row));
280 }
281 if (isvalid_prop_to_ir(&ui64Type, 9)) {
282 json_object_object_add(
283 section_ir, "column",
284 json_object_new_uint64(memory_error->Column));
285 }
286 if (isvalid_prop_to_ir(&ui64Type, 10)) {
287 json_object_object_add(
288 section_ir, "rank",
289 json_object_new_uint64(memory_error->Rank));
290 }
291 if (isvalid_prop_to_ir(&ui64Type, 11)) {
292 json_object_object_add(
293 section_ir, "bitPosition",
294 json_object_new_uint64(memory_error->BitPosition));
295 }
296 if (isvalid_prop_to_ir(&ui64Type, 12)) {
297 json_object_object_add(
298 section_ir, "chipID",
299 json_object_new_uint64(memory_error->ChipId));
300 }
301 if (isvalid_prop_to_ir(&ui64Type, 15)) {
302 json_object_object_add(
303 section_ir, "requestorID",
304 json_object_new_uint64(memory_error->RequestorId));
305 }
306 if (isvalid_prop_to_ir(&ui64Type, 16)) {
307 json_object_object_add(
308 section_ir, "responderID",
309 json_object_new_uint64(memory_error->ResponderId));
310 }
311 if (isvalid_prop_to_ir(&ui64Type, 17)) {
312 json_object_object_add(
313 section_ir, "targetID",
314 json_object_new_uint64(memory_error->TargetId));
315 }
316 if (isvalid_prop_to_ir(&ui64Type, 18)) {
317 json_object_object_add(
318 section_ir, "cardSmbiosHandle",
319 json_object_new_uint64(memory_error->CardHandle));
320 }
321 if (isvalid_prop_to_ir(&ui64Type, 19)) {
322 json_object_object_add(
323 section_ir, "moduleSmbiosHandle",
324 json_object_new_uint64(memory_error->ModuleHandle));
325 }
Lawrence Tange407b4c2022-07-21 13:54:01 +0100326
327 return section_ir;
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100328}
329
330//Converts a single Memory Error IR section into CPER binary, outputting to the provided stream.
Lawrence Tange407b4c2022-07-21 13:54:01 +0100331void ir_section_memory_to_cper(json_object *section, FILE *out)
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100332{
Lawrence Tange407b4c2022-07-21 13:54:01 +0100333 EFI_PLATFORM_MEMORY_ERROR_DATA *section_cper =
334 (EFI_PLATFORM_MEMORY_ERROR_DATA *)calloc(
335 1, sizeof(EFI_PLATFORM_MEMORY_ERROR_DATA));
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100336
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800337 ValidationTypes ui64Type = { UINT_64T, .value.ui64 = 0 };
338 struct json_object *obj = NULL;
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100339
Lawrence Tange407b4c2022-07-21 13:54:01 +0100340 //Error status.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800341 if (json_object_object_get_ex(section, "errorStatus", &obj)) {
342 ir_generic_error_status_to_cper(obj,
343 &section_cper->ErrorStatus);
344 add_to_valid_bitfield(&ui64Type, 0);
345 }
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100346
Lawrence Tange407b4c2022-07-21 13:54:01 +0100347 //Bank.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800348 if (json_object_object_get_ex(section, "bank", &obj)) {
349 json_object *bank = obj;
350 if (json_object_object_get_ex(bank, "value", &obj)) {
351 //Bank just uses simple address.
352 section_cper->Bank =
353 (UINT16)json_object_get_uint64(obj);
354 add_to_valid_bitfield(&ui64Type, 6);
355 } else {
356 //Bank uses address/group style address.
357 UINT16 address = (UINT8)json_object_get_uint64(
358 json_object_object_get(bank, "address"));
359 UINT16 group = (UINT8)json_object_get_uint64(
360 json_object_object_get(bank, "group"));
361 section_cper->Bank = address + (group << 8);
362 add_to_valid_bitfield(&ui64Type, 19);
363 add_to_valid_bitfield(&ui64Type, 20);
364 }
Lawrence Tange407b4c2022-07-21 13:54:01 +0100365 }
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100366
Lawrence Tange407b4c2022-07-21 13:54:01 +0100367 //"Extended" field.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800368 if (json_object_object_get_ex(section, "extended", &obj)) {
369 json_object *extended = obj;
370 section_cper->Extended = 0;
371 section_cper->Extended |= json_object_get_boolean(
372 json_object_object_get(extended, "rowBit16"));
373 section_cper->Extended |=
374 json_object_get_boolean(
375 json_object_object_get(extended, "rowBit17"))
376 << 1;
377 if (json_object_object_get_ex(extended, "chipIdentification",
378 &obj)) {
379 section_cper->Extended |= json_object_get_int(obj) << 5;
380 add_to_valid_bitfield(&ui64Type, 21);
381 }
382 add_to_valid_bitfield(&ui64Type, 18);
383 }
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100384
Lawrence Tange407b4c2022-07-21 13:54:01 +0100385 //Miscellaneous value fields.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800386 if (json_object_object_get_ex(section, "memoryErrorType", &obj)) {
387 section_cper->ErrorType = (UINT8)readable_pair_to_integer(obj);
388 add_to_valid_bitfield(&ui64Type, 14);
389 }
390 if (json_object_object_get_ex(section, "physicalAddress", &obj)) {
391 section_cper->PhysicalAddress = json_object_get_uint64(obj);
392 add_to_valid_bitfield(&ui64Type, 1);
393 }
394 if (json_object_object_get_ex(section, "physicalAddressMask", &obj)) {
395 section_cper->PhysicalAddressMask = json_object_get_uint64(obj);
396 add_to_valid_bitfield(&ui64Type, 2);
397 }
398 if (json_object_object_get_ex(section, "node", &obj)) {
399 section_cper->Node = (UINT16)json_object_get_uint64(obj);
400 add_to_valid_bitfield(&ui64Type, 3);
401 }
402 if (json_object_object_get_ex(section, "card", &obj)) {
403 section_cper->Card = (UINT16)json_object_get_uint64(obj);
404 add_to_valid_bitfield(&ui64Type, 4);
405 }
406 if (json_object_object_get_ex(section, "moduleRank", &obj)) {
407 section_cper->ModuleRank = (UINT16)json_object_get_uint64(obj);
408 add_to_valid_bitfield(&ui64Type, 5);
409 }
410 if (json_object_object_get_ex(section, "device", &obj)) {
411 section_cper->Device = (UINT16)json_object_get_uint64(obj);
412 add_to_valid_bitfield(&ui64Type, 7);
413 }
414 if (json_object_object_get_ex(section, "row", &obj)) {
415 section_cper->Row = (UINT16)json_object_get_uint64(obj);
416 add_to_valid_bitfield(&ui64Type, 8);
417 }
418 if (json_object_object_get_ex(section, "column", &obj)) {
419 section_cper->Column = (UINT16)json_object_get_uint64(obj);
420 add_to_valid_bitfield(&ui64Type, 9);
421 }
422 if (json_object_object_get_ex(section, "bitPosition", &obj)) {
423 section_cper->BitPosition = (UINT16)json_object_get_uint64(obj);
424 add_to_valid_bitfield(&ui64Type, 10);
425 }
426 if (json_object_object_get_ex(section, "requestorID", &obj)) {
427 section_cper->RequestorId = json_object_get_uint64(obj);
428 add_to_valid_bitfield(&ui64Type, 11);
429 }
430 if (json_object_object_get_ex(section, "responderID", &obj)) {
431 section_cper->ResponderId = json_object_get_uint64(obj);
432 add_to_valid_bitfield(&ui64Type, 12);
433 }
434 if (json_object_object_get_ex(section, "targetID", &obj)) {
435 section_cper->TargetId = json_object_get_uint64(obj);
436 add_to_valid_bitfield(&ui64Type, 13);
437 }
438 if (json_object_object_get_ex(section, "rankNumber", &obj)) {
439 section_cper->RankNum = (UINT16)json_object_get_uint64(
440 json_object_object_get(section, "rankNumber"));
441 add_to_valid_bitfield(&ui64Type, 15);
442 }
443 if (json_object_object_get_ex(section, "cardSmbiosHandle", &obj)) {
444 section_cper->CardHandle = (UINT16)json_object_get_uint64(obj);
445 add_to_valid_bitfield(&ui64Type, 16);
446 }
447 if (json_object_object_get_ex(section, "moduleSmbiosHandle", &obj)) {
448 section_cper->ModuleHandle =
449 (UINT16)json_object_get_uint64(obj);
450 add_to_valid_bitfield(&ui64Type, 17);
451 }
452 section_cper->ValidFields = ui64Type.value.ui64;
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100453
Lawrence Tange407b4c2022-07-21 13:54:01 +0100454 //Write to stream, free up resources.
455 fwrite(section_cper, sizeof(EFI_PLATFORM_MEMORY_ERROR_DATA), 1, out);
456 fflush(out);
457 free(section_cper);
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100458}
459
460//Converts a single Memory Error 2 IR section into CPER binary, outputting to the provided stream.
Lawrence Tange407b4c2022-07-21 13:54:01 +0100461void ir_section_memory2_to_cper(json_object *section, FILE *out)
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100462{
Lawrence Tange407b4c2022-07-21 13:54:01 +0100463 EFI_PLATFORM_MEMORY2_ERROR_DATA *section_cper =
464 (EFI_PLATFORM_MEMORY2_ERROR_DATA *)calloc(
465 1, sizeof(EFI_PLATFORM_MEMORY2_ERROR_DATA));
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100466
Lawrence Tange407b4c2022-07-21 13:54:01 +0100467 //Validation bits.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800468 ValidationTypes ui64Type = { UINT_64T, .value.ui64 = 0 };
469 struct json_object *obj = NULL;
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100470
Lawrence Tange407b4c2022-07-21 13:54:01 +0100471 //Error status.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800472 if (json_object_object_get_ex(section, "errorStatus", &obj)) {
473 ir_generic_error_status_to_cper(obj,
474 &section_cper->ErrorStatus);
475 add_to_valid_bitfield(&ui64Type, 0);
476 }
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100477
Lawrence Tange407b4c2022-07-21 13:54:01 +0100478 //Bank.
479 json_object *bank = json_object_object_get(section, "bank");
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800480 if (json_object_object_get_ex(bank, "value", &obj)) {
Lawrence Tange407b4c2022-07-21 13:54:01 +0100481 //Bank just uses simple address.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800482 section_cper->Bank = (UINT16)json_object_get_uint64(obj);
483 add_to_valid_bitfield(&ui64Type, 6);
Lawrence Tange407b4c2022-07-21 13:54:01 +0100484 } else {
485 //Bank uses address/group style address.
486 UINT16 address = (UINT8)json_object_get_uint64(
487 json_object_object_get(bank, "address"));
488 UINT16 group = (UINT8)json_object_get_uint64(
489 json_object_object_get(bank, "group"));
490 section_cper->Bank = address + (group << 8);
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800491 add_to_valid_bitfield(&ui64Type, 20);
492 add_to_valid_bitfield(&ui64Type, 21);
Lawrence Tange407b4c2022-07-21 13:54:01 +0100493 }
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100494
Lawrence Tange407b4c2022-07-21 13:54:01 +0100495 //Miscellaneous value fields.
Aushim Nagarkattiae8f6d92025-01-29 17:34:44 -0800496 if (json_object_object_get_ex(section, "memoryErrorType", &obj)) {
497 section_cper->MemErrorType = readable_pair_to_integer(obj);
498 add_to_valid_bitfield(&ui64Type, 13);
499 }
500 if (json_object_object_get_ex(section, "status", &obj)) {
501 section_cper->Status = (UINT8)readable_pair_to_integer(obj);
502 add_to_valid_bitfield(&ui64Type, 14);
503 }
504 if (json_object_object_get_ex(section, "physicalAddress", &obj)) {
505 section_cper->PhysicalAddress = json_object_get_uint64(obj);
506 add_to_valid_bitfield(&ui64Type, 1);
507 }
508 if (json_object_object_get_ex(section, "physicalAddressMask", &obj)) {
509 section_cper->PhysicalAddressMask = json_object_get_uint64(obj);
510 add_to_valid_bitfield(&ui64Type, 2);
511 }
512 if (json_object_object_get_ex(section, "node", &obj)) {
513 section_cper->Node = (UINT16)json_object_get_uint64(obj);
514 add_to_valid_bitfield(&ui64Type, 3);
515 }
516 if (json_object_object_get_ex(section, "card", &obj)) {
517 section_cper->Card = (UINT16)json_object_get_uint64(obj);
518 add_to_valid_bitfield(&ui64Type, 4);
519 }
520 if (json_object_object_get_ex(section, "module", &obj)) {
521 section_cper->Module = (UINT32)json_object_get_uint64(obj);
522 add_to_valid_bitfield(&ui64Type, 5);
523 }
524 if (json_object_object_get_ex(section, "device", &obj)) {
525 section_cper->Device = (UINT32)json_object_get_uint64(obj);
526 add_to_valid_bitfield(&ui64Type, 7);
527 }
528 if (json_object_object_get_ex(section, "row", &obj)) {
529 section_cper->Row = (UINT32)json_object_get_uint64(obj);
530 add_to_valid_bitfield(&ui64Type, 8);
531 }
532 if (json_object_object_get_ex(section, "column", &obj)) {
533 section_cper->Column = (UINT32)json_object_get_uint64(obj);
534 add_to_valid_bitfield(&ui64Type, 9);
535 }
536 if (json_object_object_get_ex(section, "rank", &obj)) {
537 section_cper->Rank = (UINT32)json_object_get_uint64(obj);
538 add_to_valid_bitfield(&ui64Type, 10);
539 }
540 if (json_object_object_get_ex(section, "bitPosition", &obj)) {
541 section_cper->BitPosition = (UINT32)json_object_get_uint64(obj);
542 add_to_valid_bitfield(&ui64Type, 11);
543 }
544 if (json_object_object_get_ex(section, "chipID", &obj)) {
545 section_cper->ChipId = (UINT8)json_object_get_uint64(obj);
546 add_to_valid_bitfield(&ui64Type, 12);
547 }
548 if (json_object_object_get_ex(section, "requestorID", &obj)) {
549 section_cper->RequestorId = json_object_get_uint64(obj);
550 add_to_valid_bitfield(&ui64Type, 15);
551 }
552 if (json_object_object_get_ex(section, "responderID", &obj)) {
553 section_cper->ResponderId = json_object_get_uint64(obj);
554 add_to_valid_bitfield(&ui64Type, 16);
555 }
556 if (json_object_object_get_ex(section, "targetID", &obj)) {
557 section_cper->TargetId = json_object_get_uint64(obj);
558 add_to_valid_bitfield(&ui64Type, 17);
559 }
560 if (json_object_object_get_ex(section, "cardSmbiosHandle", &obj)) {
561 section_cper->CardHandle = (UINT32)json_object_get_uint64(obj);
562 add_to_valid_bitfield(&ui64Type, 18);
563 }
564 if (json_object_object_get_ex(section, "moduleSmbiosHandle", &obj)) {
565 section_cper->ModuleHandle =
566 (UINT32)json_object_get_uint64(obj);
567 add_to_valid_bitfield(&ui64Type, 19);
568 }
569
570 section_cper->ValidFields = ui64Type.value.ui64;
Lawrence Tang3b7f45b2022-07-14 14:14:30 +0100571
Lawrence Tange407b4c2022-07-21 13:54:01 +0100572 //Write to stream, free up resources.
573 fwrite(section_cper, sizeof(EFI_PLATFORM_MEMORY2_ERROR_DATA), 1, out);
574 fflush(out);
575 free(section_cper);
John Chungf8fc7052024-05-03 20:05:29 +0800576}