[信息] STM32 单片机ADC 使用内部电压基准

[复制链接]
299|0
磨砂 发表于 2025-11-8 17:45 | 显示全部楼层 |阅读模式
无校准测量
ADC 默认使用VDDA 作为电压基准,一般就是指外加的+3.3V 电源电压。ADC 默认分辨率12bit,也就是4095 格分辨率,测量值每一格对应的电压是:

240690d597a00b58.png


要知道测量值对应的电压是多少,就用实测值乘以上面这个系数。如果是用+3.3V LDO 供电,一般精度至少能有2%,精度高一点的LDO 能到1%,比如ME6211,此时基本不需要额外处理,直接这么用就行了。有时+3.3V 电源电压精度比较低,比如用DC-DC 电源,精度可能会到5%,这表示最坏情况下,ADC 测量3V 电池电压,误差能有0.15V,要是外部加了分压电路来测量较高的电池电压,那么误差就更大了。

内部电压基准
STM32 和很多别的单片机都内置了电压基准,用来在不变更硬件电路配置的条件下尽量提高测量精度。根据F410 的数据手册的说法,内置基准电压为+1.2V,精度1%。

43061690d597208f77.png

此时ADC 系数可以按如下计算:

190690d596b89f38.png
其中REFREFREF 是用ADC 采样VREFINTV_{REFINT}V
REFINT

  通道得到的实测值,这样的精度一般就够用了。

内部基准校准值
理论上精度还可以更高一点,就是使用芯片出厂时内部参考的校准值来替代手写的1.2V,这个校准值就是1.2V 基准的实测电压。根据F410 的手册,校准值是在外加VDDA = 3.3V 时测量的结果,就是芯片厂里用外置高精度3.3V 电源作为基准,测量内置基准电压。

40092690d59633913e.png

校准值是用12bit 模式测量的ADC 输出值。用HAL库的话,adc 头文件里提供了两个宏定义:VREFINT_CAL_ADDR 和VREFINT_CAL_VREF,前者是指向校准值的指针,后者是工厂里用的外部参考电压,也就是3300mV。

1.2V 基准的校准电压可以用下式计算:

67670690d595c8b8db.png

其中,VREFINTV_{REFINT}V
REFINT

  是实测电压,CALCALCAL 是校准值。然后就用这个校准电压代替手写的1.2V 来计算ADC 系数:

10317690d59528250b.png

实际上用了这个校准值以后精度可能没什么提升,相比直接手写1.2V 的算法,差异可能也就几十毫伏。

整数电压单位
实际写代码的时候有一个要注意的地方。如果不用浮点数计算电压,用整数计算的话,要注意整数除法损失精度的问题,最好是用μV 作为单位。

比方说,如果用mV 单位,要计算基准电压的话,上面的算式就写成:

auto cal = *VREFINT_CAL_ADDR;  // 读取校准值
auto v_refint = 3300 / 4095 * cal;


这样结果算出来就是0。改为μV 单位,计算ADC 系数:

auto cal = *VREFINT_CAL_ADDR;  // 读取校准值
auto v_refint = 3300'000 / 4095 * cal;
auto k = v_refint / ref;


然后要把ADC 输出结果计算为电压值,注意单位转换:

auto micro_volt = adc * k;
auto milli_volt = micro_volt / 1000;


有另一种算法,用mV 当单位,但是先不计算K 的值:

auto kk = 3300 * cal / ref;


然后转换ADC 输出结果:

auto milli_volt = adc * kk / 4095;


这就是官方手册里的算法:

95848690d592752c52.png


还是要注意整数除法运算的次序问题,比如,一定不能单独先计算CAL/REFCAL / REFCAL/REF。此外,这种算法不能把系数 K 缓存下来,每次测量结果都要除以4095。当然,用μV 算法,每次也还是要除以1000 才能得到毫伏电压。
————————————————
版权声明:本文为CSDN博主「刻BITTER」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/Etberzin/article/details/153181812

您需要登录后才可以回帖 登录 | 注册

本版积分规则

133

主题

4415

帖子

3

粉丝
快速回复 在线客服 返回列表 返回顶部