天天看點

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

原文作者:FPGA設計論壇

        建構SoC系統,畢竟是需要實作PS和PL間的資料互動,而像上一講那樣PL主機與PL從機之間通過AXI4-Lite總線進行互動有點殺雞用牛刀了。

        如果PS與PL端進行資料互動,可以直接設計PL端為從機,PS端向PL端的reg寫入資料即可,但是對于圖像處理等大資料量的資料互動來說,PL端的BRAM畢竟容量有限,很難用BRAM作為兩者間的資料緩存器。對于這樣的應用來說,利用DDR3作為PS端與PL端之間互動的資料緩存器是最合适不過的。

1.工程規劃

        再ZedBoard闆子的硬體設計方案中,DDR晶片的管腳是綁定到Zynq的DDR接口上的。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        而Zynq系統的這個DDR總線接口有是連結在其内部“Memory Interfaces”中的“DDR2/3,LPDDR2 Controller”可配置硬核上的。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        是以,要想PL通路闆上的DDR3存儲器,必須借道Zynq中的“Memory Interfaces----DDR2/3,LPDDR2 Controller”(後文簡稱“DDR3 Controller”)。根據之前的經驗,在Zynq系統中,ARM Core(CPU)能夠通路硬核“DDR3 Controller”,根據經驗可以确定“DDR3 Controller”一定是一個從裝置,而PL要想通路“DDR3 Controller”的話,PL一定要是一個主裝置,由PL發起讀寫操作。

        “DDR3 Controller”是封裝在Zynq子系統中的,是以,PL必須連接配接Zynq的從機接口。從上圖可以看出,Zynq有兩個從機接口,分别是“32b GP AXI Slave Ports”和“High Performance AXI 32b/64b Slave Ports”根據名稱可以看出,一個是高性能的,另一個應該是普通的。之前Zynq作為主機連接配接AXI4-Lite從裝置時,走的是“32b GP AXI Master Ports”,可以輔助證明,對于本節應用,走的接口應該是“32b GP AXI Slave Ports”。

        互動資料将會經過Zynq子系統的内部總線(用空再考證一下是什麼名稱)控制器“Central Interconnect”轉發給Memory Interfaces。具體資料互動路徑如下圖所示:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        根據上述分析,SoC系統內建方案框圖如下:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        根據之前的經驗,利用向導生成的PL端AXI4-Lite Master IP 使用者用例再txn負脈沖觸發下,主機子產品的邏輯是連續4次(次數預設為4,可通過修改參數C_M00_AXI_TRANSACTIONS_NUM的數值改變次數)向遞增的位址區間寫入4組測試資料,測試資料每次加1。然後主機子產品自動讀取剛才寫入資料的位址内的資料,将讀的的資料與寫入資料進行比較,如果正确,主機IP的ERROR信号保持低電平,如果錯誤,ERROR給出高電平。

        本文後面的行為仿真證明:再次給主機IP子產品一個txn的觸發信号,重新執行4次寫入操作+4次讀取操作+比較操作。隻不過每次觸發都從原始基位址開始操作,目标寄存器位址并不增加。

        本節的測試工程本着少改動邏輯代碼的原則,仍基本采用此邏輯。每次按鍵觸發,執行4次寫操作+4次讀操作+比對檢查操作,增加利用4個LED燈表示每個位址比對結果是否正确(如果正确LED燈亮)。但是當再次按下按鈕,LED燈全滅,松開按鈕後再執行一組(4次寫操作+4次讀操作+比對檢查)操作,隻是新的一組操作位址會遞進增加。

2.Zynq系統裁剪

        建立工程後,添加一個Zynq IP核,然後調用官方對ZedBoard闆中Zynq子系統的預設配置。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        得到預設的Zynq硬核配置如下圖所示:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        對應的Zynq封裝如下圖所示:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        明顯看出有很多Zynq中的硬核在本項目中是不需要的,修改配置,将其裁剪掉。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇
FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        修改後的Zynq配置顯示如下:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        Zynq的封裝圖如下所示:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        輸出端的FCLK_CLK0和FCLK_RESET0_N是輸出時鐘和複位信号。這兩個信号的出處已在前一個圖中進行标注。

        ZedBoard開發闆的ARM端時鐘由IC18有源晶振提供33.33333MHz的時鐘信号,綁定到Zynq晶片的F7(PS_CLK)管腳上,該管腳是Zynq子系統(PS)的時鐘信号。如果工程中添加了Zynq子系統,Vivado會自動将F7綁定到Zynq子系統的PS_CLK管腳上(其實也不需要綁定,這是固話的。F7本身就是專用引腳,但是從硬體結構上也可以看出一個工程隻能執行個體化一個Zynq子系統)。該綁定在限制檔案上看不到,而在“Synthesis Design”的“I/O Planning”頁面中可以看到。(因為這個管腳是專用管腳,不需要綁定)這裡欠個圖,後文會有,記着啊!!!

        FCLK_CLK0是經過一個時鐘管理子產品(類似V4中的DCM)生成的,可以修改其參數。Zynq中包含了4個時鐘生成子產品。配置界面如下:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        如果取消勾選,Zynq将不輸出時鐘信号。

        那對于PL端的時序邏輯子產品,需要另外尋找時鐘信号,在ZedBoard開發闆上,IC17有源晶振提供100MHz的GCLK時鐘信号,連接配接到Y9上,可用PL端使用。但是這種方案PS端和PL端由獨立的時鐘分别驅動,必須考慮跨時鐘域問題。

        取消FCLK_CLK0的勾選後,Zynq的封裝圖如下所示:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        FCLK_CLK0管腳就沒有了,但是FCLK_RESET0_N仍然存在,因為Zynq中的Resets子產品是不可配置的。但是Resets有四路輸出,為什麼這裡隻有1個呢?是不是跟FCLK_CLKx有綁定呢?

        【添加,事後發現,FCLK_RESET0_N也是可以關閉的,操作如下】

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇
FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

太強大的軟體了,永遠别覺得自己學明白了!!!

為了驗證上述疑問,勾選兩路FCLK_CLK0和FCLK_CLK2,觀察之後的Zynq子產品封裝如下所示:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        沒有喚出其餘的幾路Resets信号。如何召喚其他幾路複位信号,還得研究研究。

【個人猜想】:這個FCLK_RESET0_N應該是跟Zynq子系統的複位工作是同步的,有可能Zynq子系統收到複位信号(PS-RST,BTN7,C9,低電平複位)後,FCLK_RESET0_N被拉低,等待一定時間保證Zynq子系統複位完成後,再延時一段時間,再拉高,是的PL端的子產品完成複位進入正常工作狀态時,Zynq子系統一定已經正常工作。

        本項目中,Zynq子系統裁剪完畢後,封裝圖采用下圖方案。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        利用FCLK_CLK0驅動PL端的時序邏輯。而将Y9管腳引入的100MHzGCLK信号旁路。

        再來看看S_AXI_GP0,即AXI4總線接口(相容AXI4-Lite)。如下圖所示:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        終于,畫箭頭的管腳我們都熟悉了。其他的以後再說。

        至此,Zynq子系統我們裁剪完畢了。

【還有個問題】:“DDR3 Controller”硬核在Zynq子系統内部的記憶體映射還沒有看到。打開Address Editor頁面,也沒有配置資訊。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        另外,作為從機接口,讀寫位址總線均為32bits,而不像之前的驗證方案,從機的讀寫位址去掉高位的段位址隻留下低位的offset Address,這樣的位址接口,能跟PL端的AXI InterConnect比對嗎?

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

3.PL端主機IP核設計編碼

        根據之前的經驗,利用向導生成一個AXI4-Lite Master IP示例代碼,建構主從子產品直連的測試系統,從機子產品預設内部寄存器數量為4個,建構本仿真系統時,将從機子產品内部寄存器數量設定為32個,其餘不用修改。

        功能仿真檔案(詳見附錄2),模拟連續兩次觸發txn信号,設定參數,每次txn觸發執行兩次寫讀操作,對應的仿真結果如下圖所示。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        每次txn觸發,起始位址均歸零,即恢複成初始位址0x4000_0000,寫入的資料也變為初始值0xaa00_0000。跟工程設計的邏輯需求不一緻。

        是以根據需求改造代碼邏輯,底層子產品的源碼詳見附錄。編碼時一定避免Multi-Driver禁告。修改後的邏輯仿真結果如下所示。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

可也看出主機子產品的功能滿足設計要求。

之後将該IP核加入到工程的IP Catalog中。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

4.在Block Design中增加PL端IP核

        首先在Block Design中執行個體化一個AzIP_AXI_Master_3的一個IP子產品,如下圖所示,此時沒有連接配接。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        點選頁面上的Run Connection Audomation按鈕,自動建立連接配接。整形以後如下圖所示。新加的兩個子產品都是老朋友了,基本邏輯核管腳時序都基本明确了。此時再來看這個連接配接,基本上就沒有問題了。圖中用彩色标注出了PL端的時鐘信号和複位信号。均由Zynq子系統産生。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        同樣按F6鍵檢查連接配接,如果檢查無誤,表示這個系統的“原理圖”畫的基本沒有問題了。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

5.記憶體映射分析

        點選Address Editor标簽,看一看,這個圖前文在zynq子系統配置完後曾經出現過,但是當時是沒有資料的,現在我們放在一起對比一下:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        下面我們嘗試解讀一下,第一幅圖時,軟體僅僅檢測到存在一個AXI Slave接口GP0,當時沒有比對的,是以沒有資料,但是當我們加上自行設計的AXI Master接口IP後,軟體将二者比對上了,通過層級結構發現,Zynq上的GP0的Slave接口是比對使用者IP的主機接口的,然後軟體自動配置設定了位址。有一個Base Name,名字是GP0_DDR_LOWOCM,這個名字沒看過,不過猜也知道是跟GP0口和DDR相關的,神奇軟體怎麼知道我想操作DDR呢?猜想應該是配置Zynq時,配置了DDR,是以在Zynq中的總線控制其中激活了DDR相關的段位址,即DDR_LOWCOM。

        為了驗證上述想法,在Zynq中裁剪掉DDR,具體操作如下:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        得到的Zynq封裝如下:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        可以看到Zynq子系統各種去掉了DDR Control子產品,再看Address Editor頁面。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        可以看到,由于GP0子產品的存在,對于Zynq内部總線接口來說,它配置了一個位址GP0_LOW_OCM,關鍵詞是OCM,經過查詢,得知OCM的意思是片上存儲器(On-Chip Memory),說白了就是記憶體映射位址。Zynq内部任何一個可配置的外設硬核,其電路均已經硬體實作了,對應的Zynq内部片位址也是固定的,增加外設,應該就會有新的片内位址。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        增加了外設USRT1,SD0,USB0,ENET0,QUARD SPI,注意此時沒有激活DDR Controller子產品。先來看看Zynq的封裝。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        再來看Address Editor頁面

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        可以看到,對于Quard SPI子產品,有單獨的位址映射GP0_QSPI_LINEAR,而USRT1,SD0,USB0,ENET0等外設沒有,根據Zynq的結構圖,大膽猜測,USRT1,SD0,USB0,ENET0等外設均包含在IO Peripherals子產品内,是以它們的統一片内位址映射(OCM)的基位址均為GP0_IOP,其中IOP應該就是IO Peripherals的簡寫。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        開始這些資料都沒有配置設定位址,但是前面說了,Zynq中,由于硬體結構都是固定的,剪裁操作是指不激活某些功能子產品,個人猜測目的可能是為了低功耗,但是對應的功能子產品的記憶體位址映射都是固定的,跟使用者設計的SoC工程無關。

        是以這些Zynq内部的映射應該是固定的,我們怎麼能夠看到呢?點選Address Editor中的Auto Assign Address按鈕,如下圖所示,系統就會自動填寫響應記憶體映射的Offset Address和Range了。這些都應該是經由GP0路由到這些外設硬核的映射位址。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇
FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

