1、结构化过程语句
verilog有两种结构化过程语句: always initial
verilog本质上是并发的。
//声明初值
//方法一
reg clk ;
initial
clk = 1'b0 ;
//方法二
reg clk = 1'b0 ;
2、过程赋值语句
阻塞赋值
非阻塞赋值
非阻塞赋值可以避免竞争:
第一种阻塞赋值会产生竞争的情况,a = b b = a 执行的先后取决与仿真器。
第二种非阻塞赋值避免了竞争,达到了 交换 a b 的效果。
//阻塞赋值
always@( posedge clk )
begin
a = b ;
end
always@( posedge clk )
begin
b = a ;
end
//非阻塞赋值
always@( posedge clk )
begin
a <= b ;
end
always@( posedge clk )
begin
b <= a ;
end
3、时序控制
verilog提供三种时序控制方法:
基于延迟的时序控制、基于事件的时序控制、电平敏感的时序控制
基于延迟的时序控制
initial
begin
x = 1'b0 ;
#10
x = 1'b1 ;
end
基于事件的时序控制
常规事件控制、命名事件控制、or事件控制、电平敏感时序控制
//命名事件控制
event received_data ;
always@( posedge clk )
begin
if( last_data )
begin
->received_data ;
end
end
always@( received_data )
begin
data = ......... ;
end
->received_data 表示事件的触发。关键词 event 表示 事件 。
电平敏感的时序控制
always
wait(count_enable) #20 count = count + 1'b1 ;
当 count_enable为 1 的时候执行,为0的时候仿真会不执行后面的语句,会停顿下来。
4、条件语句
if( )
begin
end
else if( )
begin
end
else
begin
end
5、多支路语句
case casex casez
always@( posedge clk )
begin
case( {s1,s0} )
2'd0: out = in1 ;
2'd1: out = in2 ;
2'd2: out = in3 ;
2'd3: out = in4 ;
default: out = in1 ;
endcase
end
6、循环语句
while for repeat forever
//while
while( )
begin
end
//for
for( ; ; )
begin
end
//repeat
repeat(128) ;//循环128次
//foreber
initial
begin
forever #10 clk = ~clk ;
end
7、顺序块和并行块
顺序块:语句按照顺序执行。
begin end
1、语句一条一条执行、
2、延迟 是相对于前面那条语句的完成时间。
并行块:所有语句一起执行。
fork join
块语句的命名:
always@( posedge clk )
begin:xxxxxxxx
end
块的禁用:disable
initial
begin
i = 0 ;
begin: block1
while( i < 16 )
begin
if( )
begin
disable block1 ;
end
end
end
end
8、生成块
genvar i ;
generate for( i = 0 ;i < 100 ;i=i+1 )
begin
end
endgenerate
9、demo 交通信号灯
code:
`timescale 1ns / 1ps
//
// Company:
// Engineer:
//
// Create Date: 2025/03/07 15:34:34
// Design Name:
// Module Name: sig_control
// Project Name:
// Target Devices:
// Tool Versions:
// Description:
//
// Dependencies:
//
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
//
//
`define TURE 1'b1
`define FALSE 1'b0
//延迟
`define Y2R_DELAY 3
`define R2G_DELAY 2
module sig_control(
output reg [1:0] hwy ,
output reg [1:0] cntry ,
input wire x ,
input wire clk ,
input wire rst_n
);
parameter RED = 2'd0 ;
parameter YELLOW = 2'd1 ;
parameter GREEN = 2'd2 ;
//定义状态 HEW CNTRY
parameter S0 = 3'd0 ;//green red
parameter S1 = 3'd1 ;//yellow red
parameter S2 = 3'd2 ;//red red
parameter S3 = 3'd3 ;//red green
parameter S4 = 3'd4 ;// red yellow
reg [2:0] state ;
reg [2:0] next_state ;
always@( posedge clk or negedge rst_n )
begin
if( rst_n == 0 )
begin
state <= S0 ;
end
else
begin
state <= next_state ;
end
end
always@(*)
begin
case( state )
S0:
begin
if( x == 1 )
begin
next_state = S1 ;
end
else
begin
next_state = S0 ;
end
end
S1:
begin
repeat(`Y2R_DELAY) @(posedge clk) ;
next_state = S2 ;
end
S2:
begin
repeat(`R2G_DELAY) @(posedge clk) ;
next_state = S3 ;
end
S3:
begin
if( x == 1 )
begin
next_state = S3 ;
end
else
begin
next_state = S4 ;
end
end
S4:
begin
repeat(`Y2R_DELAY) @( posedge clk ) ;
next_state = S0 ;
end
default:
begin
next_state = S0 ;
end
endcase
end
always@( posedge clk )
begin
case( state )
S0:
begin
hwy <= GREEN ;
cntry <= RED ;
end
S1:
begin
hwy <= YELLOW ;
cntry <= RED ;
end
S2:
begin
hwy <= RED ;
cntry <= RED ;
end
S3:
begin
hwy <= RED ;
cntry <= GREEN ;
end
S4:
begin
hwy <= RED ;
cntry <= ~YELLOW ;
end
default:
begin
hwy <= GREEN ;
cntry <= RED ;
end
endcase
end
endmodule
tb
`timescale 1ns / 1ps
//
// Company:
// Engineer:
//
// Create Date: 2025/03/07 15:35:01
// Design Name:
// Module Name: tb_sig_control
// Project Name:
// Target Devices:
// Tool Versions:
// Description:
//
// Dependencies:
//
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
//
//
module tb_sig_control();
wire [1:0] MAIN_SIG ,CNTRY_SIG ;
reg CAR_ON_CNTRY_RD ;
reg clk,rst_n ;
sig_control sig_control_inst
(
.hwy (MAIN_SIG) ,
.cntry (CNTRY_SIG) ,
.x (CAR_ON_CNTRY_RD) ,
.clk (clk) ,
.rst_n (rst_n)
);
initial
begin:monitor
$monitor($time,"Main_sig = %b Cntry_sig = %b CAR_ON_CNTRY_RD = %b ",MAIN_SIG,CNTRY_SIG,CAR_ON_CNTRY_RD ) ;
end
initial
begin // clk
clk = `TURE ;
forever #5 clk = ~clk ;
end
initial //rst
begin
rst_n = 1'b0 ;
repeat(5) @( posedge clk ) ;
rst_n = 1'b1 ;
end
initial
begin
CAR_ON_CNTRY_RD = 1'b0 ;
repeat (20) @( posedge clk ) ;
CAR_ON_CNTRY_RD = 1'b1 ;
repeat (10) @( posedge clk ) ;
CAR_ON_CNTRY_RD = 1'b0 ;
repeat (20) @( posedge clk ) ;
CAR_ON_CNTRY_RD = 1'b1 ;
repeat (10) @( posedge clk ) ;
CAR_ON_CNTRY_RD = 1'b0 ;
repeat (20) @( posedge clk ) ;
CAR_ON_CNTRY_RD = 1'b1 ;
repeat (10) @( posedge clk ) ;
CAR_ON_CNTRY_RD = 1'b0 ;
repeat ( 10 ) @( posedge clk ) ;
$stop ;
end
endmodule