--------------------------------------------------------------------------------
-- CERN BE-CO-HT
-- LHC Instability Trigger Distribution (LIST)
-- https://ohwr.org/projects/list
--------------------------------------------------------------------------------
--
-- unit name:   spec_list_top
--
-- description: Top entity for LHC Instability Trigger Distribution project
--
-- Top level design of the SVEC-based LIST WR trigger distribution node, with
-- an FMC TDC in slot and an FMC Fine Delay in slot 2.
--
--------------------------------------------------------------------------------
-- Copyright CERN 2014-2018
--------------------------------------------------------------------------------
-- Copyright and related rights are licensed under the Solderpad Hardware
-- License, Version 2.0 (the "License"); you may not use this file except
-- in compliance with the License. You may obtain a copy of the License at
-- http://solderpad.org/licenses/SHL-2.0.
-- Unless required by applicable law or agreed to in writing, software,
-- hardware and materials distributed under this License is distributed on an
-- "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
-- or implied. See the License for the specific language governing permissions
-- and limitations under the License.
--------------------------------------------------------------------------------

library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;

library work;
use work.gencores_pkg.all;
use work.wishbone_pkg.all;
use work.gn4124_core_pkg.all;
use work.carrier_csr_wbgen2_pkg.all;
use work.mt_mqueue_pkg.all;
use work.mock_turtle_pkg.all;
use work.synthesis_descriptor.all;
use work.wr_xilinx_pkg.all;
use work.wr_board_pkg.all;
use work.wr_spec_pkg.all;
use work.wr_fabric_pkg.all;
{use}

entity {name}_top is
  generic (
    g_WRPC_INITF : string  := "{topdir}/wr-cores/bin/wrpc/wrc_phy8.bram";
    g_MT_CPU0_INITF  : string  := "../../../../software/firmware/tdc/wrtd-rt-tdc.bram";
    g_MT_CPU1_INITF  : string  := "../../../../software/firmware/fd/wrtd-rt-fd.bram";
    -- Simulation-mode enable parameter. Set by default (synthesis) to 0, and
    -- changed to non-zero in the instantiation of the top level DUT in the
    -- testbench. Its purpose is to reduce some internal counters/timeouts
    -- to speed up simulations.
    g_SIMULATION     : integer := 0);
  port (
    -- Reset button
    button1_n_i : in  std_logic;

    -- Local oscillators
    clk_20m_vcxo_i : in std_logic;  -- 20MHz VCXO clock

    clk_125m_pllref_p_i : in std_logic;  -- 125 MHz PLL reference
    clk_125m_pllref_n_i : in std_logic;

    clk_125m_gtp_n_i : in std_logic;  -- 125 MHz GTP reference
    clk_125m_gtp_p_i : in std_logic;

    -- DAC interface (20MHz and 25MHz VCXO)
    pll25dac_sync_n_o : out std_logic;          -- 25MHz VCXO
    pll20dac_sync_n_o : out std_logic;          -- 20MHz VCXO
    plldac_din_o      : out std_logic;
    plldac_sclk_o     : out std_logic;

    -- Carrier front panel LEDs
    led_sfp_red_o   : out std_logic;
    led_sfp_green_o : out std_logic;

    -- Auxiliary pins
    aux_leds_o : out std_logic_vector(3 downto 0);

    -- PCB version
    pcbrev_i : in std_logic_vector(3 downto 0);

    -- Carrier 1-wire interface (DS18B20 thermometer + unique ID)
    carrier_onewire_b : inout std_logic;

    -- SFP
    sfp_txp_o         : out   std_logic;
    sfp_txn_o         : out   std_logic;
    sfp_rxp_i         : in    std_logic;
    sfp_rxn_i         : in    std_logic;
    sfp_mod_def0_i    : in    std_logic;        -- sfp detect
    sfp_mod_def1_b    : inout std_logic;        -- scl
    sfp_mod_def2_b    : inout std_logic;        -- sda
    sfp_rate_select_o : out   std_logic;
    sfp_tx_fault_i    : in    std_logic;
    sfp_tx_disable_o  : out   std_logic;
    sfp_los_i         : in    std_logic;

    -- SPI
    spi_sclk_o : out std_logic;
    spi_ncs_o  : out std_logic;
    spi_mosi_o : out std_logic;
    spi_miso_i : in  std_logic := 'L';

    -- UART
    uart_rxd_i : in  std_logic;
    uart_txd_o : out std_logic;

    ------------------------------------------
    -- GN4124 interface
    --
    -- gn_gpio_b[0] -> AB19 -> GN4124 GPIO9
    -- gn_gpio_b[1] -> U16  -> GN4124 GPIO8
    ------------------------------------------
    gn_rst_n_i      : in    std_logic;
    gn_p2l_clk_n_i  : in    std_logic;
    gn_p2l_clk_p_i  : in    std_logic;
    gn_p2l_rdy_o    : out   std_logic;
    gn_p2l_dframe_i : in    std_logic;
    gn_p2l_valid_i  : in    std_logic;
    gn_p2l_data_i   : in    std_logic_vector(15 downto 0);
    gn_p_wr_req_i   : in    std_logic_vector(1 downto 0);
    gn_p_wr_rdy_o   : out   std_logic_vector(1 downto 0);
    gn_rx_error_o   : out   std_logic;
    gn_l2p_clk_n_o  : out   std_logic;
    gn_l2p_clk_p_o  : out   std_logic;
    gn_l2p_dframe_o : out   std_logic;
    gn_l2p_valid_o  : out   std_logic;
    gn_l2p_edb_o    : out   std_logic;
    gn_l2p_data_o   : out   std_logic_vector(15 downto 0);
    gn_l2p_rdy_i    : in    std_logic;
    gn_l_wr_rdy_i   : in    std_logic_vector(1 downto 0);
    gn_p_rd_d_rdy_i : in    std_logic_vector(1 downto 0);
    gn_tx_error_i   : in    std_logic;
    gn_vc_rdy_i     : in    std_logic_vector(1 downto 0);
    gn_gpio_b       : inout std_logic_vector(1 downto 0);

{ports}

    -- FMC slot management

    fmc0_prsnt_m2c_n_i : in std_logic;

    fmc0_scl_b : inout std_logic;
    fmc0_sda_b : inout std_logic);

