三段式状态机
优点:容易消除毛刺现象
模板:
//第一个进程,同步时序always模块,格式化描述次态寄存器迁移到现态寄存器
always @ (posedge clk or negedge rst_n) //异步复位
if(!rst_n)
current_state <= IDLE;
else
current_state <= next_state; //注意,使用的是非阻塞赋值
//第二个进程,组合逻辑always模块,描述状态转移条件判断
always @ (current_state) //电平触发
begin
next_state = x; //要初始化,使得系统复位后能进入正确的状态
case(current_state)
S1: if(...)
next_state = S2; //阻塞赋值
...
endcase
end
//第三个进程,同步时序always模块,格式化描述次态寄存器输出
always @ (posedge clk or negedge rst_n)
...//初始化
case(next_state)
S1:
out1 <= 1'b1; //注意是非阻塞逻辑
S2:
out2 <= 1'b1;
default:... //default的作用是免除综合工具综合出锁存器
endcase
end
案例:
module state3 ( nrst,clk,
i1,i2,
o1,o2,
err
);
input nrst,clk;
input i1,i2;
output o1,o2,err;
reg o1,o2,err;
reg [2:0] NS,CS;
parameter [2:0] //one hot with zero idle
IDLE = 3'b000,
S1 = 3'b001,
S2 = 3'b010,
ERROR = 3'b100;
//描述次态寄存器 迁移到现态寄存器
always @ (posedge clk or negedge nrst)
if (!nrst)
CS <= IDLE;
else
CS <=NS;
//描述状态转移条件判断
always @ (nrst or CS or i1 or i2)
begin
NS = 3'bx;
case (CS)
IDLE: begin
if (~i1) NS = IDLE;
if (i1 && i2) NS = S1;
if (i1 && ~i2) NS = ERROR;
end
S1: begin
if (~i2) NS = S1;
if (i2 && i1) NS = S2;
if (i2 && (~i1)) NS = ERROR;
end
S2: begin
if (i2) NS = S2;
if (~i2 && i1) NS = IDLE;
if (~i2 && (~i1)) NS = ERROR;
end
ERROR: begin
if (i1) NS = ERROR;
if (~i1) NS = IDLE;
end
endcase
end
//3描述次态寄存器输出
always @ (posedge clk or negedge nrst)
if (!nrst)
{o1,o2,err} <= 3'b000;
else
begin
{o1,o2,err} <= 3'b000;
case (NS)
IDLE: {o1,o2,err}<=3'b000;
S1: {o1,o2,err}<=3'b100;
S2: {o1,o2,err}<=3'b010;
ERROR: {o1,o2,err}<=3'b111;
endcase
end
endmodule