4.2.5. 设计说明¶
4.2.5.1. 源码说明¶
CMU 相关 .c
和 .h
文件分别位于 luban-lite\bsp\artinchip\hal\cmu
和 luban-lite\bsp\artinchip\include\hal
目录。主要源文件说明如下:
文件 |
说明 |
---|---|
aic_clk_id.h |
时钟 ID 以及 寄存器设置 |
aic_hal_clk.h |
hal 层 clk api 的头文件 |
aic_hal_clk.c |
hal 层 clk api 的实现 |
aic_hal_reset.h |
hal 层 reset api 的头文件 |
aic_hal_reset.c |
hal 层 reset api 的实现 |
aic_hal_pll_clk.c |
PLL 时钟的具体实现 |
aic_hal_fixed_rate_clk.c |
固定频率时钟的具体实现 |
aic_hal_fixed_parent_clk.c |
单个父时钟的时钟的具体实现 |
aic_hal_multi_parent_clk.c |
多个父时钟的时钟的具体实现 |
aic_hal_disp_clk.c |
DISP 时钟的具体实现 |
aic_hal_fpga_clk_def_v10.c |
CMU V1.0 的 Clock 配置 |
aic_hal_fpga_clk_def_v11.c |
CMU V1.1 的 Clock 配置 |
aic_hal_fpga_clk_def_v12.c |
CMU V1.2 的 Clock 配置 |
aic_hal_reset_def_v10.c |
CMU V1.0 的 Reset 配置 |
aic_hal_reset_def_v11.c |
CMU V1.1 的 Reset 配置 |
aic_hal_reset_def_v12.c |
CMU V1.2 的 Reset 配置 |
4.2.5.2. 模块架构¶

CMU 驱动的逻辑比较简单,目前只在 HAL 层提供了 Clock 和 Reset 的 API 接口。RTOS 驱动和 Baremetal 驱动都可以直接使用。
4.2.5.2.1. Clock¶
4.2.5.2.1.1. 时钟树¶

CMU 驱动将时钟树中的时钟分为五种类型:
fixed rate clock
包含 OSC24M、RC1M、OSC32K 三个时钟,这种时钟频率固定,不能调节频率,不能打开或关闭。fixed parent module clock
实现只有一个父时钟源的时钟驱动,主要是各个外设模块的时钟,该类型时钟可以改变时钟频率,打开或关闭时钟,获取父时钟源参数,但不能设置或改变父时钟源。multiple parent module clock
实现有多个父时钟源的时钟驱动,主要是各种总线时钟,该类型的时钟最为复杂,可以打开或关闭时钟,调节频率,获取或改变父时钟源。display module clock
实现了几个与显示模块相关的时钟驱动,由于显示模块除了自身的模块时钟外,还有一个像素时钟,相应的底层寄存器的设计也不同,所以将显示相关的几个时钟重新设计了底层驱动。pll clock
实现了 CMU 的 pll 时钟驱动。
类型 |
时钟 |
---|---|
fixed rate clock |
OSC24M |
OSC32K |
|
RC1M |
|
fixed parent clock |
CLK_DMA |
CLK_CE |
|
CLK_USBD |
|
CLK_USBH0-1 |
|
CLK_USB_PHY0-1 |
|
CLK_GMAC0-1 |
|
CLK_SPI0-1 |
|
CLK_SDMMC0-2 |
|
CLK_SYSCON |
|
CLK_RTC |
|
CLK_I2S0-1 |
|
CLK_ADDA |
|
CLK_DE |
|
CLK_GE |
|
CLK_VE |
|
CLK_WDOG |
|
CLK_SID |
|
CLK_GTC |
|
CLK_GPIO |
|
CLK_UART0-7 |
|
CLK_I2C0-3 |
|
CLK_CAN0-1 |
|
CLK_PWM |
|
CLK_ADCIM |
|
CLK_GPADC |
|
CLK_RTP |
|
CLK_TSEN |
|
CLK_CIR |
|
CLK_RGB |
|
CLK_LVDS |
|
CLK_MIPIDSI |
|
multi parent clock |
CLK_CPU |
CLK_AHB0 |
|
CLK_APB0 |
|
CLK_APB1 |
|
CLK_AXI0 |
|
CLK_OUT0 |
|
CLK_OUT1 |
|
CLK_OUT2 |
|
CLK_OUT3 |
|
pll clock |
CLK_PLL_INT0 |
CLK_PLL_INT1 |
|
CLK_PLL_FRA0 |
|
CLK_PLL_FRA1 |
|
CLK_PLL_FRA2 |
|
disp clock |
CLK_PIX |
CLK_SCLK |
4.2.5.2.2. Reset¶
CMU 在提供 Clock 控制的同时,也提供了 Reset 控制功能。但是相对时钟树来说,并不是每一级的时钟都对应有 Reset 控制,只有终端模块才会有 Reset 控制的需求。对应上一节五种类型的时钟,只有 fixed parent clock
同时拥有 Reset 功能。
4.2.5.3. 关键流程设计¶
4.2.5.4. 数据结构设计¶
CMU 模块关键结构体定义如下:
4.2.5.4.1. aic_clk_fixed_parent_cfg¶
struct aic_clk_fixed_parent_cfg {
struct aic_clk_comm_cfg comm; // 时钟操作的函数集合
u32 offset_reg; // 寄存器偏移地址
s8 bus_gate_bit; // 总线使能位偏移
s8 mod_gate_bit; // 模块使能位偏移
u8 div_bit; // 分频系数位偏移
u8 div_mask; // 分频系数 Mask
u8 id; // 时钟 id
u8 type; // 时钟类型
u8 parent_id; // 父时钟 id
u8 flag;
};
4.2.5.4.2. aic_clk_multi_parent_cfg¶
struct aic_clk_multi_parent_cfg {
struct aic_clk_comm_cfg comm; // 时钟操作的函数集合
u32 offset_reg; // 寄存器偏移地址
s32 gate_bit; // 时钟使能位偏移
u8 mux_bit; // 父时钟源选择位的bit偏移
u8 mux_mask; // 父时钟源选择位 Mask
u8 div0_bit; // 分频系数位偏移
u8 div0_mask; // 分频系数 Mask
u8 id; // 时钟 id
u8 num_parents; // 父时钟个数
const u8 *parent_ids; // 父时钟数组
};
4.2.5.4.3. aic_clk_pll_cfg¶
struct aic_clk_pll_cfg {
struct aic_clk_comm_cfg comm; // 时钟操作的函数集合
u32 offset_gen; // 整数分频寄存器的偏移
u32 offset_fra; // 小数分频寄存器的偏移
u32 offset_sdm; // 展频寄存器的偏移
u8 id; // 时钟 id
u8 type; // 时钟类型
u8 parent_id; // 父时钟 id
u8 flag;
};
4.2.5.4.4. aic_clk_disp_cfg¶
struct aic_clk_disp_cfg {
struct aic_clk_comm_cfg comm; // 时钟操作的函数集合
u32 offset_reg; // 寄存器偏移地址
u8 divn_bit; // 分频系数 N 位偏移
u8 divn_mask; // 分频系数 N 位 Mask
u8 divm_bit; // 分频系数 M 位偏移
u8 divm_mask; // 分频系数 M 位 Mask
u8 divl_bit; // 分频系数 L 位偏移
u8 divl_mask; // 分频系数 L 位 Mask
u8 pix_divsel_bit; // pix 分频系数位偏移
u8 pix_divsel_mask; // pix 分频系数位 Mask
u8 id; // 时钟 id
u8 parent_id; // 父时钟 id
};
4.2.5.5. 接口设计¶
4.2.5.5.1. Clock API¶
CMU 驱动提供了 Clock API 接口函数,不同类型时钟支持的 API 接口函数如下表:
API 函数
|
功能描述
|
fixed
rate
clock
|
fixed
parent
clock
|
multi
parent
clock
|
disp
clock
|
pll
clock
|
---|---|---|---|---|---|---|
hal_clk_enable() |
使能时钟 |
√ |
√ |
√ |
||
hal_clk_disable() |
关闭时钟 |
√ |
√ |
√ |
||
hal_clk_enable_deassertrst() |
使能时钟的同时放开复位 |
√ |
||||
hal_clk_disable_assertrst() |
关闭时钟的同时使能复位 |
√ |
||||
hal_clk_enable_iter() |
迭代的使能时钟及其父时钟 |
√ |
√ |
√ |
||
hal_clk_enable_deassertrst_iter()
|
迭代的使能时钟及其父时钟
同时放开复位
|
√
|
||||
hal_clk_get_freq() |
获取时钟频率 |
√ |
√ |
√ |
√ |
√ |
hal_clk_set_freq() |
设置时钟频率 |
√ |
√ |
√ |
√ |
|
hal_clk_get_parent() |
获取父时钟 id |
√ |
√ |
√ |
||
hal_clk_set_parent() |
设置父时钟 id |
√ |
4.2.5.5.1.1. hal_clk_enable¶
函数原型 |
int hal_clk_enable(uint32_t clk_id) |
---|---|
功能说明 |
使能时钟 |
参数定义 |
clk_id:时钟 ID (CLK_xxxx 格式定义的宏) |
返回值 |
操作是否成功 (0=OK, other=Error) |
注意事项 |
4.2.5.5.1.2. hal_clk_disable¶
函数原型 |
int hal_clk_disable(uint32_t clk_id) |
---|---|
功能说明 |
关闭时钟 |
参数定义 |
clk_id:时钟 ID (CLK_xxxx 格式定义的宏) |
返回值 |
操作是否成功 (0=OK, other=Error) |
注意事项 |
4.2.5.5.1.3. hal_clk_enable_deassertrst¶
函数原型 |
int hal_clk_enable_deassertrst(uint32_t clk_id) |
---|---|
功能说明 |
使能时钟的同时放开复位 |
参数定义 |
clk_id:时钟 ID (CLK_xxxx 格式定义的宏) |
返回值 |
操作是否成功 (0=OK, other=Error) |
注意事项 |
4.2.5.5.1.4. hal_clk_disable_assertrst¶
函数原型 |
int hal_clk_disable_assertrst(uint32_t clk_id) |
---|---|
功能说明 |
关闭时钟的同时使能复位 |
参数定义 |
clk_id:时钟 ID (CLK_xxxx 格式定义的宏) |
返回值 |
操作是否成功 (0=OK, other=Error) |
注意事项 |
4.2.5.5.1.5. hal_clk_enable_iter¶
函数原型 |
int hal_clk_enable_iter(uint32_t clk_id) |
---|---|
功能说明 |
迭代的使能时钟及其父时钟 |
参数定义 |
clk_id:时钟 ID (CLK_xxxx 格式定义的宏) |
返回值 |
操作是否成功 (0=OK, other=Error) |
注意事项 |
4.2.5.5.1.6. hal_clk_enable_deassertrst_iter¶
函数原型 |
int hal_clk_enable_deassertrst_iter(uint32_t clk_id) |
---|---|
功能说明 |
迭代的使能时钟及其父时钟,同时放开复位 |
参数定义 |
clk_id:时钟 ID (CLK_xxxx 格式定义的宏) |
返回值 |
操作是否成功 (0=OK, other=Error) |
注意事项 |
4.2.5.5.1.7. hal_clk_get_freq¶
函数原型 |
unsigned long hal_clk_get_freq(uint32_t clk_id) |
---|---|
功能说明 |
获取时钟频率 |
参数定义 |
clk_id:时钟 ID (CLK_xxxx 格式定义的宏) |
返回值 |
时钟频率,单位为 Hz |
注意事项 |
4.2.5.5.1.8. hal_clk_set_freq¶
函数原型 |
int hal_clk_set_freq(uint32_t clk_id, unsigned long freq) |
---|---|
功能说明 |
设置时钟频率 |
参数定义 |
clk_id:时钟 ID (CLK_xxxx 格式定义的宏)
freq:时钟频率,单位为 Hz
|
返回值 |
操作是否成功 (0=OK, other=Error) |
注意事项 |
4.2.5.5.1.9. hal_clk_get_parent¶
函数原型 |
unsigned int hal_clk_get_parent(uint32_t clk_id) |
---|---|
功能说明 |
获取时钟频率 |
参数定义 |
clk_id:时钟 ID (CLK_xxxx 格式定义的宏) |
返回值 |
父时钟 ID |
注意事项 |
4.2.5.5.1.10. hal_clk_set_parent¶
函数原型 |
int hal_clk_set_parent(uint32_t clk_id, unsigned int parent_clk_id) |
---|---|
功能说明 |
设置时钟频率 |
参数定义 |
clk_id:时钟 ID (CLK_xxxx 格式定义的宏)
parent_clk_id:父时钟 ID
|
返回值 |
操作是否成功 (0=OK, other=Error) |
注意事项 |
4.2.5.5.2. Reset API¶
CMU 驱动提供了 Reset API 接口函数:
API 函数 |
功能描述 |
---|---|
hal_reset_assert() |
使能复位 |
hal_reset_deassert() |
放开复位 |
hal_reset_status() |
获取复位状态 |
4.2.5.5.2.1. hal_reset_assert¶
函数原型 |
int hal_reset_assert(uint32_t rst_id) |
---|---|
功能说明 |
使能复位 |
参数定义 |
rst_id:Reset ID (RESET_xxxx 格式定义的宏) |
返回值 |
操作是否成功 (0=OK, other=Error) |
注意事项 |
4.2.5.5.2.2. hal_reset_deassert¶
函数原型 |
int hal_reset_deassert(uint32_t rst_id) |
---|---|
功能说明 |
放开复位 |
参数定义 |
rst_id:Reset ID (RESET_xxxx 格式定义的宏) |
返回值 |
操作是否成功 (0=OK, other=Error) |
注意事项 |
4.2.5.5.2.3. hal_reset_status¶
函数原型 |
int hal_reset_status(uint32_t rst_id) |
---|---|
功能说明 |
查看复位状态 |
参数定义 |
rst_id:Reset ID (RESET_xxxx 格式定义的宏) |
返回值 |
操作是否成功 (0=复位有效, 1=复位无效) |
注意事项 |