【補充】LOW_OCM應該就是低速(低性能)存儲器位址。有低速對應的肯定就有高速。如下所示。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        勾選上圖所示項,應該能夠打開HIGH_OCM

    從上文看出,對于GP0_QSPI_LINEAR和GP0_IOP的命名并沒有LOW和OCM等資訊。Zynq外設配置不變,僅僅是勾選上圖Allow Access to High OCM項,位址映射資料如下。其中HIGH_OCM應該是個獨立的記憶體區域。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        去除USRT1,SD0,USB0,ENET0,QUARD SPI等外設,啟動DDR Control,仍然勾選Allow Access to High OCM項,得到的Zynq封裝如下圖:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        對應的Address Editor頁面如下:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        可以看出DDR還是屬于LOW_OCM,而HIGH_OCM應該是Zynq系統中的一個特殊區域,具體在哪還不确定,因為跟DDR無關,這裡暫時就不關注了。

        由于PL中的IP核對Zynq管理的DDR操作是通過位址進行的,是以我們需要對DDR的記憶體映射整明白。下面再研究研究。

        GP0_LOW_OCM已經沒有了,但是其對應的位址被包含在GP0_DDR_LOWOCM位址段的低位區間上。

        回想《筆記3:PS讀寫DDR3存儲》中的記憶體映射:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        對應的片外DDR3存儲晶片的位址的起始位為0x00100000,和這個有點意思。

        當然,Address Editor頁面中的Offset Address參數和Range參數是可以修改的,而High Address參數是根據前兩個參數計算出來的。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇
FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        必須對Zynq子系統的記憶體映射原理特别明白,才能正确修改這些參數,是以我們在深入研究研究,看看能不能整明白。

        為了深度研究這個問題,在Xilinx Documentation Navigator中搜尋OCM,得到如下資訊。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇
FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        可以看到OCM還分為指令OCM和資料OCM。但是這些檔案都是比較老的,不是針對Zynq晶片的。沒有收獲。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        上圖這些檔案也沒用,這些講到都是在PL端用HDL編碼實作一個與DDR直接向量的接口控制器的使用方案,而不是設計到Zynq的位址映射方案。

        換個思路,查詢Zynq的技術文檔。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        在該文檔中得到一些資訊,先摘錄如下:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇
FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        Zynq内部有256KB的RAM,就是前面GP0_LOW_OCM或者GP0_HIGH_OCM映射的嗎?這個有意思,一定想辦法找到。因為之前實驗中C語言程式可能就運作在這個記憶體空間中。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

這是前文提到的I/O Peripherals中的内容。

ZedBoard闆子用到的晶片是XC7Z020,封裝為clg484,但是由于晶片上覆寫了個散熱片,不知道是-?。有空問問供貨商。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇
FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        難道是-1???可憐啊,CPU主頻最高為667MHz。上圖應該是從配置檔案中獲得的,硬體具體是-?其實還是從晶片絲印看最可靠。不過應該差别不會太大,畢竟是通用開發闆,不是為了最求性能的。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇
FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        下面圖很重要!

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        250KB的RAM(OCM)在圖中箭頭處。

        我的猜測,前面出現的記憶體映射Base Name,應該指的是Central Interconnect的出口,示意圖如下:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        找到了,就是在這篇文檔中,有下列資訊:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        從上圖看到,0x0000_0000是DDR and OCM, 0xFFFC_0000是OCM

        那麼Zynq内的256KB RAM(OCM)到底怎麼通路呢????郁悶

        最後的DDR記憶體映射配置按照系統預設的,如下:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        記得主機子產品開發是,使用的預設起始位址是0x4000_0000,這個在代碼中定義的。不過利用IP核的GUI也能看到。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        從前文知道,這個位址是向PL AXI Slave Port #0,即GP0的,Size是1G。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

【問題】PL 中的Master IP向0x4000_0000位址寫入資料,經過PL中的AXI Interconnect直連,将會轉發給GP0,GP0收到後,怎麼在轉給DDR呢????

【個人猜測】:傳入的位址-0x4000_0000,然後進行路由判斷嗎?假設是這樣的,跑起來看看。

        至此,本實驗的硬體設計完畢。儲存後,退出Block Design頁面。

6.封裝 & Synthesis

        然後記得建立HDL Wrapper,

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        之後對這個工程進行Run Synthesis。

        結果沒有error和critical warning。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

7.行為仿真

        想對這個包含Zynq的頂層子產品進行行為仿真,但是看了一眼端口定義。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇
FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        跟DDR相關的接口時序我根本沒法設定,故此放棄了。直接下闆測試吧。

8.管腳綁定

        綜合完成後,進入Synthesized Design頁面,先看看Schematic

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        然後重點看I/O Planning

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        根據原理圖,PS_CLK(F7)和PS_POR_B(B5)是在Bank500上,驅動電壓是3.3V,而PS_RST(C9)是在Bank501上,驅動電壓是1.8V。但是這幾項是Fixed,改不了,就這樣吧。

        隻能綁定使用者管腳,最後的配置圖如下:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        之後會建立限制檔案。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇
FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        之後,執行Run Implementation和Generate Bitstream。

9.是否還需要啟用SDK

        直接下闆嘗試。

        沒有反應啊。郁悶!Why????

        時序邏輯沒反應,先檢查時鐘信号和複位信号,在本實驗系統中,PL端的時鐘信号和複位信号均是從Zynq子系統中輸出的,是以對工程做如下改變,将時鐘信号和複位信号引到闆上的LED燈處,用于顯示和測量。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        該工程Synthesis & Implementation後,仍然通過Hardware Manager下載下傳後,現象為FCLK_CLK0驅動的LED燈常亮,使用示波器檢測輸出為持續高電平,FCLK_RESET0_N驅動的LED燈不亮。根據現象猜測,Zynq子系統中的時鐘單元沒有正常工作。

        原因分析(個人觀點):因為Zynq其實是一個ARM系統,其内部的硬核要想按照配置正常工作,應該是在初始化階段對相應硬核的控制寄存器進行初始化配置,如果是使用Hardware Manager下載下傳是無法操作這一步的。是以嘗試使用SDK進行SoC工程配置。

10.是否還需要啟用SDK

        根據之前的學習,使用SDK有下列幾步,不清楚的參看之間的學習筆記。

第一步:Vivado中Export Hardware...(其中需要Include Bitstream)

第二步:Vivado中Launch SDK

第三步:SDK中建立闆載支援庫函數,Board Support Package

第四步:建立使用者工程,Application Project

第五步:編譯

第六步:Program FPGA

        下面對其中跟本實驗有關的進行簡單說明

(1)在第三步中,啟用SDK可以看到記憶體映射資訊,跟記憶體相關的一個是DDR,一個是Zynq系統内部的RAM,記憶體位址如下,根據标題分析,應該是Zynq子系統内部,對于CPU來說的位址設定。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        個人猜測:從上圖可以看出在Zynq内部,對于兩個CPU Core,同一個硬核,操作位址是相同的,進而能夠實作雙核的資料互動。比如ps7_cortexa9_0能夠直接對0x0010_0000的DDR讀寫資料,同樣的ps7_cortexa9_1也可以對該位址的DDR直接讀寫資料。同時這将會帶來一個問題就是同步。另外,還有個問題就是如果是雙核運作,每個核都将有自己獨立的代碼段和棧空間(這兩個空間是程式運作時系統使用的,使用者不能強行進行讀寫操作),而堆空間是使用者自行申請使用的記憶體空間,通常用來進行使用者資料存儲,也就是說堆空間才是雙core可以公用的。而無論代碼段、棧空間、堆空間的實體載體都是記憶體(RAM or DDR),是以c語言嵌入式程式對實體記憶體直接讀寫時,要避免對代碼段和棧空間的位址進行操作。而對代碼段和棧空間的配置應該是在編譯過程中的link階段配置的。具體配置接口如下:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        這是配置界面,與傳統ARM開發對應的配置檔案如下所示,相應的詳細原理參考傳統ARM開發的相關知識。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

(2)對Zynq子系統中各個硬核的初始化配置。

        前面分析過,對于Zynq子系統,在不使用CPU Core的架構設計中,如果僅僅使用HardWare下載下傳,Zynq子系統内部的外設硬核也是不能正常工作的。前面分析認為是沒有進行初始化配置,在SDK軟體中,打開ps7_init.tcl檔案如下圖所示,從名字可以看出,這是一個初始化的腳本配置檔案,既然是tcl檔案,應該就不需要c語言調用,而是直接配置,下面截圖可以看出是對PLL硬核,Clock硬核、DDR硬核控制寄存器的初始化配置。

        其中猜測:mask_write 0XF8000008 0x0000FFFF 0x0000DF0D

        應該表示的是向0xF800_0008位址寫入資料0x0000_ffff_0000_df0f(共計32bits)

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        在Run時,SDK軟體會在配置“Run ps7_init”項對應的邏輯狀态下自動調用該tcl檔案完成初始化操作的。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

