目前我們已經(jīng)單獨(dú)使用 HLS 創(chuàng)建了IP(見上一節(jié))。在本實(shí)踐中,我們將實(shí)際實(shí)現(xiàn) HLS 組件作為 FPGA 設(shè)計的一部分。首先我們將學(xué)習(xí)如何做到這一點(diǎn),然后我們將創(chuàng)建硬件來解決一些實(shí)際問題。
首先使用上一節(jié)的文件創(chuàng)建一個新的 HLS 項(xiàng)目:
重新綜合一下
每次我們更改硬件時,我們都需要告訴 HLS 將其導(dǎo)出為硬件描述語言并生成 Vivado 需要的所有各種源數(shù)據(jù)。
選擇Solution → Export RTL → 選擇 "Vivado IP for System Generator" → 單擊確定
接下來我們需要告訴 Vivado 我們的新 IP 在哪里
回到 Vivado,打開 Block Design。單擊Window -> IP Catalog以打開 IP 目錄。單擊左側(cè) Flow Navigator 中的設(shè)置。選擇 IP,然后選擇存儲庫。按加號圖標(biāo)。從文件瀏覽器中選擇 HLS 項(xiàng)目目錄,然后單擊選擇。Vivado 將掃描 HLS 項(xiàng)目,并彈出一個框,顯示 IP 已添加到項(xiàng)目中。單擊確定。
回到 Block Design,單擊圖表左側(cè)的 Add IP 按鈕。IP 核將被稱為之前創(chuàng)建IP時輸入的顯示名稱,或者 Toplevel 。雙擊 IP 進(jìn)行添加。
要允許 IP 內(nèi)核訪問 DDR 存儲器,需要在 Zynq 處理系統(tǒng)上啟用 AXI 從接口。雙擊 Zynq IP ,選擇“PS-PL Configuration”,展開“HP Slave AXI Interface”,勾選 S AXI HP0 interface. 單擊確定,應(yīng)該會看到 Zynq 模塊上出現(xiàn)一個新端口。
現(xiàn)在可以使用連接自動化來完成連接。運(yùn)行連接自動化并檢查 S_AXI_HP0. 應(yīng)該建議連接到 m_axi IP 核上的端口。
同樣在連接自動化檢查 s_axi_AXILiteS和s_axi_control. 應(yīng)該連接到M_AXI_GP0 處理系統(tǒng)上。單擊確定。
現(xiàn)在,IP將通過其從接口連接到processing_system7_0_AXI_periph,并通過其主接口連接到AXI_mem_intercon。
現(xiàn)在可以保存模塊設(shè)計、生成比特流并再次導(dǎo)出硬件。覆蓋現(xiàn)有的硬件規(guī)范(XSA 文件)。
連接自動化問題
如果對使用連接自動化生成的 AXI 總線有問題(即,如果它們與上述結(jié)構(gòu)不同),請嘗試刪除所有AXI 互連模塊并再次運(yùn)行它。
一般原則是, Zynq 模塊的 M_AXI 應(yīng)該可追溯至 IP 內(nèi)核上的所有 S_AXI,而 IP 內(nèi)核的 M_AXI 應(yīng)可追溯至 Zynq 模塊上的 S_AXI_HP0。
在 Vitis 中使用 IP
當(dāng) HLS 導(dǎo)出我們的 IP 時,它幫助我們自動生成了一個軟件驅(qū)動程序。但是我們需要告訴 Vitis 在哪里可以找到這個驅(qū)動程序。
在 Vitis 中,選擇 Xilinx → Repositories。在 Local Repositories 下,單擊 New 并選擇 HLS 項(xiàng)目的文件夾。單擊重新掃描存儲庫,然后單擊確定。
右鍵單擊design_1_wrapper 平臺并單擊“Update Hardware Specification”以更新我們已更改硬件的問題。
我們現(xiàn)在應(yīng)該能夠看到新 IP 及其驅(qū)動程序。
在 Board Support Package 設(shè)置下的platform.spr 文件中,應(yīng)該能夠看到列出的 IP,以及它使用驅(qū)動程序.
現(xiàn)在可以與IP進(jìn)行交互了,如下例所示。
#include#include"platform.h" #include"xil_printf.h" #include"xparameters.h" #include"xtoplevel.h" #include"xil_cache.h" u32shared[1000]; intmain(){ inti; XToplevelhls; init_platform(); Xil_DCacheDisable(); print(" HLStest "); for(i=0;i100;?i++)?{ ????????shared[i]?=?i; ????} ????shared[0]?=?8000; ? ????XToplevel_Initialize(&hls,?XPAR_TOPLEVEL_0_DEVICE_ID); ????XToplevel_Set_ram(&hls,?(u32)?shared); ????XToplevel_Start(&hls); ????while(!XToplevel_IsDone(&hls)); ? ????printf("arg2?=?%lu arg3?=?%lu ",?XToplevel_Get_arg2(&hls),?XToplevel_Get_arg3(&hls)); ? ????cleanup_platform(); ????return?0; }
對 FPGA 進(jìn)行編程并啟動此代碼,應(yīng)該會看到以下內(nèi)容:
HLStest arg2=12950 arg3=3050
如您所見,目前組件可以使用XToplevel_Start啟動,xtopleevel_IsDone會告訴你何時完成。XToplevel_Set_ram告訴HLS組件共享內(nèi)存在主內(nèi)存中的位置。允許HLS讀寫,就像RAM從0開始一樣,但實(shí)際上它將指向我們的共享內(nèi)存。不要忘記設(shè)置RAM偏移量,否則HLS組件將寫入隨機(jī)內(nèi)存位!
當(dāng)更改 HLS 時
當(dāng)更改 HLS 代碼時,請執(zhí)行以下步驟以確保的最終文件已更新。
重新運(yùn)行綜合。
重新導(dǎo)出 IP 核。
在 Vivado 中,應(yīng)該已經(jīng)識別到了變化,并且會出現(xiàn)一條消息說“IP Catalog is out-of-date”。
如果沒有,請單擊 IP Status,然后單擊重新運(yùn)行報告
單擊刷新 IP 目錄
在“Generate Output Products”對話框中,單擊“Generate”。
單擊生成比特流。
導(dǎo)出硬件(包括比特流)。
在 Vitis 中重新編程 FPGA 并運(yùn)行軟件。
如果更改了硬件接口,可能需要重新生成系統(tǒng)并將應(yīng)用程序項(xiàng)目移入其中。
測量執(zhí)行時間
下面將舉例使用 ARM 處理系統(tǒng)中的計時器來測量執(zhí)行一段代碼需要多長時間,然后演示可以在硬件中更快地執(zhí)行相同的操作。我們要測量的代碼實(shí)現(xiàn)了對Collatz(柯拉茲) 猜想的測試。該猜想指出:
柯拉茲猜想
取任何 正整數(shù)n(其中n不為0)。如果 n 是偶數(shù),則除以 2 得到 n / 2。如果 n 是奇數(shù),則將其乘以 3 并加 1 得到 3 n + 1。無限重復(fù)該過程。猜想是,無論你從哪個數(shù)字開始,你最終總會達(dá)到 1。
創(chuàng)建一個 HLS 組件來測試前 1000 個整數(shù),以驗(yàn)證如果執(zhí)行上述步驟,它們最終都會收斂到 1。將在共享數(shù)組中輸出每個數(shù)字達(dá)到 1 所需的步數(shù)。
下面的代碼是使用的ARM軟件:
#include#include"platform.h" #include"xil_printf.h" #include"xparameters.h" #include"xtoplevel.h" #include"xil_cache.h" intshared[1000]; XToplevelhls; unsignedintcollatz(unsignedintn){ intcount=0; while(n!=1){ if(n%2==0){ n/=2; }else{ n=(3*n)+1; } count++; } returncount; } voidsoftware(){ inti; for(i=0;i1000;?i++)?{ ????????shared[i]?=?collatz(i?+?1); ????} } ? void?hardware()?{ ????//Start?the?hardware?IP?core ????XToplevel_Start(&hls); ????//Wait?until?it?is?done ????while(!XToplevel_IsDone(&hls)); } ? void?print_shared()?{ ????int?i; ????for(i?=?0;?i?1000;?i++)?{ ????????xil_printf("%d?",?shared[i]); ????} ????xil_printf(" "); } ? void?setup_shared()?{ ????int?i; ????for(i?=?0;?i?1000;?i++)?{ ????????shared[i]?=?i+1;?//(we?use?i+1?because?collatz?of?0?is?an?infinite?loop) ????} } ? int?main()?{ ????init_platform(); ????Xil_DCacheDisable(); ????//Initialise?the?HLS?driver ????XToplevel_Initialize(&hls,?XPAR_TOPLEVEL_0_DEVICE_ID); ????XToplevel_Set_ram(&hls,?(int)?shared); ????xil_printf(" Start "); ?? ????setup_shared(); ????software(); ????print_shared(); ? ????setup_shared(); ????hardware(); ????print_shared(); ? ????cleanup_platform(); ????return?0; }
檢查此代碼。該函數(shù)software()是前 1000 個整數(shù)的 Collatz 迭代階段的軟件實(shí)現(xiàn),將迭代計數(shù)放在全局?jǐn)?shù)組shared中。該main函數(shù)設(shè)置 shared為 1 到 1001 的整數(shù),運(yùn)行software(),然后將結(jié)果打印出來。然后它重置共享并運(yùn)行hardware()并打印結(jié)果。
在 HLS 中實(shí)現(xiàn)一個硬件組件來計算前 1000 個整數(shù)的 Collatz 計數(shù)(就像 ARM 軟件一樣)。從以下頂級結(jié)構(gòu)開始:
#include//Requiredformemcpy() uint32workingmem[1000]; uint32toplevel(uint32*ram,uint32*arg1,uint32*arg2,uint32*arg3,uint32*arg4){ #pragmaHLSINTERFACEm_axiport=ramoffset=slavebundle=MAXI #pragmaHLSINTERFACEs_axiliteport=arg1bundle=AXILiteS #pragmaHLSINTERFACEs_axiliteport=arg2bundle=AXILiteS #pragmaHLSINTERFACEs_axiliteport=arg3bundle=AXILiteS #pragmaHLSINTERFACEs_axiliteport=arg4bundle=AXILiteS #pragmaHLSINTERFACEs_axiliteport=returnbundle=AXILiteS //Readinstartingvalues memcpy(workingmem,ram,4000); //CalculatetheCollatzresults. //workingmem[x]=collatz(workingmem[x]); //...yourcodehere... //Burstcopyworkingmemtomainmemory memcpy(ram,workingmem,4000); return0; }
因?yàn)?Collatz 循環(huán)是無界的,所以 HLS 將只有問號而不是時間估計。
然后將 IP 核放入設(shè)計中并運(yùn)行 IP 核以測試它是否輸出正確的答案。以上main.c應(yīng)該可以驅(qū)動 IP 內(nèi)核。
那么,硬件或軟件更快?
審核編輯:劉清
-
FPGA設(shè)計
+關(guān)注
關(guān)注
9文章
428瀏覽量
26639 -
Vivado
+關(guān)注
關(guān)注
19文章
815瀏覽量
66915 -
HLS
+關(guān)注
關(guān)注
1文章
130瀏覽量
24213
原文標(biāo)題:在 Vivado 中使用 HLS 創(chuàng)建的IP
文章出處:【微信號:Open_FPGA,微信公眾號:OpenFPGA】歡迎添加關(guān)注!文章轉(zhuǎn)載請注明出處。
發(fā)布評論請先 登錄
相關(guān)推薦
請問一下怎樣去設(shè)計一種基于stm32f103的數(shù)字示波器呢
使用Vitis HLS創(chuàng)建屬于自己的IP相關(guān)資料分享
使用教程分享:在Zynq AP SoC設(shè)計中高效使用HLS IP(一)
![使用教程分享:在Zynq AP SoC設(shè)計中高效使用<b class='flag-5'>HLS</b> <b class='flag-5'>IP</b>(<b class='flag-5'>一</b>)](https://file1.elecfans.com//web2/M00/A6/A5/wKgZomUMP2GAfzGJAAAxmJ2OQAk438.png)
評論