Class to communicate with ELV(R) MAX! wireless devices with RFM22B-Modules. Based on Library RF22. Initial version unable to send! Only receive! See http://mbed.org/users/charly/notebook/reading-a-max-wireless-window-sensor-with-rfm22-an/

Dependents:   RF22_MAX_test_Send

RF22Max.h

Committer:
charly
Date:
2013-09-18
Revision:
1:6321e6784ada
Parent:
0:565a81d6f278
Child:
2:f75e51ce001b

File content as of revision 1:6321e6784ada:

// RF22Max.h
//
// decode messages from ELV-MAX! wireless devices
// based on RF22-Class (C) by Mike McCauley (mikem@open.com.au) for RFM22 transceiver-modules by HopeRF
//

///  \version 1.00 Working class for Receive
///  \author  Karl Zweimueller http://mbed.org/users/charly/

#ifndef RF22Max_h
#define RF22Max_h

#include "mbed.h"
#include <RF22.h>

// define DEBUG if you want to see bufer-output on pc (defined in main)
#ifdef DEBUG
extern Serial pc;
#endif

#define lengthof(x) (sizeof(x) / sizeof(*x))
/////////////////////////////////////////////////////////////////////
/// \class RF22Max RF22Max.h <RF22Max.h>
/// \brief receive (in future also send) packets from/to MAX! Devices by ELV (http://www.elv.de/max-funk-heizungsregler-system.html)
///
/// This class provides basic functions for sending and receiving MAX!-messages,
/// at the moment only receiving possible
/// ueses recv() from RF22
/// based on RF22-Class (C) by Mike McCauley (mikem@open.com.au) for RFM22 transceiver-modules by HopeRF
/// returns decodes message and payload for further processing
///
class RF22Max : public RF22
{
public:
    /// \brief a message from a max!-Device
    ///
    /// structure for a MAX!-Message
    /// includes decoded fields and the payload
    /// also has some specific field, which are only valid on some message-types
        ///
    /// Message-types:
    ///
    /// 0x00: "PairPing"
    ///
    /// 0x01: "PairPong";
    ///
    /// 0x02: "Ack";
    ///
    /// 0x03: "TimeInformation";
    ///
    /// 0x10: "ConfigWeekProfile";
    ///
    /// 0x11: "ConfigTemperatures";
    ///
    /// 0x12: "ConfigValve";
    ///
    /// 0x20: "AddLinkPartner";
    ///
    /// 0x21: "RemoveLinkPartner";
    ///
    /// 0x22: "SetGroupId";
    ///
    /// 0x23: "RemoveGroupId";
    ///
    /// 0x30: "ShutterContactState";
    ///
    /// 0x40: "SetTemperature";
    ///
    /// 0x42: "WallThermostatState";
    ///
    /// 0x43: "SetComfortTemperature";
    ///
    /// 0x44: "SetEcoTemperature";
    ///
    /// 0x50: "PushButtonState";
    ///
    /// 0x60: "ThermostatState";
    ///
    /// 0x82: "SetDisplayActualTemperature";
    ///
    /// 0xF1: "WakeUp";
    ///
    /// 0xF0: "Reset";
    ///       

    typedef struct {
        uint8_t    len;                ///<  Message-length
        uint8_t    cnt;                ///<  Message-counter
        uint8_t    flags;              ///<  unknown
        uint8_t    type;               ///<  Message-type
        char       type_str[50];       ///<  Message-Type in text
        uint32_t   frm_adr;            ///<  Unique address of device From
        uint32_t   to_adr;             ///<  Unique address of device To
        uint8_t    groupid;            ///<  Groupid
        uint8_t    payload[50];        ///<  Data
        uint16_t   crc;                ///<  CRC for the message
        char       state[50];          ///<  State of the device: open, closed, auto, eco,...
        char       battery_state[50];  ///<  Battery-state of the device : good, low
    } max_message;

/// Constructor
/// Create an object for a RFM22-module connected to the controller via SPI, SlaveSelect and Interrupt-pin
/// \param[in] slaveSelectPin SlaveSelectPin
/// \param[in] mosi SPI
/// \param[in] miso SPI
/// \param[in] sclk SPI
/// \param[in] interrupt Interrupt line for RFM22
    RF22Max(PinName slaveSelectPin, PinName mosi, PinName miso, PinName sclk, PinName interrupt);

    /// Initialize the module for MAX!-messages
    /// sets frequency, datarate, ...
    /// \return  true if everything was successful
    boolean init();

    /// start receiver and see if a valid MAX!-message is available and return it undecoded to the caller
    /// nonblocking
    /// check crc and do dewithening
    /// \param[in] buf Location to copy the received message
    /// \param[in,out] len Pointer to available space in buf(copies maximum len bytes!). Set to the actual number of octets copied.
    /// \return true if a valid message was copied to buf
    boolean recv(uint8_t* buf, uint8_t* len);

    /// start receiver and see if a valid MAX!-message is available and return the decoded message to the caller
    /// nonblocking
    /// check crc and do dewithening and do decoding of fields
    /// \param[in] message A pointer to a RF22Max::max_message
    /// \return true if a valid message was copied to buf
    boolean recv_max(RF22Max::max_message* message);

private:

#ifdef DEBUG
    /// show received buffer on serial pc
    void printHex(uint8_t *buf, size_t len, bool nl);
#endif

    /// calc_crc_setup setup crc-calculation
    uint16_t calc_crc_step(uint8_t crcData, uint16_t crcReg);

    /// calc_crc calculate crc for the data in buf
    uint16_t calc_crc(uint8_t *buf, size_t len);


}; // end class RF22Max

#endif