专栏前言
本专栏的内容主要是记录本人学习Verilog过程中的一些知识点,刷题网站用的是牛客网
1、寄存器的位是可以分开单独运算的,并不是一个输入就一定是一个数据,在很多情况下,一个输入既包括数据又包括地址等其他有效信息
2、需要考虑数据锁存的问题,一定要在sel为0的时候进行锁存,只有此时的写入才是有效的(validout的下降沿写入有效),同时存在多种情况且没有优先级问题,建议使用case语句
- `timescale 1ns/1ns
-
- module data_cal(
- input clk,
- input rst,
- input [15:0]d,
- input [1:0]sel,
-
- output reg [4:0] out,
- output reg validout
- );
- //*************code***********//
- reg [15:0] data_lock ;
-
- always @ (posedge clk or negedge rst) begin
- if (~rst)
- data_lock <= 0 ;
- else if (!sel)
- data_lock <= d ;
- end
-
- always @ (posedge clk or negedge rst) begin
- if (~rst) begin
- out <= 1'b0 ;
- validout <= 0 ;
- end
- else begin
- case (sel)
- 0 : begin
- out <= 1'b0 ;
- validout <= 0 ;
- end
- 1 : begin
- out <= data_lock[3:0] + data_lock[7:4] ;
- validout <= 1 ;
- end
- 2 : begin
- out <= data_lock[3:0] + data_lock[11:8] ;
- validout <= 1 ;
- end
- 3 : begin
- out <= data_lock[3:0] + data_lock[15:12] ;
- validout <= 1 ;
- end
- endcase
- end
- end
-
- //*************code***********//
- endmodule
Testbench
- `timescale 1ns/1ns
-
- module testbench();
- reg clk = 1 ;
- always #5 clk = ~clk ; // Create clock with period=10
- // A testbench
- reg rst ;
- reg [15:0] d ;
- reg [1:0] sel ;
- wire [4:0] out ;
- wire validout ;
-
- data_cal u1(
- .clk(clk),
- .rst(rst),
- .d(d),
- .sel(sel),
- .out(out),
- .validout(validout)
- );
-
- initial begin
- rst = 0 ;
- # 10 ;
- rst = 1 ;
- # 150 ;
- end
-
- initial begin
- sel = 0 ;
- # 30 sel = 2 ;
- # 30 sel = 1 ;
- # 30 sel = 0 ;
- # 10 sel = 3 ;
- # 50 ;
- $finish ;
- end
-
- initial begin
- d = 16'b0 ;
- # 20 d = 16'b1000010000100001 ;
- # 40 d = 16'b1000010000100011 ;
- # 50 d = 16'b1000010000100111 ;
- # 40 ;
- end
- //end
- initial begin
- $dumpfile("out.vcd");
- // This will dump all signal, which may not be useful
- //$dumpvars;
- // dumping only this module
- //$dumpvars(1, testbench);
- // dumping only these variable
- // the first number (level) is actually useless
- $dumpvars(0, testbench);
- end
-
- endmodule