第20回
VHDLによるロジック設計(2)
前回に引き続き「VHDLの文法」について概要を学ぶ。前号の例題に取り上げたVHDLソースリストdataflow.vhd(図2)とリスト3のstructure.vhdを中心にその内容を解釈できるように解説しており、VHDLの文法を網羅しているものではないので、詳細は必要に応じて巻末の参考文献などを参照して頂きたい。
最後に、初心者がVHDLの設計を学習するのに便利なツールVHDLブラウザに触れる。
VHDLの文法(つづき)
3.パッケージ宣言
階層構造をなしている下位のコンポーネントxnor2とand4はパッケージ記述により定義され、コンパイルされたものがgatespkgというライブラリに収められている。workライブラリにあるこのgatespkgパッケージのコンポーネントをアクセスするために、上位ファイル(リスト2)にはuse節
use work.gatespkg.all;
が置かれている。
コンポーネントxnor2とand4のソースファイルをリスト4とリスト5に示す。いずれもエンティティ宣言の前にパッケージが宣言を含んでおり、上位ファイルでuse節を用いるとアクセス可能となる(可視性を持たされる)。
library ieee;
use ieee.std_logic_1164.all;
package gatespkg is
component xnor2
port ( a,b: in std_logic;
y: out std_logic );
end component;
end gatespkg;
library ieee;
use ieee.std_logic_1164.all;
entity xnor2 is
port ( a: in std_logic;
b: in std_logic;
y: out std_logic);
end xnor2;
architecture behavior of xnor2 is
begin
y <= not(a xor b);
end behavior;
リスト4 xnor2のソースリスト
library ieee;
use ieee.std_logic_1164.all;
package gatespkg is
component and4
port ( a,b,c,d : in std_logic;
y: out std_logic );
end component;
end gatespkg;
library ieee;
use ieee.std_logic_1164.all;
entity and4 is
port ( a,b,c,d: in std_logic;
y: out std_logic );
end and4;
architecture behavior of and4 is
begin
y <= a and b and c and d;
end behavior;
リスト5 and4のソースリスト
4.各記述法の特徴
この例(リスト3と下位のリスト4、リスト5)では、リスト2の機能(ビヘイビア)記述に比べると相当煩わしいものとなり、適当な記述ではないと言える。しかし、大規模な設計では、管理しやすいサブモジュールに分解でき、個々にエンティティの定義やシミュレーションができるので複数の設計者やチームで開発するのにメリットがある。またベンダーから提供される特定のライブラリのコンポーネントを利用すれば特定のデバイスを効率良く開発できる。
また、同じ機能をリスト6のようなブール方程式によるデータフロー記述で簡潔に表現することも可能である。
このように同じエンティティに対して異なるいくつかの記述が可能であるが、結局、ビヘイビア記述とデータフロー記述がネットリストに比べはるかに読み易く理解しやすく保守しやすいもので、VHDLの特徴を最大限に発揮できる。
library ieee;
use ieee.std_logic_1164.all;
entity eqcomp4 is port(
a, b: in std_logic_vector(3 downto 0);
equals: out std_logic);
end eqcomp4;
architecture bool of eqcomp4 is
begin
equals <= not(a(0) xor b(0))
and not(a(1) xor b(1))
and not(a(2) xor b(2))
and not(a(3) xor b(3));
end bool;
リスト6 eqcomp4のブール式による記述
5.ライブラリ宣言とパッケ−ジの呼び出し
VHDLには二つの重要な標準IEEE1164とIEEE1076.3がある。
IEEE1164標準のデータ型を使用するには少なくとも次の二行のステートメントをVHDLのソースファイルの冒頭に加えなければならない。
library ieee;
use ieee.std_logic_1164.all;
もし設計ユニット(エンティティとアーキテクチャの対、デザイン・インティティとも呼ばれる)が二つ以上あるときは、各設計ユニットの前にこの二行のステートメントを繰り返さなければならない。
またユーザーが定義したライブラリ、例えば前述のgatespkgを使用するにはuse節を加える必要がある。
library ieee;
use ieee.std_logic_1164.all;
use work.gatespkg.all
この記述はIEEE1164標準をロードし、その内容std_logic_1164パッケージを可視性にする。従来のデータ型bitが'1'か'0'の値しか取れないのに対し、新たに追加されたstd_logic_1164パッケージの二つのデータ型std_logicとstd_ulogicは次の9個の値を持つことができる(リスト7)。
'U'---未初期化値
'X'---アンノウン
'0'---”L”
'1'---”H”
'L'---弱い信号の”L”
'H'---弱い信号の”H”
'W'---弱い信号のアンノウン
'Z'---ハイインピーダンス
'-'---ドントケア
リスト7 std_logicの取りうる値
もしワイヤ上に同時に異なる信号レベル(例えば、'1'と'Z'のように)で駆動される複数の値を持つバスインタフェースなどの回路を記述する場合には、Resolved型であるstd_logicを用いる必要がある。andゲートなどで、スタンドアローン回路として動作する時にはその出力が二つの異なる値で駆動されることはないが、大きな回路で階層化されるときはそのような状況が起こりうるのでstd_logicが要求される。
このようにIEEE1164標準の長所は、アンノウン、ハイインピーダンスやドントケアを含む9個の値を持つデータ型をサポートしている点で、これにより組合せ回路の最適化に利用されたり、トライステートバスの記述ができるなどのメリットがある。
std_logic_vectorとstd_ulogic_vectorはそれぞれstd_logicとstd_ulogicのベクタタイプである。ベクタ(配列)std_logic_vectorはバスのように複数のビットで構成される信号で、4ビットの信号はstd_logic_vector(3
downto
0)のように表す。最初の3がMSBとして、0がLSBとして扱われるので(0 to
3)とするとMSBとLSBの関係が逆になる。宣言のしかたはどちらかに統一しておいた方がよい。さもないと思わぬところでトラブルの種を播くことになる。
6.オブジェクトとデータ型
VHDLは、総称的にオブジェクトと呼ばれる言語要素で構成され、オブジェクトによってシステムのデータを表したり記憶したりする。論理合成のための設計記述やテストベンチという書式の機能テストの作成で用いられるオブジェクトの三つの基本的な型は信号(signal)、変数(variable)、および定数(constant)である。
各オブジェクトはbitやintegerのような特定のデータ型と、唯一の取りうる値のセットを持つ。オブジェクトが取りうる値は、そのオブジェクトで用いられる型の定義に依存する。
例えば、realという型のオブジェクトがVHDL規格で定義された精度とその範囲内の多数の浮動小数点数値を取り得るのに対し、bitという型のオブジェクトは'0'か'1'のただ二つの値だけしか取ることができない。
VHDLにはリスト8に示すような多くの異なるデータ型がある。はじめのintegerからbit_vectorまでの8項はVHDLに内蔵される基本データ型で、後の2項std_logicとstd_logic_vectorは追加可能な標準データ型で先の項で述べたIEEE標準のライブラリを読み込んだときに利用可能である。
integer 整数32ビット
real 浮動小数点数値
bit ロジック値'0','1'
bit_vector bitのベクタタイプ
boolean 論理値FALSE、TRUE
time 時間の物理タイプfs,ps,n,.us,ms,sec,min,hr
character ASCII文字
string charactorのベクタタイプ
std_logic ロジック値9値(MVL9)
std_logic_vector std_logicのベクタタイプ
リスト8 データ型
6.1 信号(Signal)
Signalは部品を接続するオブジェクトで、回路基板や回路図で部品を接続するのにワイヤが用いられるのと似ている。Signal文は内部信号を宣言する。signalは外部パッケージでグローバルに宣言されるたり、アーキテクチャや他の宣言セクションでローカルに宣言することができる。ポート文とローカルに宣言されたsignal文の間の差はポート文が方向を持つという点だけである。
signalを宣言するにはsignal記述を次のリスト9ように書く。図7(前号)で各xnor2の出力からand4の入力につながる4本のワイヤを表している。
architecture structure of eqcomp4 is
signal x: std_logic_vector(3 downto 0);
bigin
・・・・
end structure;
リスト9 signal文(1)
この簡単な例では、信号xはstructureの宣言セクションに宣言される。最小限、signal宣言は信号名(この場合x)と型(この場合std_logic_vector(3
downto 0))を含んでいなければならない。
同じ型の信号が一つ以上必要なときは、複数の信号名を一つの宣言の中に規定できる。
architecture arch of my_design is
signal Bus1,Bus2: std_logic_vector(7 downto 0);
bigin
・・・
end arch;
リスト10 signal文(2)
6.2 変数(Variable)
Variableは一時記憶領域で、従来のプログラミング言語の変数と似たものと考えてよい。
6.3 定数(Constant)
定数は変更できない値のオブジェクトである。この値は通常宣言文で割り付けられ、必ず初期値が必要になる。初期値は代入演算子":="によってデータタイプの後に代入する。
定数はコードの読みやすさを改善するためとコードの修正を容易にするために用いられる。例えばレジスタの幅を示す定数を次のように宣言しておくと
constant width: integer := 8;
widthはコードの中で数箇所に渡って用いられていたとしても、widthの値を変更する必要が生じた場合は、定数宣言部の初期値(この例では8)を変更して再コンパイルすればよい。
ソースファイルの作成
これまでExampleとして添付された完成されたファイルdataflow.vhdを使ってWarp2の操作手順を追ってみた。文法の概略を学んだところで新しいソースファイルを作ってみよう。
一般的な方法はVHDLエディタでリスト5のような内容を1行ずつ打ち込んでゆく方法である。libraryやuse、packageなどの単語は予約語であるのでスペルに間違いがなければカラー表示される。
もう一つはVHDLブラウザを利用する方法で初心者には便利である。VHDLブラウザを開くにはVHDLメニュでBrowseをクリックする。図8のようなVHDLブラウザが開くので、左欄のリストから適当な予約語(例えばPackage
decl.)選んでInsertをクリックする。

図8 VHDLブラウザ
図9のVHDLプロンプタが開くのでgatespkgと入力しOKをクリックすると自動的に翻訳されてVHDLエディタの4行目と6行目が入力される(図10)。次に5行目の空行にカーソルを移動させてVHDLブラウザでComp.decl.を選んで挿入する。以下同様の作業を繰り返す。
VHDLエディタで入力するより予約語を入力する手間が省けるし、少なくともミス入力の心配がない。

図9 VHDLプロンプタ

図10 VHDLエディタへの翻訳入力
(つづく)
参考文献
1.「VHDLによるロジック設計入門」トランジスタ技術、1997年12月号特集
2.「パソコン用VHDLシミュレータの登場」CQ出版、Design Wave
Magazine No.2
2.Warp User's Guide, Release 4.2, Cypress Semiconductor
Inc.,1997.
3.Warp Refference Manual, Release 4.2, Cypress Semiconductor
Inc.,1997.
4.David Pellerin・Douglas Taylor "VHDL Made Easy!" (Prentice
Hall,1997)
5.Kevin Skahill "VHDL for programmable logic"
(Addison-Wesley,1996)
6.Peter J. Ashenden "The Designer's Guide to VHDL"(Morgan
Kaufmann:San
Fran,1996)