OpenEdv-开源电子网

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

请教高手,我用f103ct6的T1CH4和T3CH2同时计数脉冲,当两路脉冲同时到达,同时产生中断时会丢脉冲,怎么解决?

[复制链接]

23

主题

131

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
329
金钱
329
注册时间
2015-6-23
在线时间
68 小时
发表于 2015-9-1 19:46:40 | 显示全部楼层 |阅读模式
5金钱
请教高手,我用f103ct6的T1CH4和T3CH2同时计数脉冲,当两路脉冲同时到达,同时产生中断时会丢脉冲,怎么解决?

最佳答案

查看完整内容[请看2#楼]

尽量精简中断,然后同时产生的话,mcu会根据你设置的优先级,来先后处理的,只是低优先级的会稍微放后处理,只要你的处理时间(2个定时器的处理),少于下一次中断到来的时间,就不会有问题。
正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165540
金钱
165540
注册时间
2010-12-1
在线时间
2117 小时
发表于 2015-9-1 19:46:41 | 显示全部楼层
尽量精简中断,然后同时产生的话,mcu会根据你设置的优先级,来先后处理的,只是低优先级的会稍微放后处理,只要你的处理时间(2个定时器的处理),少于下一次中断到来的时间,就不会有问题。
我是开源电子网www.openedv.com站长,有关站务问题请与我联系。
正点原子STM32开发板购买店铺http://openedv.taobao.com
正点原子官方微信公众平台,点击这里关注“正点原子”
回复

使用道具 举报

23

主题

131

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
329
金钱
329
注册时间
2015-6-23
在线时间
68 小时
 楼主| 发表于 2015-9-1 21:35:33 | 显示全部楼层
回复【2楼】正点原子:
---------------------------------
我把TIM1CH4的优先级设为抢占优先级2,副优先级0,TIM3CH2设为抢占优先级2,副优先级1;或者TIM1CH4设为抢占优先级1,副优先级0,TIM3CH2设为抢占优先级2,副优先级0。两种情况下,两路脉冲的频率是相同的:当两路脉冲同时到来时,脉冲的频率低于20P/S都会丢脉冲;但当两脉冲是正交到来时(也就是1路和2路的脉冲是轮流等时间间隔),频率高达1700P/S时,两路脉冲都能正确计算脉冲的周期和个数。这样的情况应该不是中断处理的时间过长引起的脉冲丢失吧。
回复

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165540
金钱
165540
注册时间
2010-12-1
在线时间
2117 小时
发表于 2015-9-1 22:06:43 | 显示全部楼层
回复【3楼】luyongyun:
---------------------------------
你看看中断处理占了多少时间。
我是开源电子网www.openedv.com站长,有关站务问题请与我联系。
正点原子STM32开发板购买店铺http://openedv.taobao.com
正点原子官方微信公众平台,点击这里关注“正点原子”
回复

使用道具 举报

23

主题

131

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
329
金钱
329
注册时间
2015-6-23
在线时间
68 小时
 楼主| 发表于 2015-9-1 22:36:33 | 显示全部楼层
回复【4楼】正点原子:
---------------------------------
请问怎么看呢?只能初略计算吧?
       如果用上面的数据计算(每路1700P/S时)就是,当两路脉冲正交到来时,每路脉冲中断处理时间<1/(2x1700)s=294.11us这,CPU完成两路脉冲各一次中断的时间之和<588.22us。当两路脉冲同时到来并采用很低的频率时(每路20P/S时)两次脉冲到来的时间间隔是1/20=50000us, CPU完成两路脉冲各一次中断的时间之和不变,为<588.22us,所以CPU完全是够时间进行中断处理程序运行的,但这时却出现了漏脉冲现象。
回复

使用道具 举报

22

主题

180

帖子

1

精华

高级会员

Rank: 4

积分
616
金钱
616
注册时间
2015-6-29
在线时间
101 小时
发表于 2015-9-2 13:40:59 | 显示全部楼层
难道是这两个脉冲真的非常非常同时,导致两个IO口同时出现中断信号,MCU漏了?不懂,占个楼围观下
我是菜鸟
回复

使用道具 举报

23

主题

131

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
329
金钱
329
注册时间
2015-6-23
在线时间
68 小时
 楼主| 发表于 2015-9-2 13:52:48 | 显示全部楼层
回复【6楼】负西弱:
---------------------------------
我用的是同一个脉冲源,分两路进入F103
回复

使用道具 举报

23

主题

131

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
329
金钱
329
注册时间
2015-6-23
在线时间
68 小时
 楼主| 发表于 2015-9-4 00:03:44 | 显示全部楼层
回复【5楼】luyongyun:
---------------------------------
 我想是不是先来的脉冲中断处理完后,在清除自己的中断标志时会把几乎同时到来的脉冲中断标志也清除掉,导致没有进入几乎同时到来的另一个中断的处理程序,这样就丢了脉冲?
我的中断配置程序如下,请高手帮看看会不会产生我说的情况发生
TIM_ICInitTypeDef  TIM1_ICInitStructure;
void TIM1_Cap_Init(u16 arr,u16 psc)
{  
 GPIO_InitTypeDef GPIO_InitStructure;
TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure;
  NVIC_InitTypeDef NVIC_InitStructure;

RCC_APB2PeriphClockCmd(RCC_APB2Periph_TIM1, ENABLE);// 
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA , ENABLE);  //使能GPIO外设时钟使能
                                                                     
   //设置该引脚为复用输出功能,TIM1 CH4
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_11; //TIM_CH4
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPD; //PA11 输入  
GPIO_Init(GPIOA, &GPIO_InitStructure);
GPIO_ResetBits(GPIOA,GPIO_Pin_11);  //PA11 下拉

//初始化定时器1 TIM1
TIM_DeInit(TIM1);
TIM_TimeBaseStructure.TIM_Period = arr; //设置在下一个更新事件装入活动的自动重装载寄存器周期的值  80K
TIM_TimeBaseStructure.TIM_Prescaler =psc; //设置用来作为TIMx时钟频率除数的预分频值  不分频
TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;  //设置时钟分割:TDTS = Tck_tim
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;  //TIM向上计数模式
TIM_TimeBaseInit(TIM1, &TIM_TimeBaseStructure); //根据TIM_TimeBaseInitStruct中指定的参数初始化TIMx的时间基数单位

//初始化TIM1输入捕获参数 
TIM1_ICInitStructure.TIM_Channel = TIM_Channel_4; //CC4S=01  选择输入端 IC4映射到TI4上
   TIM1_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_Rising; //上升沿捕获
   TIM1_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI; //映射到TI4上
   TIM1_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1;  //配置输入分频,不分频 
   TIM1_ICInitStructure.TIM_ICFilter = 0x03;//IC1F=0011 配置输入滤波器 8次滤波,8us
   TIM_ICInit(TIM1, &TIM1_ICInitStructure);

//中断分组初始化
NVIC_InitStructure.NVIC_IRQChannel = TIM1_CC_IRQn;  //TIM1中断
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 2;  //先占优先级2级
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;  //从优先级0级
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道被使能
NVIC_Init(&NVIC_InitStructure);  //根据NVIC_InitStruct中指定的参数初始化外设NVIC寄存器 
TIM_ClearFlag(TIM1, TIM_FLAG_Update);
TIM_ITConfig(TIM1,TIM_IT_CC4|TIM_IT_Update,ENABLE);//允许更新中断 ,允许CC4IE捕获中断

TIM_Cmd(TIM1, ENABLE);  //使能TIM1
    
}

