blob: 350d5d3c00948593d0f68f8a4e3f3b7c39f7b359 [file] [log] [blame]
Francois Toguo15cbc3b2021-01-26 10:27:49 -08001/* SPDX-License-Identifier: GPL-2.0-or-later */
2
3#include <acpi/acpi.h>
4#include <acpi/acpigen.h>
5#include <arch/bert_storage.h>
6#include <console/console.h>
7#include <intelblocks/acpi.h>
8#include <intelblocks/crashlog.h>
9
Felix Heldfba479262021-05-28 16:11:43 +020010static bool boot_error_src_present(void)
11{
Felix Heldfba479262021-05-28 16:11:43 +020012 if (!discover_crashlog()) {
13 printk(BIOS_SPEW, "Crashlog discovery result: crashlog not found\n");
14 return false;
15 }
16
17 collect_pmc_and_cpu_crashlog_from_srams();
18
19 /* Discovery tables sizes can be larger than the actual valid collected data */
20 u32 crashlog_size = cl_get_total_data_size();
21
22 return (crashlog_size > 0);
23}
Francois Toguo15cbc3b2021-01-26 10:27:49 -080024
Jonathan Zhang01acc032022-10-26 17:53:25 -070025static enum cb_err record_crashlog_into_bert(void **region, size_t *length)
Francois Toguo15cbc3b2021-01-26 10:27:49 -080026{
27 acpi_generic_error_status_t *status = NULL;
28 size_t cpu_record_size, pmc_record_size;
Francois Toguo Fotsoc1751462021-05-27 01:10:16 -070029 size_t gesb_header_size;
Francois Toguo15cbc3b2021-01-26 10:27:49 -080030 void *cl_data = NULL;
31
Felix Heldfba479262021-05-28 16:11:43 +020032 if (!boot_error_src_present()) {
33 return CB_ERR;
34 }
35
Francois Toguo15cbc3b2021-01-26 10:27:49 -080036 if (!cl_get_total_data_size()) {
Julius Wernere9665952022-01-21 17:06:20 -080037 printk(BIOS_ERR, "No crashlog record present\n");
Felix Held29405482021-05-28 16:01:57 +020038 return CB_ERR;
Francois Toguo15cbc3b2021-01-26 10:27:49 -080039 }
40
41 status = bert_new_event(&CPER_SEC_FW_ERR_REC_REF_GUID);
Francois Toguo Fotsoc1751462021-05-27 01:10:16 -070042 gesb_header_size = sizeof(*status);
43
Francois Toguo15cbc3b2021-01-26 10:27:49 -080044 if (!status) {
Julius Wernere9665952022-01-21 17:06:20 -080045 printk(BIOS_ERR, "unable to allocate GSB\n");
Felix Held29405482021-05-28 16:01:57 +020046 return CB_ERR;
Francois Toguo15cbc3b2021-01-26 10:27:49 -080047 }
48
49 if (cl_get_total_data_size() > bert_storage_remaining()) {
Julius Wernere9665952022-01-21 17:06:20 -080050 printk(BIOS_ERR, "Crashlog entry would exceed "
Francois Toguo15cbc3b2021-01-26 10:27:49 -080051 "available region\n");
Felix Held29405482021-05-28 16:01:57 +020052 return CB_ERR;
Francois Toguo15cbc3b2021-01-26 10:27:49 -080053 }
54
55 cpu_record_size = cl_get_cpu_record_size();
56 if (cpu_record_size) {
57 cl_data = new_cper_fw_error_crashlog(status, cpu_record_size);
58 if (!cl_data) {
Pratikkumar Prajapatif5a07b02023-06-18 10:27:44 -070059 printk(BIOS_ERR, "Crashlog CPU entry(size 0x%zx) "
Francois Toguo15cbc3b2021-01-26 10:27:49 -080060 "would exceed available region\n",
61 cpu_record_size);
Felix Held29405482021-05-28 16:01:57 +020062 return CB_ERR;
Francois Toguo15cbc3b2021-01-26 10:27:49 -080063 }
Pratikkumar Prajapatif5a07b02023-06-18 10:27:44 -070064 printk(BIOS_DEBUG, "cl_data %p, cpu_record_size 0x%zx\n",
Francois Toguo15cbc3b2021-01-26 10:27:49 -080065 cl_data, cpu_record_size);
66 cl_fill_cpu_records(cl_data);
67 }
68
69 pmc_record_size = cl_get_pmc_record_size();
70 if (pmc_record_size) {
Pratikkumar Prajapatid4330e72023-05-30 10:38:23 -070071 /* Allocate new FW ERR structure in case PMC crashlog is present */
72 if (pmc_record_size && !bert_append_fw_err(status)) {
Julius Wernere9665952022-01-21 17:06:20 -080073 printk(BIOS_ERR, "Crashlog PMC entry would "
Francois Toguo15cbc3b2021-01-26 10:27:49 -080074 "exceed available region\n");
Felix Held29405482021-05-28 16:01:57 +020075 return CB_ERR;
Francois Toguo15cbc3b2021-01-26 10:27:49 -080076 }
77
78 cl_data = new_cper_fw_error_crashlog(status, pmc_record_size);
79 if (!cl_data) {
Pratikkumar Prajapatif5a07b02023-06-18 10:27:44 -070080 printk(BIOS_ERR, "Crashlog PMC entry(size 0x%zx) "
Francois Toguo15cbc3b2021-01-26 10:27:49 -080081 "would exceed available region\n",
82 pmc_record_size);
Felix Held29405482021-05-28 16:01:57 +020083 return CB_ERR;
Francois Toguo15cbc3b2021-01-26 10:27:49 -080084 }
Pratikkumar Prajapatif5a07b02023-06-18 10:27:44 -070085 printk(BIOS_DEBUG, "cl_data %p, pmc_record_size 0x%zx\n",
Francois Toguo15cbc3b2021-01-26 10:27:49 -080086 cl_data, pmc_record_size);
87 cl_fill_pmc_records(cl_data);
88 }
89
Pratikkumar Prajapatie4893d62023-05-30 12:30:36 -070090 if (CONFIG(SOC_INTEL_IOE_DIE_SUPPORT)) {
91 size_t ioe_record_size = cl_get_ioe_record_size();
92 if (ioe_record_size) {
93 /* Allocate new FW ERR structure in case IOE crashlog is present */
94 if (ioe_record_size && !bert_append_fw_err(status)) {
95 printk(BIOS_ERR, "Crashlog IOE entry would "
96 "exceed available region\n");
97 return CB_ERR;
98 }
99
100 cl_data = new_cper_fw_error_crashlog(status, ioe_record_size);
101 if (!cl_data) {
Pratikkumar Prajapatif5a07b02023-06-18 10:27:44 -0700102 printk(BIOS_ERR, "Crashlog IOE entry(size 0x%zx) "
Pratikkumar Prajapatie4893d62023-05-30 12:30:36 -0700103 "would exceed available region\n",
104 ioe_record_size);
105 return CB_ERR;
106 }
Pratikkumar Prajapatif5a07b02023-06-18 10:27:44 -0700107 printk(BIOS_DEBUG, "cl_data %p, ioe_record_size 0x%zx\n",
Pratikkumar Prajapatie4893d62023-05-30 12:30:36 -0700108 cl_data, ioe_record_size);
109 cl_fill_ioe_records(cl_data);
110 }
111 }
112
Francois Toguo Fotsoc1751462021-05-27 01:10:16 -0700113 *length = status->data_length + gesb_header_size;
Francois Toguo15cbc3b2021-01-26 10:27:49 -0800114 *region = (void *)status;
115
Felix Held29405482021-05-28 16:01:57 +0200116 return CB_SUCCESS;
Francois Toguo15cbc3b2021-01-26 10:27:49 -0800117}
Jonathan Zhang01acc032022-10-26 17:53:25 -0700118
119enum cb_err acpi_soc_get_bert_region(void **region, size_t *length)
120{
121 if (CONFIG(SOC_INTEL_CRASHLOG)) {
122 return record_crashlog_into_bert(region, length);
123 } else {
124 /* Check if MCA error has been added into BERT. */
125 if (bert_should_generate_acpi_table()) {
126 bert_errors_region(region, length);
127 if (!*region) {
128 printk(BIOS_ERR, "Can't find BERT storage area\n");
129 return CB_ERR;
130 }
131 }
132 return CB_SUCCESS;
133 }
134}