I'm working on a Verilog project using a FPGA (BEMICROMAX10) and some breadboard components. The project is to make a digital clock in which you can also set the time using the buttons on the FPGA. I realize this verilog code is not the most efficient way to write this but it's how I currently have it set up and the deadline approaches so can't restart. I think I'm almost done so I'm hoping you guys can get me over the last hurdle.
The time from seconds to minutes to hours, is working perfectly when I power it but I can not get the buttons to function to change the minutes and hours manually (while the seconds are running). If you look at line 98 after the large chunk of seconds, I run into the error when I add 'or posedge outm'. I've tried other things but it seems I either get the 'cannot match operands' error or the 'multiple constant drivers' error which I assume is telling me I'm trying to change countmin and counthr with multiple inputs (from clk and btn). I'm really stuck and have no idea where to go from here.
I've just made an edit to drive slow_clk2 with another clock input on the FPGA, and added the outm line for the button, but still no luck.
Thanks for your help.
module digital_clock(clk, clk2, minbtn, hrbtn, segsec, segmin, seghr);
input clk, clk2, minbtn, hrbtn;
output [13:0] segsec;
output [13:0] segmin;
output [13:0] seghr;
parameter N = 25;
reg [N-1:0] slow_clk = 0;
reg [7:0] countsec = 0, countmin = 0, counthr = 8'h1;
parameter M = 13;
reg [M-1:0] slow_clk2 = 0;
reg [7:0] delay = 0;
reg [7:0] delay2 = 0;
wire outm, outh;
always @ (posedge clk)
slow_clk <= slow_clk + 1'b1;
always @ (posedge clk2)
slow_clk2 <= slow_clk2 + 1;
always @ (posedge slow_clk2[M-1])
begin
delay <= delay << 1;
delay2 <= delay2 << 1;
delay[0] <= ~minbtn;
delay2[0] <= ~hrbtn;
end
assign outm = delay[7] & delay[6] & delay[5] & delay[4] & delay[3] & delay[2] & delay[1] & delay[0];
assign outh = delay2[7] & delay2[6] & delay2[5] & delay2[4] & delay2[3] & delay2[2] & delay2[1] & delay2[0];
always @ (posedge slow_clk[N-1])
if (countsec == 8'b00111011) countsec <= 8'b0;
else countsec <= countsec + 8'b1;
assign segsec = (countsec == 8'h0 ) ? 16'b01111110111111:
(countsec == 8'h1) ? 16'b01111110000110: //1 0000110 0111111
(countsec == 8'h2) ? 16'b01111111011011: //2 1011011
(countsec == 8'h3) ? 16'b01111111001111: //3 1001111
(countsec == 8'h4) ? 16'b01111111100110: //4 1100110
(countsec == 8'h5) ? 16'b01111111101101: //5 1101101
(countsec == 8'h6) ? 16'b01111111111101: //6 1111101
(countsec == 8'h7) ? 16'b01111110000111: //7 0000111
(countsec == 8'h8) ? 16'b01111111111111: //8 1111111
(countsec == 8'h9) ? 16'b01111111101111: //9 1101111
(countsec == 8'ha) ? 16'b00001100111111: //10
(countsec == 8'hb) ? 16'b00001100000110://11
(countsec == 8'hc) ? 16'b00001101011011://12
(countsec == 8'hd) ? 16'b00001101001111://13
(countsec == 8'he) ? 16'b00001101100110: //14
(countsec == 8'hf) ? 16'b00001101101101: //15
(countsec == 8'h10) ? 16'b00001101111101://16
(countsec == 8'h11) ? 16'b00001100000111://17
(countsec == 8'h12) ? 16'b00001101111111://18
(countsec == 8'h13) ? 16'b00001101101111://19
(countsec == 8'h14) ? 16'b10110110111111://20
(countsec == 8'h15) ? 16'b10110110000110://21
(countsec == 8'h16) ? 16'b10110111011011://22
(countsec == 8'h17) ? 16'b10110111001111://23
(countsec == 8'h18) ? 16'b10110111100110://24
(countsec == 8'h19) ? 16'b10110111101101://25
(countsec == 8'h1a) ? 16'b10110111111101://26
(countsec == 8'h1b) ? 16'b10110110000111://27
(countsec == 8'h1c) ? 16'b10110111111111://28
(countsec == 8'h1d) ? 16'b10110111101111://29
(countsec == 8'h1e) ? 16'b10011110111111://30
(countsec == 8'h1f) ? 16'b10011110000110://31
(countsec == 8'h20) ? 16'b10011111011011://32
(countsec == 8'h21) ? 16'b10011111001111://33
(countsec == 8'h22) ? 16'b10011111100110://34
(countsec == 8'h23) ? 16'b10011111101101://35
(countsec == 8'h24) ? 16'b10011111111101://36
(countsec == 8'h25) ? 16'b10011110000111://37
(countsec == 8'h26) ? 16'b10011111111111://38
(countsec == 8'h27) ? 16'b10011111101111://39
(countsec == 8'h28) ? 16'b11001100111111://40
(countsec == 8'h29) ? 16'b11001100000110://41
(countsec == 8'h2a) ? 16'b11001101011011://42
(countsec == 8'h2b) ? 16'b11001101001111://43
(countsec == 8'h2c) ? 16'b11001101100110://44
(countsec == 8'h2d) ? 16'b11001101101101://45
(countsec == 8'h2e) ? 16'b11001101111101://46
(countsec == 8'h2f) ? 16'b11001100000111://47
(countsec == 8'h30) ? 16'b11001101111111://48
(countsec == 8'h31) ? 16'b11001101101111://49
(countsec == 8'h32) ? 16'b11011010111111://50
(countsec == 8'h33) ? 16'b11011010000110://51
(countsec == 8'h34) ? 16'b11011011011011://52
(countsec == 8'h35) ? 16'b11011011001111://53
(countsec == 8'h36) ? 16'b11011011100110://54
(countsec == 8'h37) ? 16'b11011011101101://55
(countsec == 8'h38) ? 16'b11011011111101://56
(countsec == 8'h39) ? 16'b11011010000111://57
(countsec == 8'h3a) ? 16'b11011011111111://58
(countsec == 8'h3b) ? 16'b11011011101111://59
16'b01111110111111;
always @ (posedge slow_clk[N-1] or posedge outm)
if (outm)
countmin <= countmin + 8'b1;
else if (countmin == 8'b00111011 && countsec == 8'b00111011) countmin <= 8'b0;
else if (countmin != 00111011 && countsec == 8'b00111011) countmin <= countmin + 8'b1;
else countmin <= countmin;
assign segmin = (countmin == 8'h0) ? 16'b01111110111111:
(countmin == 8'h1) ? 16'b01111110000110: //1 0000110 0111111
(countmin == 8'h2) ? 16'b01111111011011: //2 1011011
(countmin == 8'h3) ? 16'b01111111001111: //3 1001111
(countmin == 8'h4) ? 16'b01111111100110: //4 1100110
(countmin == 8'h5) ? 16'b01111111101101: //5 1101101
(countmin == 8'h6) ? 16'b01111111111101: //6 1111101
(countmin == 8'h7) ? 16'b01111110000111: //7 0000111
(countmin == 8'h8) ? 16'b01111111111111: //8 1111111
(countmin == 8'h9) ? 16'b01111111101111: //9 1101111
(countmin == 8'ha) ? 16'b00001100111111: //10
(countmin == 8'hb) ? 16'b00001100000110: //11
(countmin == 8'hc) ? 16'b00001101011011: //12
(countmin == 8'hd) ? 16'b00001101001111: //13
(countmin == 8'he) ? 16'b00001101100110: //14
(countmin == 8'hf) ? 16'b00001101101101: //15
(countmin == 8'h10) ? 16'b00001101111101://16
(countmin == 8'h11) ? 16'b00001100000111://17
(countmin == 8'h12) ? 16'b00001101111111://18
(countmin == 8'h13) ? 16'b00001101101111://19
(countmin == 8'h14) ? 16'b10110110111111://20
(countmin == 8'h15) ? 16'b10110110000110://21
(countmin == 8'h16) ? 16'b10110111011011://22
(countmin == 8'h17) ? 16'b10110111001111://23
(countmin == 8'h18) ? 16'b10110111100110://24
(countmin == 8'h19) ? 16'b10110111101101://25
(countmin == 8'h1a) ? 16'b10110111111101://26
(countmin == 8'h1b) ? 16'b10110110000111://27
(countmin == 8'h1c) ? 16'b10110111111111://28
(countmin == 8'h1d) ? 16'b10110111101111://29
(countmin == 8'h1e) ? 16'b10011110111111://30
(countmin == 8'h1f) ? 16'b10011110000110://31
(countmin == 8'h20) ? 16'b10011111011011://32
(countmin == 8'h21) ? 16'b10011111001111://33
(countmin == 8'h22) ? 16'b10011111100110://34
(countmin == 8'h23) ? 16'b10011111101101://35
(countmin == 8'h24) ? 16'b10011111111101://36
(countmin == 8'h25) ? 16'b10011110000111://37
(countmin == 8'h26) ? 16'b10011111111111://38
(countmin == 8'h27) ? 16'b10011111101111://39
(countmin == 8'h28) ? 16'b11001100111111://40
(countmin == 8'h29) ? 16'b11001100000110://41
(countmin == 8'h2a) ? 16'b11001101011011://42
(countmin == 8'h2b) ? 16'b11001101001111://43
(countmin == 8'h2c) ? 16'b11001101100110://44
(countmin == 8'h2d) ? 16'b11001101101101://45
(countmin == 8'h2e) ? 16'b11001101111101://46
(countmin == 8'h2f) ? 16'b11001100000111://47
(countmin == 8'h30) ? 16'b11001101111111://48
(countmin == 8'h31) ? 16'b11001101101111://49
(countmin == 8'h32) ? 16'b11011010111111://50
(countmin == 8'h33) ? 16'b11011010000110://51
(countmin == 8'h34) ? 16'b11011011011011://52
(countmin == 8'h35) ? 16'b11011011001111://53
(countmin == 8'h36) ? 16'b11011011100110://54
(countmin == 8'h37) ? 16'b11011011101101://55
(countmin == 8'h38) ? 16'b11011011111101://56
(countmin == 8'h39) ? 16'b11011010000111://57
(countmin == 8'h3a) ? 16'b11011011111111://58
(countmin == 8'h3b) ? 16'b11011011101111://59
16'b11011010111111;
always @ (posedge slow_clk[N-1] or posedge outh)
if (outh) begin
counthr <= counthr + 8'b1;
end
else if(counthr != 8'b00001100 && countmin == 8'b00111011 && countsec == 8'b00111011) counthr <= counthr + 8'b1;
else if (counthr == 8'b00001100 && countmin == 8'b00111011 && countsec == 8'b00111011 ) counthr <= 8'b1;
else counthr <= counthr;
assign seghr = (counthr == 8'h1) ? 16'b01111110000110: //1 0000110 0111111
(counthr == 8'h2) ? 16'b01111111011011: //2 1011011
(counthr == 8'h3) ? 16'b01111111001111: //3 1001111
(counthr == 8'h4) ? 16'b01111111100110: //4 1100110
(counthr == 8'h5) ? 16'b01111111101101: //5 1101101
(counthr == 8'h6) ? 16'b01111111111101: //6 1111101
(counthr == 8'h7) ? 16'b01111110000111: //7 0000111
(counthr == 8'h8) ? 16'b01111111111111: //8 1111111
(counthr == 8'h9) ? 16'b01111111101111: //9 1101111
(counthr == 8'ha) ? 16'b00001100111111: //10
(counthr == 8'hb) ? 16'b00001100000110: //11
(counthr == 8'hc) ? 16'b00001101011011: //12
16'b01111110000110;
endmodule
always @ (posedge slow_clk2[M-1])
using registers as clocks like this is just asking for trouble. You really, really should rework things to use one clock, and then within that edge-triggered block a condition which enables the register assignment. So basically your huge variety of clocks should instead become enables. \$\endgroup\$