03:11\\\\\\\\r\\\\\\\\n修修补补,凑活着
01 零点偏置
一、前言
昨天调试的电路中, 遇到一个非常奇怪的问题。 那就是 所使用的单片机STM32F301 的 ADC的零点问题, 也就是在ADC输入有电压的情况下, 居然ADC的转换始终为0, 直到输入电压超过某一阈值之后, ADC才有输出。 这就使得测量电路在微小信号测量中出现了一个盲区。 为了解决这个问题, 曾在电路中增加了一个偏置电阻。 它给AD620 放大器的反向输入端口增加一个下拉电流, 使得输出能够稍微多出几十个毫伏。 谁承想, 这个偏置给前级带来了大约 6个微安的误差电流。 所以下面将这个电阻调整到AD620的正向输入端口, 通过上拉5V电压来抬高输出电压。 由此, 来消除单片机的ADC零点死区所带来的测试问题。 下面来测量一下具体的修改效果。
二、电路修改
修改电路。 将昨天焊接的电阻从AD620的反向输入端, 移植到正向输入端与5V之间。 将电阻只修改为 360k 欧姆, 后来发现修改为 300k欧姆更好。 下面重新进行测量电路的ADC,DAC的特性。
三、电路测量
测量单片机DAC输出从 0 到 2000 变化时, 外部电压所测量得到的ADC的变化。 可以看到在最开始的部分, 似乎有一点点的死区, 这是硬件电路中 DAC输出有一个反向偏置造成的。 则可以保证, 输出电流信号能够 从 0 开始。 这是传感器电压与ADC之间的关系, 能够看到, 这个曲线能够几乎从 0 点开始, 只是在 0 点附近, 略有失真。 但输出再没有了初始的偏置电流了。 这是给定的DAC与电路输出电流之间的关系, 线性关系非常好。 利用所测量得到的数据, 可以获得 ADC与信号电压之间的线性拟合系数, 这是拟合误差。 除了第一个数据之外, 其他都在正负1mV 之内。 这里给出了 DAC与输出电流之间的关系, 同样, 线性拟合误差除了前后两点之外, 绝大多数都在 0.5微安之内。
▲ 图1.3.1 DAC与ADC之间的数值关系
#!/usr/local/bin/python
# -*- coding: gbk -*-
#============================================================
# TEST1.PY -- by Dr. ZhuoQing 2024-06-24
#
# Note:
#============================================================
from headm import *
from tsmodule.tsvisa import *
from tsmodule.tsstm32 import *
dacdim = list(range(0, 2000, 20))
adcdim = []
vdim = []
dm3068open()
for d in dacdim:
stm32cmd("pvdac %d\r"%d)
time.sleep(2)
stm32cmd("CLEAR")
time.sleep(.5)
stm32cmd("pvadc\r")
time.sleep(.5)
stm32cmd("COPY")
time.sleep(.25)
s = clipboard.paste().split("\r\n")
printf(s)
adc = int(s[3])
adcdim.append(adc)
v = dm3068vdc()
vdim.append(v)
tspsave("dac", dacdim=dacdim, adcdim=adcdim, vdim=vdim)
printff(d, adc, v)
plt.plot(dacdim, adcdim, lw=3)
plt.xlabel("DAC")
plt.ylabel("ADC")
plt.grid(True)
plt.tight_layout()
plt.show()
#------------------------------------------------------------
# END OF FILE : TEST1.PY
#============================================================
dacdim=[0.0000,20.0000,40.0000,60.0000,80.0000,100.0000,120.0000,140.0000,160.0000,180.0000,200.0000,220.0000,240.0000,260.0000,280.0000,300.0000,320.0000,340.0000,360.0000,380.0000,400.0000,420.0000,440.0000,460.0000,480.0000,500.0000,520.0000,540.0000,560.0000,580.0000,600.0000,620.0000,640.0000,660.0000,680.0000,700.0000,720.0000,740.0000,760.0000,780.0000,800.0000,820.0000,840.0000,860.0000,880.0000,900.0000,920.0000,940.0000,960.0000,980.0000,1000.0000,1020.0000,1040.0000,1060.0000,1080.0000,1100.0000,1120.0000,1140.0000,1160.0000,1180.0000,1200.0000,1220.0000,1240.0000,1260.0000,1280.0000,1300.0000,1320.0000,1340.0000,1360.0000,1380.0000,1400.0000,1420.0000,1440.0000,1460.0000,1480.0000,1500.0000,1520.0000,1540.0000,1560.0000,1580.0000,1600.0000,1620.0000,1640.0000,1660.0000,1680.0000,1700.0000,1720.0000,1740.0000,1760.0000,1780.0000,1800.0000,1820.0000,1840.0000,1860.0000,1880.0000,1900.0000,1920.0000,1940.0000,1960.0000,1980.0000]
adcdim=[0.0000,104.0000,274.0000,434.0000,606.0000,761.0000,925.0000,1085.0000,1242.0000,1411.0000,1568.0000,1737.0000,1900.0000,2066.0000,2228.0000,2390.0000,2541.0000,2714.0000,2873.0000,3040.0000,3201.0000,3362.0000,3529.0000,3696.0000,3855.0000,4014.0000,4172.0000,4329.0000,4501.0000,4658.0000,4821.0000,4982.0000,5142.0000,5310.0000,5471.0000,5633.0000,5805.0000,5960.0000,6120.0000,6286.0000,6444.0000,6613.0000,6774.0000,6947.0000,7102.0000,7267.0000,7442.0000,7606.0000,7760.0000,7925.0000,8087.0000,8254.0000,8416.0000,8567.0000,8737.0000,8899.0000,9069.0000,9224.0000,9386.0000,9558.0000,9707.0000,9880.0000,10045.0000,10212.0000,10365.0000,10525.0000,10695.0000,10855.0000,11021.0000,11180.0000,11352.0000,11508.0000,11672.0000,11830.0000,11988.0000,12158.0000,12321.0000,12483.0000,12642.0000,12813.0000,12976.0000,13132.0000,13295.0000,13464.0000,13627.0000,13789.0000,13950.0000,14113.0000,14282.0000,14444.0000,14602.0000,14763.0000,14924.0000,15091.0000,15253.0000,15415.0000,15575.0000,15732.0000,15902.0000,16051.0000]
vdim=[-0.0000,0.0134,0.0293,0.0452,0.0612,0.0771,0.0930,0.1090,0.1249,0.1409,0.1568,0.1727,0.1886,0.2047,0.2206,0.2366,0.2525,0.2685,0.2844,0.3003,0.3162,0.3322,0.3481,0.3640,0.3800,0.3959,0.4111,0.4271,0.4430,0.4589,0.4749,0.4908,0.5067,0.5226,0.5385,0.5545,0.5704,0.5863,0.6022,0.6179,0.6338,0.6498,0.6656,0.6816,0.6975,0.7134,0.7294,0.7454,0.7613,0.7774,0.7934,0.8095,0.8248,0.8409,0.8569,0.8729,0.8889,0.9049,0.9208,0.9368,0.9528,0.9687,0.9847,1.0006,1.0163,1.0323,1.0482,1.0641,1.0801,1.0960,1.1119,1.1278,1.1438,1.1597,1.1756,1.1915,1.2075,1.2231,1.2391,1.2550,1.2709,1.2868,1.3027,1.3187,1.3346,1.3505,1.3664,1.3823,1.3983,1.4142,1.4299,1.4459,1.4618,1.4777,1.4936,1.5095,1.5254,1.5413,1.5570,1.5722]
▲ 图1.3.2 ADC与电压的拟合误差:STD=0.567mV
▲ 图1.3.3 DAC与输出电流线性拟合误差:STD=0.338uA
#!/usr/local/bin/python
# -*- coding: gbk -*-
#============================================================
# TEST1.PY -- by Dr. ZhuoQing 2024-06-25
#
# Note:
#============================================================
from headm import *
from scipy.optimize import curve_fit
dacdim, adcdim, vdim = tspload('dac', 'dacdim', 'adcdim', 'vdim')
R = 1e3
idim = [v/R*1e6 for v in vdim]
#------------------------------------------------------------
'''
plt.plot(vdim, adcdim, lw=3)
plt.xlabel("Voltage(V)")
plt.ylabel("ADC")
plt.grid(True)
plt.tight_layout()
plt.show()
'''
#------------------------------------------------------------
'''
plt.plot(dacdim, idim, lw=3)
plt.xlabel("DAC")
plt.ylabel("Current(uA)")
plt.grid(True)
plt.tight_layout()
plt.show()
'''
#------------------------------------------------------------
'''
def linefun(x, a, b):
return a*x + b
param = (1e-5, 0)
param, conv = curve_fit(linefun, adcdim, vdim, p0=param)
printf(param)
vfit = linefun(adcdim, *param)
err = [v1-v2 for v1,v2 in zip(vdim, vfit)]
printf(std(err))
plt.plot(adcdim, err, lw=3)
plt.xlabel("ADC")
plt.ylabel("Error(V)")
plt.grid(True)
plt.tight_layout()
plt.show()
'''
#------------------------------------------------------------
def linefun(x, a, b):
return a*x + b
param = (1, 0)
param, conv = curve_fit(linefun, dacdim, idim, p0=param)
printf(param)
ifit = linefun(dacdim, *param)
err = [v1-v2 for v1,v2 in zip(idim, ifit)]
printf(std(err))
plt.plot(dacdim, err, lw=3)
plt.xlabel("DAC")
plt.ylabel("Error(uA)")
plt.grid(True)
plt.tight_layout()
plt.show()
#------------------------------------------------------------
# END OF FILE : TEST1.PY
#============================================================
※ 总 结 ※
本文 记录了对电路板调试过程, 修改了昨天测量电路中偏置电压的方式, 消除了铂电极传感器的零偏电流, 通过测量数据, 获得了DAC与ADC的线性拟合系数。 但是问题来了, 为什么所使用的单片机的 ADC 在 0 点附近会有一个 70mV的死区呢? 现在这个问题仍然不得而知。 只是对电路进行修修补补, 使其能够工作起来。
■ 相关文献链接:
● 相关图表链接: