简介:一套完整的电赛双向DC-DC变换器赛题方案,面向全国大学生电子设计竞赛参赛者、电气工程专业毕业设计学生及电力电子入门开发者,解决从电路原理到软硬件联调的全流程参考需求。资源共25个文件,压缩包5.14MB,涵盖原理图(SCHDOC)、PCB设计源文件(PCBDOC)、基于STC12C5A60S2的Keil工程(C/HEX/A51源码)、设计论文(DOCX)等类型,可分别对应硬件拓扑理解、板级布局实现、控制算法烧录与理论分析验证环节。已有251人学习下载。内含2020年全国电子设计大赛电源方向的双向变换器原始工程,既展示Boost/Buck双向升降压的功率级设计细节,也包含PWM调制、电压电流闭环调节的固件代码,论文部分则补充效率优化与稳定性分析思路。适合需要对照完整项目快速上手、或希望复现竞赛作品的人群,可直接基于Altium Designer与Keil环境打开源文件进行二次开发与调试。
1. 双向DC-DC变换器:电赛里「看着简单、上电就炸」的硬骨头
双向DC-DC变换器是电赛电源题里最典型的双修题型:同一套主电路,既要降压给电池充电,又要升压把电池能量送回母线。原理图翻来覆去就是半桥加电感、两侧电容,但很多组打到样回来,上电就冒烟,最后连题目都交不完整。我带过好几届队伍做这个方向,最深的感受是:拓扑本身不值钱,值钱的是PCB布局、死区参数、数字环路这三样「看不见的东西」。这篇文章按我自己的落地顺序拆开讲,从拓扑选型、参数计算,到原理图PCB、源代码调参,再到最常见的翻车现场和验证方法,新手能照着复现,熟手也能对比一下自己的边界。
2. 先定拓扑与指标:双向半桥为什么是电赛的主流方案
2.1 拓扑选型:双向Buck-Boost与两级式怎么选
电赛题目里最常见的双向DC-DC,工作点是低压侧电池(典型24V)和高压侧母线(典型48V)之间互传能量,功率从几十瓦到两三百瓦。这个范围下,我一般会优先选双向Buck-Boost半桥拓扑,也就是一个半桥、一个电感、两侧各一组电容。降压模式时高压侧上管高频开关,低压侧下管做同步整流;升压模式时角色互换,下管高频,上管同步。两个方向共用一个电感,器件数量最少,控制也最直观。
还有一种两级式方案,前级Buck调压、后级全桥做隔离,适合功率更大(500W以上)或者输入输出需要电气隔离的题目。但电赛大多数题目不要求隔离,加一级隔离只会把效率做低、把调试周期拉长。我做过的模拟项目X就是把第一版做成两级式,结果光变压器设计就耗了三天,后面换回双向半桥一天就调通了。选型时可以按下面这张表快速判断:
| 对比项 | 双向半桥(同步Buck-Boost) | 两级隔离式 |
|---|---|---|
| 典型功率 | ≤300W | ≥500W |
| 效率 | 90%~95% | 85%~92% |
| 控制复杂度 | 低,一套环路 | 高,两级分别控制 |
| 电气隔离 | 无 | 有 |
| 元件数量 | 少 | 多,含变压器 |
| 电赛适配度 | 高 | 低,除非题目强制隔离 |
2.2 控制架构:CC/CV双环与模式状态机
控制策略上,双向DC-DC需要跑三种基本模式:降压恒流充电、降压恒压充电、升压恒流放电。恒流和恒压本质上是两个PI环,哪个环起作用取决于当前误差,我用一个简单的状态机管理模式切换,而不是直接在PI输出里取小值。取小值虽然也能工作,但模式切换瞬间容易产生电流尖峰,状态机加软启动过渡会更稳。
状态机跑在10kHz~20kHz的中断里,每个周期做一次ADC采样、一次PI计算、一次PWM占空比更新。10kHz的控制频率对100kHz的开关频率来说是够用的,而且方便用标准外设库的定时器更新事件触发中断。
模式切换要处理的边界是「恒流切恒压」:当低压侧电压接近目标电压时,电流环让位给电压环,如果不做任何处理,积分器里存着大电流误差,切换瞬间输出会突变。我的做法是切换前把新激活环路的积分值复位,同时限制每次PWM占空比的变化步长,也就是给占空比加一个斜率限制,通常每秒不超过10%的满量程。
2.3 主电路参数计算:电感、MOS管、驱动与采样
我以一个典型电赛工作点为例:高压侧48V,低压侧24V,额定功率200W,开关频率100kHz。第一步算电感,双向半桥在降压模式下的电感纹波公式是ΔIL = (Vout/Vin) × (Vin-Vout) / (f × L)。取额定电流4.17A的20%作为纹波,即ΔIL=0.83A,代入后L = (24/48)×(48-24)/(100000×0.83),算出来约145μH,我取标称120μH~150μH都行,饱和电流要留到8A以上。
第二步选MOS管:耐压按高压侧电压的1.5~2倍,48V系统选80V~100V耐压的管子;额定电流按低压侧峰值电流6A左右再加1.5倍余量,也就是选20A以上的。RDS(on)尽量低,几毫欧到十几毫欧,Qg也要小,这样驱动损耗和开关损耗才压得住。驱动芯片用常见的半桥驱动,自举电容取100nF~1μF,并在旁边并联一个100nF的高速瓷片电容。
第三步是采样参数。电流采样电阻一般取1mΩ~5mΩ的合金电阻,我用3mΩ、额定电流6A时压降18mV,后面接一个差分放大器放大到1.8V左右,正好匹配MCU的ADC满量程。电压采样用1%精度电阻分压,中点对地并一个100nF~1μF电容做滤波。核心参数见下表:
| 参数 | 计算值 | 说明 |
|---|---|---|
| 电感L | 120μH~150μH | 纹波电流≤20%,饱和电流≥8A |
| 高压侧电容 | 470μF电解+若干22μF瓷片 | 靠近半桥放置,提供高频脉冲电流 |
| 低压侧电容 | 220μF电解+若干10μF瓷片 | 兼顾输出纹波和负载瞬态 |
| MOS管 | 80V~100V / 20A以上 | RDS(on)尽量小,Qg尽量小 |
| 自举电容 | 0.1μF~1μF | X7R/C0G材质,紧贴驱动芯片 |
| 采样电阻 | 3mΩ 合金电阻 | 封装2512或更大,开尔文走线 |
| 电流放大倍数 | 100倍 | 满量程对应约6A |
| 开关频率 | 100kHz | 可在80kHz~150kHz调整 |
这套参数不是唯一的答案,但量级可以作为模板。如果你的题目是低压12V、高压36V,或者功率只有60W,按公式重新算一遍就行,不用照抄。
3. 原理图与PCB这样画,才能避免「跑不起来」的返工
3.1 原理图五大模块:功率级、驱动、采样、保护、MCU
原理图我按功率级、驱动级、采样级、保护级、MCU五块画,每块都留下独立的测试点。功率级就是半桥两颗MOS、电感、两侧电容,再加一个RC吸收电路(典型100pF~1nF串联10Ω~47Ω),并联在开关节点对地之间,用于抑制开关振铃。注意RC吸收先预留封装,实测振铃不明显可以不焊。
驱动级是半桥驱动芯片加自举电容,驱动电阻选3.3Ω~10Ω,大小直接影响开关速度和振铃。驱动电阻太小,开关瞬间di/dt太大,容易振铃甚至炸管;太大则开关损耗高。我一般先贴4.7Ω,示波器看SW节点波形再微调。
采样级两条路:电压采样用电阻分压,两个分压电阻都选1%精度温漂低的类型;电流采样用差分放大器,注意放大器的共模输入范围要覆盖低压侧电压范围,很多同学选错放大器导致大电流时读数非线性。运放输出到ADC之间加一个RC低通,截止频率取开关频率的1/10左右,也就是10kHz,滤掉开关噪声,又能保留控制带宽内的信号。
保护级一定要有硬件过流比较器,输出直接接MCU定时器的刹车输入,过流时硬件立即封锁PWM,不依赖软件中断。软件过流最快也要几个微秒才反应,硬件比较器可以做到百纳秒级,差别很大。
MCU部分选带互补PWM输出和可编程死区插入的型号,确认PWM引脚电平与驱动芯片输入兼容,不兼容就加电平转换或选用3.3V逻辑兼容的驱动芯片。
3.2 PCB布局:功率回路面积、开尔文走线与地平面
PCB布局是双向DC-DC最容易拉胯的地方。原理图没问题、代码没问题,照样上电炸管或效率低得离谱,十有八九是布局问题。我自己总结的优先级是:功率回路面积 > 驱动芯片位置 > 采样走线 > 地平面。
功率回路面积是第一位。降压模式下的高频电流路径是:高压侧母线电容→上管→电感→低压侧电容→下管→回到母线电容。这个环路包围的面积越小,寄生电感越小,开关尖峰越低。具体做法是把高压侧母线电容紧贴半桥,开关节点与电感之间的铜皮短而宽,不要绕圈。上管的漏极、下管的源极都接到母线电容的同一对焊盘附近,让高频电流在板子上走「直线」。
驱动芯片要放在被驱动的MOS管旁边,栅极驱动线越短越好。自举电容紧贴驱动芯片的Boot引脚和开关节点引脚,这段线长了,上管驱动电压会掉得很厉害。
电流采样用开尔文接法:采样电阻两端各引一对线,一对走功率电流,一对走采样信号,信号线在采样电阻本体处就近差分引出,走到运放输入端,不要在功率地回路里绕一圈。采样线还要远离开关节点,避免容性耦合。模拟地与功率地在采样电阻的功率地侧单点相连,其他地方完全分开。
3.3 打样前检查清单:丝印、测试点、电气规则
打样前花半小时过一遍检查清单,比板子回来再返工省一天。以下是我每次发板前的固定动作:
电气规则检查:电源极性有没有接反,电容耐压够不够,MOS管引脚顺序对不对,驱动芯片供电电压是否匹配。电感下方不要铺大面积铜皮,否则涡流会发热,这一点很多PCB软件检查不出来,纯靠人工看。
丝印检查:MOS管方向、二极管方向、电解电容极性,这三样错了基本就是上电烟花。我会在丝印层加粗标注地线、母线、电池三个关键网络。
测试点检查:母线电压、电池电压、开关节点、PWM信号、电流采样输出这五个测试点必须有,用标准的测试环或焊盘。调试时示波器探头要有个地方下针,没有测试点的板子调起来非常痛苦。
爬电距离检查:48V系统不算高压,但高低压网络之间还是留至少1mm间距,潮湿环境留2mm更稳。螺丝孔附近走线退避1mm以上,避免安装时划破铜皮短路。
4. 源代码里的关键:互补PWM、数字PI与模式切换
4.1 互补PWM输出与死区配置
双向半桥需要两路带死区的互补PWM,死区必须由硬件定时器插入,不能靠软件翻转,否则一次中断抖动就直接直通炸管。以下代码基于某款带高级定时器的32位MCU的标准外设库写成,核心是配置时基、输出比较和死区刹车三个结构体:
/* 定时器1初始化:100kHz互补PWM,带死区 */ void PWM_Init(void) { TIM_TimeBaseInitTypeDef tb; TIM_OCInitTypeDef oc; TIM_BDTRInitTypeDef bdtr; /* 100kHz:定时器时钟72MHz,ARR=720-1 */ tb.Period = 720 - 1; /* 720/72MHz = 10us */ tb.Prescaler = 0; tb.CounterMode = TIM_CounterMode_Up; TIM_TimeBaseInit(TIM1, &tb); /* PWM1模式,初始占空比50% */ oc.OCMode = TIM_OCMode_PWM1; oc.Pulse = 360; /* 占空比 = Pulse/(Period+1) */ oc.OCPolarity = TIM_OCPolarity_High; oc.OCNPolarity = TIM_OCPolarity_High; TIM_OC1Init(TIM1, &oc); /* 死区约234ns:DeadTime=18,DTS=72MHz */ bdtr.DeadTime = 18; bdtr.BreakState = TIM_BreakState_Enable; bdtr.BreakPolarity = TIM_BreakPolarity_Low; bdtr.AutomaticOutputState = TIM_AutomaticOutputState_Enable; TIM_BDTRConfig(TIM1, &bdtr); TIM_OC1PreloadConfig(TIM1, TIM_OCPreload_Enable); TIM_ARRPreloadConfig(TIM1, ENABLE); TIM_CtrlPWMOutputs(TIM1, ENABLE); TIM_Cmd(TIM1, ENABLE); }死区寄存器值不是随便填的。以定时器时钟72MHz为例,DeadTime每加1大约对应13.9ns,填18就是约250ns。对100kHz开关频率下的常见MOS管,100ns~400ns是比较稳妥的范围,具体数值要结合你选的管子驱动延迟来定。程序里预留一个变量,调参时直接改寄存器值在线观察效率,不需要重新编译烧录。
注意Pulse初始值我故意设为360,也就是50%占空比,但代码里真正使能主输出是在所有初始化完成之后,避免上电瞬间PWM引脚出现不受控的乱跳。
4.2 数字PI控制器与CC/CV切换的核心代码
数字PI是整个控制环的核心,我一般不用完全浮点库里的复杂写法,就用一个结构体加一个更新函数。重点是抗积分饱和和最小占空比限制,这两个不做,炸管只是时间问题:
typedef struct { float Kp; /* 比例系数,初始0.5~2.0 */ float Ki; /* 积分系数,初始0.01~0.1 */ float out_max; /* 占空比上限,0.90 */ float out_min; /* 占空比下限,0.05 */ float integral; /* 积分累计值 */ float tau; /* 控制周期,0.0001s @10kHz */ } PI_TypeDef; float PI_Update(PI_TypeDef *pi, float ref, float fb) { float err = ref - fb; float out; /* 积分项,带输出限幅抗饱和 */ pi->integral += pi->Ki * err * pi->tau; pi->integral = CLAMP(pi->integral, pi->out_min, pi->out_max); out = pi->Kp * err + pi->integral; out = CLAMP(out, pi->out_min, pi->out_max); return out; }out_min设为0.05不是随便写的。CCM模式下占空比过低会让电感电流断续,环路特性突然改变,轻载启动时特别容易冲过头,0.05~0.1的下限能挡住大部分启动异常。CLAMP宏做限幅,误差极大时积分也不会飞。
CC/CV切换逻辑放在10kHz控制中断里,伪代码如下:
void Control_ISR(void) { float v_lo = ADC_GetVoltage(LO_V); /* 低压侧电压 */ float v_hi = ADC_GetVoltage(HI_V); /* 高压侧电压 */ float i_lo = ADC_GetCurrent(LO_I); /* 低压侧电流 */ float duty; switch (state) { case MODE_BUCK_CV: /* 恒压:目标是低压侧电压 */ duty = PI_Update(&pi_v, v_ref, v_lo); break; case MODE_BUCK_CC: /* 恒流:目标是低压侧电流 */ duty = PI_Update(&pi_i, i_ref, i_lo); /* 电压超过目标,自动切恒压 */ if (v_lo > v_ref) state = MODE_BUCK_CV; break; case MODE_BOOST_CC: duty = PI_Update(&pi_i_boost, i_ref, i_lo); break; default: duty = 0.1f; /* IDLE模式下低压输出 */ break; } PWM_SetDuty(duty); }切入恒压模式时,pi_i会保留积分值,需要立刻清零,否则切换瞬间PI输出的历史积分会叠加到新环路上。我这里直接在切换分支里执行pi_i.integral = 0.0f,同时把pi_v的积分也复位,保证新环路从零开始。这个细节是调模式切换时最容易漏的。
AI 在写代码时往往会忽略这个积分复位问题,实际调试时你会发现CC切CV瞬间电压过冲0.5V以上,多半就是积分没清。
4.3 调试顺序:先开环后闭环,先电压环后电流环
代码写完后不要直接上闭环,我的调试顺序是:开环固定占空比跑通、再调电压环、最后加电流环。开环阶段把占空比固定在一个安全值,比如0.5,空载上电,示波器看SW节点波形,确认死区正常、没有直通、振铃可接受。这一步能排除大部分硬件问题。
电压环调试从低压侧给定目标电压的一半开始,比如目标24V就先给12V,看稳态精度和动态响应,然后逐步抬高。电流环放到最后,给定电流从0.2倍额定值开始,确认恒流精度和纹波都正常,再往额定值加。
PI参数的经验值:控制周期100μs下,Kp从1.0附近起步,太小响应慢,太大的话电压会振;Ki从0.01起动,等Kp调稳了再慢慢加。每调一个参数,记录输出电压波形和电流波形,不要凭感觉记。
5. 双向DC-DC避坑手册:最容易翻车的5个现场
5.1 自举电容容量不够导致上管驱动电压跌落
现象:重载时上管温度明显高于下管,SW节点波形高电平幅度达不到母线电压,继续加大负载就直接炸管。
原因:上管导通时栅极驱动能量全靠自举电容,电容量太小,高占空比下电容电荷被持续消耗,驱动电压一路跌到欠压阈值以下,上管进入线性区,导通损耗飙增。
解决:自举电容换成100nF~1μF的X7R或C0G瓷片电容,紧贴驱动芯片的Boot引脚;高频开关时再并一个10nF小瓷片。确认自举二极管是高频快恢复类型,不要用普通整流二极管。如果占空比经常超过90%,则要考虑改成独立的隔离驱动电源。
5.2 电流采样噪声导致CC模式振荡
现象:恒流模式电感电流波形上有明显毛刺,电流读数来回跳,输出电压伴随低频嘶嘶声。
原因:采样时刻落在开关瞬间附近,开关节点的高dV/dt通过寄生电容耦合进采样走线;或者运放输出到ADC之间的RC截止频率设得太高,噪声没滤掉。
解决:运放输出到ADC之间加二阶RC低通,截止频率取10kHz左右,大约是开关频率的1/10。ADC采样时刻通过定时器触发,把采样点移到PWM周期的中间或者谷值,远离开关边沿。采样走线用开尔文差分引一对线,不要在功率地回流路径上取信号。
5.3 空载/轻载启动炸管
现象:输出电压还没建立,电流瞬间冲到保护值,MOS击穿,板子冒烟。
原因:输出电容初始电压为零,PI环误差极大,积分快速饱和后输出100%占空比,电感电流不受控。轻载时电感电流断续,环路增益变化也容易让系统失控。
解决:代码里上电初始占空比限制在0.1~0.2,PI积分上限不能超过0.3,等输出电压建立后再逐步放开。启动阶段用软启动斜坡,目标是让占空比以固定斜率爬升。还要确保MCU复位期间PWM引脚保持低电平,最好加一个下拉电阻,防止复位瞬间引脚悬空导致管子全开。
5.4 死区时间设置不当导致效率低或直通
现象:效率测出来只有80%出头,或者跑一会儿低压侧管子就烧了,SW波形上能看到明显直通尖峰。
原因:死区太大,两个管子都关断时电流从体二极管走,二极管压降0.7V左右,损耗成倍增加;死区太小,上管还没完全关断下管就开,出现短暂直通。
解决:用示波器放大看SW节点波形,测量上下管都关断的时间间隔。死区时间应该大于上管关断延迟与下管开通延迟之差,再乘1.5倍余量。100kHz下常见值是100ns~400ns,先按200ns调,再根据效率曲线微调。效率对死区异常敏感,每次调完死区都重新测效率,能明显看到变化。
5.5 万用表测纹波和效率,数据完全不可信
现象:万用表显示的纹波电压和示波器差一个数量级,算出来的效率波动很大。
原因:万用表频率响应只有几百赫兹到几千赫兹,量不到开关纹波的真实峰值;示波器探头用长地线夹子时,地线电感会引入额外尖峰,数字虚高。
解决:纹波用示波器测,探头去掉夹子,用弹簧地线或铜线直接接地,尽量缩短回路电感。效率测量用同一台直流电源和电子负载,电压电流都用四线法接,分别记录输入电压、输入电流、输出电压、输出电流,再算效率。保留原始数据,论文里要用。
6. 最后一公里:用效率与动态响应验证这套设计
6.1 双向效率测试:别只看一个方向
测试流程要固定:低压侧接直流源、高压侧接电子负载,测升压方向;反过来降压方向。每个功率点记录四个量,计算效率,画成两条曲线。注意满载之前先把死区和驱动电阻调到位,不然测出的效率低到会让你误判哪一块有问题。
6.2 动态响应:负载阶跃与电压跌落
电子负载设成周期性阶跃,比如10%负载跳到50%再跳回,示波器同时看输出电压和电流。记录过冲量和恢复时间。恢复时间过长优先加Kp,出现振荡就减Ki。
6.3 论文实测素材:三张图就够了
论文里放双向效率曲线、负载阶跃波形、稳态纹波波形这三张图就够了,每张图把关键参数标上去:死区时间、电感感值、开关频率。我习惯第一张图横轴功率百分比、纵轴效率,两个方向用不同颜色;第二张标过冲幅度和恢复时间;第三张标纹波峰峰值。这套图配合参数表,比大段文字说明有说服力得多。
我每次打完板,第一步永远是接低压电源、限流100mA,检查空载功耗再上高压。这个习惯救过我很多次,有两次都是电流异常,最后查出来是电容焊反和MOS封装画反。电赛这种时间紧的题目,多花半小时做这一步,比炸两块板再返工划算得多。希望帮到你。
本文还有配套的精品资源,点击获取