

LIBRARY ieee;
USE ieee.std_logic_1164.ALL;
USE ieee.numeric_std.ALL;


USE std.textio.ALL;


entity tb_i2s IS


END ENTITY tb_i2s;

ARCHITECTURE truc OF tb_i2s IS

  COMPONENT i2s IS
    GENERIC (
      CLK_RATE   : natural :=50000000;
      AUDIO_DW   : natural :=16;
      AUDIO_RATE : natural :=96000);
    PORT (
      reset : IN std_logic;
      clk_sys : IN std_logic;
      half_rate : IN std_logic;

      sclk : OUT std_logic;
      lrclk : OUT std_logic;
      sdata : OUT std_logic;

      left_chan : IN std_logic_vector(AUDIO_DW-1 DOWNTO 0);
      right_chan : IN std_logic_vector(AUDIO_DW-1 DOWNTO 0)
      );
  END COMPONENT i2s;
  
  COMPONENT i2s2 IS
    GENERIC (
      CLK_RATE   : natural :=50000000;
      AUDIO_DW   : natural :=16;
      AUDIO_RATE : natural :=96000);
    PORT (
      reset : IN std_logic;
      clk_sys : IN std_logic;
      half_rate : IN std_logic;

      sclk : OUT std_logic;
      lrclk : OUT std_logic;
      sdata : OUT std_logic;

      left_chan : IN std_logic_vector(AUDIO_DW-1 DOWNTO 0);
      right_chan : IN std_logic_vector(AUDIO_DW-1 DOWNTO 0)
      );
  END COMPONENT i2s2;
    
  SIGNAL reset,reset2 : std_logic;
  SIGNAL clk_sys : std_logic :='0';
  SIGNAL half_rate : std_logic :='0';
  SIGNAL sclk,sclk2 : std_logic;
  SIGNAL lrclk,lrclk2 : std_logic;
  SIGNAL sdata,sdata2 : std_logic;

  CONSTANT AUDIO_DW : natural :=16;

  SIGNAL left_chan,right_chan : std_logic_vector(AUDIO_DW-1 DOWNTO 0);
  SIGNAL cpt_sclk,cpt_sclk2 : natural RANGE 0 TO 10000000;
  SIGNAL sclk_t0,sclk2_t0 : time :=0 ms;

BEGIN

  u:i2s
    GENERIC MAP (
      CLK_RATE => 50_000_000,
      AUDIO_DW => 16,
      AUDIO_RATE => 96000)
    PORT MAP (
      reset => reset,
      clk_sys => clk_sys,
      half_rate => half_rate,
      sclk => sclk,
      lrclk => lrclk,
      sdata => sdata,
      left_chan => left_chan,
      right_chan => right_chan);
    
  v:i2s2
    GENERIC MAP (
      CLK_RATE => 50_000_000,
      AUDIO_DW => 16,
      AUDIO_RATE => 96000)
    PORT MAP (
      reset => reset2,
      clk_sys => clk_sys,
      half_rate => half_rate,
      sclk => sclk2,
      lrclk => lrclk2,
      sdata => sdata2,
      left_chan => left_chan,
      right_chan => right_chan);
    
  
  clk_sys<=NOT clk_sys AFTER 1 us / 50 / 2;


  Test:PROCESS
  BEGIN
    reset<='1';
    reset2<='1';
    WAIT FOR 10 us;
    reset<='0';

    WAIT FOR 4.7 us;
    reset2<='0';
    
    left_chan<=x"FFFF";
    right_chan<=x"FFFF";
    WAIT FOR 100 us;
    left_chan<=x"0001";
    right_chan<=x"8000";
    WAIT FOR 100 us;
    left_chan<=x"8000";
    right_chan<=x"0001";
    WAIT FOR 100 us;
    left_chan<=x"5555";
    right_chan<=x"5555";
    WAIT FOR 100 us;
    left_chan<=x"AAAA";
    right_chan<=x"AAAA";
    WAIT FOR 100 us;
    left_chan<=x"F0F0";
    right_chan<=x"0F0F";
    
    WAIT;
  END PROCESS Test;


  cpt_sclk<=cpt_sclk+1 WHEN rising_edge(sclk);

  PROCESS (sclk) IS
  BEGIN
    IF rising_edge(sclk) AND sclk_t0<1 us THEN
      sclk_t0<=now;
    END IF;
    IF rising_edge(sclk) AND cpt_sclk>10 AND cpt_sclk MOD 1000=0 THEN
      REPORT "Per=" & time'image(now - sclk_t0) & "/" &
        integer'image(cpt_sclk) & "=" &
        time'image((now - sclk_t0)/(cpt_sclk-1));
    END IF;
  END PROCESS;

 
  cpt_sclk2<=cpt_sclk2+1 WHEN rising_edge(sclk2);
  
  PROCESS (sclk2) IS
  BEGIN
    IF rising_edge(sclk2) AND sclk2_t0<1 us THEN
      sclk2_t0<=now;
    END IF;
    IF rising_edge(sclk2) AND cpt_sclk2>10 AND cpt_sclk2 MOD 1000=0 THEN
      REPORT "Per2=" & time'image(now - sclk2_t0) & "/" &
        integer'image(cpt_sclk2) & "=" &
        time'image((now - sclk2_t0)/(cpt_sclk2-1));
     END IF;
  END PROCESS;


  half_rate<='0','1' AFTER 5000 us;


  
END ARCHITECTURE truc;



