Peter
Peter

Reputation: 508

Why is this code getting inferred latches?

I'm currently working on some Verilog code in Vivado, and even though I specified every possible path, somehow I'm receiving the "inferring latch for variable" message during the synthesis stage.

`timescale 1ns / 1ps //My implementation

module my_pe #(parameter L_RAM_SIZE = 4)
(
    //  clk //reset
    input aclk,
    input aresetn,
    // port A
    input [31:0] ain,
    // peram --> port B
    input [31:0] din,
    input [8-1:0] addr,
    input we,
    // integrated valid signal
    input valid,
    // computation result
    output dvalid,
    output [31:0] dout
);

(*ram_style = "block" *) reg [31:0] peram [0:2**L_RAM_SIZE-1]; // local register 
reg [32-1:0] bin;
reg [31:0] psum;
wire [31:0] result;

always @(we, din, addr) begin
    if (we==1) begin
        peram[addr] = din;
    end
    else begin
        bin = peram[addr];
    end
end

always @(aresetn, dvalid, result) begin
    if (!aresetn) begin
        psum = 0;
    end
    else
        if (dvalid ==1)
            psum = result;
        else
            psum = psum;
end 

The warning occurs in the two always blocks. Below are a few of the 100 "inferring latch" warning messages:

[Synth 8-327] inferring latch for variable 'peram_reg[15]'
[Synth 8-327] inferring latch for variable 'psum_reg'
[Synth 8-327] inferring latch for variable 'bin_reg'

Upvotes: 1

Views: 2344

Answers (2)

m4j0rt0m
m4j0rt0m

Reputation: 354

In order to don't infer latches, all the different states of your reg variables (if not clocked), should be well defined, if there is a missing logical state, the compiler would understand that the actual value has be latched and be saved until the next condition is encountered. For example:

input a, b;
reg c;

always @ (*) begin
  if(a)
    c = 10;
  else if(b)
    c = 12;
end

If you notice, there is a missing condition, where a and b are in 0, thus, this will infer a latch for reg c. This should be done as:

always @ (*) begin
  if(a)
    c = 10;
  else if(b)
    c = 12;
  else
    c = 0; //..just an example
end

Like this, all the logical conditions for reg c are well defined.

Upvotes: 2

toolic
toolic

Reputation: 62009

For the bin signal, the always block is triggered whenever any change occurs on these 3 signals:

we, din, addr

bin is only assigned a value when we is 0. When we is 1, bin retains its state. This infers a latch.

Your module has a clock input (aclk), but you do not show it being used. If you want to infer flip-flops, you should use something like:

always @(posedge clk)

Upvotes: 1

Related Questions