Skip to content
JackKelly edited this page Dec 13, 2012 · 2 revisions

== Motivation and Aims ==

I need to monitor the power consumption of every appliance in my home (for [http://jack-kelly.com/about my academic research on smart meter disaggregation]). I tried using 30 Current Cost IAMs (with 4 EnviR receivers) but this setup suffered from lost data due to RF collisions. So I now plan to use 30 EDF IAMs to monitor appliances, plus 3 Current Cost whole-house transmitters to monitor things like my boiler and kitchen ceiling lights. EDF IAMs differ from CC IAMs in that the EDF units wait to be polled before transmitting data and hence we should be able to avoid RF collisions. But the EDF EcoManager “base” can only handle 14 EDF IAMs; and there’s little point using multiple EcoManagers (because then we’ll get collisions again) so I need to build my own base station for EDF IAMs.

The ultimate aim is to build a DIY base station which can talk to an arbitrary number of EDF IAMs and a small number (say 0-3) CC transmitters. The idea is that the Nanode will connect to a PC which will log data. The Nanode should do the bare minimum to allow software running on a PC to perform its data logging function.

== Hardware Requirements ==

The easiest way to get started is to buy a [http://www.nanode.eu/products/ Nanode Classic] and a 433MHz [http://www.hoperf.com/rf_fsk/fsk/21.htm RFM12b] wireless transceiver. Note that the Nanode RF kit comes with an 868 MHz RFM12b, which is not what you want.

If you build a DIY board, or if you connect an RFM12b to an Arduino, make sure the RFM12b’s nFFS pin is set permanently high.

== Installation ==

=== Uploading pre-compiled hex file ===

First change directory into this project’s <code>Release/</code> directory.

Uploading to AVR using FTDI serial cable:

<code> avrdude -pm328p -carduino -P/dev/ttyUSB0 -b57600 -F -V -Uflash:w:rfm_edf_ecomanager.hex:a </code>

Uploading to AVR using STK500v2 programmer:

<code> avrdude -pm328p -cstk500v2 -P/dev/ttyACM0 -Uflash:w:rfm_edf_ecomanager.hex:a </code>

=== Building from source ===

==== Using the Arduino IDE ====

With the Arduino IDE closed, place the rfm_edf_ecomanager directory and files into your sketchbook directory. You will also need to add the [/JackKelly/nanode_rf_utils nanode_rf_utils] library, as per the instructions in that repository’s README.md file.

Then start the Arduino IDE and go to Open -> rfm_edf_ecomanager. Please note that I’m currently using Eclipse to develop this code (not the Arduino IDE). However, I do try to test in the Arduino IDE regularly. Many thanks to [/robomotic robomotic] for help converting my code to compile in the Arduino IDE.

==== Using Eclipse ====

==== Building without Eclipse or the Arduino IDE ====

I’m afraid building this code isn’t especially user-friendly at the moment because I’m developing on Eclipse and am using the auto-generated makefile at the moment while there’s a lot of code churn. If I have time I’ll manually create a more user friendly makefile.

I haven’t tried this so I’m afraid I don’t know if this will work but here are some pointers.

First, open Release/subdir.mk. You’ll almost certainly need to modify the include directories to point to the relevant directories on your system.

Then run:

<code> cd Release make all </code>

Then upload your `rfm_edf_ecomanager.hex` using the “[/JackKelly/rfm_edf_ecomanager/wiki#wiki-Uploading_precompiled_hex_file Uploading pre-compiled hex file]” instructions above.

== Two Types of Wireless Sensor ==

The code makes a fundamental distinction between two types of Current Cost wireless sensor: CC_TX and CC_TRX sensors. The two types of sensors use fundamentally different RF protocols.

=== CC_TX === Current Cost transmit-only sensors (“TX” is an abbreviation for “transmitter”). These units can only transmit and hence cannot do any carrier detection; and lost data cannot be re-sent e.g.:

Current Cost IAM

Current Cost “Sensable” Whole-House Transmitter

EDF whole-house transmitter

=== CC_TRX === CC_TRX transceivers (“TRX” is an abbreviation for “[http://en.wikipedia.org/wiki/Transceiver transceiver]”). These transceivers require a “polling” request from the base station to send data and hence RF collisions can be avoided. e.g.:

EDF IAMs

== Introduction to the Behaviour of this Code ==

The code keeps two separate lists: one of CC_TXs and one of CC_TRXs. We need a list of CC_TXs so we can learn when each CC_TX is due to transmit and cease any transmissions around the time that we expect a CC_TX to transmit in order to avoid causing RF collisions with CC_TXs (because there is no way to ask for lost data to be reset with CC_TXs). We need a list of CC_TRXs so we can poll them in order.

=== Quick start guide ===

Please see the section on serial commands for details of other commands.

=== Data Format ===

The code sends received data over the serial port in simple JSON format like this:

{“type”: “tx”, “id”: 2431, “t”: 29048, “sensors”: {“1”: 0, “2”: 0}} {“type”: “tx”, “id”: 2339, “t”: 31920, “sensors”: {“1”: 316}} {“type”: “trx”, “id”: 2200180225, “t”: 40274, “sensors”: {“1”: 0}, “state”: 0}

<code>type</code> is type of wireless transmitter. It can take two values: <code>tx</code> or <code>trx</code>

<code>id</code> is the radio ID of the transmitter

<code>t</code> is the time in milliseconds when the first byte of the packet arrives. The time is the number of milliseconds since the Nanode was powered on (but note that the ATMEGA’s clock isn’t very accurate because <code>millis()</code> stops counting when interrupts are disabled e.g. while an interrupt service routine is running; hence this clock falls behind quite rapidly)

<code>sensors</code> is the reported power consumption in watts for sensor each sensor connected to the transmitter (the Current Cost Sensable TX can accept up to 3 CT clamps). Sensor indices start from 1 not 0.

<code>state</code> is the state reported by EDF IAMs (1 == on; 0 == off).

== Serial commands ==

You can send simple commands over serial to control things like the verbosity of output, which packets to report, to control pairing etc. (these are detailed below).

The Nanode talks to the host PC over serial at a baud rate of 115200. If you’re using Linux then try the command-line application <code>screen -L /dev/ttyUSB0 115200</code>.

{| class=”wikitable”

! scope=”col” | Command ! scope=”col” | Description

<code>a</code> ”’a”’uto pairing. Turn auto_pair mode on. (default)
<code>m</code> ”’m”’anual pairing. Turn auto_pair mode off.
<code>p<ID></code> ”’p”’air with ID (only valid in manual pairing mode)*. e.g. <code>p1234</code>
<code>s<SIZE></code> ”’s”’et size of array for CC_TXs*. e.g. <code>s20</code>
<code>S<SIZE></code> ”’S”’et size of array for CC_TRXs*. e.g. <code>S20</code>
<code>n<ID></code> Add ”’n”’ew radio ID to list of CC_TXs*. e.g. <code>n1234</code>
<code>N<ID></code> Add ”’N”’ew radio ID to list of CC_TRXs*. e.g. <code>N1234</code>
<code>d</code> ”’d”’elete all stored CC_TX radio IDs
<code>D</code> ”’D”’elete all stored CC_TRX radio IDs
<code>r<ID></code> ”’r”’emove single CC_TX radio ID*. e.g. <code>r1234</code>
<code>R<ID></code> ”’R”’emove single CC_TRX radio ID*. e.g. <code>R1234</code>
<code>l</code> ”’l”’ist all stored CC_TX radio IDs
<code>L</code> ”’L”’ist all stored CC_TRX radio IDs
<code>t</code> ”’t”’imecheck. Just respond with milliseconds since last reset (after a 10ms delay). No ACK.
<code>0<ID></code> Turn TRX ID off
<code>1<ID></code> Turn TRX ID on
<code>v<level></code> ”’v”’erbose logging threshold. e.g. <code>v0</code>. Only works if code has been compiled with the symbol <code>LOGGING</code> defined. The lower the number, the more logging messages. 0=DEBUG, 1=INFO, 2=WARNING (something went wrong but it shouldn’t affect us) (default), 3=ERROR (something went wrong badly enough to affect us but we can continue), 4=FATAL (something has blown up and we can’t continue).
<code>k</code> Only print data from ”’k”’nown IDs
<code>u</code> (default) Print all valid received packets including from ”’u”’nkown IDs; but don’t print broken packets
<code>b</code> Print all received packets, even ”’b”’roken ones. Note that broken packets will be displayed as raw packets in hex like this: <code>C FF 80 0 0 0 0 0</code> Packets from CC_TXs will be displayed after being de-manchesterised, even though the demanchesterisation failed. How does the code know if packets are broken? CC_TX packets don’t have checksums so we use the manchesterised nature of the data as a primitive validation check (broken packets slip through this validation though). CC_TRX packets, on the other hand, have a checksum.
}

<nowiki>*</nowiki> Numbers can be decimal e.g. <code>12345</code> (no leading zero), octal e.g. <code>01234</code> (with leading zero) or hex e.g. <code>0xABCD123</code> (with leading <code>0x</code> or <code>0X</code>). Number input blocks until carriage return <code>’\r’</code> is received (but RF packets will still be received by the interrupt service routine. But don’t take too long to enter the number of the receive buffer will overflow!) Backspace key does what you’d expect it to do.

Commands are either acknowledged or rejected by <code>ACK</code> or <code>NAK</code> respectively. A short description usually follows the <code>ACK</code> or <code>NAK</code>.

== Pairing ==

The code can pair with both TX-only sensors (like Current Cost whole-house transmitters) and transceivers (e.g. EDF IAMs).

There are two pairing modes: auto pairing and manual pairing (see “Serial commands” section for how to change modes).

In auto pairing mode, the Nanode will accept all received pairing requests.

In manual pairing mode, the Nanode will notify the user that a pair request has been made with the JSON <code>{pr: <id>}</code> (where ‘pr’ is short for pair request). If the user wants to pair with this ID then send the Nanode a <code>p<id></code> command (see “Serial commands” section for more info). The Nanaode will then pair with that ID if a further pair request is received.

In both modes, if the pairing process is successful then the ID is added to the Nanode’s internal list and the pairing is acknowledged over serial with the JSON <code>{pw: <id>}</code> (where ‘pw’ is short for ‘paired with’).

If a pair request is received from an ID already known to the Nanode then no action is taken.

== Development ==

=== Bug Reports and Feature Requests ===

We’re using the [https://github.com/JackKelly/rfm_edf_ecomanager/issues GitHub Issue tracker] for bug reports and feature requests.

If you have a problem with compilation in the Arduino IDE then please turn on “Show verbose output during compilation” in File -> Preferences and copy-and-paste the entire console output into the bug report.

Please note that my ultimate aim is to produce a data logging system suitable for [http://jack-kelly.com/about my PhD research] and hence I’m afraid I won’t have much time to work on features which don’t directly relate to my PhD research, sorry. But please go ahead and fork the code, add a feature and submit a pull request.

=== Code Style ===

Code style is roughly the [http://www.python.org/dev/peps/pep-0008 Python PEP8] code style adapted for C++. i.e.:

CamelCase for class names

UPPERCASE_WITH_UNDERSCORES for constants

lowercase_with_underscores for variables and functions

Use 4 spaces for indentation (not tabs)

== Acknowledgements & further reading ==

A massive thank you to Graham Murphy, Matt Thorpe and Paul Cooper who helped to decode the Current Cost and EDF RF protocols.

Many thanks to the good folks who wrote [https://github.com/jcw/jeelib JeeLib] as it provided lots of help.

As did [https://sites.google.com/site/qeewiki/books/avr-guide/spi this tutorial on SPI on AVR devices].

If you want an indepth insight into the RFM01 then read the [http://www.hoperf.com/upload/rf/RFM12B.pdf RFM12B.pdf manual] BEFORE or INSTEAD OF [http://www.hoperf.com/upload/rf/RF12B_code.pdf RFM12B_code.pdf] as the latter has far less detail. The only advantage of the RFM12B_code.pdf is that it contains a code example in C.

For more details please see [http://jack-kelly.com/taxonomy/term/121 the CurrentCost category on my blog].

== Known issues ==

== Related projects ==

[/JackKelly/rfm_ecomanager_logger rfm_ecomanager_logger] A Python script specifically designed to interface with RFM_EDF_ECOMANAGER for adding and editing transmitters and then for logging power consumption data to text files.