跳至正文

编写AXI4协议读写BRAM并仿真验证

前篇博文我们试验了AXI4-Lite协议读写BRAM,这里我们试验一下完整的AXI4协议。流程跟AXI4-Lite是一样的。省略的部分请参考:编写AXI4-Lite协议读写BRAM并仿真验证


一. 建立工程


二. 创建块设计

原理图同AXI4-Lite,不同点在于可以直接拖入三个IP直接连线,AXI BRAM Controller协议选择AXI4。

搭建完成后,需要进行封装。


三. 编写testbench

axiBram_tb.sv,代码如下:

/*
 * @Author: Xu XiaoKang
 * @Email: xuxiaokang_up@qq.com
 * @Date: 2020-08-03 14:40:33
 * @LastEditors: xu XiaoKang
 * @LastEditTime: 2020-08-04 16:40:00
 * @Filename:
 * @Description: AXI4 Master
 */



module axi4Bram_tb ();

timeunit 1ns;
timeprecision 1ps;


logic [14:0] M_AXI_awaddr;
logic [7 :0] M_AXI_awlen;
logic [2 :0] M_AXI_awsize;
logic [1 :0] M_AXI_awburst;
logic        M_AXI_awlock;
logic [3 :0] M_AXI_awcache;
logic [2 :0] M_AXI_awprot;
logic [3 :0] M_AXI_awqos;
logic        M_AXI_awvalid;
logic        M_AXI_awready;

logic [31:0] M_AXI_wdata;
logic [3 :0] M_AXI_wstrb;
logic        M_AXI_wlast;
logic        M_AXI_wvalid;
logic        M_AXI_wready;

logic [1:0] M_AXI_bresp;
logic       M_AXI_bvalid;
logic       M_AXI_bready;

logic [14:0] M_AXI_araddr;
logic [7 :0] M_AXI_arlen;
logic [2 :0] M_AXI_arsize;
logic [1 :0] M_AXI_arburst;
logic        M_AXI_arlock;
logic [3 :0] M_AXI_arcache;
logic [2 :0] M_AXI_arprot;
logic [3 :0] M_AXI_arqos;
logic        M_AXI_arvalid;
logic        M_AXI_arready;

logic [31:0] M_AXI_rdata;
logic [1 :0] M_AXI_rresp;
logic        M_AXI_rlast;
logic        M_AXI_rvalid;
logic        M_AXI_rready;

logic clk;
logic rstn;


// 生成时钟
localparam CLKT = 2;
initial begin
  clk = 0;
  forever #(CLKT / 2) clk = ~clk;
end


// 初始化一些不变的信号
initial begin
  M_AXI_awlock  = 1'b0// Normal access
  M_AXI_awcache = 4'b0000// 指示内存类型
  M_AXI_awprot  = 3'b000// 非特权且安全的数据访问
  M_AXI_awqos   = 4'b0000;

  M_AXI_arlock  = 1'b0// Normal access
  M_AXI_arcache = 4'b0000// 指示内存类型
  M_AXI_arprot  = 3'b000// 非特权且安全的数据访问
  M_AXI_arqos   = 4'b0000;
end


initial begin
  rstn = 0;
  #(CLKT * 5)
  rstn = 1;

  // 写交易
  M_AXI_awaddr  = 15'b000_0000_0000_0000// 写入基地址
  M_AXI_awlen   = 8'd10// 实际传输数据量 = awlem + 1
  M_AXI_awsize  = 3'd2;  // 每份数据占2^2=4字节, 默认是数据总线宽度
  M_AXI_awburst = 2'b01// INCR, 增地址模式
  M_AXI_awvalid = 1'b1;
  wait(M_AXI_awready == 1'b1#(CLKT * 1) M_AXI_awvalid = 1'b0;

  #(CLKT * 10.5)
  M_AXI_wdata = 32'd12;
  M_AXI_wstrb = 4'b1111;
  M_AXI_wlast = 1'b0;
  repeat(M_AXI_awlen) begin
    M_AXI_wvalid = 1'b1;
    wait(M_AXI_wready == 1'b1)
    #(CLKT * 1)
    M_AXI_wdata = M_AXI_wdata + 1'b1;
  end

  M_AXI_wlast = 1'b1;
  wait(M_AXI_wready == 1'b1)
  #(CLKT * 1)
  M_AXI_wvalid = 1'b0;
  M_AXI_wlast = 1'b0;


  M_AXI_bready = 1'b1;
  wait(M_AXI_bvalid == 1'b1#(CLKT * 1) M_AXI_bready = 1'b0;

  // 读交易
  M_AXI_araddr  = M_AXI_awaddr;
  M_AXI_arlen   = M_AXI_awlen;
  M_AXI_arsize  = M_AXI_awsize;
  M_AXI_arburst = M_AXI_awburst;
  M_AXI_arvalid = 1'b1;
  wait(M_AXI_arready == 1'b1#(CLKT * 1) M_AXI_arvalid = 1'b0;

  M_AXI_rready = 1'b1;
  wait(M_AXI_rlast == 1'b1#(CLKT * 1) M_AXI_rready = 1'b0;

  #(CLKT * 5) $stop;
end


bram_wrapper  bram_wrapper_inst_0 (.*);


endmodule


四. 运行仿真

使用vivado 2018.3 和 modelsim 10.6e SE-64 联合仿真。

可见,采用增地址模式,连续写入11个数据,从机能正确返回写响应bresp 和 bvalid,对同一地址的读取,读到的数据同之前写入的数据相同,故AXI4读写BRAM没有问题。


五. 总结与分享

AXI4相较AXI4-Lite支持连续写和连续读,当需要交互的数据量大时,可采用AXI4。另外,如果存储器件支持同时读写,用AXI4进行同时读写也没问题,读写通道是相互独立的。

工程文件:axiRwRam2018.7z。

欢迎大家关注我的公众号:徐晓康的博客,回复以下四位数字获取。

4136

建议复制过去不会码错字!


如果本文对你有所帮助,欢迎点赞、转发、收藏、评论让更多人看到,赞赏支持就更好了。

如果对文章内容有疑问,请务必清楚描述问题,留言评论或私信告知我,我看到会回复。


徐晓康的博客持续分享高质量硬件、FPGA与嵌入式知识,软件,工具等内容,欢迎大家关注。

0 0 投票数
文章评分
订阅评论
提醒
0 评论
内联反馈
查看所有评论
0
希望看到您的想法,请您发表评论x
目录