Search code examples
vhdl

Do you have any idea how I can make this code generate numbers only between 1 and 6, it generates between 1 and 7


entity LFSR is
  Port (   clk : in STD_LOGIC; 
           en: in STD_LOGIC; 
           reset: in STD_LOGIC;  
           output_lfsr: out STD_LOGIC_VECTOR(2 downto 0) 
           ); 
end LFSR;

architecture Behavioral of LFSR is
    signal lfsr : std_logic_vector(2 downto 0); 
    constant poly : std_logic_vector(2 downto 0) := "011"; 
    begin 
        process(clk, reset, lfsr)  
        variable ext_inbit: std_logic_vector(2 downto 0);
        variable inbit: std_logic;  
    begin 
        inbit:=lfsr(2);   -- preia valoarea iesirii Q2 
            for i in 0 to 2 loop    
        ext_inbit(i):=inbit; 
            end loop; 
        if (reset='1') then   
          lfsr<="111";
        elsif (clk'event and clk='1') then 
            if(en='1') then   
                   lfsr<=(lfsr(1 downto 0) & '0') xor (ext_inbit and poly);  
                                 
            end if; 
        end if; 
    end process; 
    output_lfsr <= lfsr;   
end Behavioral;

Solution

  • This is a quick and dirty solution. There are ways to clean it up and pipeline it. Do the operation once again if the value is 7.

    library ieee;
    use ieee.std_logic_1164.all;
    use ieee.numeric_std.all;
    
    entity lfsr is
      port (clk         : in  std_logic;
            en          : in  std_logic;
            reset       : in  std_logic;
            output_lfsr : out std_logic_vector(2 downto 0)
            );
    end lfsr;
    
    architecture behavioral of lfsr is
    
      signal s_lfsr     : std_logic_vector(2 downto 0);
      constant poly     : std_logic_vector(2 downto 0) := "011";
    
    begin
      process(clk, reset)
        variable v_lfsr_int : std_logic_vector(2 downto 0);
        variable ext_inbit : std_logic_vector(2 downto 0);
        variable inbit     : std_logic;
      begin
    
        if (reset = '1') then
          s_lfsr <= "011";
        elsif (rising_edge(clk)) then
        
          inbit := s_lfsr(2);               -- preia valoarea iesirii Q2
          for i in 0 to 2 loop
            ext_inbit(i) := inbit;
          end loop;
          
          if(en = '1') then
            v_lfsr_int := (s_lfsr(1 downto 0) & '0') xor (ext_inbit and poly);
            if(v_lfsr_int = "111") then
              s_lfsr <= (v_lfsr_int(1 downto 0) & '0') xor (ext_inbit and poly);
            else
              s_lfsr <= v_lfsr_int;
            end if;
          end if;
        end if;
    
      end process;
    
      output_lfsr <= s_lfsr;
    
    end behavioral;
    

    As you can see, I've changed a few things as well:

    • Added ieee libraries
    • process sensitivity list updated for a asynchronous reset
    • rearranged the ext_inbit to avoid the tool shouting that the sensitivity list is incomplete. Considering that the value is same as lfsr(2) after elaboration, you can even put this outside the process.
    • signal name and entity name was the same. renamed to increase readability. Recheck the standard to see if it is allowed.