Commit 01932e88 authored by Tomasz Wlostowski's avatar Tomasz Wlostowski

platform: GTHE3 PHY wrapper, non-functioning initial version

parent 2d9130e5
files = [
"gtp_bitslide.vhd",
"gtp_bitslide.vhd",
];
if (syn_device[0:4].upper()=="XC6S"): # Spartan6
files.extend(["spartan6/wr_gtp_phy_spartan6.vhd",
"spartan6/whiterabbitgtp_wrapper_tile_spartan6.vhd",
"spartan6/gtp_phase_align.vhd"])
"spartan6/whiterabbitgtp_wrapper_tile_spartan6.vhd",
"spartan6/gtp_phase_align.vhd"])
elif (syn_device[0:4].upper()=="XC6V"): # Virtex6
files.extend(["virtex6/wr_gtx_phy_virtex6.vhd",
"virtex6/whiterabbitgtx_wrapper_gtx.vhd",
"virtex6/gtp_phase_align_virtex6.vhd",
"virtex6/gtx_reset.vhd"])
"virtex6/whiterabbitgtx_wrapper_gtx.vhd",
"virtex6/gtp_phase_align_virtex6.vhd",
"virtex6/gtx_reset.vhd"])
elif (syn_device[0:4].upper()=="XC7A"): # Family 7 GTP (Artix7)
files.extend(["family7-gtp/wr_gtp_phy_family7.vhd",
"family7-gtp/whiterabbit_gtpe2_channel_wrapper.vhd",
"family7-gtp/whiterabbit_gtpe2_channel_wrapper_gt.vhd",
"family7-gtp/whiterabbit_gtpe2_channel_wrapper_gtrxreset_seq.vhd" ]);
"family7-gtp/whiterabbit_gtpe2_channel_wrapper.vhd",
"family7-gtp/whiterabbit_gtpe2_channel_wrapper_gt.vhd",
"family7-gtp/whiterabbit_gtpe2_channel_wrapper_gtrxreset_seq.vhd" ]);
elif (syn_device[0:4].upper()=="XC7K" or # Family 7 GTX (Kintex7 and Virtex7 585, 2000, X485)
syn_device[0:7].upper()=="XC7V585" or
syn_device[0:8].upper()=="XC7V2000" or
syn_device[0:8].upper()=="XC7VX485"):
files.extend(["family7-gtx/wr_gtx_phy_family7.vhd",
"family7-gtx/whiterabbit_gtxe2_channel_wrapper_gt.vhd"]);
"family7-gtx/whiterabbit_gtxe2_channel_wrapper_gt.vhd"]);
elif (syn_device[0:4].upper()=="XC7V"): # Family 7 GTH (other Virtex7 devices)
files.extend(["family7-gth/wr_gth_phy_family7.vhd",
"whiterabbit_gthe2_channel_wrapper_gt.vhd",
"whiterabbit_gthe2_channel_wrapper_gtrxreset_seq.vhd",
"whiterabbit_gthe2_channel_wrapper_sync_block.vhd" ]);
"whiterabbit_gthe2_channel_wrapper_gt.vhd",
"whiterabbit_gthe2_channel_wrapper_gtrxreset_seq.vhd",
"whiterabbit_gthe2_channel_wrapper_sync_block.vhd" ]);
elif (syn_device[0:4].upper()=="XCKU"): # Kintex Ultrascale GTH
files.extend(["wr_gth_phy_kintex7ultrascale.vhd"]);
files.extend(["family7-gthe3/wr_gthe3_phy_family7.vhd",
"family7-gthe3/wr_gthe3_reset.vhd",
"family7-gthe3/wr_gthe3_rx_buffer_bypass.vhd",
"family7-gthe3/wr_gthe3_tx_buffer_bypass.vhd",
"family7-gthe3/wr_gthe3_wrapper.vhd"]);
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.gencores_pkg.all;
entity wr_gthe3_reset is
port (
rst_i : in std_logic;
clk_free_i : in std_logic;
-- CPLL reset I/O
CPLLPD_o : out std_logic;
CPLLLOCK_i : in std_logic;
-- RX path resets
RXCDRLOCK_i : in std_logic;
RXRESETDONE_i : in std_logic;
GTRXRESET_o : out std_logic;
RXPROGDIVRESET_o : out std_logic;
RXUSERRDY_o : out std_logic;
-- TX path resets
GTTXRESET_o : out std_logic;
TXRESETDONE_i : in std_logic;
TXPROGDIVRESET_o : out std_logic;
TXUSERRDY_o : out std_logic;
rx_active_i : in std_logic;
tx_active_i : in std_logic;
done_o : out std_logic
);
end wr_gthe3_reset;
architecture rtl of wr_gthe3_reset is
constant c_RESET_TIMEOUT : integer := 1000;
type t_state is (RESTART, DONE, CPLL_WAIT_LOCK, CPLL_RESET_TIMEOUT, CDR_WAIT_LOCK, TX_ACTIVE_WAIT, RX_ACTIVE_WAIT, TX_RESET_DONE_WAIT, RX_RESET_DONE_WAIT, TX_RESET_TIMER_WAIT);
signal state : t_state;
signal rst_master_clk_free : std_logic;
signal CPLLLOCK_clk_free, tx_active_clk_free : std_logic;
signal rx_active_clk_free : std_logic;
signal TXRESETDONE_clk_free : std_logic;
signal RXRESETDONE_clk_free : std_logic;
signal RXCDRLOCK_clk_free : std_logic;
signal timeout_cnt : unsigned(15 downto 0);
begin
U_SyncResetAll : gc_sync_ffs
generic map (
g_sync_edge => "positive")
port map (
clk_i => clk_free_i,
rst_n_i => '1',
data_i => rst_i,
synced_o => rst_master_clk_free);
U_SyncCPLLLOCK : gc_sync_ffs
generic map (
g_sync_edge => "positive")
port map (
clk_i => clk_free_i,
rst_n_i => '1',
data_i => CPLLLOCK_i,
synced_o => CPLLLOCK_clk_free);
U_SyncTxActive : gc_sync_ffs
generic map (
g_sync_edge => "positive")
port map (
clk_i => clk_free_i,
rst_n_i => '1',
data_i => tx_active_i,
synced_o => tx_active_clk_free);
U_SyncRxActive : gc_sync_ffs
generic map (
g_sync_edge => "positive")
port map (
clk_i => clk_free_i,
rst_n_i => '1',
data_i => rx_active_i,
synced_o => rx_active_clk_free);
U_SyncRxResetDone : gc_sync_ffs
generic map (
g_sync_edge => "positive")
port map (
clk_i => clk_free_i,
rst_n_i => '1',
data_i => RXRESETDONE_i,
synced_o => RXRESETDONE_clk_free);
U_SyncTxResetDone : gc_sync_ffs
generic map (
g_sync_edge => "positive")
port map (
clk_i => clk_free_i,
rst_n_i => '1',
data_i => TXRESETDONE_i,
synced_o => TXRESETDONE_clk_free);
U_SyncRxCdrLock : gc_sync_ffs
generic map (
g_sync_edge => "positive")
port map (
clk_i => clk_free_i,
rst_n_i => '1',
data_i => RXCDRLOCK_i,
synced_o => RXCDRLOCK_clk_free);
TXPROGDIVRESET_o <= not CPLLLOCK_clk_free;
-- TX side:
-- - assert pllreset_tx, gttxreset
-- - wait for lock (plllock_tx, pllreset_tx -> 0)
-- - gttxreset -> 0
-- - wait for tx_active
-- - wait for txresetdone
-- - we're done
-- RX side:
-- - assert pllreset_rx, rxprogdivreset, gtrxreset
-- - wait for plllock_rx, pllreset_rx->0
-- - deassert gtrxreset
-- - wait for cdr lock
-- - deassert progdiv reset
-- - wait for rx_active
-- - wait for rxresetdone
-- - we're done
process(clk_free_i)
begin
if rising_edge(clk_free_i)then
if rst_master_clk_free = '1' then
state <= RESTART;
done_o <= '0';
GTTXRESET_o <= '1';
GTRXRESET_o <= '1';
RXPROGDIVRESET_o <= '1';
TXUSERRDY_o <= '0';
RXUSERRDY_o <= '0';
else
done_o <= '0';
case state is
when RESTART =>
CPLLPD_o <= '1'; -- assert both TX and RX PLL reset (we're using the
-- CPLL that serves both)
GTTXRESET_o <= '1';
GTRXRESET_o <= '1';
RXPROGDIVRESET_o <= '1';
TXUSERRDY_o <= '0';
RXUSERRDY_o <= '0';
state <= CPLL_WAIT_LOCK;
timeout_cnt <= to_unsigned(c_RESET_TIMEOUT, 16);
when CPLL_RESET_TIMEOUT =>
timeout_cnt <= timeout_cnt - 1;
if timeout_cnt = 0 then
CPLLPD_o <= '0';
state <= CPLL_WAIT_LOCK;
end if;
when CPLL_WAIT_LOCK =>
CPLLPD_o <= '0';
if CPLLLOCK_clk_free = '1' then
GTTXRESET_o <= '1';
GTRXRESET_o <= '1';
timeout_cnt <= to_unsigned(c_RESET_TIMEOUT, 16);
state <= TX_RESET_TIMER_WAIT;
end if;
when TX_RESET_TIMER_WAIT =>
timeout_cnt <= timeout_cnt - 1;
if timeout_cnt = 0 then
GTTXRESET_o <= '0';
GTRXRESET_o <= '0';
state <= TX_ACTIVE_WAIT;
end if;
when TX_ACTIVE_WAIT =>
if tx_active_clk_free = '1' then
state <= TX_RESET_DONE_WAIT;
TXUSERRDY_o <= '1';
end if;
when TX_RESET_DONE_WAIT =>
if TXRESETDONE_clk_free = '1' then
state <= CDR_WAIT_LOCK;
end if;
when CDR_WAIT_LOCK =>
if RXCDRLOCK_clk_free = '1' then
RXPROGDIVRESET_o <= '0';
state <= RX_ACTIVE_WAIT;
end if;
when RX_ACTIVE_WAIT =>
if rx_active_clk_free = '1' then
state <= RX_RESET_DONE_WAIT;
RXUSERRDY_o <= '1';
end if;
when RX_RESET_DONE_WAIT =>
if RXRESETDONE_clk_free = '1' then
state <= DONE;
end if;
when DONE =>
done_o <= '1';
end case;
end if;
end if;
end process;
end rtl;
library ieee;
use ieee.std_logic_1164.all;
use work.gencores_pkg.all;
entity wr_gthe3_rx_buffer_bypass is
port
(
clk_free_i : in std_logic;
rst_i : in std_logic;
RXUSRCLK2_i : in std_logic;
RXRESETDONE_i : in std_logic;
RXDLYSRESET_o : out std_logic;
RXSYNCDONE_i : in std_logic;
done_o : out std_logic
);
end wr_gthe3_rx_buffer_bypass;
architecture rtl of wr_gthe3_rx_buffer_bypass is
type t_state is (WAIT_RESTART, ASSERT_DLY_RESET, WAIT_SYNC_DONE, DONE);
signal state : t_state;
signal rst_rxusrclk2 : std_logic;
signal RXRESETDONE_clk_free : std_logic;
signal RXSYNCDONE_clk_free_p1 : std_logic;
signal done_int : std_logic;
begin
U_Sync_Reset : gc_sync_ffs
port map (
clk_i => RXUSRCLK2_i,
rst_n_i => '1',
data_i => rst_i,
synced_o => rst_rxusrclk2);
U_Sync_Done : gc_sync_ffs
port map (
clk_i => clk_free_i,
rst_n_i => '1',
data_i => done_int,
synced_o => done_o);
-- RX dly align procedure:
--
-- start on RXRESETDONE
-- rxdlysreset_out = 1
-- rxdlysreset_out = 0
-- wait for RE of rxsyncdone
p_rx_buffer_bypass : process(RXUSRCLK2_i)
begin
if rising_edge(RXUSRCLK2_i) then
if rst_rxusrclk2 = '1' then
state <= WAIT_RESTART;
RXDLYSRESET_o <= '0';
done_int <= '0';
else
RXDLYSRESET_o <= '0';
done_int <= '0';
case state is
when WAIT_RESTART =>
if RXRESETDONE_i = '1' then
state <= ASSERT_DLY_RESET;
end if;
when ASSERT_DLY_RESET =>
RXDLYSRESET_o <= '1';
state <= WAIT_SYNC_DONE;
when WAIT_SYNC_DONE =>
RXDLYSRESET_o <= '0';
if RXSYNCDONE_i = '1' then
state <= DONE;
end if;
when DONE =>
done_int <= '1';
end case;
end if;
end if;
end process;
end rtl;
library ieee;
use ieee.std_logic_1164.all;
use work.gencores_pkg.all;
entity wr_gthe3_tx_buffer_bypass is
port
(
clk_free_i : in std_logic;
rst_i : in std_logic;
TXUSRCLK2_i : in std_logic;
TXRESETDONE_i : in std_logic;
TXDLYSRESET_o : out std_logic;
TXSYNCDONE_i : in std_logic;
done_o : out std_logic
);
end wr_gthe3_tx_buffer_bypass;
architecture rtl of wr_gthe3_tx_buffer_bypass is
type t_state is (WAIT_RESTART, ASSERT_DLY_RESET, WAIT_SYNC_DONE, DONE);
signal rst_txusrclk2 : std_logic;
signal TXRESETDONE_clk_free : std_logic;
signal TXSYNCDONE_clk_free_p1 : std_logic;
signal done_int : std_logic;
signal state : t_state;
signal rst_n : std_logic;
begin
rst_n <= not rst_i;
U_Sync_Reset : gc_sync_ffs
port map (
clk_i => TXUSRCLK2_i,
rst_n_i => rst_n,
data_i => rst_i,
synced_o => rst_txusrclk2);
U_Sync_Done : gc_sync_ffs
port map (
clk_i => clk_free_i,
rst_n_i => rst_n,
data_i => done_int,
synced_o => done_o);
U_Sync_TXRESETDONE : gc_sync_ffs
port map (
clk_i => clk_free_i,
rst_n_i => rst_n,
data_i => TXRESETDONE_i,
synced_o => TXRESETDONE_clk_free);
U_Sync_TXSYNCDONE : gc_sync_ffs
port map (
clk_i => clk_free_i,
rst_n_i => rst_n,
data_i => TXSYNCDONE_i,
ppulse_o => TXSYNCDONE_clk_free_p1);
-- TX dly align procedure:
--
-- start on TXRESETDONE
-- txdlysreset_out = 1
-- txdlysreset_out = 0
-- wait for RE of txsyncdone
p_tx_buffer_bypass : process(TXUSRCLK2_i)
begin
if rising_edge(TXUSRCLK2_i) then
if rst_txusrclk2 = '1' then
state <= WAIT_RESTART;
TXDLYSRESET_o <= '0';
done_int <= '0';
else
TXDLYSRESET_o <= '0';
done_int <= '0';
case state is
when WAIT_RESTART =>
if TXRESETDONE_i = '1' then
state <= ASSERT_DLY_RESET;
end if;
when ASSERT_DLY_RESET =>
TXDLYSRESET_o <= '1';
state <= WAIT_SYNC_DONE;
when WAIT_SYNC_DONE =>
TXDLYSRESET_o <= '0';
if TXSYNCDONE_i = '1' then
state <= DONE;
end if;
when DONE =>
done_int <= '1';
end case;
end if;
end if;
end process;
end rtl;
This diff is collapsed.
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.gencores_pkg.all;
use work.disparity_gen_pkg.all;
entity wr_gth_phy_kintex7ultrascale is
generic (
-- set to non-zero value to speed up the simulation by reducing some delays
g_simulation : integer := 0
);
port (
-- Dedicated reference 125 MHz clock for the GTX transceiver
clk_gth_p_i : in std_logic;
clk_gth_n_i : in std_logic;
clk_freerun_i : in std_logic;
-- TX path, synchronous to tx_out_clk_o (62.5 MHz):
tx_out_clk_o : out std_logic;
tx_locked_o : out std_logic;
-- data input (8 bits, not 8b10b-encoded)
tx_data_i : in std_logic_vector(15 downto 0);
-- 1 when tx_data_i contains a control code, 0 when it's a data byte
tx_k_i : in std_logic_vector(1 downto 0);
-- disparity of the currently transmitted 8b10b code (1 = plus, 0 = minus).
-- Necessary for the PCS to generate proper frame termination sequences.
-- Generated for the 2nd byte (LSB) of tx_data_i.
tx_disparity_o : out std_logic;
-- Encoding error indication (1 = error, 0 = no error)
tx_enc_err_o : out std_logic;
-- RX path, synchronous to ch0_rx_rbclk_o.
-- RX recovered clock
rx_rbclk_o : out std_logic;
-- 8b10b-decoded data output. The data output must be kept invalid before
-- the transceiver is locked on the incoming signal to prevent the EP from
-- detecting a false carrier.
rx_data_o : out std_logic_vector(15 downto 0);
-- 1 when the byte on rx_data_o is a control code
rx_k_o : out std_logic_vector(1 downto 0);
-- encoding error indication
rx_enc_err_o : out std_logic;
-- RX bitslide indication, indicating the delay of the RX path of the
-- transceiver (in UIs). Must be valid when ch0_rx_data_o is valid.
rx_bitslide_o : out std_logic_vector(4 downto 0);
-- reset input, active hi
rst_i : in std_logic;
loopen_i : in std_logic_vector(2 downto 0);
debug_i : in std_logic_vector(15 downto 0);
debug_o : out std_logic_vector(15 downto 0);
pad_txn_o : out std_logic;
pad_txp_o : out std_logic;
pad_rxn_i : in std_logic := '0';
pad_rxp_i : in std_logic := '0';
rdy_o : out std_logic);
end wr_gth_phy_kintex7ultrascale;
architecture rtl of wr_gth_phy_kintex7ultrascale is
component wr_gth_wrapper_example_top is
port (
ch0_gthrxn_in : in std_logic;
ch0_gthrxp_in : in std_logic;
ch0_gthtxn_out : out std_logic;
ch0_gthtxp_out : out std_logic;
hb_gtwiz_reset_all_in : in std_logic;
hb_gtwiz_reset_clk_freerun_in : in std_logic;
mgtrefclk0_x0y2_n : in std_logic;
mgtrefclk0_x0y2_p : in std_logic;
rx_byte_is_aligned_o : out std_logic;
rx_clk_o : out std_logic;
rx_comma_det_o : out std_logic;
rx_data_o : out std_logic_vector(15 downto 0);
rx_k_o : out std_logic_vector(1 downto 0);
rx_slide_i : in std_logic;
tx_clk_o : out std_logic;
tx_data_i : in std_logic_vector(15 downto 0);
tx_k_i : in std_logic_vector(1 downto 0);
ready_o : out std_logic);
end component wr_gth_wrapper_example_top;
component gtp_bitslide is
generic (
g_simulation : integer;
g_target : string);
port (
gtp_rst_i : in std_logic;
gtp_rx_clk_i : in std_logic;
gtp_rx_comma_det_i : in std_logic;
gtp_rx_byte_is_aligned_i : in std_logic;
serdes_ready_i : in std_logic;
gtp_rx_slide_o : out std_logic;
gtp_rx_cdr_rst_o : out std_logic;
bitslide_o : out std_logic_vector(4 downto 0);
synced_o : out std_logic);
end component gtp_bitslide;
signal rx_clk, tx_clk : std_logic;
signal serdes_ready, rx_comma_det, rx_byte_is_aligned, rx_slide : std_logic;
signal rx_synced,rst_rxclk : std_logic;
signal rx_data_int : std_logic_vector(15 downto 0);
signal rx_k_int : std_logic_vector(1 downto 0);
signal cur_disp : t_8b10b_disparity;
signal tx_is_k_swapped : std_logic_vector(1 downto 0);
signal tx_data_swapped : std_logic_vector(15 downto 0);
attribute keep : string;
attribute keep of rx_data_int : signal is "true";
attribute keep of rx_k_int : signal is "true";
begin
U_Sync_Reset : gc_sync_ffs
port map (
clk_i => rx_clk,
rst_n_i => '1',
data_i => rst_i,
synced_o => rst_rxclk);
U_Bitslide : gtp_bitslide
generic map (
g_simulation => g_simulation,
g_target => "virtex6")
port map (
gtp_rst_i => rst_i,
gtp_rx_clk_i => rx_clk,
gtp_rx_comma_det_i => rx_comma_det,
gtp_rx_byte_is_aligned_i => rx_byte_is_aligned,
serdes_ready_i => serdes_ready,
gtp_rx_slide_o => rx_slide,
gtp_rx_cdr_rst_o => open,
bitslide_o => rx_bitslide_o,
synced_o => rx_synced);
tx_is_k_swapped <= tx_k_i(0) & tx_k_i(1);
tx_data_swapped <= tx_data_i(7 downto 0) & tx_data_i(15 downto 8);
U_Wrapped_GTH : wr_gth_wrapper_example_top
port map (
ch0_gthrxn_in => pad_rxn_i,
ch0_gthrxp_in => pad_rxp_i,
ch0_gthtxn_out => pad_txn_o,
ch0_gthtxp_out => pad_txp_o,
hb_gtwiz_reset_all_in => rst_i,
hb_gtwiz_reset_clk_freerun_in => clk_freerun_i,
mgtrefclk0_x0y2_n => clk_gth_n_i,
mgtrefclk0_x0y2_p => clk_gth_p_i,
rx_byte_is_aligned_o => rx_byte_is_aligned,
rx_clk_o => rx_clk,
rx_comma_det_o => rx_comma_det,
rx_data_o => rx_data_int,
rx_k_o => rx_k_int,
rx_slide_i => rx_slide,
tx_clk_o => tx_clk,
tx_data_i => tx_data_swapped,
tx_k_i => tx_is_k_swapped,
ready_o => serdes_ready);
p_gen_rx_outputs : process(rx_clk, rst_rxclk)
begin
if(rst_rxclk = '1') then
rx_data_o <= (others => '0');
rx_k_o <= (others => '0');
rx_enc_err_o <= '0';
elsif rising_edge(rx_clk) then
if(serdes_ready = '1' and rx_synced = '1') then
rx_data_o <= rx_data_int(7 downto 0) & rx_data_int(15 downto 8);
rx_k_o <= rx_k_int(0) & rx_k_int(1);
rx_enc_err_o <= '0'; --rx_disp_err(0) or rx_disp_err(1) or rx_code_err(0) or rx_code_err(1);
else
rx_data_o <= (others => '1');
rx_k_o <= (others => '1');
rx_enc_err_o <= '1';
end if;
end if;
end process;
p_gen_tx_disparity : process(tx_clk)
begin
if rising_edge(tx_clk) then
if serdes_ready = '0' then
cur_disp <= RD_MINUS;
else
cur_disp <= f_next_8b10b_disparity16(cur_disp, tx_k_i, tx_data_i);
end if;
end if;
end process;
tx_disparity_o <= to_std_logic(cur_disp);
tx_out_clk_o <= tx_clk;
rx_rbclk_o <= rx_clk;
rdy_o <= serdes_ready and rx_synced;
tx_locked_o <= '1';
tx_enc_err_o <= '0';
end rtl;
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment