Design up counter in VHDL using generate statement

counterripple-countervhdl

I need to design an 8 bit up counter in VHDL using T flip flop and generate statement. I know how the counter works, but I am not able to design it in VHDL.

The main problem is "using generate statement" . As I can see, in an up counter (ripple or synchronous ; either is OK ; I decided to use ripple ) , the previous output is fed as a clock. So I can map Q(i -1) for clock in the i'th generated flip flop. But what about the first flip flop ? It has a clock explicitly applied.

So if I use generate statement, I cannot simply map the clock to previous output ; the first flip flop will always create problem. Another thought which came was to initialise first counter explicitly and then use generate statement for remaining 7 flip flops. But here as well, I think, the first (or rather, second) flip flop using generate statement will pose a similar problem ( ie mapping clock).

Am I incorrect or missing something important here ?

Here is the code ( planned code, not actual code) :

component tff is
Port ( t   : IN BIT ; 
       clk : IN BIT ;
       q   : OUT BIT );
end component

--Other irrelevant stuff

For i IN 0 TO 7 GENERATE
tffx : tff PORT MAP ( tIn , q(i-1) , q(i) ) ;
end GENERATE ;

--More irrelevant stuff

Thank you.

Best Answer

Here is a simple generate statement, which generates 8 TFFs and connects the clock input of the tff to the q output from previous FF. Because you are using indices calculations (i+1 or i-1), you need to wider range for the tff_clocks range or you must shorten the generate loop.

I'm using a loop from 0 to 7 so I extended tff_clocks by 1. Index 0 is connected to the original system clock.

architecture ....
  signal tff_clocks : std_logic_vector(8 downto 0);

begin
  tff_clocks(0)  <= clk;   -- first tff is clock with main clock

  genTFF : for i in 0 to 7 generate
    tff_inst : tff
      port map (
        clk   => tff_clocks(i),
        t     => '1',
        q     => tff_clocks(i + 1)
      );
  end generate;

  async_counter_result <= tff_clocks(8 downto 1);
end;