end entity {name}_top;

architecture arch of {name}_top is

  -----------------------------------------------------------------------------
  -- Constants
  -----------------------------------------------------------------------------

  -- WRPC Xilinx platform auxiliary clock configuration, used for DDR clock
  constant c_WRPC_PLL_CONFIG : t_px_pll_cfg := (
    enabled => TRUE, divide => 3, multiply => 8 );

  -- SPEC carrier CSR constants
  constant c_CARRIER_TYPE : std_logic_vector(15 downto 0) := X"0001";

  -- Number of masters attached to the primary wishbone crossbar
  constant c_NUM_WB_MASTERS : integer := 1;

  -- Number of slaves attached to the primary wishbone crossbar
  constant c_NUM_WB_SLAVES : integer := {nbr_slaves} + 4;

  -- Primary Wishbone master(s) offsets
  constant c_WB_MASTER_GENNUM : integer := 0;

  -- Primary Wishbone slave(s) offsets
  constant c_WB_SLAVE_SPEC_CSR : integer := 0;
  constant c_WB_SLAVE_VIC      : integer := 1;
  constant c_WB_SLAVE_BASE     : integer := 2;
{slaves_decl}
  constant c_WB_SLAVE_MT   : integer := c_WB_SLAVE_BASE + 0 + {nbr_slaves};
  constant c_WB_SLAVE_WRC  : integer := c_WB_SLAVE_BASE + 1 + {nbr_slaves};
  constant c_WB_DESC_SYN   : integer := c_WB_SLAVE_BASE + 2 + {nbr_slaves};
  constant c_WB_DESC_URL   : integer := c_WB_SLAVE_BASE + 3 + {nbr_slaves};

  -- sdb header address on primary crossbar
  constant c_SDB_ADDRESS : t_wishbone_address := x"00000000";

  -- f_xwb_bridge_manual_sdb(size, sdb_addr)
  -- Note: sdb_addr is the sdb records address relative to the bridge base address
  constant c_wrc_bridge_sdb : t_sdb_bridge :=
    f_xwb_bridge_manual_sdb(x"0003ffff", x"00030000");

  constant c_WB_SPEC_CSR_SDB : t_sdb_device := (
    abi_class     => x"0000",                     -- undocumented device
    abi_ver_major => x"01",
    abi_ver_minor => x"01",
    wbd_endian    => c_SDB_ENDIAN_BIG,
    wbd_width     => x"4",                        -- 32-bit port granularity
    sdb_component => (
      addr_first  => x"0000000000000000",
      addr_last   => x"000000000000001F",
      product     => (
        vendor_id => x"000000000000CE42",         -- CERN
        device_id => x"00000603",
        version   => x"00000001",
        date      => x"20121116",
        name      => "WB-SPEC-CSR        ")));


