initial commit
This commit is contained in:
674
rtl/ip/APB_UART/axi2apb.v
Normal file
674
rtl/ip/APB_UART/axi2apb.v
Normal file
@@ -0,0 +1,674 @@
|
||||
/*------------------------------------------------------------------------------
|
||||
--------------------------------------------------------------------------------
|
||||
Copyright (c) 2016, Loongson Technology Corporation Limited.
|
||||
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification,
|
||||
are permitted provided that the following conditions are met:
|
||||
|
||||
1. Redistributions of source code must retain the above copyright notice, this
|
||||
list of conditions and the following disclaimer.
|
||||
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation and/or
|
||||
other materials provided with the distribution.
|
||||
|
||||
3. Neither the name of Loongson Technology Corporation Limited nor the names of
|
||||
its contributors may be used to endorse or promote products derived from this
|
||||
software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL LOONGSON TECHNOLOGY CORPORATION LIMITED BE LIABLE
|
||||
TO ANY PARTY FOR DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
|
||||
GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
|
||||
THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
--------------------------------------------------------------------------------
|
||||
------------------------------------------------------------------------------*/
|
||||
|
||||
`include "config.h"
|
||||
|
||||
module axi2apb_bridge(
|
||||
clk,
|
||||
rst_n,
|
||||
axi_s_awid,
|
||||
axi_s_awaddr,
|
||||
axi_s_awlen,
|
||||
axi_s_awsize,
|
||||
axi_s_awburst,
|
||||
axi_s_awlock,
|
||||
axi_s_awcache,
|
||||
axi_s_awprot,
|
||||
axi_s_awvalid,
|
||||
axi_s_awready,
|
||||
axi_s_wid,
|
||||
axi_s_wdata,
|
||||
axi_s_wstrb,
|
||||
axi_s_wlast,
|
||||
axi_s_wvalid,
|
||||
axi_s_wready,
|
||||
axi_s_bid,
|
||||
axi_s_bresp,
|
||||
axi_s_bvalid,
|
||||
axi_s_bready,
|
||||
axi_s_arid,
|
||||
axi_s_araddr,
|
||||
axi_s_arlen,
|
||||
axi_s_arsize,
|
||||
axi_s_arburst,
|
||||
axi_s_arlock,
|
||||
axi_s_arcache,
|
||||
axi_s_arprot,
|
||||
axi_s_arvalid,
|
||||
axi_s_arready,
|
||||
axi_s_rid,
|
||||
axi_s_rdata,
|
||||
axi_s_rresp,
|
||||
axi_s_rlast,
|
||||
axi_s_rvalid,
|
||||
axi_s_rready,
|
||||
|
||||
apb_valid_cpu,
|
||||
cpu_grant,
|
||||
apb_word_trans,
|
||||
apb_high_24b_rd,
|
||||
apb_high_24b_wr,
|
||||
apb_clk,
|
||||
apb_reset_n,
|
||||
reg_psel,
|
||||
reg_enable,
|
||||
reg_rw,
|
||||
reg_addr,
|
||||
reg_datai,
|
||||
reg_ready_1,
|
||||
reg_datao
|
||||
);
|
||||
parameter L_ADDR_APB = 20;
|
||||
|
||||
input clk;
|
||||
input rst_n;
|
||||
|
||||
input [`LID :0] axi_s_awid;
|
||||
input [`Lawaddr -1 :0] axi_s_awaddr;
|
||||
input [`Lawlen -1 :0] axi_s_awlen;
|
||||
input [`Lawsize -1 :0] axi_s_awsize;
|
||||
input [`Lawburst -1 :0] axi_s_awburst;
|
||||
input [`Lawlock -1 :0] axi_s_awlock;
|
||||
input [`Lawcache -1 :0] axi_s_awcache;
|
||||
input [`Lawprot -1 :0] axi_s_awprot;
|
||||
input axi_s_awvalid;
|
||||
output axi_s_awready;
|
||||
input [`LID :0] axi_s_wid;
|
||||
input [`Lwdata -1 :0] axi_s_wdata;
|
||||
input [`Lwstrb -1 :0] axi_s_wstrb;
|
||||
input axi_s_wlast;
|
||||
input axi_s_wvalid;
|
||||
output axi_s_wready;
|
||||
output [`LID :0] axi_s_bid;
|
||||
output [`Lbresp -1 :0] axi_s_bresp;
|
||||
output axi_s_bvalid;
|
||||
input axi_s_bready;
|
||||
input [`LID :0] axi_s_arid;
|
||||
input [`Laraddr -1 :0] axi_s_araddr;
|
||||
input [`Larlen -1 :0] axi_s_arlen;
|
||||
input [`Larsize -1 :0] axi_s_arsize;
|
||||
input [`Larburst -1 :0] axi_s_arburst;
|
||||
input [`Larlock -1 :0] axi_s_arlock;
|
||||
input [`Larcache -1 :0] axi_s_arcache;
|
||||
input [`Larprot -1 :0] axi_s_arprot;
|
||||
input axi_s_arvalid;
|
||||
output axi_s_arready;
|
||||
output [`LID :0] axi_s_rid;
|
||||
output [`Lrdata -1 :0] axi_s_rdata;
|
||||
output [`Lrresp -1 :0] axi_s_rresp;
|
||||
output axi_s_rlast;
|
||||
output axi_s_rvalid;
|
||||
input axi_s_rready;
|
||||
input apb_word_trans;
|
||||
input cpu_grant;
|
||||
output apb_valid_cpu;
|
||||
input [23:0] apb_high_24b_rd;
|
||||
output [23:0] apb_high_24b_wr;
|
||||
output apb_clk;
|
||||
output apb_reset_n;
|
||||
output reg_psel;
|
||||
output reg_enable;
|
||||
output reg_rw;
|
||||
output[L_ADDR_APB-1:0] reg_addr;
|
||||
output[7:0] reg_datai;
|
||||
input [7:0] reg_datao;
|
||||
input reg_ready_1;
|
||||
|
||||
wire csr_rw_send_axi_rsp_done;
|
||||
wire reg_ready;
|
||||
|
||||
parameter CSR_RW_SM_IDLE = 4'b0001,
|
||||
CSR_RW_SM_GET_AXI_ADDR = 4'b0010,
|
||||
CSR_RW_SM_SEND_AXI_RSP = 4'b1000;
|
||||
|
||||
reg reg_psel;
|
||||
reg reg_enable;
|
||||
reg axi_s_sel_rd;
|
||||
reg axi_s_sel_wr;
|
||||
reg[3:0] csr_rw_sm;
|
||||
reg[3:0] csr_rw_sm_nxt;
|
||||
reg[L_ADDR_APB-1:0] axi_s_req_addr;
|
||||
reg[`LID:0] axi_s_w_id;
|
||||
reg[`LID:0] axi_s_r_id;
|
||||
reg[23:0] apb_high_24b_wr;
|
||||
|
||||
assign apb_clk = clk;
|
||||
assign apb_reset_n = rst_n;
|
||||
assign reg_rw = axi_s_sel_wr;
|
||||
assign reg_addr = axi_s_req_addr;
|
||||
assign reg_ready = reg_enable & reg_ready_1;
|
||||
assign apb_valid_cpu = axi_s_sel_wr | axi_s_sel_rd | axi_s_awvalid | axi_s_arvalid;
|
||||
reg axi_s_rlast;
|
||||
reg axi_s_rvalid;
|
||||
reg axi_s_wready;
|
||||
reg axi_s_awready;
|
||||
reg axi_s_arready;
|
||||
|
||||
reg [3:0]axi_s_rstrb;
|
||||
reg [3:0]apb_s_wstrb;
|
||||
reg [31:0]reg_datai_32;
|
||||
reg [31:0]reg_datao_32;
|
||||
reg [2:0] rd_count;
|
||||
reg [2:0] apb_rd_size;
|
||||
reg [2:0] apb_wr_size;
|
||||
reg [7:0] reg_datai;
|
||||
reg axi_s_bvalid;
|
||||
|
||||
always@(posedge clk)
|
||||
begin
|
||||
if(!rst_n)
|
||||
begin
|
||||
reg_datai_32 <= 32'h0;
|
||||
reg_datao_32 <= 32'h0;
|
||||
axi_s_req_addr <= 20'h0;
|
||||
apb_s_wstrb <= 4'b0;
|
||||
axi_s_rstrb <= 4'b0;
|
||||
axi_s_wready <= 1'b0;
|
||||
reg_enable <= 1'b0;
|
||||
reg_psel <= 1'b0;
|
||||
rd_count <= 3'b0;
|
||||
apb_rd_size <= 3'b0;
|
||||
apb_wr_size <= 3'b0;
|
||||
axi_s_rlast <= 1'b0;
|
||||
axi_s_rvalid <= 1'b0;
|
||||
reg_datai <= 8'b0;
|
||||
axi_s_awready <= 1'b0;
|
||||
axi_s_arready <= 1'b0;
|
||||
axi_s_bvalid <= 1'b0;
|
||||
axi_s_sel_wr <= 1'b0;
|
||||
axi_s_sel_rd <= 1'b0;
|
||||
axi_s_w_id <= 'h0;
|
||||
axi_s_r_id <= 'h0;
|
||||
apb_high_24b_wr <= 24'h0;
|
||||
end
|
||||
else begin
|
||||
if(axi_s_awvalid & ~axi_s_bvalid & ~axi_s_sel_rd & (csr_rw_sm == CSR_RW_SM_IDLE) &cpu_grant) begin
|
||||
axi_s_req_addr <= axi_s_awaddr[L_ADDR_APB-1:0];
|
||||
axi_s_awready <= 1'b1;
|
||||
axi_s_sel_wr <= 1'b1;
|
||||
apb_wr_size <= axi_s_awsize;
|
||||
end
|
||||
else if(axi_s_sel_wr) begin
|
||||
axi_s_awready <= 1'b0;
|
||||
if(axi_s_wvalid && ~axi_s_wready) begin
|
||||
`ifdef AXI128
|
||||
axi_s_req_addr <= (axi_s_wstrb[15:0]==16'h0002)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h1):
|
||||
(axi_s_wstrb[15:0]==16'h0004)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h2):
|
||||
(axi_s_wstrb[15:0]==16'h0008)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h3):
|
||||
(axi_s_wstrb[15:0]==16'h0010)&&(axi_s_req_addr[ 2]==1'h0)? (axi_s_req_addr + 4'h4):
|
||||
(axi_s_wstrb[15:0]==16'h0020)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h5):
|
||||
(axi_s_wstrb[15:0]==16'h0040)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h6):
|
||||
(axi_s_wstrb[15:0]==16'h0080)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h7):
|
||||
(axi_s_wstrb[15:0]==16'h0100)&&(axi_s_req_addr[ 3]==1'h0)? (axi_s_req_addr + 4'h8):
|
||||
(axi_s_wstrb[15:0]==16'h0200)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h9):
|
||||
(axi_s_wstrb[15:0]==16'h0400)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'ha):
|
||||
(axi_s_wstrb[15:0]==16'h0800)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'hb):
|
||||
(axi_s_wstrb[15:0]==16'h1000)&&(axi_s_req_addr[ 2]==1'h0)? (axi_s_req_addr + 4'hc):
|
||||
(axi_s_wstrb[15:0]==16'h2000)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'hd):
|
||||
(axi_s_wstrb[15:0]==16'h4000)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'he):
|
||||
(axi_s_wstrb[15:0]==16'h8000)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'hf):
|
||||
(axi_s_wstrb[15:0]==16'h0006)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h1):
|
||||
(axi_s_wstrb[15:0]==16'h000c)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h2):
|
||||
(axi_s_wstrb[15:0]==16'h0018)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h3):
|
||||
(axi_s_wstrb[15:0]==16'h0030)&&(axi_s_req_addr[ 2]==1'h0)? (axi_s_req_addr + 4'h4):
|
||||
(axi_s_wstrb[15:0]==16'h0060)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h5):
|
||||
(axi_s_wstrb[15:0]==16'h00c0)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h6):
|
||||
(axi_s_wstrb[15:0]==16'h0180)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h7):
|
||||
(axi_s_wstrb[15:0]==16'h0300)&&(axi_s_req_addr[ 3]==1'h0)? (axi_s_req_addr + 4'h8):
|
||||
(axi_s_wstrb[15:0]==16'h0600)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h9):
|
||||
(axi_s_wstrb[15:0]==16'h0c00)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'ha):
|
||||
(axi_s_wstrb[15:0]==16'h1800)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'hb):
|
||||
(axi_s_wstrb[15:0]==16'h3000)&&(axi_s_req_addr[ 2]==1'h0)? (axi_s_req_addr + 4'hc):
|
||||
(axi_s_wstrb[15:0]==16'h6000)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'hd):
|
||||
(axi_s_wstrb[15:0]==16'hc000)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'he):
|
||||
(axi_s_wstrb[15:0]==16'h001e)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h1):
|
||||
(axi_s_wstrb[15:0]==16'h003c)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h2):
|
||||
(axi_s_wstrb[15:0]==16'h0078)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h3):
|
||||
(axi_s_wstrb[15:0]==16'h00f0)&&(axi_s_req_addr[ 2]==1'h0)? (axi_s_req_addr + 4'h4):
|
||||
(axi_s_wstrb[15:0]==16'h01e0)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h5):
|
||||
(axi_s_wstrb[15:0]==16'h03c0)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h6):
|
||||
(axi_s_wstrb[15:0]==16'h0780)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h7):
|
||||
(axi_s_wstrb[15:0]==16'h0f00)&&(axi_s_req_addr[ 3]==1'h0)? (axi_s_req_addr + 4'h8):
|
||||
(axi_s_wstrb[15:0]==16'h1e00)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h9):
|
||||
(axi_s_wstrb[15:0]==16'h3c00)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'ha):
|
||||
(axi_s_wstrb[15:0]==16'h7800)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'hb):
|
||||
(axi_s_wstrb[15:0]==16'hf000)&&(axi_s_req_addr[ 2]==1'h0)? (axi_s_req_addr + 4'hc):
|
||||
(axi_s_wstrb[15:0]==16'h01fe)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h1):
|
||||
(axi_s_wstrb[15:0]==16'h03fc)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h2):
|
||||
(axi_s_wstrb[15:0]==16'h07f8)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h3):
|
||||
(axi_s_wstrb[15:0]==16'h0ff0)&&(axi_s_req_addr[ 2]==1'h0)? (axi_s_req_addr + 4'h4):
|
||||
(axi_s_wstrb[15:0]==16'h1fe0)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h5):
|
||||
(axi_s_wstrb[15:0]==16'h3fc0)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h6):
|
||||
(axi_s_wstrb[15:0]==16'h7f80)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 4'h7):
|
||||
(axi_s_wstrb[15:0]==16'hff00)&&(axi_s_req_addr[ 3]==1'h0)? (axi_s_req_addr + 4'h8): axi_s_req_addr ;
|
||||
`elsif AXI64
|
||||
axi_s_req_addr <= (axi_s_wstrb[7:0]==8'h02)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h1):
|
||||
(axi_s_wstrb[7:0]==8'h04)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h2):
|
||||
(axi_s_wstrb[7:0]==8'h08)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h3):
|
||||
(axi_s_wstrb[7:0]==8'h10)&&(axi_s_req_addr[ 2]==1'h0)? (axi_s_req_addr + 2'h4):
|
||||
(axi_s_wstrb[7:0]==8'h20)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h5):
|
||||
(axi_s_wstrb[7:0]==8'h40)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h6):
|
||||
(axi_s_wstrb[7:0]==8'h80)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h7):
|
||||
(axi_s_wstrb[7:0]==8'h06)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h1):
|
||||
(axi_s_wstrb[7:0]==8'h0c)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h2):
|
||||
(axi_s_wstrb[7:0]==8'h18)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h3):
|
||||
(axi_s_wstrb[7:0]==8'h30)&&(axi_s_req_addr[ 2]==1'h0)? (axi_s_req_addr + 2'h4):
|
||||
(axi_s_wstrb[7:0]==8'h60)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h5):
|
||||
(axi_s_wstrb[7:0]==8'hc0)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h6):
|
||||
(axi_s_wstrb[7:0]==8'h1e)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h1):
|
||||
(axi_s_wstrb[7:0]==8'h3c)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h2):
|
||||
(axi_s_wstrb[7:0]==8'h78)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h3):
|
||||
(axi_s_wstrb[7:0]==8'hf0)&&(axi_s_req_addr[ 2]==1'h0)? (axi_s_req_addr + 2'h4): axi_s_req_addr ;
|
||||
`else
|
||||
axi_s_req_addr <= (axi_s_wstrb[3:0]==4'h2)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h1):
|
||||
(axi_s_wstrb[3:0]==4'h4)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h2):
|
||||
(axi_s_wstrb[3:0]==4'h8)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h3):
|
||||
(axi_s_wstrb[3:0]==4'h6)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h1):
|
||||
(axi_s_wstrb[3:0]==4'hc)&&(axi_s_req_addr[1:0]==2'h0)? (axi_s_req_addr + 2'h2): axi_s_req_addr ;
|
||||
`endif
|
||||
|
||||
axi_s_wready <= 1'b1;
|
||||
reg_psel <= 1'b0;
|
||||
reg_enable <= 1'b0;
|
||||
axi_s_w_id <= axi_s_wid;
|
||||
`ifdef AXI128
|
||||
case({axi_s_req_addr[3:0]})
|
||||
4'b0000: begin apb_s_wstrb <= axi_s_wstrb[ 3: 0]; reg_datai_32 <=axi_s_wdata[ 31: 0]; end
|
||||
4'b0001: begin apb_s_wstrb <= axi_s_wstrb[ 4: 1]; reg_datai_32 <=axi_s_wdata[ 39: 8]; end
|
||||
4'b0010: begin apb_s_wstrb <= axi_s_wstrb[ 5: 2]; reg_datai_32 <=axi_s_wdata[ 47: 16]; end
|
||||
4'b0011: begin apb_s_wstrb <= axi_s_wstrb[ 6: 3]; reg_datai_32 <=axi_s_wdata[ 55: 24]; end
|
||||
4'b0100: begin apb_s_wstrb <= axi_s_wstrb[ 7: 4]; reg_datai_32 <=axi_s_wdata[ 63: 32]; end
|
||||
4'b0101: begin apb_s_wstrb <= axi_s_wstrb[ 8: 5]; reg_datai_32 <=axi_s_wdata[ 71: 40]; end
|
||||
4'b0110: begin apb_s_wstrb <= axi_s_wstrb[ 9: 6]; reg_datai_32 <=axi_s_wdata[ 79: 48]; end
|
||||
4'b0111: begin apb_s_wstrb <= axi_s_wstrb[10: 7]; reg_datai_32 <=axi_s_wdata[ 87: 56]; end
|
||||
4'b1000: begin apb_s_wstrb <= axi_s_wstrb[11: 8]; reg_datai_32 <=axi_s_wdata[ 95: 64]; end
|
||||
4'b1001: begin apb_s_wstrb <= axi_s_wstrb[12: 9]; reg_datai_32 <=axi_s_wdata[103: 72]; end
|
||||
4'b1010: begin apb_s_wstrb <= axi_s_wstrb[13:10]; reg_datai_32 <=axi_s_wdata[111: 80]; end
|
||||
4'b1011: begin apb_s_wstrb <= axi_s_wstrb[14:11]; reg_datai_32 <=axi_s_wdata[119: 88]; end
|
||||
4'b1100: begin apb_s_wstrb <= axi_s_wstrb[15:12]; reg_datai_32 <=axi_s_wdata[127: 96]; end
|
||||
4'b1101: begin apb_s_wstrb <= {1'b0, axi_s_wstrb[15:13]}; reg_datai_32 <={ 8'b0, axi_s_wdata[127:104]}; end
|
||||
4'b1110: begin apb_s_wstrb <= {2'b0, axi_s_wstrb[15:14]}; reg_datai_32 <={16'b0, axi_s_wdata[127:112]}; end
|
||||
4'b1111: begin apb_s_wstrb <= {3'b0, axi_s_wstrb[ 15]}; reg_datai_32 <={24'b0, axi_s_wdata[127:120]}; end
|
||||
default: begin apb_s_wstrb <= 4'b0; reg_datai_32 <=32'h0; end
|
||||
endcase
|
||||
`elsif AXI64
|
||||
case({axi_s_req_addr[2:0]})
|
||||
3'b000: begin apb_s_wstrb <= axi_s_wstrb[3:0]; reg_datai_32 <=axi_s_wdata[31: 0]; end
|
||||
3'b001: begin apb_s_wstrb <= axi_s_wstrb[4:1]; reg_datai_32 <=axi_s_wdata[39: 8]; end
|
||||
3'b010: begin apb_s_wstrb <= axi_s_wstrb[5:2]; reg_datai_32 <=axi_s_wdata[47:16]; end
|
||||
3'b011: begin apb_s_wstrb <= axi_s_wstrb[6:3]; reg_datai_32 <=axi_s_wdata[55:24]; end
|
||||
3'b100: begin apb_s_wstrb <= axi_s_wstrb[7:4]; reg_datai_32 <=axi_s_wdata[63:32]; end
|
||||
3'b101: begin apb_s_wstrb <= {1'b0, axi_s_wstrb[7:5]}; reg_datai_32 <={8 'b0, axi_s_wdata[63:40]}; end
|
||||
3'b110: begin apb_s_wstrb <= {2'b0, axi_s_wstrb[7:6]}; reg_datai_32 <={16'b0, axi_s_wdata[63:48]}; end
|
||||
3'b111: begin apb_s_wstrb <= {3'b0, axi_s_wstrb[ 7]}; reg_datai_32 <={24'b0, axi_s_wdata[63:56]}; end
|
||||
default: begin apb_s_wstrb <= 4'b0; reg_datai_32 <=32'h0; end
|
||||
endcase
|
||||
`else
|
||||
case({axi_s_req_addr[1:0]})
|
||||
2'b00: begin apb_s_wstrb <= axi_s_wstrb[3:0]; reg_datai_32 <=axi_s_wdata[31:0]; end
|
||||
2'b01: begin apb_s_wstrb <= {1'b0,axi_s_wstrb[3:1]}; reg_datai_32 <={8'h0,axi_s_wdata[31:8]}; end
|
||||
2'b10: begin apb_s_wstrb <= {2'b0,axi_s_wstrb[3:2]}; reg_datai_32 <={16'b0,axi_s_wdata[31:16]}; end
|
||||
2'b11: begin apb_s_wstrb <= {3'b0,axi_s_wstrb[3]}; reg_datai_32 <={24'b0,axi_s_wdata[31:24]}; end
|
||||
default: begin apb_s_wstrb <= 4'b0; reg_datai_32 <=32'h0; end
|
||||
endcase
|
||||
`endif
|
||||
end
|
||||
else if((~reg_psel) && (apb_s_wstrb!=4'h0) ) begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b0;
|
||||
reg_datai <= (apb_s_wstrb == 4'h1) ? reg_datai_32[7:0]:
|
||||
(apb_s_wstrb == 4'h2) ? reg_datai_32[15:8]:
|
||||
(apb_s_wstrb == 4'h6) ? reg_datai_32[15:8]:
|
||||
(apb_s_wstrb == 4'h4) ? reg_datai_32[23:16]:
|
||||
(apb_s_wstrb == 4'h8) ? reg_datai_32[31:24]: reg_datai_32[7:0];
|
||||
apb_high_24b_wr <= reg_datai_32[31:8];
|
||||
if(axi_s_bready) axi_s_bvalid <= 1'b0;
|
||||
end
|
||||
else if(apb_word_trans & apb_s_wstrb==4'hf ) begin
|
||||
if(~reg_ready)begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b1;
|
||||
end
|
||||
else begin
|
||||
reg_psel <= 1'b0;
|
||||
reg_enable <= 1'b0;
|
||||
axi_s_sel_wr <= 1'b0;
|
||||
axi_s_bvalid <= 1'b1;
|
||||
apb_s_wstrb <= 4'b0;
|
||||
end
|
||||
reg_datai <= reg_datai_32[7:0];
|
||||
apb_high_24b_wr <= reg_datai_32[31:8];
|
||||
axi_s_wready <= 1'b0;
|
||||
end
|
||||
else if(apb_s_wstrb[0]) begin
|
||||
if(~reg_ready)begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b1;
|
||||
reg_datai <= reg_datai_32[7:0];
|
||||
end
|
||||
else begin
|
||||
if(apb_s_wstrb[3:1] ==3'b0)
|
||||
begin
|
||||
reg_psel <= 1'b0;
|
||||
axi_s_sel_wr<= 1'b0;
|
||||
axi_s_bvalid <= 1'b1;
|
||||
end
|
||||
else
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b0;
|
||||
apb_s_wstrb[0] <= 1'b0;
|
||||
axi_s_req_addr <= axi_s_req_addr +1'b1;
|
||||
reg_datai <= reg_datai_32[15:8];
|
||||
end
|
||||
axi_s_wready <= 1'b0;
|
||||
end
|
||||
else if (apb_s_wstrb[1]) begin
|
||||
if(~reg_ready)begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b1;
|
||||
end
|
||||
else begin
|
||||
if(apb_s_wstrb[3:2] ==2'b0)
|
||||
begin
|
||||
reg_psel <= 1'b0;
|
||||
axi_s_sel_wr <= 1'b0;
|
||||
axi_s_bvalid <= 1'b1;
|
||||
end
|
||||
else
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b0;
|
||||
apb_s_wstrb[1] <= 1'b0;
|
||||
axi_s_req_addr <= axi_s_req_addr +1'b1;
|
||||
reg_datai <= reg_datai_32[23:16];
|
||||
end
|
||||
axi_s_wready <= 1'b0;
|
||||
end
|
||||
else if (apb_s_wstrb[2]) begin
|
||||
if(~reg_ready)begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b1;
|
||||
end
|
||||
else begin
|
||||
if(apb_s_wstrb[3] ==1'b0)
|
||||
begin
|
||||
reg_psel <= 1'b0;
|
||||
axi_s_sel_wr <= 1'b0;
|
||||
axi_s_bvalid <= 1'b1;
|
||||
end
|
||||
else
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b0;
|
||||
apb_s_wstrb[2] <= 1'b0;
|
||||
axi_s_req_addr <= axi_s_req_addr +1'b1;
|
||||
reg_datai <= reg_datai_32[31:24];
|
||||
end
|
||||
axi_s_wready <= 1'b0;
|
||||
end
|
||||
else if (apb_s_wstrb[3]) begin
|
||||
if(~reg_ready)begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b1;
|
||||
end
|
||||
else begin
|
||||
reg_psel <= 1'b0;
|
||||
reg_enable <= 1'b0;
|
||||
axi_s_sel_wr <= 1'b0;
|
||||
axi_s_bvalid <= 1'b1;
|
||||
apb_s_wstrb[3] <= 1'b0;
|
||||
end
|
||||
axi_s_wready <= 1'b0;
|
||||
end
|
||||
else begin
|
||||
reg_psel <= 1'b0;
|
||||
reg_enable <= 1'b0;
|
||||
reg_datai <= 8'h0;
|
||||
apb_s_wstrb <= 4'h0;
|
||||
axi_s_wready <= 1'b0;
|
||||
if(csr_rw_sm == CSR_RW_SM_IDLE) axi_s_sel_wr <= 1'b0;
|
||||
end
|
||||
end
|
||||
else if(axi_s_arvalid & ~axi_s_arready & ~axi_s_bvalid & (csr_rw_sm == CSR_RW_SM_IDLE)&cpu_grant)
|
||||
begin
|
||||
reg_enable <= 1'b0;
|
||||
reg_psel <= 1'b1;
|
||||
axi_s_arready <= 1'b1;
|
||||
axi_s_sel_rd <= 1'b1;
|
||||
axi_s_r_id <= axi_s_arid;
|
||||
apb_rd_size <= axi_s_arsize;
|
||||
axi_s_req_addr <= axi_s_araddr[L_ADDR_APB-1:0];
|
||||
axi_s_rstrb <= axi_s_araddr[3:0];
|
||||
if(axi_s_arsize==3'b010)
|
||||
rd_count<= 3'h4;
|
||||
else if(axi_s_arsize==3'b01)
|
||||
rd_count<= 3'h2;
|
||||
else if(axi_s_arsize==3'b0)
|
||||
rd_count<= 3'h1;
|
||||
end
|
||||
else if(axi_s_sel_rd)
|
||||
begin
|
||||
axi_s_arready <= 1'b0;
|
||||
if(apb_word_trans)
|
||||
begin
|
||||
if(reg_ready)
|
||||
begin
|
||||
reg_psel <= rd_count==3'b10;
|
||||
reg_enable <= 1'b0;
|
||||
rd_count <= rd_count-3'b1;
|
||||
axi_s_rlast <= apb_rd_size==3'h2|rd_count==2'b1;
|
||||
axi_s_rvalid <= apb_rd_size==3'h2|rd_count==2'b1;
|
||||
axi_s_sel_rd <= rd_count==3'b10;
|
||||
reg_datao_32 <= {apb_high_24b_rd,reg_datao};
|
||||
end
|
||||
else begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b1;
|
||||
end
|
||||
end
|
||||
else if(rd_count==3'h4)
|
||||
begin
|
||||
if(reg_ready)
|
||||
begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b0;
|
||||
rd_count <= rd_count-3'h1;
|
||||
reg_datao_32[7:0] <= reg_datao;
|
||||
axi_s_req_addr <= axi_s_req_addr +1'b1;
|
||||
end
|
||||
else begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b1;
|
||||
end
|
||||
end
|
||||
else if(rd_count==3'h3)
|
||||
begin
|
||||
if(reg_ready)
|
||||
begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b0;
|
||||
rd_count <= rd_count-3'h1;
|
||||
reg_datao_32[15:8] <= reg_datao;
|
||||
axi_s_req_addr <= axi_s_req_addr +1'b1;
|
||||
end
|
||||
else begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b1;
|
||||
end
|
||||
end
|
||||
else if(rd_count==3'h2)
|
||||
begin
|
||||
if(reg_ready)
|
||||
begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b0;
|
||||
rd_count <= rd_count-3'h1;
|
||||
axi_s_req_addr <= axi_s_req_addr +1'b1;
|
||||
if(apb_rd_size==3'h2 )
|
||||
reg_datao_32[23:16] <= reg_datao;
|
||||
else if(apb_rd_size==3'h1)
|
||||
reg_datao_32[7:0] <= reg_datao;
|
||||
end
|
||||
else begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b1;
|
||||
end
|
||||
end
|
||||
else if(rd_count==3'h1)
|
||||
begin
|
||||
if(reg_ready)
|
||||
begin
|
||||
reg_psel <= 1'b0;
|
||||
reg_enable <= 1'b0;
|
||||
axi_s_rlast <= 1'b1;
|
||||
axi_s_rvalid <= 1'b1;
|
||||
axi_s_sel_rd <= 1'b0;
|
||||
if(apb_rd_size==3'h2 )
|
||||
reg_datao_32[31:24] <= reg_datao;
|
||||
else if(apb_rd_size==3'h1)
|
||||
reg_datao_32[15:8] <= reg_datao;
|
||||
else if(apb_rd_size==3'h0)
|
||||
reg_datao_32[7:0] <= reg_datao;
|
||||
end
|
||||
else begin
|
||||
reg_psel <= 1'b1;
|
||||
reg_enable <= 1'b1;
|
||||
end
|
||||
end// end if(rd_count)
|
||||
else begin
|
||||
axi_s_arready <= 1'b0;
|
||||
axi_s_rlast <= 1'b1;
|
||||
axi_s_rvalid <= 1'b1;
|
||||
reg_psel <= 1'b0;
|
||||
reg_enable <= 1'b0;
|
||||
if(axi_s_rvalid && axi_s_rready)
|
||||
begin
|
||||
reg_datao_32 <= 32'h0;
|
||||
axi_s_rlast <= 1'b0;
|
||||
axi_s_rvalid <= 1'b0;
|
||||
end
|
||||
if(csr_rw_sm == CSR_RW_SM_IDLE) axi_s_sel_rd <= 1'b0;
|
||||
if(axi_s_bready) axi_s_bvalid <= 1'b0;
|
||||
end
|
||||
end//end if(axi_s_sel_rd)
|
||||
else begin
|
||||
reg_psel <= 1'b0;
|
||||
reg_enable <= 1'b0;
|
||||
axi_s_sel_wr <= 1'b0;
|
||||
axi_s_sel_rd <= 1'b0;
|
||||
axi_s_wready <= 1'b0;
|
||||
axi_s_arready <= 1'b0;
|
||||
axi_s_req_addr <= 32'h0;
|
||||
reg_datai_32 <= 32'h0;
|
||||
if(axi_s_bready) axi_s_bvalid <= 1'b0;
|
||||
if(axi_s_rvalid && axi_s_rready)
|
||||
begin
|
||||
reg_datao_32 <= 32'h0;
|
||||
axi_s_rlast <= 1'b0;
|
||||
axi_s_rvalid <= 1'b0;
|
||||
end
|
||||
end
|
||||
end//end if(rst_n)
|
||||
end//end always
|
||||
|
||||
assign csr_rw_send_axi_rsp_done = csr_rw_sm == CSR_RW_SM_SEND_AXI_RSP && axi_s_rlast && axi_s_rready || axi_s_bvalid && axi_s_bready;
|
||||
|
||||
assign axi_s_bid = axi_s_w_id;
|
||||
assign axi_s_rid = axi_s_r_id;
|
||||
assign axi_s_bresp = 2'b00;
|
||||
assign axi_s_rresp = 2'b00;
|
||||
`ifdef AXI128
|
||||
assign axi_s_rdata= ( axi_s_rstrb == 4'h0) ? {96'b0, reg_datao_32 } :
|
||||
( axi_s_rstrb == 4'h1) ? {88'b0, reg_datao_32, 8'b0 } :
|
||||
( axi_s_rstrb == 4'h2) ? {80'b0, reg_datao_32, 16'b0 } :
|
||||
( axi_s_rstrb == 4'h3) ? {72'b0, reg_datao_32, 24'b0 } :
|
||||
( axi_s_rstrb == 4'h4) ? {64'b0, reg_datao_32, 32'b0 } :
|
||||
( axi_s_rstrb == 4'h5) ? {56'b0, reg_datao_32, 40'b0 } :
|
||||
( axi_s_rstrb == 4'h6) ? {48'b0, reg_datao_32, 48'b0 } :
|
||||
( axi_s_rstrb == 4'h7) ? {40'b0, reg_datao_32, 56'b0 } :
|
||||
( axi_s_rstrb == 4'h8) ? {32'b0, reg_datao_32, 64'b0 } :
|
||||
( axi_s_rstrb == 4'h9) ? {24'b0, reg_datao_32, 72'b0 } :
|
||||
( axi_s_rstrb == 4'ha) ? {16'b0, reg_datao_32, 80'b0 } :
|
||||
( axi_s_rstrb == 4'hb) ? { 8'b0, reg_datao_32, 88'b0 } :
|
||||
( axi_s_rstrb == 4'hc) ? {reg_datao_32, 96'b0 } :
|
||||
( axi_s_rstrb == 4'hd) ? {reg_datao_32[23:0], 104'b0 } :
|
||||
( axi_s_rstrb == 4'he) ? {reg_datao_32[15:0], 112'b0 } :
|
||||
( axi_s_rstrb == 4'hf) ? {reg_datao_32[ 7:0], 120'b0 } : 128'h0;
|
||||
|
||||
`elsif AXI64
|
||||
assign axi_s_rdata= ( axi_s_rstrb[2:0] == 3'h0) ? {32'b0, reg_datao_32 } :
|
||||
( axi_s_rstrb[2:0] == 3'h1) ? {24'b0, reg_datao_32, 8'b0 } :
|
||||
( axi_s_rstrb[2:0] == 3'h2) ? {16'b0, reg_datao_32, 16'b0 } :
|
||||
( axi_s_rstrb[2:0] == 3'h3) ? { 8'b0, reg_datao_32, 24'b0 } :
|
||||
( axi_s_rstrb[2:0] == 3'h4) ? {reg_datao_32, 32'b0 } :
|
||||
( axi_s_rstrb[2:0] == 3'h5) ? {reg_datao_32[23:0], 40'b0 } :
|
||||
( axi_s_rstrb[2:0] == 3'h6) ? {reg_datao_32[15:0], 48'b0 } :
|
||||
( axi_s_rstrb[2:0] == 3'h7) ? {reg_datao_32[ 7:0], 56'b0 } : 64'h0;
|
||||
`else
|
||||
assign axi_s_rdata= ( axi_s_rstrb[1:0] == 2'h0) ? { reg_datao_32 } :
|
||||
( axi_s_rstrb[1:0] == 2'h1) ? {reg_datao_32[23:0], 8'h0} :
|
||||
( axi_s_rstrb[1:0] == 2'h2) ? {reg_datao_32[15:0],16'h0} :
|
||||
( axi_s_rstrb[1:0] == 2'h3) ? {reg_datao_32[7:0], 24'h0} : 32'h0;
|
||||
`endif
|
||||
always@(csr_rw_sm or axi_s_awvalid or axi_s_arvalid or axi_s_sel_rd or axi_s_sel_wr or
|
||||
axi_s_wready or csr_rw_send_axi_rsp_done or cpu_grant) begin
|
||||
case(csr_rw_sm)
|
||||
CSR_RW_SM_IDLE:
|
||||
if((axi_s_awvalid || axi_s_arvalid)&&~(axi_s_sel_wr||axi_s_sel_rd)&cpu_grant)
|
||||
csr_rw_sm_nxt = CSR_RW_SM_GET_AXI_ADDR;
|
||||
else
|
||||
csr_rw_sm_nxt = CSR_RW_SM_IDLE;
|
||||
CSR_RW_SM_GET_AXI_ADDR:
|
||||
if(axi_s_sel_wr)
|
||||
csr_rw_sm_nxt = CSR_RW_SM_SEND_AXI_RSP;
|
||||
else if(axi_s_sel_rd)
|
||||
csr_rw_sm_nxt = CSR_RW_SM_SEND_AXI_RSP;
|
||||
else
|
||||
csr_rw_sm_nxt = CSR_RW_SM_GET_AXI_ADDR;
|
||||
CSR_RW_SM_SEND_AXI_RSP:
|
||||
if(csr_rw_send_axi_rsp_done)
|
||||
csr_rw_sm_nxt = CSR_RW_SM_IDLE;
|
||||
else
|
||||
csr_rw_sm_nxt = CSR_RW_SM_SEND_AXI_RSP;
|
||||
default:
|
||||
csr_rw_sm_nxt = CSR_RW_SM_IDLE;
|
||||
endcase
|
||||
end
|
||||
|
||||
always@(posedge clk) begin
|
||||
if(!rst_n)
|
||||
csr_rw_sm <= CSR_RW_SM_IDLE;
|
||||
else
|
||||
csr_rw_sm <= csr_rw_sm_nxt;
|
||||
end
|
||||
|
||||
endmodule
|
||||
|
||||
Reference in New Issue
Block a user