找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 3284|回复: 0
打印 上一主题 下一主题
收起左侧

UCOS的初始化后加载任务过程汇编代码

[复制链接]
跳转到指定楼层
楼主
ID:82781 发表于 2015-6-13 16:44 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
昨晚看到了任务切换时的汇编文件,才终于知道人为怎么才可以制造一次模拟中断,任务切换时就是模拟发生了一次中断,其实!他工作的原理是什么呢?
这就要看汇编文件:
MOV DPH,#HIGH (OSRunning)
MOV DPL,#LOW  (OSRunning)
MOV A,#1
MOVX @DPTR,A

SETB TR0
这一段是把系统状态改成运行
并且开启系统定时器
MOV DPH,#HIGH(OSTCBHighRdy)
MOV DPL,#LOW (OSTCBHighRdy)
MOVX A,@DPTR
MOV R0,A
INC DPTR
MOVX A,@DPTR
MOV DPH,R0
MOV DPL,A

;Move OSTCBStkPtr to dptr
MOVX A,@DPTR
MOV R0,A
INC DPTR
MOVX A,@DPTR
MOV DPH,R0
MOV DPL,A

上面的一段是用DPTR指向任务的堆栈,这一点非常重要。这里不得不说他分两次查找,第一次它装载指向堆栈的指针,找到这指针变量的位置后他再一次的吧指针里面的地址取出来装载到DPTR中,所以看到的是两次对DPTR进行赋值,R0作为暂存无实际意义
MOVX A,@DPTR
MOV ?C_IBP,A

JZ OSCPUASmltRstOver ;
INC DPTR
MOVX A,@DPTR  

MOV R0,#StkBottom - 1 ;
MOV R1,A   ;
ADD A,R0   ;sp
MOV SP,A

这一段非常重要他做了什么?
他首先取出用户堆栈的第一个数据,这个数据叫做IBP,
然后取出堆栈的第二个数据,就是初始化的时后定义的堆栈的大小,
然后又取出系统设定好的堆栈开始地址,然后两者求和,求出的和就是SP最后的大小,也就是说SP指针已经指向了最高的地址(如果堆栈向上升成长)
OSCPUARstHardStk:
INC R0   
INC DPTR
MOVX A,@DPTR
MOV @R0,A
DJNZ R1,OSCPUARstHardStk

显然这是一个循环,他的做用就是吧剩下的用户对战里的数据全部加载到CPU硬件堆栈中,比如函数入口地址,ACCb,psw等保存在用户堆栈的数据全部加载到系统栈中,接下来才是关键的也是最后的一哆嗦,
POP 07
POP 06
POP 05
POP 04
POP 03
POP 02
POP 01
POP 00
POP PSW
POP DPL
POP DPH
POP B
POP ACC ;A is register but ACC is direct ram

SETB EA ;after start, enable EA
RETI
这个是个出栈命令,POP,前面已经说到SP已经指向了最高的堆栈地值,那么这就表示把系统栈的所有的数据全部弹入对应的寄存器寄存器中,也就是说他用MOV指令代替了PUSH,他用MOV把用户栈数据复制到系统栈中,然后用户POP把系统栈的数据又恢复到寄存器中,是不是有点多此一举?直接把用户数据恢复到CPU寄存器不是更快马?开始我那么想,向下看,有个RETI,再看栈顶正好存入的是函数的入口地址,哈哈所以他就跳转到了对应的任务中去了,跟中断几乎是一模一样的,都是保护现场,一个样,


注意区分户任务栈和系统栈,所谓系统栈就是那个用SP做栈指针,用RETI返回的栈,而用户栈其实说白了就是个数组而已!需要用户自己定义。
以上是出栈,入站的问题上比较纠结,主要是不符合预想,有待学习!他压栈的时候是把一组从f0-ff之间的数据写进去了后面又紧跟着系统栈的内容,按理说入栈就把系统栈内的寄存器保存就可以了吧,为什么还要入一块不相关的内存?而且任务加载总是从初始化开始,没有进行任务间的转换,还看不到他处理的方法,不过思路都差不多,入站的格式一定得和出站的格式是一样的存放顺序(在用户站立)否则他不可能找到正确的如口的!纠结中。。。。。。。







分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏 分享淘帖 顶 踩
回复

使用道具 举报

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

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

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