Why use this 2 DFF method every time a button press is involved? - verilog

I have been reading verilog code online and have noticed this in many of the code examples. Whenever an input is needed from a hardware source such as a button press, the input is copied to a flip flop and then AND'd with the invert of the input. I dont know if this made much sense but in code here it is:
input btn;
reg dff1, dff2;
wire db_tick;
always # (posedge clock) dff1 <= btn;
always # (posedge clock) dff2 <= dff1;
assign db_tick = ~dff1 & dff2;
And then db_tick is used as the button press.
In some cases this is also used as a rising edge detector, but cant a rising edge detector easily be implemented with always#(posedge signal)

It's called a monostable multivibrator or, specifically for digital circuits, a one-shot. The purpose of the circuit is to change an edge into a single cycle pulse.
When connected directly to a physical switch it can be a way to effect switch debouncing, but that's not really a good use for it. It's hard to say what the intent is in the code without more context.

This is providing edge detection synchronous to your clock domain. I do not see any debouncing happing here, it is quite common to also include 2 meta stability flip flops before the edge detection.
input a;
reg [2:0] a_meta;
always #(posedge clk or negedge rst_n) begin
if (~rst_n) begin
a_meta <= 3'b0 ;
end
else begin
a_meta <= {a_meta[1:0], a};
end
end
// The following signals will be 1 clk wide, Clock must be faster than event rate.
// a[2] is the oldest data,
// if new data (a[1]) is high and old data low we have just seen a rising edge.
wire a_sync_posedge = ~a_meta[2] & a_meta[1];
wire a_sync_negedge = a_meta[2] & ~a_meta[1];
wire a_sync_anyedge = a_meta[2] ^ a_meta[1]; //XOR

Related

How do I drive a signal from 2 sources in system verilog

I'm trying to write a RTL model in which I monitor independent clock sources. These clock sources can have variable frequency (range 5 to 50MHz)
Let us say clk1 and clk2. I'm trying to drive a signal 'toggle' which is set '1' at every posedge of clk1 and is set to '0' at every negedge of clk2. I'm having trouble realizing this model.
I tried using 1 flop triggered at the positive edge of clk1 with inputs of this flop tied to 'high' and another flip flop triggered at the negative edge of clk2 with input tied to 'low'. I sent these outputs to a mux, but I have trouble figuring out how to drive the select signal of this mux
Here is my code snippet :
always_ff #(posedge clk1 or rstb) begin
if(!rstb) begin
flop1_out <= 0;
end else begin
flop1_out <= 1;
end
end
always_ff #(negedge clk2) begin
flop2_out <= 0;
end
assign toggle = sel ? flop1 : flop2;
So, as of now nothing is driving sel and trying to figure this out is where I'm having trouble
If I try to drive the same signal (toggle) from 2 different clock sources, I get an error saying that multiple drivers found for signal toggle, which makes sense.
Please let me know if you have any suggestions
EDIT: fixed a typo and removed rstb from the sensitivity list for flop2
assign rstn = clk2;
always # (posedge clk1 or negedge rstn)
if (~rstn)
toggle = 1'b0;
else
toggle <= 1'b1;
note: depending on the clock frequency and insertion delay relationships this circuit may become metastable. if you can tolerate delay, add a synchronizer on the output. better yet, if you can tolerate distortion, add a reset synchronizer on clk2 to clk1mx, where clk1mx is synchronous to clock1 but x times faster.

two clock ring counter with verilog

