2022-11-01 04:03 PM
I have tried Timer 2 CH1, and Timer 3 CH1. No Luck.
I know the pin has a square wave going into it and the timer is counting, because I can poll GPIOB->IDR and read TIM3->CNT.
Nothing I can do can get a reading other then zero from TIM3->CC1
I cannot get a IRQ from TIM3 unless I force it via TIM3->EGR |= 2;
My Init Code:-
void InitTimer3(void)
{
GPIOB->PUPDR &= ~(3<<8); // No Pullup or Pulldown
GPIOB->OSPEEDR |= (3<<8); // Very High speed
GPIOB->MODER &= ~(3<<8); // PB4 Input
GPIOB->AFR[0] &= ~(0x0F << 16);
GPIOB->AFR[0] |= (2<<16); // AF2
RCC->APB1ENR |= 2; // Timer 3 enable
RCC->AHB1ENR |= 2; // PORTB Clock Enable
TIM3->CCER = 0;
TIM3->PSC = 511; // Prescale
TIM3->ARR = 0xFFFF;//250; // Max Count
TIM3->CCMR1 = 1; // Compare 1
TIM3->DIER = (1<<1) | 1; // CC1 IRQ enabled
TIM3->CR1 = (1<<7) | 1; // Enabled, UP, Auto Reload Buffered
TIM3->CR2 = 0;
TIM3->CCER = (1<<3) | (1<<1) | 1;//1; // Enable Compare 1, Both Edges
TIM3->SR = 0;
NVIC_SetPriority(TIM3_IRQn, 0);
NVIC_EnableIRQ(TIM3_IRQn);
}
My IRQ:-
void TIM3_IRQHandler(void)
{
if ((TIM3->SR & 2) != 0) // Capture 1
{
Dwell ++;
TIM3->SR &= ~2;
}
if ((TIM3->SR & 1) != 0) // OVF WORKS!!!!!!
{
TIM3->SR &= ~1;
}
}
Dwell will not advance, unless I put Dwell ++; into the OVF code
Solved! Go to Solution.
2022-11-01 08:16 PM
Found it!!!
GPIOB->MODER |= (2<<8); // Alternative Function Mode
So not only do you have to choose the applicable AF via GPIOB->AFR, but also set MODER to AF mode!
*SOLVED*
2022-11-01 04:50 PM
If you enable GPIOB clock *after* you set its registers, then those registers won't get set.
If in doubts, the first thing always is to read out the relevant registers content and check/compare.
JW
PS. Don't
TIM3->SR &= ~2;
do
TIM3->SR = ~2;
2022-11-01 05:18 PM
Thankyou for your quick response.
I moved the RCC clock enables to the begining of the Init code, and put an ELSE on the OVF IF to see what else is happeneing.
Now some real strange things happen:-
Erratically, I get the OVF ELSE excecuting, which would indicate another IRQ source. Only problem is, that source is not CCR1! When that happens, TIM3->SR reads back as 28 (B2, B3, B4), which are output compares (disabled) and they do not have the ability to generate an IRQ with this code!
Still no IRQ from CCR1.
Does that make sense? After Init, All registers read back correct.
Also, I need to use TIM3->SR &= ~2 to clear ONLY bit 1. Without the & it will clear all other IRQ flags as well. I want to preserve the other flags.
2022-11-01 07:29 PM
So My new code:-
void InitTimer3(void)
{
RCC->APB1ENR |= 2; // Timer 3 enable
RCC->AHB1ENR |= 2; // PORTB Clock Enable
GPIOB->PUPDR &= ~(3<<8); // No Pullup or Pulldown
GPIOB->OSPEEDR |= (3<<8); // Very High speed
GPIOB->MODER &= ~(3<<8); // PB4 Input
GPIOB->AFR[0] &= ~(0x0F << 16);
GPIOB->AFR[0] |= (2<<16); // AF2
TIM3->CCER = 0; // Timer Channel OFF
TIM3->PSC = 511; // Prescale
TIM3->ARR = 0xFFFF; // Max Count
TIM3->CR1 = (1<<7) | 1; // Enabled, UP, Auto Reload Buffered
TIM3->CR2 = 0;
TIM3->CCMR1 = 0; // Clear
TIM3->CCMR1 |= 1; // Compare 1
TIM3->CCMR1 |= (3<<4); // Filter
TIM3->CCER = 10; // Capture on both edges
TIM3->CCER |= 1; // Enable Compare 1
TIM3->DIER |= 3; // CC1 + TOF IRQ enabled
NVIC_SetPriority(TIM3_IRQn, 0);
NVIC_EnableIRQ(TIM3_IRQn);
}
//
//
//
void TIM3_IRQHandler(void)
{
if ((TIM3->SR & 1) != 0) // OVF
{
TIM3->SR &= ~1;
Dwell ++;
}
else
Debug+= 100;
if ((TIM3->SR & 2) != 0) // Capture 1
{
Debug++;
TIM3->SR &= ~2;
}
Dwell ++;
}
SO if Dwell is not an even number, then an IRQ other then TOF Update has occured. It is always Even.
Debug always stays on ZERO, so no CCR1 IRQ.
2022-11-01 08:16 PM
Found it!!!
GPIOB->MODER |= (2<<8); // Alternative Function Mode
So not only do you have to choose the applicable AF via GPIOB->AFR, but also set MODER to AF mode!
*SOLVED*