移位寄存器专题(verilog HDL设计)

移位寄存器

移位寄存器内的数据可以在移位脉冲(时钟信号)的作用下依次左移或右移。移位寄存器不仅可以存储数据,还可以用来实现数据的串并转换、分频,构成序列码发生器、序列码检测器,进行数值运算以及数据处理等,它也是数字系统中应用非常广泛的时序逻辑部件之一。

移位寄存器按数据移位方向可以分为左移寄存器、右移寄存器、也可以根据数据输入、输出方式分为并行输入/串行输出、串行输入/并行输出、串行输入/串行输出、并行输入/并行输出。

下图是一个4位右移位寄存器的逻辑电路图。其工作原理为:串行数据从触发器DI端输入,触发器FA的状态方程为:。其余触发器的状态方程分别为,,。可见,右移位寄存器的特点是右边寄存器的次态等于左边触发器的现态。串行输出数据从触发器FDQD端输出,并行数据从个触发器的QA~QD端输出,两种输出方式都属于同向输出。各触发器都采用同一时钟信号,所以它们工作在同步状态。如果将FD的输出端QD接到FA的输入端DI,则可以构成循环移位的右移位寄存器。

 

4位右移位寄存器逻辑电路

 

1、 16位右移位寄存器

下面描述的是一个位宽为16位的右移位寄存器,实际具有环形移位的功能,是在右移位寄存器的基础上将最低位的输出端接到最高位的输入端构成的。其功能为当时钟上升沿到达时,输入信号的最低位移位到最高位,其余各位依次向右移动一位。

 

verilog HDL设计代码如下:

 

1. module register_right(clk, din, dout);  

2.     input clk;  

3.     input [15:0] din;  

4.     output [15:0] dout;  

5.     reg [15:0] dout;  

6.   

7.     always @(posedge clk)  

8.         begin  

9.             dout <= {din[0], din[15:1]};  

10.         end  

11. endmodule  

其测试文件为:

1. `timescale 1ns/1ps  

2. module register_right_tb;  

3.     reg clk;  

4.     reg [15:0] din;  

5.     wire [15:0] dout;  

6.     always  

7.         begin  

8.         #10 clk = ~clk;  

9.         end  

10.     initial  

11.         begin  

12.             clk = 1'b0;  

13.             din = 16'b0000_0000_0000_0000;  

14.             #10 din = 16'b0000_0000_0000_1011;  

15.             #20 din = 16'b0000_0000_0111_0000;  

16.             #20 din = 16'b0000_0000_0000_0011;  

17.             #100;  

18.         end  

19.     register_right U1(.clk(clk), .din(din), .dout(dout));  

20.   

21. endmodule  

Modelsim中仿真得到的波形图如下:

  

2、 16位左移寄存器

同右移位寄存器原理一致,下面直接给出verilog HDL 设计代码:

1. module register_left(clk, din, dout);  

2.     input clk;  

3.     input [15:0] din;  

4.     output [15:0] dout;  

5.     reg [15:0] dout;  

6.       

7.     always @(posedge clk)  

8.         begin  

9.             dout <= {din[14:0], din[15]};  

10.         end  

11. endmodule  

测试文件为:

1. `timescale 1ns/1ps  

2. module register_left_tb;  

3.     reg clk;  

4.     reg [15:0] din;  

5.     wire [15:0] dout;  

6.       

7.     always  

8.         #10 clk = ~clk;  

9.           

10.     initial  

11.         begin  

12.             clk = 1'b0;  

13.             din = 16'b0000_0000_0000_0000;  

14.             #10 din = 16'b0000_0000_0000_0011;  

15.             #20 din = 16'b0000_0000_0011_0000;  

16.             #100;  

17.         end  

18.           

19.     register_left U1(.clk(clk), .din(din), .dout(dout));  

20. endmodule  

Modelsim中仿真所得波形图如下:

 

 3、 串行输入并行输出寄存器

下面描述一个位宽为8的串行输入并行输出的寄存器,其实现的功能为:1位数据的串行输入,8位数据的并行输出。当时钟上升沿到达时,1位输入数据din进入qtemp的最低位,qtemp的其余各位依次向左移动1位,在assign 赋值语句中,将qtemp连续赋值给dout,实现8位的数据并行输出。

 verilog HDL设计代码为:

1. module left_shifter_reg(clk, din, dout);  

2.     input clk;  

3.     input din;  

4.     output [7:0] dout;  

5.     wire [7:0] dout;  

6.     reg [7:0] qtemp;  

7.     always @ (posedge clk)  

8.         begin  

9.             qtemp <= {qtemp[6:0], din}; //每次输入一位  

10.         end  

11.     assign dout = qtemp; //并行输出  

12.   

13. endmodule  

测试文件为:

1. module left_shifter_reg_tb;  

2.     reg din;  

3.     reg clk;  

4.     wire [7:0] dout;  

5.       

6.     always   

7.         #10 clk = ~clk;  

8.       

9.     initial  

10.         begin  

11.             clk = 1'b0;  

12.             #100 din = 1'b1;  

13.             #100 din = 1'b1;  

14.             #100 din = 1'b0;  

15.         end  

16.           

17.     left_shifter_reg U1(.din(din), .clk(clk), .dout(dout));  

18. endmodule  

 Modelsim中仿真所得波形图:

  


4、 并行输入串行输出移位寄存器

 

下面描述一个位宽为8的并行输入串行输出的寄存器,其实现的功能为:当使能端 en = 1时,将输入数据din存入一个8位的中间变量,然后在每个时钟上升沿到来时,将qtemp的最低端输出,然后再将qtemp右移一位,从而实现将din输入数据从最低位到最高位依次串行输出。

 

verilog HDL设计代码为:

1. module right_shifter_reg(clk, en, din, dout);  

2.     input [7:0] din;  

3.     input en,clk;  

4.     output dout;  

5.     reg dout;  

6.     reg [7:0] qtemp;  

7.     always @(posedge clk)  

8.         begin  

9.             if(en == 1)  

10.                 qtemp <= din;  

11.             else  

12.                 begin  

13.                     dout <= qtemp[0];  

14.                     qtemp <= {qtemp[0], qtemp[7:1]};  

15.                 end  

16.         end  

17.   

18. endmodule 

测试文件为:

1. `timescale 1ns/1ps  

2. module right_shifter_reg_tb;  

3.     reg [7:0] din;  

4.     reg clk;  

5.     reg en;  

6.     wire dout;  

7.       

8.     always  

9.         #10 clk = ~clk;  

10.       

11.     initial  

12.         begin  

13.             clk = 0;  

14.             en = 1'b0;  

15.             #10 en = 1'b1;  

16.             din = 8'b1110_0010;  

17.             #20 en = 1'b0;  

18.             #100;  

19.         end  

20.     right_shifter_reg U1(.clk(clk), .en(en), .din(din), .dout(dout));  

21.   

22. endmodule  

Modelsim中仿真所得波形图如下:

 

 

猜你喜欢

转载自blog.csdn.net/Reborn_Lee/article/details/80377919