Verilog基礎知識(狀態機與序列檢測)

狀態機

狀態機分moore機和mealy機,其中:

  • moore機的輸出只與狀態有關
  • mealy機的輸出與當前狀態和輸入都有關
  • 體現在狀態轉移圖上就是,moore機的輸出在狀態圓圈內,mealy機的輸出在轉移曲線上
  • moore完全描述狀態轉移圖會比mealy機多一個狀態
  • 體現在verilog代碼中就是,moore機的最後輸出邏輯只判斷state,mealy機的輸出邏輯中判斷state && input

狀態機3段式代碼風格

描述方式:
同步狀態轉換過程的邊沿敏感行爲(時序邏輯,用“<=”非阻塞賦值);
描述下一個狀態和輸出邏輯的電平敏感行爲(組合邏輯,用“=”阻塞賦值)。

下面以檢測10010序列爲例說明。

狀態轉移圖


測試代碼

module pattern_det(
    input in, clk, rst,
    output reg moore_out, mealy_out
    );

reg [4:0] state, state_next;

localparam S_idle = 5'b00000;
localparam S1 = 5'b00001;
localparam S10 = 5'b00010;
localparam S100 = 5'b00100;
localparam S1001 = 5'b01000;
localparam S10010 = 5'b10000;

always @(posedge clk or posedge rst) begin
    if (rst) begin
        state <= S_idle;
    end
    else begin
        state <= state_next;
    end
end

always @(*) begin
    if (rst) begin
        state_next = S_idle;
    end
    else begin
        case(state)
            S_idle: if (in == 1) state_next = S1;
                else state_next = S_idle;
            S1: if (in == 0) state_next = S10;
                else state_next = S1;
            S10: if (in == 0) state_next = S100;
                else state_next = S1;
            S100: if (in == 1) state_next = S1001;
                else state_next = S_idle;
            S1001: if (in ==0) state_next = S10010;
                else state_next = S1;
            S10010: if (in == 0) state_next = S100;
                else state_next = S1;
            default: state_next = S_idle;
        endcase
    end
end

//Moore Machine
always @(posedge clk or posedge rst) begin
    if (rst) begin
        moore_out <= 1'b0;
    end
    else begin
//      moore_out <= (state == S10010) ? 1'b1 : 1'b0;
        case(state)
            S10010: moore_out <= 1'b1;
            default: moore_out <= 1'b0;
        endcase
    end
end

//Mealy Machine
always @(posedge clk or posedge rst) begin
    if (rst) begin
        mealy_out <= 1'b0;
    end
    else begin
        mealy_out <= (state == S1001 && in ==0) ? 1'b1 : 1'b0;
    end
end

endmodule
`timescale 1ns/100ps
module pattern_det_tb;

reg clk, rst;
reg [23:0] data;
wire in, moore_out, mealy_out;

assign in = data[23];

initial begin
    clk = 1'b0;
    rst = 1'b0;
    #2 rst = 1'b1;
    #30 rst = 1'b0;
    data = 20'b1100_1001_0000_1001_0100;
    #20000 $finish;
end

always #20 clk = ~clk;
always @(posedge clk)
    #2 data = {data[22:0], data[23]};

pattern_det U1(
    .in(in),
    .clk(clk),
    .rst(rst),
    .moore_out(moore_out),
    .mealy_out(mealy_out)
    );

endmodule


可以看出綜合出的電路中mealy機最後輸出是input和state在做與運算。

moore機因爲是到達S10010狀態才輸出,mealy機則是S1001狀態下輸入爲0就輸出,所以moore機的輸出比mealy機輸出慢一個週期。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章