2013-09-05 34 views
3

我來自Verilog-95背景,我試圖弄清楚什麼Verilog-95箍我不必跳過了。SystemVerilog是否代表觸發器具有異步設置和復位功能,而無需添加無法合成的代碼?

寫與異步設置觸發器和用Verilog-95復位的顯而易見的方法是:

always @(posedge clk or negedge resetb or negedge setb) begin 
    if (!resetb)  q <= 0; 
    else if (!setb) q <= 1; 
    else    q <= d; 
end 

這個工作在合成。但是,如果我們曾經聲明過resetb和setb,然後在解除置位setb之前取消置位resetb,那麼這在模擬中不起作用,因爲這兩個信號都沒有posedge觸發器。我們需要增加(這取決於你的綜合工具)以下,以獲得模擬匹配合成:

// synopsys translate_off 
always @(resetb or setb) 
    if (resetb && !setb) force q = 1; 
    else    release q; 
// synopsys translate_on 

是否有SystemVerilog的構造,將讓你這樣做沒有這個額外的垃圾?更好的是,在Verilog-95中有沒有一種簡單的方法呢?

回答

4

觸發器具有多個異步控制,最好避免。確保它們正常工作所必需的時間檢查非常複雜且容易混淆。如果你真的需要使用它們,那麼最好在需要的地方手動實例化它們。如果你讓你的綜合工具推斷它們,它可能會在你不想要的地方使用它們,這增加了時間檢查不能正確完成的風險。

最後一個問題是,如果復位的有效沿位於時間零,並且在觸發器初始化爲x之前模擬,並且時鐘未運行,則所有異步觸發器都會出現類似的模擬合成不匹配問題在重置。我相信一些模擬器有特殊的情況來確保邏輯不按這個順序初始化。

這就是說,我很幸運的移動順序always塊之外的優先級邏輯。注意爲了簡單起見,我使用了高電平有效信號。

assign s_int = s && !c; 

always @(posedge clk or posedge s_int or posedge c) begin 
     if (c) 
       q <= 1'b0; 
     else if (s_int) 
       q <= 1'b1; 
     else 
       q <= d; 
end 
-2

試試這個: always_ff @(posedge時鐘或negedge RESETB或negedge SETB)

SystemVerilog的使用always_ff時鐘觸發邏輯和always_comb的組合邏輯

+1

這是怎麼改變行爲呢?如果我們斷言resetb和setb,然後取消置位setb,那麼posedge setb不會甚至觸發模擬,並且模擬不會與綜合相匹配,不是? always_ff是否改變always塊的語義?我的印象是,它只是檢查,以防止你做某些壞事。當然,使用always_ff通常是很好的建議,但這似乎與問題正交。 – dan

2

這是我希望的SystemVerilog有所改善。如果你想讓兩者同時變低,那麼堅持使用當前的方法。

另一種選擇是創建一個設計規則,聲明異步信號不能同時處於活動狀態並通過斷言強制執行規則。斷言假設被合成器忽略,因此translate_off/on 不應該是是必要的。

下面是使用在線斷言一個例子:

always_ff @(posedge clk, negedge resetb, negedge setb) begin : dff_asyncRbSb 
    if (!resetb)  q <= 0; 
    else if (!setb) q <= 1; 
    else    q <= d; 
    asrt_setrst : assert(resetb||setb) 
    else $error("resetb and setb can not be low at the same time."); 
end : dff_asyncRbSb 
2

我不知道任何SV,所以這不是一個答案,但這裏的問題是, 的Verilog(而且,我認爲,SV)事件表達式基本上打破。問題 是,當你有一個事件表達多個條件:

event_expression ::= 
    expression 
    | hierarchical_identifier 
    | posedge expression 
    | negedge expression 
    | event_expression or event_expression 
    | event_expression , event_expression 

那麼就沒有防彈方法來確定哪些表達引起 事件,因爲你唯一可以做的事情是檢查當前狀態的 表達式。所以,如果你有@(posedge clk, posedge rst),例如,你看現在的clk和rst水平,希望這足以做 這份工作。一般情況下,這不是,但你的例子是導致問題的唯一實際案例(我認爲是)。

VHDL通過具有信號屬性來處理這個問題,它使您可以確定信號是否導致事件。在VHDL中,當 中的任何信號的靈敏度列表發生變化時,您將收到一個事件,然後您檢查其'event屬性爲 ,以確定它們是否解除了該過程。沒有混亂,沒有posedge或negedge, ,它的一切工作。

我剛剛看過SV LRM,SV屬性看起來像Verilog屬性的 ,所以我認爲你運氣不好。

0

沒有定義邊沿時,復位和置位信號的斷言和解除斷言應該能夠在模擬中觸發這個代碼。

always_ff should be able to create a flop at synthesis. 

下面的代碼是使用synopsys VCS工具進行編譯清理。

always_ff @(posedge clk, resetb, setb) begin 
    if (!resetb)  q <= 0; 
    else if (!setb) q <= 1; 
    else    q <= d; 
end 
相關問題