Student ID: 20726557 # AXI ### Design the interface logic between AXI and SRAM using minimum hardware resource, and draw timing waveform ![image](https://hackmd.io/_uploads/HkI6Nh_cyl.png) Interface Logic ``` module axi_interface (); wire clk; wire rst_n; wire awvalid; wire awready; wire [31:0] waddr; wire wvalid; wire wready; wire [31:0] wadata; wire arvalid; wire arready; wire rvalid; wire [31:0] rdata; wire [31:0] datain; wire [31:0] address; wire en; wire we; wire [31:0] dataout; reg [2:0] axilite_fsm; reg [31:0] axilite_A_pre; reg [31:0] axilite_Di_pre; reg axilite_rr; parameter AXILITE_FSM_RESET = 3'b000; parameter AXILITE_FSM_IDLE = 3'b001; parameter AXILITE_FSM_AWREADY = 3'b010; parameter AXILITE_FSM_WREADY = 3'b011; parameter AXILITE_FSM_RREADY = 3'b100; axi_hardware a1 ( .awvalid (awvalid), .awready (awready), .waddr (waddr ), .wvalid (wvalid ), .wready (wready ), .wadata (wadata ), .arvalid (arvalid), .arready (arready), .rvalid (rvalid ), .rdata (rdata ) ); sram_hardware s1( .datain (datain ), .address (address), .en (en ), .we (we ), .dataout (dataout) ); // AXI-Lite always @(posedge clk or negedge rst_n) begin if (~rst_n) begin axilite_fsm <= AXILITE_FSM_RESET; axilite_A_pre <= {pADDR_WIDTH{1'b0}}; axilite_Di_pre <= {pDATA_WIDTH{1'b0}}; axilite_rr <= 1'b0; end else begin case (axilite_fsm) AXILITE_FSM_RESET: begin axilite_fsm <= AXILITE_FSM_IDLE; axilite_A_pre <= {pADDR_WIDTH{1'b0}}; axilite_Di_pre <= {pDATA_WIDTH{1'b0}}; axilite_rr <= 1'b0; end AXILITE_FSM_IDLE: begin if (awvalid & ~(arvalid & axilite_rr)) begin axilite_fsm <= AXILITE_FSM_AWREADY; axilite_A_pre <= awaddr; axilite_Di_pre <= {pDATA_WIDTH{1'b0}}; axilite_rr <= 1'b1; end else if (wvalid & ~(arvalid & axilite_rr)) begin axilite_fsm <= AXILITE_FSM_WREADY; axilite_A_pre <= {pADDR_WIDTH{1'b0}}; axilite_Di_pre <= wdata; axilite_rr <= 1'b1; end else if (arvalid) begin axilite_fsm <= AXILITE_FSM_RREADY; axilite_A_pre <= araddr; axilite_Di_pre <= {pDATA_WIDTH{1'b0}}; axilite_rr <= 1'b0; end else begin axilite_fsm <= AXILITE_FSM_IDLE; axilite_A_pre <= {pADDR_WIDTH{1'b0}}; axilite_Di_pre <= {pDATA_WIDTH{1'b0}}; axilite_rr <= axilite_rr; end end AXILITE_FSM_AWREADY: begin if (wvalid) begin axilite_fsm <= AXILITE_FSM_IDLE; axilite_A_pre <= {pADDR_WIDTH{1'b0}}; axilite_Di_pre <= {pDATA_WIDTH{1'b0}}; axilite_rr <= axilite_rr; end else begin axilite_fsm <= AXILITE_FSM_AWREADY; axilite_A_pre <= axilite_A; axilite_Di_pre <= {pDATA_WIDTH{1'b0}}; axilite_rr <= axilite_rr; end end AXILITE_FSM_WREADY: begin if (awvalid) begin axilite_fsm <= AXILITE_FSM_IDLE; axilite_A_pre <= {pADDR_WIDTH{1'b0}}; axilite_Di_pre <= {pDATA_WIDTH{1'b0}}; axilite_rr <= axilite_rr; end else begin axilite_fsm <= AXILITE_FSM_WREADY; axilite_A_pre <= {pADDR_WIDTH{1'b0}}; axilite_Di_pre <= axilite_Di; axilite_rr <= axilite_rr; end end AXILITE_FSM_RREADY: begin axilite_fsm <= AXILITE_FSM_IDLE; axilite_A_pre <= {pADDR_WIDTH{1'b0}}; axilite_Di_pre <= {pDATA_WIDTH{1'b0}}; axilite_rr <= axilite_rr; end default: begin axilite_fsm <= AXILITE_FSM_IDLE; axilite_A_pre <= {pADDR_WIDTH{1'b0}}; axilite_Di_pre <= {pDATA_WIDTH{1'b0}}; axilite_rr <= 1'b0; end endcase end end assign awready = (axilite_fsm == AXILITE_FSM_IDLE ) & awvalid & ~(arvalid & axilite_rr) | (axilite_fsm == AXILITE_FSM_WREADY ); assign wready = (axilite_fsm == AXILITE_FSM_IDLE ) & ~awvalid & wvalid & ~(arvalid & axilite_rr) | (axilite_fsm == AXILITE_FSM_AWREADY); assign arready = (axilite_fsm == AXILITE_FSM_IDLE ) & arvalid & ~((awvalid | wvalid) & ~axilite_rr); assign rvalid = (axilite_fsm == AXILITE_FSM_RREADY ); assign rdata = dataout; assign we = ((axilite_fsm == AXILITE_FSM_AWREADY) & wvalid | (axilite_fsm == AXILITE_FSM_WREADY) & awvalid); assign en = ((axilite_fsm == AXILITE_FSM_AWREADY) & wvalid | (axilite_fsm == AXILITE_FSM_WREADY) & awvalid | rvalid); assign datain = (axilite_fsm == AXILITE_FSM_WREADY) ? axilite_Di_pre : wdata; assign address = (axilite_fsm == AXILITE_FSM_WREADY) ? awaddr : axilite_A_pre; endmodule ``` Timing Waveform ![image](https://hackmd.io/_uploads/BkfyC7m3Je.png) --- ### Interleave order: axi burst type = interleave order, the starting address is 011, what is address sequence for data access? The address sequence will be the following: > 3'b011, 3'b010, 3'b001, 3'b000, 3'b111, 3'b110, 3'b101, 3'b100 --- ### How to handle different access order from CPU and IO ![image](https://hackmd.io/_uploads/S1PMlNX3yg.png) DMA controller should be chosen to handle the different access orders as it can handle the IO operations directly with the DRAM without the CPU, allowing for higher transfer efficiency. --- # IO cache ### TPH Implementation options ![image](https://hackmd.io/_uploads/SJw5GN7n1l.png)