欧美极品高清xxxxhd,国产日产欧美最新,无码AV国产东京热AV无码,国产精品人与动性XXX,国产传媒亚洲综合一区二区,四库影院永久国产精品,毛片免费免费高清视频,福利所导航夜趣136

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 1538|回復: 1
打印 上一主題 下一主題
收起左側

不借助工具,使用串口輸出對STC8A8K64S4A12的IRTRIM值進行標定

[復制鏈接]
跳轉到指定樓層
樓主
ID:912806 發表于 2021-11-11 19:03 | 只看該作者 回帖獎勵 |正序瀏覽 |閱讀模式
STC8A8K64S4A12這個型號的MCU, 因為沒有固化的頻率調節值, 要么在STC-ISP燒錄時設置寫入, 要么通過idata高地址區讀取, 這對于Linux下的SDCC用戶就非常不方便, 既不能用STC-ISP, 寫入SDCC編譯后的程序也無法在idata區讀取對應的值. 相比較STC8A8K64D4就方便許多, 在xdata區域有固定的值可以讀取.
那么對于Linux下的SDCC用戶, 如何去確定這個頻率調節值? 一個辦法是通過邏輯分析儀去標定, 但是如果沒有邏輯分析儀呢? 還可以通過指定的串口波特率去標定.

這種方式是因為串口波特率與系統時鐘是關聯的, 如果假定當前系統時鐘頻率為X, 那么對應一個確定的波特率, 例如9600, 對應的寄存器值是固定的, 如果芯片按這個值運行, 只有當系統時鐘頻率與預設的值接近, 上位機才接收到正確的輸出, 其它情況看到的都是亂碼, 如果在代碼中不斷調節頻率, 同時輸出當前頻率對應的IRTRIM和LIRTRIM值, 根據亂碼和正常接收的情況, 就能判斷出對應此頻率的IRTRIM和LIRTRIM值.

編譯這個程序后寫入STC8A8K64S4A12, 使用USB2TTL連接串口1, 波特率9600, 觀察輸出的字符串.
當實際頻率接近預設的頻率時, 能觀察到非亂碼的輸出. 取非亂碼區間的中間點對應的值, 就可以作為此頻率對應的IRTRIM和LIRTRIM值.

代碼已經添加了對應的宏處理, 可以兼容SDCC和Keil C51環境.
  1. /*****************************************************************************/
  2. /**
  3. * \file        itrim_detect.c
  4. * \brief       使用固定波特率串口輸出標定STC8A8K64S4A12各頻率的ITRIM
  5. * \version     v0.1
  6. ******************************************************************************/

  7. /*****************************************************************************/
  8. /**
  9. * \brief       自適應SDCC和Keil C51的宏處理
  10. ******************************************************************************/

  11. #if defined (SDCC) || defined (__SDCC)
  12. # define SBIT(name, addr, bit)  __sbit  __at(addr+bit)                    name
  13. # define SFR(name, addr)        __sfr   __at(addr)                        name
  14. # define SFRX(name, addr)       __xdata volatile unsigned char __at(addr) name
  15. #define NOP() __asm NOP __endasm


  16. #elif defined __CX51__
  17. # define SBIT(name, addr, bit)  sbit  name = addr^bit
  18. # define SFR(name, addr)        sfr   name = addr
  19. # define SFRX(name, addr)       volatile unsigned char xdata name _at_ addr
  20. extern void _nop_ (void);
  21. #define NOP() _nop_()

  22. /** default
  23.   * unrecognized compiler
  24. */
  25. #else
  26. # warning unrecognized compiler
  27. # define SBIT(name, addr, bit)  volatile bool           name
  28. # define SFR(name, addr)        volatile unsigned char  name
  29. # define SFRX(name, addr)       volatile unsigned char  name

  30. #endif

  31. /*****************************************************************************/
  32. /**
  33. * \brief       代碼中涉及的寄存器
  34. ******************************************************************************/

  35. SBIT(TI,                0x98, 1);

  36. SFR(PCON,               0x87);
  37. SFR(AUXR,               0x8E);
  38. SFR(SCON,               0x98);
  39. SFR(SBUF,               0x99);
  40. SFR(LIRTRIM,            0x9E);
  41. SFR(IRTRIM,             0x9F);
  42. SFR(P_SW2,              0xBA);
  43. SFR(T2H,                0xD6);
  44. SFR(T2L,                0xD7);

  45. SFRX(CLKDIV,            0xfe01);
  46. SFRX(IRC24MCR,          0xfe02);

  47. static const char hexTable[16] = { '0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};

  48. /*****************************************************************************/
  49. /**
  50. * \brief       時鐘和串口1初始化
  51. ******************************************************************************/
  52. void clock_init()
  53. {
  54.   // [  BAH,0,0x00]: 外設端口切換控制寄存器2,串口2/3/4,I2C,比較器
  55.   P_SW2      = 0x80;
  56.   // [FE01H,1,0x00]: 時鐘分頻寄存器,ISP可能寫入預設值
  57.   CLKDIV     = 0x00;
  58.   // [  9EH,0,0x00]: IRC頻率微調寄存器, ISP可能寫入預設值
  59.   LIRTRIM    = 0x00;
  60.   // [  BAH,0,0x00]: 外設端口切換控制寄存器2,串口2/3/4,I2C,比較器
  61.   P_SW2      = 0x00;

  62.   // [  87H,0,0x30]: 電源控制寄存器
  63.   PCON       = 0xB0;
  64.   // [  98H,0,0x00]: 串口1控制寄存器
  65.   SCON       = 0x50;
  66.   // [  8EH,0,0x01]: 輔助寄存器
  67.   AUXR       = 0x15;
  68. }

  69. /*****************************************************************************/
  70. /**
  71. * \brief       不同頻率對應的串口初始化程序
  72. ******************************************************************************/
  73. void uart_init_18m_9600()
  74. {
  75.     // [  D6H,0,0x00]: 定時器2高字節
  76.     T2H        = 0xFE;
  77.     // [  D7H,0,0x00]: 定時器2低字節
  78.     T2L        = 0x2B;
  79. }

  80. void uart_init_22m1184_9600()
  81. {
  82.   // [  D6H,0,0x00]: 定時器2高字節
  83.   T2H        = 0xFD;
  84.   // [  D7H,0,0x00]: 定時器2低字節
  85.   T2L        = 0xC0;
  86. }

  87. void uart_init_24m_9600()
  88. {
  89.   // [  D6H,0,0x00]: 定時器2高字節
  90.   T2H        = 0xFD;
  91.   // [  D7H,0,0x00]: 定時器2低字節
  92.   T2L        = 0x8F;
  93. }

  94. void uart_init_28m_9600()
  95. {
  96.   // [  D6H,0,0x00]: 定時器2高字節
  97.   T2H        = 0xFD;
  98.   // [  D7H,0,0x00]: 定時器2低字節
  99.   T2L        = 0x26;
  100. }

  101. void uart_init_32m_9600()
  102. {
  103.   // [  D6H,0,0x00]: 定時器2高字節
  104.   T2H        = 0xFC;
  105.   // [  D7H,0,0x00]: 定時器2低字節
  106.   T2L        = 0xBE;
  107. }

  108. /*****************************************************************************/
  109. /**
  110. * \brief       通過修改IRTRIM和LIRTRIM調節內部時鐘頻率
  111. ******************************************************************************/
  112. void trim_freq(unsigned char trim, unsigned char litrim)
  113. {
  114.   IRTRIM = trim;
  115.   LIRTRIM = litrim;
  116.   while(!(IRC24MCR & 0x01));
  117. }

  118. void PrintChar(unsigned char dat)
  119. {
  120.   SBUF = dat;
  121.   while(!TI);
  122.   TI = 0;
  123. }

  124. void PrintHex(unsigned char hex)
  125. {
  126.   PrintChar(hexTable[hex >> 4]);
  127.   PrintChar(hexTable[hex & 0xF]);
  128. }

  129. void PrintString(unsigned char *str)
  130. {
  131.   while (*str != '\0')
  132.   {
  133.     SBUF = *str;
  134.     while(!TI);
  135.     TI = 0;     /* clear */
  136.     str++;
  137.   }
  138. }

  139. void Delay100ms()                //@22.1184MHz
  140. {
  141.   unsigned char j, k;
  142.   j = 100;
  143.   k = 228;
  144.   do
  145.   {
  146.     while (--k);
  147.   } while (--j);
  148. }

  149. void DetectItrim(unsigned char *str)
  150. {
  151.   unsigned char i, j;
  152.   do
  153.   {
  154.     j = 3;
  155.     do
  156.     {
  157.       trim_freq(i, j);
  158.       PrintHex(IRTRIM);
  159.       PrintChar(0x20);
  160.       PrintHex(LIRTRIM);
  161.       PrintChar(0x20);
  162.       PrintString(str);
  163.       Delay100ms();
  164.     } while (--j);
  165.   } while(--i);
  166. }

  167. void main()
  168. {
  169.   clock_init();

  170.   while(1)
  171.   {
  172.     uart_init_18m_9600();
  173.     DetectItrim(" 18MHz 9600\r\n");
  174.     uart_init_22m1184_9600();
  175.     DetectItrim(" 22.1184MHz 9600\r\n");
  176.     uart_init_24m_9600();
  177.     DetectItrim(" 24MHz 9600\r\n");
  178.     uart_init_28m_9600();
  179.     DetectItrim(" 28MHz 9600\r\n");
  180.     uart_init_32m_9600();
  181.     DetectItrim(" 32MHz 9600\r\n");
  182.   }
  183. }
復制代碼




評分

參與人數 1黑幣 +50 收起 理由
admin + 50 共享資料的黑幣獎勵!

查看全部評分

分享到:  QQ好友和群QQ好友和群 QQ空間QQ空間 騰訊微博騰訊微博 騰訊朋友騰訊朋友
收藏收藏 分享淘帖 頂 踩
回復

使用道具 舉報

沙發
ID:519089 發表于 2021-11-16 11:33 | 只看該作者
51 用linux啊,,,簡直沒誰了。。。。
回復

使用道具 舉報

您需要登錄后才可以回帖 登錄 | 立即注冊

本版積分規則

小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術交流QQ群281945664

Powered by 單片機教程網

快速回復 返回頂部 返回列表