I、原理描述
![](https://img.haomeiwen.com/i1653010/7371433d820e5d99.png)
image.png
My Code
//double DutyCycle, Frequency, FullCycle;
//uint32_t IC2Value;
//uint32_t cnt;
//uint8_t timer5_cap_sta = 0;
//uint16_t timer5_cap_val = 0;
PwmValType cap_val[4];
PwmValType cap_val_cp[4];
void drv_pwm_reader_init()
{
GPIO_InitTypeDef GPIO_InitStructure;
NVIC_InitTypeDef NVIC_InitStructure;
TIM_ICInitTypeDef TIM_ICInitStructure;
TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
// T4CH1-4, PD12-15
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4, ENABLE);
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOD, ENABLE);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12 | GPIO_Pin_13 | GPIO_Pin_14 | GPIO_Pin_15 ;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
//GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; //GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;
GPIO_Init(GPIOD, &GPIO_InitStructure);
GPIO_PinAFConfig(GPIOD, GPIO_PinSource12, GPIO_AF_TIM4);
GPIO_PinAFConfig(GPIOD, GPIO_PinSource13, GPIO_AF_TIM4);
GPIO_PinAFConfig(GPIOD, GPIO_PinSource14, GPIO_AF_TIM4);
GPIO_PinAFConfig(GPIOD, GPIO_PinSource15, GPIO_AF_TIM4);
TIM_TimeBaseStructure.TIM_Period = 10000 - 1;
TIM_TimeBaseStructure.TIM_Prescaler = (SystemCoreClock / 4) / 50000 - 1;
TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;
TIM_TimeBaseStructure.TIM_RepetitionCounter = 0;
TIM_TimeBaseInit(TIM4, &TIM_TimeBaseStructure);
TIM_ClearFlag(TIM4, TIM_FLAG_Update | TIM_FLAG_CC1 | TIM_FLAG_CC2 | TIM_FLAG_CC3 | TIM_FLAG_CC4);
TIM_ICInitStructure.TIM_Channel = TIM_Channel_1;
TIM_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_Rising;
TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI;
TIM_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1;
TIM_ICInitStructure.TIM_ICFilter = 0x0;
TIM_ICInit(TIM4, &TIM_ICInitStructure);
TIM_ICInitStructure.TIM_Channel = TIM_Channel_2;
TIM_ICInit(TIM4, &TIM_ICInitStructure);
TIM_ICInitStructure.TIM_Channel = TIM_Channel_3;
TIM_ICInit(TIM4, &TIM_ICInitStructure);
TIM_ICInitStructure.TIM_Channel = TIM_Channel_4;
TIM_ICInit(TIM4, &TIM_ICInitStructure);
// TIM_PWMIConfig(TIM1, &TIM_ICInitStructure);
// TIM_SelectInputTrigger(TIM1, TIM_TS_TI2FP2);
// TIM_SelectSlaveMode(TIM1, TIM_SlaveMode_Reset);
// TIM_SelectMasterSlaveMode(TIM1, TIM_MasterSlaveMode_Enable);
TIM_Cmd(TIM4, ENABLE);
// WARNING: TIM_IT_CC4 will inference other so that cannot work
TIM_ITConfig(TIM4, TIM_IT_CC1 | TIM_IT_CC2 | TIM_IT_CC3 | /*TIM_IT_CC4 |*/ TIM_IT_Update, ENABLE);
NVIC_InitStructure.NVIC_IRQChannel = TIM4_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
memset((void*)&(cap_val[0]), 0, sizeof(PwmValType) *4);
}
void update_val(int index, uint32_t val)
{
uint16_t tmpccer = 0;
if((cap_val[index].status&0x40) == 0) // rising, start count
{
cap_val[index].val = val;
cap_val[index].status = 0x40;
// TIM_OC3PolarityConfig(TIM4, TIM_ICPolarity_Falling);
tmpccer = TIM4->CCER;
/* Set or Reset the CC1P Bit */
tmpccer &= (uint16_t)(~(0x0002 << (index *4)));
tmpccer |= TIM_ICPolarity_Falling << (index *4);
TIM4->CCER = tmpccer;
}
else if(cap_val[index].status&0x40) // rising, end count
{
if(val <= cap_val[index].val)
{
cap_val[index].status = 0x00;
return;
}
cap_val[index].status = 0x80; // finish cap
cap_val[index].val = val - cap_val[index].val; // diff
cap_val_cp[index].status = 0x80; // finish cap
cap_val_cp[index].val = cap_val[index].val; // diff
// TIM_OC3PolarityConfig(TIM4, TIM_ICPolarity_Rising);
tmpccer = TIM4->CCER;
/* Set or Reset the CC1P Bit */
tmpccer &= (uint16_t)(~(0x0002 << (index *4)));
tmpccer |= TIM_ICPolarity_Rising << (index *4);
TIM4->CCER = tmpccer;
}
// TIM_ClearITPendingBit(TIM4, TIM_IT_CC1);
}
void TIM4_IRQHandler(void)
{
// if((timer5_cap_sta & 0x80) == 0)
{
if(TIM_GetITStatus(TIM4, TIM_IT_CC1) != RESET)
{
update_val(0, TIM_GetCapture1(TIM4));
TIM_ClearITPendingBit(TIM4, TIM_IT_CC1);
}
if(TIM_GetITStatus(TIM4, TIM_IT_CC2) != RESET)
{
update_val(1, TIM_GetCapture2(TIM4));
TIM_ClearITPendingBit(TIM4, TIM_IT_CC2);
}
if(TIM_GetITStatus(TIM4, TIM_IT_CC3) != RESET)
{
update_val(2, TIM_GetCapture3(TIM4));
TIM_ClearITPendingBit(TIM4, TIM_IT_CC3);
}
if(TIM_GetITStatus(TIM4, TIM_IT_CC4) != RESET)
{
update_val(3, TIM_GetCapture4(TIM4));
TIM_ClearITPendingBit(TIM4, TIM_IT_CC4);
}
// overflow and clean
if(TIM_GetITStatus(TIM4, TIM_IT_Update) != RESET)
{
int i = 0;
for(i = 0; i < 4; i++)
{
cap_val[i].status = 0x00;
cap_val_cp[i].status = 0x00;
}
TIM_ClearITPendingBit(TIM4, TIM_IT_Update);
}
// finish and clean
if(cap_val[0].status & 0x80 &&
cap_val[1].status & 0x80 &&
cap_val[2].status & 0x80 /*&&
cap_val[3].status & 0x80 */)
{
int i = 0;
for(i = 0; i < 4; i++) cap_val[i].status = 0x00;
TIM_SetCounter(TIM4, 0);
}
}
}
void drv_pwm_read(PwmValType * val)
{
memcpy((void *)val, (void *)&(cap_val_cp[0]), 4 * sizeof(PwmValType));
}
参考
https://www.cnblogs.com/strongerHuang/p/5662338.html
网友评论