<acronym id="s8ci2"><small id="s8ci2"></small></acronym>
<rt id="s8ci2"></rt><rt id="s8ci2"><optgroup id="s8ci2"></optgroup></rt>
<acronym id="s8ci2"></acronym>
<acronym id="s8ci2"><center id="s8ci2"></center></acronym>
0
  • 聊天消息
  • 系統消息
  • 評論與回復
登錄后你可以
  • 下載海量資料
  • 學習在線課程
  • 觀看技術視頻
  • 寫文章/發帖/加入社區
創作中心

完善資料讓更多小伙伴認識你,還能領取20積分哦,立即完善>

3天內不再提示

使用AXI-Full接口的IP進行DDR的讀寫測試

FPGA之家 ? 來源:CSDN ? 作者:Vuko-wxh ? 2022-07-18 09:53 ? 次閱讀

學習內容

本文首先進行自定義IP的AXI總線IP的設計,然后在SDK下編寫代碼進行DDR的讀寫數據的測試。

開發環境

vivado 18.3&SDKPYNQ-Z2開發板

系統框圖

首先對本次工程進行簡要說明:本次工程使用AXI-Full接口的IP進行DDR的讀寫測試。在我們的DDR讀寫IP中,我們把讀寫完成和讀寫錯誤信號關聯到PL端的LED上,用于指示DDR讀寫IP的讀寫運行狀態。然后使用PL部分消抖處理后的按鍵進行啟動AXI總線工作,控制數據寫入。通過AXI互聯模塊連接到AXI_HP0端口,由PS端口進行數據的讀取操作,并通過串口進行讀寫數據的監控。pYYBAGLUvaaAO6XJAADNvLJIgRs591.jpg

自定義IP設計

首先打開Vivado軟件,在Tasks這里選擇New IP lacation

pYYBAGLUvd-ACdbiAABua1bs3Q0706.jpg

點擊next,對IP的信息進行設置,這里我們使用默認配置即可。設置好我們IP要保存的位置。

pYYBAGLUvfeAFFyrAACnp8gLUGw995.jpg

點擊Tools中的創建和封裝新的IP選項,

poYBAGLUvhuAeE9FAAEoh3_cWvg980.jpg

點擊NEXT ,選擇我們的封裝類型。因為這里我們是直接進行打開IP設計的界面,前兩個選項是可以在我們的vivado當前工程下面進行封裝設計,這里我們只進行了IP設計沒有建立工程,所以前兩個選項是無法選中的。我們也可以通過工程界面,進入點擊Tools中的創建和封裝新的IP選項。

poYBAGLUvkiABDIMAADAe_CgTXQ316.jpg

這里是用DDR讀寫IP來做主機,控制數據寫入,PS作為從機進行讀取IP中寫入的數據。

poYBAGLUvmGAYs8sAACvY_BPA7Q036.jpg

可以直接選中進行編輯IP,用戶可以根據自己的設計進行修改編輯IP的功能,這里沒有對IP進行修改處理,所以可以直接保存選擇第一個添加到IP庫中即可。poYBAGLUvniAYb5jAADUz1w-kew197.jpg

若修改相應的邏輯功能打開IP,在對應位置編輯添加代碼即可。

poYBAGLUvpKAEv8jAAC-SdZJ3ag510.jpg

添加完成綜合后對IP進行重新打包。DDR讀寫IP設計完成,創建的 IP 核將通過 AXI4 Master 端口向 Slave 端指定的 4K 存儲空間中連續寫入 1024 個數據, 寫入的數值從 1 累加到 1024, 每個數據占 32bit。然后進行硬件平臺的構建。

硬件平臺構建

首先,添加ZYNQ7 IP核,以及添加已經完成設計的ddr讀寫IP核。

添加用戶自定義IP

用戶自定義的IP可通過以下步驟完成添加。點擊Settings,

poYBAGLUv6iAFPyfAAD4DSU52ZE818.jpg

在project settings選擇IP,依次點擊,在IP庫那里點擊加號,把對應的IP目錄文件夾添加后,點擊OK或者Apply即可完成添加,在IP庫中就可以找到用戶設計的IP。

poYBAGLUv7-AVlyxAADZpe6vJnU483.jpg

完成IP和ZYNQ7 IP的導入后,如下圖:

