平臺:XC4VSX55 ISE10.1
設計過FPGA的原理圖,看FPGA的手冊,說管腳的分配問題,如時鐘管腳要用GC類管腳,而且單端時鐘輸入時要用P類型的管腳,不能用N類型管腳等等。
一直以來都沒有試驗過,今天試驗一把,以求各種驗證。
1)GC類全局時鐘管腳是否可用作普通IO使用?
所謂GC類管腳,就是在管腳的稱是諸如IO_L1P_GC_LC等帶有GC的管腳。其實手冊中說的是GC類管腳可以用作IO的,但在《Xilinx FPGA開發實用教程》(清華出版社)574頁倒數第八行提到:“所有從全局時鐘管腳輸入的信號必須經過IBUF元,否則在布局布線時會報錯”,于是今天我試了一下,將某一GC類管腳分配給一個普通的輸入口(也試驗了分配給一個普通的輸出口),經布局布線后,未出錯。
因此得出結論:GC類全局時鐘管腳可以作為普通IO使用。(不知道是不是我對書中提到的全局時鐘管腳理解有誤,如果是,請網友別拍我,敬請留言指正)
2)非GC類全局時鐘管腳是否可以作時鐘使用?
其實至于說能否作為時鐘使用,這里有另一層函義。當然,如果你把一個普通IO口配置成輸入口,就把它的輸入信號作為時鐘,那是沒問題的。但我們一般不這么做,因為時鐘信號對于我們來說是一個很重要的信號,因此FPGA在內部會有特殊照顧,如果你使用FPGA傳門為時鐘預留的管腳,并作一些處理,那么你的時鐘對于各種模塊的時延是可以忽略的,因為時鐘在布線時是單獨走的一層,而如果你就僅用普通IO的話,經過FPGA內部布局布線后,從它的輸到,再到各個使用時鐘的地方,有的線長,有的線短,它的時延將是不一樣的。這些東西還是看一些FPGA結構的內容吧。
在xilinx里有專門的DCM IP核可供調用,在ISE中執行project——>New Source——>IP(CORE Generator & Architecture Wizard)——>FPGA Features and Design——>Clocking——>Virtex-4——>Single DCM ADV v9.1i,可得如下界面:
需要特別注意的是CLKIN Source需要選擇是External還是Internal,各自生成的源文件如下:
==========================選擇External=========================
`timescale 1ns / 1ps
module clk_test(CLKIN_IN,
CLKIN_IBUFG_OUT,
CLK0_OUT,
LOCKED_OUT);
input CLKIN_IN;
output CLKIN_IBUFG_OUT;
output CLK0_OUT;
output LOCKED_OUT;
wire CLKFB_IN;
wire CLKIN_IBUFG;
wire CLK0_BUF;
wire GND_BIT;
wire [6:0] GND_BUS_7;
wire [15:0] GND_BUS_16;
assign GND_BIT = 0;
assign GND_BUS_7 = 7'b0000000;
assign GND_BUS_16 = 16'b0000000000000000;
assign CLKIN_IBUFG_OUT = CLKIN_IBUFG;
assign CLK0_OUT = CLKFB_IN;
IBUFG CLKIN_IBUFG_INST (.I(CLKIN_IN),
.O(CLKIN_IBUFG));
BUFG CLK0_BUFG_INST (.I(CLK0_BUF),
.O(CLKFB_IN));
DCM_ADV DCM_ADV_INST (.CLKFB(CLKFB_IN),
.CLKIN(CLKIN_IBUFG),
.DADDR(GND_BUS_7[6:0]),
.DCLK(GND_BIT),
.DEN(GND_BIT),
.DI(GND_BUS_16[15:0]),
.DWE(GND_BIT),
.PSCLK(GND_BIT),
.PSEN(GND_BIT),
.PSINCDEC(GND_BIT),
.RST(GND_BIT),
.CLKDV(),
.CLKFX(),
.CLKFX180(),
.CLK0(CLK0_BUF),
.CLK2X(),
.CLK2X180(),
.CLK90(),
.CLK180(),
.CLK270(),
.DO(),
.DRDY(),
.LOCKED(LOCKED_OUT),
.PSDONE());
defparam DCM_ADV_INST.CLK_FEEDBACK = "1X";
defparam DCM_ADV_INST.CLKDV_DIVIDE = 2.0;
defparam DCM_ADV_INST.CLKFX_DIVIDE = 1;
defparam DCM_ADV_INST.CLKFX_MULTIPLY = 4;
defparam DCM_ADV_INST.CLKIN_DIVIDE_BY_2 = "FALSE";
defparam DCM_ADV_INST.CLKIN_PERIOD = 16.129;
defparam DCM_ADV_INST.CLKOUT_PHASE_SHIFT = "NONE";
defparam DCM_ADV_INST.DCM_AUTOCALIBRATION = "TRUE";
defparam DCM_ADV_INST.DCM_PERFORMANCE_MODE = "MAX_SPEED";
defparam DCM_ADV_INST.DESKEW_ADJUST = "SYSTEM_SYNCHRONOUS";
defparam DCM_ADV_INST.DFS_FREQUENCY_MODE = "LOW";
defparam DCM_ADV_INST.DLL_FREQUENCY_MODE = "LOW";
defparam DCM_ADV_INST.DUTY_CYCLE_CORRECTION = "TRUE";
defparam DCM_ADV_INST.FACTORY_JF = 16'hF0F0;
defparam DCM_ADV_INST.PHASE_SHIFT = 0;
defparam DCM_ADV_INST.STARTUP_WAIT = "FALSE";
endmodule
==========================選擇Internal=========================
`timescale 1ns / 1ps
module clk1_test(CLKIN_IN,
CLK0_OUT,
LOCKED_OUT);
input CLKIN_IN;
output CLK0_OUT;
output LOCKED_OUT;
wire CLKFB_IN;
wire CLK0_BUF;
wire GND_BIT;
wire [6:0] GND_BUS_7;
wire [15:0] GND_BUS_16;
assign GND_BIT = 0;
assign GND_BUS_7 = 7'b0000000;
assign GND_BUS_16 = 16'b0000000000000000;
assign CLK0_OUT = CLKFB_IN;
BUFG CLK0_BUFG_INST (.I(CLK0_BUF),
.O(CLKFB_IN));
DCM_ADV DCM_ADV_INST (.CLKFB(CLKFB_IN),
.CLKIN(CLKIN_IN),
.DADDR(GND_BUS_7[6:0]),
.DCLK(GND_BIT),
.DEN(GND_BIT),
.DI(GND_BUS_16[15:0]),
.DWE(GND_BIT),
.PSCLK(GND_BIT),
.PSEN(GND_BIT),
.PSINCDEC(GND_BIT),
.RST(GND_BIT),
.CLKDV(),
.CLKFX(),
.CLKFX180(),
.CLK0(CLK0_BUF),
.CLK2X(),
.CLK2X180(),
.CLK90(),
.CLK180(),
.CLK270(),
.DO(),
.DRDY(),
.LOCKED(LOCKED_OUT),
.PSDONE());
defparam DCM_ADV_INST.CLK_FEEDBACK = "1X";
defparam DCM_ADV_INST.CLKDV_DIVIDE = 2.0;
defparam DCM_ADV_INST.CLKFX_DIVIDE = 1;
defparam DCM_ADV_INST.CLKFX_MULTIPLY = 4;
defparam DCM_ADV_INST.CLKIN_DIVIDE_BY_2 = "FALSE";
defparam DCM_ADV_INST.CLKIN_PERIOD = 16.129;
defparam DCM_ADV_INST.CLKOUT_PHASE_SHIFT = "NONE";
defparam DCM_ADV_INST.DCM_AUTOCALIBRATION = "TRUE";
defparam DCM_ADV_INST.DCM_PERFORMANCE_MODE = "MAX_SPEED";
defparam DCM_ADV_INST.DESKEW_ADJUST = "SYSTEM_SYNCHRONOUS";
defparam DCM_ADV_INST.DFS_FREQUENCY_MODE = "LOW";
defparam DCM_ADV_INST.DLL_FREQUENCY_MODE = "LOW";
defparam DCM_ADV_INST.DUTY_CYCLE_CORRECTION = "TRUE";
defparam DCM_ADV_INST.FACTORY_JF = 16'hF0F0;
defparam DCM_ADV_INST.PHASE_SHIFT = 0;
defparam DCM_ADV_INST.STARTUP_WAIT = "FALSE";
endmodule
比較以上兩段代碼,區別在于選擇是External時CLKIN經過了IBUFG才到的DCM_ADV,而選擇Internal的CLKIN則直接到了DCM_AV,而IBUFG就是原語“全局時鐘緩沖”單元,我們使用時要選擇External,只有當我們的級聯兩個DCM模塊時,直接與外面相連的選External,而另一個選擇Internal。
這也是本文的一個知識點吧:兩個DCM級聯時,直接與外面相連的選External,而另一個選擇Internal。
所以本段的主題是“非GC類全局時鐘管腳是否可以作時鐘使用?”其實更多應該指的是“非GC類全局時鐘管腳是否可以接到IBUFG?”
試驗中,我們將External的DCM的輸入CLKIN輸入引腳配置成一個普通的IO口,即非GC類全局時鐘管腳,布局布線階段出現以下錯誤:
ERROR:Place:645 - A clock IOB clock component is not placed at an optimal clock IOB site. The clock IOB component
因此得出結論:非GC類全局時鐘管腳不可以作時鐘使用(其實是不可以接到IBUFG的輸入端)。
3)在Xilinx手冊中提到,如果使用單端輸入時鐘,要使用P類型GC全局時鐘管腳,那么空間N類型的管腳是否可以么?
所謂P類型還是N類型其實指的是IO_L1P_GC_LC或IO_L1N_GC_LC,注意這里的L1P和L1N,這就標識這個管腳是P類型還是N類型。
試驗中,我們將N類型全局時鐘管腳配置給CLKIN,結果布局布線時出現與(2)中一樣的錯誤。
因此得出結論:GC類全局時鐘管腳N類型管腳不可以作為單端時鐘輸入管腳(其實也是不能作為IBUFG的輸入端)
4)差分時鐘輸入時鐘管腳能否配置普通IO?N類型管腳和P類型管腳必須分別給配置P類型GC全局時鐘管腳和N類型GC全局時鐘管腳?
<4.1>使用了一對普通IO配置給DCM的CLKIN_N_IN和CLKIN_P_IN,并且將這對普通的IO的P型分配給DCM的CLKIN_N_IN型輸入,IO的N型分配給DCM的CLKIN_P_IN型輸入,出現如下錯誤:
ERROR:Place:604 - The I/O components "clkp" and "clkn" are the P- and N-sides of a differental I/O pair. The component
<4.2>使用了一對普通IO配置給DCM的CLKIN_N_IN和CLKIN_P_IN,并且對應地將這對普通的IO的P型分配給DCM的CLKIN_P_IN型輸入,IO的N型分配給DCM的CLKIN_N_IN型輸入,出現如下錯誤:
ERROR:Place:645 - A clock IOB clock component is not placed at an optimal clock IOB site. The clock IOB component
<4.3>使用一對GC類全局時鐘IO管腳配置給DCM的CLKIN_N_IN和CLKIN_P_IN,并且將這對普通的IO的P型分配給DCM的CLKIN_N_IN型輸入,IO的N型分配給DCM的CLKIN_P_IN型輸入,出現與4.1中相同的錯誤。
<4.4>正常配置,即使用了一對GC類全局時鐘IO管腳配置給DCM的CLKIN_N_IN和CLKIN_P_IN,并且對應地將這對普通的IO的P型分配給DCM的CLKIN_P_IN型輸入,IO的N型分配給DCM的CLKIN_N_IN型輸入,則完全正確。
因此得出結論:差分時鐘輸入時必須使用一對GC類全局時鐘IO管腳配置給DCM的CLKIN_N_IN和CLKIN_P_IN,且N類型和P類型要匹配。
其實這個歸根到底還是原語IBUFGDS在作怪,查看一下差分輸入DCM的原文件就行了:
IBUFGDS CLKIN_IBUFGDS_INST (.I(CLKIN_P_IN),
.IB(CLKIN_N_IN),
.O(CLKIN_IBUFGDS));
5)那么如果將輸入輸出口配置成非IO管腳會怎么樣呢?
在試驗中,將某一VCCO配置成了給了輸出口,結果在映射階段出現如下錯誤:
ERROR:MapLib:30 - LOC constraint AF17 on q<2> is invalid: No such site on the
因此,不能將輸入輸出口配置成非IO管腳,當然這樣配置本身也是不合理的。
評論
查看更多