void TIM1_CC_IRQHandler(void)
{
脉冲1的周期和计数
}

TIM_ICInitTypeDef  TIM3_ICInitStructure;

void TIM3_Cap_Init(u16 arr,u16 psc)
{  
GPIO_InitTypeDef GPIO_InitStructure;
TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure;
  NVIC_InitTypeDef NVIC_InitStructure;

RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE); //使能TIM3时钟
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);  //使能GPIOA时钟

GPIO_InitStructure.GPIO_Pin  = GPIO_Pin_7;  //PA7 清除之前设置 
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPD; //PA7 输入  GPIO_Mode_IPD
GPIO_Init(GPIOA, &GPIO_InitStructure);
GPIO_ResetBits(GPIOA,GPIO_Pin_7);  //PA7 下拉

//初始化定时器3 TIM3  
TIM_TimeBaseStructure.TIM_Period = arr; //设定计数器自动重装值 
TIM_TimeBaseStructure.TIM_Prescaler =psc;  //预分频器   
TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1; //设置时钟分割:TDTS = Tck_tim
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;  //TIM向上计数模式
TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure); //根据TIM_TimeBaseInitStruct中指定的参数初始化TIMx的时间基数单位
  
//初始化TIM3输入捕获参数
TIM3_ICInitStructure.TIM_Channel = TIM_Channel_2; //CC2S=01  选择输入端 IC2映射到TI2上
   TIM3_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_Rising; //上升沿捕获
   TIM3_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI; //映射到TI1上
   TIM3_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1;  //配置输入分频,不分频 
   TIM3_ICInitStructure.TIM_ICFilter = 0x03;//IC1F=0011 配置输入滤波器 8次滤波,8us
   TIM_ICInit(TIM3, &TIM3_ICInitStructure);

//中断分组初始化
NVIC_InitStructure.NVIC_IRQChannel = TIM3_IRQn;  //TIM3中断
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 2;  //先占优先级2级
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 2;  //从优先级0级
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道被使能
NVIC_Init(&NVIC_InitStructure);  //根据NVIC_InitStruct中指定的参数初始化外设NVIC寄存器 

TIM_ITConfig(TIM3,TIM_IT_CC2,ENABLE);//允许更新中断 ,允许CC2IE捕获中断

    TIM_Cmd(TIM3,ENABLE );  //使能定时器3
}

void TIM3_IRQHandler(void)
{
脉冲2的周期和计数
}
回复

使用道具 举报

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

本版积分规则



关闭

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

正点原子公众号

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

GMT+8, 2025-6-17 02:19

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

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