pYYBAGLUv9SADRg_AACmGmBsULY185.jpg

雙擊打開zynq刪除多余的接口,這里只需要保留uart,并打開Slave HP0端口、時鐘、復位端口。

pYYBAGLUv-mAMZ-LAAD5l36TuIA990.jpg
poYBAGLUwACAW9nYAAEaUjbSIYE282.jpg
pYYBAGLUwBWAOl4qAAEGuRUv9Vk221.jpg

配置完,選擇自動連接接口,完成部分連接設計。

pYYBAGLUwCiAXfUlAACZ8qfpjpo680.jpg

整體設計圖如下,

pYYBAGLUwDuAErT7AACuhz9p7N4226.jpg

添加按鍵消抖IP

pYYBAGLUwFOAFkGuAACHbMdxz4c065.jpg

由于ddr讀寫IP的axi_init_axi_txn接入的是按鍵,這里按鍵按下會產生抖動,axi_init_axi_txn與好多讀寫信號關聯,如果不添加消抖IP,在按鍵按下的時,產生的毛刺會進行影響后續的操作,從而導致讀寫操作的錯誤,也就是讀寫操作的指示燈會亮起。

pYYBAGLUwGuALaHZAACeCniyL-E421.jpg

系統復位后, 狀態機處于初始狀態,在該狀態下等待外部輸入的啟動傳輸脈沖 init_txn_pulse。一旦檢測到 init_txn_pulse 為高電平,狀態機跳轉到 INIT_WRITE 狀態。在 INIT_WRITE 狀態下, 狀態機拉高 start_single_burst_write 信號, 來不斷地啟動 AXI4 Master 接口對Slave 端大小為 4KB 的存儲空間進行突發寫操作。寫操作完成后, write_done 信號會拉高,狀態機進入INIT_READ 狀態。在 INIT_READ 狀態下, 狀態機拉高 start_single_burst_read 信號, 不斷地啟動 AXI4 Master 接口對 Slave端同一存儲空間進行突發讀操作, 同時將讀出的數據與寫入的數據進行對比。讀操作完成后, read_done 信號拉高,狀態機進入 INIT_COMPARE 狀態。在 INIT_COMPARE 狀態下, 判斷 AXI4 接口在讀寫過程中的是否發生錯誤, 并將錯誤狀態賦值給ERROR 信號, 然后將 compare_done 信號拉高,表示一次讀寫測試完成。最后跳轉到 IDLE 狀態,等待下一次讀寫操作的啟動信號。這里的消抖模塊直接添加之前寫過的按鍵消抖模塊即可,這里給出我的設計:

module key_filter(
Clk,      //50M時鐘輸入
Rst_n,    //模塊復位
key_in,   //按鍵輸入
key_flag, //按鍵標志信號
key_state //按鍵狀態信號
);

input Clk;
input Rst_n;
input key_in;

output reg key_flag;
output reg key_state;

localparam
IDEL= 4'b0001,
FILTER0= 4'b0010,
DOWN= 4'b0100,
FILTER1 = 4'b1000;

reg [3:0]state;
reg [19:0]cnt;
reg en_cnt;//使能計數寄存器

//對外部輸入的異步信號進行同步處理
reg key_in_sa,key_in_sb;
always@(posedge Clk or negedge Rst_n)
if(!Rst_n)begin
key_in_sa <= 1'b0;
key_in_sb <= 1'b0;
end
else begin
key_in_sa <= key_in;
key_in_sb <= key_in_sa;
end

reg key_tmpa,key_tmpb;
wire pedge,nedge;
reg cnt_full;//計數滿標志信號

//使用D觸發器存儲兩個相鄰時鐘上升沿時外部輸入信號(已經同步到系統時鐘域中)的電平狀態
always@(posedge Clk or negedge Rst_n)
if(!Rst_n)begin
key_tmpa <= 1'b0;
key_tmpb <= 1'b0;
end
else begin
key_tmpa <= key_in_sb;
key_tmpb <= key_tmpa;
end

//產生跳變沿信號
assign nedge = !key_tmpa & key_tmpb;
assign pedge = key_tmpa & (!key_tmpb);

always@(posedge Clk or negedge Rst_n)
if(!Rst_n)begin
en_cnt <= 1'b0;
state <= IDEL;
key_flag <= 1'b0;
key_state <= 1'b1;
end
else begin
case(state)
IDEL :
begin
key_flag <= 1'b0;
if(nedge)begin
state <= FILTER0;
en_cnt <= 1'b1;
end
else
state <= IDEL;
end

FILTER0:
if(cnt_full)begin
key_flag <= 1'b1;
key_state <= 1'b0;
en_cnt <= 1'b0;
state <= DOWN;
end
else if(pedge)begin
state <= IDEL;
en_cnt <= 1'b0;
end
else
state <= FILTER0;

DOWN:
begin
key_flag <= 1'b0;
if(pedge)begin
state <= FILTER1;
en_cnt <= 1'b1;
end
else
state <= DOWN;
end

FILTER1:
if(cnt_full)begin
key_flag <= 1'b1;
key_state <= 1'b1;
state <= IDEL;
en_cnt <= 1'b0;
end
else if(nedge)begin
en_cnt <= 1'b0;
state <= DOWN;
end
else
state <= FILTER1;

default:
begin 
state <= IDEL; 
en_cnt <= 1'b0;
key_flag <= 1'b0;
key_state <= 1'b1;
end

endcase
end



always@(posedge Clk or negedge Rst_n)
if(!Rst_n)
cnt <= 20'd0;
else if(en_cnt)
cnt <= cnt + 1'b1;
else
cnt <= 20'd0;

