Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up

FPGA Clock Configuration Device Driver for Linux

License

NotificationsYou must be signed in to change notification settings

ikwzm/fclkcfg

Repository files navigation

Overview

fclkcfg

fclkcfg, which stands for FPGA Clock Configuration, is a device driver that enablesuser-space configuration of clock supplied to Programmable Logic (PL) of Zynq/Zynq UltraScale+.

Architecture

fclkcfg exposes Linux Kernel'sclk driver functions to user space so that PL clock configurationcan be done from the user space.

Fig.1 Architecture of fclkcfg

Fig.1 Architecture of fclkcfg

Supported platforms

  • OS: Linux Kernel Version 4.4.4 or later
  • CPU: ARM(Zynq-7000), ARM64(Zynq UltraScale+)

Note: fclkcfg is being tested on Altera-SoC as of 2016-04-08, but not confirmed to fully work on the platform.

Install

Build

The repository contains an exampleMakefile, which could be modified depending on the target platform and/orthe build tool chain.

Install on Linux

Thefclkcfg kernel object can be loaded via theinsmod command.

When loaded, device drivers are instantiated based on the configuration in a device tree overlay.See the following section for details of the device tree overlay.

zynq# insmod fclkcfg.ko[  102.044387] fclkcfg amba:fclk0: driver installed.[  102.049016] fclkcfg amba:fclk0: device name   : fclk0[  102.053949] fclkcfg amba:fclk0: clock  name   : fclk0[  102.058748] fclkcfg amba:fclk0: clock  rate   : 100000000[  102.058748] fclkcfg amba:fclk0: clock  enable : 1

Uninstall

The loaded module can be removed using thermmod command.

zynq# rmmod fclkcfg[  261.514039] fclkcfg amba:fclk0: driver unloaded

Installation with the Debian package

For details, refer to the following URL.

Device Tree

Configuration of clock (frequency, enable/disable status) can be passed as a device tree overlay blob.The following is an example device tree overlay sourcedts that configuresclk0 to be 100 MHz.

        fclk0 {            compatible    = "ikwzm,fclkcfg";            device-name   = "fpga-clk0";            clocks        = <&clkc 15>, <&clkc 2>;            insert-rate   = "100000000";            insert-enable = <1>;            remove-rate   = "1000000";            remove-enable = <0>;        };

The subsections below describe details of the properties configurable in the device tree overlay.

compatible property

Thecompatible property specifies a keyword which is used to find an appropriate device driveramong available kernel module. Forfclkcfg, this field is mandatory and shall contain"ikwzm,fclkcfg-0.10.a" or"ikwzm,fclkcfg". (Prior to v1.6.0, only"ikwzm,fclkcfg-0.10.a" could be used. After v1.6.0,"ikwzm,fclkcfg" also can be used).

device-name property

device-name is a optional property that specifies a name give to a created device.When thedevice-name property is not specified, the device tree node name (fclk0 in theabove example) will be used as a name.

clocks property

Theclock property takes a target clock to be configured as a first argument, andits resource clocks as a second and subsequent arguments (optional).Theclock property is a mandatory field in thefclkcfg device tree overlay entry.

Clocks passed to theclocks property should be in the format of<clock_handle clock_index>, e.g.<&clkc 15>.

For example, in the case of Zynq, the clock list is defined as follows in the device tree.

/dts-v1/;        :          ...        :        slcr: slcr@f8000000 {            #address-cells = <1>;            #size-cells = <1>;            compatible = "xlnx,zynq-slcr", "syscon", "simple-bus";            reg = <0xF8000000 0x1000>;            ranges;            clkc: clkc@100 {                #clock-cells = <1>;                compatible = "xlnx,ps7-clkc";                fclk-enable = <0>;                clock-output-names = "armpll", "ddrpll", "iopll", "cpu_6or4x",                        "cpu_3or2x", "cpu_2x", "cpu_1x", "ddr2x", "ddr3x",                        "dci", "lqspi", "smc", "pcap", "gem0", "gem1",                        "fclk0", "fclk1", "fclk2", "fclk3", "can0", "can1",                        "sdio0", "sdio1", "uart0", "uart1", "spi0", "spi1",                        "dma", "usb0_aper", "usb1_aper", "gem0_aper",                        "gem1_aper", "sdio0_aper", "sdio1_aper",                        "spi0_aper", "spi1_aper", "can0_aper", "can1_aper",                        "i2c0_aper", "i2c1_aper", "uart0_aper", "uart1_aper",                        "gpio_aper", "lqspi_aper", "smc_aper", "swdt",                        "dbg_trc", "dbg_apb";                reg = <0x100 0x100>;            };        :          ...        :

When the above device tree is loaded, clock configuration should be done viaslcr's (System Level Control Register's)clkc.clocks = <&clkc 15>;, in this case, corresponds to the 15th entry (note the number is zero-indexed) of the clock list,namelyfclk0 or equivalently PL Clock 0.

