考了好幾次終於過了,有種安心的感覺,原本還以為要到下一星期才過的了呢!
接下來就利用空閒時間來好好計畫我的期末報告了,期望是別寫到詞窮@@
2007年4月23日 星期一
2007年4月9日 星期一
2007年4月2日 星期一
除法機範例
`define NUM_STATE_BITS 2
`define IDLE 2'b00
`define INIT 2'b01
`define COMPUTE1 2'b10
`define COMPUTE2 2'b11
module cl(clk);
parameter TIME_LIMIT = 110000; //1250;
output clk;
reg clk;
initial
clk = 0;
always
#50 clk = ~clk;
always @(posedge clk)
if ($time > TIME_LIMIT) #70 $stop;
endmodule
module slow_div_system(pb,ready,x,y,r2,sysclk);
input pb,x,y,sysclk;
output ready,r2;
wire pb;
wire [11:0] x,y;
reg ready;
reg [11:0] r1,r2;
reg [`NUM_STATE_BITS-1:0] present_state;
always
begin
@(posedge sysclk) enter_new_state(`IDLE);
r1 <= @(posedge sysclk) x;
ready = 1;
if (pb)
begin
@(posedge sysclk) enter_new_state(`INIT);
r2 <= @(posedge sysclk) 0;
while (r1 >= y)
begin
@(posedge sysclk) enter_new_state(`COMPUTE1);
r1 <= @(posedge sysclk) r1 - y;
@(posedge sysclk) enter_new_state(`COMPUTE2);
r2 <= @(posedge sysclk) r2 + 1;
end
end
end
task enter_new_state;
input [`NUM_STATE_BITS-1:0] this_state;
begin
present_state = this_state;
#1 ready=0;
end
endtask
always @(posedge sysclk) #20
$display("%d r1=%d r2=%d pb=%b ready=%b", $time, r1,r2, pb, ready);
endmodule
module top;
reg pb;
reg [11:0] x,y;
wire [11:0] quotient;
wire ready;
integer s;
wire sysclk;
cl #20000 clock(sysclk);
slow_div_system slow_div_machine(pb,ready,x,y,quotient,sysclk);
initial
begin
pb= 0;
x = 0;
y = 7;
#250;
@(posedge sysclk);
for (x=0; x<=14; x = x+1)
begin
@(posedge sysclk);
pb = 1;
@(posedge sysclk);
pb = 0;
@(posedge sysclk);
wait(ready);
@(posedge sysclk);
if (x/y === quotient)
$display("ok");
else
$display("error x=%d y=%d x/y=%d quotient=%d",x,y,x/y,quotient);
end
$stop;
end
endmodule

雖然結果已經跑出來,但還在研究語法的意義,接下來就嘗試修改成乘法機了
`define IDLE 2'b00
`define INIT 2'b01
`define COMPUTE1 2'b10
`define COMPUTE2 2'b11
module cl(clk);
parameter TIME_LIMIT = 110000; //1250;
output clk;
reg clk;
initial
clk = 0;
always
#50 clk = ~clk;
always @(posedge clk)
if ($time > TIME_LIMIT) #70 $stop;
endmodule
module slow_div_system(pb,ready,x,y,r2,sysclk);
input pb,x,y,sysclk;
output ready,r2;
wire pb;
wire [11:0] x,y;
reg ready;
reg [11:0] r1,r2;
reg [`NUM_STATE_BITS-1:0] present_state;
always
begin
@(posedge sysclk) enter_new_state(`IDLE);
r1 <= @(posedge sysclk) x;
ready = 1;
if (pb)
begin
@(posedge sysclk) enter_new_state(`INIT);
r2 <= @(posedge sysclk) 0;
while (r1 >= y)
begin
@(posedge sysclk) enter_new_state(`COMPUTE1);
r1 <= @(posedge sysclk) r1 - y;
@(posedge sysclk) enter_new_state(`COMPUTE2);
r2 <= @(posedge sysclk) r2 + 1;
end
end
end
task enter_new_state;
input [`NUM_STATE_BITS-1:0] this_state;
begin
present_state = this_state;
#1 ready=0;
end
endtask
always @(posedge sysclk) #20
$display("%d r1=%d r2=%d pb=%b ready=%b", $time, r1,r2, pb, ready);
endmodule
module top;
reg pb;
reg [11:0] x,y;
wire [11:0] quotient;
wire ready;
integer s;
wire sysclk;
cl #20000 clock(sysclk);
slow_div_system slow_div_machine(pb,ready,x,y,quotient,sysclk);
initial
begin
pb= 0;
x = 0;
y = 7;
#250;
@(posedge sysclk);
for (x=0; x<=14; x = x+1)
begin
@(posedge sysclk);
pb = 1;
@(posedge sysclk);
pb = 0;
@(posedge sysclk);
wait(ready);
@(posedge sysclk);
if (x/y === quotient)
$display("ok");
else
$display("error x=%d y=%d x/y=%d quotient=%d",x,y,x/y,quotient);
end
$stop;
end
endmodule
雖然結果已經跑出來,但還在研究語法的意義,接下來就嘗試修改成乘法機了
2007年3月19日 星期一
除法機程式碼
module div(r1,r2,r3,pb,clk,x,y,ready) ;
input pb , clk;
input [3:0] x,y;
output [3:0]ready,r3,r2,r1;
wire pb;
wire[3:0] r1,r2,r3;
reg[3:0] r1,r2,r3,ready;
always
begin
@(posedge clk)
r1<=x ;
r2<=0 ;
ready=1;
if (pb) begin while(r1>=1)
begin
@(posedge clk)
r1<=r1-y;
@(posedge clk) r2<=r2+1;
@(posedge clk) r3<=r2;
end
end
end
endmodule
input pb , clk;
input [3:0] x,y;
output [3:0]ready,r3,r2,r1;
wire pb;
wire[3:0] r1,r2,r3;
reg[3:0] r1,r2,r3,ready;
always
begin
@(posedge clk)
r1<=x ;
r2<=0 ;
ready=1;
if (pb) begin while(r1>=1)
begin
@(posedge clk)
r1<=r1-y;
@(posedge clk) r2<=r2+1;
@(posedge clk) r3<=r2;
end
end
end
endmodule
2007年3月12日 星期一
範例
一個計數器的電路如下︰
module Div20x (rst, clk, cet, cep, count,tc);
//TITLE 'Divide-by-20 Counter with enables'
//enable CEP is a clock enable only
//enable CET is a clock enable and enables the TC output
// 使用 Verilog 語言描述的一個計數器
parameter size = 5;
parameter length = 20;
input rst; // 這些輸出/輸入表示這個模組的對外連線
input clk;
input cet;
input cep;
output [size-1:0] count;
output tc;
reg [size-1:0] count; // 宣告硬體內的暫存器
wire tc; // 連接線
// 下方的 always 塊是屬於平行執行的塊,當任何時間 rst 或 clk 訊號有從 low 到 high 的轉變時候就會被執行
always @ (posedge rst or posedge clk)
begin
if (rst) // 這個模擬計數器的重設
count <= 5'b0;
else if (cet && cep) // 這個模擬兩個 enable 訊號都為 true
begin
if (count == length-1)
begin
count <= 5'b0;
end
else
count <= count + 5'b1; // 5'b1 是 5 bits 寬度且等於 1 的數值
end
end
// tc的值將按照後面的運算式實時改變
assign tc = (cet && (count == length-1));
endmodule
Verilog 中的"<="運算子的是它成為硬體描述語言而跟普通程序語言不同之處。這種敘述稱為"非阻塞賦值"(non-blocking)。當電路模擬執行時候,所有使用 "<=" 運算子的訊號(signals)都是平行被執行。這點跟實際硬體中觸發器(台譯:正反器)(Flip-Flop)的行為很相似。
另外一種指定運算的描述是 "=" 運算子,也就是 "阻塞賦值"(blocking) 的賦值方式。當使用 "=" 運算子時後,所有的東西都會循序的執行,類似普通的程式語言一樣。
範例:
...
reg a, b, c, d;
wire e;
...
always @(b or e)
begin
a = b & e;
b = a b;
#5 c = b;
d = #6 c ^ e;
end
上面的 always 句子描述了另外一種使用的方法,例如,任何在表列中的實體,像是 b 或 e 的內容在任何時候有所改變,always 後的就會被執行。當這些值有所改變,a 和 b 就會馬上給上新的值。經過 5 個時間單位的延遲,b 的值才會指定給 c,且 c ^ e 運算的值會藏入看不到儲存的空間中。然後經過 6 單位的時間後,d 才會得到剛才計算的值。
來自 維基百科
module Div20x (rst, clk, cet, cep, count,tc);
//TITLE 'Divide-by-20 Counter with enables'
//enable CEP is a clock enable only
//enable CET is a clock enable and enables the TC output
// 使用 Verilog 語言描述的一個計數器
parameter size = 5;
parameter length = 20;
input rst; // 這些輸出/輸入表示這個模組的對外連線
input clk;
input cet;
input cep;
output [size-1:0] count;
output tc;
reg [size-1:0] count; // 宣告硬體內的暫存器
wire tc; // 連接線
// 下方的 always 塊是屬於平行執行的塊,當任何時間 rst 或 clk 訊號有從 low 到 high 的轉變時候就會被執行
always @ (posedge rst or posedge clk)
begin
if (rst) // 這個模擬計數器的重設
count <= 5'b0;
else if (cet && cep) // 這個模擬兩個 enable 訊號都為 true
begin
if (count == length-1)
begin
count <= 5'b0;
end
else
count <= count + 5'b1; // 5'b1 是 5 bits 寬度且等於 1 的數值
end
end
// tc的值將按照後面的運算式實時改變
assign tc = (cet && (count == length-1));
endmodule
Verilog 中的"<="運算子的是它成為硬體描述語言而跟普通程序語言不同之處。這種敘述稱為"非阻塞賦值"(non-blocking)。當電路模擬執行時候,所有使用 "<=" 運算子的訊號(signals)都是平行被執行。這點跟實際硬體中觸發器(台譯:正反器)(Flip-Flop)的行為很相似。
另外一種指定運算的描述是 "=" 運算子,也就是 "阻塞賦值"(blocking) 的賦值方式。當使用 "=" 運算子時後,所有的東西都會循序的執行,類似普通的程式語言一樣。
範例:
...
reg a, b, c, d;
wire e;
...
always @(b or e)
begin
a = b & e;
b = a b;
#5 c = b;
d = #6 c ^ e;
end
上面的 always 句子描述了另外一種使用的方法,例如,任何在表列中的實體,像是 b 或 e 的內容在任何時候有所改變,always 後的就會被執行。當這些值有所改變,a 和 b 就會馬上給上新的值。經過 5 個時間單位的延遲,b 的值才會指定給 c,且 c ^ e 運算的值會藏入看不到儲存的空間中。然後經過 6 單位的時間後,d 才會得到剛才計算的值。
來自 維基百科
Verilog HDL
Verilog HDL是一種硬體描述語言(hardware description language),為了製作數位電路(數字電路)而用來描述ASICs和FPGA的設計之用。Verilog 的設計者想要以 C 程式語言(en:C programming language)為基礎設計一種語言,可以使工程師比較熟悉跟容易接受。事實上,它產生與 C 程式語言類似的不嚴謹性質,並且大概與Pascal很相像。
這種語言跟傳統的程式設計語言不同,在於它的程式敘述並非嚴格地線性(循序)執行。Verilog 模式包含不同模組(modules)的階層關係。模組(modules)是輸出(inputs)和輸入(outputs)所定義出來的一個集合。在每個模組中,有一串的電線(wires)、暫存器(registers)和子模組(submodules)的定義。並且在每個模組裡面,語言敘述大部分都被群組成為各種的執行區塊(blocks),用來定義該模組所產生的行為描述。在每個區塊(blocks)內,使用 begin 和 end 的關鍵字來區隔開來,其中的敘述是循序被執行。但是同一個設計,不同的區塊間的執行是平行的。
Verlilog中,僅有部分的代碼被稱為可綜合的(synthesizable)。如果在一個電路設計的模組中僅包含可綜合的敘述,那麼這個電路設計就可以被適當的軟體,綜合為電腦晶片的電路layout。
截自 維基百科
這種語言跟傳統的程式設計語言不同,在於它的程式敘述並非嚴格地線性(循序)執行。Verilog 模式包含不同模組(modules)的階層關係。模組(modules)是輸出(inputs)和輸入(outputs)所定義出來的一個集合。在每個模組中,有一串的電線(wires)、暫存器(registers)和子模組(submodules)的定義。並且在每個模組裡面,語言敘述大部分都被群組成為各種的執行區塊(blocks),用來定義該模組所產生的行為描述。在每個區塊(blocks)內,使用 begin 和 end 的關鍵字來區隔開來,其中的敘述是循序被執行。但是同一個設計,不同的區塊間的執行是平行的。
Verlilog中,僅有部分的代碼被稱為可綜合的(synthesizable)。如果在一個電路設計的模組中僅包含可綜合的敘述,那麼這個電路設計就可以被適當的軟體,綜合為電腦晶片的電路layout。
截自 維基百科
訂閱:
文章 (Atom)