Due to increasing numbers of interesting infrastructure projects, and how annoying (i.e. impossible) Ethernet is to implement on a small microcontroller without extra hardware, we've decided to implement a hackerspace-wide low-speed bus system. This will allow devices to communicate, opening up many interesting project interactions (hook up the air hockey score board to the sound system or what have you), as well as your run-of-the-mill domotics stuff (controlling the lights in a semi-intelligent manner, for example). This page serves to coordinate and document the design (and later, implementation) of this system.
We have completed a first iteration of the link-level protocol (named SBLP) design, and intend to use OpenCTRL as the logical-layer protocol. Currently, we are prototyping hardware and implementing a portable C library along with a few platform-dependent drivers.
Current work involves:
- Writing of a clean, modular protocol stack for devices. smeding and gmc have started work on the generic SBLP library and an ATTiny85 implementation.
- Developing, building and testing reference hardware
Once a fully working reference implementation has been developed, up to (at least) the SBLP layer, we can begin to wire the space and develop more actual bus hardware.
The first meeting/brainstorming session was scheduled for the evening of Friday, July 15th 2011.
What was done:
- Everyone formally agreed on the electrical spec, which had already been discussed extensively. For wiring, cat5 & 8p8c were chosen with a pin-out supporting data, power and return for T-junctions (see specification)
- A first draft of the link-layer protocol was thought out, though this has since been revised (see the specification linked above for the current draft)
- A whiteboard simulation of above protocol was done to check for any obvious errors.
- The line drivers gmc ordered were tested (and found to be working adequately) and some rough tests were done to gauge possible transmission speeds. Limits imposed by the electrical layer were found to probably be unattainable in a microcontroller anyway.
This was a small hackathon to make a push towards a functional system.
- Transmission now works up to the SBLP level
- Reception has stopped working and will need to be debugged in more detail.
These are the general things we're looking for in the protocol:
- Robustness - e.g. powering on a welder in the space should at most cause a transient disturbance of the bus
- Simplicity: implementation should run on an AVR family microcontroller with a minimum of external parts
- Low cost: aforementioned external parts shouldn't cost more than the rest of the project to be connected to the bus, in general
- Possibility for many different underlying networks: its own dedicated electrical bus, Ethernet, wireless, etc. with bridges between them.
- Many-to-many operation: No real master/slave distinction except possibly some simple hardware to keep the bus sane electrically... communications should be possible from any device to any device directly, as well as "event"-type broadcast messages.
To demonstrate the viability of the bus design and provide a starting point for other projects, it seems like a good idea to develop a reference implementation of several bus devices. This also helps for showing what bugs may exist in the design itself, and what additional features are desirable. I think the reference implementation should consist of:
- A device demonstrating event functionality: this could be something like a spacebus-enabled space-is-open switch
- A device demonstrating analog/digital in/outputs and possibly another device to read them out, e.g. a sensor and/or relay board
- A bridge between the space bus and rs-232 or usb so a computer can be connected and possibly export the bus over tcp/ip
Bridging and adressing
One question to ponder upon is whether the logical layer needs an adressing scheme seperate from the link-layer adressing scheme. Note that 'link-layer' is kind of a vague target here: udp could be used as the link-layer protocol on top of which the logical-layer protocol sits.
Imagine a bridge between a rs485 bus and an ethernet with IP. The bridge would need to know what devices are on the rs485 bus, but also what devices are on the ethernet bus.
The logical addresses provide a uniform adress space for devices on any kind of bus. I'm just brainstorming here, but suppose you take a 16-bit field as the logical address. You can then split this up like so:
- bit 15-12 : network
- bit 11-0 : device
Which would give you 4 bits = 16 possible networks, and 12 bits to address individual devices on the bus (of course, you can play with the exact split point, or even introduce further distinctions).
A simple avr will be able to send simple packets with logical addresses over the rs485 bus. A bridge on the rs485 network can read the packets, see that it is actually destined for a device on another network and will forward the packet. If it is another rs485 bus, nothing special will need to be done. Yet, if it needs to go over ethernet, it will have to get the logical packet out of the link-level frame, and repack it in another link-level frame (eg udp).
You could take the logical address 0xffff to mean 'broadcast', and this would then be forwarded to all busses (mind the loops!).
First experiment: sending 1-0-1-0-1-0 continuously we went up to 1mbit/sec.
- add 9th bit, alternating between 0 and 1 each byte? enables line-idle detection ??
- prioritizing traffic -> fairness/starvation prevention in arbiters