上次我們用開源EDA工具iverilog在Linux系統上成功仿真了wujian100_open,那麼這次我們將使用Xilinx的FPGA開發工具vivado綜合和實現wujian100,並最終生成可以直接下載到FPGA裡的比特流文件。
不過這次我們不用Linux系統了,因為我之前已經在Windows系統上安裝了Vivado 2018.3,沒在Linux上裝vivado,vivado這個軟件也挺龐大的,下載安裝有點兒麻煩,而且我也沒在Linux上裝別的綜合工具(比如官方推薦的Synplify),所以我就直接在Windows系統上用vivado實現吧。
確定工程所用文件
因為官方是用在Linux系統上用Synplify + Vivado生成比特流的,我們要在Windows系統上實現的話,就不能直接用官方的腳本文件啊啥的了,那麼我們第一步就是要搞清楚,工程要用到哪些文件。我們打開synplify目錄下的“wujian100_open_200t_3b.prj”文件,看看Synplify工程的建立細節。
好了,工程所用的源文件我們現在知道了,到時候用vivado創建工程的時候再對照著添進去就行了。注意,添加的時候要仔細看好,不要不要添錯了哦,別一股腦地 全選,添加。
這裡注意一下“wujian100_open_200t_3b.prj”文件下面的內容。
紅色框框的那裡是時序約束文件,“wujian100_open-masterfpgaxdcXC7A200T3B.xdc”這個約束文件只是管腳約束,到時候我們還要把紅色框框那個文件裡的時序約束內容添到“XC7A200T3B.xdc”裡。藍色框框裡的是包含文件,添源文件時別忘記把“soc/param”裡的包含文件也添進去。綠色框框裡是器件信息,到時候建立工程時選器件要用上。
然後我們來看一下“wujian100_open.sdc”這個約束文件裡有什麼內容。
# Clocks
#top
define_clock {n:PIN_EHS} -name PIN_EHS -freq 20 -clockgroup clkgroup_2
define_clock {n:PAD_JTAG_TCLK} -name PAD_JTAG_TCLK -freq 2 -clockgroup clkgroup_3
define_clock {n:x_aou_top.x_rtc0_sec_top.x_rtc_aou_top.x_rtc_clk_div.i_rtc_ext_clk} -name I_RTC_EXT_CLK -freq 1 -clockgroup clkgroup_4
define_clock {n:x_aou_top.x_rtc0_sec_top.x_rtc_aou_top.x_rtc_clk_div.rtc_clk_div} -name RTC_CLK_DIV -freq 0.5 -clockgroup clkgroup_4
#pwm
define_clock {n:x_pdu_top.x_sub_apb0_top.x_pwm_sec_top.x_pwm.x_pwm_ctrl.clkdiv} -name CLKDIV -freq 5 -clockgroup clkgroup_2
#
這個約束文件的內容描述了 五個時鐘:PIN_EHS、PAD_JTAG_TCLK、I_RTC_EXT_CLK、RTC_CLK_DIV 和 CLKDIV,三個時鐘組:clkgroup_2、clkgroup_3 和 clkgroup_4 。
好的,我們把這些約束轉化為xdc文件的語法,寫入到“XC7A200T3B.xdc”裡。向“XC7A200T3B.xdc”中加入以下語句:
create_clock -period 50.00 -name PIN_EHS [get_ports PIN_EHS]
create_clock -period 500.00 -name PAD_JTAG_TCLK [get_ports PAD_JTAG_TCLK]
create_clock -period 1000.00 -name I_RTC_EXT_CLK [get_cells x_aou_top/x_rtc0_sec_top/x_rtc_aou_top/x_rtc_clk_div/i_rtc_ext_clk]
create_clock -period 2000.00 -name RTC_CLK_DIV [get_cells x_aou_top/x_rtc0_sec_top/x_rtc_aou_top/x_rtc_clk_div/rtc_clk_div]
create_clock -period 200.00 -name CLKDIV [get_cells x_pdu_top/x_sub_apb0_top/x_pwm_sec_top/x_pwm/x_pwm_ctrl/clkdiv]
set_clock_groups -name clkgroup_2 -asynchronous -group [get_clocks PIN_EHS] -group [get_clocks CLKDIV]
set_clock_groups -name clkgroup_3 -asynchronous -group [get_clocks PAD_JTAG_TCLK]
set_clock_groups -name clkgroup_4 -asynchronous -group [get_clocks I_RTC_EXT_CLK] -group [get_clocks RTC_CLK_DIV]
完了之後,再把下面圖片中的紅色框框中的“_c”給刪掉(看了群友的博文,說不然後面會報錯,本著不給自己找麻煩的原則,咱也刪了嘻嘻……)。然後保存。
好的我們現在可以打開vivado,建立工程了。
用建立Vivado工程並綜合實現
打開vivado,點擊左側的“create project”建立工程。
選“RTL Project”。
點擊“Add Files”添加源文件,選擇準備好的源文件。完了之後紅框框裡的全給勾上。
點擊“Add Files”添加約束文件,選擇準備好的約束文件。
器件選擇“XC7A200TFBG484-2L”。
然後工程創建成功之後會自動打開。工程打開後,在“Sources”窗口中,切換到“Compile Order”,在“Design Sources”下找到“wujian100_open_fpga_top.v”,右鍵點擊它,然後在彈出的菜單中點擊“Move to Top”這個選項,調整綜合順序。
然後我們就可以開始綜合實現了。點擊“Run Implementation”,進行綜合實現。
然後,我們等待它完成。
根據綜合實現結果更改約束文件重新綜合實現
綜合實現完成之後,我們看一下結果如何。
我們看到WHS為負,保持時間不滿足。我們雙擊查看詳細的實現報告。
點擊紅色框框的數字,查看時序違例的具體路徑。
雙擊違例路徑“Path 31”查看詳細情況。
我們看到時鐘路徑和數據路徑的終點都是同一個元件。我們再右鍵點擊“Path 31”,選擇“Schematic”,打開這條路徑的電路原理圖。
再雙擊器件的時鐘端口C(紅色框框處),查看器件時鐘的連接。
我們可以看到器件的時鐘端口C和數據端口D是連在一起的,導致這一條路徑不滿足保持時間要求。要把這條“奇怪的路徑”設為時序例外,靜態時序分析時跳過這條路徑。
此外,我們看一下實現後有哪些“warning”。
有三個時鐘無法創建,找不到對應的端口(我之前在實現的時候也有這個報錯,我到電路原理圖上一層層找,也沒有找到對應的cell)。我不太清除是我的語法錯誤還是其他原因,無法創建這三個時鐘,那就只留下主時鐘和邊界掃描時鐘吧,那三個時鐘就不創建了。
所以我們修改“XC7A200T3B.xdc”文件,去掉那三個時鐘,增加一條偽路徑,修改一下時鐘組。增加偽路徑的語句如下:
set_false_path -from [get_ports PIN_EHS] -to [get_pins x_cpu_top/CPU/x_cr_tcipif_top/x_cr_coretim_top/refclk_ff1_reg/D]
保存.xdc文件後,點擊“Run Implementation”,重新進行綜合實現。
又是一番等待之後(論有一臺好電腦的重要性!),Implementation終終終於Complete了。我們來看看結果如何。
好了,這次成功了。
生成比特流文件
實現成功之後,我們可以生成比特流文件了。
等待一會兒之後,成功生成比特流文件。
把比特流文件下載到FPGA上
有了比特流文件之後呢,就可以連接FPGA開發板,把比特流文件下載到FPGA上,這樣,你設計的電路就真正實現在FPGA(硬件)上了,然後你就可以在FPGA上運行、驗證你所設計的的電路啦~~
不過我手上沒有開發板,這一步就做不了了~
終於肝完了,啥也不懂的小白 + 慢的一匹的電腦 + 又傻又軸的死腦筋 = 肝……不過雖然這樣,這次對“約束”特別是“時序約束”有了更深一步的瞭解,之前對約束尤其是時序約束一竅不通,全靠別人寫好的約束續命,碰到時序違例更是不知所措,這次查了很多資料,終於瞭解了一點點,以後再做東西會比之前好很多。總之,這次收穫還是不少的,肝就肝了吧。
最後,一如既往地歡迎大家拍磚哦~~
文章來源:芯片開放社區
文章鏈接:https://occ.t-head.cn/community/post/detail?spm=a2cl5.14300636.0.0.1b87180flWxVN5&id=654091577878118400