Verilogの構文(1)

Verilogの構文(1)

 Verilogの書き方を解説します。VHDLは別途全く同じ内容で記載していますので、そちらを参考にしてください。

 HDLに限らずプログラム言語なども全体を通して書き方のルールがあります。Verilogの仕様書や解説書を読んでいると書き方がいろいろあるのに気がつくと思います。おそらく、エンジニアによっても書き方が違うと思います。初心者がその多くの書き方を見てしまい、どれが正解なんだ。と考え込む傾向にあります。なので、あまり考えないで、人のスタイルを真似てみてください。

 会社によっては、スタイルのルールがある場合がありますので、それに従うようにしてください。

 次に示すのは、私のルールです。ソースコードの中に // がありますが、// 以降のテキストはコメントとして判断されます。

//  TITLE:					"datasel.v"
//  MODULE NAME:			datasel
//  PROJECT CODE:			
//  AUTHOR:					 (****@nakaharagiken.com)
//  CREATION DATE:			2020.1.1
//  SOURCE:            		
//  LICENSE:           		Copyright (c) 2020 ***************. All rights reserved. 
//  DESCRIPTION:            2系統の信号から1系統を選択。レジスタ付き
//  NOTES TO USER:			入力信号は予めチャタリング処理しておくこと
//  SOURCE CONTROL:			
//  REVISION HISTORY:  	    v0.1	2020.1.2	First edition
//
//
//
//
//
//
//
//
`timescale 1ns/1ps					// [構文] コンパイラ指定子 シミュレーションの単位/制度

module datasel(						// [構文] モジュール宣言
	clock,							// [構文] ポートリスト
	nreset,							// [構文] ポートリスト
	enable,							// [構文] ポートリスト
	SwitchIn_A,						// [構文] ポートリスト 				
	SwitchIn_B,						// [構文] ポートリスト				
	input_sel,						// [構文] ポートリスト
	output_ans,						// [構文] ポートリスト
);

input	clock;						// [構文] ポート宣言
input	nreset;						// [構文] ポート宣言
input	enable;						// [構文] ポート宣言
input	SwitchIn_A;					// [構文] ポート宣言				
input	SwitchIn_B;					// [構文] ポート宣言			
input	input_sel;					// [構文] ポート宣言
output	output_ans;					// [構文] ポート宣言

///////////////////////////////////////////////////////////////
// SIGNALS
///////////////////////////////////////////////////////////////
wire	wInputSeldA;				// [構文] ネット宣言
wire	wInputSeldB;				// [構文] ネット宣言
wire	wnInputSel;					// [構文] ネット宣言
wire	wSeldSignal;				// [構文] ネット宣言
reg		rSeldSignal;				// [構文] レジスタ宣言



assign	wnInputSel = ~input_sel;					// 論理ゲート記述
assign	wInputSeldA = SwitchIn_A & input_sel;		// 論理ゲート記述
assign	wInputSeldB = SwitchIn_B & wnInputSel;		// 論理ゲート記述
assign	wSeldSignal = wInputSeldA | wInputSeldB;	// 論理ゲート記述



//////////////////////////////////////////
// rSeldSignal レジスタ
//////////////////////////////////////////
always @ (posedge  clock, negedge nreset) begin		// DFF記述 clock 立ち上がり指示
	if (!nreset) begin								// リセット初期化
		rSeldSignal <= 1'b0;						// リセット時の初期値挿入
	end else begin
		if (enable == 1'b1) begin					// イネーブル処理
			rSeldSignal <= wSeldSignal;				// D端子の入力接続
		end
	end
end

assign	output_ans = rSeldSignal;					// 論理ゲート記述:出力信号接続

endmodule											// [構文]	モジュール宣言:終わり

 コメントに[構文]と記した部分があります。これは、Verilogのルール部分です。そしてほとんどの場合、[構文]と書いた部分は順番も大切です。
 たとえば、最初に出てくる[構文]はコンパイラ指定子ですが、これはこの場所に書く必要がある。という事です。
 ちょっと戻って、1〜19行目にコメントが長く記載されていますが、これは私のルールです。すべてのソースコードにこのようなコメントをヘッダーとして記載しています。このようなヘッダーは無くても良いのですが、ソースコードの管理の意味でも同様のヘッダーを記述する事をお勧めします。

コンパイラ指定子

 コンパイラ指定子はコンパイラへのスイッチです。timescaleは本来回路では無く、シミュレータの命令なので、本当はこの命令は必要ありません。しかし、私はできる限りシミュレータも同じ形式で書きたいために残しています。

 Verilogのわかりにくいところは、このtimescaleにあると思います。初心者が最初に混乱する指定子です。

 ほとんどのVerilogの構文解説書にtimescaleを記述していますが、実のところ意味はありません。timescaleが生きてくるのはシミュレータの時です。

 timescaleを書いたからといって、遅延を回路で作れるわけではありません。そこを間違わないようにしてください。

 さて、timescaleのようにコンパイラへの指示は予約語という特別な単語です。プログラムをコーディングする方であれば、言語の予約語と同じ意味です。予約語とは言語の仕様の中で予め決めた単語です。主に言語への命令がありますが、論理式のand,orなども予約語として分類されます。
 予約語は回路を設計していくうちに自然と覚えてしまいますが、XilinxやIntelなどの統合開発環境でHDLを記述すると、予約語をハイライトする機能がありますので、それを見ながら覚えるのが良いでしょう。

 そして、予約語は言語への命令になりますので、ユーザがそれ以外の目的で使う事はできません。たとえば、入出力信号名やモジュール内信号定義の名前に使えません。

モジュール宣言

 22行目はモジュール宣言といって、本ファイルの名称を宣言します。VWrilogの場合、モジュールという単位で回路を作成していきます。

ポートリスト

 23行目からはモジュールの入出力を宣言します。Verilogの場合ポートリストという入出力の名前宣言と、ポート宣言という入出力の区分宣言に分かれるのでちょっと面倒です。

ポート宣言

 32〜38行目でポートリストで宣言した信号が入力なのか、出力なのかを宣言します。ポート宣言ポートリストの中に書く事もできます。

ネット宣言、レジスタ宣言

 43〜47行目はネットの宣言とレジスタの宣言です。ネットとレジスタを区別して宣言できるのは、Verilogの特徴です。宣言はwireとregで分けて行うのですが、名前はVerilogもVHDLもエンジニアが勝手につける事ができます。ソースコードの中で混乱しない為にも区別できるような名前付けをお勧めします。

論理ゲート記述

 Verilogの一番わかりにくいのが論理ゲートの記述方法です。ブール代数のままという訳にいきません。assignで宣言する必要があります。assignで書かれている分はwireだと思って間違いありません。

DFF記述

 61行目からDFFの記述になりますが、クロックの扱いがVHDLとはちょっと違います。Verilogの場合クロックという概念が薄いのか、すべての信号で同じように記述する事ができます。

 61行目を見ても、Clockとnresetはposedgeとnegedgeで区別されていますが、これは立ち上がりか、立ち下がりかを区別しているだけなので、同等の扱いになります。

 追々各項目を説明していきますが、ここで覚えるのは「目次」で示した各構文の場所(順序)です。しかし、がんばって覚える必要はありません。このソースコードをコピーして、自分の好きなようにアレンジしていけば、おのずと順序は同じになります。そのようなコーディングを雛形を使う。といいますが、それで問題ありません。

 プロの現場でも、昨日までVerilogで今日からVHDLなんて時には、雛形を持ってきて、コーディングを始めます。その方が間違いが無く、仕事が早いですから。