我用一个外部中断(用于按键检测)、两个定时器做了一个简易门铃,但是程序好像有点跑飞,不晓得是什么原因,请大虾们指点一下,程序如下:
#include <stm32f10x_lib.h>
#include "menling.h"
#include "led.h"
#include "delay.h"
u8 k=0,m=0,key_num=0;
u16 time=0;
/*==============================以下为定时器3程序部分=================================*/
/*定时器3中断服务函数*/
void TIM3_IRQHandler(void)
{
if(TIM3->SR&0X0001)//溢出中断
{
Auto=!Auto;
}
TIM3->SR&=0<<0;//清除中断标志位
}
/*定时器2中断服务函数*/
void TIM2_IRQHandler(void)
{
if(TIM2->SR&0X0001)//溢出中断
{
time++;
}
TIM2->SR&=0<<0;//清除中断标志位
}
/************************************************************
函数名称:Timer3_Init
函数功能:通用定时器3中断初始化
入口函数:arr(自动重装值)
psc(时钟预分频数)
返回参数:无
备 注:时钟为2倍APB1(36M)
溢出时间(MS)=(arr*(psc+1))/输入时钟频率(10KHZ)
************************************************************/
void Timer3_Init(u16 arr,u16 psc)
{
RCC->APB1ENR|=1<<1;//使能TIM3时钟
TIM3->ARR=arr;//设置计数器自动重装值(0.1ms)
TIM3-> SC=psc;//预分频器7200,刚好10khz
TIM3->DIER|=1<<0; //允许更新中断
TIM3->DIER|=1<<6; //允许触发中断
TIM3->CR1|=0X01; //使能定时器3
MY_NVIC_Init(1,1,TIM3_IRQChannel,2);// 抢占1,子优先级1,组2
}
void Timer2_Init(u16 arr,u16 psc)
{
RCC->APB1ENR|=1<<0;//使能TIM2时钟
TIM2->ARR=arr;//设置计数器自动重装值(0.1ms)
TIM2-> SC=psc;//预分频器7200,刚好10khz
TIM2->DIER|=1<<0; //允许更新中断
TIM2->DIER|=1<<6; //允许触发中断
//TIM2->CR1|=0X01; //使能定时器2
MY_NVIC_Init(1,2,TIM2_IRQChannel,2);// 抢占1,子优先级2,组2
}
////////////////////////////////////////////////////////////////////////////////////
/********************************
函数名称:外部中断端口初始化函数
入口参数:无
返回参数:无
备注:初始化PA13/PA15为中断输入
********************************/
void EXTI0_Init(void)
{
RCC->APB2ENR|=1<<2; //使能PORTA时钟
JTAG_Set(JTAG_SWD_DISABLE);//关闭JTAG和SWD
GPIOA->CRH&=0X0F0FFFFF;//PA13,15设置成输入
GPIOA->CRH|=0X80800000;
GPIOA->ODR|=1<<13; //PA13上拉,PA0默认下拉
GPIOA->ODR|=1<<15; //PA15上拉
Ex_NVIC_Config(GPIO_A,13,FTIR);//下降沿触发
MY_NVIC_Init(2,1,EXTI15_10_IRQChannel,2);//抢占2,子优先级1,组2
}
/*门铃控制*/
void Menling_Control(void)
{
u8 i;
if(key_num==3&&time>60)
{
key_num=0;
k=10;
time=0;
LED0=!LED0;
}
for(i=k;i>0;i--)
{
//TIM3->CR1|=0X01; //使能定时器3
Timer3_Init(9,7199);//90khz ()
delay_ms(70);
Timer3_Init(6,7199);//60khz ()
delay_ms(70);
}
k=0;
Auto=0;
TIM3->CR1|=0X00; //关闭定时器3
}
/*门铃控制*/
void Menling_Control1(void)
{
Timer3_Init(5,7199);//50khz ()
//TIM3->CR1|=0X01; //使能定时器3
delay_ms(140);
Auto=0;
TIM3->CR1|=0X00; //关闭定时器3
}
/*外部中断15~10服务程序*/
void EXTI15_10_IRQHandler(void)
{
delay_ms(10); //消抖
if(KEY0==0) //按键0
{
time=0;
TIM2->CR1|=0X01; //使能定时器2
Menling_Control1();
key_num++;
while(!KEY0);
}
TIM2->CR1|=0X00; //关闭定时器2
EXTI-> R = 1<<13; //清除line13上的中断标志位
}
void Menling_Init(void)
{
RCC->APB2ENR|=1<<3; //使能PORTB时钟
GPIOB->CRL&=0XFFFFFFF0;
GPIOB->CRL|=0X00000003;//PB0 推挽输出
GPIOB->ODR|=1<<0;
EXTI0_Init();
Timer2_Init(5,7199) ;
}
|