新聞中心

        EEPW首頁 > 嵌入式系統 > 設計應用 > Freescale 9S12 系列單片機應用筆記(SCI)1

        Freescale 9S12 系列單片機應用筆記(SCI)1

        作者: 時間:2016-11-20 來源:網絡 收藏

        SCI模塊應用筆記(1)

        UART,也就是異步串行通訊接口是單片機中最常見的外設,幾乎每種類型的單片機都必備1到2個UART接口,9S12系列單片機也不例外。不過,摩托羅拉給他自己的單片機的串口起了個很有個性的縮寫名稱SCI(serialcommunicationinterface),其實就是我們常說的UART。

        本文引用地址:http://www.104case.com/article/201611/318823.htm

        各種單片機串口的編程都大同小異,無非就是設置波特率、起始位、停止位、校驗位等等。下面通過給出編程例子的方式分別介紹。

        設置波特率

        1. /**
        2. *SettheBaudRateoftheSCI.
        3. *@paramport,portcanbeSCI0/SCI1
        4. *@parambaudRate,thewantedbaudrate.
        5. *@parambusClk,TheSCImoduleclock.
        6. */
        7. voidSCISetBaudRate(unsignedcharport,unsignedlongbaudRate,unsignedlongbusClk)
        8. {
        9. unsignedshortbaudRateReg;
        10. baudRateReg=(unsignedshort)(busClk/baudRate/16);
        11. if(port==SCI0)
        12. {
        13. //HerewemustwriteBDHfirst!
        14. SCI0BDH=(0x1f&(baudRateReg>>8));
        15. SCI0BDL=(0xff&baudRateReg);
        16. }
        17. elseif(port==SCI1)
        18. {
        19. SCI1BDH=(0x1f&(baudRateReg>>8));
        20. SCI1BDL=(0xff&baudRateReg);
        21. }
        22. else
        23. {
        24. //Somethingmustgowrong.Donothinghere!
        25. }
        26. }

        設置奇偶校驗位

        1. /**
        2. *Enable/DisableparityfunctionandsettheParitytype
        3. *@paramportportcanbeSCI0/SCI1
        4. *@paramisEnable0fordisableparityfunction,1forenable
        5. *@paramtype0forEvenParity,1forOddParity
        6. */
        7. voidSCISetParity(unsignedcharport,unsignedcharisEnable,unsignedchartype)
        8. {
        9. if(port==SCI0)
        10. {
        11. SCI0CR1_PE=(isEnable&0x01);
        12. SCI0CR1_PT=(type&0x01);
        13. }
        14. elseif(port==SCI1)
        15. {
        16. SCI1CR1_PE=(isEnable&0x01);
        17. SCI1CR1_PT=(type&0x01);
        18. }
        19. else
        20. {
        21. //Ifcoderunhere,somethingmustgowrong.Donothinghere!
        22. }
        23. }


        使能數據位的長度

        1. /**
        2. *SettheDataFormatModeBit
        3. *@paramportportcanbeSCI0/SCI1
        4. *@parambitsmustbe8or9
        5. */
        6. voidSCISetDataBit(unsignedcharport,unsignedcharbits)
        7. {
        8. if(port==SCI0)
        9. {
        10. switch(bits)
        11. {
        12. case8:
        13. SCI0CR1_M=0;/*1startbit,8databits,1stopbit*/
        14. break;
        15. case9:
        16. SCI0CR1_M=1;/*1startbit,9databits,1stopbit*/
        17. break;
        18. default:
        19. //Ifcoderunhere,somethingmustgowrong.Donothinghere!
        20. break;
        21. }
        22. }
        23. elseif(port==SCI1)
        24. {
        25. switch(bits)
        26. {
        27. case8:
        28. SCI1CR1_M=0;/*1startbit,8databits,1stopbit*/
        29. break;
        30. case9:
        31. SCI1CR1_M=1;/*1startbit,9databits,1stopbit*/
        32. break;
        33. default:
        34. //Ifcoderunhere,somethingmustgowrong.Donothinghere!
        35. break;
        36. }
        37. }
        38. else
        39. {
        40. //Ifcoderunhere,somethingmustgowrong.Donothinghere!
        41. }
        42. }


        設置串口的工作模式

        NORMAL_MODE是我們通常用的模式

        LOOP_MODE是自發自收模式

        SING_WIRE_MODE就是收發公用一條數據線的模式

        1. /**
        2. *Settheworkmodeofoperation
        3. *@paramportportcanbeSCI0/SCI1
        4. *@parammodemodecanbeNORMAL_MODE/LOOP_MODE/SING_WIRE_MODE
        5. */
        6. voidSCISetWorkMode(unsignedcharport,unsignedcharmode)
        7. {
        8. if(port==SCI0)
        9. {
        10. switch(mode)
        11. {
        12. caseNORMAL_MODE:
        13. SCI0CR1_LOOPS=0;
        14. SCI0CR1_RSRC=0;
        15. break;
        16. caseLOOP_MODE:
        17. SCI0CR1_LOOPS=1;
        18. SCI0CR1_RSRC=0;
        19. break;
        20. caseSING_WIRE_MODE:
        21. SCI0CR1_LOOPS=1;
        22. SCI0CR1_RSRC=1;
        23. break;
        24. default:
        25. //Ifcoderunhere,somethingmustgowrong.Donothinghere!
        26. break;
        27. }
        28. }
        29. elseif(port==SCI1)
        30. {
        31. switch(mode)
        32. {
        33. caseNORMAL_MODE:
        34. SCI1CR1_LOOPS=0;
        35. SCI1CR1_RSRC=0;
        36. break;
        37. caseLOOP_MODE:
        38. SCI1CR1_LOOPS=1;
        39. SCI1CR1_RSRC=0;
        40. break;
        41. caseSING_WIRE_MODE:
        42. SCI1CR1_LOOPS=1;
        43. SCI1CR1_RSRC=1;
        44. break;
        45. default:
        46. //Ifcoderunhere,somethingmustgowrong.Donothinghere!
        47. break;
        48. }
        49. }
        50. else
        51. {
        52. //Ifcoderunhere,somethingmustgowrong.Donothinghere!
        53. }
        54. }

        設置SCI模塊是否在Wait模式下工作

        1. /**
        2. *Enable/DisabletheSCIinwaitmode
        3. *@paramportportcanbeSCI0/SCI1
        4. *@parammodemodecanbeRUN_MODE/WAIT_MODE
        5. */
        6. voidSCISetPowerMode(unsignedcharport,unsignedcharmode)
        7. {
        8. if(port==SCI0)
        9. {
        10. switch(mode)
        11. {
        12. caseRUN_MODE:
        13. SCI0CR1_SCISWAI=0;
        14. break;
        15. caseWAIT_MODE:
        16. SCI0CR1_SCISWAI=1;
        17. break;
        18. default:
        19. //Ifcoderunhere,somethingmustgowrong.Donothinghere!
        20. break;
        21. }
        22. }
        23. elseif(port==SCI1)
        24. {
        25. switch(mode)
        26. {
        27. caseRUN_MODE:
        28. SCI1CR1_SCISWAI=0;
        29. break;
        30. caseWAIT_MODE:
        31. SCI1CR1_SCISWAI=1;
        32. break;
        33. default:
        34. //Ifcoderunhere,somethingmustgowrong.Donothinghere!
        35. break;
        36. }
        37. }
        38. else
        39. {
        40. //Ifcoderunhere,somethingmustgowrong.Donothinghere!
        41. }
        42. }

        使能SCI模塊的接收功能

        1. /**
        2. *Enable/DisableSCIReceiver
        3. *@paramportportcanbeSCI0/SCI1
        4. *@paramisEnable0disable1enable
        5. */
        6. voidSCIEnableRecv(unsignedcharport,unsignedcharisEnable)
        7. {
        8. if(port==SCI0)
        9. {
        10. SCI0CR2_RE=(isEnable&0x01);
        11. }
        12. elseif(port==SCI1)
        13. {
        14. SCI1CR2_RE=(isEnable&0x01);
        15. }
        16. else
        17. {
        18. //Ifcoderunhere,somethingmustgowrong.Donothinghere!
        19. }
        20. }

        使能SCI模塊的發送功能

        1. /**
        2. *Enable/DisableSCITransmitter
        3. *@paramportportcanbeSCI0/SCI1
        4. *@paramisEnable0disable1enable
        5. */
        6. voidSCIEnableTrans(unsignedcharport,unsignedcharisEnable)
        7. {
        8. if(port==SCI0)
        9. {
        10. SCI0CR2_TE=(isEnable&0x01);
        11. }
        12. elseif(port==SCI1)
        13. {
        14. SCI1CR2_TE=(isEnable&0x01);
        15. }
        16. else
        17. {
        18. //Ifcoderunhere,somethingmustgowrong.Donothinghere!
        19. }
        20. }

        發送數據

        1. /**
        2. *SendacharthrounghSCImodule.
        3. *@paramportportcanbeSCI0/SCI1
        4. *@paramsthedatatobesent
        5. */
        6. voidSCIPutChar(unsignedcharport,unsignedchars)
        7. {
        8. if(port==SCI0)
        9. {
        10. while(SCI0SR1_TDRE==0);//SCI0SR1_TC是發送完成
        11. SCI0DRL=s;
        12. }
        13. else
        14. {
        15. while(SCI1SR1_TDRE==0);//SCI1SR1_TC
        16. SCI1DRL=s;
        17. }
        18. }
        19. /**
        20. *SendacharstringthrounghSCImodule.
        21. *@paramportportcanbeSCI0/SCI1
        22. *@param*strthestringtobesent
        23. */
        24. voidSCIPutStr(unsignedcharport,unsignedchar*str)
        25. {
        26. while(0!=*str)
        27. {
        28. SCIPutChar(port,*str);
        29. str++;
        30. }
        31. }
        32. /**
        33. *SenddatathrounghSCImodule.
        34. *@paramportportcanbeSCI0/SCI1
        35. *@param*ppointertothedatatobesent
        36. *@paramsizethesize(byte)ofthedata
        37. */
        38. voidSCIWrite(unsignedcharport,void*p,intsize)
        39. {
        40. unsignedchar*str=(unsignedchar*)p;
        41. while(size>0)
        42. {
        43. SCIPutChar(port,*str);
        44. str++;
        45. size--;
        46. }
        47. }
        48. /**
        49. *Sendashortintvalue(BigEndian)throunghSCImodule.
        50. *@paramportportcanbeSCI0/SCI1
        51. *@paramithedatatobesent
        52. */
        53. voidSCIPutShortBigEndian(unsignedcharport,shorti)
        54. {
        55. char*p=(char*)&i;
        56. SCIPutChar(port,p[0]);
        57. SCIPutChar(port,p[1]);
        58. }
        59. /**
        60. *Sendashortintvalue(LittleEndian)throunghSCImodule.
        61. *@paramportportcanbeSCI0/SCI1
        62. *@paramithedatatobesent
        63. */
        64. voidSCIPutShortLittleEndian(unsignedcharport,shorti)
        65. {
        66. char*p=(char*)&i;
        67. SCIPutChar(port,p[1]);
        68. SCIPutChar(port,p[0]);
        69. }
        70. /**
        71. *Sendalongintvalue(BigEndian)throunghSCImodule.
        72. *@paramportportcanbeSCI0/SCI1
        73. *@paramithedatatobesent
        74. */
        75. voidSCIPutLongBigEndian(unsignedcharport,longi)
        76. {
        77. char*p=(char*)&i;
        78. SCIPutChar(port,p[0]);
        79. SCIPutChar(port,p[1]);
        80. SCIPutChar(port,p[2]);
        81. SCIPutChar(port,p[3]);
        82. }
        83. /**
        84. *Sendalongintvalue(LittleEndian)throunghSCImodule.
        85. *@paramportportcanbeSCI0/SCI1
        86. *@paramithedatatobesent
        87. */
        88. voidSCIPutLongLittleEndian(unsignedcharport,longi)
        89. {
        90. char*p=(char*)&i;
        91. SCIPutChar(port,p[3]);
        92. SCIPutChar(port,p[2]);
        93. SCIPutChar(port,p[1]);
        94. SCIPutChar(port,p[0]);
        95. }


        接收數據

        1. /**
        2. *ReceiveachardatafromSCImodule,noreply.
        3. *@paramportportcanbeSCI0/SCI1
        4. *@returnthereceivedchar
        5. */
        6. unsignedcharSCIGetChar(unsignedcharport)
        7. {
        8. if(port==SCI0)
        9. {
        10. while(SCI0SR1_RDRF==0);
        11. returnSCI0DRL;
        12. }
        13. else
        14. {
        15. while(SCI1SR1_RDRF==0);
        16. returnSCI1DRL;
        17. }
        18. }

        相應的頭文件

        1. /**
        2. *filesci.h
        3. *authorLiYuan
        4. *platform:mc9s12dp256B
        5. *date:2012-4-16
        6. *version:1.0.0
        7. *description:SCI(SerialCommunicationInterface)SupportCode
        8. */
        9. #ifndef_SCI_H_
        10. #define_SCI_H_
        11. #defineSCI00
        12. #defineSCI11
        13. #defineIDLE_LINE0
        14. #defineADDRESS_MARK1
        15. #defineNORMAL_MODE0
        16. #defineLOOP_MODE1
        17. #defineSING_WIRE_MODE2
        18. #defineRUN_MODE0
        19. #defineWAIT_MODE1
        20. /*FunctionDeclaration*/
        21. /**
        22. *SettheBaudRateoftheSCI.
        23. *@paramport,portcanbeSCI0/SCI1
        24. *@parambaudRate,thewantedbaudrate.
        25. *@parambusClk,TheSCImoduleclock.
        26. */
        27. voidSCISetBaudRate(unsignedcharport,unsignedlongbaudRate,unsignedlongbusClk);
        28. /**
        29. *SettheInterruptEnableBit
        30. *@paramportportcanbeSCI0/SCI1
        31. *@paramtieTransmitterInterruptEnableBIt
        32. *@paramtcieTransmissionCompleteInterruptEnableBIt
        33. *@paramrieReceiverFullInterruptEnableBIt
        34. *@paramilieIdleLineInterruptEnableBIt
        35. *0InterruptrequestsDisabled
        36. *1InterruptrequestsEnabled
        37. */
        38. voidSCISetIEBit(unsignedcharport,unsignedchartie,unsignedchartcie,unsignedcharrie,unsignedcharilie);
        39. /**
        40. *EnableTheTxinterrupt(TransmitterInterruptEnableBIt)
        41. *@paramport,portcanbeSCI0/SCI1
        42. */
        43. voidSCIEnableTxInt(unsignedcharport);
        44. /**
        45. *DisableTheTxinterrupt(TransmitterInterruptEnableBIt)
        46. *@paramport,portcanbeSCI0/SCI1
        47. */
        48. voidSCIDisTxInt(unsignedcharport);
        49. /**
        50. *Enable/DisableSCIReceiver
        51. *@paramportportcanbeSCI0/SCI1
        52. *@paramisEnable0disable1enable
        53. */
        54. voidSCIEnableRecv(unsignedcharport,unsignedcharisEnable);
        55. /**
        56. *Enable/DisableSCITransmitter
        57. *@paramportportcanbeSCI0/SCI1
        58. *@paramisEnable0disable1enable
        59. */
        60. voidSCIEnableTrans(unsignedcharport,unsignedcharisEnable);
        61. /**
        62. *SettheIdleLineType
        63. *@paramportportcanbeSCI0/SCI1
        64. *@paramtype0Idlecharbitcountbeginsafterstartbit
        65. *1Idlecharbitcountbeginsafterstopbit
        66. */
        67. voidSCISetIdleLineType(unsignedcharport,unsignedchartype);
        68. /**
        69. *SettheWakeupCondition.
        70. *@paramportportcanbeSCI0/SCI1
        71. *@paramcondi0forIdlelinewakeup,1foraddressmarkwakeup
        72. */
        73. voidSCISetWakeupCondi(unsignedcharport,unsignedcharcondi);
        74. /**
        75. *Enable/DisableparityfunctionandsettheParitytype
        76. *@paramportportcanbeSCI0/SCI1
        77. *@paramisEnable0fordisableparityfunction,1forenable
        78. *@paramtype0forEvenParity,1forOddParity
        79. */
        80. voidSCISetParity(unsignedcharport,unsignedcharisEnable,unsignedchartype);
        81. /**
        82. *SettheDataFormatModeBit
        83. *@paramportportcanbeSCI0/SCI1
        84. *@parambitsmustbe8or9
        85. */
        86. voidSCISetDataBit(unsignedcharport,unsignedcharbits);
        87. /**
        88. *Settheworkmodeofoperation
        89. *@paramportportcanbeSCI0/SCI1
        90. *@parammodemodecanbeNORMAL_MODE/LOOP_MODE/SING_WIRE_MODE
        91. */
        92. voidSCISetWorkMode(unsignedcharport,unsignedcharmode);
        93. /**
        94. *Enable/DisabletheSCIinwaitmode
        95. *@paramportportcanbeSCI0/SCI1
        96. *@parammodemodecanbeRUN_MODE/WAIT_MODE
        97. */
        98. voidSCISetPowerMode(unsignedcharport,unsignedcharmode);
        99. /**
        100. *SettheTXDIR(OnlyforSingleWireMODE)
        101. *@paramportportcanbeSCI0/SCI1
        102. *@paramdir0TXDusedasinput,1TXDusedasoutput
        103. */
        104. voidSCISetTXDIR(unsignedcharport,unsignedchardir);
        105. /**
        106. *SendacharthrounghSCImodule.
        107. *@paramportportcanbeSCI0/SCI1
        108. *@paramsthedatatobesent
        109. */
        110. voidSCIPutChar(unsignedcharport,unsignedchars);
        111. /**
        112. *ReceiveachardatafromSCImodule,noreply.
        113. *@paramportportcanbeSCI0/SCI1
        114. *@returnthereceivedchar
        115. */
        116. unsignedcharSCIGetChar(unsignedcharport);
        117. /**
        118. *Sendashortintvalue(BigEndian)throunghSCImodule.
        119. *@paramportportcanbeSCI0/SCI1
        120. *@paramithedatatobesent
        121. */
        122. voidSCIPutShortBigEndian(unsignedcharport,shorti);
        123. /**
        124. *Sendashortintvalue(LittleEndian)throunghSCImodule.
        125. *@paramportportcanbeSCI0/SCI1
        126. *@paramithedatatobesent
        127. */
        128. voidSCIPutShortLittleEndian(unsignedcharport,shorti);
        129. /**
        130. *Sendalongintvalue(BigEndian)throunghSCImodule.
        131. *@paramportportcanbeSCI0/SCI1
        132. *@paramithedatatobesent
        133. */
        134. voidSCIPutLongBigEndian(unsignedcharport,longi);
        135. /**
        136. *Sendalongintvalue(LittleEndian)throunghSCImodule.
        137. *@paramportportcanbeSCI0/SCI1
        138. *@paramithedatatobesent
        139. */
        140. voidSCIPutLongLittleEndian(unsignedcharport,longi);
        141. /**
        142. *SendacharstringthrounghSCImodule.
        143. *@paramportportcanbeSCI0/SCI1
        144. *@param*strthestringtobesent
        145. */
        146. voidSCIPutStr(unsignedcharport,unsignedchar*str);
        147. /**
        148. *SenddatathrounghSCImodule.
        149. *@paramportportcanbeSCI0/SCI1
        150. *@param*ppointertothedatatobesent
        151. *@paramsizethesize(byte)ofthedata
        152. */
        153. voidSCIWrite(unsignedcharport,void*p,intsize);
        154. #endif

        下面給個簡單的例子

        1. #include/*commondefinesandmacros*/
        2. #include"derivative.h"/*derivative-specificdefinitions*/
        3. #include"sci.h"
        4. voidmain(void)
        5. {
        6. charC;
        7. EnableInterrupts;
        8. SCISetWorkMode(SCI0,NORMAL_MODE);
        9. SCISetPowerMode(SCI0,RUN_MODE);
        10. SCISetBaudRate(SCI0,9600,16384000L);//16MClock
        11. SCISetDataBit(SCI0,8);
        12. SCISetParity(SCI0,0,0);
        13. SCIEnableRecv(SCI0,1);
        14. SCIEnableTrans(SCI0,1);
        15. for(;;)
        16. {
        17. _FEED_COP();/*feedsthedog*/
        18. C=SCIGetChar(SCI0);
        19. SCIPutChar(SCI0,C);
        20. }/*loopforever*/
        21. /*pleasemakesurethatyouneverleavemain*/
        22. }


        先寫這么多,剩下的明天繼續。下一篇筆記中將給出如何利用串口的收發中斷和環形緩沖區來實現較為完善的串口驅動。



        評論


        技術專區

        關閉
        主站蜘蛛池模板: 仲巴县| 山东省| 吐鲁番市| 丹东市| 恭城| 清新县| 贵阳市| 托克逊县| 香港| 湘潭县| 桑植县| 剑河县| 双流县| 慈溪市| 漳平市| 台中县| 鲁甸县| 南城县| 五河县| 隆德县| 东宁县| 富平县| 东至县| 蒲江县| 长宁区| 泸溪县| 南宫市| 宝山区| 扬州市| 东安县| 册亨县| 曲水县| 承德县| 巴彦县| 岳阳县| 永丰县| 连州市| 古田县| 巴彦淖尔市| 潞城市| 抚顺市|