<meter id="pryje"><nav id="pryje"><delect id="pryje"></delect></nav></meter>
          <label id="pryje"></label>

          新聞中心

          EEPW首頁 > 嵌入式系統(tǒng) > 設計應用 > 單片機C51編程幾個有用的模塊

          單片機C51編程幾個有用的模塊

          作者: 時間:2012-07-04 來源:網(wǎng)絡 收藏

          為了能夠使用用SyncRecePackage或AsyncRecePackage函數(shù)從接收到的數(shù)據(jù)中識別出如上格式的數(shù)據(jù)包,有兩種方法:
          第一種辦法是在Config.h文件中定義宏SCOMM_SimplePackageFormat,說明數(shù)據(jù)包為一種簡單格式,比如上面的協(xié)議。
          之后還要定義兩個宏分別用來識別數(shù)據(jù)包頭和數(shù)據(jù)包尾,兩個宏分別是:
          IsPackageHeader(x)和IsPackageTailer(x,y,z)
          接收函數(shù)(SyncRecePackage和AsyncRecePackage)在沒有開始接收數(shù)據(jù)包(準確的說是還沒有從接收到的數(shù)據(jù)包中找到包頭的時候),會對接收到的每一個字節(jié)的數(shù)據(jù)調(diào)用IsPackageHeader宏,將相應的數(shù)據(jù)作為參數(shù),如果IsPackageHeader宏的結果為TRUE,則認為找到了數(shù)據(jù)包頭,否則繼續(xù)對下一個字節(jié)進行判斷。
          上面的協(xié)議對應的IsPackageHeader宏可以寫為:
          #defineIsPackageHeader(x)((x)==0xff)
          當接收到包頭之后,接收函數(shù)會對接下來的每一個字節(jié)數(shù)據(jù)調(diào)用IsPackagTailer宏來判斷是不是已經(jīng)接收完數(shù)據(jù)包,三個參數(shù)分別為:
          x:當前判斷的數(shù)據(jù)。
          y:從包頭開始到當前被判斷的數(shù)據(jù)止的計數(shù)值,即當前已經(jīng)接收到的字節(jié)數(shù)。
          z:用戶在調(diào)用SyncRecePackage或AsyncRecePackage時指定的byParam參數(shù)。
          與IsPackageHeader相似,如果宏IsPackageTailer的運算結果為TRUE,則認為接收到完整的數(shù)據(jù)包,則調(diào)用相應的回調(diào)函數(shù)(對于異步接收函數(shù))或返回(對于接收函數(shù))。如果運算結果為FALSE則繼續(xù)判斷下一個字節(jié)的數(shù)據(jù)。
          上面的協(xié)議對應的IsPackageTailer宏可以寫為:
          #defineIsPackageTailer(x,y,z)((y)>=(z))
          當然,用戶也可以將IsPackageHeader和IsPackageTailer定義成為函數(shù),通過BIT類型的返回值來向調(diào)用者提供與相應宏相同的信息。

          另一種辦法需要在Config.h文件中定義宏SCOMM_ComplexPackageFormat。(需要注意的是,不能夠同時定義SCOMM_SimplePackageFormat和SCOMM_ComplexPackageFormat宏,否則會造成嚴重的不可預見性錯誤。
          這時需要提供回調(diào)函數(shù)QueryPackageFormat,原形如下:
          BYTEQueryPackageFormat(BYTEbyData,BYTEbyCount,BYTEbyParam);
          函數(shù)中三個參數(shù)的含義與使用簡單數(shù)據(jù)包格式時判斷數(shù)據(jù)包尾的宏的參數(shù)相同。
          函數(shù)通過返回值來通知作為調(diào)用者的接收函數(shù)對接收到的數(shù)據(jù)如何處理,但目前這種方法僅為需要處理復雜數(shù)據(jù)包格式時的一種可選方法,但不推薦。用戶如果想使用這種方法可以自己更改接收函數(shù)中相應的
          #ifdefSCOM_ComplexPackageFormat
          #endif//SCOMM_ComplexPackageFormat
          預編譯指令之間的內(nèi)容。
          例如指定QueryPackageFormat的返回值的含義:
          0:繼續(xù)找數(shù)據(jù)包頭或繼續(xù)找數(shù)據(jù)包尾。
          1:找到數(shù)據(jù)包頭。
          2:找到數(shù)據(jù)包尾。
          3:數(shù)據(jù)包出錯,需要拋棄。
          然后更改源代碼來實現(xiàn)上面的協(xié)議。

          注意:當用戶需要使用字符串的時候,可以利用簡單的包裝函數(shù)將字符串轉換為字節(jié)數(shù)組。所以沒有必要提供專用的字符串處理函數(shù)。

          鍵盤掃描模塊
          鍵盤掃描模塊有兩種工作方式,一種為自動的由時鐘模塊調(diào)用,另一種是由程序員自行調(diào)用。
          1)由時鐘模塊自動調(diào)用的方式
          將時鐘模塊實現(xiàn)文件(Timer.h)及鍵盤掃描模塊的實現(xiàn)文件(KBScan。c)包含進工程,在Config.h文件中添加TIMER_KBSCANDELAY宏。時鐘模塊自動對時鐘中斷進行計數(shù),當達到TIMER_KBSCANDELAY宏所定義的值后,自動調(diào)用鍵盤掃描模塊中的函數(shù)KBScanProcess()進行鍵盤掃描,也就是說,這個宏的值可以決定按鍵消抖動的時間。
          用戶應該提供兩個回調(diào)函數(shù)OnKBScan()及OnKeysPressed()。在函數(shù)OnKBScan中進行鍵盤掃描,并返回掃描碼。掃描碼的類型缺省為BYTE,當鍵盤規(guī)模較大時,BYTE不能夠完全包含鍵盤信息時,可在Config.h文件中重定義宏KBVALUE,如下:
          #defineKBVALUEWORD
          這樣,就可以使用16位的鍵盤掃描碼,如果此時還達不到要求,可以將鍵盤掃描碼定義成一個結構,但這樣做將會增加代碼量及消耗更多的RAM資源,故不推薦。
          掃描模塊調(diào)用OnKBScan取得掃描碼,并調(diào)用用戶可以重定義的宏IsNoKeyPressed來判斷是否有鍵按下,缺省的IsNoKeyPressed實現(xiàn)如下:
          #defineIsNoKeyPressed(x)((x)==0x00)
          即認為OnKBScan返回0掃描碼時為沒有鍵按下,如果掃描函數(shù)返回其它非零掃描碼做為無鍵按下的掃描碼時,可以在Config.h文件中重定義IsNoKeyPressed宏的實現(xiàn)。
          8位鍵盤掃描碼(缺省值)時,相應的掃描函數(shù)為:
          BYTEOnKBScan()
          當掃描模塊經(jīng)過軟件消抖動之后,發(fā)現(xiàn)有鍵按下,就會調(diào)用另一個回調(diào)函數(shù)OnKeysPressed。函數(shù)的聲明應該如下:
          voidOnKeyPressed(BYTEbyKBValue,BYTEbyState)
          其中中的參數(shù)byKBValue的類型為BYTE,此為缺省值,如果使用其它類型的掃描碼,就將此參數(shù)變?yōu)橄鄳愋?。這個值由OnKBScan返回。另一個參數(shù)byState在通常情況下為零。但當用戶在Config.h中定義宏KBSCAN_BRUSTCOUNT,同時鍵盤上的某鍵被按住不放時,掃描模塊對它自己的調(diào)用(注意這里和TIMER_KBSCANDELAY宏不同,TIMER_KBSCANDELAY是時鐘中斷足夠的次數(shù)后調(diào)用掃描模塊,而KBSCAN_BRUSHCOUNT為掃描模塊自身的被調(diào)用次數(shù))進行計數(shù),當達到KBSCAN_BRUSTCOUNT時,掃描模塊調(diào)用OnKeysPressed,此時第一個參數(shù)的含義不變,而byState變成1,同時計數(shù)器復位,又經(jīng)過一段時間后,用值為3的byState調(diào)用OnKeysPressed。這樣就可以很方便的實現(xiàn)多功能鍵或者檢測某鍵的長時間被按下。
          2)由用戶自行調(diào)用
          由用戶自行在程序中調(diào)用掃描模塊,而不是由時鐘中斷自行調(diào)用。其它與方式1相同。

          注意:
          1)函數(shù)KBScanProcess為非阻塞函數(shù),它將在很快的時間內(nèi)返回,等待再次分配給它執(zhí)行的機會。
          2)函數(shù)KBScanProcess是在時鐘中斷外部運行的,它的過程可以被任何中斷打斷,但不影響系統(tǒng)運行。
          3)byState的最大值為250,之后被復位為零。


          上一頁 1 2 3 下一頁

          評論


          相關推薦

          技術專區(qū)

          關閉
          看屁屁www成人影院,亚洲人妻成人图片,亚洲精品成人午夜在线,日韩在线 欧美成人 (function(){ var bp = document.createElement('script'); var curProtocol = window.location.protocol.split(':')[0]; if (curProtocol === 'https') { bp.src = 'https://zz.bdstatic.com/linksubmit/push.js'; } else { bp.src = 'http://push.zhanzhang.baidu.com/push.js'; } var s = document.getElementsByTagName("script")[0]; s.parentNode.insertBefore(bp, s); })();