# Micro-controller project



## ullbergm (Apr 19, 2010)

I've been lurking on here for a long time now so i figured it's about time to post something 

I have started working on a micro-controller project to manage/monitor my newest tank, a Fluval Edge.

Architecture
The idea is to have a modular system so that it can be "easily" modified and extended when i want to add functionality.

Controller
Atmel AVR running atomthreads, prototyping using ATMEGA1284p
RTC will be handled using a DS1307
RS-485 IC to talk to sensors and other peripherals
RS-232/USB/Bluetooth etc for status updates and to transfer logs to the computer
LCD and a joystick will be the interface at the tank.
Maybe a piezo electric speaker for audible feedback (over temp alarm, etc.)

Sensor
Atmel AVR, probably some flavor of ATtiny, all it needs to do is take commands over the RS-485 bus, collect sensor data and reply to the controller when queried.
Sensor, probably just using the ADC to get readings
RS-485 IC to talk to the controller

Actor
Atmel AVR, probably some flavor of ATtiny, all it needs to do is take commands over the RS-485 bus, trigger relays/change lighting/etc. and reply to the controller when queried.
RS-485 IC to talk to the controller

Scheduling
As for the scheduling i'm starting out with the same schedule for each day of the week, later on i may add a real schedule or at least for each day of the week to have its own list of actions where the actions are things like:
Turn CO2 relay on
Fade lighting to a specified RGB value over a specified time
etc.

Current status
FreeRTOS has been replaced with atomthreads and is running fine. The serial i/o is working fine, the LCD is also up and running with a menu system.


----------



## ullbergm (Apr 19, 2010)

*Change Log*
_2010-07-19_


> Wow, been a while since i updated this. Whoops.
> 
> I've made some progress finally, my atmega1284p and other misc. junk came in and i got my prototype done up on a prototype board.


_2010-05-10_


> Not a whole lot of progress, added some to the programming interface and are tossing some ideas around as far as overall system design.


_2010-05-05_


> Command parsing extended, see post #20 for an example of what i'm thinking the scheduling interface may look like.


_2010-05-04_


> Command parsing implemented, see post #19


_2010-04-28_


> Finally figured out the serial input stuff.
> Working on the serial user interface, probably going to model it after a certain router manufacturer's interface.


_2010-04-27_


> FreeRTOS v6.0.4 running on the ATMega2560
> Still can't get serial input working, posted on avrfreaks to see if anyone has seen this before.


_2010-04-19_


> FreeRTOS v6.0.4 running.
> Serial output working, input it not working for some reason.


----------



## TeamTeal (Mar 31, 2010)

sound like a great project
very interested to see how this turns out


----------



## northey87 (May 24, 2009)

Sounds fun, I would be interested in the cost comparision of this compared to a RKE or other preassembled units.


----------



## ullbergm (Apr 19, 2010)

TeamTeal said:


> sound like a great project
> very interested to see how this turns out


I have a history of not completing projects that i start so hopefully by posting my progress i'll actually finish this one


----------



## ullbergm (Apr 19, 2010)

northey87 said:


> Sounds fun, I would be interested in the cost comparision of this compared to a RKE or other preassembled units.


Not sure if it will be cost effective or not, i'm trying to build it in a modular way so that each piece is self-contained but that will bump the cost up some. Only time will tell.

Hopefully i'll have some fun doing it and get something that does everything i want it to do


----------



## pmd5700 (Oct 27, 2007)

I'll be interested in seeing how this turns out as well. I've always wanted to do something like this.


----------



## ullbergm (Apr 19, 2010)

pmd5700 said:


> I'll be interested in seeing how this turns out as well. I've always wanted to do something like this.


I know of two other similar projects here on the forum:
RobotGuy
http://www.plantedtank.net/forums/t...puter-controlled-nano-electronics-3-14-a.html

and

Mistergreen
http://www.plantedtank.net/forums/diy/102267-dimmable-led-component.html#post1009586

Be sure to check those out if you haven't already :smile:


----------



## ullbergm (Apr 19, 2010)

Currently working on running both FreeRTOS and FreeModbus for communication, looks like i'm going to have to upgrade to a chip with two 16-bit timers. I'll probably go with the biggest chip that is available in a DIP package so that i'm not hitting any walls while building this, i can always port it to something smaller in the end.

I have a atmega2560 that i'm using now but it is not available in a dip package so i'll probably pick up a atmega128 when it is available.

http://search.digikey.com/scripts/DkSearch/dksus.dll?Detail&name=ATMEGA1284P-PU-ND


----------



## insta (Jan 27, 2010)

Let me know if you need anything for lighting controllers. PWM is my specialty


----------



## mistergreen (Dec 9, 2006)

post pictures!


----------



## ullbergm (Apr 19, 2010)

Not much to take pictures of yet.... :icon_smil

I think I've decided to go with the ATmega1280, once it becomes available. Some of the reasons are that it has 4 timers, multiple USARTs and one of the timers is tweaked to be a real time clock (RTC).

I'm ordering a 32.768KHz crystal for the RTC and various ATmegas / ATtinys for whatever i might need them for.  The ATtinys are more than likely what will drive the peripherals, whatever the smallest chip that i can get freemodbus running on.

Yes, i'm being lazy and 'outsourcing' as much as i can, RTOS, bus protocol, LED drivers, etc. Or at least that is the current plan since i can get some free sample ICs from the different manufacturers and they are pretty cheap (most of them are less than $1).

The current task I'm working on is getting FreeRTOS running on the ATmega2560, which is basically the same chip as the ATmega1280 but with more flash. The unfortunate thing is that the 2560 has more than the 128k flash that FreeRTOS / GCC can address so some changes has to be made to FreeRTOS to get it to work. Luckily someone has already done the work, i just need to integrate their work into my toolchain.
http://www.avrfreaks.net/index.php?name=PNphpBB2&file=viewtopic&t=70387

After FreeRTOS and Freemodbus is working i'll be working on some of the other framework pieces, the scheduling framework, specs for the communication between components, etc.
The reason i've postponed adding more components and moving the chip to a prototype board is that in the end i plan on using the 1280 but it wont be available for a couple of months. 
The silver lining is that i can get some of the mundane pieces done before i get the more fun and flashy stuff going, ie. less chance that i stop working on the project. (once you get the flashy stuff going you feel like you have overcome the hurdle and feel like moving on to new challenges. or atleast that is what i usually do...)


----------



## Joefish4jc (Mar 18, 2010)

Just as an FYI. You can order free sample parts from digikey, microchip, national instruments. They dont mind giving away a couple of pieces here and there, because if you invent something with their parts youre more likely to mass produce it with their parts. All you have to do is register on their websites prior to ordering.

I find that one of the most powerful and easiest to program chips is the PIC-18f4321. It has a decent amount of memory its got an adjustable internal clock, 32kHz secondary timer, high/low priority interrupt settings, decent flash space availalbe, 10 bit Analog/digital converter, fast serial connection, watchdog timer to help not waste power or get it stuck in long processes, and a great operating voltage range, and I cant remember if the I2C and serial use the same I/O pins or not.... I used the PIC18f4321 to control a self balancing robot. 

Ive wanted to do this for some time as well....Ive been looking for so decent peripheral sensors for cheap but Im not seeing too many out there.

So let us know how it comes out!


----------



## ullbergm (Apr 19, 2010)

Joefish4jc said:


> Just as an FYI. You can order free sample parts from digikey, microchip, national instruments. They dont mind giving away a couple of pieces here and there, because if you invent something with their parts youre more likely to mass produce it with their parts. All you have to do is register on their websites prior to ordering.


Hehe, yeah, i've had packages trickle in for the last couple of weeks from the different companies 



Joefish4jc said:


> I find that one of the most powerful and easiest to program chips is the PIC-18f4321. It has a decent amount of memory its got an adjustable internal clock, 32kHz secondary timer, high/low priority interrupt settings, decent flash space availalbe, 10 bit Analog/digital converter, fast serial connection, watchdog timer to help not waste power or get it stuck in long processes, and a great operating voltage range, and I cant remember if the I2C and serial use the same I/O pins or not.... I used the PIC18f4321 to control a self balancing robot.


I'm probably going to go with the ATmega128, i'm used to the AVR platform and i have the development tools for it. In the end they are all about the same. It's funny how people go on holy-wars defending their platform of choice, i dont really care its just what i'm used to. 

Flash (Kbytes): 128
EEPROM (Bytes): 4096
SRAM (Bytes): 8192
Max I/O Pins: 86
F.max (MHz): 16
Vcc (V): 1.8-5.5
10-bit A/D Channels: 16
Analog Comparator: Yes
16-bit Timers: 4
8-bit Timer: 2
Brown Out Detector: Yes
Ext Interrupts: 32
Hardware Multiplier: Yes
Interrupts: 57
ISP: Yes
On Chip Oscillator: Yes
PWM Channels: 16
RTC: Yes
Self Program Memory: Yes
SPI: 1+USART
TWI: Yes
UART: 4
Watchdog: Yes



Joefish4jc said:


> Ive wanted to do this for some time as well....Ive been looking for so decent peripheral sensors for cheap but Im not seeing too many out there.
> 
> So let us know how it comes out!


----------



## Joefish4jc (Mar 18, 2010)

Yeah Ive been a defender of the microchip products since Ive taken a couple of classes at GaTech. Its their holy grail next to the Arduino (which I think is powerful but the programming interface confuses the be-jesus out of me). 

My idea for senior design a few years ago was a fully automated tank, but my team shot me down.

I wanted it to include:
daytime/nightime light simulation with the lunar phases programmed in (use an LED array across the whole hood)
temperature control
co2 controller
Auto dosing
pH monitor (via sensor, also any other water parameter you can monitor via sensor)
possibly a pushbutton chemical tester (a machine to extract tank water and add the testing chemicals automatically)
web cam monitoring of the tank/ live feed of parameters
remote/web control capabilities
and auto feeder (not just flakes, but algea wafers too for my pleco)


----------



