1.PWM输出配置步骤
EPWM相关库函数在DSP2833x_EPwm.c和DSP2833x_EPwm.h文件中。
(1)开启ePWM外设时钟及失能时基模块时钟
使用ePWM外设需开启相应时钟,在对ePWM相关寄存器配置时需要先关闭时基模块时钟,待配置好后再开启,可以保证同步。
EALLOW;
SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 0; // Disable TBCLK within the ePWM要保证时基同步的话,首先在配置TB/CC寄存器时先把时钟关闭,即所有TBCLK停止,不产生。等全部配置后之后再打开,保证时钟同步
SysCtrlRegs.PCLKCR1.bit.EPWM1ENCLK = 1; // 开启ePWM1外设时钟
EDIS;
(2)开启ePWM对应GPIO时钟及初始化配置
PWM输出通道对应F28335的IO口,所以需要使能对应的端口时钟,并将对应的IO口配置为ePWM输出功能。这里使用GPIO10、GPIO11的ePWM6A和ePWM6B功能,即对这两个IO口初始化,使能上拉和GPIO外设复用功能。
InitEPwm6Gpio();//开启时钟,对应ePWM复用功能的开启
(3)初始化时基模块,即配置TB相关寄存器值(确定计数方式、周期、相位)
通过配置时基模块,可以确定计数器的计数方式,周期频率,是否同步等。这里设置ePWM6计数方式为向上计数,不使用相位同步功能,计数器计数频率为系统时钟频率,计数器初值为0。
// Setup Sync
EPwm6Regs.TBCTL.bit.SYNCOSEL = TB_SYNC_DISABLE; // 禁止(即不使用(输出))ePWMxSYNCO信号
// Allow each timer to be sync'ed
EPwm6Regs.TBCTL.bit.PHSEN = TB_DISABLE;//禁止TBCTR加载相位寄存器TBPHS中的值
EPwm6Regs.TBPHS.half.TBPHS = 0;//将相位寄存器中的值清零
EPwm6Regs.TBCTR = 0x0000; // Clear counter时间基准计数寄存器设置为0
EPwm6Regs.TBPRD = tbprd;//设定周期值
EPwm6Regs.TBCTL.bit.CTRMODE = TB_COUNT_UP; // Count up向上计数模式
EPwm6Regs.TBCTL.bit.HSPCLKDIV=TB_DIV1;//采用系统时钟作为TBCLK
EPwm6Regs.TBCTL.bit.CLKDIV=TB_DIV1;//同样是配置TBCLK的时钟
(4)初始化比较模块,配置CC相关寄存器
通过配置CC模块,可以确定比较寄存器值的加载方式,比较器值、占空比等。这里设置ePWM6加载方式为计数器为0加载、比较器值为0。
// Setup shadow register load on ZERO
EPwm6Regs.CMPCTL.bit.SHDWAMODE = CC_SHADOW;// 使用影子寄存器
EPwm6Regs.CMPCTL.bit.SHDWBMODE = CC_SHADOW;// 使用影子寄存器
EPwm6Regs.CMPCTL.bit.LOADAMODE = CC_CTR_ZERO;//CTR等于0时加载
EPwm6Regs.CMPCTL.bit.LOADBMODE = CC_CTR_ZERO;
// Set Compare values
EPwm6Regs.CMPA.half.CMPA = 0; // Set compare A value
EPwm6Regs.CMPB = 0; // Set Compare B value
(5)初始化动作限定模块,配置AQ相关寄存器值
通过配置AQ模块可以确定PWM输出波形方式等。这里配置ePWM6输出,当ePWMA计数器计数到0时输出低电平,当ePWMA计数器计数到CMPA时输出高电平;当ePWMB计数器计数到0时输出低电平,当ePWMB计数器计数到CMPA时输出高电平。
// Set actions
EPwm6Regs.AQCTLA.bit.ZRO = AQ_CLEAR; // Set PWM1A on Zero
EPwm6Regs.AQCTLA.bit.CAU = AQ_SET; // Clear PWM1A on event A, up count
EPwm6Regs.AQCTLB.bit.ZRO = AQ_CLEAR; // Set PWM1B on Zero
EPwm6Regs.AQCTLB.bit.CBU = AQ_SET; // Clear PWM1B on event B, up count
(6)初始化事件触发模块,即配置ET相关寄存器值
当需要事件触发输出控制,就需要对ET相关寄存器配置。这里选择计数器计数到0时,同时使能事件触发中断,每发生一次触发事件就输出PWM。
EPwm6Regs.ETSEL.bit.INTSEL = ET_CTR_ZERO; // Select INT on Zero event
EPwm6Regs.ETSEL.bit.INTEN = 1; // Enable INT
EPwm6Regs.ETPS.bit.INTPRD = ET_1ST; // Generate INT on 1st event每发生一次事件产生中断信号EPWM6_INT
(7)初始化死区模块、斩波模块,即配置DB、PC相关寄存器值
一般不对死区和斩波模块进行配置。
(8)使能时基计数器时钟
各模块寄存器配置好后,最后开启时基计数器时钟,完成这一步,对应IO口便可以输出PWM波
EALLOW;
SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 1; // Start all the timers synced
EDIS;
2.通过ePWM6A和ePWM6B两个管脚输出PWM波,分别控制D6和D7指示灯亮度
主函数代码如下所示
#include "DSP2833x_Device.h" // DSP2833x Headerfile Include File
#include "DSP2833x_Examples.h" // DSP2833x Examples Include File
#include "leds.h"
#include "time.h"//在定时器中控制灯的闪烁
#include "epwm.h"//存放PWM的驱动程序
void main()
{
int i=0;
unsigned char fx=0;//fx指示了一个方向
InitSysCtrl();
InitPieCtrl();
IER = 0x0000;
IFR = 0x0000;
InitPieVectTable();
// LED_Init();
EPWM6_Init(500);//EPWM管脚也即控制了LED,也就是说周期值是500个系统时钟
while(1)
{
if(fx==0)
{
i++;
if(i==300)
{
fx=1;
}
}
else
{
i--;
if(i==0)
{
fx=0;
}
}
EPwm6A_SetCompare(i); //i值最大可以取499,因为ARR最大值是499.
EPwm6B_SetCompare(300-i); //i值最大可以取499,因为ARR最大值是499.
DELAY_US(10*1000);
}
}