AXI总线slave模式下接收数据---verilog代码

时间:2024-02-01 16:47:58

AXI总线slave模式下接收数据---verilog代码

Posted on 2020-05-15 22:37  沉默改良者  阅读(...)  评论(...编辑  收藏

AXI总线slave模式下接收数据---verilog代码

`timescale 1ns / 1ps
//////////////////////////////////////////////////////////////////////////////////
// Company: 
// Engineer: chensimin
// 
// Create Date: 2020/04/17 18:45:54
// Design Name: 
// Module Name: axi_slave_receive
// Project Name: 
// Target Devices: 
// Tool Versions: 
// Description: 
// 
// Dependencies: 
// 
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
// 
//////////////////////////////////////////////////////////////////////////////////


module axi_slave_receive #
(

    parameter integer S_AXI_DATA_WIDTH    = 32,
    parameter integer S_AXI_ADDR_WIDTH    = 32
)
(

    input  wire                              s_axi_aclk,
    input  wire                              s_axi_aresetn,
    input  wire  [S_AXI_DATA_WIDTH-1 : 0]    s_axi_wdata,
    input  wire  [S_AXI_ADDR_WIDTH-1 : 0]    s_axi_awaddr,
    input  wire                              s_axi_wvalid,
    input  wire                              s_axi_awvalid,
    output reg                               s_axi_wready,
    output reg                               s_axi_awready,
    output reg                               s_axi_bvalid,
    input  wire                              s_axi_bready,
    output reg   [S_AXI_DATA_WIDTH-1 : 0]    data,
    output reg   [S_AXI_ADDR_WIDTH-1 : 0]    address,
    output reg                               valid

);


//---------------------------------------------------------------------------------

parameter  IDLE                = 0;
parameter  READY               = 1;
parameter  BVALID              = 2;
parameter  BREADY              = 3;

//---------------------------------------------------------------------------------

reg [3:0] current_state = 0;
reg [3:0] next_state = 0;

always @(posedge s_axi_aclk or posedge s_axi_aresetn)
begin
    if(s_axi_aresetn == 1'b0)
        current_state <= IDLE;
    else
        current_state <= next_state;
end

//---------------------------------------------------------------------------------

always @(*)
begin
    case(current_state)
    IDLE:
    begin
        if(s_axi_wvalid && s_axi_awvalid)
            next_state <= READY;
        else 
            next_state <= IDLE;
    end
    READY:
    begin
        next_state <= BVALID;
    end
    BVALID:
    begin
        next_state <= BREADY;
    end
    BREADY:
    begin
        if(s_axi_bready)
            next_state <= IDLE;
        else 
            next_state <= BREADY;
    end
    default:
    begin
        next_state <= IDLE;
    end
    endcase
end

//---------------------------------------------------------------------------------

always @(posedge s_axi_aclk)
begin
    s_axi_wready  <= 1'b0;
    s_axi_awready <= 1'b0;
    valid         <= 1'b0;
    case(current_state)
    IDLE:
    begin
        data         <= 0;
        address      <= 0;
        s_axi_bvalid <= 1'b0;
    end
    READY:
    begin
        data          <= s_axi_wdata;
        address       <= s_axi_awaddr;
        valid         <= 1'b1;
        s_axi_wready  <= 1'b1;
        s_axi_awready <= 1'b1;
        s_axi_bvalid  <= 1'b0;
    end
    BVALID:
    begin
        s_axi_bvalid  <= 1'b1;
    end
    BREADY:
    begin
        if(s_axi_bready)
            s_axi_bvalid <= 1'b0;
    end
    default:
    begin
        data         <= 0;
        address      <= 0;
        s_axi_bvalid <= 1'b0;
    end
    endcase
end


endmodule