From 47f958f5c4d00eedcb073d41f4715113686660f3 Mon Sep 17 00:00:00 2001 From: Byron Lathi Date: Mon, 19 Aug 2024 20:27:27 -0700 Subject: [PATCH] Update regs --- .../network_processor/src/regs/mac_regs.rdl | 121 ++++ .../network_processor/src/regs/mac_regs.sv | 553 ++++++++++++++++++ .../src/regs/mac_regs_pkg.sv | 144 +++++ .../sub/network_processor/src/regs/mac_t.sv | 547 +++++++++++++++++ .../network_processor/src/regs/mac_t_pkg.sv | 136 +++++ .../src/regs/ntw_top_regfile.sv | 350 +++++++++++ .../src/regs/ntw_top_regfile_pkg.sv | 46 ++ .../src/regs/ntw_top_regs.rdl | 4 + .../src/regs/run_precompile.sh | 14 +- .../{tcp_stream.rdl => tcp_stream_regs.rdl} | 6 +- .../src/regs/tcp_stream_regs.sv | 300 +++++----- .../src/regs/tcp_stream_regs_pkg.sv | 72 +-- .../src/regs/tcp_top_regfile.sv | 209 +------ .../src/regs/tcp_top_regfile_pkg.sv | 8 +- .../src/regs/tcp_top_regs.rdl | 2 +- 15 files changed, 2114 insertions(+), 398 deletions(-) create mode 100644 hw/super6502_fpga/src/sub/network_processor/src/regs/mac_regs.rdl create mode 100644 hw/super6502_fpga/src/sub/network_processor/src/regs/mac_regs.sv create mode 100644 hw/super6502_fpga/src/sub/network_processor/src/regs/mac_regs_pkg.sv create mode 100644 hw/super6502_fpga/src/sub/network_processor/src/regs/mac_t.sv create mode 100644 hw/super6502_fpga/src/sub/network_processor/src/regs/mac_t_pkg.sv create mode 100644 hw/super6502_fpga/src/sub/network_processor/src/regs/ntw_top_regfile.sv create mode 100644 hw/super6502_fpga/src/sub/network_processor/src/regs/ntw_top_regfile_pkg.sv create mode 100644 hw/super6502_fpga/src/sub/network_processor/src/regs/ntw_top_regs.rdl rename hw/super6502_fpga/src/sub/network_processor/src/regs/{tcp_stream.rdl => tcp_stream_regs.rdl} (98%) diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_regs.rdl b/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_regs.rdl new file mode 100644 index 0000000..63805bb --- /dev/null +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_regs.rdl @@ -0,0 +1,121 @@ +addrmap mac_t { + reg { + name = "Control"; + desc = "Control bits for the MAC"; + + field { + name = "TX Enable"; + desc = "Enable TX"; + hw = r; + sw = rw; + } tx_en[0:0] = 0x0; + + field { + name = "RX Enable"; + desc = "Enable RX"; + hw = r; + sw = rw; + } rx_en[1:1] = 0x0; + + field { + name = "PHY Reset"; + desc = "phy_rstn"; + hw = r; + sw = rw; + } phy_rstn[2:2] = 0x1; + + field { + name = "Interframe Gap"; + desc = "Interframe gap in mii clock cycles"; + hw = r; + sw = rw; + } ifg[15:8] = 0x0; + + } ctrl @ 0x0; + + reg { + name = "Error"; + desc = "Latched Error from the MAC"; + + field { + name = "tx_error_underflow"; + desc = ""; + hw = r; + sw = r; + rclr; + hwset; + } tx_error_underflow[0:0] = 0x0; + + field { + name = "tx_fifo_overflow"; + desc = ""; + hw = r; + sw = r; + rclr; + hwset; + } tx_fifo_overflow[1:1] = 0x0; + + field { + name = "tx_fifo_bad_frame"; + desc = ""; + hw = r; + sw = r; + rclr; + hwset; + } tx_fifo_bad_frame[2:2] = 0x0; + + field { + name = "tx_fifo_good_frame"; + desc = ""; + hw = r; + sw = r; + rclr; + hwset; + } tx_fifo_good_frame[3:3] = 0x0; + + field { + name = "rx_error_bad_frame"; + desc = ""; + hw = r; + sw = r; + rclr; + hwset; + } rx_error_bad_frame[4:4] = 0x0; + + field { + name = "rx_error_bad_fcs"; + desc = ""; + hw = r; + sw = r; + rclr; + hwset; + } rx_error_bad_fcs[5:5] = 0x0; + + field { + name = "rx_fifo_overflow"; + desc = ""; + hw = r; + sw = r; + rclr; + hwset; + } rx_fifo_overflow[6:6] = 0x0; + + field { + name = "rx_fifo_bad_frame"; + desc = ""; + hw = r; + sw = r; + rclr; + hwset; + } rx_fifo_bad_frame[7:7] = 0x0; + + field { + name = "rx_fifo_good_frame"; + desc = ""; + hw = r; + sw = r; + rclr; + hwset; + } rx_fifo_good_frame[8:8] = 0x0; + } stats @ 0x4; +}; \ No newline at end of file diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_regs.sv b/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_regs.sv new file mode 100644 index 0000000..25538e1 --- /dev/null +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_regs.sv @@ -0,0 +1,553 @@ +// Generated by PeakRDL-regblock - A free and open-source SystemVerilog generator +// https://github.com/SystemRDL/PeakRDL-regblock + +module mac_regs ( + input wire clk, + input wire rst, + + input wire s_cpuif_req, + input wire s_cpuif_req_is_wr, + input wire [2:0] s_cpuif_addr, + input wire [31:0] s_cpuif_wr_data, + input wire [31:0] s_cpuif_wr_biten, + output wire s_cpuif_req_stall_wr, + output wire s_cpuif_req_stall_rd, + output wire s_cpuif_rd_ack, + output wire s_cpuif_rd_err, + output wire [31:0] s_cpuif_rd_data, + output wire s_cpuif_wr_ack, + output wire s_cpuif_wr_err, + + input mac_regs_pkg::mac_regs__in_t hwif_in, + output mac_regs_pkg::mac_regs__out_t hwif_out + ); + + //-------------------------------------------------------------------------- + // CPU Bus interface logic + //-------------------------------------------------------------------------- + logic cpuif_req; + logic cpuif_req_is_wr; + logic [2:0] cpuif_addr; + logic [31:0] cpuif_wr_data; + logic [31:0] cpuif_wr_biten; + logic cpuif_req_stall_wr; + logic cpuif_req_stall_rd; + + logic cpuif_rd_ack; + logic cpuif_rd_err; + logic [31:0] cpuif_rd_data; + + logic cpuif_wr_ack; + logic cpuif_wr_err; + + assign cpuif_req = s_cpuif_req; + assign cpuif_req_is_wr = s_cpuif_req_is_wr; + assign cpuif_addr = s_cpuif_addr; + assign cpuif_wr_data = s_cpuif_wr_data; + assign cpuif_wr_biten = s_cpuif_wr_biten; + assign s_cpuif_req_stall_wr = cpuif_req_stall_wr; + assign s_cpuif_req_stall_rd = cpuif_req_stall_rd; + assign s_cpuif_rd_ack = cpuif_rd_ack; + assign s_cpuif_rd_err = cpuif_rd_err; + assign s_cpuif_rd_data = cpuif_rd_data; + assign s_cpuif_wr_ack = cpuif_wr_ack; + assign s_cpuif_wr_err = cpuif_wr_err; + + logic cpuif_req_masked; + + // Read & write latencies are balanced. Stalls not required + assign cpuif_req_stall_rd = '0; + assign cpuif_req_stall_wr = '0; + assign cpuif_req_masked = cpuif_req + & !(!cpuif_req_is_wr & cpuif_req_stall_rd) + & !(cpuif_req_is_wr & cpuif_req_stall_wr); + + //-------------------------------------------------------------------------- + // Address Decode + //-------------------------------------------------------------------------- + typedef struct { + struct { + logic ctrl; + logic stats; + } mac; + } decoded_reg_strb_t; + decoded_reg_strb_t decoded_reg_strb; + logic decoded_req; + logic decoded_req_is_wr; + logic [31:0] decoded_wr_data; + logic [31:0] decoded_wr_biten; + + always_comb begin + decoded_reg_strb.mac.ctrl = cpuif_req_masked & (cpuif_addr == 3'h0); + decoded_reg_strb.mac.stats = cpuif_req_masked & (cpuif_addr == 3'h4); + end + + // Pass down signals to next stage + assign decoded_req = cpuif_req_masked; + assign decoded_req_is_wr = cpuif_req_is_wr; + assign decoded_wr_data = cpuif_wr_data; + assign decoded_wr_biten = cpuif_wr_biten; + + //-------------------------------------------------------------------------- + // Field logic + //-------------------------------------------------------------------------- + typedef struct { + struct { + struct { + struct { + logic next; + logic load_next; + } tx_en; + struct { + logic next; + logic load_next; + } rx_en; + struct { + logic next; + logic load_next; + } phy_rstn; + struct { + logic [7:0] next; + logic load_next; + } ifg; + } ctrl; + struct { + struct { + logic next; + logic load_next; + } tx_error_underflow; + struct { + logic next; + logic load_next; + } tx_fifo_overflow; + struct { + logic next; + logic load_next; + } tx_fifo_bad_frame; + struct { + logic next; + logic load_next; + } tx_fifo_good_frame; + struct { + logic next; + logic load_next; + } rx_error_bad_frame; + struct { + logic next; + logic load_next; + } rx_error_bad_fcs; + struct { + logic next; + logic load_next; + } rx_fifo_overflow; + struct { + logic next; + logic load_next; + } rx_fifo_bad_frame; + struct { + logic next; + logic load_next; + } rx_fifo_good_frame; + } stats; + } mac; + } field_combo_t; + field_combo_t field_combo; + + typedef struct { + struct { + struct { + struct { + logic value; + } tx_en; + struct { + logic value; + } rx_en; + struct { + logic value; + } phy_rstn; + struct { + logic [7:0] value; + } ifg; + } ctrl; + struct { + struct { + logic value; + } tx_error_underflow; + struct { + logic value; + } tx_fifo_overflow; + struct { + logic value; + } tx_fifo_bad_frame; + struct { + logic value; + } tx_fifo_good_frame; + struct { + logic value; + } rx_error_bad_frame; + struct { + logic value; + } rx_error_bad_fcs; + struct { + logic value; + } rx_fifo_overflow; + struct { + logic value; + } rx_fifo_bad_frame; + struct { + logic value; + } rx_fifo_good_frame; + } stats; + } mac; + } field_storage_t; + field_storage_t field_storage; + + // Field: mac_regs.mac.ctrl.tx_en + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.ctrl.tx_en.value; + load_next_c = '0; + if(decoded_reg_strb.mac.ctrl && decoded_req_is_wr) begin // SW write + next_c = (field_storage.mac.ctrl.tx_en.value & ~decoded_wr_biten[0:0]) | (decoded_wr_data[0:0] & decoded_wr_biten[0:0]); + load_next_c = '1; + end + field_combo.mac.ctrl.tx_en.next = next_c; + field_combo.mac.ctrl.tx_en.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.ctrl.tx_en.value <= 1'h0; + end else if(field_combo.mac.ctrl.tx_en.load_next) begin + field_storage.mac.ctrl.tx_en.value <= field_combo.mac.ctrl.tx_en.next; + end + end + assign hwif_out.mac.ctrl.tx_en.value = field_storage.mac.ctrl.tx_en.value; + // Field: mac_regs.mac.ctrl.rx_en + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.ctrl.rx_en.value; + load_next_c = '0; + if(decoded_reg_strb.mac.ctrl && decoded_req_is_wr) begin // SW write + next_c = (field_storage.mac.ctrl.rx_en.value & ~decoded_wr_biten[1:1]) | (decoded_wr_data[1:1] & decoded_wr_biten[1:1]); + load_next_c = '1; + end + field_combo.mac.ctrl.rx_en.next = next_c; + field_combo.mac.ctrl.rx_en.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.ctrl.rx_en.value <= 1'h0; + end else if(field_combo.mac.ctrl.rx_en.load_next) begin + field_storage.mac.ctrl.rx_en.value <= field_combo.mac.ctrl.rx_en.next; + end + end + assign hwif_out.mac.ctrl.rx_en.value = field_storage.mac.ctrl.rx_en.value; + // Field: mac_regs.mac.ctrl.phy_rstn + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.ctrl.phy_rstn.value; + load_next_c = '0; + if(decoded_reg_strb.mac.ctrl && decoded_req_is_wr) begin // SW write + next_c = (field_storage.mac.ctrl.phy_rstn.value & ~decoded_wr_biten[2:2]) | (decoded_wr_data[2:2] & decoded_wr_biten[2:2]); + load_next_c = '1; + end + field_combo.mac.ctrl.phy_rstn.next = next_c; + field_combo.mac.ctrl.phy_rstn.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.ctrl.phy_rstn.value <= 1'h1; + end else if(field_combo.mac.ctrl.phy_rstn.load_next) begin + field_storage.mac.ctrl.phy_rstn.value <= field_combo.mac.ctrl.phy_rstn.next; + end + end + assign hwif_out.mac.ctrl.phy_rstn.value = field_storage.mac.ctrl.phy_rstn.value; + // Field: mac_regs.mac.ctrl.ifg + always_comb begin + automatic logic [7:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.ctrl.ifg.value; + load_next_c = '0; + if(decoded_reg_strb.mac.ctrl && decoded_req_is_wr) begin // SW write + next_c = (field_storage.mac.ctrl.ifg.value & ~decoded_wr_biten[15:8]) | (decoded_wr_data[15:8] & decoded_wr_biten[15:8]); + load_next_c = '1; + end + field_combo.mac.ctrl.ifg.next = next_c; + field_combo.mac.ctrl.ifg.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.ctrl.ifg.value <= 8'h0; + end else if(field_combo.mac.ctrl.ifg.load_next) begin + field_storage.mac.ctrl.ifg.value <= field_combo.mac.ctrl.ifg.next; + end + end + assign hwif_out.mac.ctrl.ifg.value = field_storage.mac.ctrl.ifg.value; + // Field: mac_regs.mac.stats.tx_error_underflow + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.stats.tx_error_underflow.value; + load_next_c = '0; + if(decoded_reg_strb.mac.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.mac.stats.tx_error_underflow.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.mac.stats.tx_error_underflow.next = next_c; + field_combo.mac.stats.tx_error_underflow.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.stats.tx_error_underflow.value <= 1'h0; + end else if(field_combo.mac.stats.tx_error_underflow.load_next) begin + field_storage.mac.stats.tx_error_underflow.value <= field_combo.mac.stats.tx_error_underflow.next; + end + end + assign hwif_out.mac.stats.tx_error_underflow.value = field_storage.mac.stats.tx_error_underflow.value; + // Field: mac_regs.mac.stats.tx_fifo_overflow + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.stats.tx_fifo_overflow.value; + load_next_c = '0; + if(decoded_reg_strb.mac.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.mac.stats.tx_fifo_overflow.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.mac.stats.tx_fifo_overflow.next = next_c; + field_combo.mac.stats.tx_fifo_overflow.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.stats.tx_fifo_overflow.value <= 1'h0; + end else if(field_combo.mac.stats.tx_fifo_overflow.load_next) begin + field_storage.mac.stats.tx_fifo_overflow.value <= field_combo.mac.stats.tx_fifo_overflow.next; + end + end + assign hwif_out.mac.stats.tx_fifo_overflow.value = field_storage.mac.stats.tx_fifo_overflow.value; + // Field: mac_regs.mac.stats.tx_fifo_bad_frame + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.stats.tx_fifo_bad_frame.value; + load_next_c = '0; + if(decoded_reg_strb.mac.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.mac.stats.tx_fifo_bad_frame.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.mac.stats.tx_fifo_bad_frame.next = next_c; + field_combo.mac.stats.tx_fifo_bad_frame.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.stats.tx_fifo_bad_frame.value <= 1'h0; + end else if(field_combo.mac.stats.tx_fifo_bad_frame.load_next) begin + field_storage.mac.stats.tx_fifo_bad_frame.value <= field_combo.mac.stats.tx_fifo_bad_frame.next; + end + end + assign hwif_out.mac.stats.tx_fifo_bad_frame.value = field_storage.mac.stats.tx_fifo_bad_frame.value; + // Field: mac_regs.mac.stats.tx_fifo_good_frame + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.stats.tx_fifo_good_frame.value; + load_next_c = '0; + if(decoded_reg_strb.mac.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.mac.stats.tx_fifo_good_frame.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.mac.stats.tx_fifo_good_frame.next = next_c; + field_combo.mac.stats.tx_fifo_good_frame.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.stats.tx_fifo_good_frame.value <= 1'h0; + end else if(field_combo.mac.stats.tx_fifo_good_frame.load_next) begin + field_storage.mac.stats.tx_fifo_good_frame.value <= field_combo.mac.stats.tx_fifo_good_frame.next; + end + end + assign hwif_out.mac.stats.tx_fifo_good_frame.value = field_storage.mac.stats.tx_fifo_good_frame.value; + // Field: mac_regs.mac.stats.rx_error_bad_frame + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.stats.rx_error_bad_frame.value; + load_next_c = '0; + if(decoded_reg_strb.mac.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.mac.stats.rx_error_bad_frame.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.mac.stats.rx_error_bad_frame.next = next_c; + field_combo.mac.stats.rx_error_bad_frame.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.stats.rx_error_bad_frame.value <= 1'h0; + end else if(field_combo.mac.stats.rx_error_bad_frame.load_next) begin + field_storage.mac.stats.rx_error_bad_frame.value <= field_combo.mac.stats.rx_error_bad_frame.next; + end + end + assign hwif_out.mac.stats.rx_error_bad_frame.value = field_storage.mac.stats.rx_error_bad_frame.value; + // Field: mac_regs.mac.stats.rx_error_bad_fcs + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.stats.rx_error_bad_fcs.value; + load_next_c = '0; + if(decoded_reg_strb.mac.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.mac.stats.rx_error_bad_fcs.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.mac.stats.rx_error_bad_fcs.next = next_c; + field_combo.mac.stats.rx_error_bad_fcs.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.stats.rx_error_bad_fcs.value <= 1'h0; + end else if(field_combo.mac.stats.rx_error_bad_fcs.load_next) begin + field_storage.mac.stats.rx_error_bad_fcs.value <= field_combo.mac.stats.rx_error_bad_fcs.next; + end + end + assign hwif_out.mac.stats.rx_error_bad_fcs.value = field_storage.mac.stats.rx_error_bad_fcs.value; + // Field: mac_regs.mac.stats.rx_fifo_overflow + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.stats.rx_fifo_overflow.value; + load_next_c = '0; + if(decoded_reg_strb.mac.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.mac.stats.rx_fifo_overflow.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.mac.stats.rx_fifo_overflow.next = next_c; + field_combo.mac.stats.rx_fifo_overflow.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.stats.rx_fifo_overflow.value <= 1'h0; + end else if(field_combo.mac.stats.rx_fifo_overflow.load_next) begin + field_storage.mac.stats.rx_fifo_overflow.value <= field_combo.mac.stats.rx_fifo_overflow.next; + end + end + assign hwif_out.mac.stats.rx_fifo_overflow.value = field_storage.mac.stats.rx_fifo_overflow.value; + // Field: mac_regs.mac.stats.rx_fifo_bad_frame + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.stats.rx_fifo_bad_frame.value; + load_next_c = '0; + if(decoded_reg_strb.mac.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.mac.stats.rx_fifo_bad_frame.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.mac.stats.rx_fifo_bad_frame.next = next_c; + field_combo.mac.stats.rx_fifo_bad_frame.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.stats.rx_fifo_bad_frame.value <= 1'h0; + end else if(field_combo.mac.stats.rx_fifo_bad_frame.load_next) begin + field_storage.mac.stats.rx_fifo_bad_frame.value <= field_combo.mac.stats.rx_fifo_bad_frame.next; + end + end + assign hwif_out.mac.stats.rx_fifo_bad_frame.value = field_storage.mac.stats.rx_fifo_bad_frame.value; + // Field: mac_regs.mac.stats.rx_fifo_good_frame + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.mac.stats.rx_fifo_good_frame.value; + load_next_c = '0; + if(decoded_reg_strb.mac.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.mac.stats.rx_fifo_good_frame.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.mac.stats.rx_fifo_good_frame.next = next_c; + field_combo.mac.stats.rx_fifo_good_frame.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.mac.stats.rx_fifo_good_frame.value <= 1'h0; + end else if(field_combo.mac.stats.rx_fifo_good_frame.load_next) begin + field_storage.mac.stats.rx_fifo_good_frame.value <= field_combo.mac.stats.rx_fifo_good_frame.next; + end + end + assign hwif_out.mac.stats.rx_fifo_good_frame.value = field_storage.mac.stats.rx_fifo_good_frame.value; + + //-------------------------------------------------------------------------- + // Write response + //-------------------------------------------------------------------------- + assign cpuif_wr_ack = decoded_req & decoded_req_is_wr; + // Writes are always granted with no error response + assign cpuif_wr_err = '0; + + //-------------------------------------------------------------------------- + // Readback + //-------------------------------------------------------------------------- + + logic readback_err; + logic readback_done; + logic [31:0] readback_data; + + // Assign readback values to a flattened array + logic [31:0] readback_array[2]; + assign readback_array[0][0:0] = (decoded_reg_strb.mac.ctrl && !decoded_req_is_wr) ? field_storage.mac.ctrl.tx_en.value : '0; + assign readback_array[0][1:1] = (decoded_reg_strb.mac.ctrl && !decoded_req_is_wr) ? field_storage.mac.ctrl.rx_en.value : '0; + assign readback_array[0][2:2] = (decoded_reg_strb.mac.ctrl && !decoded_req_is_wr) ? field_storage.mac.ctrl.phy_rstn.value : '0; + assign readback_array[0][7:3] = '0; + assign readback_array[0][15:8] = (decoded_reg_strb.mac.ctrl && !decoded_req_is_wr) ? field_storage.mac.ctrl.ifg.value : '0; + assign readback_array[0][31:16] = '0; + assign readback_array[1][0:0] = (decoded_reg_strb.mac.stats && !decoded_req_is_wr) ? field_storage.mac.stats.tx_error_underflow.value : '0; + assign readback_array[1][1:1] = (decoded_reg_strb.mac.stats && !decoded_req_is_wr) ? field_storage.mac.stats.tx_fifo_overflow.value : '0; + assign readback_array[1][2:2] = (decoded_reg_strb.mac.stats && !decoded_req_is_wr) ? field_storage.mac.stats.tx_fifo_bad_frame.value : '0; + assign readback_array[1][3:3] = (decoded_reg_strb.mac.stats && !decoded_req_is_wr) ? field_storage.mac.stats.tx_fifo_good_frame.value : '0; + assign readback_array[1][4:4] = (decoded_reg_strb.mac.stats && !decoded_req_is_wr) ? field_storage.mac.stats.rx_error_bad_frame.value : '0; + assign readback_array[1][5:5] = (decoded_reg_strb.mac.stats && !decoded_req_is_wr) ? field_storage.mac.stats.rx_error_bad_fcs.value : '0; + assign readback_array[1][6:6] = (decoded_reg_strb.mac.stats && !decoded_req_is_wr) ? field_storage.mac.stats.rx_fifo_overflow.value : '0; + assign readback_array[1][7:7] = (decoded_reg_strb.mac.stats && !decoded_req_is_wr) ? field_storage.mac.stats.rx_fifo_bad_frame.value : '0; + assign readback_array[1][8:8] = (decoded_reg_strb.mac.stats && !decoded_req_is_wr) ? field_storage.mac.stats.rx_fifo_good_frame.value : '0; + assign readback_array[1][31:9] = '0; + + // Reduce the array + always_comb begin + automatic logic [31:0] readback_data_var; + readback_done = decoded_req & ~decoded_req_is_wr; + readback_err = '0; + readback_data_var = '0; + for(int i=0; i<2; i++) readback_data_var |= readback_array[i]; + readback_data = readback_data_var; + end + + assign cpuif_rd_ack = readback_done; + assign cpuif_rd_data = readback_data; + assign cpuif_rd_err = readback_err; +endmodule diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_regs_pkg.sv b/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_regs_pkg.sv new file mode 100644 index 0000000..d18298b --- /dev/null +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_regs_pkg.sv @@ -0,0 +1,144 @@ +// Generated by PeakRDL-regblock - A free and open-source SystemVerilog generator +// https://github.com/SystemRDL/PeakRDL-regblock + +package mac_regs_pkg; + + localparam MAC_REGS_DATA_WIDTH = 32; + localparam MAC_REGS_MIN_ADDR_WIDTH = 3; + + typedef struct { + logic hwset; + } mac_t__stats__tx_error_underflow__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__tx_fifo_overflow__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__tx_fifo_bad_frame__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__tx_fifo_good_frame__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__rx_error_bad_frame__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__rx_error_bad_fcs__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__rx_fifo_overflow__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__rx_fifo_bad_frame__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__rx_fifo_good_frame__in_t; + + typedef struct { + mac_t__stats__tx_error_underflow__in_t tx_error_underflow; + mac_t__stats__tx_fifo_overflow__in_t tx_fifo_overflow; + mac_t__stats__tx_fifo_bad_frame__in_t tx_fifo_bad_frame; + mac_t__stats__tx_fifo_good_frame__in_t tx_fifo_good_frame; + mac_t__stats__rx_error_bad_frame__in_t rx_error_bad_frame; + mac_t__stats__rx_error_bad_fcs__in_t rx_error_bad_fcs; + mac_t__stats__rx_fifo_overflow__in_t rx_fifo_overflow; + mac_t__stats__rx_fifo_bad_frame__in_t rx_fifo_bad_frame; + mac_t__stats__rx_fifo_good_frame__in_t rx_fifo_good_frame; + } mac_t__stats__in_t; + + typedef struct { + mac_t__stats__in_t stats; + } mac_t__in_t; + + typedef struct { + mac_t__in_t mac; + } mac_regs__in_t; + + typedef struct { + logic value; + } mac_t__ctrl__tx_en__out_t; + + typedef struct { + logic value; + } mac_t__ctrl__rx_en__out_t; + + typedef struct { + logic value; + } mac_t__ctrl__phy_rstn__out_t; + + typedef struct { + logic [7:0] value; + } mac_t__ctrl__ifg__out_t; + + typedef struct { + mac_t__ctrl__tx_en__out_t tx_en; + mac_t__ctrl__rx_en__out_t rx_en; + mac_t__ctrl__phy_rstn__out_t phy_rstn; + mac_t__ctrl__ifg__out_t ifg; + } mac_t__ctrl__out_t; + + typedef struct { + logic value; + } mac_t__stats__tx_error_underflow__out_t; + + typedef struct { + logic value; + } mac_t__stats__tx_fifo_overflow__out_t; + + typedef struct { + logic value; + } mac_t__stats__tx_fifo_bad_frame__out_t; + + typedef struct { + logic value; + } mac_t__stats__tx_fifo_good_frame__out_t; + + typedef struct { + logic value; + } mac_t__stats__rx_error_bad_frame__out_t; + + typedef struct { + logic value; + } mac_t__stats__rx_error_bad_fcs__out_t; + + typedef struct { + logic value; + } mac_t__stats__rx_fifo_overflow__out_t; + + typedef struct { + logic value; + } mac_t__stats__rx_fifo_bad_frame__out_t; + + typedef struct { + logic value; + } mac_t__stats__rx_fifo_good_frame__out_t; + + typedef struct { + mac_t__stats__tx_error_underflow__out_t tx_error_underflow; + mac_t__stats__tx_fifo_overflow__out_t tx_fifo_overflow; + mac_t__stats__tx_fifo_bad_frame__out_t tx_fifo_bad_frame; + mac_t__stats__tx_fifo_good_frame__out_t tx_fifo_good_frame; + mac_t__stats__rx_error_bad_frame__out_t rx_error_bad_frame; + mac_t__stats__rx_error_bad_fcs__out_t rx_error_bad_fcs; + mac_t__stats__rx_fifo_overflow__out_t rx_fifo_overflow; + mac_t__stats__rx_fifo_bad_frame__out_t rx_fifo_bad_frame; + mac_t__stats__rx_fifo_good_frame__out_t rx_fifo_good_frame; + } mac_t__stats__out_t; + + typedef struct { + mac_t__ctrl__out_t ctrl; + mac_t__stats__out_t stats; + } mac_t__out_t; + + typedef struct { + mac_t__out_t mac; + } mac_regs__out_t; +endpackage diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_t.sv b/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_t.sv new file mode 100644 index 0000000..8c6b76e --- /dev/null +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_t.sv @@ -0,0 +1,547 @@ +// Generated by PeakRDL-regblock - A free and open-source SystemVerilog generator +// https://github.com/SystemRDL/PeakRDL-regblock + +module mac_t ( + input wire clk, + input wire rst, + + input wire s_cpuif_req, + input wire s_cpuif_req_is_wr, + input wire [2:0] s_cpuif_addr, + input wire [31:0] s_cpuif_wr_data, + input wire [31:0] s_cpuif_wr_biten, + output wire s_cpuif_req_stall_wr, + output wire s_cpuif_req_stall_rd, + output wire s_cpuif_rd_ack, + output wire s_cpuif_rd_err, + output wire [31:0] s_cpuif_rd_data, + output wire s_cpuif_wr_ack, + output wire s_cpuif_wr_err, + + input mac_t_pkg::mac_t__in_t hwif_in, + output mac_t_pkg::mac_t__out_t hwif_out + ); + + //-------------------------------------------------------------------------- + // CPU Bus interface logic + //-------------------------------------------------------------------------- + logic cpuif_req; + logic cpuif_req_is_wr; + logic [2:0] cpuif_addr; + logic [31:0] cpuif_wr_data; + logic [31:0] cpuif_wr_biten; + logic cpuif_req_stall_wr; + logic cpuif_req_stall_rd; + + logic cpuif_rd_ack; + logic cpuif_rd_err; + logic [31:0] cpuif_rd_data; + + logic cpuif_wr_ack; + logic cpuif_wr_err; + + assign cpuif_req = s_cpuif_req; + assign cpuif_req_is_wr = s_cpuif_req_is_wr; + assign cpuif_addr = s_cpuif_addr; + assign cpuif_wr_data = s_cpuif_wr_data; + assign cpuif_wr_biten = s_cpuif_wr_biten; + assign s_cpuif_req_stall_wr = cpuif_req_stall_wr; + assign s_cpuif_req_stall_rd = cpuif_req_stall_rd; + assign s_cpuif_rd_ack = cpuif_rd_ack; + assign s_cpuif_rd_err = cpuif_rd_err; + assign s_cpuif_rd_data = cpuif_rd_data; + assign s_cpuif_wr_ack = cpuif_wr_ack; + assign s_cpuif_wr_err = cpuif_wr_err; + + logic cpuif_req_masked; + + // Read & write latencies are balanced. Stalls not required + assign cpuif_req_stall_rd = '0; + assign cpuif_req_stall_wr = '0; + assign cpuif_req_masked = cpuif_req + & !(!cpuif_req_is_wr & cpuif_req_stall_rd) + & !(cpuif_req_is_wr & cpuif_req_stall_wr); + + //-------------------------------------------------------------------------- + // Address Decode + //-------------------------------------------------------------------------- + typedef struct { + logic ctrl; + logic stats; + } decoded_reg_strb_t; + decoded_reg_strb_t decoded_reg_strb; + logic decoded_req; + logic decoded_req_is_wr; + logic [31:0] decoded_wr_data; + logic [31:0] decoded_wr_biten; + + always_comb begin + decoded_reg_strb.ctrl = cpuif_req_masked & (cpuif_addr == 3'h0); + decoded_reg_strb.stats = cpuif_req_masked & (cpuif_addr == 3'h4); + end + + // Pass down signals to next stage + assign decoded_req = cpuif_req_masked; + assign decoded_req_is_wr = cpuif_req_is_wr; + assign decoded_wr_data = cpuif_wr_data; + assign decoded_wr_biten = cpuif_wr_biten; + + //-------------------------------------------------------------------------- + // Field logic + //-------------------------------------------------------------------------- + typedef struct { + struct { + struct { + logic next; + logic load_next; + } tx_en; + struct { + logic next; + logic load_next; + } rx_en; + struct { + logic next; + logic load_next; + } phy_rstn; + struct { + logic [7:0] next; + logic load_next; + } ifg; + } ctrl; + struct { + struct { + logic next; + logic load_next; + } tx_error_underflow; + struct { + logic next; + logic load_next; + } tx_fifo_overflow; + struct { + logic next; + logic load_next; + } tx_fifo_bad_frame; + struct { + logic next; + logic load_next; + } tx_fifo_good_frame; + struct { + logic next; + logic load_next; + } rx_error_bad_frame; + struct { + logic next; + logic load_next; + } rx_error_bad_fcs; + struct { + logic next; + logic load_next; + } rx_fifo_overflow; + struct { + logic next; + logic load_next; + } rx_fifo_bad_frame; + struct { + logic next; + logic load_next; + } rx_fifo_good_frame; + } stats; + } field_combo_t; + field_combo_t field_combo; + + typedef struct { + struct { + struct { + logic value; + } tx_en; + struct { + logic value; + } rx_en; + struct { + logic value; + } phy_rstn; + struct { + logic [7:0] value; + } ifg; + } ctrl; + struct { + struct { + logic value; + } tx_error_underflow; + struct { + logic value; + } tx_fifo_overflow; + struct { + logic value; + } tx_fifo_bad_frame; + struct { + logic value; + } tx_fifo_good_frame; + struct { + logic value; + } rx_error_bad_frame; + struct { + logic value; + } rx_error_bad_fcs; + struct { + logic value; + } rx_fifo_overflow; + struct { + logic value; + } rx_fifo_bad_frame; + struct { + logic value; + } rx_fifo_good_frame; + } stats; + } field_storage_t; + field_storage_t field_storage; + + // Field: mac_t.ctrl.tx_en + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.ctrl.tx_en.value; + load_next_c = '0; + if(decoded_reg_strb.ctrl && decoded_req_is_wr) begin // SW write + next_c = (field_storage.ctrl.tx_en.value & ~decoded_wr_biten[0:0]) | (decoded_wr_data[0:0] & decoded_wr_biten[0:0]); + load_next_c = '1; + end + field_combo.ctrl.tx_en.next = next_c; + field_combo.ctrl.tx_en.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.ctrl.tx_en.value <= 1'h0; + end else if(field_combo.ctrl.tx_en.load_next) begin + field_storage.ctrl.tx_en.value <= field_combo.ctrl.tx_en.next; + end + end + assign hwif_out.ctrl.tx_en.value = field_storage.ctrl.tx_en.value; + // Field: mac_t.ctrl.rx_en + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.ctrl.rx_en.value; + load_next_c = '0; + if(decoded_reg_strb.ctrl && decoded_req_is_wr) begin // SW write + next_c = (field_storage.ctrl.rx_en.value & ~decoded_wr_biten[1:1]) | (decoded_wr_data[1:1] & decoded_wr_biten[1:1]); + load_next_c = '1; + end + field_combo.ctrl.rx_en.next = next_c; + field_combo.ctrl.rx_en.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.ctrl.rx_en.value <= 1'h0; + end else if(field_combo.ctrl.rx_en.load_next) begin + field_storage.ctrl.rx_en.value <= field_combo.ctrl.rx_en.next; + end + end + assign hwif_out.ctrl.rx_en.value = field_storage.ctrl.rx_en.value; + // Field: mac_t.ctrl.phy_rstn + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.ctrl.phy_rstn.value; + load_next_c = '0; + if(decoded_reg_strb.ctrl && decoded_req_is_wr) begin // SW write + next_c = (field_storage.ctrl.phy_rstn.value & ~decoded_wr_biten[2:2]) | (decoded_wr_data[2:2] & decoded_wr_biten[2:2]); + load_next_c = '1; + end + field_combo.ctrl.phy_rstn.next = next_c; + field_combo.ctrl.phy_rstn.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.ctrl.phy_rstn.value <= 1'h1; + end else if(field_combo.ctrl.phy_rstn.load_next) begin + field_storage.ctrl.phy_rstn.value <= field_combo.ctrl.phy_rstn.next; + end + end + assign hwif_out.ctrl.phy_rstn.value = field_storage.ctrl.phy_rstn.value; + // Field: mac_t.ctrl.ifg + always_comb begin + automatic logic [7:0] next_c; + automatic logic load_next_c; + next_c = field_storage.ctrl.ifg.value; + load_next_c = '0; + if(decoded_reg_strb.ctrl && decoded_req_is_wr) begin // SW write + next_c = (field_storage.ctrl.ifg.value & ~decoded_wr_biten[15:8]) | (decoded_wr_data[15:8] & decoded_wr_biten[15:8]); + load_next_c = '1; + end + field_combo.ctrl.ifg.next = next_c; + field_combo.ctrl.ifg.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.ctrl.ifg.value <= 8'h0; + end else if(field_combo.ctrl.ifg.load_next) begin + field_storage.ctrl.ifg.value <= field_combo.ctrl.ifg.next; + end + end + assign hwif_out.ctrl.ifg.value = field_storage.ctrl.ifg.value; + // Field: mac_t.stats.tx_error_underflow + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.stats.tx_error_underflow.value; + load_next_c = '0; + if(decoded_reg_strb.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.stats.tx_error_underflow.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.stats.tx_error_underflow.next = next_c; + field_combo.stats.tx_error_underflow.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.stats.tx_error_underflow.value <= 1'h0; + end else if(field_combo.stats.tx_error_underflow.load_next) begin + field_storage.stats.tx_error_underflow.value <= field_combo.stats.tx_error_underflow.next; + end + end + assign hwif_out.stats.tx_error_underflow.value = field_storage.stats.tx_error_underflow.value; + // Field: mac_t.stats.tx_fifo_overflow + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.stats.tx_fifo_overflow.value; + load_next_c = '0; + if(decoded_reg_strb.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.stats.tx_fifo_overflow.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.stats.tx_fifo_overflow.next = next_c; + field_combo.stats.tx_fifo_overflow.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.stats.tx_fifo_overflow.value <= 1'h0; + end else if(field_combo.stats.tx_fifo_overflow.load_next) begin + field_storage.stats.tx_fifo_overflow.value <= field_combo.stats.tx_fifo_overflow.next; + end + end + assign hwif_out.stats.tx_fifo_overflow.value = field_storage.stats.tx_fifo_overflow.value; + // Field: mac_t.stats.tx_fifo_bad_frame + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.stats.tx_fifo_bad_frame.value; + load_next_c = '0; + if(decoded_reg_strb.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.stats.tx_fifo_bad_frame.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.stats.tx_fifo_bad_frame.next = next_c; + field_combo.stats.tx_fifo_bad_frame.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.stats.tx_fifo_bad_frame.value <= 1'h0; + end else if(field_combo.stats.tx_fifo_bad_frame.load_next) begin + field_storage.stats.tx_fifo_bad_frame.value <= field_combo.stats.tx_fifo_bad_frame.next; + end + end + assign hwif_out.stats.tx_fifo_bad_frame.value = field_storage.stats.tx_fifo_bad_frame.value; + // Field: mac_t.stats.tx_fifo_good_frame + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.stats.tx_fifo_good_frame.value; + load_next_c = '0; + if(decoded_reg_strb.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.stats.tx_fifo_good_frame.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.stats.tx_fifo_good_frame.next = next_c; + field_combo.stats.tx_fifo_good_frame.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.stats.tx_fifo_good_frame.value <= 1'h0; + end else if(field_combo.stats.tx_fifo_good_frame.load_next) begin + field_storage.stats.tx_fifo_good_frame.value <= field_combo.stats.tx_fifo_good_frame.next; + end + end + assign hwif_out.stats.tx_fifo_good_frame.value = field_storage.stats.tx_fifo_good_frame.value; + // Field: mac_t.stats.rx_error_bad_frame + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.stats.rx_error_bad_frame.value; + load_next_c = '0; + if(decoded_reg_strb.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.stats.rx_error_bad_frame.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.stats.rx_error_bad_frame.next = next_c; + field_combo.stats.rx_error_bad_frame.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.stats.rx_error_bad_frame.value <= 1'h0; + end else if(field_combo.stats.rx_error_bad_frame.load_next) begin + field_storage.stats.rx_error_bad_frame.value <= field_combo.stats.rx_error_bad_frame.next; + end + end + assign hwif_out.stats.rx_error_bad_frame.value = field_storage.stats.rx_error_bad_frame.value; + // Field: mac_t.stats.rx_error_bad_fcs + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.stats.rx_error_bad_fcs.value; + load_next_c = '0; + if(decoded_reg_strb.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.stats.rx_error_bad_fcs.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.stats.rx_error_bad_fcs.next = next_c; + field_combo.stats.rx_error_bad_fcs.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.stats.rx_error_bad_fcs.value <= 1'h0; + end else if(field_combo.stats.rx_error_bad_fcs.load_next) begin + field_storage.stats.rx_error_bad_fcs.value <= field_combo.stats.rx_error_bad_fcs.next; + end + end + assign hwif_out.stats.rx_error_bad_fcs.value = field_storage.stats.rx_error_bad_fcs.value; + // Field: mac_t.stats.rx_fifo_overflow + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.stats.rx_fifo_overflow.value; + load_next_c = '0; + if(decoded_reg_strb.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.stats.rx_fifo_overflow.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.stats.rx_fifo_overflow.next = next_c; + field_combo.stats.rx_fifo_overflow.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.stats.rx_fifo_overflow.value <= 1'h0; + end else if(field_combo.stats.rx_fifo_overflow.load_next) begin + field_storage.stats.rx_fifo_overflow.value <= field_combo.stats.rx_fifo_overflow.next; + end + end + assign hwif_out.stats.rx_fifo_overflow.value = field_storage.stats.rx_fifo_overflow.value; + // Field: mac_t.stats.rx_fifo_bad_frame + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.stats.rx_fifo_bad_frame.value; + load_next_c = '0; + if(decoded_reg_strb.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.stats.rx_fifo_bad_frame.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.stats.rx_fifo_bad_frame.next = next_c; + field_combo.stats.rx_fifo_bad_frame.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.stats.rx_fifo_bad_frame.value <= 1'h0; + end else if(field_combo.stats.rx_fifo_bad_frame.load_next) begin + field_storage.stats.rx_fifo_bad_frame.value <= field_combo.stats.rx_fifo_bad_frame.next; + end + end + assign hwif_out.stats.rx_fifo_bad_frame.value = field_storage.stats.rx_fifo_bad_frame.value; + // Field: mac_t.stats.rx_fifo_good_frame + always_comb begin + automatic logic [0:0] next_c; + automatic logic load_next_c; + next_c = field_storage.stats.rx_fifo_good_frame.value; + load_next_c = '0; + if(decoded_reg_strb.stats && !decoded_req_is_wr) begin // SW clear on read + next_c = '0; + load_next_c = '1; + end else if(hwif_in.stats.rx_fifo_good_frame.hwset) begin // HW Set + next_c = '1; + load_next_c = '1; + end + field_combo.stats.rx_fifo_good_frame.next = next_c; + field_combo.stats.rx_fifo_good_frame.load_next = load_next_c; + end + always_ff @(posedge clk) begin + if(rst) begin + field_storage.stats.rx_fifo_good_frame.value <= 1'h0; + end else if(field_combo.stats.rx_fifo_good_frame.load_next) begin + field_storage.stats.rx_fifo_good_frame.value <= field_combo.stats.rx_fifo_good_frame.next; + end + end + assign hwif_out.stats.rx_fifo_good_frame.value = field_storage.stats.rx_fifo_good_frame.value; + + //-------------------------------------------------------------------------- + // Write response + //-------------------------------------------------------------------------- + assign cpuif_wr_ack = decoded_req & decoded_req_is_wr; + // Writes are always granted with no error response + assign cpuif_wr_err = '0; + + //-------------------------------------------------------------------------- + // Readback + //-------------------------------------------------------------------------- + + logic readback_err; + logic readback_done; + logic [31:0] readback_data; + + // Assign readback values to a flattened array + logic [31:0] readback_array[2]; + assign readback_array[0][0:0] = (decoded_reg_strb.ctrl && !decoded_req_is_wr) ? field_storage.ctrl.tx_en.value : '0; + assign readback_array[0][1:1] = (decoded_reg_strb.ctrl && !decoded_req_is_wr) ? field_storage.ctrl.rx_en.value : '0; + assign readback_array[0][2:2] = (decoded_reg_strb.ctrl && !decoded_req_is_wr) ? field_storage.ctrl.phy_rstn.value : '0; + assign readback_array[0][7:3] = '0; + assign readback_array[0][15:8] = (decoded_reg_strb.ctrl && !decoded_req_is_wr) ? field_storage.ctrl.ifg.value : '0; + assign readback_array[0][31:16] = '0; + assign readback_array[1][0:0] = (decoded_reg_strb.stats && !decoded_req_is_wr) ? field_storage.stats.tx_error_underflow.value : '0; + assign readback_array[1][1:1] = (decoded_reg_strb.stats && !decoded_req_is_wr) ? field_storage.stats.tx_fifo_overflow.value : '0; + assign readback_array[1][2:2] = (decoded_reg_strb.stats && !decoded_req_is_wr) ? field_storage.stats.tx_fifo_bad_frame.value : '0; + assign readback_array[1][3:3] = (decoded_reg_strb.stats && !decoded_req_is_wr) ? field_storage.stats.tx_fifo_good_frame.value : '0; + assign readback_array[1][4:4] = (decoded_reg_strb.stats && !decoded_req_is_wr) ? field_storage.stats.rx_error_bad_frame.value : '0; + assign readback_array[1][5:5] = (decoded_reg_strb.stats && !decoded_req_is_wr) ? field_storage.stats.rx_error_bad_fcs.value : '0; + assign readback_array[1][6:6] = (decoded_reg_strb.stats && !decoded_req_is_wr) ? field_storage.stats.rx_fifo_overflow.value : '0; + assign readback_array[1][7:7] = (decoded_reg_strb.stats && !decoded_req_is_wr) ? field_storage.stats.rx_fifo_bad_frame.value : '0; + assign readback_array[1][8:8] = (decoded_reg_strb.stats && !decoded_req_is_wr) ? field_storage.stats.rx_fifo_good_frame.value : '0; + assign readback_array[1][31:9] = '0; + + // Reduce the array + always_comb begin + automatic logic [31:0] readback_data_var; + readback_done = decoded_req & ~decoded_req_is_wr; + readback_err = '0; + readback_data_var = '0; + for(int i=0; i<2; i++) readback_data_var |= readback_array[i]; + readback_data = readback_data_var; + end + + assign cpuif_rd_ack = readback_done; + assign cpuif_rd_data = readback_data; + assign cpuif_rd_err = readback_err; +endmodule diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_t_pkg.sv b/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_t_pkg.sv new file mode 100644 index 0000000..82f6301 --- /dev/null +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/mac_t_pkg.sv @@ -0,0 +1,136 @@ +// Generated by PeakRDL-regblock - A free and open-source SystemVerilog generator +// https://github.com/SystemRDL/PeakRDL-regblock + +package mac_t_pkg; + + localparam MAC_T_DATA_WIDTH = 32; + localparam MAC_T_MIN_ADDR_WIDTH = 3; + + typedef struct { + logic hwset; + } mac_t__stats__tx_error_underflow__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__tx_fifo_overflow__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__tx_fifo_bad_frame__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__tx_fifo_good_frame__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__rx_error_bad_frame__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__rx_error_bad_fcs__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__rx_fifo_overflow__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__rx_fifo_bad_frame__in_t; + + typedef struct { + logic hwset; + } mac_t__stats__rx_fifo_good_frame__in_t; + + typedef struct { + mac_t__stats__tx_error_underflow__in_t tx_error_underflow; + mac_t__stats__tx_fifo_overflow__in_t tx_fifo_overflow; + mac_t__stats__tx_fifo_bad_frame__in_t tx_fifo_bad_frame; + mac_t__stats__tx_fifo_good_frame__in_t tx_fifo_good_frame; + mac_t__stats__rx_error_bad_frame__in_t rx_error_bad_frame; + mac_t__stats__rx_error_bad_fcs__in_t rx_error_bad_fcs; + mac_t__stats__rx_fifo_overflow__in_t rx_fifo_overflow; + mac_t__stats__rx_fifo_bad_frame__in_t rx_fifo_bad_frame; + mac_t__stats__rx_fifo_good_frame__in_t rx_fifo_good_frame; + } mac_t__stats__in_t; + + typedef struct { + mac_t__stats__in_t stats; + } mac_t__in_t; + + typedef struct { + logic value; + } mac_t__ctrl__tx_en__out_t; + + typedef struct { + logic value; + } mac_t__ctrl__rx_en__out_t; + + typedef struct { + logic value; + } mac_t__ctrl__phy_rstn__out_t; + + typedef struct { + logic [7:0] value; + } mac_t__ctrl__ifg__out_t; + + typedef struct { + mac_t__ctrl__tx_en__out_t tx_en; + mac_t__ctrl__rx_en__out_t rx_en; + mac_t__ctrl__phy_rstn__out_t phy_rstn; + mac_t__ctrl__ifg__out_t ifg; + } mac_t__ctrl__out_t; + + typedef struct { + logic value; + } mac_t__stats__tx_error_underflow__out_t; + + typedef struct { + logic value; + } mac_t__stats__tx_fifo_overflow__out_t; + + typedef struct { + logic value; + } mac_t__stats__tx_fifo_bad_frame__out_t; + + typedef struct { + logic value; + } mac_t__stats__tx_fifo_good_frame__out_t; + + typedef struct { + logic value; + } mac_t__stats__rx_error_bad_frame__out_t; + + typedef struct { + logic value; + } mac_t__stats__rx_error_bad_fcs__out_t; + + typedef struct { + logic value; + } mac_t__stats__rx_fifo_overflow__out_t; + + typedef struct { + logic value; + } mac_t__stats__rx_fifo_bad_frame__out_t; + + typedef struct { + logic value; + } mac_t__stats__rx_fifo_good_frame__out_t; + + typedef struct { + mac_t__stats__tx_error_underflow__out_t tx_error_underflow; + mac_t__stats__tx_fifo_overflow__out_t tx_fifo_overflow; + mac_t__stats__tx_fifo_bad_frame__out_t tx_fifo_bad_frame; + mac_t__stats__tx_fifo_good_frame__out_t tx_fifo_good_frame; + mac_t__stats__rx_error_bad_frame__out_t rx_error_bad_frame; + mac_t__stats__rx_error_bad_fcs__out_t rx_error_bad_fcs; + mac_t__stats__rx_fifo_overflow__out_t rx_fifo_overflow; + mac_t__stats__rx_fifo_bad_frame__out_t rx_fifo_bad_frame; + mac_t__stats__rx_fifo_good_frame__out_t rx_fifo_good_frame; + } mac_t__stats__out_t; + + typedef struct { + mac_t__ctrl__out_t ctrl; + mac_t__stats__out_t stats; + } mac_t__out_t; +endpackage diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/ntw_top_regfile.sv b/hw/super6502_fpga/src/sub/network_processor/src/regs/ntw_top_regfile.sv new file mode 100644 index 0000000..b4eaf50 --- /dev/null +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/ntw_top_regfile.sv @@ -0,0 +1,350 @@ +// Generated by PeakRDL-regblock - A free and open-source SystemVerilog generator +// https://github.com/SystemRDL/PeakRDL-regblock + +module ntw_top_regfile ( + input wire clk, + input wire rst, + + output logic s_axil_awready, + input wire s_axil_awvalid, + input wire [9:0] s_axil_awaddr, + input wire [2:0] s_axil_awprot, + output logic s_axil_wready, + input wire s_axil_wvalid, + input wire [31:0] s_axil_wdata, + input wire [3:0]s_axil_wstrb, + input wire s_axil_bready, + output logic s_axil_bvalid, + output logic [1:0] s_axil_bresp, + output logic s_axil_arready, + input wire s_axil_arvalid, + input wire [9:0] s_axil_araddr, + input wire [2:0] s_axil_arprot, + input wire s_axil_rready, + output logic s_axil_rvalid, + output logic [31:0] s_axil_rdata, + output logic [1:0] s_axil_rresp, + + input ntw_top_regfile_pkg::ntw_top_regfile__in_t hwif_in, + output ntw_top_regfile_pkg::ntw_top_regfile__out_t hwif_out + ); + + //-------------------------------------------------------------------------- + // CPU Bus interface logic + //-------------------------------------------------------------------------- + logic cpuif_req; + logic cpuif_req_is_wr; + logic [9:0] cpuif_addr; + logic [31:0] cpuif_wr_data; + logic [31:0] cpuif_wr_biten; + logic cpuif_req_stall_wr; + logic cpuif_req_stall_rd; + + logic cpuif_rd_ack; + logic cpuif_rd_err; + logic [31:0] cpuif_rd_data; + + logic cpuif_wr_ack; + logic cpuif_wr_err; + + // Max Outstanding Transactions: 2 + logic [1:0] axil_n_in_flight; + logic axil_prev_was_rd; + logic axil_arvalid; + logic [9:0] axil_araddr; + logic axil_ar_accept; + logic axil_awvalid; + logic [9:0] axil_awaddr; + logic axil_wvalid; + logic [31:0] axil_wdata; + logic [3:0] axil_wstrb; + logic axil_aw_accept; + logic axil_resp_acked; + + // Transaction request acceptance + always_ff @(posedge clk) begin + if(rst) begin + axil_prev_was_rd <= '0; + axil_arvalid <= '0; + axil_araddr <= '0; + axil_awvalid <= '0; + axil_awaddr <= '0; + axil_wvalid <= '0; + axil_wdata <= '0; + axil_wstrb <= '0; + axil_n_in_flight <= '0; + end else begin + // AR* acceptance register + if(axil_ar_accept) begin + axil_prev_was_rd <= '1; + axil_arvalid <= '0; + end + if(s_axil_arvalid && s_axil_arready) begin + axil_arvalid <= '1; + axil_araddr <= s_axil_araddr; + end + + // AW* & W* acceptance registers + if(axil_aw_accept) begin + axil_prev_was_rd <= '0; + axil_awvalid <= '0; + axil_wvalid <= '0; + end + if(s_axil_awvalid && s_axil_awready) begin + axil_awvalid <= '1; + axil_awaddr <= s_axil_awaddr; + end + if(s_axil_wvalid && s_axil_wready) begin + axil_wvalid <= '1; + axil_wdata <= s_axil_wdata; + axil_wstrb <= s_axil_wstrb; + end + + // Keep track of in-flight transactions + if((axil_ar_accept || axil_aw_accept) && !axil_resp_acked) begin + axil_n_in_flight <= axil_n_in_flight + 1'b1; + end else if(!(axil_ar_accept || axil_aw_accept) && axil_resp_acked) begin + axil_n_in_flight <= axil_n_in_flight - 1'b1; + end + end + end + + always_comb begin + s_axil_arready = (!axil_arvalid || axil_ar_accept); + s_axil_awready = (!axil_awvalid || axil_aw_accept); + s_axil_wready = (!axil_wvalid || axil_aw_accept); + end + + // Request dispatch + always_comb begin + cpuif_wr_data = axil_wdata; + for(int i=0; i<4; i++) begin + cpuif_wr_biten[i*8 +: 8] = {8{axil_wstrb[i]}}; + end + cpuif_req = '0; + cpuif_req_is_wr = '0; + cpuif_addr = '0; + axil_ar_accept = '0; + axil_aw_accept = '0; + + if(axil_n_in_flight < 2'd2) begin + // Can safely issue more transactions without overwhelming response buffer + if(axil_arvalid && !axil_prev_was_rd) begin + cpuif_req = '1; + cpuif_req_is_wr = '0; + cpuif_addr = {axil_araddr[9:2], 2'b0}; + if(!cpuif_req_stall_rd) axil_ar_accept = '1; + end else if(axil_awvalid && axil_wvalid) begin + cpuif_req = '1; + cpuif_req_is_wr = '1; + cpuif_addr = {axil_awaddr[9:2], 2'b0}; + if(!cpuif_req_stall_wr) axil_aw_accept = '1; + end else if(axil_arvalid) begin + cpuif_req = '1; + cpuif_req_is_wr = '0; + cpuif_addr = {axil_araddr[9:2], 2'b0}; + if(!cpuif_req_stall_rd) axil_ar_accept = '1; + end + end + end + + + // AXI4-Lite Response Logic + struct { + logic is_wr; + logic err; + logic [31:0] rdata; + } axil_resp_buffer[2]; + + logic [1:0] axil_resp_wptr; + logic [1:0] axil_resp_rptr; + + always_ff @(posedge clk) begin + if(rst) begin + for(int i=0; i<2; i++) begin + axil_resp_buffer[i].is_wr <= '0; + axil_resp_buffer[i].err <= '0; + axil_resp_buffer[i].rdata <= '0; + end + axil_resp_wptr <= '0; + axil_resp_rptr <= '0; + end else begin + // Store responses in buffer until AXI response channel accepts them + if(cpuif_rd_ack || cpuif_wr_ack) begin + if(cpuif_rd_ack) begin + axil_resp_buffer[axil_resp_wptr[0:0]].is_wr <= '0; + axil_resp_buffer[axil_resp_wptr[0:0]].err <= cpuif_rd_err; + axil_resp_buffer[axil_resp_wptr[0:0]].rdata <= cpuif_rd_data; + + end else if(cpuif_wr_ack) begin + axil_resp_buffer[axil_resp_wptr[0:0]].is_wr <= '1; + axil_resp_buffer[axil_resp_wptr[0:0]].err <= cpuif_wr_err; + end + axil_resp_wptr <= axil_resp_wptr + 1'b1; + end + + // Advance read pointer when acknowledged + if(axil_resp_acked) begin + axil_resp_rptr <= axil_resp_rptr + 1'b1; + end + end + end + + always_comb begin + axil_resp_acked = '0; + s_axil_bvalid = '0; + s_axil_rvalid = '0; + if(axil_resp_rptr != axil_resp_wptr) begin + if(axil_resp_buffer[axil_resp_rptr[0:0]].is_wr) begin + s_axil_bvalid = '1; + if(s_axil_bready) axil_resp_acked = '1; + end else begin + s_axil_rvalid = '1; + if(s_axil_rready) axil_resp_acked = '1; + end + end + + s_axil_rdata = axil_resp_buffer[axil_resp_rptr[0:0]].rdata; + if(axil_resp_buffer[axil_resp_rptr[0:0]].err) begin + s_axil_bresp = 2'b10; + s_axil_rresp = 2'b10; + end else begin + s_axil_bresp = 2'b00; + s_axil_rresp = 2'b00; + end + end + + logic cpuif_req_masked; + logic external_req; + logic external_pending; + logic external_wr_ack; + logic external_rd_ack; + always_ff @(posedge clk) begin + if(rst) begin + external_pending <= '0; + end else begin + if(external_req & ~external_wr_ack & ~external_rd_ack) external_pending <= '1; + else if(external_wr_ack | external_rd_ack) external_pending <= '0; + assert(!external_wr_ack || (external_pending | external_req)) + else $error("An external wr_ack strobe was asserted when no external request was active"); + assert(!external_rd_ack || (external_pending | external_req)) + else $error("An external rd_ack strobe was asserted when no external request was active"); + end + end + + // Read & write latencies are balanced. Stalls not required + // except if external + assign cpuif_req_stall_rd = external_pending; + assign cpuif_req_stall_wr = external_pending; + assign cpuif_req_masked = cpuif_req + & !(!cpuif_req_is_wr & cpuif_req_stall_rd) + & !(cpuif_req_is_wr & cpuif_req_stall_wr); + + //-------------------------------------------------------------------------- + // Address Decode + //-------------------------------------------------------------------------- + typedef struct { + logic mac; + logic tcp_top; + } decoded_reg_strb_t; + decoded_reg_strb_t decoded_reg_strb; + logic decoded_strb_is_external; + + logic [9:0] decoded_addr; + + logic decoded_req; + logic decoded_req_is_wr; + logic [31:0] decoded_wr_data; + logic [31:0] decoded_wr_biten; + + always_comb begin + automatic logic is_external; + is_external = '0; + decoded_reg_strb.mac = cpuif_req_masked & (cpuif_addr >= 10'h0) & (cpuif_addr <= 10'h0 + 10'h7); + is_external |= cpuif_req_masked & (cpuif_addr >= 10'h0) & (cpuif_addr <= 10'h0 + 10'h7); + decoded_reg_strb.tcp_top = cpuif_req_masked & (cpuif_addr >= 10'h200) & (cpuif_addr <= 10'h200 + 10'h1ff); + is_external |= cpuif_req_masked & (cpuif_addr >= 10'h200) & (cpuif_addr <= 10'h200 + 10'h1ff); + decoded_strb_is_external = is_external; + external_req = is_external; + end + + // Pass down signals to next stage + assign decoded_addr = cpuif_addr; + + assign decoded_req = cpuif_req_masked; + assign decoded_req_is_wr = cpuif_req_is_wr; + assign decoded_wr_data = cpuif_wr_data; + assign decoded_wr_biten = cpuif_wr_biten; + + //-------------------------------------------------------------------------- + // Field logic + //-------------------------------------------------------------------------- + + + + + assign hwif_out.mac.req = decoded_reg_strb.mac; + assign hwif_out.mac.addr = decoded_addr[3:0]; + assign hwif_out.mac.req_is_wr = decoded_req_is_wr; + assign hwif_out.mac.wr_data = decoded_wr_data; + assign hwif_out.mac.wr_biten = decoded_wr_biten; + assign hwif_out.tcp_top.req = decoded_reg_strb.tcp_top; + assign hwif_out.tcp_top.addr = decoded_addr[9:0]; + assign hwif_out.tcp_top.req_is_wr = decoded_req_is_wr; + assign hwif_out.tcp_top.wr_data = decoded_wr_data; + assign hwif_out.tcp_top.wr_biten = decoded_wr_biten; + + //-------------------------------------------------------------------------- + // Write response + //-------------------------------------------------------------------------- + always_comb begin + automatic logic wr_ack; + wr_ack = '0; + wr_ack |= hwif_in.mac.wr_ack; + wr_ack |= hwif_in.tcp_top.wr_ack; + external_wr_ack = wr_ack; + end + assign cpuif_wr_ack = external_wr_ack | (decoded_req & decoded_req_is_wr & ~decoded_strb_is_external); + // Writes are always granted with no error response + assign cpuif_wr_err = '0; + + //-------------------------------------------------------------------------- + // Readback + //-------------------------------------------------------------------------- + logic readback_external_rd_ack_c; + always_comb begin + automatic logic rd_ack; + rd_ack = '0; + rd_ack |= hwif_in.mac.rd_ack; + rd_ack |= hwif_in.tcp_top.rd_ack; + readback_external_rd_ack_c = rd_ack; + end + + logic readback_external_rd_ack; + + assign readback_external_rd_ack = readback_external_rd_ack_c; + + logic readback_err; + logic readback_done; + logic [31:0] readback_data; + + // Assign readback values to a flattened array + logic [31:0] readback_array[2]; + assign readback_array[0] = hwif_in.mac.rd_ack ? hwif_in.mac.rd_data : '0; + assign readback_array[1] = hwif_in.tcp_top.rd_ack ? hwif_in.tcp_top.rd_data : '0; + + // Reduce the array + always_comb begin + automatic logic [31:0] readback_data_var; + readback_done = decoded_req & ~decoded_req_is_wr & ~decoded_strb_is_external; + readback_err = '0; + readback_data_var = '0; + for(int i=0; i<2; i++) readback_data_var |= readback_array[i]; + readback_data = readback_data_var; + end + + assign external_rd_ack = readback_external_rd_ack; + assign cpuif_rd_ack = readback_done | readback_external_rd_ack; + assign cpuif_rd_data = readback_data; + assign cpuif_rd_err = readback_err; +endmodule diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/ntw_top_regfile_pkg.sv b/hw/super6502_fpga/src/sub/network_processor/src/regs/ntw_top_regfile_pkg.sv new file mode 100644 index 0000000..0f263d2 --- /dev/null +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/ntw_top_regfile_pkg.sv @@ -0,0 +1,46 @@ +// Generated by PeakRDL-regblock - A free and open-source SystemVerilog generator +// https://github.com/SystemRDL/PeakRDL-regblock + +package ntw_top_regfile_pkg; + + localparam NTW_TOP_REGFILE_DATA_WIDTH = 32; + localparam NTW_TOP_REGFILE_MIN_ADDR_WIDTH = 10; + + typedef struct { + logic rd_ack; + logic [31:0] rd_data; + logic wr_ack; + } mac_t__external__in_t; + + typedef struct { + logic rd_ack; + logic [31:0] rd_data; + logic wr_ack; + } tcp_top_regfile__external__in_t; + + typedef struct { + mac_t__external__in_t mac; + tcp_top_regfile__external__in_t tcp_top; + } ntw_top_regfile__in_t; + + typedef struct { + logic req; + logic [2:0] addr; + logic req_is_wr; + logic [31:0] wr_data; + logic [31:0] wr_biten; + } mac_t__external__out_t; + + typedef struct { + logic req; + logic [8:0] addr; + logic req_is_wr; + logic [31:0] wr_data; + logic [31:0] wr_biten; + } tcp_top_regfile__external__out_t; + + typedef struct { + mac_t__external__out_t mac; + tcp_top_regfile__external__out_t tcp_top; + } ntw_top_regfile__out_t; +endpackage diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/ntw_top_regs.rdl b/hw/super6502_fpga/src/sub/network_processor/src/regs/ntw_top_regs.rdl new file mode 100644 index 0000000..c0d8e61 --- /dev/null +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/ntw_top_regs.rdl @@ -0,0 +1,4 @@ +addrmap ntw_top_regfile { + external mac_t mac; + external tcp_top_regfile tcp_top; +}; \ No newline at end of file diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/run_precompile.sh b/hw/super6502_fpga/src/sub/network_processor/src/regs/run_precompile.sh index 7df9a6a..528ca19 100644 --- a/hw/super6502_fpga/src/sub/network_processor/src/regs/run_precompile.sh +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/run_precompile.sh @@ -1,10 +1,4 @@ -peakrdl regblock tcp_stream.rdl tcp_top_regs.rdl -o . --cpuif axi4-lite-flat -peakrdl regblock -t tcp_stream_regs tcp_stream.rdl -o . --cpuif passthrough - -# sed -i -e 's/struct/struct packed/g' tcp_stream_regs.sv -# sed -i -e 's/struct/struct packed/g' tcp_stream_regs_pkg.sv -# sed -i -e 's/automatic/static/g' tcp_stream_regs.sv - -# sed -i -e 's/struct/struct packed/g' tcp_top_regfile.sv -# sed -i -e 's/struct/struct packed/g' tcp_top_regfile_pkg.sv -# sed -i -e 's/automatic/static/g' tcp_top_regfile.sv +peakrdl regblock -t tcp_top_regfile tcp_stream_regs.rdl tcp_top_regs.rdl -o . --cpuif passthrough +peakrdl regblock -t tcp_stream_regs tcp_stream_regs.rdl -o . --cpuif passthrough +peakrdl regblock -t mac_t mac_regs.rdl -o . --cpuif passthrough +peakrdl regblock -t ntw_top_regfile mac_regs.rdl tcp_stream_regs.rdl tcp_top_regs.rdl ntw_top_regs.rdl -o . --cpuif axi4-lite-flat \ No newline at end of file diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream.rdl b/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream_regs.rdl similarity index 98% rename from hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream.rdl rename to hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream_regs.rdl index 99a9474..31ab8b2 100644 --- a/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream.rdl +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream_regs.rdl @@ -1,4 +1,4 @@ -regfile tcp_stream { +addrmap tcp_stream_regs { name = "TCP Stream Regs"; desc = ""; @@ -132,8 +132,4 @@ regfile tcp_stream { } rx_bad_crc @ 0x8; }; -}; - -addrmap tcp_stream_regs { - tcp_stream tcp_streams; }; \ No newline at end of file diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream_regs.sv b/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream_regs.sv index 48704c0..7ab91f5 100644 --- a/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream_regs.sv +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream_regs.sv @@ -66,13 +66,11 @@ module tcp_stream_regs ( // Address Decode //-------------------------------------------------------------------------- typedef struct { - struct { - logic source_port; - logic source_ip; - logic dest_port; - logic dest_ip; - logic control; - } tcp_streams; + logic source_port; + logic source_ip; + logic dest_port; + logic dest_ip; + logic control; } decoded_reg_strb_t; decoded_reg_strb_t decoded_reg_strb; logic decoded_req; @@ -81,11 +79,11 @@ module tcp_stream_regs ( logic [31:0] decoded_wr_biten; always_comb begin - decoded_reg_strb.tcp_streams.source_port = cpuif_req_masked & (cpuif_addr == 5'h0); - decoded_reg_strb.tcp_streams.source_ip = cpuif_req_masked & (cpuif_addr == 5'h4); - decoded_reg_strb.tcp_streams.dest_port = cpuif_req_masked & (cpuif_addr == 5'h8); - decoded_reg_strb.tcp_streams.dest_ip = cpuif_req_masked & (cpuif_addr == 5'hc); - decoded_reg_strb.tcp_streams.control = cpuif_req_masked & (cpuif_addr == 5'h10); + decoded_reg_strb.source_port = cpuif_req_masked & (cpuif_addr == 5'h0); + decoded_reg_strb.source_ip = cpuif_req_masked & (cpuif_addr == 5'h4); + decoded_reg_strb.dest_port = cpuif_req_masked & (cpuif_addr == 5'h8); + decoded_reg_strb.dest_ip = cpuif_req_masked & (cpuif_addr == 5'hc); + decoded_reg_strb.control = cpuif_req_masked & (cpuif_addr == 5'h10); end // Pass down signals to next stage @@ -100,237 +98,233 @@ module tcp_stream_regs ( typedef struct { struct { struct { - struct { - logic [31:0] next; - logic load_next; - } d; - } source_port; + logic [31:0] next; + logic load_next; + } d; + } source_port; + struct { struct { - struct { - logic [31:0] next; - logic load_next; - } d; - } source_ip; + logic [31:0] next; + logic load_next; + } d; + } source_ip; + struct { struct { - struct { - logic [31:0] next; - logic load_next; - } d; - } dest_port; + logic [31:0] next; + logic load_next; + } d; + } dest_port; + struct { struct { - struct { - logic [31:0] next; - logic load_next; - } d; - } dest_ip; + logic [31:0] next; + logic load_next; + } d; + } dest_ip; + struct { struct { - struct { - logic next; - logic load_next; - } enable; - struct { - logic next; - logic load_next; - } open; - struct { - logic next; - logic load_next; - } close; - } control; - } tcp_streams; + logic next; + logic load_next; + } enable; + struct { + logic next; + logic load_next; + } open; + struct { + logic next; + logic load_next; + } close; + } control; } field_combo_t; field_combo_t field_combo; typedef struct { struct { struct { - struct { - logic [31:0] value; - } d; - } source_port; + logic [31:0] value; + } d; + } source_port; + struct { struct { - struct { - logic [31:0] value; - } d; - } source_ip; + logic [31:0] value; + } d; + } source_ip; + struct { struct { - struct { - logic [31:0] value; - } d; - } dest_port; + logic [31:0] value; + } d; + } dest_port; + struct { struct { - struct { - logic [31:0] value; - } d; - } dest_ip; + logic [31:0] value; + } d; + } dest_ip; + struct { struct { - struct { - logic value; - } enable; - struct { - logic value; - } open; - struct { - logic value; - } close; - } control; - } tcp_streams; + logic value; + } enable; + struct { + logic value; + } open; + struct { + logic value; + } close; + } control; } field_storage_t; field_storage_t field_storage; - // Field: tcp_stream_regs.tcp_streams.source_port.d + // Field: tcp_stream_regs.source_port.d always_comb begin automatic logic [31:0] next_c; automatic logic load_next_c; - next_c = field_storage.tcp_streams.source_port.d.value; + next_c = field_storage.source_port.d.value; load_next_c = '0; - if(decoded_reg_strb.tcp_streams.source_port && decoded_req_is_wr) begin // SW write - next_c = (field_storage.tcp_streams.source_port.d.value & ~decoded_wr_biten[31:0]) | (decoded_wr_data[31:0] & decoded_wr_biten[31:0]); + if(decoded_reg_strb.source_port && decoded_req_is_wr) begin // SW write + next_c = (field_storage.source_port.d.value & ~decoded_wr_biten[31:0]) | (decoded_wr_data[31:0] & decoded_wr_biten[31:0]); load_next_c = '1; end - field_combo.tcp_streams.source_port.d.next = next_c; - field_combo.tcp_streams.source_port.d.load_next = load_next_c; + field_combo.source_port.d.next = next_c; + field_combo.source_port.d.load_next = load_next_c; end always_ff @(posedge clk) begin if(rst) begin - field_storage.tcp_streams.source_port.d.value <= 32'h0; - end else if(field_combo.tcp_streams.source_port.d.load_next) begin - field_storage.tcp_streams.source_port.d.value <= field_combo.tcp_streams.source_port.d.next; + field_storage.source_port.d.value <= 32'h0; + end else if(field_combo.source_port.d.load_next) begin + field_storage.source_port.d.value <= field_combo.source_port.d.next; end end - assign hwif_out.tcp_streams.source_port.d.value = field_storage.tcp_streams.source_port.d.value; - // Field: tcp_stream_regs.tcp_streams.source_ip.d + assign hwif_out.source_port.d.value = field_storage.source_port.d.value; + // Field: tcp_stream_regs.source_ip.d always_comb begin automatic logic [31:0] next_c; automatic logic load_next_c; - next_c = field_storage.tcp_streams.source_ip.d.value; + next_c = field_storage.source_ip.d.value; load_next_c = '0; - if(decoded_reg_strb.tcp_streams.source_ip && decoded_req_is_wr) begin // SW write - next_c = (field_storage.tcp_streams.source_ip.d.value & ~decoded_wr_biten[31:0]) | (decoded_wr_data[31:0] & decoded_wr_biten[31:0]); + if(decoded_reg_strb.source_ip && decoded_req_is_wr) begin // SW write + next_c = (field_storage.source_ip.d.value & ~decoded_wr_biten[31:0]) | (decoded_wr_data[31:0] & decoded_wr_biten[31:0]); load_next_c = '1; end - field_combo.tcp_streams.source_ip.d.next = next_c; - field_combo.tcp_streams.source_ip.d.load_next = load_next_c; + field_combo.source_ip.d.next = next_c; + field_combo.source_ip.d.load_next = load_next_c; end always_ff @(posedge clk) begin if(rst) begin - field_storage.tcp_streams.source_ip.d.value <= 32'h0; - end else if(field_combo.tcp_streams.source_ip.d.load_next) begin - field_storage.tcp_streams.source_ip.d.value <= field_combo.tcp_streams.source_ip.d.next; + field_storage.source_ip.d.value <= 32'h0; + end else if(field_combo.source_ip.d.load_next) begin + field_storage.source_ip.d.value <= field_combo.source_ip.d.next; end end - assign hwif_out.tcp_streams.source_ip.d.value = field_storage.tcp_streams.source_ip.d.value; - // Field: tcp_stream_regs.tcp_streams.dest_port.d + assign hwif_out.source_ip.d.value = field_storage.source_ip.d.value; + // Field: tcp_stream_regs.dest_port.d always_comb begin automatic logic [31:0] next_c; automatic logic load_next_c; - next_c = field_storage.tcp_streams.dest_port.d.value; + next_c = field_storage.dest_port.d.value; load_next_c = '0; - if(decoded_reg_strb.tcp_streams.dest_port && decoded_req_is_wr) begin // SW write - next_c = (field_storage.tcp_streams.dest_port.d.value & ~decoded_wr_biten[31:0]) | (decoded_wr_data[31:0] & decoded_wr_biten[31:0]); + if(decoded_reg_strb.dest_port && decoded_req_is_wr) begin // SW write + next_c = (field_storage.dest_port.d.value & ~decoded_wr_biten[31:0]) | (decoded_wr_data[31:0] & decoded_wr_biten[31:0]); load_next_c = '1; end - field_combo.tcp_streams.dest_port.d.next = next_c; - field_combo.tcp_streams.dest_port.d.load_next = load_next_c; + field_combo.dest_port.d.next = next_c; + field_combo.dest_port.d.load_next = load_next_c; end always_ff @(posedge clk) begin if(rst) begin - field_storage.tcp_streams.dest_port.d.value <= 32'h0; - end else if(field_combo.tcp_streams.dest_port.d.load_next) begin - field_storage.tcp_streams.dest_port.d.value <= field_combo.tcp_streams.dest_port.d.next; + field_storage.dest_port.d.value <= 32'h0; + end else if(field_combo.dest_port.d.load_next) begin + field_storage.dest_port.d.value <= field_combo.dest_port.d.next; end end - assign hwif_out.tcp_streams.dest_port.d.value = field_storage.tcp_streams.dest_port.d.value; - // Field: tcp_stream_regs.tcp_streams.dest_ip.d + assign hwif_out.dest_port.d.value = field_storage.dest_port.d.value; + // Field: tcp_stream_regs.dest_ip.d always_comb begin automatic logic [31:0] next_c; automatic logic load_next_c; - next_c = field_storage.tcp_streams.dest_ip.d.value; + next_c = field_storage.dest_ip.d.value; load_next_c = '0; - if(decoded_reg_strb.tcp_streams.dest_ip && decoded_req_is_wr) begin // SW write - next_c = (field_storage.tcp_streams.dest_ip.d.value & ~decoded_wr_biten[31:0]) | (decoded_wr_data[31:0] & decoded_wr_biten[31:0]); + if(decoded_reg_strb.dest_ip && decoded_req_is_wr) begin // SW write + next_c = (field_storage.dest_ip.d.value & ~decoded_wr_biten[31:0]) | (decoded_wr_data[31:0] & decoded_wr_biten[31:0]); load_next_c = '1; end - field_combo.tcp_streams.dest_ip.d.next = next_c; - field_combo.tcp_streams.dest_ip.d.load_next = load_next_c; + field_combo.dest_ip.d.next = next_c; + field_combo.dest_ip.d.load_next = load_next_c; end always_ff @(posedge clk) begin if(rst) begin - field_storage.tcp_streams.dest_ip.d.value <= 32'h0; - end else if(field_combo.tcp_streams.dest_ip.d.load_next) begin - field_storage.tcp_streams.dest_ip.d.value <= field_combo.tcp_streams.dest_ip.d.next; + field_storage.dest_ip.d.value <= 32'h0; + end else if(field_combo.dest_ip.d.load_next) begin + field_storage.dest_ip.d.value <= field_combo.dest_ip.d.next; end end - assign hwif_out.tcp_streams.dest_ip.d.value = field_storage.tcp_streams.dest_ip.d.value; - // Field: tcp_stream_regs.tcp_streams.control.enable + assign hwif_out.dest_ip.d.value = field_storage.dest_ip.d.value; + // Field: tcp_stream_regs.control.enable always_comb begin automatic logic [0:0] next_c; automatic logic load_next_c; - next_c = field_storage.tcp_streams.control.enable.value; + next_c = field_storage.control.enable.value; load_next_c = '0; - if(decoded_reg_strb.tcp_streams.control && decoded_req_is_wr) begin // SW write - next_c = (field_storage.tcp_streams.control.enable.value & ~decoded_wr_biten[0:0]) | (decoded_wr_data[0:0] & decoded_wr_biten[0:0]); + if(decoded_reg_strb.control && decoded_req_is_wr) begin // SW write + next_c = (field_storage.control.enable.value & ~decoded_wr_biten[0:0]) | (decoded_wr_data[0:0] & decoded_wr_biten[0:0]); load_next_c = '1; end - field_combo.tcp_streams.control.enable.next = next_c; - field_combo.tcp_streams.control.enable.load_next = load_next_c; + field_combo.control.enable.next = next_c; + field_combo.control.enable.load_next = load_next_c; end always_ff @(posedge clk) begin if(rst) begin - field_storage.tcp_streams.control.enable.value <= 1'h0; - end else if(field_combo.tcp_streams.control.enable.load_next) begin - field_storage.tcp_streams.control.enable.value <= field_combo.tcp_streams.control.enable.next; + field_storage.control.enable.value <= 1'h0; + end else if(field_combo.control.enable.load_next) begin + field_storage.control.enable.value <= field_combo.control.enable.next; end end - assign hwif_out.tcp_streams.control.enable.value = field_storage.tcp_streams.control.enable.value; - // Field: tcp_stream_regs.tcp_streams.control.open + assign hwif_out.control.enable.value = field_storage.control.enable.value; + // Field: tcp_stream_regs.control.open always_comb begin automatic logic [0:0] next_c; automatic logic load_next_c; - next_c = field_storage.tcp_streams.control.open.value; + next_c = field_storage.control.open.value; load_next_c = '0; - if(decoded_reg_strb.tcp_streams.control && decoded_req_is_wr) begin // SW write - next_c = (field_storage.tcp_streams.control.open.value & ~decoded_wr_biten[1:1]) | (decoded_wr_data[1:1] & decoded_wr_biten[1:1]); + if(decoded_reg_strb.control && decoded_req_is_wr) begin // SW write + next_c = (field_storage.control.open.value & ~decoded_wr_biten[1:1]) | (decoded_wr_data[1:1] & decoded_wr_biten[1:1]); load_next_c = '1; - end else if(hwif_in.tcp_streams.control.open.hwclr) begin // HW Clear + end else if(hwif_in.control.open.hwclr) begin // HW Clear next_c = '0; load_next_c = '1; end - field_combo.tcp_streams.control.open.next = next_c; - field_combo.tcp_streams.control.open.load_next = load_next_c; + field_combo.control.open.next = next_c; + field_combo.control.open.load_next = load_next_c; end always_ff @(posedge clk) begin if(rst) begin - field_storage.tcp_streams.control.open.value <= 1'h0; - end else if(field_combo.tcp_streams.control.open.load_next) begin - field_storage.tcp_streams.control.open.value <= field_combo.tcp_streams.control.open.next; + field_storage.control.open.value <= 1'h0; + end else if(field_combo.control.open.load_next) begin + field_storage.control.open.value <= field_combo.control.open.next; end end - assign hwif_out.tcp_streams.control.open.value = field_storage.tcp_streams.control.open.value; - // Field: tcp_stream_regs.tcp_streams.control.close + assign hwif_out.control.open.value = field_storage.control.open.value; + // Field: tcp_stream_regs.control.close always_comb begin automatic logic [0:0] next_c; automatic logic load_next_c; - next_c = field_storage.tcp_streams.control.close.value; + next_c = field_storage.control.close.value; load_next_c = '0; - if(decoded_reg_strb.tcp_streams.control && decoded_req_is_wr) begin // SW write - next_c = (field_storage.tcp_streams.control.close.value & ~decoded_wr_biten[2:2]) | (decoded_wr_data[2:2] & decoded_wr_biten[2:2]); + if(decoded_reg_strb.control && decoded_req_is_wr) begin // SW write + next_c = (field_storage.control.close.value & ~decoded_wr_biten[2:2]) | (decoded_wr_data[2:2] & decoded_wr_biten[2:2]); load_next_c = '1; - end else if(hwif_in.tcp_streams.control.close.hwclr) begin // HW Clear + end else if(hwif_in.control.close.hwclr) begin // HW Clear next_c = '0; load_next_c = '1; end - field_combo.tcp_streams.control.close.next = next_c; - field_combo.tcp_streams.control.close.load_next = load_next_c; + field_combo.control.close.next = next_c; + field_combo.control.close.load_next = load_next_c; end always_ff @(posedge clk) begin if(rst) begin - field_storage.tcp_streams.control.close.value <= 1'h0; - end else if(field_combo.tcp_streams.control.close.load_next) begin - field_storage.tcp_streams.control.close.value <= field_combo.tcp_streams.control.close.next; + field_storage.control.close.value <= 1'h0; + end else if(field_combo.control.close.load_next) begin + field_storage.control.close.value <= field_combo.control.close.next; end end - assign hwif_out.tcp_streams.control.close.value = field_storage.tcp_streams.control.close.value; + assign hwif_out.control.close.value = field_storage.control.close.value; //-------------------------------------------------------------------------- // Write response @@ -349,14 +343,14 @@ module tcp_stream_regs ( // Assign readback values to a flattened array logic [31:0] readback_array[5]; - assign readback_array[0][31:0] = (decoded_reg_strb.tcp_streams.source_port && !decoded_req_is_wr) ? field_storage.tcp_streams.source_port.d.value : '0; - assign readback_array[1][31:0] = (decoded_reg_strb.tcp_streams.source_ip && !decoded_req_is_wr) ? field_storage.tcp_streams.source_ip.d.value : '0; - assign readback_array[2][31:0] = (decoded_reg_strb.tcp_streams.dest_port && !decoded_req_is_wr) ? field_storage.tcp_streams.dest_port.d.value : '0; - assign readback_array[3][31:0] = (decoded_reg_strb.tcp_streams.dest_ip && !decoded_req_is_wr) ? field_storage.tcp_streams.dest_ip.d.value : '0; - assign readback_array[4][0:0] = (decoded_reg_strb.tcp_streams.control && !decoded_req_is_wr) ? field_storage.tcp_streams.control.enable.value : '0; - assign readback_array[4][1:1] = (decoded_reg_strb.tcp_streams.control && !decoded_req_is_wr) ? field_storage.tcp_streams.control.open.value : '0; - assign readback_array[4][2:2] = (decoded_reg_strb.tcp_streams.control && !decoded_req_is_wr) ? field_storage.tcp_streams.control.close.value : '0; - assign readback_array[4][5:3] = (decoded_reg_strb.tcp_streams.control && !decoded_req_is_wr) ? hwif_in.tcp_streams.control.state.next : '0; + assign readback_array[0][31:0] = (decoded_reg_strb.source_port && !decoded_req_is_wr) ? field_storage.source_port.d.value : '0; + assign readback_array[1][31:0] = (decoded_reg_strb.source_ip && !decoded_req_is_wr) ? field_storage.source_ip.d.value : '0; + assign readback_array[2][31:0] = (decoded_reg_strb.dest_port && !decoded_req_is_wr) ? field_storage.dest_port.d.value : '0; + assign readback_array[3][31:0] = (decoded_reg_strb.dest_ip && !decoded_req_is_wr) ? field_storage.dest_ip.d.value : '0; + assign readback_array[4][0:0] = (decoded_reg_strb.control && !decoded_req_is_wr) ? field_storage.control.enable.value : '0; + assign readback_array[4][1:1] = (decoded_reg_strb.control && !decoded_req_is_wr) ? field_storage.control.open.value : '0; + assign readback_array[4][2:2] = (decoded_reg_strb.control && !decoded_req_is_wr) ? field_storage.control.close.value : '0; + assign readback_array[4][5:3] = (decoded_reg_strb.control && !decoded_req_is_wr) ? hwif_in.control.state.next : '0; assign readback_array[4][31:6] = '0; // Reduce the array diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream_regs_pkg.sv b/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream_regs_pkg.sv index 13b6a1a..f053abf 100644 --- a/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream_regs_pkg.sv +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_stream_regs_pkg.sv @@ -8,89 +8,81 @@ package tcp_stream_regs_pkg; typedef struct { logic hwclr; - } tcp_stream__control__open__in_t; + } tcp_stream_regs__control__open__in_t; typedef struct { logic hwclr; - } tcp_stream__control__close__in_t; + } tcp_stream_regs__control__close__in_t; typedef struct { logic [2:0] next; - } tcp_stream__control__state__in_t; + } tcp_stream_regs__control__state__in_t; typedef struct { - tcp_stream__control__open__in_t open; - tcp_stream__control__close__in_t close; - tcp_stream__control__state__in_t state; - } tcp_stream__control__in_t; + tcp_stream_regs__control__open__in_t open; + tcp_stream_regs__control__close__in_t close; + tcp_stream_regs__control__state__in_t state; + } tcp_stream_regs__control__in_t; typedef struct { - tcp_stream__control__in_t control; - } tcp_stream__in_t; - - typedef struct { - tcp_stream__in_t tcp_streams; + tcp_stream_regs__control__in_t control; } tcp_stream_regs__in_t; typedef struct { logic [31:0] value; - } tcp_stream__source_port__d__out_t; + } tcp_stream_regs__source_port__d__out_t; typedef struct { - tcp_stream__source_port__d__out_t d; - } tcp_stream__source_port__out_t; + tcp_stream_regs__source_port__d__out_t d; + } tcp_stream_regs__source_port__out_t; typedef struct { logic [31:0] value; - } tcp_stream__source_ip__d__out_t; + } tcp_stream_regs__source_ip__d__out_t; typedef struct { - tcp_stream__source_ip__d__out_t d; - } tcp_stream__source_ip__out_t; + tcp_stream_regs__source_ip__d__out_t d; + } tcp_stream_regs__source_ip__out_t; typedef struct { logic [31:0] value; - } tcp_stream__dest_port__d__out_t; + } tcp_stream_regs__dest_port__d__out_t; typedef struct { - tcp_stream__dest_port__d__out_t d; - } tcp_stream__dest_port__out_t; + tcp_stream_regs__dest_port__d__out_t d; + } tcp_stream_regs__dest_port__out_t; typedef struct { logic [31:0] value; - } tcp_stream__dest_ip__d__out_t; + } tcp_stream_regs__dest_ip__d__out_t; typedef struct { - tcp_stream__dest_ip__d__out_t d; - } tcp_stream__dest_ip__out_t; + tcp_stream_regs__dest_ip__d__out_t d; + } tcp_stream_regs__dest_ip__out_t; typedef struct { logic value; - } tcp_stream__control__enable__out_t; + } tcp_stream_regs__control__enable__out_t; typedef struct { logic value; - } tcp_stream__control__open__out_t; + } tcp_stream_regs__control__open__out_t; typedef struct { logic value; - } tcp_stream__control__close__out_t; + } tcp_stream_regs__control__close__out_t; typedef struct { - tcp_stream__control__enable__out_t enable; - tcp_stream__control__open__out_t open; - tcp_stream__control__close__out_t close; - } tcp_stream__control__out_t; + tcp_stream_regs__control__enable__out_t enable; + tcp_stream_regs__control__open__out_t open; + tcp_stream_regs__control__close__out_t close; + } tcp_stream_regs__control__out_t; typedef struct { - tcp_stream__source_port__out_t source_port; - tcp_stream__source_ip__out_t source_ip; - tcp_stream__dest_port__out_t dest_port; - tcp_stream__dest_ip__out_t dest_ip; - tcp_stream__control__out_t control; - } tcp_stream__out_t; - - typedef struct { - tcp_stream__out_t tcp_streams; + tcp_stream_regs__source_port__out_t source_port; + tcp_stream_regs__source_ip__out_t source_ip; + tcp_stream_regs__dest_port__out_t dest_port; + tcp_stream_regs__dest_ip__out_t dest_ip; + tcp_stream_regs__control__out_t control; } tcp_stream_regs__out_t; endpackage diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_top_regfile.sv b/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_top_regfile.sv index cbb4044..0c3bfe9 100644 --- a/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_top_regfile.sv +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_top_regfile.sv @@ -5,25 +5,18 @@ module tcp_top_regfile ( input wire clk, input wire rst, - output logic s_axil_awready, - input wire s_axil_awvalid, - input wire [8:0] s_axil_awaddr, - input wire [2:0] s_axil_awprot, - output logic s_axil_wready, - input wire s_axil_wvalid, - input wire [31:0] s_axil_wdata, - input wire [3:0]s_axil_wstrb, - input wire s_axil_bready, - output logic s_axil_bvalid, - output logic [1:0] s_axil_bresp, - output logic s_axil_arready, - input wire s_axil_arvalid, - input wire [8:0] s_axil_araddr, - input wire [2:0] s_axil_arprot, - input wire s_axil_rready, - output logic s_axil_rvalid, - output logic [31:0] s_axil_rdata, - output logic [1:0] s_axil_rresp, + input wire s_cpuif_req, + input wire s_cpuif_req_is_wr, + input wire [8:0] s_cpuif_addr, + input wire [31:0] s_cpuif_wr_data, + input wire [31:0] s_cpuif_wr_biten, + output wire s_cpuif_req_stall_wr, + output wire s_cpuif_req_stall_rd, + output wire s_cpuif_rd_ack, + output wire s_cpuif_rd_err, + output wire [31:0] s_cpuif_rd_data, + output wire s_cpuif_wr_ack, + output wire s_cpuif_wr_err, input tcp_top_regfile_pkg::tcp_top_regfile__in_t hwif_in, output tcp_top_regfile_pkg::tcp_top_regfile__out_t hwif_out @@ -47,172 +40,18 @@ module tcp_top_regfile ( logic cpuif_wr_ack; logic cpuif_wr_err; - // Max Outstanding Transactions: 2 - logic [1:0] axil_n_in_flight; - logic axil_prev_was_rd; - logic axil_arvalid; - logic [8:0] axil_araddr; - logic axil_ar_accept; - logic axil_awvalid; - logic [8:0] axil_awaddr; - logic axil_wvalid; - logic [31:0] axil_wdata; - logic [3:0] axil_wstrb; - logic axil_aw_accept; - logic axil_resp_acked; - - // Transaction request acceptance - always_ff @(posedge clk) begin - if(rst) begin - axil_prev_was_rd <= '0; - axil_arvalid <= '0; - axil_araddr <= '0; - axil_awvalid <= '0; - axil_awaddr <= '0; - axil_wvalid <= '0; - axil_wdata <= '0; - axil_wstrb <= '0; - axil_n_in_flight <= '0; - end else begin - // AR* acceptance register - if(axil_ar_accept) begin - axil_prev_was_rd <= '1; - axil_arvalid <= '0; - end - if(s_axil_arvalid && s_axil_arready) begin - axil_arvalid <= '1; - axil_araddr <= s_axil_araddr; - end - - // AW* & W* acceptance registers - if(axil_aw_accept) begin - axil_prev_was_rd <= '0; - axil_awvalid <= '0; - axil_wvalid <= '0; - end - if(s_axil_awvalid && s_axil_awready) begin - axil_awvalid <= '1; - axil_awaddr <= s_axil_awaddr; - end - if(s_axil_wvalid && s_axil_wready) begin - axil_wvalid <= '1; - axil_wdata <= s_axil_wdata; - axil_wstrb <= s_axil_wstrb; - end - - // Keep track of in-flight transactions - if((axil_ar_accept || axil_aw_accept) && !axil_resp_acked) begin - axil_n_in_flight <= axil_n_in_flight + 1'b1; - end else if(!(axil_ar_accept || axil_aw_accept) && axil_resp_acked) begin - axil_n_in_flight <= axil_n_in_flight - 1'b1; - end - end - end - - always_comb begin - s_axil_arready = (!axil_arvalid || axil_ar_accept); - s_axil_awready = (!axil_awvalid || axil_aw_accept); - s_axil_wready = (!axil_wvalid || axil_aw_accept); - end - - // Request dispatch - always_comb begin - cpuif_wr_data = axil_wdata; - for(int i=0; i<4; i++) begin - cpuif_wr_biten[i*8 +: 8] = {8{axil_wstrb[i]}}; - end - cpuif_req = '0; - cpuif_req_is_wr = '0; - cpuif_addr = '0; - axil_ar_accept = '0; - axil_aw_accept = '0; - - if(axil_n_in_flight < 2'd2) begin - // Can safely issue more transactions without overwhelming response buffer - if(axil_arvalid && !axil_prev_was_rd) begin - cpuif_req = '1; - cpuif_req_is_wr = '0; - cpuif_addr = {axil_araddr[8:2], 2'b0}; - if(!cpuif_req_stall_rd) axil_ar_accept = '1; - end else if(axil_awvalid && axil_wvalid) begin - cpuif_req = '1; - cpuif_req_is_wr = '1; - cpuif_addr = {axil_awaddr[8:2], 2'b0}; - if(!cpuif_req_stall_wr) axil_aw_accept = '1; - end else if(axil_arvalid) begin - cpuif_req = '1; - cpuif_req_is_wr = '0; - cpuif_addr = {axil_araddr[8:2], 2'b0}; - if(!cpuif_req_stall_rd) axil_ar_accept = '1; - end - end - end - - - // AXI4-Lite Response Logic - struct { - logic is_wr; - logic err; - logic [31:0] rdata; - } axil_resp_buffer[2]; - - logic [1:0] axil_resp_wptr; - logic [1:0] axil_resp_rptr; - - always_ff @(posedge clk) begin - if(rst) begin - for(int i=0; i<2; i++) begin - axil_resp_buffer[i].is_wr <= '0; - axil_resp_buffer[i].err <= '0; - axil_resp_buffer[i].rdata <= '0; - end - axil_resp_wptr <= '0; - axil_resp_rptr <= '0; - end else begin - // Store responses in buffer until AXI response channel accepts them - if(cpuif_rd_ack || cpuif_wr_ack) begin - if(cpuif_rd_ack) begin - axil_resp_buffer[axil_resp_wptr[0:0]].is_wr <= '0; - axil_resp_buffer[axil_resp_wptr[0:0]].err <= cpuif_rd_err; - axil_resp_buffer[axil_resp_wptr[0:0]].rdata <= cpuif_rd_data; - - end else if(cpuif_wr_ack) begin - axil_resp_buffer[axil_resp_wptr[0:0]].is_wr <= '1; - axil_resp_buffer[axil_resp_wptr[0:0]].err <= cpuif_wr_err; - end - axil_resp_wptr <= axil_resp_wptr + 1'b1; - end - - // Advance read pointer when acknowledged - if(axil_resp_acked) begin - axil_resp_rptr <= axil_resp_rptr + 1'b1; - end - end - end - - always_comb begin - axil_resp_acked = '0; - s_axil_bvalid = '0; - s_axil_rvalid = '0; - if(axil_resp_rptr != axil_resp_wptr) begin - if(axil_resp_buffer[axil_resp_rptr[0:0]].is_wr) begin - s_axil_bvalid = '1; - if(s_axil_bready) axil_resp_acked = '1; - end else begin - s_axil_rvalid = '1; - if(s_axil_rready) axil_resp_acked = '1; - end - end - - s_axil_rdata = axil_resp_buffer[axil_resp_rptr[0:0]].rdata; - if(axil_resp_buffer[axil_resp_rptr[0:0]].err) begin - s_axil_bresp = 2'b10; - s_axil_rresp = 2'b10; - end else begin - s_axil_bresp = 2'b00; - s_axil_rresp = 2'b00; - end - end + assign cpuif_req = s_cpuif_req; + assign cpuif_req_is_wr = s_cpuif_req_is_wr; + assign cpuif_addr = s_cpuif_addr; + assign cpuif_wr_data = s_cpuif_wr_data; + assign cpuif_wr_biten = s_cpuif_wr_biten; + assign s_cpuif_req_stall_wr = cpuif_req_stall_wr; + assign s_cpuif_req_stall_rd = cpuif_req_stall_rd; + assign s_cpuif_rd_ack = cpuif_rd_ack; + assign s_cpuif_rd_err = cpuif_rd_err; + assign s_cpuif_rd_data = cpuif_rd_data; + assign s_cpuif_wr_ack = cpuif_wr_ack; + assign s_cpuif_wr_err = cpuif_wr_err; logic cpuif_req_masked; logic external_req; diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_top_regfile_pkg.sv b/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_top_regfile_pkg.sv index 6a22f62..9631184 100644 --- a/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_top_regfile_pkg.sv +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_top_regfile_pkg.sv @@ -10,10 +10,10 @@ package tcp_top_regfile_pkg; logic rd_ack; logic [31:0] rd_data; logic wr_ack; - } tcp_stream__external__in_t; + } tcp_stream_regs__external__in_t; typedef struct { - tcp_stream__external__in_t tcp_streams[8]; + tcp_stream_regs__external__in_t tcp_streams[8]; } tcp_top_regfile__in_t; typedef struct { @@ -22,9 +22,9 @@ package tcp_top_regfile_pkg; logic req_is_wr; logic [31:0] wr_data; logic [31:0] wr_biten; - } tcp_stream__external__out_t; + } tcp_stream_regs__external__out_t; typedef struct { - tcp_stream__external__out_t tcp_streams[8]; + tcp_stream_regs__external__out_t tcp_streams[8]; } tcp_top_regfile__out_t; endpackage diff --git a/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_top_regs.rdl b/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_top_regs.rdl index f2d4c61..a2c774a 100644 --- a/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_top_regs.rdl +++ b/hw/super6502_fpga/src/sub/network_processor/src/regs/tcp_top_regs.rdl @@ -1,3 +1,3 @@ addrmap tcp_top_regfile{ - external tcp_stream tcp_streams[8] += 0x40; + external tcp_stream_regs tcp_streams[8] += 0x40; }; \ No newline at end of file