----------------------------------------------------------------------------------
--
--  ML505 clock settings:
--
--     for 125 MHz (Gigabit Ethernet) set:
--     N0  N1  N2  M0  M1  M2  SEL1  SEL0
--     0   0   1   1   1   0   1     0
----------------------------------------------------------------------------------
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
library UNISIM;
use UNISIM.Vcomponents.ALL;
----------------------------------------------------------------------------------
ENTITY Splitter_TOP IS PORT(
    -- 125 MHz differential reference clock (SFP + SMA) --------------------------
    CLK_MGT_SFP_REF_N       : IN    STD_LOGIC;      -- H3
    CLK_MGT_SFP_REF_P       : IN    STD_LOGIC;      -- H4

    -- 125 MHz differential reference clock (PHY + Loopback) ---------------------
    CLK_MGT_PHY_REF_N       : IN    STD_LOGIC;      -- P3
    CLK_MGT_PHY_REF_P       : IN    STD_LOGIC;      -- P4

    -- SFP SGMII interface; MGT_116_0 (LX50T: X0Y4, LX110T: X0Y5) ----------------
    SFP_RX_P                : IN    STD_LOGIC;      -- G1
    SFP_RX_N                : IN    STD_LOGIC;      -- H1
    SFP_TX_P                : OUT   STD_LOGIC;      -- F2
    SFP_TX_N                : OUT   STD_LOGIC;      -- G2

    -- SMA interface; MGT_116_1 (LX50T: X0Y4, LX110T: X0Y5) ----------------------
    SMA_RX_P                : IN    STD_LOGIC;      -- K1
    SMA_RX_N                : IN    STD_LOGIC;      -- J1
    SMA_TX_P                : OUT   STD_LOGIC;      -- L2
    SMA_TX_N                : OUT   STD_LOGIC;      -- K2

    -- Marvell 88E1111 SGMII interface; MGT_112_0 (LX50T: X0Y3, LX110T: X0Y4) ----
    PHY_RX_P                : IN    STD_LOGIC;      -- N1
    PHY_RX_N                : IN    STD_LOGIC;      -- P1
    PHY_TX_P                : OUT   STD_LOGIC;      -- M2
    PHY_TX_N                : OUT   STD_LOGIC;      -- N2

    -- unused loopback interface; MGT_112_1 (LX50T: X0Y3, LX110T: X0Y4) ----------
    LOOP_RX_P               : IN    STD_LOGIC;      -- T1
    LOOP_RX_N               : IN    STD_LOGIC;      -- R1
    LOOP_TX_P               : OUT   STD_LOGIC;      -- U2
    LOOP_TX_N               : OUT   STD_LOGIC;      -- T2

    -- UART ----------------------------------------------------------------------
    UART_RXD                : IN    STD_LOGIC;
    UART_TXD                : OUT   STD_LOGIC;

    -- PHY controll --------------------------------------------------------------
    PHY_MDC                 : OUT   STD_LOGIC;        -- serial interface clock
    PHY_MDIO                : INOUT STD_LOGIC;        -- serial interface data
    PHY_RESET               : OUT   STD_LOGIC;        -- PHY HW reset, active HIGH; J14

    -- SFP controll --------------------------------------------------------------
    SFP_M1                  : OUT   STD_LOGIC;        -- SCL; serial interface clock; max 100 kHz, active rising edge
    SFP_M2                  : INOUT STD_LOGIC;        -- SDA; serial interface data
    SFP_TXDIS               : OUT   STD_LOGIC;        -- Tx disable; active H; hold for > 10 us to clear Tx Falut

  -- the following SFP ports are not routed to FPGA on ML505 board
  --SFP_M0                  : IN    STD_LOGIC;        -- L when module present
  --SFP_RS                  : OUT   STD_LOGIC;        -- Rate select; H for full-bandwidth
  --SFP_TXF                 : IN    STD_LOGIC;        -- Tx fault; active H
  --SFP_LOS                 : IN    STD_LOGIC);       -- Los of Signal; active H
    
    -- GPIO ----------------------------------------------------------------------
    GPIO_DIP                : IN    STD_LOGIC_VECTOR( 7 DOWNTO 0);
    GPIO_BTN                : IN    STD_LOGIC_VECTOR( 4 DOWNTO 0);
    GPIO_LED                : OUT   STD_LOGIC_VECTOR( 7 DOWNTO 0);
    HDR1                    : OUT   STD_LOGIC_VECTOR(31 DOWNTO 0);
    
    -- DDR2 ----------------------------------------------------------------------
    DDR2_A                  : OUT   STD_LOGIC_VECTOR(12 DOWNTO 0);
    DDR2_BA                 : OUT   STD_LOGIC_VECTOR(1 DOWNTO 0);
    DDR2_CAS_N              : OUT   STD_LOGIC;
    DDR2_CKE                : OUT   STD_LOGIC_VECTOR(0 DOWNTO 0);
    DDR2_CK_N               : OUT   STD_LOGIC_VECTOR(1 DOWNTO 0);
    DDR2_CK                 : OUT   STD_LOGIC_VECTOR(1 DOWNTO 0);
    DDR2_CS_N               : OUT   STD_LOGIC_VECTOR(0 DOWNTO 0);
    DDR2_DQ                 : INOUT STD_LOGIC_VECTOR(63 DOWNTO 0);
    DDR2_DQS_N              : INOUT STD_LOGIC_VECTOR(7 DOWNTO 0);
    DDR2_DQS                : INOUT STD_LOGIC_VECTOR(7 DOWNTO 0);
    DDR2_ODT                : OUT   STD_LOGIC_VECTOR(0 DOWNTO 0);
    DDR2_RAS_N              : OUT   STD_LOGIC;
    DDR2_WE_N               : OUT   STD_LOGIC;
    sys_rst_n               : IN    STD_LOGIC;
    sys_clk_p               : IN    STD_LOGIC;
    sys_clk_n               : IN    STD_LOGIC;
    clk200_p                : IN    STD_LOGIC;
    clk200_n                : IN    STD_LOGIC
    );
