久久久久久久999_99精品久久精品一区二区爱城_成人欧美一区二区三区在线播放_国产精品日本一区二区不卡视频_国产午夜视频_欧美精品在线观看免费

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

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

AVR單片機的TWI中斷模式

[復制鏈接]
跳轉到指定樓層
樓主
ID:282997 發表于 2018-2-8 09:43 | 只看該作者 回帖獎勵 |倒序瀏覽 |閱讀模式
使用AVR單片機內部的TWI功能,并采用中斷工作模式,可以很好的使用Atmega系列的內部資源,并提高程序的穩定性;
  1. #include <BCD.h>

  2. unsigned char i2c_sla;
  3. unsigned char i2c_addrh,i2c_addrl;
  4. unsigned char i2c_wr;
  5. unsigned char i2c_sub_flag;
  6. unsigned char i2c_num;
  7. unsigned char *i2c_buf;
  8. unsigned char i2c_end;

  9. /***********************************************************************************************************************************************************************
  10. 函數名稱:interrupt [TWI] void twi_isr(void)
  11. 函數功能:i2c底層中斷處理函數(時鐘SD2201和AT24C256共同的)
  12. ***********************************************************************************************************************************************************************/
  13. interrupt [TWI] void twi_isr(void)
  14. {

  15.      unsigned char i2c_sta,tmp = 0;
  16.      i2c_sta = TWSR;
  17.      switch(i2c_sta)
  18.      {
  19.           case 0x08:
  20.                    if(i2c_sub_flag == 1)
  21.                    {
  22.                         TWDR = i2c_sla&0xfe;
  23.                    }
  24.                    else
  25.                    {
  26.                         TWDR = i2c_sla;
  27.                    }
  28.                    //TWCR &= 0xcf;
  29.                    //TWCR |= 0x80;
  30.                    TWCR = 0x85;
  31.                    break;
  32.           case 0x10:
  33.                    TWDR = i2c_sla;
  34.                    //TWCR &= 0xcf;
  35.                    //TWCR |= 0x80;
  36.                    TWCR = 0x85;
  37.                    //i2c_sub_flag = 1;
  38.                    break;
  39.           case 0x18:
  40.                    if(i2c_sub_flag == 0)
  41.                    {
  42.                         if(i2c_num > 0)
  43.                         {
  44.                              TWDR = *i2c_buf;
  45.                              //TWCR &= 0xcf;
  46.                              //TWCR |= 0x80;
  47.                              TWCR = 0x85;
  48.                              i2c_buf++;
  49.                              i2c_num--;
  50.                         }
  51.                         else
  52.                         {
  53.                              //TWCR &= 0xdf;
  54.                              //TWCR |= 0x90;
  55.                              TWCR = 0x95;
  56.                              i2c_end = 1;
  57.                         }
  58.                    }
  59.                    if(i2c_sub_flag == 1)
  60.                    {
  61.                         TWDR = i2c_addrh;
  62.                         //TWCR &= 0xcf;
  63.                         //TWCR |= 0x80;
  64.                         TWCR = 0x85;
  65.                         i2c_sub_flag = 2;
  66.                    }
  67.                    break;
  68.           case 0x28:
  69.                    if(i2c_sub_flag == 3)
  70.                    {
  71.                         if(i2c_wr == 0)
  72.                         {
  73.                              if(i2c_num > 0)
  74.                              {
  75.                                  
  76.                                   TWDR = *i2c_buf;
  77.                                   i2c_buf++;
  78.                                   //TWCR &= 0xcf;
  79.                                   //TWCR |= 0x80;
  80.                                   TWCR = 0x85;
  81.                                   i2c_num--;
  82.                              }
  83.                              else
  84.                              {
  85.                                   //TWCR &= 0xdf;
  86.                                   //TWCR |= 0x90;
  87.                                   TWCR = 0x95;
  88.                                   i2c_end = 1;
  89.                              }
  90.                         }
  91.                    }
  92.                    if(i2c_sub_flag == 2)
  93.                    {
  94.                         TWDR = i2c_addrl;
  95.                         //TWCR &= 0xcf;
  96.                         //TWCR |= 0x80;
  97.                         TWCR = 0x85;
  98.                         i2c_sub_flag = 3;
  99.                    }
  100.                   
  101.                    if(i2c_sub_flag == 3)
  102.                    {
  103.                         if(i2c_wr == 1)
  104.                         {
  105.                              //TWCR &= 0xef;
  106.                              //TWCR |= 0xa0;
  107.                              TWCR = 0xa5;
  108.                         }
  109.                    }
  110.                    if(i2c_sub_flag == 0)
  111.                    {
  112.                         if(i2c_num > 0)
  113.                         {
  114.                              TWDR = *i2c_buf;
  115.                              //TWCR &= 0xcf;
  116.                              //TWCR |= 0x80;
  117.                              TWCR = 0x85;
  118.                              i2c_buf++;
  119.                              i2c_num--;
  120.                         }
  121.                         else
  122.                         {
  123.                              //TWCR &= 0xdf;
  124.                              //TWCR |= 0x90;
  125.                              TWCR = 0x95;
  126.                              i2c_end = 1;
  127.                         }
  128.                    }
  129.                    break;
  130.           case 0x20:
  131.           case 0x30:
  132.           case 0x48:
  133.                    i2c_end = 0xff;
  134.                    //TWCR &= 0xfe;
  135.                    break;
  136.           case 0x38:
  137.                    TWCR &= 0xed;
  138.                    TWCR |= 0xa4;
  139.                    i2c_end = 0xfe;
  140.                    //TWCR &= 0xfe;
  141.                    break;
  142.           case 0x40:
  143.                    //TWCR &= 0xcf;
  144.                    //TWCR |= 0xc0;
  145.                    TWCR = 0xc5;
  146.                    break;
  147.           case 0x50:
  148.                    *i2c_buf = TWDR;
  149.                    i2c_buf++;
  150.                    i2c_num--;
  151.                    if(i2c_num == 0)
  152.                    {
  153.                         //TWCR &= 0x8f;
  154.                         //TWCR |= 0x80;
  155.                         TWCR = 0x85;
  156.                    }
  157.                    else
  158.                    {
  159.                         //TWCR &= 0xcf;
  160.                         //TWCR |= 0xc0;
  161.                         TWCR = 0xc5;
  162.                    }
  163.                    break;
  164.           case 0x58:
  165.                    tmp = TWDR;
  166.                    //TWCR &= 0xdf;
  167.                    //TWCR |= 0x90;
  168.                    TWCR = 0x95;
  169.                    i2c_end = 1;
  170.                    break;
  171.           default:
  172.                   TWCR &= 0xfe;
  173.                   break;
  174.      }
  175. }
  176. /***********************************************************************************************************************************************************************
  177. 函數名稱:void tran_dat(unsigned char *a,unsigned char num,unsigned char fx)
  178. 函數功能:i2c傳輸數據是由MSB開始LSB結束,而SD2201的數據傳輸是由LSB開始MSB結束,此函數負責數據做此轉換的
  179. 函數參數:unsigned char *a  數據的啟始指針,
  180.            unsigned char num 數據的字節個數
  181.            unsigned char fx  時鐘寫和讀的標志位, 1-寫,0-讀
  182. ***********************************************************************************************************************************************************************/
  183. void tran_dat(unsigned char *a,unsigned char num,unsigned char fx)
  184. {
  185.      unsigned char j,k,dat;
  186.      for(j = 0;j < num;j++)
  187.      {
  188.           dat = *a;
  189.           if(fx == 1)
  190.           {
  191.                *a = bin2bcd(dat);
  192.           }
  193.          
  194.           dat = *a;
  195.           *a = 0;
  196.           *a |= dat & 0x01;  
  197.           for(k = 1;k < 8;k++)
  198.           {
  199.                *a <<= 1;
  200.                dat >>= 1;
  201.                *a |= dat & 0x01;
  202.           }
  203.           dat = *a;
  204.           if(fx == 0)
  205.           {
  206.                if((j == 4)&&(num == 7))
  207.                {
  208.                     dat &= 0x3f;
  209.                }
  210.                if((j == 0)&&(num == 3))
  211.                {
  212.                     dat &= 0x3f;
  213.                }
  214.                *a = bcd2bin(dat);
  215.           }
  216.           a++;
  217.      }
  218. }
  219. /***********************************************************************************************************************************************************************
  220. 函數名稱:unsigned char i2c_w_n(unsigned char sla,unsigned char *s,unsigned char num)
  221. 函數功能:無子地址寫入N字節數據
  222. 函數參數:unsigned char sla  器件地址
  223.            unsigned char *s   寫入數據緩沖區指針
  224.            unsigned char num  寫入數據個數  
  225. ***********************************************************************************************************************************************************************/
  226. unsigned char i2c_w_n(unsigned char sla,unsigned char *s,unsigned char num)
  227. {
  228.      i2c_sla =  sla;
  229.      i2c_buf = s;
  230.      i2c_num = num;
  231.      i2c_sub_flag = 0;
  232.      i2c_end = 0;
  233.      TWCR=0xa5;
  234.      while(i2c_end == 0);
  235.      if(i2c_end == 1)
  236.      {
  237.           delay_ms(10);
  238.           return(1);
  239.      }
  240.      else
  241.      {
  242.           return(0);
  243.      }
  244. }
  245. /***********************************************************************************************************************************************************************
  246. 函數名稱:unsigned char i2c_rec_n(unsigned char sla,unsigned char *s,unsigned char num)
  247. 函數功能:無子地址讀出N字節數據
  248. 函數參數:unsigned char sla  器件地址
  249.            unsigned char *s   讀出數據緩沖區指針
  250.            unsigned char num  讀出數據個數
  251. ***********************************************************************************************************************************************************************/
  252. unsigned char i2c_rec_n(unsigned char sla,unsigned char *s,unsigned char num)
  253. {
  254.      i2c_sla =  sla + 1;
  255.      i2c_buf = s;
  256.      i2c_num = num;
  257.      i2c_sub_flag = 0;
  258.      i2c_end = 0;
  259.      TWCR=0xa5;
  260.      while(i2c_end == 0);
  261.      if(i2c_end == 1)
  262.      {
  263.           return(1);
  264.      }
  265.      else
  266.      {
  267.           return(0);
  268.      }
  269.      
  270. }
  271. /***********************************************************************************************************************************************************************
  272. 函數名稱:unsigned char i2c_w_subn(unsigned char sla,unsigned char ah,unsigned char al,unsigned char *s,unsigned char num)
  273. 函數功能:有子地址寫入N字節數據
  274. 函數參數:unsigned char sla  器件地址
  275.            unsigned char ah   器件子地址高字節
  276.            unsigned char al   器件子地址低字節
  277.            unsigned char *s   寫入數據緩沖區指針
  278.            unsigned char num  寫入數據個數  
  279. ***********************************************************************************************************************************************************************/
  280. unsigned char i2c_w_subn(unsigned char sla,unsigned char ah,unsigned char al,unsigned char *s,unsigned char num)
  281. {
  282.      i2c_sla =  sla;
  283.      i2c_buf = s;
  284.      i2c_num = num;
  285.      i2c_addrh = ah;
  286.      i2c_addrl = al;
  287.      i2c_wr = 0;
  288.      i2c_sub_flag = 1;
  289.      i2c_end = 0;
  290.      TWCR=0xa5;
  291.      while(i2c_end == 0);
  292.      if(i2c_end == 1)
  293.      {
  294.           delay_ms(10);
  295.           return(1);
  296.      }
  297.      else
  298.      {
  299.           return(0);
  300.      }
  301. }
  302. /***********************************************************************************************************************************************************************
  303. 函數名稱:unsigned char i2c_rec_subn(unsigned char sla,unsigned char ah,unsigned char al,unsigned char *s,unsigned char num)
  304. 函數功能:無子地址讀出N字節數據
  305. 函數參數:unsigned char sla  器件地址
  306.            unsigned char ah   器件子地址高字節
  307.            unsigned char al   器件子地址低字節
  308.            unsigned char *s   讀出數據緩沖區指針
  309.            unsigned char num  讀出數據個數
  310. ***********************************************************************************************************************************************************************/
  311. unsigned char i2c_rec_subn(unsigned char sla,unsigned char ah,unsigned char al,unsigned char *s,unsigned char num)
  312. {
  313.      i2c_sla =  sla + 1;
  314.      i2c_buf = s;
  315.      i2c_num = num;
  316.      i2c_addrh = ah;
  317.      i2c_addrl = al;
  318.      i2c_wr = 1;
  319.      i2c_sub_flag = 1;
  320.      i2c_end = 0;
  321.      TWCR=0xa5;
  322.      while(i2c_end == 0);
  323.      if(i2c_end == 1)
  324.      {
  325.           return(1);
  326.      }
  327.      else
  328.      {
  329.           return(0);
  330.      }
  331. }
復制代碼


評分

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

查看全部評分

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

使用道具 舉報

沙發
ID:259979 發表于 2018-3-11 06:48 來自手機 | 只看該作者
謝謝分享代碼
回復

使用道具 舉報

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

本版積分規則

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

Powered by 單片機教程網

快速回復 返回頂部 返回列表
主站蜘蛛池模板: 99在线免费观看视频 | 人人玩人人添人人澡欧美 | 亚洲精品电影网在线观看 | 成人精品久久日伦片大全免费 | 国产美女一区二区 | 亚洲黄色片免费观看 | 综合网在线 | 亚洲欧洲一区二区 | 国产精品一区二区三区四区 | 成人黄色电影在线播放 | 国产99久久精品一区二区300 | 男女羞羞视频免费看 | 精品在线播放 | 仙人掌旅馆在线观看 | 精品国产一区二区三区性色av | 亚洲www啪成人一区二区麻豆 | 91精品久久久 | 成人在线a| 久久久久久久一区 | 色播av | 日韩成人免费在线视频 | 久久综合久久自在自线精品自 | 欧美色综合天天久久综合精品 | 欧美日韩一区二区视频在线观看 | 午夜寂寞影院在线观看 | 在线欧美一区二区 | 亚洲综合大片69999 | 国产精品综合网 | 成人影音 | 中文字幕视频在线观看 | 久久亚洲欧美日韩精品专区 | 欧美国产精品一区二区三区 | 亚洲精品久久久久中文字幕欢迎你 | 在线久草| 国产精品入口麻豆www | 亚洲一区成人 | 区一区二在线观看 | 国产精品视频一区二区三区 | 亚洲香蕉在线视频 | wwww.8888久久爱站网 | 夜夜骚 |