/*------------------------------------------------------------------------------
© [2025] Microchip Technology Inc. and its subsidiaries
Subject to your compliance with the terms and conditions of the license 
agreement accompanying this software, you may use this Microchip software and 
any derivatives exclusively with Microchip products. You are responsible for 
complying with third party license terms applicable to your use of third party 
software (including open source software) that may accompany this Microchip 
software. SOFTWARE IS AS IS. NO WARRANTIES, WHETHER EXPRESS, IMPLIED OR 
STATUTORY, APPLY TO THIS SOFTWARE, INCLUDING ANY IMPLIED WARRANTIES OF 
NON-INFRINGEMENT, MERCHANTABILITY, OR FITNESS FOR A PARTICULAR PURPOSE. IN NO 
EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT, SPECIAL, PUNITIVE, INCIDENTAL 
OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE OF ANY KIND WHATSOEVER RELATED 
TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP HAS BEEN ADVISED OF THE 
POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. TO THE FULLEST EXTENT ALLOWED BY 
LAW, MICROCHIP’S TOTAL LIABILITY ON ALL CLAIMS RELATED TO THE SOFTWARE WILL 
NOT EXCEED AMOUNT OF FEES, IF ANY, YOU PAID DIRECTLY TO MICROCHIP FOR THIS 
SOFTWARE
------------------------------------------------------------------------------*/

/*******************************************************************************
**    File Name       : FiFo_wrapper_Top.v
**    Description     : The FIFO State machine takes the 10G MAC RX control
						signals and stores them in the CORE FIFO IP. These 
						signals are read from the FIFO and placed onto the MAC 
						TX signals for the Loop back DesignEthernet Frames are 
						transmitted onto the 10GMAC and loopback frames are 
						captured
**    Targeted device : Microchip FPGAs
/******************************************************************************/

module FiFo_wrapper_Top( 
  mtx_rx_clk,
  reset_n,
  //tx port signals
  i_sys_mac_tx_en, 
  i_sys_mac_tx_sop,
  i_sys_mac_tx_eop,
  i_sys_mac_tx_bc,
  i_sys_mac_tx_data,
  i_sys_mac_tx_fifo_af,
   
  //rx port Signals
  o_sys_mac_rx_en,
  o_sys_mac_rx_sop,
  o_sys_mac_rx_eop,
  o_sys_mac_rx_bc,
  o_sys_mac_rx_data);

input mtx_rx_clk;
input reset_n;

//output ports
output  i_sys_mac_tx_en;
output  i_sys_mac_tx_sop;
output  i_sys_mac_tx_eop;
output [7:0] i_sys_mac_tx_bc;
output [63:0] i_sys_mac_tx_data;


//input ports
input o_sys_mac_rx_en;
input o_sys_mac_rx_sop;
input o_sys_mac_rx_eop;
input [7:0] o_sys_mac_rx_bc;
input [63:0] o_sys_mac_rx_data;

input i_sys_mac_tx_fifo_af;


parameter en_pos = 74;
parameter sop_pos = 73;
parameter eop_pos = 72 ;
parameter bc_st_pos = 71;
parameter bc_end_pos = 64;
parameter data_st_pos = 63;
parameter data_end_pos = 0;


//FIFO Instantiation signal Declaration
reg [en_pos:data_end_pos] fifo_datain /* synthesis syn_preserve = 1 */;
reg fifo_rd;
reg fifo_wr;

wire fifo_empty;
wire fifo_full;
wire [en_pos:data_end_pos] fifo_dataout;

////FIFO Component Instantiation
corefifo_lpbk corefifo_lpbk_0(
  .CLK(mtx_rx_clk),
  .DATA(fifo_datain),
  .RE(fifo_rd),
  .RESET_N(reset_n),
  .WE(fifo_wr),
  .EMPTY(fifo_empty),
  .FULL(fifo_full),
  .Q(fifo_dataout));

//State Machine to Receive data from Core_10G MAC and write into FiFO
//Data is stored as
//{o_sys_mac_rx_en,o_sys_mac_rx_sop,o_sys_mac_rx_eop,
// o_sys_mac_rx_bc,o_sys_mac_rx_data} in the FIFO

//Modified by SB   --> For FIFO version 3.1
always @(*)
begin 
  if(!reset_n) begin
    fifo_wr = 1'b0;
    fifo_datain = 75'd0;
  end else begin
    if(!fifo_full && o_sys_mac_rx_en ) begin
      fifo_datain = {o_sys_mac_rx_en,
                      o_sys_mac_rx_sop,
                      o_sys_mac_rx_eop,
                      o_sys_mac_rx_bc,
                      o_sys_mac_rx_data};
      fifo_wr = 1'b1;
    end else           
      fifo_wr = 1'b0;
  end
end 

///TX statemachine to read data from FIFO and put back on MAC TX interface
//Data is read until the FIFO is empty and the coreesponding bits are mapped to 
//MAC TX signals
always @(*)begin 
  if(!reset_n) begin
    fifo_rd = 1'b0;
  end else begin
    if((!fifo_empty) && (!i_sys_mac_tx_fifo_af))
    begin
      fifo_rd = 1'b1;
    end else begin
        fifo_rd = 1'b0;
    end
  end 
end 

assign i_sys_mac_tx_en = fifo_rd? fifo_dataout[en_pos]:1'b0;
assign i_sys_mac_tx_sop = fifo_rd? fifo_dataout[sop_pos] : 1'b0;
assign i_sys_mac_tx_eop = fifo_rd? fifo_dataout[eop_pos] : 1'b0;
assign i_sys_mac_tx_bc = fifo_rd? fifo_dataout[bc_st_pos:bc_end_pos] : 8'd0;
assign i_sys_mac_tx_data = fifo_rd? fifo_dataout[data_st_pos:data_end_pos] : 64'd0;


endmodule 

