u32 MX_FirmwareUpdateFinish(u32 u32TotalLen) { #if 1 mico_logic_partition_t* part; int len; OSStatus err = kNoErr; uint32_t update_data_offset = 0x0; CRC16_Context crc_context; u32 total_len = u32TotalLen; CRC16_Init( &crc_context ); mico_logic_partition_t *para_partition_info; para_partition_info = MicoFlashGetInfo(MICO_PARTITION_OTA_TEMP); memset(&(context->flashContentInRam.bootTable), 0, sizeof(boot_table_t)); context->flashContentInRam.bootTable.length = u32TotalLen; context->flashContentInRam.bootTable.start_address = para_partition_info->partition_start_addr; context->flashContentInRam.bootTable.type = 'A'; context->flashContentInRam.bootTable.upgrade_type = 'U'; while(total_len > 0){ if( SizePerRW < total_len ){ len = SizePerRW; } else { len = total_len; } err = MicoFlashRead( MICO_PARTITION_OTA_TEMP, &update_data_offset, data , len); total_len -= len; CRC16_Update( &crc_context, data, len ); } CRC16_Final( &crc_context, &context->flashContentInRam.bootTable.crc ); MICOUpdateConfiguration(context); return ZC_RET_OK; #endif }
USED void PlatformEasyLinkButtonClickedCallback(void) { mico_log_trace(); bool needsUpdate = false; mico_log("PlatformEasyLinkButtonClickedCallback"); if(context->flashContentInRam.micoSystemConfig.easyLinkByPass != EASYLINK_BYPASS_NO){ context->flashContentInRam.micoSystemConfig.easyLinkByPass = EASYLINK_BYPASS_NO; needsUpdate = true; } if(context->flashContentInRam.micoSystemConfig.configured == allConfigured){ context->flashContentInRam.micoSystemConfig.configured = wLanUnConfigured; needsUpdate = true; } if(needsUpdate == true) MICOUpdateConfiguration(context); context->micoStatus.sys_state = eState_Software_Reset; require(context->micoStatus.sys_state_change_sem, exit); mico_rtos_set_semaphore(&context->micoStatus.sys_state_change_sem); exit: return; }
void RptConfigmodeRslt(network_InitTypeDef_st *nwkpara) { if(nwkpara == NULL) { printf("open easy link\n"); //OpenEasylink(60*5); context->micoStatus.sys_state = eState_Software_Reset; mico_rtos_set_semaphore(&context->micoStatus.sys_state_change_sem); } else { printf("recv config\n"); memcpy(context->flashContentInRam.micoSystemConfig.ssid, nwkpara->wifi_ssid, maxSsidLen); memset(context->flashContentInRam.micoSystemConfig.bssid, 0x0, 6); memcpy(context->flashContentInRam.micoSystemConfig.user_key, nwkpara->wifi_key, maxKeyLen); context->flashContentInRam.micoSystemConfig.user_keyLength = strlen(nwkpara->wifi_key); context->flashContentInRam.micoSystemConfig.configured = allConfigured; /*Clear fastlink record*/ MICOUpdateConfiguration(context); #if (MICO_CONFIG_MODE == CONFIG_MODE_EASYLINK) || (MICO_CONFIG_MODE == CONFIG_MODE_EASYLINK_WITH_SOFTAP) context->micoStatus.sys_state = eState_Software_Reset; mico_rtos_set_semaphore(&context->micoStatus.sys_state_change_sem); #endif } }
OSStatus MVDCloudInterfaceResetCloudDevInfo(mico_Context_t* const inContext, MVDResetRequestData_t devResetRequestData) { OSStatus err = kUnknownErr; // login_id/dev_passwd ok ? if((0 != strncmp(inContext->flashContentInRam.appConfig.virtualDevConfig.loginId, devResetRequestData.loginId, strlen(inContext->flashContentInRam.appConfig.virtualDevConfig.loginId))) || (0 != strncmp(inContext->flashContentInRam.appConfig.virtualDevConfig.devPasswd, devResetRequestData.devPasswd, strlen(inContext->flashContentInRam.appConfig.virtualDevConfig.devPasswd)))) { // devPass err cloud_if_log("ERROR: MVDCloudInterfaceResetCloudDevInfo: loginId/devPasswd mismatch!"); return kMismatchErr; } cloud_if_log("MVDCloudInterfaceResetCloudDevInfo: loginId/devPasswd ok!"); err = EasyCloudDeviceReset(&easyCloudContext); require_noerr_action( err, exit, cloud_if_log("ERROR: EasyCloudDeviceReset failed! err=%d", err) ); mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); inContext->flashContentInRam.appConfig.virtualDevConfig.isActivated = false; // need to reActivate sprintf(inContext->flashContentInRam.appConfig.virtualDevConfig.deviceId, DEFAULT_DEVICE_ID); sprintf(inContext->flashContentInRam.appConfig.virtualDevConfig.masterDeviceKey, DEFAULT_DEVICE_KEY); sprintf(inContext->flashContentInRam.appConfig.virtualDevConfig.loginId, DEFAULT_LOGIN_ID); sprintf(inContext->flashContentInRam.appConfig.virtualDevConfig.devPasswd, DEFAULT_DEV_PASSWD); inContext->appStatus.virtualDevStatus.isCloudConnected = false; MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); exit: return err; }
void _sys_state_thread(void *arg) { UNUSED_PARAMETER( arg ); /*System status changed*/ while(mico_rtos_get_semaphore(&context->micoStatus.sys_state_change_sem, MICO_WAIT_FOREVER)==kNoErr){ if(needsUpdate == true) MICOUpdateConfiguration(context); switch(context->micoStatus.sys_state){ case eState_Normal: break; case eState_Software_Reset: sendNotifySYSWillPowerOff(); mico_thread_msleep(500); MicoSystemReboot(); break; case eState_Wlan_Powerdown: sendNotifySYSWillPowerOff(); mico_thread_msleep(500); micoWlanPowerOff(); break; case eState_Standby: sendNotifySYSWillPowerOff(); mico_thread_msleep(200); micoWlanPowerOff(); MicoSystemStandBy(MICO_WAIT_FOREVER); break; default: break; } } }
OSStatus _FTCRespondInComingMessage(int fd, HTTPHeader_t* inHeader, mico_Context_t * const inContext) { OSStatus err = kUnknownErr; const char * value; size_t valueSize; easylink_log_trace(); switch(inHeader->statusCode){ case kStatusAccept: easylink_log("Easylink server accepted!"); err = kNoErr; goto exit; break; case kStatusOK: easylink_log("Easylink server respond status OK!"); err = HTTPGetHeaderField( inHeader->buf, inHeader->len, "Content-Type", NULL, NULL, &value, &valueSize, NULL ); require_noerr(err, exit); if( strnicmpx( value, valueSize, kMIMEType_JSON ) == 0 ){ easylink_log("Receive JSON config data!"); err = ConfigIncommingJsonMessage( inHeader->extraDataPtr, inContext); SocketClose(&fd); inContext->micoStatus.sys_state = eState_Software_Reset; require(inContext->micoStatus.sys_state_change_sem, exit); mico_rtos_set_semaphore(&inContext->micoStatus.sys_state_change_sem); }else if(strnicmpx( value, valueSize, kMIMEType_MXCHIP_OTA ) == 0){ easylink_log("Receive OTA data!"); mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); memset(&inContext->flashContentInRam.bootTable, 0, sizeof(boot_table_t)); inContext->flashContentInRam.bootTable.length = inHeader->contentLength; inContext->flashContentInRam.bootTable.start_address = UPDATE_START_ADDRESS; inContext->flashContentInRam.bootTable.type = 'A'; inContext->flashContentInRam.bootTable.upgrade_type = 'U'; inContext->flashContentInRam.micoSystemConfig.easyLinkEnable = false; MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); SocketClose(&fd); inContext->micoStatus.sys_state = eState_Software_Reset; require(inContext->micoStatus.sys_state_change_sem, exit); mico_rtos_set_semaphore(&inContext->micoStatus.sys_state_change_sem); }else{ return kUnsupportedDataErr; } err = kNoErr; goto exit; break; default: goto exit; } exit: return err; }
void PlatformEasyLinkButtonClickedCallback(void) { mico_log_trace(); if(context->flashContentInRam.micoSystemConfig.configured == allConfigured){ context->flashContentInRam.micoSystemConfig.configured = wLanUnConfigured; MICOUpdateConfiguration(context); } context->micoStatus.sys_state = eState_Software_Reset; require(context->micoStatus.sys_state_change_sem, exit); mico_rtos_set_semaphore(&context->micoStatus.sys_state_change_sem); exit: return; }
OSStatus ConfigIncommingJsonMessage( const char *input, mico_Context_t * const inContext ) { OSStatus err = kNoErr; json_object *new_obj; config_delegate_log_trace(); new_obj = json_tokener_parse(input); require_action(new_obj, exit, err = kUnknownErr); config_delegate_log("Recv config object=%s", json_object_to_json_string(new_obj)); mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); json_object_object_foreach(new_obj, key, val) { if(!strcmp(key, "Device Name")){ strncpy(inContext->flashContentInRam.micoSystemConfig.name, json_object_get_string(val), maxNameLen); }else if(!strcmp(key, "RF power save")){ inContext->flashContentInRam.micoSystemConfig.rfPowerSaveEnable = json_object_get_boolean(val); }else if(!strcmp(key, "MCU power save")){ inContext->flashContentInRam.micoSystemConfig.mcuPowerSaveEnable = json_object_get_boolean(val); }else if(!strcmp(key, "Bonjour")){ inContext->flashContentInRam.micoSystemConfig.bonjourEnable = json_object_get_boolean(val); }else if(!strcmp(key, "Wi-Fi")){ strncpy(inContext->flashContentInRam.micoSystemConfig.ssid, json_object_get_string(val), maxSsidLen); inContext->flashContentInRam.micoSystemConfig.channel = 0; memset(inContext->flashContentInRam.micoSystemConfig.bssid, 0x0, 6); inContext->flashContentInRam.micoSystemConfig.security = SECURITY_TYPE_AUTO; memcpy(inContext->flashContentInRam.micoSystemConfig.key, inContext->flashContentInRam.micoSystemConfig.user_key, maxKeyLen); inContext->flashContentInRam.micoSystemConfig.keyLength = inContext->flashContentInRam.micoSystemConfig.user_keyLength; }else if(!strcmp(key, "Password")){ inContext->flashContentInRam.micoSystemConfig.security = SECURITY_TYPE_AUTO; strncpy(inContext->flashContentInRam.micoSystemConfig.key, json_object_get_string(val), maxKeyLen); strncpy(inContext->flashContentInRam.micoSystemConfig.user_key, json_object_get_string(val), maxKeyLen); inContext->flashContentInRam.micoSystemConfig.keyLength = strlen(inContext->flashContentInRam.micoSystemConfig.key); inContext->flashContentInRam.micoSystemConfig.user_keyLength = strlen(inContext->flashContentInRam.micoSystemConfig.key); }else if(!strcmp(key, "Connect SPP Server")){ inContext->flashContentInRam.appConfig.remoteServerEnable = json_object_get_boolean(val); }else if(!strcmp(key, "SPP Server")){ strncpy(inContext->flashContentInRam.appConfig.remoteServerDomain, json_object_get_string(val), 64); }else if(!strcmp(key, "SPP Server Port")){ inContext->flashContentInRam.appConfig.remoteServerPort = json_object_get_int(val); }else if(!strcmp(key, "Baurdrate")){ inContext->flashContentInRam.appConfig.USART_BaudRate = json_object_get_int(val); } } json_object_put(new_obj); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); inContext->flashContentInRam.micoSystemConfig.configured = allConfigured; MICOUpdateConfiguration(inContext); exit: return err; }
void fogcloud_ota_thread(void *arg) { OSStatus err = kUnknownErr; MVDOTARequestData_t devOTARequestData; mico_Context_t *inContext = (mico_Context_t *)arg; fogcloud_log("OTA: check new firmware ..."); memset((void*)&devOTARequestData, 0, sizeof(devOTARequestData)); strncpy(devOTARequestData.loginId, inContext->flashContentInRam.appConfig.fogcloudConfig.loginId, MAX_SIZE_LOGIN_ID); strncpy(devOTARequestData.devPasswd, inContext->flashContentInRam.appConfig.fogcloudConfig.devPasswd, MAX_SIZE_DEV_PASSWD); strncpy(devOTARequestData.user_token, inContext->flashContentInRam.appConfig.fogcloudConfig.userToken, MAX_SIZE_USER_TOKEN); err = fogCloudDevFirmwareUpdate(inContext, devOTARequestData); if(kNoErr == err){ if(inContext->appStatus.fogcloudStatus.RecvRomFileSize > 0){ fogcloud_log("OTA: firmware download success, system will reboot && update..."); // set bootloader to reboot && update app firmware mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); memset(&inContext->flashContentInRam.bootTable, 0, sizeof(boot_table_t)); inContext->flashContentInRam.bootTable.length = inContext->appStatus.fogcloudStatus.RecvRomFileSize; inContext->flashContentInRam.bootTable.start_address = UPDATE_START_ADDRESS; inContext->flashContentInRam.bootTable.type = 'A'; inContext->flashContentInRam.bootTable.upgrade_type = 'U'; if(inContext->flashContentInRam.micoSystemConfig.configured != allConfigured) inContext->flashContentInRam.micoSystemConfig.easyLinkByPass = EASYLINK_SOFT_AP_BYPASS; MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); inContext->micoStatus.sys_state = eState_Software_Reset; if(inContext->micoStatus.sys_state_change_sem != NULL ){ mico_rtos_set_semaphore(&inContext->micoStatus.sys_state_change_sem); } mico_thread_sleep(MICO_WAIT_FOREVER); } else{ fogcloud_log("OTA: firmware is up-to-date!"); } } else{ fogcloud_log("OTA: firmware download failed, err=%d", err); } fogcloud_log("fogcloud_ota_thread exit err=%d.", err); mico_rtos_delete_thread(NULL); return; }
void micoNotify_WiFIParaChangedHandler(apinfo_adv_t *ap_info, char *key, int key_len, mico_Context_t * const inContext) { mico_log_trace(); bool _needsUpdate = false; require(inContext, exit); mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); if(strncmp(inContext->flashContentInRam.micoSystemConfig.ssid, ap_info->ssid, maxSsidLen)!=0){ strncpy(inContext->flashContentInRam.micoSystemConfig.ssid, ap_info->ssid, maxSsidLen); _needsUpdate = true; } if(memcmp(inContext->flashContentInRam.micoSystemConfig.bssid, ap_info->bssid, 6)!=0){ memcpy(inContext->flashContentInRam.micoSystemConfig.bssid, ap_info->bssid, 6); _needsUpdate = true; } if(inContext->flashContentInRam.micoSystemConfig.channel != ap_info->channel){ inContext->flashContentInRam.micoSystemConfig.channel = ap_info->channel; _needsUpdate = true; } if(inContext->flashContentInRam.micoSystemConfig.security != ap_info->security){ inContext->flashContentInRam.micoSystemConfig.security = ap_info->security; _needsUpdate = true; } if(memcmp(inContext->flashContentInRam.micoSystemConfig.key, key, maxKeyLen)!=0){ memcpy(inContext->flashContentInRam.micoSystemConfig.key, key, maxKeyLen); _needsUpdate = true; } if(inContext->flashContentInRam.micoSystemConfig.keyLength != key_len){ inContext->flashContentInRam.micoSystemConfig.keyLength = key_len; _needsUpdate = true; } if(_needsUpdate== true) MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); exit: return; }
void EasyLinkNotify_EasyLinkCompleteHandler(network_InitTypeDef_st *nwkpara, mico_Context_t * const inContext) { OSStatus err; easylink_log_trace(); easylink_log("EasyLink return @ %d", mico_get_time()); require_action(inContext, exit, err = kParamErr); require_action(nwkpara, exit, err = kTimeoutErr); mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); memcpy(inContext->flashContentInRam.micoSystemConfig.ssid, nwkpara->wifi_ssid, maxSsidLen); memcpy(inContext->flashContentInRam.micoSystemConfig.user_key, nwkpara->wifi_key, maxKeyLen); inContext->flashContentInRam.micoSystemConfig.user_keyLength = strlen(nwkpara->wifi_key); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); easylink_log("Get SSID: %s, Key: %s", inContext->flashContentInRam.micoSystemConfig.ssid, inContext->flashContentInRam.micoSystemConfig.user_key); return; /*EasyLink is not start*/ exit: easylink_log("ERROR, err: %d", err); #if defined (CONFIG_MODE_EASYLINK_WITH_SOFTAP) EasylinkFailed = true; mico_rtos_set_semaphore(&inContext->micoStatus.easylink_sem); #else ConfigWillStop(inContext); /*so roll back to previous settings (if it has) and reboot*/ mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); if(inContext->flashContentInRam.micoSystemConfig.configured != unConfigured){ inContext->flashContentInRam.micoSystemConfig.configured = allConfigured; MICOUpdateConfiguration(inContext); PlatformSoftReboot(); } mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); /*module should powd down in default setting*/ wifi_power_down(); mico_stop_timer(&_Led_EL_timer); Platform_LED_SYS_Set_Status(OFF); #endif return; }
void MVDDevCloudInfoResetThread(void *arg) { OSStatus err = kUnknownErr; mico_Context_t *inContext = (mico_Context_t *)arg; // stop EasyCloud service first err = MVDCloudInterfaceStop(inContext); require_noerr_action( err, exit, mvd_log("ERROR: stop EasyCloud service failed!") ); // cloud reset request MVDDevInterfaceSend(DEFAULT_MVD_RESET_CLOUD_INFO_START_MSG_2MCU, strlen(DEFAULT_MVD_RESET_CLOUD_INFO_START_MSG_2MCU)); err = easycloud_reset_cloud_info(inContext); if(kNoErr == err){ inContext->appStatus.virtualDevStatus.isCloudConnected = false; mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); inContext->flashContentInRam.appConfig.virtualDevConfig.isActivated = false; MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); //mvd_log("[MVD]MVDDevCloudInfoResetThread: cloud reset success!"); MVDDevInterfaceSend(DEFAULT_MVD_RESET_CLOUD_INFO_OK_MSG_2MCU, strlen(DEFAULT_MVD_RESET_CLOUD_INFO_OK_MSG_2MCU)); // send ok semaphore mico_rtos_set_semaphore(&_reset_cloud_info_sem); } exit: if(kNoErr != err){ mvd_log("[MVD]MVDDevCloudInfoResetThread EXIT: err=%d",err); MVDDevInterfaceSend(DEFAULT_MVD_RESET_CLOUD_INFO_FAILED_MSG_2MCU, strlen(DEFAULT_MVD_RESET_CLOUD_INFO_FAILED_MSG_2MCU)); } mico_rtos_delete_thread(NULL); return; }
void EasyLinkNotify_EasyLinkCompleteHandler(network_InitTypeDef_st *nwkpara, mico_Context_t * const inContext) { OSStatus err; easylink_log_trace(); easylink_log("EasyLink return"); require_action(inContext, exit, err = kParamErr); require_action(nwkpara, exit, err = kTimeoutErr); mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); memcpy(inContext->flashContentInRam.micoSystemConfig.ssid, nwkpara->wifi_ssid, maxSsidLen); memset(inContext->flashContentInRam.micoSystemConfig.bssid, 0x0, 6); memcpy(inContext->flashContentInRam.micoSystemConfig.user_key, nwkpara->wifi_key, maxKeyLen); inContext->flashContentInRam.micoSystemConfig.user_keyLength = strlen(nwkpara->wifi_key); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); easylink_log("Get SSID: %s, Key: %s", inContext->flashContentInRam.micoSystemConfig.ssid, inContext->flashContentInRam.micoSystemConfig.user_key); return; /*EasyLink timeout or error*/ exit: easylink_log("ERROR, err: %d", err); #if ( MICO_CONFIG_MODE == CONFIG_MODE_EASYLINK_WITH_SOFTAP) EasylinkFailed = true; mico_rtos_set_semaphore(&easylink_sem); #else ConfigWillStop(inContext); /*so roll back to previous settings (if it has) and reboot*/ mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); if(inContext->flashContentInRam.micoSystemConfig.configured != unConfigured){ inContext->flashContentInRam.micoSystemConfig.configured = allConfigured; MICOUpdateConfiguration(inContext); MicoSystemReboot(); } mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); /*module should powd down in default setting*/ micoWlanPowerOff(); #endif return; }
void uartRecvMfg_thread(void *inContext) { mico_Context_t *Context = inContext; int recvlen; uint8_t *inDataBuffer; inDataBuffer = malloc(500); require(inDataBuffer, exit); while(1) { recvlen = _uart_get_one_packet(inDataBuffer, 500); if (recvlen <= 0) continue; else{ /* if(......) Should valid the UART input */ Context->flashContentInRam.micoSystemConfig.configured = unConfigured; MICOUpdateConfiguration ( Context ); } } exit: if(inDataBuffer) free(inDataBuffer); }
void easylink_thread(void *inContext) { OSStatus err = kNoErr; mico_Context_t *Context = inContext; fd_set readfds; int reConnCount = 0; int clientFdIsSet; easylink_log_trace(); require_action(easylink_sem, threadexit, err = kNotPreparedErr); if(Context->flashContentInRam.micoSystemConfig.easyLinkByPass == EASYLINK_BYPASS){ Context->flashContentInRam.micoSystemConfig.easyLinkByPass = EASYLINK_BYPASS_NO; MICOUpdateConfiguration(Context); _easylinkConnectWiFi_fast(Context); }else if(Context->flashContentInRam.micoSystemConfig.easyLinkByPass == EASYLINK_SOFT_AP_BYPASS){ ConfigWillStop( Context ); _easylinkStartSoftAp(Context); mico_rtos_delete_thread(NULL); return; }else{ #ifdef EasyLink_Plus easylink_log("Start easylink plus mode"); micoWlanStartEasyLinkPlus(EasyLink_TimeOut/1000); #else easylink_log("Start easylink V2"); micoWlanStartEasyLink(EasyLink_TimeOut/1000); #endif mico_rtos_get_semaphore(&easylink_sem, MICO_WAIT_FOREVER); if(EasylinkFailed == false) _easylinkConnectWiFi(Context); else{ msleep(20); _cleanEasyLinkResource( Context ); ConfigWillStop( Context ); _easylinkStartSoftAp(Context); mico_rtos_delete_thread(NULL); return; } } err = mico_rtos_get_semaphore(&easylink_sem, EasyLink_ConnectWlan_Timeout); require_noerr(err, reboot); httpHeader = HTTPHeaderCreate(); require_action( httpHeader, threadexit, err = kNoMemoryErr ); HTTPHeaderClear( httpHeader ); while(1){ if(easylinkClient_fd == -1){ err = _connectFTCServer(inContext, &easylinkClient_fd); require_noerr(err, Reconn); }else{ FD_ZERO(&readfds); FD_SET(easylinkClient_fd, &readfds); if(httpHeader->len == 0){ err = select(1, &readfds, NULL, NULL, NULL); require(err>=1, threadexit); clientFdIsSet = FD_ISSET(easylinkClient_fd, &readfds); } if(clientFdIsSet||httpHeader->len){ err = SocketReadHTTPHeader( easylinkClient_fd, httpHeader ); switch ( err ) { case kNoErr: // Read the rest of the HTTP body if necessary do{ err = SocketReadHTTPBody( easylinkClient_fd, httpHeader ); require_noerr(err, Reconn); PrintHTTPHeader(httpHeader); // Call the HTTPServer owner back with the acquired HTTP header err = _FTCRespondInComingMessage( easylinkClient_fd, httpHeader, Context ); require_noerr( err, Reconn ); if(httpHeader->contentLength == 0) break; } while( httpHeader->chunkedData == true || httpHeader->dataEndedbyClose == true); // Reuse HTTPHeader HTTPHeaderClear( httpHeader ); break; case EWOULDBLOCK: // NO-OP, keep reading break; case kNoSpaceErr: easylink_log("ERROR: Cannot fit HTTPHeader."); goto Reconn; case kConnectionErr: // NOTE: kConnectionErr from SocketReadHTTPHeader means it's closed easylink_log("ERROR: Connection closed."); /*Roll back to previous settings (if it has) and reboot*/ if(Context->flashContentInRam.micoSystemConfig.configured == wLanUnConfigured ){ Context->flashContentInRam.micoSystemConfig.configured = allConfigured; MICOUpdateConfiguration( Context ); MicoSystemReboot(); }else{ micoWlanPowerOff(); msleep(20); } goto threadexit; default: easylink_log("ERROR: HTTP Header parse internal error: %d", err); goto Reconn; } } } continue; Reconn: HTTPHeaderClear( httpHeader ); SocketClose(&easylinkClient_fd); easylinkClient_fd = -1; require(reConnCount < 6, reboot); reConnCount++; sleep(5); } /*Module is ignored by FTC server, */ threadexit: _cleanEasyLinkResource( Context ); ConfigWillStop( Context ); mico_rtos_delete_thread( NULL ); return; /*SSID or Password is not correct, module cannot connect to wlan, so reboot and enter EasyLink again*/ reboot: MicoSystemReboot(); return; }
int application_start(void) { OSStatus err = kNoErr; IPStatusTypedef para; struct tm currentTime; mico_rtc_time_t time; char wifi_ver[64] = {0}; mico_log_trace(); /*Read current configurations*/ context = ( mico_Context_t *)malloc(sizeof(mico_Context_t) ); require_action( context, exit, err = kNoMemoryErr ); memset(context, 0x0, sizeof(mico_Context_t)); mico_rtos_init_mutex(&context->flashContentInRam_mutex); mico_rtos_init_semaphore(&context->micoStatus.sys_state_change_sem, 1); MICOReadConfiguration( context ); err = MICOInitNotificationCenter ( context ); err = MICOAddNotification( mico_notify_READ_APP_INFO, (void *)micoNotify_ReadAppInfoHandler ); require_noerr( err, exit ); err = MICOAddNotification( mico_notify_WIFI_CONNECT_FAILED, (void *)micoNotify_ConnectFailedHandler ); require_noerr( err, exit ); err = MICOAddNotification( mico_notify_WIFI_Fatal_ERROR, (void *)micoNotify_WlanFatalErrHandler ); require_noerr( err, exit ); err = MICOAddNotification( mico_notify_Stack_Overflow_ERROR, (void *)micoNotify_StackOverflowErrHandler ); require_noerr( err, exit ); /*wlan driver and tcpip init*/ mico_log( "MiCO starting..." ); MicoInit(); #ifdef MICO_CLI_ENABLE MicoCliInit(); #endif MicoSysLed(true); mico_log("Free memory %d bytes", MicoGetMemoryInfo()->free_memory); micoWlanGetIPStatus(¶, Station); formatMACAddr(context->micoStatus.mac, (char *)¶.mac); MicoGetRfVer(wifi_ver, sizeof(wifi_ver)); mico_log("%s mxchipWNet library version: %s", APP_INFO, MicoGetVer()); mico_log("Wi-Fi driver version %s, mac %s", wifi_ver, context->micoStatus.mac); /*Start system monotor thread*/ err = MICOStartSystemMonitor(context); require_noerr_action( err, exit, mico_log("ERROR: Unable to start the system monitor.") ); err = MICORegisterSystemMonitor(&mico_monitor, APPLICATION_WATCHDOG_TIMEOUT_SECONDS*1000); require_noerr( err, exit ); mico_init_timer(&_watchdog_reload_timer,APPLICATION_WATCHDOG_TIMEOUT_SECONDS*1000/2, _watchdog_reload_timer_handler, NULL); mico_start_timer(&_watchdog_reload_timer); /* Enter test mode, call a build-in test function amd output on MFG UART */ if(MicoShouldEnterMFGMode()==true){ mico_log( "Enter MFG mode by MFG button" ); mico_mfg_test(context); } /*Read current time from RTC.*/ if( MicoRtcGetTime(&time) == kNoErr ){ currentTime.tm_sec = time.sec; currentTime.tm_min = time.min; currentTime.tm_hour = time.hr; currentTime.tm_mday = time.date; currentTime.tm_wday = time.weekday; currentTime.tm_mon = time.month - 1; currentTime.tm_year = time.year + 100; mico_log("Current Time: %s",asctime(¤tTime)); }else mico_log("RTC function unsupported"); /* Regisist notifications */ err = MICOAddNotification( mico_notify_WIFI_STATUS_CHANGED, (void *)micoNotify_WifiStatusHandler ); require_noerr( err, exit ); if( context->flashContentInRam.micoSystemConfig.configured == wLanUnConfigured || context->flashContentInRam.micoSystemConfig.configured == unConfigured){ mico_log("Empty configuration. Starting configuration mode..."); #if (MICO_CONFIG_MODE == CONFIG_MODE_EASYLINK) || (MICO_CONFIG_MODE == CONFIG_MODE_EASYLINK_WITH_SOFTAP) err = startEasyLink( context ); require_noerr( err, exit ); #elif (MICO_CONFIG_MODE == CONFIG_MODE_SOFT_AP) err = startEasyLinkSoftAP( context ); require_noerr( err, exit ); #elif (MICO_CONFIG_MODE == CONFIG_MODE_AIRKISS) err = startAirkiss( context ); require_noerr( err, exit ); #elif (MICO_CONFIG_MODE == CONFIG_MODE_WPS) || MICO_CONFIG_MODE == defined (CONFIG_MODE_WPS_WITH_SOFTAP) err = startWPS( context ); require_noerr( err, exit ); #elif ( MICO_CONFIG_MODE == CONFIG_MODE_WAC) WACPlatformParameters_t* WAC_Params = NULL; WAC_Params = calloc(1, sizeof(WACPlatformParameters_t)); require(WAC_Params, exit); str2hex((unsigned char *)para.mac, WAC_Params->macAddress, 6); WAC_Params->isUnconfigured = 1; WAC_Params->supportsAirPlay = 0; WAC_Params->supportsAirPrint = 0; WAC_Params->supports2_4GHzWiFi = 1; WAC_Params->supports5GHzWiFi = 0; WAC_Params->supportsWakeOnWireless = 0; WAC_Params->firmwareRevision = FIRMWARE_REVISION; WAC_Params->hardwareRevision = HARDWARE_REVISION; WAC_Params->serialNumber = SERIAL_NUMBER; WAC_Params->name = context->flashContentInRam.micoSystemConfig.name; WAC_Params->model = MODEL; WAC_Params->manufacturer = MANUFACTURER; WAC_Params->numEAProtocols = 1; WAC_Params->eaBundleSeedID = BUNDLE_SEED_ID; WAC_Params->eaProtocols = (char **)eaProtocols; err = startMFiWAC( context, WAC_Params, MICO_I2C_CP, 1200); free(WAC_Params); require_noerr( err, exit ); #else #error "Wi-Fi configuration mode is not defined" #endif } #ifdef MFG_MODE_AUTO else if( context->flashContentInRam.micoSystemConfig.configured == mfgConfigured ){ mico_log( "Enter MFG mode automatically" ); mico_mfg_test(context); mico_thread_sleep(MICO_NEVER_TIMEOUT); } #endif else{ mico_log("Available configuration. Starting Wi-Fi connection..."); err = MICOAddNotification( mico_notify_WiFI_PARA_CHANGED, (void *)micoNotify_WiFIParaChangedHandler ); require_noerr( err, exit ); err = MICOAddNotification( mico_notify_DHCP_COMPLETED, (void *)micoNotify_DHCPCompleteHandler ); require_noerr( err, exit ); if(context->flashContentInRam.micoSystemConfig.rfPowerSaveEnable == true){ micoWlanEnablePowerSave(); } if(context->flashContentInRam.micoSystemConfig.mcuPowerSaveEnable == true){ MicoMcuPowerSaveConfig(true); } /*Local configuration server*/ if(context->flashContentInRam.micoSystemConfig.configServerEnable == true){ err = MICOStartConfigServer(context); require_noerr_action( err, exit, mico_log("ERROR: Unable to start the local server thread.") ); } err = MICOStartNTPClient(context); require_noerr_action( err, exit, mico_log("ERROR: Unable to start the NTP client thread.") ); /*Start mico application*/ err = MICOStartApplication( context ); require_noerr( err, exit ); _ConnectToAP( context ); } mico_log("Free memory %d bytes", MicoGetMemoryInfo()->free_memory) ; /*System status changed*/ while(mico_rtos_get_semaphore(&context->micoStatus.sys_state_change_sem, MICO_WAIT_FOREVER)==kNoErr){ if(needsUpdate == true) MICOUpdateConfiguration(context); switch(context->micoStatus.sys_state){ case eState_Normal: break; case eState_Software_Reset: sendNotifySYSWillPowerOff(); mico_thread_msleep(500); MicoSystemReboot(); break; case eState_Wlan_Powerdown: sendNotifySYSWillPowerOff(); mico_thread_msleep(500); micoWlanPowerOff(); break; case eState_Standby: mico_log("Enter standby mode"); sendNotifySYSWillPowerOff(); mico_thread_msleep(200); micoWlanPowerOff(); MicoSystemStandBy(MICO_WAIT_FOREVER); break; default: break; } } require_noerr_action( err, exit, mico_log("Closing main thread with err num: %d.", err) ); exit: mico_rtos_delete_thread(NULL); return kNoErr; }
void easylink_thread(void *inContext) { OSStatus err = kNoErr; mico_Context_t *Context = inContext; fd_set readfds; struct timeval_t t; int reConnCount = 0; easylink_log_trace(); require_action(easylink_sem, threadexit, err = kNotPreparedErr); if(Context->flashContentInRam.micoSystemConfig.easyLinkEnable != false){ OpenEasylink2_withdata(EasyLink_TimeOut); easylink_log("Start easylink"); mico_rtos_get_semaphore(&easylink_sem, MICO_WAIT_FOREVER); if(EasylinkFailed == false) _easylinkConnectWiFi(Context); else{ _easylinkStartSoftAp(Context); mico_rtos_delete_thread(NULL); return; } }else{ mico_rtos_lock_mutex(&Context->flashContentInRam_mutex); Context->flashContentInRam.micoSystemConfig.easyLinkEnable = true; MICOUpdateConfiguration(Context); mico_rtos_unlock_mutex(&Context->flashContentInRam_mutex); _easylinkConnectWiFi_fast(Context); } err = mico_rtos_get_semaphore(&easylink_sem, ConnectFTC_Timeout); require_noerr(err, reboot); httpHeader = HTTPHeaderCreate(); require_action( httpHeader, threadexit, err = kNoMemoryErr ); HTTPHeaderClear( httpHeader ); t.tv_sec = 100; t.tv_usec = 0; while(1){ if(easylinkClient_fd == -1){ err = _connectFTCServer(inContext, &easylinkClient_fd); require_noerr(err, Reconn); }else{ FD_ZERO(&readfds); FD_SET(easylinkClient_fd, &readfds); err = select(1, &readfds, NULL, NULL, &t); if(FD_ISSET(easylinkClient_fd, &readfds)){ err = SocketReadHTTPHeader( easylinkClient_fd, httpHeader ); switch ( err ) { case kNoErr: // Read the rest of the HTTP body if necessary err = SocketReadHTTPBody( easylinkClient_fd, httpHeader ); require_noerr(err, Reconn); PrintHTTPHeader(httpHeader); // Call the HTTPServer owner back with the acquired HTTP header err = _FTCRespondInComingMessage( easylinkClient_fd, httpHeader, Context ); require_noerr( err, Reconn ); // Reuse HTTPHeader HTTPHeaderClear( httpHeader ); break; case EWOULDBLOCK: // NO-OP, keep reading break; case kNoSpaceErr: easylink_log("ERROR: Cannot fit HTTPHeader."); goto Reconn; break; case kConnectionErr: // NOTE: kConnectionErr from SocketReadHTTPHeader means it's closed easylink_log("ERROR: Connection closed."); goto threadexit; //goto Reconn; break; default: easylink_log("ERROR: HTTP Header parse internal error: %d", err); goto Reconn; } } } continue; Reconn: HTTPHeaderClear( httpHeader ); SocketClose(&easylinkClient_fd); easylinkClient_fd = -1; require(reConnCount < 6, threadexit); reConnCount++; sleep(5); } /*Module is ignored by FTC server, */ threadexit: ConfigWillStop( Context ); _cleanEasyLinkResource( Context ); /*Roll back to previous settings (if it has) and reboot*/ mico_rtos_lock_mutex(&Context->flashContentInRam_mutex); if(Context->flashContentInRam.micoSystemConfig.configured != unConfigured){ Context->flashContentInRam.micoSystemConfig.configured = allConfigured; MICOUpdateConfiguration( Context ); PlatformSoftReboot(); } mico_rtos_unlock_mutex(&Context->flashContentInRam_mutex); wifi_power_down(); mico_rtos_delete_thread( NULL ); return; /*SSID or Password is not correct, module cannot connect to wlan, so reboot and enter EasyLink again*/ reboot: ConfigWillStop( Context ); PlatformSoftReboot(); return; }
void MVDMainThread(void *arg) { OSStatus err = kUnknownErr; mico_Context_t *inContext = (mico_Context_t *)arg; bool connected = false; MVDOTARequestData_t devOTARequestData; MVDActivateRequestData_t devDefaultActivateData; mvd_log("MVD main thread start."); while(kNoErr != mico_rtos_get_semaphore(&_wifi_station_on_sem, MICO_WAIT_FOREVER)); /* check reset cloud info */ if((inContext->flashContentInRam.appConfig.virtualDevConfig.needCloudReset) && (inContext->flashContentInRam.appConfig.virtualDevConfig.isActivated)){ // start a thread to reset device info on EasyCloud mico_rtos_init_semaphore(&_reset_cloud_info_sem, 1); mico_rtos_create_thread(NULL, MICO_APPLICATION_PRIORITY, "MVDResetCloudInfo", MVDDevCloudInfoResetThread, 0x800, inContext ); err = mico_rtos_get_semaphore(&_reset_cloud_info_sem, MICO_WAIT_FOREVER); if(kNoErr == err){ mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); inContext->flashContentInRam.appConfig.virtualDevConfig.needCloudReset = false; inContext->flashContentInRam.appConfig.virtualDevConfig.isActivated = false; err = MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); mvd_log("MVD Cloud reset success!"); } else{ mvd_log("MVD Cloud reset failed!"); } mvd_log("Press reset button..."); goto exit; // do nothing after reset, please press reset button. } /* OTA check */ //mvd_log(DEFAULT_MVD_OTA_CHECK_MSG_2MCU); MVDDevInterfaceSend(DEFAULT_MVD_OTA_CHECK_MSG_2MCU, strlen(DEFAULT_MVD_OTA_CHECK_MSG_2MCU)); memset((void*)&devOTARequestData, 0, sizeof(devOTARequestData)); strncpy(devOTARequestData.loginId, inContext->flashContentInRam.appConfig.virtualDevConfig.loginId, MAX_SIZE_LOGIN_ID); strncpy(devOTARequestData.devPasswd, inContext->flashContentInRam.appConfig.virtualDevConfig.devPasswd, MAX_SIZE_DEV_PASSWD); strncpy(devOTARequestData.user_token, inContext->micoStatus.mac, MAX_SIZE_USER_TOKEN); err = MVDCloudInterfaceDevFirmwareUpdate(inContext, devOTARequestData); if(kNoErr == err){ if(inContext->appStatus.virtualDevStatus.RecvRomFileSize > 0){ //mvd_log(DEFAULT_MVD_OTA_UPDATE_MSG_2MCU); MVDDevInterfaceSend(DEFAULT_MVD_OTA_UPDATE_MSG_2MCU, strlen(DEFAULT_MVD_OTA_UPDATE_MSG_2MCU)); // set bootloader to reboot && update app fw memset(&inContext->flashContentInRam.bootTable, 0, sizeof(boot_table_t)); inContext->flashContentInRam.bootTable.length = inContext->appStatus.virtualDevStatus.RecvRomFileSize; inContext->flashContentInRam.bootTable.start_address = UPDATE_START_ADDRESS; inContext->flashContentInRam.bootTable.type = 'A'; inContext->flashContentInRam.bootTable.upgrade_type = 'U'; if(inContext->flashContentInRam.micoSystemConfig.configured != allConfigured) inContext->flashContentInRam.micoSystemConfig.easyLinkByPass = EASYLINK_SOFT_AP_BYPASS; MICOUpdateConfiguration(inContext); inContext->micoStatus.sys_state = eState_Software_Reset; if(inContext->micoStatus.sys_state_change_sem != NULL ); mico_rtos_set_semaphore(&inContext->micoStatus.sys_state_change_sem); mico_thread_sleep(MICO_WAIT_FOREVER); } else{ //mvd_log(DEFAULT_MVD_OTA_UP_TO_DATE_MSG_2MCU); MVDDevInterfaceSend(DEFAULT_MVD_OTA_UP_TO_DATE_MSG_2MCU, strlen(DEFAULT_MVD_OTA_UP_TO_DATE_MSG_2MCU)); } } else{ //mvd_log(DEFAULT_MVD_OTA_DOWNLOAD_FAILED_MSG_2MCU); MVDDevInterfaceSend(DEFAULT_MVD_OTA_DOWNLOAD_FAILED_MSG_2MCU, strlen(DEFAULT_MVD_OTA_DOWNLOAD_FAILED_MSG_2MCU)); } /* activate when wifi on */ while(false == inContext->flashContentInRam.appConfig.virtualDevConfig.isActivated){ // auto activate, using default login_id/dev_pass/user_token //mvd_log(DEFAULT_MVD_DEV_ACTIVATE_START_MSG_2MCU); MVDDevInterfaceSend(DEFAULT_MVD_DEV_ACTIVATE_START_MSG_2MCU, strlen(DEFAULT_MVD_DEV_ACTIVATE_START_MSG_2MCU)); memset((void*)&devDefaultActivateData, 0, sizeof(devDefaultActivateData)); strncpy(devDefaultActivateData.loginId, inContext->flashContentInRam.appConfig.virtualDevConfig.loginId, MAX_SIZE_LOGIN_ID); strncpy(devDefaultActivateData.devPasswd, inContext->flashContentInRam.appConfig.virtualDevConfig.devPasswd, MAX_SIZE_DEV_PASSWD); strncpy(devDefaultActivateData.user_token, inContext->micoStatus.mac, MAX_SIZE_USER_TOKEN); err = MVDCloudInterfaceDevActivate(inContext, devDefaultActivateData); if(kNoErr == err){ //mvd_log("device activate success!"); MVDDevInterfaceSend(DEFAULT_MVD_DEV_ACTIVATE_OK_MSG_2MCU, strlen(DEFAULT_MVD_DEV_ACTIVATE_OK_MSG_2MCU)); } else{ //mvd_log("device activate failed, err = %d, retry in %d s ...", err, 1); MVDDevInterfaceSend(DEFAULT_MVD_DEV_ACTIVATE_FAILED_MSG_2MCU, strlen(DEFAULT_MVD_DEV_ACTIVATE_FAILED_MSG_2MCU)); } mico_thread_sleep(1); } mvd_log("[MVD]device already activated."); /* start EasyCloud service */ err = MVDCloudInterfaceStart(inContext); require_noerr_action(err, exit, mvd_log("ERROR: MVDCloudInterfaceStart failed!") ); /* loop connect status */ while(1) { if(inContext->appStatus.virtualDevStatus.isCloudConnected){ if (!connected){ connected = true; // set LED to blue means cloud connected, data: on/off,H,S,B LedControlMsgHandler("1,240,100,100", strlen("1,240,100,100")); //mvd_log("[MVD]Cloud: connected"); MVDDevInterfaceSend(DEFAULT_MVD_CLOUD_CONNECTED_MSG_2MCU, strlen(DEFAULT_MVD_CLOUD_CONNECTED_MSG_2MCU)); MVDCloudInterfaceSendtoChannel(PUBLISH_TOPIC_CHANNEL_STATUS, DEFAULT_MVD_CLOUD_CONNECTED_MSG_2CLOUD, strlen(DEFAULT_MVD_CLOUD_CONNECTED_MSG_2CLOUD)); } } else{ if (connected){ connected = false; // white means cloud disconnect. LedControlMsgHandler("1,0,0,10", strlen("1,0,0,10")); mvd_log("[MVD]cloud service disconnected!"); //mvd_log("[MVD]Cloud: disconnected"); MVDDevInterfaceSend(DEFAULT_MVD_CLOUD_DISCONNECTED_MSG_2MCU, strlen(DEFAULT_MVD_CLOUD_DISCONNECTED_MSG_2MCU)); } } mico_thread_sleep(1); } exit: mvd_log("[MVD]MVDMainThread exit err=%d.", err); mico_rtos_delete_thread(NULL); return; }
OSStatus fogCloudDevActivate(mico_Context_t* const inContext, MVDActivateRequestData_t devActivateRequestData) { cloud_if_log_trace(); OSStatus err = kUnknownErr; cloud_if_log("fogCloudDevActivate: entry"); cloud_if_log("Device activate..."); // login_id/dev_passwd set(not default value) ? if((0 != strncmp((char*)DEFAULT_LOGIN_ID, inContext->flashContentInRam.appConfig.fogcloudConfig.loginId, strlen((char*)DEFAULT_LOGIN_ID))) || (0 != strncmp((char*)DEFAULT_DEV_PASSWD, inContext->flashContentInRam.appConfig.fogcloudConfig.devPasswd, strlen((char*)DEFAULT_DEV_PASSWD)))) { // login_id/dev_passwd ok ? if((0 != strncmp(inContext->flashContentInRam.appConfig.fogcloudConfig.loginId, devActivateRequestData.loginId, strlen(inContext->flashContentInRam.appConfig.fogcloudConfig.loginId))) || (0 != strncmp(inContext->flashContentInRam.appConfig.fogcloudConfig.devPasswd, devActivateRequestData.devPasswd, strlen(inContext->flashContentInRam.appConfig.fogcloudConfig.devPasswd)))) { // devPass err cloud_if_log("ERROR: fogCloudDevActivate: loginId/devPasswd mismatch!"); return kMismatchErr; } } cloud_if_log("fogCloudDevActivate: loginId/devPasswd ok!"); //ok, set cloud context strncpy(easyCloudContext.service_config_info.loginId, devActivateRequestData.loginId, MAX_SIZE_LOGIN_ID); cloud_if_log("fogCloudDevActivate: loginId: %s", easyCloudContext.service_config_info.loginId); strncpy(easyCloudContext.service_config_info.devPasswd, devActivateRequestData.devPasswd, MAX_SIZE_DEV_PASSWD); cloud_if_log("fogCloudDevActivate: devPasswd: %s", easyCloudContext.service_config_info.devPasswd); strncpy(easyCloudContext.service_config_info.userToken, devActivateRequestData.user_token, MAX_SIZE_USER_TOKEN); cloud_if_log("fogCloudDevActivate: userToken: %s", easyCloudContext.service_config_info.userToken); // activate request cloud_if_log("fogCloudDevActivate: start FogCloudActivate()"); err = FogCloudActivate(&easyCloudContext); cloud_if_log("fogCloudDevActivate: FogCloudActivate() finished"); require_noerr_action(err, exit, cloud_if_log("ERROR: fogCloudDevActivate failed! err=%d", err) ); inContext->appStatus.fogcloudStatus.isActivated = true; cloud_if_log("fogCloudDevActivate: inContext->appStatus.fogcloudStatus.isActivated = true"); // write activate data back to flash mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); inContext->flashContentInRam.appConfig.fogcloudConfig.isActivated = true; strncpy(inContext->flashContentInRam.appConfig.fogcloudConfig.deviceId, easyCloudContext.service_status.deviceId, MAX_SIZE_DEVICE_ID); strncpy(inContext->flashContentInRam.appConfig.fogcloudConfig.masterDeviceKey, easyCloudContext.service_status.masterDeviceKey, MAX_SIZE_DEVICE_KEY); strncpy(inContext->flashContentInRam.appConfig.fogcloudConfig.loginId, easyCloudContext.service_config_info.loginId, MAX_SIZE_LOGIN_ID); strncpy(inContext->flashContentInRam.appConfig.fogcloudConfig.devPasswd, easyCloudContext.service_config_info.devPasswd, MAX_SIZE_DEV_PASSWD); strncpy(inContext->flashContentInRam.appConfig.fogcloudConfig.userToken, easyCloudContext.service_config_info.userToken, MAX_SIZE_USER_TOKEN); err = MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); require_noerr_action(err, exit, cloud_if_log("ERROR: activate write flash failed! err=%d", err) ); return kNoErr; exit: return err; }
void fogcloud_main_thread(void *arg) { OSStatus err = kUnknownErr; mico_Context_t *inContext = (mico_Context_t *)arg; MVDResetRequestData_t devResetRequestData; #ifdef ENABLE_FOGCLOUD_AUTO_ACTIVATE MVDActivateRequestData_t devDefaultActivateData; #endif /* wait for station on */ while(!inContext->appStatus.isWifiConnected){ mico_thread_msleep(500); } //--- create msg recv queue, NOTE: just push msg pionter into queue, so msg memory must be freed after used. if(NULL == msg_recv_queue_mutex){ err = mico_rtos_init_mutex(&msg_recv_queue_mutex); require_noerr_action(err, exit, fogcloud_log("ERROR: mico_rtos_init_mutex (msg_recv_queue_mutex) failed, err=%d.", err)); } err = mico_rtos_init_queue(&msg_recv_queue, "fog_recv_queue", sizeof(int), FOGCLOUD_MAX_RECV_QUEUE_LENGTH); require_noerr_action(err, exit, fogcloud_log("ERROR: mico_rtos_init_queue (msg_recv_queue) failed, err=%d", err)); /* start FogCloud service */ err = fogCloudStart(inContext); require_noerr_action(err, exit, fogcloud_log("ERROR: MicoFogCloudCloudInterfaceStart failed!") ); /* start configServer for fogcloud (server for activate/authorize/reset/ota cmd from user APP) */ if(false == inContext->flashContentInRam.appConfig.fogcloudConfig.owner_binding){ err = MicoStartFogCloudConfigServer( inContext); require_noerr_action(err, exit, fogcloud_log("ERROR: start FogCloud configServer failed!") ); } #ifdef ENABLE_FOGCLOUD_AUTO_ACTIVATE /* activate when wifi on */ while(false == inContext->flashContentInRam.appConfig.fogcloudConfig.isActivated){ // auto activate, using default login_id/dev_pass/user_token fogcloud_log("device activate start..."); memset((void*)&devDefaultActivateData, 0, sizeof(devDefaultActivateData)); strncpy(devDefaultActivateData.loginId, inContext->flashContentInRam.appConfig.fogcloudConfig.loginId, MAX_SIZE_LOGIN_ID); strncpy(devDefaultActivateData.devPasswd, inContext->flashContentInRam.appConfig.fogcloudConfig.devPasswd, MAX_SIZE_DEV_PASSWD); strncpy(devDefaultActivateData.user_token, inContext->micoStatus.mac, // use MAC as default user_token MAX_SIZE_USER_TOKEN); err = fogCloudDevActivate(inContext, devDefaultActivateData); if(kNoErr == err){ fogcloud_log("device activate success!"); break; } else{ fogcloud_log("device auto activate failed, err = %d, will retry in 3s ...", err); } mico_thread_sleep(3); } #endif // ENABLE_FOGCLOUD_AUTO_ACTIVATE #ifndef DISABLE_FOGCLOUD_OTA_CHECK /* OTA check just device activated */ if( (!inContext->appStatus.noOTACheckOnSystemStart) && (inContext->flashContentInRam.appConfig.fogcloudConfig.isActivated) ){ // start ota thread err = mico_rtos_create_thread(NULL, MICO_APPLICATION_PRIORITY, "fogcloud_ota", fogcloud_ota_thread, STACK_SIZE_FOGCLOUD_OTA_THREAD, inContext); if(kNoErr != err){ fogcloud_log("ERROR: start FogCloud OTA thread failed, err=%d.", err); } } inContext->appStatus.noOTACheckOnSystemStart = false; #endif // DISABLE_FOGCLOUD_OTA_CHECK while(1){ // device info reset if(device_need_delete){ fogcloud_log("delete device from cloud ..."); memset((void*)&devResetRequestData, 0, sizeof(devResetRequestData)); strncpy(devResetRequestData.loginId, inContext->flashContentInRam.appConfig.fogcloudConfig.loginId, MAX_SIZE_LOGIN_ID); strncpy(devResetRequestData.devPasswd, inContext->flashContentInRam.appConfig.fogcloudConfig.devPasswd, MAX_SIZE_DEV_PASSWD); strncpy(devResetRequestData.user_token, inContext->flashContentInRam.appConfig.fogcloudConfig.userToken, MAX_SIZE_USER_TOKEN); err = fogCloudResetCloudDevInfo(inContext, devResetRequestData); if(kNoErr == err){ device_need_delete = false; fogcloud_log("delete device success, system need reboot..."); mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); MicoFogCloudRestoreDefault(inContext); MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); // system restart inContext->micoStatus.sys_state = eState_Software_Reset; if(inContext->micoStatus.sys_state_change_sem){ mico_rtos_set_semaphore(&inContext->micoStatus.sys_state_change_sem); } } else{ fogcloud_log("delete device failed, err = %d.", err); } } mico_thread_sleep(1); if(inContext->appStatus.fogcloudStatus.isOTAInProgress){ continue; // ota is in progress, the oled && system led will be holding } if(inContext->appStatus.fogcloudStatus.isCloudConnected){ set_RF_LED_cloud_connected(inContext); // toggle LED } else{ set_RF_LED_cloud_disconnected(inContext); // stop LED blink } } exit: fogcloud_log("fogcloud_main_thread exit err=%d.", err); if(NULL != msg_recv_queue_mutex){ mico_rtos_deinit_mutex(&msg_recv_queue_mutex); } if(NULL != msg_recv_queue){ mico_rtos_deinit_queue(&msg_recv_queue); } mico_rtos_delete_thread(NULL); return; }
OSStatus _LocalConfigRespondInComingMessage(int fd, HTTPHeader_t* inHeader, mico_Context_t * const inContext) { OSStatus err = kUnknownErr; const char * json_str; uint8_t *httpResponse = NULL; size_t httpResponseLen = 0; json_object* report = NULL; config_log_trace(); if(HTTPHeaderMatchURL( inHeader, kCONFIGURLRead ) == kNoErr){ report = ConfigCreateReportJsonMessage( inContext ); require( report, exit ); json_str = json_object_to_json_string(report); require_action( json_str, exit, err = kNoMemoryErr ); config_log("Send config object=%s", json_str); err = CreateSimpleHTTPMessageNoCopy( kMIMEType_JSON, strlen(json_str), &httpResponse, &httpResponseLen ); require_noerr( err, exit ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); require_noerr( err, exit ); err = SocketSend( fd, (uint8_t *)json_str, strlen(json_str) ); require_noerr( err, exit ); config_log("Current configuration sent"); goto exit; } else if(HTTPHeaderMatchURL( inHeader, kCONFIGURLWrite ) == kNoErr){ if(inHeader->contentLength > 0){ config_log("Recv new configuration, apply and reset"); err = ConfigIncommingJsonMessage( inHeader->extraDataPtr, inContext); require_noerr( err, exit ); inContext->flashContentInRam.micoSystemConfig.configured = allConfigured; MICOUpdateConfiguration(inContext); err = CreateSimpleHTTPOKMessage( &httpResponse, &httpResponseLen ); require_noerr( err, exit ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); inContext->micoStatus.sys_state = eState_Software_Reset; if(inContext->micoStatus.sys_state_change_sem != NULL ); mico_rtos_set_semaphore(&inContext->micoStatus.sys_state_change_sem); mico_thread_sleep(MICO_WAIT_FOREVER); } goto exit; } else if(HTTPHeaderMatchURL( inHeader, kCONFIGURLWriteByUAP ) == kNoErr){ if(inHeader->contentLength > 0){ config_log("Recv new configuration from uAP, apply and connect to AP"); err = ConfigIncommingJsonMessageUAP( inHeader->extraDataPtr, inContext); require_noerr( err, exit ); MICOUpdateConfiguration(inContext); err = CreateSimpleHTTPOKMessage( &httpResponse, &httpResponseLen ); require_noerr( err, exit ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); require_noerr( err, exit ); sleep(1); micoWlanSuspendSoftAP(); _easylinkConnectWiFi( inContext ); err = kConnectionErr; //Return an err to close socket and exit the current thread } goto exit; } #ifdef MICO_FLASH_FOR_UPDATE else if(HTTPHeaderMatchURL( inHeader, kCONFIGURLOTA ) == kNoErr){ if(inHeader->contentLength > 0){ config_log("Receive OTA data!"); memset(&inContext->flashContentInRam.bootTable, 0, sizeof(boot_table_t)); inContext->flashContentInRam.bootTable.length = inHeader->contentLength; inContext->flashContentInRam.bootTable.start_address = UPDATE_START_ADDRESS; inContext->flashContentInRam.bootTable.type = 'A'; inContext->flashContentInRam.bootTable.upgrade_type = 'U'; if(inContext->flashContentInRam.micoSystemConfig.configured != allConfigured) inContext->flashContentInRam.micoSystemConfig.easyLinkByPass = EASYLINK_SOFT_AP_BYPASS; MICOUpdateConfiguration(inContext); SocketClose(&fd); inContext->micoStatus.sys_state = eState_Software_Reset; if(inContext->micoStatus.sys_state_change_sem != NULL ); mico_rtos_set_semaphore(&inContext->micoStatus.sys_state_change_sem); mico_thread_sleep(MICO_WAIT_FOREVER); } goto exit; } #endif else{ return kNotFoundErr; }; exit: if(inHeader->persistent == false) //Return an err to close socket and exit the current thread err = kConnectionErr; if(httpResponse) free(httpResponse); if(report) json_object_put(report); return err; }
OSStatus _LocalConfigRespondInComingMessage(int fd, ECS_HTTPHeader_t* inHeader, mico_Context_t * const inContext) { OSStatus err = kUnknownErr; const char * json_str; uint8_t *httpResponse = NULL; size_t httpResponseLen = 0; json_object* report = NULL; char err_msg[32] = {0}; MVDActivateRequestData_t devActivateRequestData; MVDAuthorizeRequestData_t devAuthorizeRequestData; MVDResetRequestData_t devResetRequestData; MVDOTARequestData_t devOTARequestData; MVDGetStateRequestData_t devGetStateRequestData; fogcloud_config_log_trace(); if(ECS_HTTPHeaderMatchURL( inHeader, kCONFIGURLDevState ) == kNoErr){ if(inHeader->contentLength > 0){ fogcloud_config_log("Recv device getState request."); memset((void*)&devGetStateRequestData, '\0', sizeof(devGetStateRequestData)); err = getMVDGetStateRequestData(inHeader->extraDataPtr, &devGetStateRequestData); require_noerr( err, exit ); report = json_object_new_object(); err = MicoFogCloudGetState(inContext, devGetStateRequestData, report); require_noerr( err, exit ); fogcloud_config_log("get device state success!"); json_str = (char*)json_object_to_json_string(report); //config_log("json_str=%s", json_str); err = ECS_CreateSimpleHTTPMessage( ECS_kMIMEType_JSON, (uint8_t*)json_str, strlen(json_str), &httpResponse, &httpResponseLen ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); } goto exit; } else if(ECS_HTTPHeaderMatchURL( inHeader, kCONFIGURLDevActivate ) == kNoErr){ if(inHeader->contentLength > 0){ fogcloud_config_log("Recv device activate request."); memset((void*)&devActivateRequestData, '\0', sizeof(devActivateRequestData)); err = getMVDActivateRequestData(inHeader->extraDataPtr, &devActivateRequestData); require_noerr( err, exit ); err = MicoFogCloudActivate(inContext, devActivateRequestData); require_noerr( err, exit ); fogcloud_config_log("Device activate success!"); report = json_object_new_object(); require_action(report, exit, err = kNoMemoryErr); json_object_object_add(report, "device_id", json_object_new_string(inContext->flashContentInRam.appConfig.fogcloudConfig.deviceId)); json_str = (char*)json_object_to_json_string(report); //config_log("json_str=%s", json_str); err = ECS_CreateSimpleHTTPMessage( ECS_kMIMEType_JSON, (uint8_t*)json_str, strlen(json_str), &httpResponse, &httpResponseLen ); require_noerr( err, exit ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); } goto exit; } else if(ECS_HTTPHeaderMatchURL( inHeader, kCONFIGURLDevAuthorize ) == kNoErr){ if(inHeader->contentLength > 0){ fogcloud_config_log("Recv device authorize request."); memset((void*)&devAuthorizeRequestData, '\0', sizeof(devAuthorizeRequestData)); err = getMVDAuthorizeRequestData( inHeader->extraDataPtr, &devAuthorizeRequestData); require_noerr( err, exit ); err = MicoFogCloudAuthorize(inContext, devAuthorizeRequestData); require_noerr( err, exit ); fogcloud_config_log("Device authorize success!"); report = json_object_new_object(); require_action(report, exit, err = kNoMemoryErr); json_object_object_add(report, "device_id", json_object_new_string(inContext->flashContentInRam.appConfig.fogcloudConfig.deviceId)); json_str = (char*)json_object_to_json_string(report); //config_log("json_str=%s", json_str); err = ECS_CreateSimpleHTTPMessage( ECS_kMIMEType_JSON, (uint8_t*)json_str, strlen(json_str), &httpResponse, &httpResponseLen ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); } goto exit; } else if(ECS_HTTPHeaderMatchURL( inHeader, kCONFIGURLResetCloudDevInfo ) == kNoErr){ if(inHeader->contentLength > 0){ fogcloud_config_log("Recv cloud device info reset request."); memset((void*)&devResetRequestData, '\0', sizeof(devResetRequestData)); err = getMVDResetRequestData( inHeader->extraDataPtr, &devResetRequestData); require_noerr( err, exit ); err = MicoFogCloudResetCloudDevInfo(inContext, devResetRequestData); require_noerr( err, exit ); fogcloud_config_log("Device cloud reset success!"); err = ECS_CreateSimpleHTTPOKMessage( &httpResponse, &httpResponseLen ); require_noerr( err, exit ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); inContext->micoStatus.sys_state = eState_Software_Reset; require(inContext->micoStatus.sys_state_change_sem, exit); mico_rtos_set_semaphore(&inContext->micoStatus.sys_state_change_sem); } goto exit; } #ifdef MICO_FLASH_FOR_UPDATE else if(ECS_HTTPHeaderMatchURL( inHeader, kCONFIGURLDevFWUpdate ) == kNoErr){ if(inHeader->contentLength > 0){ fogcloud_config_log("Recv device fw_update request."); memset((void*)&devOTARequestData, '\0', sizeof(devOTARequestData)); err = getMVDOTARequestData( inHeader->extraDataPtr, &devOTARequestData); require_noerr( err, exit ); err = MicoFogCloudFirmwareUpdate(inContext, devOTARequestData); require_noerr( err, exit ); fogcloud_config_log("Device firmware update success!"); err = ECS_CreateSimpleHTTPOKMessage( &httpResponse, &httpResponseLen ); require_noerr( err, exit ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); fogcloud_config_log("OTA bin_size=%lld, bin_version=%s", inContext->appStatus.fogcloudStatus.RecvRomFileSize, inContext->flashContentInRam.appConfig.fogcloudConfig.romVersion ); if(0 == inContext->appStatus.fogcloudStatus.RecvRomFileSize){ //no need to update, return size = 0, no need to boot bootloader err = kNoErr; goto exit; } mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); memset(&inContext->flashContentInRam.bootTable, 0, sizeof(boot_table_t)); inContext->flashContentInRam.bootTable.length = inContext->appStatus.fogcloudStatus.RecvRomFileSize; inContext->flashContentInRam.bootTable.start_address = UPDATE_START_ADDRESS; inContext->flashContentInRam.bootTable.type = 'A'; inContext->flashContentInRam.bootTable.upgrade_type = 'U'; MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); inContext->micoStatus.sys_state = eState_Software_Reset; require(inContext->micoStatus.sys_state_change_sem, exit); mico_rtos_set_semaphore(&inContext->micoStatus.sys_state_change_sem); } goto exit; } #endif else{ return kNotFoundErr; }; exit: if((kNoErr != err) && (fd > 0)){ //ECS_CreateSimpleHTTPFailedMessage( &httpResponse, &httpResponseLen ); sprintf(err_msg, "{\"error\": %d}", err); ECS_CreateHTTPFailedMessage("500", "FAILED", ECS_kMIMEType_JSON, strlen(err_msg), (uint8_t*)err_msg, strlen(err_msg), &httpResponse, &httpResponseLen ); require( httpResponse, exit ); SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); } if(httpResponse) free(httpResponse); if(report) json_object_put(report); return err; }
OSStatus MVDCloudInterfaceDevFirmwareUpdate(mico_Context_t* const inContext, MVDOTARequestData_t devOTARequestData) { cloud_if_log_trace(); OSStatus err = kUnknownErr; cloud_if_log("MVDCloudInterfaceDevFirmwareUpdate: start ..."); // login_id/dev_passwd ok ? if((0 != strncmp(inContext->flashContentInRam.appConfig.virtualDevConfig.loginId, devOTARequestData.loginId, strlen(inContext->flashContentInRam.appConfig.virtualDevConfig.loginId))) || (0 != strncmp(inContext->flashContentInRam.appConfig.virtualDevConfig.devPasswd, devOTARequestData.devPasswd, strlen(inContext->flashContentInRam.appConfig.virtualDevConfig.devPasswd)))) { // devPass err cloud_if_log("ERROR: MVDCloudInterfaceDevFirmwareUpdate: loginId/devPasswd mismatch!"); return kMismatchErr; } cloud_if_log("MVDCloudInterfaceDevFirmwareUpdate: loginId/devPasswd ok!"); //get latest rom version, file_path, md5 cloud_if_log("MVDCloudInterfaceDevFirmwareUpdate: get latest rom version from server ..."); err = EasyCloudGetLatestRomVersion(&easyCloudContext); require_noerr_action( err, exit, cloud_if_log("ERROR: EasyCloudGetLatestRomVersion failed! err=%d", err) ); //FW version compare cloud_if_log("currnt_version=%s", inContext->flashContentInRam.appConfig.virtualDevConfig.romVersion); cloud_if_log("latestRomVersion=%s", easyCloudContext.service_status.latestRomVersion); cloud_if_log("bin_file=%s", easyCloudContext.service_status.bin_file); cloud_if_log("bin_md5=%s", easyCloudContext.service_status.bin_md5); if(0 == strncmp(inContext->flashContentInRam.appConfig.virtualDevConfig.romVersion, easyCloudContext.service_status.latestRomVersion, strlen(inContext->flashContentInRam.appConfig.virtualDevConfig.romVersion))){ cloud_if_log("the current firmware version[%s] is up-to-date!", inContext->flashContentInRam.appConfig.virtualDevConfig.romVersion); inContext->appStatus.virtualDevStatus.RecvRomFileSize = 0; return kNoErr; } cloud_if_log("MVDCloudInterfaceDevFirmwareUpdate: new firmware[%s] found on server, downloading ...", easyCloudContext.service_status.latestRomVersion); //get rom data err = EasyCloudGetRomData(&easyCloudContext); require_noerr_action( err, exit, cloud_if_log("ERROR: EasyCloudGetRomData failed! err=%d", err) ); //update rom version in flash cloud_if_log("MVDCloudInterfaceDevFirmwareUpdate: return rom version && file size."); mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); memset(inContext->flashContentInRam.appConfig.virtualDevConfig.romVersion, 0, MAX_SIZE_FW_VERSION); strncpy(inContext->flashContentInRam.appConfig.virtualDevConfig.romVersion, easyCloudContext.service_status.latestRomVersion, strlen(easyCloudContext.service_status.latestRomVersion)); inContext->appStatus.virtualDevStatus.RecvRomFileSize = easyCloudContext.service_status.bin_file_size; MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); return kNoErr; exit: return err; }
OSStatus fogCloudDevFirmwareUpdate(mico_Context_t* const inContext, MVDOTARequestData_t devOTARequestData) { cloud_if_log_trace(); OSStatus err = kUnknownErr; ecs_ota_flash_params_t ota_flash_params = { MICO_FLASH_FOR_UPDATE, UPDATE_START_ADDRESS, UPDATE_END_ADDRESS, UPDATE_FLASH_SIZE }; cloud_if_log("fogCloudDevFirmwareUpdate: start ..."); // login_id/dev_passwd ok ? if((0 != strncmp(inContext->flashContentInRam.appConfig.fogcloudConfig.loginId, devOTARequestData.loginId, strlen(inContext->flashContentInRam.appConfig.fogcloudConfig.loginId))) || (0 != strncmp(inContext->flashContentInRam.appConfig.fogcloudConfig.devPasswd, devOTARequestData.devPasswd, strlen(inContext->flashContentInRam.appConfig.fogcloudConfig.devPasswd)))) { // devPass err cloud_if_log("ERROR: fogCloudDevFirmwareUpdate: loginId/devPasswd mismatch!"); return kMismatchErr; } cloud_if_log("fogCloudDevFirmwareUpdate: loginId/devPasswd ok!"); //get latest rom version, file_path, md5 cloud_if_log("fogCloudDevFirmwareUpdate: get latest rom version from server ..."); err = FogCloudGetLatestRomVersion(&easyCloudContext); if(kNoErr != err){ if(kNotFoundErr == err){ cloud_if_log("WARNING: FogCloudGetLatestRomVersion: ROM not found on server!"); inContext->appStatus.fogcloudStatus.RecvRomFileSize = 0; // no rom to update return kNoErr; } else{ cloud_if_log("ERROR: FogCloudGetLatestRomVersion failed! err=%d", err); goto exit; } } //FW version compare cloud_if_log("currnt_version=%s", inContext->flashContentInRam.appConfig.fogcloudConfig.romVersion); cloud_if_log("latestRomVersion=%s", easyCloudContext.service_status.latestRomVersion); cloud_if_log("bin_file=%s", easyCloudContext.service_status.bin_file); cloud_if_log("bin_md5=%s", easyCloudContext.service_status.bin_md5); if(0 == strncmp(inContext->flashContentInRam.appConfig.fogcloudConfig.romVersion, easyCloudContext.service_status.latestRomVersion, strlen(inContext->flashContentInRam.appConfig.fogcloudConfig.romVersion))){ cloud_if_log("the current firmware version[%s] is up-to-date!", inContext->flashContentInRam.appConfig.fogcloudConfig.romVersion); inContext->appStatus.fogcloudStatus.RecvRomFileSize = 0; return kNoErr; } cloud_if_log("fogCloudDevFirmwareUpdate: new firmware[%s] found on server, downloading ...", easyCloudContext.service_status.latestRomVersion); //get rom data err = FogCloudGetRomData(&easyCloudContext, ota_flash_params); require_noerr_action( err, exit, cloud_if_log("ERROR: FogCloudGetRomData failed! err=%d", err) ); //update rom version in flash cloud_if_log("fogCloudDevFirmwareUpdate: return rom version && file size."); mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); memset(inContext->flashContentInRam.appConfig.fogcloudConfig.romVersion, 0, MAX_SIZE_FW_VERSION); strncpy(inContext->flashContentInRam.appConfig.fogcloudConfig.romVersion, easyCloudContext.service_status.latestRomVersion, strlen(easyCloudContext.service_status.latestRomVersion)); inContext->appStatus.fogcloudStatus.RecvRomFileSize = easyCloudContext.service_status.bin_file_size; MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); return kNoErr; exit: return err; }
OSStatus _LocalConfigRespondInComingMessage(int fd, ECS_HTTPHeader_t* inHeader, mico_Context_t * const inContext) { OSStatus err = kUnknownErr; const char * json_str; uint8_t *httpResponse = NULL; size_t httpResponseLen = 0; json_object* report = NULL; char err_msg[32] = {0}; char *bonjour_txt_record = NULL; char *bonjour_txt_field = NULL; MVDActivateRequestData_t devActivateRequestData; MVDAuthorizeRequestData_t devAuthorizeRequestData; MVDResetRequestData_t devResetRequestData; MVDOTARequestData_t devOTARequestData; MVDGetStateRequestData_t devGetStateRequestData; fogcloud_config_log_trace(); if(ECS_HTTPHeaderMatchURL( inHeader, kCONFIGURLDevState ) == kNoErr){ if(inHeader->contentLength > 0){ fogcloud_config_log("Recv device getState request."); memset((void*)&devGetStateRequestData, '\0', sizeof(devGetStateRequestData)); err = getMVDGetStateRequestData(inHeader->extraDataPtr, &devGetStateRequestData); require_noerr( err, exit ); report = json_object_new_object(); err = MicoFogCloudGetState(inContext, devGetStateRequestData, report); require_noerr( err, exit ); fogcloud_config_log("get device state success!"); json_str = (char*)json_object_to_json_string(report); //config_log("json_str=%s", json_str); err = ECS_CreateSimpleHTTPMessage( ECS_kMIMEType_JSON, (uint8_t*)json_str, strlen(json_str), &httpResponse, &httpResponseLen ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); } goto exit; } else if(ECS_HTTPHeaderMatchURL( inHeader, kCONFIGURLDevActivate ) == kNoErr){ if(inHeader->contentLength > 0){ fogcloud_config_log("Recv device activate request."); memset((void*)&devActivateRequestData, '\0', sizeof(devActivateRequestData)); err = getMVDActivateRequestData(inHeader->extraDataPtr, &devActivateRequestData); require_noerr( err, exit ); err = MicoFogCloudActivate(inContext, devActivateRequestData); require_noerr( err, exit ); fogcloud_config_log("Device activate success!"); //------------------------------------------------------------------------ fog_config_server_running = false; // stop fog config server fogcloud_config_log("update bonjour txt record."); // update owner binding flag in txt record of bonjour suspend_bonjour_service(true); mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); inContext->flashContentInRam.appConfig.fogcloudConfig.owner_binding = true; err = MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); bonjour_txt_record = malloc(550); require_action(bonjour_txt_record, exit, err = kNoMemoryErr); bonjour_txt_field = __strdup_trans_dot(inContext->micoStatus.mac); sprintf(bonjour_txt_record, "MAC=%s.", bonjour_txt_field); free(bonjour_txt_field); bonjour_txt_field = __strdup_trans_dot((inContext->flashContentInRam.appConfig.fogcloudConfig.owner_binding) ? "true" : "false"); sprintf(bonjour_txt_record, "%sBinding=%s.", bonjour_txt_record, bonjour_txt_field); free(bonjour_txt_field); bonjour_txt_field = __strdup_trans_dot(FIRMWARE_REVISION); sprintf(bonjour_txt_record, "%sFirmware Rev=%s.", bonjour_txt_record, bonjour_txt_field); free(bonjour_txt_field); bonjour_txt_field = __strdup_trans_dot(HARDWARE_REVISION); sprintf(bonjour_txt_record, "%sHardware Rev=%s.", bonjour_txt_record, bonjour_txt_field); free(bonjour_txt_field); bonjour_txt_field = __strdup_trans_dot(MicoGetVer()); sprintf(bonjour_txt_record, "%sMICO OS Rev=%s.", bonjour_txt_record, bonjour_txt_field); free(bonjour_txt_field); bonjour_txt_field = __strdup_trans_dot(MODEL); sprintf(bonjour_txt_record, "%sModel=%s.", bonjour_txt_record, bonjour_txt_field); free(bonjour_txt_field); bonjour_txt_field = __strdup_trans_dot(PROTOCOL); sprintf(bonjour_txt_record, "%sProtocol=%s.", bonjour_txt_record, bonjour_txt_field); free(bonjour_txt_field); bonjour_txt_field = __strdup_trans_dot(MANUFACTURER); sprintf(bonjour_txt_record, "%sManufacturer=%s.", bonjour_txt_record, bonjour_txt_field); free(bonjour_txt_field); sprintf(bonjour_txt_record, "%sSeed=%u.", bonjour_txt_record, inContext->flashContentInRam.micoSystemConfig.seed); bonjour_update_txt_record(bonjour_txt_record); if(NULL != bonjour_txt_record) free(bonjour_txt_record); suspend_bonjour_service(false); //------------------------------------------------------------------------ report = json_object_new_object(); require_action(report, exit, err = kNoMemoryErr); json_object_object_add(report, "device_id", json_object_new_string(inContext->flashContentInRam.appConfig.fogcloudConfig.deviceId)); json_str = (char*)json_object_to_json_string(report); //config_log("json_str=%s", json_str); err = ECS_CreateSimpleHTTPMessage( ECS_kMIMEType_JSON, (uint8_t*)json_str, strlen(json_str), &httpResponse, &httpResponseLen ); require_noerr( err, exit ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); } goto exit; } else if(ECS_HTTPHeaderMatchURL( inHeader, kCONFIGURLDevAuthorize ) == kNoErr){ if(inHeader->contentLength > 0){ fogcloud_config_log("Recv device authorize request."); memset((void*)&devAuthorizeRequestData, '\0', sizeof(devAuthorizeRequestData)); err = getMVDAuthorizeRequestData( inHeader->extraDataPtr, &devAuthorizeRequestData); require_noerr( err, exit ); err = MicoFogCloudAuthorize(inContext, devAuthorizeRequestData); require_noerr( err, exit ); fogcloud_config_log("Device authorize success!"); report = json_object_new_object(); require_action(report, exit, err = kNoMemoryErr); json_object_object_add(report, "device_id", json_object_new_string(inContext->flashContentInRam.appConfig.fogcloudConfig.deviceId)); json_str = (char*)json_object_to_json_string(report); //config_log("json_str=%s", json_str); err = ECS_CreateSimpleHTTPMessage( ECS_kMIMEType_JSON, (uint8_t*)json_str, strlen(json_str), &httpResponse, &httpResponseLen ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); } goto exit; } else if(ECS_HTTPHeaderMatchURL( inHeader, kCONFIGURLResetCloudDevInfo ) == kNoErr){ if(inHeader->contentLength > 0){ fogcloud_config_log("Recv cloud device info reset request."); memset((void*)&devResetRequestData, '\0', sizeof(devResetRequestData)); err = getMVDResetRequestData( inHeader->extraDataPtr, &devResetRequestData); require_noerr( err, exit ); err = MicoFogCloudResetCloudDevInfo(inContext, devResetRequestData); require_noerr( err, exit ); fogcloud_config_log("Device cloud reset success!"); err = ECS_CreateSimpleHTTPOKMessage( &httpResponse, &httpResponseLen ); require_noerr( err, exit ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); inContext->micoStatus.sys_state = eState_Software_Reset; require(inContext->micoStatus.sys_state_change_sem, exit); mico_rtos_set_semaphore(&inContext->micoStatus.sys_state_change_sem); } goto exit; } else if(ECS_HTTPHeaderMatchURL( inHeader, kCONFIGURLDevFWUpdate ) == kNoErr){ if(inHeader->contentLength > 0){ fogcloud_config_log("Recv device fw_update request."); memset((void*)&devOTARequestData, '\0', sizeof(devOTARequestData)); err = getMVDOTARequestData( inHeader->extraDataPtr, &devOTARequestData); require_noerr( err, exit ); err = MicoFogCloudFirmwareUpdate(inContext, devOTARequestData); require_noerr( err, exit ); fogcloud_config_log("Device firmware update success!"); err = ECS_CreateSimpleHTTPOKMessage( &httpResponse, &httpResponseLen ); require_noerr( err, exit ); require( httpResponse, exit ); err = SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); fogcloud_config_log("OTA bin_size=%lld, bin_version=%s", inContext->appStatus.fogcloudStatus.RecvRomFileSize, inContext->flashContentInRam.appConfig.fogcloudConfig.romVersion ); if(0 == inContext->appStatus.fogcloudStatus.RecvRomFileSize){ //no need to update, return size = 0, no need to boot bootloader err = kNoErr; goto exit; } mico_rtos_lock_mutex(&inContext->flashContentInRam_mutex); memset(&inContext->flashContentInRam.bootTable, 0, sizeof(boot_table_t)); inContext->flashContentInRam.bootTable.length = inContext->appStatus.fogcloudStatus.RecvRomFileSize; inContext->flashContentInRam.bootTable.start_address = UPDATE_START_ADDRESS; inContext->flashContentInRam.bootTable.type = 'A'; inContext->flashContentInRam.bootTable.upgrade_type = 'U'; MICOUpdateConfiguration(inContext); mico_rtos_unlock_mutex(&inContext->flashContentInRam_mutex); inContext->micoStatus.sys_state = eState_Software_Reset; require(inContext->micoStatus.sys_state_change_sem, exit); mico_rtos_set_semaphore(&inContext->micoStatus.sys_state_change_sem); } goto exit; } else{ return kNotFoundErr; }; exit: if((kNoErr != err) && (fd > 0)){ //ECS_CreateSimpleHTTPFailedMessage( &httpResponse, &httpResponseLen ); sprintf(err_msg, "{\"error\": %d}", err); ECS_CreateHTTPFailedMessage("500", "FAILED", ECS_kMIMEType_JSON, strlen(err_msg), (uint8_t*)err_msg, strlen(err_msg), &httpResponse, &httpResponseLen ); require( httpResponse, exit ); SocketSend( fd, httpResponse, httpResponseLen ); SocketClose(&fd); } if(httpResponse) free(httpResponse); if(report) json_object_put(report); return err; }