This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

i2c SDA cannot read acknowledge

In the I2C process it seams nRF52832 cannot read device acknowledge pulse from device due to the Nordic output do not goto high impedance during device acknowledge pulse, but stay in drive high level output.

I connect a temp sensor SI7055 to the Nordic development board.

When I send the address it looks ok, but then at the last clock pulse I expect a low level as acknowledge, but the level is approx 1V in between high and low. By put a 560 ohm in serial to SDA I can see that the device actually send a low level signal, but on the other side, at Nordic SDA the level is still high (0.5V from high). It seams obvious that Nordic still hold the level high output when the device send acknowledge and that seams me wrong behavior.

Is there any register configuration required to get the SDA port in high impedance or pull up during the device acknowledge ?

Here the code I currently try read device mod. Clock and address pulse look fine, except for the device acknowledge pulse.

#include "io_i2c.h"

static volatile int DebugBreak;

// master 0
uint32_t *TASKS_STARTTX = ((uint32_t*)(0x40003000+0x008)); 
uint32_t *TASKS_STARTRX = ((uint32_t*)(0x40003000+0x000)); 
uint32_t *TASKS_STOP = ((uint32_t*)(0x40003000+0x014)); 

uint32_t *ENABLE = ((uint32_t*)(0x40003000+0x500)); 
uint32_t *PSELSCL = ((uint32_t*)(0x40003000+0x508)); 
uint32_t *PSELSDA = ((uint32_t*)(0x40003000+0x50C)); 
uint32_t *FREQ = ((uint32_t*)(0x40003000+0x524)); 
uint32_t *TXDPTR = ((uint32_t*)(0x40003000+0x544));
uint32_t *TXDMAXCNT = ((uint32_t*)(0x40003000+0x548));
uint32_t *TXDLIST = ((uint32_t*)(0x40003000+0x550));
uint32_t *ADDRESS = ((uint32_t*)(0x40003000+0x588));
  
uint32_t *TXDAMOUNT = ((uint32_t*)(0x40003000+0x54C));

uint32_t *INTEN = ((uint32_t*)(0x40003000+0x300)); 
uint32_t *INTENSET = ((uint32_t*)(0x40003000+0x304)); 

uint32_t *RXDPTR =  ((uint32_t*)(0x40003000+0x534));
uint32_t *RXDMAXCNT =  ((uint32_t*)(0x40003000+0x538));
uint32_t *RXDAMOUNT =  ((uint32_t*)(0x40003000+0x53C));
uint32_t *RXDLIST =  ((uint32_t*)(0x40003000+0x540));

uint32_t *PIN_CNF27 = ((uint32_t*)(0x50000000+0x76C));
  
static char txdata[100];
static char rxdata[100];
  
void io_i2cInit()
{
	for(int x = 0; x<100; x++)
		txdata[x]=0xF0;

    *PSELSCL = 26;//19;
    *PSELSDA = 27;//20;
	
	*FREQ = 0x01980000; // 100k                
	
	*TXDMAXCNT = 100;
	*TXDLIST = 1;
	
	*ADDRESS = 0x40;//7F;// 0x40;//120;
	
	*ENABLE = 6;
  
	*INTEN = 0xFFFFFFFF;
	*INTENSET = 0xFFFFFFFF;
	
	*TXDPTR = (uint32_t)(&txdata[0]);
	
	*RXDPTR = (uint32_t)(&rxdata[0]);
	*RXDMAXCNT =  100;
	*RXDLIST = 1;


	
}

void io_i2cTx(uint8_t Address, char *data, uint16_t Len) 
{
 	
	static int once;
	if(!once)
	{
		once =1;
	
		//*TASKS_STARTTX = 1; // SCL Led no 3 goes ON
		*TASKS_STARTRX = 1; // SCL Led no 3 goes ON
		
		uint32_t ta = *TXDAMOUNT; 
		if(ta !=0)
			DebugBreak = 1; // Never reached
	}	
	else 
	{
        #if 1 // if apply stop or not, *TXDAMOUNT does anyway never count up.
		*TASKS_STOP =1; // SCL Led no 3 goes OFF
        #endif

	}
	
	uint32_t ta = *TXDAMOUNT;
	if(ta !=0)
		DebugBreak = 1; // Never reached
}
uint16_t io_i2cRx(uint8_t Address, char *dest, uint16_t Len)
{
}

Related