【问题标题】:Vhdl- Counter has latch(es)Vhdl- 计数器有锁存器
【发布时间】:2014-01-27 01:47:31
【问题描述】:

我只是想计算按下按钮的次数。我尝试了两种方法,但它们都有用于“Cnt_But”和“Current_state”信号的锁存器。

问题是“IF(Button_db_s='1' and Button_db_ff_s='0')Then”行。但是,该行只允许我在“Rising_edge(Clock)”条件下计数一次。

如果没有闩锁,我怎么能做到这一点?

1)

library IEEE;
use IEEE.STD_LOGIC_1164.all;
use IEEE.NUMERIC_STD.all;
-------------------------------------------------------------------------------
Entity Tim3 is
Port(
Clock: in std_logic;
Reset: in std_logic;
Button: in std_logic
);
END Tim3;
-------------------------------------------------------------------------------
Architecture Tim3_a of Tim3 is
-------------------------------------------------------------------------------
Signal Button_db_s, Button_db_ff_s : std_logic:='0';
Signal Cnt_But : integer range 0 to 5 :=0;
BEGIN
-------------------------------------------------------------------------------
PROCESS(Clock, Reset)
BEGIN
    IF(Reset='1')Then
        Cnt_But<=0;
    ELSIF(Rising_Edge(Clock))Then   
        IF(Button_db_s='1' and Button_db_ff_s='0')Then      
            Cnt_But<=Cnt_But+1;
        END IF;
    END IF;         
END PROCESS;
-------------------------------------------------------------------------------
PROCESS(Clock,Reset) -- Button_db Flip Flop
BEGIN
    IF(Reset='1')Then
        button_db_ff_s<='0';
    ELSIF(Rising_Edge(Clock))Then
        button_db_ff_s<=button_db_s;
    END IF;
END PROCESS;
-------------------------------------------------------------------------------
End Tim3_a;

2)

PROCESS(Clock, Reset)
BEGIN
    IF(Reset='1')Then
        Cnt_But<=0;
        Current_state<=Zero;
    ELSIF(Rising_Edge(Clock))Then
            IF(Button_db_s='1' and Button_db_ff_s='0')Then
                Case current_state is
                    When Zero =>
                        IF(Button_db_s='1')Then
                            current_state<=One;
                            Cnt_But<=1;
                        ELSE
                            current_state<=Zero;
                            Cnt_But<=0;
                        END IF;

                    When One =>
                        IF(Button_db_s='1')Then
                            current_state<=Two;
                            Cnt_But<=2;
                        ELSE
                            current_state<=One;
                            Cnt_But<=1;
                        END IF;

                    When Two =>
                        IF(Button_db_s='1')Then
                            current_state<=Three;
                            Cnt_But<=3;
                        ELSE
                            current_state<=Two;
                            Cnt_But<=2;
                        END IF;

                    When Three =>
                        IF(Button_db_s='1')Then
                            current_state<=Four;
                            Cnt_But<=4;
                        ELSE
                            current_state<=Three;
                            Cnt_But<=3;
                        END IF;

                    When Four =>
                        IF(Button_db_s='1')Then
                            Current_state<=Zero;
                            Cnt_But<=5;
                            Error_2_s<='1'; -- Press only 4 times.
                        ELSE
                            Current_state<=Four;
                            Cnt_But<=4;
                        END IF;
                END CASE;
            END IF;
        END IF;
    END IF;         
END PROCESS;

谢谢。

【问题讨论】:

  • 您实际在哪里使用按钮输入?我看到 button_db_ff_s 在重置后被分配给 button_db_s,但我没有看到 button_db_s 被分配过。
  • 我将在一个组件中使用它,它会给我输出信号 button_db_s(debounced)。我只是想在事情变得复杂之前看看我的代码是否按我的意愿工作。是这个问题吗?
  • 如果您正在合成,大多数合成工具会看到并注意到它没有分配给任何东西并对其进行优化,从而优化更高级别的东西。基于 (1) 没有合成任何内容,因为 button_db_s 始终为“0”,这使得 button_db_ff_s 始终为“0”,这使得“if”语句始终为假,这使得 Cnt_But 始终为 0。
  • 谢谢先生的解释。我更改了代码,现在没有任何闩锁。
  • 输入第二个代码示例时你在想什么? “当一,当二,当三……”如果你的设计需要数到一百或一百万,你会怎么做?

标签: counter vhdl


【解决方案1】:

如前所述,在第一个代码中,您还没有 Button_db_s 的驱动程序。

在第二个代码中,也有问题。例如,当您从状态 4 移动到状态 0 时分配 Cnt_But=5,然后您立即用状态 0 中的 Cnt_But=0 覆盖该值。无论如何,在使用有限状态机 (FSM) 方法设计电路时,您忽略了最重要的阶段,即为其绘制详细的状态图。我在下面提供了一个可能的解决方案。

但是,请注意以下内容。

  • 你说去抖器是由另一个电路提供的,所以上面的FSM中就是这种情况(对于称为按钮的信号),但是去抖器可以嵌入到这台机器中.

  • 此外,假设计数器从 0 计数到最大值,然后自动返回零(这对于常规模 2**N 二进制计数器来说很好,其中 N 是计数器的 FF 数)。

  • 请注意,这是一个 递归 机器(输出 cnt 是递归的)。这种 FSM 在下面的参考文献1 的第 11 章中有详细的介绍。另一方面,好的去抖动器是定时(而不是递归)电路。 1 第 8 章也详细介绍了定时 FSM。

1 V. A. Pedroni,硬件中的有限状态机:理论与设计(使用 VHDL 和 SystemVerilog),麻省理工学院出版社,2013 年 12 月。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-11-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-04-04
    • 2015-04-25
    • 2020-05-13
    • 1970-01-01
    相关资源
    最近更新 更多