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

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 3881|回復: 0
收起左側

24C02、24C16進行字節、頁讀取、頁存取操作

[復制鏈接]
ID:372961 發表于 2019-9-26 12:25 | 顯示全部樓層 |閱讀模式
本帖最后由 Vence 于 2019-9-26 12:51 編輯

以下這篇文章是自己折騰了三天存儲芯片后,并且能夠成功進行字節操作、頁操作的一篇應用型文章,不太想研究原理的可以直接采用本文的代碼和注意事項。

在對24C02或者24C16進行字節、頁讀取、頁存取前,我們需要弄清楚I2C協議、24C02/24C16存儲空間、字節操作和頁操作的時序
————————————————
版權聲明:本文為CSDN博主「Pvence」的原創文章,遵循 CC 4.0 BY-SA 版權協議,轉載請附上原文出處鏈接及本聲明。
原文鏈接:https://blog.csdn.net/weixin_40814407/article/details/101228190

I2C協議:I2C是什么協議網上進行百度方可知道,以下只寫使用代碼

  1. void i2cStart(void)            //開始時序
  2. {
  3.   SDA=1;
  4.   SCL=1;
  5.   _delay(2);  //延時2μs
  6.   SDA=0;
  7.   _delay(2);
  8.   SCL=0;
  9. }

  10. void i2cStop(void)            //結束時序
  11. {
  12.   SDA=0;
  13.   _delay(2);
  14.   SCL=1;
  15.   _delay(2);
  16.   SDA=1;
  17. }

  18. void i2cAck_MCU(void)        //應答時序
  19. {
  20.   SDA=0;
  21.   _delay(2);
  22.   SCL=1;
  23.   _delay(2);
  24.   SCL=0;
  25.   _delay(2);
  26.   SDA=1;
  27.   _delay(4);
  28. }


  29. void i2cNoAck_MCU(void)      //非應答時序
  30. {
  31.   SDA=1;
  32.   _delay(2);
  33.   SCL=1;
  34.   _delay(2);
  35.   SCL=0;
  36.   _delay(2);
復制代碼
24C02/24C16存儲空間大小24C02就是有2Kbit = 2000/8 = 250個字節,24C16就是有16kbit  = 2000個字節,24C02一頁最多可以寫入8個字節,因此可以分成32頁,24C16一頁最多可以寫入16個字節,因此可以分成128頁。


字節寫操作
  1. void WriteByte_24LC16B(unsigned char input)
  2. {
  3.   unsigned char bit_count;
  4.   for(bit_count=8;bit_count!=0;bit_count--)
  5.   {
  6.     _delay(2);
  7.     SDA=(_Bool)(input&0x80);
  8.     _delay(2);
  9.     SCL=1;
  10.     _delay(2);
  11.     SCL=0;
  12.     input=input<<1;
  13.     _delay(2);
  14.   }
  15.   SDA=1;
  16.   SDA_CTRL=1;        //這里需要看自己使用的芯片設置SDA的IO口為輸入狀態,我用的是HT45F67芯片,SDA端口設置為輸入狀態,用于判斷SDA是否接到主機的應答信號
  17.   _delay(2);
  18.   SCL=1;
  19.   _delay(2);
  20.   if(SDA == 1)
  21.           ack = 0;
  22.   else
  23.     ack = 1;
  24.   SCL=0;
  25.   SDA_CTRL=0;    //此處根據自己所使用的芯片將SDA所在的Io口設置為輸出狀態
  26. }

  27. void Write_24LC16B(unsigned char Wdata,unsigned int RomAddress)
  28. {
  29.   unsigned char block;
  30.   WriteDeviceAddress=0B10100000;
  31.   block=RomAddress/256;
  32.   RomAddress=RomAddress%256;
  33.   WriteDeviceAddress=WriteDeviceAddress|(block<<1);
  34.   i2cStart();
  35.   WriteByte_24LC16B(WriteDeviceAddress);
  36.   WriteByte_24LC16B((unsigned char)RomAddress);
  37.   WriteByte_24LC16B(Wdata);
  38.   i2cStop();
  39.   _delay(5500);
  40. }
復制代碼

字節讀操作

  1. unsigned char ReadByte_24LC16B()
  2. {
  3.   unsigned char bit_count,rbyte=0;
  4.   SDA=1;
  5.   SDA_CTRL=1;
  6.   _delay(10);
  7.   for(bit_count=8;bit_count!=0;bit_count--)
  8.   {
  9.     rbyte=rbyte<<1;
  10.     _delay(2);
  11.     SCL=1;
  12.     rbyte=rbyte|((unsigned char)(SDA));
  13.     _delay(2);
  14.     SCL=0;
  15.     _delay(2);
  16.   }
  17.   SDA_CTRL=0;
  18.   return(rbyte);
  19. }


  20. unsigned char Read_24LC16B(unsigned int RomAddress)
  21. {
  22.   unsigned char output,block;
  23.   ReadDeviceAddress=0B10100001;
  24.   WriteDeviceAddress=0B10100000;
  25.   block=RomAddress/256;
  26.   RomAddress=RomAddress%256;
  27.   WriteDeviceAddress=WriteDeviceAddress|(block<<1);
  28.   ReadDeviceAddress=ReadDeviceAddress|(block<<1);
  29.   i2cStart();
  30.   WriteByte_24LC16B(WriteDeviceAddress);
  31.   WriteByte_24LC16B((unsigned char)RomAddress);
  32.   i2cStart();
  33.   WriteByte_24LC16B(ReadDeviceAddress);
  34.   output=ReadByte_24LC16B();
  35.   i2cNoAck_MCU();
  36.   i2cStop();
  37.   _delay(2000);
  38.   return(output);  
  39. }
復制代碼

頁寫操作
  1. Wdata為輸入數組的首地址,RomAddress為需要進行存儲的地址,范圍在0~2047之間,cnt為一次需要寫入的字節個數,建議采用8的倍數的cnt,因為本函數不采用自動分頁,不是8的倍數會在超出頁寫入最多的字節數之后覆蓋掉原來的數。
  2. void WritePage_24LC16B(unsigned char *Wdata,unsigned int RomAddress,unsigned char cnt)
  3. {
  4.   unsigned char block;
  5.   WriteDeviceAddress=0B10100000;
  6.   block=RomAddress/256;
  7.   RomAddress=RomAddress%256;
  8.   WriteDeviceAddress=WriteDeviceAddress|(block<<1);
  9.   i2cStart();
  10.   WriteByte_24LC16B(WriteDeviceAddress);
  11.   WriteByte_24LC16B((unsigned char)RomAddress);
  12.   while(cnt--)
  13.   {
  14.           WriteByte_24LC16B(*Wdata++);
  15.   }
  16.   i2cStop();
  17. }

  18. 注意:連續進行多頁寫操作,需要在WritePage_24LC16B函數后添加150μs以上的延遲,這段時間,24C02內部需要將數據存儲到芯片內部。
  19. 例子:
  20. D_buffer[8] = {1,2,3,4,5,6,7,8};
  21. WritePage_24LC16B(D_buffer,0,8);
  22. _delay(150);        //延遲150μs以及以上
  23. WritePage_24LC16B(D_buffer,8,8);
復制代碼

頁讀操作
  1. void ReadPage_24LC16B(unsigned char *Rdata,unsigned int RomAddress,unsigned char cnt)
  2. {
  3.   unsigned char block;
  4.   ReadDeviceAddress=0B10100001;
  5.   WriteDeviceAddress=0B10100000;
  6.   block=RomAddress/256;
  7.   RomAddress=RomAddress%256;
  8.   WriteDeviceAddress=WriteDeviceAddress|(block<<1);
  9.   ReadDeviceAddress=ReadDeviceAddress|(block<<1);
  10.   i2cStart();
  11.   WriteByte_24LC16B(WriteDeviceAddress);
  12.   WriteByte_24LC16B((unsigned char)RomAddress);
  13.   i2cStart();
  14.   WriteByte_24LC16B(ReadDeviceAddress);
  15.   while(cnt>1)
  16.   {
  17.           *Rdata++ = ReadByte_24LC16B();
  18.           cnt--;
  19.           i2cAck_MCU();                        //發送完讀地址后,需要應答一下
  20.   }
  21.   *Rdata = ReadByte_24LC16B();
  22.   i2cNoAck_MCU();                        //讀取最后一個字節需要非應答
  23.   i2cStop();
  24.   _delay(2000);
  25. }
復制代碼






回復

使用道具 舉報

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

本版積分規則

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

Powered by 單片機教程網

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