fpga4student.com FPGA digital design projects using Verilog/ VHDL: Verilog code for Traffic light controller

Friday, November 4, 2016

Verilog code for Traffic light controller

A Verilog source code for a traffic light controller on FPGA is presented. A sensor on the farm  is  to detect if there is any vehicles and change the traffic light to allow the vehicles to cross the highway. Otherwise, highway light is always green since it has higher priority than the farm. 


Verilog code for Traffic light controller


module traffic_light(light_highway, light_farm, C, clk, rst_n);
parameter HGRE_FRED=2'b00, // Highway green and farm red
 HYEL_FRED = 2'b01,// Highway yellow and farm red
 HRED_FGRE=2'b10,// Highway red and farm green
 HRED_FYEL=2'b11;// Highway red and farm yellow
input C, // sensor
 clk, // clock = 50 MHz
 rst_n; // reset active low
output reg[2:0] light_highway, light_farm; // output of lights

reg[15:0] count=0,count1=0,a=0;

reg delay10s=0, delay3s=0,dem1=0,dem2=0;
reg clk1, clk2;
reg[1:0] state, next_state;
// next state
always @(posedge clk or negedge rst_n)
begin
if(~rst_n) state <= 2'b00;
else 
state <= next_state; 
end
// FSM
always @(*)
begin
case(state)
HGRE_FRED: begin
dem1=0;
dem2=0;
light_highway = 3'b001;
light_farm = 3'b100;
if(C) next_state = HYEL_FRED;
else next_state =HGRE_FRED;
end
HYEL_FRED: begin
light_highway = 3'b010;
light_farm = 3'b100;
dem1=0;
dem2=1;
if(delay3s) next_state = HRED_FGRE;
else next_state = HYEL_FRED;
end
HRED_FGRE: begin
light_highway = 3'b100;
light_farm = 3'b001;
dem1=1;
dem2=0;
if(delay10s) next_state = HRED_FYEL;
else next_state =HRED_FGRE;
end
HRED_FYEL:begin
light_highway = 3'b100;
light_farm = 3'b010;
dem1=0;
dem2=1;
if(delay3s) next_state = HGRE_FRED;
else next_state =HRED_FYEL;
end
default: next_state = HGRE_FRED;
endcase
end

always @(posedge clk2)

begin
if(dem1||dem2)
a <=a +1'd1;
if((a == 9)&&dem1) 
begin
delay10s=1;
delay3s=0;
a<=0;
end
else if((a == 2)&&dem2) 
begin
delay10s=0;
delay3s=1;
a<=0;
end
else
begin
delay10s=0;
delay3s=0;
end 
end
// create delay 1s
always @(posedge clk)
begin
count <=count +1'd1;
//if(count == 32500) // 32500 for 50 MHz clock in real FPGA
if(count == 2) // for testbench
clk1 <= 1;
// else if(count == 65000) //65000 for 50 MHz clock in real FPGA
else if(count == 5)// for testbench
begin
clk1 <=0;
count <=0;
end
else 
clk1 <=clk1;
end
always @(posedge clk1)
begin
count1 <=count1 +1'd1;
if(count1 == 207) 
clk2 <= 1;
else if(count1 == 414) 
begin
clk2 <=0;
count1 <=0;
end
else 
clk2 <=clk2;
end
endmodule 

Testbench for functional simulation

// 1. The timescale directive
`timescale 10 ns/ 1 ps
// 2. Preprocessor Directives
`define DELAY 1
// 3. Include Statements
//`include "counter_define.h"
module tb_traffic;
// 4. Parameter definitions
parameter ENDTIME = 400000;
// 5. DUT Input regs
//integer count, count1, a;
reg clk;
reg rst_n;
reg sensor;
wire [2:0] light_farm;
// 6. DUT Output wires
wire [2:0] light_highway;

// 7. DUT Instantiation
traffic_light tb(light_highway, light_farm, sensor, clk, rst_n);

// 8. Initial Conditions
initial
begin
clk = 1'b0;
rst_n = 1'b0;
sensor = 1'b0;
// count = 0;
//// count1=0;
// a=0;
end
// 9. Generating Test Vectors
initial
begin
main;
end
task main;
fork
clock_gen;
reset_gen;
operation_flow;
debug_output;
endsimulation;
join
endtask
task clock_gen;
begin
forever #`DELAY clk = !clk;
end
endtask

task reset_gen;
begin
rst_n = 0;
# 2000
rst_n = 1;
end
endtask

task operation_flow;
begin
sensor = 0;
# 60000
sensor = 1;
# 120000
sensor = 0;
# 120000
sensor = 1;
end
endtask
// 10. Debug output
task debug_output;
begin
$display("----------------------------------------------");
        $display("------------------     -----------------------");
$display("----------- SIMULATION RESULT ----------------");
$display("--------------             -------------------");
$display("----------------         ---------------------");
$display("----------------------------------------------");
$monitor("TIME = %d, reset = %b, sensor = %b, light of highway = %h, light of farm road = %h",$time,rst_n ,sensor,light_highway,light_farm );
end
endtask

//12. Determines the simulation limit
task endsimulation;
begin
#ENDTIME
$display("-------------- THE SIMUALTION END ------------");
$finish;
end
endtask
    
endmodule

Simulation results:

TIME = 2000, reset = 1, sensor = 0, light of highway = 1, light of farm road = 4
TIME = 60000, reset = 1, sensor = 1, light of highway = 1, light of farm road = 4
TIME = 60001, reset = 1, sensor = 1, light of highway = 2, light of farm road = 4
TIME = 72211, reset = 1, sensor = 1, light of highway = 4, light of farm road = 1
TIME = 122011, reset = 1, sensor = 1, light of highway = 4, light of farm road = 2
TIME = 136951, reset = 1, sensor = 1, light of highway = 1, light of farm road = 4
TIME = 136953, reset = 1, sensor = 1, light of highway = 2, light of farm road = 4
TIME = 136955, reset = 1, sensor = 1, light of highway = 4, light of farm road = 1
TIME = 180000, reset = 1, sensor = 0, light of highway = 4, light of farm road = 1
TIME = 186751, reset = 1, sensor = 0, light of highway = 4, light of farm road = 2
TIME = 201691, reset = 1, sensor = 0, light of highway = 1, light of farm road = 4
TIME = 300000, reset = 1, sensor = 1, light of highway = 1, light of farm road = 4
TIME = 300001, reset = 1, sensor = 1, light of highway = 2, light of farm road = 4
TIME = 311251, reset = 1, sensor = 1, light of highway = 4, light of farm road = 1
TIME = 361051, reset = 1, sensor = 1, light of highway = 4, light of farm road = 2
TIME = 375991, reset = 1, sensor = 1, light of highway = 1, light of farm road = 4
TIME = 375993, reset = 1, sensor = 1, light of highway = 2, light of farm road = 4
TIME = 375995, reset = 1, sensor = 1, light of highway = 4, light of farm road = 1


 Waveform

Verilog code for Traffic light controller

2 comments: