summaryrefslogtreecommitdiffstats
path: root/hw
diff options
context:
space:
mode:
authorVasant Hegde <hegdevasant@linux.vnet.ibm.com>2014-07-11 21:26:26 +0530
committerBenjamin Herrenschmidt <benh@kernel.crashing.org>2014-07-21 11:51:52 +1000
commitd2ea5b38ac3b4e1b9bbce826b8376189c19b51d2 (patch)
treeccf902af3f9702cfdcf6723ce74fb8e223132a7c /hw
parent95c59eb7132c83613703b3fec93aebb90c34460d (diff)
downloadblackbird-skiboot-d2ea5b38ac3b4e1b9bbce826b8376189c19b51d2.tar.gz
blackbird-skiboot-d2ea5b38ac3b4e1b9bbce826b8376189c19b51d2.zip
CUPD: Handle FSP R/R
At present, if FSP R/R happens while retrieving marker LID, then we don't get marker LID from FSP and this will result in inband code update failure. This patch handles FSP R/R. Signed-off-by: Vasant Hegde <hegdevasant@linux.vnet.ibm.com> Signed-off-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
Diffstat (limited to 'hw')
-rw-r--r--hw/fsp/fsp-codeupdate.c48
1 files changed, 48 insertions, 0 deletions
diff --git a/hw/fsp/fsp-codeupdate.c b/hw/fsp/fsp-codeupdate.c
index 1df87167..3eeb7b94 100644
--- a/hw/fsp/fsp-codeupdate.c
+++ b/hw/fsp/fsp-codeupdate.c
@@ -29,6 +29,7 @@ enum flash_state {
FLASH_STATE_INVALID, /* IPL side marker lid is invalid */
FLASH_STATE_READING,
FLASH_STATE_READ,
+ FLASH_STATE_ABORT,
};
enum lid_fetch_side {
@@ -207,6 +208,7 @@ static int64_t code_update_check_state(void)
case FLASH_STATE_ABSENT:
return OPAL_HARDWARE;
case FLASH_STATE_INVALID:
+ case FLASH_STATE_ABORT:
return OPAL_INTERNAL_ERROR;
case FLASH_STATE_READING:
return OPAL_BUSY;
@@ -1158,6 +1160,50 @@ static bool code_update_notify(uint32_t cmd_sub_mod, struct fsp_msg *msg)
return true;
}
+/*
+ * Handle FSP R/R event.
+ *
+ * Note:
+ * If FSP R/R happens during code update, then entire system reboots
+ * and comes up with P side image (and T side image will be invalid).
+ * Hence we don't need to handle R/R during code update.
+ *
+ * Also if FSP R/R happens in init path (while retrieving in_flight_params)
+ * then system fails to continue booting (because we have not yet loaded
+ * all required data/LID from FSP). Hence we don't need to handle R/R
+ * for system params.
+ */
+static bool fsp_code_update_rr(uint32_t cmd_sub_mod,
+ struct fsp_msg *msg __unused)
+{
+ switch (cmd_sub_mod) {
+ case FSP_RESET_START:
+ lock(&flash_lock);
+
+ if (code_update_check_state() == OPAL_BUSY)
+ flash_state = FLASH_STATE_ABORT;
+
+ unlock(&flash_lock);
+ return true;
+ case FSP_RELOAD_COMPLETE:
+ lock(&flash_lock);
+
+ /* Lets try to parse marker LID again, if we failed
+ * to parse marker LID last time.
+ */
+ if (code_update_check_state() == OPAL_INTERNAL_ERROR)
+ fetch_com_marker_lid();
+
+ unlock(&flash_lock);
+ return true;
+ }
+ return false;
+}
+
+static struct fsp_client fsp_cupd_client_rr = {
+ .message = fsp_code_update_rr,
+};
+
static struct fsp_client fsp_get_notify = {
.message = code_update_notify,
};
@@ -1176,6 +1222,8 @@ void fsp_code_update_init(void)
/* register Code Update Class D3 */
fsp_register_client(&fsp_get_notify, FSP_MCLASS_CODE_UPDATE);
+ /* Register for Class AA (FSP R/R) */
+ fsp_register_client(&fsp_cupd_client_rr, FSP_MCLASS_RR_EVENT);
/* Flash hook */
fsp_flash_term_hook = NULL;
OpenPOWER on IntegriCloud