I'm trying to write a roll shift/ ring counter that takes two switches as the clocks in verilog.
My code is as follows:
module roll(CLK1, CLK2, LEDS);
input CLK1;
input CLK2;
output [3:0] LEDS;
reg [3:0] LEDS;
initial
begin
LEDS = 4'b0001;
end
always#(posedge CLK1 or posedge CLK2)
begin
if(CLK1)
begin
LEDS[3]<=LEDS[2];
LEDS[2]<=LEDS[1];
LEDS[1]<=LEDS[0];
LEDS[0]<=LEDS[3];
end
// Roll Right
if(CLK2)
begin
LEDS[3]<=LEDS[0];
LEDS[2]<=LEDS[3];
LEDS[1]<=LEDS[2];
LEDS[0]<=LEDS[1];
end
end
endmodule
I tried using two always blocks, but then figured out that I cannot do that. and when I have the posedge CLK2 in the always statement, the leds on my FPGA all stay on.
Remember Verilog is not a programming language it is a hardware description language.
And when coding for synthesis, you will only be successful if you write code that can be instantiated with actual gates. So writing an always block with sensitivity to edges of two different signals can't be synthesized unless the response to one of the two signals has the effect of a RESET or PRESET operation.
Your code also logically doesn't do what it seems you want to. Consider what your code says will happen if there is a rising edge on CLK2 when CLK1 is already high (or vice versa). Your lights will roll left and then immediately roll right gain, resulting in no change.
A more usual approach would be to have a clock running much faster than the UP and DOWN inputs are expected to change, and use that to drive the logic. For example
module roller(input clk, input rst, input UP, input DOWN, output reg LEDS[3:0]);
reg UP1, DOWN1;
always #(posedge clk or posedge rst)
if (rst) begin
LEDS[3:0] <= 4'b0001;
end
else
begin
UP1 <= UP;
DOWN1 <= DOWN;
if (UP & ~UP1) begin
LEDS[3:0] <= {LEDS[2:0], LEDS[3]};
end
else if (DOWN & ~DOWN1) begin
LEDS[3:0] <= {LEDS[0], LEDS[3:1]};
end
end
endmodule;
Notice that this gives priority to UP. If both UP and DOWN are asserted, the pattern will roll "up" rather than down. If you want a different behavior, you'd have to modify the code to achieve it.

Verilog always#(..) output not working as expected

So, im trying to synthesize my verilog code to send data from ps2 keybord ->fpga->vga. Just for the background of the code, I want to press the button "1", and that to appear on the center of the screen (called the display_area)
I realised that something is not working as expected.
After carefull debugging, i realised that the problem lies in the module that converts the parallel data bus from the rom, into serial output, to assign a value in each pixel.
The code itself is pretty simple, im just providing as much info as i can.
We need a positive edge of the clock to enter the always area (or a reset). If the value display_area_enable is 1, we activate a counter from 7 till 0 (8 cycles) to index the data from the rom.
However, on the first clock, if the display area becomes 1 the exact moment when the vga_clk pulse becomes 1, the counter gets the value as it should, but the one_bit_output (the output of the module) doesnt. One_bit_output gets its first correct value the 2nd time that the always block is accessed. as a result we need 9 cycles to access an 8 bit bus.
I ll provide the code and a modelsim testbench
module shifter(reset,char_rom_data_out,vga_clk,display_area_enable,one_bit_output,counter);
input [7:0]char_rom_data_out;
input vga_clk,display_area_enable,reset;
output reg one_bit_output;
output reg [2:0]counter;
always #(posedge vga_clk or posedge reset)
begin
if (reset)
begin
counter=3'd7;
one_bit_output=0;
end
else if (display_area_enable==1)
begin
one_bit_output<=(char_rom_data_out[counter]==1);
counter<=counter-1;
end
else if (display_area_enable==0)
begin
counter<=3'd7;
one_bit_output<=0;
end
end
endmodule
module testbz();
reg reset,vga_clk,display_area_enable;
reg [7:0]char_rom_data_out;
wire [2:0] counter;
wire one_bit_output;
shifter dignitas(reset,char_rom_data_out,vga_clk,display_area_enable,one_bit_output,counter);
initial
begin
reset<=1; char_rom_data_out<=8'b11110001; vga_clk<=0;display_area_enable=0; //sto 10 skaei o prwtos kyklos, kai meta ana 20
#5 reset<=0; display_area_enable<=0;
#5 display_area_enable<=1;
#160 display_area_enable<=0;
end
always
begin
#10 vga_clk=~vga_clk;
end
endmodule
and the simulation is :
Can someone explain to me why on the first pulse of the vga_clk, the output is not expected?
Change one_bit_output so that it does not change in relation to the clock edge, but asynchronously in relation to the display_area_enable. The counter keeps track of which element to output. This is essentially a multiplexer with display_area_enable as the selector, or more likely an AND gate with one input being display_area_enable.
As toolic said, the synchronous one_bit_output cannot change on the same cycle as its activating signal. This is because of the set-up times of the flip-flops, the signal must be stable for some time before the clock edge. Now, if you are using one_bit_output to drive some flip-flop, then it MUST update on the next edge. Don't try to avoid this by using latches, that will make synthesis quite hard.
module shifter(reset,char_rom_data_out,vga_clk,display_area_enable,one_bit_output,counter);
input [7:0]char_rom_data_out;
input vga_clk,display_area_enable,reset;
output reg one_bit_output;
output reg [2:0]counter;
always #(posedge vga_clk or posedge reset)
begin
if (reset)
begin
counter<=3'd7;
//one_bit_output<=0;
end
else if (display_area_enable==1)
begin
//one_bit_output<=(char_rom_data_out[counter]==1);
counter<=counter-1;
end
else if (display_area_enable==0)
begin
counter<=3'd7;
//one_bit_output<=0;
end
end
assign one_bit_output = display_area_enable ? char_rom_data_out[counter] : 0;
endmodule

