2012-05-20 31 views
1

,如果你有過這樣的處理。例如:VHDL如果報表

process (clk) 
if (var = '1') then 
    var2 = '1'; 
end if; 

if (var2 = '1') then 
    //do something 
end if; 
end process; 

請問if語句得到下一個時鐘週期執行,或將它得到儘快VAR2 =執行第二個「1」是執行?

下面的代碼是否與上面的代碼完全一樣?

process (clk) 
if (var = '1') then 
    var2 = '1'; 
end if; 
end process; 

process (var2) 
if (var2 = '1') then 
    //do something 
end if; 
end process; 

如果有人能解釋時間問題,那將是很棒的。

回答

3

如果你的var是變量,那麼你不能明智地做第二種選擇,因爲你不能在整個過程中使用變量(在大多數情況下,請參閱後面的內容)。如果他們實際上是信號,那麼是的,你可以。

在第一個代碼中 - 如果它們是變量,那麼是的,它們將立即更新,代碼的第二部分將運行。

如果它們是信號,那麼第二個if塊將只在下一次運行,因爲信號只在寫入它們的過程結束時更新。

第二個示例代碼將在第一個運行後的下一個「增量循環」中運行第二個進程,因爲它對var2的變化很敏感。


可以在進程間使用變量,但他們必須被指定爲shared variable秒。如果你使用「直線」變量來做到這一點,那麼你就會冒着可怕的類似Verilog的競爭條件,因爲讀取和更新的順序是不確定的。

你應該使它們成爲一個類似OO的protected type,並且具有對允許訪問在多個進程中是原子的值進行操作的方法。

2

在你的第一段代碼 - 由於var2是一個變量,它會立即得到新的值。因此if語句將看到新的值,並且//do something將發生在同一時間片中。

//意見嗎?真的嗎?這是VHDL。我們使用--

你的第二個代碼段不會工作。變量的作用域是一個進程,不能用於在進程之間傳遞值。你必須使用信號,所以規則改變。考慮以下代碼:

signal sig : std_logic := 1; 
signal sig2 : std_logic := 0; 

process (clk) 
    if (sig = '1') then 
    sig2 <= '1'; 
    end if; 

    if (sig2 = '1') then 
    -- do something 
    end if; 
end process; 

process (sig2) 
    if (sig2 = '1') then 
    -- do something else 
    end if; 
end process; 

初始條件:sig1sig20,所以我們只是在等待一個clk邊緣。

當時鍾沿到達我們進入,我們看到sig1並分配給1sig2第一個進程。迄今爲止所有的簡單,但因爲sig2是一個信號,分配將不會發生,直到過程完成。比當我們在下一行比較sig21時,它會是假的(sig2現在仍然是0),我們不會-- do something。然後我們結束這個過程。

現在,由於在第一過程sig2變化值0 -> 1第二個進程將被觸發的結束(這是敏感sig2)。它看到sig21,所以它會-- do something else

當一個時鐘沿到來時(它可能是與此代碼下降沿),sig2仍然是1,因此現在我們將-- do something,我們將做到這一點對每個時鐘邊沿。

綜上所述事件的這個代碼的順序將是:

Clk : 0->1 
Sig2 : 0->1 
-- Do Something Else 
Clk : 1->0 
-- Do Something 
Clk : 0->1 
-- Do Something 
Clk : 1->0 
-- Do Something 
Clk : 0->1 
-- Do Something 
......... 

當你明白排序,你就會明白如何VHDL安排事情的重要組成部分。

+0

嗨,謝謝你的回答,我現在明白了。但是,由於sig <='1'仍然會使if語句執行,而sig2會不斷地被賦值爲'1'?或者它不知何故知道它已經是'1',並且跳過那條語句? (只是因爲你沒有在你的例子中的'do something'之前顯示sig2 <='1') –

+0

你是對的。它會不斷地被分配'1',但是因爲這不是從當前值的變化,所以它不會導致第二個過程重新評估。我只列出了會導致某些事情發生的任務。 –