aboutsummaryrefslogtreecommitdiffstats
path: root/fpga/usrp3/lib/zynq_fifo/zf_stream_to_host.v
diff options
context:
space:
mode:
Diffstat (limited to 'fpga/usrp3/lib/zynq_fifo/zf_stream_to_host.v')
-rw-r--r--fpga/usrp3/lib/zynq_fifo/zf_stream_to_host.v154
1 files changed, 154 insertions, 0 deletions
diff --git a/fpga/usrp3/lib/zynq_fifo/zf_stream_to_host.v b/fpga/usrp3/lib/zynq_fifo/zf_stream_to_host.v
new file mode 100644
index 000000000..b85b56ab8
--- /dev/null
+++ b/fpga/usrp3/lib/zynq_fifo/zf_stream_to_host.v
@@ -0,0 +1,154 @@
+//////////////////////////////////////////////////////////////////////////////////
+//
+// Copyright Ettus Research LLC
+// Copyright 2014 Ettus Research, a National Instruments Company
+//
+// SPDX-License-Identifier: LGPL-3.0-or-later
+//
+// The ZYNQ FIFO - read FIFO and write to DDR:
+// - implements write state machine for AXI master on DDR
+// - provides input fifos from external fabric
+//////////////////////////////////////////////////////////////////////////////////
+
+
+//This implementation takes many states to do individual
+//64 bit xfers from FIFO to the AXI write master.
+//TODO: use axi 4/full with busts,
+//in this case we should be able to directly connect the fifo
+//to the write lines with much less state machinery.
+
+module zf_stream_to_host
+#(
+ parameter PROT = 3'b010, //data, non-secure, unpriv
+ parameter STRB = 4'b1111 //write all bytes
+)
+(
+ input clk,
+ input rst,
+ input enb,
+
+ //------------------------------------------------------------------
+ //-- DDR write signals - master
+ //------------------------------------------------------------------
+ output [31:0] AXI_AWADDR,
+ output [2:0] AXI_AWPROT,
+ output AXI_AWVALID,
+ input AXI_AWREADY,
+ output [63:0] AXI_WDATA,
+ output [3:0] AXI_WSTRB,
+ output AXI_WVALID,
+ input AXI_WREADY,
+ input [1:0] AXI_BRESP,
+ input AXI_BVALID,
+ output AXI_BREADY,
+
+ //------------------------------------------------------------------
+ // FIFO streaming interfaces
+ //------------------------------------------------------------------
+ input [63:0] i_tdata,
+ input i_tlast,
+ input i_tvalid,
+ output i_tready,
+
+ //------------------------------------------------------------------
+ // configuration interface
+ //------------------------------------------------------------------
+ input [31:0] mem_addr,
+ input mem_valid,
+ output mem_ack,
+
+ output [31:0] debug
+);
+
+////////////////////////////////////////////////////////////////////////
+///////////////////////////// Begin R T L //////////////////////////////
+////////////////////////////////////////////////////////////////////////
+
+ localparam STATE_WAIT_MEM = 0;
+ localparam STATE_READ_LINE = 1;
+ localparam STATE_WRITE_ADDR = 2;
+ localparam STATE_WRITE_DATA = 3;
+ localparam STATE_WRITE_B = 4;
+ localparam STATE_DONE = 5;
+
+ reg [31:0] base_addr;
+ reg [63:0] line;
+ reg last;
+
+ reg [2:0] state;
+ always @(posedge clk) begin
+ if (rst) begin
+ state <= STATE_WAIT_MEM;
+ base_addr <= 0;
+ line <= 0;
+ last <= 0;
+ end
+ else if (enb) case (state)
+ STATE_WAIT_MEM: begin
+ if (mem_valid) begin
+ state <= STATE_READ_LINE;
+ end
+ base_addr <= mem_addr;
+ end
+
+ STATE_READ_LINE: begin
+ if (i_tvalid && i_tready) begin
+ line <= i_tdata;
+ last <= i_tlast;
+ state <= STATE_WRITE_ADDR;
+ end
+ end
+
+ STATE_WRITE_ADDR: begin
+ if (AXI_AWVALID && AXI_AWREADY) begin
+ state <= STATE_WRITE_DATA;
+ end
+ end
+
+ STATE_WRITE_DATA: begin
+ if (AXI_WVALID && AXI_WREADY) begin
+ state <= STATE_WRITE_B;
+ end
+ end
+
+ STATE_WRITE_B: begin
+ if (AXI_BREADY && AXI_BVALID) begin//FIXME, slave may not assert valid
+ if (last) state <= STATE_DONE;
+ else state <= STATE_READ_LINE;
+ base_addr <= base_addr + 32'h8;
+ end
+ end
+
+ STATE_DONE: begin
+ state <= STATE_WAIT_MEM;
+ end
+
+ default: state <= STATE_WAIT_MEM;
+
+ endcase //state
+ end
+
+ assign i_tready = (state == STATE_READ_LINE);
+ assign mem_ack = (state == STATE_DONE);
+
+ //assign to master write
+ assign AXI_AWVALID = (state == STATE_WRITE_ADDR);
+ assign AXI_WVALID = (state == STATE_WRITE_DATA);
+ assign AXI_AWADDR = base_addr;
+ assign AXI_WDATA = {line[31:0], line[63:32]};
+
+ assign AXI_WSTRB = STRB;
+ assign AXI_AWPROT = PROT;
+ assign AXI_BREADY = (state == STATE_WRITE_B);
+
+ assign debug[2:0] = state;
+ assign debug[4] = mem_valid;
+ assign debug[5] = mem_ack;
+ assign debug[6] = AXI_AWVALID;
+ assign debug[7] = AXI_AWREADY;
+ assign debug[8] = AXI_WVALID;
+ assign debug[9] = AXI_WREADY;
+ assign debug[10] = AXI_BVALID;
+ assign debug[11] = AXI_BREADY;
+
+endmodule //zf_stream_to_host