diff mbox

[v2,09/11] libflash/mbox-flash: Understand v3

Message ID 20170803071808.7256-10-cyril.bur@au1.ibm.com
State Changes Requested
Headers show

Commit Message

Cyril Bur Aug. 3, 2017, 7:18 a.m. UTC
Signed-off-by: Cyril Bur <cyril.bur@au1.ibm.com>
---
 include/lpc-mbox.h    |  4 ++-
 libflash/mbox-flash.c | 95 ++++++++++++++++++++++++++++++++++-----------------
 2 files changed, 67 insertions(+), 32 deletions(-)
diff mbox

Patch

diff --git a/include/lpc-mbox.h b/include/lpc-mbox.h
index 569f1f72..819522f2 100644
--- a/include/lpc-mbox.h
+++ b/include/lpc-mbox.h
@@ -34,7 +34,8 @@ 
 #define MBOX_C_WRITE_FLUSH 0x08
 #define MBOX_C_BMC_EVENT_ACK 0x09
 #define MBOX_C_MARK_WRITE_ERASED 0x0a
-#define MBOX_COMMAND_COUNT 10
+#define MBOX_C_MARK_LOCKED 0x0b
+#define MBOX_COMMAND_COUNT 11
 
 #define MBOX_R_SUCCESS 0x01
 #define MBOX_R_PARAM_ERROR 0x02
@@ -44,6 +45,7 @@ 
 #define MBOX_R_BUSY 0x06
 #define MBOX_R_WINDOW_ERROR 0x07
 #define MBOX_R_SEQ_ERROR 0x08
+#define MBOX_R_LOCKED 0x09
 
 #define MBOX_ATTN_ACK_MASK 0x3
 #define MBOX_ATTN_BMC_REBOOT (1 << 0)
diff --git a/libflash/mbox-flash.c b/libflash/mbox-flash.c
index bbb54c51..a1b002e9 100644
--- a/libflash/mbox-flash.c
+++ b/libflash/mbox-flash.c
@@ -71,36 +71,56 @@  struct mbox_flash_data {
 static mbox_handler mbox_flash_do_nop;
 static mbox_handler mbox_flash_do_illegal;
 
-/* Version 1 and Version 2 compatible */
+/* Version 1, 2, 3 compatible */
 static mbox_handler mbox_flash_do_get_mbox_info;
 
-static mbox_handler mbox_flash_do_get_flash_info_v2;
+/* Version 2 and 3 compatible */
+static mbox_handler mbox_flash_do_get_flash_info;
 static mbox_handler mbox_flash_do_get_flash_info_v1;
 
-static mbox_handler mbox_flash_do_create_read_window_v2;
+/* Version 2 and 3 compatible */
+static mbox_handler mbox_flash_do_create_read_window;
 static mbox_handler mbox_flash_do_create_read_window_v1;
 
-static mbox_handler mbox_flash_do_create_write_window_v2;
+/* Version 2 and 3 compatible */
+static mbox_handler mbox_flash_do_create_write_window;
 static mbox_handler mbox_flash_do_create_write_window_v1;
 
-/* Version 1 and Version 2 compatible */
+/* Version 1, 2, 3 compatible */
 static mbox_handler mbox_flash_do_close_window;
 
 /* Plus one, commands start at 1 */
-static mbox_handler *handlers_v2[MBOX_COMMAND_COUNT + 1] = {
+static mbox_handler *handlers_v3[MBOX_COMMAND_COUNT + 1] = {
 	NULL,
 	&mbox_flash_do_nop,
 	&mbox_flash_do_get_mbox_info,
-	&mbox_flash_do_get_flash_info_v2,
-	&mbox_flash_do_create_read_window_v2,
+	&mbox_flash_do_get_flash_info,
+	&mbox_flash_do_create_read_window,
 	&mbox_flash_do_close_window,
-	&mbox_flash_do_create_write_window_v2,
+	&mbox_flash_do_create_write_window,
+	&mbox_flash_do_nop,
 	&mbox_flash_do_nop,
 	&mbox_flash_do_nop,
 	&mbox_flash_do_nop,
 	&mbox_flash_do_nop
 };
 
+/* Plus one, commands start at 1 */
+static mbox_handler *handlers_v2[MBOX_COMMAND_COUNT + 1] = {
+	NULL,
+	&mbox_flash_do_nop,
+	&mbox_flash_do_get_mbox_info,
+	&mbox_flash_do_get_flash_info,
+	&mbox_flash_do_create_read_window,
+	&mbox_flash_do_close_window,
+	&mbox_flash_do_create_write_window,
+	&mbox_flash_do_nop,
+	&mbox_flash_do_nop,
+	&mbox_flash_do_nop,
+	&mbox_flash_do_nop,
+	&mbox_flash_do_illegal
+};
+
 /*
  * Plus one, commands start at 1.
  * V2 adds a command so there should never be a response for the last
@@ -118,6 +138,7 @@  static mbox_handler *handlers_v1[MBOX_COMMAND_COUNT + 1] = {
 	&mbox_flash_do_nop,
 	&mbox_flash_do_nop,
 	&mbox_flash_do_nop,
+	&mbox_flash_do_illegal,
 	&mbox_flash_do_illegal
 };
 
@@ -395,22 +416,26 @@  static void mbox_flash_do_illegal(struct mbox_flash_data *mbox_flash __unused,
 	prlog(PR_CRIT, "Got response to unknown message type\n");
 }
 
-/* Version 1 and Version 2 compatible */
+/* Version 1, 2 and 3 compatible */
 static void mbox_flash_do_get_mbox_info(struct mbox_flash_data *mbox_flash,
 		struct bmc_mbox_msg *msg)
 {
 
 	mbox_flash->version = msg_get_u8(msg, 0);
-	if (mbox_flash->version == 1) {
-		/* Not all version 1 daemons set argument 5 correctly */
-		mbox_flash->shift = 12; /* Protocol hardcodes to 4K anyway */
-		mbox_flash->read.size = blocks_to_bytes(mbox_flash, msg_get_u16(msg, 1));
-		mbox_flash->write.size = blocks_to_bytes(mbox_flash, msg_get_u16(msg, 3));
-	} else { /* V2 compatible */
-		mbox_flash->shift = msg_get_u8(msg, 5);
-		mbox_flash->timeout = msg_get_u16(msg, 6);
-		if (mbox_flash->timeout == 0)
-			mbox_flash->timeout = MBOX_DEFAULT_TIMEOUT;
+	switch (mbox_flash->version) {
+		case 1:
+			/* Not all version 1 daemons set argument 5 correctly */
+			mbox_flash->shift = 12; /* Protocol hardcodes to 4K anyway */
+			mbox_flash->read.size = blocks_to_bytes(mbox_flash, msg_get_u16(msg, 1));
+			mbox_flash->write.size = blocks_to_bytes(mbox_flash, msg_get_u16(msg, 3));
+			break;
+		case 3:
+		case 2:
+			mbox_flash->shift = msg_get_u8(msg, 5);
+			mbox_flash->timeout = msg_get_u16(msg, 6);
+			if (mbox_flash->timeout == 0)
+				mbox_flash->timeout = MBOX_DEFAULT_TIMEOUT;
+			break;
 	}
 	/* Callers will handle the case where the version is not known
 	 *
@@ -421,7 +446,8 @@  static void mbox_flash_do_get_mbox_info(struct mbox_flash_data *mbox_flash,
 	 */
 }
 
-static void mbox_flash_do_get_flash_info_v2(struct mbox_flash_data *mbox_flash,
+/* Version 2 and 3 compatible */
+static void mbox_flash_do_get_flash_info(struct mbox_flash_data *mbox_flash,
 		struct bmc_mbox_msg *msg)
 {
 	mbox_flash->total_size = blocks_to_bytes(mbox_flash, msg_get_u16(msg, 0));
@@ -435,7 +461,8 @@  static void mbox_flash_do_get_flash_info_v1(struct mbox_flash_data *mbox_flash,
 	mbox_flash->erase_granule = msg_get_u32(msg, 4);
 }
 
-static void mbox_flash_do_create_read_window_v2(struct mbox_flash_data *mbox_flash,
+/* Version 2 and 3 compatible */
+static void mbox_flash_do_create_read_window(struct mbox_flash_data *mbox_flash,
 		struct bmc_mbox_msg *msg)
 {
 	mbox_flash->read.lpc_addr = blocks_to_bytes(mbox_flash, msg_get_u16(msg, 0));
@@ -453,7 +480,8 @@  static void mbox_flash_do_create_read_window_v1(struct mbox_flash_data *mbox_fla
 	mbox_flash->write.open = false;
 }
 
-static void mbox_flash_do_create_write_window_v2(struct mbox_flash_data *mbox_flash,
+/* Version 2 and 3 compatible */
+static void mbox_flash_do_create_write_window(struct mbox_flash_data *mbox_flash,
 		struct bmc_mbox_msg *msg)
 {
 	mbox_flash->write.lpc_addr = blocks_to_bytes(mbox_flash, msg_get_u16(msg, 0));
@@ -946,39 +974,40 @@  static int protocol_init(struct mbox_flash_data *mbox_flash)
 	struct bmc_mbox_msg msg = MSG_CREATE(MBOX_C_GET_MBOX_INFO);
 	int rc;
 
-	/* Assume V2 */
+	/* Assume V2+ */
 	mbox_flash->bl.read = &mbox_flash_read;
 	mbox_flash->bl.write = &mbox_flash_write;
 	mbox_flash->bl.erase = &mbox_flash_erase_v2;
 	mbox_flash->bl.get_info = &mbox_flash_get_info;
 
-	/* Assume V2 */
-	mbox_flash->handlers = handlers_v2;
+	/* Assume V3 */
+	mbox_flash->handlers = handlers_v3;
 
 	bmc_mbox_register_callback(&mbox_flash_callback, mbox_flash);
 	bmc_mbox_register_attn(&mbox_flash_attn, mbox_flash);
 
 	/*
 	 * For V1 of the protocol this is fixed.
-	 * V2: The init code will update this
+	 * V2+: The init code will update this
 	 */
 	mbox_flash->shift = 12;
 
 	/*
 	 * For V1 we'll use this value.
-	 * V2: The init code (may) update this
+	 * V2+: The init code (may) update this
 	 */
 	mbox_flash->timeout = MBOX_DEFAULT_TIMEOUT;
 
 	/*
-	 * Always attempt init with V2.
+	 * Always attempt init with highest version known.
 	 * The GET_MBOX_INFO response will confirm that the other side can
 	 * talk the highest version, we'll update this variable then if
 	 * our highest version is not supported
 	 */
-	mbox_flash->version = 2;
+	mbox_flash->version = 3;
 
 	msg_put_u8(&msg, 0, mbox_flash->version);
+	msg_put_u8(&msg, 1, 0); /* Don't request a shift, let the BMC give us one */
 	rc = msg_send(mbox_flash, &msg, mbox_flash->timeout);
 	if (rc) {
 		prlog(PR_ERR, "Failed to enqueue/send BMC MBOX message\n");
@@ -998,6 +1027,10 @@  static int protocol_init(struct mbox_flash_data *mbox_flash)
 			mbox_flash->handlers = handlers_v1;
 			break;
 		case 2:
+			mbox_flash->handlers = handlers_v2;
+			break;
+		case 3:
+			/* Nothing to do we assumed it would be V3 */
 			break;
 		default:
 			/*
@@ -1025,7 +1058,7 @@  int mbox_flash_init(struct blocklevel_device **bl)
 	if (!mbox_flash)
 		return FLASH_ERR_MALLOC_FAILED;
 
-	/* Assume V2 */
+	/* Assume V2+ */
 	mbox_flash->bl.read = &mbox_flash_read;
 	mbox_flash->bl.write = &mbox_flash_write;
 	mbox_flash->bl.erase = &mbox_flash_erase_v2;