diff --git a/examples/hdl4se_riscv/verilog/axi/axi_master.v b/examples/hdl4se_riscv/verilog/axi/axi_master.v deleted file mode 100644 index 78d81d56c336ca4c0024d942e66ff22ec7800c34..0000000000000000000000000000000000000000 --- a/examples/hdl4se_riscv/verilog/axi/axi_master.v +++ /dev/null @@ -1,714 +0,0 @@ - -`timescale 1 ns / 1 ps - - module myip_v1_0_M00_AXI # - ( - // Users to add parameters here - - // User parameters ends - // Do not modify the parameters beyond this line - - // The master will start generating data from the C_M_START_DATA_VALUE value - parameter C_M_START_DATA_VALUE = 32'hAA000000, - // The master requires a target slave base address. - // The master will initiate read and write transactions on the slave with base address specified here as a parameter. - parameter C_M_TARGET_SLAVE_BASE_ADDR = 32'h40000000, - // Width of M_AXI address bus. - // The master generates the read and write addresses of width specified as C_M_AXI_ADDR_WIDTH. - parameter integer C_M_AXI_ADDR_WIDTH = 32, - // Width of M_AXI data bus. - // The master issues write data and accept read data where the width of the data bus is C_M_AXI_DATA_WIDTH - parameter integer C_M_AXI_DATA_WIDTH = 32, - // Transaction number is the number of write - // and read transactions the master will perform as a part of this example memory test. - parameter integer C_M_TRANSACTIONS_NUM = 4 - ) - ( - // Users to add ports here - - // User ports ends - // Do not modify the ports beyond this line - - // Initiate AXI transactions - input wire INIT_AXI_TXN, - // Asserts when ERROR is detected - output reg ERROR, - // Asserts when AXI transactions is complete - output wire TXN_DONE, - // AXI clock signal - input wire M_AXI_ACLK, - // AXI active low reset signal - input wire M_AXI_ARESETN, - // Master Interface Write Address Channel ports. Write address (issued by master) - output wire [C_M_AXI_ADDR_WIDTH-1 : 0] M_AXI_AWADDR, - // Write channel Protection type. - // This signal indicates the privilege and security level of the transaction, - // and whether the transaction is a data access or an instruction access. - output wire [2 : 0] M_AXI_AWPROT, - // Write address valid. - // This signal indicates that the master signaling valid write address and control information. - output wire M_AXI_AWVALID, - // Write address ready. - // This signal indicates that the slave is ready to accept an address and associated control signals. - input wire M_AXI_AWREADY, - // Master Interface Write Data Channel ports. Write data (issued by master) - output wire [C_M_AXI_DATA_WIDTH-1 : 0] M_AXI_WDATA, - // Write strobes. - // This signal indicates which byte lanes hold valid data. - // There is one write strobe bit for each eight bits of the write data bus. - output wire [C_M_AXI_DATA_WIDTH/8-1 : 0] M_AXI_WSTRB, - // Write valid. This signal indicates that valid write data and strobes are available. - output wire M_AXI_WVALID, - // Write ready. This signal indicates that the slave can accept the write data. - input wire M_AXI_WREADY, - // Master Interface Write Response Channel ports. - // This signal indicates the status of the write transaction. - input wire [1 : 0] M_AXI_BRESP, - // Write response valid. - // This signal indicates that the channel is signaling a valid write response - input wire M_AXI_BVALID, - // Response ready. This signal indicates that the master can accept a write response. - output wire M_AXI_BREADY, - // Master Interface Read Address Channel ports. Read address (issued by master) - output wire [C_M_AXI_ADDR_WIDTH-1 : 0] M_AXI_ARADDR, - // Protection type. - // This signal indicates the privilege and security level of the transaction, - // and whether the transaction is a data access or an instruction access. - output wire [2 : 0] M_AXI_ARPROT, - // Read address valid. - // This signal indicates that the channel is signaling valid read address and control information. - output wire M_AXI_ARVALID, - // Read address ready. - // This signal indicates that the slave is ready to accept an address and associated control signals. - input wire M_AXI_ARREADY, - // Master Interface Read Data Channel ports. Read data (issued by slave) - input wire [C_M_AXI_DATA_WIDTH-1 : 0] M_AXI_RDATA, - // Read response. This signal indicates the status of the read transfer. - input wire [1 : 0] M_AXI_RRESP, - // Read valid. This signal indicates that the channel is signaling the required read data. - input wire M_AXI_RVALID, - // Read ready. This signal indicates that the master can accept the read data and response information. - output wire M_AXI_RREADY - ); - - // function called clogb2 that returns an integer which has the - // value of the ceiling of the log base 2 - - function integer clogb2 (input integer bit_depth); - begin - for(clogb2=0; bit_depth>0; clogb2=clogb2+1) - bit_depth = bit_depth >> 1; - end - endfunction - - // TRANS_NUM_BITS is the width of the index counter for - // number of write or read transaction. - localparam integer TRANS_NUM_BITS = clogb2(C_M_TRANSACTIONS_NUM-1); - - // Example State machine to initialize counter, initialize write transactions, - // initialize read transactions and comparison of read data with the - // written data words. - parameter [1:0] IDLE = 2'b00, // This state initiates AXI4Lite transaction - // after the state machine changes state to INIT_WRITE - // when there is 0 to 1 transition on INIT_AXI_TXN - INIT_WRITE = 2'b01, // This state initializes write transaction, - // once writes are done, the state machine - // changes state to INIT_READ - INIT_READ = 2'b10, // This state initializes read transaction - // once reads are done, the state machine - // changes state to INIT_COMPARE - INIT_COMPARE = 2'b11; // This state issues the status of comparison - // of the written data with the read data - - reg [1:0] mst_exec_state; - - // AXI4LITE signals - //write address valid - reg axi_awvalid; - //write data valid - reg axi_wvalid; - //read address valid - reg axi_arvalid; - //read data acceptance - reg axi_rready; - //write response acceptance - reg axi_bready; - //write address - reg [C_M_AXI_ADDR_WIDTH-1 : 0] axi_awaddr; - //write data - reg [C_M_AXI_DATA_WIDTH-1 : 0] axi_wdata; - //read addresss - reg [C_M_AXI_ADDR_WIDTH-1 : 0] axi_araddr; - //Asserts when there is a write response error - wire write_resp_error; - //Asserts when there is a read response error - wire read_resp_error; - //A pulse to initiate a write transaction - reg start_single_write; - //A pulse to initiate a read transaction - reg start_single_read; - //Asserts when a single beat write transaction is issued and remains asserted till the completion of write trasaction. - reg write_issued; - //Asserts when a single beat read transaction is issued and remains asserted till the completion of read trasaction. - reg read_issued; - //flag that marks the completion of write trasactions. The number of write transaction is user selected by the parameter C_M_TRANSACTIONS_NUM. - reg writes_done; - //flag that marks the completion of read trasactions. The number of read transaction is user selected by the parameter C_M_TRANSACTIONS_NUM - reg reads_done; - //The error register is asserted when any of the write response error, read response error or the data mismatch flags are asserted. - reg error_reg; - //index counter to track the number of write transaction issued - reg [TRANS_NUM_BITS : 0] write_index; - //index counter to track the number of read transaction issued - reg [TRANS_NUM_BITS : 0] read_index; - //Expected read data used to compare with the read data. - reg [C_M_AXI_DATA_WIDTH-1 : 0] expected_rdata; - //Flag marks the completion of comparison of the read data with the expected read data - reg compare_done; - //This flag is asserted when there is a mismatch of the read data with the expected read data. - reg read_mismatch; - //Flag is asserted when the write index reaches the last write transction number - reg last_write; - //Flag is asserted when the read index reaches the last read transction number - reg last_read; - reg init_txn_ff; - reg init_txn_ff2; - reg init_txn_edge; - wire init_txn_pulse; - - - // I/O Connections assignments - - //Adding the offset address to the base addr of the slave - assign M_AXI_AWADDR = C_M_TARGET_SLAVE_BASE_ADDR + axi_awaddr; - //AXI 4 write data - assign M_AXI_WDATA = axi_wdata; - assign M_AXI_AWPROT = 3'b000; - assign M_AXI_AWVALID = axi_awvalid; - //Write Data(W) - assign M_AXI_WVALID = axi_wvalid; - //Set all byte strobes in this example - assign M_AXI_WSTRB = 4'b1111; - //Write Response (B) - assign M_AXI_BREADY = axi_bready; - //Read Address (AR) - assign M_AXI_ARADDR = C_M_TARGET_SLAVE_BASE_ADDR + axi_araddr; - assign M_AXI_ARVALID = axi_arvalid; - assign M_AXI_ARPROT = 3'b001; - //Read and Read Response (R) - assign M_AXI_RREADY = axi_rready; - //Example design I/O - assign TXN_DONE = compare_done; - assign init_txn_pulse = (!init_txn_ff2) && init_txn_ff; - - - //Generate a pulse to initiate AXI transaction. - always @(posedge M_AXI_ACLK) - begin - // Initiates AXI transaction delay - if (M_AXI_ARESETN == 0 ) - begin - init_txn_ff <= 1'b0; - init_txn_ff2 <= 1'b0; - end - else - begin - init_txn_ff <= INIT_AXI_TXN; - init_txn_ff2 <= init_txn_ff; - end - end - - - //-------------------- - //Write Address Channel - //-------------------- - - // The purpose of the write address channel is to request the address and - // command information for the entire transaction. It is a single beat - // of information. - - // Note for this example the axi_awvalid/axi_wvalid are asserted at the same - // time, and then each is deasserted independent from each other. - // This is a lower-performance, but simplier control scheme. - - // AXI VALID signals must be held active until accepted by the partner. - - // A data transfer is accepted by the slave when a master has - // VALID data and the slave acknoledges it is also READY. While the master - // is allowed to generated multiple, back-to-back requests by not - // deasserting VALID, this design will add rest cycle for - // simplicity. - - // Since only one outstanding transaction is issued by the user design, - // there will not be a collision between a new request and an accepted - // request on the same clock cycle. - - always @(posedge M_AXI_ACLK) - begin - //Only VALID signals must be deasserted during reset per AXI spec - //Consider inverting then registering active-low reset for higher fmax - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - begin - axi_awvalid <= 1'b0; - end - //Signal a new address/data command is available by user logic - else - begin - if (start_single_write) - begin - axi_awvalid <= 1'b1; - end - //Address accepted by interconnect/slave (issue of M_AXI_AWREADY by slave) - else if (M_AXI_AWREADY && axi_awvalid) - begin - axi_awvalid <= 1'b0; - end - end - end - - - // start_single_write triggers a new write - // transaction. write_index is a counter to - // keep track with number of write transaction - // issued/initiated - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - begin - write_index <= 0; - end - // Signals a new write address/ write data is - // available by user logic - else if (start_single_write) - begin - write_index <= write_index + 1; - end - end - - - //-------------------- - //Write Data Channel - //-------------------- - - //The write data channel is for transfering the actual data. - //The data generation is speific to the example design, and - //so only the WVALID/WREADY handshake is shown here - - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - begin - axi_wvalid <= 1'b0; - end - //Signal a new address/data command is available by user logic - else if (start_single_write) - begin - axi_wvalid <= 1'b1; - end - //Data accepted by interconnect/slave (issue of M_AXI_WREADY by slave) - else if (M_AXI_WREADY && axi_wvalid) - begin - axi_wvalid <= 1'b0; - end - end - - - //---------------------------- - //Write Response (B) Channel - //---------------------------- - - //The write response channel provides feedback that the write has committed - //to memory. BREADY will occur after both the data and the write address - //has arrived and been accepted by the slave, and can guarantee that no - //other accesses launched afterwards will be able to be reordered before it. - - //The BRESP bit [1] is used indicate any errors from the interconnect or - //slave for the entire write burst. This example will capture the error. - - //While not necessary per spec, it is advisable to reset READY signals in - //case of differing reset latencies between master/slave. - - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - begin - axi_bready <= 1'b0; - end - // accept/acknowledge bresp with axi_bready by the master - // when M_AXI_BVALID is asserted by slave - else if (M_AXI_BVALID && ~axi_bready) - begin - axi_bready <= 1'b1; - end - // deassert after one clock cycle - else if (axi_bready) - begin - axi_bready <= 1'b0; - end - // retain the previous value - else - axi_bready <= axi_bready; - end - - //Flag write errors - assign write_resp_error = (axi_bready & M_AXI_BVALID & M_AXI_BRESP[1]); - - - //---------------------------- - //Read Address Channel - //---------------------------- - - //start_single_read triggers a new read transaction. read_index is a counter to - //keep track with number of read transaction issued/initiated - - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - begin - read_index <= 0; - end - // Signals a new read address is - // available by user logic - else if (start_single_read) - begin - read_index <= read_index + 1; - end - end - - // A new axi_arvalid is asserted when there is a valid read address - // available by the master. start_single_read triggers a new read - // transaction - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - begin - axi_arvalid <= 1'b0; - end - //Signal a new read address command is available by user logic - else if (start_single_read) - begin - axi_arvalid <= 1'b1; - end - //RAddress accepted by interconnect/slave (issue of M_AXI_ARREADY by slave) - else if (M_AXI_ARREADY && axi_arvalid) - begin - axi_arvalid <= 1'b0; - end - // retain the previous value - end - - - //-------------------------------- - //Read Data (and Response) Channel - //-------------------------------- - - //The Read Data channel returns the results of the read request - //The master will accept the read data by asserting axi_rready - //when there is a valid read data available. - //While not necessary per spec, it is advisable to reset READY signals in - //case of differing reset latencies between master/slave. - - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - begin - axi_rready <= 1'b0; - end - // accept/acknowledge rdata/rresp with axi_rready by the master - // when M_AXI_RVALID is asserted by slave - else if (M_AXI_RVALID && ~axi_rready) - begin - axi_rready <= 1'b1; - end - // deassert after one clock cycle - else if (axi_rready) - begin - axi_rready <= 1'b0; - end - // retain the previous value - end - - //Flag write errors - assign read_resp_error = (axi_rready & M_AXI_RVALID & M_AXI_RRESP[1]); - - - //-------------------------------- - //User Logic - //-------------------------------- - - //Address/Data Stimulus - - //Address/data pairs for this example. The read and write values should - //match. - //Modify these as desired for different address patterns. - - //Write Addresses - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - begin - axi_awaddr <= 0; - end - // Signals a new write address/ write data is - // available by user logic - else if (M_AXI_AWREADY && axi_awvalid) - begin - axi_awaddr <= axi_awaddr + 32'h00000004; - - end - end - - // Write data generation - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1 ) - begin - axi_wdata <= C_M_START_DATA_VALUE; - end - // Signals a new write address/ write data is - // available by user logic - else if (M_AXI_WREADY && axi_wvalid) - begin - axi_wdata <= C_M_START_DATA_VALUE + write_index; - end - end - - //Read Addresses - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - begin - axi_araddr <= 0; - end - // Signals a new write address/ write data is - // available by user logic - else if (M_AXI_ARREADY && axi_arvalid) - begin - axi_araddr <= axi_araddr + 32'h00000004; - end - end - - - - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - begin - expected_rdata <= C_M_START_DATA_VALUE; - end - // Signals a new write address/ write data is - // available by user logic - else if (M_AXI_RVALID && axi_rready) - begin - expected_rdata <= C_M_START_DATA_VALUE + read_index; - end - end - //implement master command interface state machine - always @ ( posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 1'b0) - begin - // reset condition - // All the signals are assigned default values under reset condition - mst_exec_state <= IDLE; - start_single_write <= 1'b0; - write_issued <= 1'b0; - start_single_read <= 1'b0; - read_issued <= 1'b0; - compare_done <= 1'b0; - ERROR <= 1'b0; - end - else - begin - // state transition - case (mst_exec_state) - - IDLE: - // This state is responsible to initiate - // AXI transaction when init_txn_pulse is asserted - if ( init_txn_pulse == 1'b1 ) - begin - mst_exec_state <= INIT_WRITE; - ERROR <= 1'b0; - compare_done <= 1'b0; - end - else - begin - mst_exec_state <= IDLE; - end - - INIT_WRITE: - // This state is responsible to issue start_single_write pulse to - // initiate a write transaction. Write transactions will be - // issued until last_write signal is asserted. - // write controller - if (writes_done) - begin - mst_exec_state <= INIT_READ;// - end - else - begin - mst_exec_state <= INIT_WRITE; - - if (~axi_awvalid && ~axi_wvalid && ~M_AXI_BVALID && ~last_write && ~start_single_write && ~write_issued) - begin - start_single_write <= 1'b1; - write_issued <= 1'b1; - end - else if (axi_bready) - begin - write_issued <= 1'b0; - end - else - begin - start_single_write <= 1'b0; //Negate to generate a pulse - end - end - - INIT_READ: - // This state is responsible to issue start_single_read pulse to - // initiate a read transaction. Read transactions will be - // issued until last_read signal is asserted. - // read controller - if (reads_done) - begin - mst_exec_state <= INIT_COMPARE; - end - else - begin - mst_exec_state <= INIT_READ; - - if (~axi_arvalid && ~M_AXI_RVALID && ~last_read && ~start_single_read && ~read_issued) - begin - start_single_read <= 1'b1; - read_issued <= 1'b1; - end - else if (axi_rready) - begin - read_issued <= 1'b0; - end - else - begin - start_single_read <= 1'b0; //Negate to generate a pulse - end - end - - INIT_COMPARE: - begin - // This state is responsible to issue the state of comparison - // of written data with the read data. If no error flags are set, - // compare_done signal will be asseted to indicate success. - ERROR <= error_reg; - mst_exec_state <= IDLE; - compare_done <= 1'b1; - end - default : - begin - mst_exec_state <= IDLE; - end - endcase - end - end //MASTER_EXECUTION_PROC - - //Terminal write count - - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - last_write <= 1'b0; - - //The last write should be associated with a write address ready response - else if ((write_index == C_M_TRANSACTIONS_NUM) && M_AXI_AWREADY) - last_write <= 1'b1; - else - last_write <= last_write; - end - - //Check for last write completion. - - //This logic is to qualify the last write count with the final write - //response. This demonstrates how to confirm that a write has been - //committed. - - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - writes_done <= 1'b0; - - //The writes_done should be associated with a bready response - else if (last_write && M_AXI_BVALID && axi_bready) - writes_done <= 1'b1; - else - writes_done <= writes_done; - end - - //------------------ - //Read example - //------------------ - - //Terminal Read Count - - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - last_read <= 1'b0; - - //The last read should be associated with a read address ready response - else if ((read_index == C_M_TRANSACTIONS_NUM) && (M_AXI_ARREADY) ) - last_read <= 1'b1; - else - last_read <= last_read; - end - - /* - Check for last read completion. - - This logic is to qualify the last read count with the final read - response/data. - */ - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - reads_done <= 1'b0; - - //The reads_done should be associated with a read ready response - else if (last_read && M_AXI_RVALID && axi_rready) - reads_done <= 1'b1; - else - reads_done <= reads_done; - end - - //----------------------------- - //Example design error register - //----------------------------- - - //Data Comparison - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - read_mismatch <= 1'b0; - - //The read data when available (on axi_rready) is compared with the expected data - else if ((M_AXI_RVALID && axi_rready) && (M_AXI_RDATA != expected_rdata)) - read_mismatch <= 1'b1; - else - read_mismatch <= read_mismatch; - end - - // Register and hold any data mismatches, or read/write interface errors - always @(posedge M_AXI_ACLK) - begin - if (M_AXI_ARESETN == 0 || init_txn_pulse == 1'b1) - error_reg <= 1'b0; - - //Capture any error types - else if (read_mismatch || write_resp_error || read_resp_error) - error_reg <= 1'b1; - else - error_reg <= error_reg; - end - // Add user logic here - - // User logic ends - - endmodule diff --git a/examples/hdl4se_riscv/verilog/axi/riscv_core_with_axi_master.v b/examples/hdl4se_riscv/verilog/axi/riscv_core_with_axi_master.v new file mode 100644 index 0000000000000000000000000000000000000000..8700219a7f082b98f316af1faebf84bc19036964 --- /dev/null +++ b/examples/hdl4se_riscv/verilog/axi/riscv_core_with_axi_master.v @@ -0,0 +1,147 @@ + +`timescale 1 ns / 1 ps + +module riscv_core_with_axi_master ( + // clock and reset + input wire wClk, + input wire nwReset, + + // Write Address + output wire wAWValid, + output wire [31 : 0] bAWAddr, + output wire [2 : 0] bAWProt, + input wire wAWReady, + + // Write Data + output wire wWValid, + output wire [31 : 0] bWData, + output wire [3 : 0] bWStrb, + input wire wWReady, + + // Write Response + output wire wBReady, + input wire [1 : 0] bBResp, + input wire wBValid, + + // ReadAddr + output wire wARValid, + output wire [31 : 0] bARAddr, + output wire [2 : 0] bARProt, + input wire wARReady, + + //ReadData + output wire wRReady + input wire wRValid, + input wire [31 : 0] bRData, + input wire [1 : 0] bRResp +); + + reg axi_awvalid; assign wAWValid = axi_awvalid; + reg [31:0] axi_awaddr; assign bAWAddr = axi_awaddr; + assign bAWProt = 3'b000; + + reg axi_wvalid; assign wWValid = axi_wvalid; + reg [31:0] axi_wdata; assign bWData = axi_wdata; + reg [3:0] axi_wstrb; assign bWStrb = axi_wstrb; + + assign wBReady = 1'b1; + + reg axi_arvalid; assign wARValid = axi_arvalid; + reg [31:0] axi_araddr; assign bARAddr = axi_araddr; + assign bARProt = 3'b001; + + assign wRReady = 1'b1; + + wire wWrite, wRead, wReadReady, wWriteReady; + wire [31:0] bWriteAddr, bWriteData, bReadAddr, bReadData, bReadDataRam, bReadDataKey; + + wire [4:0] regno; + wire [3:0] regena; + wire [31:0] regwrdata; + wire regwren; + wire [31:0] regrddata; + wire [4:0] regno2; + wire [3:0] regena2; + wire [31:0] regwrdata2; + wire regwren2; + wire [31:0] regrddata2; + + regfile regs(regno, regena, wClk, regwrdata, regwren, regrddata); + regfile regs2(regno2, regena2, wClk, regwrdata2, regwren2, regrddata2); + riscv_core core(wClk, nwReset, + wWrite, bWriteAddr, bWriteData, bWriteMask, wWriteReady, + wRead, bReadAddr, bReadData, wReadReady, + regno, regena, regwrdata, regwren, regrddata, + regno2, regena2, regwrdata2, regwren2, regrddata2 + ); + + + //Write Address + reg [31:0] awaddr; + reg awvalid; + always @(posedge wClk) + if (~nwReset) begin + awvalid <= 1'b0; + end else if (wWrite) begin + awaddr <= bWriteAddr; + awvalid <= 1'b1; + end else if (wAWReady) begin + awvalid <= 1'b0; + end + + assign wWriteReady = (wWrite || awvalid) && wAWReady; + + always @(*) + begin + axi_awvalid = wWrite ? 1'b1 : awvalid; + axi_awaddr = wWrite ? bWriteAddr : awaddr; + end + + /* Write Data */ + reg [31:0] wdata; + reg [3:0] wstrb; + reg wvalid; + always @(wClk) + begin + if (~nwReset) begin + wvalid <= 1'b0; + end if (wWrite) begin + wdata <= bWriteData; + wstrb <= ~bWriteMask; + wvalid <= 1'b1; + end if (wWReady) begin + wvalid <= 1'b0; + end + end + + always @(*) + begin + axi_wvalid = wWrite ? 1'b1 : wvalid; + axi_wdata = wWrite ? bWriteData : wdata; + axi_wstrb = wWrite ? ~bWriteMask : wstrb; + end + + //Read Address + reg [31:0] araddr; + reg arvalid; + always @(posedge wClk) + if (~nwReset) begin + arvalid <= 1'b0; + end else if (wRead) begin + araddr <= bReadAddr; + arvalid <= 1'b1; + end else if (wARReady) begin + arvalid <= 1'b0; + end + + assign wReadyReady = (wRead || arvalid) && wARReady; + + always @(*) + begin + axi_arvalid = wRead ? 1'b1 : arvalid; + axi_araddr = wRead ? bReadAddr : araddr; + end + + assign bReadData = bRData; + +endmodule