Connection Manager library for u-blox cellular modules. It manages the modem for keeping data connection always active.
Diff: CNManager.cpp
- Revision:
- 1:29ad1d1ac1f9
- Parent:
- 0:86284a262735
--- a/CNManager.cpp Tue Jan 12 09:08:15 2016 +0000 +++ b/CNManager.cpp Thu Jan 21 14:00:25 2016 +0000 @@ -5,7 +5,7 @@ #include "CNLib.h" #include "CNReg.h" -//! internal state +//! Manager internal state typedef enum { MNG_NOT_INIT = 0, //!< not initiated MNG_RADIO_OFF, //!< radio is off @@ -16,26 +16,27 @@ MNG_ERROR_STUCK //!< unrecoverable error } MngState; - static MngState state = MNG_NOT_INIT; //!< Manager state static bool moduleOn; //!< Module power requested power status static bool dataOn; static CNLib* cnLib; //!< Pointer to CN library static char simPin[10]; //!< Sim Pin static int errorCounter; //!< Error counter -static evDataHandler clientHandler; //!< function point handler +static evMngHandler mngHandler; //!< Function point handler +static void* paramDataHandler; //!< Pointer to pass to the handler +static int respError; static CNResp radioSwitchOn(CNLib*& lib); static CNResp radioSwitchOff(CNLib*& lib); static CNResp simInit(CNLib* lib, char* simPin); -static void dump(); - -bool cnInit(evDataHandler handler /*=NULL*/, bool powerOn /*=true*/, bool dataEnabled /*=true*/, bool roomingEnabled /*=true*/){ - clientHandler = handler; +bool cnInit(bool powerOn /*=true*/, bool dataEnabled /*=true*/, bool roomingEnabled /*=true*/){ + mngHandler = NULL; + paramDataHandler = NULL; state = MNG_RADIO_OFF; moduleOn = powerOn; errorCounter = 0; + respError = 0; cnRegInit(); cnDataInit(); dataOn = dataEnabled; @@ -43,8 +44,14 @@ return true; } -CNLib* cnGetMDM(){ - return cnLib; +void cnRegHandler(evMngHandler handler, void* param/*=NULL*/) +{ + mngHandler = handler; + paramDataHandler = param; +} + +MDMSerial* cnGetMDM(){ + return (MDMSerial*) cnLib; } void cnSetPower(bool on){ @@ -52,6 +59,7 @@ } void cnSetDataEnabled(bool hasDataConnToBeEnabled){ + TRACE("%s enter \r\n", __FUNCTION__); dataOn = hasDataConnToBeEnabled; cnDataEnable(dataOn); } @@ -65,12 +73,12 @@ } void cnSetSimPin(const char* pin){ - if (pin!=NULL) + if (pin) strncpy(simPin,pin, sizeof(simPin)); } -DataStatus cnGetDataConnStatus(){ - return (state == MNG_DATA_UP)? DATA_CONNECTED : DATA_DISCONNECTED; +bool cnIsDataUp(){ + return (state == MNG_DATA_UP)? true : false; } bool cnSetDebug(int level){ @@ -95,6 +103,7 @@ cnDataEnable(dataOn); ret = radioSwitchOn(cnLib); state = (ret == RES_OK) ? MNG_RADIO_ON : MNG_ERROR_RESET; + } //switch off if (state != MNG_RADIO_OFF && !moduleOn){ @@ -114,22 +123,27 @@ if (state == MNG_RADIO_ON ){ ret = simInit(cnLib, simPin); state = (ret == RES_OK) ? MNG_IDLE : MNG_ERROR_RESET; + if (state == MNG_IDLE && mngHandler) + mngHandler(MNG_EV_IDLE, paramDataHandler); } //cycle the registration and data service if (state == MNG_IDLE || state == MNG_DATA_UP){ RegStatus regStatus; + int res; DataConnStatus dataStatus; //Tick the registration service - cnRegLoop(cnLib, ®Status); + res = cnRegLoop(cnLib, ®Status); + if (res != RES_OK && ++respError > MEX_RESP_ERROR) + state = MNG_ERROR_RESET; //Tick Data service cnDataLoop(cnLib, regStatus, &dataStatus); //manage data status if (dataStatus == DATA_IS_CONNECTED){ - state = MNG_DATA_UP; - if (clientHandler!=NULL) clientHandler(DATA_CONNECTED); + state = MNG_DATA_UP; + if (mngHandler) mngHandler(MNG_EV_DATA_UP, paramDataHandler); } else if (dataStatus == DATA_IS_DISCONNECTED){ state = MNG_IDLE; - if (clientHandler!=NULL) clientHandler(DATA_DISCONNECTED); + if (mngHandler) mngHandler(MNG_EV_DATA_DOWN, paramDataHandler); } } //error management @@ -139,7 +153,8 @@ state = MNG_ERROR_STUCK; else{ //otherwise start reset procedure - ERROR("State machine is in Error state, doing Reset.\r\n"); + ERROR("%s: State machine is in Error state, doing Reset.\r\n", __FUNCTION__); + respError=0; cnDataReset(); cnRegReset(); radioSwitchOff(cnLib); @@ -148,23 +163,20 @@ } //when the state is stuck stay here forever if (state == MNG_ERROR_STUCK){ - ERROR("State machine is in Blocked state, please change setting.\r\n"); + ERROR("%s: State machine is in Blocked state, please change setting.\r\n", __FUNCTION__); return false; } //dump info - if (getUtilDebugLevel() > 1 && oldState != state) - dump(); + if (getUtilDebugLevel() > 1 && oldState != state){ + INFO("CNManager Dump\r\n"); + const char* txtState[] = { "Not Initiated", "Radio is Off", "Radio is On", \ + "Idle", "Connected", "Reset Error", "Blocked Error"}; + if (state < sizeof(txtState)/sizeof(*txtState)) + INFO(" Internal State: %s\r\n", txtState[state]); + } return true; } -void dump(){ - INFO("cnanager Dump\r\n"); - const char* txtState[] = { "Not Initiated", "Radio is Off", "Radio is On", \ - "Idle", "Connected", "Reset Error", "Blocked Error"}; - if (state < sizeof(txtState)/sizeof(*txtState)) - INFO(" Internal State: %s\r\n", txtState[state]); -} - /** Switch On Radio \param lib pointer to library */ @@ -173,23 +185,23 @@ TRACE("%s enter \r\n", __FUNCTION__); lib = new CNLib(); if (lib == NULL){ - ERROR("Error on allocating lib\r\n"); + ERROR("%s: Error on allocating lib\r\n", __FUNCTION__); goto error; } lib->setDebug(getUtilDebugLevel()); //power on the module and detect if alive if (!RESPOK(lib->powerOnModem())){ - ERROR("Error on detecting the modem\r\n"); + ERROR("%s: Error on detecting the modem\r\n", __FUNCTION__); goto error; } //init generic modem if (!RESPOK(lib->initModem())){ - ERROR("Error on init device\r\n"); + ERROR("%s: Error on init device\r\n", __FUNCTION__); goto error; } //handle unknown device if (lib->getDev()->dev == MDMParser::DEV_UNKNOWN){ - ERROR("Device is unknown\r\n"); + ERROR("%s: Device is unknown\r\n", __FUNCTION__); goto error; } return RES_OK; @@ -219,14 +231,14 @@ int res; if (simPin == NULL){ - ERROR("Sim Pin is required but not provided\r\n"); + ERROR("%s: Sim Pin is required but not provided\r\n", __FUNCTION__); return RES_ERROR_STUCK; } res = lib->simInit(simPin); if (RESPOK(res) ) return RES_OK; if (lib->getDev()->sim == MDMParser::WRONG_PIN){ - ERROR("Sim pin, %s ,provided is wrong\r\n", simPin); + ERROR("%s: Sim pin, %s ,provided is wrong\r\n", simPin); return RES_ERROR_STUCK; } return RES_ERROR; @@ -251,27 +263,27 @@ //handle sim status switch (lib->getDev()->sim){ case MDMParser::SIM_READY: - INFO("Sim has been initiated correctly\r\n"); + INFO("%s: Sim has been initiated correctly\r\n", __FUNCTION__); res = RES_OK; break; case MDMParser::SIM_PIN: - INFO("Sim Pin is requested\r\n"); + INFO("%s: Sim Pin is requested\r\n"); res = simEnterPin(lib, simPin); break; case MDMParser::SIM_MISSING: - ERROR("Sim has not been inserted, HALT\r\n"); + ERROR("%s: Sim has not been inserted, HALT\r\n", __FUNCTION__); res = RES_ERROR; break; case MDMParser::SIM_PUK: - ERROR("Sim Puk is required, HALT\r\n"); + ERROR("%s: Sim Puk is required, HALT\r\n", __FUNCTION__); res = RES_ERROR_STUCK; break; case MDMParser::SIM_UNKNOWN: - ERROR("Sim Unknown state\r\n"); + ERROR("%s: Sim Unknown state\r\n", __FUNCTION__); res = RES_ERROR_STUCK; break; case MDMParser::WRONG_PIN: - ERROR("Wrong sim pin provided, HALT\r\n"); + ERROR("%s: Wrong sim pin provided, HALT\r\n", __FUNCTION__); res = RES_ERROR_STUCK; break; } @@ -280,4 +292,13 @@ lib->getSimInfo(); } return res; +} + +void getNetStatus(MDMParser::NetStatus* net){ + if (net && cnLib) + memcpy(net, cnLib->getNet(), sizeof(MDMParser::NetStatus)); +} +void getDevStatus(MDMParser::DevStatus* dev){ + if (dev && cnLib) + memcpy(dev, cnLib->getDev(), sizeof(MDMParser::DevStatus)); } \ No newline at end of file