always@(posedge Clk or negedge Rst_n)
if(!Rst_n)
cnt_full <= 1'b0;
else if(cnt == 20'd999_999)
cnt_full <= 1'b1;
else
cnt_full <= 1'b0;

endmodule

添加完模塊后系統設計如下:注:axi_init_axi_txn是上升沿有效,這里為了保證系統上電后是初始默認隨機狀態,要確保按鍵未按下給啟動脈沖時,是低電平。因為PYNQZ2開發板按鍵默認電位是低,按下為高,這里不用進行處理,若按鍵按下后為低,默認拉高,這里可以對按鍵進行添加非邏輯的IP進行取反。(使用 utility vector logic IP完成配置)

pYYBAGLUwIaALS_fAAD68Czzad8486.jpg

雙擊DDR讀寫的IP核進行配置,這里沒有用到user的接口所以都設置為0,如圖:

pYYBAGLUwJqAJ5MsAADn9RQGLk4990.jpg

對于Base address,我們可以查看下接口的地址范圍,避免數據操作超過可操作范圍,這里我們就取中間值0X10000000。

poYBAGLUwK2AYJ35AACMfjhmlww326.jpg

然后我們進行generate output product 然后生成HDL封裝。接著就對應引腳進行引腳約束即可(PYNQ的粉色開發板可以直接引用這個約束):

##LEDs
set_property -dict { PACKAGE_PIN R14   IOSTANDARD LVCMOS33 } [get_ports { m0_axi_error_0 }]; #IO_L6N_T0_VREF_34 Sch=led[0]
set_property -dict { PACKAGE_PIN P14   IOSTANDARD LVCMOS33 } [get_ports { m0_axi_txn_done_0}]; #IO_L6P_T0_34 Sch=led[1]

##Buttons
set_property -dict { PACKAGE_PIN D19   IOSTANDARD LVCMOS33 } [get_ports { key }]; #IO_L4P_T0_35 Sch=btn[0]

完成約束后進行綜合布局布線,等待生成bit流文件。

poYBAGLUwMSAco7DAACV94ZYr9Y653.jpg

bit文件生成后在FILE處,點擊導出硬件資源(包含bit流文件),接著launch SDK。

SDK軟件部分

打開SDK后,新建application project。在main.c中輸入以下代碼:

#include "stdio.h"
#include "xil_cache.h"
#include "xil_printf.h"
#include "xil_io.h"
int main(){
int i;
char chardata;
Xil_DCacheDisable();
printf("AXI4-FULL RW TEST~

");
while(1){
scanf("%c",chardata);
if(chardata="y"){
printf("start
");
for(i=0;i<4096;i=i+4){
printf("%d is %d
",i,(int)(Xil_In32(0x10000000+i)));
}
}
}
return 0;
}

代碼簡要說明

這里使用的IP我們設定成不需要進行緩存的,所以在main函數中調用Xil_DCacheDisable();。使用Xil_In32(),對DDR對應位置的數據進行讀取。參數只需要傳遞所要讀取的地址即可。因為一次寫入的數據是32位的,每個地址的數據位寬是8位,所以在for循環中使用了i=i+4。

在串口中使用printf("%d is %d ",i,(int)(Xil_In32(0x10000000+i)));對相應地址的數據進行讀取顯示。

運行效果

當按鍵未按下時,也就是未進行寫入操作直接讀取數據,DDR中的數據是默認的隨機狀態,如下所示:

pYYBAGLUwOCASjXAAACEo9Cvmvs368.jpg

當按鍵按下后,IP完成數據寫入操作,數據是從1-1024自增的

poYBAGLUwPaALuQFAADuMKaD0XY062.jpg

如何波形進行debug?

這里我們選中要進行DEBUG的數據信號右擊選中debug


poYBAGLUwQyAU7ulAACFBd-cCPc264.jpg

然后點擊自動連接,完成debug功能搭建

pYYBAGLUwSGAH797AACUjZ-uvnQ516.jpg

綜合后會多出ILA的IP進行波形分析幫助DEBUG。

poYBAGLUwTaAfPOLAAA10xprmRg156.jpg

然后打開硬件設備,如下圖在ila界面即可看到我們debug的波形數據了。

poYBAGLUwU2AWu4-AAF0R7VMSXE599.jpg

添加觸發條件,標號2是單次觸發,標號1是一直運行debug抓取波形。

pYYBAGLUwVyAOqXOAAGcBZHMWR4164.jpg


審核編輯:劉清

聲明:本文內容及配圖由入駐作者撰寫或者入駐合作網站授權轉載。文章觀點僅代表作者本人,不代表電子發燒友網立場。文章及其配圖僅供工程師學習之用,如有內容侵權或者其他違規問題,請聯系本站處理。 舉報投訴
  • DDR
    DDR
    +關注

    關注

    10

    文章

    684

    瀏覽量

    64393
  • AXI總線
    +關注

    關注

    0

    文章

    66

    瀏覽量

    14167
  • SDK
    SDK
    +關注

    關注

    3

    文章

    973

    瀏覽量

    44845
  • AXI
    AXI
    +關注

    關注

    1

    文章

    126

    瀏覽量

    16323

原文標題:如何波形進行debug?

文章出處:【微信號:zhuyandz,微信公眾號:FPGA之家】歡迎添加關注!文章轉載請注明出處。

收藏 人收藏

    評論

    相關推薦

    如何使用AXI VIP在AXI4(Full)主接口中執行驗證和查找錯誤

    AXI 基礎第 2 講 一文中,曾提到賽靈思 Verification IP (AXI VIP) 可用作為 AXI 協議檢查工具。在本次第4講中,我們將來了解下如何使用它在
    發表于 07-08 09:31 ?2171次閱讀

    創建AXI Sniffer IP以在Vivado IP Integrator中使用教程

    在某些情況下,通過嗅探 AXI 接口來分析其中正在發生的傳輸事務是很有用的。在本文中,我將為大家演示如何創建基本 AXI4-Lite Sniffer IP 以對特定地址上正在發生的
    發表于 07-08 09:35 ?857次閱讀

    例說FPGA連載41:DDR控制器集成與讀寫測試DDR2 IP接口描述

    `例說FPGA連載41:DDR控制器集成與讀寫測試DDR2 IP接口描述特權同學,版權所有配
    發表于 10-27 16:36

    ZYNQ調用XDMA PCIE IP同時讀寫PS DDR,導致藍屏問題。

    你好!我在ZYNQ 7015里(或者7035)調用XDMA PCIE IP 從上位機HOST PC通過PCIE接口給ZYNQ的PS DDR發送數據(XDMA PCIE IP接到了PS的
    發表于 11-21 10:35

    如何用zedboard創建一個AXI接口應用程序?

    FULL支持突發傳輸)。在我的vivado設計中,我使用AXI CDMA作為DDR RAM,BRAM以及定制從AXI的主設備。zynq為AXI
    發表于 08-12 10:37

    【正點原子FPGA連載】第十五章AXI4接口DDR讀寫實驗--領航者ZYNQ之嵌入式開發指南

    ,Xilinx在IP核中繼續使用AXI協議。本章我們對AXI協議作一個簡單介紹,并在Vivado中實現一個AXI4接口
    發表于 09-04 11:10

    【正點原子FPGA連載】第九章AXI4接口DDR讀寫實驗--摘自【正點原子】達芬奇之Microblaze 開發指南

    Vivado中實現一個AXI4接口IP核,用于對DDR3進行讀寫
    發表于 10-22 15:16

    XILINX MIG(DDR3) IPAXI接口與APP接口的區別以及優缺點對比

    XILINX MIG(DDR3) IPAXI接口與APP接口的區別以及優缺點對比
    發表于 11-24 21:47

    AXI接口簡介_AXI IP核的創建流程及讀寫邏輯分析

    本文包含兩部分內容:1)AXI接口簡介;2)AXI IP核的創建流程及讀寫邏輯分析。 1AXI
    的頭像 發表于 06-29 09:33 ?1.5w次閱讀
    <b class='flag-5'>AXI</b><b class='flag-5'>接口</b>簡介_<b class='flag-5'>AXI</b> <b class='flag-5'>IP</b>核的創建流程及<b class='flag-5'>讀寫</b>邏輯分析

    如何創建基本AXI4-Lite Sniffer IP以對特定地址上正在發生的讀寫傳輸事務進行計數

    這將創建一個附帶 BD 的 Vivado 工程,此 BD 包含 AXI VIP (設置為 AXI4-Lite 主接口) 和 AXI GPIO IP
    的頭像 發表于 04-30 16:24 ?2122次閱讀
    如何創建基本<b class='flag-5'>AXI</b>4-Lite Sniffer <b class='flag-5'>IP</b>以對特定地址上正在發生的<b class='flag-5'>讀寫</b>傳輸事務<b class='flag-5'>進行</b>計數

    簡單講解AXI Interconnect IP核的使用方法

    最近需要用到AXI接口的模塊,xilinx的IP核很多都用到了AXI總線進行數據和指令傳輸。如果有多個設備需要使用
    的頭像 發表于 06-19 15:45 ?5956次閱讀
    簡單講解<b class='flag-5'>AXI</b> Interconnect <b class='flag-5'>IP</b>核的使用方法

    基于AXI總線的DDR3讀寫測試

    本文開源一個FPGA項目:基于AXI總線的DDR3讀寫。之前的一篇文章介紹了DDR3簡單用戶接口讀寫
    的頭像 發表于 09-01 16:20 ?2549次閱讀
    基于<b class='flag-5'>AXI</b>總線的<b class='flag-5'>DDR</b>3<b class='flag-5'>讀寫</b><b class='flag-5'>測試</b>

    基于FPGA的DDR3讀寫測試

    本文介紹一個FPGA開源項目:DDR3讀寫。該工程基于MIG控制器IP核對FPGA DDR3實現讀寫操作。
    的頭像 發表于 09-01 16:23 ?966次閱讀
    基于FPGA的<b class='flag-5'>DDR</b>3<b class='flag-5'>讀寫</b><b class='flag-5'>測試</b>

    AXI傳輸數據的過程

    AXI4為例,有AXI full/lite/stream之分。 在Xilinx系列FPGA及其有關IP核中,經常見到AXI總線
    的頭像 發表于 10-31 15:37 ?522次閱讀
    <b class='flag-5'>AXI</b>傳輸數據的過程

    AXI通道讀寫DDR的阻塞問題?

    基于vivado2020.1和zcu102開發板(rev1.1)開發項目,工程涉及DDR4(MIG)和PL端多個讀寫接口交互的問題,通過AXI interconnect
    的頭像 發表于 12-01 09:04 ?524次閱讀
    <b class='flag-5'>AXI</b>通道<b class='flag-5'>讀寫</b><b class='flag-5'>DDR</b>的阻塞問題?
    亚洲欧美日韩精品久久_久久精品AⅤ无码中文_日本中文字幕有码在线播放_亚洲视频高清不卡在线观看
    <acronym id="s8ci2"><small id="s8ci2"></small></acronym>
    <rt id="s8ci2"></rt><rt id="s8ci2"><optgroup id="s8ci2"></optgroup></rt>
    <acronym id="s8ci2"></acronym>
    <acronym id="s8ci2"><center id="s8ci2"></center></acronym>