我想用28377的ecap功能来实现连续采样PWM波的频率,ecap时钟用系统时钟200M,连续采样周期值先放在ecap1的寄存器CAP1-4中。再利用epwm的计数功能,每1/40kHz个周期触发中断,在中断程序里将CAP1-4的数值取出计算频率。下面是我的ecap部分的程序,但是一直采样不到频率,寄存器CAP1-4的值也没有。
//主程序里的ECAP设置
void InitECapture();
GPIO_SetupPinOptions(19,GPIO_INPUT,GPIO_ASYNC); void SetCap1Mode();
void InitECapture(void)
{
EALLOW;
InputXbarRegs.INPUT7SELECT = 19; // Set eCAP1 source to GPIO-pin
EDIS;
//GpioCtrlRegs.GPAPUD.bit.GPIO24=0;
//GpioCtrlRegs.GPAQSEL2.bit.GPIO24=0;
//GpioCtrlRegs.GPAMUX2.bit.GPIO24=1;
//EDIS;
}
void SetCap1Mode(void)
{
ECap1Regs.ECEINT.all = 0x0000; // Disable all capture __interrupts
ECap1Regs.ECCLR.all = 0xFFFF; // Clear all CAP __interrupt flags
ECap1Regs.ECCTL1.bit.CAPLDEN = 0; // Disable CAP1-CAP4 register loads
ECap1Regs.ECCTL2.bit.TSCTRSTOP = 0; // Make sure the counter is stopped
ECap1Regs.ECCTL1.bit.CAP1POL=0; //捕捉上升沿
ECap1Regs.ECCTL1.bit.CAP2POL=0;
ECap1Regs.ECCTL1.bit.CAP3POL=0;
ECap1Regs.ECCTL1.bit.CAP4POL=0;
ECap1Regs.ECCTL1.bit.CTRRST1=1; //差分模式
ECap1Regs.ECCTL1.bit.CTRRST2=1;
ECap1Regs.ECCTL1.bit.CTRRST3=1;
ECap1Regs.ECCTL1.bit.CTRRST4=1;
ECap1Regs.ECCTL1.bit.CAPLDEN=1; //使能事件捕捉时捕捉寄存器装载计算器值
ECap1Regs.ECCTL1.bit.PRESCALE=00000; //不分频
ECap1Regs.ECCTL2.bit.CAP_APWM=0; //捕捉模式
ECap1Regs.ECCTL2.bit.CONT_ONESHT=0; //连续模式
ECap1Regs.ECCTL2.bit.SYNCO_SEL=2; //屏蔽0x0010
ECap1Regs.ECCTL2.bit.SYNCI_EN=0; //屏蔽
ECap1Regs.ECEINT.all=0x0000; //关闭所有CAP中断
ECap1Regs.ECCLR.all=0xFFFF; //清除所有中断标志
ECap1Regs.ECCTL2.bit.TSCTRSTOP=1; //启动计数
//eCAP1Regs.ECEINT.bit.CEVT4=1; //使能4级事件中断
}
//中断程序采样频率取值
T1=ECap1Regs.CAP1;
T2=ECap1Regs.CAP2;
T3=ECap1Regs.CAP3;
T4=ECap1Regs.CAP4;
fs=200000*1000*(1/T1+1/T2+1/T3+1/T4)/4;
Green Deng:
你好,官方提供了两个eCAP捕获ePWM的例程是否有参考过?有没有确认过GPIO口是否设置正确?
Green Deng:
回复 Green Deng:
C:\ti\c2000\C2000Ware_3_02_00_00\device_support\f2837xd\examples\cpu1\ecap_capture_pwm
C:\ti\c2000\C2000Ware_3_02_00_00\device_support\f2837xd\examples\cpu1\ecap_capture_pwm_xbar
user6158867:
回复 Green Deng:
感谢您的回复,我再参考了下例程,这两个都是单次捕获模式的,同时设置上我也参考了下,应该是没问题。
GPIO口的设置不是这个函数吗
//Setup up the GPIO input/output options for the specified pin.//The flags are a 16-bit mask produced by ORing together options.//For input pins, the valid flags are://GPIO_PULLUP Enable pull-up//GPIO_INVERT Enable input polarity inversion//GPIO_SYNC Synchronize the input latch to PLLSYSCLK (default — you don't need to specify this)//GPIO_QUAL3 Use 3-sample qualification//GPIO_QUAL6 Use 6-sample qualification//GPIO_ASYNC Do not use synchronization or qualification//(Note: only one of SYNC, QUAL3, QUAL6, or ASYNC is allowed)////For output pins, the valid flags are://GPIO_OPENDRAIN Output in open drain mode//GPIO_PULLUP If open drain enabled, also enable the pull-up//and the input qualification flags (SYNC/QUAL3/QUAL6/SYNC) listed above.////With no flags, the default input state is synchronous with no//pull-up or polarity inversion. The default output state is//the standard digital output.void GPIO_SetupPinOptions(Uint16 pin, Uint16 output, Uint16 flags){ volatile Uint32 *gpioBaseAddr; volatile Uint32 *dir, *pud, *inv, *odr, *qsel; Uint32 pin32, pin16, pinMask, qual; pin32 = pin % 32; pin16 = pin % 16; pinMask = 1UL << pin32; gpioBaseAddr = (Uint32 *)&GpioCtrlRegs + (pin/32)*GPY_CTRL_OFFSET; //Create pointers to the appropriate registers. This is a workaround //for the way GPIO registers are defined. The standard definition //in the header file makes it very easy to do named accesses of one //register or bit, but hard to do arbitrary numerical accesses. It's //easier to have an array of GPIO modules with identical registers, //including arrays for multi-register groups like GPyQSEL1-2. But //the header file doesn't define anything we can turn into an array, //so manual pointer arithmetic is used instead. dir = gpioBaseAddr + GPYDIR; pud = gpioBaseAddr + GPYPUD; inv = gpioBaseAddr + GPYINV; odr = gpioBaseAddr + GPYODR; qsel = gpioBaseAddr + GPYQSEL + pin32/16; EALLOW; //Set the data direction *dir &= ~pinMask; if (output == 1) { //Output, with optional open drain mode and pull-up *dir |= pinMask; //Enable open drain if necessary if (flags & GPIO_OPENDRAIN) *odr |= pinMask; else *odr &= ~pinMask; //Enable pull-up if necessary. Open drain mode must be active. if (flags & (GPIO_OPENDRAIN | GPIO_PULLUP)) *pud &= ~pinMask; else *pud |= pinMask; } else { //Input, with optional pull-up, qualification, and polarity inversion *dir &= ~pinMask; //Enable pull-up if necessary if (flags & GPIO_PULLUP) *pud &= ~pinMask; else *pud |= pinMask; //Invert polarity if necessary if (flags & GPIO_INVERT) *inv |= pinMask; else *inv &= ~pinMask; } //Extract the qualification parameter and load it into the register. This is //also needed for open drain outputs, so we might as well do it all the time. qual = (flags & GPIO_ASYNC) / GPIO_QUAL3; *qsel &= ~(0x3L << (2 * pin16)); if (qual != 0x0) *qsel |= qual << (2 * pin16); EDIS;}