Forum Discussion

Altera_Forum's avatar
Altera_Forum
Icon for Honored Contributor rankHonored Contributor
11 years ago

Code Check - Traffic Simulation

Hey guys,

My program seems to be stuck in the first step of the State Machine and I cannot for the life of me figure out why, I suspect a problem with the counter?

Any help is appreciated.

counter:

library IEEE;

use IEEE.STD_LOGIC_1164.ALL;

use IEEE.NUMERIC_STD.ALL;

use IEEE.STD_LOGIC_ARITH.ALL;

use IEEE.STD_LOGIC_UNSIGNED.ALL;

library UNISIM;

use UNISIM.VComponents.all;

entity Counter is

Port ( reset : in STD_LOGIC;

clear : in STD_LOGIC;

clock : in STD_LOGIC;

counto : out STD_LOGIC_vector (9 downto 0); -- count output

finish : out STD_LOGIC

finish2 : out STD_LOGIC

);

end Counter;

architecture Behavioral of Counter is

signal count_i: std_logic_vector (9 downto 0); -- 9 bit timer appropriate for 100Hz required speed

signal cen: std_logic; -- count enable

begin

counto <= count_i;

cen <= '1'; -- start count enable

process (clear, reset, clock) begin -- begin process

if (reset = '1') then -- if reset begin count to as if EW car has been there for a 'long time'

count_i <= "1000000001";

elsif rising_edge (clock) then -- on rising edge of clock

if (clear = '1') then

cen <= '1'; -- if cleared begin counting

count_i <= "0000000001";

elsif (cen = '1') then -- when count is enabled count up from 000000001

count_i <= count_i + "000000001";

if (count_i >= "1000000001") then -- if minimum time is reached stop counting and wait for an input

cen <= '0';

finish <= '1';

if (count_i >= "0000100001") then

cen <= '0';

finish2 <= '1';

end if;

end if;

end if;

end process;

end architecture Behavioral;

state machine

library IEEE;

use IEEE.STD_LOGIC_1164.ALL;

use IEEE.NUMERIC_STD.ALL;

use IEEE.STD_LOGIC_ARITH.ALL;

use IEEE.STD_LOGIC_UNSIGNED.ALL;

library UNISIM;

use UNISIM.VComponents.all;

-- Uncomment the following library declaration if using

-- arithmetic functions with Signed or Unsigned values

--use IEEE.NUMERIC_STD.ALL;

-- Uncomment the following library declaration if instantiating

-- any Xilinx primitives in this code.

--library UNISIM;

--use UNISIM.VComponents.all;

entity StateMachine is

Port (

clock : in STD_LOGIC;

reset : in STD_LOGIC;

carNS : in STD_LOGIC;

carEW : in STD_LOGIC;

finish : in STD_LOGIC;

pedNS : in STD_LOGIC;

pedEW : in STD_LOGIC;

pedo : out STD_LOGIC;

clearo : out STD_LOGIC;

lightsEW : out STD_LOGIC_VECTOR (1 downto 0); -- controls EW lights

lightsNS : out STD_LOGIC_VECTOR (1 downto 0); -- controls NS lights

pedcount : in STD_LOGIC_vector (7 downto 0));

end StateMachine;

architecture Behavioral of StateMachine is

type StateType is (greenNS, amberNS, redNS, greenEW, amberEW, redEW);

signal state, nextState: StateType;

begin

SynchronousProcess: -- execute all at once

process (clock) begin -- only list clock, program auto fills required variables

nextState <= greenEW; -- start at green EW light

lightsEW <= "10"; -- car EW light green (10)

lightsNS <= "00"; -- car NS lights red (01)

case state is

when greenEW => -- when car EW is green (10)

lightsEW <= "10"; -- Good up to here

if (finish = '1') then -- if count is above 1000000001 and a car is present on NS road then set EW light to amber

if (carNS = '1') then

nextState <= amberEW;

clearo <= '1'; -- begin amber state, stop counting

else -- else remain green for EW

nextState <= greenEW;

end if;

end if;

if (pedNS = '1') then -- if NS pedestrian button pressed

nextState <= amberEW;

clearo <= '1'; -- begin amber state, stop counting

else

nextState <= greenEW; -- else remain green for EW

end if;

when amberEW => -- when amber set lights to amber (01)

