OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 5676|回复: 4

学习开发板的中断问题,无法进入中断

[复制链接]

14

主题

98

帖子

0

精华

初级会员

Rank: 2

积分
174
金钱
174
注册时间
2014-3-5
在线时间
0 小时
发表于 2014-3-6 21:39:32 | 显示全部楼层 |阅读模式
void EXTI2_IRQHandler(void)
{
delay_ms(10);//消抖
if(KEY2==0)  //按键KEY2
{
LED0=!LED0;
}  
EXTI_ClearITPendingBit(EXTI_Line2);  //清除LINE2上的中断标志位  
}

这个是开发板上的中断函数,正常运行。。delay_ms(10)用的系统定时器中断产生,系统定时器中断优先级高于外部中断,会不会造成进入延时后死循环??
我改了下函数,想要实现的功能是按key1,进入中断函数,启动定时器T3、T1;按KEY2,
进入中断函数,关闭定时器,定时器引脚全为高。。
但是按键后,引脚没有pwm波形。。于是去掉中断函数中的延时,有波形输出。。
main.c 函数
#include  "stm32f10x.h"
#include  "stm32f10x_tim.h"
#include  "stm32f10x_exti.h"
#include  "main.h"
#include  "misc.h"
extern void time_ini(void);
void TimingDelay_Decrement(void);
void Delay(__IO uint32_t nTime);
static __IO uint32_t TimingDelay;
void NVIC_Configuration(void);
unsigned char _it0=0,num=0;
unsigned int CCR2_Val1=800,CCR2_Val2=800;

/****************************************************************************
* 名    称:void RCC_Configuration(void)
* 功    能:系统时钟配置为72MHZ, 外设时钟配置
* 入口参数:无
* 出口参数:无
* 说    明:
* 调用方法:无 
****************************************************************************/ 
void RCC_Configuration(void){

  SystemInit(); 
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE); 
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_GPIOB | RCC_APB2Periph_GPIOC 
  | RCC_APB2Periph_GPIOD| RCC_APB2Periph_GPIOE , ENABLE);
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_TIM1,ENABLE);
  RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);

}

/****************************************************************************
* 名    称:int main(void)
* 功    能:主函数
* 入口参数:无
* 出口参数:无
* 说    明:
* 调用方法:无 
****************************************************************************/ 
int main(void)
{
// unsigned char a=0;
  RCC_Configuration();
NVIC_Configuration( ); 
GPIO_Configuration();      
    SysTick_Config(72000);   //配置SYSTICK时钟节拍为1ms一次
  while(1)
{
Delay(10); 
GPIO_ResetBits(GPIOE,GPIO_Pin_11);
GPIO_SetBits( GPIOE,GPIO_Pin_10);
  }
}
/****************************************************************************
* 名    称:void Delay(__IO uint32_t nTime)
* 功    能:定时延时程序 1ms为单位
****************************************************************************/  
void Delay(__IO uint32_t nTime)
  TimingDelay = nTime;

  while(TimingDelay != 0);
}
/****************************************************************************
* 名    称:void TimingDelay_Decrement(void)
* 功    能:获取节拍程序
****************************************************************************/  
void TimingDelay_Decrement(void)
{
  if (TimingDelay != 0x00)
  { 
    TimingDelay--;
  }
}


