本文介绍: TC3xx芯片的Clock System功能详解

目录

前言

正文

1.时钟源

1.1 有源晶振和无源晶振

1.1.1 无源晶振

1.1.2 有源晶振

1.1.3 有源晶振和无源晶振的区别

1.1 振荡器电路(OSC)

1.1.1外部输入时钟模式

1.1.2 外部晶体 / 陶瓷谐振器模式

1.1.3 OSC控制寄存器

1.1.4 配置OSC

1.1.5 OSC看门狗

1.1.6 配置SMU和时钟相关的Alarm

1.2 备用时钟

1.3 OSC实际应用配置

2. 时钟倍频PLL

2.1 特点

2.2 系统时钟锁相环PLL

2.3 系统PLL寄存器

2.4 外设时钟锁相环PLL

2.5 PLL实际应用配置

3. 时钟分配(CCU)

3.1 时钟控制单元

3.2 以MCCAN为例配置时钟频率

4. 总结


前言

时钟好比MCU的心跳,只有时钟正常了,MCU的核及外设才能正常工作。从源头到系统到外设理解每一个时钟的来源及其具体值才能方便后面理解MCAL的GPT,PWM,ICU等模块配置(MCAL模块中的Tick数就是基于模块时钟的)。本系列文章就来详细介绍TC3xx芯片时钟系统及其具体配置

缩略词

简写

全称

OSC

Oscillator Circuit

PLL

Phase-Locked Loop

DCO

Digitally Controlled Oscillator

正文

1.时钟

晶振好比人的心脏,晶振产生的时钟脉冲好比心脏产生的心跳,所以,晶振对于MCU来讲必不可少,晶振没有起振,MCU必定无法工作。

1.1 有源晶振和无源晶振

无源晶振又名“无源晶体”、“石英晶体谐振器”,英文名Crystal或Crystal Resonator。有源晶振又称“石英晶体振荡器”,英文名Crystal Oscillator。

1.1.1 无源晶振

无源晶振一般有两个引脚,无极性。它自身无法振动, 一般外部都接有两个10-22PF的瓷片电容。

无源晶振参考电路无源晶振信号质量较差,通常需要精确匹配外围电路(用于信号匹配的电容、电感、电阻等),更换不同频率的晶体时周边配置 电路需要做相应的调整。一般建议采用精度较高的石英晶体。

1.1.2 有源晶振

有源晶振有4只引脚,是一个完整的振荡器,其中除了石英晶体外,还有晶体管和阻容元件,因此体积较大。有源晶振的封装有4个引脚,分别为VCC (电压)、GND (地)、OUT (时钟信号输出)、NC (空脚)。

有源晶振参考电路有源晶振不需要CPU的内部振荡器,信号稳定,质量较好,且连接方式

简单(主要做好电源滤波,通常使用一个电容和电感构成滤波网络,输出端用一个小阻值的

电阻过滤信号即可) , 不需要复杂的配置电路

 

1.1.3 有源晶振和无源晶振的区别

1、有源晶振比较, 但是有源晶振自身就能振动。无论无源晶振, 还是有源晶振, 都有自身的优点和缺点所在, 若考虑产品成本, 建议可以选择无源晶振电路; 若考虑产品性能, 建议选择有源晶振电路, 省时方便也能保证产品性能。

2、无源晶振最高精度为5ppm, 而有源晶振的精度则可以达到0. 1ppm。精度越高, 频率稳定性也更好。有源晶振在稳定性上要胜过无源晶振, 但也有自身小小的缺陷, 有源晶振的信号电平是固定, 所以需要选择好合适输出电平,灵活性较差。

3、有源晶振一般4个脚,1个电源,1个接地,1个信号输出端,1个NC (空脚)。有个点标记的为1脚, 按逆时针(管脚向下)分别为2、3、4。

4、无源晶振有2个引脚,要借助于外部的时钟电路(接到主IC内部的振荡电路) 才能产生振荡信号, 自身无法振荡。

参考文档

http://www.interquip-china.com/?c=msg&id=2553&bd_vid=6323699165298490610

1.1 振荡器电路(OSC)

振荡器电路是一种 Pierce 振荡器(Pierce oscillator),设计用于与外部晶体(external crystal) / 陶瓷谐振器(ceramic resonator)或外部稳定时钟源(external stable clock source)配合使用。 该电路由一个反向放大器组成, XTAL1 作为输入, XTAL2 作为带有集成反馈电阻的输出。

1.1.1外部输入时钟模式

使用外部输入时钟模式时,外部时钟信号连接到OSC模块的XTAL1引进,XTAL2引脚保持悬空状态

Figure 1 AURIX™ TC3xx Platform Direct Clock Input

如果在正常模式直接使用外部时钟提供的时钟信号时,不使用外部晶体 / 陶瓷谐振器并绕过振荡器,则输入频率需要等于或大于 PLL 的 DCO 输入频率 (该值在Data sheet中列出)。

1.1.2 外部晶体 / 陶瓷谐振器模式

Figure 2 显示了两种工作模式的推荐外部电路:外部晶体 / 陶瓷谐振器模式 (带和不带外部组件)。

Figure 2 External Circuitry for Crystal / Ceramic Resonator operation

1.1.3 OSC控制寄存器

Oscillator Circuit Control Register用来配置OSC模式和晶振频率。主要用到配置位域为:

OSCCON.MODE 配置晶振模式

OSCCON.OSCVAL 配置晶振频率

OSCCON.PLLLV 标识OSC频率是否可用

OSCCON.PLLHV标识OSC频率是否可用

1.1.4 配置OSC

只有配置了OSC后,外部晶振才能作为时钟源工作。

Power-on复位后OSC模块是被disabled需要重新配置。在任何其他重置过程中和之后,振荡器不会受到影响,并按照先前配置的方式工作,这种情况下不需要重新配置。

可以通过SSW来配置OSC,也可以在App中直接配置OSC。值得注意的是:OSCCON寄存器是受Endinit保护的,配置的时候需要解锁Endinit。

参考文档【TC3xx芯片】TC3xx芯片的Endinit功能详解

1.1.5 OSC看门狗

通过配置 SYSPLLCON0.Insel = 01B ,选择振荡器时钟作为看门狗的源。

系统 PLL 结合使用时,将实施监控功能定义功能的目的是检测外部晶体 / 陶瓷谐振器的严重故障系统可以检测到时钟输入丢失输入频率过高 (在较高谐波上运行)。

振荡器监视程序监视来自 OSC 的传入时钟频率 fOSC。 稳定且定义输入频率是操作的强制要求。 因此,每次系统重置后都会自动选择模式

预期输入频率 fOSC 通过位字段 OSCCON.OSCVAL 选择。 OSC WDT 检查频率是否过低或过高。

fOSC = OSCCON.OSCVAL – 1 + 16MHz

在配置 OSC WDT 功能之前,应禁用所有 SMU 振荡器看门狗报警响应选项,以避免意外的 SMU 报警。 此后,可以更改 OSCCON.OSCVAL 的值。 然后, OSC_WDT 应通过设置 OSCCON.OSCRES 重置。 这将请求使用新配置启动 OSC WDT 监控。 当设定 OSCCON.PLLLV 和 / 或 OSCCON.PLLHV 的预期正监测结果时,输入频率处于预期范围内。 当设置 OSCCON.OSCRES 清除 OSCCON.PLLLV 和 OSCCON.PLLHV 时,应设置两个状态标志。 因此,在再次启用 SMU 报警响应之前,应清除这两个标志。 如果只设置了位 OSCCON.OSCRES 而未对 OSCCON.OSCVAL 进行任何修改,也应使用 SMU 报警禁用 – 清除 – 启用序列

如果 SMU 检测到振荡器监视报警,则必须执行与 PLL 锁定丢失事件相同的恢复过程

Note:

振荡器看门狗主要用于 PLL 输入时钟 fOSC _i 通过寄存器 SYSPLLCON0.Insel = 01B 设置为 fOSC0 时。 如果 SYSCLK 通过 SYSPLLCON0.Insel = 10B 用作 fOSC _i 的源,用户应将 SYSCLK 频率限制在与使用晶体相同的范围内,或禁用 SMU 中的看门狗报警。 通过 SYSPLLCON0.Insel = 00B 使用备份时钟作为 fOSC _i 的输入时,也需要禁用看门狗报警。 数据表中列出了通过分配的 GPIO 输入引脚驱动 SYSCLK 时的可用晶体频率范围和允许的频率范围

1.1.6 配置SMU和时钟相关的Alarm

SMU模块在后续的TC3xx系类文章中再详细讲解,这里仅仅列出在配置OSC时相关的SMU寄存器。

只有SMU_KEYS寄存器的CFGLCK[7:0]配置为0xBC时才能配置SMU.

配置SMU_AGiCFj寄存器Disable Clock相关的Alarm.

和Clock Alarm相关的Group是Group 8, 也就是AGiCFj中I == 8.

Note: AG8CF0, AG8CF1, AG8CF2三个寄存器的同一个bit组合关系决定一个Alarm类型

举例:

AG8CF0[0].CF0, AG8CF1[0] .CF0, AG8CF2[0] .CF0 就是三个bit, 组合为一个0x0 – 0x7的具体Alarm类型,如果

AG8CF0[0] == 1,

AG8CF1[0] .CF0 == 1,

AG8CF2[0] .CF0== 1,

那么最后组合为111 = 0x7,产生的Alarm就是SMU_CPU_RST.

1.2 备用时钟

备用时钟源可用作备用时钟源。 此时钟源提供稳定但可靠的时钟源,可用作系统的时钟源。 它提供的准确度低于外部晶体或陶瓷谐振器。 不能启用或禁用备份时钟,也不能通过其他方式控制备份时钟,以阻止其常规操作。 因此,除了选择备份时钟作为源 (CCUCON0.CLKSEL = 00B 作为时钟分配的时钟源, SYSPLLCON0.Insel = 00B 作为两个 PLL 的时钟源) 外,没有可用的控制位。

1.3 OSC实际应用配置

需求:配置使用一个20MHz的外部无源晶振。

#include "IfxScu_reg.h"

#include "IfxSmu_reg.h"



static uint8 Startup_ClockInit_ConfigOSC(void)