{sdb-decl}

  -- Primary wishbone crossbar layout
  constant c_WB_LAYOUT : t_sdb_record_array(c_NUM_WB_SLAVES + 1 downto 0) := (
    c_WB_SLAVE_SPEC_CSR => f_sdb_embed_device(c_WB_SPEC_CSR_SDB, x"00001000"),
    c_WB_SLAVE_VIC      => f_sdb_embed_device(c_XWB_VIC_SDB,     x"00001200"),
{sdb-layout}
    c_WB_SLAVE_MT   => f_sdb_embed_device(c_MOCK_TURTLE_SDB, x"00020000"),
    c_WB_SLAVE_WRC  => f_sdb_embed_bridge(c_wrc_bridge_sdb, x"00040000"),
    c_WB_DESC_SYN   => f_sdb_embed_synthesis(c_SDB_SYNTHESIS_INFO),
    c_WB_DESC_URL   => f_sdb_embed_repo_url(c_SDB_REPO_URL));

  -- not really used, will be reprogrammed by software
  constant c_VIC_VECTOR_TABLE : t_wishbone_address_array(0 to 5) := (
    0 => x"00011500",   -- FMC  EIC address
    1 => x"00018000",   -- FMC  DMA FIXME.
    2 => x"00020000",   -- MT Mqueue in interrupt
    3 => x"00020001",   -- MT Mqueue out interrupt
    4 => x"00020002",   -- MT Console interrupt
    5 => x"00020003");  -- MT Notify interrupt

  constant c_FMC_MUX_ADDR : t_wishbone_address_array(0 downto 0) :=
    (0 => x"00000000");
  constant c_FMC_MUX_MASK : t_wishbone_address_array(0 downto 0) :=
    (0 => x"10000000");

 {mt_config}

  -----------------------------------------------------------------------------
  -- Signals
  -----------------------------------------------------------------------------

  -- Clocks and resets
  signal clk_sys_62m5       : std_logic;
  signal clk_ref_125m       : std_logic;
  signal sys_clk_pll_locked : std_logic;
  signal clk_ddr_333m       : std_logic;

  signal rst_sys_62m5_n     : std_logic := '0';
  signal rst_ref_125m_n     : std_logic := '0';
  signal rst_ddr_333m_n     : std_logic := '0';
  signal sw_rst_fmc         : std_logic := '1';
  signal sw_rst_fmc_sync    : std_logic := '1';
  signal fmc_rst_ref_125m_n : std_logic := '0';
  signal fmc_rst_sys_n      : std_logic := '0';
  signal ddr0_rst           : std_logic := '1';

  attribute keep                 : string;
  attribute keep of clk_sys_62m5 : signal is "TRUE";
  attribute keep of clk_ref_125m : signal is "TRUE";
  attribute keep of clk_ddr_333m : signal is "TRUE";
  attribute keep of ddr0_rst     : signal is "TRUE";

  -- GN4124
  signal gn4124_status : std_logic_vector(31 downto 0);
  signal gn4124_access : std_logic;

  -- Wishbone buse(s) from master(s) to crossbar slave port(s)
  signal cnx_master_out : t_wishbone_master_out_array(c_NUM_WB_MASTERS-1 downto 0);
  signal cnx_master_in  : t_wishbone_master_in_array(c_NUM_WB_MASTERS-1 downto 0);

  -- Wishbone buse(s) from crossbar master port(s) to slave(s)
  signal cnx_slave_out : t_wishbone_slave_out_array(c_NUM_WB_SLAVES-1 downto 0);
  signal cnx_slave_in  : t_wishbone_slave_in_array(c_NUM_WB_SLAVES-1 downto 0);

  -- GN4124 core DMA port to DDR wishbone bus
  signal gn_wb_ddr_in  : t_wishbone_master_in;
  signal gn_wb_ddr_out : t_wishbone_master_out;

  -- Interrupts and status
  signal dma_irq           : std_logic_vector(1 downto 0);
  signal fmc_host_irq   : std_logic_vector(0 downto 0) := "0";
  signal mt_hmq_in_irq  : std_logic;
  signal mt_hmq_out_irq : std_logic;
  signal mt_console_irq : std_logic;
  signal mt_notify_irq  : std_logic;
  signal vic_master_irq : std_logic;

  -- Front panel LED control
  signal led_red   : std_logic;
  signal led_green : std_logic;

  -- SFP
  signal sfp_sda_in  : std_logic;
  signal sfp_sda_out : std_logic;
  signal sfp_scl_in  : std_logic;
  signal sfp_scl_out : std_logic;

  -- OneWire
  signal onewire_data : std_logic;
  signal onewire_oe   : std_logic;

  -- LEDs and GPIO
  signal pps         : std_logic;
  signal pps_led     : std_logic;
  signal pps_ext_in  : std_logic;
  signal svec_led    : std_logic_vector(15 downto 0);
  signal wr_led_link : std_logic;
  signal wr_led_act  : std_logic;


  --  MT endpoints
  signal rmq_endpoint_out : t_mt_rmq_endpoint_iface_out;
  signal rmq_endpoint_in  : t_mt_rmq_endpoint_iface_in;
  signal rmq_src_in       : t_mt_stream_source_in;
  signal rmq_src_out      : t_mt_stream_source_out;
  signal rmq_src_cfg_in   : t_mt_stream_config_in;
  signal rmq_src_cfg_out  : t_mt_stream_config_out;
  signal rmq_snk_in       : t_mt_stream_sink_in;
  signal rmq_snk_out      : t_mt_stream_sink_out;
  signal rmq_snk_cfg_in   : t_mt_stream_config_in;
  signal rmq_snk_cfg_out  : t_mt_stream_config_out;

  --  MT fabric.
  signal eth_tx_out : t_wrf_source_out;
  signal eth_tx_in  : t_wrf_source_in;
  signal eth_rx_out : t_wrf_sink_out;
  signal eth_rx_in  : t_wrf_sink_in;

  -- MT Dedicated WB interfaces to FMCs
  signal fmc_dp_wb_out : t_wishbone_master_out_array(0 to {ncpus} - 1);
  signal fmc_dp_wb_in  : t_wishbone_master_in_array(0 to {ncpus} - 1);

  -- WRPC TM interface and aux clocks
  signal tm_link_up         : std_logic;
  signal tm_tai             : std_logic_vector(39 downto 0);
  signal tm_cycles          : std_logic_vector(27 downto 0);
  signal tm_time_valid      : std_logic;
  signal tm_clk_aux_lock_en : std_logic_vector(1 downto 0);
  signal tm_clk_aux_locked  : std_logic_vector(1 downto 0) := "00";
  signal tm_dac_value       : std_logic_vector(23 downto 0);
  signal tm_dac_wr          : std_logic_vector(1 downto 0);
  signal wrabbit_en         : std_logic;

  -- MT TM interface
  signal tm : t_mt_timing_if;

  signal fmc0_scl_out : std_logic := '1';
  signal fmc0_sda_out : std_logic := '1';

  attribute iob : string;
  attribute iob of pps : signal is "FORCE";

  -- IO for CSR registers
  signal csr_regin  : t_carrier_csr_in_registers;
  signal csr_regout : t_carrier_csr_out_registers;

