亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频

? 歡迎來到蟲蟲下載站! | ?? 資源下載 ?? 資源專輯 ?? 關于我們
? 蟲蟲下載站

?? 在51系列單片機上移植ucos.htm

?? 該源碼是本人經(jīng)調(diào)試通過的UCOS2操作系統(tǒng)在51單片機上移植好的源代碼
?? HTM
?? 第 1 頁 / 共 3 頁
字號:
      ;指針占3字節(jié)。+0類型+1高8位數(shù)據(jù)+2低8位數(shù)據(jù)<BR>MOVX A,@DPTR ;.OSTCBStkPtr是void指針<BR>MOV 
      R0,A<BR>INC DPTR<BR>MOVX A,@DPTR<BR>MOV R1,A<BR>MOV DPH,R0<BR>MOV 
      DPL,R1<BR><BR>;*UserStkPtr ===&gt; R5 用戶堆棧起始地址內(nèi)容(即用戶堆棧長度放在此處) 詳見文檔說明 
      指針用法詳見C51.PDF第178頁 <BR>MOVX A,@DPTR ;用戶堆棧中是unsigned char類型數(shù)據(jù)<BR>MOV R5,A 
      ;R5=用戶堆棧長度<BR><BR>;恢復現(xiàn)場堆棧內(nèi)容<BR>MOV 
      R0,#OSStkStart<BR><BR>restore_stack:<BR><BR>INC DPTR<BR>INC R0<BR>MOVX 
      A,@DPTR<BR>MOV @R0,A<BR>DJNZ R5,restore_stack<BR><BR>;恢復堆棧指針SP<BR>MOV 
      SP,R0<BR><BR>;OSRunning=TRUE<BR>MOV R0,#LOW (OSRunning)<BR>MOV 
      @R0,#01<BR><BR>POPALL<BR>SETB EA 
      ;開中斷<BR>RETI<BR>;-------------------------------------------------------------------------<BR>RSEG 
      ?PR?OSCtxSw?OS_CPU_A<BR>OSCtxSw: 
      <BR>PUSHALL<BR><BR>OSIntCtxSw_in:<BR><BR>;獲得堆棧長度和起址<BR>MOV A,SP<BR>CLR 
      C<BR>SUBB A,#OSStkStart<BR>MOV R5,A ;獲得堆棧長度 <BR><BR>;OSTCBCur ===&gt; DPTR 
      獲得當前TCB指針,詳見C51.PDF第178頁<BR>MOV R0,#LOW (OSTCBCur) 
      ;獲得OSTCBCur指針低地址,指針占3字節(jié)。+0類型+1高8位數(shù)據(jù)+2低8位數(shù)據(jù)<BR>INC R0<BR>MOV DPH,@R0 
      ;全局變量OSTCBCur在IDATA中<BR>INC R0<BR>MOV 
      DPL,@R0<BR><BR>;OSTCBCur-&gt;OSTCBStkPtr ===&gt; DPTR 獲得用戶堆棧指針<BR>INC DPTR 
      ;指針占3字節(jié)。+0類型+1高8位數(shù)據(jù)+2低8位數(shù)據(jù)<BR>MOVX A,@DPTR ;.OSTCBStkPtr是void指針<BR>MOV 
      R0,A<BR>INC DPTR<BR>MOVX A,@DPTR<BR>MOV R1,A<BR>MOV DPH,R0<BR>MOV 
      DPL,R1<BR><BR>;保存堆棧長度<BR>MOV A,R5<BR>MOVX @DPTR,A<BR><BR>MOV 
      R0,#OSStkStart ;獲得堆棧起址<BR>save_stack:<BR><BR>INC DPTR<BR>INC R0<BR>MOV 
      A,@R0<BR>MOVX @DPTR,A<BR>DJNZ R5,save_stack<BR><BR>;調(diào)用用戶程序<BR>LCALL 
      _?OSTaskSwHook<BR><BR>;OSTCBCur = OSTCBHighRdy<BR>MOV R0,#OSTCBCur<BR>MOV 
      R1,#OSTCBHighRdy<BR>MOV A,@R1<BR>MOV @R0,A<BR>INC R0<BR>INC R1<BR>MOV 
      A,@R1<BR>MOV @R0,A<BR>INC R0<BR>INC R1<BR>MOV A,@R1<BR>MOV 
      @R0,A<BR><BR>;OSPrioCur = OSPrioHighRdy 
      使用這兩個變量主要目的是為了使指針比較變?yōu)樽止?jié)比較,以便節(jié)省時間。<BR>MOV R0,#OSPrioCur<BR>MOV 
      R1,#OSPrioHighRdy<BR>MOV A,@R1<BR>MOV @R0,A<BR><BR>LJMP 
      OSCtxSw_in<BR>;-------------------------------------------------------------------------<BR>RSEG 
      ?PR?OSIntCtxSw?OS_CPU_A<BR><BR>OSIntCtxSw:</FONT></P>
      <P><FONT 
      color=#000080>;調(diào)整SP指針去掉在調(diào)用OSIntExit(),OSIntCtxSw()過程中壓入堆棧的多余內(nèi)容<BR>;SP=SP-4</FONT></P>
      <P><FONT color=#000080>MOV A,SP<BR>CLR C<BR>SUBB A,#4<BR>MOV 
      SP,A<BR><BR>LJMP 
      OSIntCtxSw_in<BR>;-------------------------------------------------------------------------<BR>CSEG 
      AT 000BH ;OSTickISR<BR>LJMP OSTickISR ;使用定時器0<BR>RSEG 
      ?PR?OSTickISR?OS_CPU_A</FONT></P>
      <P><FONT color=#000080>OSTickISR: <BR><BR>USING 0 <BR>PUSHALL<BR><BR>CLR 
      TR0<BR>MOV TH0,#70H ;定義Tick=50次/秒(即0.02秒/次)<BR>MOV TL0,#00H ;OS_CPU_C.C 和 
      OS_TICKS_PER_SEC<BR>SETB TR0<BR><BR>LCALL _?OSIntEnter<BR>LCALL 
      _?OSTimeTick<BR>LCALL _?OSIntExit<BR>POPALL 
      <BR>RETI<BR>;-------------------------------------------------------------------------<BR>CSEG 
      AT 0023H ;串口中斷<BR>LJMP SerialISR ;工作于系統(tǒng)態(tài),無任務切換。<BR>RSEG 
      ?PR?_?serial?OS_CPU_A<BR><BR>SerialISR:<BR><BR>USING 0 <BR>PUSHALL<BR>CLR 
      EA<BR>LCALL _?serial <BR>SETB EA<BR>POPALL 
      <BR>RETI<BR>;-------------------------------------------------------------------------<BR>END<BR>;-------------------------------------------------------------------------</FONT></P>
      <P><FONT color=#000080>文件名 : OS_CPU_C.C</FONT></P>
      <P><FONT color=#000080>void *OSTaskStkInit (void (*task)(void *pd), void 
      *ppdata, void *ptos, INT16U opt) reentrant<BR>{ <BR>OS_STK 
*stk;</FONT></P>
      <P><FONT color=#000080>ppdata = ppdata;<BR>opt = opt; 
      //opt沒被用到,保留此語句防止告警產(chǎn)生 <BR>stk = (OS_STK *)ptos; //用戶堆棧最低有效地址<BR>*stk++ = 
      15; //用戶堆棧長度<BR>*stk++ = (INT16U)task &amp; 0xFF; //任務地址低8位<BR>*stk++ = 
      (INT16U)task &gt;&gt; 8; //任務地址高8位 <BR>*stk++ = 0x00; //PSW<BR>*stk++ = 
      0x0A; //ACC<BR>*stk++ = 0x0B; //B<BR>*stk++ = 0x00; //DPL<BR>*stk++ = 
      0x00; //DPH<BR>*stk++ = 0x00; //R0<BR>*stk++ = 0x01; //R1<BR>*stk++ = 
      0x02; //R2<BR>*stk++ = 0x03; //R3<BR>*stk++ = 0x04; //R4<BR>*stk++ = 0x05; 
      //R5<BR>*stk++ = 0x06; //R6<BR>*stk++ = 0x07; 
      //R7<BR>//不用保存SP,任務切換時根據(jù)用戶堆棧長度計算得出。 <BR>return ((void 
      *)ptos);<BR>}</FONT></P>
      <P><FONT color=#000080>#if OS_CPU_HOOKS_EN<BR>void OSTaskCreateHook 
      (OS_TCB *ptcb) reentrant<BR>{<BR>ptcb = ptcb; /* Prevent compiler warning 
      */<BR>}</FONT></P>
      <P><FONT color=#000080>void OSTaskDelHook (OS_TCB *ptcb) 
      reentrant<BR>{<BR>ptcb = ptcb; /* Prevent compiler warning 
      */<BR>}</FONT></P>
      <P><FONT color=#000080>void OSTimeTickHook (void) 
      reentrant<BR>{<BR>}<BR>#endif</FONT></P>
      <P><FONT color=#000080>//初始化定時器0<BR>void InitTimer0(void) 
      reentrant<BR>{<BR>TMOD=TMOD&amp;0xF0;<BR>TMOD=TMOD|0x01; 
      //模式1(16位定時器),僅受TR0控制<BR>TH0=0x70; //定義Tick=50次/秒(即0.02秒/次)<BR>TL0=0x00; 
      //OS_CPU_A.ASM 和 OS_TICKS_PER_SEC<BR>ET0=1; //允許T0中斷<BR>TR0=1; 
      <BR>}</FONT></P>
      <P><FONT color=#000080>文件名 : YY.C</FONT></P>
      <P><FONT color=#000080>#include <INCLUDES.H></FONT></P>
      <P><FONT color=#000080>#define MAX_STK_SIZE 64</FONT></P>
      <P><FONT color=#000080>void TaskStartyya(void *yydata) reentrant;<BR>void 
      TaskStartyyb(void *yydata) reentrant;<BR>void TaskStartyyc(void *yydata) 
      reentrant;</FONT></P>
      <P><FONT color=#000080>OS_STK 
      TaskStartStkyya[MAX_STK_SIZE+1];//注意:我在ASM文件中設置?STACK空間為40H即64,不要超出范圍。<BR>OS_STK 
      TaskStartStkyyb[MAX_STK_SIZE+1];//用戶棧多一個字節(jié)存長度<BR>OS_STK 
      TaskStartStkyyc[MAX_STK_SIZE+1];</FONT></P>
      <P><FONT color=#000080>void 
      main(void)<BR>{<BR>OSInit();<BR><BR>InitTimer0();<BR>InitSerial();<BR>InitSerialBuffer();<BR><BR>OSTaskCreate(TaskStartyya, 
      (void *)0, &amp;TaskStartStkyya[0],2);<BR>OSTaskCreate(TaskStartyyb, (void 
      *)0, &amp;TaskStartStkyyb[0],3);<BR>OSTaskCreate(TaskStartyyc, (void *)0, 
      &amp;TaskStartStkyyc[0],4);<BR><BR>OSStart();<BR>}</FONT></P>
      <P><FONT color=#000080><BR>void TaskStartyya(void *yydata) 
      reentrant<BR>{<BR>yydata=yydata;<BR>clrscr();<BR>PrintStr("\n\t\t*******************************\n");<BR>PrintStr("\t\t* 
      Hello! The world. 
      *\n");<BR>PrintStr("\t\t*******************************\n\n\n");<BR><BR>for(;;){<BR>PrintStr("\tAAAAAA111111 
      is active.\n");<BR>OSTimeDly(OS_TICKS_PER_SEC); <BR>} <BR>}</FONT></P>
      <P><FONT color=#000080>void TaskStartyyb(void *yydata) 
      reentrant<BR>{<BR>yydata=yydata; 
      <BR><BR>for(;;){<BR>PrintStr("\tBBBBBB333333 is 
      active.\n");<BR>OSTimeDly(3*OS_TICKS_PER_SEC); <BR>} <BR>}</FONT></P>
      <P><FONT color=#000080>void TaskStartyyc(void *yydata) 
      reentrant<BR>{<BR>yydata=yydata; 
      <BR><BR>for(;;){<BR>PrintStr("\tCCCCCC666666 is 
      active.\n");<BR>OSTimeDly(6*OS_TICKS_PER_SEC); <BR>} <BR>}</FONT></P>
      <P><FONT 
      color=#000080>重入問題的解決:<BR>任務函數(shù)中帶有形參和局部變量時若使用reentrant關鍵字會引起重入,從C51.PDF 
      129-131頁的內(nèi)容知:為了函數(shù)重入,形參和局部變量必須保存在堆棧里,由于51硬件堆棧太小,KEIL將根據(jù)內(nèi)存模式在相應內(nèi)存空間仿真堆棧(生長方向由上向下,與硬件棧相反)。對于大模式編譯,函數(shù)返回地址保存在硬件堆棧里,形參和局部變量放在仿真堆棧中,棧指針為?C_XBP,XBPSTACK=1時,起始值在startup.a51中初始化為FFFFH+1。仿真堆棧效率低下,KEIL建議盡量不用,但為了重入操作必須使用。KEIL可以混合使用3種仿真堆棧(大、中、小模式),為了提高效率,針對51推薦統(tǒng)一使用大模式編譯。<BR>為了支持重入,重新設計了堆棧結構(如下圖)。增加了保存仿真堆棧指針?C_XBP和堆棧內(nèi)容的數(shù)據(jù)結構。相應改變的文件有:OS_CPU_A.ASM、OS_CPU_C.C、OS_CPU.H、YY.C。由圖可知,用戶棧中保存的仿真棧與硬件棧相向生長,中間為空閑間隔,顯然uCOSII的堆棧檢測函數(shù)失效。硬件棧的保存恢復詳見上節(jié),仿真堆棧的保存與8086移植中的一樣,OS只提供堆??臻g和只操作堆棧指針,不進行內(nèi)存拷貝,效率相對很高。<BR>建議使用統(tǒng)一的固定大小的堆??臻g,盡管uCOSII原作者把不同任務使用不同空間看成是優(yōu)點,但為了在51上有效實現(xiàn)任務重入,針對51筆者還是堅持不使用這個優(yōu)點。<BR>用戶堆??臻g的大小是可以精確計算出來的。用戶堆??臻g=硬件堆棧空間+仿真堆??臻g。硬件棧占用內(nèi)部RAM,內(nèi)部RAM執(zhí)行效率高,如果堆??臻g過大,會影響KEIL編譯的程序性能。如果堆??臻g小,在中斷嵌套和程序調(diào)用時會造成系統(tǒng)崩潰。綜合考慮,我把硬件堆??臻g大小定成了64字節(jié),用戶根據(jù)實際情況可以自行設定。仿真堆棧大小取決于形參和局部變量的類型及數(shù)量,可以精確算出。因為所有用戶棧使用相同空間大小,所以取占用空間最大的任務函數(shù)的空間大小為仿真堆棧空間大小。這樣用戶堆??臻g大小就唯一確定了。我將用戶堆棧空間大小用宏定義在OS_CFG.H文件中,宏名為MaxStkSize。<BR>51的SP只有8位,無法在64K空間中自由移動,只好采用拷貝全部硬件堆棧內(nèi)容的笨辦法。51 
      本來就弱,這么一來缺點更明顯了。其實,引入OS必然要付出代價,一般OS要占用CPU10%-20%的負荷能力,請權衡利弊決定。切換頻率決定了CPU的耗費,頻率越高耗費越大,大到一定程度就該換更強的CPU了。我選了50Hz的切換頻率,不高也不低,用戶可以根據(jù)需要自行定奪。在耗費無法避免的情況下,我采取了幾個措施來提高效率:1。ret和reti混用減少代碼;2。IE、SP不入出棧,通過另外方式解決;3。用IDATA關鍵字聲明在匯編中用到的全局變量,變DPTR操作為Ri操作;4。設計堆棧結構,簡化算法;5。讓串口輸入輸出工作在系統(tǒng)態(tài),不占用任務TCB和優(yōu)先級,增加彈性緩沖區(qū),減少等待。</FONT></P>
      <P><FONT 
      color=#000080>在51單片機上硬件仿真uCOS51的說明:<BR>zyware網(wǎng)友2002/11/22來信詢問uCOS51在單片機上的硬件仿真問題,具體情況是“在51上用uCOS51核,以及一些構件,keilc上仿真通過,用wave接硬件仿真程序亂飛,wave仿真以前的程序沒有問題,不知是何緣故”。<BR>由于我的OS程序已經(jīng)在KEIL軟件仿真和硬件上實際測試過,所以不可能是程序錯??赡艿脑蛑荒苁怯布抡孳浖O置問題。本人用的是Medwin軟件,在Insight上調(diào)試,使用uCOS51編譯測試程序一樣跑飛。即使添加修改后的startup.a51(詳見《在51單片機上固化uCOS51的說明》)也不正常。我發(fā)現(xiàn)Medwin似乎沒有編譯startup.a51,因為它把該文件加在了other 
      Files目錄下而不是source Files目錄,于是我猜測只有放在source 
      Files目錄下的文件才被編譯。由觀察知,以.c和.asm做后綴的文件均被放在此目錄下且被編譯。于是我立即將startup.a51改成startup.asm并加入項目編譯,結果測試正常。不必擔心startup改名造成沖突,KEIL在鏈接目標文件時會自動處理重名段,本目錄的文件優(yōu)先級高(我是這么理解的,具體原理不清楚,這只是根據(jù)實踐得到的結論,希望了解此處理過程的朋友能告之,不勝感激。)。<BR><BR>具體做法如下:<BR>1。按《在51單片機上固化uCOS51的說明》一文修改startup.a51,并將其更名為startup.asm。<BR>2。將startup.asm、yy1.c、os_cpu_c.c、ucos_ii.c、os_cpu_a.asm五個文件加入項目編譯。<BR>3。運行</FONT></P>

?? 快捷鍵說明

復制代碼 Ctrl + C
搜索代碼 Ctrl + F
全屏模式 F11
切換主題 Ctrl + Shift + D
顯示快捷鍵 ?
增大字號 Ctrl + =
減小字號 Ctrl + -
亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频
国产欧美日韩在线看| 亚洲一区二区三区四区在线观看| 国产精品每日更新| 午夜精品成人在线视频| 成人涩涩免费视频| 欧美成人精品福利| 亚洲伊人伊色伊影伊综合网| 国产91露脸合集magnet| 欧美一二三区在线| 亚洲国产欧美日韩另类综合 | 成人手机在线视频| 日韩一区二区三区三四区视频在线观看| 中文字幕精品一区二区精品绿巨人 | 久久精品亚洲麻豆av一区二区 | 麻豆精品在线播放| 欧美特级限制片免费在线观看| 国产欧美日韩另类视频免费观看 | 国产一区高清在线| 欧美一区二区二区| 婷婷国产在线综合| 国产日韩av一区| 老鸭窝一区二区久久精品| 欧美自拍偷拍午夜视频| 亚洲欧美日韩一区二区| 成人精品免费看| 亚洲国产成人一区二区三区| 国产伦精一区二区三区| 精品91自产拍在线观看一区| 老司机午夜精品99久久| 日韩天堂在线观看| 久久精品久久综合| 欧美电影免费观看高清完整版在 | 国产精品亚洲一区二区三区在线 | 国产精品久久久久7777按摩| 国产999精品久久| 久久免费的精品国产v∧| 国产精品小仙女| 国产欧美日韩久久| yourporn久久国产精品| 国产精品国产三级国产aⅴ原创| 高清不卡一区二区在线| 国产精品欧美一级免费| 99在线精品视频| 亚洲欧美激情视频在线观看一区二区三区| 成人成人成人在线视频| 国产精品九色蝌蚪自拍| 色综合欧美在线| 午夜日韩在线观看| 久久天堂av综合合色蜜桃网| 国产成人aaa| 亚洲欧美日韩国产综合| 欧美日韩精品电影| 韩国三级电影一区二区| 亚洲国产精品v| 91福利国产精品| 日韩电影免费在线看| 久久久91精品国产一区二区精品 | 免费人成黄页网站在线一区二区 | 亚洲日本在线a| 欧美视频中文一区二区三区在线观看 | 国产日韩三级在线| 色综合久久精品| 日韩影院精彩在线| 国产日本欧美一区二区| 91国产免费看| 国产在线精品一区在线观看麻豆| 国产精品理论在线观看| 欧美精品第一页| 国产精品1区二区.| 艳妇臀荡乳欲伦亚洲一区| 日韩欧美一二区| 99久久精品免费| 免费不卡在线观看| 日韩毛片在线免费观看| 日韩一区二区三区电影在线观看 | 日本视频一区二区| 国产精品高清亚洲| 91精品国产综合久久精品图片| 国内外精品视频| 亚洲国产毛片aaaaa无费看 | 亚洲狼人国产精品| 精品黑人一区二区三区久久 | 国产a视频精品免费观看| 亚洲一区二区三区四区的 | 欧美夫妻性生活| 成人精品视频一区| 国产真实乱对白精彩久久| 一片黄亚洲嫩模| 国产精品麻豆欧美日韩ww| 91精品国产91热久久久做人人| 99久久99久久久精品齐齐| 久久精品国产99久久6| 亚洲成人一区二区| 亚洲人精品午夜| 国产欧美精品一区二区三区四区| 制服丝袜亚洲色图| 欧美色电影在线| 色婷婷国产精品| 99精品视频在线观看| 国产麻豆视频一区| 久久er99热精品一区二区| 亚洲成人www| 一区二区三区国产精品| 国产精品久久久久久久久图文区 | 在线成人免费观看| 欧美日韩一区二区三区免费看| av午夜精品一区二区三区| 国产在线视视频有精品| 免费成人在线观看| 久久精品久久综合| 久久精品国产一区二区三| 欧美a级一区二区| 日韩成人一级片| 麻豆一区二区三区| 国模少妇一区二区三区| 免费成人在线影院| 激情文学综合插| 国内精品免费**视频| 久久丁香综合五月国产三级网站| 美女任你摸久久| 精品制服美女丁香| 国产精品一区久久久久| 国产精品一卡二卡在线观看| 国产一区视频在线看| 国产成人精品一区二区三区网站观看| 久久黄色级2电影| 国产剧情在线观看一区二区| 国产精品一区二区你懂的| 国产成人aaa| 91精彩视频在线观看| 欧美日韩在线三区| 日韩一区二区三区av| 精品国产sm最大网站免费看| 国产欧美1区2区3区| 国产精品乱码久久久久久| 一区二区三区欧美激情| 亚洲国产色一区| 久久国产精品色| gogo大胆日本视频一区| 欧美三级韩国三级日本三斤 | 欧美天天综合网| 欧美一区二区三区免费大片 | 91在线高清观看| 欧美午夜电影网| 精品国产乱码久久久久久图片 | 一区二区三区日韩| 看片的网站亚洲| 91丨九色丨黑人外教| 911国产精品| 国产色91在线| 亚洲va国产天堂va久久en| 精品中文字幕一区二区小辣椒| 大白屁股一区二区视频| 欧美最猛黑人xxxxx猛交| 欧美tk丨vk视频| 亚洲欧美日韩系列| 国产永久精品大片wwwapp | 福利视频网站一区二区三区| 在线中文字幕一区| 久久久久久黄色| 一二三区精品视频| 国产精品一区不卡| 91精品国产综合久久精品图片 | 成人一区二区三区| av动漫一区二区| 日韩欧美色电影| 一区二区三区欧美久久| 国产成人免费视频网站| 欧美精品高清视频| 亚洲美女免费在线| 国产资源在线一区| 欧美一卡二卡三卡| 一区二区三区不卡在线观看| 国产精品一区二区免费不卡 | 亚洲不卡av一区二区三区| 大桥未久av一区二区三区中文| 91精品国产麻豆国产自产在线 | 久久精品99国产国产精| 欧美午夜精品一区| 中文字幕在线一区| 国产乱一区二区| 日韩欧美视频一区| 亚洲高清免费一级二级三级| 97久久精品人人做人人爽50路| 精品久久久三级丝袜| 丝袜美腿一区二区三区| 91福利小视频| 亚洲色图欧美在线| 99精品视频在线观看免费| 中文字幕免费在线观看视频一区| 青青草97国产精品免费观看| 欧美视频在线一区| 一区av在线播放| 欧美三级视频在线| 亚洲大片精品永久免费| 欧美日韩在线观看一区二区| 亚洲综合一区在线| 欧美日韩在线一区二区| 五月天一区二区| 欧美一区二区黄色|