END Splitter_TOP;
--################################################################################
ARCHITECTURE Behavioral OF Splitter_TOP IS
--################################################################################
  COMPONENT Pico_sys PORT(
    clk_sys         : IN    STD_LOGIC;          -- 125 MHz system clock
    UART_RXD        : IN    STD_LOGIC;          -- RS232 Rx
    UART_TXD        : OUT   STD_LOGIC;          -- RS232 Rx
    STOP_tx         : OUT   STD_LOGIC;
    Buffer_active   : IN    STD_LOGIC;
--  PHY_MDC         : OUT   STD_LOGIC;          -- serial interface clock
--  PHY_MDIO        : INOUT STD_LOGIC;          -- serial interface data
    HOST_0_OPCODE   : OUT   STD_LOGIC_VECTOR( 1 DOWNTO 0);
    HOST_0_REQ      : OUT   STD_LOGIC;
    HOST_0_MIIMSEL  : OUT   STD_LOGIC;
    HOST_0_ADDR     : OUT   STD_LOGIC_VECTOR( 9 DOWNTO 0); 
    HOST_0_WRDATA   : OUT   STD_LOGIC_VECTOR(31 DOWNTO 0);
    HOST_0_MIIMRDY  : IN    STD_LOGIC;
    HOST_0_RDDATA   : IN    STD_LOGIC_VECTOR(31 DOWNTO 0);
    HOST_0_EMAC1SEL : OUT   STD_LOGIC;
    HOST_1_OPCODE   : OUT   STD_LOGIC_VECTOR( 1 DOWNTO 0);
    HOST_1_REQ      : OUT   STD_LOGIC;
    HOST_1_MIIMSEL  : OUT   STD_LOGIC;
    HOST_1_ADDR     : OUT   STD_LOGIC_VECTOR( 9 DOWNTO 0); 
    HOST_1_WRDATA   : OUT   STD_LOGIC_VECTOR(31 DOWNTO 0);
    HOST_1_MIIMRDY  : IN    STD_LOGIC;
    HOST_1_RDDATA   : IN    STD_LOGIC_VECTOR(31 DOWNTO 0);
    HOST_1_EMAC1SEL : OUT   STD_LOGIC;
    SFP_M0          : IN    STD_LOGIC;          -- L when module present
    SFP_M1          : OUT   STD_LOGIC;          -- SCL; serial interface clock; max 100 kHz, active rising edge
    SFP_M2          : INOUT STD_LOGIC;          -- SDA; serial interface data
    SFP_RS          : OUT   STD_LOGIC;          -- Rate select; H for full-bandwidth
    SFP_TXDIS       : OUT   STD_LOGIC;          -- Tx disable; active H; hold for > 10 us to clear Tx Falut
    SFP_TXF         : IN    STD_LOGIC;          -- Tx fault; active H
    SFP_LOS         : IN    STD_LOGIC);         -- Los of Signal; active H

  END COMPONENT;
  --------------------------------------------------------------------------------
  component TEMAC_SGMII_block is
   port(
      -- EMAC0 Clocking
      -- 125MHz clock output from transceiver
      CLK125_OUT                      : out std_logic;
      -- 125MHz clock input from BUFG
      CLK125                          : in  std_logic;
      -- Tri-speed clock output from EMAC0
      CLIENT_CLK_OUT_0                : out std_logic;
      -- EMAC0 Tri-speed clock input from BUFG
      CLIENT_CLK_0                    : in  std_logic;

      -- Client Receiver Interface - EMAC0
      EMAC0CLIENTRXD                  : out std_logic_vector(7 downto 0);
      EMAC0CLIENTRXDVLD               : out std_logic;
      EMAC0CLIENTRXGOODFRAME          : out std_logic;
      EMAC0CLIENTRXBADFRAME           : out std_logic;
      EMAC0CLIENTRXFRAMEDROP          : out std_logic;
      EMAC0CLIENTRXSTATS              : out std_logic_vector(6 downto 0);
      EMAC0CLIENTRXSTATSVLD           : out std_logic;
      EMAC0CLIENTRXSTATSBYTEVLD       : out std_logic;

      -- Client Transmitter Interface - EMAC0
      CLIENTEMAC0TXD                  : in  std_logic_vector(7 downto 0);
      CLIENTEMAC0TXDVLD               : in  std_logic;
      EMAC0CLIENTTXACK                : out std_logic;
      CLIENTEMAC0TXFIRSTBYTE          : in  std_logic;
      CLIENTEMAC0TXUNDERRUN           : in  std_logic;
      EMAC0CLIENTTXCOLLISION          : out std_logic;
      EMAC0CLIENTTXRETRANSMIT         : out std_logic;
      CLIENTEMAC0TXIFGDELAY           : in  std_logic_vector(7 downto 0);
      EMAC0CLIENTTXSTATS              : out std_logic;
      EMAC0CLIENTTXSTATSVLD           : out std_logic;
      EMAC0CLIENTTXSTATSBYTEVLD       : out std_logic;

      -- MAC Control Interface - EMAC0
      CLIENTEMAC0PAUSEREQ             : in  std_logic;
      CLIENTEMAC0PAUSEVAL             : in  std_logic_vector(15 downto 0);

      --EMAC-MGT link status
      EMAC0CLIENTSYNCACQSTATUS        : out std_logic;
      -- EMAC0 Interrupt
      EMAC0ANINTERRUPT                : out std_logic;

      -- Clock Signals - EMAC0
      -- SGMII Interface - EMAC0
      TXP_0                           : out std_logic;
      TXN_0                           : out std_logic;
      RXP_0                           : in  std_logic;
      RXN_0                           : in  std_logic;
      PHYAD_0                         : in  std_logic_vector(4 downto 0);
      RESETDONE_0                     : out std_logic;

      -- unused transceiver
      TXN_1_UNUSED                    : out std_logic;
      TXP_1_UNUSED                    : out std_logic;
      RXN_1_UNUSED                    : in  std_logic;
      RXP_1_UNUSED                    : in  std_logic;

      -- MDIO Interface - EMAC0
      MDC_0                           : out std_logic;
      MDIO_0_I                        : in  std_logic;
      MDIO_0_O                        : out std_logic;
      MDIO_0_T                        : out std_logic;

      -- Generic Host Interface
      HOSTCLK                         : in  std_logic;
      HOSTOPCODE                      : in  std_logic_vector(1 downto 0);
      HOSTREQ                         : in  std_logic;
      HOSTMIIMSEL                     : in  std_logic;
      HOSTADDR                        : in  std_logic_vector(9 downto 0);
      HOSTWRDATA                      : in  std_logic_vector(31 downto 0);
      HOSTMIIMRDY                     : out std_logic;
      HOSTRDDATA                      : out std_logic_vector(31 downto 0);
      HOSTEMAC1SEL                    : in  std_logic;
      -- SGMII RocketIO Reference Clock buffer inputs
      CLK_DS                          : in  std_logic;

      -- RocketIO Reset input
      GTRESET                         : in  std_logic;

      -- Asynchronous Reset
      RESET                           : in  std_logic
   );
  end component;
  --------------------------------------------------------------------------------
  COMPONENT eth_fifo_8 IS
	PORT(
      -- Transmit FIFO MAC TX Interface
      tx_clk                        : IN std_logic;
      tx_reset                      : IN std_logic;
      tx_enable                     : IN std_logic;
      tx_ack                        : IN std_logic;
      tx_collision                  : IN std_logic;
      tx_retransmit                 : IN std_logic;
      tx_data                       : OUT std_logic_vector(7 downto 0);
      tx_data_valid                 : OUT std_logic;
      tx_underrun                   : OUT std_logic;     
      
      -- Receive FIFO MAC RX Interface
      rx_clk                        : IN std_logic;
      rx_reset                      : IN std_logic;
      rx_enable                     : IN std_logic;
      rx_data                       : IN std_logic_vector(7 downto 0);
      rx_data_valid                 : IN std_logic;
      rx_good_frame                 : IN std_logic;
      rx_bad_frame                  : IN std_logic;
      rx_overflow                   : OUT std_logic;
      
      -- Transmit FIFO Local-link Interface
      tx_ll_clock                   : in  std_logic;  -- Local link write clock
      tx_ll_reset                   : in  std_logic;  -- synchronous reset (tx_ll_clock)
      tx_ll_data_in                 : in  std_logic_vector(7 downto 0);  -- Data to Tx FIFO
      tx_ll_sof_in_n                : in  std_logic;  -- sof indicator to FIFO
      tx_ll_eof_in_n                : in  std_logic;  -- eof indicator to FIFO
      tx_ll_src_rdy_in_n            : in  std_logic;  -- src ready indicator to FIFO
      tx_ll_dst_rdy_out_n           : out std_logic;  -- dst ready indicator from FIFO
      tx_fifo_status                : out std_logic_vector(3 downto 0);  -- FIFO memory status
      tx_overflow                   : out std_logic;  -- FIFO overflow indicator from FIFO
      
      -- Receive FIFO Local-link Interface
      rx_ll_clock                   : in  std_logic;  -- Local link read clock
      rx_ll_reset                   : in  std_logic;  -- synchronous reset (rx_ll_clock)
      rx_ll_data_out                : out std_logic_vector(7 downto 0);  -- Data from Rx FIFO
      rx_ll_sof_out_n               : out std_logic;  -- sof indicator from FIFO
      rx_ll_eof_out_n               : out std_logic;  -- eof indicator from FIFO
      rx_ll_src_rdy_out_n           : out std_logic;  -- src ready indicator from FIFO
      rx_ll_dst_rdy_in_n            : in  std_logic;  -- dst ready indicator to FIFO
      rx_fifo_status                : out std_logic_vector(3 downto 0)  -- FIFO memory status
	);
	END COMPONENT;
    
    COMPONENT DDR2_FSM
	PORT(
		FSM_in_clk          : IN std_logic;
		FSM_in_rst          : IN std_logic;
		FSM_in_data         : IN std_logic_vector(7 downto 0);
		FSM_in_sof          : IN std_logic;
		FSM_in_eof          : IN std_logic;
		FSM_in_src_rdy      : IN std_logic;
		FSM_out_clk         : IN std_logic;
		FSM_out_rst         : IN std_logic;
		FSM_out_dst_rdy     : IN std_logic;
		DDR2_sys_rst_n      : IN std_logic;
		DDR2_clk_sys        : IN std_logic;
		DDR2_clk_200        : IN std_logic;    
		DDR2_dq             : INOUT std_logic_vector(63 downto 0);
		DDR2_dqs_n          : INOUT std_logic_vector(7 downto 0);
		DDR2_dqs            : INOUT std_logic_vector(7 downto 0);      
		FSM_in_dst_rdy      : OUT std_logic;
		FSM_out_data        : OUT std_logic_vector(7 downto 0);
		FSM_out_sof         : OUT std_logic;
		FSM_out_eof         : OUT std_logic;
		FSM_out_src_rdy     : OUT std_logic;
		DDR2_a              : OUT std_logic_vector(12 downto 0);
		DDR2_ba             : OUT std_logic_vector(1 downto 0);
		DDR2_cas_n          : OUT std_logic;
		DDR2_cke            : OUT std_logic_vector(0 to 0);
		DDR2_ck_n           : OUT std_logic_vector(1 downto 0);
		DDR2_ck             : OUT std_logic_vector(1 downto 0);
		DDR2_cs_n           : OUT std_logic_vector(0 to 0);
		DDR2_odt            : OUT std_logic_vector(0 to 0);
		DDR2_ras_n          : OUT std_logic;
		DDR2_we_n           : OUT std_logic;
		DDR2_interface_rst  : OUT std_logic
		);
	END COMPONENT;

--################################################################################
  
  SIGNAL CLK_DDR2_SYS           : STD_LOGIC;
  SIGNAL CLK_DDR2_200           : STD_LOGIC;
  
  SIGNAL CLK_125_OUT_SFP        : STD_LOGIC;
  SIGNAL CLK_125_SYS_SFP        : STD_LOGIC;        -- 125 MHz global clock (derived from SFP)
  SIGNAL CLK_TX_SFP_MAC_OUT     : STD_LOGIC;
  SIGNAL CLK_TX_SFP             : STD_LOGIC;        -- Tri-speed global clock (derived from SFP)
  SIGNAL GTP_REFCLK_SFP         : STD_LOGIC;

  SIGNAL CLK_125_OUT_PHY        : STD_LOGIC;
  SIGNAL CLK_125_SYS_PHY        : STD_LOGIC;        -- 125 MHz global clock (derived from PHY)
  SIGNAL CLK_TX_PHY_MAC_OUT     : STD_LOGIC;
  SIGNAL CLK_TX_PHY             : STD_LOGIC;        -- Tri-speed global clock (derived from PHY)
  SIGNAL GTP_REFCLK_PHY         : STD_LOGIC;

  SIGNAL SFP_TX_DATA            : STD_LOGIC_VECTOR( 7 DOWNTO 0);
  SIGNAL SFP_TX_DV              : STD_LOGIC;
  SIGNAL SFP_TX_ACK             : STD_LOGIC;

  SIGNAL PHY_TX_DATA            : STD_LOGIC_VECTOR( 7 DOWNTO 0);
  SIGNAL PHY_TX_DV              : STD_LOGIC;
  SIGNAL PHY_TX_ACK             : STD_LOGIC;


  SIGNAL cnt_CLK_TX_SFP         : STD_LOGIC_VECTOR(23 DOWNTO 0) := (OTHERS => '0');
  SIGNAL LED_CLK_TX_SFP         : STD_LOGIC := '0';

  SIGNAL cnt_CLK_TX_PHY         : STD_LOGIC_VECTOR(23 DOWNTO 0) := (OTHERS => '0');
  SIGNAL LED_CLK_TX_PHY         : STD_LOGIC := '0';

  SIGNAL cnt_CLK_125_SYS_SFP    : STD_LOGIC_VECTOR(27 DOWNTO 0) := (OTHERS => '0');
  SIGNAL LED_CLK_125_SYS_SFP    : STD_LOGIC := '0';

  SIGNAL cnt_CLK_125_SYS_PHY    : STD_LOGIC_VECTOR(27 DOWNTO 0) := (OTHERS => '0');
  SIGNAL LED_CLK_125_SYS_PHY    : STD_LOGIC := '0';


  SIGNAL LED_SYNC_STATUS_SFP    : STD_LOGIC := '0';
  SIGNAL LED_SYNC_STATUS_PHY    : STD_LOGIC := '0';

  SIGNAL ANEG_IRQ_SFP           : STD_LOGIC;
  SIGNAL ANEG_IRQ_PHY           : STD_LOGIC;

  SIGNAL LED_ANEG_IRQ_SFP       : STD_LOGIC := '0';
  SIGNAL LED_ANEG_IRQ_PHY       : STD_LOGIC := '0';

--  SIGNAL cnt_LED_ANEG_IRQ_SFP   : STD_LOGIC_VECTOR(23 DOWNTO 0) := (OTHERS => '0');
--  SIGNAL cnt_LED_ANEG_IRQ_PHY   : STD_LOGIC_VECTOR(23 DOWNTO 0) := (OTHERS => '0');


  SIGNAL HOST_0_OPCODE          : STD_LOGIC_VECTOR( 1 DOWNTO 0);
  SIGNAL HOST_0_REQ             : STD_LOGIC;
  SIGNAL HOST_0_MIIMSEL         : STD_LOGIC;
  SIGNAL HOST_0_ADDR            : STD_LOGIC_VECTOR( 9 DOWNTO 0);
  SIGNAL HOST_0_WRDATA          : STD_LOGIC_VECTOR(31 DOWNTO 0);
  SIGNAL HOST_0_MIIMRDY         : STD_LOGIC;
  SIGNAL HOST_0_RDDATA          : STD_LOGIC_VECTOR(31 DOWNTO 0);
  SIGNAL HOST_0_EMAC1SEL        : STD_LOGIC;
             
  SIGNAL HOST_1_OPCODE          : STD_LOGIC_VECTOR( 1 DOWNTO 0);
  SIGNAL HOST_1_REQ             : STD_LOGIC;
  SIGNAL HOST_1_MIIMSEL         : STD_LOGIC;
  SIGNAL HOST_1_ADDR            : STD_LOGIC_VECTOR( 9 DOWNTO 0);
  SIGNAL HOST_1_WRDATA          : STD_LOGIC_VECTOR(31 DOWNTO 0);
  SIGNAL HOST_1_MIIMRDY         : STD_LOGIC;
  SIGNAL HOST_1_RDDATA          : STD_LOGIC_VECTOR(31 DOWNTO 0);
  SIGNAL HOST_1_EMAC1SEL        : STD_LOGIC;

--SIGNAL MDIO_0_I               : STD_LOGIC;
--SIGNAL MDIO_0_O               : STD_LOGIC;
--SIGNAL MDIO_0_T               : STD_LOGIC;

  SIGNAL MDIO_1_I               : STD_LOGIC;
  SIGNAL MDIO_1_O               : STD_LOGIC;
  SIGNAL MDIO_1_T               : STD_LOGIC;
  
  SIGNAL PHY_TX_UNDERRUN        : STD_LOGIC;
  SIGNAL PHY_TX_COLLISION       : STD_LOGIC;
  SIGNAL PHY_TX_RETRANSMIT      : STD_LOGIC;
  
  SIGNAL PHY_RX_DATA            : STD_LOGIC_VECTOR(7 DOWNTO 0);
  SIGNAL PHY_RX_DV              : STD_LOGIC;
  SIGNAL PHY_RX_GOODFRAME       : STD_LOGIC;
  SIGNAL PHY_RX_BADFRAME        : STD_LOGIC;
  
  SIGNAL SFP_TX_UNDERRUN        : STD_LOGIC;
  SIGNAL SFP_TX_COLLISION       : STD_LOGIC;
  SIGNAL SFP_TX_RETRANSMIT      : STD_LOGIC;
  
  SIGNAL SFP_RX_DATA            : STD_LOGIC_VECTOR(7 DOWNTO 0);
  SIGNAL SFP_RX_DV              : STD_LOGIC;
  SIGNAL SFP_RX_GOODFRAME       : STD_LOGIC;
  SIGNAL SFP_RX_BADFRAME        : STD_LOGIC;
  
  SIGNAL toPHY_data             : STD_LOGIC_VECTOR(7 DOWNTO 0);
  SIGNAL toPHY_sof              : STD_LOGIC;
  SIGNAL toPHY_eof              : STD_LOGIC;
  SIGNAL toPHY_src_rd           : STD_LOGIC;
  SIGNAL toPHY_dst_rd           : STD_LOGIC;
  
  SIGNAL toSFP_data             : STD_LOGIC_VECTOR(7 DOWNTO 0);
  SIGNAL toSFP_sof              : STD_LOGIC;
  SIGNAL toSFP_eof              : STD_LOGIC;
  SIGNAL toSFP_src_rd           : STD_LOGIC;
  SIGNAL toSFP_dst_rd           : STD_LOGIC;
  
  SIGNAL fromPHY_data           : STD_LOGIC_VECTOR(7 DOWNTO 0);
  SIGNAL fromPHY_sof            : STD_LOGIC;
  SIGNAL fromPHY_eof            : STD_LOGIC;
  SIGNAL fromPHY_src_rd         : STD_LOGIC;
  SIGNAL fromPHY_dst_rd         : STD_LOGIC;
  
  SIGNAL DDR2_RST_OUT           : STD_LOGIC;
  
  SIGNAL BUFF_ACT               : STD_LOGIC;
  SIGNAL STOP_TX                : STD_LOGIC;

--################################################################################
BEGIN
--################################################################################

  CLKSYS_DDR2_IBUFGDS : IBUFGDS PORT MAP(
    O  => CLK_DDR2_SYS,
    I  => sys_clk_p,
    IB => sys_clk_n);
    
  CLK200_DDR2_IBUFGDS : IBUFGDS PORT MAP(
    O  => CLK_DDR2_200,
    I  => clk200_p,
    IB => clk200_n);

  --------------------------------------------------------------------------------
  -- Ethernet FIFO 8 (from SFP to PHY)
  SFPtoPHY_eth_fifo_8: eth_fifo_8 PORT MAP(
	tx_clk              => CLK_TX_PHY,
	tx_reset            => '0',
	tx_enable           => '1',
	tx_data             => PHY_TX_DATA,
	tx_data_valid       => PHY_TX_DV,
	tx_ack              => PHY_TX_ACK,
	tx_underrun         => PHY_TX_UNDERRUN,
	tx_collision        => PHY_TX_COLLISION,
	tx_retransmit       => PHY_TX_RETRANSMIT,
	
	rx_clk              => CLK_TX_SFP,
	rx_reset            => '0',
	rx_enable           => '1',
	rx_data             => SFP_RX_DATA,
	rx_data_valid       => SFP_RX_DV,
	rx_good_frame       => SFP_RX_GOODFRAME,
	rx_bad_frame        => SFP_RX_BADFRAME,
	rx_overflow         => OPEN,
    
    tx_ll_clock         => CLK_125_SYS_SFP,                
    tx_ll_reset         => '0',            
    tx_ll_data_in       => toPHY_data,     
    tx_ll_sof_in_n      => toPHY_sof,      
    tx_ll_eof_in_n      => toPHY_eof,      
    tx_ll_src_rdy_in_n  => toPHY_src_rd,   
    tx_ll_dst_rdy_out_n => toPHY_dst_rd,   
    tx_fifo_status      => OPEN,           
    tx_overflow         => OPEN,           
    
    rx_ll_clock         => CLK_125_SYS_SFP,                
    rx_ll_reset         => '0',            
    rx_ll_data_out      => toPHY_data,     
    rx_ll_sof_out_n     => toPHY_sof,      
    rx_ll_eof_out_n     => toPHY_eof,      
    rx_ll_src_rdy_out_n => toPHY_src_rd,   
    rx_ll_dst_rdy_in_n  => toPHY_dst_rd,   
    rx_fifo_status      => OPEN            
  );
  
  --------------------------------------------------------------------------------
  -- Ethernet FIFO 8 (from PHY to SFP)
  PHYtoSFP_eth_fifo_8: eth_fifo_8  PORT MAP(
	tx_clk              => CLK_TX_SFP,
	tx_reset            => '0',
	tx_enable           => STOP_TX,
	tx_data             => SFP_TX_DATA,
	tx_data_valid       => SFP_TX_DV,
	tx_ack              => SFP_TX_ACK,
	tx_underrun         => SFP_TX_UNDERRUN,
	tx_collision        => SFP_TX_COLLISION,
	tx_retransmit       => SFP_TX_RETRANSMIT,
	
	rx_clk              => CLK_TX_PHY,
	rx_reset            => '0',
	rx_enable           => '1',
	rx_data             => PHY_RX_DATA,
	rx_data_valid       => PHY_RX_DV,
	rx_good_frame       => PHY_RX_GOODFRAME,
	rx_bad_frame        => PHY_RX_BADFRAME,
	rx_overflow         => OPEN,
    
    tx_ll_clock         => CLK_125_SYS_SFP,                
    tx_ll_reset         => '0',            
    tx_ll_data_in       => toSFP_data,     
    tx_ll_sof_in_n      => toSFP_sof,      
    tx_ll_eof_in_n      => toSFP_eof,      
    tx_ll_src_rdy_in_n  => toSFP_src_rd,   
    tx_ll_dst_rdy_out_n => toSFP_dst_rd,   
    tx_fifo_status      => OPEN,           
    tx_overflow         => OPEN,           
    
    rx_ll_clock         => CLK_125_SYS_SFP,                
    rx_ll_reset         => '0',            
    rx_ll_data_out      => fromPHY_data,     
    rx_ll_sof_out_n     => fromPHY_sof,      
    rx_ll_eof_out_n     => fromPHY_eof,      
    rx_ll_src_rdy_out_n => fromPHY_src_rd,   
    rx_ll_dst_rdy_in_n  => fromPHY_dst_rd,   
    rx_fifo_status      => OPEN            
  );
  
  Inst_DDR2_FSM: DDR2_FSM PORT MAP(
		FSM_in_clk          => CLK_125_SYS_SFP,
		FSM_in_rst          => '0',
		FSM_in_data         => fromPHY_data,
		FSM_in_sof          => fromPHY_sof,
		FSM_in_eof          => fromPHY_eof,
		FSM_in_src_rdy      => fromPHY_src_rd,
		FSM_in_dst_rdy      => fromPHY_dst_rd,
		FSM_out_clk         => CLK_125_SYS_SFP,
		FSM_out_rst         => '0',
		FSM_out_data        => toSFP_data,
		FSM_out_sof         => toSFP_sof,
		FSM_out_eof         => toSFP_eof,
		FSM_out_src_rdy     => toSFP_src_rd,
		FSM_out_dst_rdy     => toSFP_dst_rd,
		DDR2_a              => DDR2_A,
		DDR2_ba             => DDR2_BA,
		DDR2_cas_n          => DDR2_CAS_N,
		DDR2_cke            => DDR2_CKE,
		DDR2_ck_n           => DDR2_CK_N,
		DDR2_ck             => DDR2_CK,
		DDR2_cs_n           => DDR2_CS_N,
		DDR2_dq             => DDR2_DQ,
		DDR2_dqs_n          => DDR2_DQS_N,
		DDR2_dqs            => DDR2_DQS,
		DDR2_odt            => DDR2_ODT,
		DDR2_ras_n          => DDR2_RAS_N,
		DDR2_we_n           => DDR2_WE_N,
		DDR2_sys_rst_n      => sys_rst_n,
		DDR2_clk_sys        => CLK_DDR2_SYS,
		DDR2_clk_200        => CLK_DDR2_200,
		DDR2_interface_rst  => DDR2_RST_OUT
	);


