LoRa_Miun_Lib

Dependents:   Light

Fork of LoRa_Miun_lib by BIN WANG

Files at this revision

API Documentation at this revision

Comitter:
biwa1400
Date:
Mon Oct 02 16:09:14 2017 +0000
Parent:
2:3ecde145ebf2
Commit message:
20171002

Changed in this revision

LoRa.cpp Show diff for this revision Revisions of this file
LoRa.h Show diff for this revision Revisions of this file
MIUN.LoRa.cpp Show annotated file Show diff for this revision Revisions of this file
MIUN.LoRa.h Show annotated file Show diff for this revision Revisions of this file
--- a/LoRa.cpp	Wed May 03 08:49:14 2017 +0000
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,611 +0,0 @@
-#include "LoRa.h"
-#include "mbed.h"
-#include "mDot.h"
-#include "MacEvents.h"
-#include "MTSLog.h"
-#include "MTSText.h"
-#include <vector>
-#include <string>
-
-
-MIUN::LoRa::LoRa():macCommandEvent(*this)
-{
-
-    //1. Set dot
-    dot = mDot::getInstance();
-    
-    //2. Register Event
-     dot->setEvents(&macCommandEvent);
-     
-     //3. getDefaultSleepTime
-     defaultSleepTime = readSleepTime();
-
-    //4. set batteryLevel
-    batteryLevel = 255;
-    
-    //5. Print Version
-    logInfo("Library Version: %s", dot->getId().c_str());
-
-    
-}
-
-void MIUN::LoRa::reset()
-{
-    // start from a well-known state
-    logInfo("defaulting Dot configuration");
-    dot->resetConfig();
-    dot->resetNetworkSession();
-}
-
-
-/*** public method ***/
-
-std::string MIUN::LoRa::receive(int* port)
-{
-    int32_t ret;
-    vector<uint8_t> receive_data;
-     if ((ret = dot->recv(receive_data)) != mDot::MDOT_OK) 
-    {
-            logError("failed to recv: [%d][%s]", ret, mDot::getReturnCodeString(ret).c_str());
-            return "";
-    } 
-    else 
-    {
-            //1. Set Receive Payload
-            string str(receive_data.begin(),receive_data.end());
-            //2. Set Receive Port
-            *port = receivePort;
-            receivePort = -1;
-            return str;
-    }           
-}
-
-
-bool MIUN::LoRa::send_basic(std::string input_data)
-{
-    int32_t ret;
-    vector<uint8_t> sent_data;
-     logInfo("Send with %s", dot->getDateRateDetails(dot->getTxDataRate()).c_str());
-    for (std::string::iterator it = input_data.begin(); it != input_data.end(); it++)
-    {
-        sent_data.push_back((uint8_t) *it);   
-    }
-     std::vector<uint8_t> sendData;
-        sendData.push_back(0x80); 
-    /*
-    for (int i=0;i<commandLength;i++)
-    {
-        sendData.push_back(command[i]);   
-    }
-    */
-    if (dot->injectMacCommand(sendData) != mDot::MDOT_OK) 
-    {
-        logError("failed to injectMacCommand");
-    }
-    else
-    {
-        logInfo("injectMacCommand Successful");
-    }
-    if ((ret = dot->send(sent_data)) != mDot::MDOT_OK) 
-    {
-        logError("failed to send", ret, mDot::getReturnCodeString(ret).c_str());
-        return false;
-    } 
-    else 
-    {
-        logInfo("successfully sent data to gateway");
-        return true;
-    }
-
-}
-
-
-
-void MIUN::LoRa::sleep(const uint32_t& interval_s)
-{
-    uint32_t sleep_time = std::max(interval_s*1000, (uint32_t)dot->getNextTxMs()) / 1000;
-        logInfo("sleep %u seconds until next free channel",sleep_time);
-    dot->sleep(sleep_time, mDot::RTC_ALARM, true);
-}
-
-void MIUN::LoRa::sleepWaitingNextFreeChannel()
-{
-    uint32_t sleep_time =std::max((uint32_t)10*1000, (uint32_t)dot->getNextTxMs()) / 1000;
-        logInfo("sleep %u seconds until next free channel",sleep_time);
-    dot->sleep(sleep_time, mDot::RTC_ALARM, false);
-}
-
-void MIUN::LoRa::sleep()
-{
-    if(sleepTime!=0)
-    {
-        sleep(sleepTime);
-    }
-}
-
-void MIUN::LoRa::joinNetwork ()
-{
-    if (!dot->getNetworkJoinStatus()) 
-    {
-        //1. Try Connect
-        tryConnectNet();
-        
-        //2. reset SF
-        if(dot->getAdr() == true)
-        {
-            resetSF();
-        }
-
-
-    }  
-}
-
-
-
-
-
- void MIUN::LoRa::networkConfig(std::string network_name, 
-                                std::string network_passphrase, 
-                                uint8_t     retransTimes,
-                                uint8_t     joinDelay,
-                                bool        ADR,
-                                uint8_t     sf,
-                                uint32_t    defaultSleepTime)
-{
-    //1. Reset
-    reset();
-    
-    //2.  make sure library logging is turned on
-    dot->setLogLevel(mts::MTSLog::INFO_LEVEL);
-    
-    //3. Change mode to AUTO_OTA
-    changeModeToAUTO_OTA();
-    
-
-    //4. Change network name
-    changeNetworkName(network_name);
-    
-    //5. Change Password
-    changePassword(network_passphrase);
-    
-    //6. Change Ack
-    changeAck(retransTimes);
-    
-    //7. Public Network
-    changePublicNetwork(true);
-    
-    //8. Change Join Delay
-    changeJoinDelay(joinDelay);
-    
-    //9. Set Adapt Datarate
-    changeAdaptSF(ADR);
-    
-    //9. Change sf
-    changeSF(ADR);
-    
-    //10. Save Default Time
-    saveSleepTime(defaultSleepTime);
-
-    //10. Save Setting
-    saveSetting();
-    
-    
-}
-
-
-
-void MIUN::LoRa::saveSleepTime(uint32_t sleepTime)
-{
-     dot->saveUserFile("sleepTm",(void*)&sleepTime,4);
-}
-
-uint32_t MIUN::LoRa::readSleepTime()
-{
-    uint8_t intBuffer[4];
-    dot->readUserFile("sleepTm",intBuffer,4);
-    return sleepTime = (((uint32_t)intBuffer[3])<<24)+
-                         (((uint32_t)intBuffer[2])<<16)+
-                         (((uint32_t)intBuffer[1])<<8)+
-                         intBuffer[0];
-}
-
-bool MIUN::LoRa::checkSleepTime(uint32_t sleepTime)
-{
-    if(sleepTime<60*60*24)
-    {
-        return true;
-    }
-    logError("Wrong Sleep Time");
-    return false;
-}  
-
-
-    
-void MIUN::LoRa::setFPending(bool isPending)
-{
-     uint8_t macArray[50]={'\0'};
-     memcpy(macArray,dot->_mote.GetMac(),50);
-     for(int i=0;i<50;i++)
-     {
-         logError("mac: %.2x", macArray[i]);
-
-     }
-
-}
-
-void MIUN::LoRa::setSleepTime(uint32_t inSleepTime)
-{
-    if(checkSleepTime(inSleepTime)==true)
-    {
-        sleepTime = inSleepTime;
-        logInfo("SetSleepTimeTo: %u", inSleepTime);
-    }
-    
-}
-
-void MIUN::LoRa::changeSF(const uint8_t& sf)
-{
-    uint8_t current_SF = dot->getTxDataRate();
-    if (current_SF != sf) 
-    {
-        logInfo("changing spreading factor from %s to %s", dot->getDateRateDetails(current_SF).c_str(), dot->getDateRateDetails(sf).c_str());
-        if (dot->setTxDataRate(sf)!= mDot::MDOT_OK) {
-            logError("failed to change SF to %s", dot->getDateRateDetails(sf).c_str());
-        }
-    }
-}
-
-void MIUN::LoRa::changeAdaptSF(bool adaptSF)
-{
-    bool current_adaptSF = dot->getAdr();
-    if (current_adaptSF != adaptSF) 
-    {
-        logInfo("changing AdaptSF from %s to %s", current_adaptSF ? "on" : "off", adaptSF ? "on" : "off");
-        if (dot->setAdr(adaptSF) != mDot::MDOT_OK) {
-            logError("failed to set AdaptSF to %s", adaptSF ? "on" : "off");
-        }
-    }
-}
-
-void MIUN::LoRa::changePublicNetwork(bool public_network)
-{
-    bool current_public_network = dot->getPublicNetwork();
-    if (current_public_network != public_network) 
-    {
-        logInfo("changing public network from %s to %s", current_public_network ? "on" : "off", public_network ? "on" : "off");
-        if (dot->setPublicNetwork(public_network) != mDot::MDOT_OK) {
-            logError("failed to set public network to %s", public_network ? "on" : "off");
-        }
-    }
-}
-
-void MIUN::LoRa::changeModeToAUTO_OTA()
-{
-    if (dot->getJoinMode() != mDot::AUTO_OTA) 
-    {
-        logInfo("changing network join mode to AUTO_OTA");
-        if (dot->setJoinMode(mDot::AUTO_OTA) != mDot::MDOT_OK) 
-        {
-            logError("failed to set network join mode to AUTO_OTA");
-        }
-    }
-}
-
-void MIUN::LoRa::changePassword(const std::string& network_passphrase)
-{
-    std::string current_network_passphrase = dot->getNetworkPassphrase();
-    if (current_network_passphrase != network_passphrase) 
-    {
-        logInfo("changing network passphrase from \"%s\" to \"%s\"", current_network_passphrase.c_str(), network_passphrase.c_str());
-        if (dot->setNetworkPassphrase(network_passphrase) != mDot::MDOT_OK) 
-        {
-            logError("failed to set network passphrase to \"%s\"", network_passphrase.c_str());
-        }
-    }
-}
-
-void MIUN::LoRa::changeNetworkName(const std::string& network_name)
-{
-    std::string current_network_name = dot->getNetworkName();
-    if (current_network_name != network_name) 
-    {
-        if (current_network_name != network_name) 
-        {
-            logInfo("changing network name from \"%s\" to \"%s\"", current_network_name.c_str(), network_name.c_str());
-            if (dot->setNetworkName(network_name) != mDot::MDOT_OK) {
-                logError("failed to set network name to \"%s\"", network_name.c_str());
-            }
-        }
-    }
-}
-
-void MIUN::LoRa::changeJoinDelay(uint8_t joinDelay)
-{
-    logInfo("changing join delay");
-    if (dot->setJoinDelay(joinDelay) != mDot::MDOT_OK) 
-    {
-        logError("failed to set join delay to %u", joinDelay);
-    }
-}
-
-void MIUN::LoRa::changeAck(const uint8_t& retries)
-{
-    logInfo("Set Ack to %u", retries);
-    if (dot->setAck(retries) != mDot::MDOT_OK) {
-        logError("failed to set  Ack to %u", retries);
-    }
-}
-
-
-
-void MIUN::LoRa::saveSetting()
-{
-    logInfo("saving configuration");
-    if (!dot->saveConfig()) 
-    {
-        logError("failed to save configuration");
-    }
-}
-
-void MIUN::LoRa::showInfo()
-{
-        // display configuration and library version information
-    logInfo("=====================");
-    logInfo("general configuration");
-    logInfo("=====================");
-    logInfo("version ------------------ %s", dot->getId().c_str());
-    logInfo("device ID/EUI ------------ %s", mts::Text::bin2hexString(dot->getDeviceId()).c_str());
-    logInfo("frequency band ----------- %s", mDot::FrequencyBandStr(dot->getFrequencyBand()).c_str());
-    if (dot->getFrequencySubBand() != mDot::FB_EU868) {
-        logInfo("frequency sub band ------- %u", dot->getFrequencySubBand());
-    }
-    logInfo("public network ----------- %s", dot->getPublicNetwork() ? "on" : "off");
-    logInfo("=========================");
-    logInfo("credentials configuration");
-    logInfo("=========================");
-    logInfo("device class ------------- %s", dot->getClass().c_str());
-    logInfo("network join mode -------- %s", mDot::JoinModeStr(dot->getJoinMode()).c_str());
-    if (dot->getJoinMode() == mDot::MANUAL || dot->getJoinMode() == mDot::PEER_TO_PEER) {
-    logInfo("network address ---------- %s", mts::Text::bin2hexString(dot->getNetworkAddress()).c_str());
-    logInfo("network session key------- %s", mts::Text::bin2hexString(dot->getNetworkSessionKey()).c_str());
-    logInfo("data session key---------- %s", mts::Text::bin2hexString(dot->getDataSessionKey()).c_str());
-    } else {
-    logInfo("network name ------------- %s", dot->getNetworkName().c_str());
-    logInfo("network phrase ----------- %s", dot->getNetworkPassphrase().c_str());
-    logInfo("network EUI -------------- %s", mts::Text::bin2hexString(dot->getNetworkId()).c_str());
-    logInfo("network KEY -------------- %s", mts::Text::bin2hexString(dot->getNetworkKey()).c_str());
-    
-    logInfo("session NWK KEY -------------- %s", mts::Text::bin2hexString(dot->getNetworkSessionKey()).c_str());
-    logInfo("session APP KEY -------------- %s", mts::Text::bin2hexString(dot->getDataSessionKey()).c_str());
-    }
-    logInfo("========================");
-    logInfo("communication parameters");
-    logInfo("========================");
-    if (dot->getJoinMode() == mDot::PEER_TO_PEER) {
-    logInfo("TX frequency ------------- %lu", dot->getTxFrequency());
-    } else {
-    logInfo("acks --------------------- %s, %u attempts", dot->getAck() > 0 ? "on" : "off", dot->getAck());
-    }
-    logInfo("TX datarate -------------- %s", mDot::DataRateStr(dot->getTxDataRate()).c_str());
-    logInfo("TX power ----------------- %lu dBm", dot->getTxPower());
-    logInfo("atnenna gain ------------- %u dBm", dot->getAntennaGain());
-    logInfo("channels -------------");
-    std::vector<uint32_t>::iterator channelItreator;
-    uint32_t i=0;
-    for(channelItreator = dot->getChannels().begin();channelItreator!=dot->getChannels().end();channelItreator++)
-    {
-        logInfo("channel(%u) ------------- %u Hz",i++,*channelItreator);
-    }
-}
-
-
-
-
-
-mDot& MIUN::LoRa::getHandler()
-{
-    return *dot;
-}
-
-/*** private function  ***/
-
-void MIUN::LoRa::tryConnectNet()
-{
-    int32_t j_attempts = 0;
-    int32_t ret = mDot::MDOT_ERROR;
-    
-    // attempt to join the network
-    while (ret != mDot::MDOT_OK) {
-        logInfo("attempt %d to join network", ++j_attempts);
-        ret = dot->joinNetwork();
-        if (ret != mDot::MDOT_OK) {
-            logError("failed to join network %d:%s", ret, mDot::getReturnCodeString(ret).c_str());
-            // in some frequency bands we need to wait until another channel is available before transmitting again
-            uint32_t delay_s = (dot->getNextTxMs() / 1000) + 1;
-            if (delay_s < 2) {
-                logInfo("waiting %lu s until next free channel", delay_s);
-                wait(delay_s);
-            } else {
-                logInfo("sleeping %lu s until next free channel", delay_s);
-                sleep(delay_s);
-            }
-        }
-    }
-}
-
-
-
-bool MIUN::LoRa::send(std::string input_data, int port)
-{
-    //1. Set Port
-    dot->setAppPort(port);
-    //1. if it use ADR
-    if(dot->getAdr() == true)
-    {
-        int i=0;
-        while(!send_basic(input_data))
-        {
-            i++;
-            if(i>3)
-            {
-                // 1. increase SF
-                if(increaseSF()==false)
-                {
-                    //1. Clean Network Session
-                    dot->resetNetworkSession();
-                    //2. Reset SF
-                    resetSF();
-                    tryConnectNet();
-                    return false;
-                }
-                else
-                {
-                    return true;
-                }
-            }
-            sleepWaitingNextFreeChannel();
-                
-        }
-            
-    }
-        
-    else
-    {
-        return send_basic(input_data);
-    }
-    
-}
-
-
-bool MIUN::LoRa::increaseSF()
-{
-    uint8_t current_SF = dot->getTxDataRate();
-    if(current_SF>0)
-    {
-        changeSF(--current_SF);
-        return true;
-    }
-    return false;
-}
-
-bool MIUN::LoRa::decreaseSF()
-{
-    uint8_t current_SF = dot->getTxDataRate();
-    if(current_SF<5)
-    {
-        changeSF(++current_SF);
-        return true;
-    }
-    return false;
-}
-
-void MIUN::LoRa::resetSF()
-{
-    changeSF(5);
-}
-
-
-void MIUN::LoRa::setBatteryLevel(uint8_t batteryLevelValue)
-{
-    batteryLevel = batteryLevelValue;
-}
-
-
-
-
-
-
-
-
-MIUN::MacCommandEvent::MacCommandEvent(LoRa& loraHandle):loraHandle(loraHandle)
-{
-}
-
-void MIUN::MacCommandEvent::RxDone(uint8_t *payload, uint16_t size, int16_t rssi, int8_t snr, lora::DownlinkControl ctrl, uint8_t slot)
-{
-    /*
-    for(int i=0;i<20;i++)
-    {
-          logInfo("Payload %.2x", payload[i]);
-    }
-    */
-    if(payload[0] == 0xa0 || payload[0] == 0x60)
-    {
-        //1. Process Mac Command        
-        int macCommandLength =  payload[5] & 0x0f;
-        if(macCommandLength>0)
-        {
-            uint8_t macCommand[macCommandLength];
-            memcpy(macCommand,payload+8,macCommandLength);
-            
-            for(int i=0;i<macCommandLength;i++)
-            {
-                logInfo("Mac Command: %.2x", macCommand[i]);
-            }
-
-            switch(macCommand[0])
-            {
-            case decreaseSF:
-            if(macCommandLength == decreaseSF_length)
-            {
-                 processSFDecrease(macCommand);
-            }
-            break;
-            
-            case increaseSF:
-            if(macCommandLength == increaseSF_length)
-            {
-                processSFIncrease(macCommand);
-            }
-            break;
-            
-            case changeSleepTime:
-            if(macCommandLength == changeSleepTime_length)
-            {
-                processChangeSleepTm(macCommand);
-            }
-            break;
-                   
-            }
-        }
-        
-        //2. Receive Port
-        if((size-12-macCommandLength)>0)
-        {
-            loraHandle.receivePort = payload[8+macCommandLength];
-        }
-        else
-        {
-            loraHandle.receivePort = -1;
-        }
-    }
-}
-
-void MIUN::MacCommandEvent::processChangeSleepTm(uint8_t *macCommand)
-{
-        
-        uint32_t sleepTime_s = (((uint32_t)macCommand[4])<<24)+
-                               (((uint32_t)macCommand[3])<<16)+
-                               (((uint32_t)macCommand[2])<<8)+
-                                macCommand[1];
-        logInfo("Change Sleep Time: %u", sleepTime_s);
-        loraHandle.setSleepTime(sleepTime_s);
-        
-}
-
-void MIUN::MacCommandEvent::processSFDecrease(uint8_t *payload)
-{
-    loraHandle.decreaseSF();
-}
-
-void MIUN::MacCommandEvent::processSFIncrease(uint8_t *payload)
-{
-    loraHandle.increaseSF();
-}
-
-uint8_t MIUN::MacCommandEvent::MeasureBattery() 
-{
-     return loraHandle.batteryLevel;
-}
-
-
--- a/LoRa.h	Wed May 03 08:49:14 2017 +0000
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,177 +0,0 @@
-/**
- * @file    LoRa.h
- * @brief   Application call
- * @author  Bin Wang
- * @version 1.0
- */
- 
-#ifndef MIUN_LORA_H
-#define MIUN_LORA_H
-
-#include "mDot.h"
-#include "mDotEvent.h"
-
-
-namespace MIUN
-{
-    
-class LoRa;
-
-class MacCommandEvent : public mDotEvent
-{
-/*** CommandType ***/
-private:
-    enum CommmandType 
-    {
-        decreaseSF = 0x80,
-        increaseSF = 0x81,
-        changeSleepTime = 0x82,
-    };
-    
-    enum CommmandType_length 
-    {
-        decreaseSF_length = 1,
-        increaseSF_length = 1,
-        changeSleepTime_length = 5,
-    };
-    
-
-
-private:
-    LoRa& loraHandle;
-public:
-    MacCommandEvent(LoRa& loraHandle);
- 
-    virtual ~MacCommandEvent() {}
- 
-    virtual void RxDone(uint8_t *payload, uint16_t size, int16_t rssi, int8_t snr, lora::DownlinkControl ctrl, uint8_t slot);
-
-    virtual uint8_t MeasureBattery(); 
-    
-private:
-    void processSFDecrease(uint8_t *payload);
-    void processSFIncrease(uint8_t *payload);
-    void processChangeSleepTm(uint8_t *macCommand);
-    void processqueryBatteryLevel(uint8_t *macCommand);
-    
-    void sendCommand (uint8_t* command, int commandLength);
-};
-
-class LoRa
-{
-/*** Parameters ***/
-private:
-    uint8_t rejoinTimes;
-    uint8_t retransTimes;
-    uint8_t installSF;
-    uint32_t sleepTime;
-    uint32_t defaultSleepTime;
-    
-    int receivePort;
-    
-    uint8_t batteryLevel;
-
-/*** component ***/
-private:
-    mDot* dot;
-    MacCommandEvent macCommandEvent;
-
-/*** constructor ***/
-public:
-    LoRa();
-
-/*** Handle Functins ***/
-
-public:
-    /*** Information ***/
-    void showInfo();
-    
-    /*** sleep ***/
-    void sleep(const uint32_t& interval_s);
-    void sleep();
-    void sleepWaitingNextFreeChannel();
-    
-    /*** Network ***/
-    void joinNetwork ();
-    bool send_basic(std::string input_data);
-    bool send(std::string input_data, int port);
-    std::string receive(int* port);
-    
-    /*** check ***/
-    bool checkSleepTime(uint32_t sleepTime);  
-       
-    /*** Setting ***/
-    void reset();
-    
-    void networkConfig(std::string network_name, 
-                                std::string network_passphrase, 
-                                uint8_t     retransTimes,
-                                uint8_t     joinDelay,
-                                bool        ADR,
-                                uint8_t     sf,
-                                uint32_t    defaultSleepTime); // Include reset and setting save.
-    
-    /*** getting ***/
-    
-        
-    /*** Setting ***/
-public:
-
-    void setBatteryLevel(uint8_t batteryLevel);
-
-    void setFPending(bool isPending);
-    
-    void setDefaultSleepTime(uint32_t inSleepTime);
-    
-    void setSleepTime(uint32_t inSleepTime);
-    
-    bool increaseSF();
-    
-    bool decreaseSF();
-    
-    void resetSF();
-
-    void changeSF(const uint8_t& sf);
-
-    void changeAdaptSF(bool adaptSF);
-
-    void changeModeToAUTO_OTA();
-    
-    void changeNetworkName(const std::string& network_name);
-    
-    void changePassword(const std::string& networkKey);
-    
-    void changeAck(const uint8_t& retries);
-    
-    void changeJoinDelay(uint8_t joinDelay);
-    
-    void changePublicNetwork(bool isPublicNetwork);    
-    
-    /*** Save & get***/
-private:
-    void saveSetting();
-    void saveSleepTime(uint32_t sleepTime);
-    uint32_t readSleepTime();
-
-
-    
-    /*** Get ***/
-public:
-    mDot& getHandler();
-    
-/*** Private Functions ***/
-private:
-    void tryConnectNet();
-    
-friend class MacCommandEvent;
-};
-
-
-
-
-
-} // CLOSE NAMESPACE
-
-
-
-#endif
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/MIUN.LoRa.cpp	Mon Oct 02 16:09:14 2017 +0000
@@ -0,0 +1,616 @@
+#include "MIUN.LoRa.h"
+#include "mbed.h"
+#include "mDot.h"
+#include "MacEvents.h"
+#include "MTSLog.h"
+#include "MTSText.h"
+#include <vector>
+#include <string>
+
+
+MIUN::LoRa::LoRa():macCommandEvent(*this)
+{
+
+    //1. Set dot
+    dot = mDot::getInstance();
+    
+    //2. Register Event
+     dot->setEvents(&macCommandEvent);
+     
+    //3. getDefaultSleepTime
+    //defaultSleepTime = readSleepTime();
+    defaultSleepTime = 30; //seconds
+
+    //4. set batteryLevel
+    batteryLevel = 255;
+    
+    //5. Print Version
+    logInfo("Library Version: %s", dot->getId().c_str());
+
+    
+}
+
+void MIUN::LoRa::reset()
+{
+    // start from a well-known state
+    logInfo("defaulting Dot configuration");
+    dot->resetConfig();
+    dot->resetNetworkSession();
+}
+
+
+/*** public method ***/
+
+std::string MIUN::LoRa::receive(int* port)
+{
+    int32_t ret;
+    vector<uint8_t> receive_data;
+     if ((ret = dot->recv(receive_data)) != mDot::MDOT_OK) 
+    {
+            logError("failed to recv: [%d][%s]", ret, mDot::getReturnCodeString(ret).c_str());
+            return "";
+    } 
+    else 
+    {
+            //1. Set Receive Payload
+            string str(receive_data.begin(),receive_data.end());
+            //2. Set Receive Port
+            *port = receivePort;
+            receivePort = -1;
+            return str;
+    }           
+}
+
+
+bool MIUN::LoRa::send_basic(std::string input_data)
+{
+    int32_t ret;
+    vector<uint8_t> sent_data;
+     logInfo("Send with %s", dot->getDateRateDetails(dot->getTxDataRate()).c_str());
+    for (std::string::iterator it = input_data.begin(); it != input_data.end(); it++)
+    {
+        sent_data.push_back((uint8_t) *it);   
+    }
+     std::vector<uint8_t> sendData;
+        sendData.push_back(0x80); 
+    /*
+    for (int i=0;i<commandLength;i++)
+    {
+        sendData.push_back(command[i]);   
+    }
+    */
+    if (dot->injectMacCommand(sendData) != mDot::MDOT_OK) 
+    {
+        logError("failed to injectMacCommand");
+    }
+    else
+    {
+        logInfo("injectMacCommand Successful");
+    }
+    if ((ret = dot->send(sent_data)) != mDot::MDOT_OK) 
+    {
+        logError("failed to send", ret, mDot::getReturnCodeString(ret).c_str());
+        return false;
+    } 
+    else 
+    {
+        logInfo("successfully sent data to gateway");
+        return true;
+    }
+
+}
+
+
+
+void MIUN::LoRa::sleep(const uint32_t& interval_s)
+{
+    uint32_t sleep_time = std::max(interval_s*1000, (uint32_t)dot->getNextTxMs()) / 1000;
+        logInfo("sleep %u seconds until next free channel",sleep_time);
+    dot->sleep(sleep_time, mDot::RTC_ALARM, true);
+}
+
+void MIUN::LoRa::sleepWaitingNextFreeChannel()
+{
+    uint32_t sleep_time =std::max((uint32_t)10*1000, (uint32_t)dot->getNextTxMs()) / 1000;
+        logInfo("sleep %u seconds until next free channel",sleep_time);
+    dot->sleep(sleep_time, mDot::RTC_ALARM, false);
+}
+
+void MIUN::LoRa::sleep()
+{
+    if(sleepTime!=0)
+    {
+        sleep(sleepTime);
+    }
+}
+
+bool MIUN::LoRa::joinNetwork ()
+{
+    if (!dot->getNetworkJoinStatus()) 
+    {
+        //1. Try Connect
+       if(tryConnectNet() == false)
+       {
+           return false;
+       }
+        //2. reset SF
+        if(dot->getAdr() == true)
+        {
+            resetSF();
+        }
+    }  
+    return true;
+}
+
+
+
+
+
+ void MIUN::LoRa::networkConfig(std::string network_name, 
+                                std::string network_passphrase, 
+                                uint8_t     retransTimes,
+                                uint8_t     joinDelay,
+                                bool        ADR,
+                                uint8_t     sf)
+{
+    //1. Reset
+    reset();
+    
+    //2.  make sure library logging is turned on
+    dot->setLogLevel(mts::MTSLog::INFO_LEVEL);
+    
+    //3. Change mode to AUTO_OTA
+    changeModeToAUTO_OTA();
+    
+
+    //4. Change network name
+    changeNetworkName(network_name);
+    
+    //5. Change Password
+    changePassword(network_passphrase);
+    
+    //6. Change Ack
+    changeAck(retransTimes);
+    
+    //7. Public Network
+    changePublicNetwork(true);
+    
+    //8. Change Join Delay
+    changeJoinDelay(joinDelay);
+    
+    //9. Set Adapt Datarate
+    changeAdaptSF(ADR);
+    
+    //9. Change sf
+    changeSF(ADR);
+    
+    //10. Save Default Time
+    //saveSleepTime(defaultSleepTime);
+
+    //10. Save Setting
+    saveSetting();
+    
+    
+}
+
+
+/*
+void MIUN::LoRa::saveSleepTime(uint32_t sleepTime)
+{
+     dot->saveUserFile("sleepTm",(void*)&sleepTime,4);
+}
+
+uint32_t MIUN::LoRa::readSleepTime()
+{
+    uint8_t intBuffer[4];
+    dot->readUserFile("sleepTm",intBuffer,4);
+    return sleepTime = (((uint32_t)intBuffer[3])<<24)+
+                         (((uint32_t)intBuffer[2])<<16)+
+                         (((uint32_t)intBuffer[1])<<8)+
+                         intBuffer[0];
+}
+*/
+
+bool MIUN::LoRa::checkSleepTime(uint32_t sleepTime)
+{
+    if(sleepTime<60*60*24)
+    {
+        return true;
+    }
+    logError("Wrong Sleep Time");
+    return false;
+}  
+
+
+    
+void MIUN::LoRa::setFPending(bool isPending)
+{
+     uint8_t macArray[50]={'\0'};
+     memcpy(macArray,dot->_mote.GetMac(),50);
+     for(int i=0;i<50;i++)
+     {
+         logError("mac: %.2x", macArray[i]);
+
+     }
+
+}
+
+void MIUN::LoRa::setSleepTime(uint32_t inSleepTime)
+{
+    if(checkSleepTime(inSleepTime)==true)
+    {
+        sleepTime = inSleepTime;
+        logInfo("SetSleepTimeTo: %u", inSleepTime);
+    }
+    
+}
+
+void MIUN::LoRa::changeSF(const uint8_t& sf)
+{
+    uint8_t current_SF = dot->getTxDataRate();
+    if (current_SF != sf) 
+    {
+        logInfo("changing spreading factor from %s to %s", dot->getDateRateDetails(current_SF).c_str(), dot->getDateRateDetails(sf).c_str());
+        if (dot->setTxDataRate(sf)!= mDot::MDOT_OK) {
+            logError("failed to change SF to %s", dot->getDateRateDetails(sf).c_str());
+        }
+    }
+}
+
+void MIUN::LoRa::changeAdaptSF(bool adaptSF)
+{
+    bool current_adaptSF = dot->getAdr();
+    if (current_adaptSF != adaptSF) 
+    {
+        logInfo("changing AdaptSF from %s to %s", current_adaptSF ? "on" : "off", adaptSF ? "on" : "off");
+        if (dot->setAdr(adaptSF) != mDot::MDOT_OK) {
+            logError("failed to set AdaptSF to %s", adaptSF ? "on" : "off");
+        }
+    }
+}
+
+void MIUN::LoRa::changePublicNetwork(bool public_network)
+{
+    bool current_public_network = dot->getPublicNetwork();
+    if (current_public_network != public_network) 
+    {
+        logInfo("changing public network from %s to %s", current_public_network ? "on" : "off", public_network ? "on" : "off");
+        if (dot->setPublicNetwork(public_network) != mDot::MDOT_OK) {
+            logError("failed to set public network to %s", public_network ? "on" : "off");
+        }
+    }
+}
+
+void MIUN::LoRa::changeModeToAUTO_OTA()
+{
+    if (dot->getJoinMode() != mDot::AUTO_OTA) 
+    {
+        logInfo("changing network join mode to AUTO_OTA");
+        if (dot->setJoinMode(mDot::AUTO_OTA) != mDot::MDOT_OK) 
+        {
+            logError("failed to set network join mode to AUTO_OTA");
+        }
+    }
+}
+
+void MIUN::LoRa::changePassword(const std::string& network_passphrase)
+{
+    std::string current_network_passphrase = dot->getNetworkPassphrase();
+    if (current_network_passphrase != network_passphrase) 
+    {
+        logInfo("changing network passphrase from \"%s\" to \"%s\"", current_network_passphrase.c_str(), network_passphrase.c_str());
+        if (dot->setNetworkPassphrase(network_passphrase) != mDot::MDOT_OK) 
+        {
+            logError("failed to set network passphrase to \"%s\"", network_passphrase.c_str());
+        }
+    }
+}
+
+void MIUN::LoRa::changeNetworkName(const std::string& network_name)
+{
+    std::string current_network_name = dot->getNetworkName();
+    if (current_network_name != network_name) 
+    {
+        if (current_network_name != network_name) 
+        {
+            logInfo("changing network name from \"%s\" to \"%s\"", current_network_name.c_str(), network_name.c_str());
+            if (dot->setNetworkName(network_name) != mDot::MDOT_OK) {
+                logError("failed to set network name to \"%s\"", network_name.c_str());
+            }
+        }
+    }
+}
+
+void MIUN::LoRa::changeJoinDelay(uint8_t joinDelay)
+{
+    logInfo("changing join delay");
+    if (dot->setJoinDelay(joinDelay) != mDot::MDOT_OK) 
+    {
+        logError("failed to set join delay to %u", joinDelay);
+    }
+}
+
+void MIUN::LoRa::changeAck(const uint8_t& retries)
+{
+    logInfo("Set Ack to %u", retries);
+    if (dot->setAck(retries) != mDot::MDOT_OK) {
+        logError("failed to set  Ack to %u", retries);
+    }
+}
+
+
+
+void MIUN::LoRa::saveSetting()
+{
+    logInfo("saving configuration");
+    if (!dot->saveConfig()) 
+    {
+        logError("failed to save configuration");
+    }
+}
+
+void MIUN::LoRa::showInfo()
+{
+        // display configuration and library version information
+    logInfo("=====================");
+    logInfo("general configuration");
+    logInfo("=====================");
+    logInfo("version ------------------ %s", dot->getId().c_str());
+    logInfo("device ID/EUI ------------ %s", mts::Text::bin2hexString(dot->getDeviceId()).c_str());
+    logInfo("frequency band ----------- %s", mDot::FrequencyBandStr(dot->getFrequencyBand()).c_str());
+    if (dot->getFrequencySubBand() != mDot::FB_EU868) {
+        logInfo("frequency sub band ------- %u", dot->getFrequencySubBand());
+    }
+    logInfo("public network ----------- %s", dot->getPublicNetwork() ? "on" : "off");
+    logInfo("=========================");
+    logInfo("credentials configuration");
+    logInfo("=========================");
+    logInfo("device class ------------- %s", dot->getClass().c_str());
+    logInfo("network join mode -------- %s", mDot::JoinModeStr(dot->getJoinMode()).c_str());
+    if (dot->getJoinMode() == mDot::MANUAL || dot->getJoinMode() == mDot::PEER_TO_PEER) {
+    logInfo("network address ---------- %s", mts::Text::bin2hexString(dot->getNetworkAddress()).c_str());
+    logInfo("network session key------- %s", mts::Text::bin2hexString(dot->getNetworkSessionKey()).c_str());
+    logInfo("data session key---------- %s", mts::Text::bin2hexString(dot->getDataSessionKey()).c_str());
+    } else {
+    logInfo("network name ------------- %s", dot->getNetworkName().c_str());
+    logInfo("network phrase ----------- %s", dot->getNetworkPassphrase().c_str());
+    logInfo("network EUI -------------- %s", mts::Text::bin2hexString(dot->getNetworkId()).c_str());
+    logInfo("network KEY -------------- %s", mts::Text::bin2hexString(dot->getNetworkKey()).c_str());
+    
+    logInfo("session NWK KEY -------------- %s", mts::Text::bin2hexString(dot->getNetworkSessionKey()).c_str());
+    logInfo("session APP KEY -------------- %s", mts::Text::bin2hexString(dot->getDataSessionKey()).c_str());
+    }
+    logInfo("========================");
+    logInfo("communication parameters");
+    logInfo("========================");
+    if (dot->getJoinMode() == mDot::PEER_TO_PEER) {
+    logInfo("TX frequency ------------- %lu", dot->getTxFrequency());
+    } else {
+    logInfo("acks --------------------- %s, %u attempts", dot->getAck() > 0 ? "on" : "off", dot->getAck());
+    }
+    logInfo("TX datarate -------------- %s", mDot::DataRateStr(dot->getTxDataRate()).c_str());
+    logInfo("TX power ----------------- %lu dBm", dot->getTxPower());
+    logInfo("atnenna gain ------------- %u dBm", dot->getAntennaGain());
+    logInfo("channels -------------");
+    std::vector<uint32_t>::iterator channelItreator;
+    uint32_t i=0;
+    for(channelItreator = dot->getChannels().begin();channelItreator!=dot->getChannels().end();channelItreator++)
+    {
+        logInfo("channel(%u) ------------- %u Hz",i++,*channelItreator);
+    }
+}
+
+
+
+
+
+mDot& MIUN::LoRa::getHandler()
+{
+    return *dot;
+}
+
+/*** private function  ***/
+
+bool MIUN::LoRa::tryConnectNet()
+{
+    int32_t j_attempts = 0;
+    int32_t ret = mDot::MDOT_ERROR;
+    
+    // attempt to join the network
+    while (ret != mDot::MDOT_OK) 
+    {
+        logInfo("attempt %d to join network", ++j_attempts);
+        ret = dot->joinNetwork();
+        if (ret != mDot::MDOT_OK) {
+            logError("failed to join network %d:%s It will retry...", ret, mDot::getReturnCodeString(ret).c_str());
+            // in some frequency bands we need to wait until another channel is available before transmitting again
+            uint32_t delay_s = (dot->getNextTxMs() / 1000) + 1;
+            if (delay_s < 2) 
+            {
+                logInfo("waiting %lu s until next free channel", delay_s);
+                wait(delay_s);
+            } else {
+                logInfo("sleeping %lu s until next free channel", delay_s);
+                sleep(delay_s);
+            }
+        }
+        
+        if(j_attempts >3)
+        {
+            logError("failed to join network %d:%s, give up.", ret, mDot::getReturnCodeString(ret).c_str());
+            return false;
+        }
+    }
+    return true;
+}
+
+
+
+bool MIUN::LoRa::send(std::string input_data, int port)
+{
+    //1. Set Port
+    dot->setAppPort(port);
+    //1. if it use ADR
+    if(dot->getAdr() == true)
+    {
+        int i=0;
+        while(!send_basic(input_data))
+        {
+            i++;
+            if(i>3)
+            {
+                // 1. increase SF
+                if(increaseSF()==false)
+                {
+                    //1. Clean Network Session
+                    dot->resetNetworkSession();
+                    //2. Reset SF
+                    resetSF();
+                    tryConnectNet();
+                    return false;
+                }
+            }
+            sleepWaitingNextFreeChannel();      
+        }
+            
+    }
+    else
+    {
+        return send_basic(input_data);
+    }
+    return true;
+}
+
+
+bool MIUN::LoRa::increaseSF()
+{
+    uint8_t current_SF = dot->getTxDataRate();
+    if(current_SF>0)
+    {
+        changeSF(--current_SF);
+        return true;
+    }
+    return false;
+}
+
+bool MIUN::LoRa::decreaseSF()
+{
+    uint8_t current_SF = dot->getTxDataRate();
+    if(current_SF<5)
+    {
+        changeSF(++current_SF);
+        return true;
+    }
+    return false;
+}
+
+void MIUN::LoRa::resetSF()
+{
+    changeSF(5);
+}
+
+
+void MIUN::LoRa::setBatteryLevel(uint8_t batteryLevelValue)
+{
+    batteryLevel = batteryLevelValue;
+}
+
+
+
+
+
+
+
+
+MIUN::MacCommandEvent::MacCommandEvent(LoRa& loraHandle):loraHandle(loraHandle)
+{
+}
+
+void MIUN::MacCommandEvent::RxDone(uint8_t *payload, uint16_t size, int16_t rssi, int8_t snr, lora::DownlinkControl ctrl, uint8_t slot)
+{
+    /*
+    for(int i=0;i<20;i++)
+    {
+          logInfo("Payload %.2x", payload[i]);
+    }
+    */
+    if(payload[0] == 0xa0 || payload[0] == 0x60)
+    {
+        //1. Process Mac Command        
+        int macCommandLength =  payload[5] & 0x0f;
+        if(macCommandLength>0)
+        {
+            uint8_t macCommand[macCommandLength];
+            memcpy(macCommand,payload+8,macCommandLength);
+            
+            for(int i=0;i<macCommandLength;i++)
+            {
+                logInfo("Mac Command: %.2x", macCommand[i]);
+            }
+
+            switch(macCommand[0])
+            {
+            case decreaseSF:
+            if(macCommandLength == decreaseSF_length)
+            {
+                 processSFDecrease(macCommand);
+            }
+            break;
+            
+            case increaseSF:
+            if(macCommandLength == increaseSF_length)
+            {
+                processSFIncrease(macCommand);
+            }
+            break;
+            
+            case changeSleepTime:
+            if(macCommandLength == changeSleepTime_length)
+            {
+                processChangeSleepTm(macCommand);
+            }
+            break;
+                   
+            }
+        }
+        
+        //2. Receive Port
+        if((size-12-macCommandLength)>0)
+        {
+            loraHandle.receivePort = payload[8+macCommandLength];
+        }
+        else
+        {
+            loraHandle.receivePort = -1;
+        }
+    }
+}
+
+void MIUN::MacCommandEvent::processChangeSleepTm(uint8_t *macCommand)
+{
+        
+        uint32_t sleepTime_s = (((uint32_t)macCommand[4])<<24)+
+                               (((uint32_t)macCommand[3])<<16)+
+                               (((uint32_t)macCommand[2])<<8)+
+                                macCommand[1];
+        logInfo("Change Sleep Time: %u", sleepTime_s);
+        loraHandle.setSleepTime(sleepTime_s);
+        
+}
+
+void MIUN::MacCommandEvent::processSFDecrease(uint8_t *payload)
+{
+    loraHandle.decreaseSF();
+}
+
+void MIUN::MacCommandEvent::processSFIncrease(uint8_t *payload)
+{
+    loraHandle.increaseSF();
+}
+
+uint8_t MIUN::MacCommandEvent::MeasureBattery() 
+{
+     return loraHandle.batteryLevel;
+}
+
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/MIUN.LoRa.h	Mon Oct 02 16:09:14 2017 +0000
@@ -0,0 +1,177 @@
+/**
+ * @file    LoRa.h
+ * @brief   Application call
+ * @author  Bin Wang
+ * @version 1.0
+ */
+ 
+#ifndef MIUN_LORA_H
+#define MIUN_LORA_H
+
+#include "mDot.h"
+#include "mDotEvent.h"
+
+
+namespace MIUN
+{
+    
+class LoRa;
+
+class MacCommandEvent : public mDotEvent
+{
+/*** CommandType ***/
+private:
+    enum CommmandType 
+    {
+        decreaseSF = 0x80,
+        increaseSF = 0x81,
+        changeSleepTime = 0x82,
+    };
+    
+    enum CommmandType_length 
+    {
+        decreaseSF_length = 1,
+        increaseSF_length = 1,
+        changeSleepTime_length = 5,
+    };
+    
+
+
+private:
+    LoRa& loraHandle;
+public:
+    MacCommandEvent(LoRa& loraHandle);
+ 
+    virtual ~MacCommandEvent() {}
+ 
+    virtual void RxDone(uint8_t *payload, uint16_t size, int16_t rssi, int8_t snr, lora::DownlinkControl ctrl, uint8_t slot);
+
+    virtual uint8_t MeasureBattery(); 
+    
+private:
+    void processSFDecrease(uint8_t *payload);
+    void processSFIncrease(uint8_t *payload);
+    void processChangeSleepTm(uint8_t *macCommand);
+    void processqueryBatteryLevel(uint8_t *macCommand);
+    
+    void sendCommand (uint8_t* command, int commandLength);
+};
+
+class LoRa
+{
+/*** Parameters ***/
+private:
+    uint8_t rejoinTimes;
+    uint8_t retransTimes;
+    uint8_t installSF;
+    uint32_t sleepTime;
+    uint32_t defaultSleepTime;
+    
+    int receivePort;
+    
+    uint8_t batteryLevel;
+
+/*** component ***/
+private:
+    mDot* dot;
+    MacCommandEvent macCommandEvent;
+
+/*** constructor ***/
+public:
+    LoRa();
+
+/*** Handle Functins ***/
+
+public:
+    /*** Information ***/
+    void showInfo();
+    
+    /*** sleep ***/
+    void sleep();
+    void sleep(const uint32_t& interval_s);
+    void sleepWaitingNextFreeChannel();
+    
+    /*** Network ***/
+    bool joinNetwork ();
+    bool send_basic(std::string input_data);
+    bool send(std::string input_data, int port);
+    std::string receive(int* port);
+    
+    /*** check ***/
+    bool checkSleepTime(uint32_t sleepTime);  
+       
+    /*** Setting ***/
+    void reset();
+    
+    void networkConfig(std::string network_name, 
+                                std::string network_passphrase, 
+                                uint8_t     retransTimes,
+                                uint8_t     joinDelay,
+                                bool        ADR,
+                                uint8_t     sf); // Include reset and setting save.
+    
+    /*** getting ***/
+    
+        
+    /*** Setting ***/
+public:
+
+    void setBatteryLevel(uint8_t batteryLevel);
+
+    void setFPending(bool isPending);
+    
+    void setDefaultSleepTime(uint32_t inSleepTime);
+    
+    void setSleepTime(uint32_t inSleepTime);
+    
+    bool increaseSF();
+    
+    bool decreaseSF();
+    
+    void resetSF();
+
+    void changeSF(const uint8_t& sf);
+
+    void changeAdaptSF(bool adaptSF);
+
+    void changeModeToAUTO_OTA();
+    
+    void changeNetworkName(const std::string& network_name);
+    
+    void changePassword(const std::string& networkKey);
+    
+    void changeAck(const uint8_t& retries);
+    
+    void changeJoinDelay(uint8_t joinDelay);
+    
+    void changePublicNetwork(bool isPublicNetwork);    
+    
+    /*** Save & get***/
+private:
+    void saveSetting();
+    /*
+    void saveSleepTime(uint32_t sleepTime);
+    uint32_t readSleepTime();
+    */
+
+    
+    /*** Get ***/
+public:
+    mDot& getHandler();
+    
+/*** Private Functions ***/
+private:
+    bool tryConnectNet();
+    
+friend class MacCommandEvent;
+};
+
+
+
+
+
+} // CLOSE NAMESPACE
+
+
+
+#endif
\ No newline at end of file