IIC_Send_Byte(0XA0+((ReadAddr/256)<<1)); //发送器件地址0XA0,写数据

2019-07-21 08:20发布

u8 AT24CXX_ReadOneByte(u16 ReadAddr)
{     
 u8 temp=0;                         
    IIC_Start(); 
 if(EE_TYPE>AT24C16)
 {
  IIC_Send_Byte(0XA0);    //发送写命令
  IIC_Wait_Ack();
  IIC_Send_Byte(ReadAddr>>8);//发送高地址    
 }else IIC_Send_Byte(0XA0+((ReadAddr/256)<<1));   //发送器件地址0XA0,写数据    
 IIC_Wait_Ack();
    IIC_Send_Byte(ReadAddr%256);   //发送低地址
 IIC_Wait_Ack();    
 IIC_Start();       
 IIC_Send_Byte(0XA1);           //进入接收模式     
 IIC_Wait_Ack(); 
    temp=IIC_Read_Byte(0);    
    IIC_Stop();//产生一个停止条件    
 return temp;
}

IIC_Send_Byte(0XA0+((ReadAddr/256)<<1));   //发送器件地址0XA0,写数据

((ReadAddr/256)<<1)这个是干什么用的,难道可以实现自动器件寻址?但我又不理解。。。
友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。
该问题目前已经被作者或者管理员关闭, 无法添加新回复
13条回答
通大Ahk1993
1楼-- · 2019-07-21 12:36

新手上路,请多指教。

先看这个图1,这是从24c02datasheet上截下来的,从这里看到如果插入2k的eeprom就可以插8片,当然这个就需要片选信号了,就是A2,A1,A0,(原子的板子是一个2k的,

所以他就把A2A1A0都给接地了,可以看板子的原理图找到。)4k的就可以插4片片选就是A2和A1,依次类推,16k的只能插一片(当然就不需要片选了,不用A2A1A0了)

也就是说,它总共能管理的大小为16kbit。

然后再看图2和图3;

对照着时序看代码,继START之后先给出器件地址,因为16k(也就是AT24C16)不需要片选信号,所以只需要发送16位的字节地址,

if(EE_TYPE>AT24C16)
 {
  IIC_Send_Byte(0XA0);    //发送写命令
  IIC_Wait_Ack();
  IIC_Send_Byte(ReadAddr>>8);//发送高地址    
 }在确定写命令后,用来发送16位的高地址。

else
  IIC_Send_Byte(0XA0+((ReadAddr/256)<<1));  
         //发送器件地址0XA0,写数据  

取16位地址的高8位,对于24C02而言,高8位完全就是片选信号(其实只有8,9,10三位是,11,12,13,14,15都为0);而对于24C04而言,高7位才是片选信号,

第8位是page信号,就是P0;依次类推

对于左移是让片选信号位依次对应,A0的0才是表示写数据。

 

 

正点原子
2楼-- · 2019-07-21 14:41
这个,你对比看24C02以上的数据手册,和24C02的数据手册,发现有没有不一样的地方?
love1evol
3楼-- · 2019-07-21 18:27
回复【2楼】正点原子:
---------------------------------
原子哥我想问一下 那个0XA0是什么意思  在数据手册上没看到相关的
正点原子
4楼-- · 2019-07-21 20:40
 精彩回答 2  元偷偷看……
Tang青
5楼-- · 2019-07-21 22:03
回复【4楼】正点原子:
---------------------------------
原子哥,如果用24C256,改成发/收16位数据,读写命令该怎么改0x00A1?还是0xA100?
正点原子
6楼-- · 2019-07-21 22:35
还是一样啊。。。你只需要修改:EE_TYPE 为  24C256即可。

一周热门 更多>