veriloghdl

Parallel shift of 4-bits by 1 clock cycle, simulation of delay on Verilog


I want to implement the following timing diagram (the numbers here are arbitrary, the main thing is the general principle). In my task a sequence of 4-bit data. This sequence must be written to registers A, B and C and shifted in each corresponding register by 1 clock cycle relative to the previous one.

enter image description here

Here is my code on Verilog:

module shift4bit(clock, data, out, outRegA, outRegB, outRegC);
input clock;
input [3:0] data;
output [3:0] out;
output [3:0] outRegA;
output [3:0] outRegB;
output [3:0] outRegC;

reg [3:0] RegA;
reg [3:0] RegB;
reg [3:0] RegC;

always @(posedge clock) begin
  RegA <= data;
  RegB <= RegA;
  RegC <= RegB;
end

assign out = data;
assign outRegA = RegA;
assign outRegB = RegB;
assign outRegC = RegC;

endmodule

And testbench:

`timescale 1ns / 1ps

module shift4bit_tb; 

// Inputs
reg [3:0] data;
reg clock;
// Outputs
wire [3:0] out;
wire [3:0] outRegA;
wire [3:0] outRegB;
wire [3:0] outRegC;

// Instantiate the Unit Under Test (UUT)
shift4bit uut (.clock(clock),.data(data),.out(out),.outRegA(outRegA),.outRegB(outRegB),.outRegC(outRegC));

initial begin
  // Initialize Inputs
  data  = 4'b1111;
  clock  = 1'b1;
  // Wait 100 ns for global reset to finish
  #20;
  // Add stimulus here
  data = 4'b0001; #20;
  data = 4'b0010; #20;
  data = 4'b0011; #20;
  data = 4'b0100; #20;
  data = 4'b0101; #20;
  data = 4'b0110; #20;
  data = 4'b0111; #20;
  data = 4'b1000; #20;
end

always #10 clock = ~clock;  

endmodule

I got the following result. There seems to be a shift. Tell me, is my code correct and can it be synthesized into a real circuit on an FPGA?

enter image description here


Solution

  • It would be better to re-write testbench like this:

    @( posedge clock );
    data <= 4'b0001;
    @( posedge clock );
    data <= 4'b0010;
    @( posedge clock );
    data <= 4'b0011;
    @( posedge clock );
    

    Because if you use '=', posedge clock and data changes at the same time, simulator cannot determine which one comes first. If it treats data change first, then the posedge clock, you will see data passes to outRegA without 1 clock cycle latency.

    In a real design, D flip-flop output is slightly behind posedge clock. So put the "@( posedge clock )" in testbench to make sure of this.