From 071ea1d8114b786615068b47f83571b8ec16e001 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Joachim=20Stro=CC=88mbergson?= <joachim@secworks.se>
Date: Wed, 24 Sep 2014 09:46:17 +0200
Subject: Updates to fix bugs found during synthesis. Adding more debug outputs
 in API. Adding security error port for future internal health tests.

---
 src/rtl/rosc.v              |  14 ++--
 src/rtl/rosc_entropy.v      | 123 +++++++++++++++++++++--------------
 src/rtl/rosc_entropy_core.v | 155 +++++++++++++++++++++++++++-----------------
 3 files changed, 173 insertions(+), 119 deletions(-)

(limited to 'src')

diff --git a/src/rtl/rosc.v b/src/rtl/rosc.v
index afcc9bf..5557353 100644
--- a/src/rtl/rosc.v
+++ b/src/rtl/rosc.v
@@ -55,13 +55,7 @@ module rosc #(parameter WIDTH = 2)
   // Registers.
   //----------------------------------------------------------------
   reg dout_reg;
-
-
-  //----------------------------------------------------------------
-  // Wires.
-  //----------------------------------------------------------------
-  reg [WIDTH : 0] sum;
-  reg 	          cin;
+  reg dout_new;
 
 
   //----------------------------------------------------------------
@@ -83,7 +77,7 @@ module rosc #(parameter WIDTH = 2)
            begin
              if (we)
                begin
-                 dout_reg <= cin;
+                 dout_reg <= dout_new;
                end
            end
        end
@@ -99,8 +93,12 @@ module rosc #(parameter WIDTH = 2)
   //----------------------------------------------------------------
   always @*
     begin: adder_osc
+      reg [WIDTH : 0] sum;
+      reg             cin;
+
       cin = ~sum[WIDTH];
       sum = opa + opb + cin;
+      dout_new = sum[WIDTH];
     end
 endmodule // rosc
 
diff --git a/src/rtl/rosc_entropy.v b/src/rtl/rosc_entropy.v
index b407f3b..32fc3d2 100644
--- a/src/rtl/rosc_entropy.v
+++ b/src/rtl/rosc_entropy.v
@@ -40,32 +40,42 @@ module rosc_entropy(
                     input wire           clk,
                     input wire           reset_n,
 
-                    output wire [7 : 0]  debug,
-                    input wire           debug_update,
-
                     input wire           cs,
                     input wire           we,
                     input wire  [7 : 0]  address,
                     input wire  [31 : 0] write_data,
                     output wire [31 : 0] read_data,
-                    output wire          error
+                    output wire          error,
+
+                    output wire [31 : 0] entropy_data,
+                    output wire          entropy_valid,
+                    input wire           entropy_ack,
+
+                    output wire [7 : 0]  debug,
+                    input wire           debug_update,
+
+                    output wire          security_error
                    );
 
 
   //----------------------------------------------------------------
   // Parameters.
   //----------------------------------------------------------------
-  parameter ADDR_CTRL            = 8'h00;
-  parameter CTRL_ENABLE_BIT      = 0;
+  parameter ADDR_CTRL                = 8'h00;
+  parameter CTRL_ENABLE_BIT          = 0;
 
-  parameter ADDR_STATUS          = 8'h01;
-  parameter STATUS_RND_VALID_BIT = 0;
+  parameter ADDR_STATUS              = 8'h01;
+  parameter STATUS_ENTROPY_VALID_BIT = 0;
 
-  parameter ADDR_OPA             = 8'h08;
-  parameter ADDR_OPB             = 8'h09;
+  parameter ADDR_OP_A                = 8'h08;
+  parameter ADDR_OP_B                = 8'h09;
 
-  parameter ADDR_ENTROPY         = 8'h10;
-  parameter ADDR_RND             = 8'h20;
+  parameter ADDR_ENTROPY             = 8'h10;
+  parameter ADDR_RAW                 = 8'h20;
+  parameter ADDR_ROSC_OUTPUTS        = 8'h21;
+
+  parameter DEFAULT_OP_A             = 8'haaaaaaaa;
+  parameter DEFAULT_OP_B             = ~DEFAULT_OP_A;
 
 
   //----------------------------------------------------------------
@@ -87,11 +97,14 @@ module rosc_entropy(
   //----------------------------------------------------------------
   // Wires.
   //----------------------------------------------------------------
-  wire [31 : 0] entropy;
+  wire [31 : 0] raw_entropy;
+  wire [31 : 0] rosc_outputs;
+
+  wire [31 : 0] internal_entropy_data;
+  wire          internal_entropy_valid;
+  wire          internal_entropy_ack;
+  reg           api_entropy_ack;
 
-  wire [31 : 0] rnd_data;
-  wire          rnd_valid;
-  reg           rnd_ack;
 
   reg [31 : 0]  tmp_read_data;
   reg           tmp_error;
@@ -100,8 +113,13 @@ module rosc_entropy(
   //----------------------------------------------------------------
   // Concurrent connectivity for ports etc.
   //----------------------------------------------------------------
-  assign read_data = tmp_read_data;
-  assign error     = tmp_error;
+  assign read_data            = tmp_read_data;
+  assign error                = tmp_error;
+  assign security_error       = 0;
+
+  assign internal_entropy_ack = api_entropy_ack | entropy_ack;
+  assign entropy_data         = internal_entropy_data;
+  assign entropy_data_valid   = internal_entropy_valid;
 
 
   //----------------------------------------------------------------
@@ -111,16 +129,17 @@ module rosc_entropy(
                          .clk(clk),
                          .reset_n(reset_n),
 
-                         .enable(en_reg),
+                         .en(en_reg),
 
                          .opa(op_a_reg),
                          .opb(op_b_reg),
 
-                         .entropy(entropy),
+                         .raw_entropy(raw_entropy),
+                         .rosc_outputs(rosc_outputs),
 
-                         .rnd_data(rnd_data),
-                         .rnd_valid(rnd_valid),
-                         .rnd_ack(rnd_ack),
+                         .entropy_data(internal_entropy_data),
+                         .entropy_valid(internal_entropy_valid),
+                         .entropy_ack(internal_entropy_ack),
 
                          .debug(debug),
                          .debug_update(debug_update)
@@ -139,8 +158,8 @@ module rosc_entropy(
       if (!reset_n)
         begin
           en_reg   <= 1;
-          op_a_reg <= 32'h01010101;
-          op_a_reg <= 32'h10101010;
+          op_a_reg <= DEFAULT_OP_A;
+          op_b_reg <= DEFAULT_OP_B;
         end
       else
         begin
@@ -158,7 +177,6 @@ module rosc_entropy(
             begin
               op_b_reg <= op_b_new;
             end
-
          end
     end // reg_update
 
@@ -171,15 +189,15 @@ module rosc_entropy(
   //----------------------------------------------------------------
   always @*
     begin : api_logic
-      en_new        = 0;
-      en_we         = 0;
-      op_a_new      = 0;
-      op_a_we       = 0;
-      op_b_new      = 0;
-      op_b_we       = 0;
-      rnd_ack       = 0;
-      tmp_read_data = 32'h00000000;
-      tmp_error     = 0;
+      en_new          = 0;
+      en_we           = 0;
+      op_a_new        = 0;
+      op_a_we         = 0;
+      op_b_new        = 0;
+      op_b_we         = 0;
+      api_entropy_ack = 0;
+      tmp_read_data   = 32'h00000000;
+      tmp_error       = 0;
 
       if (cs)
         begin
@@ -193,13 +211,13 @@ module rosc_entropy(
                     en_we  = 1;
                   end
 
-                ADDR_OPA:
+                ADDR_OP_A:
                   begin
                     op_a_new = write_data;
                     op_a_we  = 1;
                   end
 
-                ADDR_OPB:
+                ADDR_OP_B:
                   begin
                     op_b_new = write_data;
                     op_b_we  = 1;
@@ -221,28 +239,33 @@ module rosc_entropy(
 
                 ADDR_STATUS:
                   begin
-                    tmp_read_data[STATUS_RND_VALID_BIT] = rnd_valid;
+                    tmp_read_data[STATUS_ENTROPY_VALID_BIT] = entropy_valid;
                   end
 
-              ADDR_OPA:
-                begin
-                  tmp_read_data = op_a_reg;
-                end
+                ADDR_OP_A:
+                  begin
+                    tmp_read_data = op_a_reg;
+                  end
 
-              ADDR_OPB:
-                begin
-                  tmp_read_data = op_b_reg;
-                end
+                ADDR_OP_B:
+                  begin
+                    tmp_read_data = op_b_reg;
+                  end
 
                 ADDR_ENTROPY:
                   begin
-                    tmp_read_data = entropy;
+                    tmp_read_data = entropy_data;
+                    api_entropy_ack = 1;
+                  end
+
+                ADDR_RAW:
+                  begin
+                    tmp_read_data = raw_entropy;
                   end
 
-                ADDR_RND:
+                ADDR_ROSC_OUTPUTS:
                   begin
-                    tmp_read_data = rnd_data;
-                    rnd_ack       = 1;
+                    tmp_read_data = rosc_outputs;
                   end
 
                 default:
diff --git a/src/rtl/rosc_entropy_core.v b/src/rtl/rosc_entropy_core.v
index 5b4b8c4..98e08e6 100644
--- a/src/rtl/rosc_entropy_core.v
+++ b/src/rtl/rosc_entropy_core.v
@@ -40,16 +40,17 @@ module rosc_entropy_core(
                          input wire           clk,
                          input wire           reset_n,
 
-                         input wire           enable,
+                         input wire           en,
 
                          input wire [31 : 0]  opa,
                          input wire [31 : 0]  opb,
 
-                         output [31 : 0]      entropy,
+                         output wire [31 : 0] raw_entropy,
+                         output wire [31 : 0] rosc_outputs,
 
-                         output wire [31 : 0] rnd_data,
-                         output wire          rnd_valid,
-                         input wire           rnd_ack,
+                         output wire [31 : 0] entropy_data,
+                         output wire          entropy_valid,
+                         input wire           entropy_ack,
 
                          output wire [7 : 0]  debug,
                          input wire           debug_update
@@ -59,6 +60,7 @@ module rosc_entropy_core(
   //----------------------------------------------------------------
   // Parameters.
   //----------------------------------------------------------------
+  parameter DEBUG_DELAY       = 32'h002c4b40;
   parameter NUM_SHIFT_BITS    = 8'h20;
   parameter SAMPLE_CLK_CYCLES = 8'hff;
 
@@ -68,16 +70,14 @@ module rosc_entropy_core(
   //----------------------------------------------------------------
   reg [31 : 0] ent_shift_reg;
   reg [31 : 0] ent_shift_new;
+  reg          ent_shift_we;
 
-  reg          ent_shift_we_reg;
-  reg          ent_shift_we_new;
+  reg [31 : 0] entropy_reg;
+  reg          entropy_we;
 
-  reg [31 : 0] rnd_reg;
-  reg          rnd_we;
-
-  reg          rnd_valid_reg;
-  reg          rnd_valid_new;
-  reg          rnd_valid_we;
+  reg          entropy_valid_reg;
+  reg          entropy_valid_new;
+  reg          entropy_valid_we;
 
   reg          bit_we_reg;
   reg          bit_we_new;
@@ -90,7 +90,13 @@ module rosc_entropy_core(
   reg [7 : 0]  sample_ctr_reg;
   reg [7 : 0]  sample_ctr_new;
 
+  reg [31 : 0] debug_delay_ctr_reg;
+  reg [31 : 0] debug_delay_ctr_new;
+  reg          debug_delay_ctr_we;
+
   reg [7 : 0]  debug_reg;
+  reg          debug_we;
+
   reg          debug_update_reg;
 
 
@@ -104,10 +110,11 @@ module rosc_entropy_core(
   //----------------------------------------------------------------
   // Concurrent connectivity for ports etc.
   //----------------------------------------------------------------
-  assign entropy   = ent_shift_reg;
-  assign rnd_data  = rnd_reg;
-  assign rnd_valid = rnd_valid_reg;
-  assign debug     = debug_reg;
+  assign rosc_outputs  = rosc_dout;
+  assign raw_entropy   = ent_shift_reg;
+  assign entropy_data  = entropy_reg;
+  assign entropy_valid = entropy_valid_reg;
+  assign debug         = debug_reg;
 
 
   //----------------------------------------------------------------
@@ -142,22 +149,21 @@ module rosc_entropy_core(
     begin
       if (!reset_n)
         begin
-          ent_shift_reg    <= 32'h00000000;
-          ent_shift_we_reg <= 0;
-          rnd_reg          <= 32'h00000000;
-          rnd_valid_reg    <= 0;
-          bit_ctr_reg      <= 8'h00;
-          sample_ctr_reg   <= 8'h00;
-          debug_reg        <= 8'h00;
-          debug_update_reg <= 0;
+          ent_shift_reg       <= 32'h00000000;
+          entropy_reg         <= 32'h00000000;
+          entropy_valid_reg   <= 0;
+          bit_ctr_reg         <= 8'h00;
+          sample_ctr_reg      <= 8'h00;
+          debug_delay_ctr_reg <= 32'h00000000;
+          debug_reg           <= 8'h00;
+          debug_update_reg    <= 0;
         end
       else
         begin
           sample_ctr_reg   <= sample_ctr_new;
-          ent_shift_we_reg <= ent_shift_we_new;
           debug_update_reg <= debug_update;
 
-          if (ent_shift_we_reg)
+          if (ent_shift_we)
             begin
               ent_shift_reg <= ent_shift_new;
             end
@@ -167,38 +173,69 @@ module rosc_entropy_core(
               bit_ctr_reg <= bit_ctr_new;
             end
 
-          if (rnd_we)
+          if (entropy_we)
+            begin
+              entropy_reg <= ent_shift_reg;
+            end
+
+          if (entropy_valid_we)
             begin
-              rnd_reg <= ent_shift_reg;
+              entropy_valid_reg <= entropy_valid_new;
             end
 
-          if (rnd_valid_we)
+          if (debug_delay_ctr_we)
             begin
-              rnd_valid_reg <= rnd_valid_new;
+              debug_delay_ctr_reg <= debug_delay_ctr_new;
             end
 
-          if (debug_update_reg)
+          if (debug_we)
             begin
-              debug_reg <= rnd_reg[7 : 0];
+              debug_reg <= ent_shift_reg[7 : 0];
             end
          end
     end // reg_update
 
 
   //----------------------------------------------------------------
-  // rnd_out
+  // debug_out
+  //
+  // Logic that updates the debug port.
+  //----------------------------------------------------------------
+  always @*
+    begin : debug_out
+      debug_delay_ctr_new = 8'h00000000;
+      debug_delay_ctr_we  = 0;
+      debug_we            = 0;
+
+      if (debug_update_reg)
+        begin
+          debug_delay_ctr_new = debug_delay_ctr_reg + 1'b1;
+          debug_delay_ctr_we  = 1;
+        end
+
+      if (debug_delay_ctr_reg == DEBUG_DELAY)
+        begin
+          debug_delay_ctr_new = 8'h00000000;
+          debug_delay_ctr_we  = 1;
+          debug_we            = 1;
+        end
+    end
+
+
+  //----------------------------------------------------------------
+  // entropy_out
   //
   // Logic that implements the random output control. If we have
-  // added more than NUM_SHIFT_BITS we raise the rnd_valid flag.
+  // added more than NUM_SHIFT_BITS we raise the entropy_valid flag.
   // When we detect and ACK, the valid flag is dropped.
   //----------------------------------------------------------------
   always @*
-    begin : rnd_out
-      bit_ctr_new   = 8'h00;
-      bit_ctr_we    = 0;
-      rnd_we        = 0;
-      rnd_valid_new = 0;
-      rnd_valid_we  = 0;
+    begin : entropy_out
+      bit_ctr_new       = 8'h00;
+      bit_ctr_we        = 0;
+      entropy_we        = 0;
+      entropy_valid_new = 0;
+      entropy_valid_we  = 0;
 
       if (bit_ctr_inc)
         begin
@@ -210,52 +247,48 @@ module rosc_entropy_core(
             end
           else
             begin
-              rnd_we        = 1;
-              rnd_valid_new = 1;
-              rnd_valid_we  = 1;
+              entropy_we        = 1;
+              entropy_valid_new = 1;
+              entropy_valid_we  = 1;
             end
         end
 
-      if (rnd_ack)
+      if (entropy_ack)
         begin
-          bit_ctr_new   = 8'h00;
-          bit_ctr_we    = 1;
-          rnd_valid_new = 0;
-          rnd_valid_we  = 1;
+          bit_ctr_new       = 8'h00;
+          bit_ctr_we        = 1;
+          entropy_valid_new = 0;
+          entropy_valid_we  = 1;
         end
     end
 
 
   //----------------------------------------------------------------
-  // rnd_gen
+  // entropy_gen
   //
-  // Logic that implements the actual random bit value generator
+  // Logic that implements the actual entropy bit value generator
   // by XOR mixing the oscillator outputs. These outputs are
   // sampled once every SAMPLE_CLK_CYCLES.
-  //
-  // Note that the update of the shift register is delayed
-  // one cycle to allow the outputs from the oscillators
-  // to be updated.
   //----------------------------------------------------------------
   always @*
-    begin : rnd_gen
+    begin : entropy_gen
       reg ent_bit;
 
-      bit_ctr_inc      = 0;
-      rosc_we          = 0;
-      ent_shift_we_new = 0;
+      bit_ctr_inc  = 0;
+      rosc_we      = 0;
+      ent_shift_we = 0;
 
       ent_bit        = ^rosc_dout;
       ent_shift_new  = {ent_shift_reg[30 : 0], ent_bit};
 
       sample_ctr_new = sample_ctr_reg + 1'b1;
 
-      if (enable && (sample_ctr_reg == SAMPLE_CLK_CYCLES))
+      if (en && (sample_ctr_reg == SAMPLE_CLK_CYCLES))
         begin
           sample_ctr_new   = 8'h00;
           bit_ctr_inc      = 1;
           rosc_we          = 1;
-          ent_shift_we_new = 1;
+          ent_shift_we     = 1;
         end
     end
 endmodule // rosc_entropy_core
-- 
cgit v1.2.3