2016-05-19 129 views
1

我在使用這段代碼時遇到了一些麻煩。看起來狀態S0總是有效的,即使它不應該是。看起來這個狀態的輸出是反轉的(當它被禁止時是有效的)。有任何想法嗎?底部的模擬打印。由於VHDL爲什麼當狀態S0不應該是活動狀態?

library IEEE; 
use IEEE.STD_LOGIC_1164.all; 

entity ControlUnit is 
    port(clk   : in std_logic; 
      reset   : in std_logic; 
      validTime  : in std_logic; 
      timeData  : in std_logic_vector(3 downto 0); 
      writeEnable : out std_logic; 
      writeAddress : out std_logic_vector(3 downto 0); 
      averageReady : out std_logic); 
end ControlUnit; 

architecture Behavioral of ControlUnit is 
    type TState is (S0, S1, S2, S3, S4, S5); 
    signal PState, NState: TState; 
begin 

    sync_proc: process(clk, reset) 
    begin 
     if(reset = '1') then 
      PState <= S0; 
     elsif(rising_edge(clk)) then 
      PState <= NState; 
     end if; 
    end process; 

    comb_proc: process(PState, validTime, timeData) 
    begin 
     averageReady <= '0'; 
     writeEnable <= '0'; 
     case PState is 
      when S0 => 
       if(validTime = '1') then 
        writeEnable <= '1'; 
        NState <= S1; 
       else 
        NState <= S0; 
       end if; 
      when S1 => 
       if(validTime = '1') then 
        writeEnable <= '1'; 
        NState <= S2; 
       else 
        NState <= S1; 
       end if; 
      when S2 => 
       if(validTime = '1') then 
        writeEnable <= '1'; 
        NState <= S3; 
       else 
        NState <= S2; 
       end if; 
      when S3 => 
       if(validTime = '1') then 
        writeEnable <= '1'; 
        NState <= S4; 
       else 
        NState <= S3; 
       end if; 
      when S4 => 
       if(validTime = '1') then 
        writeEnable <= '1'; 
        NState <= S5; 
       else 
        NState <= S4; 
       end if; 
      when S5 => 
       averageReady <= '1'; 
       NState <= S0; 
      when others => 
       NState <= S0; 
     end case; 
    end process; 

    with PState select 
     writeAddress <= "0000" when S0, 
          "0001" When S1, 
          "0010" when S2, 
          "0011" when S3, 
          "0100" when S4, 
          "XXXX" when others; 
end Behavioral; 

這裏是模擬的打印:

(點擊)

+2

這似乎是一個熱門編碼(暗示這是後合成模擬)。 PState.S0的極性看起來是倒置的,而其餘的看起來是正確的。合成的硬件需要保持極性直線,但PState不是輸出,它是否正確模擬?您尚未提供允許預綜合模擬的[最小,完整和可驗證示例](http://stackoverflow.com/help/mcve)。 *任何想法?*對於一個問題有點寬泛。如果你想要在內部進行同步,也許你可以以不同的方式限制合成。 – user1155120

回答

0

一切都確定了你的代碼。爲什麼你認爲S0狀態總是激活?你不能從波形中說出來,因爲你不知道編碼方案。另一方面,你不斷地寫地址信號變化,這意味着你的狀態機改變它的狀態。

+0

如果你看一下S0狀態並想它倒置,是不是應該看起來像這樣倒置?我的意思是,S0狀態是「默認」......如果沒有其他狀態是活動的,那麼只有一個活動應該是S0,對吧?如果你看一下〜100ns的差距,那就沒有活躍的狀態......這對我來說聽起來有點奇怪 –

+0

首先。如果您想確切地確定自己所處的狀態,請不要使用該類型的枚舉定義。對於狀態信號,請使用簡單的std_logic_vector類型,並自行定義狀態的常量。我們這裏的自動枚舉類型爲std_logic_vector convertion,可能導致S0狀態被編碼爲「000000」,這是我們在復位信號之後的波形處看到的。 –

+0

另外我還需要指出代碼中的另一個錯誤 - 在復位期間,writeEnable處於活動狀態。這是因爲當復位處於活動狀態時,您處於S0狀態,並且如果在此狀態下validTime = 1,則writeEn也爲1.這不是我想要的。我會建議有一個叫做RST_ST的狀態。復位信號有效時保持在此位置,否則移到S0。因此,在復位期間,您的writeEn信號不會有效 –