当前位置:首页 > 单片机 > 单片机
[导读]/******************************************************说 明:S3C2440 I2C实现*****************************************************/1:I2C原理 总线的构成及信号类型 I2C总线是由数据线SDA和时钟SCL构成的

/*****************************************************

*说 明:S3C2440 I2C实现

*****************************************************/


1:I2C原理

总线的构成及信号类型 I2C总线是由数据线SDA和时钟SCL构成的串行总线,可发送和接收数据。在CPU与被控IC之间、IC与IC之间进行双向传送,最高传送速率100kbps。各种被控制电路均并联在这条总线上,但就像电话机一样只有拨通各自的号码才能工作,所以每个电路和模块都有唯一的地址,在信息的传输过程中,I2C总线上并接的每一模块电路既是主控器(或被控器),又是发送器(或接收器),这取决于它所要完成的功能。CPU发出的控制信号分为地址码和控制量两部分,地址码用来选址,即接通需要控制的电路,确定控制的种类;控制量决定该调整的类别(如对比度、亮度等)及需要调整的量。这样,各控制电路虽然挂在同一条总线上,却彼此独立,互不相关。 I2C总线在传送数据过程中共有三种类型信号, 它们分别是:开始信号、结束信号和应答信号。 开始信号:SCL为高电平时,SDA由高电平向低电平跳变,开始传送数据。 结束信号:SCL为高电平时,SDA由低电平向高电平跳变,结束传送数据。 应答信号:接收数据的从控器在接收到8bit数据后,向发送数据的主控器发出特定的低电平脉冲,表示已收到数据。CPU向从控器发出一个信号后,等待从控器发出一个应答信号,CPU接收到应答信号后,根据实际情况作出是否继续传递信号的判断。若未收到应答信号,判断为受控单元出现故障。 这些信号中,起始信号是必需的,结束信号和应答信号,都可以不要。


2:I2C实验代码

/*
---------------------------------------------------------------
文件名称:I2C.c
说 明:I2C协议 读写AT24C08
作 者:温子祺
创建时间:2010-08-17
测试结果:[OK]
注意事项:

(1)24C02数据速率I2C总线的数据传送速率在标准工作方式下为100kbit/s,
在快速方式下,最高传送速率可达400kbit/s。
(2)当前S3C2440各频率如下:FCLK 405MHz
HCLK 135MHz
PCLK 67.5MHz
(3)当前I2C协议在三星提供的源代码进行修改,并提升代码的容错能力
如I2C进行读写时,都有进行超时处理。
---------------------------------------------------------------
*/
#include "S3C244x.h"
#include "Global.h"
#include "IIC.h"
/*
1:rIICON IIC总线控制寄存器
2:rIICSTAT IIC总线控制状态寄存器
3:rIICADD IIC总线地址寄存器
4:rIICDS IIC总线发送接收数据移位寄存器
5:rIICLC IIC总线多主设备线路控制寄存器
*/

/*
====================================================

I2C基本函数接口

====================================================
*/
static volatile UINT8 g_ucI2CDataBuf[256]; //I2C发送数据缓冲区
static volatile UINT32 g_unI2CCurDataCount; //I2C当前数据计数
static volatile UINT32 g_unI2CCurStatus; //I2C当前状态
static volatile UINT32 g_unI2CCurDataOffset; //I2C当前发送数据偏移量
static UINT32 g_unI2CCurMode; //I2C当前模式
static UINT32 g_unIICCONSave; //临时保存rIICCON寄存器值

static void __irq I2CISR(void) ; //I2C中断服务函数

static BOOL I2CWriteByte(UINT32 unSlaveAddress,UINT32 ucWriteAddress,UINT8 *pucWriteByte);
static BOOL I2CReadByte (UINT32 unSlaveAddress,UINT32 ucReadAddress ,UINT8 *pucReadByte);


/******************************************************
*文件名称:I2CWriteByte
*输 入:unSlaveAddress 从机地址
unWriteAddress 写地址
pucWriteByte 写字节
*输 出:TRUE/FALSE
*功能说明:I2C 写单个字节
*注意事项:
主机发送起始信号后,发送一个寻址字节,收到应答后紧跟着的就是数据传输,
数据传输一般由主机产生的停止位终止。但是,如果主机仍希望在总线上通讯,
它可以产生重复起始信号和寻址另一个从机,而不是首先产生一个停止信号。
在这种传输中,可能有不同的读/写格式。
*******************************************************/
static BOOL I2CWriteByte(UINT32 unSlaveAddress,
UINT32 unWriteAddress,
UINT8 *pucWriteByte)
{
BOOL bRt=TRUE;
UINT32 unTimeouts;

g_unI2CCurMode = WRDATA; //当前I2C模式:写
g_unI2CCurDataOffset= 0; //I2C数据缓冲区偏移量为0
g_ucI2CDataBuf[0] = (UINT8)unWriteAddress; //写地址
g_ucI2CDataBuf[1] = *pucWriteByte; //写数据
g_unI2CCurDataCount = 2; //当前数据计数值(即地址+数据=2字节)

rIICDS = unSlaveAddress; //0xa0(高四位默认是1010,低四位为xxxx)
rIICSTAT = 0xf0; //主机发送启动

unTimeouts=1000;

while(g_unI2CCurDataCount!=-1 && unTimeouts--)
{
DelayNus(1);
}

if(!unTimeouts)
{
bRt=FALSE;

goto end;
}


g_unI2CCurMode = POLLACK;

while(1)
{
rIICDS = unSlaveAddress;
g_unI2CCurStatus = 0x100;
rIICSTAT = 0xf0; //主机发送启动

rIICCON=g_unIICCONSave; //恢复I2C运行

unTimeouts=1000;

while(g_unI2CCurStatus==0x100 && unTimeouts--)
{
DelayNus(1);
}

if(!unTimeouts)
{
bRt=FALSE;

goto end;
}


if(!(g_unI2CCurStatus&0x1))
{
break; //接收到应答(ACK)信号
}

}

end:
rIICSTAT = 0xd0; //停止主机发送状态Stop MasTx condition
rIICCON = g_unIICCONSave; //恢复I2C运行
DelayNus(10); //等待直到停止条件是有效的

return bRt;
}

/******************************************************
*文件名称:I2CReadByte
*输 入:unSlaveAddress 从机地址
unReadAddress 读地址
pucReadByte 读字节
*输 出:TRUE/FALSE
*功能说明:I2C 读单个字节
*注意事项:
主机发送完寻址字节后,主机立即读取从机中的数据。
当寻址字节的"R/W"位为1时,在从机产生应答信号后,
主机发送器变成主机接收器,从机接收器变成从机发送器。
之后,数据由从机发送,主机接收,每个应答由主机产生,
时钟信号CLK仍由主机产生。若主机要终止本次传输,则发送
一个非应答信号,接着主机产生停止信号
*******************************************************/
static BOOL I2CReadByte(UINT32 unSlaveAddress,
UINT32 unReadAddress,
UINT8 *pucReadByte)
{
BOOL bRt=TRUE;
UINT32 unTimeouts;

g_unI2CCurMode = SETRDADDR;
g_unI2CCurDataOffset= 0;
g_ucI2CDataBuf[0] = (UINT8)unReadAddress;
g_unI2CCurDataCount = 1;

rIICDS = unSlaveAddress;
rIICSTAT = 0xf0; //主机发送启动

unTimeouts=1000;

while(g_unI2CCurDataCount!=-1 && unTimeouts--)
{
DelayNus(1);
}

if(!unTimeouts)
{
bRt=FALSE;

goto end;
}

g_unI2CCurMode = RDDATA;
g_unI2CCurDataOffset = 0;
g_unI2CCurDataCount = 1;

rIICDS = unSlaveAddress;
rIICSTAT = 0xb0; //主机接收启动
rIICCON = g_unIICCONSave; //恢复I2C运行

unTimeouts=1000;

while(g_unI2CCurDataCount!=-1 && unTimeouts--)
{
DelayNus(1);
}

if(!unTimeouts)
{
bRt=FALSE;

goto end;
}

*pucReadByte= g_ucI2CDataBuf[1];

end:

return bRt;
}

/******************************************************
*文件名称:I2CWriteNBytes
*输 入:unSlaveAddress 从机地址
unWriteAddress 写地址
pucWriteByte 写字节
unNumOfBytes 写字节数
*输 出:TRUE/FALSE
*功能说明:I2C 写多个字节
*******************************************************/
BOOL I2CWriteNBytes(UINT32 unSlaveAddress,
UINT32 unWriteAddress,
UINT8 *pucWriteBytes,
UINT32 unNumOfBytes)
{
UINT32 unSpareOfBytes=unNumOfBytes;

while(unSpareOfBytes--)
{
if(!I2CWriteByte( unSlaveAddress,
unWriteAddress,
pucWriteBytes))
{

I2CMSG("I2C[ERROR]:fail to write data fail at address %d
success to write %d bytes rn",
unWriteAddress,(unNumOfBytes-unSpareOfBytes));

return FALSE;

}

unWriteAddress++;
pucWriteBytes++;

}

return TRUE;
}
/******************************************************
*文件名称:I2CReadNBytes
*输 入:unSlaveAddress 从机地址
unReadAddress 读地址
unNumOfBytes
*输 出:TRUE/FALSE
*功能说明:I2C 读多个字节
*******************************************************/
BOOL I2CReadNBytes(UINT32 unSlaveAddress,
UINT32 unReadAddress,
UINT8 *pucReadByte,
UINT32 unNumOfBytes)

{
UINT32 unSpareOfBytes=unNumOfBytes;

while(unSpareOfBytes--)
{
if(!I2CReadByte( unSlaveAddress,
unReadAddress,
pucReadByte))
{

I2CMSG("I2C[ERROR]:fail to read data fail at address %d
success to read %d bytes rn",
unReadAddress,(unNumOfBytes-unSpareOfBytes));

return FALSE;

}

unReadAddress++;
pucReadByte++;

}

return TRUE;
}
/*
====================================================

中断服务函数

====================================================
*/
/******************************************************
*文件名称:I2CISR
*输 入:无
*输 出:无
*功能说明:I2C 中断服务函数
*******************************************************/
void __irq I2CISR(void)
{
UINT32 unI2CStatus;


unI2CStatus = rIICSTAT;

if(unI2CStatus & 0x8){} //When bus arbitration is failed.
if(unI2CStatus & 0x4){} //When a slave address is matched with IICADD
if(unI2CStatus & 0x2){} //When a slave address is 0000000b
if(unI2CStatus & 0x1){} //When ACK isn't received

switch(g_unI2CCurMode)
{
case POLLACK:
g_unI2CCurStatus = unI2CStatus;
break;


case RDDATA:

if((g_unI2CCurDataCount--)==0)
{
g_ucI2CDataBuf[g_unI2CCurDataOffset++] = rIICDS;

rIICSTAT = 0x90; //停止I2C接收状态
rIICCON = g_unIICCONSave; //恢复I2C运行
DelayNus(1); //等待直到停止条件是有效的

//The pending bit will not be set after issuing stop condition.
break;
}
g_ucI2CDataBuf[g_unI2CCurDataOffset++] = rIICDS; //The last data has to be read with no ack.

if((g_unI2CCurDataCount)==0)
rIICCON = 0x2f; //Resumes IIC operation with NOACK.
else
rIICCON = g_unIICCONSave; //Resumes IIC operation with ACK
break;

case WRDATA:

rIICDS = g_ucI2CDataBuf[g_unI2CCurDataOffset++]; //g_ucI2CDataBuf[0] has dummy.
DelayNus(10); //for setup time until rising edge of IICSCL

rIICCON = g_unIICCONSave; //恢复I2C运行

if((g_unI2CCurDataCount--)==0)
{
rIICSTAT = 0xd0; //Stop MasTx condition
rIICCON = g_unIICCONSave; //恢复I2C运行
DelayNus(10); //Wait until stop condtion is in effect.
//The pending bit will not be set after issuing stop condition.
}

break;

case SETRDADDR:

if((g_unI2CCurDataCount--)==0)
{
break;
}
//IIC operation is stopped because of IICCON[4]
rIICDS = g_ucI2CDataBuf[g_unI2CCurDataOffset++];
DelayNus(10); //For setup time until rising edge of IICSCL
rIICCON = g_unIICCONSave; //恢复I2C运行
break;

default:
break;
}

rSRCPND = BIT_IIC; //Clear pending bit
rINTPND = BIT_IIC;
}
/*
====================================================

测试代码

====================================================
*/
/******************************************************
*文件名称:I2CTest
*输 入:无
*输 出:无
*功能说明:I2C 测试代码
*******************************************************/
void I2CTest(void)
{
UINT32 i;
UINT8 buf[256];

I2CMSG("nIIC Test(Interrupt) using AT24C02n");


rGPEUP |= 0xc000; //Pull-up disable
rGPECON |= 0xa00000; //GPE15:IICSDA , GPE14:IICSCL
rCLKCON |= 1<<16;
pISR_IIC = (UINT32)I2CISR;
rINTMSK &= ~(BIT_IIC);


/*
IIC时序太重要了,要认真设置好发送时钟和接收数据时钟
当前PCLK = 405/6 = 67.5MHz

IICCLK=67.5/16= 4.22MHz

Tx Clock = 4.22/11=0.384MHz

*/

g_unIICCONSave=rIICCON = (1<<7) | (0<<6) | (1<<5) | (0xa);

rIICADD = 0x10; //S3C2440 从机地址设置
rIICSTAT = 0x10; //I2C总线数据输出使能(Rx/Tx)
rIICLC =(1<<2)|(1); //滤波器使能,SDA数据延时输出

I2CMSG("Write test data into AT24C02n");


for(i=0;i<256;i++)
{
buf[i]=i;
}


I2CWriteNBytes(0xA0,0,buf,256);

for(i=0;i<256;i++)
buf[i] = 0;

I2CMSG("Read test data from AT24C02n");


I2CReadNBytes(0xA0,0,buf,256);

I2CMSG("Read Data Finishrn");

for(i=0;i<256;i++)
{
I2CMSG("%d ",buf[i]);

}

rINTMSK |= BIT_IIC;

}

本站声明: 本文章由作者或相关机构授权发布,目的在于传递更多信息,并不代表本站赞同其观点,本站亦不保证或承诺内容真实性等。需要转载请联系该专栏作者,如若文章内容侵犯您的权益,请及时联系本站删除。
换一批
延伸阅读

9月2日消息,不造车的华为或将催生出更大的独角兽公司,随着阿维塔和赛力斯的入局,华为引望愈发显得引人瞩目。

关键字: 阿维塔 塞力斯 华为

加利福尼亚州圣克拉拉县2024年8月30日 /美通社/ -- 数字化转型技术解决方案公司Trianz今天宣布,该公司与Amazon Web Services (AWS)签订了...

关键字: AWS AN BSP 数字化

伦敦2024年8月29日 /美通社/ -- 英国汽车技术公司SODA.Auto推出其旗舰产品SODA V,这是全球首款涵盖汽车工程师从创意到认证的所有需求的工具,可用于创建软件定义汽车。 SODA V工具的开发耗时1.5...

关键字: 汽车 人工智能 智能驱动 BSP

北京2024年8月28日 /美通社/ -- 越来越多用户希望企业业务能7×24不间断运行,同时企业却面临越来越多业务中断的风险,如企业系统复杂性的增加,频繁的功能更新和发布等。如何确保业务连续性,提升韧性,成...

关键字: 亚马逊 解密 控制平面 BSP

8月30日消息,据媒体报道,腾讯和网易近期正在缩减他们对日本游戏市场的投资。

关键字: 腾讯 编码器 CPU

8月28日消息,今天上午,2024中国国际大数据产业博览会开幕式在贵阳举行,华为董事、质量流程IT总裁陶景文发表了演讲。

关键字: 华为 12nm EDA 半导体

8月28日消息,在2024中国国际大数据产业博览会上,华为常务董事、华为云CEO张平安发表演讲称,数字世界的话语权最终是由生态的繁荣决定的。

关键字: 华为 12nm 手机 卫星通信

要点: 有效应对环境变化,经营业绩稳中有升 落实提质增效举措,毛利润率延续升势 战略布局成效显著,战新业务引领增长 以科技创新为引领,提升企业核心竞争力 坚持高质量发展策略,塑强核心竞争优势...

关键字: 通信 BSP 电信运营商 数字经济

北京2024年8月27日 /美通社/ -- 8月21日,由中央广播电视总台与中国电影电视技术学会联合牵头组建的NVI技术创新联盟在BIRTV2024超高清全产业链发展研讨会上宣布正式成立。 活动现场 NVI技术创新联...

关键字: VI 传输协议 音频 BSP

北京2024年8月27日 /美通社/ -- 在8月23日举办的2024年长三角生态绿色一体化发展示范区联合招商会上,软通动力信息技术(集团)股份有限公司(以下简称"软通动力")与长三角投资(上海)有限...

关键字: BSP 信息技术
关闭
关闭