counter in state machine

  • Thread starter tringuyen858@gmail.com
  • Start date
T

tringuyen858@gmail.com

Guest
Hi all,

I am trying to simulate a state machine that has a counter. Below is
the code. When I run the simulation, it gets stuck at BEGIN_COUNT and
start_flag_counter is X"01" throughout the whole simulation. I can't
figure out what is wrong. May be it is something obvious that I can't
see. thank you for your input.

SYNC_PROC: process (clk_100, SYS_RST_N)
begin
if (SYS_RST_N='0') then
state_count <= INIT;
clk_100_locked_reg <= '0';
lock_reg_int_reg <= '0';
elsif rising_edge(clk_100) then
state_count <= next_state;
clk_100_locked_reg <= clk_100_locked;
lock_reg_int_reg <= lock_reg_int;
end if;
end process;

start_sig: process(state_count, clk_100_locked_reg,
lock_reg_int_reg)
begin
case state_count is
when INIT =>
start_reg <= '0';
start_flag_counter <= X"00";
if clk_100_locked_reg = '1' and lock_reg_int_reg = '1'
then
next_state <= BEGIN_COUNT;
else
next_state <= INIT;
end if;
when BEGIN_COUNT =>
start_flag_counter <= start_flag_counter + 1;
start_reg <= '0';
if start_flag_counter = X"64" then
next_state <= START_FLAG;
else
next_state <= BEGIN_COUNT;
end if;
when START_FLAG =>
start_flag_counter <= start_flag_counter + 1;
start_reg <= '1';
if start_flag_counter = X"6A" then
next_state <= STOP_COUNT;
else
next_state <= START_FLAG;
end if;
when STOP_COUNT =>
start_flag_counter <= X"00";
start_reg <= '0';
next_state <= STOP_COUNT;
end case;
end process;
 
tringuyen858@gmail.com a exposé le 09/04/2009 :
start_flag_counter <= start_flag_counter + 1;
In a combinational process ?????
Bad, bad, bad....

You probably wouldn't have goofed if you had your FSM in a single
process.

Bert
 
On 9 Apr, 04:16, "tringuyen...@gmail.com" <tringuyen...@gmail.com>
wrote:
Hi all,

I am trying to simulate a state machine that has a counter.  Below is
the code.  When I run the simulation, it gets stuck at BEGIN_COUNT and
start_flag_counter is X"01" throughout the whole simulation.  I can't
figure out what is wrong.  May be it is something obvious that I can't
see.  thank you for your input.

   SYNC_PROC: process (clk_100, SYS_RST_N)
   begin
      if (SYS_RST_N='0') then
         state_count <= INIT;
         clk_100_locked_reg <= '0';
         lock_reg_int_reg <= '0';
      elsif rising_edge(clk_100) then
         state_count <= next_state;
         clk_100_locked_reg <= clk_100_locked;
         lock_reg_int_reg <= lock_reg_int;
      end if;
   end process;

   start_sig: process(state_count, clk_100_locked_reg,
lock_reg_int_reg)
   begin
      case state_count is
         when INIT =
            start_reg <= '0';
            start_flag_counter <= X"00";
            if clk_100_locked_reg = '1' and lock_reg_int_reg = '1'
then
               next_state <= BEGIN_COUNT;
            else
               next_state <= INIT;
            end if;
         when BEGIN_COUNT =
            start_flag_counter <= start_flag_counter + 1;
            start_reg <= '0';
            if start_flag_counter = X"64" then
               next_state <= START_FLAG;
            else
               next_state <= BEGIN_COUNT;
            end if;
         when START_FLAG =
            start_flag_counter <= start_flag_counter + 1;
            start_reg <= '1';
            if start_flag_counter = X"6A" then
               next_state <= STOP_COUNT;
            else
               next_state <= START_FLAG;
            end if;
         when STOP_COUNT =
            start_flag_counter <= X"00";
            start_reg <= '0';
            next_state <= STOP_COUNT;
      end case;
   end process;

You need to put the counter in it's own clocked process. At the
moment, when it gets into the "BEGIN_COUNT" state, nothing is changing
that causes the sensitivity list to fire and cause the counter to
increment. instead of putting the counter inside the state, put an
enable instead:

when BEGIN_COUNT =>
start_flag_count_en <= '1';
.......


count_proc : process(clk_100, SYS_RST_N)
begin
if SYS_RST_N = '0' then
start_flag_counter <= x"00";
elsif rising_edge(clk_100) then
if start_flag_count_en = '1' then
--add sync reset conditions first
start_flag_counter <= start_flag_counter + 1;
end if;
end if;
end process;



Of course, moving the whole state machine into a single process would
eliminate this problem because it would be clocked anyway.
 
On Apr 9, 2:49 am, Tricky <Trickyh...@gmail.com> wrote:>
Of course, moving the whole state machine into a single process would
eliminate this problem because it would be clocked anyway.
Agreed. Two-process (separate clocked and combinatorial processes)
descriptions are prone to latches (what you got), require twice the
signal declarations, twice the process executions per clock cycle,
cumbersome sensitivity lists, and a host of other bad side effects.

Andy
 
On Apr 8, 8:16 pm, "tringuyen...@gmail.com" <tringuyen...@gmail.com>
wrote:
Hi all,

I am trying to simulate a state machine that has a counter.  Below is
the code.  When I run the simulation, it gets stuck at BEGIN_COUNT and
start_flag_counter is X"01" throughout the whole simulation.  I can't
figure out what is wrong.  May be it is something obvious that I can't
see.  thank you for your input.

   SYNC_PROC: process (clk_100, SYS_RST_N)
   begin
      if (SYS_RST_N='0') then
         state_count <= INIT;
         clk_100_locked_reg <= '0';
         lock_reg_int_reg <= '0';
      elsif rising_edge(clk_100) then
         state_count <= next_state;
         clk_100_locked_reg <= clk_100_locked;
         lock_reg_int_reg <= lock_reg_int;
      end if;
   end process;

   start_sig: process(state_count, clk_100_locked_reg,
lock_reg_int_reg)
   begin
      case state_count is
         when INIT =
            start_reg <= '0';
            start_flag_counter <= X"00";
            if clk_100_locked_reg = '1' and lock_reg_int_reg = '1'
then
               next_state <= BEGIN_COUNT;
            else
               next_state <= INIT;
            end if;
         when BEGIN_COUNT =
            start_flag_counter <= start_flag_counter + 1;
            start_reg <= '0';
            if start_flag_counter = X"64" then
               next_state <= START_FLAG;
            else
               next_state <= BEGIN_COUNT;
            end if;
         when START_FLAG =
            start_flag_counter <= start_flag_counter + 1;
            start_reg <= '1';
            if start_flag_counter = X"6A" then
               next_state <= STOP_COUNT;
            else
               next_state <= START_FLAG;
            end if;
         when STOP_COUNT =
            start_flag_counter <= X"00";
            start_reg <= '0';
            next_state <= STOP_COUNT;
      end case;
   end process;
thanks for all the suggestions. It works!!
 

Welcome to EDABoard.com

Sponsor

Back
Top