打印

关于中断函数调用带参数函数的问题

[复制链接]
9194|12
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
kin0001|  楼主 | 2012-3-26 18:54 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
/*
大家好,现在有一个问题想弄明白:如果在中断函数中调用带有参数和和返回值的函数应该如何处理:
我是这样处理的:
*/
unsigned char Adr,Chan ADC_RES;//全局变量
//==============================================
unsigned char ADCFun(Chan)        //ad采集函数
{
        static unsigned char ClkNum;
        for(ClkNum=0x05;ClkNum!=0x00;--ClkNum)
        {
                Clk_port=0;
                if(Chan&0x80)
                        Data_port=1;
                else
                        Data_port=0;
                Clk_port=1;
                Chan=Chan<<1;
        }
        ......
        return(ADC_RES);
}
//==============================================
void interrupt TMR0Server(void)//中断函数
{
        static unsigned int        Adc0=0x0000;
        static unsigned int        Adc1=0x0000;
        ......
        static unsigned int        Adc7=0x0000;
       
        TMR0IF=0;
        ......
        switch(Adr)
        {
                case 0x00:
                Adc0+=ADCFun(0x88);                //调用ad采集函数
                break;
                case 0x01:
                Adc1+=ADCFun(0x98);
                break;
                ......
                case 0x07:
                Adc7+=ADCFun(0xc8);
                break;
        }
        if(++Adr>=0x08)
                Adr=0x00;
        ......
}
/*以上只是举个例子,相似程序编译通过并且可以使用,但感觉上好像并不科学,请问大家有没有其他方法可以实现*/

相关帖子

沙发
airwill| | 2012-3-26 21:27 | 只看该作者
应该说, 中断中调用函数和其他方式调用函数是完全一致的.
也许你会感觉中断中会有现场保护等方面的处理, 那些是有编译器来完成的, 程序员无需关注, 也不会影响用户使用(当然如果用汇编, 那程序员就要处理了).

使用特权

评论回复
板凳
原野之狼| | 2012-3-26 22:48 | 只看该作者
不科学在何处  说出来和大伙儿探讨一下

使用特权

评论回复
地板
ayb_ice| | 2012-3-27 08:29 | 只看该作者
必须确保中断与被调用函数使用同一寄存器组,其它的没有什么

使用特权

评论回复
5
sunhq02| | 2012-3-27 08:33 | 只看该作者
中断中调用别的函数的话有几个要注意的,主要是可重入性方面的
一个是被调函数有没有被别的地方调用,是否有冲突的可能性
,对于你的例子要保证 ADCFun(Chan)  没有在别的地方被调用
另外一个是,函数中的局部变量是不是处理好了
,比如 ADCFun(Chan)  中的静态变量
还有一个比较容易忽视的地方, 就是被调函数的参数不能太多
,参数太多的话 Rn中存放不完(当然,前提是你设置了在Rn中传递参数)
,参数会被存放到堆中
,而中断函数是不参与覆盖分析的
,那样有可能会导致被调函数的参数出错

使用特权

评论回复
6
kin0001|  楼主 | 2012-3-27 10:54 | 只看该作者
首先谢谢各位的回答:
其实我的疑问就是unsigned char ADCFun(Chan)这个函数,如果在没用定义Chan全局变量的前提下,可不可以像普通函数那样unsigned char ADCFun(unsigned char Chan);但在中断中调用这个函数的时候Chan变量会不会和其他局部变量有冲突

当时我想到静态局部变量,写成unsigned char ADCFun(static unsigend char Chan),不过编译出错

使用特权

评论回复
7
airwill| | 2012-3-27 13:14 | 只看该作者
unsigned char ADCFun(static unsigend char Chan)

呵呵, c 语言是值应用的. 按照调用规则, 参数都是局部变量, 通过堆栈传递, 怎么能定义 static 变量呢?

使用特权

评论回复
8
yewuyi| | 2012-3-27 13:22 | 只看该作者
不建议在中断中调用太复杂的函数,建议中断中就处理几个标志量后抓紧退出。

使用特权

评论回复
9
liang7143| | 2012-3-27 14:07 | 只看该作者
LZ 这个函数 有重入问题

使用特权

评论回复
10
dqyubsh| | 2012-3-27 17:01 | 只看该作者
中断重入确实是**烦,这也是最难查找的出错原因——如果程序99%情况下都是对的,只在某种特定情况下出现了莫名其妙的问题,而这种问题仅仅是个表象,问题背后的代码找不到错误,此时有理由高度怀疑中断函数的重入。

象楼主这种代码结构,最大的坏处是,某一天想加一个函数或一个算法,比如乘除法、显示等等,但这个函数加上之后,可能某个其它位置就出错了,而这个位置之前一直是对的。为了解决这个问题,恐怕要把代码结构重新推倒重来,这也是嵌入式程序员进阶的重要一步。

使用特权

评论回复
11
kin0001|  楼主 | 2012-3-27 21:35 | 只看该作者
/*
听大伙一说,我真没用考虑到这个问题.
9楼说有重入问题,是一定有还是有可能有;
重入我能不能理解为:当中断外的某些函数调用某一块代码段时,此时发生中断,中断函数恰好也调用这块代码
比如说pic16的芯片,中断外的函数有使用到乘法时,中断函数有乘法操作就有可能会发生重入?
上边只是举例,实际上我的中断比上面的复杂得多,里边有很多数据需要及时处理,实在不知道在中断函数外能
不能及时处理过来,不过中断外的函数却不存在像乘法这种数据运算,这样应该没用问题吧
没想不到牵出另一个问题来了
本人比较菜,不专业,大家见笑了
*/

使用特权

评论回复
12
刘前辈| | 2012-3-28 12:31 | 只看该作者
呵呵,很简单:如果担心有重入问题,只要在主函数/中断函数 可能共享的函数前面关闭中断即可:例如下面:
#pragma  disable
unsigned char ADCFun(Chan)        //ad采集函数
{
        static unsigned char ClkNum;
        for(ClkNum=0x05;ClkNum!=0x00;--ClkNum)
        {
                Clk_port=0;
                if(Chan&0x80)
                        Data_port=1;
                else
                        Data_port=0;
                Clk_port=1;
                Chan=Chan<<1;
        }
        ......
        return(ADC_RES);
}
//==============================================


//

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

23

主题

63

帖子

0

粉丝