A simple CIoT message protocol, used in the Water Meter Demos.

This library provides a small messaging protocol for a CIoT device, intended for use with the Water Meter Demo. As well as building for the C027 target, files are included for building a C DLL and, from that, a C Sharp DLL which can be linked into the PC-end of the Water Meter Demo (see the .ZIP file stored in the Wiki of the Water Meter Demo project) to provide end-to-end messaging with complete transparency. Since these PC files cannot be built inside mbed the source files are post-fixed with a ".txt" extension to keep them out of the way.

If a water pump is to be switched on/off as part of the demo, an interface circuit is required, which is described on the Wiki of the WaterMeterSupport library.

Committer:
RobMeades
Date:
Fri May 22 11:41:38 2015 +0000
Revision:
0:5c46cb3be899
Initial commit of CIoT message protocol, used for water meter demo demonstrations, to mbed cloud.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
RobMeades 0:5c46cb3be899 1 /* DLL wrapper for C027N/water-meter message handling functions
RobMeades 0:5c46cb3be899 2 * for MWC demo 2015
RobMeades 0:5c46cb3be899 3 *
RobMeades 0:5c46cb3be899 4 * Copyright (C) u-blox Melbourn Ltd
RobMeades 0:5c46cb3be899 5 * u-blox Melbourn Ltd, Melbourn, UK
RobMeades 0:5c46cb3be899 6 *
RobMeades 0:5c46cb3be899 7 * All rights reserved.
RobMeades 0:5c46cb3be899 8 *
RobMeades 0:5c46cb3be899 9 * This source file is the sole property of u-blox Melbourn Ltd.
RobMeades 0:5c46cb3be899 10 * Reproduction or utilization of this source in whole or part is
RobMeades 0:5c46cb3be899 11 * forbidden without the written consent of u-blox Melbourn Ltd.
RobMeades 0:5c46cb3be899 12 */
RobMeades 0:5c46cb3be899 13
RobMeades 0:5c46cb3be899 14 /**
RobMeades 0:5c46cb3be899 15 * @file iot_meter_dll_wrapper.cpp
RobMeades 0:5c46cb3be899 16 * This file implements the encapsulation necessary to
RobMeades 0:5c46cb3be899 17 * call the CPP Message Handling functions from C#.
RobMeades 0:5c46cb3be899 18 */
RobMeades 0:5c46cb3be899 19 #include <stdint.h>
RobMeades 0:5c46cb3be899 20 #include <IotMeterApi.hpp>
RobMeades 0:5c46cb3be899 21 #include <IotMeterDllWrapper.hpp>
RobMeades 0:5c46cb3be899 22 #include "windows.h"
RobMeades 0:5c46cb3be899 23
RobMeades 0:5c46cb3be899 24 #ifdef __cplusplus
RobMeades 0:5c46cb3be899 25 extern "C" {
RobMeades 0:5c46cb3be899 26 #endif
RobMeades 0:5c46cb3be899 27
RobMeades 0:5c46cb3be899 28 // Instantiate a messageHandler
RobMeades 0:5c46cb3be899 29 MessageCodec gMessageCodec;
RobMeades 0:5c46cb3be899 30
RobMeades 0:5c46cb3be899 31 // ----------------------------------------------------------------
RobMeades 0:5c46cb3be899 32 // CONSTANTS
RobMeades 0:5c46cb3be899 33 // ----------------------------------------------------------------
RobMeades 0:5c46cb3be899 34
RobMeades 0:5c46cb3be899 35 uint32_t __cdecl maxDatagramSizeRaw (void)
RobMeades 0:5c46cb3be899 36 {
RobMeades 0:5c46cb3be899 37 return MAX_DATAGRAM_SIZE_RAW;
RobMeades 0:5c46cb3be899 38 }
RobMeades 0:5c46cb3be899 39
RobMeades 0:5c46cb3be899 40 uint32_t __cdecl gpioWaterPump (void)
RobMeades 0:5c46cb3be899 41 {
RobMeades 0:5c46cb3be899 42 return GPIO_WATER_PUMP;
RobMeades 0:5c46cb3be899 43 }
RobMeades 0:5c46cb3be899 44
RobMeades 0:5c46cb3be899 45 // ----------------------------------------------------------------
RobMeades 0:5c46cb3be899 46 // PRIVATE FUNCTIONS
RobMeades 0:5c46cb3be899 47 // ----------------------------------------------------------------
RobMeades 0:5c46cb3be899 48
RobMeades 0:5c46cb3be899 49 // ----------------------------------------------------------------
RobMeades 0:5c46cb3be899 50 // MESSAGE ENCODE WRAPPER FUNCTIONS
RobMeades 0:5c46cb3be899 51 // ----------------------------------------------------------------
RobMeades 0:5c46cb3be899 52
RobMeades 0:5c46cb3be899 53 // Wrap encodeRebootReqDlMsg
RobMeades 0:5c46cb3be899 54 uint32_t __cdecl encodeRebootReqDlMsg (char * pBuffer,
RobMeades 0:5c46cb3be899 55 bool devModeOnNotOff)
RobMeades 0:5c46cb3be899 56 {
RobMeades 0:5c46cb3be899 57 RebootReqDlMsg_t msg;
RobMeades 0:5c46cb3be899 58 msg.devModeOnNotOff = devModeOnNotOff;
RobMeades 0:5c46cb3be899 59
RobMeades 0:5c46cb3be899 60 return gMessageCodec.encodeRebootReqDlMsg (pBuffer, &msg);
RobMeades 0:5c46cb3be899 61 }
RobMeades 0:5c46cb3be899 62
RobMeades 0:5c46cb3be899 63 // Wrap encodeSerialNumberGetReqDlMsg
RobMeades 0:5c46cb3be899 64 uint32_t __cdecl encodeSerialNumberGetReqDlMsg (char * pBuffer)
RobMeades 0:5c46cb3be899 65 {
RobMeades 0:5c46cb3be899 66 return gMessageCodec.encodeSerialNumberGetReqDlMsg (pBuffer);
RobMeades 0:5c46cb3be899 67 }
RobMeades 0:5c46cb3be899 68
RobMeades 0:5c46cb3be899 69 // Wrap encodeReadingIntervalSetReqDlMsg
RobMeades 0:5c46cb3be899 70 uint32_t __cdecl encodeReadingIntervalSetReqDlMsg (char * pBuffer,
RobMeades 0:5c46cb3be899 71 uint32_t readingIntervalSeconds)
RobMeades 0:5c46cb3be899 72 {
RobMeades 0:5c46cb3be899 73 ReadingIntervalSetReqDlMsg_t msg;
RobMeades 0:5c46cb3be899 74 msg.readingIntervalSeconds = readingIntervalSeconds;
RobMeades 0:5c46cb3be899 75
RobMeades 0:5c46cb3be899 76 return gMessageCodec.encodeReadingIntervalSetReqDlMsg (pBuffer, &msg);
RobMeades 0:5c46cb3be899 77 }
RobMeades 0:5c46cb3be899 78
RobMeades 0:5c46cb3be899 79 // Wrap encodeReadingIntervalGetReqDlMsg
RobMeades 0:5c46cb3be899 80 uint32_t __cdecl encodeReadingIntervalGetReqDlMsg (char * pBuffer)
RobMeades 0:5c46cb3be899 81 {
RobMeades 0:5c46cb3be899 82 return gMessageCodec.encodeReadingIntervalGetReqDlMsg (pBuffer);
RobMeades 0:5c46cb3be899 83 }
RobMeades 0:5c46cb3be899 84
RobMeades 0:5c46cb3be899 85 // Wrap encodeGpioSetReqDlMsg
RobMeades 0:5c46cb3be899 86 uint32_t __cdecl encodeGpioSetReqDlMsg (char * pBuffer,
RobMeades 0:5c46cb3be899 87 uint8_t gpio,
RobMeades 0:5c46cb3be899 88 bool inputNotOutput,
RobMeades 0:5c46cb3be899 89 bool onNotOff)
RobMeades 0:5c46cb3be899 90 {
RobMeades 0:5c46cb3be899 91 GpioSetReqDlMsg_t msg;
RobMeades 0:5c46cb3be899 92 msg.gpioState.gpio = gpio;
RobMeades 0:5c46cb3be899 93 msg.gpioState.inputNotOutput = inputNotOutput;
RobMeades 0:5c46cb3be899 94 msg.gpioState.onNotOff = onNotOff;
RobMeades 0:5c46cb3be899 95
RobMeades 0:5c46cb3be899 96 return gMessageCodec.encodeGpioSetReqDlMsg (pBuffer, &msg);
RobMeades 0:5c46cb3be899 97 }
RobMeades 0:5c46cb3be899 98
RobMeades 0:5c46cb3be899 99 // Wrap encodeGpioGetReqDlMsg
RobMeades 0:5c46cb3be899 100 uint32_t __cdecl encodeGpioGetReqDlMsg (char * pBuffer,
RobMeades 0:5c46cb3be899 101 uint32_t gpio)
RobMeades 0:5c46cb3be899 102 {
RobMeades 0:5c46cb3be899 103 GpioGetReqDlMsg_t msg;
RobMeades 0:5c46cb3be899 104 msg.gpio = (uint8_t) gpio;
RobMeades 0:5c46cb3be899 105
RobMeades 0:5c46cb3be899 106 return gMessageCodec.encodeGpioGetReqDlMsg (pBuffer, &msg);
RobMeades 0:5c46cb3be899 107 }
RobMeades 0:5c46cb3be899 108
RobMeades 0:5c46cb3be899 109 // Wrap encodeLedSetReqDlMsg
RobMeades 0:5c46cb3be899 110 uint32_t __cdecl encodeLedSetReqDlMsg (char * pBuffer,
RobMeades 0:5c46cb3be899 111 bool onNotOff)
RobMeades 0:5c46cb3be899 112 {
RobMeades 0:5c46cb3be899 113 LedSetReqDlMsg_t msg;
RobMeades 0:5c46cb3be899 114 msg.onNotOff = onNotOff;
RobMeades 0:5c46cb3be899 115
RobMeades 0:5c46cb3be899 116 return gMessageCodec.encodeLedSetReqDlMsg (pBuffer, &msg);
RobMeades 0:5c46cb3be899 117 }
RobMeades 0:5c46cb3be899 118
RobMeades 0:5c46cb3be899 119 // Wrap encodeLedGetReqDlMsg
RobMeades 0:5c46cb3be899 120 uint32_t __cdecl encodeLedGetReqDlMsg (char * pBuffer)
RobMeades 0:5c46cb3be899 121 {
RobMeades 0:5c46cb3be899 122 return gMessageCodec.encodeLedGetReqDlMsg (pBuffer);
RobMeades 0:5c46cb3be899 123 }
RobMeades 0:5c46cb3be899 124
RobMeades 0:5c46cb3be899 125 // Wrap encodeFlashSetReqDlMsg
RobMeades 0:5c46cb3be899 126 uint32_t __cdecl encodeFlashSetReqDlMsg (char * pBuffer,
RobMeades 0:5c46cb3be899 127 bool onNotOff)
RobMeades 0:5c46cb3be899 128 {
RobMeades 0:5c46cb3be899 129 FlashSetReqDlMsg_t msg;
RobMeades 0:5c46cb3be899 130 msg.onNotOff = onNotOff;
RobMeades 0:5c46cb3be899 131
RobMeades 0:5c46cb3be899 132 return gMessageCodec.encodeFlashSetReqDlMsg (pBuffer, &msg);
RobMeades 0:5c46cb3be899 133 }
RobMeades 0:5c46cb3be899 134
RobMeades 0:5c46cb3be899 135 // Wrap encodeFlashGetReqDlMsg
RobMeades 0:5c46cb3be899 136 uint32_t __cdecl encodeFlashGetReqDlMsg (char * pBuffer)
RobMeades 0:5c46cb3be899 137 {
RobMeades 0:5c46cb3be899 138 return gMessageCodec.encodeFlashGetReqDlMsg (pBuffer);
RobMeades 0:5c46cb3be899 139 }
RobMeades 0:5c46cb3be899 140
RobMeades 0:5c46cb3be899 141 // ----------------------------------------------------------------
RobMeades 0:5c46cb3be899 142 // MESSAGE DECODE WRAPPER FUNCTIONS
RobMeades 0:5c46cb3be899 143 // ----------------------------------------------------------------
RobMeades 0:5c46cb3be899 144
RobMeades 0:5c46cb3be899 145 // Unpack a gpioState struct from with a uint32_t value
RobMeades 0:5c46cb3be899 146 void __cdecl unpackGpioState (uint32_t value,
RobMeades 0:5c46cb3be899 147 uint32_t *pGpio,
RobMeades 0:5c46cb3be899 148 bool * pInputNotOutput,
RobMeades 0:5c46cb3be899 149 bool * pOnNotOff)
RobMeades 0:5c46cb3be899 150 {
RobMeades 0:5c46cb3be899 151 *pGpio = (uint32_t) ((value & 0x00FF0000) >> 16);
RobMeades 0:5c46cb3be899 152 if (pInputNotOutput != NULL)
RobMeades 0:5c46cb3be899 153 {
RobMeades 0:5c46cb3be899 154 *pInputNotOutput = (bool) ((value & 0x0000FF00) >> 8);
RobMeades 0:5c46cb3be899 155 }
RobMeades 0:5c46cb3be899 156 if (pOnNotOff != NULL)
RobMeades 0:5c46cb3be899 157 {
RobMeades 0:5c46cb3be899 158 *pOnNotOff = (bool) (value & 0x000000FF);
RobMeades 0:5c46cb3be899 159 }
RobMeades 0:5c46cb3be899 160 }
RobMeades 0:5c46cb3be899 161
RobMeades 0:5c46cb3be899 162 // Wrap decodeUlMsg
RobMeades 0:5c46cb3be899 163 uint32_t __cdecl decodeUlMsg (const char ** ppInBuffer,
RobMeades 0:5c46cb3be899 164 uint32_t sizeInBuffer,
RobMeades 0:5c46cb3be899 165 uint32_t * pContents)
RobMeades 0:5c46cb3be899 166 {
RobMeades 0:5c46cb3be899 167 MessageCodec::DecodeResult_t decodeResult;
RobMeades 0:5c46cb3be899 168 UlMsgUnion_t outBuffer;
RobMeades 0:5c46cb3be899 169 decodeResult = gMessageCodec.decodeUlMsg (ppInBuffer,
RobMeades 0:5c46cb3be899 170 sizeInBuffer,
RobMeades 0:5c46cb3be899 171 &outBuffer);
RobMeades 0:5c46cb3be899 172 switch (decodeResult)
RobMeades 0:5c46cb3be899 173 {
RobMeades 0:5c46cb3be899 174 case (MessageCodec::DECODE_RESULT_INIT_IND_UL_MSG):
RobMeades 0:5c46cb3be899 175 *pContents = (uint32_t) outBuffer.initIndUlMsg.wakeUpCode;
RobMeades 0:5c46cb3be899 176 break;
RobMeades 0:5c46cb3be899 177 case (MessageCodec::DECODE_RESULT_SERIAL_NUMBER_GET_CNF_UL_MSG):
RobMeades 0:5c46cb3be899 178 *pContents = outBuffer.serialNumberCnfUlMsg.serialNumber;
RobMeades 0:5c46cb3be899 179 break;
RobMeades 0:5c46cb3be899 180 case (MessageCodec::DECODE_RESULT_SERIAL_NUMBER_IND_UL_MSG):
RobMeades 0:5c46cb3be899 181 *pContents = outBuffer.serialNumberIndUlMsg.serialNumber;
RobMeades 0:5c46cb3be899 182 break;
RobMeades 0:5c46cb3be899 183 case (MessageCodec::DECODE_RESULT_VOLUME_IND_UL_MSG):
RobMeades 0:5c46cb3be899 184 *pContents = outBuffer.volumeIndUlMsg.volumeLitres;
RobMeades 0:5c46cb3be899 185 break;
RobMeades 0:5c46cb3be899 186 case (MessageCodec::DECODE_RESULT_RSSI_IND_UL_MSG):
RobMeades 0:5c46cb3be899 187 *pContents = outBuffer.rssiIndUlMsg.rssi;
RobMeades 0:5c46cb3be899 188 break;
RobMeades 0:5c46cb3be899 189 case (MessageCodec::DECODE_RESULT_READING_INTERVAL_SET_CNF_UL_MSG):
RobMeades 0:5c46cb3be899 190 *pContents = outBuffer.readingIntervalSetCnfUlMsg.readingIntervalSeconds;
RobMeades 0:5c46cb3be899 191 break;
RobMeades 0:5c46cb3be899 192 case (MessageCodec::DECODE_RESULT_READING_INTERVAL_GET_CNF_UL_MSG):
RobMeades 0:5c46cb3be899 193 *pContents = outBuffer.readingIntervalGetCnfUlMsg.readingIntervalSeconds;
RobMeades 0:5c46cb3be899 194 break;
RobMeades 0:5c46cb3be899 195 case (MessageCodec::DECODE_RESULT_GPIO_SET_CNF_UL_MSG):
RobMeades 0:5c46cb3be899 196 *pContents = (uint32_t) outBuffer.gpioSetCnfUlMsg;
RobMeades 0:5c46cb3be899 197 break;
RobMeades 0:5c46cb3be899 198 case (MessageCodec::DECODE_RESULT_GPIO_GET_CNF_UL_MSG):
RobMeades 0:5c46cb3be899 199 *pContents = (uint32_t) outBuffer.gpioGetCnfUlMsg;
RobMeades 0:5c46cb3be899 200 break;
RobMeades 0:5c46cb3be899 201 case (MessageCodec::DECODE_RESULT_LED_SET_CNF_UL_MSG):
RobMeades 0:5c46cb3be899 202 *pContents = (uint32_t) outBuffer.ledSetCnfUlMsg.onNotOff;
RobMeades 0:5c46cb3be899 203 break;
RobMeades 0:5c46cb3be899 204 case (MessageCodec::DECODE_RESULT_LED_GET_CNF_UL_MSG):
RobMeades 0:5c46cb3be899 205 *pContents = (uint32_t) outBuffer.ledGetCnfUlMsg.onNotOff;
RobMeades 0:5c46cb3be899 206 break;
RobMeades 0:5c46cb3be899 207 case (MessageCodec::DECODE_RESULT_FLASH_SET_CNF_UL_MSG):
RobMeades 0:5c46cb3be899 208 *pContents = (uint32_t) outBuffer.flashSetCnfUlMsg.onNotOff;
RobMeades 0:5c46cb3be899 209 break;
RobMeades 0:5c46cb3be899 210 case (MessageCodec::DECODE_RESULT_FLASH_GET_CNF_UL_MSG):
RobMeades 0:5c46cb3be899 211 *pContents = (uint32_t) outBuffer.flashGetCnfUlMsg.onNotOff;
RobMeades 0:5c46cb3be899 212 break;
RobMeades 0:5c46cb3be899 213 default:
RobMeades 0:5c46cb3be899 214 // The decodeResult will be left as Unknown message
RobMeades 0:5c46cb3be899 215 break;
RobMeades 0:5c46cb3be899 216 }
RobMeades 0:5c46cb3be899 217
RobMeades 0:5c46cb3be899 218 return decodeResult;
RobMeades 0:5c46cb3be899 219 }
RobMeades 0:5c46cb3be899 220
RobMeades 0:5c46cb3be899 221 // ----------------------------------------------------------------
RobMeades 0:5c46cb3be899 222 // MISC FUNCTIONS
RobMeades 0:5c46cb3be899 223 // ----------------------------------------------------------------
RobMeades 0:5c46cb3be899 224
RobMeades 0:5c46cb3be899 225 void initDll (void (*printToConsole) (const char *))
RobMeades 0:5c46cb3be899 226 {
RobMeades 0:5c46cb3be899 227 gMessageCodec.initDll (printToConsole);
RobMeades 0:5c46cb3be899 228 }
RobMeades 0:5c46cb3be899 229
RobMeades 0:5c46cb3be899 230 #ifdef __cplusplus
RobMeades 0:5c46cb3be899 231 } // extern "C"
RobMeades 0:5c46cb3be899 232 #endif
RobMeades 0:5c46cb3be899 233
RobMeades 0:5c46cb3be899 234 // End Of File