LRM読解(Chap.2 字句定義/語彙規約)

2008/08/31Verilog::文法import

字句定義/語彙規約 ~ Lexical conventions (LRM-Chap.2)

LRMから,少し抜粋.

数値表現

| binary  | [size]*'[s|S]*(b|B)[01]+
| octal   | [size]*'[s|S]*(o|O)[0-7]+
| hexa    | [size]*'[s|S]*(h|H)[0-9a-fA-F]+
| decimal | ([size]*'[s|S]*(d|D)[0-9]+)|([0-9]+)

LRM 2.5.1 Integer constants

Example 3 Using sign with constant numbers

8'd-6   // 構文違反.
-8'd6   // 6の2の補数を示します.8bitサイズを保持します.
4'shf   // これはbinaryで 4bitの'1111'と書き直せます.
        // 2の補数表現では-1になります.
        // 即ち,これは -4'h1と等価です.
-4'sd15 // 同様にして,これは 4'd1と等価です.(-(-4'd1))

LRM 2.6 Strings

一行内で,double quotes("")で閉じられた部分を文字列とみなします.unsigned int定数として 8bit ASCII文字を取り扱うことができます.

文字列変数?の定義と使い方

stringvarというレジスタ変数を用意し,"Hello world!"を代入してみましょう.

 reg [8*12:1] stringvar;
 initial begin
   stringvar = "Hello world!";
 end

8bit widthの[12:1]配列,と見ればいいんですかねぇ.[8*(欲しい文字数):1]とすればよいようです.C言語と違い,NULL挿入はされない模様です.


LRM 2.6.2 の NOTE

意訳で敵どうだけれど,まぁ,こんなもんで.

When a variable is larger than required to hold a value being assigned,
the contents on the left are padded with zeros after the assignment.
This is consistent with the padding that occurs during assignment of nonstring values.

変数のほうが,文字列よりも大きい場合には,左側がゼロパディングされます.これは,定数のパディングと矛盾しないようになっているからである.(意訳)

If a string is larger than the destination string variable,
the string is truncated to the left, and the leftmost characters will be lost.
文字列のほうが長い場合には,文字列の左側が失われます.
LRM 2.6.3 特殊文字

C言語と同様に,下記の特殊文字が定義されます.エスケープ記号とか..

Escape Stringescape stringで示される文字
\n改行文字
\tタブ文字
\\\(バックスラッシュ, \x5C)
\"double quote(",\x22)
\dddキャラクタコード指定. dは0~7の数値を示す. ただし, 1~3個で構成する(3個必要なわけではない).

LRM 2.7 Identifiers, keywords, and system names

識別子は、それに参照をつけることができるようにユニークな名前をオブジェクトに与えるのに使用されます。識別子は、簡単な識別子かエスケープされた識別子(LRM 2.7.1参照)のどちらかです。簡単な識別子は 文字、数字、ドル記号($)、およびアンダースコア(_)の組み合わせである。簡単な識別氏の一文字目は,数値やドル記号にすべきではないです.英字か,アンダースコアなら可能です.識別子は大文字と小文字を区別するでしょう.

原文

An identifier is used to give an object a unique name so it can be referenced.
An identifier is either a simple identifier or an escaped identifier (see 2.7.1).
A simple identifier shall be any sequence of letters, digits, dollar signs ($), and underscore characters (_).
The first character of a simple identifier shall not be a digit or $;
it can be a letter or an underscore. Identifiers shall be case sensitive.

naming rule?
  • System task/functionの名前は,'$'で始まる.[LRM2.7.4]

2.8 Attribute[LRM 2.8]

syntax

attribute_instance ::= (From Annex A - A.9.1)
  (* attr_spec { , attr_spec } *)

attr_spec ::=
  attr_name = constant_expression
  | attr_name

attr_name ::=
  identifier

module

2008/08/20Verilog::文法import

module文(synthesizable/TestBench)

概要

階層化設計の一塊.入出力信号・パラメータを引数として、実体化する.
順序回路・組み合わせ回路の0個以上の組み合わせの回路ブロックを記述する.

書式

ANSI式*1を以下に示す.

module <module-name> (
   input foo,
   output bar,
   inout bus
  );
  // local signal/variable...
  begin
   // 式
  end
endmodule

それ以前の書式は以下のように記述する.

module <module-name> ;
   input foo,
   output bar,
   inout bus
// (略)
endmodule


*1 : ANSI-Cの関数記述相当.K&R時代は変数だけを並べて,型+変数名は後に記述した.Verilogでも、module名だけでセミコロンを打ち,信号名を並べてからbegin文を置く記述も可能.

moduleのパラメタ変更方法

パラメタの使い方を理解しておらず,つい最近に例を見かけて知ったので記載しておく.
defineとは違い、インスタンス化する際に値を変化させて利用することができる,と推測する.

  • defparam文
  • instance化する際に, 渡す.
     module-name #(
    		.paramete-name(value),
    		...
    	) instance-name (
    		.signal-name(symbol),
    		....
    	) ;
    

※インデントはxilinx webpack 10.1sp2の自動生成ツールの出力を真似た.

wait

2008/08/20Verilog::文法import

待ち処理(TestBench)

Test記述時に有効. 式の評価結果が TRUEになるまで待つ.
initial文でクロックに同期して処理をさせたい場合に使うとよさそう. @(posedge CLK)で十分です.

  always #20 CLK <= ~CLK;

  initial begin
   ...
   wait( CLK==0 );
   wait( CLK==1 );
→ @(posedge CLK);
  # 2  // CLK's posedge + 2 [nSec]
   hoge <= 1;
   ...
  end

wait(式?)

前述のとおり.


@ (式?)

式の状態を待つ?立ち上がり:posedge
立ち下り:negedge
などなど...と思う.調べてないけれども使ったものだけ記述.サイトではなく仕様書を見て転記してこないと、ですね.

task

2008/08/20Verilog::文法import

書式

task <name>;
	// input ; 値渡し. 呼び出しもとのreg等に影響を与えない.
	// output

	// process...
endtask

syntax

task_declaration ::= (From Annex A - A.2.7)
   task [ automatic ] task_identifier ;
     { task_item_declaration }
     statement
   endtask
 | task [ automatic ] task_identifier ( task_port_list ) ;
     { block_item_declaration }
     statement
   endtask

task_item_declaration ::=
  block_item_declaration
  | { attribute_instance } tf_input_declaration ;
  | { attribute_instance } tf_output_declaration ;
  | { attribute_instance } tf_inout_declaration ;

task_port_list ::=
  task_port_item { , task_port_item }

task_port_item ::=
  { attribute_instance } tf_input_declaration
  | { attribute_instance } tf_output_declaration
  | { attribute_instance } tf_inout_declaration

tf_input_declaration ::=
  input [ reg ] [ signed ] [ range ] list_of_port_identifiers
  | input [ task_port_type ] list_of_port_identifiers

tf_output_declaration ::=
  output [ reg ] [ signed ] [ range ] list_of_port_identifiers
  | output [ task_port_type ] list_of_port_identifiers

tf_inout_declaration ::=
  inout [ reg ] [ signed ] [ range ] list_of_port_identifiers
  | inout [ task_port_type ] list_of_port_identifiers

task_port_type ::=
  time | real | realtime | integer

block_item_declaration ::= (From Annex A - A.2.8)
  { attribute_instance } block_reg_declaration
  | { attribute_instance } event_declaration
  | { attribute_instance } integer_declaration
  | { attribute_instance } local_parameter_declaration
  | { attribute_instance } parameter_declaration
  | { attribute_instance } real_declaration
  | { attribute_instance } realtime_declaration
  | { attribute_instance } time_declaration

block_reg_declaration ::=
  reg [ signed ] [ range ]
  list_of_block_variable_identifiers ;

list_of_block_variable_identifiers ::=
  block_variable_type { , block_variable_type }

block_variable_type ::=
  variable_identifier
  | variable_identifier dimension { dimension }


概要

  • 記述はmoduleとほぼ同じ. 許容される型/process文が増える程度.
  • 引数は宣言した順に渡される.名前渡しも可能.(ドット+名前(信号))
  • input引数は値渡しになる.呼び出し元に影響はでない.
  • inout/outputは代入すると呼び元に値を返すことができる.[LRM 10.1]
  • 実回路としてsynthesize不可. simulation modelでのみ使用可能
  • "#値"による待ち処理を入れることができる. task呼び出し元は, task内で消費した時間の後に返ってくる.

その他メモ

if文を用いて、条件によって待ち時間を変化させることもできる.ex.

  if (t_AD > t_CS)  begin
    # (t_CS)
    CS_n <= 0;
    # (t_AD - t_CS)
    ADR <= ADR_buf;
  end
  else begin
    # (t_AD)
    ADR <= ADR_buf;
    # (t_CS - t_AD)
    CS_n <= 0;
  end

※CS_nとADRの変化時間が、パラメタt_ADとt_CSの大小関係により前後するため、分岐させた.後日,CPUバスの試験パターンを振るための例を示す.waveformを外部プログラムで吐いて,取り込んだほうが早かった気がするけれど。。。

Verilog覚書

2008/08/13Verilog::文法import

Verilog記述に関するメモ

Master Reference

OVI版 Verilog-LRM*1 http://www.vlsi-design.net/general/languages/verilog/

名称(IEEE-STD-1364-2001)で検索すると,まぁ,アレゲですが出てきますね.

*1 : Language Referenec Manual

Verilog Reserved Words


reference

参考にさせていただいたサイトをメモしておきます.検索するより便利か?(個人的なメモを兼ねて・・・