{decls}

begin  -- architecture arch

  ------------------------------------------------------------------------------
  -- Reset logic
  ------------------------------------------------------------------------------

  sys_clk_pll_locked <= '1';

  -- reset for mezzanine
  -- including soft reset, with re-sync from 62.5MHz domain
  -- and registers to help with timing
  cmp_fmc_sw_reset_sync : gc_sync_ffs
    port map (
      clk_i    => clk_ref_125m,
      rst_n_i  => '1',
      data_i   => sw_rst_fmc,
      synced_o => sw_rst_fmc_sync);

  fmc_rst_ref_125m_n <= rst_ref_125m_n and not sw_rst_fmc_sync;
  fmc_rst_sys_n <= rst_sys_62m5_n and not sw_rst_fmc;

  -- reset for DDR including soft reset.
  -- This is treated as async and will be re-synced by the DDR controller
  ddr0_rst <= not rst_ddr_333m_n or sw_rst_fmc;

  ------------------------------------------------------------------------------
  -- Carrier CSR
  --    Carrier type and PCB version
  --    Bitstream (firmware) type and date
  --    Release tag
  --    VCXO DAC control (CLR_N)
  ------------------------------------------------------------------------------
  cmp_carrier_csr : entity work.carrier_csr
    port map (
      rst_n_i    => rst_sys_62m5_n,
      clk_sys_i  => clk_sys_62m5,
      wb_adr_i   => cnx_slave_in(c_WB_SLAVE_SPEC_CSR).adr(3 downto 2),  -- cnx_slave_in.adr is byte address
      wb_dat_i   => cnx_slave_in(c_WB_SLAVE_SPEC_CSR).dat,
      wb_dat_o   => cnx_slave_out(c_WB_SLAVE_SPEC_CSR).dat,
      wb_cyc_i   => cnx_slave_in(c_WB_SLAVE_SPEC_CSR).cyc,
      wb_sel_i   => cnx_slave_in(c_WB_SLAVE_SPEC_CSR).sel,
      wb_stb_i   => cnx_slave_in(c_WB_SLAVE_SPEC_CSR).stb,
      wb_we_i    => cnx_slave_in(c_WB_SLAVE_SPEC_CSR).we,
      wb_ack_o   => cnx_slave_out(c_WB_SLAVE_SPEC_CSR).ack,
      wb_stall_o => open,
      regs_i     => csr_regin,
      regs_o     => csr_regout);

  csr_regin.carrier_pcb_rev_i    <= pcbrev_i;
  csr_regin.carrier_reserved_i   <= (others => '0');
  csr_regin.carrier_type_i       <= c_CARRIER_TYPE;
  csr_regin.stat_fmc_pres_i      <= fmc0_prsnt_m2c_n_i;
  csr_regin.stat_p2l_pll_lck_i   <= gn4124_status(0);
  csr_regin.stat_sys_pll_lck_i   <= sys_clk_pll_locked;
  csr_regin.stat_ddr3_cal_done_i <= ddr0_calib_done;

  led_red    <= csr_regout.ctrl_led_red_o;
  led_green  <= csr_regout.ctrl_led_green_o;
  sw_rst_fmc <= csr_regout.rst_fmc0_o;

  -- Unused wishbone signals
  cnx_slave_out(c_WB_SLAVE_SPEC_CSR).err   <= '0';
  cnx_slave_out(c_WB_SLAVE_SPEC_CSR).rty   <= '0';
  cnx_slave_out(c_WB_SLAVE_SPEC_CSR).stall <= '0';

  ------------------------------------------------------------------------------
  -- GN4124 interface
  ------------------------------------------------------------------------------
  cmp_gn4124_core : xwb_gn4124_core
    port map (
      rst_n_a_i          => gn_rst_n_i,
      status_o           => gn4124_status,
      p2l_clk_p_i        => gn_p2l_clk_p_i,
      p2l_clk_n_i        => gn_p2l_clk_n_i,
      p2l_data_i         => gn_p2l_data_i,
      p2l_dframe_i       => gn_p2l_dframe_i,
      p2l_valid_i        => gn_p2l_valid_i,
      p2l_rdy_o          => gn_p2l_rdy_o,
      p_wr_req_i         => gn_p_wr_req_i,
      p_wr_rdy_o         => gn_p_wr_rdy_o,
      rx_error_o         => gn_rx_error_o,
      l2p_clk_p_o        => gn_l2p_clk_p_o,
      l2p_clk_n_o        => gn_l2p_clk_n_o,
      l2p_data_o         => gn_l2p_data_o,
      l2p_dframe_o       => gn_l2p_dframe_o,
      l2p_valid_o        => gn_l2p_valid_o,
      l2p_edb_o          => gn_l2p_edb_o,
      l2p_rdy_i          => gn_l2p_rdy_i,
      l_wr_rdy_i         => gn_l_wr_rdy_i,
      p_rd_d_rdy_i       => gn_p_rd_d_rdy_i,
      tx_error_i         => gn_tx_error_i,
      vc_rdy_i           => gn_vc_rdy_i,
      dma_irq_o          => dma_irq,
      irq_p_i            => vic_master_irq,
      irq_p_o            => gn_gpio_b(1),
      wb_master_clk_i    => clk_sys_62m5,
      wb_master_rst_n_i  => rst_sys_62m5_n,
      wb_master_i        => cnx_master_in(c_WB_MASTER_GENNUM),
      wb_master_o        => cnx_master_out(c_WB_MASTER_GENNUM),
      wb_dma_cfg_clk_i   => clk_sys_62m5,
      wb_dma_cfg_rst_n_i => rst_sys_62m5_n,
      wb_dma_cfg_i       => cnx_slave_in(c_WB_SLAVE_DMA),
      wb_dma_cfg_o       => cnx_slave_out(c_WB_SLAVE_DMA),
      wb_dma_dat_clk_i   => clk_sys_62m5,
      wb_dma_dat_rst_n_i => rst_sys_62m5_n,
      wb_dma_dat_i       => gn_wb_ddr_in,
      wb_dma_dat_o       => gn_wb_ddr_out);

  -- Assign unused outputs
  gn_gpio_b(0) <= '0';

  ------------------------------------------------------------------------------
  -- Primary wishbone crossbar
  ------------------------------------------------------------------------------

  cmp_sdb_crossbar : xwb_sdb_crossbar
    generic map (
      g_NUM_MASTERS => c_NUM_WB_MASTERS,
      g_NUM_SLAVES  => c_NUM_WB_SLAVES,
      g_REGISTERED  => TRUE,
      g_WRAPAROUND  => TRUE,
      g_LAYOUT      => c_WB_LAYOUT,
      g_SDB_ADDR    => c_SDB_ADDRESS)
    port map (
      clk_sys_i => clk_sys_62m5,
      rst_n_i   => rst_sys_62m5_n,
      slave_i   => cnx_master_out,
      slave_o   => cnx_master_in,
      master_i  => cnx_slave_out,
      master_o  => cnx_slave_in);

  -----------------------------------------------------------------------------
  -- Vectored Interrupt Controller (WB Slave)
  -----------------------------------------------------------------------------

  cmp_vic : xwb_vic
    generic map (
      g_INTERFACE_MODE      => PIPELINED,
      g_ADDRESS_GRANULARITY => BYTE,
      g_NUM_INTERRUPTS      => 6,
      g_INIT_VECTORS        => c_VIC_VECTOR_TABLE)
    port map (
      clk_sys_i    => clk_sys_62m5,
      rst_n_i      => rst_sys_62m5_n,
      slave_i      => cnx_slave_in(c_WB_SLAVE_VIC),
      slave_o      => cnx_slave_out(c_WB_SLAVE_VIC),
      irqs_i(0)    => fmc_host_irq(0),
      irqs_i(1)    => '0',
      irqs_i(2)    => mt_hmq_in_irq,
      irqs_i(3)    => mt_hmq_out_irq,
      irqs_i(4)    => mt_console_irq,
      irqs_i(5)    => mt_notify_irq,
      irq_master_o => vic_master_irq);

  -----------------------------------------------------------------------------
  -- Mock Turtle (WB Slave)
  -----------------------------------------------------------------------------

  cmp_mock_turtle : entity work.mock_turtle_core
    generic map (
      g_CONFIG            => c_MT_CONFIG,
      g_CPU0_IRAM_INITF   => g_MT_CPU0_INITF,
      g_CPU1_IRAM_INITF   => g_MT_CPU1_INITF,
      g_WITH_WHITE_RABBIT => TRUE)
    port map (
      clk_i          => clk_sys_62m5,
      rst_n_i        => rst_sys_62m5_n,
      sp_master_o    => open,
      sp_master_i    => c_DUMMY_WB_MASTER_IN,
      dp_master_o    => fmc_dp_wb_out,
      dp_master_i    => fmc_dp_wb_in,
      rmq_endpoint_o => rmq_endpoint_out,
      rmq_endpoint_i => rmq_endpoint_in,
      host_slave_i   => cnx_slave_in(c_WB_SLAVE_MT),
      host_slave_o   => cnx_slave_out(c_WB_SLAVE_MT),
      clk_ref_i      => clk_ref_125m,
      tm_i           => tm,
      hmq_in_irq_o   => mt_hmq_in_irq,
      hmq_out_irq_o  => mt_hmq_out_irq,
      notify_irq_o   => mt_notify_irq,
      console_irq_o  => mt_console_irq);

  tm.cycles                 <= tm_cycles;
  tm.tai                    <= tm_tai;
  tm.time_valid             <= tm_time_valid;
  tm.link_up                <= tm_link_up;
  tm.aux_locked(1 downto 0) <= tm_clk_aux_locked;
  tm.aux_locked(7 downto 2) <= (others => '0');

  cmp_eth_endpoint : entity work.mt_ep_ethernet_single
    port map (
      clk_i            => clk_sys_62m5,
      rst_n_i          => rst_sys_62m5_n,
      rmq_src_i        => rmq_src_in,
      rmq_src_o        => rmq_src_out,
      rmq_src_config_i => rmq_snk_cfg_out,
      rmq_src_config_o => rmq_snk_cfg_in,
      rmq_snk_i        => rmq_snk_in,
      rmq_snk_o        => rmq_snk_out,
      rmq_snk_config_i => rmq_src_cfg_out,
      rmq_snk_config_o => rmq_src_cfg_in,
      eth_src_o        => eth_tx_out,
      eth_src_i        => eth_tx_in,
      eth_snk_o        => eth_rx_out,
      eth_snk_i        => eth_rx_in);

  p_rmq_assign : process (rmq_endpoint_out, rmq_snk_cfg_in, rmq_snk_out,
                          rmq_src_cfg_in, rmq_src_out) is
  begin

    rmq_endpoint_in <= c_MT_RMQ_ENDPOINT_IFACE_IN_DEFAULT_VALUE;

    -- WR->MT (RX, to MT CPU1)
    rmq_src_in                          <= rmq_endpoint_out.snk_out(1)(0);
    rmq_endpoint_in.snk_in(1)(0)        <= rmq_src_out;
    rmq_snk_cfg_out                     <= rmq_endpoint_out.snk_config_out(1)(0);
    rmq_endpoint_in.snk_config_in(1)(0) <= rmq_snk_cfg_in;

    -- MT->WR (TX, from MT CPU0)
    rmq_snk_in                          <= rmq_endpoint_out.src_out(0)(0);
    rmq_endpoint_in.src_in(0)(0)        <= rmq_snk_out;
    rmq_src_cfg_out                     <= rmq_endpoint_out.src_config_out(0)(0);
    rmq_endpoint_in.src_config_in(0)(0) <= rmq_src_cfg_in;

  end process p_rmq_assign;

  -----------------------------------------------------------------------------
  -- The WR PTP core SVEC board package (WB Slave)
  -----------------------------------------------------------------------------

  cmp_xwrc_board_spec : xwrc_board_spec
    generic map (
      g_SIMULATION                => g_SIMULATION,
      g_WITH_EXTERNAL_CLOCK_INPUT => FALSE,
      g_DPRAM_INITF               => g_WRPC_INITF,
      g_AUX_PLL_CONFIG            => c_WRPC_PLL_CONFIG,
      g_FABRIC_IFACE              => PLAIN)
    port map (
      clk_20m_vcxo_i      => clk_20m_vcxo_i,
      clk_125m_pllref_p_i => clk_125m_pllref_p_i,
      clk_125m_pllref_n_i => clk_125m_pllref_n_i,
      clk_125m_gtp_n_i    => clk_125m_gtp_n_i,
      clk_125m_gtp_p_i    => clk_125m_gtp_p_i,
      areset_n_i          => button1_n_i,
      areset_edge_n_i     => gn_rst_n_i,
      clk_sys_62m5_o      => clk_sys_62m5,
      clk_ref_125m_o      => clk_ref_125m,
      clk_pll_aux_o       => clk_ddr_333m,
      rst_sys_62m5_n_o    => rst_sys_62m5_n,
      rst_ref_125m_n_o    => rst_ref_125m_n,
      rst_pll_aux_n_o     => rst_ddr_333m_n,
      plldac_sclk_o       => plldac_sclk_o,
      plldac_din_o        => plldac_din_o,
      pll25dac_cs_n_o     => pll25dac_sync_n_o,
      pll20dac_cs_n_o     => pll20dac_sync_n_o,
      sfp_txp_o           => sfp_txp_o,
      sfp_txn_o           => sfp_txn_o,
      sfp_rxp_i           => sfp_rxp_i,
      sfp_rxn_i           => sfp_rxn_i,
      sfp_det_i           => sfp_mod_def0_i,
      sfp_sda_i           => sfp_sda_in,
      sfp_sda_o           => sfp_sda_out,
      sfp_scl_i           => sfp_scl_in,
      sfp_scl_o           => sfp_scl_out,
      sfp_rate_select_o   => sfp_rate_select_o,
      sfp_tx_fault_i      => sfp_tx_fault_i,
      sfp_tx_disable_o    => sfp_tx_disable_o,
      sfp_los_i           => sfp_los_i,
      onewire_i           => onewire_data,
      onewire_oen_o       => onewire_oe,
      uart_rxd_i          => uart_rxd_i,
      uart_txd_o          => uart_txd_o,
      flash_sclk_o        => spi_sclk_o,
      flash_ncs_o         => spi_ncs_o,
      flash_mosi_o        => spi_mosi_o,
      flash_miso_i        => spi_miso_i,
      wb_slave_o          => cnx_slave_out(c_WB_SLAVE_WRC),
      wb_slave_i          => cnx_slave_in(c_WB_SLAVE_WRC),

      wrf_src_o            => eth_rx_in,
      wrf_src_i            => eth_rx_out,
      wrf_snk_o            => eth_tx_in,
      wrf_snk_i            => eth_tx_out,

      tm_link_up_o        => tm_link_up,
      tm_time_valid_o     => tm_time_valid,
      tm_tai_o            => tm_tai,
      tm_cycles_o         => tm_cycles,
      pps_p_o             => open,
      pps_led_o           => pps_led,
      led_link_o          => wr_led_link,
      led_act_o           => wr_led_act,
      link_ok_o           => wrabbit_en);

  -- Tristates for SFP EEPROM
  sfp_mod_def1_b <= '0' when sfp_scl_out = '0' else 'Z';
  sfp_mod_def2_b <= '0' when sfp_sda_out = '0' else 'Z';
  sfp_scl_in     <= sfp_mod_def1_b;
  sfp_sda_in     <= sfp_mod_def2_b;

  -- Tristates for Carrier OneWire
  carrier_onewire_b <= '0' when onewire_oe = '1' else 'Z';
  onewire_data      <= carrier_onewire_b;

  --  fmc i2c

  fmc0_scl_b     <= '0' when (fmc0_scl_out = '0') else 'Z';
  fmc0_sda_b     <= '0' when (fmc0_sda_out = '0') else 'Z';

{body}

  ------------------------------------------------------------------------------
  -- Carrier LEDs
  ------------------------------------------------------------------------------

  cmp_pci_access_led : gc_extend_pulse
    generic map (
      g_width => 2500000)
    port map (
      clk_i      => clk_sys_62m5,
      rst_n_i    => rst_sys_62m5_n,
      pulse_i    => cnx_slave_in(c_WB_MASTER_GENNUM).cyc,
      extended_o => gn4124_access);

  aux_leds_o(0) <= not gn4124_access;
  aux_leds_o(1) <= '1';
  aux_leds_o(2) <= not tm_time_valid;
  aux_leds_o(3) <= not pps_led;

  -- SPEC front panel leds
  led_sfp_red_o   <= led_red or wr_led_act;
  led_sfp_green_o <= led_green or wr_led_link;

end architecture arch;
