Verilog-HDLのtask文を回路記述に使ってみよう -まず手始めに-
taskでVerilogをCっぽく書いてみる・・・がしかし
ハードウェア記述言語のVerilog-HDLにはtask文という構文がある.
task文中では逐次的にreg変数への代入が記述できる.
通常,task文はテストベンチ中でテストターゲットの操作を行うために利用するが,
これをなんとかうまくつかって,逐次処理の記述を楽に行うことは出来ないだろうか.
「4ビットのLEDでナイトライダー」を普通に書く
まずは普通に書いてみる.
module led(CLK, RST_X, O_ULED); input CLK; input RST_X; output reg [3:0] O_ULED; parameter skip_max = 1024*1024*45; parameter state_max = 5; reg [26:0] skip_cnt; reg [2:0] state; always @(posedge CLK or negedge RST_X) begin if(!RST_X) begin O_ULED <= 4'b0101; state <= 0; skip_cnt <= 0; end else begin skip_cnt <= (skip_cnt==skip_max)? 0:skip_cnt +1; if(skip_cnt == skip_max) begin state <= (state == state_max)? 0: state +1; case(state) 0: O_ULED <= 4'b0001; 1: O_ULED <= 4'b0010; 2: O_ULED <= 4'b0100; 3: O_ULED <= 4'b1000; 4: O_ULED <= 4'b0100; 5: O_ULED <= 4'b0010; default: O_ULED <= 4'b0000; endcase end end end endmodule
「4ビットのLEDでナイトライダー」をこんな風に書きたい
module led(CLK, RST_X, O_ULED); input CLK, RST_X; output reg [3:0] O_ULED; parameter skip_max = 1024*1024*45; task nclk; begin @(posedge CLK); end endtask task skip; input integer step; integer i; begin for(i=0;i<step;i=i+1) nclk(); end endtask task flash; O_ULED = 4'b0001; skip(skip_max); O_ULED = 4'b0010; skip(skip_max); O_ULED = 4'b0100; skip(skip_max); O_ULED = 4'b1000; skip(skip_max); O_ULED = 4'b0100; skip(skip_max); O_ULED = 4'b0010; skip(skip_max); O_ULED = 4'b0001; skip(skip_max); endtask initial begin O_ULED = 0; flash(); end endmodule
もちろん,
シミュレーションでは動いても,ISEさんは合成してくれないよ!!
task文中で"1クロック待つ"ということが実現できれば,
なんとかなりそうなのに.
でもreg変数への代入の競合を避けなければいけないから,
結局同じことかなぁ.