The handling of clocks in accelerator cards has evolved to support multiple platform clocks and clock frequencies. The kernels can have any number of independent and edge-aligned clocks, and platforms can have multiple kernels running at different clock frequencies under user-control. A platform can have scalable clocks and fixed clocks.
- Scalable Clocks
An Alveo™ platform provides a frequency scalable kernel clock with ID 0 that drives all XRT managed kernels. XRT can set the clock frequency of this clock according to the meta-data contained in the xclbin file, when loading the file. An Alveo platform also provides a second scalable clock with ID 1 that is XRT also controllable based on xclbin meta-data. You do not need to provide an option to connect to scalable clocks, but you can specify the clock frequency during
v++linking using the
--kernel_frequencycommand, as described in v++ General Options. For example, the
v++linker will automatically wire kernel clocks
ap_clkto clock ID 0, and
ap_clk2to clock ID 1.Tip: In practice,
ap_clk2is primarily found on RTL kernels, because Vitis HLS does not generate kernels with multiple clocks.
- Fixed Clocks
You can generate any number of derived fixed clocks that are not controllable by XRT. The
v++linker provides the --clock Options for users to specify which kernel clock pins should be connected to which clocks, and to define clock frequencies that are not defined on the platform. Fixed clocks are more commonly used for embedded platforms and RTL kernels.
v++to use the fixed clocks of a platform, rather then the scalable clocks. For HLS kernels, the clock ID 0 is always used. For RTL kernels with one clock, clock ID 0 is used by default, but you can select a different clock.
Scalable clocks can be used to scale the clock itself whereas fixed clocks are used to add MMCMs to generate frequencies other than the frequencies defined on the platform. For example, if you choose to specify clock frequencies: 60, 200, and 450, Vitis will add all the necessary logic to generated the required clocks.
If Vivado place and route tools
are unable to meet the frequency specification, the tools can scale the clock frequency
to an achievable frequency if the scalable clock has been used (
--kernel_frequency). If a fixed clock is used (
--clock), then you will need to re-run the implementation
to update the frequency target.
platforminfocommand. For example, the following command returns verbose information related to a newer shell for the U250 platform:
platforminfo -v -p xilinx_u250_gen3x16_xdma_3_1_202020_1 -o pfmClocks.txt
================= Clock Information ================= Default Clock Index: 0 Default Clock Frequency: 300.000000 Default Clock Pretty Name: PL 0 Clock Index: 0 Frequency: 300.000000 Name: ss_ucs_aclk_kernel_00 Pretty Name: PL 0 Inst Ref: ss_ucs Comp Ref: shell_ucs_subsystem Period: 3.333333 Normalized Period: .003333 Status: scalable Clock Index: 1 Frequency: 500.000000 Name: ss_ucs_aclk_kernel_01 Pretty Name: PL 1 Inst Ref: ss_ucs Comp Ref: shell_ucs_subsystem Period: 2.000000 Normalized Period: .002000 Status: scalable Clock Index: 2 Frequency: 50.000000 Name: ii_level1_wire_ulp_m_aclk_ctrl_00 Pretty Name: PL 2 Inst Ref: ii_level1_wire Comp Ref: ii_level1_wire Period: 20.000000 Normalized Period: .020000 Status: fixed Clock Index: 3 Frequency: 250.000000 Name: ii_level1_wire_ulp_m_aclk_pcie_user_00 Pretty Name: PL 3 Inst Ref: ii_level1_wire Comp Ref: ii_level1_wire Period: 4.000000 Normalized Period: .004000 Status: fixed Clock Index: 4 Frequency: 100.000000 Name: ii_level1_wire_ulp_m_aclk_freerun_ref_00 Pretty Name: PL 4 Inst Ref: ii_level1_wire Comp Ref: ii_level1_wire Period: 10.000000 Normalized Period: .010000 Status: fixed
The following are some examples of clock management using the --clock Options in increasing order of precedence:
- In absence of any
--clockoption, a scalable default clock will be applied. For kernels with two clocks clock ID 0 will be assigned to ap_clk, and clock ID 1 will be assigned to ap_clk_2.
--clock.defaultId=<id>overrides the platform default. The specified clock <id> will be used as a reference clock for all pins on all CUs, unless additional
--clockoptions are specified.
--clock.defaultFreq=<Hz>overrides platform default with a clock of the specified frequency. The default clock will be assigned to all pins on all CUs, unless additional
--clockoptions are specified.
--clock.id=<id>:<cu>assigns the specified ID to all clock pins on the specified CU.
--clock.id=<id>:<cu>.<clk0>assigns the specified ID to the specified clock pin on the specified CU.
There are a couple of high-level considerations in practice. Scalable clocks help you to achieve timing without having to regenerate the .xclbin file, by allowing the tool to scale the clock as needed to achieve a specific frequency or to meet timing.
Designs requiring different kernels to run at different clock rates, e.g., to
close timing or to meet performance targets require the
--clock directive that targets fixed clocks. Similarly, RTL kernels
requiring multiple clocks, in general, require the
--clock directives. For most serious designs, the expectation is that the
user will at some point know what their achievable frequency targets are, and will need
to specify these (fixed clocks) when they exceed the scalable clock frequencies (scaling
will not increase a scaled clock frequency above the platform default).