2024-07-31 02:32 AM
Hello,
I am currently trying to setup a timer to measure time in between two pulses. I have managed to get it working with the code below but the issue is that I get very imprecise readings on the frequency. I get an error that is hovering around 1-1.5%, what can I do to minimize this error or is it not possible to get less then 1% error in this type of reading?
(The setting in values is done within the init function. I just dont want to send the whole code base)
Regards,
Björn
void HAL_TIM_IC_CaptureCallback(TIM_HandleTypeDef *htim){
if (htim->Channel == HAL_TIM_ACTIVE_CHANNEL_3)
{
if (Is_First_Captured==0) // if the first rising edge is not captured
{
IC_Val1 = HAL_TIM_ReadCapturedValue(htim, TIM_CHANNEL_3); // read the first value
Is_First_Captured = 1; // set the first captured as true
}
else // If the first rising edge is captured, now we will capture the second edge
{
IC_Val2 = HAL_TIM_ReadCapturedValue(htim, TIM_CHANNEL_3); // read second value
if (IC_Val2 > IC_Val1)
{
Difference = IC_Val2-IC_Val1;
}
else if (IC_Val1 > IC_Val2)
{
Difference = (0xffff - IC_Val1) + IC_Val2;
}
float refClock = TIMCLOCK/(PRESCALAR);
frequency = refClock/Difference;
__HAL_TIM_SET_COUNTER(htim, 0); // reset the counter
Is_First_Captured = 0; // set it back to false
}
}
}
uint32_t IC_Val1 = 0;
uint32_t IC_Val2 = 0;
uint32_t Difference = 0;
int Is_First_Captured = 0;
/* Measure Frequency */
float frequency = 0;
#define TIMCLOCK 270000000
#define PRESCALAR 1375
htim23.Instance = TIM23;
htim23.Init.Prescaler = 1374;
htim23.Init.CounterMode = TIM_COUNTERMODE_UP;
htim23.Init.Period = 4294967295;
htim23.Init.ClockDivision = TIM_CLOCKDIVISION_DIV1;
htim23.Init.AutoReloadPreload = TIM_AUTORELOAD_PRELOAD_DISABLE;
sConfigIC.ICPolarity = TIM_INPUTCHANNELPOLARITY_RISING;
sConfigIC.ICSelection = TIM_ICSELECTION_DIRECTTI;
sConfigIC.ICPrescaler = TIM_ICPSC_DIV1;
sConfigIC.ICFilter = 0;