打印

屏蔽

[复制链接]
418|16
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
tian111|  楼主 | 2016-6-19 17:16 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
这个函数在中断处理完了后调用的,时间不做要求,里面用到了DPTR和B。

可是C51无论什么优先级,是否inline,还要color register, 以及是否手工插入 _push_   _pop_ ,还要using....

结果都是一个,在进入中断函数的时候,压栈DPTR和B,进入子函数后直接mov dpl,xxx

谁有没有个好的办法屏蔽?
沙发
宋倩2010| | 2016-6-19 17:17 | 只看该作者
你都在中断调用了函数,KEIL还能说什么,这种情况下KEIl肯定认为你使用了全部寄存器,当然要压栈了,否则可能出错,把函数直接展开在中断中。

使用特权

评论回复
板凳
tian111|  楼主 | 2016-6-19 17:19 | 只看该作者
时间不做要求的话,在中断里设个标志。

那个函数放在主程序里。

使用特权

评论回复
地板
chenho| | 2016-6-19 17:23 | 只看该作者
LZ说了中断函数本身的实时性要求很高,而这个功能模块只要中断完成后实现就行、时间不做要求,所以觉得3L的方法靠谱。

使用特权

评论回复
5
happy_10| | 2016-6-19 17:25 | 只看该作者
很简单的事。把中断程序写在另一个模块,用汇编语言写,自己愿意怎么屏蔽都行。然后放在项目里和C主函数一起编译、连接即可。
给你个框架,当然我这里用的是串口中断4,    CSEG  AT  0023h;  自己按要求作相应修改即可:
例如  text2.asm

NAME        TEXT2
?PR?ssio?TEXT2    SEGMENT   CODE
        PUBLIC        ssio
CSEG        AT        00023H
           LJMP        ssio

; void  ssio(void)  interrupt 4  using 1

         RSEG  ?PR?ssio?TEXT2
           USING        1
ssio:
         ;填写自己的汇编程序语句        

        ACALL    (  你的C函数 )
           RETI         
           END

如果C中断函数过于复杂,只要把C中断函数编译结果化为汇编文件test2.src,然后自己修改即可。

使用特权

评论回复
6
冰清玉洁| | 2016-6-19 17:27 | 只看该作者
如果在中断函数里调用外部函数,那么中断函数一旦触发,就需要开辟现场保护区,保护被中断的CPU现场。——不单单是保护dptr和B。与LZ外部函数是否用到dptr、B寄存器无关。这种保护并不会造成程序运行结果错误,为何要屏蔽?——保护就保护吧,反正还要恢复的。

这是按照“系统调用陷入机制”来做的,尽管你不是系统调用,但是C51按标准做,一切简单标准化了。

使用特权

评论回复
7
wenfen| | 2016-6-19 17:29 | 只看该作者
两个中断函数,把我说的那个带dptr的函数放定时器中断里面去,收数据包的这个函数,收完数据包后,不再调用带dptr的函数,而是关自己中断,直接触发定时器中断。在接口上,给客户实现最快速度的同时,也保证了数据的完整性。

使用特权

评论回复
8
zhuhuis| | 2016-6-19 17:31 | 只看该作者

"1 数据包内速度要求特别快,也就是我说的收到数据中断到应答之间不能超过9条汇编语句,其中包括地址等简单的协议判断"
以上要求不是开玩笑吧,理论上51的中断延时都可能不止这个条件,根本就不可能实现,9条指令多长时间(9~18US),串口发个数据多少时间。。。

使用特权

评论回复
9
宋倩2010| | 2016-6-19 17:36 | 只看该作者

51类型单片机,12M晶振,串口9600 bps,发送一个字节大概是1ms,也就是1,000us。
很高级的能够自动发出响应(不影响CPU工作)的智能通信控制器,响应时间大概是1、2个比特之内,如若仍是9600 bps,自动响应时间为100us左右。当然智能通信控制器的传输比特率至少是64Kbps的(同步传输技术)。

使用特权

评论回复
10
chenho| | 2016-6-19 17:37 | 只看该作者
补充一下,Keil C51有个优化选项,可以对全局的寄存器使用情况进行优化

使用特权

评论回复
11
gongche| | 2016-6-19 17:39 | 只看该作者
正确的做法应该在中断程序中设置标志,或者写事件队列,退出中断后在主程序中检测处理,既然中断的实时要求高,就不应该在中断里做太多事情

使用特权

评论回复
12
huwr| | 2016-6-19 17:40 | 只看该作者
编译程序有责任保护中断程序中使用到的寄存器,无论如何,你确实用了DPTR,编译程序就不可能不闻不问

使用特权

评论回复
13
huanghuac| | 2016-6-19 17:42 | 只看该作者
如果你确实不想中断程序自动保存DPTR,要么不要使用DPTR,要么自己手工汇编写中断ISR,没得其他办法

使用特权

评论回复
14
happy_10| | 2016-6-19 17:43 | 只看该作者

我的实际情况是数据包内速度要求特别快,也就是我说的收到数据中断到应答之间不能超过9条汇编语句,其中包括地址等简单的协议判断。

使用特权

评论回复
15
happy_10| | 2016-6-19 17:44 | 只看该作者
而且 数据包收完后,可以稍等处理,但是我的主循环是20ms的,等的也太长了。。。。。

使用特权

评论回复
16
tian111|  楼主 | 2016-6-19 17:46 | 只看该作者
我好像明白了什么。。。多谢几位

使用特权

评论回复
17
CallReceiver| | 2016-6-21 13:34 | 只看该作者
宋倩2010 发表于 2016-6-19 17:17
你都在中断调用了函数,KEIL还能说什么,这种情况下KEIl肯定认为你使用了全部寄存器,当然要压栈了,否则可 ...

是的,必须得压栈处理吧。。。

使用特权

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

本版积分规则

797

主题

8878

帖子

7

粉丝