Can't set I2C speed

I’m unable to change the bus speed on I2C3. No matter what I do, it always runs at 85.84 KHz.

1226-i2xspeed.jpg

The following code is pretty mature, and has been used in other work. It was only while I was hunting down an I2C problem on a new project that I noticed the speed issue. The code first re-maps pins 88 and 92 for I2C3 functionality, and then sets the configInts. Note the speed setting to 400 KHz near the end. No matter what I change that number to, the result is always the same as above.

This is not a show-stopper; the thing is working fine. I’d like to speed it up because the device interrupts the CPU every 10 msec with new data, and right now the I2C stuff actually takes up quite a lot of CPU time.

Any idea what I may be doing wrong or if this is a defect in the I2C library?

bool I2Cdev::bI2C_Init(void) //ok//
{
    DWORD   dwIRq;
    bool    bSuccess = false;
    tVersion ver;	
	BOOL result;

    // set default values
    dwI2C_Adr           = I2C_ADR;                      // I2C address of the IMU chip
    dwINT_Pin           = INT_PIN;                      // pin for Int
    dwINT_Sig_Lvl       = INT_SIG_LVL;                  // Int signal invertetd
    dwHwAdaptPrio       = HWADAPTPRIO;                  // Task priority

	uIo IntIo = COLIBRI_PIN(dwINT_Pin);

    g_hi2c =I2c_Init(L"I2C3");

	uIo i2cSclPin;
	i2cSclPin.ColibriPin.Tp = ioColibriPin;
	i2cSclPin.ColibriPin.Nr = 88;

	result = I2c_SetConfigInt(g_hi2c, L"ioScl", i2cSclPin.GenericDefinition, StoreVolatile);
	if (result == false)
	{
		DEBUGMSG(ZONE_ERROR,(TEXT("IMU driver:Failed to set config int for ioScl\r\n")));
		return false;
	}

	uIo i2cSdaPin;
	i2cSdaPin.ColibriPin.Tp = ioColibriPin;
	i2cSdaPin.ColibriPin.Nr = 92;

	result = I2c_SetConfigInt(g_hi2c, L"ioSda", i2cSdaPin.GenericDefinition, StoreVolatile);
	if (result == false)
	{
		DEBUGMSG(ZONE_ERROR,(TEXT("IMU driver:Failed to set config int for ioSda\r\n")));
		return false;
	}

    I2c_Open(g_hi2c);
    if (g_hi2c == NULL)
    {
		DEBUGMSG(ZONE_INFO,(TEXT("IMU driver: failed to open I2C handle\r\n")));
		return false;
    }

	HANDLE gpioHandle = Gpio_Init(L"SOFTWARE\\Toradex\\gpio");
	result = Gpio_SetConfigString(gpioHandle, i2cSclPin, NULL, L"altfn=6,sion=force", StoreVolatile);
	if (result == false)
	{
		DEBUGMSG(ZONE_ERROR,(TEXT("IMU driver:Failed Gpio_SetConfigString altfn=6\r\n")));
		return false;
	}

	result = Gpio_SetConfigString(gpioHandle, i2cSdaPin, NULL, L"altfn=1,sion=force", StoreVolatile);
	if (result == false)
	{
		DEBUGMSG(ZONE_ERROR,(TEXT("IMU driver:Failed Gpio_SetConfigString altfn=1\r\n")));
		return false;
	}

    I2c_SetConfigInt(g_hi2c, L"BitRateHz",        400000,  StoreVolatile);  // Set I2C speed to 400KHz
    I2c_SetConfigInt(g_hi2c, L"SlaveAddrSize",    7,       StoreVolatile);  // Set 7 bit Slave address
    I2c_SetConfigInt(g_hi2c, L"SlaveAddr",        dwI2C_Adr,   StoreVolatile);  // Set Slave address
    I2c_SetConfigInt(g_hi2c, L"RegisterAddrSize", 8,      StoreVolatile);  // 8 bit Register address to send
	//I2c_SetConfigInt(g_hi2c, L"RegisterAddrLE", 1 ,StoreVolatile);		// Little endian.

Dear @guzoo,

Thank you for contacting support. We are able to reproduce the issue, please wait for a couple of days and we will get back to you soon.

Thanks Raja. I’ll stand by for further instructions once you investigate.

Sure, I can wait for this. Please advise when you have a fix/patch ready.

Dear @guzoo,

Thank you for your patience. There was an issue in the library and that I fixed it. Please download the preliminary release and let us know if you face any issue on this.

Also, due to clock divider limitation, we may not get the exact 100KHz or 400KHz frequency from the I2c controller, nearest less than configured clock will be driving on the bus.

Thank you

Thanks for the test load. I’ll try it later today. And yes I understand the clock divider limitation. That should not be a problem, as long as I can get close to the 400 KHz bus frequency.

I tested the preliminary release and it works fine: I can now change the speed of the I2C bus.

Thanks for the fix!