title: Verilog module generates impossible data when running on FPGA
body: <p>I’m developing a boolean data logger on a ZYNQ 7000 SoC. The logger takes a boolean input from GPIO and logs the input’s value and the time it takes to flip.</p>
  <p>I use a 32-bit register as a log entry, the MSB bit is the boolean value. The 30:0 bits is an unsigned integer which records the time between last 2 flips. The logger should work like the following picture.</p>
  <p><a href="https://i.stack.imgur.com/rgO5A.png" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/rgO5A.png" alt="logger" /></a></p>
  <p>Here's my implementation of the logger in Verilog. To read the logged data from the processor, I use an AXI slave interface generated by vivado and inline my logger in the AXI module.</p>
  <pre><code>module BoolLogger_AXI #(
      parameter BufferDepth = 512
  )(
      input wire data_in, // boolean input
      input wire S_AXI_ACLK, // clock
      input wire S_AXI_ARESETN, // reset_n
      // other AXI signals
  );
  wire slv_reg_wren; // write enable of AXI interface
  reg[31:0] buff[0:BufferDepth-1];
  
  reg[15:0] idx;
  reg[31:0] count;
  reg last_data;
  always @(posedge S_AXI_ACLK) begin
      if((!S_AXI_ARESETN) || slv_reg_wren) begin
          idx &lt;= 0;
          count &lt;= 1;
          last_data &lt;= data_in;
      end else begin
          if(last_data!=data_in) begin // add an entry only when input flips
              last_data &lt;= data_in;
              if(idx &lt; BufferDepth) begin // stop logging if buffer is full
                  buff[idx] &lt;= count | (data_in &lt;&lt; 31);
                  idx &lt;= idx + 1;
              end
              count &lt;= 1;
          end else begin
              count &lt;= count + 1;
          end
      end
  end
  
  //other AXI stuff
  endmodule
  </code></pre>
  <p><a href="https://i.stack.imgur.com/RpaeO.jpg" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/RpaeO.jpg" alt="block design" /></a></p>
  <p>In the AXI module, the 512*32bit logged data is mapped to addresses from 0x43c20000 to 0x43c20800.</p>
  <p>In the Verilog code, the logger adds a new entry only when the boolean input flips. In simulation, the module works as expected. But in the FPGA, sometimes the logged data is not valid. There are successive 2 data and their MSB bit is the same, which means the entry is added even when the boolean input stays the same.</p>
  <p><a href="https://i.stack.imgur.com/rVi8p.jpg" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/rVi8p.jpg" alt="logged data" /></a></p>
  <p>The invalid data appear from time to time. I've tried reading from the address programmatically (<code>*(u32*)(0x43c20000+4*idx)</code>), and there are still invalid data. I watch <code>idx</code> in a ILA module and <code>idx</code> is 512, which means the logging finishes when I read the data.</p>
  <p>The FPGA clock is 10 MHz. The input signal is 10 Hz. So the typical period is 10e6/10/2=0x7A120, which most of the data is close to, except the invalid data.</p>
  <p>I think if the Verilog code is implemented well, there should be no such invalid data. What may be the problem? Is this an issue about timing?</p>
  <p><a href="https://github.com/mjs225/BoolLogger" rel="nofollow noreferrer">The code</a></p>