defineでなくparameterを使う

[] [] []


defineでなくparameterを使う」

RTL記述中の定数を可変にしておきたいときや、数値でなく名前で表記したいときがある。

1RTL記述に汎用性を持たせるため、ビット幅を可変にする

2)シミュレーション時間を短縮するために、長いカウンタ周期を短くする

3)ステートマシンの状態をしめす定数を、数値でなく名前で表記する

このようなときVerilogでは定数をマクロにする方法とparameter変数にする方法があるが、マクロは危険なので使わない方がよい。なぜならば、

・マクロはどのソースファイル内でdefineしても、FPGA全体のソースファイルに対して有効になるので、もし複数のソースファイルでたまたま同じ名前のマクロが存在していると、defineしている場所によっては意図しない方の値が使われてしまう。

・マクロはシミュレータや論理合成ツールのオプションでも値をdefineできてしまうので、ソースファイルに書かれている値が使われる保証もない。

・マクロは単なる文字列置換なので、計算式を間違えやすい。例) define M N+1 , define K 2*M と書くとK=2*(N+1)でなくK=2*N+1と解釈される。

・しかもコンパイルエラーにはならないので気がつかない。

一方、parameterは定義したモジュール内のみで有効なので安全である。

・上位モジュールから指定することもできるので、複数の下位モジュールをインスタンシエートしてそれぞれに異なる値を指定することもできる。

・上位から設定させたくないパラメータはlocalparamとすればよい。

・テストベンチからFPGA内部のparameterに対してもモジュール名の階層パスを明示的に指定すれば

 defparam top_mod.sub_mod1.PERIOD=4'd15; と値を設定することができる。

また、parameterは単なる文字列置換ではなく、値として計算される。 例) M=N+1, K=2*Mと書くとK=2*(N+1)と解釈される。

`define MSB 15

`define PERIOD = 4'd15  // マクロの定義

 

module my_module

    ...

× reg[`MSB:0] a_reg;          // マクロを定数として使っている

    ...

× if(counter_reg==`PERIOD)    // マクロを定数として使っている

    ...

endmodule

 

my_module #(.MSB(15),.PERIOD(4'd15)) mod_1(...) // 下位モジュールに設定す

 

module my_module #(parameter MSB=7,PERIOD=4'd8) // デフォルト値を記述

    ...

○ localparam NUM=100; // 外に見せないパラメータはlocalparamとして宣言

  ...

○ reg[MSB:0] a_reg;           // パラメータを定数として使っている

    ...

○ if(counter_reg==PERIOD)     // パラメータを定数として使っている

    ...

endmodule

()parameter値を設定する文の#記号は時刻のディレイを表す#と同じだが意味は無関係


[] [] []