Gambling machine in VHDL
Casino-type Game
PURPOSE – In this lab you will design a casino-type game using the random number generator.
Writing the Verilog description
You will have to design a simple game using the random number generator.
This game will function as follows: The random number generator will start generating numbers.
When the Roll button is pressed you will compare these two hex digits and declare a win if they areequal or a loss otherwise.
In order to reuse the most code possible you will have the two random hex numbers displayed inreal time on the seven segment display (on either the left two or the right two digits), and then display the win “UI” or lose “LO” notification on the remaining two digits.
Read the followingexample to understand the proper operation of the game:
A sample play of the game is as follows:
1) The player starts to generate the random numbers on two of the digits just as in lab 4.
2) The player then taps the Roll button. If the current two hex numbers are equal then “UI” is displayed,if not, then “LO” is displayed (on the other remaining two digits). The “UI” or “LO” is still displayed untilthe next tap of the Roll button. The two hex numbers are still changing throughout this entire process.
3) The player can then tap the Roll button again and the (new) current two hex numbers are compared again to see if the other two digits should display “UI” or “LO”.
For simplicity “LO” can be displayed before the first tap of the roll button.
Of course, the player can always see the value of the hex digits, and thus tap the Roll button at theright time in order to win or lose the game, but this is done for debugging purposes.
2. Verification
Synthesize and implement the game to verify the correctness. You will have to write an .xdc file to correctly map the pins (you only need to add two more lines for the Roll button.)
Solution
clock_divider.v
module clock_divider (cout, cin);
input cin;
output cout;
parameter timeconst = 60;//constant
integer count0;
integer count1;
integer count2;
integer count3;
reg d;
reg cout;
initial begin
count0=0;
count1=0;
count2=0;
count3=0;
d = 0;
end
always @ (posedge cin )
begin
count0 <= (count0 + 1); if
((count0 == timeconst))
begin
count0 <= 0;
count1 <= (count1 + 1);
end
else if ((count1 == timeconst))
begin
count1 <= 0;
count2 <= (count2 + 1);
end
else if ((count2 == timeconst))
begin
count2 <= 0;
count3 <= (count3 + 1);
end
else if ((count3 == timeconst))
begin
count3 <= 0;
d <= ~ (d);
end
cout <= d;
end
endmodule
decoder.v
module decoder(
output reg [6:0] seg,
input [3:0] a
);
always @*
begin
case(a)
4’b0000 : seg = 7’b1111110; //0
4’b0001 : seg = 7’b0110000 ; //1
4’b0010 : seg = 7’b1101101 ; //2
4’b0011 : seg = 7’b1111001 ; //3
4’b0100 : seg = 7’b0110011 ; //4
4’b0101 : seg = 7’b1011011 ; //5
4’b0110 : seg = 7’b1011111 ; //6
4’b0111 : seg = 7’b1110000; //7
4’b1000 : seg = 7’b1111111; //8
4’b1001 : seg = 7’b1111011 ; //9
4’b1010 : seg= 7’b1110111 ; //A
4’b1011 : seg = 7’b0011111; //b
4’b1100 : seg = 7’b1001110 ; //C
4’b1101 : seg = 7’b0111101 ; //d
4’b1110 :seg = 7’b1001111 ; //E
4’b1111 : seg = 7’b1000111 ; //F
default: seg = 7’b1111110;
endcase
end
endmodule
lab5_top.v
// casino-type game
module lab5_top(
output reg[6:0] seg,
output [7:0] q,
output reg [3:0] an,
input clk,
input rst,
input [7:0] sw,
input roll
);
wire[7:0] seed;
wire [6:0] seg1,seg2;
reg [19:0] refresh_counter;
wire [1:0] anode_counter;
reg[6:0] result1,result2;
reg [3:0] rn1=0,rn2=1;
assign seed = sw;
clock_divider CDIV (cout, clk);
lsfr LSFR (q, seed, rst, clk, cout);
// clock_divider #(15) CDIV2 (cout2, clk);
decoder SEG1 (seg1,q[3:0]);
decoder SEG2 (seg2,q[7:4]);
always @(posedge clk)
begin
if(roll)begin
rn1 <= q[3:0];
rn2 <= q[7:4];
end
end
always @(posedge clk or posedge rst)
begin
if(rst) begin
result1 <= 7’b0000001;
result2 <= 7’b1110001;
end
else if(roll) begin
result1 <= rn1==rn2 ? 7’b1111001: 7’b0000001;
result2 <= rn1==rn2 ? 7’b1000001: 7’b1110001;
end
end
always @(posedge clk or posedge rst)
begin
if(rst)
refresh_counter <= 0;
else
refresh_counter <= refresh_counter + 1;
end
assign anode_counter = refresh_counter[19:18];
always @(*)
begin
case(anode_counter)
2’b00: begin
an=4’b1110;
seg=~seg1;
end
2’b01: begin
an=4’b1101;
seg=~seg2;
end
2’b10: begin
an=4’b1011;
seg=result1;
end
2’b11: begin
an=4’b0111;
seg=result2;
end
endcase
end
endmodule
lsfr.v
module lsfr(
output reg [7:0] q,
input [7:0] seed,
input rst,
input clock,
input clock_en
);
wire din;
assign din = q[1]^q[2]^q[3]^q[7];
always @(posedge clock)
begin
if(rst)
q<= seed[7:0];
else if(clock_en)
q<={q[6:0],din};
end
endmodule