## ullbergm (Apr 19, 2010)

Joefish4jc said:


> Yeah Ive been a defender of the microchip products since Ive taken a couple of classes at GaTech. Its their holy grail next to the Arduino (which I think is powerful but the programming interface confuses the be-jesus out of me).
> 
> My idea for senior design a few years ago was a fully automated tank, but my team shot me down.
> 
> ...


Same things that i want to do, basically control everything about the aquarium as well as detailed monitoring/graphing.

I'd like to have multiple temperature sensors and use the average to control the heaters, not just the water around the heater it self. Also i think it would be interesting to have inlet temperature vs outlet temperature if you have a inline heater.

The sky is the limit


----------



## ullbergm (Apr 19, 2010)

Still fighting with the dumb serial stuff, output works great, input not so much.


----------



## ullbergm (Apr 19, 2010)

finally got the input working as well, working on the serial interface now.

i've got it to where i can prompt the user for input and they can type a answer and even use backspace, etc. to edit their input.

working on the menu / command syntax now.


----------



## ullbergm (Apr 19, 2010)

Made some more progress, starting to parse commands now:


```
[*] Aquarium Brain Initializing

[*] Version: 1.0

[?]: show ver
Version 1.0                                                                     
[?]:
```


----------



## ullbergm (Apr 19, 2010)

Sorry for the non-aquarium updates, but i think documenting my work will help me keep motivated to actually finish this thing... 

Still working on the configuration interface, here is the current idea as far as configuring the schedule.

Each entry in the schedule has a line number, that way i can do things like "schedule delete 104" to remove a entry from the schedule.

Each entry also has a time, a module and a command to send to that module. For now i'm not going to worry about the weekday, i'm just going to have the same schedule every day. 


```
[*] Aquarium Brain Initializing                                                 
[*] Version: 1.0                                                                
                                                                                
[?]: show version                                                               
Aquarium Brain Version 1.0                                                      
                                                                                
[?]: show schedule                                                              
Line            Time            Module          Command                         
----            ----            ------          -------                         
 100            07:00           Lights          RGB|300|255255255                   
 101            07:00           CO2             ON                              
 102            09:00           FEED            1                               
 103            19:00           FEED            1                               
 104            22:00           CO2             OFF                             
 105            22:30           Lights          RGB|300|000000000  

[?]:
```
In this example the lights would fade to bright white over the course of 5 minutes starting at 7am, and the CO2 would also be turned on at the same time.
At 9am and 7pm the feeder would dump food in to the aquarium.
At 11pm the CO2 would turn off
And at 11.30pm the lights would start to fade to black and be completely out 300 seconds (5 minutes) later.

This is obviously subject to change :icon_smil


----------



## jnunn (May 8, 2010)

I presently use an Allen-Bradley Pico controller on two of my tanks. This is a small industrial relay logic controller. It controls the lights in two stages a morning level and an afternoon level with an over lap at noon time, the moon lights, Pumps and heater. An auto water change is also programmed along with a feeding cycle (stops the pumps for 30 minutes. Programming is built in to the device but you can also program the unit via a laptop but a special cable is required. The RLC can be found on EBay for under $100.

I have heard that the Pico will be discontinued in the next few months and replaced by a true micro Program Logic Controller (PLC) that has analog inputs, relay outputs, built in RS485/RTU communications (mod bus) and Ethernet IP (industrial protocol). The programming software is built in the PLC and accessed via Ethernet with an Ethernet crossover cable or through a standard switch. I’m hearing that the cost will be in the range of $60 to $70 for smallest PLC which would handle anything we would need to do.
Free tool kits should be available with sample code for communications and control systems

PLC’s are a different breed from the typical dedicated processor, their programming is compiled in to native machine code so very little Ram is required and the processors do not need to run at high speed to get fast clock cycles. It is normal for an industrial PLC to operate continuously for 10 years. I am aware of a couple of Allen-Bradley PLC’s that have been operating for around 24 years with out stopping. The Pico I presently use has been in operation for about 6 years.

To answer an unasked question No I do not work for Allen-Bradley but I do work in relm of Industrial Automation. 

Jim


----------



## mistergreen (Dec 9, 2006)

What is your interface?
it's neat that you can query the programming like that. Can you set values to the chip through the interface as well?

I built my own interface using java using buttons to trigger events through serial.

I found an interesting bug with my fading RGB lights. On random occasions there are current surges which normally happens. That would reset my light value to some random value so on occasion in the middle of the night, my lights would turn on and wake me up!
I'll have to find a better/more expensive power supply to see if that would correct the issue.


----------



## ullbergm (Apr 19, 2010)

mistergreen said:


> What is your interface?
> it's neat that you can query the programming like that. Can you set values to the chip through the interface as well?


That's the plan, right now it's just a serial port interface because its easy but i have a stack of different LCD displays that will be other potential interfaces to the thing.

In the end i think there will be a serial (potentially upgrade to USB if i go crazy) interface to do the configuration and a LCD + joystick type interface at the tank it self.

The serial interface is also easy to use as a debug logging interface since the different threads in the application can push information to it and i can just look at it using a terminal connection.

As far as setting values i'll store all the config in the eeprom as a long string (can you see that i'm imitating a cisco router yet? ) so that i can modify it in a text editor and copy/paste it to the device if i want.