{

    /*Disable SMU Clock Alarm*/

    MODULE_SMU.KEYS.U = (uint32)0xBCU;             /* Enable access to SMU registers */

    MODULE_SMU.CMD.U  = (uint32)0x05U;

    MODULE_SMU.AG[8].U  = 0x1FU;                   /* Clear SMU Alarms*/

    MODULE_SMU.KEYS.U = (uint32)0U;


    /*Congig OSC -- Start*/

    Ifx_SCU_OSCCON scuOsccon;

    uint32 timeoutCount;

    uint8 error = 0;

    UnlockEndinit_Core0();


    scuOsccon.U      = MODULE_SCU.OSCCON.U;

    scuOsccon.B.MODE = 0U;


    /*fOSC = OSCCON.OSCVAL - 1 + 16MHz */

    scuOsccon.B.OSCVAL = (uint32)5U;


    MODULE_SCU.OSCCON.U       = scuOsccon.U;


     /* Check if the configuration is valid */

    timeoutCount = 0xFFFFF;

    while((MODULE_SCU.OSCCON.B.PLLLV == 0U) && (MODULE_SCU.OSCCON.B.PLLHV == 0U))                                         
    {

        if (((--(timeoutCount)) <= 0)

        {
            (error) = 1;
            break;

        }

    }  

    /*Congig OSC -- End*/


    /* Enable SMU Clock Alarms */

    MODULE_SMU.KEYS.U = (uint32)0xBCU;             /* Enable access to SMU registers */

    MODULE_SMU.CMD.U  = (uint32)0x00000005;

    MODULE_SMU.AG[8].U  = 0x1FU;   /* Clear SMU Alarms*/

    MODULE_SMU.KEYS.U = (uint32)0U;


    LockEndinit_Core0();

    return error;

}

2. 时钟倍频PLL

系统 PLL 可以将低频外部时钟信号转换为高速内部时钟,以获得最佳性能。 它允许通过改变不同的分频器因子来使用多种输入和输出频率。

系统 PLL 还具有故障安全逻辑,可检测到非生成外部时钟行为,如异常频率偏差或外部时钟完全丢失。 如果它在外部时钟上失去锁定,它可以执行紧急操作。

2.1 特点

. DCO锁检测

. 3 位输入分隔器 P (除以 PDIV+1)

. 7 位反馈分隔器 N (乘以 NDIV+1)

. 3 位输出分隔器 K2 (除以 K2DIV+1)

. 振荡器监视(Oscillator Watchdog)

        –检测输入频率是否太低

        –检测输入频率是否太高

. 低频率抖动调制

2.2 系统时钟锁相环PLL

Figure 3 System PLL Block Diagram

输入频率 fOSC 除以因子 P ,乘以因子 N ,然后再除以因子 K2。

输出频率计算公式如下:

fPLL0 = (N* fOSC) / (P * K2)

fPLL0需要 fOSC 的输入时钟频率。 因此,建议通过检查 OSCCON.PLLV 来检查监控输入频率 fOSC 是否可用。 为了更好监控,还可以通过 OSCCON.PLLHV 监控上频。

系统操作频率由三个分频器(divider)的值控制: P , N 和 K2。 修改两个分频器 P 和 N 对 DCO 频率有直接影响,可能导致锁定状态丢失修改 K2 分频器对锁定状态没有影响,但仍会更改系统 PLL 输出频率 fPLL0.

注意:通过更改 K2-Divider 的值来更改系统操作频率,可以直接连接到设备的功耗。 因此,必须谨慎行事。

当必须修改系统 PLL 输出频率的频率时,应遵循以下顺序

应禁用为失去锁定而生成的 SMU 警报。

CCU 使用不同的时钟源时,可以配置系统 PLL 并检查位置 DCO 锁定状态。 第一个目标频率的选择方式应与 CCU 当前使用的目标频率相匹配,或仅略高一些。 这可以避免在以后切换至系统 PLL 时发生系统操作频率 (因此也避免功耗) 的大变化。 应按以下方式选择 P 和 N 分频因子(divider):

. 选择 P 和 N 时, fDCO位于其允许值的下半部分。 这会导致功耗略有降低,但抖动略有增加。

. 选择 P 和 N 时, fDCO位于其允许值的上部区域。 这会导致功耗略有增加,但抖动略有降低。

通过更新 P , N 和 K2 分频因子完成第一次PLL时钟配置后,应检查 DCO 锁定状态指示 (SYSPLLSTAT.LOCK = 1)。

系统 PLL 锁定后,可以切换至系统 PLL。 系统 PLL 丢失锁定事件的 SMU 状态标志应被清除,然后再次启用SMU监控。

现在只能通过更改 K2-Divider 来配置目标系统 PLL 输出目标频率。 根据 K2-Divider 的值,选择输出时钟的周期时间。 这可能会对使用外部通信接口的操作产生影响。 多步更改 k2-Divider ,以避免输出频率发生大变化,从而避免功耗发生大变化。

注意:

1.建议配置完P 和 N 分频器(divider)的新值后重置 DCO 锁定检测 (SYSPLLCON0.RESLD = 1) ,这样就能得到一个芯片定义好的DCO锁的检测时间(让DCO锁有充足时间检测并锁定) 。

2. 由于两个 PLL (System PLL and Peripheral PLL)的紧急从 PLL 切换至备用时钟同时激活,强烈建议仅在设置了外围 PLL 并将其锁定到目标频率时,才将系统时钟切换至系统 PLL。 如果执行了顺序设置,则可能会发生外设 PLL 在设置过程中丢失锁定事件,这也会导致系统时钟切换至备用时钟。

3. 建议在设置 DCO 频率并锁定系统 PLL 后步进的设置系统 PLL K2-Divider (降低功率突变冲击)。 此外,用户必须在再次更改 SYSPLLCON1.K2DIV 值之前检查 SYSPLLSTAT.K2RDY =1。 SYSPLLCON1.K2DIV 寄存器在上一次写入仍在进行时被锁定,如 SYSPLLSTAT.K2RDY =0 所示。

System PLL Lock Detection

系统 PLL 具有锁定检测(lock detection)功能,用于监控系统 PLL 的 DCO 部分,以区分稳定和不稳定的 DCO 电路行为。 如果两个输入fREF 和 fDIV 的差异太大,锁定探测器(lock detector)会将 DCO 电路标记为不稳定,因此 DCO 的输出fDCO. 低于某一级别的一个或两个输入频率的变化不会被锁定标记,因为 DCO 可以处理小的变化且保证系统没有任何问题

System PLL Loss-of-Lock Event

由于晶体 / 陶瓷谐振器或外部时钟线断裂,系统PLL 可能会解锁。 在这种情况下,会生成 SMU 警报事件

System PLL Power Down Mode

系统 PLL 提供断电模式。 如果根本不需要外围 PLL ,则可以进入此模式以节省电源。 通过设置位 SYSPLLCON0.PLLPWD 进入断电模式。 当系统 PLL 处于断电模式时,不会生成系统PLL 输出频率。

Frequency Modulation

系统 PLL 输出频率 fPLL0还可以通过低频调制进行修改,以减少 EMI。 随机序列添加到 DCO ,从而形成随机调制的 fDCO。 调制频率由 fREF定义

调制通过位 SYSPLLCON0.MODEN 启用。 调制本身会在配置的调制幅度 (MA) 范围随机改变 DCO 频率。 调制振幅通过 SYSPLLCON2.MODCFG[9:0] 选择。

SYSPLLCON2.MODCFG[9:0] = HEX[(64 * (MA / 100)) * (fOSC / P) *(N/ fMV)]

Example: for MA = 1.25%; fOSC = 20 MHz; P = 2; N = 60; fMV = 3.6 MHz the resulting bit field setting is 0x85.

调制的执行方式是,调制所增加的累积抖动保持在JMOD以下 (有关定义的值,请参阅数据表)。 调制本身通过 fREF进行监控,因此应使用尽可能最小的值配置分压器。

2.3 系统PLL寄存器

系统PLL状态寄存器

系统控制寄存器0

系统PLL配置寄存器1

2.4 外设时钟锁相环PLL

外设PLL配置基本和系统PLL类似,这里只给出时钟倍频图及其计算公式

Figure 4 Peripheral PLL Block Diagram

fPLL1 = (N* fOSC) / (P * K2)

fPLL2 = (N* fOSC) / (P * K3 * 1.6) if DIVBY = 0 or fPLL2 = (N* fOSC) / (P * K3 * 2) if DIVBY = 1

fHSCT = fDCO / 2

通过配置外设PLL的配置寄存器就能配置P, K2, K3参数的具体值。

2.5 PLL实际应用配置

需求1:配置fOSC到100MHz.

公式fPLL0 = (N* fOSC) / (P * K2)

fOSC == 20MHz

N = SYSPLLCON0.NDIV + 1 = 29(0x1D, 配置SYSPLLCON0.NDIV为29) + 1 = 30

P = SYSPLLCON0.PDIV + 1 = 0(配置SYSPLLCON0.PDIV为0) + 1 = 1

K2 = SYSPLLCON1.K2DIV + 1 = 5(配置SYSPLLCON1.K2DIV为5) +1 = 6

fPLL0 = (N* fOSC) / (P * K2) = (30 * 20)/(1 * 6) = 100MHz

查看SYSPLLSTAT寄存器的PWDSTAT和K2RD位域来判断时钟配置结果

需求2:配置fPLL1到320MHz.

需求3:配置fPLL2到200MHz.

需求4:配置fHSCT到640MHz.

计算公式

fPLL1 = (N* fOSC) / (P * K2)

fPLL2 = (N* fOSC) / (P * K3 * 1.6) if DIVBY = 0 or fPLL2 = (N* fOSC) / (P * K3 * 2) if DIVBY = 1

fHSCT = fDCO / 2

同样,我们配置:

N = 32

P = 1

K2 = 2

K3 = 2

fPLL1 = (N* fOSC) / (P * K2) = (32 * 20) / (1 * 2) = 320 MHz.

fPLL2 = (N* fOSC) / (P * K3 * 1.6) if DIVBY = 0 or fPLL2 = (N* fOSC) / (P * K3 * 2) if DIVBY = 1

= (32 * 20) / (1 * 2 * 1.6) = 200 MHz.

fHSCT = fDCO / 2 = = (N* fOSC) / (P) = 640 MHz.

示例代码

#include "IfxScu_reg.h"

#include "IfxSmu_reg.h"


static uint8 Startup_ClockInit_ConfigPLL(void)
{
    Ifx_SCU_SYSPLLCON0 SysPLLCon0;

    Ifx_SCU_PERPLLCON0 ScuPerPllCon0;

    Ifx_SCU_PERPLLCON1 ScuPerPllCon1;

    uint32 TimeoutCount;

    uint8 Error = 0;

    LockEndinit_Core0();

    /* Configure the system PLL */

    SysPLLCon0.U       = MODULE_SCU.SYSPLLCON0.U;

    SysPLLCon0.B.PDIV  = 0x00;

    SysPLLCon0.B.NDIV  = 0x1D;

    SysPLLCon0.B.INSEL = 1; // fOSC is used as clock source

    MODULE_SCU.SYSPLLCON0.U   = SysPLLCon0.U;


    /* Configure the peripheral PLL */

    ScuPerPllCon0.U       = MODULE_SCU.PERPLLCON0.U;

    ScuPerPllCon0.B.DIVBY = 0x00;

    ScuPerPllCon0.B.PDIV  = 0x00;

    ScuPerPllCon0.B.NDIV  = 0x1F;

    MODULE_SCU.PERPLLCON0.U      = ScuPerPllCon0.U;


    /* Power up the system PLL and peripheral PLL */

    MODULE_SCU.SYSPLLCON0.B.PLLPWD = 1;

    MODULE_SCU.PERPLLCON0.B.PLLPWD = 1;


/* Check if the configuration is valid */

    TimeoutCount = 0x3000;

    while((MODULE_SCU.SYSPLLSTAT.B.PWDSTAT == 1U) || (MODULE_SCU.PERPLLSTAT.B.PWDSTAT == 1U))                                         

    {

        if (((--(TimeoutCount)) <= 0)

        {

            (Error ) = 1;

            break;

        }

    }  


/* Check if the configuration is valid */

    TimeoutCount = 0x5000;

    while((MODULE_SCU.SYSPLLSTAT.B.K2RDY == 0U) ||

               (MODULE_SCU.PERPLLSTAT.B.K2RDY == 0U) ||

              (MODULE_SCU.PERPLLSTAT.B.K3RDY == 0U))                                        
    {
        if (((--TimeoutCount)) <= 0)
        {
            (Error ) = 1;
            break;
        }

    }  

   MODULE_SCU.SYSPLLCON1.B.K2DIV = 5;

    ScuPerPllCon1.U       = MODULE_SCU.PERPLLCON1.U;

    ScuPerPllCon1.B.K2DIV = 1;

    ScuPerPllCon1.B.K3DIV = 1;

    MODULE_SCU.PERPLLCON1.U = ScuPerPllCon1.U;

    TimeoutCount = 0x5000;

    while((MODULE_SCU.SYSPLLSTAT.B.K2RDY == 0U) ||

               (MODULE_SCU.PERPLLSTAT.B.K2RDY == 0U) ||

               (MODULE_SCU.PERPLLSTAT.B.K3RDY == 0U))                                       

    {

        if (((--(TimeoutCount)) <= 0)

        {

            (Error ) = 1;

            break;

        }

    }  

/* Start PLL locking for latest set values*/

    MODULE_SCU.SYSPLLCON0.B.RESLD = 1;  

    MODULE_SCU.PERPLLCON0.B.RESLD = 1;

   /*Wait for PLL lock to be set*/

    TimeoutCount = 0x3000;

    while((MODULE_SCU.SYSPLLSTAT.B.LOCK == 0U) || (MODULE_SCU.PERPLLSTAT.B.LOCK == 0U))                                         

    {

        if (((--(TimeoutCount)) <= 0)
        {
            (Error ) = 1;
            break;
        }
    }  

    UnlockEndinit_Core0();

}

3. 时钟分配(CCU)

配置好时钟系统的时钟源(OSC)和锁相环倍频(PLL),系统操作所依赖的Root Clock就有了。 接下来,MCU的所有外设模块,CPU核都需要从Root Clock通过分屏来适配自己需要的时钟。 各个模块都需要适配时钟,主要是为了优化性能和降低功耗

对于时钟分配,系统分为多个子时钟域,可以在这些域中单独配置时钟速度。 内部接口派生的每个子时钟域也有限制。 每个子时钟域从时钟角度定义逻辑单元。

时钟分配通过时钟控制单元 (CCU) 完成。 CCU 接收由两个 PLL (fPLL0 and fPLL1/2) ,备用时钟fBack 和 fOSC0创建的时钟。 这些时钟可以直接转发划分以便提供子时钟域。

3.1 时钟控制单元

Figure 5 Clock Control Unit Overview

对于大多数时钟,提供了线性分频器来调整时钟频率以满足应用要求。 此分隔符由寄存器 CCUCONy 中的位字段 XXXDIV 控制。

时钟系统的配置非常灵活。 这允许将频率变化调整为应用程序定义的特定电流限制

每个模块都有default时钟源以及推荐(√)的时钟源,以及可选的倍频/分频系数。在配置某个具体模块的时钟时,首先选择时钟源,然后再选分频系数。

3.2 以MCCAN为例配置时钟频率

CCUCON0.CLKSEL配置fsource0, fsrc1, and fsource2三个时钟的时钟源。

MCAN的配置在CCUCON1寄存器上

CCUCON1.MCANDIV配置fMCANI的分频系数。

CCUCON1.CLKSELMCAN配置MCAN的时钟源。

CCUCON1寄存器的默认值位0x1010 0302,也就是:

CCUCON1.MCANDIV = 2

CCUCON1.CLKSELMCAN = 0  à  fMCAN clock是不工作的。

需求fMCAN clock配置到80MHz.

第一步:了解时钟源

从第二章已知

fPLL0为100MHz.

fPLL1为320MHz.

fPLL2为200MHz.

第二步:CCUCON0.CLKSEL配置为0x01B

也就是

 fsource0 == fPLL0 == 100MHz

fsource1 == fPLL1 == 320MHz

fsource2 == fPLL2 == 200MHz

第三步:配置CCUCON1.MCANDIV = 0x4H

也就是

fMCANI = fsource1/4 = 320/4 = 80MHz.

第四步:配置CCUCON1.CLKSELMCAN = 01B,fMCANI is used as clock source fMCAN

也就是

fMCANI ==  fMCAN  == 80MHz.

4. 总结

时钟配置基本都是按下图的推荐参数来配置的

Figure 6 Clocking System example with external 20MHz crystal / clock input

原文地址:https://blog.csdn.net/qq_36056498/article/details/134624914

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。

如若转载,请注明出处:http://www.7code.cn/show_5097.html

如若内容造成侵权/违法违规/事实不符,请联系代码007邮箱:suwngjj01@126.com进行投诉反馈,一经查实,立即删除

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注