--################################################################################
-- SFP MAC and its clocking circuitry

  REFCLK_SFP_IBUFGDS : IBUFGDS PORT MAP(
        O  => GTP_REFCLK_SFP,
        I  => CLK_MGT_SFP_REF_P,
        IB => CLK_MGT_SFP_REF_N);

  TX_CLK_SFP_BUFG : BUFG PORT MAP(
        O  => CLK_TX_SFP,
        I  => CLK_TX_SFP_MAC_OUT);

  CLK_125_SFP_BUFG : BUFG PORT MAP(
        O  => CLK_125_SYS_SFP,
        I  => CLK_125_OUT_SFP);

    SFP_TEMAC : TEMAC_SGMII_block PORT MAP (

      CLK125_OUT                      => CLK_125_OUT_SFP,       -- 125MHz clock output from transceiver (refclkout form GTP transceiver)
      CLK125                          => CLK_125_SYS_SFP,       -- 125MHz clock input from BUFG (GTP USRCLK2)
      CLIENT_CLK_OUT_0                => CLK_TX_SFP_MAC_OUT,    -- Tri-speed clock output from EMAC0 (EMAC0CLIENTTXCLIENTCLKOUT)
      CLIENT_CLK_0                    => CLK_TX_SFP,            -- EMAC0 Tri-speed clock input from BUFG (MAC Rx and Tx client clock)

      EMAC0CLIENTRXD                  => SFP_RX_DATA,                  -- Client Receiver Interface - EMAC0
      EMAC0CLIENTRXDVLD               => SFP_RX_DV,
      EMAC0CLIENTRXGOODFRAME          => SFP_RX_GOODFRAME,
      EMAC0CLIENTRXBADFRAME           => SFP_RX_BADFRAME,
      EMAC0CLIENTRXFRAMEDROP          => OPEN,
      EMAC0CLIENTRXSTATS              => OPEN,
      EMAC0CLIENTRXSTATSVLD           => OPEN,
      EMAC0CLIENTRXSTATSBYTEVLD       => OPEN,

      CLIENTEMAC0TXD                  => SFP_TX_DATA,           -- Client Transmitter Interface - EMAC0
      CLIENTEMAC0TXDVLD               => SFP_TX_DV,
      EMAC0CLIENTTXACK                => SFP_TX_ACK,
      CLIENTEMAC0TXFIRSTBYTE          => '0',                   -- tie low (see ug194, page 33)
      CLIENTEMAC0TXUNDERRUN           => SFP_TX_UNDERRUN,       -- assert to force data corruption
      EMAC0CLIENTTXCOLLISION          => SFP_TX_COLLISION,
      EMAC0CLIENTTXRETRANSMIT         => SFP_TX_RETRANSMIT,
      CLIENTEMAC0TXIFGDELAY           => X"00",
      EMAC0CLIENTTXSTATS              => OPEN,
      EMAC0CLIENTTXSTATSVLD           => OPEN,
      EMAC0CLIENTTXSTATSBYTEVLD       => OPEN,

      CLIENTEMAC0PAUSEREQ             => '0',                   -- MAC Control Interface - EMAC0
      CLIENTEMAC0PAUSEVAL             => X"0000",

      EMAC0CLIENTSYNCACQSTATUS        => LED_SYNC_STATUS_SFP,   -- EMAC-MGT link status
      EMAC0ANINTERRUPT                => ANEG_IRQ_SFP,          -- EMAC0 Interrupt

      TXP_0                           => SFP_TX_P,              -- SGMII Interface - EMAC0
      TXN_0                           => SFP_TX_N,
      RXP_0                           => SFP_RX_P,
      RXN_0                           => SFP_RX_N,
      PHYAD_0                         => "00001",
      RESETDONE_0                     => OPEN,

      TXN_1_UNUSED                    => SMA_TX_N,              -- unused transceiver
      TXP_1_UNUSED                    => SMA_TX_P,
      RXN_1_UNUSED                    => SMA_RX_N,
      RXP_1_UNUSED                    => SMA_RX_P,

--      MDC_0                           => SFP_M1,
--      MDIO_0_I                        => MDIO_0_I,
--      MDIO_0_O                        => MDIO_0_O,
--      MDIO_0_T                        => MDIO_0_T,
      MDC_0                           => OPEN,
      MDIO_0_I                        => '1',
      MDIO_0_O                        => OPEN,
      MDIO_0_T                        => OPEN,

      HOSTCLK                         => CLK_125_SYS_SFP,       -- Generic Host Interface
      HOSTOPCODE                      => HOST_0_OPCODE,
      HOSTREQ                         => HOST_0_REQ,
      HOSTMIIMSEL                     => HOST_0_MIIMSEL,
      HOSTADDR                        => HOST_0_ADDR,
      HOSTWRDATA                      => HOST_0_WRDATA,
      HOSTMIIMRDY                     => HOST_0_MIIMRDY,
      HOSTRDDATA                      => HOST_0_RDDATA,
      HOSTEMAC1SEL                    => HOST_0_EMAC1SEL,

--    HOSTOPCODE                      => "00",
--    HOSTREQ                         => '0',
--    HOSTMIIMSEL                     => '0',                   -- 0 for MAC access, 1 for MDIO access
--    HOSTADDR                        => "0000000000",
--    HOSTWRDATA                      => X"00000000",
--    HOSTMIIMRDY                     => OPEN,
--    HOSTRDDATA                      => OPEN,
--    HOSTEMAC1SEL                    => '0',                   -- MAC 0/1 select

      CLK_DS                          => GTP_REFCLK_SFP,        -- SGMII RocketIO Reference Clock buffer inputs
      GTRESET                         => '0',                   -- RocketIO Reset input
      RESET                           => '0');                  -- Asynchronous Reset

