25 comments

[ 2.9 ms ] story [ 56.7 ms ] thread
"Used properly, the two protocols offer the same level of robustness..."

How are you measuring robustness there? Do you have some data on the prevalence of bugs related to I2C and SPI implementation/use?

By "same level of robustness" means none in this case since neither have any CRC or checksum for data integrity.
That's more up to your application layer to define. Everything has a cost so forcing a CRC in the transport layer might not be good for things that need to be fast and don't care about potential errors. If you need reliable transmission you can do CRCs or other error correcting checks in your application.
For delivery of something like IR remote input a CRC isn't really necessary, but for more complex peripherals I found delivery receipt was useful.
In practice, personally I prefer SPI due to the tendency of cheap I2C devices to lock up the bus and not respond to the semi-standard reset protocol. This necessitates hacky workarounds to power-cycle the device via a GPIO for example. SPI is more robust in this sense due to the devices reliance on a falling edge of CS to clock data in rather than have a truly shared bus as in I2C. Performance-wise also, SPI can be orders of magnitude quicker than I2C.
I2C clock-stretching is also a weird thing to have to have to engineer around.
It's handy when you have truly cheapo component with a software I2C stack that can't actually keep up in some cases. No problem, just hang that bus!
I'm not seeing an apples:apples comparison even makes sense, having worked with both of these protocols on and off for a 10+ years.

SPI is a fast one-way media bus that might use master, slave, or synthetic clocking, I2C is a slower master-clocked bus. The similarities don't even stop there.

SPI is bidirectional as is I2C. They both get used for similar applications, though SPI more often for anything needing a modicum of performance. Microwire or 1-wire should also be brought into the discussion to make it more complete.
There's now Ultra-Fast Mode for I2C that acts a lot like SPI for high-speed 1-way clocking at 5MHz. Mostly for large LED arrays and the like.
Two overlays that cannot be closed by ESC. Nice article, but this just sucks.
holy crap no kidding.
Yep, I left after the second popped up. There's enough info about I2C and SPI around that I'm not going to tolerate the annoyance.
One nice thing you can do with SPI is to daisy chain the chips your interfacing with so that the MOSI of chip A goes into the MISO of chip B and so on. If you've got got a bunch of, e.g., ADCs you want to poll at the same time you can just get the output from all of them at once without needing extra select lines.
Please note that is not a universal properties of SPI devices. Only some can be daisy chained. E.g. the first google-hit I get for an "SPI ADC" is the MCP3004 that doesn't daisy-chain.
I've seen a lot more hardware problems involving i2c than involving spi. If an i2c device fails its a pain because it is not apparent which chip on the bus failed. If I do have to use an i2c device I try to avoid having more than one on the same i2c bus. Spi might require more tracks but tracks are cheap and hardware problems are expensive.
Very true. I2C devices are prone to locking the bus. Its a failure mode that SPI does not suffer from due to its use of chip-select (and hence is completely controlled from the master). This is a real drawback in creating reliable systems using I2C.
Terminator resistors! although it's not rocket science they can be quite PITA to figure our during development phase when you are testing different i2c components with different impedances
I2C peripherals in microcontrollers tend to be finnicky as well, because the interpretation of certain events depends on the device and so the interface between the hardware and sofware winds up very complex (and prone to error, I've had to reset an I2C peripheral at the start of each transaction in order to get it to work properly).
Sometimes it's easier just to periodically reset I2C slave devices from the bus master (either with a dedicated reset line or just power-cycling the chip using a FET)
If you just power down by running the i2c slave power through a FET, either the i2c-slave might pull down the i2c lines in an uncontrolled fashion.. or the i2c-slave might still be powered through the i2c SDA/SCL pullups.

So if you really want to decouple a i2c slave for the purpose of resetting it, also run the i2c lines through a CMOS switch, which of course will complicate this even further. Then better don't use the buggy i2c device at all.

Good article. There was a recent kickstarter for something called 'i2c and spi education shield' with some great tutorials and hw also..
If you plan to spend a lot of time down low working with these protocols, definitely get a Saleae Logic. I can't recommend it enough:

https://www.saleae.com/

It's a small USB-powered digital logic analyzer in various sizes with the buffer size limited only by your host computer's memory. The real magic is their software - it gives you protocol analysis capabilities that used to cost you thousands if you were an HP/Agilent/Tek customer. You get I2C, SPI, RS232/485, DMX, 1Wire, CEC, USB, tons more. Best part? The host software also runs on Mac and Linux.

And if you are interested, support these guys and buy the real thing. Don't buy a knockoff and then use Saleae's software (which they give away for free to let you try).

I bought a bus pirate and after dealing with all its problems I'd have paid twice as much for something like the Saleae. Never again
Their products are really neat, I second your recommendation. Very handy for what they do. At work I have the legacy 8-bit-wide and the faster 16-bit-wide devices, and they've paid for themselves tenfold.

And their software indeed is very shiny, even though the latest version I got (1.1.20, 64bit, Linux) starts up but then completely hangs on my machine :-(. 1.1.15 is fine, on the other hand.

Add: Just tried the latest beta (Logic 1.1.34), it's working ok again.