在上一篇文章中,笔者以buck电路为例,讲述了数字电源内部的控制环路、采样环节是如何数字化的,以及经典的PID算法是如何让电源稳定的。在本文中,将介绍开发板另一部分的Boost升压电路是如何配置外设寄存器的。
现在开始。
主电路如下,是最传统的电路形式
在上一篇文章中的附件里有开发板完整的原理图。先要说明一下,为了能使初学者更容易明白代码的结构体系和功能,笔者将上文中的buck电路的程序和本文中的boost电路的程序完全分开,即不能在以前buck程序的基础上添加boost的程序代码,否则boost电路工作不正常。代码分开的好处就是让初学者关注数字电源本身的功能实现,至于两套电路代码融合的问题并不是本文关心的重点。
我们开始编写boost升压电路程序代码。
同样在MPLAB X IDE中新建一个工程文件。注意是“新建”,不能用上文中的Buck电路的代码。然后打开MCC。
1)配置系统时钟
系统时钟为60MHz,PWM时钟为240MHz。
2)数字PWM发生器
因为是用PWM2发生器控制Boost主开关管,所以要配置PWM2的寄存器,PWM1用缺省值。
使能PWM总开关“Enable PWM”,然后将PWM的开关周期定为10us(100KHz),最大占空比设为60%(这是数字PWM的一大特点,最大占空比是可以设置的,模拟芯片几乎不可能实现这一功能)。其中“Primary Duty Cycle”寄存器设置最大占空比,“Primaty Phase Shift”寄存器确定开关周期。计算公式如下:
这里240,是在系统时钟里设置的PWM工作时钟240MHz,8是公式的常数,10是需要的PWM开关周期10us的意思。19192的十六进制数就是0x4AF8。同理可以算出对应60%占空比的“Primary Duty Cycle”寄存器值为0x2D00。但是计算公式稍有不同。
接下来
“1”与buck电路有所不同,boost只是用“PWM2L”控制主开关MOS管,所以把“PWM2H”关掉。“2”PWM的输出形式选择“冗余输出”模式。“3”限流比较器是“CMP1”,“4”发生限流时,“PWM2L PWM2H”都处于关断状态。“5”表示每个PWM周期要触发一次ADC的采样,采样频率越快,控制环路的带宽上限越宽。“6”是死区时间,不同于同步降压BUCK电路,boost电路不存在两mos管直通的问题。所以死区是0。数字PWM配置完成。
3)ADC配置
和同步buck电路中的ADC配置相似,但是我们将ADC的采样时间更改为100ns,也可以使电路稳定。至于有何种影响,会在后面文章中涉及。注意,boost输出电压的ADC采样用的是AN3通道。并将中断使能勾选,触发源选“PWM2 Primary Trigger”。其它的中断都应该禁止。
4)限流比较器
上文buck电路用的是CMP2,boost要用CMP1,即内部比较器1,查看电路图可以确认。
比较器输入源是“CMP1B”,完成比较器1的配置。
5)控制环路的算法
自动生成代码后,还是在“adc1.c”文件中添加PID算法代码。先声明变量
输出电压:
将上面的代码添加至
回调函数中。在AN3中断的回调函数中,笔者还加入了“软启动”和“开关控制”的功能,这两项功能很简单,并不影响对PID算法的理解。
“软启动”让电路在初次上电时,最大占空比缓慢的从0到设定值,防止过冲。
“开关控制”是当X3短路时,boost电路开机工作,有输出电压。X3断开时,boost电路停止工作,输出电压为零。
同样用PI补偿器就能使boost控制环路达到稳定。其中Kp=24.6,Ki=0.122
6)控制环路稳定性验证
用网络分析仪测量环路参数。额定输入电压15V,输出电压19.8V
19.8V0.5A(穿越频率2.2KHz,相位裕度73.5°)
输出19.8V0.25A(穿越频率356Hz,相位裕度108.4°)
输出19.8V0A(穿越频率120Hz,相位裕度114°)
输出纹波(0.5A负载,基波95mv,峰峰值1.6V)
负载阶跃响应(0A至0.5A,向下过冲195mv,恢复时间1.41ms)
总结:
通过调整boost控制环路的PI参数,能使电路有较好的稳定性,但是轻载状态时的穿越频率较低,动态响应不够快,有改进的空间。本例中用到的PID算法虽然有点简陋和不完善,但也具备使控制环路稳定的能力,实现了数字电源最基本的功能:稳压及负载变化的快速响应。
下面根据前面内容,笔者认为还有一些技术细节和读者探讨一下:
1)PID公式中的数据是不是用浮点数据结构更直观更简捷。
其它牌子的dsp笔者还没用过,但是单就本文中提到的dspic33系列的dsp,笔者曾尝试将u_N、u_P等这些变量变成float(浮点型)后,单独一个执行PID算法的ADC中断处理程序就要用去40us的时间,已经远远超过了一个PWM周期的时间,严重影响ADC的触发中断。即使将PWM触发ADC采样的频率调整为每5个PWM周期触发一次ADC采样(即控制环路的带宽上限为20KHz),用浮点型数据也是不行的。因为在实际的数字电源中,dsp程序内还会有其它功能代码,也是会占用一定的时间的,PID差分方程占用过多的CPU时间,一定会导致其它功能工作不正常。
2)PID公式中的Kp和Ki如何得到
PID中的Kp和Ki可以用多种方式获得,其实笔者以前的文章中也讲述过一种方法,用simplis+matlab。但是得到的是s域的传递函数,怎么变成差分方程?matlab中有“双线性变换”函数,自动完成s域的传递函数到z域中的差分方程的变换。至于是否准确,还要在实际调试中验证,即使建模不准确,但也能得到一些基础数据,再做调整就事半功倍了。
在MPLAB X IDE中有一个插件,也可以方便计算出结果。
如果什么方法都不会,那就一个一个参数试吧,只要有耐心总是能试出来的。
3)官方开发板工作频率为350KHz,为何笔者的开发板开关频率降为100KHz
为了绕过用汇编语言编写PID算法的代码,只能将PID的代码以C语言写入到ADC中断里,代价就是C语言的执行速度比汇编代码要慢的多,所以为了适应较慢的PID计算速度,我们也只能将开关频率降低。经过验证,100KHz的PWM开关频率时,C语言代码在dsp时钟频率为60MHz速度下,执行PID计算的时间是满足要求的。
4)电流采样都没有斜率补偿
按照理论来说,峰值电流型反馈控制系统要求对电流斜坡进行斜率补偿,但在buck和boost电路中,pwm驱动波形都没有超过50%,所以也就没有必要补偿,而且还减少了一个干扰因素,使环路设计更简单。其实斜坡补偿也可以用代码的方式实现,甚至限流比较器都可以用代码实现,这样才是真正意义上的数字电源。有时间笔者会在这方面探索一下。
5)官方开发板代码内容简介
在这里说说笔者对官方代码的理解,如有不对请多指出,谢谢。
这是所有代码的结构图
“1”main主函数,程序执行的入口,里面包括一些出始化的操作和外设的配置。
“2”这是汇编代码,包含在系统初始化代码内,这段代码只在程序初始化时执行一次。主要的功能就是把要计算的差分方程的参数装入CPU内核的备用工作寄存器中,目地是在进入或离开ADC中断时,尽量节省工作寄存器压入堆栈和弹出堆栈的时间,从而减少整体ADC中断处理程序的执行时间,这在高频的PWM应用中是非常重要的。在代码中有下面一条汇编指令:
就是告诉CPU当ADC1有中断产生时,内核要切换到该备用工作寄存器。怎么把ADC中断与上图黄色标示出的“CTXTSWP #0x01;”绑定起来?在mcc界面下,“Interrupt Module”选项中,比如,要把ADC1通道中的AN11中断操作与1号备用工作寄存器绑定,就选择“CTXT1”。从图上可以发现,该颗dsp内核其中是有4套备用工作寄存器可供切换,意味着dsp内核支持多种控制算法的切换,这是数字电源最大的优点之一。
“3”是数字电源控制环路的算法,也是用汇编代码写的,核心功能很简单,处理ADC产生的中断,并调用库中的算法函数。注意,如果是用mcc生成的代码,一定要在C代码中,去掉相应的ADC中断处理程序,否则与汇编代码中的中断程序产生冲突,不知该执行哪个中断处理程序。前面提到的库函数就在“5”,将它包含进工程文件中并且要在“init.h”文件中包含该函数库的头文件。
然后就可以调用里面的算法了。该算法函数库中包含2P2Z、3P3Z、4P4Z和PID等多种算法,方便程序员调用。具体函数名称还是要查看帮助手册。
“4” 其实是由MPLAB X IDE中的一个插件“Digital Compensator Design Tool”生成的控制环路的参数,也比较方便易用,笔者用的不多。对此感兴趣的读者可以试试。
以上就是数字电源控制环路的主功能,官方软件代码中还包括LCD显示、通讯、负载控制等功能,读者可以自己探索。