--  OBUFT_SFP : OBUFT PORT MAP(
--      O  => SFP_M2,
--      I  => MDIO_0_O,
--      T  => MDIO_0_T);
--
--  IBUF_SFP : IBUF PORT MAP(
--      O  => MDIO_0_I,
--      I  => SFP_M2);

--################################################################################

-- PHY MAC and its clocking circuitry

  REFCLK_PHY_IBUFGDS : IBUFGDS PORT MAP(
        O  => GTP_REFCLK_PHY,
        I  => CLK_MGT_PHY_REF_P,
        IB => CLK_MGT_PHY_REF_N);

  TX_CLK_PHY_BUFG : BUFG PORT MAP(
        O  => CLK_TX_PHY,
        I  => CLK_TX_PHY_MAC_OUT);

  CLK_125_PHY_BUFG : BUFG PORT MAP(
        O  => CLK_125_SYS_PHY,
        I  => CLK_125_OUT_PHY);

    PHY_TEMAC : TEMAC_SGMII_block PORT MAP (

      CLK125_OUT                      => CLK_125_OUT_PHY,       -- 125MHz clock output from transceiver (refclkout form GTP transceiver)
      CLK125                          => CLK_125_SYS_PHY,       -- 125MHz clock input from BUFG (GTP USRCLK2)
      CLIENT_CLK_OUT_0                => CLK_TX_PHY_MAC_OUT,    -- Tri-speed clock output from EMAC0 (EMAC0CLIENTTXCLIENTCLKOUT)
      CLIENT_CLK_0                    => CLK_TX_PHY,            -- EMAC0 Tri-speed clock input from BUFG (MAC Rx and Tx client clock)

      EMAC0CLIENTRXD                  => PHY_RX_DATA,           -- Client Receiver Interface - EMAC0
      EMAC0CLIENTRXDVLD               => PHY_RX_DV,
      EMAC0CLIENTRXGOODFRAME          => PHY_RX_GOODFRAME,
      EMAC0CLIENTRXBADFRAME           => PHY_RX_BADFRAME,
      EMAC0CLIENTRXFRAMEDROP          => OPEN,
      EMAC0CLIENTRXSTATS              => OPEN,
      EMAC0CLIENTRXSTATSVLD           => OPEN,
      EMAC0CLIENTRXSTATSBYTEVLD       => OPEN,

      CLIENTEMAC0TXD                  => PHY_TX_DATA,           -- Client Transmitter Interface - EMAC0
      CLIENTEMAC0TXDVLD               => PHY_TX_DV,
      EMAC0CLIENTTXACK                => PHY_TX_ACK,
      CLIENTEMAC0TXFIRSTBYTE          => '0',                   -- tie low (see ug194, page 33)
      CLIENTEMAC0TXUNDERRUN           => PHY_TX_UNDERRUN,       -- assert to force data corruption
      EMAC0CLIENTTXCOLLISION          => PHY_TX_COLLISION,
      EMAC0CLIENTTXRETRANSMIT         => PHY_TX_RETRANSMIT,
      CLIENTEMAC0TXIFGDELAY           => X"00",
      EMAC0CLIENTTXSTATS              => OPEN,
      EMAC0CLIENTTXSTATSVLD           => OPEN,
      EMAC0CLIENTTXSTATSBYTEVLD       => OPEN,

      CLIENTEMAC0PAUSEREQ             => '0',                   -- MAC Control Interface - EMAC0
      CLIENTEMAC0PAUSEVAL             => X"0000",

      EMAC0CLIENTSYNCACQSTATUS        => LED_SYNC_STATUS_PHY,   -- EMAC-MGT link status
      EMAC0ANINTERRUPT                => ANEG_IRQ_PHY,          -- EMAC0 Interrupt

      TXP_0                           => PHY_TX_P,              -- SGMII Interface - EMAC0
      TXN_0                           => PHY_TX_N,
      RXP_0                           => PHY_RX_P,
      RXN_0                           => PHY_RX_N,
      PHYAD_0                         => "00001",
      RESETDONE_0                     => OPEN,

      TXN_1_UNUSED                    => LOOP_TX_N,             -- unused transceiver
      TXP_1_UNUSED                    => LOOP_TX_P,
      RXN_1_UNUSED                    => LOOP_RX_N,
      RXP_1_UNUSED                    => LOOP_RX_P,

      MDC_0                           => PHY_MDC,
      MDIO_0_I                        => MDIO_1_I,
      MDIO_0_O                        => MDIO_1_O,
      MDIO_0_T                        => MDIO_1_T,

      HOSTCLK                         => CLK_125_SYS_SFP,       -- Generic Host Interface
      HOSTOPCODE                      => HOST_1_OPCODE,
      HOSTREQ                         => HOST_1_REQ,
      HOSTMIIMSEL                     => HOST_1_MIIMSEL,
      HOSTADDR                        => HOST_1_ADDR,
      HOSTWRDATA                      => HOST_1_WRDATA,
      HOSTMIIMRDY                     => HOST_1_MIIMRDY,
      HOSTRDDATA                      => HOST_1_RDDATA,
      HOSTEMAC1SEL                    => HOST_1_EMAC1SEL,

--    HOSTOPCODE                      => "00",
--    HOSTREQ                         => '0',
--    HOSTMIIMSEL                     => '0',                   -- 0 for MAC access, 1 for MDIO access
--    HOSTADDR                        => "0000000000",
--    HOSTWRDATA                      => X"00000000",
--    HOSTMIIMRDY                     => OPEN,
--    HOSTRDDATA                      => OPEN,
--    HOSTEMAC1SEL                    => '0',                   -- MAC 0/1 select

      CLK_DS                          => GTP_REFCLK_PHY,        -- SGMII RocketIO Reference Clock buffer inputs
      GTRESET                         => '0',                   -- RocketIO Reset input
      RESET                           => '0');                  -- Asynchronous Reset

  OBUFT_PHY : OBUFT PORT MAP(
      O  => PHY_MDIO,
      I  => MDIO_1_O,
      T  => MDIO_1_T);

  IBUF_PHY : IBUF PORT MAP(
      O  => MDIO_1_I,
      I  => PHY_MDIO);

  PHY_RESET <= '1';

