aboutsummaryrefslogtreecommitdiff
path: root/src/rtl/keywrap_mkmif.v
diff options
context:
space:
mode:
Diffstat (limited to 'src/rtl/keywrap_mkmif.v')
-rw-r--r--src/rtl/keywrap_mkmif.v449
1 files changed, 449 insertions, 0 deletions
diff --git a/src/rtl/keywrap_mkmif.v b/src/rtl/keywrap_mkmif.v
new file mode 100644
index 0000000..d73c5bd
--- /dev/null
+++ b/src/rtl/keywrap_mkmif.v
@@ -0,0 +1,449 @@
+//======================================================================
+//
+// keywrap_mkmif.v
+// ---------------
+// Wrapper for the mkmif_core. This allow us to simplify the
+// integration of the mkmif in keywrap_core.
+//
+//
+// Author: Joachim Strombergson
+// Copyright (c) 2018, NORDUnet A/S
+// All rights reserved.
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions are
+// met:
+// - Redistributions of source code must retain the above copyright notice,
+// this list of conditions and the following disclaimer.
+//
+// - Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+// - Neither the name of the NORDUnet nor the names of its contributors may
+// be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
+// IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+// TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+// PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+// HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
+// TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//
+//======================================================================
+
+module keywrap_mkmif (
+ input wire clk,
+ input wire reset_n,
+
+ output wire mkm_spi_sclk,
+ output wire mkm_spi_cs_n,
+ input wire mkm_spi_do,
+ output wire mkm_spi_di,
+
+ input wire init,
+ input wire read,
+ input wire write,
+ input wire key_status,
+ output wire ready,
+
+ input wire [31 : 0] wr_status,
+ output wire [31 : 0] rd_status,
+ input wire [255 : 0] wr_key,
+ output wire [255 : 0] rd_key
+ );
+
+
+ //----------------------------------------------------------------
+ // Paramenters and local defines.
+ //----------------------------------------------------------------
+ localparam CTRL_IDLE = 4'h0;
+ localparam CTRL_WAIT = 4'h1;
+ localparam CTRL_INIT = 4'h2;
+ localparam CTRL_READ = 4'h3;
+ localparam CTRL_READ_STATUS_WAIT = 4'h4;
+ localparam CTRL_READ_KEY = 4'h5;
+ localparam CTRL_READ_KEY_WAIT = 4'h6;
+ localparam CTRL_WRITE = 4'h8;
+ localparam CTRL_WRITE_KEY = 4'h9;
+ localparam CTRL_WRITE_KEY_WAIT = 4'ha;
+
+ // Addresses for storage in the mkm
+ localparam MKM_STATUS_WORD = 16'h00;
+ localparam MKM_KEY_BASE_WORD = 16'h04;
+
+ localparam DEFAULT_SCLK_DIV = 16'h0020;
+
+
+ //----------------------------------------------------------------
+ // Registers and memories including control signals.
+ //----------------------------------------------------------------
+ reg [31 : 0] key_reg [0 : 7];
+ reg key_we;
+
+ reg [2 : 0] key_word_ctr_reg;
+ reg [2 : 0] key_word_ctr_new;
+ reg key_word_ctr_we;
+ reg key_word_ctr_rst;
+ reg key_word_ctr_inc;
+
+ reg [15 : 0] mkm_addr_reg;
+ reg [15 : 0] mkm_addr_new;
+ reg mkm_addr_we;
+
+ reg [31 : 0] mkm_write_data_reg;
+ reg [31 : 0] mkm_write_data_new;
+ reg mkm_write_data_we;
+
+ reg [31 : 0] status_reg;
+ reg [31 : 0] status_new;
+ reg status_we;
+
+ reg ready_reg;
+ reg ready_new;
+ reg ready_we;
+
+ reg [3 : 0] keywrap_mkmif_ctrl_reg;
+ reg [3 : 0] keywrap_mkmif_ctrl_new;
+ reg keywrap_mkmif_ctrl_we;
+
+ reg init_op_reg;
+ reg read_op_reg;
+ reg write_op_reg;
+
+
+ //----------------------------------------------------------------
+ // Wires.
+ //----------------------------------------------------------------
+ reg mkm_init_op;
+ reg mkm_read_op;
+ reg mkm_write_op;
+ wire mkm_ready;
+ wire mkm_valid;
+ reg [15 : 0] mkm_addr;
+ reg [31 : 0] mkm_write_data;
+ wire [31 : 0] mkm_read_data;
+
+
+ //----------------------------------------------------------------
+ // Instantiations.
+ //----------------------------------------------------------------
+ mkmif_core mkm(
+ .clk(clk),
+ .reset_n(reset_n),
+
+ .spi_sclk(mkm_spi_sclk),
+ .spi_cs_n(mkm_spi_cs_n),
+ .spi_do(mkm_spi_do),
+ .spi_di(mkm_spi_di),
+
+ .init_op(init_op_reg),
+ .read_op(read_op_reh),
+ .write_op(write_op_reg),
+
+ .ready(mkm_ready),
+ .valid(mkm_valid),
+
+ .sclk_div(DEFAULT_SCLK_DIV),
+ .addr(mkm_addr_reg),
+ .write_data(mkm_write_data_reg),
+ .read_data(mkm_read_data)
+ );
+
+
+ //----------------------------------------------------------------
+ // Assignments for ports.
+ //----------------------------------------------------------------
+ assign ready = ready_reg;
+
+ assign rd_status = status_reg;
+
+ assign rd_key = {key_reg[7], key_reg[6], key_reg[5], key_reg[4],
+ key_reg[3], key_reg[2], key_reg[1], key_reg[0]};
+
+
+ //----------------------------------------------------------------
+ // reg_update
+ //----------------------------------------------------------------
+ always @ (posedge clk or negedge reset_n)
+ begin: reg_update
+ integer i;
+
+ if (!reset_n)
+ begin
+ for (i = 0 ; i < 8 ; i = i + 1)
+ key_reg[i] <= 32'h0;
+
+ ready_reg <= 1'h1;
+ status_reg <= 32'h0;
+ mkm_addr_reg <= 16'h0;
+ mkm_write_data_reg <= 32'h0;
+ key_word_ctr_reg <= 3'h0;
+ init_op_reg <= 1'h0;
+ read_op_reg <= 1'h0;
+ write_op_reg <= 1'h0;
+ keywrap_mkmif_ctrl_reg <= CTRL_IDLE;
+ end
+
+ else
+ begin
+ init_op_reg <= mkm_init_op;
+ read_op_reg <= mkm_read_op;
+ write_op_reg <= mkm_write_op;
+
+ if (ready_we)
+ ready_reg <= ready_new;
+
+ if (mkm_addr_we)
+ mkm_addr_reg <= mkm_addr_new;
+
+ if (mkm_write_data_we)
+ mkm_write_data_reg <= mkm_write_data_new;
+
+ if (key_we)
+ key_reg[key_word_ctr_reg] <= mkm_read_data;
+
+ if (status_we)
+ status_reg <= mkm_read_data;
+
+ if (key_word_ctr_we)
+ key_word_ctr_reg <= key_word_ctr_new;
+
+ if (keywrap_mkmif_ctrl_we)
+ keywrap_mkmif_ctrl_reg <= keywrap_mkmif_ctrl_new;
+ end
+ end // reg_update
+
+
+ //----------------------------------------------------------------
+ // key_word_ctr
+ //----------------------------------------------------------------
+ always @*
+ begin : key_word_ctr
+ key_word_ctr_new = 3'h0;
+ key_word_ctr_we = 1'h0;
+
+ if (key_word_ctr_rst)
+ begin
+ key_word_ctr_new = 3'h0;
+ key_word_ctr_we = 1'h1;
+ end
+
+ if (key_word_ctr_inc)
+ begin
+ key_word_ctr_new = key_word_ctr_reg + 1'h1;
+ key_word_ctr_we = 1'h1;
+ end
+
+ end
+
+
+ //----------------------------------------------------------------
+ // keywrap_mkmif_ctrl
+ //----------------------------------------------------------------
+ always @*
+ begin : keywrap_mkmif_ctrl
+ ready_new = 1'h0;
+ ready_we = 1'h0;
+ key_we = 1'h0;
+ key_word_ctr_rst = 1'h0;
+ key_word_ctr_inc = 1'h0;
+ status_we = 1'h0;
+ mkm_init_op = 1'h0;
+ mkm_read_op = 1'h0;
+ mkm_write_op = 1'h0;
+ mkm_addr_new = 16'h0;
+ mkm_addr_we = 1'h0;
+ mkm_write_data_new = 32'h0;
+ mkm_write_data_we = 1'h0;
+ keywrap_mkmif_ctrl_new = CTRL_IDLE;
+ keywrap_mkmif_ctrl_we = 1'h0;
+
+ case (keywrap_mkmif_ctrl_reg)
+ CTRL_IDLE:
+ begin
+ if (init)
+ begin
+ mkm_init_op = 1'h1;
+ ready_new = 1'h0;
+ ready_we = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_INIT;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+
+ if (read)
+ begin
+ ready_new = 1'h0;
+ ready_we = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_READ;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+
+ if (write)
+ begin
+ ready_new = 1'h0;
+ ready_we = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_WRITE;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ end
+
+
+ CTRL_INIT:
+ begin
+ keywrap_mkmif_ctrl_new = CTRL_WAIT;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+
+
+ CTRL_READ:
+ begin
+ if (key_status)
+ begin
+ key_word_ctr_rst = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_READ_KEY;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ else
+ begin
+ mkm_read_op = 1'h1;
+ mkm_addr_new = MKM_STATUS_WORD;
+ mkm_addr_we = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_READ_STATUS_WAIT;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ end
+
+
+ CTRL_WAIT:
+ begin
+ if (mkm_ready)
+ begin
+ ready_new = 1'h1;
+ ready_we = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_IDLE;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ end
+
+
+ CTRL_READ_STATUS_WAIT:
+ begin
+ ready_new = 1'h1;
+ ready_we = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_IDLE;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ if (mkm_ready)
+ begin
+ status_we = 1'h1;
+ ready_new = 1'h1;
+ ready_we = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_IDLE;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ end
+
+
+ CTRL_READ_KEY:
+ begin
+ if (key_word_ctr_reg < 8)
+ begin
+ mkm_read_op = 1'h1;
+ mkm_addr_new = MKM_KEY_BASE_WORD + {key_word_ctr_reg, 2'h0};
+ mkm_addr_we = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_READ_KEY_WAIT;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ else
+ begin
+ ready_new = 1'h1;
+ ready_we = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_IDLE;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ end
+
+
+ CTRL_READ_KEY_WAIT:
+ begin
+ if (mkm_ready)
+ begin
+ key_we = 1'h1;
+ key_word_ctr_inc = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_READ_KEY;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ end
+
+
+ CTRL_WRITE:
+ begin
+ if (key_status)
+ begin
+ key_word_ctr_rst = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_WRITE_KEY;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ else
+ begin
+ mkm_write_op = 1'h1;
+ mkm_addr_new = MKM_STATUS_WORD;
+ mkm_addr_we = 1'h1;
+ mkm_write_data_new = wr_status;
+ mkm_write_data_we = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_WAIT;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ end
+
+
+ CTRL_WRITE_KEY:
+ begin
+ if (key_word_ctr_reg < 8)
+ begin
+ mkm_write_op = 1'h1;
+ mkm_addr_new = MKM_KEY_BASE_WORD + {key_word_ctr_reg, 2'h0};
+ mkm_addr_we = 1'h1;
+ mkm_write_data_new = wr_key[key_word_ctr_reg * 32 +: 32];
+ mkm_write_data_we = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_WRITE_KEY_WAIT;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ else
+ begin
+ ready_new = 1'h1;
+ ready_we = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_IDLE;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ end
+
+
+ CTRL_WRITE_KEY_WAIT:
+ begin
+ if (mkm_ready)
+ begin
+ key_word_ctr_inc = 1'h1;
+ keywrap_mkmif_ctrl_new = CTRL_WRITE_KEY;
+ keywrap_mkmif_ctrl_we = 1'h1;
+ end
+ end
+
+
+ default:
+ begin
+ end
+ endcase // case (keywrap_mkmif_ctrl_reg)
+ end // keywrap_mkmif_ctrl
+
+endmodule // keywrap_mkmif
+
+//======================================================================
+// EOF keywrap_mkmif.v
+//======================================================================