Verilog Code for SIPO Shift Register: Syntax and Example
A Serial-In Parallel-Out (SIPO) shift register in Verilog reads data serially on each clock pulse and outputs the stored bits in parallel. Use a
reg array to store bits, shift them on the clock's rising edge, and output the register content in parallel.Syntax
The basic syntax for a SIPO shift register includes defining inputs for clock and serial data, an output for parallel data, and a reg array to hold the bits. On each rising edge of the clock, the register shifts left and the new serial bit is loaded at the rightmost position.
input clk: Clock signal to trigger shifting.input serial_in: Serial data input bit.output reg [N-1:0] parallel_out: Parallel output of all stored bits.always @(posedge clk): Block triggered on clock rising edge.- Shift register logic:
parallel_out << 1shifts bits left, new bit loaded at LSB.
verilog
module sipo_shift_register(
input clk,
input serial_in,
output reg [3:0] parallel_out
);
always @(posedge clk) begin
parallel_out <= {parallel_out[2:0], serial_in};
end
endmoduleExample
This example shows a 4-bit SIPO shift register. It takes serial bits one by one on serial_in at each clock pulse and outputs the 4-bit parallel value on parallel_out. The bits shift left, with the newest bit entering at the right.
verilog
module sipo_shift_register(
input clk,
input serial_in,
output reg [3:0] parallel_out
);
always @(posedge clk) begin
parallel_out <= {parallel_out[2:0], serial_in};
end
endmodule
// Testbench
module testbench();
reg clk = 0;
reg serial_in = 0;
wire [3:0] parallel_out;
sipo_shift_register uut(.clk(clk), .serial_in(serial_in), .parallel_out(parallel_out));
always #5 clk = ~clk; // 10 time units clock period
initial begin
// Send bits 1,0,1,1 serially
serial_in = 1; #10;
serial_in = 0; #10;
serial_in = 1; #10;
serial_in = 1; #10;
$finish;
end
initial begin
$monitor("At time %0t: parallel_out = %b", $time, parallel_out);
end
endmoduleOutput
At time 10: parallel_out = 0001
At time 20: parallel_out = 0010
At time 30: parallel_out = 0101
At time 40: parallel_out = 1011
Common Pitfalls
Common mistakes when writing a SIPO shift register include:
- Not using a clock edge trigger (
posedge clk) causing incorrect timing. - Forgetting to declare
parallel_outasreg, which is needed for assignment insidealwaysblocks. - Incorrect bit concatenation order, which reverses the bit order.
- Not initializing the register, which can cause unknown outputs at start.
verilog
/* Wrong: Using blocking assignment and no clock edge */ always @(*) begin parallel_out = {parallel_out[2:0], serial_in}; // Wrong: combinational, no clock end /* Right: Use non-blocking assignment on posedge clock */ always @(posedge clk) begin parallel_out <= {parallel_out[2:0], serial_in}; end
Quick Reference
Tips for writing SIPO shift registers in Verilog:
- Use
always @(posedge clk)for synchronous shifting. - Use non-blocking assignment
<=insidealwaysblocks. - Concatenate bits with
{}to shift and insert new bit. - Declare output as
regif assigned insidealways. - Initialize registers if needed to avoid unknown states.
Key Takeaways
Use a clock edge triggered always block to shift bits synchronously.
Declare the parallel output as reg to assign inside always blocks.
Shift bits by concatenating the register with the new serial input.
Use non-blocking assignments (<=) for correct sequential logic.
Initialize registers to avoid unknown startup values.