--################################################################################
-- PicoBlaze with 2xI2C (PHY + SFP) and UART

  Pico : Pico_sys PORT MAP(
    clk_sys                 => CLK_125_SYS_SFP,
    UART_RXD                => UART_RXD,
    UART_TXD                => UART_TXD,
    STOP_tx                 => STOP_TX,
    Buffer_active           => BUFF_ACT,
--  PHY_MDC                 => PHY_MDC,
--  PHY_MDIO                => PHY_MDIO,

    HOST_0_OPCODE           => HOST_0_OPCODE,
    HOST_0_REQ              => HOST_0_REQ,
    HOST_0_MIIMSEL          => HOST_0_MIIMSEL,
    HOST_0_ADDR             => HOST_0_ADDR,
    HOST_0_WRDATA           => HOST_0_WRDATA,
    HOST_0_MIIMRDY          => HOST_0_MIIMRDY,
    HOST_0_RDDATA           => HOST_0_RDDATA,
    HOST_0_EMAC1SEL         => HOST_0_EMAC1SEL,
                                   
    HOST_1_OPCODE           => HOST_1_OPCODE,
    HOST_1_REQ              => HOST_1_REQ,
    HOST_1_MIIMSEL          => HOST_1_MIIMSEL,
    HOST_1_ADDR             => HOST_1_ADDR,
    HOST_1_WRDATA           => HOST_1_WRDATA,
    HOST_1_MIIMRDY          => HOST_1_MIIMRDY,
    HOST_1_RDDATA           => HOST_1_RDDATA,
    HOST_1_EMAC1SEL         => HOST_1_EMAC1SEL,

    SFP_M0                  => '0',             -- unconnected on ML505
    SFP_M1                  => SFP_M1,          -- clock
    SFP_M2                  => SFP_M2,          -- data
    SFP_RS                  => OPEN,            -- unconnected on ML505
    SFP_TXDIS               => SFP_TXDIS,
    SFP_TXF                 => '0',             -- unconnected on ML505
    SFP_LOS                 => '0');            -- unconnected on ML505

--################################################################################


  --------------------------------------------------------------------------------
  -- Tri-speed clock check (5 Hz for 125 MHz, 0,5 Hz for 12,5 MHz)

  PROCESS(CLK_TX_SFP) BEGIN
    IF rising_edge(CLK_TX_SFP) THEN
      IF cnt_CLK_TX_SFP = X"5F5E10" THEN
        cnt_CLK_TX_SFP <= X"000000";
        LED_CLK_TX_SFP <= NOT LED_CLK_TX_SFP;
      ELSE
        cnt_CLK_TX_SFP <= cnt_CLK_TX_SFP + 1;
      END IF;
    END IF;
  END PROCESS;


  PROCESS(CLK_TX_PHY) BEGIN
    IF rising_edge(CLK_TX_PHY) THEN
      IF cnt_CLK_TX_PHY = X"5F5E10" THEN
        cnt_CLK_TX_PHY <= X"000000";
        LED_CLK_TX_PHY <= NOT LED_CLK_TX_PHY;
      ELSE
        cnt_CLK_TX_PHY <= cnt_CLK_TX_PHY + 1;
      END IF;
    END IF;
  END PROCESS;


  --------------------------------------------------------------------------------
  -- 125 MHz clock check (1 Hz for 125 MHz)

  PROCESS(CLK_125_SYS_SFP) BEGIN
    IF rising_edge(CLK_125_SYS_SFP) THEN
      IF cnt_CLK_125_SYS_SFP = X"3B9ACA0" THEN
        cnt_CLK_125_SYS_SFP <= X"0000000";
        LED_CLK_125_SYS_SFP <= NOT LED_CLK_125_SYS_SFP;
      ELSE
        cnt_CLK_125_SYS_SFP <= cnt_CLK_125_SYS_SFP + 1;
      END IF;
    END IF;
  END PROCESS;


  PROCESS(CLK_125_SYS_PHY) BEGIN
    IF rising_edge(CLK_125_SYS_PHY) THEN
      IF cnt_CLK_125_SYS_PHY = X"3B9ACA0" THEN
        cnt_CLK_125_SYS_PHY <= X"0000000";
        LED_CLK_125_SYS_PHY <= NOT LED_CLK_125_SYS_PHY;
      ELSE
        cnt_CLK_125_SYS_PHY <= cnt_CLK_125_SYS_PHY + 1;
      END IF;
    END IF;
  END PROCESS;

  --------------------------------------------------------------------------------
  -- Autonegotiation IRQ pulse enlogation

--  PROCESS(CLK_125_SYS_SFP) BEGIN
--    IF rising_edge(CLK_125_SYS_SFP) THEN
--      IF ANEG_IRQ_SFP = '1' THEN
--        LED_ANEG_IRQ_SFP <= '1';
--        cnt_LED_ANEG_IRQ_SFP <= X"000000";
--      ELSIF cnt_LED_ANEG_IRQ_SFP = X"BEBC20" THEN
--        LED_ANEG_IRQ_SFP <= '0';
--      ELSE
--        cnt_LED_ANEG_IRQ_SFP <= cnt_LED_ANEG_IRQ_SFP + 1;
--      END IF;
--    END IF;
--  END PROCESS;

  LED_ANEG_IRQ_SFP <= ANEG_IRQ_SFP;
  LED_ANEG_IRQ_PHY <= ANEG_IRQ_PHY;

  --------------------------------------------------------------------------------
-- GPIO
  BUFF_ACT <= GPIO_DIP(3);

  GPIO_LED(0) <= LED_CLK_TX_SFP;
--GPIO_LED(1) <= LED_CLK_125_SYS_SFP;
  GPIO_LED(1) <= DDR2_RST_OUT;
  GPIO_LED(2) <= NOT LED_SYNC_STATUS_SFP;
  GPIO_LED(3) <= LED_ANEG_IRQ_SFP;
  GPIO_LED(4) <= LED_CLK_TX_PHY;
--GPIO_LED(5) <= LED_CLK_125_SYS_PHY;
  GPIO_LED(5) <= '0';
  GPIO_LED(6) <= NOT LED_SYNC_STATUS_PHY;
  GPIO_LED(7) <= LED_ANEG_IRQ_PHY;

  HDR1 <= (OTHERS => '0');

--################################################################################
END Behavioral;
--################################################################################
