STM32正交编码器,怎么读取数据,避免中断更新值的影响

2019-12-10 18:15发布

应该问题可以简化为如果用定时器来计时,怎样在主程序里读取的时候,避免正好进入中断,影响最终结果。
比如设置溢出的周期是4000个,脉冲,那我在中断里面 对变量 Circle ++; 然后主程序要用到编码器的值,只需要读取定时器当前的值X = TIMx->CNT,
然后总脉冲数 = Circle*4000 + X;  如果在计算上面式子的时候,定时器又中断了,那应该算出来的值有问题的吧。
这个怎么避免?
友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。
该问题目前已经被作者或者管理员关闭, 无法添加新回复
14条回答
374184600
1楼-- · 2019-12-10 20:32
 精彩回答 2  元偷偷看……
dtlz
2楼-- · 2019-12-10 20:35
把你的定时器中断设置成最高就可以
error_dan
3楼-- · 2019-12-11 02:18
几乎不可能的事情,如果一定要做到万无一失,实际上不是万无一失,你算算中断里面操作这个数才多久,外面读取这个数据进行一次加法又要多久,两个操作占总的运行时间的比例是非常小的,几乎不会碰到一起去,除非你一直在操作这个数...
一定要保证没问题的:给这个数据加锁,实际上就是数据的同步问题,进中断开锁,准备要读取做加法的时候锁上,加完了检查一下锁如果被打开了说明碰到了中断,数据已经变更,重来一次.

如果要进一步,对这把锁的操作必须要是原子操作,也是不可中断的.CM3里面这个很容易,不嫌麻烦的用互斥指令,这样最保险连同后面的读取和做加法一起受互斥条件保护,最简单的是把锁定义到位带区但是这样加锁和解锁是原子的,但是对变量操作还是有可能被中断,只是这个概率太太太低了,少年...
374184600
4楼-- · 2019-12-11 03:34
dtlz 发表于 2015-9-25 15:50
把你的定时器中断设置成最高就可以

没有理解为什么?
中断优先级设置最高,那也会存在主程序,和中断竞争的问题啊。
374184600
5楼-- · 2019-12-11 07:13
error_dan 发表于 2015-9-25 17:30
几乎不可能的事情,如果一定要做到万无一失,实际上不是万无一失,你算算中断里面操作这个数才多久,外面读取这 ...

中断跟主程序竞争的问题,应该是编程的时候需要注意的问题吧?
就算概率小,那遇到了,也是不小的么。
我的使用场景是 步进电机编码器这块,我需要2ms就读取一次编码器的值,判断是否失步,那日积月累的,总是会出错的。
我印象中,之前书上看到过读两次的方法,我用了下,看看,这样有没有问题?
        int c1;
        int c2;
        do
        {
                c1 = Encoder_PPR_Local * 4 * m->EncodeCircles + ENCODER_TIMER->CNT;
                c2 = Encoder_PPR_Local * 4 * m->EncodeCircles + ENCODER_TIMER->CNT;
        }
        while(((c1>c2) ? c1-c2 : c2-c1) < 2000);
68336016
6楼-- · 2019-12-11 09:52
 精彩回答 2  元偷偷看……

一周热门 更多>