Beispiel #1
0
int I2C::write(int address, const char *data, int length, bool repeated)
{
	unsigned char addr = (unsigned char)address>>1;
	for (int i = 0; i < length; i++)
		I2CMasterTXBuffer[i] = *data++;
	I2C_MstSend( LPC_I2C, address, (uint8_t *)I2CMasterTXBuffer, length);
	return length;
}
Beispiel #2
0
/*****************************************************************************
** Function name:		I2C_MstSendRcv
**
** Descriptions:		Send a block of data to the I2C port combining master
**                      send and master recevie with repeated start in the middle.
**
** parameters:			Dev addr. TX ptr, TX length, RX ptr, and RX length.
** Returned value:		None
** 
*****************************************************************************/
void I2C_MstSendRcv( LPC_I2C_TypeDef *I2Cx, uint32_t addr, uint8_t *tx, uint32_t txlen, uint8_t *rx, uint32_t rxlen )
{
  uint32_t i;

  I2Cx->MSTDAT = addr;
  I2Cx->MSTCTL = CTL_MSTSTART;
#if I2C_INTERRUPT
  msttxrdy = mstrxrdy = 0;
  I2Cx->INTENSET = STAT_MSTPEND;
#endif 
  for ( i = 0; i < txlen; i++ ) 
  {
#if I2C_INTERRUPT
		while(!msttxrdy) 
		{
			if ( I2C_CheckError(I2Cx) ) {
				I2C_CheckIdle(I2Cx);
				/* Recursive call here. Be very careful with stack over flow if come here, especially
				when the other master trys to grab the bus all the time. */
//				while ( 1 );
				I2C_MstSend( I2Cx, addr, tx, txlen );
				return;
	  	}
		}
	msttxrdy = 0;
	I2Cx->MSTDAT = *tx++;
	I2Cx->MSTCTL = CTL_MSTCONTINUE;
	I2Cx->INTENSET = STAT_MSTPEND;
#else
	/* Move only if TXRDY is ready */
	while (!(I2Cx->STAT & STAT_MSTPEND));
	if((I2Cx->STAT & MASTER_STATE_MASK) != STAT_MSTTX)
	  while(1);
	I2Cx->MSTDAT = *tx++;
	I2Cx->MSTCTL = CTL_MSTCONTINUE;
#endif
  }

  /* Wait for the last TX to finish before setting repeated start. */
#if I2C_INTERRUPT
  while(!msttxrdy) 
  {
		if ( I2C_CheckError(I2Cx) ) {
			I2C_CheckIdle(I2Cx);
			/* Recursive call here. Be very careful with stack over flow if come here. especially
			when the other master trys to grab the bus all the time. */
//			while ( 1 );
			I2C_MstSend( I2Cx, addr, tx, txlen );
			return;
		}
  }
  msttxrdy = 0;
#else
  /* Move on only if TXRDY is ready */
  while (!(I2Cx->STAT & STAT_MSTPEND));
  if((I2Cx->STAT & MASTER_STATE_MASK) != STAT_MSTTX)
    while(1);
#endif

  /* Repeated Start */
  I2Cx->MSTDAT = addr|RD_BIT;   
  I2Cx->MSTCTL = CTL_MSTSTART|CTL_MSTCONTINUE;
#if I2C_INTERRUPT
  I2Cx->INTENSET = STAT_MSTPEND;
#endif

  for ( i = 0; i < rxlen; i++ )
  {
#if I2C_INTERRUPT
		while(!mstrxrdy) {
			if ( I2C_CheckError(I2Cx) ) {
				I2C_CheckIdle(I2Cx);
				/* Recursive call here. Be very careful with stack over flow if come here, especially
				when the other master trys to grab the bus all the time. */
//				while ( 1 );
				I2C_MstReceive( I2Cx, addr|RD_BIT, rx, rxlen );
				return;
			}
		}
		mstrxrdy = 0;
		*rx++ = I2Cx->MSTDAT;
		if ( i != rxlen-1 ) {
			I2Cx->MSTCTL = CTL_MSTCONTINUE;
			I2Cx->INTENSET = STAT_MSTPEND;
		}
#else
		/* Slave address has been sent, master receive is ready. */
		while (!(I2Cx->STAT & STAT_MSTPEND));
		if((I2Cx->STAT & MASTER_STATE_MASK) != STAT_MSTRX)
			while(1);
		*rx++ = I2Cx->MSTDAT;
		if ( i != rxlen-1 ) {
			I2Cx->MSTCTL = CTL_MSTCONTINUE;
		}
#endif
  }

  I2Cx->MSTCTL = CTL_MSTSTOP | CTL_MSTCONTINUE;
  I2C_CheckIdle(I2Cx);
  return; 
}
Beispiel #3
0
/*****************************************************************************
** Function name:		I2C_MstSend
**
** Descriptions:		Send a block of data to the I2C port, the 
**									first parameter is the device addre, the 2nd is buffer 
**                  pointer, the 3rd is the block length.
**
** parameters:			device addr, buffer pointer, and the block length
** Returned value:		None
** 
*****************************************************************************/
void I2C_MstSend( LPC_I2C_TypeDef *I2Cx, uint32_t addr, uint8_t *tx, uint32_t Length )
{
  uint32_t i;

  I2Cx->MSTDAT = addr;
  I2Cx->MSTCTL = CTL_MSTSTART;
#if I2C_INTERRUPT
  msttxrdy = 0;
  I2Cx->INTENSET = STAT_MSTPEND;
#endif
#if I2C_INTERRUPT
  for ( i = 0; i < Length; i++ ) 
  {
		while(!msttxrdy) {
			if ( I2C_CheckError(I2Cx) ) {
				I2C_CheckIdle(I2Cx);
				/* Recursive call here. Be very careful with stack over flow if come here, especially
				when the other master trys to grab the bus all the time. */
//				while ( 1 );
				I2C_MstSend( I2Cx, addr, tx, Length );
				return;
			}
		}
		msttxrdy = 0;
		I2Cx->MSTDAT = tx[i];
		I2Cx->MSTCTL = CTL_MSTCONTINUE;
		I2Cx->INTENSET = STAT_MSTPEND;
  }
  
  /* Wait for the last one to go out. */
  while(!msttxrdy) {
		if ( I2C_CheckError(I2Cx) ) {
	    I2C_CheckIdle(I2Cx);
			/* Recursive call here. Be very careful with stack over flow if come here. especially
			when the other master trys to grab the bus all the time. */
//			while ( 1 );
			I2C_MstSend( I2Cx, addr, tx, Length );
			return;
		}
  }
  msttxrdy = 0;
#else
  for ( i = 0; i < Length; i++ ) 
  {
		/* Move only if TXRDY is ready */
		while (!(I2Cx->STAT & STAT_MSTPEND));
		if((I2Cx->STAT & MASTER_STATE_MASK) != STAT_MSTTX)
			while(1);
		I2Cx->MSTDAT = *tx++;
		I2Cx->MSTCTL = CTL_MSTCONTINUE;
  }
  
  /* Wait for the last one to go out. */
  while (!(I2Cx->STAT & STAT_MSTPEND));
  if((I2Cx->STAT & MASTER_STATE_MASK) != STAT_MSTTX)
		while(1);
#endif
  /* Send STOP condition. */  
  I2Cx->MSTCTL = CTL_MSTSTOP | CTL_MSTCONTINUE;
  I2C_CheckIdle(I2Cx);
  return; 
}