IF with ternary operator - Verilog

I am trying to write a program in Verilog that should "move" a light LED on an array of LEDs. With a button the light should move to the left, with another one it should move to the right. This is my code:
module led_shift(UP, DOWN, RES, CLK, LED);
input UP, DOWN, RES, CLK;
output reg [7:0] LED;
reg [7:0] STATE;
always#(negedge DOWN or negedge UP or negedge RES)
begin
if(!RES)
begin
STATE <= 8'b00010000;
end
else
begin
STATE <= UP ? STATE>>1 : STATE<<1;
end
end
always # (posedge CLK)
begin
LED <= STATE;
end
endmodule
The problem is in STATE <= UP ? STATE>>1 : STATE<<1; and the error the following:
Error (10200): Verilog HDL Conditional Statement error at led_shift.v(34): cannot match operand(s) in the condition to the corresponding edges in the enclosing event control of the always construct
I tried to modify the code without using that kind of if:
always#(negedge DOWN or negedge UP or negedge RES)
begin
if(!RES)
STATE <= 8'b00010000;
else
begin
if(!DOWN)
STATE <= STATE<<1;
else
begin
if(!UP)
STATE <= STATE>>1;
else
STATE <= STATE;
end
end
end
It compiles, but does not work: the LED "moves" only to the left, when I press the other button all LEDs shut down. Probably there is a problem in my code, but I cannot understand why my first code does not compile at all.
Thank you for any help!
harrym
It is not clear for the synthesizer to know how to control STATE with the 3 asynchronous control signals.
Most likely your your synthesizer is trying to map STATE to a D flip flop with asynchronous active low set and reset. For example it might be trying to synthesize to something like:
dff state_0_(.Q(STATE[0], .CLK(DOWN), .SET_N(UP), .RST_N(RES(, .D(/*...*/));
In a real flop with asynchronous set and reset, the default should be consent and would explain the error in your first code. In your second attempt, UP becomes part of the combination logic cloud along with DOWN. DOWN is also being used as a clock. Since UP is not a clock, shifting continuously happens while UP is low, completely shifting the on bit out instantly. Another error for the second case would actually be more appropriate.
For the synthesizer to do a better job, you first need to synchronize your asynchronous control signals. Use the same technique as CDC (clock domain crossing; A paper by Cliff Cummings goes into detains here). A basic example:
always #(posedge clk) begin
pre_sync_DOWN <= DOWN;
sync_DOWN <= pre_sync_DOWN;
end
Now that the controls signals are synchronized, make STATE the output of your combination logic. Example:
always #* begin
if(!sync_RES)
STATE = 8'b00010000;
else
case({sync_UP,sync_DOWN})
2'b01 : STATE = LED>>1;
2'b10 : STATE = LED<<1;
default: STATE = LED;
endcase
end
With everything running on one clock domain and explicitly defined combination logic, the synthesizer can construct equivalent logic using flops and basic gates.
FYI:
To shift only on a negedge event you need to keep the last sync value and check for the high to low transition. Remember to swap sync_ with do_ in the combination logic that drives STATE.
always #(posedge clk)
keep_DOWN <= sync_DOWN;
always #*
do_DOWN = (keep_DOWN && !sync_DOWN);

verilog always #(posedge) failing in uart

I'm learning verilog and I think there is something that I must not understand about always #* and always (#posedge clk, ...)
Here is a piece of code supposed to send bits via uart. It fails at synthesization.
The error is
" The logic for does not match a known FF or Latch template. The description style you are using to describe a register or latch is not supported in the current software release."
(and 3 other errors for , and )
If I change the always #(...) by always #*, things fail in the next step ("implement design") because things are not connected.
In the book that I have, they implement an fsmd with an always (posedge clk) for the state, and always #* for the other logic, but I don't understand why this doesn't work.
On another forum, I read that the error could come from too complicated conditions. But I have simplified things too (not code the code here but basically I removed the case(state) and the ifs to have single line assignments with ? : or binary conditions, but it didn't work either)
I have seen this error before in other pieces of code that I wrote but I didn't get to the bottom of it, so if you could help me understand the general problem (with this uart thing as a support for a concrete example), I would be very happy.
Thanks
Thomas
P.S : Im using xilinx spartan 3e starter kit and xilinx ise 14.4
module UART_out #(parameter [3:0] NUM_BITS = 8)
(
input wire baud_clk,
input wire send_tick,
input wire[NUM_BITS-1:0] data_in,
output wire tx,
output wire debug_done
);
localparam
IDLE = 0,
TRANSMIT = 1;
reg[NUM_BITS:0] bits_to_send;
reg state;
reg out_bit;
reg[4:0] cnt;
always #(posedge baud_clk, posedge send_tick)
begin
case (state)
IDLE:
if (send_tick)
begin
bits_to_send <= {data_in, 0};
state <= TRANSMIT;
cnt <= 0;
end
TRANSMIT:
begin
if (cnt < NUM_BITS)
cnt <= cnt + 1;
else
state <= IDLE;
bits_to_send <= {1, bits_to_send[NUM_BITS:1]};
out_bit <= bits_to_send[0];
end
endcase
end
assign tx = (state == IDLE ? 1 : out_bit);
assign debug_done = (state == IDLE);
endmodule
The error:
The logic for does not match a known FF or Latch template. The description style you are using to describe a register or latch is not supported in the current software release.
Is referring to the fact that the synthesis tool does not have any hardware cells to use which match your description.
What hardware do you want from :
always #(posedge baud_clk, posedge send_tick)
This looks like you want a flip-flop with an enable signal. The enable signal (send_tick) should be 1 clock period wide. This is then used to select the path of logic on a clock edge. not as an alternative trigger.
I think that this is all you really need:
always #(posedge baud_clk) begin
case (state)
IDLE:
if (send_tick) begin
//...
end
//...
endcase
end
If send_tick is from another clock domain then you will need to do some clock domain crossing to turn it it to a clock wide pulse on the baud_clk.
You may be getting confused with blocks which have multiple triggers, they are normally a clk and reset. A negedge reset_n or posedge reset are often added for reset (initialisation) conditions.
If adding a reset :
always #(posedge baud_clk or negedge reset_n) begin
if (~reset_n) begin
//reset conditions
state <= IDLE;
//...
end
else begin
// Standard logic
end
end
You will notice that there is a very definite structure here, if reset else ... The synthesis tools recognise this as a flip-flop with an asynchronous reset. The data in the reset condition is also static, typically setting everything to zero.

Resources