How to Handle Clock Domain Crossing in Verilog: Fix and Best Practices
clock domain crossing in Verilog, use synchronizer flip-flops to safely transfer signals between different clock domains and avoid metastability. This typically involves passing signals through two or more flip-flops clocked by the destination clock domain.Why This Happens
When signals move from one clock domain to another with a different clock, timing mismatches can cause metastability. This means the receiving flip-flop may not settle to a stable 0 or 1 in time, causing unpredictable behavior.
Here is an example of broken code that directly assigns a signal from one clock domain to another without synchronization:
module broken_cdc(
input wire clk_a,
input wire clk_b,
input wire signal_a,
output reg signal_b
);
// Direct assignment without synchronization
always @(posedge clk_b) begin
signal_b <= signal_a; // Unsafe crossing
end
endmoduleThe Fix
The correct way is to use a two-stage synchronizer in the destination clock domain. This reduces metastability risk by giving the signal time to settle before use.
Here is the fixed code using two flip-flops to synchronize the signal from clk_a to clk_b domain:
module fixed_cdc(
input wire clk_a,
input wire clk_b,
input wire signal_a,
output reg signal_b
);
reg sync_ff1, sync_ff2;
// Synchronize signal_a into clk_b domain
always @(posedge clk_b) begin
sync_ff1 <= signal_a;
sync_ff2 <= sync_ff1;
signal_b <= sync_ff2;
end
endmodulePrevention
To avoid clock domain crossing issues in the future, follow these best practices:
- Always use at least two flip-flops for synchronizing single-bit signals crossing clock domains.
- For multi-bit buses, use handshake protocols or FIFOs designed for CDC.
- Use static timing analysis tools and CDC checkers to detect unsafe crossings.
- Keep clock domains clearly separated and document their interactions.
Related Errors
Other common errors related to clock domain crossing include:
- Data corruption: When multi-bit signals cross without synchronization, bits can arrive at different times causing invalid data.
- Glitches: Unsynchronized signals can cause short pulses that trigger unintended logic.
- Timing violations: Setup and hold time violations occur if signals are sampled too close to clock edges.
Quick fixes involve adding synchronizers, using handshake signals, or employing asynchronous FIFOs.