STM 8 I / O 포트 시 뮬 레이 션 I2C

STM8I/O   I2C       
STM8 I/O   I2C


#define I2C_ERR   0

#define I2C_CRR   1

#define  I2CDataIn  1

#define  I2CDataOut 0

#define I2C_PORT  (GPIOC)

#define I2CSCL   (GPIO_PIN_7)

#define I2CSDA   (GPIO_PIN_6)


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

// I2C Data input/output

// 0-Output, 1-Input

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

void I2CDataInOut(bool InOut)

{

if(InOut)

  {

  GPIO_Init(I2C_PORT,I2CSDA,GPIO_MODE_IN_FL_NO_IT);

  }

else

  {

  GPIO_Init(I2C_PORT,I2CSDA,GPIO_MODE_OUT_OD_LOW_FAST);

  }

}

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

//  Send start condition

//  ensure data is high then issue a start condition

//  see also i2c_Start() macro

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

void I2C_Start (void)

{

GPIO_WriteHigh(I2C_PORT, I2CSDA);

_delay_5us(5);

GPIO_WriteHigh(I2C_PORT, I2CSCL);

_delay_5us(5);

GPIO_WriteLow(I2C_PORT, I2CSDA);

_delay_5us(5);

}

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

//   Send stop condition

//   data low-high while clock high

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

void I2C_Stop (void)

{

GPIO_WriteLow(I2C_PORT, I2CSDA);

_delay_5us(5);

GPIO_WriteHigh(I2C_PORT, I2CSCL);

_delay_5us(5);

GPIO_WriteHigh(I2C_PORT, I2CSDA);

}

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

//ROUTINE NAME : I2C_Ack

//INPUT/OUTPUT : None.

//DESCRIPTION  : Acknoledge generation from now.

//COMMENTS     : Transfer sequence = DATA, ACK.

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

void I2C_Rack(void)

{

GPIO_WriteLow(I2C_PORT, I2CSDA);

_delay_5us(5);

GPIO_WriteHigh(I2C_PORT, I2CSCL);

_delay_5us(5);

GPIO_WriteLow(I2C_PORT, I2CSCL);

_delay_5us(5);

}


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

//ROUTINE NAME : I2C_nAck

//INPUT/OUTPUT : None.

//DESCRIPTION  : Non acknoledge generation from now.

//COMMENTS     : Transfer sequence = DATA, NACK.

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

void I2C_nAck (void)

{

GPIO_WriteHigh(I2C_PORT, I2CSDA);

_delay_5us(5);

GPIO_WriteHigh(I2C_PORT, I2CSCL);

_delay_5us(5);

GPIO_WriteLow(I2C_PORT, I2CSCL);

_delay_5us(5);

}

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

//  Send a byte to the slave          

//  return I2C_ERR OR I2C_CRR

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

bool SendByte(UCHAR I2cData)

{

UCHAR i;

bool I2CStatus;


for(i=0; i<8; i++)

  {

  GPIO_WriteLow(I2C_PORT, I2CSCL);

  _delay_5us(5);

  if(I2cData & 0x80)

   {GPIO_WriteHigh(I2C_PORT, I2CSDA);}

  else

   {GPIO_WriteLow(I2C_PORT, I2CSDA);}

  GPIO_WriteHigh(I2C_PORT, I2CSCL);

  _delay_5us(5);

  I2cData <<= 1;

  }

  GPIO_WriteLow(I2C_PORT, I2CSCL);

  GPIO_WriteHigh(I2C_PORT, I2CSDA);//      ,    

  

  I2CDataInOut(I2CDataIn);


  GPIO_WriteHigh(I2C_PORT, I2CSCL);

  _delay_5us(5);

  if(GPIO_ReadInputPin(I2C_PORT,I2CSDA) == 0)

   {

   I2CStatus = I2C_CRR;

   }

  else

   {

   I2CStatus = I2C_ERR;

   }

  I2CDataInOut(I2CDataOut);

  return I2CStatus;

}


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

//ROUTINE NAME : I2Cm_RxData

//INPUT/OUTPUT : Last byte to receive flag (active high)/Received data byte.

//DESCRIPTION  : Receive a data byte.

//COMMENTS     : Transfer sequence = DATA, ACK, EV7...

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

UCHAR RcvByte(void)

{   

    UCHAR i;

    UCHAR ReadByte=0;

   GPIO_WriteHigh(I2C_PORT, I2CSDA);


I2CDataInOut(I2CDataIn);

_delay_5us(10);

for(i=0; i<8; i++)

  {

   ReadByte <<= 1;

   GPIO_WriteLow(I2C_PORT, I2CSCL);

   _delay_5us(5);

   GPIO_WriteHigh(I2C_PORT, I2CSCL);

   _delay_5us(5);


   if(GPIO_ReadInputPin(I2C_PORT,I2CSDA) == 1)

    {ReadByte |= 0x01;}

   _delay_5us(5);

  }  

GPIO_WriteLow(I2C_PORT, I2CSCL);

I2CDataInOut(I2CDataOut);

_delay_5us(10);

   return ReadByte;

}


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

   N   ,  :?

   wrDAdr: write device-address      ??

   wordAdr: word address          ??

   rdDAdr: read device-address      

   *pRdDat: p->read data      

   num: number         

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

bool I2C_Read(UCHAR wrDAdr,UCHAR wordAdr,UCHAR *pRdDat,UCHAR num)

{

bool I2CAck;

UCHAR i=0;

UCHAR rdDAdr;

rdDAdr = wrDAdr+1; //          1

I2C_Start();  /*  I2C*/

_delay_5us(5);

I2CAck = SendByte(wrDAdr); /*      */

if(!I2CAck)

  {

   return I2C_ERR;

  }

I2CAck = SendByte(wordAdr); /*      */

if(!I2CAck)

  {

   return I2C_ERR;

  }


I2C_Start();   /*  I2C*/

  I2CAck = SendByte(rdDAdr); /*      */

if(!I2CAck)

  {

   return I2C_ERR;

  }

_delay_5us(5);

for(i=0;i<num-1;i++)

  {

  *(pRdDat+i) = RcvByte();

  I2C_Rack();

   }

if(i==num-1)

  {

  *(pRdDat+i) = RcvByte();

  I2C_nAck();

  }

I2C_Stop();

return I2C_CRR;

}


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

 N   , N-1    ,        

wrDAdr: write device-address      ??

  wordAdr: word address          ?

  *pWrDat: p->write data      

  num: number           

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

bool I2C_Write(UCHAR wrDAdr,UCHAR wordAdr,UCHAR *pWrDat,UCHAR num)

{

bool I2CAck;

unsigned char i;


I2C_Start();      /*  I2C*/

_delay_5us(5);

I2CAck = SendByte(wrDAdr); /*      */

if(!I2CAck)

  {

   return I2C_ERR;

  }

I2CAck = SendByte(wordAdr);  /*         */

if(!I2CAck)

  {

   return I2C_ERR;

  }

for(i=0;i<num-1;i++)

  {

  I2CAck = SendByte(*(pWrDat+i));

  if(!I2CAck)

   {return I2C_ERR;}

  }

if(i==num-1)

  {

  I2CAck = SendByte(*(pWrDat+num-1));

  if(!I2CAck)

   {return I2C_ERR;}

  }

I2C_Stop();

return I2CAck;

} 

상기 코드 는 왠 지 데이터 가 정확 하지 않 습 니 다. 오실로그래프 로 제 가 보 낸 부속품 주소, 레지스터 주소 등 이 모두 옳 습 니 다. 부속품 이 출력 한 데 이 터 는 0xFF 이 고 프로그램 에서 읽 은 데 이 터 는 0x 00 입 니 다. 하루 동안 맞 추 지 못 해 상당히 답답 합 니 다. 동지 들 은 지적 하 였 습 니 다.
드디어 끝 났 습 니 다. 제 부속품 과 관련 이 있 을 겁 니 다. 그리고 if (GPIO ReadInputPin (I2C PORT, I2CSDA) = 1) 는 = 1 로 쓸 수 없습니다. if (GPIO ReadInputPin (I2C PORT, I2CSDA) 로 직접 써 야 합 니 다. 너무 답답 합 니 다.

좋은 웹페이지 즐겨찾기