09 蓝桥杯---IIc通信与EEPROM

IIC通信的内容(只看重点)
1.IIC通信主要依靠两根线:SCL和SDA.
2.高位在先,低位在后。
3.有ACK和NAK之说。
4.起始信号和终止信号时,SCL在高电平时变化。数据信号时,SCL为低电平期间变化,SCL高电平读取。
5.“整体上来说器件都是有一个最快速度的限制,而没有一个最慢速度的限制,所以在换用高速的单片机后,通常都是靠在个步骤步骤之间,插入软件延时来满足最慢时序的要求”对这句话有深刻理解的话,就会大体上掌握时序。

EEPROM
EEPROM有好几个系列:24x01/02/04/08/16,观察发现最后两位是01等等,代表容量为1K bit。其他也是这个道理。
我们需要阅读AT2402的手册,在此之前,需要补充一些知识。
<1>8-byte page(1k,2k),16-byte page(4k,8k,16k)(1k和2K的页数是8字节,其余的几页都是16字节)
<2>1k/2k的硬件地址有3个,言外之意可以一个总线挂8个1k/2k的IIc器件。而4K两个地址位最多挂4个,8K一个地址位最多挂两个,16K只能一个总线挂一个。
正式进入手册,跟之前认识温度传感器是类似的,还是需要读和写的操作,但与IIc结合使用,又会有很多的不同。
还是要先看原理图:
在这里插入图片描述
在这些脚中,我们写程序只用SCL和SDA 两个引脚。
接下来,看着说明书写程序。
第一步:先来看看一张图有一个整体的把握。
在这里插入图片描述
第二步:先写开始和停止的子函数。

		void iicstrat()//1 iic的起始信号
			{
				sda=1;
				_nop_();
				scl=1;
				_nop_();
				sda=0;
				_nop_();
				scl=0;
				_nop_();
				//以上由起始信号起始部分的图写成的
			}

	void iicstop()//2 iic的停止信号
	{
		sda=0;
		_nop_();
		scl=1;
		_nop_();
		sda=1;
		_nop_();
		//以上由起始信号停止部分的图完成
		
	}

这里需要说明的是,起始命令时,SCL和SDA都是由高到低的。而停止命令时,与之相反。

第三步:写的命令。在写之前,看一张存储地址的图。
在这里插入图片描述

	 void iicwrite(uchar add,uchar dat)//3 写数据,定义一个地址,定义一个数据
		{
			iicstrat();//一 启动一次iic的转换
			writebyte(0x90);//在存储位上,高8位是固定的:1010,低8位是默认的:0000  所以起始值是 90
			//iic时,为a0,但现在是A/D转换器,只需一处做出改变,其他地方一样
			ack();//响应信号的程序
			writebyte(add);//写地址
			ack();//等待
			writebyte(dat);//写数据
			ack();//再等待
			iicstop();//最后,停止
		}
		
	void writebyte(uchar dat)//4 写字节
	{
		uchar i;
		for(i=0;i<8;i++)//1010 00008位逐一写
		{
			scl=0;//先是拉低SCL的信号
			sda=dat&0x80;//然后是给SDA一个信号
			scl=1;//随后将其拉高
			dat<<=1;//最后将其一位一位的写入
		}
		scl=0;//必须置0,因为要给一个返回的信号
	}
	
	uchar ack()//5 响应信号的程序
	{
		scl=1;//因其又是一个时钟周期,才会给我们一个数据
		iicdelay(5);//这里必须是特殊的延迟,不能是其他
		if(sda==1)//判断是否出现了错误
		{
			scl=0;
			iicstop();
			return 0;
		}
		else //返回是1的时候,才会回到写数据的函数中
		{
			scl=0;
			return 1;
		}
	}

	void iicdelay(uchar m)//6 特殊的延迟,此处定义了5个时钟周期
	{
		do
		{
			_nop_();
		}
		while(m--);
	}

第四步:读的命令。

uchar iicread(uchar add)//7 读的操作
		{
			uchar temp;
			//与写的操作一样的
			iicstrat();
			writebyte(0x90);
			ack();
			writebyte(add);
			ack();
			iicstop();
			//之后重新开始
			iicstrat();
			writebyte(0x91);//让最后1为位置1,是进行读的操作
			ack();
			temp=iicreadbyte();
			iicstop();
			
			temp=0.39*temp;
			
			return temp;
		}

	uchar iicreadbyte()//8 写字节
	{
		uchar dat;
		uchar i;
		//一部分仿照读字节的程序
		for(i=0;i<8;i++)
		{
			scl=1;
			iicdelay(5);
			dat<<=1;
			
			if(sda==1)//可以简写为sda
			{
				dat|=0x01;
			}
			scl=0;
		}
		
		return dat;
	}
  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值