mistergreen said:


> I built my own interface using java using buttons to trigger events through serial.


Cool, i'm thinking about something similar but i've always wanted to play with doing an actual USB device instead of a serial connection so i may end up there one day.



mistergreen said:


> I found an interesting bug with my fading RGB lights. On random occasions there are current surges which normally happens. That would reset my light value to some random value so on occasion in the middle of the night, my lights would turn on and wake me up!
> 
> I'll have to find a better/more expensive power supply to see if that would correct the issue.


Interesting... Thanks for the hint, i'm thinking that since i'm going to have a small uC on each of my slave devices i could use one with a small eeprom and store the current config on it whenever it receives a command from the brain. That way it could also check its value in memory against the eeprom every so often to make sure it is still doing what the last command said to do.

As far as progress i haven't made much as lately as i got sidetracked with another uC project but i did make a few minor decisions as far as the command line interface is concerned.


```
[*] Aquarium Brain Initializing

[*] Version: 1.0

[?]: show version
Aquarium Brain Version 1.0

[?]: show modules                                                               
Module  Type            Version                 Notes                           
------  ----            -------                 -----                           
L21     Lights          RGB LED                 General lighting                
L33     Lights          RGB LED                 Moonlights                      
R04     Relay           110v relay              CO2 relay                       
S52     Stepper         Stepper control         Feeder                          
                                                                                
[?]: show schedule                                                              
Line    Time    Module  Command                                                 
----    ----    ------  -------                                                 
 100    07:00   L21     RGB|300|255255255                                       
 101    07:00   L33     RGB|300|000000000                                       
 102    07:00   R04     ON                                                      
 103    09:00   S52     1                                                       
 104    19:00   S52     1                                                       
 105    22:00   R04     OFF                                                     
 106    22:30   L21     RGB|300|000000000                                       
 107    22:30   L33     RGB|300|000000128                                       
                                                                                
[?]:
```
Basically i added a 'show modules' command and made the schedule reference module ID's.

