Going both ways with I2C

I'm planning a project and it looks like it will involve multiple Arduino: likely one Mega and 3 or 4 Uno. I2C looks a reasonable way to bus them. Each will have to send and receive messages/requests. My reading of the reference material on Wire library is that this is doable using onRequest() and onReceive(). Did I understand this right? Asking before experimenting because I will have to develop a different approach if this will not work.

My reading of the reference material on Wire library is that this is doable using onRequest() and onReceive(). Did I understand this right?

Yes, it is right. The role of master and slave can change to. It really depends on which device makes the request.

What is the project that will require so many Arduinos? How far apart will the Arduinos be? I2C is designed for devices close together.

It really depends on which device makes the request.

It does but if any device can make a request then you have to worry about collisions and collision detection / retry.
It is better to have just one master and have it request data from the other devices.
While a multi master system is possible, and I have implemented many in my time, they always prove to be problematic.

Thanks for the hint about distance: everything will be within about 30cm radius. Total bus length less than 60cms (I hope). Since you ask I'm building a control system for a model train set. The I2C bus would have (possibly)

3 train controllers, each with a 2x16 LCD display, keypad, switch and rheostat

1 layout controller with a 4x40 LCD display and about 30 switches, controlling 16 servos and a bunch of relays with a 128Kbyte EEPROM containing configuration details, readable by the train controllers and the layout controller

and possibly 1 DCC bus controller, assuming it is easier to keep it apart from the rest of the stuff.

It might be possible to load all this into the Mega, but for implementation, separating them would be easier, provided the I2C bus is up to it. Data rates would be small.

Just try the multimaster I2C. Works fine for me (at this moment). Does anyone know if the protocol works well when 2 Arduinos need to send data at the same time? Do they both send their data and everything crashes or do they wait and send one after the other? http://digitalcave.ca/resources/avr/arduino-i2c.jsp

Do they both send their data and everything crashes or do they wait and send one after the other?

The way multi master systems work is 1) Before sending the master checks to see if there is any bus activity. If there is it backs off for a random time. 2) It sends the data and checks for a collision. If there has been it backs off for a random time. The major problem I have encountered is that certain levels of noise are seen as bus activity but can lead to latch up of the bus. This happens very infrequently but is a bugger to find.

hamiljf: Thanks for the hint about distance: everything will be within about 30cm radius. Total bus length less than 60cms (I hope). Since you ask I'm building a control system for a model train set. The I2C bus would have (possibly)

3 train controllers, each with a 2x16 LCD display, keypad, switch and rheostat

1 layout controller with a 4x40 LCD display and about 30 switches, controlling 16 servos and a bunch of relays with a 128Kbyte EEPROM containing configuration details, readable by the train controllers and the layout controller

and possibly 1 DCC bus controller, assuming it is easier to keep it apart from the rest of the stuff.

It might be possible to load all this into the Mega, but for implementation, separating them would be easier, provided the I2C bus is up to it. Data rates would be small.

You seem to need more gpio, pwm and analog in ports you can get chips for all of those functions and control them from a single arduino. Depending on what you need more advanced i2c chips can be used for things like the lcd's that can make things a lot easier. A model train set should not push the cpu power of a single arduino.

Grumpy_Mike:

Do they both send their data and everything crashes or do they wait and send one after the other?

The way multi master systems work is 1) Before sending the master checks to see if there is any bus activity. If there is it backs off for a random time. 2) It sends the data and checks for a collision. If there has been it backs off for a random time. The major problem I have encountered is that certain levels of noise are seen as bus activity but can lead to latch up of the bus. This happens very infrequently but is a bugger to find.

Sounds Great, so is it possible to use the wire lib for the true Multimaster mode? Im using it in this way http://digitalcave.ca/resources/avr/arduino-i2c.jsp I heard that the wire Library isnt able to use the Multimaster mode of the Atmel.