Library for LoRa communication using MultiTech MDOT.

Dependents:   mDot_test_rx adc_sensor_lora mDotEVBM2X mDot_AT_firmware ... more

Function documentation is in mDot.h

Warning

Using libmDot 2.0.3 and above with an existing application may require a change in the MacEvent handler!
Compile applications with mbed v121 and mbed-rtos v116 libraries.

In AT Command Firmware remove line 803.

CommandTerminal/CommandTerminal.cpp

        delete[] info->RxBuffer;

Likewise, if your application is handling events from the library asynchronously.

Files at this revision

API Documentation at this revision

Comitter:
Mike Fiore
Date:
Wed Jun 24 17:03:08 2015 -0500
Parent:
0:c62615f15125
Child:
2:6385bf37bfe7
Commit message:
add README, LICENSE, headers, and library - from git tag mbed_24June2015

Changed in this revision

LICENSE.txt Show annotated file Show diff for this revision Revisions of this file
MTSCircularBuffer.h Show annotated file Show diff for this revision Revisions of this file
MTSLog.h Show annotated file Show diff for this revision Revisions of this file
MTSText.h Show annotated file Show diff for this revision Revisions of this file
README.txt Show annotated file Show diff for this revision Revisions of this file
Utils.h Show annotated file Show diff for this revision Revisions of this file
libmDot.ar Show annotated file Show diff for this revision Revisions of this file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/LICENSE.txt	Wed Jun 24 17:03:08 2015 -0500
@@ -0,0 +1,31 @@
+IMPORTANT – READ BEFORE OPERATING OR INSTALLING THE MULTI-TECH PRODUCT OR SOFTWARE
+
+MULTI-TECH SYSTEMS, INC.
+END USER LICENSE AGREEMENT
+PLEASE READ THIS END USER LICENSE AGREEMENT (“AGREEMENT”) CAREFULLY BEFORE USING THE MULTI-TECH PRODUCT, INSTALLING OR ACCESSING THE SOFTWARE, OR DOWNLOADING ANY SOFTWARE UPDATES FOR USE WITH THE MULTI-TECH PRODUCT. BY USING THE MULTI-TECH PRODUCT, INSTALLING OR ACCESSING THE SOFTWARE OR DOWNLOADING SOFTWARE UPDATES FOR THE MULTI-TECH PRODUCT, YOU AGREE TO BE BOUND BY THE TERMS OF THIS LICENSE. IF YOU DO NOT AGREE TO THE TERMS OF THIS AGREEMENT, DO NOT USE THE MULTI-TECH PRODUCT, INSTALL OR ACCESS THE SOFTWARE, OR DOWNLOAD THE SOFTWARE UPDATES. INSTEAD, PLEASE CONTACT MULTI-TECH’S CUSTOMER SERVICE DEPARTMENT AT customerservice@multitech.com. 
+
+1. DEFINITIONS. The following terms are defined as follows: (a) ”Documentation” means any user guides, data sheets, manuals, specifications, or other written description of the Software provided by Multi-Tech; (b) “Multi-Tech” means, collectively, Multi-Tech Systems, Inc., its directors, officers, employees, representatives, agents, licensors, and affiliated entities; (c) “Software” means, collectively, (i) the software provided by Multi-Tech, (ii) the software pre-installed on any Multi-Tech product, and (iii) any Documentation; and (d) “You” means you, an individual, if you are accessing the Software on your behalf, or if you are accessing the Software on behalf of your employer or a third party, “You” means the legal entity of the employer or third party as applicable. 
+
+2. ACCEPTANCE. You accept the terms of this Agreement either by: (a) clicking “I Accept” when offered by Multi-Tech; or (b) using the Multi-Tech product, installing or accessing the Software or downloading Software updates. You acknowledge and agree that You have read and understood this Agreement, have had an opportunity to discuss this Agreement with Your legal and other advisors, and agree to be bound by the terms and conditions of this Agreement. 
+
+3. LICENSE. The Software is licensed, and is not sold. Subject to the terms of this Agreement, You are granted a limited, non-transferable, non-exclusive license that permits You to use the Software with the Multi-Tech product for internal business or personal use. This License does not grant to You any rights to re-license or sublicense or otherwise resell or re-distribute the Software. This License does not grant to You any rights to obtain future Software updates (e.g., upgrades, fixes, etc.). If future Software updates are obtained by You, whether through a version release, Multi-Tech technical support, or another Multi-Tech authorized method, such Software updates are subject to the terms of this Agreement. If applicable, any previous version of the Software must be destroyed or returned to Multi-Tech within 90 days of receipt of the Software updates. 
+
+4. RESTRICTIONS. This Agreement does not authorize You to: (a) sell, lease, copy, assign, license, sublicense, translate, distribute, or otherwise transfer, in whole or in part, the Software; (b) modify, distribute, copy, reproduce, or publish, in whole or in part, the Documentation; (c) use the Software on a timesharing basis to operate a service bureau facility or providing hosting of the Software for the benefit of third parties; (d) decompile, disassemble, reverse engineer or otherwise attempt to derive source code from the Software, except as, and then only to the extent, required by applicable law or an applicable open source license; (e) modify or create derivative works of the Software; or (f) create, develop, license, install, use or deploy any software or services to circumvent, enable, modify or provide access, permissions or rights which violate the technical restrictions in the Software. You acknowledge and agree that the Software and Documentation is subject to U.S. export control laws, including the U.S. Export Administration Act and its associated regulations, and may be subject to export or import regulations in other countries. You agree to strictly comply with all such regulations and acknowledge that You are responsible for obtaining any applicable licenses to export, re-export or import the Software and Documentation.
+
+5. OWNERSHIP; CONFIDENTIALITY. You agree that the Software contains trade secret information, copyrights, trademarks, and other intellectual property rights that are owned by Multi-Tech Systems, Inc. or its licensors. Multi-Tech retains all right, title and interest in and to the Software. All rights not expressly granted herein are reserved. You acknowledge and agree that the Software was developed at considerable time and expense by Multi-Tech and is confidential to and a trade secret of Multi-Tech. You agree to maintain the Software in strict confidence and not disclose the Software or provide access thereto to any other third party.
+
+6. THIRD PARTY SOFTWARE. The Software may contain software from sources other than Multi-Tech Systems, Inc., including without limitation, third party proprietary software and free and open source software. To the extent the Software includes free and open source software, it is subject to the applicable free and open source software license. Multi-Tech Systems, Inc. makes available information related to the free and open source software at www.multitech.com/licensing.go or upon written request. 
+
+7. DISCLAIMER OF WARRANTY. EXCEPT AS SET FORTH IN THE MULTI-TECH STANDARD WARRANTY THAT ACCOMPANIES THE MULTI-TECH PRODUCT, ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND WARRANTIES OF THE SOFTWARE, SUCH AS THE IMPLIED WARRANTY OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND NONINFRINGEMENT, OR OTHERWISE ARISING FROM A COURSE OF DEALING, USAGE, OR TRADE PRACTICE, ARE HEREBY EXCLUDED TO THE EXTENT ALLOWED BY APPLICABLE LAW. 
+
+8. LIMITATION OF LIABILITY. TO THE FULLEST EXTENT ALLOWABLE BY APPLICABLE LAW, Multi-Tech IS NOT LIABLE TO YOU FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL, PUNITIVE, OR CONSEQUENTIAL DAMAGES, INCLUDING WITHOUT LIMITATION, LOST PROFITS, LOST REVENUE AND BUSINESS INTERRUPTION, ARISING OUT OF THE SOFTWARE, WHETHER BASED ON CONTRACT, TORT, OR OTHER THEORY AND REGARDLESS OF WHETHER SUCH PERSON OR ENTITY SHALL BE ADVISED OR HAVE REASON TO KNOW OF THE POSSIBILITY OF SUCH DAMAGES. IF Multi-Tech IS EVER DEEMED LIABLE TO YOU, ITS AGGREGATE LIABILITY, WHETHER BASED IN TORT, CONTRACT, STATUTE OR OTHERWISE, IS LIMITED TO THE NET AMOUNT PAID BY YOU FOR THE Multi-Tech PRODUCT.
+
+9. TERMINATION. Multi-Tech may, upon written notice to You, immediately terminate this Agreement and the warranty period set forth in the Multi-Tech Standard Warranty if You breach the terms set forth in this Agreement.
+
+10. GENERAL. This Agreement: (a) contains the complete and exclusive agreement regarding its subject matter, (b) supersedes all prior or contemporaneous written or oral agreements, representations, promises, and understandings related thereto (except those previously referenced third party license agreements), (c) may be modified, supplemented or amended by Multi-Tech with or without notice (which modification, supplement or amendment may be made available with Software updates or future purchases of Multi-Tech products), (d) is between sophisticated parties, and so the rule of construing ambiguities against the drafter will not apply, (e) will be governed by Minnesota law, without regard to its choice of law provisions, and (f) is binding upon the parties and their successors, will not benefit or create any right or cause of action for any other person or entity other than the parties, except Multi-Tech’s third party licensors. No waiver of this Agreement is effective by Multi-Tech unless in writing signed by a duly authorized representative. If any provision of this Agreement is held to be invalid, it shall be interpreted so as to best advance the spirit of this Agreement and Multi-Tech’s intent. All disputes arising from this Agreement shall be heard in the exclusive jurisdiction of the state courts of Minnesota, U.S.A. and You agree to submit to the personal jurisdiction of such courts. You acknowledge that You are age thirteen or older, and by accepting this Agreement, You agree that You are fully authorized, able and competent to enter into this Agreement.
+
+   Multi-Tech Systems, Inc. 
+   2205 Woodale Drive
+   Mounds View, Minnesota 55112
+   customerservice@multitech.com 
+   20130910
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/MTSCircularBuffer.h	Wed Jun 24 17:03:08 2015 -0500
@@ -0,0 +1,165 @@
+/************************************************
+ * MultiTech MTDOT Library
+ * Copyright (c) 2015 MultiTech Systems
+ *
+ * See LICENSE file for license information
+ ***********************************************/
+
+#ifndef MTSCIRCULARBUFFER_H
+#define MTSCIRCULARBUFFER_H
+
+#include "Utils.h"
+
+namespace mts
+{
+
+/** This class provides a circular byte buffer meant for temporary storage
+* during IO transactions.  It contains many of the common methods you
+* would expect from a circular buffer like read, write, and various
+* methods for checking the size or status.  It should be noted that
+* this class does not include any special code for thread safety like
+* a lock.  In most cases this is not problematic, but is something
+* to be aware of.
+*/
+class MTSCircularBuffer
+{
+public:
+    /** Creates an MTSCircularBuffer object with the specified static size.
+    *
+    * @prarm bufferSize size of the buffer in bytes.
+    */
+    MTSCircularBuffer(int bufferSize);
+
+    /** Destructs an MTSCircularBuffer object and frees all related resources.
+    */
+    ~MTSCircularBuffer();
+
+    /** This method enables bulk reads from the buffer.  If more data is
+    * requested then available it simply returns all remaining data within the
+    * buffer.
+    *
+    * @param data the buffer where data read will be added to.
+    * @param length the amount of data in bytes to be read into the buffer.
+    * @returns the total number of bytes that were read.
+    */
+    int read(char* data, int length);
+
+    /** This method reads a single byte from the buffer.
+    *
+    * @param data char where the read byte will be stored.
+    * @returns 1 if byte is read or 0 if no bytes available.
+    */
+    int read(char& data);
+
+    /** This method enables bulk writes to the buffer. If more data
+    * is requested to be written then space available the method writes
+    * as much data as possible and returns the actual amount written.
+    *
+    * @param data the byte array to be written.
+    * @param length the length of data to be written from the data paramter.
+    * @returns the number of bytes written to the buffer, which is 0 if
+    * the buffer is full.
+    */
+    int write(const char* data, int length);
+
+    /** This method writes a signle byte as a char to the buffer.
+    *
+    * @param data the byte to be written as a char.
+    * @returns 1 if the byte was written or 0 if the buffer was full.
+    */
+    int write(char data);
+
+    /** This method is used to setup a callback funtion when the buffer reaches
+    * a certain threshold. The threshold condition is checked after every read
+    * and write call is completed. The condition is made up of both a threshold
+    * value and operator. An example that would trigger a callback is if the
+    * threshold was 10, the operator GREATER, and there were 12 bytes added to an
+    * empty buffer.
+    *
+    * @param tptr a pointer to the object to be called when the condition is met.
+    * @param mptr a pointer to the function within the object to be called when
+    * the condition is met.
+    * @param threshold the value in bytes to be used as part of the condition.
+    * @param op the operator to be used in conjunction with the threshold
+    * as part of the condition.
+    */
+    template<typename T>
+    void attach(T *tptr, void( T::*mptr)(void), int threshold, RelationalOperator op) {
+        _threshold = threshold;
+        _op = op;
+        notify.attach(tptr, mptr);
+    }
+
+    /** This method is used to setup a callback funtion when the buffer reaches
+    * a certain threshold. The threshold condition is checked after every read
+    * and write call is completed. The condition is made up of both a threshold
+    * value and operator. An example that would trigger a callback is if the
+    * threshold was 10, the operator GREATER, and there were 12 bytes added to an
+    * empty buffer.
+    *
+    * @param fptr a pointer to the static function to be called when the condition
+    * is met.
+    * @param threshold the value in bytes to be used as part of the condition.
+    * @param op the operator to be used in conjunction with the threshold
+    * as part of the condition.
+    */
+    void attach(void(*fptr)(void), int threshold, RelationalOperator op) {
+        _threshold = threshold;
+        _op = op;
+        notify.attach(fptr);
+    }
+
+    /** This method returns the size of the storage space currently allocated for
+    * the buffer. This value is equivalent to the one passed into the constructor.
+    * This value is equal or greater than the size() of the buffer.
+    *
+    * @returns the allocated size of the buffer in bytes.
+    */
+    int capacity();
+
+    /** This method returns the amount of space left for writing.
+    *
+    * @returns numbers of unused bytes in buffer.
+    */
+    int remaining();
+
+    /** This method returns the number of bytes available for reading.
+    *
+    * @returns number of bytes currently in buffer.
+    */
+    int size();
+
+    /** This method returns whether the buffer is full.
+    *
+    * @returns true if full, otherwise false.
+    */
+    bool isFull();
+
+    /** This method returns whether the buffer is empty.
+    *
+    * @returns true if empty, otherwise false.
+    */
+    bool isEmpty();
+
+    /** This method clears the buffer. This is done through
+    * setting the internal read and write indexes to the same
+    * value and is therefore not an expensive operation.
+    */
+    void clear();
+
+
+private:
+    int bufferSize; // total size of the buffer
+    char* buffer; // internal byte buffer as a character buffer
+    int readIndex; // read index for circular buffer
+    int writeIndex; // write index for circular buffer
+    int bytes; // available data
+    FunctionPointer notify; // function pointer used for the internal callback notification
+    int _threshold; // threshold for the notification
+    RelationalOperator _op; // operator that determines the direction of the threshold
+    void checkThreshold(); // private function that checks thresholds and processes notifications
+};
+
+}
+
+#endif /* MTSCIRCULARBUFFER_H */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/MTSLog.h	Wed Jun 24 17:03:08 2015 -0500
@@ -0,0 +1,99 @@
+/************************************************
+ * MultiTech MTDOT Library
+ * Copyright (c) 2015 MultiTech Systems
+ *
+ * See LICENSE file for license information
+ ***********************************************/
+
+#ifndef MTSLOG_H
+#define MTSLOG_H
+
+#ifdef MTS_DEBUG
+#define logFatal(format, ...) \
+    MTSLog::printMessage(MTSLog::FATAL_LEVEL, "%s:%s:%s| [%s] " format "\r\n", __FILE__, __func__, __LINE__, MTSLog::FATAL_LABEL, ##__VA_ARGS__)
+#define logError(format, ...) \
+    MTSLog::printMessage(MTSLog::ERROR_LEVEL, "%s:%s:%s| [%s] " format "\r\n", __FILE__, __func__, __LINE__, MTSLog::ERROR_LABEL, ##__VA_ARGS__)
+#define logWarning(format, ...) \
+    MTSLog::printMessage(MTSLog::WARNING_LEVEL, "%s:%s:%s| [%s] " format "\r\n", __FILE__, __func__, __LINE__, MTSLog::WARNING_LABEL, ##__VA_ARGS__)
+#define logInfo(format, ...) \
+    MTSLog::printMessage(MTSLog::INFO_LEVEL, "%s:%s:%s| [%s] " format "\r\n", __FILE__, __func__, __LINE__, MTSLog::INFO_LABEL, ##__VA_ARGS__)
+#define logDebug(format, ...) \
+    MTSLog::printMessage(MTSLog::DEBUG_LEVEL, "%s:%s:%s| [%s] " format "\r\n", __FILE__, __func__, __LINE__, MTSLog::DEBUG_LABEL, ##__VA_ARGS__)
+#define logTrace(format, ...) \
+    MTSLog::printMessage(MTSLog::TRACE_LEVEL, "%s:%s:%s| [%s] " format "\r\n", __FILE__, __func__, __LINE__, MTSLog::TRACE_LABEL, ##__VA_ARGS__)
+#else
+#define logFatal(format, ...) \
+    MTSLog::printMessage(MTSLog::FATAL_LEVEL, "[%s] " format "\r\n", MTSLog::FATAL_LABEL, ##__VA_ARGS__)
+#define logError(format, ...) \
+    MTSLog::printMessage(MTSLog::ERROR_LEVEL, "[%s] " format "\r\n", MTSLog::ERROR_LABEL, ##__VA_ARGS__)
+#define logWarning(format, ...) \
+    MTSLog::printMessage(MTSLog::WARNING_LEVEL, "[%s] " format "\r\n", MTSLog::WARNING_LABEL, ##__VA_ARGS__)
+#define logInfo(format, ...) \
+    MTSLog::printMessage(MTSLog::INFO_LEVEL, "[%s] " format "\r\n", MTSLog::INFO_LABEL, ##__VA_ARGS__)
+#define logDebug(format, ...) \
+    MTSLog::printMessage(MTSLog::DEBUG_LEVEL, "[%s] " format "\r\n", MTSLog::DEBUG_LABEL, ##__VA_ARGS__)
+#define logTrace(format, ...) \
+    MTSLog::printMessage(MTSLog::TRACE_LEVEL, "[%s] " format "\r\n", MTSLog::TRACE_LABEL, ##__VA_ARGS__)
+#endif
+
+namespace mts {
+
+class MTSLog
+{
+public:
+
+    /** Enum of log levels.
+     */
+    enum logLevel {
+        NONE_LEVEL = 0,
+        FATAL_LEVEL = 1,
+        ERROR_LEVEL = 2,
+        WARNING_LEVEL = 3,
+        INFO_LEVEL = 4,
+        DEBUG_LEVEL = 5,
+        TRACE_LEVEL = 6
+    };
+
+    /** Print log message.
+     */
+    static void printMessage(int level, const char* format, ...);
+
+    /** Determine if the given level is currently printable.
+     */
+    static bool printable(int level);
+
+    /** Set log level
+     * Messages with lower priority than the current level will not be printed.
+     * If the level is set to NONE, no messages will print.
+     */
+    static void setLogLevel(int level);
+
+    /** Get the current log level.
+     */
+    static int getLogLevel();
+
+    /** Get string representation of the current log level.
+     */
+    static const char* getLogLevelString();
+
+    static const char* NONE_LABEL;
+    static const char* FATAL_LABEL;
+    static const char* ERROR_LABEL;
+    static const char* WARNING_LABEL;
+    static const char* INFO_LABEL;
+    static const char* DEBUG_LABEL;
+    static const char* TRACE_LABEL;
+
+private:
+
+    /** Constructor
+     */
+    MTSLog();
+
+    static int currentLevel;
+
+};
+
+}
+
+#endif
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/MTSText.h	Wed Jun 24 17:03:08 2015 -0500
@@ -0,0 +1,84 @@
+/************************************************
+ * MultiTech MTDOT Library
+ * Copyright (c) 2015 MultiTech Systems
+ *
+ * See LICENSE file for license information
+ ***********************************************/
+
+#ifndef MTSTEXT_H
+#define MTSTEXT_H
+
+#include <string>
+#include <vector>
+#include <stddef.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <string.h>
+
+namespace mts
+{
+
+/** This class contains a number of static methods for manipulating strings and other
+* text data.
+*/
+class Text
+{
+public:
+    /** This static method can be used to pull out a string at the next line break. A
+    * break can either be a newline '\n', carriage return '\r' or both.
+    *
+    * @param source the source string to look for the line break on.
+    * @param start the start postion within the string to begin looking for the line
+    * break.
+    * @param cursor this value will be updated with the index for the next available character
+    * after the line break. If a line break is not found returns -1.
+    * @returns the string beginning with the start index up to including the line breaks.
+    */
+    static std::string getLine(const std::string& source, const size_t& start, size_t& cursor);
+
+    /** This is a static method for splitting strings using a delimeter value.
+    *
+    * @param str the string to try and split.
+    * @param delimiter the delimeter value to split on as a character.
+    * @param limit the maximum number of splits. If equal to 0 it splits as amny times as possible.
+    * The default is 0.
+    * @returns an ordered vector of strings conatining the splits of the original string.
+    */
+    static std::vector<std::string> split(const std::string& str, char delimiter, int limit = 0);
+
+    /** This is a static method for splitting strings using a delimeter value.
+    *
+    * @param str the string to try and split.
+    * @param delimiter the delimeter value to split on as a string.
+    * @param limit the maximum number of splits. If equal to 0 it splits as amny times as possible.
+    * The default is 0.
+    * @returns an ordered vector of strings conatining the splits of the original string.
+    */
+    static std::vector<std::string> split(const std::string& str, const std::string& delimiter, int limit = 0);
+    
+    static std::string readString(char* index, int length);
+
+    static std::string toUpper(const std::string str);
+
+    std::string float2String(double val, int precision);
+
+    static std::string bin2hexString(const std::vector<uint8_t>& data, const char* delim = "", bool leadingZeros = false);
+
+    static std::string bin2hexString(const uint8_t* data, const uint32_t len, const char* delim = "", bool leadingZeros = false);
+
+    static void ltrim(std::string& str, const char* args);
+
+    static void rtrim(std::string& str, const char* args);
+
+    static void trim(std::string& str, const char* args);
+
+private:
+    // Safety for class with only static methods
+    Text();
+    Text(const Text& other);
+    Text& operator=(const Text& other);
+};
+
+}
+
+#endif
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/README.txt	Wed Jun 24 17:03:08 2015 -0500
@@ -0,0 +1,88 @@
+---------------------------------------
+Getting Started with the mDot Library
+---------------------------------------
+
+This README should get you started using the mDot library with your MultiTech mDot.
+
+License information can be found in the accompanying LICENSE file.
+
+The mDot header has documentation for all the public functions that will be useful to consumers of
+the library.
+
+The following source code provides an example application which configures the mDot, connects to a
+MultiTech Conduit gateway with matching configuration, and sends data packets to the gateway.
+
+/**************
+  SAMPLE CODE
+**************/
+
+#include "mbed.h"
+#include "mDot.h"
+#include <string>
+#include <vector>
+
+// these options must match the settings on your Conduit in
+// /var/config/lora/lora-network-server.conf
+static std::string config_network_name = "my_lora_network";
+static std::string config_network_pass = "my_network_password";
+static uint8_t config_frequency_sub_band = 1;
+
+void log_error(mDot* dot, const char* msg, int32_t retval);
+
+int main() {
+    int32_t ret;
+    mDot* dot;
+    std::vector<uint8_t> data;
+    std::string data_str = "hello world!";
+
+    // get a mDot handle
+    dot = mDot::getInstance();
+
+    // reset to default config so we know what state we're in
+    dot->resetConfig();
+
+    // print library version information
+    printf("version: %s\r\n", dot->getId().c_str());
+
+    // set up the mDot with our network information
+    printf("setting frequency sub band\r\n");
+    if ((ret = dot->setFrequencySubBand(config_frequency_sub_band)) != mDot::MDOT_OK) {
+        log_error(dot, "failed to set frequency sub band", ret);
+    }
+    printf("setting network name\r\n");
+    if ((ret = dot->setNetworkName(config_network_name)) != mDot::MDOT_OK) {
+        log_error(dot, "failed to set network name", ret);
+    }
+    printf("setting network password\r\n");
+    if ((ret = dot->setNetworkPassphrase(config_network_pass)) != mDot::MDOT_OK) {
+        log_error(dot, "failed to set network password", ret);
+    }
+
+    // attempt to join the network
+    printf("joining network\r\n");
+    if ((ret = dot->joinNetwork()) != mDot::MDOT_OK) {
+        log_error(dot, "failed to join network", ret);
+    }
+
+    // format data for sending to the gateway
+    for (std::string::iterator it = data_str.begin(); it != data_str.end(); it++)
+        data.push_back((uint8_t) *it);
+
+    while (true) {
+        // send the data
+        // ACKs are enabled by default, so we're expecting to get one back
+        if ((ret = dot->send(data)) != mDot::MDOT_OK) {
+            log_error(dot, "failed to send", ret);
+        } else {
+            printf("successfully sent data to gateway\r\n");
+        }
+
+        wait(5);
+    }
+
+    return 0;
+}
+
+void log_error(mDot* dot, const char* msg, int32_t retval) {
+    printf("%s - %ld:%s, %s\r\n", msg, retval, mDot::getReturnCodeString(retval).c_str(), dot->getLastError().c_str());
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/Utils.h	Wed Jun 24 17:03:08 2015 -0500
@@ -0,0 +1,48 @@
+/************************************************
+ * MultiTech MTDOT Library
+ * Copyright (c) 2015 MultiTech Systems
+ *
+ * See LICENSE file for license information
+ ***********************************************/
+
+#ifndef UTILS_H
+#define UTILS_H
+
+#include <string>
+
+//Defines a max function that can be used.
+inline int mts_max(int a, int b) { return a > b ? a : b; }
+
+//Defines a min function that can be used.
+inline int mts_min(int a, int b) { return a < b ? a : b; }
+
+///An enumeration for relational operators
+enum RelationalOperator {
+    GREATER, LESS, EQUAL, GREATER_EQUAL, LESS_EQUAL
+};
+
+/** A static method for getting a string representation for the RelationalOperator
+* enumeration.
+*
+* @param relationalOperator a RelationalOperator enumeration.
+* @returns the enumeration name as a string.
+*/
+static std::string getRelationalOperatorNames(RelationalOperator relationalOperator)
+{
+    switch(relationalOperator) {
+        case GREATER:
+            return "GREATER";
+        case LESS:
+            return "LESS";
+        case EQUAL:
+            return "EQUAL";
+        case GREATER_EQUAL:
+            return "GREATER_EQUAL";
+        case LESS_EQUAL:
+            return "LESS_EQUAL";
+        default:
+            return "UNKNOWN ENUM";
+    }
+}
+
+#endif
Binary file libmDot.ar has changed