【第一季】CH05_FPGA设计Verilog基础(二)Enter a post title

第一季】CH05_FPGA设计Verilog基础(二)

5.1状态机设计

状态机是许多数字系统的核心部件,是一类重要的时序逻辑电路。通常包括三个部分:一是下一个状态的逻辑电路,二是存储状态机当前状态的时序逻辑电路,三是输出组合逻辑电路。通常,状态机的状态数量有限,称为有限状态机(FSM)。由于状态机所有触发器的时钟由同一脉冲边沿触发,故也称之为同步状态机。

根据状态机的输出信号是否与电路的输入有关分为Mealy型状态机和Moore型状态机。

1、Moore型有限状态机:是指那些输出信号仅与当前状态有关的有限状态机,即可以把Moore型有限状态机的输出看成是当前状态的函数。

806931-20170209193212744-948759872.png

2、Mealy型有限状态机:是指那些输出信号不仅与当前状态有关,而且还与所有的输入信号有关的有限状态机,即可以把Mealy有限状态机的输出看成是当前状态和所有输入信号的函数。可见,Mealy有限状态机要比Moore型有限状态机复杂一些。

806931-20170209193216026-1313031319.png

Moore型和Mealy型有限状态机的区别:Moore型有限状态机仅与当前状态有关,而与输入信号无关;Mealy型有限状态机不但与当前状态有关,而且还与状态机的输入信号有关。

状态机的状态转移图,通常也可根据输入和内部条件画出。一般来说,状态机的设计包含下列设计步骤:

• 根据需求和设计原则,确定是Moore型还是Mealy型状态机;

• 分析状态机的所有状态,对每一状态选择合适的编码方式,进行编码;

• 根据状态转移关系和输出绘出状态转移图;

• 构建合适的状态机结构,对状态机进行硬件描述。

状态机的描述通常有三种方法,称为一段式状态机,二段式状态机和三段式状态机。状态机的描述通常包含以下四部分:

1)利用参数定义语句parameter描述状态机各个状态名称,即状态编码。状态编码通常有很多方法包含自然二进制编码,One-hot编码,格雷编码码等;

2)用时序的always块描述状态触发器实现状态存储;

3)使用敏感表和case语句(也采用if-else等价语句)描述状态转换逻辑;

4)描述状态机的输出逻辑。

下面根据状态机的三种方法,来比较各种方法的优劣。

5.2一段式状态机

module detect_1(

input clk_i,

input rst_n_i,

output out_o

    );

reg out_r;

//状态声明和状态编码

reg [1:0] state;

parameter [1:0] S0=2'b00;

parameter [1:0] S1=2'b01;

parameter [1:0] S2=2'b10;

parameter [1:0] S3=2'b11;

always@(posedge clk_i)

begin

if(!rst_n_i)begin

state<=0;

      out_r<=1'b0;

    end

else

case(state)

S0 :

begin

   out_r<=1'b0;

   state<= S1;

end

S1 :

begin

out_r<=1'b1;

    state<= S2;

end

S2 :

begin

out_r<=1'b0;

state<= S3;

end

S3 :

begin

out_r<=1'b1;

end

endcase

end

assign out_o=out_r;

endmodule

一段式状态机是应该避免使用的,该写法仅仅适用于非常简单的状态机设计,不符合组合逻辑与时序逻辑分开的原则,整个结构代码也不清晰,不利用维护和修改。

5.3两段式状态机

module detect_2(

     input clk_i,

     input rst_n_i,

     output out_o

);

    reg out_r;

    //状态声明和状态编码

    reg [1:0] Current_state;

    reg [1:0] Next_state;

    parameter [1:0] S0=2'b00;

    parameter [1:0] S1=2'b01;

    parameter [1:0] S2=2'b10;

    parameter [1:0] S3=2'b11;

    //时序逻辑:描述状态转换

    always@(posedge clk_i)

    begin

        if(!rst_n_i)

           Current_state<=0;

        else

            Current_state<=Next_state;

    end

    //组合逻辑:描述下一状态和输出

    always@(*)

    begin

        out_r=1'b0;

        case(Current_state)

            S0 :

                begin

out_r=1'b0;

               Next_state= S1;

                end

            S1 :

                begin

              out_r=1'b1;

              Next_state= S2;

                end

            S2 :

                begin

              out_r=1'b0;

              Next_state= S3;

                end

            S3 :

                 begin

                out_r=1'b1;

               Next_state=Next_state;

                 end

            endcase

    end

    assign out_o=out_r;    

endmodule

两段式状态机采用两个always模块实现状态机的功能,其中一个always采用同步时序逻辑描述状态转移,另一个always采用组合逻辑来判断状态条件转移。两段式状态机是推荐的状态机设计方法。

5.4三段式状态机

module detect_3(

        input clk_i,

        input rst_n_i,

        output out_o

        );

    reg out_r;

    //状态声明和状态编码

    reg [1:0] Current_state;

    reg [1:0] Next_state;

    parameter [1:0] S0=2'b00;

    parameter [1:0] S1=2'b01;

    parameter [1:0] S2=2'b10;

    parameter [1:0] S3=2'b11;

    //时序逻辑:描述状态转换

    always@(posedge clk_i)

    begin

        if(!rst_n_i)

            Current_state<=0;

        else

            Current_state<=Next_state;

    end

    //组合逻辑:描述下一状态

    always@(*)

    begin

        case(Current_state)

            S0:

                Next_state = S1;

            S1:

                Next_state = S2;

            S2:

                Next_state = S3;

            S3:

                begin

                Next_state = Next_state;

                end

default :

Next_state = S0;

          endcase

    end

    //输出逻辑:让输出out,经过寄存器out_r锁存后输出,消除毛刺

    always@(posedge clk_i)

    begin

        if(!rst_n_i)

            out_r<=1'b0;

        else

        begin

            case(Current_state)

               S0,S2:

                    out_r<=1'b0;

               S1,S3:

                    out_r<=1'b1;

   default :

  out_r<=out_r;

            endcase

         end

    end

    assign out_o=out_r;   

三段式状态机在第一个always模块采用同步时序逻辑方式描述状态转移,第二个always模块采用组合逻辑方式描述状态转移规律,第三个always描述电路的输出。通常让输出信号经过寄存器缓存之后再输出,消除电路毛刺。这种状态机也是比较推崇的,主要是由于维护方便,组合逻辑与时序逻辑完全独立。

转载于:https://www.cnblogs.com/milinker/p/6383654.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值