多彩编程 多彩编程MZPH · CODE BLOG
ARTICLE DETAIL

文章详情

深耕前端与后端开发技术的一线实战笔记与踩坑复盘。

AD9833 DDS谐波分析与滤波:从FFT测量到低通滤波器设计

AD9833 DDS谐波分析与滤波:从FFT测量到低通滤波器设计 第一次把AD9833焊到转接板上SPI打通频率寄存器写进去示波器探头往VOUT上一搭很多人会愣一下——说好的正弦波呢屏幕上是一根带着台阶感的曲线边缘毛毛糙糙顺手打开FFT更扎心基频旁边竖着好几根尖峰二次、三次还有几个叫不上名字的毛刺。这不是芯片坏了也不是焊接温度把内部DAC烫伤了这是DDS方案天生自带的一套“谐波交响乐”。AD9833这颗芯片便宜、低功耗、三线SPI就能控制做函数发生器、扫频源、阻抗测量激励源都很方便。但几乎每个第一次用的人都会在波形质量上栽跟头最后要么把问题归咎于“芯片精度不行”要么盲目堆一堆滤波器。其实谐波的来源是有规律可循的可以测量、可以分类、可以估算也可以在设计阶段就把它压到你能接受的水平。这篇文章就把我从踩坑到摸清门道的完整过程写出来包括谐波从哪里来、怎么用FFT给谐波“定性”、滤波器该怎么选怎么算以及整个排查链路里最容易忽略的几个细节。1. 从一颗0.1Hz起步的DDS芯片讲起AD9833到底是什么1.1 三行代码能跑起来的信号源输出却从来不“教科书”AD9833是ADI出的一颗直接数字频率合成器芯片供电2.3V到5.5V都能跑主时钟最高25MHz频率寄存器28位所以在25MHz参考时钟下理论频率分辨率能到0.1Hz量级。它内部集成了一个10位的DAC可以输出正弦、三角波、方波三种基本波形控制只需要三根线的SPIFSYNC、SCLK、SDATA所以单片机资源占用非常小。很多人把这颗芯片当“高级函数发生器”用觉得只要把频率字写进去VOUT引脚就应该出来一条干净光滑的正弦曲线。实际上不是。你看到的是一个被DAC离散重建出来的阶梯状信号阶梯的密度等于主时钟频率除以输出频率每个台阶上还有毛刺和过冲。如果直接接示波器看在低频段还能勉强看出正弦轮廓频率一高到几MHz波形就开始“脏”得厉害。这里要先建立一个基本认知AD9833的输出质量不是由“波形好不好看”决定的而是由频谱里除了基频之外还剩多少能量决定的。时域上的一点点台阶感放到频域里可能就是一串可观的谐波和杂散。理解了这一点后面所有的分析才有意义。1.2 内部五个环节每一个都在“制造”麻烦DDS的工作链路大概是这样的相位累加器不断累加频率控制字产生一个线性增长的相位值这个相位值被截断后去查正弦查找表查出来的数字幅度送到DACDAC输出模拟台阶信号最后经过外部低通滤波器变成平滑波形。这五个环节里至少三个会主动贡献谐波或杂散。相位累加器是28位但查找表的地址只用了高12位被丢掉的那16位会周期性累积误差形成相位截断杂散DAC本身有积分非线性和差分非线性会把误差映射成固定的二次、三次谐波零阶保持输出在频域上有一个sin(x)/x的包络虽然对高频有衰减但也会带来镜像混叠问题。打个比方DDS的方案本身是“音源干净”但后面跟着一个离散化的功放输出端再不做处理的话喇叭里出来的声音肯定不可能是纯粹的。这个“功放”就是DAC的量化、截断和保持机制。所以你一开始就应该预期AD9833的裸输出一定是有谐波的区别只在于多和少、能不能被你的应用接受。1.3 谐波到底算不算“失真”先建立一个底层的判断框架在很多人的直觉里“谐波”和“失真”是一回事但对DDS来说这两者要分开看。谐波是指出现在基频整数倍位置上的能量比如2MHz主频旁边的4MHz、6MHz失真则是更广义的概念包含谐波、非谐波杂散、相位噪声、噪声地板等所有偏离理想信号的东西。AD9833的裸输出里谐波主要由DAC非线性决定这部分相对稳定只要芯片没坏、电源干净每次测出来的差别不大。非谐波杂散则很“调皮”它由相位截断产生会随着你设置的频率字不同而在频谱上到处移动有时候离主频很近滤波器根本压不掉。噪声地板则由量化噪声、参考时钟抖动、PCB布局、电源纹波共同决定。后面的章节会反复用到这个框架看到频谱上某根峰先判断它是谐波、是相位截断杂散、还是混叠镜像然后再决定用滤波器还是改频率字去处理。判断错了方案就全错了。2. 别急着滤波先做一次规范的FFT测量给谐波“定性”2.1 示波器FFT的设置习惯窗函数、平均次数和RBW很多人在示波器上随便按一下FFT按钮看到几根峰就开始调滤波器这是最要命的工作方式。示波器的FFT不是给你看的“大概图”它的读数是否可信完全取决于你设置得对不对。我习惯的做法是AD9833输出端接50欧终端电阻再用同轴电缆进示波器探头用×10挡并先做补偿校准。FFT模式下窗函数选汉宁窗Hanning或者平顶窗Flat Top点数拉到示波器支持的最大值比如1M点以上平均次数开16到64次。这样做的原因是AD9833的谐波和杂散往往比较微弱如果只用单次FFT噪声地板会很高很多-50dBc级别的分量会被淹没。RBW这个概念也要有数。示波器FFT的频率分辨率取决于采样率和FFT点数点数越多越能分辨离得很近的两根峰。相位截断杂散经常出现在离主频只有几百赫兹或者几kHz的地方如果RBW太粗你会看到一根粗粗的“山包”还以为就是一个普通谐波实际上里面藏着好几根尖峰。还有一个硬限制要提前知道普通8位示波器的ADC有效位数有限FFT动态范围一般也就45到55dB。也就是说低于-50dBc的分量读数可信度已经不高-60dBc以下基本就是噪声底。想认真评估谐波最好用12位以上高分辨率示波器、频谱仪或者把信号接到高分辨率ADC上做软件FFT。我用很多次8位示波器测谐波测出来的二次谐波数值每次都不一样后来才明白是示波器自身动态范围太差。2.2 谐波、杂散、噪声地板怎么区分做FFT测量时基频峰值先归一化成0dB然后观察其他分量。判断规则其实很简单出现在2f、3f、4f这些基频整数倍位置上的叫谐波不出现在整数倍位置上的叫非谐波杂散那些铺满整个底部的、上下浮动很大的是噪声地板。THD总谐波失真是把所有谐波能量加起来和基频比SFDR无杂散动态范围是看整段频谱里除了基频之外最高的那根峰不管是谐波还是杂散比基频低多少dB。对AD9833来说SFDR通常比THD更值得关注因为相位截断杂散往往比高次谐波更扎眼。我实测下来AD9833在几百kHz到1MHz输出频段二次谐波典型在-45到-50dBc三次谐波在-50到-55dBc再高次的谐波量级就小很多了。非谐波杂散的位置和幅度则和频率控制字强相关有些频率字下杂散能到-50dBc换个频率字可能就掉到-60dBc以下。所以你在网上看到的“AD9833失真只有-XXdB”这类说法脱离测量条件和频率字去谈没有任何参考价值。2.3 时域波形能告诉你的和不能告诉你的经常有人贴示波器时域截图问我“这个波形是不是谐波太大”说实话光看时域波形很难判断谐波严重程度。一个带阶梯感的波形可能谐波只有-45dBc一个看起来挺圆润的波形可能因为滤波器把高次压了但二次谐波仍然很大。人眼对正弦波形的“圆润度”判断和频谱里的THD数值并不是线性对应关系。时域里真正有用的信息是两类一是波形边缘有没有明显振铃和过冲这通常指向输出级阻抗不匹配、探头补偿不对、或者后级放大器带宽不足二是波形有没有叠加周期性毛刺这可能来自数字串扰、电源反冲或者接地环路。这些问题在频域里表现为宽带噪声或某些固定频率尖峰但在时域里更容易定位到电路层面。想看谐波对时域的具体影响有个好办法把输出信号同时采进高分辨率ADC在DSP里把理想正弦减掉剩下的误差波形就是谐波和杂散的时域总和。误差波形如果是周期性的说明以谐波为主如果是随机起伏的说明噪声地板占比大。这个方法比肉眼盯示波器靠谱得多。3. 实测波形里的谐波来源相位截断、DAC非线性与sinc滚降3.1 相位截断杂散频率字一变尖峰就跟幽灵一样到处跑AD9833的相位累加器是28位的但查表只用了高12位低16位在累加过程里不断被“截掉”。这些被截掉的相位误差并不是随机的它有固定周期周期跟频率控制字和2的16次方之间的公约数有关。于是频谱上就会冒出一根或几根非谐波杂散峰位置离主频非常近有时候甚至近到普通滤波器根本分不开。我最早在这个坑里绕了很久。用1MHz输出时频谱很干净把频率字改成对应2.37MHz频谱上突然多了一根离主频只有几十kHz的尖峰怎么加滤波器都滤不掉。后来才明白这不是滤波器的问题而是相位截断杂散随着频率控制字变化“跑”了。处理办法有两个方向。第一个方向是选择频率控制字让截断误差周期变长杂散能量被摊薄到更多频点上单根峰的幅度就会降下来。简单说就是别选那种让低16位频繁归零的频率字。第二个方向是使用芯片内部的三角波模式相位截断杂散会以一种更平均的方式分散开代价是波形本身就变成三角波了需要后级再接整形电路一般应用用不上。3.2 DAC非线性决定了二次、三次谐波的下限AD9833内部是10位DAC。理论上10位量化对应的信噪比大约是62dB但这只是理想量化噪声不包含DAC本身的非线性误差。实际芯片里的DAC积分非线性INL和差分非线性DNL是主要失真的来源。INL误差里奇对称的成分会贡献三次、五次奇数谐波DNL误差更像一种逐点跳变容易贡献二次、四次偶数谐波。所以你会看到一个很典型的现象二次谐波和三次谐波是AD9833裸输出的“常驻嘉宾”幅度稳定不太随频率字变化。提高输出频率时DAC的建立时间和毛刺能量开始变明显谐波比例会进一步抬升尤其是接近十几MHz输出时裸输出波形几乎已经看不出正弦的样子了。这里有个容易误解的地方很多人以为降低主时钟频率能让谐波变小其实不一定。DAC的非线性是固定比例存在的谐波相对基频的比例主要由DAC特性决定不太受绝对频率影响。反而主时钟越高sinc包络在带内的滚降越平缓高次镜像离得越远后级滤波器会好做一点。当然AD9833的主时钟上限是25MHz能调的余地也不大。3.3 零阶保持与sin(x)/x滚降天然压制与混叠风险并存DDS的DAC输出是零阶保持的也就是每个时钟周期输出一个电压值保持到下一个周期。这个过程中的频域响应是sin(πf/fMCLK)/(πf/fMCLK)的形状在fMCLK的整数倍处有零点对高频分量本来是有衰减作用的。问题是这个衰减在频率不太高的时候很有限。半采样率处也就是fMCLK/2衰减只有约3.9dB根本不够用。真正麻烦的是镜像分量输出f0时DAC会在fMCLK±f0、2×fMCLK±f0等位置产生镜像频谱这些镜像如果不被外部LPF滤除一旦进入后级非线性器件比如放大器、比较器、ADC前端就可能互相混频折回带内“伪装”成谐波或者杂散。表现在实测里就是你给AD9833输出直接接一个高带宽放大器本来裸输出频谱还能接受的放大之后突然多出很多莫名其妙的尖峰。这就是放大器二次非线性把镜像混叠回带内了。所以AD9833后面最好紧跟一个低通滤波器不只是为了压谐波更是为了把镜像频谱挡在放大器之前。3.4 方波模式下的“谐波”是另一回事AD9833通过控制寄存器的MODE位和OPBITEN位可以输出方波。严格来说方波是由内部比较器把DAC输出整形得到的或者直接从比较器输出引脚取出。方波频谱天然包含基频的奇数倍分量二次、四次等偶数次反而很小这和正弦模式下“二次谐波最大”的情况完全不同。如果在实测里发现频谱是奇次谐波一串一串的那你首先该怀疑的不是DAC非线性而是芯片是不是被配置成了方波模式。我遇到过不止一次复位寄存器顺序写错MODE位被意外置1示波器上看着是个有点方、又有点尖的波形FFT打开奇次谐波一大片排查了半天还以为是芯片坏了。三角波模式也一样三角波的频谱是奇次谐波按1/n²衰减看起来也像一串谐波。所以做谐波分析之前先确认控制寄存器的配置确定当前到底在输出哪种波形。这个步骤最简单但也最容易被忽略。4. 把谐波按下去的硬件手段从单极点RC到高阶椭圆滤波器4.1 先定需求再选拓扑你只需要带内干净不是要“最陡”很多人一上来就翻出“七阶椭圆滤波器”方案把板子堆得密密麻麻最后发现群延迟大得离谱波形过冲严重反而得不偿失。滤波器设计的第一步应该是问自己输出频率范围是多少带内平坦度要求多少谐波想压到多少dBc以下对相位失真敏感不敏感比如我的一个实际项目只需要输出0.1到1MHz的正弦要求二次谐波低于-60dBc对相位不太敏感。那我的目标就很明确在2MHz处提供大约15到20dB的额外衰减同时在1MHz以内保持幅度误差小于0.5dB。这个需求四到五阶的巴特沃斯或椭圆低通就足够了没必要上高阶。如果输出频率是变化的扫描信号比如从1kHz扫到10MHz那固定截止频率的LPF就不行了你需要按频段切换滤波器或者只用宽带滤波加“谐波反正离得远”的思路。AD9833作为一片低成本芯片通常不会去做太复杂的跟踪滤波所以最实用的方案是把输出频段限定在一个较窄范围内针对这个范围优化滤波器。4.2 单极点RC便宜但是只适合低频和要求不高的场景最简单的输出滤波就是一只电阻加一只电容构成一阶RC低通截止频率f_c1/(2πRC)。它的衰减斜率是每倍频程6dB在谐波只比基频高一倍频程时对二次谐波的额外衰减就6dB上下这在很多时候是不够的。我的用法是把RC当作DAC后面的第一级粗滤波目的是先把那些高频镜像和毛刺压掉一部分再进有源滤波器。比如截止频率放在1.5MHz左右用150欧串680pF电容既能挡一部分采样毛刺又不会对1MHz以内信号造成太大衰减。后续有源级再去处理谐波。RC还有一个好处是能改善后级运放的驱动条件。DAC输出阻抗偏高直接接有源滤波器会拉偏截止频率先串一个电阻隔离一下后级运放输入端看到的是相对稳定的源阻抗。这个细节在Sallen-Key拓扑里特别重要因为Sallen-Key对源阻抗敏感。4.3 四到五阶有源/LC滤波器把二次谐波再压20dB的设计实例当RC不够用的时候我会搭Sallen-Key有源低通。Sallen-Key用运放加RC构成二阶节两个二阶节级联就是四阶三个二阶节就是六阶。设计时可以用TI的FilterPro、ADI的Filter Wizard这类工具直接生成元件值自己查归一化系数表也行但手工算容易出错工具生成再仿真验证是最高效的。运放选型很关键。如果截止频率在1.5MHz运放的增益带宽积最好在20MHz以上避免运放自己在2MHz附近又贡献几个dB的衰减。我用过AD8066、OPA836这类高速运放也用过OPA2140这类11MHz的后者在低增益配置下也能工作但相位裕量要仔细看仿真结果。滤波阶数的估算可以这样做二次谐波在2f位置比基频高一倍频程一阶RC给约6dB衰减二阶节给约12dB三阶约18dB四阶约24dB当然这是在频率远离截止点后的近似。实际过渡带要按滤波器类型查表所以我建议用工具仿真确认。比如前面那个需求滤波前二次谐波-45dBc想做到-60dBc需要额外压15dB。我用一个截止1.5MHz的四阶巴特沃斯在2MHz处仿真大约给10dB多一点衰减前面再串一级RC粗滤加起来就到15到20dB了。仿真结果和实测基本吻合。高频应用里也可以直接做无源LC滤波器比如五阶切比雪夫或椭圆用绕线电感和C0G电容。LC适合频率更高、信号更大的场景但电感寄生电容、源阻抗和负载阻抗都会影响实际响应必须用网络分析仪或至少用示波器扫频验证。有源滤波器的好处是响应比较稳定、不依赖负载坏处是运放本身会引入噪声和新的失真。4.4 别忘了输出偏置、端接和后级缓冲AD9833的VOUT输出是以AVDD/2为直流偏置的交流幅度在空载、5V供电下大约0.6Vp-p量级供电电压低时幅度更小。这个信号直接进后级电路前通常需要经过隔直电容再在后级设置合适的直流工作点。隔直电容和后级输入阻抗也构成一个高通滤波器这个低频截止点别忽略。比如电容取1μF后级输入阻抗10kΩ低频截止约16Hz对普通音频/低频应用够用但如果你要输出几Hz的低频正弦这个组合就会压低输出幅度。端接问题经常被忽视。AD9833输出引脚本身的驱动能力很弱如果你用50欧同轴线直接连示波器线缆和示波器输入阻抗会形成分压输出幅度直接掉一半以上波形形状也会变差。正确做法是输出端先经过一个缓冲放大器再用同轴传输或者接受“幅度损失”并用高阻探头测量。做谐波测量时尽量保持负载条件一致不然滤波前的读数和滤波后的读数没有可比性。5. 一套能落地的排查流程从SPI初始化到FFT读数的完整链路5.1 SPI初始化的顺序错了波形从一开始就是脏的谐波分析的第一步不是看FFT而是确认AD9833的配置流程正确。很多网上的示例代码顺序不对最容易犯的错误是没有先把RESET位置1就写频率寄存器写完频率字之后又没有清RESET位导致芯片一直处于复位状态或者频率字只写入了一半。我常用的初始化顺序是FSYNC拉高延时写控制寄存器RESET1写FREQ0频率寄存器的低14位再写高14位最后写控制寄存器清RESETRESET0让芯片开始正常工作。两个16位帧之间FSYNC必须经历一次完整的拉高再拉低不能连续拉低写两个帧。给一段简化的GPIO模拟SPI代码做参考具体寄存器值以你手头的数据手册为准void ad9833_write(uint16_t reg) { FSYNC_HIGH(); delay_us(1); FSYNC_LOW(); for (int i 15; i 0; i--) { SCLK_LOW(); SDATA (reg (1 i)) ? 1 : 0; SCLK_HIGH(); } FSYNC_HIGH(); } void ad9833_set_freq(uint32_t freq_reg) { ad9833_write(0x2100); // B281, RESET1配置为先写低14位再写高14位 ad9833_write(0x4000 | (freq_reg 0x3FFF)); // FREQ0低14位 ad9833_write(0x4000 | ((freq_reg 14) 0x3FFF)); // FREQ0高14位 ad9833_write(0x2000); // 清RESET开始输出 }写完配置后用示波器DC耦合先看直流偏置是否在AVDD/2附近再用AC耦合看波形。如果偏置不对或者输出幅度异常小先查供电、去耦和MODE配置别急着分析谐波。5.2 一个小型“判决表”从FFT峰的位置反推谐波来源FFT测出来之后按下面的思路快速归类能少走很多弯路FFT现象可能原因验证手段处理方向二次谐波明显高于三次谐波DAC差分非线性或电源耦合看电源纹波换干净电源加强供电去耦后级加LPF三次谐波异常高DAC积分非线性或后级放大削波降低输出幅度查后级工作点检查信号链电平确保没进入非线性区尖峰位置不在整数倍频点相位截断杂散换频率字比较杂散位置变化调整频率控制字摊薄杂散能量高频输出时波形迅速劣化sinc滚降叠加混叠镜像对比低频和中频输出频谱提高后级滤波器阶数降低使用频率上限时域波形带振铃过冲阻抗不匹配或探头补偿不对校准探头检查端接加缓冲输出规范测量频谱出现方波特征的奇次谐波序列芯片被配置成方波模式读回控制寄存器状态修正MODE和OPBITEN位这张表看起来简单但每条我都实际踩过。尤其是“后级放大削波”这个原因经常被忽略AD9833输出幅度本来不大但后级运放如果供电电压不足或者增益设得过高输出进入削波区三次谐波会瞬间暴涨。这时候你拼命加滤波器是没用的信号已经失真回不去了。5.3 滤波前后的实测数据能压到什么程度我在一个输出0.1到1MHz的测试板上记录过一组典型数据滤波前直接测VOUT再测经过“RC粗滤四阶有源低通”之后的输出归一化到基频0dB测量点二次谐波三次谐波带内最高非谐波杂散VOUT裸输出-45 dBc-51 dBc-48 dBc滤后输出-62 dBc-67 dBc-60 dBc数据是在特定频率字和特定板卡布局下的实验结果不是芯片保证值但趋势很明确二次谐波从-45dBc压到-62dBc三级谐波从-51dBc到-67dBc整体SFDR从44dBc提到了60dBc左右。这个水平对于多数激励源、扫频源应用已经完全够用。如果你需要更低的谐波光靠无源滤波很难再往下走可以考虑在后级加一个低失真正弦整形电路或者干脆用更高性能的DDS芯片。但对AD9833这个价位和应用定位来说能把SFDR做到60dBc已经是非常实用的状态了。5.4 布局、电源、接地这些“场外因素”反而最影响谐波最后说几个和电路板布局相关的经验。AD9833的模拟电源和数字电源最好分开走线在引脚附近各放一组1μF加0.1μF的去耦电容0.1μF的陶瓷电容尽量贴近VCC引脚。地线采用单点连接模拟地和数字地不要大面积混在一起否则DAC输出里会看到不少数字串扰毛刺。REF引脚或者CAP/2.5V引脚的外接电容也不要随意改动按数据手册推荐值接。我用过一次“手边没有正好容值”的电容随手换了一个输出波形就多了一根低频抖动分量测出来还以为是芯片坏了查了老半天才定位到是内部稳压器不稳定。测量时还要注意示波器探头的接地点。夹子线太长会在高频形成环路天线把环境里的噪声带进来。最好用接地弹簧或者尽量短的接地方式近距离测VOUT。做FFT时用平均和多点采样能显著压掉随机噪声让谐波和杂散的读数更稳定。把AD9833用好了很多仪器项目都能省下一笔不小的DDS模块费用。谐波不是这颗芯片的缺陷而是DDS工作原理决定的固有属性。你只需要学会测它、认它、滤它就能在成本和信号质量之间找到最舒服的那个平衡点。
返回列表