aboutsummaryrefslogtreecommitdiff
path: root/hw
diff options
context:
space:
mode:
Diffstat (limited to 'hw')
-rw-r--r--hw/fsp/fsp-surveillance.c11
-rw-r--r--hw/fsp/fsp.c61
2 files changed, 50 insertions, 22 deletions
diff --git a/hw/fsp/fsp-surveillance.c b/hw/fsp/fsp-surveillance.c
index d3e5c45..202b093 100644
--- a/hw/fsp/fsp-surveillance.c
+++ b/hw/fsp/fsp-surveillance.c
@@ -82,15 +82,12 @@ static void fsp_surv_check_timeout(void)
* just go ahead and check timeouts.
*/
if (tb_compare(now, surv_ack_timer) == TB_AAFTERB) {
- /* XXX: We should be logging a PEL to the host, assuming
- * the FSP is dead, pending a R/R.
- */
- log_simple_error(&e_info(OPAL_RC_SURVE_ACK),
+ uint32_t plid = log_simple_error(&e_info(OPAL_RC_SURVE_ACK),
"SURV: Surv ACK timed out; initiating R/R\n");
/* Reset the pending trigger too */
fsp_surv_ack_pending = false;
- fsp_trigger_reset();
+ fsp_trigger_reset(plid);
}
return;
@@ -149,10 +146,10 @@ static void fsp_surv_got_param(uint32_t param_id __unused, int err_len,
void *data __unused)
{
if (err_len != 4) {
- log_simple_error(&e_info(OPAL_RC_SURVE_STATUS),
+ uint32_t plid = log_simple_error(&e_info(OPAL_RC_SURVE_STATUS),
"SURV: Error (%d) retrieving surv status; initiating R/R\n",
err_len);
- fsp_trigger_reset();
+ fsp_trigger_reset(plid);
return;
}
diff --git a/hw/fsp/fsp.c b/hw/fsp/fsp.c
index a0c5a78..162d9b4 100644
--- a/hw/fsp/fsp.c
+++ b/hw/fsp/fsp.c
@@ -40,7 +40,13 @@
#include <ccan/list/list.h>
DEFINE_LOG_ENTRY(OPAL_RC_FSP_POLL_TIMEOUT, OPAL_PLATFORM_ERR_EVT, OPAL_FSP,
- OPAL_PLATFORM_FIRMWARE, OPAL_ERROR_PANIC, OPAL_NA);
+ OPAL_PLATFORM_FIRMWARE, OPAL_RECOVERED_ERR_GENERAL, OPAL_NA);
+
+DEFINE_LOG_ENTRY(OPAL_RC_FSP_MBOX_ERR, OPAL_PLATFORM_ERR_EVT, OPAL_FSP,
+ OPAL_PLATFORM_FIRMWARE, OPAL_RECOVERED_ERR_GENERAL, OPAL_NA);
+
+DEFINE_LOG_ENTRY(OPAL_RC_FSP_DISR_HIR_MASK, OPAL_PLATFORM_ERR_EVT, OPAL_FSP,
+ OPAL_PLATFORM_FIRMWARE, OPAL_RECOVERED_ERR_GENERAL, OPAL_NA);
#define FSP_TRACE_MSG
#define FSP_TRACE_EVENT
@@ -545,9 +551,12 @@ static void __fsp_trigger_reset(void)
fsp_prep_for_reset(fsp);
}
-void fsp_trigger_reset(void)
+static uint32_t fsp_hir_reason_plid;
+
+void fsp_trigger_reset(uint32_t plid)
{
lock(&fsp_lock);
+ fsp_hir_reason_plid = plid;
__fsp_trigger_reset();
unlock(&fsp_lock);
}
@@ -683,9 +692,11 @@ static void fsp_handle_errors(struct fsp *fsp)
* quite rare.
*/
if (fsp->state == fsp_mbx_err) {
- prerror("FSP #%d: Triggering HIR on mbx_err\n",
- fsp->index);
- fsp_trigger_reset();
+ uint32_t plid;
+ plid = log_simple_error(&e_info(OPAL_RC_FSP_MBOX_ERR),
+ "FSP #%d: Triggering HIR on mbx_err\n",
+ fsp->index);
+ fsp_trigger_reset(plid);
return;
}
@@ -736,16 +747,20 @@ static void fsp_handle_errors(struct fsp *fsp)
* to trigger a HIR so it can try to recover via the DRCR route.
*/
if (disr & FSP_DISR_HIR_TRIGGER_MASK) {
+ const char *reason = "Unknown FSP_DISR_HIR_TRIGGER";
+ uint32_t plid;
fsp_trace_event(fsp, TRACE_FSP_EVT_SOFT_RR, disr, 0, 0, 0);
if (disr & FSP_DISR_FSP_UNIT_CHECK)
- prlog(PR_DEBUG, "FSP: DISR Unit Check set\n");
+ reason = "DISR Unit Check set";
else if (disr & FSP_DISR_FSP_RUNTIME_TERM)
- prlog(PR_DEBUG, "FSP: DISR Runtime Terminate set\n");
+ reason = "DISR Runtime Terminate set";
else if (disr & FSP_DISR_FSP_FLASH_TERM)
- prlog(PR_DEBUG, "FSP: DISR Flash Terminate set\n");
- prlog(PR_NOTICE, "FSP: Triggering host initiated reset"
- " sequence\n");
+ reason = "DISR Flash Terminate set";
+
+ plid = log_simple_error(&e_info(OPAL_RC_FSP_DISR_HIR_MASK),
+ "FSP: %s. Triggering host initiated "
+ "reset.", reason);
/* Clear all interrupt conditions */
fsp_wreg(fsp, FSP_HDIR_REG, FSP_DBIRQ_ALL);
@@ -753,7 +768,7 @@ static void fsp_handle_errors(struct fsp *fsp)
/* Make sure this happened */
fsp_rreg(fsp, FSP_HDIR_REG);
- fsp_trigger_reset();
+ fsp_trigger_reset(plid);
return;
}
@@ -1318,6 +1333,21 @@ static bool fsp_local_command(u32 cmd_sub_mod, struct fsp_msg *msg)
}
}
return true;
+ case FSP_CMD_GET_HIR_PLID:
+ /* Get Platform Log Id with reason for Host Initiated Reset */
+ prlog(PR_DEBUG, "FSP: Sending PLID 0x%x as HIR reason\n",
+ fsp_hir_reason_plid);
+ resp = fsp_mkmsg(FSP_RSP_GET_HIR_PLID, 1, fsp_hir_reason_plid);
+ if (!resp)
+ prerror("FSP: Failed to allocate GET_HIR_PLID response\n");
+ else {
+ if (fsp_queue_msg(resp, fsp_freemsg)) {
+ fsp_freemsg(resp);
+ prerror("FSP: Failed to queue GET_HIR_PLID resp\n");
+ }
+ }
+ fsp_hir_reason_plid = 0;
+ return true;
}
return false;
}
@@ -1340,7 +1370,7 @@ static void fsp_handle_command(struct fsp_msg *msg)
cmd_sub_mod = (msg->word0 & 0xff) << 16;
cmd_sub_mod |= (msg->word1 & 0xff) << 8;
cmd_sub_mod |= (msg->word1 >> 8) & 0xff;
-
+
/* Some commands are handled locally */
if (fsp_local_command(cmd_sub_mod, msg))
goto free;
@@ -2148,9 +2178,10 @@ static void fsp_timeout_poll(void *data __unused)
fsp_complete_msg(req);
__fsp_trigger_reset();
unlock(&fsp_lock);
- log_simple_error(&e_info(OPAL_RC_FSP_POLL_TIMEOUT),
- "FSP: Response from FSP timed out, word0 = %x,"
- "word1 = %x state: %d\n", w0, w1, mstate);
+ fsp_hir_reason_plid = log_simple_error(
+ &e_info(OPAL_RC_FSP_POLL_TIMEOUT),
+ "FSP: Response from FSP timed out, word0 = %x,"
+ "word1 = %x state: %d\n", w0, w1, mstate);
}
next_bit:
cmdclass_resp_bitmask = cmdclass_resp_bitmask >> 1;