by Manuel Cernuda |
以前のVerilog HDLでは、alwaysを使って組み合わせ回路を書く場合には
Sensitivity Listに入力を全て列挙しなければならず面倒で、またバグの温床でもありました。
例えばこんな感じです。
always @ ( color or a or b or c or ... ) begin case (color) RED : x = a; BLUE : x = b & c; ....; endcase end
Verilog 2001ではalways @*がサポートされてかなりの簡潔に記述できるようになり、Sensitivity Listの記入漏れの問題は起きにくくなりました。
しかし、それでもまだ実はシミュレーション時に問題が起こる可能性があります。
always @* begin case (color) RED : x = a; BLUE : x = b & c; PINK : x = my_function(d, e, f); ....; endcase end function my_function; input sig_a; input sig_b; input sig_c; begin my_function = sig_a | sig_b | sig_c | SIG_X; end endfunction
always @*はalways内で直接使用している信号までしかsensitiveではなく、
例えば上の例の様な記述の場合、my_function()の中で使用しているSIG_Xに変化があったとしてもalways @*の出力xは変化しません。
このような問題を解決できるのがSystemVerilogのalways_combです。
always_comb begin case (color) RED : x = a; BLUE : x = b & c; PINK : x = my_function(d, e, f); ....; endcase end
このようにalways @*の場合と同様に記述出来ます(functionの内部は省略)。
しかし、always_combの場合はalways @*と違い、内部に含まれるfunctionが使用している信号に対してもsensitiveになります。つまり、この場合はSIG_Xの変化にもalways_combの出力xが連動します。
その他にも、always_combではalways @*と比べて以下のような違いがあります。
・時刻0で一度always_comb内部が実行される
・always_comb内でドライブされている信号は他の場所でドライブできない
・always_comb内ではwait()やfork...joinなどのタイミングをブロックするような制御が行えない
他にもSystemVerilogではalways_latchやalways_ffなどが追加されていますが特にこのalways_combが重要ですね。
alwaysで組み合わせ回路を記述する場合は是非使うようにしましょう。
最後に、昔書いた組み合わせ回路の記事のリンクを貼っておきます。
ここではalwaysで組み合わせ回路を記述する場合の短所としてregで出力を宣言しなければならないと書きましたが、SystemVerilogでは新たにlogicが追加されたので便利になりました。
functionを使う場合は、always_combの中に入れておくとより安全でしょう。
こちらで別の例が詳細されていたのでリンクしときます。
0 件のコメント:
コメントを投稿