フラット表示 | 前のトピック | 次のトピック |
投稿者 | スレッド |
---|---|
webadm | 投稿日時: 2008-9-19 5:14 |
Webmaster 登録日: 2004-11-7 居住地: 投稿: 3088 |
RTL: CLOCK DIVIDER 次ぎはCLOCK DIVIDERブロックのRTL設計。
最も単純だが、FPGAやCPLDで水晶発振子を直接駆動する発信回路というのだけがくせ者である。ディスクリート回路ではバッファ無しのインバーターがひとつあればいいのだが、FPGAやCPLDで単純に外部からの入力を論理反転して出力するだけの記述だと、配置配線によって不確定数のバッファが挿入されることになる。 一応デバイスベンダー固有のIOプリミティブを使用することによって入出力ピンに直接接続されているIOブロック内のインバーターを使うことは可能だがうまく発振してくれるかは保証の限りではない。 うまくいかない場合には、外付けのディスクリートのインバーター回路を設けてそれで発振をさせてその出力をXT1に入力するという手もある。 cd.v: CLOCK DIVIDERインプリメンテーション module cd(ac, xt1, xt2, c3200hz, c800hz, c10hz, c1hz); // Input Port(s) input ac, xt1; // Output Port(s) output xt2, c3200hz, c800hz; output reg c10hz, c1hz; // Inout Port(s) // Parameter Declaration(s) // Additional Module Item(s) reg [9:0] div1024; reg [1:0] div4; reg [3:0] div16; reg [2:0] div5; reg [3:0] div10; assign c3200hz = div1024[9]; assign c800hz = div4[1]; assign xt2 = ~xt1; always@(posedge xt2 or negedge ac) begin if(!ac) div1024 <= 0; else if(xt2) div1024 <= div1024 + 1'b1; end always@(posedge c3200hz or negedge ac) begin if(!ac) div4 <= 0; else if(c3200hz) div4 <= div4 + 1'b1; end always@(posedge c800hz or negedge ac) begin if(!ac) div16 <= 0; else if(c800hz) div16 <= div16 + 1'b1; end always@(posedge div16[3] or negedge ac) begin if(!ac) begin div5 <= 0; c10hz <= 0; end else if(div16[3]) begin if(div5 == 6'd5) begin c10hz <= ~c10hz; div5 <= 0; end else begin div5 <= div5 + 1'b1; end end end always@(posedge c10hz or negedge ac) begin if(!ac) begin div10 <= 0; c1hz <= 0; end else if(c10hz) if(div10 == 4'd5) begin c1hz <= ~c1hz; div10 <= 10; end else begin div10 <= div10 + 1'b1; end end endmodule コンパイルした結果のネットリストは以下の通り。ちょっと見た目は違うけどバイナリで分周する部分はカスケードになっているし、どうしても2カ所5分周が必要になるのでそれも期待通り。もっとエレガントで綺麗な記述方法があるかもしれない。 |
フラット表示 | 前のトピック | 次のトピック |
投稿するにはまず登録を | |