VHDL coding tips and tricks: How to use "generate" keyword for multiple instantiation?
Contact me for VHDL or Verilog projects and assignments

Tuesday, September 14, 2010

How to use "generate" keyword for multiple instantiation?

   Generate statement is a concurrent statement used in VHDL to describe repetitive structures.You can use generate statement in your design to instantiate multiple modules in two ways: the FOR-way and the IF-way.
   FOR-way is explained through a PISO(parallel in serial out) register example I have discussed earlier.The original post can be accessed here. I have modified the Gate level modeling code available in that post using "generate" statement.

--Library declaration.
library ieee;
use ieee.std_logic_1164.all;
--4 bit Parallel In Serial Out shift register(LSB is out first)
entity PISO is
port ( Serial_out : out std_logic;
       Parallel_In : in std_logic_vector(3 downto 0);
       --Load=1 means register is loaded parallely and Load=0 means right shift by one bit.
       Load : in std_logic;
       Clk : in std_logic
     );
end PISO;
architecture gate_level of PISO is
signal D,Q,Load_value : std_logic_vector(3 downto 0):="0000";
signal i : integer := 0;
begin
Load_value <= Parallel_In;
Serial_out <= Q(3);

--entity instantiation of the D flipflop using "generate".
F :  --label name
   for i in 0 to 3 generate   --D FF is instantiated 4 times.
    begin  --"begin" statement for "generate"
        FDRSE_inst : entity work.example_FDRSE port map   --usual port mapping
          (Q => Q(i),
          CLK => Clk,
          CE => '1',
          RESET => '0',
          D => D(i),
          SET => '0');
   end generate F;  --end "generate" block.
--The D inputs of the flip flops are controlled with the load input.
--Two AND gates with a OR gate is used for this.
D(0) <= Load_value(3) and Load;
D(1) <= (Load_value(2) and Load) or (Q(0) and not(Load));
D(2) <= (Load_value(1) and Load) or (Q(1) and not(Load));
D(3) <= (Load_value(0) and Load) or (Q(2) and not(Load));
end gate_level; 

I hope the above code is self explanatory.The for loop is used to instantiate as many number of modules as we want to instantiate.Next I will give an example on the IF-way using a Johnson counter example. The Johnson counter is explained with the help of VHDL code in one of my previous posts.Check it out here.I have modified the code using flip-flops available in this post.
The modified code is given below:

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.NUMERIC_STD.ALL;
entity johnson_counter is
port (
        DAT_O : out unsigned(3 downto 0);
        RST_I : in std_logic;
        CLK_I : in std_logic
        );
end johnson_counter;
architecture Behavioral of johnson_counter is
signal D,Q : unsigned(3 downto 0):="0000";
signal not_Q4 : std_logic:='0';
begin
not_Q4 <= not Q(3);
DAT_O <= Q;
F : for i in 0 to 3 generate
    begin
        F0 : if ( i = 0 ) generate  --The IF condition to for the "first" FF only.
            begin U1 : entity work.example_FDRSE port map --usual port mapping        
            (Q => Q(0),
          CLK => CLK_I,
          CE => '1',
          RESET => RST_I,
          D => not_Q4,
          SET => '0');
             end generate F0;
        F1 : if ( i /= 0 ) generate --generating the rest of the three FF's.
            begin U2 : entity work.example_FDRSE port map   --usual port mapping
         (Q => Q(i),
          CLK => CLK_I,
          CE => '1',
          RESET => RST_I,
          D => Q(i-1),
          SET => '0');
             end generate F1;
    end generate F;    
   
end Behavioral;


   So as you can see from the examples using "generate" keyword makes your design simple to understand  and saves your time.

2 comments:

  1. Thanks by this tutorial !
    I need create this sequence of blocks in VHDL 1,2,3,4,4,5,6,7,8,9,10,11,12,13,13,14,15,,,,40,40,,j,...
    You know or have a idea of the correct way to do this sequence?
    Thanks again

    ReplyDelete
  2. if(valueYouWant = i) generate
    for j in 0 to howManyTimes generate
    ...

    ReplyDelete