中科昊芯Start_DSC28034PNT PWM测试
本次测试主要对PWM进行测试,尝试使用DSP的PWM模块完成呼吸灯控制功能。
一、硬件连接
通过原理图可以看出,通过PWM控制呼吸灯有两种方式,一种是通过板子自身的LED完成呼吸灯功能,使用PWM7B驱动板子上的LED301。另一种方式通过板子输出PWM控制外接LED完成。本次采用外接的方式完成呼吸灯测试,也是为了测试输出PWM。由于这一套开发板的U202芯片需要手动连接,控制芯片的方向,因此需要将J302的7和8引脚短接起来,使板子为输出PWM模式。如下图:
二、程序编写
本次程序编写非常不顺利,由于之前使用的都是CCS软件和TI的芯片,这次使用的Haawking-IDE-V2.1.6和中科昊芯的芯片,在程序编写时有很大的不同。
例程代码:
主程序:
#include"dsc_config.h"
#include<syscalls.h>
#include"IQmathLib.h"
#include"epwm.h"
void INTERRUPT epmw1_isr(void);
Uint16 PWM_count=0,PWM_IFR=0;
int main(void)
{
/*将PLL配置成10倍频1分频,配置系统时钟为120M */
InitSysCtrl();
DINT;
InitPieCtrl();
/* 初始化PIE 控制寄存器 */
IER = 0x0000;
IFR = 0x0000;
InitPieVectTable();
EALLOW;
/将epmw1_isr入口地址赋给EPWM1_INT/
PieVectTable.EPWM1_INT = &epmw1_isr;
EDIS;
/每个启用的ePWM模块中的TBCLK(时基时钟)均已停止/
EALLOW;
SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 0;
EDIS;
Epwm1_Init(50000);
/所有使能的ePWM模块同步使用TBCLK/
EALLOW;
SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 1;
EDIS;
IER |= M_INT3;
//使能INT3中断,(关于中断第几组,具体查看中断向量表)
PieCtrlRegs.PIEIER3.bit.INTx1 = 1;//使能ePWM1中断
EINT;
ERTM;
while(1){}
return 0;
}
/epwm1中断函数/
void INTERRUPT epmw1_isr(void)
{
if(PWM_IFR==0)
//当前PWM_count方向是否=0 (=0表示向上,=1表示向下)
{
PWM_count=PWM_count+50;
//PWM_count是用于下面更新CMPA比较值。增加PWM_count
}
else
{
PWM_count=PWM_count-50;
//减少PWM_count
}
if(PWM_count==50000)
//当前PWM_count是否=TBPRD值
{
PWM_IFR=1;
//PWM_count方向变为向下
}
if(PWM_count==0)
//当前PWM_count是否=0
{
PWM_IFR=0;
//PWM_count方向变为向上
}
EPwm1Regs.CMPA.half.CMPA = PWM_count;//更新EPWM1的CMPA比较值
// 清除中断标志位,防止重复进入中断
EPwm1Regs.ETCLR.bit.INT = 1;
// 应答此中断,使得从第3组接收更多其他中断(关于中断第几组,具体查看中断向量表)
PieCtrlRegs.PIEACK.all = PIEACK_GROUP3;
}
epwm.h文件:
#ifndef EPWM_H_
#define EPWM_H_
#include"dsc_config.h"
void Epwm1_Init(Uint16 tbprd);
#endif
epwm.c文件:
#include"epwm.h"
/******************************************************************
函数名:void
InitEPwm1_Gpio(void)
参数:无
返回值:无
作用:配置GPIO0配置成epwm模式,
******************************************************************/
void InitEPwm1_Gpio(void)
{
EALLOW;
GpioCtrlRegs.GPAPUD.bit.GPIO0 = 1;
GpioCtrlRegs.GPAMUX1.bit.GPIO0 = 1;
EDIS;
}
void Epwm1_Init(Uint16 tbprd)
{
InitEPwm1_Gpio();
// 设置TBCLK寄存器功能
EPwm1Regs.TBPRD = tbprd;
// 设置周期值为50000
EPwm1Regs.TBPHS.half.TBPHS = 0x0000;
// 设置相移值为0
EPwm1Regs.TBCTR = 0x0000;
// 清除计数器的值
// 设置比较寄存器功能
EPwm1Regs.CMPA.half.CMPA = 0;
// 设置CMPA比较寄存器A的值为0
EPwm1Regs.CMPB = 0;
// 设置CMPB比较寄存器B的值为0
// 设置计数模式功能
EPwm1Regs.TBCTL.bit.CTRMODE = TB_COUNT_UPDOWN;
// 上下计数模式
EPwm1Regs.TBCTL.bit.PHSEN = TB_DISABLE;
// 禁止相移值装载到计数器
EPwm1Regs.TBCTL.bit.SYNCOSEL = TB_CTR_ZERO;
// 计数器值为0的时候发出同步信号,使得ePWM2/3/4/5/6的计数与1同步,不会产生误差偏移累加
EPwm1Regs.TBCTL.bit.HSPCLKDIV = TB_DIV1;
// 高速时钟预分频为1
TBCLK=150MHz
EPwm1Regs.TBCTL.bit.CLKDIV = TB_DIV1;
// 时钟预分频为1,最终时钟频率:TBCLK=SYSCKOUT/(HSPCLKDIVCLKDIV)=150MHz/(11)=150MHz
// ePWM频率
=TBCLK/(2TBPRD)=150000000/(250000)=1500Hz
// 设置装载模式功能
EPwm1Regs.CMPCTL.bit.SHDWAMODE = CC_SHADOW;
// 设定CMPA为映射模式
EPwm1Regs.CMPCTL.bit.SHDWBMODE = CC_SHADOW;
// 设定CMPB为映射模式
EPwm1Regs.CMPCTL.bit.LOADAMODE = CC_CTR_ZERO;
// 设定在计数值CTR=ZERO时,装载CMPA比较值
EPwm1Regs.CMPCTL.bit.LOADBMODE = CC_CTR_ZERO;
// 设定在计数值CTR=ZERO时,装载CMPB比较值
// 设置动作功能
EPwm1Regs.AQCTLA.bit.CAU = AQ_CLEAR;
//当计数方向为向上,CTR=CMPA时,PWM1A口输出低电平
EPwm1Regs.AQCTLA.bit.CAD = AQ_SET;
//当计数方向为向下,CTR=CMPA时,PWM1A口输出高电平
EPwm1Regs.AQCTLB.bit.CAU = AQ_CLEAR;
//当计数方向为向上,CTR=CMPA时,PWM1B口输出低电平
EPwm1Regs.AQCTLB.bit.CAD = AQ_SET ;
//当计数方向为向下,CTR=CMPA时,PWM1B口输出高电平
// 设置将要更改比较寄存器值的中断功能
EPwm1Regs.ETSEL.bit.INTSEL = ET_CTR_PRD;
// 在CTR=TBPRD时,产生中断
EPwm1Regs.ETSEL.bit.INTEN = 1;
// 使能中断
EPwm1Regs.ETPS.bit.INTPRD = ET_1ST;
// 每一次满足中断条件就产生一次中断
}
三、测验现象
通过将程序烧写到板子中,并通过外接LED到pwm1A引脚可以观察到LED灯逐渐变亮,然后逐渐变暗。