Commit 70fdb494 authored by Borislav Petkov's avatar Borislav Petkov

EDAC, MCE: Add F15h CU MCE decoder

MCE bank 2 is redefined from a BU to a CU (Combined Unit) bank on F15h.
Add a decoder function for CU MCEs.
Signed-off-by: default avatarBorislav Petkov <borislav.petkov@amd.com>
parent 86039cd4
...@@ -95,6 +95,23 @@ static const char * const f15h_ic_mce_desc[] = { ...@@ -95,6 +95,23 @@ static const char * const f15h_ic_mce_desc[] = {
"fetch address FIFO" "fetch address FIFO"
}; };
static const char * const f15h_cu_mce_desc[] = {
"Fill ECC error on data fills", /* xec = 0x4 */
"Fill parity error on insn fills",
"Prefetcher request FIFO parity error",
"PRQ address parity error",
"PRQ data parity error",
"WCC Tag ECC error",
"WCC Data ECC error",
"WCB Data parity error",
"VB Data/ECC error",
"L2 Tag ECC error", /* xec = 0x10 */
"Hard L2 Tag ECC error",
"Multiple hits on L2 tag",
"XAB parity error",
"PRB address parity error"
};
static bool f12h_dc_mce(u16 ec, u8 xec) static bool f12h_dc_mce(u16 ec, u8 xec)
{ {
bool ret = false; bool ret = false;
...@@ -405,6 +422,46 @@ static void amd_decode_bu_mce(struct mce *m) ...@@ -405,6 +422,46 @@ static void amd_decode_bu_mce(struct mce *m)
pr_emerg(HW_ERR "Corrupted BU MCE info?\n"); pr_emerg(HW_ERR "Corrupted BU MCE info?\n");
} }
static void amd_decode_cu_mce(struct mce *m)
{
u16 ec = m->status & 0xffff;
u8 xec = (m->status >> 16) & xec_mask;
pr_emerg(HW_ERR "Combined Unit Error: ");
if (TLB_ERROR(ec)) {
if (xec == 0x0)
pr_cont("Data parity TLB read error.\n");
else if (xec == 0x1)
pr_cont("Poison data provided for TLB fill.\n");
else
goto wrong_cu_mce;
} else if (BUS_ERROR(ec)) {
if (xec > 2)
goto wrong_cu_mce;
pr_cont("Error during attempted NB data read.\n");
} else if (MEM_ERROR(ec)) {
switch (xec) {
case 0x4 ... 0xc:
pr_cont("%s.\n", f15h_cu_mce_desc[xec - 0x4]);
break;
case 0x10 ... 0x14:
pr_cont("%s.\n", f15h_cu_mce_desc[xec - 0x7]);
break;
default:
goto wrong_cu_mce;
}
}
return;
wrong_cu_mce:
pr_emerg(HW_ERR "Corrupted CU MCE info?\n");
}
static void amd_decode_ls_mce(struct mce *m) static void amd_decode_ls_mce(struct mce *m)
{ {
u16 ec = m->status & 0xffff; u16 ec = m->status & 0xffff;
...@@ -665,7 +722,10 @@ int amd_decode_mce(struct notifier_block *nb, unsigned long val, void *data) ...@@ -665,7 +722,10 @@ int amd_decode_mce(struct notifier_block *nb, unsigned long val, void *data)
break; break;
case 2: case 2:
amd_decode_bu_mce(m); if (boot_cpu_data.x86 == 0x15)
amd_decode_cu_mce(m);
else
amd_decode_bu_mce(m);
break; break;
case 3: case 3:
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment