Forum Discussion

Altera_Forum's avatar
Altera_Forum
Icon for Honored Contributor rankHonored Contributor
9 years ago

FSK Modulation in VHDL

Hello,

I have written a testbench which performs FSK modulation. The testbench should perform the auto checks such that when fsk_data_i(0) = '1' then I need to push fsk_u_i to fsk_mod_o whereas if fsk_data_i(0) = '0' then I need to push fsk_l_i to fsk_mod_o. But it is not doing so in my code. I don't know why. Also I am getting an error " Index 22 out of bound 21 downto 0". The tetbench code looks like this:

stim_proc: process
  begin  
      
    wait for 10 ns;
    reset_n_i <='1';
  
    wait for clk_128meg_i_period;
    enable_i <='1';
    --fsk_u_i <= "10001000";                        -- 136
    --fsk_l_i <= "11101000";                        -- 232
    --fsk_data_i <= "1111000010101010111010";       -- 3943098
  
  new_fsk_u_s <= "10101010";
    new_fsk_l_s <= "11110000";
    new_fsk_data_s <= "1110101101010101010111";
  
  wait for 1 ns;
  new_fsk_u_s <= "10001000";
  new_fsk_l_s <= "11101000";
  new_fsk_data_s <= "1111000010101010111010";
  
    wait for 10 ms;
    reset_n_i <= '0';
 
    wait for 1 ms;
    reset_n_i <= '1';
    wait for 1 ms;
    enable_i <= '0';
    wait for 1 ms;
    enable_i <= '1';
    wait for 1 ms;
    assert false report "End of simulation" severity failure;
  end process;
  delay_rst_s <= reset_n_i after 1 ns;
  p_check :process(delay_rst_s, clk_128meg_i)
  begin
    if (delay_rst_s = '0') then
       clk_cycles_s <= (others => '0');
      cnt_s <= (others => '0');
      assert fsk_mod_o = "00000000" report " Output is not set to default value when reset_n_i is 0" severity error;
    elsif (clk_128meg_i'event and clk_128meg_i = '0') then
      if (enable_i = '1') then
   clk_cycles_s <= std_logic_vector(unsigned(clk_cycles_s) + 1);
   if (clk_cycles_s >= "1111111111") then
     cnt_s <= std_logic_vector(unsigned(cnt_s) + 1);
   if(fsk_data_i(to_integer(unsigned(cnt_s))) = '1') then
       assert fsk_mod_o = std_logic_vector(fsk_u_i) report " Wrong output: fsk_u_i should be shifted " severity error;
         elsif (fsk_data_i(to_integer(unsigned(cnt_s))) = '0') then
             assert fsk_mod_o = std_logic_vector(fsk_l_i) report " Wrong output: fsk_l_i should be shifted " severity error;
         end if;
       end if;
   else
         cnt_s <= (others =>'0');
   clk_cycles_s <= (others => '0');
      end if;
     end if;
 end process;

And the VHDL code is as follows:

begin
  p_fsk_mod : process(reset_n_i, clk_128meg_i)
  begin
    if (reset_n_i = '0') then
      temp_s <= (others => '0');
      cnt_s <= (others => '0');
      cntdiv_s <= (others => '0');
    elsif (clk_128meg_i'event and clk_128meg_i = '1') then
      if (enable_i = '1') then
 cntdiv_s <= std_logic_vector(unsigned(cntdiv_s) + 1);   -- counter to count the clock cycles--
   if (cntdiv_s >= "1111111111") then            -- condition to check if the clock cycle is equal to 1023--
     cnt_s <= std_logic_vector(unsigned(cnt_s) + 1);   -- increment the "logik" block--
       if (fsk_data_i(to_integer((unsigned(cnt_s)))) = '1') then   -- shift the bits of fsk_data_i according to the value of the "logik" block--
  temp_s <= std_logic_vector(fsk_u_i);     -- perform the muliplexer operation based on the bits being pushed by the "logik" block--
       else
  temp_s <= std_logic_vector(fsk_l_i);
       end if;
   end if;
      else
 temp_s <= (others => '0');
 cnt_s <= (others => '0');
 cntdiv_s <= (others => '0');  
      end if;
    end if;
  end process;
  fsk_mod_o <= temp_s ;

I couldn't figure out what the mistake is. Can anyone help me out. Thanks in advance.

10 Replies

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    if (fsk_data_i(to_integer((unsigned(cnt_s)))) = '1')

    '1' is std_logic, how come it passed compilation

    sorry my fault(it is index)
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Your problem is difficult to read due to too much type conversion and lack of concept explanation and lack of full code

    The issue of bit out of range should be obvious. your data is 22 bits yet the counter is exceeding 21 index. you need to account for that and constrain your counter.
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Yes, but when I tried to constrain the counter still I am having the error. I will explain how the code works, maybe you will have an idea about it.

    First of all, the clk_cycles_s is used to push each values of fsk_data_i, fsk_u_i and fsk_l_i after every 1023rd clock cycle because that's the main motive of my design. I am designing a PLL that needs to be clocked only after every 1023rd clock cycle. After the first 1023rd cycle(assume), new values of fsk_data_i, fsk_u_i and fsk_l_i has to be provided as per my code(sorry i didn't declare in my testbench, but checked only for a single values of all the above three, its working properly). Once all the 22 bits of fsk_data_i (since i have defined the bit width as 22), new values for fsk_data_i, fsk_u_i, fsk_l_i should be defined, which I don't know how to do.

    What I need exactly is, I need to change the inputs when all the 22 bits of the fsk_data_i are checked. I think so , you have understood the manner in which my code actually works. I need to help me to solve this issue
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    I just don't know why still I get the error " Index 22 out of bound 21 downto 0". Please help me out to solve this issue.

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    have a look at my changes (not tested), counters as integers (0 to 1023 & 0 to 21)

    
    begin
      process(resetn, clk)
      begin
        if resetn = '0' then
          fsk_mod_o <= (others => '0');
          cnt_s     <= 0;
          cntdiv_s  <= 0;
        elsif clk'event and clk = '1' then
          if enable = '1' then
              cntdiv_s <= cntdiv_s + 1;       
              if cntdiv_s = 1023 then  
                  cntdiv_s <= 0;    
                  cnt_s <= cnt_s + 1; 
                  if cnt_s = 21 then
                     cnt_s <= 0;
                  end if; 
             end if;
         
               if fsk_data_i(cnt_s) = '1' then  
                  fsk_mod_o <= std_logic_vector(fsk_u_i);                
               else
                  fsk_mod_o <= std_logic_vector(fsk_l_i);
               end if;
         
             end if;
           end if;
        end if;
      end process;
    
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Thanks kaz, I got it , but i need to know like how to update new values of fsk_data/ u /l once all the values of fsk_data are checked

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    --- Quote Start ---

    Thanks kaz, I got it , but i need to know like how to update new values of fsk_data/ u /l once all the values of fsk_data are checked

    --- Quote End ---

    when clock count reaches 22*1024 a new value can be passed to your design
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Instead of using the wait statement like wait for 22.5 us, is there any other way to implement it

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    I tried with the wait statement and its working well, but actually I need another method where within the module I can change the input values once all the bits of fsk_data_i are checked. Please help me to solve this issue. Thanks in advance