AMBPEX5_v20_SX50T_CORE
adm/main/cl_test_generate.vhd
00001 -------------------------------------------------------------------------------
00002 --
00003 -- Title       : cl_test_generate
00004 -- Author      : Dmitry Smekhov
00005 -- Company     : Instrumental Systems
00006 -- E-mail      : dsmv@insys.ru
00007 --
00008 -- Version     : 1.0
00009 --
00010 -------------------------------------------------------------------------------
00011 --
00012 -- Description :        Узел формирования потока данных
00013 --                              
00014 --              Тестовая последовательность представляет собой набор блоков. 
00015 --              Размер блока задаётся кратным страницы размером 4 килобайта 
00016 --              (512 слов по 64 бита)
00017 --              Первое 64-х разрядное слово в блоке содержит сигнатуру и порядковый номер.   
00018 --                  31..0  - сигнатура 0xA5A50123
00019 --                      63..32 - порядковый номер блока
00020 --
00021 --              Содержимое блока зависит от его порядкового номера в последовательности.  
00022 --
00023 --              Содержимое блока:
00024 --              0 - Бегущая единица по 64-м разрядам
00025 --              1 - Бегущий ноль по 64-м разрядам
00026 --              2 - Бегущая единица с инверсией по 64-м разрядам
00027 ---                     Чётные номера слов - бегущая единица по 64-м разрядам
00028 --                      Нечётные номера - инверсия предыдущего слова               
00029 --              3 - Бегущая единица в блоке
00030 --                      Номер слова сравнивается с номером блока (сравниваются восемь младший разрядов)
00031 --                      При совпадении - в слово записывается бегущая 1.
00032 --                      Остальные слова - значение ноль.
00033 --              4 - Бегущий ноль с инверсией по 64-м разрядам
00034 --                      Чётные номера - бегущий ноль по 64-м разрядам
00035 --                      Нечётные номера - инверсия предыдущего слова               
00036 --              5 - Бегущий ноль а в блоке
00037 --                      Номер слова сравнивается с номером блока (сравниваются восемь младший разрядов)
00038 --                      При совпадении - в слово записывается бегущий 0.
00039 --                      Остальные слова - значение 0xFFFFFFFFFFFFFFFF.
00040 --              6,7 - Счётчик по 64-м разрядам
00041 --                      Чётные номера - значение счётчика
00042 --                      Нечётные номера - инверсия предыдущего слова
00043 --              8,9 - Псевдослучайная последовательность
00044 --                      Формируется М-последовательность по 64 разрядам.
00045 --                      Начальное значение - 1
00046 --                      Слово формируется сдвигом на один разряд вправо.
00047 --                      В младший разряд слова записывается значение x[63] xor x[62]
00048 --                                                                                                                              
00049 --
00050 --              Для режима счётчика и псевдослучайной последовательности начальное значение
00051 --              формируется при инициализации тестовой последовательности.
00052 --              Для остальных режимов - при инициализации проверки блока
00053 --
00054 --
00055 --              Регистр test_check_ctrl
00056 --                         
00057 --                              0 - 1 сброс узла
00058 --                              5 - 1 старт приёма данных
00059 --                              7 - 1 фиксированный тип блока
00060 --                              11..8 - номер блока при test_check_ctrl[7]=1
00061 --                              
00062 
00063 -------------------------------------------------------------------------------
00064 --
00065 -- Version     1.1   06.12.2010
00066 --                          Исправлено использование сигнала СТАРТ при работе по счётчикам.
00067 --                              Исправлено использование бита test_gen_ctrl(12) 
00068 --                              при работе без счётчиков. 
00069 --
00070 -------------------------------------------------------------------------------
00071 
00072 
00073 
00074 
00075 library ieee;
00076 use ieee.std_logic_1164.all;     
00077 library work;
00078 use work.adm2_pkg.all;
00079 
00080 package cl_test_generate_pkg is
00081 
00082 component cl_test_generate is
00083         port(
00084         
00085                 ---- Global ----
00086                 reset           : in std_logic;         -- 0 - сброс
00087                 clk                     : in std_logic;         -- тактовая частота
00088                 
00089                 ---- DIO_IN ----
00090                 di_clk          : in  std_logic;        -- тактовая частота записи в FIFO
00091                 di_data         : out std_logic_vector( 63 downto 0 );  -- данные
00092                 di_data_we      : out std_logic;        -- 1 - запись данных
00093                 di_flag_paf     : in  std_logic;        -- 1 - есть место для записи
00094                 di_fifo_rst     : in  std_logic;        -- 0 - сброс FIFO
00095                 di_start        : in  std_logic;        -- 1 - разрешение работы (MODE0[5])
00096                 
00097                 
00098                 ---- Управление ----
00099                 test_gen_ctrl   : in  std_logic_vector( 15 downto 0 );  -- Регистр управления
00100                 test_gen_size   : in  std_logic_vector( 15 downto 0 );  -- размер в блоках по 512x64 (4096 байт)
00101                 test_gen_bl_wr  : out std_logic_vector( 31 downto 0 );  -- Число записанных блоков
00102                 test_gen_cnt1   : in  std_logic_vector( 15 downto 0 );  -- Счётчик разрешения работы
00103                 test_gen_cnt2   : in  std_logic_vector( 15 downto 0 )   -- Счётчик запрещения работы
00104         
00105         );
00106 end component;
00107 
00108 end package;
00109 
00110 
00111 library ieee;
00112 use ieee.std_logic_1164.all;     
00113 use ieee.std_logic_arith.all;
00114 use ieee.std_logic_unsigned.all;
00115 
00116 library unisim;
00117 use unisim.vcomponents.all;
00118 
00119 library work;
00120 use work.adm2_pkg.all;
00121 
00122 entity cl_test_generate is
00123         port(
00124         
00125                 ---- Global ----
00126                 reset           : in std_logic;         -- 0 - сброс
00127                 clk                     : in std_logic;         -- тактовая частота
00128                 
00129                 ---- DIO_IN ----
00130                 di_clk          : in  std_logic;        -- тактовая частота записи в FIFO
00131                 di_data         : out std_logic_vector( 63 downto 0 );  -- данные
00132                 di_data_we      : out std_logic;        -- 1 - запись данных
00133                 di_flag_paf     : in  std_logic;        -- 1 - есть место для записи
00134                 di_fifo_rst     : in  std_logic;        -- 0 - сброс FIFO
00135                 di_start        : in  std_logic;        -- 1 - разрешение работы (MODE0[5])
00136                 
00137                 ---- Управление ----
00138                 test_gen_ctrl   : in  std_logic_vector( 15 downto 0 );  -- Регистр управления
00139                 test_gen_size   : in  std_logic_vector( 15 downto 0 );  -- размер в блоках по 512x64 (4096 байт)
00140                 test_gen_bl_wr  : out std_logic_vector( 31 downto 0 );  -- Число записанных блоков
00141                 test_gen_cnt1   : in  std_logic_vector( 15 downto 0 );  -- Счётчик разрешения работы
00142                 test_gen_cnt2   : in  std_logic_vector( 15 downto 0 )   -- Счётчик запрещения работы
00143         
00144         );
00145 end cl_test_generate;
00146 
00147 
00148 architecture cl_test_generate of cl_test_generate is
00149 
00150 signal  block_rd                : std_logic_vector( 31 downto 0 );
00151 
00152 signal  data_expect             : std_logic_vector( 63 downto 0 );
00153 
00154 signal  cnt1                    : std_logic_vector( 24 downto 0 );
00155 signal  cnt1_z                  : std_logic;
00156 signal  cnt1_eq                 : std_logic;
00157 
00158 signal  rst                             : std_logic;
00159 signal  data_en                 : std_logic;    -- 1 - приём слова данных  
00160 
00161 signal  data_ex0                : std_logic_vector( 63 downto 0 );
00162 signal  data_ex1                : std_logic_vector( 63 downto 0 );
00163 signal  data_ex2                : std_logic_vector( 63 downto 0 );
00164 signal  data_ex3                : std_logic_vector( 63 downto 0 );
00165 signal  data_ex4                : std_logic_vector( 63 downto 0 );
00166 signal  data_ex5                : std_logic_vector( 63 downto 0 );
00167 
00168 
00169 signal  block_mode              : std_logic_vector( 3 downto 0 );          
00170 
00171 signal  xcnt1                   : std_logic_vector( 15 downto 0 );
00172 signal  xcnt2                   : std_logic_vector( 15 downto 0 );        
00173 
00174 signal  xcnt1_z                 : std_logic;
00175 signal  xcnt2_z                 : std_logic;
00176 
00177 type stp_type is ( s0, s1, s2, s3 );
00178 signal  stp                             : stp_type;                     
00179 
00180 signal  di_rdy                  : std_logic;
00181 
00182 begin
00183         
00184 pr_cnt1: process( di_clk ) begin        
00185         if( rising_edge( di_clk ) ) then
00186                 if( rst='0' or (cnt1_eq='1' and data_en='1') ) then                                
00187                         cnt1( 24 downto 0 )   <= (others=>'0') after 1 ns;
00188                 elsif( data_en='1' ) then
00189                         cnt1 <= cnt1 + 1 after 1 ns;
00190                 end if;
00191         end if;
00192 end process;
00193 
00194 pr_cnt1_z: process( di_clk ) begin
00195         if( rising_edge( di_clk ) ) then
00196                 
00197                 if( rst='0' ) then
00198                         cnt1_z <= '1' after 1 ns;
00199                         cnt1_eq <= '0' after 1 ns;
00200                 elsif( data_en='1' ) then
00201                         
00202                         if( cnt1_eq='1' ) then                             
00203                                 cnt1_z <= '1' after 1 ns;
00204                         else
00205                                 cnt1_z <= '0' after 1 ns;
00206                         end if;                                                                                                                                          
00207                         
00208                         if( cnt1( 24 downto 9 )=test_gen_size-1 and cnt1( 8 downto 0 )="111111110" ) then
00209                                 cnt1_eq <= '1' after 1 ns;
00210                         else
00211                                 cnt1_eq <= '0' after 1 ns;
00212                         end if;
00213                 end if;
00214                 
00215         end if;
00216 end process;
00217 
00218 
00219         
00220 --pr_data_en: process( di_clk ) begin
00221 --      if( rising_edge( di_clk ) ) then
00222 --              if( rst='0' or test_gen_ctrl(5)='0' or di_flag_paf='0' or di_start='0' ) then
00223 --                      data_en <='0' after 1 ns;
00224 --              else
00225 --                      data_en <= '1' after 1 ns;
00226 --              end if;
00227 --      end if;
00228 --end process;                          
00229 
00230 di_rdy <= (di_flag_paf or test_gen_ctrl(12) ) and di_start after 1 ns when rising_edge( di_clk );
00231 
00232 pr_state: process( di_clk ) begin
00233         if( rising_edge( di_clk ) ) then
00234                 case( stp ) is
00235                         when s0 => -- Ожидание --
00236                                 if( test_gen_ctrl(5)='1' ) then
00237                                         if( test_gen_ctrl( 6 )='1' ) then
00238                                                 stp <= s2 after 1 ns;
00239                                         else
00240                                                 stp <= s1 after 1 ns;
00241                                         end if;
00242                                 end if;
00243                                 data_en <= '0' after 1 ns;
00244                                 
00245                         when s1 => -- Передача по готовности FIFO --
00246                                 data_en <= di_rdy after 1 ns;
00247                                 if( test_gen_ctrl(5)='0' ) then
00248                                         stp <= s0 after 1 ns;
00249                                 end if;
00250                                 
00251                         when s2 => -- Передача по счётчикам CNT1, CNT2
00252                                 data_en <= di_rdy after 1 ns;
00253                                 if( test_gen_ctrl(5)='0' ) then
00254                                         stp <= s0 after 1 ns;
00255                                 elsif( xcnt1_z='1' ) then
00256                                         stp <= s3 after 1 ns;
00257                                 end if;
00258                                 
00259                         when s3 =>
00260                                 data_en <= '0' after 1 ns;
00261                                 if( test_gen_ctrl(5)='0' ) then
00262                                         stp <= s0 after 1 ns;
00263                                 elsif( xcnt2_z='1' ) then
00264                                         stp <= s2 after 1 ns;
00265                                 end if;                                  
00266                 end case;
00267                 
00268                 if( rst='0' ) then
00269                         stp <= s0 after 1 ns;
00270                 end if;
00271                 
00272         end if;
00273 end process;    
00274                 
00275 pr_xcnt1: process( di_clk ) begin
00276         if( rising_edge( di_clk ) ) then
00277                 if( stp/=s2 ) then
00278                         xcnt1 <= test_gen_cnt1 after 1 ns;
00279                 else
00280                         xcnt1 <= xcnt1 - 1 after 1 ns;
00281                 end if;
00282         end if;
00283 end process;
00284                                         
00285 pr_xcnt2: process( di_clk ) begin
00286         if( rising_edge( di_clk ) ) then
00287                 if( stp/=s3 ) then
00288                         xcnt2 <= test_gen_cnt2 after 1 ns;
00289                 else
00290                         xcnt2 <= xcnt2 - 1 after 1 ns;
00291                 end if;
00292         end if;
00293 end process;
00294 
00295 xcnt1_z <= '1' when xcnt1=x"0002" else '0';
00296         
00297 xcnt2_z <= '1' when xcnt2=x"0002" else '0';
00298         
00299 
00300 rst <= reset and not test_gen_ctrl(0);
00301                                                                                                                   
00302 pr_block_mode: process( di_clk ) begin
00303         if( rising_edge( di_clk ) ) then
00304                 if( rst='0' ) then
00305                         block_mode <= "0000" after 1 ns;        
00306                 elsif( test_gen_ctrl(7)='1' ) then
00307                         block_mode <= test_gen_ctrl( 11 downto 8 ) after 1 ns;
00308                 elsif( data_en='1' and cnt1_eq='1' ) then
00309                                 if( block_mode="1001" ) then
00310                                         block_mode <= "0000" after 1 ns;
00311                                 else
00312                                         block_mode <= block_mode + 1 after 1 ns;
00313                                 end if;
00314                 end if;
00315         end if;
00316 end process;
00317 
00318 pr_block_rd: process( di_clk ) begin
00319         if( rising_edge( di_clk ) ) then
00320                 if( rst='0' ) then
00321                         block_rd <= (others=>'0') after 1 ns;
00322                 elsif( data_en='1' and cnt1_eq='1' ) then
00323                         block_rd <= block_rd + 1 after 1 ns;
00324                 end if;
00325         end if;
00326 end process;
00327         
00328 pr_data_expect: process( di_clk ) begin
00329         if( rising_edge( di_clk ) ) then  
00330           if( rst='0' ) then
00331                   data_ex4 <= (others=>'0') after 1 ns;
00332                   data_ex5 <= (0=>'1', others=>'0') after 1 ns;
00333                   data_ex0 <= x"0000000000000001" after 1 ns;
00334           elsif( data_en='1' ) then
00335                 if( cnt1_z='1' ) then
00336                         data_expect( 31 downto 0 ) <= x"A5A50123" after 1 ns;
00337                         data_expect( 63 downto 32 ) <= block_rd after 1 ns;
00338                         case( block_mode( 3 downto 0 ) ) is
00339                           when "0000" => -- Бегущая 1 по 64-м разрядам
00340                                 data_ex0 <= x"0000000000000001" after 1 ns;
00341                           when "0001" => -- Бегущий 0 по 64-м разрядам
00342                                 data_ex0 <= not x"0000000000000001" after 1 ns;
00343                           when "0010" => -- Бегущая 1 с инверсией  по 64-м разрядам
00344                                 data_ex1 <= x"0000000000000001" after 1 ns;
00345                           when "0011" => -- Бегущий 0 с инверсией  по 64-м разрядам
00346                                 data_ex1 <= not x"0000000000000001" after 1 ns;
00347                           when "0100" => -- Бегущая 1 в блоке 0
00348                                 data_ex2 <= x"0000000000000001" after 1 ns;
00349                                 data_ex3 <= (others=>'0');
00350                           when "0101" => -- Бегущий 0 в блоке 1
00351                                 data_ex2 <= not x"0000000000000001" after 1 ns;
00352                                 data_ex3 <= (others=>'1') after 1 ns;
00353                           
00354                           when others=> null;
00355                         end case;
00356                 else
00357                         case( block_mode( 3 downto 0 ) )is
00358                           when "0000" | "0001" => 
00359                                 data_expect <= data_ex0 after 1 ns;
00360                                 data_ex0( 63 downto 1 ) <= data_ex0( 62 downto 0 ) after  1 ns;
00361                                 data_ex0( 0 ) <= data_ex0( 63 ) after 1 ns;
00362                                 
00363                           when "0010" | "0011" => -- Бегущий 0 с инверсией  по 32-м разрядам
00364 --                        when "0011" => -- Бегущий 0 с инверсией  по 64-м разрядам
00365                                 if( cnt1(0)='0' ) then
00366                                         data_expect <= data_ex1 after 1 ns;
00367                                 else
00368                                         data_expect <= not data_ex1 after 1 ns;
00369                                         data_ex1( 63 downto 1 ) <= data_ex1( 62 downto 0 ) after  1 ns;
00370                                         data_ex1( 0 ) <= data_ex1( 63 ) after 1 ns;
00371                                 end if;
00372                           when "0100" | "0101" => -- Бегущий 0 в блоке 1
00373 --                        when "0111" => -- Бегущий 1 в блоке 0
00374                                 if( cnt1( 7 downto 0 )=block_rd( 7 downto 0 ) )then
00375                                         data_expect <= data_ex2 after 1 ns;
00376                                         data_ex2( 63 downto 1 ) <= data_ex2( 62 downto 0 ) after  1 ns;
00377                                         data_ex2( 0 ) <= data_ex2( 63 ) after 1 ns;
00378                                 else
00379                                         data_expect <= data_ex3 after 1 ns;
00380                                 end if;
00381                                 
00382                           when "0110" | "0111" => -- Счётчик 
00383                             if( cnt1(0)='0' ) then
00384                                         data_expect <= data_ex4 after 1 ns;             
00385                                 else
00386                                         data_expect <= not data_ex4 after 1 ns;         
00387 --                                      data_ex4 <= data_ex4 + x"0000000000000001";
00388                                         data_ex4(31 downto 0) <= data_ex4(31 downto 0) + 1;
00389                                         if (data_ex4(31 downto 0)=x"FFFFFFFF") then
00390                                                 data_ex4(63 downto 32) <= data_ex4(63 downto 32) + 1;
00391                                         end if;
00392                                                 
00393                                 end if;
00394                                           
00395                           
00396                           when "1000" | "1001" => -- Псевдослучайная последовательность                 
00397                                         data_expect <= data_ex5 after 1 ns;
00398                                         data_ex5( 63 downto 1 ) <= data_ex5( 62 downto 0 ) after 1 ns;
00399                                         --data_ex5( 0 ) <= data_ex5( 63 ) xor data_ex5(62) after 1 ns;
00400                                         data_ex5( 0 ) <= data_ex5( 63 ) xor data_ex5(62) xor data_ex5(60) xor data_ex5(59) after 1 ns;
00401                           when others=> null;
00402                         end case;
00403                 end if; 
00404           end if;
00405         end if;
00406 end process;
00407                         
00408         
00409 di_data <= data_expect; 
00410 di_data_we <= data_en after 1 ns when rising_edge( di_clk );
00411 test_gen_bl_wr <= block_rd;
00412                                                 
00413 end cl_test_generate;