土曜日, 6月 16, 2007

抽象化 その2

Verilogではparameterを使って、固定値をパラメータ化することできる。

パラメータ化による利点の一つは、再利用性を高めることができることだがもうひとつの大きな利点は数値を抽象化できることだ。

次のような仕様があったとする。

2ビットの入力signalについて、
2'b00を赤、2'b01を黄色、2'b10を青と定義する。
また、2ビットの出力ctrlについて、
2'b11を停止、2'b10を注意、2'b01を進行と定義する。
signalが赤の時、 ctrlは停止を出力、
signalが黄色の時、ctrlは注意を出力、
signalが青の時、 ctrlは進行を出力をすること。

この仕様に対して、次のようなコードを書いたとしよう。
case (signal)
2'b00: ctrl = 2'b11;
2'b01: ctrl = 2'b10;
2'b10: ctrl = 2'b01;
default: ctrl = 2'b11;
endcase

一応これでも仕様を十分満足できる。
が、一度仕様を読んでこのコードを見てもそれが正しいかどうか理解するのに少し苦労するだろう。

次の場合はどうだろうか。

parameter Red = 2'b00;

parameter Yellow = 2'b01;
parameter Blue = 2'b10;

parameter Stop = 2'b11;
parameter Caution = 2'b10;
parameter Go = 2'b01;

・・・

case
(signal)
Red: ctrl = Stop;
Yellow: ctrl = Caution;
Blue: ctrl = Go;
defautl: ctrl = Stop;
endcase

パラメータの定義の部分は少し注意が必要だがコードの本体の部分を理解するのはこちらの方がずいぶん楽だろう。
具体的な数値がすでになくなっているので抽象度が上がり人間の言葉に近くなっているからだ。

このように、同じ機能を実現するコードでも
抽象化することによって、ミスを減少したり、メンテナンス性向上させることができる。

ハードウェアではより低レベルでの効率化のため、各ビットに意味をもたせる場合が多くそのため、現在でもまだあまり抽象化されていないコードをよく見かけることがある。
例えば、先のsignalの定義で言えばbit1を見るだけでそれが青かどうか判断できるため、次のコードの方が良いと思う人も多いかもしれない。

if
(signal[1]) ctrl = 2'b01;
else begin
if (signal[0]) ctrl = 2'b10;
else ctrl = 2'b11;
end

しかし、EDAツールやチップの性能が向上してきている現在では、よりメンテナンス性の良い方法を選択した方が今後はよりしあわせになれるのではないだろうか?

0 件のコメント: