5.2 COMP 使用说明
本章说明 N32G033 标准外设库中 COMP 驱动的文件组成、18 个公开函数,以及 COMP_OUT、CompBrake 2 个示例。比较器的输入选择、迟滞、滤波与输出消隐请配合用户手册的“COMP”章节阅读,芯片已知问题以勘误手册为准。
5.2.1 相关文件
| 相对路径 | 作用 |
|---|---|
firmware/n32g033_std_periph_driver/inc/n32g033_comp.h |
定义 COMP_InitType 结构体与时钟选择、工作模式、锁定、输出极性、同相与反相输入选择、滤波预分频、消隐、迟滞等宏,并按一段连续声明 18 个公开函数 |
firmware/n32g033_std_periph_driver/src/n32g033_comp.c |
实现上述 18 个函数:COMP 复位与初始化、输入与迟滞配置、滤波配置、输出消隐、标志与中断处理 |
projects/n32g033_EVAL/examples/COMP/ |
COMP 示例根目录,含 COMP_OUT、CompBrake 2 个示例 |
projects/n32g033_EVAL/examples/COMP/COMP_OUT/ |
该示例的工程目录组成:MDK-ARM/、EWARM/、inc/、src/、readme.txt |
projects/n32g033_EVAL/bsp/ |
示例共用的板级支持文件:delay.h 提供 SysTick 毫秒延时的接口 |
5.2.2 API 参考
以下 18 个公开函数按 n32g033_comp.h 的声明顺序分为 1 组;每个条目给出功能摘要与 n32g033_comp.c 中该函数正上方的注释原文。
复位、初始化与运行配置
COMP_DeInit、COMP_StructInit、COMP_Init、COMP_SetFilterControl、COMP_SetFilterPrescaler、COMP_SetHyst、COMP_OutputPolarityConfig、COMP_SetInpSel、COMP_SetInmSel、COMP_Enable、COMP_SetIntEn、COMP_GetIntStatus、COMP_GetOutStatus、COMP_IntStatusClear、COMP_SetLock、COMP_SetRefScl、COMP_SetBlking、COMP_VREF_Enable
void COMP_DeInit(void)复位 COMP 寄存器。
name COMP_DeInit.
fun Reset the COMP registers.
return none
void COMP_StructInit(COMP_InitType* COMP_InitStruct)用默认值填充 COMP_Initial 结构体的各个成员。
name COMP_StructInit.
fun Fills all COMP_initstruct member with default value.
param COMP_initstruct :
- ClockSelect
- LowPoweMode
- Blking
- Hyst
- PolRev
- InpSel
- InmSel
- FilterEn
- SampWindow
- Threshold
- ClkPsc
- En
return none
void COMP_Init( COMP_InitType* COMP_InitStruct)按 COMP_InitStruct 初始化 COMP 外设。
name COMP_Init.
fun Initializes the COMP peripheral according to the specified parameters in the COMP_InitStruct
param COMP_initstruct :
param Clksel :
- COMP_CLKSEL_SYSTEMCLK
- COMP_CLKSEL_LSX
param Pwrmd :
- COMP_CTRL_PWRMD_NORMAL
- COMP_CTRL_PWRMD_LOWPWR
param Blking :
- COMP_BLANKING_NO
- COMP_BLANKING_TIM1_OC5
param Hyst :
- COMP_CTRL_HYST_NO
- COMP_CTRL_HYST_LOW
- COMP_CTRL_HYST_MID
- COMP_CTRL_HYST_HIGH
param PolRev :
- COMP_OUTPOL_REV
- COMP_OUTPOL_NREV
param InpSel :
- COMP_INPSEL_PA1
- COMP_INPSEL_PA3
- COMP_INPSEL_PA7
- COMP_INPSEL_PA8
- COMP_INPSEL_PA9
- COMP_INPSEL_PA10
- COMP_INPSEL_PA12
- COMP_INPSEL_OPAMP1
- COMP_INPSEL_OPAMP2
- COMP_INPSEL_OPAMP3
param InmSel :
- COMP
- COMP_INMSEL_PA0
- COMP_INMSEL_PA4
- COMP_INMSEL_PA5
- COMP_INMSEL_PA11
- COMP_INMSEL_VREF_DAC
param ClkPsc:
Value can be set from 0 to 65535.
param FilterEn:
- ENABLE
- DISABLE
param Threshold:
- this value must be greater than SAMPW / 2 .
param SampWindow:
- from 0 to 31.
param En
- ENABLE
- DISABLE
return none
void COMP_SetFilterControl(uint8_t FilEn, uint8_t TheresNum, uint8_t SampPW)配置 COMP 滤波的阈值与采样窗口。
name COMP_SetFilterControl.
fun Configure the COMP filter value.
param FilEn:
- ENABLE.
- DISABLE.
param TheresNum:
- this value must be greater than SAMPW / 2 .
param SampPW:
- from 0 to 31.
return none
void COMP_SetFilterPrescaler(uint16_t FilPreVal)配置 COMP 低频滤波的预分频系数。
name COMP_Filter_Clock_Prescale_Config.
fun Configure The COMP low filter prescale.
param FilPreVal:
Value can be set from 0 to 65535.
return none
使用提示: 头文件 n32g033_comp.h 第 161 行声明的函数名为 COMP_SetFilterPrescaler,而其上方注释的 name 写作 COMP_Filter_Clock_Prescale_Config.,与函数名不一致。
void COMP_SetHyst(uint32_t HYST)配置 COMP 迟滞等级。
name COMP_SetHyst.
fun Configure COMP hysteresis level.
param HYST :
- COMP_CTRL_HYST_NO
- COMP_CTRL_HYST_LOW
- COMP_CTRL_HYST_MID
- COMP_CTRL_HYST_HIGH
return none
void COMP_OutputPolarityConfig(uint32_t POL)配置 COMP 输出信号是否取反。
name COMP_OutputPolarityConfig.
fun Configures COMP output signal polarity overturn or not.
param POL :
- COMP_OUTPOL_REV
- COMP_OUTPOL_NREV
return none
void COMP_SetInpSel(uint32_t VpSel)配置 COMP 同相输入端的选择。
name COMP_SetInpSel.
fun Configures COMP inpsel input selection.
param vpsel :
- COMP_INPSEL_OPAMP1
- COMP_INPSEL_OPAMP2
- COMP_INPSEL_OPAMP3
- COMP_INPSEL_PA1
- COMP_INPSEL_PA3
- COMP_INPSEL_PA7
- COMP_INPSEL_PA8
- COMP_INPSEL_PA9
- COMP_INPSEL_PA10
- COMP_INPSEL_PA12
return none
void COMP_SetInmSel(uint32_t VmSel)配置 COMP 反相输入端的选择。
name COMP_SetInmSel.
fun Configures COMP inmsel input selection..
param VmSel :
- COMP_INMSEL_VREF_DAC
- COMP_INMSEL_PA0
- COMP_INMSEL_PA4
- COMP_INMSEL_PA5
- COMP_INMSEL_PA11
return none
void COMP_Enable(FunctionalState Cmd)使能或关闭 COMP 外设。
name COMP_Enable.
fun Enable or disable COMP peripheral.
param Cmd new state of the COMP peripheral.
-ENABLE
-DISABLE
return none
void COMP_SetIntEn(FunctionalState Cmd)使能或关闭 COMP 中断。
name COMP_SetIntEn.
fun Enable or disable COMP interrupt .
param Cmd new state of the COMP peripheral.
-ENABLE
-DISABLE
return none
FlagStatus COMP_GetIntStatus(void)获取 COMP 中断标志。
name COMP_GetIntStatus.
fun Get COMPx interrupt flag .
return FlagStatus:
- SET
- RESET
FlagStatus COMP_GetOutStatus(void)获取 COMP 比较输出结果。
name COMP_GetOutStatus.
fun Get COMP result Status.
return FlagStatus:
- SET
- RESET
void COMP_IntStatusClear(void)清除 COMP 中断标志。
name COMP_IntStatusClear.
fun Clear COMP interrupt flag.
return none
void COMP_SetLock(void)使能 COMP 寄存器锁定。
name COMP_SetIntEn.
fun Enable COMP Lock .
return none
使用提示: 头文件 n32g033_comp.h 第 171 行声明的函数名为 COMP_SetLock,而其上方注释的 name 写作 COMP_SetIntEn.,与函数名不一致。
void COMP_SetRefScl(uint8_t Vv1Trim, bool Vv1En)设置 Vv1 的参考电压档位。
name COMP_SetRefScl.
fun Set Reference Volatge Scale of Vv1 .
param Vv1Trim :
- this data range of 0-0xff
param Vv1En :
- false
- true
return none
void COMP_SetBlking(uint32_t blking_mode)配置用 TIM1 输出信号控制 COMP 输出消隐。
name COMP_SetBlking.
fun Configures TIM1 output signal to control COMP Blking.
param blking_mode :
- COMP_BLANKING_NO
- COMP_BLANKING_TIM1_OC5
return none
void COMP_VREF_Enable(FunctionalState Cmd)使能或关闭 COMP 内部参考电压 DAC。
name COMP_VREF_Enable.
fun Enable or disable COMP internal voltage dac.
param Cmd new state of the COMP peripheral.
-ENABLE
-DISABLE
return none
5.2.3 Demo 示例说明
本节说明 COMP 的 2 个示例:COMP_OUT 用两个 GPIO 交替翻转比较器的差分输入并观察输出翻转,CompBrake 用比较器输出作为 TIM1 的刹车输入停止互补 PWM。
5.2.3.1 COMP_OUT 比较器输出翻转演示
工程目录: projects/n32g033_EVAL/examples/COMP/COMP_OUT/
使能 GPIO、COMP 与滤波器时钟→配置 PA0、PA1 为模拟输入、PB0、PB1 为推挽输出→初始化比较器并打开滤波与中断→主循环交替翻转 PB0、PB1 改变差分输入→输出翻转时经 EXTI 线触发中断
| 项目 | 源码解读 |
|---|---|
| 功能 | 用 PB0、PB1 两个引脚交替输出高低电平,经跳线分别送到比较器的反相、同相输入端,通过 EXTI 线 8 的比较器中断观察输出翻转。 |
| 源码组成 | src/main.c 含 ChangeVmVp、COMP_Configuration、RCC_Configuration、GPIO_Configuration、EXTI_Configuration 与 NVIC_Configuration;src/n32g033_it.c 与 inc/n32g033_it.h 中的 COMP_IRQHandler 清除中断标志;inc/main.h、readme.txt 给出声明与测试步骤;工程文件在 MDK-ARM/ 与 EWARM/。 |
| 关键配置 | 引脚:PA0 为反相输入、PA1 为同相输入、PA6 为比较器输出复用; PB0、PB1 为推挽输出; 比较器:采样窗口 31、阈值 18、滤波使能、迟滞低; 中断:EXTI 线 8 上升沿, COMP_IRQn 优先级 0。 |
| 程序与数据路径 | main → RCC_Configuration 打开 GPIO、COMP 与滤波器时钟 → NVIC_Configuration 使能 COMP 中断 → GPIO_Configuration 配置三个引脚 → EXTI_Configuration 把 EXTI 线 8 设为上升沿中断 → COMP_Configuration 初始化并使能比较器 → 主循环 ChangeVmVp 每 50 ms 翻转一次 PB0、PB1 → 输出翻转时 COMP_IRQHandler 清除标志。 |
| 主要 API | COMP_StructInit、COMP_Init、COMP_SetIntEn、COMP_Enable、COMP_IntStatusClear |
| 验证方法 | 把 PA0 与 PB0、PA1 与 PB1 用跳线相连,用示波器或逻辑分析仪观察 PA6 输出; 主循环每 50 ms 翻转一次输入,同相输入高于反相输入时 PA6 输出高电平,反之输出低电平。 |
| 使用提示 | 开发环境为 KEIL MDK-ARM V5.34.0.0 或 IAR EWARM 8.50.1,硬件基于评估板 N32G033K8Q7-1_STB V1.0; 系统时钟 64 MHz。 |
核心代码解读与移植
示例用两个 GPIO 模拟比较器的差分输入,输出翻转时经 EXTI 线触发中断。
数据路径: RCC_Configuration 打开 GPIO、COMP 与滤波器时钟 → GPIO_Configuration 配置 PA0、PA1 与 PB0、PB1 → COMP_Configuration 调用 COMP_StructInit 与 COMP_Init → ChangeVmVp 翻转 PB0、PB1 改变差分输入 → 输出翻转经 EXTI 线 8 置中断标志 → COMP_IRQHandler 调用 COMP_IntStatusClear 清除标志
1. 比较器、滤波器与 GPIO 的时钟一起打开。 比较器本身、采样滤波器与引脚分属不同的外设时钟位,必须在配置前一次性使能。
void RCC_Configuration(void)
{
/* Enable peripheral clocks ------------------------------------------------*/
/* Enable GPIO COMP clocks */
RCC_EnableAPBPeriphClk(RCC_APB_PERIPH_GPIO | RCC_APB_PERIPH_COMP | RCC_APB_PERIPH_COMPFILT, ENABLE);
}
漏掉滤波器时钟会让后面的滤波配置不生效;换到其他端口时确认对应的 GPIO 时钟位已经打开。
2. 结构体一次性给出输入、迟滞与滤波参数。 InpSel 与 InmSel 选定差分输入引脚,SampWindow 与 Threshold 决定采样滤波器的工作点。
COMP_InitType COMP_Initial;
/*Initial comp*/
COMP_StructInit(&COMP_Initial);
COMP_Initial.InpSel = COMP_INPSEL_PA1;
COMP_Initial.InmSel = COMP_INMSEL_PA0;
COMP_Initial.SampWindow = 31; //(0~31)
COMP_Initial.Threshold = 18; //(0~31)
COMP_Initial.FilterEn = ENABLE;
COMP_Initial.Hyst = COMP_CTRL_HYST_LOW;
COMP_Init(&COMP_Initial);
Threshold 必须大于 SampWindow 的一半,改动采样参数时按此约束同步核对。
3. 输出端引脚必须配成复用推挽。 比较器结果要送到 PA6,该引脚需选择对应复用编号;两个输入引脚则配成模拟输入。
GPIO_InitStruct(&GPIO_InitStructure);
/* Configure INP INM PA0 PA1 as analog input -----------------------*/
GPIO_InitStructure.Pin = GPIO_PIN_0 | GPIO_PIN_1;
GPIO_InitStructure.GPIO_Mode = GPIO_MODE_ANALOG;
GPIO_InitPeripheral(GPIOA, &GPIO_InitStructure);
/* Configure PB0 PB1 as analog input -----------------------*/
GPIO_InitStructure.Pin = GPIO_PIN_0 | GPIO_PIN_1;
GPIO_InitStructure.GPIO_Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitPeripheral(GPIOB, &GPIO_InitStructure);
/* OutSel */
GPIO_InitStructure.Pin = GPIO_PIN_6;
GPIO_InitStructure.GPIO_Mode = GPIO_MODE_AF_PP;
GPIO_InitStructure.GPIO_Alternate = GPIO_AF8;
GPIO_InitPeripheral(GPIOA, &GPIO_InitStructure);
比较器输入走模拟通道,输出走复用通道,两类引脚的配置方式不能混用。
4. 中断里先清 EXTI 挂起位再清比较器标志。 输出翻转经 EXTI 线 8 触发中断,两个标志都要清,否则会反复进入中断。
void COMP_IRQHandler(void)
{
if(EXTI_GetITStatus(EXTI_LINE8))
{
EXTI_ClrITPendBit(EXTI_LINE8);
COMP_IntStatusClear();
}
}
换用其他 EXTI 线时要同步改这里的线号与 EXTI_Configuration 中的配置。
对应源码: src/main.c、src/n32g033_it.c、firmware/n32g033_std_periph_driver/inc/n32g033_comp.h
5.2.3.2 CompBrake 比较器刹车 TIM1 演示
工程目录: projects/n32g033_EVAL/examples/COMP/CompBrake/
使能 GPIO、COMP、TIM1 与滤波器时钟→配置差分输入与 TIM1 互补输出引脚→初始化比较器并与 TIM1 刹车源相连→主循环翻转差分输入→比较器输出触发刹车使 PWM 波形消失
| 项目 | 源码解读 |
|---|---|
| 功能 | 在 COMP_OUT 的差分输入基础上增加 TIM1 互补 PWM,把比较器输出接成 TIM1 的刹车输入; 当同相输入高于反相输入时 PWM 波形消失,比较器输出 PA6 为高电平。 |
| 源码组成 | src/main.c 含 ChangeVmVp、COMP_Configuration、TIM_Configuration、RCC_Configuration、GPIO_Configuration、EXTI_Configuration 与 NVIC_Configuration;src/n32g033_it.c 与 inc/n32g033_it.h 中的 COMP_IRQHandler 清除中断标志;inc/main.h、readme.txt 给出声明与测试步骤;工程文件在 MDK-ARM/ 与 EWARM/。 |
| 关键配置 | 引脚:PA0 为反相输入、PA1 为同相输入、PA6 为比较器输出复用; PB0、PB1 为推挽输出,PB3 为 TIM1_CH1 复用、PB4 为 TIM1_CH1N 复用; TIM1:递增计数、周期 1600、脉冲 800、死区 11,主输出与互补输出使能,刹车输入取 COMP1; 比较器:采样窗口 31、阈值 18、滤波使能、迟滞低。 |
| 程序与数据路径 | main → RCC_Configuration 打开 GPIO、COMP、TIM1 与滤波器时钟 → GPIO_Configuration 配置输入、输出与互补 PWM 引脚 → COMP_Configuration 初始化比较器 → TIM_Configuration 配时基、PWM 与刹车 → 使能 TIM1 主输出与计数 → 主循环 ChangeVmVp 每 10 ms 翻转一次差分输入 → 比较器输出触发刹车。 |
| 主要 API | COMP_StructInit、COMP_Init、COMP_SetIntEn、COMP_Enable、COMP_IntStatusClear |
| 验证方法 | 把 PA0 与 PB0、PA1 与 PB1 用跳线相连,用示波器观察 PA6 与 PB3、PB4; 同相输入高于反相输入时 TIM1 波形消失、PA6 为高电平,反之波形恢复、PA6 为低电平。 |
| 使用提示 | 开发环境为 KEIL MDK-ARM V5.34.0.0 或 IAR EWARM 8.50.1,硬件基于评估板 N32G033K8Q7-1_STB V1.0; TIM1 的刹车输入分别由主输出使能与刹车配置共同控制。 |
核心代码解读与移植
示例在比较器的基础上加一路 TIM1 互补 PWM,并把比较器输出接成刹车输入。
数据路径: RCC_Configuration 打开 GPIO、COMP、TIM1 与滤波器时钟 → TIM_Configuration 配置时基与互补 PWM 并把刹车源指向 COMP1 → TIM_EnableCtrlPwmOutputs 使能主输出 → ChangeVmVp 翻转差分输入 → 比较器输出作为刹车取消 PWM → COMP_IRQHandler 清除比较器标志
1. 时基与互补 PWM 一次配好。 主频先分频到 16 MHz,再以周期 1600 得到 PWM 频率;通道 1 同时使能正输出与互补输出,脉冲值决定占空比。
PrescalerValue = (uint32_t)(SystemCoreClock / 16000000) - 1;
/* Time base configuration */
TIM_InitTimBaseStruct(&TIM_TimeBaseStructure);
TIM_TimeBaseStructure.Period = 1600;
TIM_TimeBaseStructure.Prescaler = PrescalerValue;
TIM_TimeBaseStructure.ClkDiv = TIM_CLK_DIV1;
TIM_TimeBaseStructure.CounterMode = TIM_CNT_MODE_UP;
TIM_InitTimeBase(TIM1, &TIM_TimeBaseStructure);
/* PWM1 Mode configuration: Channel1 */
TIM_InitOcStruct(&TIM_OCInitStructure);
TIM_OCInitStructure.OCMode = TIM_OCMODE_PWM1;
TIM_OCInitStructure.OutputState = TIM_OUTPUT_STATE_ENABLE;
TIM_OCInitStructure.OutputNState = TIM_OUTPUT_NSTATE_ENABLE;
TIM_OCInitStructure.Pulse = Channel1Pulse;
TIM_OCInitStructure.OCPolarity = TIM_OC_POLARITY_HIGH;
TIM_OCInitStructure.OCNPolarity = TIM_OC_POLARITY_HIGH;
TIM_InitOc1(TIM1, &TIM_OCInitStructure);
TIM_ConfigOc1Preload(TIM1, TIM_OC_PRE_LOAD_ENABLE);
改成其他 PWM 频率时同步调整 PrescalerValue 与 Period,互补输出要一起使能才能用刹车。
2. 刹车功能与刹车源都写在 BDTR 配置里。 使能刹车、设定有效极性并打开自动输出,再把刹车输入源指向比较器 1。
/* Automatic Output enable, Break, dead time and lock configuration*/
TIM_InitBkdtStruct(&TIM_BDTRInitStructure);
TIM_BDTRInitStructure.OSSRState = TIM_OSSR_STATE_ENABLE;
TIM_BDTRInitStructure.OSSIState = TIM_OSSI_STATE_ENABLE;
TIM_BDTRInitStructure.LOCKLevel = TIM_LOCK_LEVEL_OFF;
TIM_BDTRInitStructure.DeadTime = 11;
TIM_BDTRInitStructure.Break = TIM_BREAK_IN_ENABLE;
TIM_BDTRInitStructure.BreakPolarity = TIM_BREAK_POLARITY_HIGH;
TIM_BDTRInitStructure.AutomaticOutput = TIM_AUTO_OUTPUT_ENABLE;
TIM_ConfigBkdt(TIM1, &TIM_BDTRInitStructure);
TIM_BreakInputSourceEnable(TIM1,TIM_BREAK_COMP1,TIM_BREAK_IOM_COMP_POLARITY_NONINVERT,ENABLE);
刹车输入源与比较器实例一一对应,换用比较器时要同步修改这里的刹车源枚举。
3. 上电后要使能主输出与计数。 互补 PWM 需要主输出使能信号,普通定时器不需要这一步。
/* TIM1 Main Output Enable */
TIM_EnableCtrlPwmOutputs(TIM1, ENABLE);
/* TIM1 counter enable */
TIM_Enable(TIM1, ENABLE);
顺序上先使能主输出再启动计数,避免启动瞬间输出不可控的窄脉冲。
4. 比较器中断同时完成标志清除。 比较器输出翻转时经 EXTI 线 8 触发中断,中断内清理 EXTI 挂起位与比较器中断标志。
void COMP_IRQHandler(void)
{
if(EXTI_GetITStatus(EXTI_LINE8))
{
EXTI_ClrITPendBit(EXTI_LINE8);
COMP_IntStatusClear();
}
}
中断处理与 COMP_OUT 一致;把比较器接到其他定时器时,改动集中在刹车配置而不影响这里。
对应源码: src/main.c、src/n32g033_it.c、firmware/n32g033_std_periph_driver/inc/n32g033_comp.h
5.2.4 注意与排障
| 场景 | 检查与建议 | 来源 |
|---|---|---|
| 采样滤波器阈值 | 用户手册 COMP 章写明阈值必须大于采样窗口的一半,否则滤波结果不可靠; 调整 Threshold 与 SampWindow 时按此约束核对。 |
用户手册 |
| 输出消隐引脚选择 | 用户手册 COMP 章写明消隐功能由 TIM1 的输出比较事件控制; 确认所用定时器通道与消隐源一致。 |
用户手册 |
| STOP 与低功耗模式 | 用户手册 COMP 章写明低功耗运行时比较器时钟可切换到系统时钟或 LSX; 进入低功耗前按需选择时钟源并确认唤醒路径。 |
用户手册 |
| 复用输出引脚 | 用户手册 COMP 章写明比较器输出经固定的复用通道送到引脚; 换引脚时按复用映射表设置对应的复用编号。 |
用户手册 |
勘误手册 V1.0.0(2025.9.25)针对 A 版芯片,未列出 COMP 相关条目。