this is using the mbed os version 5-13-1

Dependencies:   mbed-http

Committer:
ocomeni
Date:
Fri Jul 19 16:49:26 2019 +0000
Branch:
PassingRegression
Revision:
129:590bdc2dcf5b
Parent:
127:a21788227ca6
Implementation of Access token acquisition; 1. make request with credentials - DONE; 2. get response - DONE; 3. extract Id and refresh tokens from response - DONE; 4. integrate with code - DONE; Testing ongoing

Who changed what in which revision?

UserRevisionLine numberNew contents of line
ocomeni 103:7b566b522427 1 #include "debug.h"
ocomeni 78:07bb86e3ce14 2 #include "WiFiManager.h"
ocomeni 78:07bb86e3ce14 3 #include "common_config.h"
ocomeni 103:7b566b522427 4 #define FILE_CODE "wifi"
ocomeni 108:3c8fb2c6e7bf 5 #define USE_EVENTS_FOR_HTTPS_REQUESTS
ocomeni 78:07bb86e3ce14 6
ocomeni 116:2296cf274661 7 WiFiManager::WiFiManager(wifi_config_t *wifi_config, WiFiInterface *wifi,
ocomeni 116:2296cf274661 8 internet_config_t *internet_config,
ocomeni 98:65c2333a38b6 9 events::EventQueue &event_queue,
ocomeni 80:e8f0e92e3ac9 10 MemoryPool<wifi_cmd_message_t, 16> *aT2WiFimPool,
ocomeni 80:e8f0e92e3ac9 11 Queue<wifi_cmd_message_t, 16> *aT2WiFiCmdQueue,
ocomeni 81:637a87eb8170 12 MemoryPool<at_resp_message_t, 16> *wiFi2ATmPool,
ocomeni 81:637a87eb8170 13 Queue<at_resp_message_t, 16> *wiFi2ATCmdQueue,
ocomeni 87:99b37d26ff2a 14 MemoryPool<wifi_data_msg_t, PQDSZ> *aT2WiFiDatamPool,
ocomeni 87:99b37d26ff2a 15 Queue<wifi_data_msg_t, PQDSZ> *aT2WiFiDataQueue,
ocomeni 87:99b37d26ff2a 16 MemoryPool<at_data_msg_t, PQDSZ> *wiFi2ATDatamPool,
ocomeni 87:99b37d26ff2a 17 Queue<at_data_msg_t, PQDSZ> *wiFi2ATDataQueue)
ocomeni 78:07bb86e3ce14 18 :
ocomeni 81:637a87eb8170 19 wifi_config(wifi_config),
ocomeni 81:637a87eb8170 20 network(wifi),
ocomeni 116:2296cf274661 21 internet_config(internet_config),
ocomeni 98:65c2333a38b6 22 _event_queue(event_queue),
ocomeni 81:637a87eb8170 23 _aT2WiFimPool(aT2WiFimPool),
ocomeni 81:637a87eb8170 24 _aT2WiFiCmdQueue(aT2WiFiCmdQueue),
ocomeni 81:637a87eb8170 25
ocomeni 81:637a87eb8170 26 _wiFi2ATmPool(wiFi2ATmPool),
ocomeni 81:637a87eb8170 27 _wiFi2ATCmdQueue(wiFi2ATCmdQueue),
ocomeni 81:637a87eb8170 28
ocomeni 81:637a87eb8170 29 _aT2WiFiDatamPool(aT2WiFiDatamPool),
ocomeni 81:637a87eb8170 30 _aT2WiFiDataQueue(aT2WiFiDataQueue),
ocomeni 81:637a87eb8170 31
ocomeni 81:637a87eb8170 32 _wiFi2ATDatamPool(wiFi2ATDatamPool),
ocomeni 81:637a87eb8170 33 _wiFi2ATDataQueue(wiFi2ATDataQueue)
ocomeni 78:07bb86e3ce14 34
ocomeni 78:07bb86e3ce14 35 {
ocomeni 104:11e9605093c9 36 lastScanCount = 0;
ocomeni 104:11e9605093c9 37 wifiCmd = WIFI_CMD_NONE;
ocomeni 116:2296cf274661 38 //internet_config.connectionScheme = ALWAYS_CONNECTED; // set default connection scheme
ocomeni 104:11e9605093c9 39 is_connected = false;
ocomeni 104:11e9605093c9 40 http_response = NULL;
ocomeni 104:11e9605093c9 41 chunkNum = 0;
ocomeni 104:11e9605093c9 42 socket = NULL;
ocomeni 118:8df0e9c2ee3f 43 responseString = NULL;
ocomeni 118:8df0e9c2ee3f 44 responseBytes = NULL;
ocomeni 118:8df0e9c2ee3f 45 at_data_resp = NULL;
ocomeni 104:11e9605093c9 46 https_connection_active = false;
ocomeni 113:888e262ff0a9 47 use_full_hostname = false;
ocomeni 104:11e9605093c9 48 wifiBusy = 0;
ocomeni 104:11e9605093c9 49 wifiWatchdogTimer.start();
ocomeni 104:11e9605093c9 50 watchdogCnt = 0;
ocomeni 109:c274780ff609 51 //_event_queue.call_every(10000, this, &WiFiManager::callWifiWatchDog);
ocomeni 123:a49e9ffbaca6 52 //keep_alive_id = _event_queue.call_every(CLOUD_KEEP_ALIVE_INTERVAL, this, &WiFiManager::callInternetKeepAlive);
ocomeni 123:a49e9ffbaca6 53 keep_alive_id = 0;
ocomeni 129:590bdc2dcf5b 54 https_token_valid = false;
ocomeni 129:590bdc2dcf5b 55 token_refresh_count = 0;
ocomeni 122:62166886db5f 56 //watchDogTick.attach(callback(this, &WiFiManager::callWifiWatchDogIsr), 10.0); // call flip function every 10 seconds
ocomeni 78:07bb86e3ce14 57 }
ocomeni 78:07bb86e3ce14 58
ocomeni 78:07bb86e3ce14 59 WiFiManager::~WiFiManager()
ocomeni 78:07bb86e3ce14 60 {
ocomeni 114:b11bb96c09f3 61 delete network;
ocomeni 124:eae4512b131b 62 wifiWatchdogTimer.stop();
ocomeni 124:eae4512b131b 63 socket->close();
ocomeni 124:eae4512b131b 64 delete socket;
ocomeni 127:a21788227ca6 65 free(aws_id_token);
ocomeni 127:a21788227ca6 66 free(aws_refresh_token);
ocomeni 78:07bb86e3ce14 67 }
ocomeni 105:e5ce023eee93 68 //#define DISABLE_WATCHDOG
ocomeni 109:c274780ff609 69
ocomeni 109:c274780ff609 70 void WiFiManager::callWifiWatchDogIsr()
ocomeni 109:c274780ff609 71 {
ocomeni 118:8df0e9c2ee3f 72 _event_queue.call_in(10, this, &WiFiManager::callWifiWatchDog);
ocomeni 109:c274780ff609 73 }
ocomeni 104:11e9605093c9 74 void WiFiManager::callWifiWatchDog()
ocomeni 104:11e9605093c9 75 {
ocomeni 105:e5ce023eee93 76 #ifdef DISABLE_WATCHDOG
ocomeni 105:e5ce023eee93 77 return;
ocomeni 105:e5ce023eee93 78 #else
ocomeni 104:11e9605093c9 79 static int inactivity_monitor = 0;
ocomeni 104:11e9605093c9 80 watchdogCnt++;
ocomeni 118:8df0e9c2ee3f 81 if(watchdogCnt >= 6 && outputBuffersAvailable()) // every minute
ocomeni 104:11e9605093c9 82 {
ocomeni 118:8df0e9c2ee3f 83 char * respStr = (char *) malloc(120);
ocomeni 107:f1a83fd41b17 84 sprintf(responseString, "\r\n[WiFi-MAN] WiFi Manager Alive : state = %d busy = %d httpsConnActive = %d\r\n",
ocomeni 107:f1a83fd41b17 85 wifiCmd, wifiBusy, https_connection_active);
ocomeni 118:8df0e9c2ee3f 86 sendThreadATresponseString(respStr, WIFI_WATCH_DOG);
ocomeni 104:11e9605093c9 87 watchdogCnt = 0;
ocomeni 104:11e9605093c9 88 }
ocomeni 112:a0999ea4ece0 89 else if(wifiWatchdogTimer.read() > 30 && responseString==NULL)
ocomeni 104:11e9605093c9 90 {
ocomeni 104:11e9605093c9 91 if(wifiCmd == WIFI_CMD_NONE)
ocomeni 104:11e9605093c9 92 inactivity_monitor++;
ocomeni 118:8df0e9c2ee3f 93 char * respStr = (char *) malloc(120);
ocomeni 104:11e9605093c9 94 sprintf(responseString, "\r\n[WiFi-MAN] Main Loop InActive : state = %d busy = %d httpsConnActive = %d\r\n",
ocomeni 104:11e9605093c9 95 wifiCmd, wifiBusy, https_connection_active);
ocomeni 118:8df0e9c2ee3f 96 sendThreadATresponseString(respStr, WIFI_WATCH_DOG);
ocomeni 104:11e9605093c9 97 if(inactivity_monitor >= 3)
ocomeni 104:11e9605093c9 98 {
ocomeni 104:11e9605093c9 99 free_DataMsg();
ocomeni 104:11e9605093c9 100 inactivity_monitor = 0;
ocomeni 104:11e9605093c9 101 }
ocomeni 104:11e9605093c9 102 }
ocomeni 105:e5ce023eee93 103 #endif
ocomeni 104:11e9605093c9 104 }
ocomeni 118:8df0e9c2ee3f 105
ocomeni 119:8d939a902333 106 void WiFiManager::callInternetKeepAlive()
ocomeni 119:8d939a902333 107 {
ocomeni 119:8d939a902333 108 if(https_connection_active)
ocomeni 119:8d939a902333 109 {
ocomeni 119:8d939a902333 110 setNextCommand(WIFI_CMD_INTERNET_KEEP_ALIVE);
ocomeni 119:8d939a902333 111 }
ocomeni 122:62166886db5f 112 else
ocomeni 122:62166886db5f 113 {
ocomeni 122:62166886db5f 114 setNextCommand(WIFI_CMD_TLS_CONNECT);
ocomeni 122:62166886db5f 115 }
ocomeni 119:8d939a902333 116 }
ocomeni 119:8d939a902333 117
ocomeni 119:8d939a902333 118
ocomeni 119:8d939a902333 119 void WiFiManager::keepSocketAlive()
ocomeni 119:8d939a902333 120 {
ocomeni 119:8d939a902333 121 // Send data
ocomeni 122:62166886db5f 122 nsapi_size_or_error_t error;
ocomeni 119:8d939a902333 123 //serr = socket->send("GET /nudgebox/v1 HTTP/1.0\r\nHost: https://dev2.dnanudge.io\r\n\r\n", 18);
ocomeni 127:a21788227ca6 124 dbg_printf(LOG, "\n[WIFI MAN] KEEP ALIVE SERVER REQUEST\r\n");
ocomeni 129:590bdc2dcf5b 125 char *httpsReq = new char[KEEPALIVE_MSG_SIZE];
ocomeni 129:590bdc2dcf5b 126 sprintf(httpsReq,"%s\r\nAuthorization: %s\r\n\r\n", KEEPALIVE_MSG_HDR, aws_id_token);
ocomeni 129:590bdc2dcf5b 127 int hdrlen= strlen(httpsReq);
ocomeni 129:590bdc2dcf5b 128 dbg_printf(LOG, "\n[WIFI MAN] KEEP ALIVE MSG [len = %d]\r\n%s", hdrlen, httpsReq);
ocomeni 129:590bdc2dcf5b 129 memcpy(&httpsReq[hdrlen], KEEPALIVE_MSG_BDY,sizeof(KEEPALIVE_MSG_BDY));
ocomeni 129:590bdc2dcf5b 130 error = socket->send(httpsReq, (hdrlen+sizeof(KEEPALIVE_MSG_BDY)));
ocomeni 119:8d939a902333 131
ocomeni 122:62166886db5f 132 if(error < 0)
ocomeni 119:8d939a902333 133 {
ocomeni 119:8d939a902333 134 queueATresponse(AT_SOCKET_KEEP_ALIVE_FAILED);
ocomeni 122:62166886db5f 135 https_connection_active = false;
ocomeni 122:62166886db5f 136 socket->close();
ocomeni 122:62166886db5f 137 delete socket;
ocomeni 123:a49e9ffbaca6 138 socket = NULL;
ocomeni 122:62166886db5f 139 return;
ocomeni 119:8d939a902333 140 }
ocomeni 119:8d939a902333 141
ocomeni 119:8d939a902333 142 // Receive data
ocomeni 119:8d939a902333 143 char buf[500];
ocomeni 119:8d939a902333 144 error = socket->recv(buf, 500);
ocomeni 127:a21788227ca6 145 if(error >= 0 && strstr(buf, "HTTP/1.1 200")!= NULL) // received HTTP 200 OK status
ocomeni 119:8d939a902333 146 {
ocomeni 119:8d939a902333 147 dbg_printf(LOG, "\n[WIFI MAN] KEEP ALIVE SERVER RESPONSE: \r\n %s\r\n", buf);
ocomeni 119:8d939a902333 148 queueATresponse(AT_SOCKET_KEEP_ALIVE_OK);
ocomeni 122:62166886db5f 149 https_connection_active = true;
ocomeni 119:8d939a902333 150 }
ocomeni 119:8d939a902333 151 else
ocomeni 119:8d939a902333 152 {
ocomeni 119:8d939a902333 153 queueATresponse(AT_SOCKET_KEEP_ALIVE_FAILED);
ocomeni 122:62166886db5f 154 https_connection_active = false;
ocomeni 129:590bdc2dcf5b 155 socket->close();
ocomeni 129:590bdc2dcf5b 156 delete socket;
ocomeni 129:590bdc2dcf5b 157 socket = NULL;
ocomeni 119:8d939a902333 158 }
ocomeni 129:590bdc2dcf5b 159 delete httpsReq;
ocomeni 119:8d939a902333 160 }
ocomeni 119:8d939a902333 161
ocomeni 127:a21788227ca6 162 void WiFiManager::CreateTokenHttpsRequest(char * httpsReq)
ocomeni 127:a21788227ca6 163 {
ocomeni 129:590bdc2dcf5b 164 char *httpsBody = new char[200];
ocomeni 129:590bdc2dcf5b 165 sprintf(httpsBody,"{\r\n\"AuthParameters\" : {\r\n"
ocomeni 127:a21788227ca6 166 "\"USERNAME\" : \"%s\",\r\n\"PASSWORD\" : \"%s\"\r\n},\r\n"
ocomeni 127:a21788227ca6 167 "\"AuthFlow\" : \"%s\",\r\n"
ocomeni 129:590bdc2dcf5b 168 "\"ClientId\" : \"%s\"\r\n}", UserName, Password, AuthFlow, ClientId);
ocomeni 129:590bdc2dcf5b 169 int bodyLen = strlen(httpsBody);
ocomeni 129:590bdc2dcf5b 170 sprintf(httpsReq,"%s\r\ncontent-length: %d"
ocomeni 129:590bdc2dcf5b 171 "\r\n\r\n%s", TOKEN_REQ_HDR, bodyLen, httpsBody);
ocomeni 127:a21788227ca6 172 dbg_printf(LOG, "\n[WIFI MAN] Cloud Access Token REQUEST:\r\n%s\r\n", httpsReq);
ocomeni 129:590bdc2dcf5b 173 delete httpsBody;
ocomeni 127:a21788227ca6 174 }
ocomeni 127:a21788227ca6 175
ocomeni 127:a21788227ca6 176 void WiFiManager::GetCloudAccessToken()
ocomeni 127:a21788227ca6 177 {
ocomeni 129:590bdc2dcf5b 178 int start = Kernel::get_ms_count();
ocomeni 127:a21788227ca6 179 // Send data
ocomeni 127:a21788227ca6 180 nsapi_size_or_error_t error;
ocomeni 127:a21788227ca6 181 dbg_printf(LOG, "\n[WIFI MAN] Get Cloud Access Token REQUEST\r\n");
ocomeni 129:590bdc2dcf5b 182 // first free up access token memory to avoid leak
ocomeni 129:590bdc2dcf5b 183 freeAccessTokenMemory();
ocomeni 127:a21788227ca6 184 char *httpsReq = new char[500];
ocomeni 127:a21788227ca6 185 httpsReq[0] = NULL;
ocomeni 127:a21788227ca6 186 CreateTokenHttpsRequest(httpsReq);
ocomeni 127:a21788227ca6 187 if(strlen(httpsReq) == 0)
ocomeni 127:a21788227ca6 188 {
ocomeni 129:590bdc2dcf5b 189 queueATresponse(AT_ACCESS_TOKEN_FAILED);
ocomeni 127:a21788227ca6 190 return;
ocomeni 127:a21788227ca6 191 }
ocomeni 127:a21788227ca6 192 error = socket->send(httpsReq, strlen(httpsReq)+1);
ocomeni 129:590bdc2dcf5b 193 delete httpsReq;
ocomeni 127:a21788227ca6 194 if(error < 0)
ocomeni 127:a21788227ca6 195 {
ocomeni 129:590bdc2dcf5b 196 queueATresponse(AT_ACCESS_TOKEN_FAILED);
ocomeni 127:a21788227ca6 197 return;
ocomeni 127:a21788227ca6 198 }
ocomeni 127:a21788227ca6 199
ocomeni 127:a21788227ca6 200 // Receive data
ocomeni 127:a21788227ca6 201 // reserve large buffer from heap to hold response
ocomeni 127:a21788227ca6 202 char *respBuf = new char[TOKEN_RESPONSE_SIZE];
ocomeni 127:a21788227ca6 203 error = socket->recv(respBuf, TOKEN_RESPONSE_SIZE);
ocomeni 127:a21788227ca6 204 if(error >= 0 && strstr(respBuf, "HTTP/1.1 200")!= NULL) // received HTTP 200 OK status
ocomeni 127:a21788227ca6 205 {
ocomeni 127:a21788227ca6 206 dbg_printf(LOG, "\n[WIFI MAN] ACCESS TOKEN RESPONSE: \r\n %s\r\n", respBuf);
ocomeni 127:a21788227ca6 207 // extract ID TOKEN
ocomeni 127:a21788227ca6 208 char *sp1 = strstr(respBuf,ID_TOKEN_STR_START);
ocomeni 129:590bdc2dcf5b 209 char *sp2 = strstr(sp1+strlen(ID_TOKEN_STR_START),ACCESS_TOKEN_STR_END);
ocomeni 129:590bdc2dcf5b 210 int tokenLen = sp2-sp1-(strlen(ID_TOKEN_STR_START));
ocomeni 129:590bdc2dcf5b 211 // reserve memomry on the heap for id token
ocomeni 129:590bdc2dcf5b 212 aws_id_token = new char[tokenLen+1];
ocomeni 129:590bdc2dcf5b 213 strncpy(aws_id_token, sp1+(strlen(ID_TOKEN_STR_START)), tokenLen);
ocomeni 129:590bdc2dcf5b 214 dbg_printf(LOG, "\n[WIFI MAN] Token Length: %d \r\n IdToken: \r\n %s\r\n", tokenLen, aws_id_token);
ocomeni 129:590bdc2dcf5b 215 #ifdef EXTRACT_REFRESH_TOKEN
ocomeni 127:a21788227ca6 216 // extract Refresh TOKEN
ocomeni 127:a21788227ca6 217 sp1 = strstr(respBuf,REFRESH_TOKEN_STR_START);
ocomeni 129:590bdc2dcf5b 218 sp2 = strstr(sp1+strlen(REFRESH_TOKEN_STR_START),ACCESS_TOKEN_STR_END);
ocomeni 129:590bdc2dcf5b 219 tokenLen = sp2-sp1-(strlen(REFRESH_TOKEN_STR_START));
ocomeni 129:590bdc2dcf5b 220 // reserve memomry on the heap for refresh token
ocomeni 129:590bdc2dcf5b 221 aws_refresh_token = new char[tokenLen+1];
ocomeni 129:590bdc2dcf5b 222 strncpy(aws_refresh_token, sp1+(strlen(REFRESH_TOKEN_STR_START)), tokenLen);
ocomeni 129:590bdc2dcf5b 223 dbg_printf(LOG, "\n[WIFI MAN] Token Length: %d \r\nRefreshToken: \r\n %s\r\n", tokenLen, aws_refresh_token);
ocomeni 129:590bdc2dcf5b 224 #endif
ocomeni 129:590bdc2dcf5b 225 queueATresponse(AT_ACCESS_TOKEN_SUCCESS);
ocomeni 129:590bdc2dcf5b 226 token_refresh_count++;
ocomeni 129:590bdc2dcf5b 227 //https_connection_active = true;
ocomeni 129:590bdc2dcf5b 228 https_token_valid = true;
ocomeni 129:590bdc2dcf5b 229 // schedule the invalidation of the token for 59 minutes time
ocomeni 129:590bdc2dcf5b 230 _event_queue.call_in(TOKEN_VALID_PERIOD_MS, this, &WiFiManager::invalidateAccessToken);
ocomeni 127:a21788227ca6 231 }
ocomeni 127:a21788227ca6 232 else
ocomeni 127:a21788227ca6 233 {
ocomeni 129:590bdc2dcf5b 234 dbg_printf(LOG, "\n[WIFI MAN] Failure Response: \r\n %s\r\n", respBuf);
ocomeni 129:590bdc2dcf5b 235 queueATresponse(AT_ACCESS_TOKEN_FAILED);
ocomeni 129:590bdc2dcf5b 236 //https_connection_active = false;
ocomeni 127:a21788227ca6 237 }
ocomeni 127:a21788227ca6 238 delete respBuf;
ocomeni 129:590bdc2dcf5b 239 int elapsed_ms = Kernel::get_ms_count() - start;
ocomeni 129:590bdc2dcf5b 240 dbg_printf(LOG, "\n[WIFI MAN] Access token Acquisition::\r\n Time Elapsed : %ld ms\r\n", elapsed_ms);
ocomeni 129:590bdc2dcf5b 241 socket->close();
ocomeni 129:590bdc2dcf5b 242 delete socket;
ocomeni 129:590bdc2dcf5b 243 socket = NULL;
ocomeni 127:a21788227ca6 244 }
ocomeni 127:a21788227ca6 245
ocomeni 129:590bdc2dcf5b 246 void WiFiManager::invalidateAccessToken()
ocomeni 129:590bdc2dcf5b 247 {
ocomeni 129:590bdc2dcf5b 248 https_token_valid = false;
ocomeni 129:590bdc2dcf5b 249 }
ocomeni 119:8d939a902333 250
ocomeni 129:590bdc2dcf5b 251 void WiFiManager::freeAccessTokenMemory()
ocomeni 129:590bdc2dcf5b 252 {
ocomeni 129:590bdc2dcf5b 253 free(aws_id_token);
ocomeni 129:590bdc2dcf5b 254 aws_id_token = NULL;
ocomeni 129:590bdc2dcf5b 255 #ifdef EXTRACT_REFRESH_TOKEN
ocomeni 129:590bdc2dcf5b 256 free(aws_refresh_token);
ocomeni 129:590bdc2dcf5b 257 aws_refresh_token = NULL;
ocomeni 129:590bdc2dcf5b 258 #endif
ocomeni 129:590bdc2dcf5b 259 }
ocomeni 118:8df0e9c2ee3f 260 void WiFiManager::sendThreadATresponseString(const char * buf, at_cmd_resp_t at_cmd)
ocomeni 118:8df0e9c2ee3f 261 {
ocomeni 118:8df0e9c2ee3f 262 if(at_data_resp != NULL) return;
ocomeni 118:8df0e9c2ee3f 263 int strLen = strlen(buf) + 1;
ocomeni 118:8df0e9c2ee3f 264 at_data_resp = new at_data_msg_t;
ocomeni 118:8df0e9c2ee3f 265 // set string length
ocomeni 118:8df0e9c2ee3f 266 at_data_resp->dataLen = strLen;
ocomeni 118:8df0e9c2ee3f 267 memcpy(at_data_resp->buffer, buf, strLen);
ocomeni 118:8df0e9c2ee3f 268 // package and send on wifi data queue
ocomeni 118:8df0e9c2ee3f 269 at_data_resp->at_resp = at_cmd;
ocomeni 118:8df0e9c2ee3f 270 bool queueResult = true;
ocomeni 118:8df0e9c2ee3f 271 int wait_count = 0;
ocomeni 118:8df0e9c2ee3f 272 do
ocomeni 118:8df0e9c2ee3f 273 {
ocomeni 118:8df0e9c2ee3f 274 if(!queueResult){
ocomeni 118:8df0e9c2ee3f 275 wait_count+=10;
ocomeni 119:8d939a902333 276 dbg_printf(LOG, "ATCMD Queue full waiting %d ms so far...\n", wait_count);
ocomeni 118:8df0e9c2ee3f 277 wait_ms(10);
ocomeni 118:8df0e9c2ee3f 278 }
ocomeni 118:8df0e9c2ee3f 279 queueResult = queueWiFiDataResponse(*at_data_resp);
ocomeni 118:8df0e9c2ee3f 280 }while(queueResult == false && wait_count<QUEUE_WAIT_TIMEOUT_MS);
ocomeni 118:8df0e9c2ee3f 281 delete at_data_resp;
ocomeni 118:8df0e9c2ee3f 282 at_data_resp = NULL;
ocomeni 118:8df0e9c2ee3f 283 }
ocomeni 118:8df0e9c2ee3f 284
ocomeni 118:8df0e9c2ee3f 285
ocomeni 118:8df0e9c2ee3f 286 bool WiFiManager::outputBuffersAvailable()
ocomeni 118:8df0e9c2ee3f 287 {
ocomeni 118:8df0e9c2ee3f 288 int timeout = 0;
ocomeni 118:8df0e9c2ee3f 289 while(timeout < 100)
ocomeni 118:8df0e9c2ee3f 290 {
ocomeni 118:8df0e9c2ee3f 291 if(responseBytes==NULL && responseString==NULL && at_data_resp==NULL)
ocomeni 118:8df0e9c2ee3f 292 {
ocomeni 118:8df0e9c2ee3f 293 return true;
ocomeni 118:8df0e9c2ee3f 294 }
ocomeni 118:8df0e9c2ee3f 295 else
ocomeni 118:8df0e9c2ee3f 296 {
ocomeni 118:8df0e9c2ee3f 297 timeout += 10;
ocomeni 118:8df0e9c2ee3f 298 wait_ms(10);
ocomeni 118:8df0e9c2ee3f 299 }
ocomeni 118:8df0e9c2ee3f 300 }
ocomeni 118:8df0e9c2ee3f 301 if(responseBytes==NULL && responseString==NULL && at_data_resp==NULL)
ocomeni 118:8df0e9c2ee3f 302 {
ocomeni 118:8df0e9c2ee3f 303 return true;
ocomeni 118:8df0e9c2ee3f 304 }
ocomeni 118:8df0e9c2ee3f 305 else
ocomeni 118:8df0e9c2ee3f 306 {
ocomeni 118:8df0e9c2ee3f 307 return false;
ocomeni 118:8df0e9c2ee3f 308 }
ocomeni 118:8df0e9c2ee3f 309 }
ocomeni 118:8df0e9c2ee3f 310
ocomeni 118:8df0e9c2ee3f 311
ocomeni 81:637a87eb8170 312 bool WiFiManager::queueATresponse(at_cmd_resp_t resp){
ocomeni 92:ec9550034276 313 #ifndef USE_MALLOC_FOR_COMMAND_MEMORY_POOL
ocomeni 81:637a87eb8170 314 at_resp_message_t *atResp = _wiFi2ATmPool->alloc();
ocomeni 92:ec9550034276 315 #else
ocomeni 92:ec9550034276 316 at_resp_message_t *atResp = (at_resp_message_t *) malloc(sizeof(at_resp_message_t));
ocomeni 92:ec9550034276 317 #endif
ocomeni 88:7ffa053be662 318 if(atResp == NULL) return false; // queue full;
ocomeni 81:637a87eb8170 319 atResp->at_resp = resp;
ocomeni 81:637a87eb8170 320 _wiFi2ATCmdQueue->put(atResp);
ocomeni 81:637a87eb8170 321 return true;
ocomeni 81:637a87eb8170 322 }
ocomeni 81:637a87eb8170 323
ocomeni 81:637a87eb8170 324
ocomeni 81:637a87eb8170 325 bool WiFiManager::queueWiFiDataResponse(at_data_msg_t at_resp){
ocomeni 81:637a87eb8170 326 at_data_msg_t *atData = _wiFi2ATDatamPool->alloc();
ocomeni 88:7ffa053be662 327 if(atData == NULL) return false; // queue full;
ocomeni 81:637a87eb8170 328 atData->at_resp = at_resp.at_resp;
ocomeni 81:637a87eb8170 329 atData->dataLen = at_resp.dataLen;
ocomeni 81:637a87eb8170 330 memcpy(atData->buffer, at_resp.buffer, at_resp.dataLen);
ocomeni 81:637a87eb8170 331 _wiFi2ATDataQueue->put(atData);
ocomeni 103:7b566b522427 332 dbg_printf(LOG, "[WIFI MAN] queued data size = %d : at_resp = %d\n", at_resp.dataLen, at_resp.at_resp);
ocomeni 81:637a87eb8170 333 return true;
ocomeni 81:637a87eb8170 334 }
ocomeni 81:637a87eb8170 335
ocomeni 114:b11bb96c09f3 336 void WiFiManager::getWiFiInstance()
ocomeni 114:b11bb96c09f3 337 {
ocomeni 114:b11bb96c09f3 338 network = WiFiInterface::get_default_instance();
ocomeni 114:b11bb96c09f3 339 if (!network) {
ocomeni 114:b11bb96c09f3 340 dbg_printf(LOG, "ERROR: No WiFiInterface found.\n");
ocomeni 114:b11bb96c09f3 341 }
ocomeni 114:b11bb96c09f3 342 }
ocomeni 79:a2187bbfa407 343
ocomeni 79:a2187bbfa407 344 void WiFiManager::runMain(){
ocomeni 81:637a87eb8170 345 nsapi_error_t error;
ocomeni 99:05398b3184f8 346 bool result;
ocomeni 103:7b566b522427 347 dbg_printf(LOG, "\r\n [WIFI MAN] Thread Id = %X\r\n", (uint32_t)ThisThread::get_id());
ocomeni 79:a2187bbfa407 348 while(true){
ocomeni 79:a2187bbfa407 349 dequeueWiFiCommands();
ocomeni 81:637a87eb8170 350 dequeueATdataResponse();
ocomeni 104:11e9605093c9 351 wifiWatchdogTimer.reset();
ocomeni 79:a2187bbfa407 352 switch(wifiCmd){
ocomeni 79:a2187bbfa407 353 case WIFI_CMD_NONE:
ocomeni 79:a2187bbfa407 354 // IDLE STATE
ocomeni 79:a2187bbfa407 355 break;
ocomeni 79:a2187bbfa407 356 case WIFI_CMD_SCAN:
ocomeni 104:11e9605093c9 357 wifiBusy = 1;
ocomeni 79:a2187bbfa407 358 error = scanNetworks();
ocomeni 79:a2187bbfa407 359 wifiCmd = WIFI_CMD_NONE;
ocomeni 81:637a87eb8170 360 queueATresponse(AT_SCAN_RESP);
ocomeni 104:11e9605093c9 361 wifiBusy = 0;
ocomeni 81:637a87eb8170 362 break;
ocomeni 81:637a87eb8170 363 case WIFI_CMD_DETAILED_SCAN:
ocomeni 98:65c2333a38b6 364 {
ocomeni 104:11e9605093c9 365 wifiBusy = 1;
ocomeni 81:637a87eb8170 366 nsapi_size_or_error_t cnt_err;
ocomeni 81:637a87eb8170 367 cnt_err = getAvailableAPs(lastScanCount);
ocomeni 81:637a87eb8170 368 wifiCmd = WIFI_CMD_NONE;
ocomeni 122:62166886db5f 369 if(cnt_err >= 0)
ocomeni 122:62166886db5f 370 {
ocomeni 122:62166886db5f 371 queueATresponse(AT_DETAILED_SCAN_RESP);
ocomeni 122:62166886db5f 372 }
ocomeni 104:11e9605093c9 373 wifiBusy = 0;
ocomeni 79:a2187bbfa407 374 break;
ocomeni 98:65c2333a38b6 375 }
ocomeni 79:a2187bbfa407 376 case WIFI_CMD_CONNECT:
ocomeni 98:65c2333a38b6 377 {
ocomeni 124:eae4512b131b 378 if(is_connected) // already connected
ocomeni 124:eae4512b131b 379 {
ocomeni 124:eae4512b131b 380 wifiCmd = WIFI_CMD_NONE;
ocomeni 124:eae4512b131b 381 break;
ocomeni 124:eae4512b131b 382 }
ocomeni 104:11e9605093c9 383 wifiBusy = 1;
ocomeni 81:637a87eb8170 384 error = connect();
ocomeni 93:06e755a80187 385 int secCount = 0;
ocomeni 118:8df0e9c2ee3f 386 while(secCount++ < WIFI_CONNECT_TIMEOUT_SECS && is_connected==false){
ocomeni 93:06e755a80187 387 wait(1); // wait 1 sec
ocomeni 93:06e755a80187 388 }
ocomeni 126:9bc33f8b57d5 389 wifiCmd = WIFI_CMD_NONE;
ocomeni 93:06e755a80187 390 if(is_connected==false){
ocomeni 118:8df0e9c2ee3f 391 if(outputBuffersAvailable() == false) // first free it
ocomeni 118:8df0e9c2ee3f 392 {
ocomeni 118:8df0e9c2ee3f 393 free(responseString);
ocomeni 118:8df0e9c2ee3f 394 }
ocomeni 103:7b566b522427 395 dbg_printf(LOG, "[WIFI MAN] +++ WIFI CONNECTION TIMEOUT +++ \r\n");
ocomeni 95:290859010c8c 396 //queueATresponse(AT_COMMAND_FAILED);
ocomeni 95:290859010c8c 397 responseString = (char *) malloc(100);
ocomeni 95:290859010c8c 398 sprintf(responseString, "\r\n+UUTIMEOUT\r\n");
ocomeni 95:290859010c8c 399 sendATresponseString(AT_COMMAND_FAILED);
ocomeni 93:06e755a80187 400 }
ocomeni 93:06e755a80187 401 else {
ocomeni 95:290859010c8c 402 sendATresponseString(AT_CONNECT_RESP);
ocomeni 93:06e755a80187 403 }
ocomeni 104:11e9605093c9 404 wifiBusy = 0;
ocomeni 79:a2187bbfa407 405 break;
ocomeni 98:65c2333a38b6 406 }
ocomeni 79:a2187bbfa407 407 case WIFI_CMD_DISCONNECT:
ocomeni 124:eae4512b131b 408 {
ocomeni 124:eae4512b131b 409 if(!is_connected) // already disconnected
ocomeni 124:eae4512b131b 410 {
ocomeni 124:eae4512b131b 411 wifiCmd = WIFI_CMD_NONE;
ocomeni 124:eae4512b131b 412 break;
ocomeni 124:eae4512b131b 413 }
ocomeni 104:11e9605093c9 414 wifiBusy = 1;
ocomeni 81:637a87eb8170 415 error = disconnect();
ocomeni 126:9bc33f8b57d5 416 wifiCmd = WIFI_CMD_NONE;
ocomeni 124:eae4512b131b 417 if(error >= 0)
ocomeni 124:eae4512b131b 418 {
ocomeni 124:eae4512b131b 419 int secCount = 0;
ocomeni 124:eae4512b131b 420 while(secCount++ < WIFI_CONNECT_TIMEOUT_SECS && is_connected==true){
ocomeni 124:eae4512b131b 421 wait(1); // wait 1 sec
ocomeni 124:eae4512b131b 422 }
ocomeni 124:eae4512b131b 423 if(!is_connected)
ocomeni 124:eae4512b131b 424 {
ocomeni 124:eae4512b131b 425 sendATresponseString(AT_DISCONNECT_RESP);
ocomeni 124:eae4512b131b 426 }
ocomeni 124:eae4512b131b 427 else
ocomeni 124:eae4512b131b 428 {
ocomeni 124:eae4512b131b 429 dbg_printf(LOG, "[WIFI MAN] +++ WIFI DISCONNECTION TIMEOUT +++ \r\n");
ocomeni 124:eae4512b131b 430 //queueATresponse(AT_COMMAND_FAILED);
ocomeni 124:eae4512b131b 431 responseString = (char *) malloc(100);
ocomeni 124:eae4512b131b 432 sprintf(responseString, "\r\n+UUTIMEOUT\r\n");
ocomeni 124:eae4512b131b 433 sendATresponseString(AT_COMMAND_FAILED);
ocomeni 124:eae4512b131b 434 }
ocomeni 124:eae4512b131b 435 // attempt reconnection if always connected scheme is set
ocomeni 124:eae4512b131b 436 if(internet_config->connectionScheme == ALWAYS_CONNECTED)
ocomeni 124:eae4512b131b 437 {
ocomeni 124:eae4512b131b 438 setNextCommand(WIFI_CMD_CONNECT);
ocomeni 124:eae4512b131b 439 }
ocomeni 124:eae4512b131b 440 }
ocomeni 104:11e9605093c9 441 wifiBusy = 0;
ocomeni 81:637a87eb8170 442 break;
ocomeni 124:eae4512b131b 443 }
ocomeni 81:637a87eb8170 444 case WIFI_CMD_CONFIG:
ocomeni 104:11e9605093c9 445 wifiBusy = 1;
ocomeni 81:637a87eb8170 446 set_WIFI_CONFIG();
ocomeni 81:637a87eb8170 447 wifiCmd = WIFI_CMD_NONE;
ocomeni 81:637a87eb8170 448 queueATresponse(AT_CONFIG_RESP);
ocomeni 104:11e9605093c9 449 wifiBusy = 0;
ocomeni 82:10072c1794d3 450 break;
ocomeni 81:637a87eb8170 451 case WIFI_CMD_INTERNET_CONFIG:
ocomeni 107:f1a83fd41b17 452 {
ocomeni 104:11e9605093c9 453 wifiBusy = 1;
ocomeni 107:f1a83fd41b17 454 backgroundTaskCompleted = false;
ocomeni 100:80ef4bc31b7a 455 set_internet_config();
ocomeni 111:3ab1d9644835 456 // Wait for callback semaphore
ocomeni 111:3ab1d9644835 457 #ifdef DNANUDGE_DEBUG
ocomeni 111:3ab1d9644835 458 callback_semaphore.wait();
ocomeni 111:3ab1d9644835 459 #endif
ocomeni 107:f1a83fd41b17 460 int msecCount = 0;
ocomeni 126:9bc33f8b57d5 461 while(!backgroundTaskCompleted && msecCount < 1000)
ocomeni 107:f1a83fd41b17 462 {
ocomeni 107:f1a83fd41b17 463 msecCount++;
ocomeni 107:f1a83fd41b17 464 wait_ms(10);
ocomeni 107:f1a83fd41b17 465 }
ocomeni 107:f1a83fd41b17 466 if(backgroundTaskCompleted)
ocomeni 107:f1a83fd41b17 467 {
ocomeni 107:f1a83fd41b17 468 queueATresponse(AT_INTERNET_CONFIG_RESP);
ocomeni 107:f1a83fd41b17 469 }
ocomeni 107:f1a83fd41b17 470 backgroundTaskCompleted = false;
ocomeni 81:637a87eb8170 471 wifiCmd = WIFI_CMD_NONE;
ocomeni 129:590bdc2dcf5b 472 //wifiCmd = WIFI_CMD_GET_TOKEN;
ocomeni 95:290859010c8c 473 break;
ocomeni 107:f1a83fd41b17 474 }
ocomeni 95:290859010c8c 475 case WIFI_CMD_NETWORK_STATUS:
ocomeni 104:11e9605093c9 476 wifiBusy = 1;
ocomeni 118:8df0e9c2ee3f 477 if(outputBuffersAvailable())
ocomeni 118:8df0e9c2ee3f 478 {
ocomeni 118:8df0e9c2ee3f 479 getNetworkStatus();
ocomeni 118:8df0e9c2ee3f 480 }
ocomeni 95:290859010c8c 481 sendATresponseString(AT_NETWORK_STATUS_RESP);
ocomeni 95:290859010c8c 482 wifiCmd = WIFI_CMD_NONE;
ocomeni 104:11e9605093c9 483 wifiBusy = 0;
ocomeni 95:290859010c8c 484 break;
ocomeni 95:290859010c8c 485 case WIFI_CMD_WIFI_STATUS:
ocomeni 104:11e9605093c9 486 wifiBusy = 1;
ocomeni 118:8df0e9c2ee3f 487 if(outputBuffersAvailable())
ocomeni 118:8df0e9c2ee3f 488 {
ocomeni 118:8df0e9c2ee3f 489 getWiFiStatus();
ocomeni 118:8df0e9c2ee3f 490 }
ocomeni 95:290859010c8c 491 sendATresponseString(AT_WIFI_STATUS_RESP);
ocomeni 95:290859010c8c 492 wifiCmd = WIFI_CMD_NONE;
ocomeni 104:11e9605093c9 493 wifiBusy = 0;
ocomeni 79:a2187bbfa407 494 break;
ocomeni 79:a2187bbfa407 495 case WIFI_CMD_SEND_HTTPS_REQ:
ocomeni 107:f1a83fd41b17 496 {
ocomeni 129:590bdc2dcf5b 497 wifiBusy = 1;
ocomeni 129:590bdc2dcf5b 498 if(!https_token_valid) // if this is the first time get token
ocomeni 129:590bdc2dcf5b 499 {
ocomeni 129:590bdc2dcf5b 500 wifiCmd = WIFI_CMD_NONE;
ocomeni 129:590bdc2dcf5b 501 fromWiFiCmd = WIFI_CMD_TLS_CONNECT;
ocomeni 129:590bdc2dcf5b 502 nextWiFiCmd = WIFI_CMD_SEND_HTTPS_REQ;
ocomeni 129:590bdc2dcf5b 503 setNextCommand(WIFI_CMD_GET_TOKEN);
ocomeni 129:590bdc2dcf5b 504 break;
ocomeni 129:590bdc2dcf5b 505 }
ocomeni 119:8d939a902333 506 // cancel keep alive event as not needed since new request has come in.
ocomeni 123:a49e9ffbaca6 507 if(keep_alive_id != 0) // only cancel if it has been activated
ocomeni 123:a49e9ffbaca6 508 {
ocomeni 123:a49e9ffbaca6 509 _event_queue.cancel(keep_alive_id);
ocomeni 123:a49e9ffbaca6 510 }
ocomeni 109:c274780ff609 511 #ifdef SEND_DEBUG_MESSAGES
ocomeni 118:8df0e9c2ee3f 512 if(outputBuffersAvailable())
ocomeni 104:11e9605093c9 513 {
ocomeni 104:11e9605093c9 514 responseString = (char *) malloc(100);
ocomeni 104:11e9605093c9 515 sprintf(responseString, "\r\nHTTP REQUEST RECEIVED\r\n");
ocomeni 104:11e9605093c9 516 sendATresponseString(AT_EVENT);
ocomeni 104:11e9605093c9 517 }
ocomeni 109:c274780ff609 518 #endif
ocomeni 103:7b566b522427 519 dbg_printf(LOG, "before call to send http request \n");
ocomeni 104:11e9605093c9 520 dbg_printf(LOG, "\r\n[WIFI-MAN] Received HTTPS request...\r\n");
ocomeni 88:7ffa053be662 521 print_memory_info();
ocomeni 129:590bdc2dcf5b 522 // disable network interrupts during https request
ocomeni 129:590bdc2dcf5b 523 network->attach(NULL);
ocomeni 107:f1a83fd41b17 524 #ifdef USE_EVENTS_FOR_HTTPS_REQUESTS
ocomeni 107:f1a83fd41b17 525
ocomeni 107:f1a83fd41b17 526 // Events can be cancelled as long as they have not been dispatched. If the
ocomeni 107:f1a83fd41b17 527 // event has already expired, cancel has no side-effects.
ocomeni 107:f1a83fd41b17 528 int event_id = _event_queue.call(this, &WiFiManager::createSendHttpsRequest);
ocomeni 129:590bdc2dcf5b 529 waitForBackgroundTask(6000, 10); // six second timeout
ocomeni 129:590bdc2dcf5b 530 // backgroundTaskCompleted = false;
ocomeni 129:590bdc2dcf5b 531 // int msecCount = 0;
ocomeni 129:590bdc2dcf5b 532 // int oldChunkNum = chunkNum;
ocomeni 129:590bdc2dcf5b 533 // while(!backgroundTaskCompleted && msecCount < 6000)
ocomeni 129:590bdc2dcf5b 534 // {
ocomeni 129:590bdc2dcf5b 535 // msecCount+=10;
ocomeni 129:590bdc2dcf5b 536 // wait_ms(10);
ocomeni 129:590bdc2dcf5b 537 // if(oldChunkNum != chunkNum) // new payload received
ocomeni 129:590bdc2dcf5b 538 // {
ocomeni 129:590bdc2dcf5b 539 // oldChunkNum = chunkNum;
ocomeni 129:590bdc2dcf5b 540 // msecCount = 0;
ocomeni 129:590bdc2dcf5b 541 // }
ocomeni 129:590bdc2dcf5b 542 // }
ocomeni 107:f1a83fd41b17 543 if(backgroundTaskCompleted)
ocomeni 107:f1a83fd41b17 544 {
ocomeni 109:c274780ff609 545 //queueATresponse(AT_INTERNET_CONFIG_RESP);
ocomeni 107:f1a83fd41b17 546 result = true;
ocomeni 107:f1a83fd41b17 547 }
ocomeni 107:f1a83fd41b17 548 else
ocomeni 107:f1a83fd41b17 549 {
ocomeni 109:c274780ff609 550 //_event_queue.cancel(event_id);
ocomeni 107:f1a83fd41b17 551 result = false;
ocomeni 107:f1a83fd41b17 552 }
ocomeni 107:f1a83fd41b17 553 backgroundTaskCompleted = false;
ocomeni 107:f1a83fd41b17 554 #else
ocomeni 99:05398b3184f8 555 result = createHttpsRequest();
ocomeni 107:f1a83fd41b17 556 #endif
ocomeni 118:8df0e9c2ee3f 557 if(result == false && outputBuffersAvailable())
ocomeni 98:65c2333a38b6 558 {
ocomeni 104:11e9605093c9 559 responseString = (char *) malloc(100);
ocomeni 104:11e9605093c9 560 if(http_result==TLS_CONNECTION_FAILED)
ocomeni 104:11e9605093c9 561 {
ocomeni 104:11e9605093c9 562 sprintf(responseString, "\r\nTLS CONNECTION FAILURE\r\n");
ocomeni 104:11e9605093c9 563 }
ocomeni 104:11e9605093c9 564 else
ocomeni 104:11e9605093c9 565 {
ocomeni 104:11e9605093c9 566 sprintf(responseString, "\r\nHTTP REQUEST FAILED\r\n");
ocomeni 104:11e9605093c9 567 }
ocomeni 98:65c2333a38b6 568 sendATresponseString(AT_COMMAND_FAILED);
ocomeni 98:65c2333a38b6 569 }
ocomeni 103:7b566b522427 570 dbg_printf(LOG, "after call to send http request \n");
ocomeni 88:7ffa053be662 571 print_memory_info();
ocomeni 84:7c7add00f4bf 572 wifiCmd = WIFI_CMD_NONE;
ocomeni 104:11e9605093c9 573 wifiBusy = 0;
ocomeni 119:8d939a902333 574 // enable keep alive after https request completes
ocomeni 119:8d939a902333 575 keep_alive_id = _event_queue.call_every(CLOUD_KEEP_ALIVE_INTERVAL, this, &WiFiManager::callInternetKeepAlive);
ocomeni 129:590bdc2dcf5b 576 // re-enable network interrupts after https request.
ocomeni 129:590bdc2dcf5b 577 network->attach(callback(this, &WiFiManager::status_callback));
ocomeni 79:a2187bbfa407 578 break;
ocomeni 122:62166886db5f 579 }
ocomeni 122:62166886db5f 580 case WIFI_CMD_TLS_CONNECT:
ocomeni 122:62166886db5f 581 {
ocomeni 129:590bdc2dcf5b 582 dbg_printf(LOG, "\r\n[WIFI-MAN] ATTEMPTING TLS CONNECTION\r\n");
ocomeni 122:62166886db5f 583 char* hostName = strstr(internet_config->url,"//");
ocomeni 122:62166886db5f 584 wifiBusy = 1;
ocomeni 122:62166886db5f 585 if(hostName != NULL)
ocomeni 122:62166886db5f 586 {
ocomeni 122:62166886db5f 587 hostName += 2;
ocomeni 129:590bdc2dcf5b 588 //https_connection_active = createTLSconnection(hostName);
ocomeni 129:590bdc2dcf5b 589 _event_queue.call(this, &WiFiManager::createTLSconnThreadCall, (const char*)hostName);
ocomeni 129:590bdc2dcf5b 590 waitForBackgroundTask(6000, 10); // six second timeout
ocomeni 129:590bdc2dcf5b 591 if(backgroundTaskCompleted == false)
ocomeni 122:62166886db5f 592 {
ocomeni 129:590bdc2dcf5b 593 https_connection_active = false;
ocomeni 122:62166886db5f 594 queueATresponse(AT_SOCKET_KEEP_ALIVE_FAILED);
ocomeni 123:a49e9ffbaca6 595 delete socket;
ocomeni 123:a49e9ffbaca6 596 socket = NULL;
ocomeni 122:62166886db5f 597 }
ocomeni 129:590bdc2dcf5b 598 else
ocomeni 129:590bdc2dcf5b 599 {
ocomeni 129:590bdc2dcf5b 600 https_connection_active = true;
ocomeni 129:590bdc2dcf5b 601 }
ocomeni 122:62166886db5f 602 }
ocomeni 129:590bdc2dcf5b 603 if(fromWiFiCmd == WIFI_CMD_TLS_CONNECT)
ocomeni 129:590bdc2dcf5b 604 {
ocomeni 129:590bdc2dcf5b 605 wifiCmd = nextWiFiCmd;
ocomeni 129:590bdc2dcf5b 606 fromWiFiCmd = WIFI_CMD_NONE;
ocomeni 129:590bdc2dcf5b 607 nextWiFiCmd = WIFI_CMD_NONE;
ocomeni 129:590bdc2dcf5b 608 }
ocomeni 129:590bdc2dcf5b 609 else
ocomeni 129:590bdc2dcf5b 610 {
ocomeni 129:590bdc2dcf5b 611 wifiCmd = WIFI_CMD_NONE;
ocomeni 129:590bdc2dcf5b 612 }
ocomeni 122:62166886db5f 613 wifiBusy = 0;
ocomeni 122:62166886db5f 614 break;
ocomeni 107:f1a83fd41b17 615 }
ocomeni 119:8d939a902333 616 case WIFI_CMD_INTERNET_KEEP_ALIVE:
ocomeni 129:590bdc2dcf5b 617 {
ocomeni 119:8d939a902333 618 wifiBusy = 1;
ocomeni 129:590bdc2dcf5b 619 if(!https_token_valid) // if this is the first time get token
ocomeni 129:590bdc2dcf5b 620 {
ocomeni 129:590bdc2dcf5b 621 wifiCmd = WIFI_CMD_NONE;
ocomeni 129:590bdc2dcf5b 622 fromWiFiCmd = WIFI_CMD_TLS_CONNECT;
ocomeni 129:590bdc2dcf5b 623 nextWiFiCmd = WIFI_CMD_INTERNET_KEEP_ALIVE;
ocomeni 129:590bdc2dcf5b 624 setNextCommand(WIFI_CMD_GET_TOKEN);
ocomeni 129:590bdc2dcf5b 625 break;
ocomeni 129:590bdc2dcf5b 626 }
ocomeni 119:8d939a902333 627 keepSocketAlive();
ocomeni 119:8d939a902333 628 wifiCmd = WIFI_CMD_NONE;
ocomeni 119:8d939a902333 629 wifiBusy = 0;
ocomeni 119:8d939a902333 630 break;
ocomeni 129:590bdc2dcf5b 631 }
ocomeni 129:590bdc2dcf5b 632 case WIFI_CMD_GET_TOKEN:
ocomeni 129:590bdc2dcf5b 633 {
ocomeni 129:590bdc2dcf5b 634 wifiBusy = 1;
ocomeni 129:590bdc2dcf5b 635 _event_queue.call(this, &WiFiManager::createTLSconnThreadCall, AWS_HOST_NAME);
ocomeni 129:590bdc2dcf5b 636 waitForBackgroundTask(6000, 10); // six second timeout
ocomeni 129:590bdc2dcf5b 637 if(backgroundTaskCompleted == false)
ocomeni 129:590bdc2dcf5b 638 {
ocomeni 129:590bdc2dcf5b 639 queueATresponse(AT_SOCKET_KEEP_ALIVE_FAILED);
ocomeni 129:590bdc2dcf5b 640 delete socket;
ocomeni 129:590bdc2dcf5b 641 socket = NULL;
ocomeni 129:590bdc2dcf5b 642 }
ocomeni 129:590bdc2dcf5b 643 else
ocomeni 129:590bdc2dcf5b 644 {
ocomeni 129:590bdc2dcf5b 645 https_connection_active = false;
ocomeni 129:590bdc2dcf5b 646 GetCloudAccessToken();
ocomeni 129:590bdc2dcf5b 647 wifiCmd = WIFI_CMD_NONE;
ocomeni 129:590bdc2dcf5b 648 setNextCommand(WIFI_CMD_TLS_CONNECT);
ocomeni 129:590bdc2dcf5b 649 //_event_queue.call_in(ONE_SECOND,this, &WiFiManager::setNextCommand, WIFI_CMD_TLS_CONNECT);
ocomeni 129:590bdc2dcf5b 650 //wifiCmd = WIFI_CMD_TLS_CONNECT;
ocomeni 129:590bdc2dcf5b 651 }
ocomeni 129:590bdc2dcf5b 652 //wifiBusy = 0;
ocomeni 129:590bdc2dcf5b 653 break;
ocomeni 129:590bdc2dcf5b 654 }
ocomeni 123:a49e9ffbaca6 655 case WIFI_CMD_WIFI_MAC_ADDR:
ocomeni 129:590bdc2dcf5b 656 {
ocomeni 123:a49e9ffbaca6 657 wifiBusy = 1;
ocomeni 123:a49e9ffbaca6 658 if(outputBuffersAvailable())
ocomeni 123:a49e9ffbaca6 659 {
ocomeni 123:a49e9ffbaca6 660 getWiFiMACaddress();
ocomeni 123:a49e9ffbaca6 661 sendATresponseString(AT_WIFI_MAC_RESP);
ocomeni 123:a49e9ffbaca6 662 }
ocomeni 123:a49e9ffbaca6 663 wifiCmd = WIFI_CMD_NONE;
ocomeni 123:a49e9ffbaca6 664 wifiBusy = 0;
ocomeni 123:a49e9ffbaca6 665 break;
ocomeni 129:590bdc2dcf5b 666 }
ocomeni 79:a2187bbfa407 667 case WIFI_CMD_SEND_HTTP_REQ:
ocomeni 79:a2187bbfa407 668 break;
ocomeni 79:a2187bbfa407 669 default:
ocomeni 79:a2187bbfa407 670 break;
ocomeni 79:a2187bbfa407 671 }
ocomeni 105:e5ce023eee93 672 wait_ms(WIFI_MAIN_LOOP_WAIT_TIME_MS); //
ocomeni 79:a2187bbfa407 673 }
ocomeni 79:a2187bbfa407 674
ocomeni 78:07bb86e3ce14 675 }
ocomeni 79:a2187bbfa407 676
ocomeni 107:f1a83fd41b17 677 void WiFiManager::createSendHttpsRequest()
ocomeni 107:f1a83fd41b17 678 {
ocomeni 107:f1a83fd41b17 679 backgroundTaskCompleted = createHttpsRequest();
ocomeni 107:f1a83fd41b17 680 }
ocomeni 91:d6b6319ad681 681
ocomeni 129:590bdc2dcf5b 682
ocomeni 129:590bdc2dcf5b 683 void WiFiManager::createTLSconnThreadCall(const char * hostName)
ocomeni 129:590bdc2dcf5b 684 {
ocomeni 129:590bdc2dcf5b 685 bool result;
ocomeni 129:590bdc2dcf5b 686 backgroundTaskCompleted = false;
ocomeni 129:590bdc2dcf5b 687 result = createTLSconnection(hostName);
ocomeni 129:590bdc2dcf5b 688 if(result)
ocomeni 129:590bdc2dcf5b 689 {
ocomeni 129:590bdc2dcf5b 690 // update remote peer details after socket connection
ocomeni 129:590bdc2dcf5b 691 updateRemotePeerDetails();
ocomeni 129:590bdc2dcf5b 692 // send socket connection event before proceeding to send https request
ocomeni 129:590bdc2dcf5b 693 // give about 2 ms
ocomeni 129:590bdc2dcf5b 694 sendSocketConnectionEvent();
ocomeni 129:590bdc2dcf5b 695 backgroundTaskCompleted = true;
ocomeni 129:590bdc2dcf5b 696 }
ocomeni 129:590bdc2dcf5b 697 }
ocomeni 129:590bdc2dcf5b 698 void WiFiManager::waitForBackgroundTask(int timeout_ms, int inc_ms)
ocomeni 129:590bdc2dcf5b 699 {
ocomeni 129:590bdc2dcf5b 700 backgroundTaskCompleted = false;
ocomeni 129:590bdc2dcf5b 701 int msecCount = 0;
ocomeni 129:590bdc2dcf5b 702 int oldChunkNum = chunkNum;
ocomeni 129:590bdc2dcf5b 703 while(!backgroundTaskCompleted && msecCount < timeout_ms)
ocomeni 129:590bdc2dcf5b 704 {
ocomeni 129:590bdc2dcf5b 705 msecCount+=inc_ms;
ocomeni 129:590bdc2dcf5b 706 wait_ms(inc_ms);
ocomeni 129:590bdc2dcf5b 707 if(oldChunkNum != chunkNum) // new payload received
ocomeni 129:590bdc2dcf5b 708 {
ocomeni 129:590bdc2dcf5b 709 oldChunkNum = chunkNum;
ocomeni 129:590bdc2dcf5b 710 msecCount = 0;
ocomeni 129:590bdc2dcf5b 711 }
ocomeni 129:590bdc2dcf5b 712 }
ocomeni 129:590bdc2dcf5b 713 }
ocomeni 95:290859010c8c 714 void WiFiManager::sendATresponseString(at_cmd_resp_t at_cmd)
ocomeni 91:d6b6319ad681 715 {
ocomeni 95:290859010c8c 716 int strLen = strlen(responseString) + 1;
ocomeni 91:d6b6319ad681 717 at_data_resp = new at_data_msg_t;
ocomeni 91:d6b6319ad681 718 // set string length
ocomeni 91:d6b6319ad681 719 at_data_resp->dataLen = strLen;
ocomeni 91:d6b6319ad681 720 memcpy(at_data_resp->buffer, responseString, strLen);
ocomeni 95:290859010c8c 721 free(responseString);
ocomeni 99:05398b3184f8 722 responseString = NULL;
ocomeni 91:d6b6319ad681 723 // package and send on wifi data queue
ocomeni 91:d6b6319ad681 724 at_data_resp->at_resp = at_cmd;
ocomeni 91:d6b6319ad681 725 bool queueResult = true;
ocomeni 91:d6b6319ad681 726 int wait_count = 0;
ocomeni 91:d6b6319ad681 727 do
ocomeni 91:d6b6319ad681 728 {
ocomeni 91:d6b6319ad681 729 if(!queueResult){
ocomeni 110:c722dda4f2ff 730 wait_count+=10;
ocomeni 119:8d939a902333 731 dbg_printf(LOG, "ATCMD Queue full waiting %d ms so far...\n", wait_count);
ocomeni 91:d6b6319ad681 732 wait_ms(10);
ocomeni 91:d6b6319ad681 733 }
ocomeni 91:d6b6319ad681 734 queueResult = queueWiFiDataResponse(*at_data_resp);
ocomeni 110:c722dda4f2ff 735 }while(queueResult == false && wait_count<QUEUE_WAIT_TIMEOUT_MS);
ocomeni 91:d6b6319ad681 736 delete at_data_resp;
ocomeni 99:05398b3184f8 737 at_data_resp = NULL;
ocomeni 91:d6b6319ad681 738 }
ocomeni 91:d6b6319ad681 739
ocomeni 99:05398b3184f8 740
ocomeni 99:05398b3184f8 741 void WiFiManager::sendATresponseBytes(at_cmd_resp_t at_cmd, int len)
ocomeni 99:05398b3184f8 742 {
ocomeni 99:05398b3184f8 743 at_data_resp = new at_data_msg_t;
ocomeni 99:05398b3184f8 744 // set string length
ocomeni 99:05398b3184f8 745 at_data_resp->dataLen = len;
ocomeni 99:05398b3184f8 746 memcpy(at_data_resp->buffer, responseBytes, len);
ocomeni 107:f1a83fd41b17 747 delete responseBytes;
ocomeni 99:05398b3184f8 748 responseBytes = NULL;
ocomeni 99:05398b3184f8 749 // package and send on wifi data queue
ocomeni 99:05398b3184f8 750 at_data_resp->at_resp = at_cmd;
ocomeni 99:05398b3184f8 751 bool queueResult = true;
ocomeni 99:05398b3184f8 752 int wait_count = 0;
ocomeni 99:05398b3184f8 753 do
ocomeni 99:05398b3184f8 754 {
ocomeni 99:05398b3184f8 755 if(!queueResult){
ocomeni 110:c722dda4f2ff 756 wait_count+=10;
ocomeni 99:05398b3184f8 757 wait_ms(10);
ocomeni 119:8d939a902333 758 dbg_printf(LOG, "ATCMD Queue full waited %d ms so far...\n", wait_count);
ocomeni 99:05398b3184f8 759 }
ocomeni 99:05398b3184f8 760 queueResult = queueWiFiDataResponse(*at_data_resp);
ocomeni 110:c722dda4f2ff 761 }while(queueResult == false && wait_count<QUEUE_WAIT_TIMEOUT_MS);
ocomeni 99:05398b3184f8 762 delete at_data_resp;
ocomeni 99:05398b3184f8 763 at_data_resp = NULL;
ocomeni 103:7b566b522427 764 dbg_printf(LOG, "[WIFI-MAN] sendATresponseBytes completed successfully\r\n");
ocomeni 99:05398b3184f8 765 }
ocomeni 99:05398b3184f8 766
ocomeni 99:05398b3184f8 767
ocomeni 99:05398b3184f8 768
ocomeni 79:a2187bbfa407 769 bool WiFiManager::dequeueWiFiCommands(){
ocomeni 104:11e9605093c9 770 if(wifiCmd != WIFI_CMD_NONE || wifiBusy!=0) return false; // busy
ocomeni 81:637a87eb8170 771 osEvent evt = _aT2WiFiCmdQueue->get(0);
ocomeni 79:a2187bbfa407 772 if(evt.status == osEventMessage){
ocomeni 79:a2187bbfa407 773 wifi_cmd_message_t *cmd = (wifi_cmd_message_t*)evt.value.p;
ocomeni 79:a2187bbfa407 774 setNextCommand(cmd->wifi_cmd);
ocomeni 92:ec9550034276 775 #ifndef USE_MALLOC_FOR_COMMAND_MEMORY_POOL
ocomeni 79:a2187bbfa407 776 _aT2WiFimPool->free(cmd);
ocomeni 96:f5ed273881af 777 cmd = NULL;
ocomeni 92:ec9550034276 778 #else
ocomeni 92:ec9550034276 779 free(cmd);
ocomeni 96:f5ed273881af 780 cmd = NULL;
ocomeni 92:ec9550034276 781 #endif
ocomeni 79:a2187bbfa407 782 }
ocomeni 79:a2187bbfa407 783 return true;
ocomeni 79:a2187bbfa407 784 }
ocomeni 79:a2187bbfa407 785
ocomeni 79:a2187bbfa407 786
ocomeni 81:637a87eb8170 787 bool WiFiManager::dequeueATdataResponse(){
ocomeni 104:11e9605093c9 788 if(wifiCmd != WIFI_CMD_NONE || wifiBusy!=0) return false; // busy
ocomeni 81:637a87eb8170 789 osEvent evt = _aT2WiFiDataQueue->get(0);
ocomeni 81:637a87eb8170 790 if(evt.status == osEventMessage){
ocomeni 81:637a87eb8170 791 data_msg = (wifi_data_msg_t*)evt.value.p;
ocomeni 81:637a87eb8170 792 setNextCommand(data_msg->wifi_cmd);
ocomeni 81:637a87eb8170 793 //_wiFi2ATDatamPool->free(data_msg);
ocomeni 81:637a87eb8170 794 }
ocomeni 81:637a87eb8170 795 return true;
ocomeni 81:637a87eb8170 796 }
ocomeni 81:637a87eb8170 797
ocomeni 81:637a87eb8170 798
ocomeni 79:a2187bbfa407 799 bool WiFiManager::setNextCommand(wifi_cmd_t cmd)
ocomeni 78:07bb86e3ce14 800 {
ocomeni 103:7b566b522427 801 dbg_printf(LOG, "\n [WIFI-MAN] About to set next WiFi manager command to %d\n", cmd);
ocomeni 79:a2187bbfa407 802 if(wifiCmd == WIFI_CMD_NONE){
ocomeni 79:a2187bbfa407 803 wifiCmd = cmd;
ocomeni 79:a2187bbfa407 804 return true; // success
ocomeni 79:a2187bbfa407 805 }
ocomeni 103:7b566b522427 806 dbg_printf(LOG, "\n [WIFI-MAN] Busy : current state = %d \n", wifiCmd);
ocomeni 79:a2187bbfa407 807 return false; // wiFiManager busy
ocomeni 78:07bb86e3ce14 808 }
ocomeni 79:a2187bbfa407 809
ocomeni 81:637a87eb8170 810 const char * WiFiManager::sec2str(nsapi_security_t sec)
ocomeni 81:637a87eb8170 811 {
ocomeni 81:637a87eb8170 812 switch (sec) {
ocomeni 81:637a87eb8170 813 case NSAPI_SECURITY_NONE:
ocomeni 81:637a87eb8170 814 return "None";
ocomeni 81:637a87eb8170 815 case NSAPI_SECURITY_WEP:
ocomeni 81:637a87eb8170 816 return "WEP";
ocomeni 81:637a87eb8170 817 case NSAPI_SECURITY_WPA:
ocomeni 81:637a87eb8170 818 return "WPA";
ocomeni 81:637a87eb8170 819 case NSAPI_SECURITY_WPA2:
ocomeni 81:637a87eb8170 820 return "WPA2";
ocomeni 81:637a87eb8170 821 case NSAPI_SECURITY_WPA_WPA2:
ocomeni 81:637a87eb8170 822 return "WPA/WPA2";
ocomeni 81:637a87eb8170 823 case NSAPI_SECURITY_UNKNOWN:
ocomeni 81:637a87eb8170 824 default:
ocomeni 81:637a87eb8170 825 return "Unknown";
ocomeni 81:637a87eb8170 826 }
ocomeni 81:637a87eb8170 827 }
ocomeni 81:637a87eb8170 828
ocomeni 79:a2187bbfa407 829
ocomeni 79:a2187bbfa407 830 nsapi_size_or_error_t WiFiManager::scanNetworks()
ocomeni 79:a2187bbfa407 831 {
ocomeni 114:b11bb96c09f3 832 getWiFiInstance();
ocomeni 114:b11bb96c09f3 833 if(network == NULL)
ocomeni 114:b11bb96c09f3 834 {
ocomeni 114:b11bb96c09f3 835 dbg_printf(LOG, "\n [WIFI-MAN] Error instantiating WiFi!! \n");
ocomeni 114:b11bb96c09f3 836 return 0;
ocomeni 114:b11bb96c09f3 837 }
ocomeni 129:590bdc2dcf5b 838 //nsapi_error_t error;
ocomeni 103:7b566b522427 839 dbg_printf(LOG, "\n [WIFI-MAN] About to start scan for WiFi networks\n");
ocomeni 79:a2187bbfa407 840 lastScanCount = network->scan(NULL, 0);
ocomeni 103:7b566b522427 841 dbg_printf(LOG, "\n [WIFI-MAN] Scan for WiFi networks completed - \n");
ocomeni 79:a2187bbfa407 842 return lastScanCount;
ocomeni 79:a2187bbfa407 843 }
ocomeni 79:a2187bbfa407 844
ocomeni 79:a2187bbfa407 845
ocomeni 81:637a87eb8170 846 //nsapi_size_or_error_t WiFiManager::getAvailableAPs(WiFiAccessPoint * res,
ocomeni 81:637a87eb8170 847 // nsapi_size_t ncount)
ocomeni 81:637a87eb8170 848 nsapi_size_or_error_t WiFiManager::getAvailableAPs(nsapi_size_t ncount)
ocomeni 79:a2187bbfa407 849 {
ocomeni 114:b11bb96c09f3 850 getWiFiInstance();
ocomeni 114:b11bb96c09f3 851 if(network == NULL)
ocomeni 114:b11bb96c09f3 852 {
ocomeni 114:b11bb96c09f3 853 dbg_printf(LOG, "\n [WIFI-MAN] Error instantiating WiFi!! \n");
ocomeni 114:b11bb96c09f3 854 return 0;
ocomeni 114:b11bb96c09f3 855 }
ocomeni 81:637a87eb8170 856 WiFiAccessPoint *ap;
ocomeni 81:637a87eb8170 857 nsapi_size_or_error_t count;
ocomeni 81:637a87eb8170 858 count = ncount;
ocomeni 81:637a87eb8170 859 if (count <= 0) {
ocomeni 103:7b566b522427 860 dbg_printf(LOG, "[WIFI-MAN] scan() failed with return value: %d\n", count);
ocomeni 98:65c2333a38b6 861 return 0;
ocomeni 81:637a87eb8170 862 }
ocomeni 81:637a87eb8170 863 /* Limit number of network arbitrary to 15 */
ocomeni 81:637a87eb8170 864 count = count < 15 ? count : 15;
ocomeni 81:637a87eb8170 865 ap = new WiFiAccessPoint[count];
ocomeni 81:637a87eb8170 866 count = network->scan(ap, count);
ocomeni 81:637a87eb8170 867 if (count <= 0) {
ocomeni 103:7b566b522427 868 dbg_printf(LOG, "[WIFI-MAN] scan() failed with return value: %d\n", count);
ocomeni 98:65c2333a38b6 869 return 0;
ocomeni 81:637a87eb8170 870 }
ocomeni 81:637a87eb8170 871
ocomeni 81:637a87eb8170 872 for (int i = 0; i < count; i++) {
ocomeni 103:7b566b522427 873 dbg_printf(LOG, "[WIFI-MAN]: %s secured: %s BSSID: %hhX:%hhX:%hhX:%hhx:%hhx:%hhx RSSI: %hhd Ch: %hhd\n", ap[i].get_ssid(),
ocomeni 81:637a87eb8170 874 sec2str(ap[i].get_security()), ap[i].get_bssid()[0], ap[i].get_bssid()[1], ap[i].get_bssid()[2],
ocomeni 81:637a87eb8170 875 ap[i].get_bssid()[3], ap[i].get_bssid()[4], ap[i].get_bssid()[5], ap[i].get_rssi(), ap[i].get_channel());
ocomeni 81:637a87eb8170 876 }
ocomeni 103:7b566b522427 877 dbg_printf(LOG, "[WIFI-MAN] %d networks available.\n", count);
ocomeni 81:637a87eb8170 878
ocomeni 81:637a87eb8170 879 delete[] ap;
ocomeni 79:a2187bbfa407 880 return count;
ocomeni 79:a2187bbfa407 881 }
ocomeni 79:a2187bbfa407 882
ocomeni 79:a2187bbfa407 883
ocomeni 81:637a87eb8170 884 void WiFiManager::set_WIFI_CONFIG()
ocomeni 81:637a87eb8170 885 {
ocomeni 81:637a87eb8170 886 wifi_config_t *wifi_cfg= (wifi_config_t *) data_msg->buffer;
ocomeni 82:10072c1794d3 887 if(wifi_cfg->ssid[0] != NULL)set_WIFI_SSID(wifi_cfg->ssid);
ocomeni 82:10072c1794d3 888 if(wifi_cfg->pass[0] != NULL)set_WIFI_PASSWORD(wifi_cfg->pass);
ocomeni 82:10072c1794d3 889 if(wifi_cfg->security != NSAPI_SECURITY_UNKNOWN)set_WIFI_SECURITY(wifi_cfg->security);
ocomeni 81:637a87eb8170 890 free_DataMsg();
ocomeni 81:637a87eb8170 891 }
ocomeni 81:637a87eb8170 892
ocomeni 78:07bb86e3ce14 893 void WiFiManager::set_WIFI_SSID(char * wifi_ssid)
ocomeni 78:07bb86e3ce14 894 {
ocomeni 116:2296cf274661 895 strcpy(wifi_config->ssid, wifi_ssid);
ocomeni 116:2296cf274661 896 dbg_printf(LOG, "[WIFI-MAN] wifi_ssid set to %s\n", wifi_config->ssid);
ocomeni 88:7ffa053be662 897 https_connection_active = false; // reset whenever any of the security credentials change
ocomeni 91:d6b6319ad681 898 delete socket;
ocomeni 78:07bb86e3ce14 899 }
ocomeni 79:a2187bbfa407 900
ocomeni 79:a2187bbfa407 901
ocomeni 78:07bb86e3ce14 902 void WiFiManager::set_WIFI_PASSWORD(char * wifi_pass)
ocomeni 78:07bb86e3ce14 903 {
ocomeni 116:2296cf274661 904 strcpy(wifi_config->pass, wifi_pass);
ocomeni 103:7b566b522427 905 dbg_printf(LOG, "[WIFI-MAN] wifi_pass set to %s\n", "****************");
ocomeni 88:7ffa053be662 906 https_connection_active = false; // reset whenever any of the security credentials change
ocomeni 91:d6b6319ad681 907 delete socket;
ocomeni 78:07bb86e3ce14 908 }
ocomeni 79:a2187bbfa407 909
ocomeni 79:a2187bbfa407 910
ocomeni 78:07bb86e3ce14 911 void WiFiManager::set_WIFI_SECURITY(nsapi_security_t wifi_security)
ocomeni 78:07bb86e3ce14 912 {
ocomeni 116:2296cf274661 913 wifi_config->security = wifi_security;
ocomeni 116:2296cf274661 914 dbg_printf(LOG, "[WIFI-MAN] wifi_security set to %s\n", sec2str(wifi_config->security));
ocomeni 88:7ffa053be662 915 https_connection_active = false; // reset whenever any of the security credentials change
ocomeni 91:d6b6319ad681 916 delete socket;
ocomeni 78:07bb86e3ce14 917 }
ocomeni 79:a2187bbfa407 918
ocomeni 100:80ef4bc31b7a 919 void WiFiManager::gethostbyname()
ocomeni 100:80ef4bc31b7a 920 {
ocomeni 100:80ef4bc31b7a 921 nsapi_value_or_error_t value_or_error;
ocomeni 111:3ab1d9644835 922 #ifdef DNANUDGE_DEBUG
ocomeni 111:3ab1d9644835 923 SocketAddress * addr = new SocketAddress;
ocomeni 111:3ab1d9644835 924 bool res;
ocomeni 111:3ab1d9644835 925 res = addr->set_ip_address("8.8.8.8");
ocomeni 111:3ab1d9644835 926 if(res)
ocomeni 111:3ab1d9644835 927 {
ocomeni 111:3ab1d9644835 928 dbg_printf(LOG, "[WIFI-MAN] added ip address %s\r\n", addr->get_ip_address());
ocomeni 111:3ab1d9644835 929 }
ocomeni 111:3ab1d9644835 930 else
ocomeni 111:3ab1d9644835 931 {
ocomeni 111:3ab1d9644835 932 dbg_printf(LOG, "[WIFI-MAN] Error adding ip address \r\n");
ocomeni 111:3ab1d9644835 933 }
ocomeni 111:3ab1d9644835 934 network->add_dns_server(*addr);
ocomeni 111:3ab1d9644835 935 #endif
ocomeni 111:3ab1d9644835 936 char * serverAddress = new char[100];
ocomeni 116:2296cf274661 937 char *p = strstr(internet_config->url, "//");
ocomeni 113:888e262ff0a9 938 if(p != NULL && use_full_hostname == false)
ocomeni 111:3ab1d9644835 939 {
ocomeni 111:3ab1d9644835 940 strcpy(serverAddress,p+2);
ocomeni 111:3ab1d9644835 941 }
ocomeni 111:3ab1d9644835 942 else
ocomeni 111:3ab1d9644835 943 {
ocomeni 116:2296cf274661 944 strcpy(serverAddress,internet_config->url);
ocomeni 111:3ab1d9644835 945 }
ocomeni 111:3ab1d9644835 946 value_or_error = network->gethostbyname_async(serverAddress,
ocomeni 100:80ef4bc31b7a 947 callback(this, &WiFiManager::gethostbyname_callback),
ocomeni 100:80ef4bc31b7a 948 NSAPI_UNSPEC);
ocomeni 111:3ab1d9644835 949
ocomeni 100:80ef4bc31b7a 950 if(value_or_error >= NSAPI_ERROR_OK) // success
ocomeni 100:80ef4bc31b7a 951 {
ocomeni 103:7b566b522427 952 dbg_printf(LOG, "[WIFI-MAN] hostname translation successful value_or_error = %d\r\n", value_or_error);
ocomeni 100:80ef4bc31b7a 953 //strcpy(responseString, UDDRP_WRITE_OK);
ocomeni 100:80ef4bc31b7a 954 //printBufferInHex(responseBytes, HOSTNAME_RESPONSE_LEN);
ocomeni 100:80ef4bc31b7a 955 //sendATresponseBytes(CONNECT_EVENT, HOSTNAME_RESPONSE_LEN);
ocomeni 100:80ef4bc31b7a 956 }
ocomeni 118:8df0e9c2ee3f 957 else if(outputBuffersAvailable()) // -ve number means error
ocomeni 100:80ef4bc31b7a 958 {
ocomeni 100:80ef4bc31b7a 959 responseString = (char *) malloc(20);
ocomeni 103:7b566b522427 960 dbg_printf(LOG, "[WIFI-MAN] hostname translation failed\r\n");
ocomeni 100:80ef4bc31b7a 961 strcpy(responseString, UDDRP_ERROR);
ocomeni 100:80ef4bc31b7a 962 sendATresponseString(AT_COMMAND_FAILED);
ocomeni 100:80ef4bc31b7a 963 }
ocomeni 81:637a87eb8170 964
ocomeni 100:80ef4bc31b7a 965 }
ocomeni 100:80ef4bc31b7a 966
ocomeni 100:80ef4bc31b7a 967 void WiFiManager::set_internet_config()
ocomeni 81:637a87eb8170 968 {
ocomeni 81:637a87eb8170 969 internet_config_t *internet_cfg = (internet_config_t *) data_msg->buffer;
ocomeni 116:2296cf274661 970 internet_config->peer_id = internet_cfg->peer_id;
ocomeni 116:2296cf274661 971 strncpy(internet_config->url,internet_cfg->url, strlen(internet_cfg->url)+1);
ocomeni 116:2296cf274661 972 internet_config->connectionScheme = internet_cfg->connectionScheme;
ocomeni 81:637a87eb8170 973 free_DataMsg();
ocomeni 103:7b566b522427 974 dbg_printf(LOG, "[WIFI MAN] Internet configuration setup completed\n");
ocomeni 116:2296cf274661 975 dbg_printf(LOG, "peer_id = %1d, url = %s, connScheme = %1d\n", internet_config->peer_id,
ocomeni 116:2296cf274661 976 internet_config->url,
ocomeni 116:2296cf274661 977 internet_config->connectionScheme);
ocomeni 99:05398b3184f8 978 if(https_connection_active)
ocomeni 99:05398b3184f8 979 {
ocomeni 99:05398b3184f8 980 https_connection_active = false; // reset whenever any of the security credentials change
ocomeni 99:05398b3184f8 981 socket->close(); // close socket before deleting memory
ocomeni 99:05398b3184f8 982 delete socket;
ocomeni 99:05398b3184f8 983 socket = NULL;
ocomeni 99:05398b3184f8 984 }
ocomeni 100:80ef4bc31b7a 985 _event_queue.call_in(10, this, &WiFiManager::gethostbyname);
ocomeni 81:637a87eb8170 986 }
ocomeni 81:637a87eb8170 987
ocomeni 95:290859010c8c 988
ocomeni 95:290859010c8c 989
ocomeni 95:290859010c8c 990 void WiFiManager::getNetworkStatus(){
ocomeni 95:290859010c8c 991
ocomeni 95:290859010c8c 992 responseString = (char *) malloc(MAX_RESPONSE_STRING_LEN);
ocomeni 95:290859010c8c 993 net_stat_id_t status_id;
ocomeni 95:290859010c8c 994 char * nextStrPtr = responseString;
ocomeni 95:290859010c8c 995 for(int i=0; i< NumNetworkStatus;i++){
ocomeni 95:290859010c8c 996 status_id = netStatusIds[i]; // get current status id
ocomeni 95:290859010c8c 997 switch(status_id){
ocomeni 95:290859010c8c 998 case IF_HW_ADDRESS:
ocomeni 95:290859010c8c 999 sprintf(nextStrPtr, "\r\n%s%d,%d,%s\r\n", NETWORK_STATUS,
ocomeni 95:290859010c8c 1000 WIFI_CHANNEL,
ocomeni 95:290859010c8c 1001 status_id,
ocomeni 95:290859010c8c 1002 network->get_mac_address());
ocomeni 95:290859010c8c 1003 break;
ocomeni 95:290859010c8c 1004 case NETWORK_IF_STATUS:
ocomeni 95:290859010c8c 1005 sprintf(nextStrPtr, "\r\n%s%d,%d, %d\r\n", NETWORK_STATUS,
ocomeni 95:290859010c8c 1006 WIFI_CHANNEL,
ocomeni 95:290859010c8c 1007 status_id,
ocomeni 95:290859010c8c 1008 (uint8_t)is_connected);
ocomeni 95:290859010c8c 1009 break;
ocomeni 95:290859010c8c 1010 case INTERFACE_TYPE:
ocomeni 95:290859010c8c 1011 sprintf(nextStrPtr, "\r\n%s%d,%d,%d\r\n", NETWORK_STATUS,
ocomeni 95:290859010c8c 1012 WIFI_CHANNEL,
ocomeni 95:290859010c8c 1013 status_id,
ocomeni 95:290859010c8c 1014 WIFI_STATION);
ocomeni 95:290859010c8c 1015 break;
ocomeni 95:290859010c8c 1016 case IPv4_ADDRESS:
ocomeni 95:290859010c8c 1017 sprintf(nextStrPtr, "\r\n%s%d,%d,%s\r\n", NETWORK_STATUS,
ocomeni 95:290859010c8c 1018 WIFI_CHANNEL,
ocomeni 95:290859010c8c 1019 status_id,
ocomeni 95:290859010c8c 1020 network->get_ip_address());
ocomeni 95:290859010c8c 1021 break;
ocomeni 95:290859010c8c 1022 case SUBNET_MASK:
ocomeni 95:290859010c8c 1023 sprintf(nextStrPtr, "\r\n%s%d,%d,%s\r\n", NETWORK_STATUS,
ocomeni 95:290859010c8c 1024 WIFI_CHANNEL,
ocomeni 95:290859010c8c 1025 status_id,
ocomeni 95:290859010c8c 1026 network->get_netmask());
ocomeni 95:290859010c8c 1027 break;
ocomeni 95:290859010c8c 1028 case GATEWAY_ADDRESS:
ocomeni 95:290859010c8c 1029 sprintf(nextStrPtr, "\r\n%s%d,%d,%s\r\n", NETWORK_STATUS,
ocomeni 95:290859010c8c 1030 WIFI_CHANNEL,
ocomeni 95:290859010c8c 1031 status_id,
ocomeni 95:290859010c8c 1032 network->get_gateway());
ocomeni 95:290859010c8c 1033 break;
ocomeni 95:290859010c8c 1034 case PRIMARY_DNS_SERVER:
ocomeni 95:290859010c8c 1035 sprintf(nextStrPtr, "\r\n%s%d,%d,%s\r\n", NETWORK_STATUS,
ocomeni 95:290859010c8c 1036 WIFI_CHANNEL,
ocomeni 95:290859010c8c 1037 status_id,
ocomeni 95:290859010c8c 1038 DEFAULT_DNS_ADDRESS);
ocomeni 95:290859010c8c 1039 break;
ocomeni 95:290859010c8c 1040 case SECONDARY_DNS_SERVER:
ocomeni 95:290859010c8c 1041 sprintf(nextStrPtr, "\r\n%s%d,%d,%s\r\n", NETWORK_STATUS,
ocomeni 95:290859010c8c 1042 WIFI_CHANNEL,
ocomeni 95:290859010c8c 1043 status_id,
ocomeni 95:290859010c8c 1044 DEFAULT_DNS_ADDRESS);
ocomeni 95:290859010c8c 1045 break;
ocomeni 95:290859010c8c 1046 case IPv6_ADDRESS:
ocomeni 95:290859010c8c 1047 sprintf(nextStrPtr, "\r\n%s%d,%d,::\r\n", NETWORK_STATUS,
ocomeni 95:290859010c8c 1048 WIFI_CHANNEL,
ocomeni 95:290859010c8c 1049 status_id);
ocomeni 95:290859010c8c 1050 break;
ocomeni 95:290859010c8c 1051 default:
ocomeni 95:290859010c8c 1052 sprintf(nextStrPtr, "\r\n%s,::\r\n", NETWORK_STATUS);
ocomeni 95:290859010c8c 1053 break;
ocomeni 95:290859010c8c 1054 }
ocomeni 103:7b566b522427 1055 nextStrPtr += strlen(nextStrPtr) ; // progress to end of current string
ocomeni 95:290859010c8c 1056 }
ocomeni 103:7b566b522427 1057 sprintf(nextStrPtr, "%s", UDDRP_WRITE_OK);
ocomeni 95:290859010c8c 1058 }
ocomeni 95:290859010c8c 1059
ocomeni 123:a49e9ffbaca6 1060 void WiFiManager::getWiFiMACaddress()
ocomeni 123:a49e9ffbaca6 1061 {
ocomeni 124:eae4512b131b 1062 char * mp = new char[20];
ocomeni 124:eae4512b131b 1063 sscanf(network->get_mac_address(),"%02s:%2s:%2s:%2s:%2s:%2s",&mp[0],&mp[2],&mp[4],&mp[6],&mp[8],&mp[10]);
ocomeni 123:a49e9ffbaca6 1064 responseString = (char *) malloc(100);
ocomeni 124:eae4512b131b 1065
ocomeni 124:eae4512b131b 1066 sprintf(responseString, "\r\n%s%d,%sOK\r\n", LOCAL_ADDRESS_RESP,
ocomeni 124:eae4512b131b 1067 WIFI_IF_ID,
ocomeni 124:eae4512b131b 1068 mp);
ocomeni 124:eae4512b131b 1069 delete mp;
ocomeni 123:a49e9ffbaca6 1070 }
ocomeni 95:290859010c8c 1071
ocomeni 95:290859010c8c 1072
ocomeni 95:290859010c8c 1073 void WiFiManager::getWiFiStatus(){
ocomeni 95:290859010c8c 1074
ocomeni 95:290859010c8c 1075 responseString = (char *) malloc(MAX_RESPONSE_STRING_LEN);
ocomeni 95:290859010c8c 1076 wifi_stat_id_t status_id;
ocomeni 95:290859010c8c 1077 char * nextStrPtr = responseString;
ocomeni 95:290859010c8c 1078 for(int i=0; i< NumWiFiStatus;i++){
ocomeni 95:290859010c8c 1079 status_id = wifiStatusIds[i]; // get current status id
ocomeni 95:290859010c8c 1080 switch(status_id){
ocomeni 95:290859010c8c 1081 case WIFI_SSID:
ocomeni 95:290859010c8c 1082 sprintf(nextStrPtr, "\r\n%s%d,%s\r\n", WIFI_NETWORK_STATUS,
ocomeni 95:290859010c8c 1083 status_id,
ocomeni 116:2296cf274661 1084 wifi_config->ssid);
ocomeni 95:290859010c8c 1085 break;
ocomeni 95:290859010c8c 1086 case WIFI_BSSID:
ocomeni 95:290859010c8c 1087 sprintf(nextStrPtr, "\r\n%s%d,%s\r\n", WIFI_NETWORK_STATUS,
ocomeni 95:290859010c8c 1088 status_id,
ocomeni 95:290859010c8c 1089 network->get_mac_address());
ocomeni 95:290859010c8c 1090 break;
ocomeni 95:290859010c8c 1091 case WIFI__CURRENT_CHANNEL:
ocomeni 95:290859010c8c 1092 sprintf(nextStrPtr, "\r\n%s%d,%d\r\n", WIFI_NETWORK_STATUS,
ocomeni 95:290859010c8c 1093 status_id,
ocomeni 95:290859010c8c 1094 DEFAULT_WIFI_CHANNEL);
ocomeni 95:290859010c8c 1095 break;
ocomeni 95:290859010c8c 1096 case WIFI_STA_STATUS:
ocomeni 95:290859010c8c 1097 sprintf(nextStrPtr, "\r\n%s%d,%d\r\n", WIFI_NETWORK_STATUS,
ocomeni 95:290859010c8c 1098 status_id,
ocomeni 95:290859010c8c 1099 (uint8_t)is_connected);
ocomeni 95:290859010c8c 1100 break;
ocomeni 95:290859010c8c 1101 case WIFI_RSSI:
ocomeni 95:290859010c8c 1102 sprintf(nextStrPtr, "\r\n%s%d,%d\r\n", WIFI_NETWORK_STATUS,
ocomeni 95:290859010c8c 1103 status_id,
ocomeni 95:290859010c8c 1104 network->get_rssi());
ocomeni 95:290859010c8c 1105 break;
ocomeni 95:290859010c8c 1106 default:
ocomeni 95:290859010c8c 1107 sprintf(nextStrPtr, "\r\n%s,::\r\n", WIFI_NETWORK_STATUS);
ocomeni 95:290859010c8c 1108 break;
ocomeni 95:290859010c8c 1109 }
ocomeni 103:7b566b522427 1110 nextStrPtr += strlen(nextStrPtr) ; // progress to end of current string
ocomeni 95:290859010c8c 1111 }
ocomeni 103:7b566b522427 1112 sprintf(nextStrPtr, "%s", UDDRP_WRITE_OK);
ocomeni 95:290859010c8c 1113 }
ocomeni 95:290859010c8c 1114
ocomeni 95:290859010c8c 1115
ocomeni 81:637a87eb8170 1116 void WiFiManager::free_DataMsg()
ocomeni 81:637a87eb8170 1117 {
ocomeni 81:637a87eb8170 1118 // free memory after processing
ocomeni 81:637a87eb8170 1119 _aT2WiFiDatamPool->free(data_msg);
ocomeni 96:f5ed273881af 1120 data_msg = NULL;
ocomeni 81:637a87eb8170 1121 }
ocomeni 81:637a87eb8170 1122
ocomeni 81:637a87eb8170 1123
ocomeni 88:7ffa053be662 1124
ocomeni 81:637a87eb8170 1125 void WiFiManager::status_callback(nsapi_event_t status, intptr_t param)
ocomeni 81:637a87eb8170 1126 {
ocomeni 105:e5ce023eee93 1127 dbg_printf(LOG, "[WIFI-MAN] about to call status_callback_event... \r\n");
ocomeni 98:65c2333a38b6 1128 _event_queue.call_in(50, this, &WiFiManager::status_callback_event, status, param);
ocomeni 98:65c2333a38b6 1129 }
ocomeni 98:65c2333a38b6 1130 void WiFiManager::status_callback_event(nsapi_event_t status, intptr_t param)
ocomeni 98:65c2333a38b6 1131 {
ocomeni 81:637a87eb8170 1132 switch(param) {
ocomeni 81:637a87eb8170 1133 case NSAPI_STATUS_LOCAL_UP:
ocomeni 103:7b566b522427 1134 dbg_printf(LOG, "[WIFI-MAN] Local IP address set!\r\n");
ocomeni 103:7b566b522427 1135 dbg_printf(LOG, "[WIFI-MAN] IP address: %s\n", network->get_ip_address());
ocomeni 81:637a87eb8170 1136 break;
ocomeni 81:637a87eb8170 1137 case NSAPI_STATUS_GLOBAL_UP:
ocomeni 103:7b566b522427 1138 dbg_printf(LOG, "Global IP address set!\r\n");
ocomeni 103:7b566b522427 1139 dbg_printf(LOG, "[WIFI-MAN] IP address: %s\n", network->get_ip_address());
ocomeni 116:2296cf274661 1140 dbg_printf(LOG, "[WIFI-MAN] Connected to the network %s\n", wifi_config->ssid);
ocomeni 118:8df0e9c2ee3f 1141 if(outputBuffersAvailable())
ocomeni 118:8df0e9c2ee3f 1142 {
ocomeni 118:8df0e9c2ee3f 1143 responseString = (char *) malloc(MAX_RESPONSE_STRING_LEN);
ocomeni 118:8df0e9c2ee3f 1144 sprintf(responseString, "\r\n%s%d,%s,%d\r\n", WIFI_LINK_ENABLED,
ocomeni 118:8df0e9c2ee3f 1145 WIFI_CHANNEL,
ocomeni 118:8df0e9c2ee3f 1146 network->get_mac_address(),
ocomeni 118:8df0e9c2ee3f 1147 DEFAULT_WIFI_CHANNEL);
ocomeni 118:8df0e9c2ee3f 1148
ocomeni 124:eae4512b131b 1149 wifiBusy = 0;
ocomeni 118:8df0e9c2ee3f 1150 is_connected = true;
ocomeni 118:8df0e9c2ee3f 1151 }
ocomeni 81:637a87eb8170 1152 break;
ocomeni 81:637a87eb8170 1153 case NSAPI_STATUS_DISCONNECTED:
ocomeni 103:7b566b522427 1154 dbg_printf(LOG, "No connection to network!\r\n");
ocomeni 103:7b566b522427 1155 dbg_printf(LOG, "\n [WIFI-MAN] No connection to network!\n");
ocomeni 124:eae4512b131b 1156 if(outputBuffersAvailable())
ocomeni 81:637a87eb8170 1157 {
ocomeni 124:eae4512b131b 1158 responseString = (char *) malloc(100);
ocomeni 124:eae4512b131b 1159 sprintf(responseString, "\r\n%s%d,5\r\n", WIFI_LINK_DISABLED, WIFI_CHANNEL);
ocomeni 124:eae4512b131b 1160 //sendATresponseString(AT_EVENT);
ocomeni 81:637a87eb8170 1161 }
ocomeni 124:eae4512b131b 1162 wifiBusy = 0;
ocomeni 124:eae4512b131b 1163 is_connected = false;
ocomeni 81:637a87eb8170 1164 break;
ocomeni 81:637a87eb8170 1165 case NSAPI_STATUS_CONNECTING:
ocomeni 103:7b566b522427 1166 dbg_printf(LOG, "Connecting to network!\r\n");
ocomeni 81:637a87eb8170 1167 break;
ocomeni 81:637a87eb8170 1168 default:
ocomeni 103:7b566b522427 1169 dbg_printf(LOG, "Not supported");
ocomeni 81:637a87eb8170 1170 break;
ocomeni 81:637a87eb8170 1171 }
ocomeni 81:637a87eb8170 1172 }
ocomeni 81:637a87eb8170 1173
ocomeni 81:637a87eb8170 1174
ocomeni 81:637a87eb8170 1175
ocomeni 79:a2187bbfa407 1176
ocomeni 79:a2187bbfa407 1177 nsapi_error_t WiFiManager::connect()
ocomeni 79:a2187bbfa407 1178 {
ocomeni 114:b11bb96c09f3 1179 getWiFiInstance();
ocomeni 114:b11bb96c09f3 1180 if(network == NULL)
ocomeni 114:b11bb96c09f3 1181 {
ocomeni 114:b11bb96c09f3 1182 dbg_printf(LOG, "\n [WIFI-MAN] Error instantiating WiFi!! \n");
ocomeni 114:b11bb96c09f3 1183 return 0;
ocomeni 114:b11bb96c09f3 1184 }
ocomeni 79:a2187bbfa407 1185 nsapi_error_t error;
ocomeni 103:7b566b522427 1186 dbg_printf(LOG, "\n [WIFI-MAN] About to connect to WiFi network\n");
ocomeni 81:637a87eb8170 1187 network->attach(callback(this, &WiFiManager::status_callback));
ocomeni 79:a2187bbfa407 1188 error = network->set_blocking(false);
ocomeni 79:a2187bbfa407 1189 if(error)
ocomeni 79:a2187bbfa407 1190 {
ocomeni 103:7b566b522427 1191 dbg_printf(LOG, "\n [WIFI-MAN] Could not set non-blocking mode for Wifi -- aborting!! - \n");
ocomeni 79:a2187bbfa407 1192 return error;
ocomeni 79:a2187bbfa407 1193 }
ocomeni 103:7b566b522427 1194 dbg_printf(LOG, "[WIFI-MAN] Connecting to network ssid = %s passwd = %s security = %s \r\n",
ocomeni 116:2296cf274661 1195 wifi_config->ssid,
ocomeni 96:f5ed273881af 1196 "****************",
ocomeni 116:2296cf274661 1197 sec2str(wifi_config->security));
ocomeni 116:2296cf274661 1198 error = network->connect(wifi_config->ssid,
ocomeni 116:2296cf274661 1199 wifi_config->pass,
ocomeni 116:2296cf274661 1200 wifi_config->security);
ocomeni 103:7b566b522427 1201 dbg_printf(LOG, "[WIFI-MAN] network->connect called. error = %d\r\n", error);
ocomeni 81:637a87eb8170 1202 return error;
ocomeni 79:a2187bbfa407 1203 }
ocomeni 79:a2187bbfa407 1204
ocomeni 113:888e262ff0a9 1205 void WiFiManager::processGetHostByNameResult(nsapi_error_t result, SocketAddress *address)
ocomeni 99:05398b3184f8 1206 {
ocomeni 118:8df0e9c2ee3f 1207
ocomeni 103:7b566b522427 1208 dbg_printf(LOG, "gethostbyname_callback called... result = %d \r\n", result);
ocomeni 107:f1a83fd41b17 1209 print_memory_info();
ocomeni 118:8df0e9c2ee3f 1210 if(outputBuffersAvailable())
ocomeni 99:05398b3184f8 1211 {
ocomeni 118:8df0e9c2ee3f 1212 responseBytes = new uint8_t[HOSTNAME_RESPONSE_LEN]; //malloc(HOSTNAME_RESPONSE_LEN);
ocomeni 118:8df0e9c2ee3f 1213 int i = 0;
ocomeni 118:8df0e9c2ee3f 1214 responseBytes[i++] = IPv4_CONNECTION; // connect type IPv4
ocomeni 118:8df0e9c2ee3f 1215 responseBytes[i++] = TCP_PROTOCOL; // Protocol = TCP
ocomeni 118:8df0e9c2ee3f 1216 if(is_connected && result>=0)
ocomeni 107:f1a83fd41b17 1217 {
ocomeni 118:8df0e9c2ee3f 1218 memcpy(&responseBytes[i], address->get_ip_bytes(), 4); // remote IPv4 address
ocomeni 118:8df0e9c2ee3f 1219 strcpy(internet_config->remote_IPv4Address, address->get_ip_address());
ocomeni 118:8df0e9c2ee3f 1220 i +=4;
ocomeni 118:8df0e9c2ee3f 1221 uint16_t port = address->get_port();
ocomeni 118:8df0e9c2ee3f 1222 internet_config->remote_port = port;
ocomeni 118:8df0e9c2ee3f 1223 memcpy(&responseBytes[i], &port, 2); // remote IPv4 port #
ocomeni 118:8df0e9c2ee3f 1224 i +=2;
ocomeni 118:8df0e9c2ee3f 1225 // local IPv4 address
ocomeni 118:8df0e9c2ee3f 1226 int ipAddr[4];
ocomeni 118:8df0e9c2ee3f 1227 strcpy(internet_config->local_IPv4Address, network->get_ip_address());
ocomeni 118:8df0e9c2ee3f 1228 sscanf(internet_config->local_IPv4Address, "%d.%d.%d.%d", &ipAddr[0], &ipAddr[1],
ocomeni 118:8df0e9c2ee3f 1229 &ipAddr[2], &ipAddr[3]);
ocomeni 118:8df0e9c2ee3f 1230 responseBytes[i++] = (uint8_t) ipAddr[0];
ocomeni 118:8df0e9c2ee3f 1231 responseBytes[i++] = (uint8_t) ipAddr[1];
ocomeni 118:8df0e9c2ee3f 1232 responseBytes[i++] = (uint8_t) ipAddr[2];
ocomeni 118:8df0e9c2ee3f 1233 responseBytes[i++] = (uint8_t) ipAddr[3];
ocomeni 118:8df0e9c2ee3f 1234 // local port number
ocomeni 118:8df0e9c2ee3f 1235 responseBytes[i++] = 0;
ocomeni 118:8df0e9c2ee3f 1236 responseBytes[i] = 0;
ocomeni 118:8df0e9c2ee3f 1237 printBufferInHex(responseBytes, HOSTNAME_RESPONSE_LEN);
ocomeni 118:8df0e9c2ee3f 1238 sendATresponseBytes(CONNECT_EVENT, HOSTNAME_RESPONSE_LEN);
ocomeni 107:f1a83fd41b17 1239 }
ocomeni 118:8df0e9c2ee3f 1240 else
ocomeni 118:8df0e9c2ee3f 1241 {
ocomeni 118:8df0e9c2ee3f 1242 // if unconnected set ip and port to zeroes
ocomeni 118:8df0e9c2ee3f 1243 memset(&responseBytes[i], 0x00, 6);
ocomeni 118:8df0e9c2ee3f 1244 delete responseBytes;
ocomeni 118:8df0e9c2ee3f 1245 dbg_printf(LOG, "\r\nHOSTNAME TRANSLATION FAILURE : error code = %d \r\n", result);
ocomeni 118:8df0e9c2ee3f 1246 if(responseString == NULL)
ocomeni 118:8df0e9c2ee3f 1247 {
ocomeni 118:8df0e9c2ee3f 1248 responseString = (char *) malloc(100);
ocomeni 118:8df0e9c2ee3f 1249 sprintf(responseString, "\r\nHOSTNAME TRANSLATION FAILURE : error code = %d \r\n", result);
ocomeni 118:8df0e9c2ee3f 1250 sendATresponseString(AT_EVENT);
ocomeni 118:8df0e9c2ee3f 1251 }
ocomeni 118:8df0e9c2ee3f 1252 use_full_hostname = not use_full_hostname;
ocomeni 118:8df0e9c2ee3f 1253 }
ocomeni 118:8df0e9c2ee3f 1254 wifiBusy = 0;
ocomeni 118:8df0e9c2ee3f 1255 backgroundTaskCompleted = true;
ocomeni 107:f1a83fd41b17 1256 }
ocomeni 113:888e262ff0a9 1257
ocomeni 113:888e262ff0a9 1258 }
ocomeni 104:11e9605093c9 1259
ocomeni 113:888e262ff0a9 1260 void WiFiManager::gethostbyname_callback(nsapi_error_t res, SocketAddress *addr)
ocomeni 113:888e262ff0a9 1261 {
ocomeni 113:888e262ff0a9 1262 nsapi_error_t result = res;
ocomeni 113:888e262ff0a9 1263 SocketAddress *address = new SocketAddress;
ocomeni 113:888e262ff0a9 1264 address = addr;
ocomeni 113:888e262ff0a9 1265 _event_queue.call(this, &WiFiManager::processGetHostByNameResult,
ocomeni 113:888e262ff0a9 1266 result, address);
ocomeni 113:888e262ff0a9 1267
ocomeni 113:888e262ff0a9 1268 #ifdef DNANUDGE_DEBUG
ocomeni 113:888e262ff0a9 1269 callback_semaphore.release();
ocomeni 113:888e262ff0a9 1270 #endif
ocomeni 99:05398b3184f8 1271 }
ocomeni 99:05398b3184f8 1272
ocomeni 100:80ef4bc31b7a 1273 void WiFiManager::sendSocketConnectionEvent()
ocomeni 100:80ef4bc31b7a 1274 {
ocomeni 100:80ef4bc31b7a 1275 //
ocomeni 100:80ef4bc31b7a 1276 responseString = (char *) malloc(MAX_RESPONSE_STRING_LEN);
ocomeni 100:80ef4bc31b7a 1277 sprintf(responseString, "\r\n%s%d,%d,%d,%s,%d,%s,%d\r\n", PEER_CONNECTED_URC,
ocomeni 100:80ef4bc31b7a 1278 IP_PEER_HANDLE,
ocomeni 100:80ef4bc31b7a 1279 IPv4_CONNECTION,
ocomeni 100:80ef4bc31b7a 1280 TCP_PROTOCOL,
ocomeni 116:2296cf274661 1281 internet_config->local_IPv4Address,
ocomeni 100:80ef4bc31b7a 1282 DEFAULT_LOCAL_PORT,
ocomeni 116:2296cf274661 1283 internet_config->remote_IPv4Address,
ocomeni 116:2296cf274661 1284 internet_config->remote_port);
ocomeni 100:80ef4bc31b7a 1285 sendATresponseString(AT_EVENT);
ocomeni 100:80ef4bc31b7a 1286 }
ocomeni 100:80ef4bc31b7a 1287
ocomeni 99:05398b3184f8 1288
ocomeni 79:a2187bbfa407 1289 nsapi_error_t WiFiManager::disconnect()
ocomeni 78:07bb86e3ce14 1290 {
ocomeni 79:a2187bbfa407 1291 nsapi_error_t error;
ocomeni 79:a2187bbfa407 1292 error = network->disconnect();
ocomeni 124:eae4512b131b 1293 if(error < 0)
ocomeni 124:eae4512b131b 1294 {
ocomeni 124:eae4512b131b 1295 responseString = (char *) malloc(100);
ocomeni 124:eae4512b131b 1296 sprintf(responseString, "%s", UDDRP_ERROR);
ocomeni 124:eae4512b131b 1297 sendATresponseString(AT_EVENT);
ocomeni 124:eae4512b131b 1298 }
ocomeni 79:a2187bbfa407 1299 return error;
ocomeni 78:07bb86e3ce14 1300 }
ocomeni 79:a2187bbfa407 1301
ocomeni 98:65c2333a38b6 1302 #define MIX_HDR_AND_BODY
ocomeni 88:7ffa053be662 1303 void WiFiManager::sendResponseDownloadData(at_cmd_resp_t at_cmd, const uint8_t * buf, int bufLen)
ocomeni 90:ed0267eca7b5 1304 {
ocomeni 90:ed0267eca7b5 1305
ocomeni 88:7ffa053be662 1306 at_data_resp = new at_data_msg_t;
ocomeni 88:7ffa053be662 1307 at_data_resp->at_resp = at_cmd;
ocomeni 88:7ffa053be662 1308 size_t bufSize = sizeof(at_data_resp->buffer);
ocomeni 88:7ffa053be662 1309 int pos = 0;
ocomeni 88:7ffa053be662 1310 at_data_resp->dataLen = 0;
ocomeni 88:7ffa053be662 1311 bool queueResult = true;
ocomeni 90:ed0267eca7b5 1312 int hdrLen = 0;
ocomeni 94:fb4414aff957 1313 int wait_count = 0;
ocomeni 88:7ffa053be662 1314 do {
ocomeni 94:fb4414aff957 1315 if(!queueResult){
ocomeni 94:fb4414aff957 1316 wait_count++;
ocomeni 103:7b566b522427 1317 dbg_printf(LOG, "[WIFI-MAN] ATCMD Queue full waiting %d ms so far...\n", wait_count*10);
ocomeni 94:fb4414aff957 1318 wait_ms(10);
ocomeni 90:ed0267eca7b5 1319 }
ocomeni 90:ed0267eca7b5 1320 else {
ocomeni 98:65c2333a38b6 1321 if(http_response_hdr_sent == false && chunkNum==1){ // only do this for first chunk
ocomeni 102:9748f290a1a5 1322 bool status = copyResponseHdr2Queue(buf);
ocomeni 98:65c2333a38b6 1323 if(status == true){
ocomeni 103:7b566b522427 1324 dbg_printf(LOG, "[WIFI-MAN] Http Response header copied to response buffer [bytes = %d] \r\n",at_data_resp->dataLen);
ocomeni 98:65c2333a38b6 1325 hdrLen = at_data_resp->dataLen;
ocomeni 98:65c2333a38b6 1326 http_response_hdr_sent = true;
ocomeni 98:65c2333a38b6 1327 }
ocomeni 98:65c2333a38b6 1328 else {
ocomeni 103:7b566b522427 1329 dbg_printf(LOG, "[WIFI-MAN] Http Response header copy failed\r\n");
ocomeni 98:65c2333a38b6 1330 }
ocomeni 90:ed0267eca7b5 1331 }
ocomeni 94:fb4414aff957 1332 int cpyLen = (bufLen - pos) > bufSize? bufSize : (bufLen - pos) ;
ocomeni 103:7b566b522427 1333 dbg_printf(LOG, "[WIFI-MAN] Http Response body [bytes = %d] \r\n",cpyLen);
ocomeni 90:ed0267eca7b5 1334 at_data_resp->dataLen += cpyLen;
ocomeni 90:ed0267eca7b5 1335 memcpy(&at_data_resp->buffer[hdrLen], &buf[pos], cpyLen);
ocomeni 103:7b566b522427 1336 dbg_printf(LOG, "[WIFI-MAN] Http Response header and body copied to response buffer [bytes = %d] \r\n",at_data_resp->dataLen);
ocomeni 90:ed0267eca7b5 1337 }
ocomeni 88:7ffa053be662 1338 queueResult = queueWiFiDataResponse(*at_data_resp);
ocomeni 90:ed0267eca7b5 1339 if(queueResult){
ocomeni 90:ed0267eca7b5 1340 pos+= at_data_resp->dataLen;
ocomeni 90:ed0267eca7b5 1341 at_data_resp->dataLen = 0;
ocomeni 90:ed0267eca7b5 1342 hdrLen = 0;
ocomeni 90:ed0267eca7b5 1343 }
ocomeni 88:7ffa053be662 1344 }while(queueResult == false || pos < bufLen);
ocomeni 103:7b566b522427 1345 dbg_printf(LOG, "[WIFI-MAN] response data queued - deleting data memory\r\n");
ocomeni 88:7ffa053be662 1346 delete at_data_resp;
ocomeni 100:80ef4bc31b7a 1347 at_data_resp = NULL;
ocomeni 88:7ffa053be662 1348 }
ocomeni 79:a2187bbfa407 1349
ocomeni 102:9748f290a1a5 1350 bool WiFiManager::copyResponseHdr2Queue(const uint8_t * buf)
ocomeni 90:ed0267eca7b5 1351 {
ocomeni 102:9748f290a1a5 1352 const char *arbPtr = (const char *)buf - MAX_HTTP_HDR_LEN;
ocomeni 102:9748f290a1a5 1353 const char *hdrPtr;
ocomeni 102:9748f290a1a5 1354 int len;
ocomeni 102:9748f290a1a5 1355 bool hdrFound = false;
ocomeni 102:9748f290a1a5 1356 int i;
ocomeni 102:9748f290a1a5 1357 for(i=0;i<(MAX_HTTP_HDR_LEN-50);i++)
ocomeni 101:1cfd468e5009 1358 {
ocomeni 102:9748f290a1a5 1359 // get location of start of the http header string
ocomeni 102:9748f290a1a5 1360 hdrPtr = strstr(&arbPtr[i], HTTP_HEADER_START_LINE);
ocomeni 102:9748f290a1a5 1361 len = strlen(HTTP_HEADER_START_LINE);
ocomeni 102:9748f290a1a5 1362 // validate that header string
ocomeni 102:9748f290a1a5 1363 if((strstr(&arbPtr[i+len], HTTP_HEADER_START_LINE) == NULL ||
ocomeni 102:9748f290a1a5 1364 (strstr(&arbPtr[i+len], HTTP_HEADER_START_LINE) > (const char*)buf)) && //
ocomeni 102:9748f290a1a5 1365 strstr(&arbPtr[i+len], HTTP_HEADER_CONTENT_TYPE) != NULL &&
ocomeni 102:9748f290a1a5 1366 strstr(&arbPtr[i+len], HTTP_HEADER_CONTENT_LEN) != NULL &&
ocomeni 102:9748f290a1a5 1367 hdrPtr != NULL)
ocomeni 102:9748f290a1a5 1368 {
ocomeni 102:9748f290a1a5 1369 hdrFound = true;
ocomeni 102:9748f290a1a5 1370 break;
ocomeni 102:9748f290a1a5 1371 }
ocomeni 101:1cfd468e5009 1372 }
ocomeni 102:9748f290a1a5 1373 // calculate header length
ocomeni 102:9748f290a1a5 1374 int hdrLen = (const char*) buf -hdrPtr;
ocomeni 102:9748f290a1a5 1375 // copy header
ocomeni 102:9748f290a1a5 1376 memcpy(at_data_resp->buffer, (const uint8_t *) hdrPtr, hdrLen);
ocomeni 103:7b566b522427 1377 dbg_printf(LOG, "[i = %d] This is the header\r\n%s\r\n", i, hdrPtr);
ocomeni 102:9748f290a1a5 1378 if(hdrFound == false)
ocomeni 100:80ef4bc31b7a 1379 {
ocomeni 103:7b566b522427 1380 dbg_printf(LOG, "[WIFI-MAN] copy failed: HTTP header not found!!\r\n");
ocomeni 100:80ef4bc31b7a 1381 return false;
ocomeni 100:80ef4bc31b7a 1382 }
ocomeni 102:9748f290a1a5 1383 at_data_resp->dataLen = hdrLen;
ocomeni 98:65c2333a38b6 1384 return true;
ocomeni 90:ed0267eca7b5 1385 }
ocomeni 90:ed0267eca7b5 1386
ocomeni 84:7c7add00f4bf 1387 void WiFiManager::return_response(HttpResponse* res) {
ocomeni 84:7c7add00f4bf 1388
ocomeni 88:7ffa053be662 1389 at_data_resp = new at_data_msg_t;
ocomeni 87:99b37d26ff2a 1390 int numChars = 0;
ocomeni 87:99b37d26ff2a 1391 // create message pointer for response header generation
ocomeni 88:7ffa053be662 1392 char * msgPtr = (char *)at_data_resp->buffer;
ocomeni 87:99b37d26ff2a 1393 // do status line
ocomeni 87:99b37d26ff2a 1394 numChars = sprintf(msgPtr, "HTTP/1.1 %d %s\r\n", res->get_status_code(), res->get_status_message().c_str());
ocomeni 87:99b37d26ff2a 1395 msgPtr += numChars;
ocomeni 84:7c7add00f4bf 1396 for (size_t ix = 0; ix < res->get_headers_length(); ix++) {
ocomeni 87:99b37d26ff2a 1397 numChars = sprintf(msgPtr, "%s: %s\r\n",
ocomeni 87:99b37d26ff2a 1398 res->get_headers_fields()[ix]->c_str(),
ocomeni 87:99b37d26ff2a 1399 res->get_headers_values()[ix]->c_str());
ocomeni 87:99b37d26ff2a 1400 msgPtr += numChars;
ocomeni 84:7c7add00f4bf 1401 }
ocomeni 87:99b37d26ff2a 1402 numChars = sprintf(msgPtr, "\r\n\r\n");
ocomeni 87:99b37d26ff2a 1403 msgPtr += numChars;
ocomeni 87:99b37d26ff2a 1404 // print out generated header
ocomeni 103:7b566b522427 1405 dbg_printf(LOG, "[WiFi MAN] generated response header:\n");
ocomeni 103:7b566b522427 1406 dbg_printf(LOG, "%s\r\n", (char *)at_data_resp->buffer);
ocomeni 90:ed0267eca7b5 1407 // calculate header length
ocomeni 89:45f6db09a76d 1408 at_data_resp->dataLen = (msgPtr - (char *)at_data_resp->buffer);
ocomeni 84:7c7add00f4bf 1409
ocomeni 90:ed0267eca7b5 1410 // package and send on wifi data queue
ocomeni 88:7ffa053be662 1411 at_data_resp->at_resp = AT_HTTPS_RESP;
ocomeni 89:45f6db09a76d 1412 bool queueResult = true;
ocomeni 89:45f6db09a76d 1413 int wait_count = 0;
ocomeni 89:45f6db09a76d 1414 do
ocomeni 89:45f6db09a76d 1415 {
ocomeni 89:45f6db09a76d 1416 if(!queueResult){
ocomeni 89:45f6db09a76d 1417 wait_count++;
ocomeni 103:7b566b522427 1418 dbg_printf(LOG, "ATCMD Queue full waiting %d ms so far...\n", wait_count*10);
ocomeni 89:45f6db09a76d 1419 wait_ms(10);
ocomeni 89:45f6db09a76d 1420 }
ocomeni 89:45f6db09a76d 1421 queueResult = queueWiFiDataResponse(*at_data_resp);
ocomeni 89:45f6db09a76d 1422 }while(queueResult == false);
ocomeni 88:7ffa053be662 1423 delete at_data_resp;
ocomeni 100:80ef4bc31b7a 1424 at_data_resp = NULL;
ocomeni 84:7c7add00f4bf 1425 }
ocomeni 90:ed0267eca7b5 1426
ocomeni 90:ed0267eca7b5 1427
ocomeni 104:11e9605093c9 1428 void WiFiManager::printBufferInHex(const uint8_t *buf, int pLen)
ocomeni 90:ed0267eca7b5 1429 {
ocomeni 104:11e9605093c9 1430 print_debug_hex(buf, pLen);
ocomeni 90:ed0267eca7b5 1431 }
ocomeni 90:ed0267eca7b5 1432
ocomeni 88:7ffa053be662 1433 //#define TRY_PRINTF
ocomeni 84:7c7add00f4bf 1434
ocomeni 90:ed0267eca7b5 1435 void WiFiManager::body_callback(const char *at, uint32_t length) {
ocomeni 103:7b566b522427 1436 dbg_printf(LOG, "\n Chunked response: Chunk %d : Total Bytes = %d\n", chunkNum , length);
ocomeni 84:7c7add00f4bf 1437 chunkNum++;
ocomeni 105:e5ce023eee93 1438 dbg_printf(LOG, "This is the start when response is excluded\r\n%s\r\nend of packet \r\n", at);
ocomeni 102:9748f290a1a5 1439 if(http_response == NULL)
ocomeni 102:9748f290a1a5 1440 {
ocomeni 103:7b566b522427 1441 dbg_printf(LOG, "[WIFI-MAN] response pointer NULL!!\r\n");
ocomeni 102:9748f290a1a5 1442 }
ocomeni 102:9748f290a1a5 1443 else
ocomeni 102:9748f290a1a5 1444 {
ocomeni 103:7b566b522427 1445 dbg_printf(LOG, "[WIFI-MAN] response pointer NULL not!!\r\n");
ocomeni 102:9748f290a1a5 1446 }
ocomeni 122:62166886db5f 1447 #ifdef SEND_DEBUG_MESSAGES
ocomeni 104:11e9605093c9 1448 if(responseString == NULL && chunkNum==1)
ocomeni 104:11e9605093c9 1449 {
ocomeni 104:11e9605093c9 1450 responseString = (char *) malloc(100);
ocomeni 129:590bdc2dcf5b 1451 sprintf(responseString, "\r\nHTTPS BODY CALLBACK RECEIVED:: length= %d\r\n", length);
ocomeni 104:11e9605093c9 1452 sendATresponseString(AT_EVENT);
ocomeni 104:11e9605093c9 1453 }
ocomeni 122:62166886db5f 1454 #endif
ocomeni 89:45f6db09a76d 1455 sendResponseDownloadData(AT_HTTPS_RESP_DOWNLOAD, (uint8_t *)at, length);
ocomeni 84:7c7add00f4bf 1456 }
ocomeni 84:7c7add00f4bf 1457
ocomeni 105:e5ce023eee93 1458 //#define ENABLE_MBED_TRACE
ocomeni 88:7ffa053be662 1459 bool WiFiManager::createTLSconnection(const char * hostName)
ocomeni 88:7ffa053be662 1460 {
ocomeni 93:06e755a80187 1461 #ifdef ENABLE_MBED_TRACE
ocomeni 93:06e755a80187 1462 mbed_trace_init();
ocomeni 93:06e755a80187 1463 #endif
ocomeni 88:7ffa053be662 1464 socket = new TLSSocket();
ocomeni 88:7ffa053be662 1465 nsapi_error_t r;
ocomeni 88:7ffa053be662 1466 // make sure to check the return values for the calls below (should return NSAPI_ERROR_OK)
ocomeni 88:7ffa053be662 1467 r = socket->open(network);
ocomeni 88:7ffa053be662 1468 if(r != NSAPI_ERROR_OK)
ocomeni 88:7ffa053be662 1469 {
ocomeni 103:7b566b522427 1470 dbg_printf(LOG, "TLS open failed!!\n");
ocomeni 88:7ffa053be662 1471 return false;
ocomeni 88:7ffa053be662 1472 }
ocomeni 103:7b566b522427 1473 dbg_printf(LOG, "TLS open passed!!\n");
ocomeni 88:7ffa053be662 1474 r = socket->set_root_ca_cert(SSL_CA_PEM);
ocomeni 88:7ffa053be662 1475 if(r != NSAPI_ERROR_OK)
ocomeni 88:7ffa053be662 1476 {
ocomeni 103:7b566b522427 1477 dbg_printf(LOG, "TLS set_root_ca_cert failed!!\n");
ocomeni 98:65c2333a38b6 1478 socket->close();
ocomeni 103:7b566b522427 1479 dbg_printf(LOG, "closing TLS socket!!\n");
ocomeni 88:7ffa053be662 1480 return false;
ocomeni 88:7ffa053be662 1481 }
ocomeni 103:7b566b522427 1482 dbg_printf(LOG, "TLS set_root_ca_cert passed!!\n");
ocomeni 129:590bdc2dcf5b 1483 int start_ms = _event_queue.tick();
ocomeni 129:590bdc2dcf5b 1484 int elapsed_ms;
ocomeni 129:590bdc2dcf5b 1485 do{
ocomeni 129:590bdc2dcf5b 1486 r = socket->connect(hostName, 443);
ocomeni 129:590bdc2dcf5b 1487 elapsed_ms = _event_queue.tick() - start_ms;
ocomeni 129:590bdc2dcf5b 1488 if(r == NSAPI_ERROR_OK)
ocomeni 129:590bdc2dcf5b 1489 {
ocomeni 129:590bdc2dcf5b 1490 dbg_printf(LOG, "TLS connection successful for https site : %s"
ocomeni 129:590bdc2dcf5b 1491 " \r\n[TLS conn elapsed_ms = %d]\n", hostName, elapsed_ms);
ocomeni 129:590bdc2dcf5b 1492 return true;
ocomeni 129:590bdc2dcf5b 1493 }
ocomeni 129:590bdc2dcf5b 1494 }while(elapsed_ms < TLS_RETRY_TIMEOUT_MS);
ocomeni 129:590bdc2dcf5b 1495 char errstr[100];
ocomeni 129:590bdc2dcf5b 1496 mbedtls_strerror(r, errstr, 100);
ocomeni 129:590bdc2dcf5b 1497 dbg_printf(LOG, "TLS connect failed (err = %d) for hostname '%s' -- ERROR = %s !!\n", r, hostName, errstr);
ocomeni 129:590bdc2dcf5b 1498 socket->close();
ocomeni 129:590bdc2dcf5b 1499 return false;
ocomeni 88:7ffa053be662 1500 }
ocomeni 100:80ef4bc31b7a 1501
ocomeni 100:80ef4bc31b7a 1502
ocomeni 100:80ef4bc31b7a 1503 void WiFiManager::updateRemotePeerDetails()
ocomeni 100:80ef4bc31b7a 1504 {
ocomeni 103:7b566b522427 1505 dbg_printf(LOG, "Updating internet_config... \r\n");
ocomeni 100:80ef4bc31b7a 1506 nsapi_error_t error;
ocomeni 100:80ef4bc31b7a 1507 SocketAddress * address = new SocketAddress;
ocomeni 104:11e9605093c9 1508 error = socket->getpeername(address);
ocomeni 104:11e9605093c9 1509 if(error>=0)
ocomeni 104:11e9605093c9 1510 {
ocomeni 116:2296cf274661 1511 strcpy(internet_config->remote_IPv4Address, address->get_ip_address());
ocomeni 104:11e9605093c9 1512 uint16_t port = address->get_port();
ocomeni 116:2296cf274661 1513 internet_config->remote_port = port;
ocomeni 104:11e9605093c9 1514 }
ocomeni 104:11e9605093c9 1515 else
ocomeni 104:11e9605093c9 1516 {
ocomeni 116:2296cf274661 1517 strcpy(internet_config->remote_IPv4Address, "");
ocomeni 116:2296cf274661 1518 internet_config->remote_port = 0;
ocomeni 104:11e9605093c9 1519 }
ocomeni 100:80ef4bc31b7a 1520 delete address;
ocomeni 100:80ef4bc31b7a 1521 }
ocomeni 100:80ef4bc31b7a 1522
ocomeni 105:e5ce023eee93 1523
ocomeni 105:e5ce023eee93 1524 void WiFiManager::sendDebugMessage()
ocomeni 105:e5ce023eee93 1525 {
ocomeni 107:f1a83fd41b17 1526 #ifdef SEND_HTTPS_DEBUG_MESSAGES
ocomeni 105:e5ce023eee93 1527 sendATresponseString(AT_EVENT);
ocomeni 105:e5ce023eee93 1528 wait_ms(100);
ocomeni 107:f1a83fd41b17 1529 #else
ocomeni 107:f1a83fd41b17 1530 free(responseString);
ocomeni 107:f1a83fd41b17 1531 #endif
ocomeni 105:e5ce023eee93 1532 }
ocomeni 88:7ffa053be662 1533 #define TESTING_HTTPS
ocomeni 98:65c2333a38b6 1534
ocomeni 96:f5ed273881af 1535 //#define DONT_USE_TLS_SOCKET
ocomeni 98:65c2333a38b6 1536 bool WiFiManager::createHttpsRequest()
ocomeni 79:a2187bbfa407 1537 {
ocomeni 106:e1f04c3d0647 1538 int starttime;
ocomeni 106:e1f04c3d0647 1539 int stoptime;
ocomeni 87:99b37d26ff2a 1540 // reset chunk #;
ocomeni 87:99b37d26ff2a 1541 chunkNum = 0;
ocomeni 90:ed0267eca7b5 1542 http_response_hdr_sent = false;
ocomeni 103:7b566b522427 1543 dbg_printf(LOG, "\n[WIFI MAN] Http Request received:\n");
ocomeni 84:7c7add00f4bf 1544 http_req_cfg = (http_request_t *) data_msg->buffer;
ocomeni 105:e5ce023eee93 1545 #ifdef FULL_DEBUG_ENABLED
ocomeni 103:7b566b522427 1546 dbg_printf(LOG, "\n[WIFI MAN] uri = %s\n", http_req_cfg->request_URI);
ocomeni 116:2296cf274661 1547 dbg_printf(LOG, "\n[WIFI MAN] internet cfg url = %s\n", internet_config->url);
ocomeni 105:e5ce023eee93 1548 #endif
ocomeni 87:99b37d26ff2a 1549 char full_url[100];
ocomeni 88:7ffa053be662 1550 char host[60] ;
ocomeni 116:2296cf274661 1551 strncpy(full_url,internet_config->url, strlen(internet_config->url)+1);
ocomeni 129:590bdc2dcf5b 1552 //strncpy(host,http_req_cfg->hostName, strlen(http_req_cfg->hostName)+1);
ocomeni 129:590bdc2dcf5b 1553 char *eu = strstr(internet_config->url,HTTPS_URL_PREFIX);
ocomeni 129:590bdc2dcf5b 1554 if(eu == NULL)
ocomeni 129:590bdc2dcf5b 1555 eu = internet_config->url;
ocomeni 129:590bdc2dcf5b 1556 else
ocomeni 129:590bdc2dcf5b 1557 eu += strlen(HTTPS_URL_PREFIX);
ocomeni 129:590bdc2dcf5b 1558 char *eu2 = strstr(eu, "/"); // find the api path
ocomeni 129:590bdc2dcf5b 1559 int hLen = eu2 != NULL ? eu2-eu-1: strlen(eu);
ocomeni 129:590bdc2dcf5b 1560
ocomeni 129:590bdc2dcf5b 1561
ocomeni 129:590bdc2dcf5b 1562 strncpy(host,eu, hLen+1);
ocomeni 90:ed0267eca7b5 1563 strncat(full_url, http_req_cfg->request_URI, strlen(http_req_cfg->request_URI)+1);
ocomeni 105:e5ce023eee93 1564 #ifdef FULL_DEBUG_ENABLED
ocomeni 129:590bdc2dcf5b 1565 dbg_printf(LOG, "\n[WIFI MAN] server host name = %s\n", host);
ocomeni 103:7b566b522427 1566 dbg_printf(LOG, "\n[WIFI MAN] server url+uri = %s\n", full_url);
ocomeni 103:7b566b522427 1567 dbg_printf(LOG, "\n[WIFI MAN] Host = %s\n", http_req_cfg->hostName);
ocomeni 103:7b566b522427 1568 dbg_printf(LOG, "\n[WIFI MAN] Accept = %s\n", http_req_cfg->AcceptVal);
ocomeni 103:7b566b522427 1569 dbg_printf(LOG, "\n[WIFI MAN] Content-Type = %s\n", http_req_cfg->contentType);
ocomeni 103:7b566b522427 1570 dbg_printf(LOG, "\n[WIFI MAN] contentLenstr = %s\n", http_req_cfg->contentLen);
ocomeni 105:e5ce023eee93 1571 #endif
ocomeni 84:7c7add00f4bf 1572
ocomeni 84:7c7add00f4bf 1573 int bodyLen;
ocomeni 90:ed0267eca7b5 1574 sscanf(http_req_cfg->contentLen, "%d", &bodyLen);
ocomeni 105:e5ce023eee93 1575 #ifdef FULL_DEBUG_ENABLED
ocomeni 103:7b566b522427 1576 dbg_printf(LOG, "contenLenstr = %s bodyLen = %d\n", http_req_cfg->contentLen, bodyLen);
ocomeni 90:ed0267eca7b5 1577 if(bodyLen > 10){
ocomeni 103:7b566b522427 1578 dbg_printf(LOG, "\n [WIFI MAN] Message Body:\n");
ocomeni 90:ed0267eca7b5 1579 printBufferInHex(http_req_cfg->body, bodyLen);
ocomeni 90:ed0267eca7b5 1580 }
ocomeni 105:e5ce023eee93 1581 #endif
ocomeni 116:2296cf274661 1582 if(strstr(internet_config->url, "http:")!=NULL) // http request
ocomeni 87:99b37d26ff2a 1583 {
ocomeni 87:99b37d26ff2a 1584 http_request = new HttpRequest(network,
ocomeni 90:ed0267eca7b5 1585 http_req_cfg->method,
ocomeni 90:ed0267eca7b5 1586 full_url,
ocomeni 90:ed0267eca7b5 1587 callback(this, &WiFiManager::body_callback));
ocomeni 87:99b37d26ff2a 1588 setHttpHeader("Host", http_req_cfg->hostName);
ocomeni 87:99b37d26ff2a 1589 setHttpHeader("Accept", http_req_cfg->AcceptVal);
ocomeni 88:7ffa053be662 1590 if(http_req_cfg->method == HTTP_GET){
ocomeni 103:7b566b522427 1591 dbg_printf(LOG, "HTTP_GET -- ignoring body\n");
ocomeni 88:7ffa053be662 1592 http_response = http_request->send(NULL, 0);
ocomeni 88:7ffa053be662 1593 }
ocomeni 88:7ffa053be662 1594 else{
ocomeni 88:7ffa053be662 1595 setHttpHeader("Content-Type", http_req_cfg->contentType);
ocomeni 88:7ffa053be662 1596 setHttpHeader("Content-Length", http_req_cfg->contentLen);
ocomeni 88:7ffa053be662 1597 http_response = http_request->send(http_req_cfg->body, bodyLen);
ocomeni 88:7ffa053be662 1598 }
ocomeni 87:99b37d26ff2a 1599 free_DataMsg();
ocomeni 87:99b37d26ff2a 1600 if (!http_response) {
ocomeni 87:99b37d26ff2a 1601 char buf[100];
ocomeni 87:99b37d26ff2a 1602 mbedtls_strerror(http_request->get_error(), buf, 100);
ocomeni 103:7b566b522427 1603 dbg_printf(LOG, "HttpRequest failed (error code %s)\n", buf);
ocomeni 87:99b37d26ff2a 1604 delete http_request; // free the memory
ocomeni 98:65c2333a38b6 1605 return false;
ocomeni 87:99b37d26ff2a 1606 }
ocomeni 88:7ffa053be662 1607 delete http_request; // free the memory
ocomeni 103:7b566b522427 1608 dbg_printf(LOG, "\n----- HTTP POST response -----\n");
ocomeni 84:7c7add00f4bf 1609 }
ocomeni 87:99b37d26ff2a 1610 else
ocomeni 87:99b37d26ff2a 1611 {
ocomeni 105:e5ce023eee93 1612 mbed_stats_heap_t heap_stats;
ocomeni 105:e5ce023eee93 1613 mbed_stats_heap_get(&heap_stats);
ocomeni 105:e5ce023eee93 1614 dbg_printf(LOG, "Heap size: %lu / %lu bytes\r\n", heap_stats.current_size, heap_stats.reserved_size);
ocomeni 106:e1f04c3d0647 1615 starttime = Kernel::get_ms_count();
ocomeni 90:ed0267eca7b5 1616 #ifndef DONT_USE_TLS_SOCKET
ocomeni 88:7ffa053be662 1617 if(https_connection_active == false){
ocomeni 88:7ffa053be662 1618 bool tlsResult;
ocomeni 88:7ffa053be662 1619 tlsResult = createTLSconnection(host);
ocomeni 93:06e755a80187 1620 #ifdef ENABLE_MBED_TRACE
ocomeni 93:06e755a80187 1621 mbed_trace_free(); // free trace memory
ocomeni 93:06e755a80187 1622 #endif
ocomeni 106:e1f04c3d0647 1623 stoptime = Kernel::get_ms_count();
ocomeni 106:e1f04c3d0647 1624 dbg_printf(LOG, "\r\nTLS connection time : %d ms\r\n", (stoptime - starttime));
ocomeni 88:7ffa053be662 1625 if(tlsResult == false){
ocomeni 88:7ffa053be662 1626 delete socket;
ocomeni 103:7b566b522427 1627 dbg_printf(LOG, "TLS Socket connection failed - deleting data msg\r\n");
ocomeni 88:7ffa053be662 1628 free_DataMsg();
ocomeni 103:7b566b522427 1629 dbg_printf(LOG, "data msg deleted \r\n");
ocomeni 104:11e9605093c9 1630 http_result = TLS_CONNECTION_FAILED;
ocomeni 98:65c2333a38b6 1631 return false;
ocomeni 88:7ffa053be662 1632 }
ocomeni 100:80ef4bc31b7a 1633 // update remote peer details after socket connection
ocomeni 100:80ef4bc31b7a 1634 updateRemotePeerDetails();
ocomeni 100:80ef4bc31b7a 1635 // send socket connection event before proceeding to send https request
ocomeni 100:80ef4bc31b7a 1636 // give about 2 ms
ocomeni 104:11e9605093c9 1637 sendSocketConnectionEvent();
ocomeni 88:7ffa053be662 1638 }
ocomeni 88:7ffa053be662 1639 // Pass in `socket`, instead of `network` as first argument, and omit the `SSL_CA_PEM` argument
ocomeni 106:e1f04c3d0647 1640 stoptime = Kernel::get_ms_count();
ocomeni 106:e1f04c3d0647 1641 dbg_printf(LOG, "\r\nTLS connection time : %d ms\r\n", (stoptime - starttime));
ocomeni 106:e1f04c3d0647 1642 starttime = Kernel::get_ms_count();
ocomeni 88:7ffa053be662 1643 https_request = new HttpsRequest(socket,
ocomeni 87:99b37d26ff2a 1644 http_req_cfg->method,
ocomeni 88:7ffa053be662 1645 full_url,
ocomeni 87:99b37d26ff2a 1646 callback(this, &WiFiManager::body_callback));
ocomeni 109:c274780ff609 1647 #ifdef SEND_DEBUG_MESSAGES
ocomeni 105:e5ce023eee93 1648 responseString = (char *) malloc(100);
ocomeni 105:e5ce023eee93 1649 sprintf(responseString, "\r\nHTTP REQUEST OBJECT CREATED\r\n");
ocomeni 105:e5ce023eee93 1650 sendDebugMessage();
ocomeni 109:c274780ff609 1651 #endif
ocomeni 90:ed0267eca7b5 1652 #else
ocomeni 90:ed0267eca7b5 1653 https_request = new HttpsRequest(network,
ocomeni 90:ed0267eca7b5 1654 SSL_CA_PEM,
ocomeni 90:ed0267eca7b5 1655 http_req_cfg->method,
ocomeni 90:ed0267eca7b5 1656 full_url,
ocomeni 90:ed0267eca7b5 1657 callback(this, &WiFiManager::body_callback));
ocomeni 90:ed0267eca7b5 1658 #endif
ocomeni 88:7ffa053be662 1659 #ifdef TESTING_HTTPS
ocomeni 103:7b566b522427 1660 dbg_printf(LOG, "http_req_cfg->method = %d\n", http_req_cfg->method);
ocomeni 88:7ffa053be662 1661 if(http_req_cfg->method == HTTP_GET){
ocomeni 103:7b566b522427 1662 dbg_printf(LOG, "HTTP_GET -- ignoring body\n");
ocomeni 129:590bdc2dcf5b 1663 setHttpsHeader("Host", host);
ocomeni 89:45f6db09a76d 1664 setHttpsHeader("Accept", http_req_cfg->AcceptVal);
ocomeni 88:7ffa053be662 1665 http_response = https_request->send(NULL, 0);
ocomeni 88:7ffa053be662 1666 }
ocomeni 88:7ffa053be662 1667 else{
ocomeni 129:590bdc2dcf5b 1668 setHttpsHeader("Host", host);
ocomeni 129:590bdc2dcf5b 1669 setHttpsHeader("Authorization", aws_id_token);
ocomeni 89:45f6db09a76d 1670 setHttpsHeader("Accept", http_req_cfg->AcceptVal);
ocomeni 90:ed0267eca7b5 1671 setHttpsHeader("Content-Type", http_req_cfg->contentType);
ocomeni 90:ed0267eca7b5 1672 setHttpsHeader("Content-Length", http_req_cfg->contentLen);
ocomeni 103:7b566b522427 1673 dbg_printf(LOG, "https headers setup - about to send request\r\n");
ocomeni 105:e5ce023eee93 1674 // Grab the heap statistics
ocomeni 105:e5ce023eee93 1675 dbg_printf(LOG, "Heap size: %lu / %lu bytes\r\n", heap_stats.current_size, heap_stats.reserved_size);
ocomeni 129:590bdc2dcf5b 1676 dbg_printf(LOG, "\n[WIFI MAN] Token Length: %d \r\n IdToken: \r\n %s\r\n", strlen(aws_id_token), aws_id_token);
ocomeni 129:590bdc2dcf5b 1677
ocomeni 129:590bdc2dcf5b 1678 #ifdef PRINT_REQUEST_LOGS
ocomeni 129:590bdc2dcf5b 1679 uint8_t *http_req_log_buf = (uint8_t*)calloc(2048, 1);
ocomeni 129:590bdc2dcf5b 1680 https_request->set_request_log_buffer(http_req_log_buf, 2048);
ocomeni 129:590bdc2dcf5b 1681 #endif
ocomeni 110:c722dda4f2ff 1682 http_response = https_request->send(http_req_cfg->body, bodyLen);
ocomeni 88:7ffa053be662 1683 }
ocomeni 88:7ffa053be662 1684 #else
ocomeni 129:590bdc2dcf5b 1685 setHttpsHeader("Host", host);
ocomeni 129:590bdc2dcf5b 1686 setHttpsHeader("Authorization", aws_id_token);
ocomeni 89:45f6db09a76d 1687 setHttpsHeader("Accept", http_req_cfg->AcceptVal);
ocomeni 96:f5ed273881af 1688 setHttpsHeader("Content-Type", http_req_cfg->contentType);
ocomeni 96:f5ed273881af 1689 setHttpsHeader("Content-Length", http_req_cfg->contentLen);
ocomeni 87:99b37d26ff2a 1690 http_response = https_request->send(http_req_cfg->body, bodyLen);
ocomeni 129:590bdc2dcf5b 1691 #endif
ocomeni 129:590bdc2dcf5b 1692 #ifdef PRINT_REQUEST_LOGS
ocomeni 129:590bdc2dcf5b 1693 printHttpRequestLogBuffer();
ocomeni 129:590bdc2dcf5b 1694 #endif
ocomeni 105:e5ce023eee93 1695 nsapi_error_t error = https_request->get_error();
ocomeni 105:e5ce023eee93 1696 if(error < 0)
ocomeni 105:e5ce023eee93 1697 {
ocomeni 87:99b37d26ff2a 1698 char buf[100];
ocomeni 105:e5ce023eee93 1699 mbedtls_strerror(error, buf, 100);
ocomeni 105:e5ce023eee93 1700 printf("HttpsRequest failed (error code %s)\n", buf);
ocomeni 87:99b37d26ff2a 1701 delete https_request; // free the memory
ocomeni 96:f5ed273881af 1702 https_request = NULL;
ocomeni 88:7ffa053be662 1703 https_connection_active = false; // reset true whenever connection fails
ocomeni 98:65c2333a38b6 1704 socket->close();
ocomeni 88:7ffa053be662 1705 delete socket;
ocomeni 96:f5ed273881af 1706 socket = NULL;
ocomeni 90:ed0267eca7b5 1707 free_DataMsg();
ocomeni 105:e5ce023eee93 1708 http_result = HTTP_REQUEST_FAILED;
ocomeni 98:65c2333a38b6 1709 return false;
ocomeni 87:99b37d26ff2a 1710 }
ocomeni 88:7ffa053be662 1711 https_connection_active = true; // set true whenever connection succeeds
ocomeni 103:7b566b522427 1712 dbg_printf(LOG, "\n----- HTTPS POST response -----\r\n");
ocomeni 110:c722dda4f2ff 1713 }
ocomeni 110:c722dda4f2ff 1714 if(http_response_hdr_sent == false)
ocomeni 110:c722dda4f2ff 1715 {
ocomeni 110:c722dda4f2ff 1716 socket->close();
ocomeni 110:c722dda4f2ff 1717 delete socket;
ocomeni 110:c722dda4f2ff 1718 https_connection_active = false;
ocomeni 110:c722dda4f2ff 1719 #ifdef SEND_DEBUG_MESSAGES
ocomeni 110:c722dda4f2ff 1720 responseString = (char *) malloc(100);
ocomeni 110:c722dda4f2ff 1721 sprintf(responseString, "\r\n[WIFI-MAN] NO RESPONSE RECEIVED:: CLOSING CURRENT TLS CONNECTION.\r\n");
ocomeni 110:c722dda4f2ff 1722 sendDebugMessage();
ocomeni 110:c722dda4f2ff 1723 #endif
ocomeni 110:c722dda4f2ff 1724 //return_response(http_response);
ocomeni 90:ed0267eca7b5 1725 }
ocomeni 96:f5ed273881af 1726 free_DataMsg();
ocomeni 96:f5ed273881af 1727 delete https_request; // free the request & response memory
ocomeni 103:7b566b522427 1728 dbg_printf(LOG, "deleted https_request\r\n");
ocomeni 96:f5ed273881af 1729 https_request = NULL;
ocomeni 104:11e9605093c9 1730 http_result = RESPONSE_OK;
ocomeni 106:e1f04c3d0647 1731 stoptime = Kernel::get_ms_count();
ocomeni 106:e1f04c3d0647 1732 dbg_printf(LOG, "\r\nhttp request to response time : %d ms\r\n", (stoptime - starttime));
ocomeni 98:65c2333a38b6 1733 return true;
ocomeni 79:a2187bbfa407 1734 }
ocomeni 79:a2187bbfa407 1735
ocomeni 79:a2187bbfa407 1736 void WiFiManager::createHttpRequest(http_method method,
ocomeni 79:a2187bbfa407 1737 const char* url,
ocomeni 79:a2187bbfa407 1738 Callback<void(const char *at, uint32_t length)> body_callback)
ocomeni 79:a2187bbfa407 1739 {
ocomeni 84:7c7add00f4bf 1740 http_request = new HttpRequest(network,
ocomeni 84:7c7add00f4bf 1741 method, url, body_callback);;
ocomeni 79:a2187bbfa407 1742 }
ocomeni 79:a2187bbfa407 1743
ocomeni 79:a2187bbfa407 1744 void WiFiManager::setHttpHeader(string key, string value)
ocomeni 79:a2187bbfa407 1745 {
ocomeni 79:a2187bbfa407 1746 http_request->set_header(key, value);
ocomeni 79:a2187bbfa407 1747 }
ocomeni 79:a2187bbfa407 1748
ocomeni 79:a2187bbfa407 1749 void WiFiManager::setHttpsHeader(string key, string value)
ocomeni 79:a2187bbfa407 1750 {
ocomeni 79:a2187bbfa407 1751 https_request->set_header(key, value);
ocomeni 79:a2187bbfa407 1752 }
ocomeni 79:a2187bbfa407 1753
ocomeni 129:590bdc2dcf5b 1754 void WiFiManager::printHttpRequestLogBuffer()
ocomeni 129:590bdc2dcf5b 1755 {
ocomeni 129:590bdc2dcf5b 1756
ocomeni 129:590bdc2dcf5b 1757 // after the request is done:
ocomeni 129:590bdc2dcf5b 1758 #ifdef PRINT_BUFFER_IN_HEX
ocomeni 129:590bdc2dcf5b 1759 dbg_printf(LOG, "\n----- Request buffer Hex-----\n");
ocomeni 129:590bdc2dcf5b 1760 for (size_t ix = 0; ix < https_request->get_request_log_buffer_length(); ix++) {
ocomeni 129:590bdc2dcf5b 1761 if(ix%16 == 0)dbg_printf(LOG, "\n[%04x] ", ix);
ocomeni 129:590bdc2dcf5b 1762 dbg_printf(LOG, "%02x ", http_req_log_buf[ix]);
ocomeni 129:590bdc2dcf5b 1763 }
ocomeni 129:590bdc2dcf5b 1764 #endif
ocomeni 129:590bdc2dcf5b 1765 dbg_printf(LOG, "\n[ request size = %d bytes]\r\n", https_request->get_request_log_buffer_length());
ocomeni 129:590bdc2dcf5b 1766 dbg_printf(LOG, "----- Request buffer string -----\r\n%s ", (char *)http_req_log_buf);
ocomeni 129:590bdc2dcf5b 1767 //wait_ms(100);
ocomeni 129:590bdc2dcf5b 1768 free(http_req_log_buf);
ocomeni 129:590bdc2dcf5b 1769 }
ocomeni 79:a2187bbfa407 1770 void WiFiManager::sendHttpsRequest(const char * body, int bodyLen)
ocomeni 78:07bb86e3ce14 1771 {
ocomeni 78:07bb86e3ce14 1772 }
ocomeni 79:a2187bbfa407 1773
ocomeni 79:a2187bbfa407 1774 void WiFiManager::sendHttpRequest(const char * body, int bodyLen)
ocomeni 78:07bb86e3ce14 1775 {
ocomeni 78:07bb86e3ce14 1776 }
ocomeni 79:a2187bbfa407 1777