Clock overview

来自百问网嵌入式Linux wiki
Zhouyuebiao讨论 | 贡献2020年5月7日 (四) 23:45的版本 (创建页面,内容为“This article gives information about the Linux® Clock framework. <br> Clocks are generally provided by internal/external oscillators or PLLs. <br> They can pass thr…”)
(差异) ←上一版本 | 最后版本 (差异) | 下一版本→ (差异)

This article gives information about the Linux® Clock framework.
Clocks are generally provided by internal/external oscillators or PLLs.
They can pass through a gate, a muxing, a divider or a multiplier.
All peripheral clocks are organized as a tree.

All these elements are managed by the Common Clock framework.

Framework purpose

The purpose of this article is to introduce the Common Clock Framework. It provides general information and, based on examples, explains how to use it.

Linux Common Clock framework offers a generic API for configuring and controlling the different system clocks.
Drivers can easily enable/disable clocks, change their frequency, change the parent of the clocks associated to peripherals without any knowledge of the clock characteristics.
All clock tree specificities (such as clock source selection, muxing, dividor and gate) are abstracted by the Common Clock framework and the associated system clock driver.

System overview

错误: 图像不正确或者不存在

Component description

  • foo driver: any peripheral driver which needs to control and activate clock(s) associated to a given peripheral.
  • Clock core: the Common Clock framework is the generic Linux kernel interface that controls the clock nodes available in the system.
It features two generic interfaces:
- The upper interface unifies the definition and control of the clocks for all Linux platforms. This agnostic API is used by peripheral drivers for configuring and controlling the clocks associated to a specific peripheral.
- The lower interface allows the registration of platform specific functions in order to manage a platform specific clock tree.
  • clk-stm32mp1: stm32mp1 specific clock driver that supports RCC clocks.
  • RCC: reset and clock controler RCC.


API description

Documentation on the Common Clock framework can be found in the kernel documentation folder: https://www.kernel.org/doc/Documentation/driver-api/clk.rst

  • Main kernel clock API
  • devm_get_clk(): looks up and obtains from the device tree a managed reference to a clock producer, to a root clock or to a clock node.
  • clk_prepare_enable(): selects a parent clock, configures the corresponding multiplexor and dividor, and enables the clock gating.
  • clk_disable_unprepare(): unprepares and gate a clock.
  • clk_get_rate(): obtains the current frequency (in Hz) for a given clock.
  • clk_set_rate(): sets the frequency for a given clock. If a clock has several parents, the clock framework can change the parent in order to obtain a better frequency.
  • clk_get_parent(): gets the parent clock source for a given clock
  • clk_set_parent(): sets the parent clock source for a given clock
  • ...

Configuration

Kernel configuration

By default the Common Clock framework is activated in the kernel configuration.

Device tree configuration

A detailed device tree configuration is described in Clock device tree configuration.

How to use the Common Clock framework

This paragraph describes how a standard peripheral driver can retrieve its clock configuration from the device tree and configure it.

The clocks associated to a given peripheral are declared in the device tree as described in https://www.kernel.org/doc/Documentation/devicetree/bindings/clock/clock-bindings.txt.

Specific platform define statements that abstract hardware clock offsets are defined in dt-bindings/clock/stm32mp1-clks.h header file.

Below an example of clock association to a foo driver:

	foo: foo@adcdefgh {
               compatible = "foo-driver";
               ...
		clocks = <&rcc FOO_K>;
               ...
	};

Before using the clock specified in the device tree node, the foo driver has to request it at probe execution.

	static int foo_probe(struct platform_device *pdev)
	{
		struct clk *clk;
		...
		clk = devm_clk_get(&pdev->dev, NULL);
		if (IS_ERR(clk)) {
			ret = PTR_ERR(clk);
			dev_err(&pdev->dev, "clk get failed: %d\n", ret);
			goto err_master_put;
		}
		...
	}

The clock can then be configured and enabled using the Common Clock framework API.

If the peripheral needs several clocks, a name must be associated to each clock handle in the device tree node. The specified names must be used by the driver to retrieve the corresponding pointer for each clock.