The second and subsequent arguments ofclocks specifies a resource clock of the PL clock to be generated.Either of "armpll" (<&clkc 0>), "ddrpll" (<&clkc 1>), or "iopll" (<&clkc 2>}) can be a resource clock.For example,clocks = <&clkc 16>, <&clkc 2>; means thatclkc's 16th clock (again, note zero-indexed),namelyfclk1 (i.e. PL Clock 1) is specified as the target of generation, based on the 2nd entry of theclkc's clock list, namely i.e. "iopll".

When the second and subsequent arguments is unspecified, a resource clock that is selected up on Linux boot up is used as a resource clock.

The "phandle" integer number, which is assigned when a decive tree source is compiled to device tree blob by dtc (Device Tree Compiler), can also be used in place of the symbol representation like&clkc. For instance, ifclkc is assigned a phandle number of 5 by dtc,clocks = <5 15> has the same meaning asclocks = <&clkc 15>, and can be used to control PL Clock 0.

Sometimes symbol definitions can be removed from a compiled device tree blob, and in such cases, the symbol representation like&clkc cannot be used, and therefore, a phandle number should be explicitly specified in the device tree overlay as follows:

        fclk0 {            compatible  = "ikwzm,fclkcfg";            clocks      = <5 15>;        };

Clock properties for Zynq

The following table lists clocks that are defined in the Zynq device tree and can be passed to theclock property.

Table.1 Zynq clocks

Clock NameIndexProperty ValueDescription
armpll0<&clkc 0>ARMPLL. Can be specified as a "resource clock" (optional)
ddrpll1<&clkc 1>DDRPLL. Can be specified as a "resource clock" (optional)
iopll2<&clkc 2>IOPLL. Can be specified as a "resource clock" (optional)
fclk015<&clkc 15>PL Clock 0.
fclk116<&clkc 16>PL Clock 1.
fclk217<&clkc 17>PL Clock 2.
fclk318<&clkc 18>PL Clock 3.

Clock properties for ZynqMP

The following table lists clocks that are defined in the ZynqMP device tree and can be passed to theclock property.

Table.2 ZynqMP clocks(linux-xlnx v2018.2)

Clock NameIndexProperty ValueDescription
iopll0<&clkc 0>IOPLL. Can be specified as a "resource clock" (optional)
rpll1<&clkc 1>RPLL. Can be specified as a "resource clock" (optional)
dpll_to_lpd8<&clkc 8>DPLL. Can be specified as a "resource clock" (optional)
pl0_ref71<&clkc 71>PL Clock 0.
pl1_ref72<&clkc 72>PL Clock 1.
pl2_ref73<&clkc 73>PL Clock 2.
pl3_ref74<&clkc 74>PL Clock 3.

Table.3 ZynqMP clocks(linux-xlnx v2019.1)

Clock NameIndexProperty ValueDescription
iopll0<&zynqmp_clk 0>IOPLL. Can be specified as a "resource clock" (optional)
rpll1<&zynqmp_clk 1>RPLL. Can be specified as a "resource clock" (optional)
dpll_to_lpd8<&zynqmp_clk 8>DPLL. Can be specified as a "resource clock" (optional)
pl0_ref71<&zynqmp_clk 71>PL Clock 0.
pl1_ref72<&zynqmp_clk 72>PL Clock 1.
pl2_ref73<&zynqmp_clk 73>PL Clock 2.
pl3_ref74<&zynqmp_clk 74>PL Clock 3.

insert-rate property

Theinsert-rate property specifies a frequency of the clock that is generated when the clock device is installed.A double-quoted string value (in Hz) should be passed to the property. The following snippet shows an example ofsetting a clock frequency with 100 MHz to PL Clock 0 (on Zybo).

        fclk0 {            compatible  = "ikwzm,fclkcfg";            clocks      = <&clkc 15>;            insert-rate = "100000000";        };

Theinsert-rate property is optional, and when omitted, the output clock frequency is not changed from the present value.

insert-enable property

Theinsert-enable property controls the output status of the clock when the clock device is installed.<1> and<0> mean enable output and disable output up on installation, respectively.The following example enables clock output up on installation of the clock device.

        fclk0 {            compatible    = "ikwzm,fclkcfg";            clocks        = <&clkc 15>;            insert-enable = <1>;        };

Theinsert-enable property is optional, and when omitted, the clock output is disabled up on installation.

insert-resource property

Theinsert-resource property specifies a resource clock that is generated when the clock device is installed.Theinsert-resource property only has an effect if theclocks property has second and subsequent arguments.Theinsert-resource property is an integer. The position of the second argment of theclocks property is<0>, and thereafter, the the third argment is<1>, and the fourth argment is<2>.

