目次 †概要 †
参考 †
文法 †テンプレ †// moduleのポートを設定(PORTはバスでもシグナルでもよい) module MODULE_NAME ( PORT1, // in, desc. PORT2, // in, desc. PORT3 // out, desc. ); // in / outの設定。ここでバスを明示しなければならない input selector1; input A; input B output [5:0] data; output [5:0] data_initiated = 6'd0; // output(wire)とフリップフロップ(reg)の定義。バスを明示しなければならない。 wire [5:0] output; // 本当は書かなくてもいい。outputがregの場合だけ記述しなければならない。 reg Q; reg [7:0] COUNTER; [expression] endmodule expression †NET †
代入 †
assgin O = I1 & I2; // assign文の後で Q <= D; // always文の中で
初期値を X が 1, A が 5, B が 0 とする。 ノンブロッキング代入 X <= A; B <= X; X が 5, A が 5, B が 1 となる。 ブロッキング代入 X = A; B = X; X が 5, A が 5, B が 5 となる。 以下の手続き代入文では、A = B の後に B = A が実行されるために、A と B はともに B の値として最終的に同一値を持ちます。ノンブロッキング手続き代入文では、右辺の値が確定してから左辺への代入が実行されるために、AとB の値はスワップします。 reg A, B; always @(posedge CLK) begin A = B; // ブロッキング代入 B = A; end always @(posedge CLK) begin A <= B; // ノンブロッキング代入 B <= A; end 数値 †3'b10 // 3bit 3 (3bit定数:2進数で3) 4'o10 // 4bit 8 (4bit定数:8進数で8) 8'h80 // 8bit 128 (8bit定数:16進数で80) 8'd128 // 8bit 128 (8bit定数:10進数で128) 8'bZ // ハイインピーダンス 8'bX // 不定 always †
always @([sensitivity list]) begin [expression] end
// 立ち上がり always@ (posedge CLK) begin Q <= D; end // 立ち下がり always@ (negedge CLK) begin Q <= D; end // CLKの変化 always@ (CLK) begin Q <= D; end if †if ([condition1]) begin [expression1] end else begin [expression2] end シグナルのバス化 †Q{3:0} <= {Q{2:0}, D}; assign †
assign O[7:0] = A[7:0] + 8'd1; モジュールの接続 †//以下二つは一つの記述の中では混用不可 fulladd add0(a[0], b[0], 1'b0, q[0], cout[0]); fulladd add0(.A(a[0]), .B(b[0]), .CIN(1'b0), .Q(q[0]), .COUT(cout[0])); // Recommended トラブルシューティング †Anonymous ports †
Multi-source in Unit †
コーディングルール †あと、これは、好みだと思いますが ・モジュールのI/O は大文字、内部reg, wire宣言は小文字 とするとソースが見やすくなると思います (キー入力が楽になりますよ、たぶん) ・内部reg, wire宣言は以下のルールを適用する wire xxxx_sig ; /* 後ろに"_sig"を付ける */ reg xxxx_reg ; /* 後ろに"_reg"を付ける */ ex) wire SPI_DATA_READY; // SPIモジュールデータ受信完了 ↓ wire spi_data_ready_sig ; /* SPIモジュールデータ受信完了 */ シミュレーション †
CQ Endeavor本 †
// 以下は同じ wire [7:0] dout; assign dout = (sel==1'b1) ? d1 : d0; wire [7:0] dout = (sel==1'b1) ? d1 : d0;
パターン †セレクタ †// selector wire selector1; reg [5:0] data = 6'd0; reg [11:0] latch = 12'd0; always@ (latch or selector1) begin if (selector1 == 1'd1) data[5:0] <= latch[11:6]; else data[5:0] <= latch[5:0]; end // こっちでも動くらしいが、動作が確認できない。謎。 // selector wire selector1; wire [5:0] data = 6'd0; reg [11:0] latch = 12'd0; assign data = (selector1 == 1'b1) ? latch[11:6] : latch[5:0]; ラッチ †// latch reg [11:0] latch; reg [11:0] counter; always@ (posedge request) begin latch[11:0] <= counter[11:0]; end |