/****************************************************************************
* 名    称:void NVIC_Configuration(void)
* 功    能:中断源配置
* 入口参数:无
* 出口参数:无
* 说    明:
* 调用方法:无 
****************************************************************************/ 
void NVIC_Configuration(void)
{
  NVIC_InitTypeDef NVIC_InitStructure;
  EXTI_InitTypeDef EXTI_InitStructure;
  /* Configure one bit for preemption priority */
  /* 优先级组 说明了抢占优先级所用的位数,和子优先级所用的位数   在这里是1, 7 */    
  NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1);
  
  /* Enable the EXTI Interrupt */
  NVIC_InitStructure.NVIC_IRQChannel =EXTI3_IRQn; //外部中断3
  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;     //抢占优先级 0
  NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1; //子优先级1  
  NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //使能
  NVIC_Init(&NVIC_InitStructure);

  NVIC_InitStructure.NVIC_IRQChannel = EXTI4_IRQn; //外部中断4
  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;     //抢占优先级 0
  NVIC_InitStructure.NVIC_IRQChannelSubPriority = 2; //子优先级2  
  NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //使能
  NVIC_Init(&NVIC_InitStructure);

  NVIC_InitStructure.NVIC_IRQChannel =EXTI9_5_IRQn; //外部中断9-5
  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;     //抢占优先级 1
  NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1; //子优先级1  
  NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //使能
  NVIC_Init(&NVIC_InitStructure);

  //用于配置AFIO外部中断配置寄存器AFIO_EXTICR1,用于选择EXTI1外部中断的输入源是PE3。
  GPIO_EXTILineConfig(GPIO_PortSourceGPIOE, GPIO_PinSource3);     //外部中断配置AFIO--ETXI3
  //用于配置AFIO外部中断配置寄存器AFIO_EXTICR1,用于选择EXTI2外部中断的输入源是PE4。
  GPIO_EXTILineConfig(GPIO_PortSourceGPIOE, GPIO_PinSource4);     //外部中断配置AFIO--ETXI4
  //用于配置AFIO外部中断配置寄存器AFIO_EXTICR1,用于选择EXTI2外部中断的输入源是PE5。
  GPIO_EXTILineConfig(GPIO_PortSourceGPIOE, GPIO_PinSource5);     //外部中断配置AFIO--ETXI5

  GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource7); //障碍物中断
  GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource8);
  GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource10);
  GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource11);
  GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource12);

 
  EXTI_InitStructure.EXTI_Line = EXTI_Line3; //PE1 作为键盘K1 检测状态
  EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt;    //中断模式
  EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling;    //下降沿触发
  EXTI_InitStructure.EXTI_LineCmd = ENABLE;
  EXTI_Init(&EXTI_InitStructure);
  EXTI_InitStructure.EXTI_Line = EXTI_Line4; //PE2 作为键盘K2 检测状态
  EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt;    //中断模式
  EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling;    //下降沿触发
  EXTI_InitStructure.EXTI_LineCmd = ENABLE;
  EXTI_Init(&EXTI_InitStructure);

  EXTI_InitStructure.EXTI_Line = EXTI_Line5; //PE5作为键盘K3 检测状态
  EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt;    //中断模式
  EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling;    //下降沿触发
  EXTI_InitStructure.EXTI_LineCmd = ENABLE;
  EXTI_Init(&EXTI_InitStructure); 

/**************************************
**函数名称:obstacle_action()
**函数描述:对障碍物信号做出反应
**************************************/
void  obstacle_action(void)
    {
   
    if(_it0==7) //检测到障碍物
   { 
       _it0=0;
       back( );
 
}
else if(_it0==8)  //B2检测到障碍物
   {
      _it0=0;
  back( );
 
}
else if(_it0==10)  //A2和B2都没有检测到,A1检测到
   {  
_it0=0;
 back( );
 
}
else if(_it0==11)   //A3检测到
   {
_it0=0;
back( );
turnleft( );
}
else if(_it0==12) //B1检测到
   {
_it0=0;
back( );
} //结合左右碰触开关
}
void GPIO_Configuration(void) //GPIO口配置,实际用的是GPIO口的哪些引脚,打开即可
 {

  GPIO_InitTypeDef GPIO_InitStructure;
//配置E端口的输出引脚,PE9恒高,PE8/CA1输出脉冲(左轮),PE10(MOTOR)H-L,PE12(J142)PWM,PE11/KR(L)
  GPIO_InitStructure.GPIO_Pin=( GPIO_Pin_8 |GPIO_Pin_12 |GPIO_Pin_13 | GPIO_Pin_14 );
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; 
  GPIO_Init(GPIOE, &GPIO_InitStructure); 
//TIM1完全复用功能开启
  GPIO_PinRemapConfig(GPIO_FullRemap_TIM1 , ENABLE);
  GPIO_InitStructure.GPIO_Pin = (GPIO_Pin_7 |GPIO_Pin_10 |GPIO_Pin_9| GPIO_Pin_11);
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
  GPIO_Init(GPIOE, &GPIO_InitStructure);
  GPIO_SetBits( GPIOE,GPIO_Pin_9);
  GPIO_SetBits( GPIOE,GPIO_Pin_7);
//配置E端口的输入引脚,按键功能启动或者停止 PE3-5 /KEY1-3
  GPIO_InitStructure.GPIO_Pin = (GPIO_Pin_3 |GPIO_Pin_4|GPIO_Pin_5 );
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;//上拉
  GPIO_Init(GPIOE, &GPIO_InitStructure);
  GPIO_SetBits( GPIOE,GPIO_Pin_3);
//配置B端口的输出引脚PB0复用为TIM3的通道3,右轮
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
  GPIO_Init(GPIOB, &GPIO_InitStructure);
//PB1 pin start configure and initialization
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
  GPIO_Init(GPIOB, &GPIO_InitStructure);
  GPIO_SetBits( GPIOB,GPIO_Pin_1);
 }

 void turnleft(void)   // 左转
 {
 CCR2_Val1=800;  
 CCR2_Val2=1400;
 time_ini( );
 }
 void turnright(void) //右转
 {
 CCR2_Val1=1400;
 CCR2_Val2=800 ;
 time_ini( );
 }
 void go(void)  //  前进
 {
 Delay(50);
 time_ini( );
 }
 void back(void)   // 后退
 {
  GPIO_InitTypeDef GPIO_InitStructure;  
  //PB0置0
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
  GPIO_Init(GPIOB, &GPIO_InitStructure);
  GPIO_ResetBits( GPIOB,GPIO_Pin_1); 
  //PE9置0
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9;
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
  GPIO_Init(GPIOE, &GPIO_InitStructure);
  GPIO_ResetBits( GPIOE,GPIO_Pin_9);
  Delay(50);
  CCR2_Val1=1400;
  CCR2_Val2=1400;
 }
 void stop(void)
 {
  GPIO_InitTypeDef GPIO_InitStructure;
Delay(10);
  TIM_Cmd(TIM3, DISABLE); // 关闭TIM3-CH3
PB0复用为TIM3的通道3
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
  GPIO_Init(GPIOB, &GPIO_InitStructure);
  GPIO_SetBits( GPIOB,GPIO_Pin_0);
PB9置高
  TIM_Cmd(TIM1,DISABLE); //关闭TIM1-CH1
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8;
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
  GPIO_Init(GPIOE, &GPIO_InitStructure);
  GPIO_SetBits( GPIOE,GPIO_Pin_8);
 }

 void KEY_scan(void) //按键扫描
 {
   num=0;
   if(_it0==1){  //按键按下标志 
    if(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_3)==0)
{  //KEY1/SW2  
  Delay(0xffff);  
if(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_3)==0){  //按键消抖动
while(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_3)==0);//是否松开按键  
num=1;  //键值1  为K1按下
goto n_exit;
}
 }  
   }
   else if(_it0==2){  //按键按下标志 
    if(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_4)==0){  //KEY2/SW3  
  Delay(0xffff);  
if(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_4)==0){  //按键消抖动
while(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_4)==0);//是否松开按键  
num=2;  //键值2  为K2按下
goto n_exit;
}
 }  
   }
   else if(_it0==3){  //按键按下标志 
    if(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_5)==0){  //K3/SW4
  Delay(0xffff);  
if(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_5)==0){  //按键消抖动
while(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_5)==0);//是否松开按键  
num=3;  //键值3  为K3按下
goto n_exit;
}
 }  
   }
   n_exit:;
   _it0=0; 
}

 void KEY_start(void) //根据按键确定电机行走方向
{
  if(num==1)
  {
 Delay(10);
  go();
  }
  if(num==2)
  {
  Delay(10);
  stop();
  }
  else 
  {
  stop();
  }
}

