機(jī)電之家資源網(wǎng)
單片機(jī)首頁(yè)|單片機(jī)基礎(chǔ)|單片機(jī)應(yīng)用|單片機(jī)開(kāi)發(fā)|單片機(jī)文案|軟件資料下載|音響制作|電路圖下載 |嵌入式開(kāi)發(fā)
培訓(xùn)信息
贊助商
C8051F12X中多bank的分區(qū)跳轉(zhuǎn)處理
C8051F12X中多bank的分區(qū)跳轉(zhuǎn)處理
 更新時(shí)間:2008-8-19 13:17:13  點(diǎn)擊數(shù):90
【字體: 字體顏色
行B_SWITCH3,在執(zhí)行?B_SWITCH3的(6)語(yǔ)句之前,B_CURRENTBANK還是前面執(zhí)行?B_SWITCHl時(shí)的值,即B_SWITCHl的低8位。執(zhí)行語(yǔ)句(6)后,B_CURRENTBANK恢復(fù)為B_SWITCH3的低8位,為返回main函數(shù)做準(zhǔn)備。然后PSBANK置為33h,即指向bank3,接著執(zhí)行RET語(yǔ)句,堆棧③成為RET的返回地址,程序回到了main()中Delay_noOS(10)的下一條語(yǔ)句繼續(xù)執(zhí)行,B_CURRENTBANK也已恢復(fù)。

  這個(gè)調(diào)用過(guò)程中,用了6個(gè)堆棧字節(jié),3條RET指令,關(guān)鍵內(nèi)容就是B_CURRENTBANK變量,它保存了可以恢復(fù)調(diào)用前bank環(huán)境代碼的地址低位。從被調(diào)用函數(shù)返回 到這個(gè)地址后,就能恢復(fù)調(diào)用前的bank環(huán)境,即賦予PSBANK正確的值。

  不采用直接保存PSBANK值然后再恢復(fù),而是用壓棧的方式保存了相關(guān)地址(語(yǔ)句(1)~(3)),是為了實(shí)現(xiàn)跨bank區(qū)的嵌套調(diào)用。例如,在Delay_noOS(10)函數(shù)中,如果再次跨bank去調(diào)用新函數(shù),會(huì)再次重復(fù)上述過(guò)程,堆棧從②往上再長(zhǎng)6個(gè)字節(jié)。Delay_noOS(10)函數(shù)之前執(zhí)行B_SWITCHI產(chǎn)生的B_CURRENTBANK值(B_SWITCHI的低8位)也會(huì)進(jìn)棧,為調(diào)用完新函數(shù)后返回到bankl繼續(xù)執(zhí)行Delay_noOS(10)提供保證。

2 無(wú)操作系統(tǒng)bank分區(qū)間的強(qiáng)制跳轉(zhuǎn)

  通過(guò)上面的分析得知,如果要處理跨bank區(qū)的跳轉(zhuǎn)、調(diào)用和返回,關(guān)鍵是能正確處理好PSBANK中的內(nèi)容。當(dāng)程序沒(méi)有操作系統(tǒng)用于任務(wù)切換,而又需要強(qiáng)制退出某一函數(shù)進(jìn)入到另一函數(shù)的某一地址時(shí),比如說(shuō)在中斷發(fā)生后,結(jié)束原來(lái)的工作轉(zhuǎn)入到另一工作去,就需要處理好PSBANK。

  如果不考慮bank,可以在轉(zhuǎn)入新地址之前執(zhí)行一段代碼,保存該地址處的環(huán)境變量[2],包括堆棧指針sP和需要的入口地址。然后在中斷返回之前,恢復(fù)此環(huán)境變量,執(zhí)行中斷返回指令進(jìn)入該新地址。這個(gè)思路和C51庫(kù)函數(shù)setjump和longjump比較相近,但比它們靈活,因?yàn)榄h(huán)境變量可以自己處理。

  考慮bank后的情況稍微復(fù)雜些,環(huán)境變量中需增加bank的處理信息,那么只處理PSBANK行不行呢?

  如果僅保存和恢復(fù)PSBANK,則很簡(jiǎn)單,在保存環(huán)境變量的程序中加入:

  JMPEnv[envl][3]=PSBANK;

  在恢復(fù)環(huán)境變量的程序中加入:

  PSBANK=JMPEnv[envl][3];

  這里環(huán)境變量是二維數(shù)組JMPEnv,envl代表一個(gè)環(huán)境變量,即一個(gè)返回點(diǎn)。第二維是變量中的參數(shù)個(gè)數(shù)。因此可以保存多個(gè)環(huán)境變量以供使用。

  初看起來(lái)這樣處理是沒(méi)有問(wèn)題的,可實(shí)際上不行。因?yàn)檫M(jìn)入返回點(diǎn)后,雖然PSBANK正確了,但是B_CUR-RENTBANK可能已經(jīng)被修改,不能和返回點(diǎn)程序的bank區(qū)匹配,如果再次出現(xiàn)跨bank調(diào)用的話將不能正確返回。

  處理方法是有點(diǎn)技巧的,因?yàn)镃語(yǔ)言不支持匯編變量B_CURRENTBANK的寫(xiě)法,所以在L51_bank.A51中要加上聲明:

  PUBLIC BLCURRENTBANK

  和偽指令:

  B_CURRENTBANK EQU B_CURRENTBANK

  這樣就可以在C程序中使用B_CURRENTBANK了,先聲明B_CURRENTBANK:

  extern Uchar data B_CURRENTBANK;

  然后在保存環(huán)境變量程序中加入:

  JMPEnv[envl][3]=PSBANK;

  JMPEnv[envl][4]=B_CURRENTBANK;

  恢復(fù)環(huán)境變量程序中加入:

  PSBANK=JMPEnv[envl][3];

  B_CURRENTBANK=JMPEnv[envl][4];

  這樣恢復(fù)環(huán)境變量進(jìn)入到新程序后,也將恢復(fù)該程序?qū)?yīng)的正確?B_cuRRENTBANK值,問(wèn)題得到解決。

3 no/0S-ll移植中的bank分區(qū)處理

  μC/OS-II的51版本已經(jīng)很成熟,但是所有移植版本均未處理bank問(wèn)題,需要增加該內(nèi)容,否則不能在包括C8051F12X系列及其他多bank程序中使用。

  如前所述,Keil C51提供對(duì)跨bank調(diào)用的透明切換支持,但在使用操作系統(tǒng)時(shí),這種透明切換機(jī)制還需要提供對(duì)任務(wù)切換的支持。因?yàn)槿蝿?wù)的切換,程序可能需要到別的代碼分組中去運(yùn)行,而此時(shí)PSBANK和B_CUR-RENTBANK還停留在原來(lái)代碼分組中的狀態(tài),將導(dǎo)致程序崩潰。顯然,無(wú)論由于什么情況導(dǎo)致的任務(wù)切換完成之前,都需要保存和恢復(fù)PSBANK和B_CURRENT-BANK的值。解決的辦法是在每次任務(wù)切換前將PS-BANK和B_CURRENTBANK壓入用戶(hù)任務(wù)棧。

  按照μC/OS-II的要求,在任務(wù)創(chuàng)建時(shí),任務(wù)棧必須初始化成像運(yùn)行中的任務(wù)剛剛發(fā)生過(guò)中斷一樣嘲。B_CURRENTBANK的初始值取決于該任務(wù)所在分組對(duì)應(yīng)的切換代碼段的低8位地址。所以,任務(wù)堆棧的初始化函數(shù)OSTaskStkInit需要加入一個(gè)參數(shù)INT8U bank,指明該任務(wù)位于哪個(gè)代碼分組中。又由于任務(wù)堆棧的初始化函數(shù)是被任務(wù)創(chuàng)建函數(shù)OSTaskCreate調(diào)用的,所以該函數(shù)一樣需要加入?yún)?shù)INT8U bank。

  在壓棧,出棧宏中需要加入:

PUSH PSBANK
PUSH B_CURRENTBANK

POP B_CURRENTBANK
POP PSBANK

  在任務(wù)堆棧的初始化函數(shù)OSTaskStkInit中需要加入:

*stk++=17; //堆棧長(zhǎng)度增加2個(gè)到17
;
if(bank==0x22:){ //bank2
*stk++=bank;
*stk++=CurrentBank2();
else if(bank==0x33){ //bank3
*stk++=bank;
*stk++=CurrentBank3();
}
else{ //bankl和common
*stk++=0xll; //PSBANK
  • 上一篇: 從LCD電極讀數(shù)的單片機(jī)接口技術(shù)
  • 下一篇: 采用Topswitch系列芯片的單片開(kāi)關(guān)電源效率研究
  • 發(fā)表評(píng)論   告訴好友   打印此文  收藏此頁(yè)  關(guān)閉窗口  返回頂部
    熱點(diǎn)文章
     
    推薦文章
     
    相關(guān)文章
    網(wǎng)友評(píng)論:(只顯示最新5條。)
    關(guān)于我們 | 聯(lián)系我們 | 廣告合作 | 付款方式 | 使用幫助 | 機(jī)電之家 | 會(huì)員助手 | 免費(fèi)鏈接

    點(diǎn)擊這里給我發(fā)消息66821730(技術(shù)支持)點(diǎn)擊這里給我發(fā)消息66821730(廣告投放) 點(diǎn)擊這里給我發(fā)消息41031197(編輯) 點(diǎn)擊這里給我發(fā)消息58733127(審核)
    本站提供的機(jī)電設(shè)備,機(jī)電供求等信息由機(jī)電企業(yè)自行提供,該企業(yè)負(fù)責(zé)信息內(nèi)容的真實(shí)性、準(zhǔn)確性和合法性。
    機(jī)電之家對(duì)此不承擔(dān)任何保證責(zé)任,有侵犯您利益的地方請(qǐng)聯(lián)系機(jī)電之家,機(jī)電之家將及時(shí)作出處理。
    Copyright 2007 機(jī)電之家 Inc All Rights Reserved.機(jī)電之家-由機(jī)電一體化網(wǎng)更名-聲明
    電話:0571-87774297 傳真:0571-87774298
    杭州濱興科技有限公司提供技術(shù)支持

    主辦:杭州市高新區(qū)(濱江)機(jī)電一體化學(xué)會(huì)
    中國(guó)行業(yè)電子商務(wù)100強(qiáng)網(wǎng)站

    網(wǎng)站經(jīng)營(yíng)許可證:浙B2-20080178-1