S5PV210时钟详解

一、时钟域的概念

1、由于时钟体系复杂,内部外设模块太多,因此把整个内部的时钟划分为3大类。

  • MSYS:CPU(Cortex-A8)、DRAM控制器(DMC0和DMC1),IRAM&IROM的时钟来源。
    • ARMCLK :给CPU内核工作的时钟,也就是我们经常说的主频;
    • HCLK_MSYS:MSYS域的高频时钟,给DMC0和DMC1使用的;
    • PCLK_MSYS:MSYS域的低频时钟;
    • HCLK_IMEM:给iROM和iRAM使用的时钟。
  • DSYS:都是和视频显示,编解码等有关的模块。
    • HCLK_DSYS:DSYS域的高频时钟;
    • PCLK_DSYS:DSYS域的低频时钟。
  • PSYS:和内部各种外设时钟有关的。串口、SD卡接口、USB、GPIO、IIC等。
    • HCLK_PSYS:PSYS域的高频时钟;
    • PCLK_PSYS:PSYS域的低频时钟;
    • SCLK_ONENAND:

因为x210的这些模块的工作的时钟速率差异太大,所以有必要把高速的模块放在一起,相对低速的放在一起。

 

2、时钟来源

S5PV210外部有4个晶振接口,设计板子的时候,可以根据需要来决定接哪几个晶振。接了晶振之后,给开发板上电,相应的模块就能产生振荡,产生原始时钟。原始时钟再经过一系列的筛选开关进入相应的PLL电路,生成倍频后的高频时钟。高频时钟经过分频器,达到芯片内部的各个模块上。

       

3、芯片内部的四个PLL锁相环,倍频用的

 

  • APPL:Cortex-A8和MSYS域时钟的来源。
  • MPLL&EPLL:DSYS和PSYS时钟来源和一些其他的外设模块的时钟。
  • VPLL:Video相关的时钟。

总结:210内部的各个外设都是接在内部AMBA总线上的,AMBA总线有一条高频分支叫AHB,有一条低频总线叫APB,上面的各个模块都是挂在总线上工作的,所以总线的时钟是多少,挂在总线下面的模块时钟就是多少。

4、三星推荐的芯片工作的典型值

  • freq(ARMCLK) = 1000 MHz
  • freq(HCLK_MSYS) = 200 MHz
  • freq(HCLK_IMEM) = 100 MHz
  • freq(PCLK_MSYS) = 100 MHz
  • freq(HCLK_DSYS) = 166 MHz
  • freq(PCLK_DSYS) = 83 MHz
  • freq(HCLK_PSYS) = 133 MHz
  • freq(PCLK_PSYS) = 66 MHz
  • freq(SCLK_ONENAND) = 133 MHz, 166 MHz

 

二、S5PV210时钟分析

 

1、这里面涉及到两个关键的器件

  • MUX:多路选择器,从多个输入中选择一个输入,作为输出。
  • DIV:分频器,将输入的时钟,经过一定的分频,输出到下一个模块。

MUX选择路线,DIV用于设置频率大小。

2、时钟配置所涉及到的关键寄存器

(1)xPLL_LOCK寄存器:

这些寄存器用来控制PLL的锁定周期的,就是PLL锁相环经过多长的时间,可以输出稳定的时钟频率。

(2)xPLL_CONn寄存器

例如APLL_CON0寄存器的各位详解:

  • [31]:用于控制PLL的开关。
  • [29]:只读寄存器,可以从该位,判断我们当前的APLL是否锁定了。
  • MDIV、PDIV和SDIV用于计算APLL倍频后的时钟频率,计算公式如下:

                                  FOUT = MDIV X FIN / (PDIV × 2S^(DIV-1))

例如我们系统推荐APLL的输出为1000MHz的时钟频率,输入为24MHz的晶振,我们设置P、M、S的数值为:

  • MDIV = 125
  • PDIV = 3
  • SDIV = 1

FOUT = 125 * 24/(3*2^0) = 125*8=1000

(3)CLK_SRCn(0-6)
设置始终来源,这个寄存器就是用来控制时钟框图中的对应的MUX器件,选择不同时钟来源。

例如这里CLK_SRC0寄存器:

[0]控制这时钟框图中MUXAPLL这个选择器选择什么作为输出。

(4)CLK_SRC_MASKn寄存器

这个寄存器,类似于在MUX选择器,选择输出之后,加了一个开关,只有开关打开,时钟才能输出到下一个对应的模块中。

(5)CLK_DIVn寄存器

这个寄存器,用来设置分频系数的。

(6)CLK_GATE_X寄存器

这个寄存器的作用类似于CLK_SRC_MASKn寄存器的作用,不过放置的位置是不同的。

(7)CLK_DIV_STAn和CLK_MUX_STAn

查看DIV和MUX的状态是否已经完成还是在进行中。

总结:这么多寄存器,其实还有很多寄存器,但是最重要的有3个寄存器

  • CON控制寄存器,控制PLL的倍频。
  • SRC寄存器,选择走那条路。就是时钟的来源设置。
  • DIV寄存器,分频的设置。

 

三、代码实践

1、时钟设置的步骤

  • 设置各种时钟开关,暂时不使用PLL;
  • 设置锁定时间,设置为最大值;
  • 设置分频
  • 设置PLL,主要是设置PLL的倍频系统,决定有输入端的24M的原始频率可以得到多大的输出频率,我们按默认的设置值,设置为1G;
  • 打开PLL。

2、代码分析

Step1:r0存储的是时钟寄存器的基地址,采用基地址+偏移地址的方式,寻址不同的寄存器。

// 1 设置各种时钟开关,暂时不使用PLL
	ldr	r1, =0x0
	// 芯片手册P378 寄存器CLK_SRC:Select clock source 0 (Main)
	str	r1, [r0, #CLK_SRC0_OFFSET]

将该寄存器设置为0,因为一开始,我们的时钟来源,以及时钟的分频系数,都没有初始化,所以一开始不能使用PLL,使用的频率是外部晶振的实际频率,等我们初始化好了相关寄存器,才打开PLL,然后系统才能按照我们设定的频率工作。

 

Step2:

	// 2 设置锁定时间,使用默认值即可
	// 设置PLL后,时钟从Fin提升到目标频率时,需要一定的时间,即锁定时间
	ldr	r1,	=0x0000FFFF					
	str	r1,	[r0, #APLL_LOCK_OFFSET]				
	str r1, [r0, #MPLL_LOCK_OFFSET]	 

Step3:

	// 3 设置分频
	// 清bit[0~31]
	ldr r1, [r0, #CLK_DIV0_OFFSET]					
	ldr	r2, =CLK_DIV0_MASK					
	bic	r1, r1, r2						//清零需要设置的那几位
	ldr	r2, =0x14131440						
	orr	r1, r1, r2
	str	r1, [r0, #CLK_DIV0_OFFSET]

对应的结果就是前面时钟框图中,写的数字。就是最后设置的个分频器的结果。

Step4:

// 4 设置PLL
	// FOUT = MDIV*FIN/(PDIV*2^(SDIV-1))=0x7d*24/(0x3*2^(1-1))=1000 MHz
	ldr	r1, =APLL_VAL						
	str	r1, [r0, #APLL_CON0_OFFSET]
	// FOUT = MDIV*FIN/(PDIV*2^SDIV)=0x29b*24/(0xc*2^1)= 667 MHz
	ldr	r1, =MPLL_VAL						
	str	r1, [r0, #MPLL_CON_OFFSET]

设置MPLL和APLL的倍频系数。

Step5:

	// 5 设置各种时钟开关,使用PLL
	ldr	r1, [r0, #CLK_SRC0_OFFSET]
	ldr	r2, =0x10001111
	orr	r1, r1, r2
	str	r1, [r0, #CLK_SRC0_OFFSET]

经过前面几步,我们已经设置好的分频系数和时钟来源的选择,打开了PLL,所以这里选择PLL的输出时钟,作为系统相关模块的时钟频率。

 

完整的汇编代码:

// 时钟控制器基地址
#define ELFIN_CLOCK_POWER_BASE		0xE0100000	

// 时钟相关的寄存器相对时钟控制器基地址的偏移值
#define APLL_LOCK_OFFSET		0x00		
#define MPLL_LOCK_OFFSET		0x08

#define APLL_CON0_OFFSET		0x100
#define APLL_CON1_OFFSET		0x104
#define MPLL_CON_OFFSET			0x108

#define CLK_SRC0_OFFSET			0x200
#define CLK_SRC1_OFFSET			0x204
#define CLK_SRC2_OFFSET			0x208
#define CLK_SRC3_OFFSET			0x20c
#define CLK_SRC4_OFFSET			0x210
#define CLK_SRC5_OFFSET			0x214
#define CLK_SRC6_OFFSET			0x218
#define CLK_SRC_MASK0_OFFSET	0x280
#define CLK_SRC_MASK1_OFFSET	0x284

#define CLK_DIV0_OFFSET			0x300
#define CLK_DIV1_OFFSET			0x304
#define CLK_DIV2_OFFSET			0x308
#define CLK_DIV3_OFFSET			0x30c
#define CLK_DIV4_OFFSET			0x310
#define CLK_DIV5_OFFSET			0x314
#define CLK_DIV6_OFFSET			0x318
#define CLK_DIV7_OFFSET			0x31c

#define CLK_DIV0_MASK			0x7fffffff

// 这些M、P、S的配置值都是查数据手册中典型时钟配置值的推荐配置得来的。
// 这些配置值是三星推荐的,因此工作最稳定。如果是自己随便瞎拼凑出来的那就要
// 经过严格测试,才能保证一定对。
#define APLL_MDIV      	 		0x7d		// 125
#define APLL_PDIV       		0x3
#define APLL_SDIV       		0x1

#define MPLL_MDIV				0x29b		// 667
#define MPLL_PDIV				0xc
#define MPLL_SDIV				0x1

#define set_pll(mdiv, pdiv, sdiv)	(1<<31 | mdiv<<16 | pdiv<<8 | sdiv)
#define APLL_VAL			set_pll(APLL_MDIV,APLL_PDIV,APLL_SDIV)
#define MPLL_VAL			set_pll(MPLL_MDIV,MPLL_PDIV,MPLL_SDIV)


.global clock_init
clock_init:
	ldr	r0, =ELFIN_CLOCK_POWER_BASE
	
	// 1 设置各种时钟开关,暂时不使用PLL
	ldr	r1, =0x0
	// 芯片手册P378 寄存器CLK_SRC:Select clock source 0 (Main)
	str	r1, [r0, #CLK_SRC0_OFFSET]				

	// 2 设置锁定时间,使用默认值即可
	// 设置PLL后,时钟从Fin提升到目标频率时,需要一定的时间,即锁定时间
	ldr	r1,	=0x0000FFFF					
	str	r1,	[r0, #APLL_LOCK_OFFSET]				
	str r1, [r0, #MPLL_LOCK_OFFSET]	 				

	// 3 设置分频
	// 清bit[0~31]
	ldr r1, [r0, #CLK_DIV0_OFFSET]					
	ldr	r2, =CLK_DIV0_MASK					
	bic	r1, r1, r2						//清零需要设置的那几位
	ldr	r2, =0x14131440						
	orr	r1, r1, r2
	str	r1, [r0, #CLK_DIV0_OFFSET]

	// 4 设置PLL
	// FOUT = MDIV*FIN/(PDIV*2^(SDIV-1))=0x7d*24/(0x3*2^(1-1))=1000 MHz
	ldr	r1, =APLL_VAL						
	str	r1, [r0, #APLL_CON0_OFFSET]
	// FOUT = MDIV*FIN/(PDIV*2^SDIV)=0x29b*24/(0xc*2^1)= 667 MHz
	ldr	r1, =MPLL_VAL						
	str	r1, [r0, #MPLL_CON_OFFSET]

	// 5 设置各种时钟开关,使用PLL
	ldr	r1, [r0, #CLK_SRC0_OFFSET]
	ldr	r2, =0x10001111
	orr	r1, r1, r2
	str	r1, [r0, #CLK_SRC0_OFFSET]

	mov	pc, lr       //函数返回

 

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值