今天要來分享的是verilog的其中一個語法-initial以及時間單位。
initial區塊是用來定義module在開始執行時,只執行一次的區塊,這個區塊在執行時間為0時執行。通常會在初始化信號、初始化暫存器、設置初始條件時使用,以及在特定時間點後觸發某些行為。
initial的基本結構是:
initial begin
//執行指令 eg.初始化
end
如果有一些特別的目的,希望initial區塊內的某特定指令要延遲些時間才執行的話,可以使用「#數字」,數字表示所要延遲的時間,「#15」即表示延遲15個時間單位,時間到後再繼續執行後麵的指令。
那在同一個module內,並沒有限制只能存在一個initial區塊。那如果存在好幾個initial區塊,這些區塊間的關係會是並行的,所以他們會同時執行,而每個區塊內的指令一樣會按照順序執行。
那來做個練習~
module newwork(A,B,C);
input A,B;
output C;
reg clk;
reg Q;
reg flag;
initial begin
flag = 0;
Q = 0;
end
initial begin
clk = 0;
end
always begin
#10 clk = ~clk;
end
always @( posedge clk )
begin
if( flag == 0 )begin
Q = ~A;
flag = 1;
end
else if( flag == 1 )begin
Q = ~B;
flag = 0;
end
end
assign C = Q;
endmodule
一開始的flag、Q跟clk都先初始為0,然後clk每10個單位時間就反轉一次(所以這是一個週期為20個時間單位的週期性時鐘信號),而暫存器Q的內容就會隨著clk的反轉而更新,當遇到clk的rising edge時,就會交替的換成A’或B’;如果flag值為0,Q就為A’,否則為B’,然後再將Q的內容傳給output C。
在第一個always block內,就是指每10個時間單位,clk做一次反轉。
其實我本來想寫:
module newwork(A,B,C);
input A,B;
output C;
reg clk;
reg Q;
reg flag;
initial begin
flag = 0;
Q = 0;
end
//不同的地方
initial begin
clk = 0;
forever #10 clk = ~clk;
end
//
always @( posedge clk )
begin
if( flag == 0 )begin
Q = ~A;
flag = 1;
end
else if( flag == 1 )begin
Q = ~B;
flag = 0;
end
end
assign C = Q;
endmodule
但編譯的時候,forever那行一直錯誤,日後如果有找出解決方法,再上傳來分享。
那上面提到了時間單位,一個時間單位又是多久呢?
在verilog中,時間單位是可以自己決定的,我們可以在module中指定一個時間單位的長度,他與module工具的時鐘無關。
如何定義時間單位呢?我們會用「timescale」指令來做設置,這是他的語法:
`timescale <timeunit> / <time_precision>
其中<timeunit>負責定義了module中使用的基本時間單位,像是秒、毫秒、微秒。
<time_precision>則是定義了module中時間的精度,控制小數點後的時間表示精度。
記得!timescale前面有一個「`」符號喔!然後最後面不能加分號!
以上面舉的程式碼繼續做例子:
`timescale 1ns / 1ps
module newwork(A,B,C);
input A,B;
output C;
reg clk;
reg Q;
reg flag;
initial begin
flag = 0;
Q = 0;
end
initial begin
clk = 0;
end
always begin
#10 clk = ~clk;
end
always @( posedge clk )
begin
if( flag == 0 )begin
Q = ~A;
flag = 1;
end
else if( flag == 1 )begin
Q = ~B;
flag = 0;
end
end
assign C = Q;
endmodule
這樣的話,這個程式的時間就會是以1奈秒為基礎、精確度可以到1皮秒。
所以在always block中的#10,即是代表10奈秒,所以每隔10奈秒,clk就會做一次反轉,週期為20奈秒。
那如果沒有定義時間單位,但程式中有使用到與時間有關的功能,時間單位又會是多長呢?這樣的話就會使用默認的時間單位喔,那這些值可能會因為使用的模擬器不同而不同,所以建議還是要記得定義~
那今天就到這邊~謝謝~