the new 'Stepper' module is meant to be a feeder that dumps X number of portions (in the example above it would deposit one dose at 9am and another at 7pm.


----------



## ullbergm (Apr 19, 2010)

jnunn said:


> I presently use an Allen-Bradley Pico controller on two of my tanks. This is a small industrial relay logic controller. It controls the lights in two stages a morning level and an afternoon level with an over lap at noon time, the moon lights, Pumps and heater. An auto water change is also programmed along with a feeding cycle (stops the pumps for 30 minutes. Programming is built in to the device but you can also program the unit via a laptop but a special cable is required. The RLC can be found on EBay for under $100.
> 
> I have heard that the Pico will be discontinued in the next few months and replaced by a true micro Program Logic Controller (PLC) that has analog inputs, relay outputs, built in RS485/RTU communications (mod bus) and Ethernet IP (industrial protocol). The programming software is built in the PLC and accessed via Ethernet with an Ethernet crossover cable or through a standard switch. I’m hearing that the cost will be in the range of $60 to $70 for smallest PLC which would handle anything we would need to do.
> Free tool kits should be available with sample code for communications and control systems
> ...


Interesting device, $60 is definitely very reasonable for a uC with a display, box, etc.
The uC's themselves are pretty cheap (i think the one i'm using is less than $15 but that is the very top end of the atmel 8-bit chips and i'm only using it in the case because i'm lazy :icon_smil, most of what i normally use run less than $2 per chip) but its the packaging around it that runs the bill up.

Even thou I'm doing this for fun, i'm still going to have to keep an eye on those devices as it would definately be up and running faster than writing my own thing


----------



## trag (Apr 27, 2010)

Have you considered using I2C (or IIC) for your communications from your main controller to your sensors and servors/drivers?

I started designing a tank controller a few weeks ago, started by reviewing what other folks were doing and decided that I didn't so much want to design an entire controller, as I'd like to design a controller to peripheral interface and a nice LED driver/peripheral.

I too like the idea of putting an ATtiny25 on each peripheral. The ATtiny25 (for those who don't know) is an 8 pin micro controller from Atmel which costs about $1.10 each if you buy 100 or more. It has six I/O pins.

So, for example, on an LED driver, the ATtiny25 could use two pins for the I2C interface (USI is built-in) to the main controller. One pin as a PWM control of the LED brightness. Another pin as a PWM - through low pass filter, to control the analog current adjustment on the LED driver. And a fifth pin as an analog to digital input from a potentiometer. The sixth pin could be used as an Enable pin if the LED driver has a separate enable pin from its PWM and analog brightness controls.

The ATtiny25 can then be programmed to either take all its settings from the main controller, or, on power up, to sample the potentiometer and adjust the analog brightness control accordingly. There should also be an EEPROM flag for whether to enable the driver at power-up or leave it off until a command is received from the tank controller. 

Additionally, the ATtiny25 has a temperature sensor built in to its ADC block. So without sacrificing any pins, it can be used as a temperature sensor. This can be handy if one wants to track the temperature of the LED equipment. Presumably, one could also pot one in resin or some such and use it as a tank temperature sensor although I think Maxim or Dallas Semi makes a purpose build I2C temperature sensor.

The I2C protocol is basically a byte of ID followed by as many words as the Master cares to send. The first byte may also have a read/write bit in it, but depending on the implementation in the micros one is using, that extra bit can be used as an ID bit instead. So one gets either 127 addresses or 255 addresses to peripherals.

If by some bizarre chance you need more addresses, one can by what amounts to an I2C mux chip for a couple of bucks. The controller programs the mux using I2C commands and the mux connects the controller to one of four I2C segments.

If we designed an I2C protocol, we could agree on commands for the aquarium controller to use when speaking with the peripherals. If we could get enough folks together on this, then it would simplify DIY aquarium controllers. As some folks could concentrate on the controllers being able to issue the agreed upon commands and others could build peripherals which acted on the agreed upon commands.

If we use an 8 bit command we would appear to be limited to 256 commands, but the beauty is that each *type* of peripheral can have its own set of commands. Your aquarium controller wouldn't tell a salinity probe to dim the lights, after all.

So, I have thought of the following commands:

Light (LED) specific commands
Turn lights on at PWM intensity X (where X is probably an 8 bit value for the PWM output).
Turn lights OFF (Disabling the driver is often a lower power option than changing PWM to 0 duty cycle).
Brighten Lights, starting at X intensity and ending at Y intensity with Z interval between steps. (number of steps is fixed by "distance" from X to Y)
Dim Lights, starting at current intensity and ending at Y intensity with Z interval between steps. 
Brighten lights using curve W (table mapping parabolic function?) starting at X ending at Y with interval Z. Note, each W may be a separate command rather than a parameter for one special command. 
Turn ON at Reset at Intensity X (on power up (coming out of Reset) turn the lights on at Intensity X without waiting for input from the controller. (this allows folks to use an external timer in case they don't have a central controller yet and will be the default setting when first built).
Set analog brightness (electrical current control) to X
Take analog brightness setting from ADC pin.
Shut lights off if temperature exceeds X.

More general commands
Change I2C ID to X (Changes the address to which the I2C device responds. This ID is stored in the ATtiny25 EEPROM).
Load New Software
Report temperature now.
Report temperature every X interval.
Report if temperature exceeds X.

I suspect that 32 commands will be plenty per peripheral type, so I'd like to structure the command byte as C[7:3] = command; C[2:0] = number of words of arguments following command.

This scheme has two purposes. First, it will prevent the ATtiny25 from having to find the command in a Case statement before it knows how many words of arguments to take. All it must do is mask off the upper five bits of the command and it knows how many arguments to receive. 

Second, the idea of a Case statement can be eliminated entirely by having a section of program memory contain vectors to each of the routines which will handle each command. But the ATtiny25 has only 2K of Flash. If we devoted 256 X 2 bytes to vectors just to interpret commands there wouldn't be any space left to speak of. Limiting the number of commands to 32 reduces the vector table size to 64 bytes and using a vector table to interpret the command eliminates the sizable hash of Branch statements that would have been needed to build the equivalent of a Case statement.

Those are my rough thoughts so far on a standard aquarium peripheral control language/interface. Please, anyone who wishes, jump in. 

If I can get any interest going on this I'll also post to nano-reefs and reef central as they are very active in LED DIY and each has at least a few controller projects going.

However, I won't be able to start coding for another couple of months. I have some other projects backlogged at the moment.


----------



## ullbergm (Apr 19, 2010)

trag said:


> Have you considered using I2C (or IIC) for your communications from your main controller to your sensors and servors/drivers?
> 
> I started designing a tank controller a few weeks ago, started by reviewing what other folks were doing and decided that I didn't so much want to design an entire controller, as I'd like to design a controller to peripheral interface and a nice LED driver/peripheral.
> 
> ...


I2C would work (and would probably be easier as well), i may have been over complicating things with a 485... The reason i was thinking of going with something more industrial is because of the interference from lighting ballasts, etc.

I do like the idea of creating a common open communication spec to help interoperability between our different solutions.

No sense in everybody developing their own solution, there is power in numbers 

I had not even thought about what you mentioned about making each device run on its own and have the main component configure them as needed. I like it.

We need a central site to work on the specs and share code, what do you think about using something like github, googlecode, etc. that gives us both a code/file sharing system as well as a wiki to hash out protocol specs?


----------



## ullbergm (Apr 19, 2010)

We need some kind of discovery protocol, nothing fancy i dont think, just a simple get-device-type(deviceid) should do, plus that would return the device type as well removing the need to query the type of device once one is found.

Another thing we need is a spec for the different types of devices and a list of commands they should support.
That way anyone can make a RGB LED device as long as it supports the basic commands we have agreed upon.
Maybe the device type includes the version of the protocol that it supports? That way if we add things to the RGB LED spec later we can figure out if the device supports the new commands or not.

Another thought would be to have a addon-spec that would tell you if a device supports scheduling commands or not, that way each device could be programmed to turn lights on and off without the need of having the main unit running.

maybe something like query-capabilities that returns a bit value where the bits are high level command sets that it supports


```
XXXXXXXX
 X                = CanSchedule
  X               = HaveTemperatureSensor
   X              = unused
    X             = unused
     X            = unused
```
and so on


----------



## trag (Apr 27, 2010)

ullbergm said:


> I2C would work (and would probably be easier as well), i may have been over complicating things with a 485...


I2C is not a perfect solution, but I believe it is the best of the available options. More robust standards such as CAN, ethernet and USB are also more expensive (require additional transceivers/support chips) and are not as commonly available on microcontrollers. The other simple protocols (SPI, various serial port standards) are not as supportive of having multiple devices on the same bus.

I think. 

I2C has limits which we will have to work around, but none of the limitations are especially limiting. They're merely a little less than ideal. Phillips/NXP and Texas Instruments make a variety of I2C support chips, which solve hardware problems, such as bus extenders for overlong cables, and Switches for when you need multiple independent I2C segments on the same controller.



> I do like the idea of creating a common open communication spec to help interoperability between our different solutions.
> 
> No sense in everybody developing their own solution, there is power in numbers


Yes. Everyone who develops an aquarium controller ends up needing to design all their own probes and almost inevitably a house current switch box. I would like to see more commonality. There's just no reason why everyone needs to solve all these problems over and over again. And if we can get others to go along, we can get some group buys going that will save everyone money.



> I had not even thought about what you mentioned about making each device run on its own and have the main component configure them as needed. I like it.


I'm primarily a hardware/firmware guy. I do my professional programming in assembly language (on a processor you've never heard of ). I have had a few classes in micro controller programming and interfacing, though. So when I first started looking at this, I came at it from the point of view of having a microcontroller run multiple LED drivers. 

This idea started as a choice of three PWM lines the micro would output. Grew into needing to address each driver to tell it which PWM line to grab. This led to eight more parallel lines for addressing plus control line(s). When I reached 11 parallel lines, I realized I needed a serial communications method, which made the address decoding at the driver expensive. Up to that point I'd been able to keep everything in logic chips such as latching muxes.

A coworker suggested that I just put a microcontroller at the driver, which would solve all my addressing issues, but I thought it would be too expensive. Then I looked at the ATtiny25/45/85 and saw its $1.10 @Qty100 price and that was cheaper than my PAL/addressable latching muxes scheme. And the more I read, the more versatility and features I found.



> We need a central site to work on the specs and share code, what do you think about using something like github, googlecode, etc. that gives us both a code/file sharing system as well as a wiki to hash out protocol specs?


That sounds like the way to proceed. Once we get some stuff up there, enough to show we're not just blowing hot air, we can put announcements in the relevant forums and see what kind of participation/buy-in we can drum up.

I have never used a system such as that before (although I use CVS at work), so why don't you choose the one you like the best, point me at an example on line. I'll make sure that my web browsers access it without issues and if so we'll get started there.



> We need some kind of discovery protocol, nothing fancy i dont think, just a simple get-device-type(deviceid) should do, plus that would return the device type as well removing the need to query the type of device once one is found.


A command of the type:
Report (Get) Device Type/Revision makes sense. 

However, there isn't any way that I know of in I2C to interrogate for I2C IDs, other than to walk through all of the possibilities and see if a device responds. So at certain times (after reset?, on user command?) the central controller would need to send a Report Device Type to each I2C ID possibility. If there's no response, there's no device and if there is a response, then it records the I2C ID and Device Type together.

Incidentally, the central controller should have a way to associate a human-meaningful label with each I2C ID, so that the user needn't remember which peripheral has which ID.

I2C isn't especially fast, but it should take less than 1 second to work through all of the possible IDs.

Because I2C devices can't really self-configure addresses to avoid collisions, the responsibility is on the user to assign unique IDs to each device, which is why there must be a Change I2C ID command. I consider this the clunkiest part of this standard, but I can't see any way around it.

So, for example, in my LED driver.... The best balance between economics (larger scale = cheaper) and versatility (smaller scale = more versatile) seems to be about four LED drives on a circuit board. And so, four ATtiny25s on the board. I would not want to program every ATtiny with a different ID. I would rather just program four sets (ID 1, ID 2, ID 3, ID 4). So every controller board would have four I2C IDs, but they'd be the same set as on every other board. The first thing a person would need to do after getting/building one would be to hook it up to the central controller and use the Change I2C ID to give each controller a unique ID for his rig.



> Another thing we need is a spec for the different types of devices and a list of commands they should support.


I think this is the major first step. Identify the different types of devices and develop a set of commands in common and specific to each type. Then develop an example code which others can modify to support their own devices. It's almost always easier to modify someone else's code, rather than write from scratch. 



> Maybe the device type includes the version of the protocol that it supports?


This sounds like a good idea. At worst it would add a byte to the response to the Report Device Type command.



> Another thought would be to have a addon-spec that would tell you if a device supports scheduling commands or not, that way each device could be programmed to turn lights on and off without the need of having the main unit running.


Scheduling would be a nice option. It must be an option, because micros as simple as the ATtiny25 don't have a real time clock. But some folks may decide to use more complex micros to drive their peripherals and those could have real time clocks. So it's definitely a good idea to include the option in the standard.



> maybe something like query-capabilities that returns a bit value where the bits are high level command sets that it supports


It could be part of Report Device Type. The device type could be different if scheduling is available, such that an LED controller with scheduling would be a different device type from one without. Or they could be the same type, and scheduling support could be in a supplementary byte to device type, along with revision number.

So, e.g., in response to a Report Device Type command, a device might first send it's Device Type byte, and then a second byte which contains the command set revision and whether it supports such features as scheduling and anything else we think of....

How to split the bits up in that second byte might be tricky as it would limit how many revisions there can be, but that's not necessarily a bad thing....

My name is Jeff Walther. I live in Austin, TX. I'm an electrical engineer. I've been keeping fish off and on for about 30 years. 

I think we should probably give this topic its own thread rather than hijacking yours.


----------



## ullbergm (Apr 19, 2010)

trag said:


> I2C is not a perfect solution, but I believe it is the best of the available options. More robust standards such as CAN, ethernet and USB are also more expensive (require additional transceivers/support chips) and are not as commonly available on microcontrollers. The other simple protocols (SPI, various serial port standards) are not as supportive of having multiple devices on the same bus.


The reason i was thinking rs-485 is that its a ruggedized protocol and all you really need to do is to buy some rs-485 ic's but it would $2-$5 per device which may be undesirable.



> I'm primarily a hardware/firmware guy. I do my professional programming in assembly language (on a processor you've never heard of ). I have had a few classes in micro controller programming and interfacing, though. So when I first started looking at this, I came at it from the point of view of having a microcontroller run multiple LED drivers.


I started down this line when i wanted to make a controller for some RGB LED's that i found, 3W output at full power / bright white.
Plan was to have a sunrise/sunset as well as moonlights out of the same lights.



> A command of the type:
> Report (Get) Device Type/Revision makes sense.
> 
> However, there isn't any way that I know of in I2C to interrogate for I2C IDs, other than to walk through all of the possibilities and see if a device responds. So at certain times (after reset?, on user command?) the central controller would need to send a Report Device Type to each I2C ID possibility. If there's no response, there's no device and if there is a response, then it records the I2C ID and Device Type together.


I forgot about the fact that the i2c specs have device id's already.. 



> Incidentally, the central controller should have a way to associate a human-meaningful label with each I2C ID, so that the user needn't remember which peripheral has which ID.


I'm thinking that we should have a description field that can be programmed in to the attiny, that the central controller can be reset from scratch and still be able to get useful information off the bus.

GetDescription
SetDescription



> Because I2C devices can't really self-configure addresses to avoid collisions, the responsibility is on the user to assign unique IDs to each device, which is why there must be a Change I2C ID command. I consider this the clunkiest part of this standard, but I can't see any way around it.
> 
> So, for example, in my LED driver.... The best balance between economics (larger scale = cheaper) and versatility (smaller scale = more versatile) seems to be about four LED drives on a circuit board. And so, four ATtiny25s on the board. I would not want to program every ATtiny with a different ID. I would rather just program four sets (ID 1, ID 2, ID 3, ID 4). So every controller board would have four I2C IDs, but they'd be the same set as on every other board. The first thing a person would need to do after getting/building one would be to hook it up to the central controller and use the Change I2C ID to give each controller a unique ID for his rig.


I would be easy enough to have a quick-setup mode that you use to configure your devices. When you set up your system from scratch you'd plug in a single i2c device, go to the controller and scan for devices.
Since you only have one you can give it a description, etc. and plug in the next device.
After telling your controller to rescan it would announce that it has found a second device, you configure it, etc.
rinse repeat



> I think this is the major first step. Identify the different types of devices and develop a set of commands in common and specific to each type. Then develop an example code which others can modify to support their own devices. It's almost always easier to modify someone else's code, rather than write from scratch.


Agreed, we could have standard device samples so that someone that wants to build a relay type device (simple on/off for pumps, heaters, etc.) wouldnt have to write a single line of code.

Ok, maybe a single line to indicate the manufacturer (their name ).



> Scheduling would be a nice option. It must be an option, because micros as simple as the ATtiny25 don't have a real time clock. But some folks may decide to use more complex micros to drive their peripherals and those could have real time clocks. So it's definitely a good idea to include the option in the standard.


agreed, the number of addon-specs should be small and they should only be used for major functionality, like scheduling. Carving off 8 bits should be enough for a while i think as long as we limit it to *major* functions.
Right now scheduling is the only thing i can think of.



> So, e.g., in response to a Report Device Type command, a device might first send it's Device Type byte, and then a second byte which contains the command set revision and whether it supports such features as scheduling and anything else we think of....
> 
> How to split the bits up in that second byte might be tricky as it would limit how many revisions there can be, but that's not necessarily a bad thing....


sounds good



> My name is Jeff Walther. I live in Austin, TX. I'm an electrical engineer. I've been keeping fish off and on for about 30 years.
> 
> I think we should probably give this topic its own thread rather than hijacking yours.


I'm Magnus Ullberg, currently living in Wilson, NC. I'm a computer engineer doing virtualization (mainly using VMware).

I recently came back to the fish keeping hobby after 10+ years without a single fish. As far as electronics its a hobby, not work, i have managed to stock up on quite a few samples from the various chip manufacturers and i also have a Atmel STK600 that i use for development.


----------



## ullbergm (Apr 19, 2010)

Have you looked at the modbus protocol? Maybe we could get some ideas from that:
http://en.wikipedia.org/wiki/Modbus

```
Modbus RTU Frame Format 

Name       Length      Function 
Start      3.5c idle   at least 3-1/2 character times of silence (MARK condition) 
Address    8 bits      Station Address 
Function   8 bits      Indicates the function codes like read coils / inputs 
Data       n * 8 bits  Data + length will be filled depending on the message type 
CRC Check  16 bits     Error checks 
End        3.5c idle   at least 3-1/2 character times of silence between frames
```
My plan was to use freemodbus to communicate over a rs485 protocol using DS75176 type tranceivers.
http://www.modbus.org/docs/Modbus_over_serial_line_V1_02.pdf

I admit it may be overkill but that's what i was going to use, partially because i think its interesting to use more intelligent protocols rather something quick i hacked together over a weekend


----------



## trag (Apr 27, 2010)

ullbergm said:


> Have you looked at the modbus protocol? Maybe we could get some ideas from that:
> http://en.wikipedia.org/wiki/Modbus


The RTU frame format is pretty much exactly what I had in mind for transmitting over I2C. An address followed by a function, followed by any necessary arguments for the function. 

Being a differential method, RS485 is more robust than I2C, but it is also more expensive. It's one of those trade offs. 

The thing I like about I2C is that the sender or the receiver can stall the bus using one of the two wires, so that the sender must pause. Given that these controllers are real-time systems and likely to be heavily interrupt driven, the ability to pause in the middle of communications seems like a valuable feature.


----------



## ullbergm (Apr 19, 2010)

I think that you are right that I2C is a good idea for a shared community project, just about every uC manufacturer has low end devices that supports it. 

One thought I had about the examples you listed earlier would be to combine several commands in to one. 
For example, the set PWM level could be the same as the dim-to-PWM with the duration of 0. 
Same with the power-off command, a dim to 0 could be interpreted as a power off.

I think having fewer commands to look for might be an advantage when working with limited devices. Thoughts?


----------



## ullbergm (Apr 19, 2010)

I created a separate thread to discuss the details:
http://www.plantedtank.net/forums/diy/108387-common-communication-spec-diy-aquarium-controllers.html


----------



## ullbergm (Apr 19, 2010)

Project has been on hold while waiting for some parts to come in, they finally arrived and i'm going to get going on this again.

After i build a new stand for my tank.

Some highlights from the order:
2x16 LCD display with RGB backlighting(!), the plan is to use the background color of the LCD to indicate warning or error conditions. ie. If the pH is out of whack the background would be yellow, if the pH is not back to normal levels within a certain time period the background would change to red.
mini joystick - it's about a 1/2 inch squared and has up/down/left/right as well as push indication, it should make for easy navigation thru the LCD menu system.
ATMega1284P - Monster AVR chips in PDIP-40 format
DS1307 - real-time clock chip
ATTinys - various versions
crystals - 20mhz and some 32.768's
mini speaker / buzzer - could be used for alarms
new prototyping board, the old one i had was too small


----------



## ullbergm (Apr 19, 2010)

Progress 

LCD interface prototype is running, it doesn't do anything but right now i'm just trying to get the peripherals to talk to each other.

Next up is the scheduler, basically i'll be adding a DS1307 chip to the board and with that i should have a stable clock.

Here is a (crappy) video of the interface in action.
http://qik.com/video/9358568


----------



## ullbergm (Apr 19, 2010)

The last update was a little short, here is a more detailed account of what i've been up to with this project.

After struggling to get the LCD and serial communication to work using FreeRTOS i swapped it for atomthreads which is another RTOS but not quite as large (and complex).

I have serial communication working, for now i'm mainly using it to output debugging information but in the end i may switch to using it for configuration.

The LCD is also working (in 4-bit mode so i save 4 pins) and i have a menu system that you can navigate using a mini joystick.
Up / Down to select the menu item
Right to navigate down the menu hierarchy
Left to navigate up the menu hierarchy.

The powersupply is built on the prototype board as well, it is based on a LM7805 and it puts out a stable 5V from a 9V transformer i had in my pile of junk.

Next project is the clock source which will also require the i2c stuff to be working, should be fun.


----------



## ullbergm (Apr 19, 2010)

Well, that was easier than i thought.. 

I can talk to the DS1307 to get/set the time, now i need to work on having it trigger a schedule.


----------