Below an example of foo driver managing 2 clocks:

	foo: foo@abcdefgh {
		compatible = "foo-driver";

		clocks = <&rcc FOO1_K>, <&rcc FOO2_K>;
		clock-names = "foo1", "foo2";
	};
	static int foo_probe(struct platform_device *pdev)
	{
		priv->foo1clk = devm_clk_get(&pdev->dev, "foo1");
		if (IS_ERR(priv->foo1clk)) {
			ret = PTR_ERR(priv->foo1clk);
			if (ret != -ENOENT) {
				dev_err(&pdev->dev, "Can't get 'foo1' clock\n");
				return ret;
			}
		}
  		priv->foo2clk = devm_clk_get(&pdev->dev, "foo2")';
		if (IS_ERR(priv->foo2clk)) {
			ret = PTR_ERR(priv->foo2clk);
			if (ret != -ENOENT) {
				dev_err(&pdev->dev, "Can't get 'foo2' clock\n");
				return ret;
			}
		}
 	 }
	ret = clk_prepare_enable(priv->foo1clk);
	if (ret < 0) {
		dev_err(dev, "foo1 clk enable failed\n");
		goto err_bclk_disable;
	}

How to trace and debug the framework

Tracing using dynamic debug

By default, no kernel log showing the clock activity. However the user can enable the dynamic debug for the clock framework driver:

Board $> dmesg -n8
Board $> echo "file drivers/clk/* +p" > /sys/kernel/debug/dynamic_debug/control

Refer to dynamic debug for more details.

How to monitor with debugfs

Information on clocks are available in 调试文件系统(debugfs) interface located in the '/sys/kernel/debug/clk' directory.

It helps viewing all the clocks registered in tree format.

Show clock tree:

Board $> cat /sys/kernel/debug/clk/clk_summary

   clock                         enable_cnt  prepare_cnt        rate   accuracy   phase
----------------------------------------------------------------------------------------
clk-ext-camera                           0            0    24000000          0 0  
ck_usbo_48m                              1            1    48000000          0 0  
   usbo_k                                1            1    48000000          0 0  
ck_dsi_phy                               0            0           0          0 0  
   dsi_k                                 0            0           0          0 0  
i2s_ckin                                 0            0           0          0 0  
clk-csi                                  0            0     4000000          0 0  
   ck_csi                                0            0     4000000          0 0  
      rng2_k                             0            0     4000000          0 0  
      rng1_k                             0            0     4000000          0 0  
clk-lsi                                  1            1       32000          0 0  
   ck_lsi                                1            1       32000          0 0  
      dac12_k                            0            0       32000          0 0  
clk-lse                                  1            1       32768          0 0  
   ck_lse                                1            1       32768          0 0  
      ck_rtc                             1            1       32768          0 0  
      cec_k                              0            0       32768          0 0  
clk-hsi                                  1            1    64000000          0 0  
   clk-hsi-div                           1            1    64000000          0 0  
      ck_hsi                             2            2    64000000          0 0  
         ck_mco1                         0            0    64000000          0 0  
         uart8_k                         0            0    64000000          0 0  
         uart7_k                         0            0    64000000          0 0  
         uart6_k                         0            0    64000000          0 0  
         uart5_k                         0            0    64000000          0 0  
         uart4_k                         1            1    64000000          0 0  
         usart3_k                        0            0    64000000          0 0  
         usart2_k                        0            0    64000000          0 0  
         usart1_k                        0            0    64000000          0 0  
         i2c6_k                          0            0    64000000          0 0  
         i2c4_k                          1            1    64000000          0 0  
         i2c5_k                          0            0    64000000          0 0  
         i2c3_k                          0            0    64000000          0 0  
         i2c2_k                          0            0    64000000          0 0  
         i2c1_k                          0            0    64000000          0 0  
         spi6_k                          0            0    64000000          0 0  
         spi5_k                          0            0    64000000          0 0  
         spi4_k                          0            0    64000000          0 0  
