microblaze是怎么通过把数据通过axi总线给到ip的

User: microblaze是怎么通过把数据通过axi总线给到ip的
Kimi: MicroBlaze 把数据“送”给 IP 并不是靠一根信号线,而是靠“AXI 总线协议”在地址空间上完成一次标准读写。只要 IP 核在 Vivado 里被挂到同一根 AXI 总线(通常是 AXI4-Lite 或 AXI4),MicroBlaze 就把 IP 当成一段 RAM:写数据就是一次 AXI 写事务,读数据就是一次 AXI 读事务。下面把全过程拆开说明。

  1. 地址映射
    在 Block Design 里,Vivado 会自动给每个 AXI 从设(包括你自定义的 IP)分配一段地址。
    例如 IP 的基地址是 0x44A0_0000,偏移 0x0~0xFFF。
    只要 C 程序里用指针访问这段地址,硬件就会自动翻译成 AXI 事务。

  2. 写数据流程(MicroBlaze → IP)

    1. C 代码里写 *(volatile u32 *)0x44A00000 = 0x12345678;
    2. MicroBlaze 的数据外设接口 M_AXI_DP 在总线上发起一次 AXI4-Lite 写事务:
      – 写地址通道:给出 0x44A00000 和写控制信号 AWVALID;
      – 写数据通道:给出 0x12345678 和 WVALID;
      – IP 收到地址和数据后回 AWREADY/WREADY,并在写响应通道回 BVALID,完成握手。
    3. IP 内部逻辑检测到 WVALID && WREADY,就把数据锁存到寄存器或 FIFO,完成“收到数据”。
  3. 读数据流程(IP → MicroBlaze)

    1. C 代码里 u32 val = *(volatile u32 *)0x44A00004;
    2. M_AXI_DP 发起一次 AXI4-Lite 读事务:
      – 读地址通道:给出 0x44A00004 和 ARVALID;
      – IP 回 ARREADY,并把读数据放到读数据通道 RDATA,同时拉高 RVALID;
    3. MicroBlaze 收到 RVALID && RREADY 后把数据返回给 CPU 寄存器,完成读操作。
  4. 如果数据量很大,可以用 AXI4-FIFO 或 AXI-DMA 做“流式”通道:
    – 把 IP 做成 AXI-Stream 从接口,MicroBlaze 通过 AXI-DMA 配置源地址/长度,启动后 DMA 会把内存块自动拆成连续 AXI-Stream 数据包推给 IP;
    – 反之,IP 产生的数据先进入 AXI-Stream FIFO,DMA 再搬回 DDR,MicroBlaze 只需查询中断或轮询寄存器即可 。

  5. 自己写 IP 时,只要用 Vivado 的“Create AXI Peripheral”模板,把
    – 总线接口选成 AXI4-Lite(寄存器控制)或 AXI-Stream(数据流),
    – 在 slv_reg0/1/2… 里做逻辑,就能直接享受上述读写流程 。

一句话总结:
MicroBlaze 把 IP 当内存,读写寄存器就是一次 AXI 事务;大数据就用 DMA+AXI-Stream,把内存块变成连续数据流自动送进 IP。
User: 硬件怎么把读写变成axi事务?
Kimi: MicroBlaze 核里并没有“先产生一条抽象指令、再翻译成 AXI 包”这一步——
“把读写变成 AXI 事务”这件事,在硬件上就是一次 AXI 主端口(M_AXI_DP)的时序握手本身
下面把“CPU 核 → 总线接口 → 外设”这一路拆开,让你看到“硬件到底在哪一拍把读写变成了 AXI 信号”。


  1. CPU 内核看到的只是“外部总线”
    MicroBlaze 的 LSU(load/store 单元)在执行
    lw r5, 0x44A0_0004(r0)
    时,地址 0x44A0_0004 落在“外设”区域(由 Vivado 里 C_ADDR_SIZE/C_DATA_SIZE 决定)。
    LSU 把“地址 + 字节使能 + 写数据(如果是 store)”送到内核与总线之间的 LMB/AXI 桥(官方叫 IPIF,Interface Protocol Interface)。

  2. IPIF 把“CPU 本地总线时序”直接映射成 AXI 通道
    MicroBlaze 本地总线协议非常简单:
    – 单地址相位
    – 单数据相位
    – 无突发(burst=1)
    – 无缓存/无乱序

    IPIF 里有一个状态机,同一时钟周期就把这些信号转成 AXI 通道:

    CPU 本地                AXI 主端口
    ————————————————————————————————————
    addr = 0x44A0_0004  →  ARADDR
    size = 4 B          →  ARSIZE = 2'b010
    read_req            →  ARVALID
    ……等待从机回 ARREADY 后 →  RREADY
    收到 RVALID         ←  RDATA
    

    写操作同理,只是多了 AWADDR/WDATA/WSTRB 和 B 通道握手。
    注意:这里没有任何“封包”或“协议处理器”——状态机就是并行的寄存器+组合逻辑,一拍一拍地把 CPU 本地握手映射成 AXI 握手。

  3. AXI 交叉开关(Interconnect)只做路由
    Vivado 生成的 AXI Interconnect 根据 ARADDR/AWADDR 的高位把事务路由到对应从机,并做:
    – 单主到多从的解码
    – 时钟域/数据宽度转换(可选)
    – 打拍寄存(可选)
    但它不会修改协议本身,只是把 ARVALID/ARREADY 等信号继续往下游传递。

  4. 从机(你的 IP)收到的是什么?
    就是标准的 AXI 信号线:
    input wire s_axi_arvalid,
    output wire s_axi_arready,
    input wire [31:0] s_axi_araddr,

    你在 IP 里写一个 always 块:

    always @(posedge aclk) begin
      if (s_axi_arvalid & s_axi_arready) begin
        case (araddr[7:0])
          8'h00 : rdata <= reg0;
          8'h04 : rdata <= reg1;
        endcase
      end
    end
    

    就完成了“CPU 读寄存器”。


一句话总结
“硬件把读写变成 AXI 事务”并不是额外加了一层协议转换芯片,而是——
MicroBlaze 内核的 LSU 一旦访问外设地址,在紧挨着内核的 IPIF 状态机里,同一时钟周期就把 CPU 本地总线请求直接映射成 AXI 通道握手信号;后续所有模块(Interconnect、IP)都只是在这条 AXI 信号链路上继续握手而已。

posted @ 2026-01-20 21:25  xxiaobai  阅读(0)  评论(0)    收藏  举报