目录
1、System Clock Diagram
2、CPU Clock
3、DDR Clock
4、SDIO/SMC/SPI/QSPI/UART Clock
5、USB/Etherent/CAN Clock
6、GPIO/I2C Clock
7、PL Clock
7、Clock Control Registers
在介绍完《ZYNQ 启动分析》和《ZYNQ 复位子系统》后,我认为需要对 ZYNQ 的时钟树进行了解,ZYNQ 时钟的来源,以及 PLLs,Clock Gating,等,这样一方面能够直观的知道并控制 CPU 时钟频率,对 Power 控制能够起到指导作用,同时能够更好的对系统进行认识并优化,而且在对外设编程的时候,时钟分频也一定需要配置,所以需要了解整个时钟;(先别急着写代码,系统每个模块跑多少 HZ 都不清除,这合适么,哈哈....)
时钟树框架如下所示:
A、看到最左边外部晶振输入 PS_CLK,直接作用到 3 个内部 PLLs:ARM PLL、I/O PLL、DDR PLL;
B、左下根据锁存到的 boot strap pin 来判断,在启动过程是否需要 Bypass PLL(注意:这里是否 Bypass 只有 1 bit,也就是说,启动阶段的 Bypass,要 Bypass,就会同时 Bypass 这 3 个 PLLs,要么都启用。但是在启动完成后,通过配置 ARM_PLL_CTRL、DDR_PLL_CTRL、IO_PLL_CTRL 寄存器,可以单独控制 Bypass 3 个 PLL 中的哪一个或哪几个,);
C、时钟经过 PLL 后,直到 PLL Lock 信号后,输出到后级的 MUX 选择器,上面这个 MUX 选择器选择哪一路时钟作为系统 CPU 的时钟域,下面这个 MUX 选择哪个 PLL 出来的时钟作用到后级外设部分;
D、每一路时钟都接 6-bit 可编程的分频器,按照具体的需要进行时钟分频,分别直接供给 CPU Clock Domain,DDR Clock Domain,Peropherals Clock Domain 和 PL 端
E、当然,每一路都有 Clock Gating,门控时钟,来按照需要进行时钟的开启或者关闭的控制,以按需配置达到功耗的最佳;
系统级的时钟相互框架如下所示:
可以看到细分了 CPU Clock domain,DDR Clock,FPGA
ZYNQ 中 CPU Clock 信号确定如下所示,CPU 时钟域中,根据使用地方不同,存在 4 个时钟:
CPU_1x
CPU_2x
CPU_3x2x
CPU_6x4x
注意,这几路时钟的频率不同,但是还是属于同一个时钟域,也就是同步的;
现在我们要来解释一下 CPU_1x、CPU_2x、CPU_3x2x、以及 CPU_6x4x 的含义;
CPU 时钟域提供了两种可选的时钟模式:
6:2:1
4:2:1
这是什么意思呢?上一个图就知道了:
看到了吧:
在 6:2:1 模式下如果 CPU_1x 为 133MHz,那么 CPU_2x 为它的 2 倍,即 266MHz,CPU_3x2x 为 133MHz 的 3 倍,即 399MHz(≈400MHz),CPU_6x4x 是 133MHz 的 6 倍,即 798MHz(≈800MHz)
在 4:2:1 模式下如果 CPU_1x 为 150MHz,那么 CPU_2x 为它的 2 倍,即 300MHz,CPU_3x2x 为 150MHz 的 2 倍,即 300MHz,CPU_6x4x 是 133MHz 的 4 倍,即 600 MHz
而且每一路的时钟作用域也写清楚了,最高频率时钟 CPU_6x4x 作用到 CPU 的主频,SCU 单元(Cache 一致性)等;CPU_3x2x 时钟用于 APU 的 Timers;CPU_2x 用于外设,中央互联单元时钟等;CPU_1x 用于外设 AHB 和 APB 接口总线;
现在回到 CPU Clock 的第一个图:
1、最左边的 3 个 PLLs 经过两个 MUX 选择器,输出到后级,这个选择器的输出由系统控制寄存器(System Level Control Registers 即 slcr 寄存器组)的 ARM_CLK_CTRL 寄存器的 bit 4 和 bit 5 决定(slcr.ARM_CLK_CTRL[SRCSEL]);
2、PLL 后的时钟进入 6-bit 的分频器,即 ARM_CLK_CTRL 的 bit[13:8] 来确定时钟分频(slcr.ARM_CLK_CTRL[DIVSOR]);
3、分频器的输出作用到 Clock Ratio Generator 模块,这个模块的输入最上面有个 CLK_621_TRUE[0],CLK_621_TRUE[0] 如果配置为 0,那么使用的是 4:2:1 的模式,如果为 1,那么是 6:2:1
4、Clock Ratio Generator 模块的 4 路输出分别接了 4 个与门,用来做 Clock Gate,也就是门控时钟,可以通过 ARM_CLK_CTRL 的 bit [24],bit [25],bit [26],bit [27] 分别控制是否使能对应的时钟输出;
这里官方给出了一个注意:
为了改善 CPU/DDR 的高频时钟的质量,在 slcr.ARM_CLK_CTRL[DIVSOR] 分频系数最好使用偶数;
所有的 CPU Clock domain 的时钟,都是同步的;
AMBA Bus 的时钟来源如下所示,都是 CPU 域的,也就是 CPU 通过 AMBA Bus 访问外设的寄存器的时钟,如果要使用该外设的话,需要开启对应的 AMBA Bus 的时钟;可以看到,他们可以单独控制开启或者关闭;
系统范围的时钟配置示例如下,两个例子,一个是外部输入 33.33MHz 另一个是外部输入 50MHz,使用的 6:2:1的配比模式:
这张表中,假定了各个 PLL 的倍频系数:
第一个里面假定倍频系数为 ARM_PLL=40、DDR PLL=32、I/O PLL=30;
第一个里面假定倍频系数为 ARM_PLL=20、DDR PLL=16、I/O PLL=20;
其实呢,这些个 PLL 的倍频系数是可以配置的,在 slcr.ARM_PLL_CTRL[PLL_FDIV]、slcr.DDR_PLL_CTRL[PLL_FDIV]、slcr.IO_PLL_CTRL[PLL_FDIV] 寄存器进行配置;
DDR 的时钟如下所示,由 DDR 的 PLL 倍频而来,经过两个可配置的 6-bits 寄存器来进行分频,在输出到 Clock Gate 门控来控制 DDR_2x 和 DDR_3x 是否输出;
典型的 SDIO/SMC/SPI/QSPI/UART 外设部分的时钟如下所示:
上面的一个图适用 SDIO/SMC/SPI/QSPI/UART 这几个外设,不过是不同的外设,配置的 SRCSEL 寄存器、分频寄存器不一样;
他们都有自己的时钟电路,详细参考 UG585
输入时钟域为 CPU_x1 更多的细节参考 UG585 中对应模块的设计图;
PL 端可以接受来自 PS 端的 4 路时钟输入,这 4 路时钟相互异步,下面是它的配置图;
每一路时钟通过选择时钟源和分频系数,最后得到独立的 4 路时钟:
FCLK 0
FCLK 1
FCLK 2
FCLK 3