DSP CCS12.00 芯片:TMS320F28335 PWM 的设计
DSP CCS12.00 芯片:TMS320F28335 PWM 的设计
先学习怎么 发出 PWM 的波形 (知识点看后面)
1.PWM输出配置步骤
EPWM相关文件 在DSP2833x_EPwm.c和DSP2833x_EPwm.h文件中。
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外设复用功能。
3.初始化时基模块,即配置TB相关寄存器值(确定计数方式、周期、相位)
通过配置时基模块,可以确定计数器的计数方式,周期频率,是否同步等。这里设置ePWM6计数方式为向上计数,不使用相位同步功能,计数器计数频率为系统时钟频率,计数器初值为0。
// Setup Sync
EPwm1Regs.TBCTL.bit.SYNCOSEL = TB_SYNC_DISABLE; // 禁止(即不使用(输出))ePWMxSYNCO信号
// Allow each timer to be sync'ed
EPwm1Regs.TBCTL.bit.PHSEN = TB_DISABLE;//禁止TBCTR加载相位寄存器TBPHS中的值
EPwm1Regs.TBPHS.half.TBPHS = 0;//将相位寄存器中的值清零
EPwm1Regs.TBCTR = 0x0000; // Clear counter时间基准计数寄存器设置为0
EPwm1Regs.TBPRD = tbprd;//设定周期值
EPwm1Regs.TBCTL.bit.CTRMODE = TB_COUNT_UP; // Count up向上计数模式
EPwm1Regs.TBCTL.bit.HSPCLKDIV=TB_DIV1;//采用系统时钟作为TBCLK
EPwm1Regs.TBCTL.bit.CLKDIV=TB_DIV1;//同样是配置TBCLK的时钟
(4)初始化比较模块,配置CC相关寄存器
通过配置CC模块,可以确定比较寄存器值的加载方式,比较器值、占空比等。这里设置ePWM6加载方式为计数器为0加载、比较器值为0。
// Setup shadow register load on ZERO
EPwm1Regs.CMPCTL.bit.SHDWAMODE = CC_SHADOW;// 使用影子寄存器
EPwm1Regs.CMPCTL.bit.SHDWBMODE = CC_SHADOW;// 使用影子寄存器
EPwm1Regs.CMPCTL.bit.LOADAMODE = CC_CTR_ZERO;//CTR等于0时加载
EPwm1Regs.CMPCTL.bit.LOADBMODE = CC_CTR_ZERO;
// Set Compare values
EPwm1Regs.CMPA.half.CMPA = 0; // Set compare A value
EPwm1Regs.CMPB = 0; // Set Compare B value
(5)初始化动作限定模块,配置AQ相关寄存器值
通过配置AQ模块可以确定PWM输出波形方式等。这里配置ePWM6输出,当ePWMA计数器计数到0时输出低电平,当ePWMA计数器计数到CMPA时输出高电平;当ePWMB计数器计数到0时输出低电平,当ePWMB计数器计数到CMPA时输出高电平。
// Set actions
EPwm1Regs.AQCTLA.bit.ZRO = AQ_CLEAR; // Set PWM1A on Zero
EPwm1Regs.AQCTLA.bit.CAU = AQ_SET; // Clear PWM1A on event A, up count
EPwm1Regs.AQCTLB.bit.ZRO = AQ_CLEAR; // Set PWM1B on Zero
EPwm1Regs.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;
9.完整代码 ; 代码功能 : 示波器 PWM 波形: 频率:1kHZ 占空比 : 75%
代码:
//###########################################################################
//
// 文件名: Example_2833xEPwmUpDownAQ.c
//
// 标题: 动作限定模块 - 使用增/减计数模式
//
//
// 此程序需要 DSP2833x头文件.
//
// 按以下描述用示波器观察 ePWM1 - ePWM3引脚
//
// EPWM1A定义在GPIO0上
// EPWM1B定义在GPIO1上
//
// EPWM2A定义在GPIO2上
// EPWM2B定义在GPIO3上
//
// EPWM3A定义在GPIO4上
// EPWM3B定义在GPIO5上
//
// 根据在RAM中调试的需要,这个项目配置成"boot to SARAM".2833x引导模式
// 表如下显示. 常用的还有"boot to Flash"模式,当程序在RAM调试完善后就
// 可以将代码烧进Flash中并使用"boot to Flash"引导模式.
//
// $Boot_Table:
//
// GPIO87 GPIO86 GPIO85 GPIO84
// XA15 XA14 XA13 XA12
// PU PU PU PU
// ==========================================
// 1 1 1 1 Jump to Flash
// 1 1 1 0 SCI-A boot
// 1 1 0 1 SPI-A boot
// 1 1 0 0 I2C-A boot
// 1 0 1 1 eCAN-A boot
// 1 0 1 0 McBSP-A boot
// 1 0 0 1 Jump to XINTF x16
// 1 0 0 0 Jump to XINTF x32
// 0 1 1 1 Jump to OTP
// 0 1 1 0 Parallel GPIO I/O boot
// 0 1 0 1 Parallel XINTF boot
// 0 1 0 0 Jump to SARAM <- "boot to SARAM"
// 0 0 1 1 Branch to check boot mode
// 0 0 1 0 Boot to flash, bypass ADC cal
// 0 0 0 1 Boot to SARAM, bypass ADC cal
// 0 0 0 0 Boot to SCI-A, bypass ADC cal
// Boot_Table_End$
//
// 功能描述:
//
// 本例配置ePWM1, ePWM2, ePWM3产生产生EPWMxA和EPWMxB波形
//
// 在ePWM中断子程序中,比较寄存器CMPA和CMPB的值被修改
//
// 本例时基时钟被配置为增减计数模式
// 通过示波器观察EPWM1A/B, EPWM2A/B 和 EPWM3A/B波形
//
//
//###########################################################################
// 释放日期:2013.11.25
//###########################################################################
#include "DSP2833x_Device.h" // DSP2833x Headerfile Include File
#include "DSP2833x_Examples.h" // DSP2833x Examples Include File
typedef struct
{
volatile struct EPWM_REGS *EPwmRegHandle;
Uint16 EPwm_CMPA_Direction;
Uint16 EPwm_CMPB_Direction;
Uint16 EPwmTimerIntCount;
Uint16 EPwmMaxCMPA;
Uint16 EPwmMinCMPA;
Uint16 EPwmMaxCMPB;
Uint16 EPwmMinCMPB;
}EPWM_INFO;
// Prototype statements for functions found within this file.
void InitEPwm1Example(void);
void InitEPwm2Example(void);
void InitEPwm3Example(void);
interrupt void epwm1_isr(void);
interrupt void epwm2_isr(void);
interrupt void epwm3_isr(void);
void update_compare(EPWM_INFO*);
// Global variables used in this example
EPWM_INFO epwm1_info;
EPWM_INFO epwm2_info;
EPWM_INFO epwm3_info;
// Configure the period for each timer
#define EPWM1_TIMER_TBPRD 2000 // Period register
#define EPWM1_MAX_CMPA 1950
#define EPWM1_MIN_CMPA 50
#define EPWM1_MAX_CMPB 1950
#define EPWM1_MIN_CMPB 50
#define EPWM2_TIMER_TBPRD 2000 // Period register
#define EPWM2_MAX_CMPA 1950
#define EPWM2_MIN_CMPA 50
#define EPWM2_MAX_CMPB 1950
#define EPWM2_MIN_CMPB 50
#define EPWM3_TIMER_TBPRD 2000 // Period register
#define EPWM3_MAX_CMPA 950
#define EPWM3_MIN_CMPA 50
#define EPWM3_MAX_CMPB 1950
#define EPWM3_MIN_CMPB 1050
// To keep track of which way the compare value is moving
#define EPWM_CMP_UP 1
#define EPWM_CMP_DOWN 0
void main(void)
{
// Step 1. Initialize System Control:
// PLL, WatchDog, enable Peripheral Clocks
// This example function is found in the DSP2833x_SysCtrl.c file.
InitSysCtrl();
// Step 2. Initalize GPIO:
// This example function is found in the DSP2833x_Gpio.c file and
// illustrates how to set the GPIO to it's default state.
// InitGpio(); // Skipped for this example
// For this case just init GPIO pins for ePWM1, ePWM2, ePWM3
// These functions are in the DSP2833x_EPwm.c file
InitEPwm1Gpio();
InitEPwm2Gpio();
InitEPwm3Gpio();
// Step 3. Clear all interrupts and initialize PIE vector table:
// Disable CPU interrupts
DINT;
// Initialize the PIE control registers to their default state.
// The default state is all PIE interrupts disabled and flags
// are cleared.
// This function is found in the DSP2833x_PieCtrl.c file.
InitPieCtrl();
// Disable CPU interrupts and clear all CPU interrupt flags:
IER = 0x0000;
IFR = 0x0000;
// Initialize the PIE vector table with pointers to the shell Interrupt
// Service Routines (ISR).
// This will populate the entire table, even if the interrupt
// is not used in this example. This is useful for debug purposes.
// The shell ISR routines are found in DSP2833x_DefaultIsr.c.
// This function is found in DSP2833x_PieVect.c.
InitPieVectTable();
// Interrupts that are used in this example are re-mapped to
// ISR functions found within this file.
EALLOW; // This is needed to write to EALLOW protected registers
PieVectTable.EPWM1_INT = &epwm1_isr;
PieVectTable.EPWM2_INT = &epwm2_isr;
PieVectTable.EPWM3_INT = &epwm3_isr;
EDIS; // This is needed to disable write to EALLOW protected registers
// Step 4. Initialize all the Device Peripherals:
// This function is found in DSP2833x_InitPeripherals.c
// InitPeripherals(); // Not required for this example
// For this example, only initialize the ePWM
EALLOW;
SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 0;
EDIS;
InitEPwm1Example();
InitEPwm2Example();
InitEPwm3Example();
EALLOW;
SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 1;
EDIS;
// Step 5. User specific code, enable interrupts:
// Enable CPU INT3 which is connected to EPWM1-3 INT:
IER |= M_INT3;
// Enable EPWM INTn in the PIE: Group 3 interrupt 1-3
PieCtrlRegs.PIEIER3.bit.INTx1 = 1;
PieCtrlRegs.PIEIER3.bit.INTx2 = 1;
PieCtrlRegs.PIEIER3.bit.INTx3 = 1;
// Enable global Interrupts and higher priority real-time debug events:
EINT; // Enable Global interrupt INTM
ERTM; // Enable Global realtime interrupt DBGM
// Step 6. IDLE loop. Just sit and loop forever (optional):
for(;;)
{
asm(" NOP");
}
}
interrupt void epwm1_isr(void)
{
// Update the CMPA and CMPB values
update_compare(&epwm1_info);
// Clear INT flag for this timer
EPwm1Regs.ETCLR.bit.INT = 1;
// Acknowledge this interrupt to receive more interrupts from group 3
PieCtrlRegs.PIEACK.all = PIEACK_GROUP3;
}
interrupt void epwm2_isr(void)
{
// Update the CMPA and CMPB values
update_compare(&epwm2_info);
// Clear INT flag for this timer
EPwm2Regs.ETCLR.bit.INT = 1;
// Acknowledge this interrupt to receive more interrupts from group 3
PieCtrlRegs.PIEACK.all = PIEACK_GROUP3;
}
interrupt void epwm3_isr(void)
{
// Update the CMPA and CMPB values
update_compare(&epwm3_info);
// Clear INT flag for this timer
EPwm3Regs.ETCLR.bit.INT = 1;
// Acknowledge this interrupt to receive more interrupts from group 3
PieCtrlRegs.PIEACK.all = PIEACK_GROUP3;
}
void InitEPwm1Example()
{
// Setup TBCLK M=100 0000
EPwm1Regs.TBPRD = 50000; // Set timer period 801 TBCLKs 频率控制 T =50000 * 1/ 50M hz = (1/ 1000) s f=1/T =1000HZ =1KZ
EPwm1Regs.TBPHS.half.TBPHS = 0x0000; // Phase is 0 相位设置
EPwm1Regs.TBCTR = 0x0000; // Clear counter
// Set Compare values
EPwm1Regs.CMPA.half.CMPA = EPWM1_MIN_CMPA; // Set compare A value
EPwm1Regs.CMPB = EPWM1_MAX_CMPB; // Set Compare B value
// Setup counter mode
EPwm1Regs.TBCTL.bit.CTRMODE = TB_COUNT_UPDOWN; // Count up 增计数模式
EPwm1Regs.TBCTL.bit.PHSEN = TB_DISABLE; // Disable phase loading 禁止相位寄存器加载
EPwm1Regs.TBCTL.bit.HSPCLKDIV = TB_DIV1; // Clock ratio to SYSCLKOUT 不分频
EPwm1Regs.TBCTL.bit.CLKDIV = TB_DIV1; //不分频
// Setup shadowing
EPwm1Regs.CMPCTL.bit.SHDWAMODE = CC_SHADOW; // 双缓冲操作,所有的写操作通过CPU访问映射寄存器
EPwm1Regs.CMPCTL.bit.SHDWBMODE = CC_SHADOW;
EPwm1Regs.CMPCTL.bit.LOADAMODE = CC_CTR_ZERO; // Load on Zero //当时间基准计数器等于0(TBCTR=0X0000)时加载
EPwm1Regs.CMPCTL.bit.LOADBMODE = CC_CTR_ZERO;
// Set actions
EPwm1Regs.AQCTLA.bit.CAU = AQ_SET; //TBCTR与CMPA在up计数时相等使输出置高 // Set PWM1A on event A, up count
EPwm1Regs.AQCTLA.bit.CAD = AQ_CLEAR; //CTR=CAD事件时将EPWM1A置低 // Clear PWM1A on event A, down count
EPwm1Regs.AQCTLB.bit.CBU = AQ_SET; // Set PWM1B on event B, up count
EPwm1Regs.AQCTLB.bit.CBD = AQ_CLEAR; // Clear PWM1B on event B, down count
// Interrupt where we will change the Compare Values
EPwm1Regs.ETSEL.bit.INTSEL = ET_CTR_ZERO; // Select INT on Zero event
EPwm1Regs.ETSEL.bit.INTEN = 1; // Enable INT
EPwm1Regs.ETPS.bit.INTPRD = ET_3RD; // Generate INT on 3rd event //
ETPS域描述(时间触发预分频寄存器) SOCBCNT:EPWM ADC开始变换B事件(EPWMxSOCB)计数器寄存器,这些位决定有多少选定ETSEL(SOCBSEL)事件已经发生
//:产生几次事件后发出中断信号EPWMx_INT EPwm1Regs.ETPS.bit.INTPRD=ET_1ST
/*00:没有
01:1个
10:2个
11:3个 这里 ET_3RD =11 系统时钟= 150MHZ / 3 = 50MHZ
*/
// Information this example uses to keep track
// of the direction the CMPA/CMPB values are
// moving, the min and max allowed values and
// a pointer to the correct ePWM registers
epwm1_info.EPwm_CMPA_Direction = EPWM_CMP_UP; // Start by increasing CMPA &
epwm1_info.EPwm_CMPB_Direction = EPWM_CMP_DOWN; // decreasing CMPB
epwm1_info.EPwmTimerIntCount = 0; // Zero the interrupt counter
epwm1_info.EPwmRegHandle = &EPwm1Regs; // Set the pointer to the ePWM module
epwm1_info.EPwmMaxCMPA = EPWM1_MAX_CMPA; // Setup min/max CMPA/CMPB values
epwm1_info.EPwmMinCMPA = EPWM1_MIN_CMPA;
epwm1_info.EPwmMaxCMPB = EPWM1_MAX_CMPB;
epwm1_info.EPwmMinCMPB = EPWM1_MIN_CMPB;
}
void InitEPwm2Example()
{
// Setup TBCLK
EPwm2Regs.TBPRD = EPWM2_TIMER_TBPRD; // Set timer period 801 TBCLKs
EPwm2Regs.TBPHS.half.TBPHS = 0x0000; // Phase is 0
EPwm2Regs.TBCTR = 0x0000; // Clear counter
// Set Compare values
EPwm2Regs.CMPA.half.CMPA = EPWM2_MIN_CMPA; // Set compare A value
EPwm2Regs.CMPB = EPWM2_MIN_CMPB; // Set Compare B value
// Setup counter mode
EPwm2Regs.TBCTL.bit.CTRMODE = TB_COUNT_UPDOWN; // Count up
EPwm2Regs.TBCTL.bit.PHSEN = TB_DISABLE; // Disable phase loading
EPwm2Regs.TBCTL.bit.HSPCLKDIV = TB_DIV1; // Clock ratio to SYSCLKOUT
EPwm2Regs.TBCTL.bit.CLKDIV = TB_DIV1;
// Setup shadowing
EPwm2Regs.CMPCTL.bit.SHDWAMODE = CC_SHADOW;
EPwm2Regs.CMPCTL.bit.SHDWBMODE = CC_SHADOW;
EPwm2Regs.CMPCTL.bit.LOADAMODE = CC_CTR_ZERO; // Load on Zero
EPwm2Regs.CMPCTL.bit.LOADBMODE = CC_CTR_ZERO;
// Set actions
EPwm2Regs.AQCTLA.bit.CAU = AQ_SET; // Set PWM2A on event A, up count
EPwm2Regs.AQCTLA.bit.CBD = AQ_CLEAR; // Clear PWM2A on event B, down count
EPwm2Regs.AQCTLB.bit.ZRO = AQ_CLEAR; // Clear PWM2B on zero
EPwm2Regs.AQCTLB.bit.PRD = AQ_SET ; // Set PWM2B on period
// Interrupt where we will change the Compare Values
EPwm2Regs.ETSEL.bit.INTSEL = ET_CTR_ZERO; // Select INT on Zero event
EPwm2Regs.ETSEL.bit.INTEN = 1; // Enable INT
EPwm2Regs.ETPS.bit.INTPRD = ET_3RD; // Generate INT on 3rd event
// Information this example uses to keep track
// of the direction the CMPA/CMPB values are
// moving, the min and max allowed values and
// a pointer to the correct ePWM registers
epwm2_info.EPwm_CMPA_Direction = EPWM_CMP_UP; // Start by increasing CMPA &
epwm2_info.EPwm_CMPB_Direction = EPWM_CMP_UP; // increasing CMPB
epwm2_info.EPwmTimerIntCount = 0; // Zero the interrupt counter
epwm2_info.EPwmRegHandle = &EPwm2Regs; // Set the pointer to the ePWM module
epwm2_info.EPwmMaxCMPA = EPWM2_MAX_CMPA; // Setup min/max CMPA/CMPB values
epwm2_info.EPwmMinCMPA = EPWM2_MIN_CMPA;
epwm2_info.EPwmMaxCMPB = EPWM2_MAX_CMPB;
epwm2_info.EPwmMinCMPB = EPWM2_MIN_CMPB;
}
void InitEPwm3Example(void)
{
// Setup TBCLK
EPwm3Regs.TBCTL.bit.CTRMODE = TB_COUNT_UPDOWN;// Count up/down
EPwm3Regs.TBPRD = EPWM3_TIMER_TBPRD; // Set timer period
EPwm3Regs.TBCTL.bit.PHSEN = TB_DISABLE; // Disable phase loading
EPwm3Regs.TBPHS.half.TBPHS = 0x0000; // Phase is 0
EPwm3Regs.TBCTR = 0x0000; // Clear counter
EPwm3Regs.TBCTL.bit.HSPCLKDIV = TB_DIV1; // Clock ratio to SYSCLKOUT
EPwm3Regs.TBCTL.bit.CLKDIV = TB_DIV1;
// Setup shadow register load on ZERO
EPwm3Regs.CMPCTL.bit.SHDWAMODE = CC_SHADOW;
EPwm3Regs.CMPCTL.bit.SHDWBMODE = CC_SHADOW;
EPwm3Regs.CMPCTL.bit.LOADAMODE = CC_CTR_ZERO;
EPwm3Regs.CMPCTL.bit.LOADBMODE = CC_CTR_ZERO;
// Set Compare values
EPwm3Regs.CMPA.half.CMPA = EPWM3_MIN_CMPA; // Set compare A value
EPwm3Regs.CMPB = EPWM3_MAX_CMPB; // Set Compare B value
// Set Actions
EPwm3Regs.AQCTLA.bit.PRD = AQ_SET; // Set PWM3A on period
EPwm3Regs.AQCTLA.bit.CBD = AQ_CLEAR; // Clear PWM3A on event B, down count
EPwm3Regs.AQCTLB.bit.PRD = AQ_CLEAR; // Clear PWM3A on period
EPwm3Regs.AQCTLB.bit.CAU = AQ_SET; // Set PWM3A on event A, up count
// Interrupt where we will change the Compare Values
EPwm3Regs.ETSEL.bit.INTSEL = ET_CTR_ZERO; // Select INT on Zero event
EPwm3Regs.ETSEL.bit.INTEN = 1; // Enable INT
EPwm3Regs.ETPS.bit.INTPRD = ET_3RD; // Generate INT on 3rd event
// Information this example uses to keep track
// of the direction the CMPA/CMPB values are
// moving, the min and max allowed values and
// a pointer to the correct ePWM registers
epwm3_info.EPwm_CMPA_Direction = EPWM_CMP_UP; // Start by increasing CMPA &
epwm3_info.EPwm_CMPB_Direction = EPWM_CMP_DOWN; // decreasing CMPB
epwm3_info.EPwmTimerIntCount = 0; // Zero the interrupt counter
epwm3_info.EPwmRegHandle = &EPwm3Regs; // Set the pointer to the ePWM module
epwm3_info.EPwmMaxCMPA = EPWM3_MAX_CMPA; // Setup min/max CMPA/CMPB values
epwm3_info.EPwmMinCMPA = EPWM3_MIN_CMPA;
epwm3_info.EPwmMaxCMPB = EPWM3_MAX_CMPB;
epwm3_info.EPwmMinCMPB = EPWM3_MIN_CMPB;
}
void update_compare(EPWM_INFO *epwm_info)
{
epwm_info->EPwmRegHandle->CMPB=12500; //这里 12500 是因为 50000*0.25 比列的低电平
return;
}
//===========================================================================
// No more.
//===========================================================================
10.补充知识点
1.首先从时基模块开始TB
TB模块
实质是计数器,设置产生方波的频率、周期。计数方式有三种:递减计数,递增计数,增减计数。
TB内部寄存器
TBPRD:周期寄存器 (设置的时钟周期存入此,可通过阴影寄存器缓冲后写入,也可通过活动寄存器立即写入)
TBCTR:时基计数变值寄存器 (时基当前所计数的值存入,用于和所设定周期值比较)
TBPHS:时基相位寄存器
TBSTS:时基状态寄存器
TBCTL:控制寄存器 (重要)
关于分频: 分频是什么 (分频就是把 系统时钟 时间减小(片面)
系统时钟时间 150MHZ 分频1/2 ---》 系统时钟: 75MHZ
TBCTL寄存器域描述
PHSDIR: 增减模式下,同步信号到来时,装载相位值后增减状态的计数方向
0:减计数
1:增计数
CLKDIV:分频,同HSPCLKDIV用
000:1分频
001:2分频
010:4分频
…
111:128分频
TBCLK=SYSCLKOUT/(HSPCLKDIV×CLKDIV)
HSPCLKDIV:分频,同CLKDIV用
SWFSYNC:软件强制同步脉冲
0:无效果
1:强制一次
SYNCOSEL:选择ePWMxSYNCO信号输出源(了解性)
00:ePWMxSYNCI
01:CTR=ZER0:时基计数器为0
10:CTR=CMPA:时基计数器等于比较寄存器A
11:禁止输出
PRDLD:周期寄存器阴影加载方式
0:加载阴影寄存器值
1:不加载阴影
PHSEN:使能相位
0:禁止加载
1:加载相位寄存器值
CTRMOD:计数模式
00:加
01:减
10:加减
11:停止计数
相关的配置命令:
1、TBPRD:设置TB模块计数器的计数周期 EPwm1Regs.TBPRD = 0XFFFF;
2、TBPHS:设置TB模块计数器的相位 EPwm1Regs.TBPHS.half.TBPHS = 100; (half含义,待补)
3、TBCTR:读取TB模块计数器的当前值 a= EPwm1Regs.TBCTR
4、TBCLT
4.1 FREE和SOFT:决定epwm在仿真时挂起的工作 EPwm1Regs.TBCTL.bit.FREE_SOFT=0
4.2 PHSDIR:决定同步后增减计数器的计数方向,仅用于增减计数模式 EPwm5Regs.TBCTL.bit.PHSDIR=TB_DOWN;
4.3 CLKDIV和HSPCLKDIV:TB模块时钟分频位 TBCLK=系统时钟/(HSPCLKDIV*CLKDIV) EPwm1Regs.TBCTL.bit.HSPCLKDIV = TB_DIV4 EPwm1Regs.TBCTL.bit.CLKDIV = TB_DIV4
4.4 SWFSYNC:写1将强制产生一次同步脉冲信号 EPwm1Regs.TBCTL.bit.FREE_SOFT=1
4.5 SYNCOSEL:选择epwm之间同步信号来源 EPwm1Regs.TBCTL.bit.SYNCOSEL=TB_CTR_ZERO
4.6 PRDLD:决定TBPRD映射单元何时向当前单元装载数据 EPwm1Regs.TBCTL.bit.SYNCOSEL=TB_IMMEDIATE
4.7 PHSEN:相位使能位(只有在有同步的时候才能使能相位) EPwm1Regs.TBCTL.bit.PHSEN=TB_ENABLE
4.8 CTRMODE:计数模式选择 EPwm1Regs.TBCTL.bit.CTRMODE=TB_COUNT_UPDOWN
5、TBSTS
5.1 CTRMAX:读,判读TBCTR是否打到过最大值0xFFFF a=EPwm1Regs.TBSTS.bit.CTRMAX EPwm1Regs.TBSTS.bit.CTRMAX=1清楚相应的锁存事件
5.2 SYNCI:读,判断是否发生过同步事件 a=EPwm1Regs.TBSTS.bit.SYNCI
5.3 CTRDIR:判断计数器计数模式 a=EPwm1Regs.TBSTS.bit.CTRDIR
程序:
EPwm1Regs.TBPRD = 50000; // Set timer period 801 TBCLKs 频率控制 T =50000 * 1/ 50M hz = (1/ 1000) s f=1/T =1000HZ =1KZ
EPwm1Regs.TBPHS.half.TBPHS = 0x0000; // Phase is 0 相位设置
EPwm1Regs.TBCTR = 0x0000; // Clear counter 计数器清零
// Set Compare values
//14-15CMPA计数比较A寄存器 数值
EPwm1Regs.CMPA.half.CMPA = EPWM1_MIN_CMPA; // Set compare A value
EPwm1Regs.CMPB = EPWM1_MAX_CMPB; // Set Compare B value
// Setup counter mode
EPwm1Regs.TBCTL.bit.CTRMODE = TB_COUNT_UPDOWN; // Count up 增计数模式
EPwm1Regs.TBCTL.bit.PHSEN = TB_DISABLE; // Disable phase loading 禁止相位寄存器加载
EPwm1Regs.TBCTL.bit.HSPCLKDIV = TB_DIV1; // Clock ratio to SYSCLKOUT 不分频
EPwm1Regs.TBCTL.bit.CLKDIV = TB_DIV1; //不分频
2.CC模块
联合TB模块,可以在周期内产生更多的事件。内部是2个比较器,预设值TBCTR的值与比较寄存器CMPA和CMPB不断进行比较的,当时基计数器的值等于其中之一时,就会产生相应的事件。
CC内部寄存器
CMPA:比较寄存器A,其值与TBCTR值比较,相同时,事件发送到动作模块。
CMPB:比较寄存器B,其值与TBCTR值比较,相同时,事件发送到动作模块。
CMPCTL:控制寄存器(重要)
CMPCTL寄存器域描述
SHDWAFULL(或SHDWBFULL):CMPA(或B)阴影寄存器满标志位
0:未满
1:满了
SHDWAMODE(或SHDWBMODE):CMPA(或B)写入值是否使用阴影
0:通过阴影寄存器写入
1:直接写入
LOADAMODE(或LOADBMODE):若使用阴影,加载条件模式选择
00:CTR=ZERO时
01:CTR=PRD时
10:CTR=ZERO或CTR=PRD是
11:禁止
知识:
、CMPA,CMPB:该寄存器中的值与TBCTR的计数值不断进行比较,如果相等的时候将触发AQ模块的动作 EPwm1Regs.CMPA.half.CMPA = 3000;
2、CMPCTL
2.1 SHDWAFULL,SHDWBFULL:CMPA或者CMPB映射寄存器满状态标志位 a=EPwm1Regs.CMPCTL.bit.SHDWAFULL
2.2 SHDWAMODE,SHDWBMODE: CMPA或者CMPB是否选用映射寄存器 EPwm1Regs.CMPCTL.bit.SHDWAMODE=CC_SHADOW
2.3 LOADAMODE,LOADBMODE:决定CMPA或者CMPB主寄存器何时从映射寄存器中加载数据 EPwm1Regs.CMPCTL.bit.LOADBMODE=CC_CTR_ZERO
3、CMPAHR:存放CMPA的高精度部分 EPwm1Regs.CMPAHR.half.CMPA=1000
程序:
EPwm2Regs.CMPCTL.bit.SHDWAMODE = CC_SHADOW;
EPwm2Regs.CMPCTL.bit.SHDWBMODE = CC_SHADOW;
EPwm2Regs.CMPCTL.bit.LOADAMODE = CC_CTR_ZERO; // Load on Zero
EPwm2Regs.CMPCTL.bit.LOADBMODE = CC_CTR_ZERO;
3.动作模块AQ
AQ模块
动作模块,相应事件并展开相关设计动作
AQ内部寄存器
AQCTLA:动作限定输出A控制寄存器
AQCTLB:动作限定输出A控制寄存器
AQCTLA域描述 (AQCTLB与A类似,其各项使ePWMxB输出)
CBD:时间基准计数器等于CMPB寄存器且计数为减时
00:无动作
01:清除,使ePWMxA输出低
10:置位,使ePWMxA输出高
11:切换,使ePWMxA输出翻转(高变低,低变高)
CBU:计数器等于CMPB且计数为增时
00:无动作
01:清除,使ePWMxA输出低
10:置位,使ePWMxA输出高
11:切换,使ePWMxA输出翻转(高变低,低变高)
CAD:计数器等于CMPA且计数为减时
00:无动作
01:清除,使ePWMxA输出低
10:置位,使ePWMxA输出高
11:切换,使ePWMxA输出翻转(高变低,低变高)
CAU:计数器等于CMPA且计数为增时
00:无动作
01:清除,使ePWMxA输出低
10:置位,使ePWMxA输出高
11:切换,使ePWMxA输出翻转(高变低,低变高)
PRU:当计数器等于周期动作
00:无动作
01:清除,使ePWMxA输出低
10:置位,使ePWMxA输出高
11:切换,使ePWMxA输出翻转(高变低,低变高)
ZRO:当计数器等于0时
00:无动作
01:清除,使ePWMxA输出低
10:置位,使ePWMxA输出高
11:切换,使ePWMxA输出翻转(高变低,低变高)
例:
EPwm1Regs.AQCTLA.bit.CAU = AQ_CLEAR; //递增计数时,发生比较寄存器A匹配时清除PWM1A输出
EPwm1Regs.AQCTLA.bit.ZRO = AQ_SET; //计数到0 PWM1A输出高电平
软件时间响应使用AQSFRC(动作限定软件强制寄存器)与AQCSFRC(动作限定连续软件强制寄存器)实现
(可用于模拟软件调试),(了解性)
AQSFRC域描述
BLDCSF:主寄存器从映射选项重新加载
00:遇到计数器等于0的事件加载
01:遇到计数器等于周期的事件加载
10:遇到计数器等于0或周期的事件加载
11:直接加载,不经过映射
OTSFB:对输出事件B一次性软件强制
0:写0无效果,始终读0
1:触发单一S/W事件
ACTSFB:当一次性软件强制B被调用时行动
00:禁止
01:清除(低)
10:设定(高)
11:切换(高低切换)
OTSFA:对输出事件A一次性软件强制
0:写0无效果,始终读0
1:触发单一S/W事件
ACTSFA:当一次性软件强制A被调用时行动
00:禁止
01:清除(低)
10:设定(高)
11:切换(高低切换)
AQCSFRC域描述
CSFA:对输出A连续软件强制
00:无作用
01:对输出A强制产生连续低信号
10:对输出A强制产生连续高信号
11:软件强制被禁用且无效
CSFB:对输出B连续软件强制
00:无作用
01:对输出B强制产生连续低信号
10:对输出B强制产生连续高信号
11:软件强制被禁用且无效
配置命令:
1、AQCTLA
1.1 CBD:计数值TBCTR递减计数到CMPB时的PWMA动作(翻转、高、低,无动作) EPwm1Regs.AQCTLA.bit.CBD=AQ_TOGGLE
1.2 CBU: 计数值TBCTR递增计数到CMPB时的PWMA动作(翻转、高、低,无动作) EPwm1Regs.AQCTLA.bit.CBU=AQ_TOGGLE
1.3 CAD:计数值TBCTR递减计数到CMPA时的PWMA动作(翻转、高、低,无动作) EPwm1Regs.AQCTLA.bit.CAD=AQ_TOGGLE
1.4 CAU: 计数值TBCTR递增计数到CMPA时的PWMA动作(翻转、高、低,无动作) EPwm1Regs.AQCTLA.bit.CAU=AQ_TOGGLE
1.5 PRD: 计数值TBCTR等于TBPRD周期值时的PWMA动作(翻转、高、低,无动作) EPwm1Regs.AQCTLA.bit.PRD=AQ_TOGGLE
1.6 ZRO: 计数值TBCTR等于0时的PWMA动作(翻转、高、低,无动作) EPwm1Regs.AQCTLA.bit.ZRO=AQ_TOGGLE
2、AQCTLB
2.1 CBD:计数值TBCTR递减计数到CMPB时的PWMB动作(翻转、高、低,无动作) EPwm1Regs.AQCTLB.bit.CBD=AQ_TOGGLE
2.2 CBU: 计数值TBCTR递增计数到CMPB时的PWMB动作(翻转、高、低,无动作) EPwm1Regs.AQCTLB.bit.CBU=AQ_TOGGLE
2.3 CAD:计数值TBCTR递减计数到CMPA时的PWMB动作(翻转、高、低,无动作) EPwm1Regs.AQCTLB.bit.CAD=AQ_TOGGLE
2.4 CAU: 计数值TBCTR递增计数到CMPA时的PWMB动作(翻转、高、低,无动作) EPwm1Regs.AQCTLB.bit.CAU=AQ_TOGGLE
2.5 PRD: 计数值TBCTR等于TBPRD周期值时的PWMB动作(翻转、高、低,无动作) EPwm1Regs.AQCTLB.bit.PRD=AQ_TOGGLE
2.6 ZRO: 计数值TBCTR等于0时的PWMB动作(翻转、高、低,无动作) EPwm1Regs.AQCTLB.bit.ZRO=AQ_TOGGLE
3、AQSFRC(控制产生软件的PWM动作)
3.1 RLDCSF:决定AQCSFRC何时从映射寄存器中加载数据(CTR=0、CTR=PRD、CTR=0或CTR=PRD、禁止映射寄存器) EPwm1Regs.AQSFRC.bit.RLDCSF=0x00
3.2 OTSFB:对PWMB进行一次软件强制事件 EPwm1Regs.AQSFRC.bit.OTSFB=1(写1后自动清零)
3.3 ACTSFB:定义PWMB发生一次软件强制事件后,PWMB的变化 EPwm1Regs.AQSFRC.bit.ACTSFB=AQ_TOGGLE
3.4 OTSFA:对PWMA进行一次软件强制事件 EPwm1Regs.AQSFRC.bit.OTSFA=1(写1后自动清零)
3.5 ACTSFA:定义PWMA发生一次软件强制事件后,PWMA的变化 EPwm1Regs.AQSFRC.bit.ACTSFA=AQ_TOGGLE
4、AQCSFRC(定义连续软件强制触发控制)
4.1 CSFB:定义PWMB的连续软件强制触发控制(无动作、强制低、强制高、软件强制被关闭) EPwm1Regs.AQCSFRC.bit.CSFB=01;
4.2 CSFA:定义PWMA的连续软件强制触发控制(无动作、强制低、强制高、软件强制被关闭) EPwm1Regs.AQCSFRC.bit.CSFA=01;
程序:
EPwm2Regs.AQCTLA.bit.CAU = AQ_SET; // Set PWM2A on event A, up count
EPwm2Regs.AQCTLA.bit.CBD = AQ_CLEAR; // Clear PWM2A on event B, down count
EPwm2Regs.AQCTLB.bit.ZRO = AQ_CLEAR; // Clear PWM2B on zero
EPwm2Regs.AQCTLB.bit.PRD = AQ_SET ; // Set PWM2B on period
4.ET模块
事件触发模块,产生中断,触发ADC等
ETSEL域描述(事件触发选择寄存器)
SCOBEN:使能ADC转换B(EPWMxSOCB)脉冲
0:禁止
1:使能
SCOBSEL:决定EPWMxSOCB脉冲何时被生成
000:保留
001:时基计数器(TBCTR)为0
010:TBCTR=TBPRD
011:保留
100:定时器递增时时间基准计数器等于CMPA
101:定时器递减时时间基准计数器等于CMPA
110:定时器递增时时间基准计数器等于CMPB
111:定时器递减时时间基准计数器等于CMPB
SOCAEN:使能ADC转换A(EPWMxSOCA)脉冲
0:禁止
1:使能
SCOASEL:决定EPWMxSOCB脉冲何时被生成
000:保留
001:时基计数器(TBCTR)为0
010:TBCTR=TBPRD
011:保留
100:定时器递增时时间基准计数器等于CMPA
101:定时器递减时时间基准计数器等于CMPA
110:定时器递增时时间基准计数器等于CMPB
111:定时器递减时时间基准计数器等于CMPB
INTEN:使能EPWM中断生成
0:禁止生成
1:启动生成
INTESEL:EPWM中断选项
000:保留
001:时基计数器(TBCTR)为0
010:TBCTR=TBPRD
011:保留
100:定时器递增时时间基准计数器等于CMPA
101:定时器递减时时间基准计数器等于CMPA
110:定时器递增时时间基准计数器等于CMPB
111:定时器递减时时间基准计数器等于CMPB
ETPS域描述(时间触发预分频寄存器)
SOCBCNT:EPWM ADC开始变换B事件(EPWMxSOCB)计数器寄存器,这些位决定有多少选定ETSEL(SOCBSEL)事件已经发生
00:没有
01:1个
10:2个
11:3个
SOCBPRD:EPWMxSOCB脉冲信号生成事件选择
00:禁用
01:第一个事件上生成EPWMxSOCB脉冲:ETPS[SOCBCNT]=0,1
10:第二个事件上生成EPWMxSOCB脉冲:ETPS[SOCBCNT]=1,0
11:第三个事件上生成EPWMxSOCB脉冲:ETPS[SOCBCNT]=1,1
SOCACNT与SOCAPRD类比B的
INTCNT:EPWM中断技术寄存器
00:没有事件发生
01:1个
10:2个
11:3个
INTPRD:在第几个事件发生中断
00:禁用
01:在第一个事件发生时中断,ETPS[INTCNT]=0,1
10:在第二个事件发生时中断,ETPS[INTCNT]=1,0
11:在第三个事件发生时中断,ETPS[INTCNT]=1,1
例:
EPwm1Regs.ETSEL.bit.INTSEL = ET_CTR_ZERO; //选择0匹配事件中断;
EPwm1Regs.ETSEL.bit.INTEN = 1; //使能事件触发中断
EPwm1Regs.ETPS.bit.INTPRD = ET_3RD; //三次中断请求
配置命令:
1、ETSEL
1.1 SOCBEN:是否PWMB使能ADC启动脉冲EPwmxSOCB EPwm1Regs.ETSEL.bit.SOCBEN=0
1.2 SOCAEN:是否PWMA使能ADC启动脉冲EPwmxSOCA EPwm1Regs.ETSEL.bit.SOCAEN=0
1.3 SOCBSEL:选择PWMB在计数状态下产生EPwmxSOCB条件 EPwm1Regs.ETSEL.bit.SOCBSEL=ET_CTR_PRD
1.4 SOCASEL:选择PWMA在计数状态下产生EPWMxSOCB条件 EPwm1Regs.ETSEL.bit.SOCASEL=ET_CTR_PRD
1.5 INTEN:中断信号EPWMx_INT是否使能 EPwm1Regs.ETSEL.bit.INTEN=0
1.6 INTSEL:中断信号EPWMx_INT的产生条件 EPwm1Regs.ETSEL.bit.INTSEL = ET_CTR_ZERO
2、ETPS
2.1 SOCBCNT:ADC启动信号EPWMxSOCB的计数器 a=EPwm1Regs.ETPS.bit.SOCBCNT
2.2 SOCACNT:ADC启动信号EPWMxSOCA的计数器 a=EPwm1Regs.ETPS.bit.SOCACNT
2.3 SOCBPRD:产生几次EPWMxSOCB后发出ADC启动信号 EPwm1Regs.ETPS.bit.SOCBPRD=ET_1ST
2.4 SOCAPRD:产生几次EPWMxSOCA后发出ADC启动信号 EPwm1Regs.ETPS.bit.SOCAPRD=ET_1ST
2.5 INTCNT:EPWM中断EPWMx_INT计数器 a=EPwm1Regs.ETPS.bit.INTCNT
2.6 INTPRD:产生几次事件后发出中断信号EPWMx_INT EPwm1Regs.ETPS.bit.INTPRD=ET_1ST
3、ETFLG
3.1 SOCB:ADC启动信号EPWMxSOCB状态标志位,此位置位之后可继续产生
3.2 SOCA:ADC启动信号EPWMxSOCA状态标志位,此位置位之后可继续产生
3.3 INT:中断信号EPWMx_INT状态标志位,此位置位之后需清零
4、ETCLR
4.1 SOCB:清除EPWMxSOCB状态标志位 EPwm1Regs.ETCLR.bit.SOCB=1
4.2 SOCA:清除EPWMxSOCA状态标志位 EPwm1Regs.ETCLR.bit.SOCA=1
4.3 INT:清除INT状态标志位 EPwm1Regs.ETCLR.bit.INT=1
5、ETFRC
5.1 SOCB:SOCB软件强制产生 EPwm1Regs.ETFRC.bit.SOCB=1
5.2 SOCB:SOCA软件强制产生 EPwm1Regs.ETFRC.bit.SOCA=1
5.2 INT:INT软件强制产生 EPwm1Regs.ETFRC.bit.INT=1
程序代码:
EPwm2Regs.ETSEL.bit.INTSEL = ET_CTR_ZERO; // Select INT on Zero event
EPwm2Regs.ETSEL.bit.INTEN = 1; // Enable INT
EPwm2Regs.ETPS.bit.INTPRD = ET_3RD; // Generate INT:产生几次事件后发出中断信号EPWMx_INT EPwm1Regs.ETPS.bit.INTPRD=ET_1ST
更多推荐
所有评论(0)