中断函数
void EXTI3_IRQHandler(void)
if(EXTI_GetITStatus(EXTI_Line3) != RESET)  //判别是KEY1按下
  {
_it0=1;
      go();      //按键中断标志
    EXTI_ClearITPendingBit(EXTI_Line3);  //清除中断请求标志
  } 
}
void EXTI4_IRQHandler(void)
{
if(EXTI_GetITStatus(EXTI_Line4) != RESET)  //判别是KEY2按下
  {
_it0=2;
       stop();  //按键中断标志
    EXTI_ClearITPendingBit(EXTI_Line4);  //清除中断请求标志
  }  
}
请问是哪里没配置好么?

正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

120

主题

7878

帖子

13

精华

资深版主

Rank: 8Rank: 8

积分
12012
金钱
12012
注册时间
2013-9-10
在线时间
427 小时
发表于 2014-3-7 09:52:52 | 显示全部楼层
回复【楼主位】fangxiaoyanzhou:
---------------------------------
建议清中断标志语句还是放到最前面
现在,程序把烂铜烂铁变得智能化了,人呢,一旦离开了这烂铜烂铁就不知道干啥了
回复 支持 反对

使用道具 举报

14

主题

98

帖子

0

精华

初级会员

Rank: 2

积分
174
金钱
174
注册时间
2014-3-5
在线时间
0 小时
 楼主| 发表于 2014-3-7 10:14:19 | 显示全部楼层
回复【2楼】Badu_Space:
---------------------------------
好的,试下
回复 支持 反对

使用道具 举报

14

主题

98

帖子

0

精华

初级会员

Rank: 2

积分
174
金钱
174
注册时间
2014-3-5
在线时间
0 小时
 楼主| 发表于 2014-3-7 10:41:41 | 显示全部楼层
回复【2楼】Badu_Space:
---------------------------------
楼主,先谢谢你。先清中断标志后果然能正常工作。按KEY1,启动定时器,按KEY2,停止定时器,但是为什么要先请标志么?开发板给的是后清中断标志?
回复 支持 反对

使用道具 举报

120

主题

7878

帖子

13

精华

资深版主

Rank: 8Rank: 8

积分
12012
金钱
12012
注册时间
2013-9-10
在线时间
427 小时
发表于 2014-3-7 10:49:56 | 显示全部楼层
回复【4楼】fangxiaoyanzhou:
---------------------------------
可以看下这个帖子http://www.openedv.com/posts/list/27442.htm
现在,程序把烂铜烂铁变得智能化了,人呢,一旦离开了这烂铜烂铁就不知道干啥了
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2025-5-14 03:33

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表