2012-09-24 2 views
1

Verilog에서 Finite State Machine을 만들려고합니다. 이 시스템은 4 개 1-bit입력rst, clk, A, B 하나 개 출력, Z있다.Verilog Finite State Machine

A는 마지막 두 클럭 에지에서 동일한 값을 가졌을 때 1과 같습니다.

또는 B는 마지막 규칙이 참 이후 모든 클럭 에지에서 하이 (1)였습니다.

그렇지 않으면 z=0;

나는 내 시도를 시뮬레이트 할 수있는 도구가 없다. 그래서 이것이 올바른 방법인지 그리고 내가 올바른 길을 가고 있는지 궁금합니다.

module StateMachine(R, A, B, clk, Z); 
    input R, A, B, clk; 
    output reg Z; 

    reg ATemp; 
    reg state; 

    always @ (posedge clk or A) 
     if (A == 1'b1) 
     ///////////////// 
     begin 
     if (ATemp == 1'b1) state <= 1'b1; 
     else ATemp <= A; 
     end 
     //////////////// 
     else 
     //////////// 
     begin 
      if (ATemp == 1'b0) state <= 1'b1; 
      else ATemp <= A; 
     end 


    always @ (state) 
     case(state) 
     1'b0: Z=0; 
     1'b1: Z=1; 

     default: Z=0; 
     endcase 

endmodule 
+2

시뮬레이션 도구가없는 경우 일부를 가져와야합니다. 그렇지 않으면 의미가 없으며 시뮬레이션 없이는 아무데도 가지 않을 것입니다. – Tim

+0

Sim Tools (30 일 데모를 제공하는 대부분의 상업용 툴)를 가지고있는 이유는 무엇입니까? –

답변

1

다음과 같은 도구를 사용할 수 있습니다

:

GHDL이 추가적으로 VHDL 언어 (User Guide)

을위한 오픈 소스 시뮬레이터이 가장 인기 시뮬레이션에게 있습니다 도구입니다

또한 자원 : 또한 stackexchange electronics 지역 사회와 codereview 있습니다

.

C to HDL 컴파일러 도구를주의

(.. 내가 의심도 3 분 안에 코드를 검토 할 수 있습니다 많은 나도 그들을 원하는 것)

0

다음 상태 논리가 없으므로 상태가 변경되지 않으며 재설정이 없으므로 상태가 1'bz로 시작됩니다. 상태 머신을 코딩 할 때 Xilinx guidelines으로 시작하는 것이 좋습니다.

+0

좋은 출발점 ('모든 것이 좋다'대답과는 달리). –

+0

posedge에서 상태가 변경되면 다음 상태를 정의 할 필요가 없습니다. 그러나이 경우에는 단지 1 일 뿐이므로 작동하지 않습니다. – Morgan

0

플립 플롭의 정의가 약간 잘못되었습니다. always @ (posedge clk or A)이 있습니다. 엣지 트리거와 엣지가 아닌 트리거를 결합해서는 안됩니다. 그것은 시뮬레이션에서 작동하지만 합성에서 원하는 것을 얻지는 못합니다.

클록 에지에서만 값을 변경하려면 always @(posedge clk)을 사용하거나 조합 입력에 대해 입력을 사용하면 always @(A) 또는 최신 버전 always @*으로 출력이 변경됩니다. @ * 모든 변경 사항을 트리거합니다. 민감도 목록에 누락 된 항목은 RTL과 동일하게 시뮬레이트하지 않는 합성 코드의 주요 원인으로 사용됩니다.

플립 플롭을 만들고 있다면 리셋을 포함해야한다고 말하면됩니다.always @ (posedge clk or negedge rst_n)

또한 상태가 0으로 설정되지 않으므로 첫 번째 인상은 특정 상태/출력에 고정 될 것이라는 점에 유의하십시오. 코드가 어떻게 질문을 구현 하는지를 아는 것은 어렵습니다. 내 솔루션은 다음과 같은 것이 될 것입니다.

module statemachine(
    input  rst, 
    input  A, 
    input  B, 
    input  clk, 
    output reg Z 
); 

    reg [1:0] a_last_two; 
    wire  rule_one; 

    always @ (posedge clk or negedge rst) begin 
    if (~rst) begin 
     a_last_two <= 2'b0; 
    end 
    else begin 
     a_last_two <= {a_last_two[0] ,A}; 
    end 
    end 

    assign rule_one = (a_last_two[1] == a_last_two[0]); 
    //rule one could be written as ~^a_last_two (xnor reduction operator) 

    reg rule_two; 
    always @ (posedge clk or negedge rst) begin 
    if (~rst) begin 
     rule_two <= 1'b0 ; 
    end 
    else begin 
     //rule 2 resets when rule_one is true 
     if (rule_one) begin 
     rule_two <= 1'b1 ; 
     end 
     else begin 
     rule_two <= rule_two & B ; 
     end 
    end 
    end 

    assign Z = rule_one | rule_two ; 

endmodule