VHDL 2nd Ring Oscillator Using External Clock,

102 views Asked by At

I am new to VHDL, so I have developed some code for a Ring Oscillator using the internal clock of my board, but I want to add a 2nd One using the internal clock, but I have some issues with understanding how to go by it. The first one works perfectly normal, however when I tried adding the second one numerous times, I had issues with the output. I also want to XOR both outputs and store them in the vector I have in my code, but I have been struggling as into why it doesn't work.

Below is my code for my ring oscillator using the internal clock, I also included the external clock in the entity so my question is, is it just as so just calling it within the process.

`

`library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use ieee.std_logic_unsigned.ALL;

entity RO_TRNG is
    Port ( trn : out std_logic_vector(20 downto 0);
       reset : in  STD_LOGIC; 
       sample: in STD_LOGIC;
        clk : in  std_logic);
end entity RO_TRNG;

architecture Behavioral of RO_TRNG is

component iclk is 
port(
      iclk_clk : out std_logic;
        iclk_en_oscena : in std_logic);
end component;


  signal ring    : std_logic_vector(20 downto 0):= "100101101011011101001";
  signal clk_int : std_logic;
  attribute KEEP : string; 
  attribute KEEP of ring : signal is "true"; 

begin

  u0 : COMPONENT iclk port map (iclk_clk=>clk_int,iclk_en_oscena=>'1');
  assert ring'length mod 2 = 1 report "Length of ring must be an odd number!" severity failure;

  trn <= ring when sample ='0';
  
  process (clk_int,ring,reset) begin
  if reset='0' then
      ring <= "100101101011011101001";
  else
      if rising_edge(clk_int) then
          for i in ring'range loop
             if i = ring'left then
                  ring(i) <= not ring(0) after 1ns;
             else
                ring(i)   <= not ring(i+1) after 1ns;
             end if;
          end loop;
          end if;
    end if;
  end process;

end Behavioral;


``

I tried various attempts to call it within the process, but it seems not to work. I believe it may have to do with where i placed it in the code.

1

There are 1 answers

0
Jim Lewis On

I see one issue with trn. You need an else condition with it as otherwise it creates a latch:

 trn <= ring when sample ='0' else '0';

With respect to your process, this does the same thing, but it is a little simpler. Also I removed ring from the sensitivity list as you don't need it. If the code is meant to be synthesizable, you don't need the after 1 ns.

  process (clk_int,reset) begin
    if reset='0' then
      ring <= "100101101011011101001";
    elsif rising_edge(clk_int) then
      ring <= ring(0) & ring(20 downto 1) ; 
    end if;
  end process;

You have some questions about doing something from a process. If you are referring to instancing your component, you can only do that from the architecture (concurrent code region).

  u0 : COMPONENT iclk port map (iclk_clk=>clk_int,iclk_en_oscena=>'1');

If you are struggling of what concurrency is in VHDL, it is nothing more than code that runs independently of other code. So your process runs separately from your component instance. Pieces of real hardware do the exact same thing.