clk-hse                                  1            1    24000000          0 0  
   ck_hse                                6            6    24000000          0 0  
      ck_hse_rtc                         0            0     1000000          0 0  
      stgen_k                            1            1    24000000          0 0  
      usbphy_k                           1            1    24000000          0 0  
      ck_per                             0            0    24000000          0 0  
         adc12_k                         0            0    24000000          0 0  
      ref4                               1            1    24000000          0 0  
         pll4                            1            1   508000000          0 0  
            pll4_r                       0            0    56444445          0 0  
            pll4_q                       1            1    50800000          0 0  
               ltdc_px                   1            1    50800000          0 0  
               dsi_px                    0            0    50800000          0 0  
               fdcan_k                   0            0    50800000          0 0  
            pll4_p                       0            0    56444445          0 0  
      ref3                               1            1    24000000          0 0  
         pll3                            2            3   786431640          0 0  
            pll3_r                       1            1    98303955          0 0  
               sdmmc3_k                  0            0    98303955          0 0  
               sdmmc2_k                  0            0    98303955          0 0  
               sdmmc1_k                  1            1    98303955          0 0  
            pll3_q                       0            3    49151978          0 0  
               adfsdm_k                  0            0    49151978          0 0  
               sai4_k                    0            1    49151978          0 0  
               sai3_k                    0            0    49151978          0 0  
               sai2_k                    0            2    49151978          0 0  
               sai1_k                    0            0    49151978          0 0  
               spi3_k                    0            0    49151978          0 0  
               spi2_k                    0            0    49151978          0 0  
               spi1_k                    0            0    49151978          0 0  
               spdif_k                   0            1    49151978          0 0  
            pll3_p                       1            1   196607910          0 0  
               ck_mcu                    6           19   196607910          0 0  
                  dfsdm_k                0            1   196607910          0 0  
                  gpiok                  0            1   196607910          0 0  
                  gpioj                  0            1   196607910          0 0  
                  gpioi                  0            1   196607910          0 0  
                  gpioh                  0            1   196607910          0 0  
                  gpiog                  0            1   196607910          0 0  
                  gpiof                  0            1   196607910          0 0  
                  gpioe                  0            1   196607910          0 0  
                  gpiod                  0            1   196607910          0 0  
                  gpioc                  0            1   196607910          0 0  
                  gpiob                  0            1   196607910          0 0  
                  gpioa                  0            1   196607910          0 0  
                  ipcc                   2            2   196607910          0 0  
                  hsem                   0            0   196607910          0 0  
                  crc2                   0            0   196607910          0 0  
                  rng2                   0            0   196607910          0 0  
                  hash2                  0            0   196607910          0 0  
                  cryp2                  0            0   196607910          0 0  
                  dcmi                   0            0   196607910          0 0  
                  sdmmc3                 0            0   196607910          0 0  
                  usbo                   0            0   196607910          0 0  
                  adc12                  0            0   196607910          0 0  
                  dmamux                 1            1   196607910          0 0  
                  dma2                   1            1   196607910          0 0  
                  dma1                   1            1   196607910          0 0  
                  pclk3                  1            1    98303955          0 0  
                     lptim5_k            0            0    98303955          0 0  
                     lptim4_k            0            0    98303955          0 0  
                     lptim3_k            0            0    98303955          0 0  
                     lptim2_k            0            0    98303955          0 0  
                     hdp                 0            0    98303955          0 0  
                     pmbctrl             0            0    98303955          0 0  
                     tmpsens             0            0    98303955          0 0  
                     vref                0            0    98303955          0 0  
                     syscfg              1            1    98303955          0 0  
                     sai4                0            0    98303955          0 0  
                     lptim5              0            0    98303955          0 0  
                     lptim4              0            0    98303955          0 0  
                     lptim3              0            0    98303955          0 0  
                     lptim2              0            0    98303955          0 0  
                  pclk2                  0            0    98303955          0 0  
                     fdcan               0            0    98303955          0 0  
                     dfsdm               0            0    98303955          0 0  
                     sai3                0            0    98303955          0 0  
                     sai2                0            0    98303955          0 0  
                     sai1                0            0    98303955          0 0  
                     usart6              0            0    98303955          0 0  
                     spi5                0            0    98303955          0 0  
                     spi4                0            0    98303955          0 0  
                     spi1                0            0    98303955          0 0  
                     tim17               0            0    98303955          0 0  
                     tim16               0            0    98303955          0 0  
                     tim15               0            0    98303955          0 0  
                     tim8                0            0    98303955          0 0  
                     tim1                0            0    98303955          0 0  
                     ck2_tim             0            0   196607910          0 0  
                        tim17_k           0            0   196607910          0 0  
                        tim16_k           0            0   196607910          0 0  
                        tim15_k           0            0   196607910          0 0  
                        tim8_k           0            0   196607910          0 0  
                        tim1_k           0            0   196607910          0 0  
                  pclk1                  0            2    98303955          0 0  
                     lptim1_k            0            0    98303955          0 0  
                     mdio                0            0    98303955          0 0  
                     dac12               0            1    98303955          0 0  
                     cec                 0            0    98303955          0 0  
                     spdif               0            0    98303955          0 0  
                     i2c5                0            0    98303955          0 0  
                     i2c3                0            0    98303955          0 0  
                     i2c2                0            0    98303955          0 0  
                     i2c1                0            0    98303955          0 0  
                     uart8               0            0    98303955          0 0  
                     uart7               0            0    98303955          0 0  
                     uart5               0            0    98303955          0 0  
                     uart4               0            0    98303955          0 0  
                     usart3              0            0    98303955          0 0  
                     usart2              0            0    98303955          0 0  
                     spi3                0            0    98303955          0 0  
                     spi2                0            0    98303955          0 0  
                     lptim1              0            0    98303955          0 0  
                     tim14               0            0    98303955          0 0  
                     tim13               0            0    98303955          0 0  
                     tim12               0            0    98303955          0 0  
                     tim7                0            0    98303955          0 0  
                     tim6                0            0    98303955          0 0  
                     tim5                0            0    98303955          0 0  
                     tim4                0            0    98303955          0 0  
                     tim3                0            0    98303955          0 0  
                     tim2                0            0    98303955          0 0  
                     ck1_tim             0            1   196607910          0 0  
                        tim14_k           0            0   196607910          0 0  
                        tim13_k           0            0   196607910          0 0  
                        tim12_k           0            0   196607910          0 0  
                        tim7_k           0            0   196607910          0 0  
                        tim6_k           0            1   196607910          0 0  
                        tim5_k           0            0   196607910          0 0  
                        tim4_k           0            0   196607910          0 0  
                        tim3_k           0            0   196607910          0 0  
                        tim2_k           0            0   196607910          0 0  
      ref1                               2            2    24000000          0 0  
         pll2                            2            2   533000000          0 0  
            pll2_r                       1            1   533000000          0 0  
            pll2_q                       0            0   533000000          0 0  
               gpu_k                     0            0   533000000          0 0  
            pll2_p                       1            1   266500000          0 0  
               ck_axi                    9           10   266500000          0 0  
                  ck_trace               0            0   133250000          0 0  
                  ck_sys_dbg             0            0   266500000          0 0  
                  qspi_k                 1            1   266500000          0 0  
                  fmc_k                  0            0   266500000          0 0  
                  ethstp                 0            0   266500000          0 0  
                  usbh                   1            1   266500000          0 0  
                  crc1                   0            0   266500000          0 0  
                  sdmmc2                 0            0   266500000          0 0  
                  sdmmc1                 0            0   266500000          0 0  
                  qspi                   0            0   266500000          0 0  
                  fmc                    0            0   266500000          0 0  
                  ethmac                 1            1   266500000          0 0  
                  ethrx                  1            1   266500000          0 0  
                  ethtx                  1            1   266500000          0 0  
                  gpu                    0            0   266500000          0 0  
                  mdma                   1            1   266500000          0 0  
                  bkpsram                0            0   266500000          0 0  
                  rng1                   0            0   266500000          0 0  
                  hash1                  0            0   266500000          0 0  
                  cryp1                  0            0   266500000          0 0  
                  gpioz                  0            1   266500000          0 0  
                  tzc2                   0            0   266500000          0 0  
                  tzc1                   0            0   266500000          0 0  
                  pclk5                  1            1    66625000          0 0  
                     stgen               0            0    66625000          0 0  
                     bsec                0            0    66625000          0 0  
                     iwdg1               0            0    66625000          0 0  
                     tzpc                0            0    66625000          0 0  
                     rtcapb              2            2    66625000          0 0  
                     usart1              0            0    66625000          0 0  
                     i2c6                0            0    66625000          0 0  
                     i2c4                0            0    66625000          0 0  
                     spi6                0            0    66625000          0 0  
                  pclk4                  1            1   133250000          0 0  
                     stgenro             0            0   133250000          0 0  
                     usbphy              0            0   133250000          0 0  
                     iwdg2               1            1   133250000          0 0  
                     dsi                 0            0   133250000          0 0  
                     ltdc                0            0   133250000          0 0  
         pll1                            1            1   650000000          0 0  
            pll1_p                       1            1   650000000          0 0  
               ck_mpu                    1            1   650000000          0 0  
                  ck_mco2                0            0   650000000          0 0  
      clk-hse-div2                       0            0    12000000          0 0  
ethptp_k                                 0            0           0          0 0  
ethck_k

In addition, each clock has a dedicated directory in which you can find the information such as prepare count, enable count, rate and accuracy:

Board $>/sys/kernel/debug/clk# cd usart2_k
Board $>/sys/kernel/debug/clk/usart2_k# ls
clk_accuracy      clk_flags           clk_phase             clk_prepare_count
clk_enable_count  clk_notifier_count  clk_possible_parents  clk_rate

Additional information, such as flags, notifier count and possible parents (for clocks with multiple parents) are also available. Just execute a 'cat' command to display them.

Board $>:/sys/kernel/debug/clk/usart2_k# cat clk_possible_parents 
pclk1 pll4_q ck_hsi ck_csi ck_hse

Source code location

stm32mp1 clock driver source [1]
clock dt-binding interface [2]

To go further

See "how to build a clock tree" in STM32MP15_clock_tree.

References


<securetransclude src="ProtectedTemplate:ArticleBasedOnModel" params="Framework overview article model"></securetransclude> <securetransclude src="ProtectedTemplate:PublicationRequestId" params="10342 | 2019-01-21 | AnneJ"></securetransclude>