Mbed Cloud example program for workshop in W27 2018.

Dependencies:   MMA7660 LM75B

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers simple-mbed-cloud-client.cpp Source File

simple-mbed-cloud-client.cpp

00001 // ----------------------------------------------------------------------------
00002 // Copyright 2016-2017 ARM Ltd.
00003 //
00004 // SPDX-License-Identifier: Apache-2.0
00005 //
00006 // Licensed under the Apache License, Version 2.0 (the "License");
00007 // you may not use this file except in compliance with the License.
00008 // You may obtain a copy of the License at
00009 //
00010 //     http://www.apache.org/licenses/LICENSE-2.0
00011 //
00012 // Unless required by applicable law or agreed to in writing, software
00013 // distributed under the License is distributed on an "AS IS" BASIS,
00014 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
00015 // See the License for the specific language governing permissions and
00016 // limitations under the License.
00017 // ----------------------------------------------------------------------------
00018 
00019 #include <stdio.h>
00020 #include "simple-mbed-cloud-client.h"
00021 #include "mbed-cloud-client/MbedCloudClient.h"
00022 #include "m2mdevice.h"
00023 #include "m2mresource.h"
00024 #include "mbed-client/m2minterface.h"
00025 #include "key_config_manager.h"
00026 #include "resource.h"
00027 #include "mbed-client/m2mvector.h"
00028 #include "mbed_cloud_client_resource.h"
00029 #include "factory_configurator_client.h"
00030 
00031 #ifdef MBED_CLOUD_CLIENT_USER_CONFIG_FILE
00032 #include MBED_CLOUD_CLIENT_USER_CONFIG_FILE
00033 #endif
00034 
00035 #ifdef MBED_CLOUD_CLIENT_SUPPORT_UPDATE
00036 #include "update_ui_example.h"
00037 #endif
00038 
00039 #ifdef MBED_HEAP_STATS_ENABLED
00040 #include "memory_tests.h"
00041 #endif
00042 
00043 #define DEFAULT_FIRMWARE_PATH       "/sd/firmware"
00044 
00045 SimpleMbedCloudClient::SimpleMbedCloudClient(NetworkInterface *net) :
00046     _registered(false),
00047     _register_called(false),
00048     net(net) {
00049 }
00050 
00051 SimpleMbedCloudClient::~SimpleMbedCloudClient() {
00052     for (unsigned int i = 0; _resources.size(); i++) {
00053         delete _resources[i];
00054     }
00055 }
00056 
00057 int SimpleMbedCloudClient::init() {
00058     // Initialize the FCC
00059     fcc_status_e fcc_status = fcc_init();
00060     if(fcc_status != FCC_STATUS_SUCCESS) {
00061         printf("fcc_init failed with status %d! - exit\n", fcc_status);
00062         return 1;
00063     }
00064 
00065     // Resets storage to an empty state.
00066     // Use this function when you want to clear storage from all the factory-tool generated data and user data.
00067     // After this operation device must be injected again by using factory tool or developer certificate.
00068 #ifdef RESET_STORAGE
00069     printf("Reset storage to an empty state.\n");
00070     fcc_status_e delete_status = fcc_storage_delete();
00071     if (delete_status != FCC_STATUS_SUCCESS) {
00072         printf("Failed to delete storage - %d\n", delete_status);
00073     }
00074 #endif
00075 
00076     // Deletes existing firmware images from storage.
00077     // This deletes any existing firmware images during application startup.
00078     // This compilation flag is currently implemented only for mbed OS.
00079 #ifdef RESET_FIRMWARE
00080     palStatus_t status = PAL_SUCCESS;
00081     status = pal_fsRmFiles(DEFAULT_FIRMWARE_PATH);
00082     if(status == PAL_SUCCESS) {
00083         printf("Firmware storage erased.\n");
00084     } else if (status == PAL_ERR_FS_NO_PATH) {
00085         printf("Firmware path not found/does not exist.\n");
00086     } else {
00087         printf("Firmware storage erasing failed with %" PRId32, status);
00088         return 1;
00089     }
00090 #endif
00091 
00092 #if MBED_CONF_APP_DEVELOPER_MODE == 1
00093     printf("Start developer flow\n");
00094     fcc_status = fcc_developer_flow();
00095     if (fcc_status == FCC_STATUS_KCM_FILE_EXIST_ERROR) {
00096         printf("Developer credentials already exist\n");
00097     } else if (fcc_status != FCC_STATUS_SUCCESS) {
00098         printf("Failed to load developer credentials - exit\n");
00099         return 1;
00100     }
00101 #endif
00102     fcc_status = fcc_verify_device_configured_4mbed_cloud();
00103     if (fcc_status != FCC_STATUS_SUCCESS) {
00104         printf("Device not configured for mbed Cloud - exit\n");
00105         return 1;
00106     }
00107 }
00108 
00109 bool SimpleMbedCloudClient::call_register() {
00110 
00111     _cloud_client.on_registered(this, &SimpleMbedCloudClient::client_registered);
00112     _cloud_client.on_unregistered(this, &SimpleMbedCloudClient::client_unregistered);
00113     _cloud_client.on_error(this, &SimpleMbedCloudClient::error);
00114 
00115     printf("Connecting...\n");
00116     bool setup = _cloud_client.setup(net);
00117     _register_called = true;
00118     if (!setup) {
00119         printf("Client setup failed\n");
00120         return false;
00121     }
00122 
00123 #ifdef MBED_CLOUD_CLIENT_SUPPORT_UPDATE
00124     /* Set callback functions for authorizing updates and monitoring progress.
00125        Code is implemented in update_ui_example.cpp
00126        Both callbacks are completely optional. If no authorization callback
00127        is set, the update process will procede immediately in each step.
00128     */
00129     update_ui_set_cloud_client(&_cloud_client);
00130     _cloud_client.set_update_authorize_handler(update_authorize);
00131     _cloud_client.set_update_progress_handler(update_progress);
00132 #endif
00133     return true;
00134 }
00135 
00136 void SimpleMbedCloudClient::close() {
00137     _cloud_client.close();
00138 }
00139 
00140 void SimpleMbedCloudClient::register_update() {
00141     _cloud_client.register_update();
00142 }
00143 
00144 void SimpleMbedCloudClient::client_registered() {
00145     _registered = true;
00146     printf("\nClient registered\n\n");
00147     static const ConnectorClientEndpointInfo* endpoint = NULL;
00148     if (endpoint == NULL) {
00149         endpoint = _cloud_client.endpoint_info();
00150         if (endpoint) {
00151 
00152 #if MBED_CONF_APP_DEVELOPER_MODE == 1
00153             printf("Endpoint Name: %s\r\n", endpoint->internal_endpoint_name.c_str());
00154 #else
00155             printf("Endpoint Name: %s\r\n", endpoint->endpoint_name.c_str());
00156 #endif
00157             printf("Device Id: %s\r\n", endpoint->internal_endpoint_name.c_str());
00158         }
00159     }
00160 #ifdef MBED_HEAP_STATS_ENABLED
00161     heap_stats();
00162 #endif
00163 }
00164 
00165 void SimpleMbedCloudClient::client_unregistered() {
00166     _registered = false;
00167     _register_called = false;
00168     printf("\nClient unregistered - Exiting application\n\n");
00169 #ifdef MBED_HEAP_STATS_ENABLED
00170     heap_stats();
00171 #endif
00172 }
00173 
00174 void SimpleMbedCloudClient::error(int error_code) {
00175     const char *error;
00176     switch(error_code) {
00177         case MbedCloudClient::ConnectErrorNone:
00178             error = "MbedCloudClient::ConnectErrorNone";
00179             break;
00180         case MbedCloudClient::ConnectAlreadyExists:
00181             error = "MbedCloudClient::ConnectAlreadyExists";
00182             break;
00183         case MbedCloudClient::ConnectBootstrapFailed:
00184             error = "MbedCloudClient::ConnectBootstrapFailed";
00185             break;
00186         case MbedCloudClient::ConnectInvalidParameters:
00187             error = "MbedCloudClient::ConnectInvalidParameters";
00188             break;
00189         case MbedCloudClient::ConnectNotRegistered:
00190             error = "MbedCloudClient::ConnectNotRegistered";
00191             break;
00192         case MbedCloudClient::ConnectTimeout:
00193             error = "MbedCloudClient::ConnectTimeout";
00194             break;
00195         case MbedCloudClient::ConnectNetworkError:
00196             error = "MbedCloudClient::ConnectNetworkError";
00197             break;
00198         case MbedCloudClient::ConnectResponseParseFailed:
00199             error = "MbedCloudClient::ConnectResponseParseFailed";
00200             break;
00201         case MbedCloudClient::ConnectUnknownError:
00202             error = "MbedCloudClient::ConnectUnknownError";
00203             break;
00204         case MbedCloudClient::ConnectMemoryConnectFail:
00205             error = "MbedCloudClient::ConnectMemoryConnectFail";
00206             break;
00207         case MbedCloudClient::ConnectNotAllowed:
00208             error = "MbedCloudClient::ConnectNotAllowed";
00209             break;
00210         case MbedCloudClient::ConnectSecureConnectionFailed:
00211             error = "MbedCloudClient::ConnectSecureConnectionFailed";
00212             break;
00213         case MbedCloudClient::ConnectDnsResolvingFailed:
00214             error = "MbedCloudClient::ConnectDnsResolvingFailed";
00215             break;
00216 #ifdef MBED_CLOUD_CLIENT_SUPPORT_UPDATE
00217         case MbedCloudClient::UpdateWarningCertificateNotFound:
00218             error = "MbedCloudClient::UpdateWarningCertificateNotFound";
00219             break;
00220         case MbedCloudClient::UpdateWarningIdentityNotFound:
00221             error = "MbedCloudClient::UpdateWarningIdentityNotFound";
00222             break;
00223         case MbedCloudClient::UpdateWarningCertificateInvalid:
00224             error = "MbedCloudClient::UpdateWarningCertificateInvalid";
00225             break;
00226         case MbedCloudClient::UpdateWarningSignatureInvalid:
00227             error = "MbedCloudClient::UpdateWarningSignatureInvalid";
00228             break;
00229         case MbedCloudClient::UpdateWarningVendorMismatch:
00230             error = "MbedCloudClient::UpdateWarningVendorMismatch";
00231             break;
00232         case MbedCloudClient::UpdateWarningClassMismatch:
00233             error = "MbedCloudClient::UpdateWarningClassMismatch";
00234             break;
00235         case MbedCloudClient::UpdateWarningDeviceMismatch:
00236             error = "MbedCloudClient::UpdateWarningDeviceMismatch";
00237             break;
00238         case MbedCloudClient::UpdateWarningURINotFound:
00239             error = "MbedCloudClient::UpdateWarningURINotFound";
00240             break;
00241         case MbedCloudClient::UpdateWarningRollbackProtection:
00242             error = "MbedCloudClient::UpdateWarningRollbackProtection";
00243             break;
00244         case MbedCloudClient::UpdateWarningUnknown:
00245             error = "MbedCloudClient::UpdateWarningUnknown";
00246             break;
00247         case MbedCloudClient::UpdateErrorWriteToStorage:
00248             error = "MbedCloudClient::UpdateErrorWriteToStorage";
00249             break;
00250         case MbedCloudClient::UpdateErrorInvalidHash:
00251             error = "MbedCloudClient::UpdateErrorInvalidHash";
00252             break;
00253 #endif
00254         default:
00255             error = "UNKNOWN";
00256     }
00257     printf("\nError occurred : %s\r\n", error);
00258     printf("Error code : %d\r\n\n", error_code);
00259     printf("Error details : %s\r\n\n",_cloud_client.error_description());
00260 }
00261 
00262 bool SimpleMbedCloudClient::is_client_registered() {
00263     return _registered;
00264 }
00265 
00266 bool SimpleMbedCloudClient::is_register_called() {
00267     return _register_called;
00268 }
00269 
00270 void SimpleMbedCloudClient::register_and_connect() {
00271     // TODO this might not work if called more than once...
00272     mcc_resource_def resourceDef;
00273 
00274     // TODO clean up
00275     for (unsigned int i = 0; i < _resources.size(); i++) {
00276         _resources[i]->get_data(&resourceDef);
00277         M2MResource *res = add_resource(&_obj_list, resourceDef.object_id, resourceDef.instance_id,
00278                      resourceDef.resource_id, resourceDef.name.c_str(), M2MResourceInstance::STRING,
00279                      (M2MBase::Operation)resourceDef.method_mask, resourceDef.value.c_str(), resourceDef.observable,
00280                      resourceDef.put_callback, resourceDef.post_callback, resourceDef.notification_callback);
00281         _resources[i]->set_resource(res);
00282     }
00283     _cloud_client.add_objects(_obj_list);
00284 
00285     // Start registering to the cloud.
00286     call_register();
00287 
00288     // Print memory statistics if the MBED_HEAP_STATS_ENABLED is defined.
00289     #ifdef MBED_HEAP_STATS_ENABLED
00290         printf("Register being called\r\n");
00291         heap_stats();
00292     #endif
00293 }
00294 
00295 MbedCloudClient& SimpleMbedCloudClient::get_cloud_client() {
00296     return _cloud_client;
00297 }
00298 
00299 MbedCloudClientResource* SimpleMbedCloudClient::create_resource(const char *path, const char *name) {
00300     MbedCloudClientResource *resource = new MbedCloudClientResource(this, path, name);
00301     _resources.push_back(resource);
00302     return resource;
00303 }