For example, in the device tree below, the resource clock is set to<&clk 1>.

        fclk0 {            compatible      = "ikwzm,fclkcfg";            device-name     = "fpga-clk0";            clocks          = <&clkc 15>, <&clkc 0>, <&clkc 1>, <&clkc 2>;            insert-resource = <1>;  // <0>: <&clkc 0>, <1>: <&clkc 1>, <2>: <&clkc 2>,            insert-rate     = "25000000";        };

Theinsert-resouce property is optional and defaults to<0>. In this case, if theclocks property has more than the second argument, the clock specified by the second argument will be set as the resource clock. Also, if theclocks property has only the first argument, the resource clock will not be changed.

remove-rate property

Theremove-rate property specifies a frequency of the clock that is generated when the clock device is removed.A double-quoted string value (in Hz) should be passed to the property. The following snippet shows an example ofsetting a clock frequency with 1 MHz to PL Clock 0 (on Zybo) up on removal.

        fclk0 {            compatible    = "ikwzm,fclkcfg";            clocks        = <&clkc 15>;            remove-rate   = "1000000";        };

Theremove-rate property is optional, and when omitted, the output clock frequency will stay unchangedwhen the clock device is removed.

remove-enable property

Theremove-enable property controls the output status of the clock when the clock device is removed.<1> and<0> mean enable output and disable output up on removal, respectively.The following example stops clock output up on removal of the clock device.

        fclk0 {            compatible    = "ikwzm,fclkcfg";            clocks        = <&clkc 15>;            remove-enable = <0>;        };

Theremove-enable property is optional, and when omitted, the clock output will be disabled up onremoval of the clock device.

remove-resource property

Theremove-resource property specifies a resource clock when the clock device is removed.Theremove-resource property only has an effect if theclocks property has second and subsequent arguments.Theremove-resource property is an integer. The position of the second argment of theclocks property is<0>, and thereafter, the the third argment is<1>, and the fourth argment is<2>.

For example, in the device tree below, the resource clock is set to<&clk 1>.

        fclk0 {            compatible      = "ikwzm,fclkcfg";            device-name     = "fpga-clk0";            clocks          = <&clkc 15>, <&clkc 0>, <&clkc 1>, <&clkc 2>;            remove-resource = <1>;  // <0>: <&clkc 0>, <1>: <&clkc 1>, <2>: <&clkc 2>,            remove-rate     = "25000000";        };

Theremove-resouce property is optional, and when omitted, the resource clock is unchanged when the clock device is removed.

enable-sync property

In some cases, such as ZynqMP, clock is enabled in advance by firmware.In such a case, an inconsistency with the clock driver may occur, resulting in warning such asissue #3 when the clock is stopped.

Theenable-sync property forces the clock state to be synchronized at dirver load time to suppress the occurrence of this warning.

        fclk0 {            compatible    = "ikwzm,fclkcfg";            device-name   = "fpga-clk0";            clocks        = <&clkc 15>, <&clkc 2>;            enable-sync;            insert-enable = <0>;        };

Device files

Whenfclkcfg is installed and a device tree entry is loaded (via e.g. device tree overlay), the following devicefiles will be created.\<device-name\> reads the device name specified in the device tree entry.

  • /sys/class/fclkcfg/\<device-name\>/enable
  • /sys/class/fclkcfg/\<device-name\>/rate
  • /sys/class/fclkcfg/\<device-name\>/round_rate
  • /sys/class/fclkcfg/\<device-name\>/resource
  • /sys/class/fclkcfg/\<device-name\>/resource_clks
  • /sys/class/fclkcfg/\<device-name\>/remove_rate
  • /sys/class/fclkcfg/\<device-name\>/remove_enable
  • /sys/class/fclkcfg/\<device-name\>/remove_resource

/sys/class/fclkcfg/<device-name>/enable

The file is used to controls the output status of the clock. When1 and0 are written, the clock output will beenabled and disabled, respectively. When the file is read, the output status is returned (again,1 means output enable).

zynq# echo 1 > /sys/class/fclkcfg/fclk0/enablezynq# cat /sys/class/fclkcfg/fclk0/enable1zynq# echo 0 > /sys/class/fclkcfg/fclk0/enablezynq# cat /sys/class/fclkcfg/fclk0/enable0

/sys/class/fclkcfg/<device-name>/rate

This file is used to change the output clock frequency. The following example selects an output frequency of 100 MHz.

zynq# echo 100000000 > /sys/class/fclkcfg/fclk0/ratezynq# cat /sys/class/fclkcfg/fclk0/rate100000000

Note that, due to the limitations of the PLL, it is possible that a desired clock frequency cannot be achieved.For example, Zybo cannot synthesize 133 MHz clock, and when a 133 MHz clock output is requested,an actual output frequency becomes 125 MHz.

zynq# echo 133333333 > /sys/class/fclkcfg/fclk0/ratezynq# cat /sys/class/fclkcfg/fclk0/rate125000000

/sys/class/fclkcfg/<device-name>/round_rate

As described above, not all desired output frequency can be achieved due to the limitations of the PLL.To know an actual output frequency, one can write a desired clock frequency to this file, followed by a read access.

zynq# echo 133333333 > /sys/class/fclkcfg/fclk0/round_ratezynq# cat /sys/class/fclkcfg/fclk0/round_rate133333333 => 125000000zynq# echo  75000000 > /sys/class/fclkcfg/fclk0/round_ratezynq# cat /sys/class/fclkcfg/fclk0/round_rate75000000 => 71428572

/sys/class/fclkcfg/<device-name>/resource

This file is used to change the resource clock. The following example the resource clock is changed to 1.

zynq# echo 1 > /sys/class/fclkcfg/fclk0/resourcezynq# cat /sys/class/fclkcfg/fclk0/resource1

/sys/class/fclkcfg/<device-name>/resource_clks

By reading this file, you can get the names of the resource clocks that you can select.

zynq# cat /sys/class/fclkcfg/fclk0/resource_clksarmpll, ddrpll, iopll

/sys/class/fclkcfg/<device-name>/remove_rate

This file is used to change the output clock frequency when the clock device is removed.The following example selects an output frequency of 100 MHz when the clock device is removed.

zynq# echo 100000000 > /sys/class/fclkcfg/fclk0/remove_ratezynq# cat /sys/class/fclkcfg/fclk0/remove_rate100000000

Writing a negative value to this file will not change the frequency when the clock device is removed.

/sys/class/fclkcfg/<device-name>/remove_enable

This file controls the output status of the clock when the clock device is removed.

Writing 1 will output the clock when the clock device is removed.Writing 0 will stop the clock when the clock device is removed.Writing -1 does not control the clock when the clock device is removed.

/sys/class/fclkcfg/<device-name>/remove_resource

The file specifies a resource clock when the clock device is removed.The file only has an effect if theclocks property has second and subsequent arguments.

Writing a value of 0 or greater changes to the resource clock specified when the clock device was removed.Writing a negative value does not change the resource clock when the clock device is removed.

Changing the clock frequency safely

Example of unsafely frequency change (PLL case)

A PLL (Phase-Locked Loop) frequency synthesizer creates an output clock signal with an accurate frequency by digitally setting the frequency multiplication factor to be added or subtracted from the input clock signal.The PLL generates a clock with the desired frequency by feeding back the output clock signal and adjusting the phase difference with the input clock signal. Generally, it takes some time to adjust the phase, and the output clock frequency becomes unstable during the adjustment. If this clock is output as it is, the circuit running on that clock may malfunction.

Fig.2 ADPLL(All Digital Phase-Locked Loop)

Fig.2 ADPLL(All Digital Phase-Locked Loop)

Example of unsafely frequency change (ZynqMP case)

The FPGA clock generation circuit of ZynqMP has the following structure. The feature is that two independent Dividers are connected.

Fig.3 ZynqMP Clock Generator Block Diagram

Fig.3 ZynqMP Clock Generator Block Diagram

However, if there is a time lag in the time to set each Divider, it is possible to output a clock with an unintended frequency.

For example, suppose that the Primary PLL is set to 1500MHz, pl0_division0 is set to 15, and Pl0_division1 is set to 1. In this case, the frequency of the output clock is 100MHz (=(1500MHz÷15)÷1). Now suppose you change the frequency to 250MHz. If you set pl0_division0 to 1 and then set pl0_division1 to 6 as shown in the following figure, 1500MHz clock is output from the setting of pl0_divison0 to the setting of pl1_division1. And there is a possibility that the circuit that operates with that clock may malfunction.

Fig.4 Example of ZynqMP output an unintended frequency clock

Fig.4 Example of ZynqMP output an unintended frequency clock

Changing the clock frequency safely with fclkcfg

When changing the frequency,fclkcfg stops the clock output before changing the frequency. Then, after changing the frequency, the clock is output. By preventing the output of a clock with an unintended frequency in this way, it is possible to prevent malfunction of the circuit that operates with that clock.

Fig.5 Changing the clock frequency safely with fclkcfg

Fig.5 Changing the clock frequency safely with fclkcfg

Reference

About

FPGA Clock Configuration Device Driver for Linux

Topics

Resources

License

Stars

Watchers

Forks

Packages

No packages published

[8]ページ先頭

©2009-2025 Movatter.jp