若要讓數位電路也能循序地執行演算法,最簡單的方式可以使用D-FF產生counter,根據counter的值去決定要執行不同的程式碼,如此也能達到使數位電路循序執行演算法的目的,不過這種方式僅適用於很簡單的演算法,在一般規模的演算法若使用counter方式,程式碼將不容易維護,所以實務上會使用FSM方式來實現演算法。
其實FSM方式也是利用counter來實現,所謂的counter,並不是只有counter = counter + 1才算是counter,FSM的state register就是廣義的counter,只是這種counter不是一直加1而已,而是有自己的遞增規則。FSM只是提供了一種較為高階與較容易維護的方式來實現演算法。
Moore FSM架構
使用2個always (state register與next state logic合一)寫法有幾個優點:
1.程式碼較3個always寫法精簡2.可輕易地將state diagram改用Verilog表示3.因為state register原本程式碼就不多,將next state logic與state register合一後,next state logic仍與output logic分開,因此不會增加code的複雜度,便於日後維護
//-----------------------------------------------
//Moore machine with Binary encoded state machine
//Filename : MOORE_BIN1.v
//-----------------------------------------------
module moore_1(SW, LEDR, LEDG , CLOCK_27 ,KEY ,HEX0 ,HEX1 ,HEX2,HEX3 );
input [17:0] SW; // toggle switches
input [3:0] KEY; // Push bottom
input CLOCK_27; //Clock 27MHz , 50Mhz
output [17:0] LEDR; // red LEDS
output [8:0] LEDG; // green LEDs
output [6:0] HEX0,HEX1,HEX2,HEX3; //7-segment display
//set original program input , output
//(CLK, Din, RESET, Qout);
//input CLK, RESET;
//input Din;
//output Qout;
wire CLK, RESET,Din;
reg Qout;
assign CLK=KEY[0];
assign Din=SW[0];
assign RESET=KEY[1];
assign LEDR[0]=SW[0];
assign LEDG[1:0]=KEY[1:0];
//Declare the value for all states
parameter [1:0]
S0 = 2'b00,
S1 = 2'b01,
S2 = 2'b10,
S3 = 2'b11;
//Declare current state and next state variables
reg [1:0] CS;
reg [1:0] NS;
// always @ (posedge CLK or posedge RESET)
always @ (negedge CLK or negedge RESET)
begin
if (!RESET == 1'b1)
CS = S0; //Initial state
else
CS = NS;
end
always @ (CS or Din)
begin
case (CS)
S0 : begin
Qout = 1'b0;
if (Din == 1'b0)
NS = S0;
else
NS = S2;
end
S1 : begin
Qout = 1'b1;
if (Din == 1'b0)
NS = S0;
else
NS = S2;
end
S2 : begin
Qout = 1'b1;
if (Din == 1'b0)
NS = S2;
else
NS = S3;
end
S3 : begin
Qout = 1'b0;
if (Din == 1'b0)
NS = S3;
else
NS = S1;
end
endcase
end
assign LEDG[7]=Qout;
endmodule
沒有留言:
張貼留言