这是我的按钮的代码
void PB_Init(void){
RCC->AHB1ENR |= RCC_AHB1ENR_GPIOCEN;
GPIOC->MODER |= ( 0x0 << GPIO_MODER_MODE13_Pos);
GPIOC->PUPDR |= ( 0x1 << GPIO_PUPDR_PUPD13_Pos);
}
void EXTI15_10_Init(void){
PB_Init(); // Initialize PC13 as input.
RCC->APB2ENR |= (1<<14); // Enable System configuration controller
SYSCFG->EXTICR[3] &= ~(1<<7); // Select Port C as source, EXTIx = 0b0010
SYSCFG->EXTICR[3] &= ~(1<<6); // Select Port C as source, EXTIx = 0b0010
SYSCFG->EXTICR[3] |= (1<<5); // Select Port C as source, EXTIx = 0b0010
SYSCFG->EXTICR[3] &= ~(1<<4); // Select Port C as source, EXTIx = 0b0010
EXTI->IMR |= (1<<13); // Disable interrupt request mask on EXTI line 13
EXTI->FTSR |= (1<<13); // Enable EXTI on Falling edge
EXTI->RTSR &= ~(1<<13); // Disable EXTI on Rising edge
RCC->APB2ENR &= ~(1<<14); // Disable System configuration controller
}
volatile bool flag=0;
void EXTI15_10_IRQHandler(void){
if(flag==0){
TIM2->CR1|=TIM_CR1_CEN;
flag=!flag;
EXTI->PR |= (1<<13); // Clear PR to re-enable EXTI interrupt
}else{
TIM2->CR1&=~TIM_CR1_CEN;
flag=!flag;
EXTI->PR |= (1<<13); // Clear PR to re-enable EXTI interrupt
}
}
void Interrupt_Init(void){
EXTI15_10_Init(); // Step 1, this is defined elsewhere
NVIC->IP[EXTI15_10_IRQn] = (1 << 4); // Step 3: Set priority to 1
NVIC->ISER[40 >> 5] |= (1 << (40 % 32)); // Step 4: Enable interrupt
}
它的问题是,每当我按下按钮时,我的计时器都不会暂停,它的行为是随机的,达到最大-最小,你永远不知道。永远不会真正停下来
尝试弄乱标志等,但无济于事
这是实现这一目的的最后一段代码,在您浏览这段代码之前,我必须先说几件关键的事情。所有计算都从 IRQ 处理程序中删除,因为我的导师告诉我,在 IRQ 中执行任何逻辑都是不好的做法,因此它已移至 main,正如我将在有关按钮的其他问题上发布的答案中一样。我想就是这样。
void PB_Init(void){
RCC->AHB1ENR |= RCC_AHB1ENR_GPIOCEN;
GPIOC->MODER |= ( 0x0 << GPIO_MODER_MODE13_Pos);
GPIOC->PUPDR |= ( 0x1 << GPIO_PUPDR_PUPD13_Pos);}
void EXTI15_10_Init(void){
PB_Init(); // Initialize PC13 as input.
RCC->APB2ENR |= (1<<14); // Enable System configuration controller
SYSCFG->EXTICR[3] &= ~(1<<7); // Select Port C as source, EXTIx = 0b0010
SYSCFG->EXTICR[3] &= ~(1<<6); // Select Port C as source, EXTIx = 0b0010
SYSCFG->EXTICR[3] |= (1<<5); // Select Port C as source, EXTIx = 0b0010
SYSCFG->EXTICR[3] &= ~(1<<4); // Select Port C as source, EXTIx = 0b0010
EXTI->IMR |= (1<<13); // Disable interrupt request mask on EXTI
EXTI->FTSR |= (1<<13); // Enable EXTI on Falling edge
EXTI->RTSR &= ~(1<<13); // Disable EXTI on Rising edge
}
void Interrupt_Init(void){
EXTI15_10_Init();
NVIC->IP[EXTI15_10_IRQn] = (1 << 4);
NVIC->ISER[40 >> 5] |= (1 << (40 % 32));
}
union InterruptFlag {
struct {
volatile bool flag: 1; // Just one bit for our flag
volatile bool press: 1;
} bits_access;
uint32_t reg; // We'll use this for byte access
};
volatile union InterruptFlag flag = { .bits_access.flag = 0 }; //
Initialize to 0
volatile uint16_t pressTime;
volatile bool lastButtonPress=0;
volatile bool buttonPress=1;
void EXTI15_10_IRQHandler(void){
flag.bits_access.flag = !flag.bits_access.flag;
EXTI->PR |= (1<<13); // Clear PR to re-enable EXTI interrupt
}
void clearIR(void){
flag.bits_access.flag = 0;
buttonPress=0;
}