What sucks the most about I2C for me is the fact that the bus can get stuck if the master device resets during a transmission. In which case the slave device will keep the SDA line busy while waiting indefinitely for clock pulses. Yes, you can probably send dummy clock pulses to finish the frame and get SDA released, but that's just a pain to code properly.
SPI is so much more reliable with just two extra pins, I usually don't even consider I2C anymore.
Yeah that's pretty disappointing. Gotta implement a "bus clear" feature in any system that relies on I2C working consistently.
Slave devices that rely on clock stretching are a total pain in the ass, as well. Tend not to play nice with other normal devices.
https://www.i2c-bus.org/clock-stretching/
The main thing I use I2C for in recent designs is multiple channels of power monitoring, e.g. using the INA226. I agree that SPI is preferable for sensors that support it.
And I'm currently working with the INA229, its SPI cousin I guess :) Those chips are really nice, I'm trying to use the alert feature as a configurable overcurrent trip protection, as well as overvoltage device protection.
SPI requires 3 wires plus a Chip Select for each device on the bus. That 30 device network under discussion suddenly needs 33 pins. That's more pins than any processor I've used in the last couple of years.
I mean I guess we could use an i2c GPIO expander to get extra lines. I bet that would be "fun" to get right.
Many MCUs also don't handle SPI well (via DMA) or have bugs in peripherals. So the only viable way is bit banging and that is difficult to make faster than I2C.
I am considering implementing SPI on FPGA to connect with devices and then transmit to/from MCU using "SPI" dialect that works with that MCU.
What kind of issues have you found with SPI peripherals? I've rarely found issues with SPI, certainly it's a peripheral which is far less buggy on average than I2C, where there are some absolutely awful implementations.
You can use a demultiplexer to turn e.g. 4 pins into 16 chip select. But the fact that the number of wires has to grow at all to accomodate additional devices is certainly a big downside compared to I2C, and for wired networks that basically makes it impossible to daisy chain devices.
If you had 30 SPI devices, you'd probably use a small FPGA to address them all (produce all the chip selects as needed). Basically, write an integer (e.g. 5 bits would do for 30 selects) and a strobe and you're good to go. No address conflicts, ever. And very fast.
This can be detected and usually just mux scl to a gpio and cycle until the bus is recovered. The real issue is if a device decides to hold scl low forever. At which point it's recommended to power cycle devices on the bus until it recovers.
SPI is however not useable as a bus. You need a specific chip select pin line for every chip you communicate with. But yes I like SPI much better as well.
SPI is so much more reliable with just two extra pins, I usually don't even consider I2C anymore.