MCP23017 i2C very slow

doglike
Posts: 63
Joined: Fri Aug 18, 2017 4:21 pm

MCP23017 i2C very slow

Postby doglike » Tue Apr 16, 2019 8:12 pm

Hello,

I set up my ESP32 with a MCP23017 over i2C (400kHz) and got it working quite well with Adafruit-library. Everything is working as expected.

Then I did some simple measurement to check the HIGH-LOW switch speed and it is really dissapointing.
The code below for simply switching that pin HIGH takes 8,9ms!

Why is that so slow ?
Is this caused by i2C ?
Adafruit lib ?

Is it a better choice to take the MCP23S17 with SPI ?

PS: It doesn't make any difference when I put pull-ups on the SDA/SCL lines...

Thanks!

Code: Select all

		
uint32 timestamp = micros();
mcp.digitalWrite(pin, HIGH);
Serial.println( micros() - timestamp );
Last edited by doglike on Wed Apr 17, 2019 10:54 am, edited 1 time in total.

ESP_Sprite
Posts: 9764
Joined: Thu Nov 26, 2015 4:08 am

Re: MCP23017 i2C very slow

Postby ESP_Sprite » Wed Apr 17, 2019 2:29 am

FWIW, the Adafruit library does a read-modify-write operation which needs to read the data from the chip before writing it back with the bit you want changed. You could speed everything up by caching the last-written value, but that'd only net you a factor of 2-3 improvement... I'm not sure what causes the rest of the slowdown.

doglike
Posts: 63
Joined: Fri Aug 18, 2017 4:21 pm

Re: MCP23017 i2C very slow

Postby doglike » Wed Apr 17, 2019 10:58 am

Yes, I also could figure that out.
There is another method available in the lib:
Adafruit_MCP23017::writeGPIOAB (writing all pins once)
That speeded up everything a bit, but that still takes ~3ms :(



PS: The i2C is running @400kHz of course

don01pf
Posts: 2
Joined: Sat Apr 06, 2019 4:54 pm

Re: MCP23017 i2C very slow

Postby don01pf » Thu Apr 18, 2019 7:21 am

I recently did some testing with both the I2C MCP23017 and the SPI MCP23S17, but with the esp8266 Lolin v3 board.

Reading a 8 bit port, 128*2(256 bytes) line size at 16-bits per pixel ... (SQCIF - https://en.wikipedia.org/wiki/Common_In ... ate_Format)

MCP23017 (700KHz) => 19+ ms
MCP23S17 (10MHz) => 2+ ms

Reading 128*2*96 (24576 bytes) SQCIF full 16-bit frame size
MCP23S17 (10MHz)=> approx 211+ ms

Edit: And by read port... I mean that is all it was doing in a tight loop.

doglike
Posts: 63
Joined: Fri Aug 18, 2017 4:21 pm

Re: MCP23017 i2C very slow

Postby doglike » Thu Apr 18, 2019 9:14 am

Would you generally say, that it is better to take the SPI version ?

I did another test.
Instead of printing the time to console, I connected the switched pin of MCP to a interrupt pin of the ESP and count the pulses per second.
Result is 1000 pulses (rising+falling) per second, which means that the MCP is capable to switch the pin state within 1ms after the code line was executed.
Well, this is OK for my purposes, but generally I think this is still very slow...

Code: Select all


_uint32 volatile cntr = 0;
attachInterrupt(input_pin, intr, CHANGE)

void loop()
{
   mcp.writeGPIOAB(ON_value);
   mcp.writeGPIOAB(OFF_value);
   
   // + code for:
   // + print cntr every second to console...
   // + reset cntr to 0...
}

void intr()
{
  cntr++;
}

don01pf
Posts: 2
Joined: Sat Apr 06, 2019 4:54 pm

Re: MCP23017 i2C very slow

Postby don01pf » Thu Apr 18, 2019 10:19 am

SPI version is approximately 10x quicker than I2C, but needs an extra chip select line.

Have you tried running the MCP23017 faster than 400KHz?

doglike
Posts: 63
Joined: Fri Aug 18, 2017 4:21 pm

Re: MCP23017 i2C very slow

Postby doglike » Thu Apr 18, 2019 3:13 pm

Yes, same results... (100kHz - 800kHz).
Faster then 800kHz didn't work at all, no idea way. According to the spec 1,7MHz should work.
Thanks for your support.

kissinno
Posts: 10
Joined: Tue Apr 14, 2020 11:31 am

Re: MCP23017 i2C very slow

Postby kissinno » Tue Aug 11, 2020 6:40 am

doglike wrote:
Thu Apr 18, 2019 3:13 pm
Yes, same results... (100kHz - 800kHz).
Faster then 800kHz didn't work at all, no idea way. According to the spec 1,7MHz should work.
Thanks for your support.
800khz maxi could be due to your pull-up resistors applied to SDA and SLA.

Internal ESP32 pull-up are 30...80kOhm depending on manufacturers. For fast I2C, external 5kOhm pull-up will help a lot to achieve clean I2C levels which is mandatory for realible communication.

Who is online

Users browsing this forum: No registered users and 120 guests