📄 i2cint.c
字号:
I2C_end = 0; // Clear I2C operating flag
I2CONCLR = 1 << I2EN // Clear some I2C flag, and enter master mode
| 1 << STA
| 1 << SI
| 1 << AA;
I2CONSET = 1 << I2EN // Enable I2C and start I2C Bus
| 1 << STA;
for(i=0; i<0xfffffff; )
{
if(0 == I2C_end) // I2C Bus is busy now
{
i++;
}
else if(1 == I2C_end) // I2C Bus stop normally
{
i = 0x10000000;
return TRUE;
}
else if(0xff == I2C_end) // I2C Bus stop
{
i = 0x20000000;
return FALSE;
}
else // I2C return value is error
{
return FALSE;
}
}
return FALSE; // Time of operation is too long
}
return FALSE;
}
/*********************************************************************************************************
** Function name: I2C_WriteNByte
**
** Descriptions: Write some bytes to Chip
**
** input parameters: uint8 sla Slave address
** uint32 suba_type Type of sub address
** uint32 suba Sub address
** uint8 *s Point of data buffer
** uint32 num Number of data
**
** Returned value: TRUE / FALSE
** If FALSE, check error code in I2C_err
**
** Used global variables: I2C_sla, I2C_sla, I2C_num, I2C_suba_en, I2C_end, I2C_err
**
** Calling modules: None
**
** Created by: ChenXiBing
** Created Date: 2005-10-20
**-------------------------------------------------------------------------------------------------------
** Modified by: Ganda
** Modified date: 2005-10-28
**
*********************************************************************************************************/
uint8 I2C_WriteNByte(uint8 sla, uint8 suba_type, uint32 suba, uint8 *s, uint32 num)
{ uint32 i;
I2C_err = 0x00;
if (num > 0)
{
if (suba_type == 1) // ONE_BYTE_SUBA
{
I2C_sla = sla; // Slave address of writing
I2C_suba = suba; // Sub address
I2C_suba_num = 1; // Sub address length
}
if (suba_type == 2) // TWO_BYTE_SUBA
{
I2C_sla = sla; // Slave address of writing
I2C_suba = suba; // Sub address
I2C_suba_num = 2; // Sub address length
}
if (suba_type == 3) // X_ADD_8_SUBA
{
I2C_sla = sla + ((suba >> 7 )& 0x0e); // Slave address of writing
I2C_suba = suba & 0x0ff; // Sub address
I2C_suba_num = 1; // Sub address length
}
I2C_buf = s; // Point of data buffer
I2C_num = num; // Number of data
I2C_suba_en = 2; // Enable sub address and Write mode
I2C_end = 0; // Clear I2C operating flag
I2CONCLR = 1 << I2EN // Clear some I2C flag, and enter master mode
| 1 << STA
| 1 << SI
| 1 << AA;
I2CONSET = 1 << I2EN // Enable I2C and start I2C Bus
| 1 << STA;
for(i=0; i<0xfffffff; )
{
if(0 == I2C_end) // I2C Bus is busy now
{
i++;
}
else if(1 == I2C_end) // I2C Bus stop normally
{
i = 0x10000000;
return TRUE;
}
else if(0xff == I2C_end) // I2C Bus stop
{
i = 0x20000000;
return FALSE;
}
else // I2C return value is error
{
return FALSE;
}
}
return FALSE;
}
return FALSE;
}
/*********************************************************************************************************
** Function name: I2C_IRQ_Exception
**
** Descriptions: I2C Interrupt handle
**
** input parameters: None
**
** Returned value: None
**
** Used global variables: I2C_sla, I2C_sla, I2C_num, I2C_suba_en, I2C_end, I2C_err
**
** Calling modules: None
**
** Created by: ChenXiBing
** Created Date: 2005-10-20
**-------------------------------------------------------------------------------------------------------
** Modified by: Ganda
** Modified date: 2005-10-28
** Descriptions: Check and add error handle routine
**
*********************************************************************************************************/
void I2C_IRQ_Exception(void)
{
switch (I2STAT & 0xF8)
{
case 0x08: // I2C_MO_STA1
if(I2C_suba_en == 1) // Load SLA+R
{
I2DAT = I2C_sla & 0xFE;
}
else // Load SLA+W
{
I2DAT = I2C_sla;
}
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
break;
case 0x10: // I2C_MO_STA2
// I2C_MI_STA2
I2DAT = I2C_sla; // Load SLA+R/SLR+W agin
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
break;
case 0x18: // I2C_MO_ACK_SLAW
case 0x28: // I2C_MO_ACK_I2DAT
if (I2C_suba_en == 0) // If all address has send
{
if (I2C_num > 0)
{
I2DAT = *I2C_buf++;
I2C_num--;
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
}
else
{
I2C_end = 1; // I2C Bus operation finished
I2CONSET = 1 << STO; // Stop I2C Bus
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
}
}
if(I2C_suba_en == 1) // If has address to send
{
if (I2C_suba_num == 2)
{
I2DAT = ((I2C_suba >> 8) & 0xff);
I2C_suba_num--;
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
break;
}
if(I2C_suba_num == 1)
{
I2DAT = (I2C_suba & 0xff);
I2C_suba_num--;
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
break;
}
if (I2C_suba_num == 0)
{
I2C_suba_en = 0; // I2C sub address has send
I2CONSET = 1 << STA; // Start I2C Bus
I2CONCLR = 1 << SI; // Clear SI flag
break;
}
}
if (I2C_suba_en == 2) // Send sub address
{
if (I2C_suba_num > 0)
{
if (I2C_suba_num == 2)
{
I2DAT = ((I2C_suba >> 8) & 0xff);
I2C_suba_num--;
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
break;
}
if (I2C_suba_num == 1)
{
I2DAT = (I2C_suba & 0xff);
I2C_suba_num--;
I2C_suba_en = 0;
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
break;
}
}
}
break;
case 0x40: // I2C_MI_ACK_SLAR
if (I2C_num <= 1) // Is the last byte
{
I2CONCLR = 1 << AA; // Next state will send NACK
}
else
{
I2CONSET = 1 << AA; // Next state will send ACK
}
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
break;
case 0x20: // I2C_MO_NACK_SLAW
I2CONSET = 1 << STO; // Set STO
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
I2C_err = 0x20;
I2C_end = 0xFF;
break;
case 0x30: // I2C_MO_NACK_I2DAT
I2CONSET = 1 << STO; // Set STO
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
I2C_err = 0x30;
I2C_end = 0xFF;
break;
case 0x38: // I2C_MO_ERR_BUS I2C_MI_ERR_BUS
I2CONSET = 1 << STO; // Set STO
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
I2C_err = 0x38;
I2C_end = 0xFF;
break;
case 0x48: // I2C_MI_NACK_SLAR
I2CONSET = 1 << STO; // Set STO
I2CONCLR = 1 << STA // Clear STA and SI flag
| 1 << SI;
I2C_err = 0x48;
I2C_end = 0xFF;
break;
case 0x50: // I2C_MI_ACK_I2DAT
*I2C_buf++ = I2DAT;
I2C_num--;
if (I2C_num == 1) // Is the last byte
{
I2CONCLR = 1 << SI // Clear SI and AA flag
| 1 << AA
| 1 << STA;
}
else
{
I2CONSET = 1 << AA; // Next state will send ACK
I2CONCLR = 1 << SI // Clear SI and AA flag
| 1 << STA;
}
break;
case 0x58: // I2C_MI_NACK_I2DAT
*I2C_buf++ = I2DAT; // Read the last byte
I2CONSET = 1 << STO; // Set STO
I2CONCLR = 1 << SI // Clear SI and AA flag
| 1 << AA;
I2C_end = 1;
break;
default:
break;
}
VICVectAddr = 0x00;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -