将有限状态机图转换为verilog代码

时间:2018-03-12 01:15:18

标签: verilog finite-automata state-machine

我一直在尝试将这个Mealy有限状态机转换为Verilog代码,并且它永远不会适用于状态/输入/等的所有组合。

fsm

以下是Verilog代码:

 1  `timescale 1ns/100ps
 2  `default_nettype none
 3  
 4  module OddFunction(
 5      output  reg     A,
 6      input   wire    x, y, clk, reset_b
 7  );
 8      
 9      parameter S0 = 1'b0, S1 = 1'b1;
10      
11      reg [1: 0] state, next;
12      initial next = S0;
13      
14      always @(posedge clk) begin
15          if (reset_b == 0) state <= S0;
16          else state <= next;
17          case (state)
18              S0: if ((x || y) && !(x && y)) next = S1; else next = S0;
19              S1: if (!((x || y) && !(x && y))) next = S0; else next = S1;
20          endcase
21          case (state)
22              S0: A = ((x || y) && !(x && y));
23              S1: A = !((x || y) && !(x && y));
24          endcase
25      end
26      
27  endmodule

2 个答案:

答案 0 :(得分:1)

对于最小的更改,应将next的逻辑分配移动到单独的组合块(always @*)中。将next作为组合,不需要给它初始值。这应该会给你你期望的行为。

另请注意,您有不必要的逻辑。 Astate在逻辑上是等效的。任何合理的合成器都会合并它们。类似地,您将xor逻辑扩展为与逻辑运算符等效的逻辑。您可以简单地使用xor位智能运算符(^)。

案例陈述对于状态机来说很常见。但是,当状态用两种状态编码时,它们不是必需的。您可以简化并重写将always逻辑写为:

always @(posedge clk) begin
  if (reset_b) A <= 0;
  else         A <= A ^ x ^ y;
end

答案 1 :(得分:1)

如果查看电路和状态图,您会注意到状态机的输入是纯EXOR信号。因此,最简单的方法是:

wire my_exor;
   assign my_exor = x ^ y;

下一个观察是每次exor为真时输出都会切换。

always @(posedge clk)
   if (reset)
      A <= 1'b0;
   else if (my_exor)
      A <= ~A;

将两者放在一起,你得到Gregs代码。