lightsEW <="01";

if (finish2 = '1') then -- if count is above 0000100001 and a car is present on NS road then set EW light to red

nextState <= redEW;

clearo <= '1'; -- begin red state, stop counting

end if;

when redEW => -- when red set lights to red (00)

lightsEW <="00";

if (finish = '1') then -- if count is above 1000000001 move to green state for NS road

nextState <= greenNS;

end if;

when greenNS => -- when in green state set NS car lights to green (10)

lightsNS <="10";

if (finish = '1') then -- if count is above 1000000001 and a car is present on EW road then set NS light to amber

if (carEW = '1') then -- if car present on EW road,

nextState <= amberNS;

clearo <= '1'; -- begin amber state, stop counting

else

nextState <= greenNS; -- else stay green

end if;

end if;

if (pedEW = '1') then -- if EW pedestrian button pressed

nextState <= amberNS; -- begin amber state, stop counting

clearo <= '1';

else

nextState <= greenNS; -- else remain green for NS

end if;

when amberNS =>

lightsNS <="11"; -- set NS lights to amber (11)

if (finish2 = '1') then -- if count is above 0000100001 set NS lights to red

nextState <= redNS;clearo <= '1';

end if;

when redNS =>

lightsNS <="00";

if (finish = '1') then -- if count is above 1000000001 set NS lights to red

nextState <= greenEW;

end if;

end case;

end process;

process (reset,clock) begin -- begin process

if (reset='1') then -- if reset go to state greenEW (first state)

state <= greenEW;

elsif rising_edge(clock) then -- else, if on a rising clock edge move to next state

state <= nextState;

clearo <='1'; -- stop counting

end if;

end process;

end architecture Behavioral;

7 Replies

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Actually just realised that all the light settings are wrong.. From testing, should be as follows:

    11 is green (car and pedestrian)

    10 for green (car only)

    01 for amber

    00 for red

    Clock is at 100Hz

    Will update with nicer code and added comments in a second.
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Ok, but what are the values of finish, carNS and pedNS? and what should happen if finish = '1' and carNs = '0'? or if both are 0 and pedNS is 0 as well? I think you have a few unspecified cases here.

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    --- Quote Start ---

    Ok, but what are the values of finish, carNS and pedNS? and what should happen if finish = '1' and carNs = '0'? or if both are 0 and pedNS is 0 as well? I think you have a few unspecified cases here.

    --- Quote End ---

    The values of carNS etc should just be 0 and 1 - they are tied to inputs on a module, on a breadboard.

    Finish becomes 1 after account exceeds 1000000001.

    I hope this answers your question :P
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    My question is: where is the testbench code?

    Second question: why have you put clock in the state machine sensitivity list, when it is clearly not a clocked process? and the comment is worrying, because it shows lack of understanding of VHDL:

    process (clock) begin -- only list clock, program auto fills required variables

    Quartus wont do any auto-filling for you. It will throw warnings about missing signals (note - not variables), but it ignores sensitivity lists, so you wont see a "problem". If you had a testbench, you would see that you would get many problems.

    thurdly - you state machine proces produces latches - these are not recommended. You need to assign all signals in ALL cases in an asynchronous process (it is not synchronous, it is asynchronous, despite your comments).
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Testbench code apparently was not needed.

    I did receive warnings but to me it read as though it was populating the sensitivity list with the inputs and outputs listed within the code.

    In then end I just decided to scrap the whole thing and start from scratch, end result was pretty close to what was required.

    Thank you for the input though, I have only done VHDL for about 2 weeks now and electronics is hardly my forte, more of a maths and programming man myself.

    --- Quote Start ---

    My question is: where is the testbench code?

    Second question: why have you put clock in the state machine sensitivity list, when it is clearly not a clocked process? and the comment is worrying, because it shows lack of understanding of VHDL:

    process (clock) begin -- only list clock, program auto fills required variables

    Quartus wont do any auto-filling for you. It will throw warnings about missing signals (note - not variables), but it ignores sensitivity lists, so you wont see a "problem". If you had a testbench, you would see that you would get many problems.

    thurdly - you state machine proces produces latches - these are not recommended. You need to assign all signals in ALL cases in an asynchronous process (it is not synchronous, it is asynchronous, despite your comments).

    --- Quote End ---