
Back when I gave an introduction to SDC, I brushed upon `set_false_path` statements between clocks. However, now there is a more efficient way of specifying the the clock exceptions in the design. `set_clock_groups` is a powerful way of letting the P&R and STA tools know what is expected of it during optimization and analysis.
There are three options to this command. `-asynchronous`, `-logically_exclusive` and `-physically_exclusive`. Let’s tackle them one by one.
Asynchronous Clocks
`set_clock_groups -asynchronous`
When you say two(or more) clocks are asynchronous, that means there is no phase relationship between them at all.
Consider the following statements:
`create_clock -period 10 -name ClkA [get_ports CLKA]`
`create_clock -period 1- -name ClkB [get_ports CLKB]`
`set_clock_groups -asynchronous -group {ClkA} -group {ClkB}`
This is equivalent to setting the following two false path statements.
`set_false_path -from [get_clocks ClkA] -to [get_clocks ClkB]`
`set_false_path -from [get_clocks ClkB] -to [get_clocks ClkA]`
Case 1
`set_clock_groups -asynchronous -group {ClkA ClkC} -group {ClkB ClkD}`
Breaking down the above command gives us–
1. ClkA and ClkC are synchronous to each other.
2. ClkB and ClkD are synchronous to each other.
3. ClkA & ClkC are asynchrnous to ClkB & ClkD and vice versa.
i.e. The members of a group are synchronous to each other, but asynchronous the to the elements in the other group.
Case2
Now, consider that one(or both) of these clocks generated other clock, say by a clock divider as in the figure below.
`set_clock_groups -asynchronous -group [get_clocks ClkA] -group [get_clocks {ClkB divClkB}]`
Logically Exclusive Clocks
Two clocks are said to be logically exclusive when they are both active in the design but doesn’t have any paths between them. An example would be a MUX selecting two or more of the clocks for a portion of the design using its select lines. Such clocks will not have any timing path between them. Let’s see the circuit below:
Case1
The clock clkOut is selected by the Sel line of the Mux MX1. So, Clk1 and Clk2 cannot exist together logically in the downstream path of the MX1. They are not interacting outside the MUX path.
`set_clock_groups -logically_exclusive -group [get_clocks Clk1] -group [get_clocks Clk2]`
Case2
There is logic on Clk2 outside the MUX which is interacting with flops clocked by ClkOut, we cannot specify a logical_exclusion on Clk1 and Clk2. What you can do here is create generated clock statement for the output of the MX1.
`create_generated_clk -name genClk1 -source MX1/Y -master Clk1`
`create_generated_clk -name genClk2 -source MX1/Y -master Clk2`
`set_clock_groups -logically_exclusive -group [get_clocks genClk1] -group [genClk2]`
Case 3
There is a clock divier on ClkOut. In such cases you need to create two generated clock statements for this with Clk1 & Clk2 as the master clock.
`create_generated_clk -name genDivClk1 -source ClkDiv/Y -master Clk1`
`create_generated_clk -name genDivClk2 -source ClkDiv/Y -master Clk2`
`set_clock_groups -logically_exclusive -group [get_clocks {Clk1 genDivClk1}] -group [get_clocks {Clk2 genDivClk2}]`
Physically Exclusive Clocks
These clocks do not exist in the design at the same time. e.g. Clocks defined on the same primary port but working in two different modes like the TestClk and Functional Clock. There will be no SI interaction between these clocks.
`set_clock_groups -physically_exclusive -group [get_clocks TestClk] -group [get_clocks SysClk]`