首页 文章

VHDL - 设置传感器的采样率

提问于
浏览
0

SO用户,

我正试图以5Hz的频率(每秒5个样本)对我的电阻式湿度传感器进行采样 . 我正在使用ADC来读取输出 . 现在,我被告知您可以在任何频率下运行ADC,但您需要使用5hz时钟来启动转换并从ADC读取值 .

我这样做的方法是让一个进程通过以5hz运行并有一个标志来启动转换,在时钟的上升沿将“start_convert”设置为“1” .

PROCESS (CLK_5HZ)       
BEGIN
    IF (CLK_5HZ'EVENT AND CLK_5HZ = '1') THEN
        START_CONVERT <= '1';
    END IF;
END PROCESS;

然后我有一台ADC状态机;

PROCESS (CURR_STATE, INTR)
                BEGIN

                CASE CURR_STATE IS

                        WHEN STARTUP =>
                            WR <= '0';
                            READ_DATA <= '0';
                            IF (START_CONVERT = '1') THEN
                                NEXT_STATE <= CONVERT;
                            ELSE
                                NEXT_STATE <= STARTUP;
                            END IF;

                        WHEN CONVERT =>
                            IF (INTR = '0' AND STREAM = '1') THEN
                                NEXT_STATE <= WAIT500;
                            ELSIF (INTR = '0' AND STREAM = '0') THEN
                                NEXT_STATE <= READ1;
                            ELSE
                                NEXT_STATE <= CONVERT;
                            END IF;
                            WR <= '1';
                            READ_DATA <= '0';

                        WHEN WAIT10 =>
                            IF (COUNTER_WAIT = 10) THEN
                                NEXT_STATE <= READ1;
                            ELSE
                                NEXT_STATE <= WAIT10;
                            END IF;
                            COUNTER_WAIT <= COUNTER_WAIT + 1;

                        WHEN READ1 =>
                            NEXT_STATE <= CONVERT;
                            WR <= '1';
                            READ_DATA <= '1';

                        WHEN OTHERS =>
                            NEXT_STATE <= STARTUP;
                END CASE;
                END PROCESS;

然后我在5hz使用另一个进程来检测READ_DATA是否为1,以便我从ADC读取值 .

PROCESS (CLK_5HZ, RST)
    BEGIN
    IF (RST = '1') THEN
    Y <= (OTHERS => '0');
    ELSIF (CLK_5HZ'EVENT AND CLK_5HZ = '1') THEN
        IF (READ_DATA = '1') THEN
        Y <= DATA_IN (0) & DATA_IN (1) &
         DATA_IN (2) & DATA_IN (3) &
         DATA_IN (4) & DATA_IN (5) &
         DATA_IN (6) & DATA_IN (7);
    END IF;
   END IF;
END PROCESS;

任何人都可以告诉我这是否是正确的方法?

编辑:我正在使用Spartan-3板连接ADC(ADC0804) .

1 回答

  • 3

    在不知道您尝试连接的设备的细节时,提供具体建议有点困难 .

    但是,有关您的代码的一些一般性评论:

    • 您的异步过程( PROCESS (CURR_STATE, INTR) )在合成时将生成相当多的锁存器,因为您并未在所有情况下设置所有信号 . 例如, WRREAD_DATA 未在 WAIT10 状态中设置 . 这很可能会导致严重的时间问题,所以纠正这个问题是你绝对想做的事情 .

    • 同一进程中的 WAIT10 状态将为您提供组合循环,因为只要 COUNTER_WAIT 更新,它就会运行 . 由于该状态也会更新 COUNTER_WAIT ,理论上它会继续运行,但实际上大多数合成器只会给你一个错误(我认为) . 您需要将增量移动到同步/时钟进程,这也可以控制每个周期所需的时间 .

    • 您的5 Hz进程似乎在单独的时钟( CLK_5HZ )上运行 . 我认为你的系统的其余部分运行速度更快?这实际上为您提供了两个(或更多)时钟域,这些时钟域需要特殊的接口逻辑才能将它们相互连接 . 一个更好,更好的解决方案是在同一(快速)时钟上运行所有内容,并使用时钟使能控制较慢的进程 . 因此,一切都是固有的同步,不应该给你任何令人讨厌的时间惊喜 .

相关问题