Vivadoのタイミング解析エンジンは、デフォルトで設計内のすべてのクロック間パスを解析対象とする。しかし、特定のクロック間パスを意図的に解析から除外したい場合、set_clock_groups制約を使用することで、不要なタイミングチェックを無効化できる。
クロック間の関係性
2つのクロックの関係は、以下の3種類に分類される:
- 同期クロック(Synchronous):共通の基準クロックから派生しており、位相関係が確定的。例:MMCM出力の複数クロックや、同じ入力クロックからの生成クロック。
- 非同期クロック(Asynchronous):独立した発振源(例:別々の水晶発振器)由来で、位相関係が不定。
- 非拡張クロック(Non-Expandable):理論的には位相関係が存在するが、1000周期以内に共通エッジが現れないため、タイミングツールが最悪遅延を正確に評価できない。例:5.125 nsと6.666 nsの周期を持つ2つの生成クロック。このようなケースは実質的に非同期として扱うべきである。
Vivadoでは「Report Clock Interaction」機能により、クロック間の関係を視覚的に確認できる。赤色の「Timed (Unsafe)」は非同期または非拡張クロックを示し、青色の「User Ignored Paths」はset_clock_groupsなどでユーザーが明示的に無視設定したパスを表す。
set_clock_groupsの構文と使用法
基本的なTclコマンド形式は以下の通り:
set_clock_groups -name <group_name> -asynchronous | -logically_exclusive | -physically_exclusive \
-group [get_clocks {clkA clkB}] \
-group [get_clocks {clkC}]
この制約は他のタイミング例外(例:set_false_path)よりも優先度が高く、一度適用されると該当クロック間のパスは完全に解析対象外となる。
使用例
4つのクロック(clk1, clk2, clk3, clk4)がある設計において、以下のように制約を適用すると解析範囲が変化する:
- 単一グループ(clk1のみ):
clk1は自身とのパスのみ解析され、他のクロックとは解析されない。 - グループ内複数クロック(clk1, clk2):clk1↔clk2間は解析されるが、clk3/clk4との間は無視される。
- 複数グループ({clk1}, {clk2}):clk1とclk2の間のパスが無視される。
- 複数グループで複数クロック({clk1,clk2}, {clk3,clk4}):グループ内は解析され、グループ間は無視される。
要するに、set_clock_groupsで定義された各グループ内でのみクロック間解析が行われ、グループ間および未指定クロックとの間は解析されない。
オプションの違い:asynchronous vs logically_exclusive vs physically_exclusive
これら3つのオプションはいずれもクロック間パスを無視する点では共通しているが、信号整合性(SI: Signal Integrity)解析への影響が異なる。
asynchronous
位相関係が完全に不定なクロックペアに使用。SI解析(クロストーク遅延など)は依然として実行される。典型的な使用例は非同期FIFOや一般的な非同期インタフェース。
logically_exclusive
物理的には同時に配線されているが、論理的には決して同時にアクティブにならないクロック(例:BUFGMUXの選択入力)に適用。SI解析は実行されるため、実際には存在しない同時アクティブ状態に基づく過剰に悲観的な遅延が計算される可能性がある。
physically_exclusive
物理的に同時に存在し得ないクロック(例:同一ポートに定義されたテストクロックと機能クロック)に使用。この場合、SI解析がスキップされ、より現実的なタイミング評価が可能になる。
ただし、FPGA設計においてはSIの影響が限定的なため、多くの場合、3つのオプションの違いは無視しても問題ない。一方、ASIC設計ではSIが重大な影響を持つため、適切な区別が必要となる。
等価となるケース
MMCM/PLLの出力(clkout0, clkout1)がBUFGMUXに入力されるような構成では、これら2クロックは物理的に同時にアクティブにならない。このとき、-logically_exclusiveと-physically_exclusiveはFPGA上では実質的に同等の効果を持つ。
ただし、より正確なSI解析を求める場合は、BUFGMUXの出力ピンに生成クロックを定義し、その生成クロックに対してphysically_exclusiveを適用することで、MUX入力側の結合容量の影響を適切に考慮できる:
create_generated_clock -name gCLK1 -source [get_ports CLK1] -divide_by 1 -add -master_clock [get_clocks CLK1] [get_pins U1/z]
create_generated_clock -name gCLK2 -source [get_ports CLK2] -divide_by 1 -add -master_clock [get_clocks CLK2] [get_pins U1/z]
set_clock_groups -physically_exclusive -group [get_clocks gCLK1] -group [get_clocks gCLK2]