(3)在第四步建立使用者工程(Application Project)時,如果還按照之前的經驗選擇“Hello World”,将會顯示如下資訊:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        提示資訊為:目前硬體項目設計中沒有Uart外設硬核,是以該示例不能建立,真丢本實驗,僅有Peripheral Tests和Empty Application兩項可以使用。經過驗證,利用這兩個模版都可以實作實驗要求,這裡隻介紹Empty Application模版

        使用Empty Application模版,建立的工程如下所示:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        可以看出并沒有任何c語言檔案。

        在src中建立一個c語言檔案main.c(檔案名可以随便起),其中自行輸入一個main函數(必須是這個函數名),儲存後,SDK會自動編譯,生成一個debug檔案和binaries項。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        可以看出,這裡main函數裡什麼都沒有做。

【補充】對記憶體配置設定的進一步分析研究

        輕按兩下Binaries下的elf檔案,顯示如下資訊:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        可以看出,編譯完成之後,編譯軟體對嵌入式程式進行的記憶體劃分。而且系統空間大小位址都配置設定在ddr的低位址區間,因本實驗測試時,選用的DDR位址空間應以高位址空間為宜。

        在詳細分析elf檔案中對記憶體的劃分,重點看下圖部分。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        編譯軟體分析完畢後,得到的棧空間其實位址為0010_a030,棧空間大小為0000_3800(14K Bytes)。(0010_a030+0000_3800=0010_d830)

        c語言嵌入式軟體中,如果不是直接位址操作,本實驗編譯後的軟體使用的資料空間為:0010_0000~0010_d830,空間大小為:54.046875K Bytes。

        是以,本實驗中對DDR的記憶體讀寫測試,測試的記憶體位址區間從0020_0000開始為宜。

        另外前文分析時說過,闆載DDR為512MB,但是在vivado生成的system.hdf檔案中,定義的ps7_ddr_0的記憶體空間範圍隻有511MB,少了1MB,當時不知道這1MB時怎麼被A錢的。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

【個人猜測】但是再看elf檔案,可以看到0000_0000開始的空間,是用來進行Debug調試的,是以被Vivado+SDK系統給扣下了,對使用者不可見。

        建立完使用者邏輯後,配置Run As...項,用于下載下傳程式。

        其中,Run Configurations頁面前面已經見過很多次,這次重點說明的地方已經框出:

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        其中“Reset Processor”僅僅時重新下載下傳C語言嵌入式程式,download to processor

        當選中“Reset Entire System”項,會先下載下傳PL端的bit檔案,然後再下載下傳C語言嵌入式程式,download to processor。

        具體說明如下所示。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇
FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        選擇reset processor項後,run成功,SDK Log視窗顯示如下資訊,可以看出,先執行ps_init.tcl腳本,配置PS的硬核,在運作ps7_post_config(具體工作内容還沒整明白),然後複位ps7_cortexa9_0(是的c語言程式從main函數開始運作)。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        在開發闆上,程式下載下傳成功後,如果按BTN6(PROG),相當于Program FPGA這一項需要重做。是以開發闆不再有反應。

        在開發闆上,程式下載下傳成功後,如果按BTN9(PS-RST),相當于zynq子系統複位,而非CPU(ps7_cortexa9_0)複位,此時需要重新執行Run ps7_init這一項。是以開發闆不再有反應。

【結果】下載下傳成功後,開發闆反應如設計所示。實驗結果表明:

        當設定PL端的Master裝置通路的位址為0x4020_0000(0x4000_0000為32b GP AXI Slave Port的位址 + 0x0020_0000為DDR内的位址)時,下闆運作結果表明記憶體讀寫操作是失敗的。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

        當設定PL端的Master裝置通路的位址為0x0020_0000(為Zynq子系統内CPU對DDR通路的位址段)時,下闆運作結果表明記憶體讀寫操作是成功的。

FPGA學習-PL控制PS端DDR的設計原文作者:FPGA設計論壇

【結論】:

1. 隻要SoC系統中,用到了Zynq子系統,無論邏輯上是否激活CPU,都需要使用SDK進行下載下傳,原因時初始化Zynq子系統中硬核。

2. PL端對Zynq子系統中的寄存器進行操作,不需要考慮進行二次記憶體封裝,直接使用Zynq内設定的位址即可。即整個晶片PL+PS是采用統一位址映射的。

繼續閱讀