emma controller code in production board v1

Dependencies:   ADE7758_v1 Crypto DHT11 MQTT MbedJSONValueEmma SDFileSystem TFT_ILI9341 SWSPI SetRTC TFT_fonts Touch W5500Interface mbed-rtos mbed-src SoftSerial

Fork of emma_controller_energy by Emma

Revision:
48:053e92b6dc1e
Parent:
47:97eadcb478b2
Child:
49:d11a1914ee8b
--- a/emmaCode.cpp	Fri Aug 28 04:17:31 2015 +0000
+++ b/emmaCode.cpp	Tue Sep 01 11:52:52 2015 +0000
@@ -19,6 +19,10 @@
 //MQTT::Client<MQTTEthernet, Countdown, MQTT_MAX_PACKET_SIZE> client(ipstack);
 TCPSocketConnection sock;
 
+//init gprs
+SoftSerial sim900(PC_10, PA_15); //tx, rx
+DigitalOut pwrKey(PA_8);
+
 //init sd card
 SDFileSystem sd(PA_7, PA_6, PA_5, PB_3, "sd"); //mosi, miso, sck, cs
 
@@ -325,6 +329,9 @@
     restPORT = readSetting("restPORT");
     DBG.printf("restPORT:%s\r\n",restPORT.c_str());
     
+    gprsAPN = readSetting("gprsAPN");
+    DBG.printf("gprsAPN:%s\r\n",gprsAPN.c_str());
+    
     proxySERVER = readSetting("proxySERVER");
     DBG.printf("proxySERVER:%s\r\n",proxySERVER.c_str());
     proxyPORT = readSetting("proxyPORT");
@@ -355,7 +362,10 @@
     
     //check available interface
     isEthAvailable();           //check whether cable is connected
-    wifiAvailable = true;       //wifi module will always on the board
+    
+    //wifiAvailable = true;       //wifi module will always on the board
+    wifiAvailable = false;      //for testing purpose
+    
     gprsAvailable = true;       //gprs module will always on the board
     DBG.printf("eth:%d\r\n",ethAvailable);
     DBG.printf("wifi:%d\r\n",wifiAvailable);
