From the moment I got my Netduino microprocessor board I was thinking, what are it's limitations, and how can I work around them? One of the most obvious limitations is the amount of Input/Output (I/O) ports. This image shows what the board is capable of.
I wanted to look a way around this limitation with quite some success. By adding multiple bitshift IC's it's possible to get virtually unlimited I/O-ports. The only limitation in this is the clock speed, but I haven't reached this limitation yet.
I've used two kinds of IC's, a serial-in/parallel-out, called 74HC595, and a parallel-in/serial-out, called 74HC165. They can be used in chains, so by adding more IC's, you won't need to use more I/O ports on the Netduino board. In my example below I got 32 I/O ports by only occupying 5 I/O's on the netduino.
The schematic is quite simple, I used buttons with pull-up resistor to represent of inputs and leds to represent outputs. The basic idea is that every added IC adds 8 Input or Output ports.
You can see it working at Youtube.
Then we get at the code part. Connecting stuff is one thing, making it work is another. The Netduino is filled with code compiled from C# and uses the .NET MicroFramework.
This framework has a couple of built-in classes, for example, OutputPort, InputPort and InterruptPort. I made copies of those built-in classes to work with the bitshift IC's, so usage would be a simple as the rest of the framework.
The only difference is that we need to define the IC setup first. So we got two input IC's and two output IC's. We define the connected chains first:
Ic74HC165Chain ChainIn = new Ic74HC165Chain(SPI_Devices.SPI1, Pins.GPIO_PIN_D10, 2); Ic74HC595Chain ChainOut = new Ic74HC595Chain(SPI_Devices.SPI1, Pins.GPIO_PIN_D9, 2);Both IC chains are connected to the Netduino's SPI bus (Pins 11 to 13) and use a different Chip Select-pin, in this example pins 9 and 10. Both chains contain 2 IC's.
When the chains are defined, we have to make interfaces for the IC's. This is done by this:
Ic74HC165 IcIn1 = new Ic74HC165(ChainIn, 0); Ic74HC165 IcIn2 = new Ic74HC165(ChainIn, 1); Ic74HC595 IcOut1 = new Ic74HC595(ChainOut, 0); Ic74HC595 IcOut2 = new Ic74HC595(ChainOut, 1);The enumeration starts at 0 as you can see. 0 is the first IC in the chain, 1 the second, 2 the third, etcetera.
Now we can define our Input/Output/InterruptPort classes. They have the same parameters as the regular classes except for the first one, which defines the IC it's connected to:
InterruptPortShift Button0 = new InterruptPortShift(IcIn1, Ic74HC165.Pins.GPI_PIN_D0, false, Port.ResistorMode.Disabled, Port.InterruptMode.InterruptEdgeBoth); OutputPortShift Led0 = new OutputPortShift(IcOut1, Ic74HC595.Pins.GPO_PIN_D0, false);Here we defined an InterruptPort and OutputPort using bitshift registers. From this part, the code which follows is exactly the same as it would be using the onboard I/O ports.
I wouldn't have done this without the help of two very nice guys in the Netduino Community: Mario Vernari and CW2. Thanks again
The schematics are made with the free tool Fritzing. Should also be mentioned since the tool is a great help!
Download source at http://netmftoolbox.codeplex.com/
Edited by Stefan, 13 September 2011 - 04:37 PM.
Updated download link