protocol: Add erase

Change-Id: I8b533f911e2d008f474817831836d29663511e98
Signed-off-by: Andrew Jeffery <andrew@aj.id.au>
diff --git a/protocol.c b/protocol.c
index 7a5b491..88e91b2 100644
--- a/protocol.c
+++ b/protocol.c
@@ -265,12 +265,42 @@
 				  io->req.v2.size, WINDOW_DIRTY);
 }
 
+int protocol_v2_erase(struct mbox_context *context,
+		      struct protocol_erase *io)
+{
+	size_t start, len;
+	int rc;
+
+	if (!(context->current && context->current_is_write)) {
+		MSG_ERR("Tried to call erase without open write window\n");
+		return -EPERM;
+	}
+
+	MSG_INFO("Erase window @ 0x%.8x for 0x%.8x\n",
+		 io->req.offset << context->block_size_shift,
+		 io->req.size << context->block_size_shift);
+
+	rc = window_set_bytemap(context, context->current, io->req.offset,
+				io->req.size, WINDOW_ERASED);
+	if (rc < 0) {
+		return rc;
+	}
+
+	/* Write 0xFF to mem -> This ensures consistency between flash & ram */
+	start = io->req.offset << context->block_size_shift;
+	len = io->req.size << context->block_size_shift;
+	memset(context->current->mem + start, 0xFF, len);
+
+	return 0;
+}
+
 static const struct protocol_ops protocol_ops_v1 = {
 	.reset = protocol_v1_reset,
 	.get_info = protocol_v1_get_info,
 	.get_flash_info = protocol_v1_get_flash_info,
 	.create_window = protocol_v1_create_window,
 	.mark_dirty = protocol_v1_mark_dirty,
+	.erase = NULL,
 };
 
 static const struct protocol_ops protocol_ops_v2 = {
@@ -279,6 +309,7 @@
 	.get_flash_info = protocol_v2_get_flash_info,
 	.create_window = protocol_v2_create_window,
 	.mark_dirty = protocol_v2_mark_dirty,
+	.erase = protocol_v2_erase,
 };
 
 static const struct protocol_ops *protocol_ops_map[] = {
diff --git a/protocol.h b/protocol.h
index cc6bc8f..9b652ef 100644
--- a/protocol.h
+++ b/protocol.h
@@ -73,6 +73,14 @@
 	} req;
 };
 
+struct protocol_erase {
+	struct {
+		uint16_t offset;
+		uint16_t size;
+	} req;
+};
+
+
 struct protocol_ops {
 	int (*reset)(struct mbox_context *context);
 	int (*get_info)(struct mbox_context *context,
@@ -83,6 +91,7 @@
 			     struct protocol_create_window *io);
 	int (*mark_dirty)(struct mbox_context *context,
 			  struct protocol_mark_dirty *io);
+	int (*erase)(struct mbox_context *context, struct protocol_erase *io);
 };
 
 int protocol_init(struct mbox_context *context);
@@ -110,5 +119,7 @@
 			      struct protocol_create_window *io);
 int protocol_v2_mark_dirty(struct mbox_context *context,
 			   struct protocol_mark_dirty *io);
+int protocol_v2_erase(struct mbox_context *context,
+		      struct protocol_erase *io);
 
 #endif /* PROTOCOL_H */
diff --git a/transport_mbox.c b/transport_mbox.c
index 3382d35..92b3609 100644
--- a/transport_mbox.c
+++ b/transport_mbox.c
@@ -422,38 +422,23 @@
 int mbox_handle_erase_window(struct mbox_context *context,
 				    union mbox_regs *req, struct mbox_msg *resp)
 {
-	uint32_t offset, size;
+	struct protocol_erase io;
 	int rc;
 
-	if (context->version < API_VERSION_2) {
+	io.req.offset = get_u16(&req->msg.args[0]);
+	io.req.size = get_u16(&req->msg.args[2]);
+
+	if (!context->protocol->erase) {
 		MSG_ERR("Protocol Version invalid for Erase Command\n");
 		return -MBOX_R_PARAM_ERROR;
 	}
 
-	if (!(context->current && context->current_is_write)) {
-		MSG_ERR("Tried to call erase without open write window\n");
-		return -MBOX_R_WINDOW_ERROR;
-	}
-
-	offset = get_u16(&req->msg.args[0]);
-	size = get_u16(&req->msg.args[2]);
-
-	MSG_INFO("Erase window @ 0x%.8x for 0x%.8x\n",
-		 offset << context->block_size_shift,
-		 size << context->block_size_shift);
-
-	rc = window_set_bytemap(context, context->current, offset, size,
-				WINDOW_ERASED);
+	rc = context->protocol->erase(context, &io);
 	if (rc < 0) {
-		return (rc == -EACCES) ? -MBOX_R_PARAM_ERROR
-				       : -MBOX_R_SYSTEM_ERROR;
+		return mbox_xlate_errno(context, rc);
 	}
 
-	/* Write 0xFF to mem -> This ensures consistency between flash & ram */
-	memset(context->current->mem + (offset << context->block_size_shift),
-	       0xFF, size << context->block_size_shift);
-
-	return 0;
+	return rc;
 }
 
 /*