@@ -373,7 +383,7 @@
         _ESP.printf("MODE=C");
         while(1) {
             char rcv[128] = {};
-            rcvReply(rcv,3000);
+            wifiRcvReply(rcv,3000);
             str = rcv;
             if(str.find("SC_STATUS_FIND_CHANNEL") != std::string::npos)
                 break;
@@ -387,7 +397,7 @@
         DBG.printf("entering wifi configuration mode\r\n");
         while(1) {
             char rcv[128] = {};
-            rcvReply(rcv,3000);
+            wifiRcvReply(rcv,3000);
             str = rcv;
             if(str.find("MODE=C OK") != std::string::npos) {
                 //save wifiSSID and wifiPASS
@@ -592,7 +602,7 @@
         _ESP.printf("MODE=S");
         while(1) {
             char rcv[128] = {};
-            rcvReply(rcv,3000);
+            wifiRcvReply(rcv,3000);
             str = rcv;
             if(str.find("MODE=S_OK") != std::string::npos)
                 break;
@@ -605,7 +615,7 @@
         
         while(1) {
             char rcv[512] = {};
-            rcvReply(rcv,3000);
+            wifiRcvReply(rcv,3000);
             //DBG.printf("rcv:%s\r\n",rcv);
             str = rcv;
             if(str.find("MODE=S_Config") != std::string::npos) {
@@ -672,7 +682,7 @@
     } else {
         DBG.printf("no eth or wifi is available\r\n");
         TFT.locate(0,0);
-        TFT.printf(" no iface avail, please restart!");
+        TFT.printf(" no eth or wifi, please restart!");
     }
 }
 void emmaModeRegister(void) {
@@ -699,6 +709,7 @@
     isGprsConnected();
     DBG.printf("ethConnected:%d\r\n",ethConnected);
     DBG.printf("wifiConnected:%d\r\n",wifiConnected);
+    DBG.printf("gprsConnected:%d\r\n",gprsConnected);
     
     if(ethConnected) {
         DBG.printf("emmaModeRegister - eth\r\n");
@@ -741,7 +752,7 @@
             str = ethREST(connHost,connPort,connData);
             DBG.printf("rsp reg:%s\r\n",str.c_str());
 
-            //check and save mqtt setting
+            //check and save settings
             if(str.find("[") != std::string::npos && str.find("]") != std::string::npos) {
                 str.erase(str.begin(),str.begin()+str.find("[")+1);
                 str.erase(str.begin()+str.find("]"),str.end());
@@ -845,7 +856,7 @@
         if(emmaRegistered) {
             DBG.printf("registration successful\r\n");
             TFT.locate(0,60);
-            TFT.printf(" registration successful\r\n");
+            TFT.printf(" registration successful. please restart.\r\n");
         } else {
             DBG.printf("registration unsuccessful\r\n");
             TFT.locate(0,60);
@@ -911,7 +922,7 @@
                 rest.getResponse(s,sizeof(s));
                 DBG.printf("rsp reg:%s\r\n",s);
 
-                //check and save mqtt setting
+                //check and save settings
                 str = s;
                 if(str.find("[") != std::string::npos && str.find("]") != std::string::npos) {
                     str.erase(str.begin(),str.begin()+str.find("[")+1);
@@ -1006,7 +1017,7 @@
             if(emmaRegistered) {
                 DBG.printf("registration successful\r\n");
                 TFT.locate(0,60);
-                TFT.printf(" registration successful\r\n");
+                TFT.printf(" registration successful. please restart.\r\n");
             } else {
                 DBG.printf("registration unsuccessful\r\n");
                 TFT.locate(0,60);
@@ -1014,10 +1025,108 @@
             }
             while(1);
         }
-        
     } else if(gprsConnected) {
         DBG.printf("emmaModeRegister - gprs\r\n");
         
+        //register
+        sscanf(restPORT.c_str(),"%d",&connPort);
+        connBodyLen = sprintf(connBody,"{\"uid\":\"%s\",\"hmac\":\"%s\"}",emmaUID.c_str(),hmac.c_str());
+        sprintf(s,"POST /emma/api/controller/register HTTP/1.1\nHost: %s:%d\nContent-Length: %d\n\n%s\n\n%c",restSERVER.c_str(),connPort,connBodyLen,connBody,26);
+        while(!emmaGetRegKey) {
+            str = gprsREST(restSERVER,connPort,s);
+            
+            //check and save settings
+            if(str.find("[") != std::string::npos && str.find("]") != std::string::npos) {
+                str.erase(str.begin(),str.begin()+str.find("[")+1);
+                str.erase(str.begin()+str.find("]"),str.end());
+        
+                MbedJSONValue jsonValue;
+                parse(jsonValue,str.c_str());
+    
+                char *parameter[4] = {"mqttDOMAIN","mqttKEY","mqttSECRET","registrationKey"};
+    
+                //save mqtt parameter
+                writeSetting(parameter[0],"()");    //sd card need to be initialized
+                for(int i=0; i<3; i++) {
+                    if(jsonValue.hasMember(parameter[i])) {
+                        string val = jsonValue[parameter[i]].get<std::string>();
+                        int st = writeSetting(parameter[i],val.c_str());
+                        if(st) {
+                            DBG.printf("%s: %s is saved\r\n",parameter[i],val.c_str());
+                        } else {
+                            DBG.printf("%s is not saved\r\n",parameter[i]);
+                        }
+                    }
+                }
+        
+                //get registrationKey
+                if(jsonValue.hasMember(parameter[3])) {
+                    string val = jsonValue[parameter[3]].get<std::string>();
+                    if(val.find("(") != std::string::npos && val.find(")") != std::string::npos) {
+                        val.erase(val.begin(),val.begin()+val.find("(")+1);
+                        val.erase(val.begin()+val.find(")"),val.end());
+                        regKey = val;
+                        DBG.printf("%s: %s\r\n",parameter[3],regKey.c_str());
+                            
+                        TFT.locate(0,20);
+                        TFT.printf(" %s: %s\r\n",parameter[3],regKey.c_str());
+                            
+                        emmaGetRegKey = true;
+                    }
+                }
+            }
+            wait(1);   
+        }
+        
+        //calculate hmac
+        sprintf(r,"emma-%s-%s",emmaUID.c_str(),regKey.c_str());
+        hmac = calculateMD5(r);
+        DBG.printf("hmac:%s\r\n",hmac.c_str());
+        
+        //verify registration
+        connBodyLen = sprintf(connBody,"{\"uid\":\"%s\",\"registrationKey\":\"%s\",\"hmac\":\"%s\"}",emmaUID.c_str(),regKey.c_str(),hmac.c_str());
+        sprintf(s,"POST /emma/api/controller/verify HTTP/1.1\nHost: %s:%d\nContent-Length: %d\n\n%s\n\n%c",restSERVER.c_str(),connPort,connBodyLen,connBody,26);
+        while(!emmaRegistered && loop < 12) {
+            str = gprsREST(restSERVER,connPort,s);
+            DBG.printf("rsp vrf:%s\r\n",str.c_str());
+            TFT.locate(0,40);
+            TFT.printf("                              ");
+            TFT.locate(0,40);
+            TFT.printf(" wait:%d\r\n",loop);
+            
+            //check verification
+            if(str.find("[") != std::string::npos && str.find("]") != std::string::npos) {
+                str.erase(str.begin(),str.begin()+str.find("[")+1);
+                str.erase(str.begin()+str.find("]"),str.end());
+                    
+                MbedJSONValue jsonValue;
+                parse(jsonValue,str.c_str());
+                if(jsonValue.hasMember("user")) {
+                    string val = jsonValue["user"].get<std::string>();
+                    DBG.printf(" %s is registered\r\n",val.c_str());
+                    TFT.locate(0,40);
+                    TFT.printf("                              ");
+                    TFT.locate(0,40);
+                    TFT.printf(" %s is registered\r\n",val.c_str());
+                    emmaRegistered = true;
+                }
+            }
+            wait(5);
+            loop++;    
+        }
+        
+        //check whether registration success
+        if(emmaRegistered) {
+            DBG.printf("registration successful\r\n");
+            TFT.locate(0,60);
+            TFT.printf(" registration successful. please restart.\r\n");
+        } else {
+            DBG.printf("registration unsuccessful\r\n");
+            TFT.locate(0,60);
+            TFT.printf(" registration unsuccessful. please restart.\r\n");
+        }
+        while(1);
+        
     } else {
         DBG.printf("no eth, wifi, or gprs is connected\r\n");
         TFT.locate(0,60);
@@ -1055,6 +1164,7 @@
     isGprsConnected();
     DBG.printf("ethConnected:%d\r\n",ethConnected);
     DBG.printf("wifiConnected:%d\r\n",wifiConnected);
+    DBG.printf("gprsConnected:%d\r\n",gprsConnected);
     
     TFT.locate(0,0);
     TFT.printf(" emmaModeOperation");
@@ -2301,149 +2411,12 @@
                 TFT.printf("                                        ");
                 
                 newCommand = false;
-                
-                /*
-                //check whether command is valid
-                bool validCommand = true;
-                for(int i=0; i<5; i++) {
-                    validCommand = validCommand && jsonValue.hasMember(parameter[i]);
-                }
-                DBG.printf("command validity:%d\r\n",validCommand);
-                
-                if(validCommand) {
-                    string commandFrom = jsonValue[parameter[0]].get<std::string>();
-                    string commandNType = jsonValue[parameter[1]].get<std::string>();
-                    string commandNAddr = jsonValue[parameter[2]].get<std::string>();
-                    string commandDType = jsonValue[parameter[3]].get<std::string>();
-                    string commandCmd = jsonValue[parameter[4]].get<std::string>();
-                    
-                    if(commandNType == "0") {       //switch on panel controller
-                        DBG.printf("command for switch\r\n");
-                    }
-                    else if(commandNType == "1") {  //node with mac address
-                        DBG.printf("command for node\r\n");
-                        //get node ip address based on node mac address
-                        //string nodeIP;
-                        //nodeIp = readNodeIP(commandNAddr);
-                        //nodeIP = "192.168.2.15";
-                        //DBG.printf("nodeIP: %s\r\n",nodeIP.c_str());
-                    
-                        //get index of node list based on mac address
-                        int idx = NODES_INVALID;
-                        for(int i=0; i<NODES_MAX; i++) {
-                            if(!nodes[i].macAddr.compare(commandNAddr)) {
-                                idx = i;
-                            }
-                        }
-                    
-                        //execution process
-                        //int trial;
-                        string execResult = "failed";
-                        if(idx != NODES_INVALID) {
-                            DBG.printf("index found at %d\r\n",idx);
-                        
-                            //get cmd string based on device type and command number
-                            string nodeCmd;
-                            nodeCmd = readNodeCmd(commandDType,commandCmd);
-                            //nodeCmd = "020129A0163B161315131613153C151316131514143C153C16141414141415151315141414141514141415141414143D1514143D141415141414143D14000D"; //turn off
-                            //DBG.printf("nodeCmd: %s\r\n",nodeCmd.c_str());
-                        
-                            //execute command
-                            DBG.printf("executing command\r\n");
-                            sprintf(s,"<?xml version=\"1.0\" encoding=\"utf-8\"?><app_cmd cmd=\"5\" /><app_data code=\"%s\"/>\r\n",nodeCmd.c_str());
-                            
-                            trial=0;
-                            while(1) {
-                                rxBuf.clear();
-                                //cmdExecuted = false;
-                                if(trial>=2) {   //two times trial
-                                    DBG.printf("cmd is not executed\r\n");
-                                    TFT.foreground(Red);
-                                    TFT.locate(0,180);
-                                    TFT.printf("                                        ");
-                                    TFT.locate(0,180);
-                                    TFT.printf("cmd is not executed");
-                                    wait(1);
-                                    TFT.locate(0,180);
-                                    TFT.printf("                                        ");
-                                    TFT.foreground(White);
-                                    break;    
-                                }
-                                nodes[idx].restConn->get("/",s);
-                                wait(2);
-                                if(rxBuf.find("REST: status = 200") != std::string::npos) {
-                                    DBG.printf("cmd is executed\r\n");
-                                    TFT.foreground(Green);
-                                    TFT.locate(0,180);
-                                    TFT.printf("                                        ");
-                                    TFT.locate(0,180);
-                                    TFT.printf("cmd is executed");
-                                    wait(1);
-                                    TFT.locate(0,180);
-                                    TFT.printf("                                        ");
-                                    TFT.foreground(White);
-                                    execResult = "success";
-                                    break;    
-                                }
-                                trial++;
-                            }    
-                        } else {
-                            TFT.foreground(Red);
-                            TFT.locate(0,180);
-                            TFT.printf("                                        ");
-                            TFT.locate(0,180);
-                            TFT.printf("node is invalid");
-                            wait(1);
-                            TFT.locate(0,180);
-                            TFT.printf("                                        ");
-                            TFT.foreground(White);    
-                        }
-                    
-                        wait(2);       
-                        //send execution result
-                        //DBG.printf("send execution result\r\n");
-                        
-                        //calculate hmacCmd
-                        for(int j=0; j<sizeof(p); j++) {
-                            p[j]=0; }
-                        sprintf(p,"emma-%s-%s",emmaUID.c_str(),commandCmd.c_str());   
-                        hmacCmd = calculateMD5(p);
-                        
-                        sprintf(s,"{\"uid\":\"%s\",\"nType\":\"%s\",\"nAddr\":\"%s\",\"dType\":\"%s\",\"cmd\":\"%s\",\"from\":\"%s\",\"result\":\"%s\",\"hmac\":\"%s\"}",
-                        emmaUID.c_str(), commandNType.c_str(),commandNAddr.c_str(),commandDType.c_str(),commandCmd.c_str(),commandFrom.c_str(),execResult.c_str(),hmacCmd.c_str());
-                    
-                        trial=0;
-                        while(1) {
-                            if(trial>=2) {   //two times trial
-                                DBG.printf("failed to send execution result\r\n");
-                                break;    
-                            }
-                            rest.post("/emma/api/controller/result",s);
-                            wait(2);
-                            str = rxBuf;
-                            if(str.rfind("/result") != std::string::npos) {
-                                str.erase(str.begin(),str.begin()+str.rfind("/result"));
-                                if(str.find("\"status\":\"success\"") != std::string::npos) {
-                                    DBG.printf("success to send execution result\r\n");
-                                    break;
-                                }
-                            }
-                            checkRxBuffer();
-                            trial++;
-                        }
-                    }
-                }
-                
-                //clear text on lcd
-                TFT.locate(0,160);
-                TFT.printf("                                        ");
-                
-                newCommand = false;
-                */
             }
             
             osDelay(5000);    
         }
+    } else if(gprsConnected) {
+        DBG.printf("emmaModeOperation - gprs\r\n");
     }
 }
 void emmaModeFirmwareDownload(void) {
@@ -2472,7 +2445,7 @@
     DBG.printf("set mode bridge\r\n");
     while(1) {
         char rcv[128] = {};
-        rcvReply(rcv,3000);
+        wifiRcvReply(rcv,3000);
         str = rcv;
         if(str.find("MODE=B_OK") != std::string::npos)
             break;
@@ -2977,137 +2950,73 @@
     }
     //DBG.printf("checkVoltagePower-finish\r\n");
 }
+/*end energy related*/
 
-/*
-void checkVoltagePower(void) {
-    //check if voltage or power violates threshold
-    char connBody[256];
-    char p[64];
-    char q[32];
+/*start eth rest*/
+string ethREST(string host, int port, string data) {
+    char buf[1024];
     char s[256];
-    int connBodyLen=0;
-    int connPort=0;
-    string hmacTime;
-    string str;
-    time_t seconds;
-    
-    //DBG.printf("checkVoltagePower-start\r\n");
-    
-    //vrms and irms should be placed inside energy calculation routine
-    
-    //get time
-    seconds = time(NULL);
-    strftime(q, 32, "%Y-%m-%d %H:%M:%S",localtime(&seconds));
-    
-    //calculate hmacTime
-    sprintf(p,"emma-%s-%s",emmaUID.c_str(),q);   
-    hmacTime = calculateMD5(p);
+    int ret=99;
+    Timer t;
     
-    if(AVrms > vrmsTHH || AWatt > wattTHH) {
-        DBG.printf("alert on ch1\r\n");
-        
-        connBodyLen = sprintf(connBody,"{\"uid\":\"%s\",\"hmac\":\"%s\",\"time\":\"%s\",\"voltage\":%.2f,\"power\":%.2f}",
-        emmaUID.c_str(),hmacTime.c_str(),q,AVrms,AWatt);
-        sprintf(s,"POST /%s/api/controller/alert/1 HTTP/1.0\nHost: %s\nContent-Length:%d\n\n%s\r\n\r\n",appNAME.c_str(),restSERVER.c_str(),connBodyLen,connBody);
-        DBG.printf("ch1req:%s\r\n",s);
-        sscanf(restPORT.c_str(),"%d",&connPort);
-        str.clear();
-        str = ethREST(restSERVER,connPort,s);
-        DBG.printf("ch1:%s\r\n",str.c_str());
-        
+    t.start();
+    while(eth.linkstatus() && t.read() < 5 && ret !=0) {
+        ret = sock.connect(host.c_str(),port);
+    }
+    t.stop();
+    t.reset();
     
-        //sprintf(s,"{\"uid\":\"%s\",\"hmac\":\"%s\",\"time\":\"%s\",\"voltage\":%.2f,\"power\":%.2f}",
-        //emmaUID.c_str(),hmacTime.c_str(),q,AVrms,AWatt);
-        
-        //sprintf(p,"/%s/api/controller/alert/1",appNAME.c_str());
-        //DBG.printf("ch1:%s\r\n",s);
-        
-        //rest.post(p,s);
+    memset(buf,0,sizeof(buf));
+    if(sock.is_connected()) {
+        DBG.printf("sockConnect\r\n");
+        sprintf(s,"%s",data.c_str());
+        sock.send_all(s,sizeof(s)-1);
         //wait(2);
-        //str = rxBuf;
-        //if(str.rfind("/alert/1") != std::string::npos) {
-        //    str.erase(str.begin(),str.begin()+str.rfind("/alert/1"));
-        //    if(str.find("\"status\":\"success\"") != std::string::npos) {
-        //        DBG.printf("send alert ch1 success\r\n");
-        //    } else {
-        //        DBG.printf("send alert ch1 failed\r\n");
-        //    }
-        //}
-       
-        
-    }
-    
-    if(BVrms > vrmsTHH || BWatt > wattTHH) {
-        DBG.printf("alert on ch2\r\n");
+        wait(0.5);
         
-        connBodyLen = sprintf(connBody,"{\"uid\":\"%s\",\"hmac\":\"%s\",\"time\":\"%s\",\"voltage\":%.2f,\"power\":%.2f}",
-        emmaUID.c_str(),hmacTime.c_str(),q,BVrms,BWatt);
-        sprintf(s,"POST /%s/api/controller/alert/2 HTTP/1.0\nHost: %s\nContent-Length:%d\n\n%s\r\n\r\n",appNAME.c_str(),restSERVER.c_str(),connBodyLen,connBody);
-        DBG.printf("ch2req:%s\r\n",s);
-        sscanf(restPORT.c_str(),"%d",&connPort);
-        str.clear();
-        str = ethREST(restSERVER,connPort,s);
-        DBG.printf("ch2:%s\r\n",str.c_str());
-        
-        
-        //sprintf(s,"{\"uid\":\"%s\",\"hmac\":\"%s\",\"time\":\"%s\",\"voltage\":%.2f,\"power\":%.2f}",
-        //emmaUID.c_str(),hmacTime.c_str(),q,BVrms,BWatt);
-        
-        //sprintf(p,"/%s/api/controller/alert/2",appNAME.c_str());
-        //DBG.printf("ch2:%s\r\n",s);
-        
-        //rest.post(p,s);
-        //wait(2);
-        //str = rxBuf;
-        //if(str.rfind("/alert/2") != std::string::npos) {
-        //    str.erase(str.begin(),str.begin()+str.rfind("/alert/2"));
-        //    if(str.find("\"status\":\"success\"") != std::string::npos) {
-        //        DBG.printf("send alert ch2 success\r\n");
-        //    } else {
-        //        DBG.printf("send alert ch2 failed\r\n");
-        //    }
-        //}
-        
-        
+        //receive return
+        t.start();
+        while(1) {
+            ret = sock.receive(buf, sizeof(buf));
+            if(ret<=0 || t.read() > 5) {
+                t.stop();
+                t.reset();
+                break;
+            }    
+        }
+        sock.close();    
+    } else {
+        DBG.printf("sockNotConnect\r\n");       
     }
+    return buf;
+    
+    /*
+    //eth.init(); //use DHCP
+    eth.connect();
     
-    if(CVrms > vrmsTHH || CWatt > wattTHH) {
-        DBG.printf("alert on ch3\r\n");
-        
-        connBodyLen = sprintf(connBody,"{\"uid\":\"%s\",\"hmac\":\"%s\",\"time\":\"%s\",\"voltage\":%.2f,\"power\":%.2f}",
-        emmaUID.c_str(),hmacTime.c_str(),q,CVrms,CWatt);
-        sprintf(s,"POST /%s/api/controller/alert/3 HTTP/1.0\nHost: %s\nContent-Length:%d\n\n%s\r\n\r\n",appNAME.c_str(),restSERVER.c_str(),connBodyLen,connBody);
-        DBG.printf("ch3req:%s\r\n",s);
-        sscanf(restPORT.c_str(),"%d",&connPort);
-        str.clear();
-        str = ethREST(restSERVER,connPort,s);
-        DBG.printf("ch3:%s\r\n",str.c_str());
-        
-        
-        //sprintf(s,"{\"uid\":\"%s\",\"hmac\":\"%s\",\"time\":\"%s\",\"voltage\":%.2f,\"power\":%.2f}",
-        //emmaUID.c_str(),hmacTime.c_str(),q,CVrms,CWatt);
-        
-        //sprintf(p,"/%s/api/controller/alert/3",appNAME.c_str());
-        //DBG.printf("ch3:%s\r\n",s);
-        
-        //rest.post(p,s);
-        //wait(2);
-        //str = rxBuf;
-        //if(str.rfind("/alert/3") != std::string::npos) {
-        //    str.erase(str.begin(),str.begin()+str.rfind("/alert/3"));
-        //    if(str.find("\"status\":\"success\"") != std::string::npos) {
-        //        DBG.printf("send alert ch3 success\r\n");
-        //    } else {
-        //        DBG.printf("send alert ch3 failed\r\n");
-        //    }
-        //}
-        
-        
+    //TCPSocketConnection sock;
+    Timer t;
+    
+    sprintf(s,"%s",data.c_str());
+    sock.connect(host.c_str(),port);
+    sock.send_all(s,sizeof(s)-1);
+    wait(2);
+    
+    //receive return
+    t.start();
+    while(1) {
+        ret = sock.receive(buf, sizeof(buf));
+        if(ret<=0 || t.read_ms() > 10000) {
+            t.stop();
+            break;
+        }    
     }
-    //DBG.printf("checkVoltagePower-finish\r\n");
+    sock.close();
+    eth.disconnect();
+    return buf;
+    */
 }
-*/
-/*end energy related*/
+/*end eth rest*/
 
 /*start wifi mqtt*/
 void mqttConnected(void* response) {
@@ -3186,8 +3095,199 @@
     //clear rxBuf
     rxBuf.clear();
 }
+void wifiRcvReply(char *r, int to) {
+    Timer t;
+    bool ended = false;
+    char c;
+    
+    strcpy(r,"");
+    t.start();
+    while(!ended) {
+        if(_ESP.readable()) {
+            c = _ESP.getc();
+            addChar(r,c);
+            t.start();
+        }
+        if(t.read_ms() > to) {
+            ended = true;    
+        }    
+    }
+    addChar(r, 0x00);    
+}
 /*end wifi rest*/
 
+/*start gprs rest*/
+void gprsReset(void) {
+    pwrKey = 0;
+    wait(1);
+    pwrKey = 1;
+    wait(2);
+    pwrKey = 0;
+    wait(2);    
+}
+string gprsInit(string APN) {
+    char r[128];
+    char s[128];
+    int n=0;
+    string str;
+    
+    while(1) {
+        sim900.printf("AT+CIPMUX=1\r\n");
+        gprsRcvReply(r,3000);
+        //DBG.printf("rspn[CIPMUX]:%s\r\n",r);
+        DBG.printf("AT+CIPMUX\r\n");
+        str = r;
+        if(str.find("OK") != std::string::npos) {
+            break;    
+        }
+        if(n>=3) {
+            return "ERROR";    
+        }
+        n++;
+    }
+    
+    if(!APN.compare("Telkomsel")) {
+        strcpy(s,"AT+CSTT=\"telkomsel\",\"wap\",\"wap123\"\r\n");
+    } else if(!APN.compare("Indosat")) {
+        strcpy(s,"AT+CSTT=\"indosatgprs\",\"indosat\",\"indosat\"\r\n");
+    } else if(!APN.compare("XL")) {
+        strcpy(s,"AT+CSTT=\"www.xlgprs.net\",\"xlgprs\",\"proxl\"\r\n");
+    } else if(!APN.compare("3")) {
+        strcpy(s,"AT+CSTT=\"3gprs\",\"3gprs\",\"3gprs\"\r\n");
+    } else {
+        return "ERROR";    
+    }
+    
+    n=0;
+    while(1) {
+        sim900.printf("%s",s);
+        gprsRcvReply(r,5000);
+        //DBG.printf("rspn[CSTT]:%s\r\n",r);
+        DBG.printf("AT+CSTT\r\n");
+        str = r;
+        if(str.find("OK") != std::string::npos) {
+            break;    
+        }
+        if(n>=3) {
+            return "ERROR";    
+        }
+        n++;
+    }
+    
+    n=0;
+    while(1) {
+        sim900.printf("AT+CIICR\r\n");
+        gprsRcvReply(r,3000);
+        //DBG.printf("rspn[CIICR]:%s\r\n",r);
+        DBG.printf("AT+CIICR\r\n");
+        str = r;
+        if(str.find("OK") != std::string::npos) {
+            break;    
+        }
+        if(n>=3) {
+            return "ERROR";    
+        }
+        n++;
+    }
+    
+    while(1) {
+        sim900.printf("AT+CIFSR\r\n");
+        gprsRcvReply(r,3000);
+        //DBG.printf("rspn[CIFSR]:%s\r\n",r);
+        DBG.printf("AT+CIFSR\r\n");
+        str = r;
+        if(str.find("ERROR") != std::string::npos) {
+            return "ERROR";    
+        } else {
+            return str;    
+        }
+    }
+}
+string gprsREST(string host, int port, string data) {
+    char r[128];
+    char rLong[2048];
+    int n=0;
+    string str;
+    
+    //AT+CIPSTART
+    while(1) {
+        sim900.printf("AT+CIPSTART=1,\"TCP\",\"%s\",%d\r\n",host.c_str(),port);
+        gprsRcvReply(r,3000);
+        //DBG.printf("rspn[CIPSTART]:%s",r);
+        DBG.printf("[CIPSTART]\r\n");
+        str = r;
+        if(str.find("CONNECT OK") != std::string::npos) {
+            break;    
+        }
+        if(n>5) {
+            return "ERROR:CIPSTART"; //unable to start connection    
+        }
+        n++;
+    }
+    
+    //AT+CIPSEND
+    sim900.printf("AT+CIPSEND=1,%d\r\n",data.length());
+    gprsRcvReply(r,1000);
+    //DBG.printf("rspn[CIPSEND]:%s",r);
+    DBG.printf("[CIPSEND]\r\n");
+    
+    str = r;
+    if(str.find(">") != std::string::npos) {
+        sim900.printf("%s",data.c_str());
+        gprsRcvReply(rLong,10000);
+        //DBG.printf("rspn[>]:%s\r\n",rLong);
+        DBG.printf("[>]\r\n");
+    }
+    else {
+        return "ERROR:>";   //unable to send data
+    }
+    
+    //close connection (case for get request)
+    str = rLong;
+    if(str.find("CLOSED") != std::string::npos) {
+        return rLong;
+    }
+    
+    //close connection
+    n=0;
+    while(1) {
+        sim900.printf("AT+CIPCLOSE=1,1\r\n");
+        gprsRcvReply(r,3000);
+        //DBG.printf("rspn[CIPCLOSE]:%s\r\n",r);
+        DBG.printf("[CIPCLOSE]\r\n");
+        str = r;
+        if(str.find("CLOSE OK") != std::string::npos) {
+            break;    
+        }
+        if(n>5) {
+            return "ERROR:CIPCLOSE"; //unable to close connection    
+        }
+        n++;
+    }
+    return rLong;
+}
+void gprsRcvReply(char *r, int to) {
+    Timer t;
+    bool ended = false;
+    char c;
+    
+    strcpy(r,"");
+    t.start();
+    while(!ended) {
+        if(sim900.readable()) {
+            c = sim900.getc();
+            addChar(r,c);
+            t.start();
+        }
+        if(t.read_ms() > to) {
+            ended = true;    
+        }    
+    }
+    addChar(r, 0x00);
+}
+
+/*end gprs rest*/
+
 /*start emma settings*/
 string getUID(void) {
     char s[32];
@@ -3363,72 +3463,6 @@
 }
 /*end emma node*/
 
-/*start emma connection function*/
-string ethREST(string host, int port, string data) {
-    char buf[1024];
-    char s[256];
-    int ret=99;
-    Timer t;
-    
-    t.start();
-    while(eth.linkstatus() && t.read() < 5 && ret !=0) {
-        ret = sock.connect(host.c_str(),port);
-    }
-    t.stop();
-    t.reset();
-    
-    memset(buf,0,sizeof(buf));
-    if(sock.is_connected()) {
-        DBG.printf("sockConnect\r\n");
-        sprintf(s,"%s",data.c_str());
-        sock.send_all(s,sizeof(s)-1);
-        //wait(2);
-        wait(0.5);
-        
-        //receive return
-        t.start();
-        while(1) {
-            ret = sock.receive(buf, sizeof(buf));
-            if(ret<=0 || t.read() > 5) {
-                t.stop();
-                t.reset();
-                break;
-            }    
-        }
-        sock.close();    
-    } else {
-        DBG.printf("sockNotConnect\r\n");       
-    }
-    return buf;
-    
-    /*
-    //eth.init(); //use DHCP
-    eth.connect();
-    
-    //TCPSocketConnection sock;
-    Timer t;
-    
-    sprintf(s,"%s",data.c_str());
-    sock.connect(host.c_str(),port);
-    sock.send_all(s,sizeof(s)-1);
-    wait(2);
-    
-    //receive return
-    t.start();
-    while(1) {
-        ret = sock.receive(buf, sizeof(buf));
-        if(ret<=0 || t.read_ms() > 10000) {
-            t.stop();
-            break;
-        }    
-    }
-    sock.close();
-    eth.disconnect();
-    return buf;
-    */
-}
-/*end emma connection function*/
-
 /*start emma private function*/
 void isEthAvailable(void) {
     //if(ipstack.getEth().linkstatus()) {
@@ -3565,7 +3599,33 @@
 }
 
 void isGprsConnected(void) {
-        
+    char cmd[256];
+    int connPort;
+    string str;
+    
+    gprsReset();
+    str = gprsInit(gprsAPN);
+    if(str.find("ERROR") != std::string::npos) {
+        gprsConnected = false;    
+    } else {
+        if(str.find("AT+CIFSR") != std::string::npos) {
+            str.erase(str.begin(),str.begin()+str.find("AT+CIFSR")+10);
+            str.erase(str.end()-2,str.end());
+            DBG.printf("IP Addr:%s\r\n",str.c_str());
+            //test connection
+            sscanf(restPORT.c_str(),"%d",&connPort);
+            sprintf(cmd,"GET /emma/api/controller/test HTTP/1.0\nHost: %s:%d\n\n\n\n%c",restSERVER.c_str(),connPort,26);
+            str = gprsREST(restSERVER,connPort,cmd);
+            DBG.printf("str:%s\r\n",str.c_str());
+            if(str.find("\"status\":\"OK\"") != std::string::npos) {
+                gprsConnected = true;
+            } else {
+                gprsConnected = false;
+            }
+        } else {
+            gprsConnected = false;    
+        }
+    }
 }
 
 void addChar(char *s, char c) {
@@ -3575,26 +3635,6 @@
     s[k + 1] = 0;
 }
 
-void rcvReply(char *r, int to) {
-    Timer t;
-    bool ended = false;
-    char c;
-    
-    strcpy(r,"");
-    t.start();
-    while(!ended) {
-        if(_ESP.readable()) {
-            c = _ESP.getc();
-            addChar(r,c);
-            t.start();
-        }
-        if(t.read_ms() > to) {
-            ended = true;    
-        }    
-    }
-    addChar(r, 0x00);    
-}
-
 string calculateMD5(string text) {
     char s[64];
     memset(s,0,sizeof(s));  //for unknown reason, after reading UID, the 's' will contaion UID data