From ce6cdbccef4f0f73b6e4bff3f0894a1197f5b854 Mon Sep 17 00:00:00 2001 From: Teemu Takaluoma Date: Tue, 21 Sep 2021 11:18:54 +0300 Subject: [PATCH] mbed-cloud-client-example 4.11.0 --- CHANGELOG.md | 13 + CONTRIBUTING.md | 1 + configs/wifi_esp8266_minimal.json | 5 +- define.txt | 3 +- main.cpp | 264 +------- mbed-cloud-client.lib | 2 +- mbed-os.lib | 2 +- mbed_cloud_client_user_config_mesh.h | 4 +- pal-platform/SDK/ZephyrOS/CMakeLists.txt | 3 +- pal-platform/pal-platform.json | 16 +- source/app_platform_setup.c | 119 ---- source/application_init.cpp | 184 ++++-- source/application_init.h | 30 +- source/blinky.cpp | 76 +-- source/blinky.h | 10 +- source/certificate_enrollment_user_cb.cpp | 2 +- source/fota_platform.c | 53 -- source/fota_platform_hooks_impl.cpp | 166 +++++ ...omponent.cpp => fota_platform_ifs_imp.cpp} | 83 +-- source/include/app_platform_setup.h | 44 -- source/pdmc_example.cpp | 573 ++++++++++++++++++ source/pdmc_example.h | 46 ++ source/platform/KEIL/mcc_common_setup.c | 24 +- source/platform/Linux/mcc_common_setup.c | 51 +- source/platform/NXP/mcc_common_setup.c | 29 +- .../Renesas_EK_RA6M3/mcc_common_setup.c | 35 +- .../Renesas_RX65N-CK/mcc_common_setup.c | 10 +- source/platform/ZephyrOS/mcc_common_setup.c | 59 +- source/platform/mbed-os/mcc_common_setup.cpp | 13 +- source/resource.cpp | 84 --- source/resource.h | 64 -- source/simplem2mclient.h | 395 ------------ west.yml | 2 +- 33 files changed, 1192 insertions(+), 1273 deletions(-) delete mode 100644 source/app_platform_setup.c delete mode 100644 source/fota_platform.c create mode 100644 source/fota_platform_hooks_impl.cpp rename source/{fota_platform_mesh_component.cpp => fota_platform_ifs_imp.cpp} (56%) delete mode 100644 source/include/app_platform_setup.h create mode 100644 source/pdmc_example.cpp create mode 100644 source/pdmc_example.h delete mode 100644 source/resource.cpp delete mode 100644 source/resource.h delete mode 100644 source/simplem2mclient.h diff --git a/CHANGELOG.md b/CHANGELOG.md index 449b6a2..ef831fd 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,17 @@ # Changelog for Pelion Device Management Client example application +## Release 4.11.0 (17.09.2021) + +- Application restructuring: + - `M2MInterfaceFactory::create_resource()` function used for creating object and resources. + - Replaced the deprecated status APIs with the `on_status_changed()` API. + - Removed the `MCC_MEMORY` flag. + - Replaced the `MCC_MINIMAL` flag with the `PDMC_EXAMPLE_MINIMAL` flag. +- Updated to Mbed OS 6.14.0. +- Updated Mbed TLS to 2.27.0 in `pal-platform`. +- Added a demonstration of FOTA component update. Placed component registration and callback examples in `source/fota_platform_hooks_imp.cpp`. +- [Linux] Added demonstration of FOTA combined update. Placed subcomponent registration and callback examples in `source/fota_platform_hooks_imp.cpp` under the `MBED_CLOUD_CLIENT_FOTA_SUB_COMPONENT_SUPPORT` flag. + ## Release 4.10.0 (07.07.2021) - NXP_LPC54628 target configured to use the new upgraded Update client with `FOTA_USE_ENCRYPTED_ONE_TIME_FW_KEY` key. @@ -11,6 +23,7 @@ - This release uses bootloaders compiled with the above improvement by default. - Deprecated the `FOTA_USE_DEVICE_KEY` option, which will be removed in a future version. * Updated to Mbed OS 6.12.0. + - Changed LED configuration from `LED_RED` to `LED1`. ## Release 4.9.1 (17.06.2021) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index f64db25..49a221b 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -8,3 +8,4 @@ Due to the release process, all new releases are squashed code drops. Therefore, | Author | Pull Request | Change title/summary | |----------------|---------------|----------------------------------------------------------| +| ccli8 ([@ccli8](https://github.com/ccli8)) | [#81](https://github.com/PelionIoT/mbed-cloud-client-example/pull/81) | Fix KV init on platforms using PSA Storage API | diff --git a/configs/wifi_esp8266_minimal.json b/configs/wifi_esp8266_minimal.json index e8837dd..0a564df 100644 --- a/configs/wifi_esp8266_minimal.json +++ b/configs/wifi_esp8266_minimal.json @@ -1,8 +1,7 @@ { "macros": [ - "MCC_MINIMAL", - "DISABLE_ERROR_DESCRIPTION", - "MCC_MEMORY" + "PDMC_EXAMPLE_MINIMAL", + "DISABLE_ERROR_DESCRIPTION" ], "target_overrides": { "*": { diff --git a/define.txt b/define.txt index 8f15248..57d767c 100644 --- a/define.txt +++ b/define.txt @@ -57,4 +57,5 @@ option(FOTA_ENABLE "Enable FOTA client module" ON) add_definitions(-DFOTA_DEFAULT_APP_IFS=1) add_definitions(-DTARGET_LIKE_LINUX=1) - +add_definitions(-DFOTA_CUSTOM_PLATFORM=1) +add_definitions(-DMBED_CLOUD_CLIENT_FOTA_SUB_COMPONENT_SUPPORT=1) diff --git a/main.cpp b/main.cpp index c2f9f2d..ad48fec 100755 --- a/main.cpp +++ b/main.cpp @@ -1,5 +1,5 @@ // ---------------------------------------------------------------------------- -// Copyright 2016-2020 ARM Ltd. +// Copyright 2016-2021 Pelion. // // SPDX-License-Identifier: Apache-2.0 // @@ -18,6 +18,7 @@ // Needed for PRIu64 on FreeRTOS #include + // Note: this macro is needed on armcc to get the the limit macros like UINT16_MAX #ifndef __STDC_LIMIT_MACROS #define __STDC_LIMIT_MACROS @@ -28,39 +29,39 @@ #ifndef __STDC_FORMAT_MACROS #define __STDC_FORMAT_MACROS #endif + #if defined (__RTX) #include "pdmc_main.h" #endif -#include "simplem2mclient.h" + #ifdef TARGET_LIKE_MBED #include "mbed.h" #endif -#include "application_init.h" -#include "mcc_common_button_and_led.h" -#include "blinky.h" -#ifndef MBED_CONF_MBED_CLOUD_CLIENT_DISABLE_CERTIFICATE_ENROLLMENT -#include "certificate_enrollment_user_cb.h" -#endif #if defined(MBED_CONF_NANOSTACK_HAL_EVENT_LOOP_USE_MBED_EVENTS) && \ (MBED_CONF_NANOSTACK_HAL_EVENT_LOOP_USE_MBED_EVENTS == 1) && \ defined(MBED_CONF_EVENTS_SHARED_DISPATCH_FROM_APPLICATION) && \ (MBED_CONF_EVENTS_SHARED_DISPATCH_FROM_APPLICATION == 1) +#define USE_EVENT_QUEUE #include "nanostack-event-loop/eventOS_scheduler.h" #endif -#if defined MBED_CONF_MBED_CLOUD_CLIENT_NETWORK_MANAGER && \ - (MBED_CONF_MBED_CLOUD_CLIENT_NETWORK_MANAGER == 1) -#include "NetworkManager.h" +#ifdef MEMORY_TESTS_HEAP +#include "memory_tests.h" #endif -// event based LED blinker, controlled via pattern_resource -#ifndef MCC_MEMORY -static Blinky blinky; -#endif +#include "pdmc_example.h" +#include "application_init.h" +#include "mcc_common_setup.h" static void main_application(void); +#if defined MBED_CONF_MBED_CLOUD_CLIENT_NETWORK_MANAGER && \ + (MBED_CONF_MBED_CLOUD_CLIENT_NETWORK_MANAGER == 1) +#include "NetworkManager.h" +static NetworkManager network_manager; +#endif + #if defined(MBED_CLOUD_APPLICATION_NONSTANDARD_ENTRYPOINT) extern "C" int mbed_cloud_application_entrypoint(void) @@ -71,162 +72,6 @@ int main(void) return mcc_platform_run_program(main_application); } -// Pointers to the resources that will be created in main_application(). -static M2MResource *button_res; -static M2MResource *pattern_res; -static M2MResource *blink_res; -static M2MResource *factory_reset_res; -static M2MResource *large_res; -static uint8_t *large_res_data = NULL; -const static int16_t large_res_size = 2049; -void unregister(void); - -// Pointer to mbedClient, used for calling close function. -static SimpleM2MClient *client; - -#if defined MBED_CONF_MBED_CLOUD_CLIENT_NETWORK_MANAGER && \ - (MBED_CONF_MBED_CLOUD_CLIENT_NETWORK_MANAGER == 1) -static NetworkManager network_manager; -#endif - -void counter_updated(const char *) -{ - // Converts uint64_t to a string to remove the dependency for int64 printf implementation. - char buffer[20 + 1]; - (void) m2m::itoa_c(button_res->get_value_int(), buffer); - printf("Counter resource set to %s\r\n", buffer); -} - -void pattern_updated(const char *) -{ - printf("PUT received, new value: %s\r\n", pattern_res->get_value_string().c_str()); -} - -void blink_callback(void *) -{ - String pattern_string = pattern_res->get_value_string(); - printf("POST executed\r\n"); - - // The pattern is something like 500:200:500, so parse that. - // LED blinking is done while parsing. -#ifndef MCC_MEMORY - const bool restart_pattern = false; - if (blinky.start((char *)pattern_res->value(), pattern_res->value_length(), restart_pattern) == false) { - printf("out of memory error\r\n"); - } -#endif - blink_res->send_delayed_post_response(); -} - -void notification_status_callback(const M2MBase &object, - const M2MBase::MessageDeliveryStatus status, - const M2MBase::MessageType /*type*/) -{ - switch (status) { - case M2MBase::MESSAGE_STATUS_BUILD_ERROR: - printf("Message status callback: (%s) error when building CoAP message\r\n", object.uri_path()); - break; - case M2MBase::MESSAGE_STATUS_RESEND_QUEUE_FULL: - printf("Message status callback: (%s) CoAP resend queue full\r\n", object.uri_path()); - break; - case M2MBase::MESSAGE_STATUS_SENT: - printf("Message status callback: (%s) Message sent to server\r\n", object.uri_path()); - break; - case M2MBase::MESSAGE_STATUS_DELIVERED: - printf("Message status callback: (%s) Message delivered\r\n", object.uri_path()); - break; - case M2MBase::MESSAGE_STATUS_SEND_FAILED: - printf("Message status callback: (%s) Message sending failed\r\n", object.uri_path()); - break; - case M2MBase::MESSAGE_STATUS_SUBSCRIBED: - printf("Message status callback: (%s) subscribed\r\n", object.uri_path()); - break; - case M2MBase::MESSAGE_STATUS_UNSUBSCRIBED: - printf("Message status callback: (%s) subscription removed\r\n", object.uri_path()); - break; - case M2MBase::MESSAGE_STATUS_REJECTED: - printf("Message status callback: (%s) server has rejected the message\r\n", object.uri_path()); - break; - default: - break; - } -} - -void sent_callback(const M2MBase &base, - const M2MBase::MessageDeliveryStatus status, - const M2MBase::MessageType /*type*/) -{ - switch (status) { - case M2MBase::MESSAGE_STATUS_DELIVERED: - if (strcmp("5000/0/2", base.uri_path()) == 0) { - free(large_res_data); - printf("5000/0/2 data sent to server, memory can be now released\r\n"); - } else { - unregister(); - } - break; - case M2MBase::MESSAGE_STATUS_SEND_FAILED: - if (strcmp("5000/0/2", base.uri_path()) == 0) { - printf("Failed to send 5000/0/2 data!\r\n"); - free(large_res_data); - } - break; - default: - break; - } -} - -void factory_reset_triggered(void *) -{ - printf("Factory reset resource triggered\r\n"); - - // First send response, so server won't be left waiting. - // Factory reset resource is by default expecting explicit - // delayed response sending. - factory_reset_res->send_delayed_post_response(); - - // Then run potentially long-taking factory reset routines. - kcm_factory_reset(); -} - -// This function is called when a POST request is received for resource 5000/0/1. -void unregister(void) -{ - printf("Unregister resource executed\r\n"); - client->close(); -} - -static coap_response_code_e read_requested(const M2MResourceBase& resource, - uint8_t *&buffer, - size_t &buffer_size, - size_t &total_size, - const size_t offset, - void */*client_args*/) { - printf("GET request received for resource: %s\r\n", resource.uri_path()); - - // Allocate buffer when first request comes in - if (offset == 0) { - large_res_data = (uint8_t*)malloc(large_res_size); - memset(large_res_data, 0, large_res_size); - } - - if (!large_res_data) { - return COAP_RESPONSE_INTERNAL_SERVER_ERROR; - } - - total_size = large_res_size; - - // Adjust last package size - if (offset + buffer_size > total_size) { - buffer_size = total_size - offset; - } - - // Read data from offset - buffer = (uint8_t*)large_res_data + offset; - - return COAP_RESPONSE_CONTENT; -} - void main_application(void) { #if defined(__linux__) && (MBED_CONF_MBED_TRACE_ENABLE == 0) @@ -236,7 +81,7 @@ void main_application(void) #endif // Initialize trace-library first - if (application_init_mbed_trace() != 0) { + if (!application_init_mbed_trace()) { printf("Failed initializing mbed trace\r\n"); return; } @@ -261,12 +106,6 @@ void main_application(void) print_m2mobject_stats(); #endif - // SimpleClient is used for registering and unregistering resources to a server. - SimpleM2MClient mbedClient; - - // Save pointer to mbedClient so that other functions can access it. - client = &mbedClient; - /* * Pre-initialize network stack and client library. * @@ -289,7 +128,7 @@ void main_application(void) return; } - mbedClient.init(); + pdmc_init(); #if defined MBED_CONF_MBED_CLOUD_CLIENT_NETWORK_MANAGER &&\ (MBED_CONF_MBED_CLOUD_CLIENT_NETWORK_MANAGER == 1) @@ -310,10 +149,10 @@ void main_application(void) // Initialize network int timeout_ms = 5000; int retry_counter = 0; - while (-1 == mcc_platform_interface_connect()){ + while (-1 == mcc_platform_interface_connect()) { // Will try to connect using mcc_platform_interface_connect forever. // wait timeout is always doubled - printf("Network connect failed. Try again after %d milliseconds.\n",timeout_ms); + printf("Network connect failed. Try again after %d milliseconds.\n", timeout_ms); mcc_platform_do_wait(timeout_ms); timeout_ms *= 2; @@ -332,64 +171,19 @@ void main_application(void) #if defined MBED_CONF_MBED_CLOUD_CLIENT_NETWORK_MANAGER &&\ (MBED_CONF_MBED_CLOUD_CLIENT_NETWORK_MANAGER == 1) - network_manager.create_resource(mbedClient.get_m2m_obj_list()); + network_manager.create_resource(pdmc_get_object_list()); #endif -#ifndef MCC_MEMORY - // Create resource for button count. Path of this resource will be: 3200/0/5501. - button_res = mbedClient.add_cloud_resource(3200, 0, 5501, "button_resource", M2MResourceInstance::INTEGER, - M2MBase::GET_PUT_ALLOWED, 0, true, (void *)counter_updated, (void *)notification_status_callback); - button_res->set_value(0); - - // Create resource for led blinking pattern. Path of this resource will be: 3201/0/5853. - pattern_res = mbedClient.add_cloud_resource(3201, 0, 5853, "pattern_resource", M2MResourceInstance::STRING, - M2MBase::GET_PUT_ALLOWED, "500:500:500:500", true, (void *)pattern_updated, (void *)notification_status_callback); - - // Create resource for starting the led blinking. Path of this resource will be: 3201/0/5850. - blink_res = mbedClient.add_cloud_resource(3201, 0, 5850, "blink_resource", M2MResourceInstance::STRING, - M2MBase::POST_ALLOWED, "", false, (void *)blink_callback, (void *)notification_status_callback); - // Use delayed response - blink_res->set_delayed_response(true); - - // Create optional Device resource for running factory reset for the device. Path of this resource will be: 3/0/5. - factory_reset_res = M2MInterfaceFactory::create_device()->create_resource(M2MDevice::FactoryReset); - if (factory_reset_res) { - factory_reset_res->set_execute_function(factory_reset_triggered); +#ifndef PDMC_EXAMPLE_MINIMAL + if (!create_pdmc_resources()) { + printf("Failed to create resources\r\n"); + return; } - - // Create an example resource for handling large resource payloads. Path of this resource will be: 5000/0/2. - large_res = mbedClient.add_cloud_resource(5000, 0, 2, "large_resource", M2MResourceInstance::STRING, - M2MBase::GET_ALLOWED, NULL, false, NULL, (void*)sent_callback); - large_res->set_read_resource_function(read_requested, NULL); - -#ifdef MBED_CLOUD_CLIENT_TRANSPORT_MODE_UDP_QUEUE - button_res->set_auto_observable(true); - pattern_res->set_auto_observable(true); - blink_res->set_auto_observable(true); - factory_reset_res->set_auto_observable(true); #endif -#endif + pdmc_connect(); - mbedClient.register_and_connect(); - -#ifndef MBED_CLOUD_CLIENT_SUPPORT_MULTICAST_UPDATE -#ifndef MCC_MEMORY - blinky.init(mbedClient, button_res); - blinky.request_next_loop_event(); - blinky.request_automatic_increment_event(); -#endif -#endif - -#ifndef MBED_CONF_MBED_CLOUD_CLIENT_DISABLE_CERTIFICATE_ENROLLMENT - // Add certificate renewal callback - mbedClient.get_cloud_client().on_certificate_renewal(certificate_renewal_cb); -#endif // MBED_CONF_MBED_CLOUD_CLIENT_DISABLE_CERTIFICATE_ENROLLMENT - -#if defined(MBED_CONF_NANOSTACK_HAL_EVENT_LOOP_USE_MBED_EVENTS) && \ - (MBED_CONF_NANOSTACK_HAL_EVENT_LOOP_USE_MBED_EVENTS == 1) && \ - defined(MBED_CONF_EVENTS_SHARED_DISPATCH_FROM_APPLICATION) && \ - (MBED_CONF_EVENTS_SHARED_DISPATCH_FROM_APPLICATION == 1) +#ifdef USE_EVENT_QUEUE printf("Starting mbed eventloop...\r\n"); eventOS_scheduler_mutex_wait(); @@ -401,14 +195,14 @@ void main_application(void) #if defined MBED_CONF_MBED_CLOUD_CLIENT_NETWORK_MANAGER &&\ (MBED_CONF_MBED_CLOUD_CLIENT_NETWORK_MANAGER == 1) // Wait untill client is registered. - while (mbedClient.is_client_registered() == false) { + while (pdmc_registered() == false) { mcc_platform_do_wait(100); } network_manager.nm_cloud_client_connect_indication(); #endif // Check if client is registering or registered, if true sleep and repeat. - while (mbedClient.is_register_called()) { + while (pdmc_register_called()) { mcc_platform_do_wait(100); } diff --git a/mbed-cloud-client.lib b/mbed-cloud-client.lib index 7016e5d..07619d3 100644 --- a/mbed-cloud-client.lib +++ b/mbed-cloud-client.lib @@ -1 +1 @@ -https://github.com/PelionIoT/mbed-cloud-client/#d7edc529ed3722c811ff401440ef58ea980bf543 +https://github.com/PelionIoT/mbed-cloud-client/#105a1846277c80e5eb15ad74de7e4d7b15e57c26 diff --git a/mbed-os.lib b/mbed-os.lib index f185a6b..68e51ac 100644 --- a/mbed-os.lib +++ b/mbed-os.lib @@ -1 +1 @@ -https://github.com/ARMmbed/mbed-os/#cecc47b4a53951527dd3f670465c8566396ad101 +https://github.com/ARMmbed/mbed-os/#3377f083b3a6bd7a1b45ed2cea5cf083b9007527 diff --git a/mbed_cloud_client_user_config_mesh.h b/mbed_cloud_client_user_config_mesh.h index 0f91149..2e31563 100644 --- a/mbed_cloud_client_user_config_mesh.h +++ b/mbed_cloud_client_user_config_mesh.h @@ -37,9 +37,7 @@ #define SN_COAP_MAX_BLOCKWISE_PAYLOAD_SIZE 512 #endif -#if !defined(MBED_CLOUD_CLIENT_SUPPORT_UPDATE) && !defined(MBED_CLOUD_CLIENT_FOTA_ENABLE) - #define MBED_CLOUD_CLIENT_SUPPORT_UPDATE -#endif +#define MBED_CLOUD_CLIENT_SUPPORT_UPDATE /* Sets the download buffer for update client in bytes (min. 2048 bytes). * This must be at least twice the SN_COAP_MAX_BLOCKWISE_PAYLOAD_SIZE value. diff --git a/pal-platform/SDK/ZephyrOS/CMakeLists.txt b/pal-platform/SDK/ZephyrOS/CMakeLists.txt index 213dda5..aea7f87 100644 --- a/pal-platform/SDK/ZephyrOS/CMakeLists.txt +++ b/pal-platform/SDK/ZephyrOS/CMakeLists.txt @@ -30,11 +30,10 @@ include_directories(${CMAKE_SOURCE_DIR}/source/platform/include) SET(APP_SRCS ${CMAKE_SOURCE_DIR}/main.cpp ${CMAKE_SOURCE_DIR}/update_ui_example.cpp - ${CMAKE_SOURCE_DIR}/source/app_platform_setup.c + ${CMAKE_SOURCE_DIR}/source/pdmc_example.cpp ${CMAKE_SOURCE_DIR}/source/application_init.cpp ${CMAKE_SOURCE_DIR}/source/blinky.cpp ${CMAKE_SOURCE_DIR}/source/certificate_enrollment_user_cb.cpp - ${CMAKE_SOURCE_DIR}/source/resource.cpp ${CMAKE_SOURCE_DIR}/source/platform/ZephyrOS/mcc_common_button_and_led.c ${CMAKE_SOURCE_DIR}/source/platform/ZephyrOS/mcc_common_setup.c ${CMAKE_SOURCE_DIR}/mbed_cloud_dev_credentials.c diff --git a/pal-platform/pal-platform.json b/pal-platform/pal-platform.json index ee8ad3a..a0a930a 100644 --- a/pal-platform/pal-platform.json +++ b/pal-platform/pal-platform.json @@ -34,11 +34,11 @@ }, "middleware": { "mbedtls": { - "version": "2.25.0", + "version": "2.27.0", "from": { "protocol": "git", "location": "https://github.com/ARMmbed/mbedtls.git", - "tag": "mbedtls-2.25.0" + "tag": "mbedtls-2.27.0" }, "to": "Middleware/mbedtls/mbedtls" }, @@ -81,11 +81,11 @@ }, "middleware": { "mbedtls": { - "version": "2.25.0", + "version": "2.27.0", "from": { "protocol": "git", "location": "https://github.com/ARMmbed/mbedtls.git", - "tag": "mbedtls-2.25.0" + "tag": "mbedtls-2.27.0" }, "to": "Middleware/mbedtls/mbedtls" }, @@ -109,11 +109,11 @@ }, "middleware": { "mbedtls": { - "version": "2.25.0", + "version": "2.27.0", "from": { "protocol": "git", "location": "https://github.com/ARMmbed/mbedtls.git", - "tag": "mbedtls-2.25.0" + "tag": "mbedtls-2.27.0" }, "to": "Middleware/mbedtls/mbedtls" }, @@ -201,11 +201,11 @@ }, "middleware": { "mbedtls": { - "version": "2.25.0", + "version": "2.27.0", "from": { "protocol": "git", "location": "https://github.com/ARMmbed/mbedtls.git", - "tag": "mbedtls-2.25.0" + "tag": "mbedtls-2.27.0" }, "to": "Middleware/mbedtls/mbedtls" }, diff --git a/source/app_platform_setup.c b/source/app_platform_setup.c deleted file mode 100644 index 3a8106d..0000000 --- a/source/app_platform_setup.c +++ /dev/null @@ -1,119 +0,0 @@ -/* - * Copyright (c) 2015-2019 ARM Limited. All rights reserved. - * SPDX-License-Identifier: Apache-2.0 - * Licensed under the Apache License, Version 2.0 (the License); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an AS IS BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifdef MBED_CLOUD_CLIENT_USER_CONFIG_FILE -#include MBED_CLOUD_CLIENT_USER_CONFIG_FILE -#endif - -#include -#include "app_platform_setup.h" -#include "mcc_common_setup.h" -#include "mcc_common_config.h" -#include "factory_configurator_client.h" -#include "pal.h" - -#if MBED_CONF_APP_DEVELOPER_MODE == 1 -#ifdef PAL_USER_DEFINED_CONFIGURATION - #include PAL_USER_DEFINED_CONFIGURATION -#endif -#endif // #if MBED_CONF_APP_DEVELOPER_MODE == 1 - -// Include this only for Developer mode and device which doesn't have in-built TRNG support -#if MBED_CONF_APP_DEVELOPER_MODE == 1 -#ifdef PAL_USER_DEFINED_CONFIGURATION -#define FCC_ROT_SIZE 16 -const uint8_t MBED_CLOUD_DEV_ROT[FCC_ROT_SIZE] = { 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16 }; -#if !PAL_USE_HW_TRNG -#define FCC_ENTROPY_SIZE 48 -const uint8_t MBED_CLOUD_DEV_ENTROPY[FCC_ENTROPY_SIZE] = { 0xf6, 0xd6, 0xc0, 0x09, 0x9e, 0x6e, 0xf2, 0x37, 0xdc, 0x29, 0x88, 0xf1, 0x57, 0x32, 0x7d, 0xde, 0xac, 0xb3, 0x99, 0x8c, 0xb9, 0x11, 0x35, 0x18, 0xeb, 0x48, 0x29, 0x03, 0x6a, 0x94, 0x6d, 0xe8, 0x40, 0xc0, 0x28, 0xcc, 0xe4, 0x04, 0xc3, 0x1f, 0x4b, 0xc2, 0xe0, 0x68, 0xa0, 0x93, 0xe6, 0x3a }; -#endif // PAL_USE_HW_TRNG = 0 -#endif // PAL_USER_DEFINED_CONFIGURATION -#endif // #if MBED_CONF_APP_DEVELOPER_MODE == 1 - -int mcc_platform_reset_storage(void) -{ -#if MBED_CONF_APP_DEVELOPER_MODE == 1 - printf("Resets storage to an empty state.\r\n"); - int status = fcc_storage_delete(); - if (status != FCC_STATUS_SUCCESS) { - printf("Failed to delete storage - %d\r\n", status); - } - return status; -#else - return FCC_STATUS_SUCCESS; -#endif -} - -int mcc_platform_fcc_init(void) -{ -#if MBED_CONF_APP_DEVELOPER_MODE == 1 - int status = fcc_init(); - // Ignore pre-existing RoT/Entropy in SOTP - if (status != FCC_STATUS_SUCCESS && status != FCC_STATUS_ENTROPY_ERROR && status != FCC_STATUS_ROT_ERROR) { - printf("fcc_init failed with status %d! - exit\r\n", status); - return status; - } - status = mcc_platform_sotp_init(); - if (status != FCC_STATUS_SUCCESS) { - printf("fcc_init failed with status %d! - exit\r\n", status); - mcc_platform_fcc_finalize(); - } else { - // We can return SUCCESS here as preexisting RoT/Entropy is expected flow. - status = FCC_STATUS_SUCCESS; - } - return status; -#else - return FCC_STATUS_SUCCESS; -#endif -} - -int mcc_platform_sotp_init(void) -{ - int status = FCC_STATUS_SUCCESS; -// Include this only for Developer mode and a device which doesn't have in-built TRNG support. -#if MBED_CONF_APP_DEVELOPER_MODE == 1 -#if defined (PAL_USER_DEFINED_CONFIGURATION) && !PAL_USE_HW_TRNG - status = fcc_entropy_set(MBED_CLOUD_DEV_ENTROPY, FCC_ENTROPY_SIZE); - - if (status != FCC_STATUS_SUCCESS && status != FCC_STATUS_ENTROPY_ERROR) { - printf("fcc_entropy_set failed with status %d! - exit\r\n", status); - mcc_platform_fcc_finalize(); - return status; - } -#endif // PAL_USE_HW_TRNG = 0 -/* Include this only for Developer mode. The application will use fixed RoT to simplify user-experience with the application. - * With this change the application be reflashed/SOTP can be erased safely without invalidating the application credentials. - */ - status = fcc_rot_set(MBED_CLOUD_DEV_ROT, FCC_ROT_SIZE); - - if (status != FCC_STATUS_SUCCESS && status != FCC_STATUS_ROT_ERROR) { - printf("fcc_rot_set failed with status %d! - exit\r\n", status); - mcc_platform_fcc_finalize(); - } else { - // We can return SUCCESS here as preexisting RoT/Entropy is expected flow. - printf("Using hardcoded Root of Trust, not suitable for production use.\r\n"); - status = FCC_STATUS_SUCCESS; - } -#endif // #if MBED_CONF_APP_DEVELOPER_MODE == 1 - return status; -} - -void mcc_platform_fcc_finalize(void) -{ -#if MBED_CONF_APP_DEVELOPER_MODE == 1 - (void)fcc_finalize(); -#endif -} diff --git a/source/application_init.cpp b/source/application_init.cpp index 52e7dbd..95ef4d3 100644 --- a/source/application_init.cpp +++ b/source/application_init.cpp @@ -1,5 +1,5 @@ // ---------------------------------------------------------------------------- -// Copyright 2016-2020 ARM Ltd. +// Copyright 2016-2021 Pelion. // // SPDX-License-Identifier: Apache-2.0 // @@ -23,27 +23,50 @@ #include "mbed-trace/mbed_trace.h" #include "mbed-trace-helper.h" #include "factory_configurator_client.h" -#include "app_platform_setup.h" #include "mcc_common_setup.h" #include "mcc_common_button_and_led.h" +#include "application_init.h" + #if defined (MEMORY_TESTS_HEAP) #include "memory_tests.h" #endif + #if defined (MBED_CONF_APP_ENABLE_DS_CUSTOM_METRICS_EXAMPLE) #include "ds_custom_metrics_app.h" #endif -#include "application_init.h" -#include "mbed-client-randlib/mbed-client-randlib/randLIB.h" + #ifdef MBED_CONF_MBED_CLOUD_CLIENT_SECURE_ELEMENT_SUPPORT #include "mcc_se_init.h" #endif -void print_fcc_status(int fcc_status) +#if MBED_CONF_APP_DEVELOPER_MODE == 1 +#ifdef PAL_USER_DEFINED_CONFIGURATION +#include PAL_USER_DEFINED_CONFIGURATION +#endif +#endif // #if MBED_CONF_APP_DEVELOPER_MODE == 1 + +// Include this only for Developer mode and device which doesn't have in-built TRNG support +#if MBED_CONF_APP_DEVELOPER_MODE == 1 +#ifdef PAL_USER_DEFINED_CONFIGURATION +#define FCC_ROT_SIZE 16 +const uint8_t MBED_CLOUD_DEV_ROT[FCC_ROT_SIZE] = { 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16 }; +#if !PAL_USE_HW_TRNG +#define FCC_ENTROPY_SIZE 48 +const uint8_t MBED_CLOUD_DEV_ENTROPY[FCC_ENTROPY_SIZE] = { 0xf6, 0xd6, 0xc0, 0x09, 0x9e, 0x6e, 0xf2, 0x37, 0xdc, 0x29, 0x88, 0xf1, 0x57, 0x32, 0x7d, 0xde, 0xac, 0xb3, 0x99, 0x8c, 0xb9, 0x11, 0x35, 0x18, 0xeb, 0x48, 0x29, 0x03, 0x6a, 0x94, 0x6d, 0xe8, 0x40, 0xc0, 0x28, 0xcc, 0xe4, 0x04, 0xc3, 0x1f, 0x4b, 0xc2, 0xe0, 0x68, 0xa0, 0x93, 0xe6, 0x3a }; +#endif // PAL_USE_HW_TRNG = 0 +#endif // PAL_USER_DEFINED_CONFIGURATION +#endif // #if MBED_CONF_APP_DEVELOPER_MODE == 1 + +static int reset_storage(void); +static int fcc_initialize(void); +static int sotp_initialize(void); + +static void print_fcc_status(int fcc_status) { -#ifndef MCC_MINIMAL +#ifndef PDMC_EXAMPLE_MINIMAL #ifndef DISABLE_ERROR_DESCRIPTION const char *error; - switch(fcc_status) { + switch (fcc_status) { case FCC_STATUS_SUCCESS: return; case FCC_STATUS_ERROR : @@ -162,33 +185,30 @@ void print_fcc_status(int fcc_status) #if defined(__SXOS__) || defined(__RTX) extern "C" -void trace_printer(const char* str) +void trace_printer(const char *str) { printf("%s\r\n", str); } -#endif +#endif bool application_init_mbed_trace(void) { -#ifndef MCC_MINIMAL +#ifndef PDMC_EXAMPLE_MINIMAL // Create mutex for tracing to avoid broken lines in logs - if(!mbed_trace_helper_create_mutex()) { + if (!mbed_trace_helper_create_mutex()) { printf("ERROR - Mutex creation for mbed_trace failed!\n"); - return 1; + return false; } #endif // Initialize mbed trace - (void) mbed_trace_init(); - // If you want, you can filter out the trace set. - // For example mbed_trace_include_filters_set("COAP"); - // would enable only the COAP level traces. - // Or mbed_trace_exclude_filters_set("COAP"); - // would leave them out. - // More details on mbed_trace.h file. - -#ifndef MCC_MINIMAL + if (mbed_trace_init() != 0) { + printf("ERROR - mbed_trace_init failed!\n"); + return false; + } + +#ifndef PDMC_EXAMPLE_MINIMAL mbed_trace_mutex_wait_function_set(mbed_trace_helper_mutex_wait); mbed_trace_mutex_release_function_set(mbed_trace_helper_mutex_release); #endif @@ -197,10 +217,11 @@ bool application_init_mbed_trace(void) mbed_trace_print_function_set(trace_printer); #endif - return 0; + + return true; } -static bool application_init_verify_cloud_configuration() +static bool verify_cloud_configuration() { int status; bool result = 0; @@ -216,7 +237,7 @@ static bool application_init_verify_cloud_configuration() result = 1; } #endif -#ifndef MCC_MINIMAL +#ifndef PDMC_EXAMPLE_MINIMAL #if MBED_CONF_APP_DEVELOPER_MODE == 1 status = fcc_verify_device_configured_4mbed_cloud(); print_fcc_status(status); @@ -228,24 +249,24 @@ static bool application_init_verify_cloud_configuration() return result; } -static bool application_init_fcc(void) +static bool initialize_fcc(void) { int status; - status = mcc_platform_fcc_init(); - if(status != FCC_STATUS_SUCCESS) { - printf("application_init_fcc fcc_init failed with status %d! - exit\r\n", status); + status = fcc_initialize(); + if (status != FCC_STATUS_SUCCESS) { + printf("initialize_fcc fcc_init failed with status %d! - exit\r\n", status); return 1; } #if RESET_STORAGE - status = mcc_platform_reset_storage(); - if(status != FCC_STATUS_SUCCESS) { - printf("application_init_fcc reset_storage failed with status %d! - exit\r\n", status); + status = reset_storage(); + if (status != FCC_STATUS_SUCCESS) { + printf("initialize_fcc reset_storage failed with status %d! - exit\r\n", status); return 1; } // Reinitialize SOTP - status = mcc_platform_sotp_init(); + status = sotp_initialize(); if (status != FCC_STATUS_SUCCESS) { - printf("application_init_fcc sotp_init failed with status %d! - exit\r\n", status); + printf("initialize_fcc sotp_init failed with status %d! - exit\r\n", status); return 1; } #endif @@ -258,22 +279,22 @@ static bool application_init_fcc(void) return 1; } #endif - status = application_init_verify_cloud_configuration(); + status = verify_cloud_configuration(); if (status != 0) { -#ifndef MCC_MINIMAL - // This is designed to simplify user-experience by auto-formatting the - // primary storage if no valid certificates exist. - // This should never be used for any kind of production devices. +#ifndef PDMC_EXAMPLE_MINIMAL + // This is designed to simplify user-experience by auto-formatting the + // primary storage if no valid certificates exist. + // This should never be used for any kind of production devices. #ifndef MBED_CONF_APP_MCC_NO_AUTO_FORMAT - status = mcc_platform_reset_storage(); + status = reset_storage(); if (status != FCC_STATUS_SUCCESS) { return 1; } - status = mcc_platform_sotp_init(); + status = sotp_initialize(); if (status != FCC_STATUS_SUCCESS) { return 1; } - status = application_init_verify_cloud_configuration(); + status = verify_cloud_configuration(); if (status != 0) { return 1; } @@ -302,21 +323,84 @@ bool application_init(void) printf("Start Device Management Client\r\n"); - if (application_init_fcc() != 0) { - printf("Failed initializing FCC\r\n" ); + if (initialize_fcc() != 0) { + printf("Failed initializing FCC\r\n"); return false; } return true; } -void wait_application_startup_delay() +static int reset_storage(void) { -#if (STARTUP_MIN_RANDOM_DELAY > STARTUP_MAX_RANDOM_DELAY) -#error "STARTUP_MAX_RANDOM_DELAY must be larger than STARTUP_MIN_RANDOM_DELAY" +#if MBED_CONF_APP_DEVELOPER_MODE == 1 + printf("Resets storage to an empty state.\r\n"); + int status = fcc_storage_delete(); + if (status != FCC_STATUS_SUCCESS) { + printf("Failed to delete storage - %d\r\n", status); + } + return status; +#else + return FCC_STATUS_SUCCESS; +#endif +} + +static int fcc_initialize(void) +{ +#if MBED_CONF_APP_DEVELOPER_MODE == 1 + int status = fcc_init(); + // Ignore pre-existing RoT/Entropy in SOTP + if (status != FCC_STATUS_SUCCESS && status != FCC_STATUS_ENTROPY_ERROR && status != FCC_STATUS_ROT_ERROR) { + printf("fcc_initialize failed with status %d! - exit\r\n", status); + return status; + } + status = sotp_initialize(); + if (status != FCC_STATUS_SUCCESS) { + printf("fcc_initialize failed sotp_initialize() with status %d! - exit\r\n", status); +#if MBED_CONF_APP_DEVELOPER_MODE == 1 + (void)fcc_finalize(); +#endif + } else { + // We can return SUCCESS here as preexisting RoT/Entropy is expected flow. + status = FCC_STATUS_SUCCESS; + } + return status; +#else + return FCC_STATUS_SUCCESS; #endif - randLIB_seed_random(); - uint16_t delay = randLIB_get_random_in_range(STARTUP_MIN_RANDOM_DELAY, STARTUP_MAX_RANDOM_DELAY); - printf("Delaying registration by %d seconds\r\n", delay); - mcc_platform_do_wait(delay * 1000); +} + +static int sotp_initialize(void) +{ + int status = FCC_STATUS_SUCCESS; +// Include this only for Developer mode and a device which doesn't have in-built TRNG support. +#if MBED_CONF_APP_DEVELOPER_MODE == 1 +#if defined (PAL_USER_DEFINED_CONFIGURATION) && !PAL_USE_HW_TRNG + status = fcc_entropy_set(MBED_CLOUD_DEV_ENTROPY, FCC_ENTROPY_SIZE); + + if (status != FCC_STATUS_SUCCESS && status != FCC_STATUS_ENTROPY_ERROR) { + printf("fcc_entropy_set failed with status %d! - exit\r\n", status); +#if MBED_CONF_APP_DEVELOPER_MODE == 1 + (void)fcc_finalize(); +#endif + return status; + } +#endif // PAL_USE_HW_TRNG = 0 + /* Include this only for Developer mode. The application will use fixed RoT to simplify user-experience with the application. + * With this change the application be reflashed/SOTP can be erased safely without invalidating the application credentials. + */ + status = fcc_rot_set(MBED_CLOUD_DEV_ROT, FCC_ROT_SIZE); + + if (status != FCC_STATUS_SUCCESS && status != FCC_STATUS_ROT_ERROR) { + printf("fcc_rot_set failed with status %d! - exit\r\n", status); +#if MBED_CONF_APP_DEVELOPER_MODE == 1 + (void)fcc_finalize(); +#endif + } else { + // We can return SUCCESS here as preexisting RoT/Entropy is expected flow. + printf("Using hardcoded Root of Trust, not suitable for production use.\r\n"); + status = FCC_STATUS_SUCCESS; + } +#endif // #if MBED_CONF_APP_DEVELOPER_MODE == 1 + return status; } diff --git a/source/application_init.h b/source/application_init.h index 93856d2..04b2e20 100644 --- a/source/application_init.h +++ b/source/application_init.h @@ -1,5 +1,5 @@ // ---------------------------------------------------------------------------- -// Copyright 2016-2019 ARM Ltd. +// Copyright 2016-2021 Pelion. // // SPDX-License-Identifier: Apache-2.0 // @@ -16,22 +16,12 @@ // limitations under the License. // ---------------------------------------------------------------------------- - #ifndef APPLICATION_INIT_H #define APPLICATION_INIT_H -#ifndef STARTUP_MAX_RANDOM_DELAY -#define STARTUP_MAX_RANDOM_DELAY 0 -#endif - -#ifndef STARTUP_MIN_RANDOM_DELAY -#define STARTUP_MIN_RANDOM_DELAY STARTUP_MAX_RANDOM_DELAY/4 -#endif - /* * Initializes tracing library. */ - bool application_init_mbed_trace(void); /* @@ -40,25 +30,7 @@ bool application_init_mbed_trace(void); * 2. print memory statistics if MEMORY_TESTS_HEAP is defined * 3. FCC initialization. */ - bool application_init(void); -/* - * Prints the FCC status and corresponding error description, if any. - */ -void print_fcc_status(int fcc_status); - -/* - * Wait for random delay with maximum defined using STARTUP_MAX_RANDOM_DELAY. - * Lower limit can be defined via STARTUP_MIN_RANDOM_DELAY. The lower limit defaults to - * STARTUP_MAX_RANDOM_DELAY/4. - * The delay is needed for devices connected to a large network with high latency - * and constrained bandwidth. - * For example in Wi-SUN, this stabilizes the early network formation when all - * clients do not register simultaneously. - */ -void wait_application_startup_delay(); - - #endif //APPLICATION_INIT_H diff --git a/source/blinky.cpp b/source/blinky.cpp index b004303..467019c 100644 --- a/source/blinky.cpp +++ b/source/blinky.cpp @@ -1,5 +1,5 @@ // ---------------------------------------------------------------------------- -// Copyright 2018-2020 ARM Ltd. +// Copyright 2018-2021 Pelion. // // SPDX-License-Identifier: Apache-2.0 // @@ -16,22 +16,19 @@ // limitations under the License. // ---------------------------------------------------------------------------- -#include "blinky.h" +#include +#include +#include + +#include "blinky.h" #include "sal-stack-nanostack-eventloop/nanostack-event-loop/eventOS_event.h" #include "sal-stack-nanostack-eventloop/nanostack-event-loop/eventOS_event_timer.h" #include "ns-hal-pal/ns_hal_init.h" -#include "mbed-trace/mbed_trace.h" - #include "mcc_common_button_and_led.h" -#include "simplem2mclient.h" +#include "pdmc_example.h" #include "m2mresource.h" -#include -#include - -#define TRACE_GROUP "blky" - #define BLINKY_TASKLET_LOOP_INIT_EVENT 0 #define BLINKY_TASKLET_PATTERN_INIT_EVENT 1 #define BLINKY_TASKLET_PATTERN_TIMER 2 @@ -50,27 +47,26 @@ int8_t Blinky::_tasklet = -1; extern "C" { -static void blinky_event_handler_wrapper(arm_event_s *event) -{ - assert(event); - if (event->event_type != BLINKY_TASKLET_LOOP_INIT_EVENT) { - // the init event will not contain instance pointer - Blinky *instance = (Blinky *)event->data_ptr; - if(instance) { - instance->event_handler(*event); + static void blinky_event_handler_wrapper(arm_event_s *event) + { + assert(event); + if (event->event_type != BLINKY_TASKLET_LOOP_INIT_EVENT) { + // the init event will not contain instance pointer + Blinky *instance = (Blinky *)event->data_ptr; + if (instance) { + instance->event_handler(*event); + } } } -} } Blinky::Blinky() -: _pattern(NULL), - _curr_pattern(NULL), - _client(NULL), - _button_resource(NULL), - _state(STATE_IDLE), - _restart(false) + : _pattern(NULL), + _curr_pattern(NULL), + _button_resource(NULL), + _state(STATE_IDLE), + _restart(false) { _button_count = 0; } @@ -90,21 +86,20 @@ void Blinky::create_tasklet() } // use references to encourage caller to pass this existing object -void Blinky::init(SimpleM2MClient &client, M2MResource *resource) +void Blinky::init(M2MResource *resource) { // Do not start if resource has not been allocated. if (!resource) { return; } - _client = &client; _button_resource = resource; // create the tasklet, if not done already create_tasklet(); } -bool Blinky::start(const char* pattern, size_t length, bool pattern_restart) +bool Blinky::start(const char *pattern, size_t length, bool pattern_restart) { assert(pattern); @@ -116,7 +111,7 @@ bool Blinky::start(const char* pattern, size_t length, bool pattern_restart) // allow one to start multiple times before previous sequence has completed stop(); - _pattern = (char*)malloc(length+1); + _pattern = (char *)malloc(length + 1); if (_pattern == NULL) { return false; } @@ -153,7 +148,7 @@ int Blinky::get_next_int() } else if (*endptr == '\0') { // end of result = conv_result; } else { - tr_debug("invalid char %c", *endptr); + printf("invalid char %c\n", *endptr); } } @@ -166,8 +161,6 @@ bool Blinky::run_step() { int32_t delay = get_next_int(); - // tr_debug("patt: %s, curr: %s, delay: %d", _pattern, _curr_pattern, delay); - if (delay < 0) { _state = STATE_IDLE; return false; @@ -209,7 +202,6 @@ void Blinky::handle_pattern_event() bool success = run_step(); if ((!success) && (_restart)) { - // tr_debug("Blinky restart pattern"); _curr_pattern = _pattern; run_step(); } @@ -249,19 +241,18 @@ bool Blinky::request_timed_event(uint8_t event_type, arm_library_event_priority_ void Blinky::handle_buttons() { - assert(_client); assert(_button_resource); // this might be stopped now, but the loop should then be restarted after re-registration request_next_loop_event(); - if (_client->is_client_registered()) { + if (pdmc_registered()) { if (mcc_platform_button_clicked()) { #ifdef MBED_CLOUD_CLIENT_TRANSPORT_MODE_UDP_QUEUE - if(_client->is_client_paused()) { - printf("Calling Pelion Client resumed()\r\n"); - _client->client_resumed(); - } + if (pdmc_paused()) { + printf("Calling Pelion Client resumed()\r\n"); + pdmc_resume(); + } #endif _button_count = _button_resource->get_value_int() + 1; _button_resource->set_value(_button_count); @@ -272,17 +263,16 @@ void Blinky::handle_buttons() void Blinky::handle_automatic_increment() { - assert(_client); assert(_button_resource); // this might be stopped now, but the loop should then be restarted after re-registration request_automatic_increment_event(); - if (_client->is_client_registered()) { + if (pdmc_registered()) { #ifdef MBED_CLOUD_CLIENT_TRANSPORT_MODE_UDP_QUEUE - if(_client->is_client_paused()) { + if (pdmc_paused()) { printf("Calling Pelion Client resumed()\r\n"); - _client->client_resumed(); + pdmc_resume(); } #endif _button_count = _button_resource->get_value_int() + 1; diff --git a/source/blinky.h b/source/blinky.h index 4cda8fe..f4b4a46 100644 --- a/source/blinky.h +++ b/source/blinky.h @@ -21,13 +21,11 @@ #include "sal-stack-nanostack-eventloop/nanostack-event-loop/eventOS_event.h" -class SimpleM2MClient; class M2MResource; #include -class Blinky -{ +class Blinky { typedef enum { STATE_IDLE, STATE_STARTED, @@ -38,9 +36,9 @@ class Blinky ~Blinky(); - void init(SimpleM2MClient &client, M2MResource *resource); + void init(M2MResource *resource); - bool start(const char* pattern, size_t length, bool pattern_restart); + bool start(const char *pattern, size_t length, bool pattern_restart); void stop(); @@ -68,8 +66,6 @@ class Blinky char *_pattern; const char *_curr_pattern; - SimpleM2MClient *_client; - M2MResource *_button_resource; int _button_count; diff --git a/source/certificate_enrollment_user_cb.cpp b/source/certificate_enrollment_user_cb.cpp index d827f0d..7a530f9 100644 --- a/source/certificate_enrollment_user_cb.cpp +++ b/source/certificate_enrollment_user_cb.cpp @@ -16,7 +16,7 @@ // limitations under the License. // ---------------------------------------------------------------------------- -#include "simplem2mclient.h" +#include #include "certificate_enrollment_user_cb.h" #ifndef MBED_CONF_MBED_CLOUD_CLIENT_DISABLE_CERTIFICATE_ENROLLMENT diff --git a/source/fota_platform.c b/source/fota_platform.c deleted file mode 100644 index 20c7f16..0000000 --- a/source/fota_platform.c +++ /dev/null @@ -1,53 +0,0 @@ -// ---------------------------------------------------------------------------- -// Copyright 2020 ARM Ltd. -// -// SPDX-License-Identifier: Apache-2.0 -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -// ---------------------------------------------------------------------------- - -#include "fota/fota_base.h" - -#ifdef MBED_CLOUD_CLIENT_FOTA_ENABLE - -#define TRACE_GROUP "FOTA" - -#include "fota/fota_app_ifs.h" // required for implementing custom install callback for Linux like targets -#include -#include - - -#if defined(TARGET_LIKE_LINUX) && !defined(USE_ACTIVATION_SCRIPT) // e.g. Yocto target have different update activation logic residing outside of the example -// Simplified Linux use case example. -// For MAIN component update the the binary file current process is running. -// Simulate component update by just printing its name. -// After the installation callback returns, FOTA will "reboot" by calling pal_osReboot(). - -int fota_app_on_install_candidate(const char *candidate_fs_name, const manifest_firmware_info_t *firmware_info) -{ - int ret = FOTA_STATUS_SUCCESS; - if (0 == strncmp(FOTA_COMPONENT_MAIN_COMPONENT_NAME, firmware_info->component_name, FOTA_COMPONENT_MAX_NAME_SIZE)) { - // installing MAIN component - ret = fota_app_install_main_app(candidate_fs_name); - if (FOTA_STATUS_SUCCESS == ret) { - FOTA_APP_PRINT("Successfully installed MAIN component\n"); - // FOTA does support a case where installer method reboots the system. - } - } else { - FOTA_APP_PRINT("%s component installed (example)\n", firmware_info->component_name); - } - return ret; -} -#endif // defined(TARGET_LIKE_LINUX) && !defined(USE_ACTIVATION_SCRIPT) - -#endif // MBED_CLOUD_CLIENT_FOTA_ENABLE diff --git a/source/fota_platform_hooks_impl.cpp b/source/fota_platform_hooks_impl.cpp new file mode 100644 index 0000000..e2c71c6 --- /dev/null +++ b/source/fota_platform_hooks_impl.cpp @@ -0,0 +1,166 @@ +// ---------------------------------------------------------------------------- +// Copyright 2021 Pelion Ltd. +// +// SPDX-License-Identifier: Apache-2.0 +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// ---------------------------------------------------------------------------- + +#include "mbed-cloud-client/MbedCloudClient.h" +#if (defined(MBED_CLOUD_CLIENT_FOTA_ENABLE) && (MBED_CLOUD_CLIENT_FOTA_ENABLE)) + + +#include "fota/fota_app_ifs.h" +#include "fota/fota_platform_hooks.h" +#if defined(TARGET_LIKE_LINUX) && (MBED_CLOUD_CLIENT_FOTA_SUB_COMPONENT_SUPPORT == 1) +#include "fota/fota_sub_component.h" +#endif + +#if defined(FOTA_CUSTOM_PLATFORM) + +static fota_component_desc_info_t external_component_info; + + +/* Callback examples */ + +#if defined(TARGET_LIKE_LINUX) && (MBED_CLOUD_CLIENT_FOTA_SUB_COMPONENT_SUPPORT == 1) +/*Subcomponent callbacks*/ +int sub_component_rollback_handler(const char *comp_name, const char *sub_comp_name, const uint8_t *vendor_data, size_t vendor_data_size, void *app_ctx) +{ + printf("sub_component_rollback_handler sub_comp_name: %s, vendor_data: %.*s", sub_comp_name, (int)vendor_data_size, vendor_data); + return FOTA_STATUS_SUCCESS; +} + +int sub_component_finalize_handler(const char *comp_name, const char *sub_comp_name, const uint8_t *vendor_data, size_t vendor_data_size, fota_status_e fota_status, void *app_ctx) +{ + printf("sub_component_finalize_handler sub_comp_name: %s, vendor_data: %.*s", sub_comp_name, (int)vendor_data_size, vendor_data); + return FOTA_STATUS_SUCCESS; +} +#endif //#if defined(TARGET_LIKE_LINUX) && (MBED_CLOUD_CLIENT_FOTA_SUB_COMPONENT_SUPPORT == 1) + +static void print_component_info(const char *comp_name, const char *sub_comp_name, const uint8_t *vendor_data, size_t vendor_data_size) +{ + printf("%s component installed\n", comp_name); + if (sub_comp_name) { + printf("sub_comp_name: %s\n", sub_comp_name); + } + if (vendor_data) { + printf("vendor_data: %.*s\n", (int)vendor_data_size, vendor_data); + } +} + +static int pdmc_component_verifier(const char *comp_name, const char *sub_comp_name, const uint8_t *vendor_data, size_t vendor_data_size, void* app_ctx) +{ + printf("pdmc_component_verifier called for %s\n", comp_name); + print_component_info(comp_name, sub_comp_name, vendor_data, vendor_data_size); + return FOTA_STATUS_SUCCESS; +} + +#if !defined(TARGET_LIKE_LINUX) +static int pdmc_component_installer(const char *comp_name, const char *sub_comp_name, fota_comp_candidate_iterate_callback_info *info, const uint8_t *vendor_data, size_t vendor_data_size, void *app_ctx) +{ + switch (info->status) { + case FOTA_CANDIDATE_ITERATE_START: + printf("fota candidate iterate start \n"); + return FOTA_STATUS_SUCCESS; + case FOTA_CANDIDATE_ITERATE_FRAGMENT: + printf("."); + return FOTA_STATUS_SUCCESS; + case FOTA_CANDIDATE_ITERATE_FINISH: + printf("\nfota candidate iterate finish \n"); + printf("\nApplication received external update\n"); // Use same phrase than in UCHub case. Test case is polling this line. + print_component_info(comp_name, sub_comp_name, vendor_data, vendor_data_size); + return FOTA_STATUS_SUCCESS; + default: + return FOTA_STATUS_INTERNAL_ERROR; + } + return FOTA_STATUS_SUCCESS; +} +#else +static int pdmc_component_installer(const char *comp_name, const char *sub_comp_name, const char *file_name, const uint8_t *vendor_data, size_t vendor_data_size, void *app_ctx) +{ + print_component_info(comp_name, sub_comp_name, vendor_data, vendor_data_size); + return FOTA_STATUS_SUCCESS; +} +#endif + +/* Platform hooks implementation */ +int fota_platform_init_hook(bool after_upgrade) +{ + int ret = 0; + + external_component_info.install_alignment = 1; + external_component_info.support_delta = false; + external_component_info.need_reboot = true; + external_component_info.component_verify_install_cb = NULL; + external_component_info.component_verify_cb = pdmc_component_verifier; +#if !defined(TARGET_LIKE_LINUX) + external_component_info.candidate_iterate_cb = NULL; +#endif + external_component_info.component_install_cb = pdmc_component_installer; + external_component_info.component_finalize_cb = NULL; + + external_component_info.curr_fw_read = 0; // only needed if support_delta = true + external_component_info.curr_fw_get_digest = 0; // only needed if support_delta = true + + ret = fota_component_add(&external_component_info, "METER", "0.0.0"); + +#if defined(TARGET_LIKE_LINUX) && (MBED_CLOUD_CLIENT_FOTA_SUB_COMPONENT_SUPPORT == 1) + printf("Add sub components\n"); + + fota_sub_comp_info_t dummy_sub_component_desc = { 0 }; + dummy_sub_component_desc.finalize_cb = sub_component_finalize_handler; + dummy_sub_component_desc.finalize_order = 1; + dummy_sub_component_desc.install_cb= pdmc_component_installer; + dummy_sub_component_desc.install_order = 1; + dummy_sub_component_desc.rollback_cb = sub_component_rollback_handler; + dummy_sub_component_desc.rollback_order = 2; + dummy_sub_component_desc.verify_cb= pdmc_component_verifier; + dummy_sub_component_desc.verify_order = 1; + ret = fota_sub_component_add("MAIN","img1_id", &dummy_sub_component_desc); //Component MAIN registered by default during fota initialization, no need to call `fota_component_add` for MAIN component. + if (ret != 0){ + return ret; + } + + fota_sub_comp_info_t dummy_sub_component_desc2 = { 0 }; + dummy_sub_component_desc2.finalize_cb = sub_component_finalize_handler; + dummy_sub_component_desc2.finalize_order = 2; + dummy_sub_component_desc2.install_cb = pdmc_component_installer; + dummy_sub_component_desc2.install_order = 2; + dummy_sub_component_desc2.rollback_cb = sub_component_rollback_handler; + dummy_sub_component_desc2.rollback_order = 1; + dummy_sub_component_desc2.verify_cb = pdmc_component_verifier; + dummy_sub_component_desc2.verify_order = 2; + ret = fota_sub_component_add("MAIN","img2_id", &dummy_sub_component_desc2);//Component MAIN registered by default during fota initialization, no need to call `fota_component_add` for MAIN component. +#endif + + return ret; +} + +int fota_platform_start_update_hook(const char *comp_name) +{ + return FOTA_STATUS_SUCCESS; +} + +int fota_platform_finish_update_hook(const char *comp_name) +{ + return FOTA_STATUS_SUCCESS; +} + +int fota_platform_abort_update_hook(const char *comp_name) +{ + return FOTA_STATUS_SUCCESS; +} + +#endif //#if defined(FOTA_CUSTOM_PLATFORM) +#endif //#if (defined(MBED_CLOUD_CLIENT_FOTA_ENABLE) && (MBED_CLOUD_CLIENT_FOTA_ENABLE)) diff --git a/source/fota_platform_mesh_component.cpp b/source/fota_platform_ifs_imp.cpp similarity index 56% rename from source/fota_platform_mesh_component.cpp rename to source/fota_platform_ifs_imp.cpp index 5f067a2..176e816 100644 --- a/source/fota_platform_mesh_component.cpp +++ b/source/fota_platform_ifs_imp.cpp @@ -15,15 +15,18 @@ // See the License for the specific language governing permissions and // limitations under the License. // ---------------------------------------------------------------------------- +#include +#include -#include "mbed-cloud-client/MbedCloudClient.h" +#ifdef MBED_CLOUD_CLIENT_FOTA_ENABLE -#if defined(MBED_CLOUD_CLIENT_FOTA_MULTICAST_SUPPORT) && (MBED_CLOUD_CLIENT_FOTA_MULTICAST_SUPPORT != 0) && defined(FOTA_CUSTOM_PLATFORM) && (defined(TARGET_LIKE_MBED)) -#include "fota_app_ifs.h" -#include "fota_platform_hooks.h" +#define TRACE_GROUP "FOTA" -static fota_component_desc_info_t external_component_info; +#include "fota/fota_app_ifs.h" // required for implementing custom install callback for Linux like targets +#include +#include +#if !(defined (FOTA_DEFAULT_APP_IFS) && FOTA_DEFAULT_APP_IFS==1) int fota_app_on_complete(int32_t status) { if (status == FOTA_STATUS_SUCCESS) { @@ -53,7 +56,7 @@ int fota_app_on_install_authorization() return FOTA_STATUS_SUCCESS; } -int fota_app_on_download_authorization( +int fota_app_on_download_authorization( const manifest_firmware_info_t *candidate_info, fota_component_version_t curr_fw_version) { @@ -87,57 +90,31 @@ int fota_app_on_download_authorization( return FOTA_STATUS_SUCCESS; } +#endif //#if !(defined (FOTA_DEFAULT_APP_IFS) && FOTA_DEFAULT_APP_IFS==1) -static int install_iterate_handler(fota_candidate_iterate_callback_info *info) -{ - switch (info->status) { - case FOTA_CANDIDATE_ITERATE_START: - printf("fota candidate iterate start \n"); - return FOTA_STATUS_SUCCESS; - case FOTA_CANDIDATE_ITERATE_FRAGMENT: - printf("."); - return FOTA_STATUS_SUCCESS; - case FOTA_CANDIDATE_ITERATE_FINISH: - printf("\nfota candidate iterate finish \n"); - printf("\nApplication received external update\n"); // Use same phrase than in UCHub case. Test case is polling this line. - return FOTA_STATUS_SUCCESS; - default: - return FOTA_STATUS_INTERNAL_ERROR; - } - return 0; -} -static int pdmc_component_verifier(const char *comp_name, const fota_header_info_t *expected_header_info) -{ - printf("pdmc_component_verifier called for %s\n", comp_name); - return FOTA_STATUS_SUCCESS; -} - -int fota_platform_init_hook(bool after_upgrade) -{ - external_component_info.install_alignment = 1; - external_component_info.support_delta = false; - external_component_info.need_reboot = true; - external_component_info.component_verify_install_cb = pdmc_component_verifier; - external_component_info.curr_fw_read = 0; // only needed if support_delta = true - external_component_info.curr_fw_get_digest = 0; // only needed if support_delta = true - external_component_info.candidate_iterate_cb = install_iterate_handler; - - return fota_component_add(&external_component_info, "METER", "0.0.0"); -} +#if defined(TARGET_LIKE_LINUX) && !defined(USE_ACTIVATION_SCRIPT) // e.g. Yocto target have different update activation logic residing outside of the example +// Simplified Linux use case example. +// For MAIN component update the the binary file current process is running. +// Simulate component update by just printing its name. +// After the installation callback returns, FOTA will "reboot" by calling pal_osReboot(). -int fota_platform_start_update_hook(const char *comp_name) +int fota_app_on_install_candidate(const char *candidate_fs_name, const manifest_firmware_info_t *firmware_info) { - return FOTA_STATUS_SUCCESS; + int ret = FOTA_STATUS_SUCCESS; + if (0 == strncmp(FOTA_COMPONENT_MAIN_COMPONENT_NAME, firmware_info->component_name, FOTA_COMPONENT_MAX_NAME_SIZE)) { + // installing MAIN component + ret = fota_app_install_main_app(candidate_fs_name); + if (FOTA_STATUS_SUCCESS == ret) { + FOTA_APP_PRINT("Successfully installed MAIN component\n"); + // FOTA does support a case where installer method reboots the system. + } + } else { + FOTA_APP_PRINT("fota_app_on_install_candidate deprecated for component %s, use component_install_cb\n", firmware_info->component_name); + } + return ret; } +#endif // defined(TARGET_LIKE_LINUX) && !defined(USE_ACTIVATION_SCRIPT) -int fota_platform_finish_update_hook(const char *comp_name) -{ - return FOTA_STATUS_SUCCESS; -} +#endif // MBED_CLOUD_CLIENT_FOTA_ENABLE -int fota_platform_abort_update_hook(const char *comp_name) -{ - return FOTA_STATUS_SUCCESS; -} -#endif diff --git a/source/include/app_platform_setup.h b/source/include/app_platform_setup.h deleted file mode 100644 index 985529c..0000000 --- a/source/include/app_platform_setup.h +++ /dev/null @@ -1,44 +0,0 @@ -/* - * Copyright (c) 2015-2018 ARM Limited. All rights reserved. - * SPDX-License-Identifier: Apache-2.0 - * Licensed under the Apache License, Version 2.0 (the License); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an AS IS BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef APP_PLATFORM_SETUP_H -#define APP_PLATFORM_SETUP_H - -#include - -#ifdef __cplusplus -extern "C" { -#endif - -// Erases client credentials and SOTP storage, will also reformat -// the external storage for Mbed OS if initial erase fail. -int mcc_platform_reset_storage(void); - -// Initialize common details for fcc. -int mcc_platform_fcc_init(void); - -// For developer-mode only, (re)initializes the RoT and for non-TRNG boards -// also the entropy. -int mcc_platform_sotp_init(void); - -// Reverse the resource allocations done by mcc_platform_fcc_init(). -void mcc_platform_fcc_finalize(void); - -#ifdef __cplusplus -} -#endif - -#endif // #ifndef APP_PLATFORM_SETUP_H diff --git a/source/pdmc_example.cpp b/source/pdmc_example.cpp new file mode 100644 index 0000000..4f19b61 --- /dev/null +++ b/source/pdmc_example.cpp @@ -0,0 +1,573 @@ +// ---------------------------------------------------------------------------- +// Copyright 2016-2021 Pelion. +// +// SPDX-License-Identifier: Apache-2.0 +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// ---------------------------------------------------------------------------- + +#include + +#include "pdmc_example.h" +#include "mcc_common_setup.h" +#include "MbedCloudClient.h" +#include "m2mresource.h" +#include "m2minterfacefactory.h" +#include "key_config_manager.h" +#include "factory_configurator_client.h" +#include "mbed-client/m2minterface.h" + +#ifndef MBED_CONF_MBED_CLOUD_CLIENT_DISABLE_CERTIFICATE_ENROLLMENT +#include "certificate_enrollment_user_cb.h" +#endif + +#ifdef MBED_CLOUD_CLIENT_SUPPORT_UPDATE +#include "update_ui_example.h" +#endif + +#if defined (MEMORY_TESTS_HEAP) +#include "memory_tests.h" +#endif + +// This defines how many consecutive errors can occur before application will perform reboot as recovery. +// Set to 0 to disable the feature. +#ifndef MAX_ERROR_COUNT +#define MAX_ERROR_COUNT 5 +#endif + +// Resource callback functions +static void button_counter_updated(const char *); +static void blink_pattern_updated(const char *); +static void blink_cb(void *); +static void factory_reset_cb(void *); +static void delivery_status_cb(const M2MBase &object, const M2MBase::MessageDeliveryStatus status, const M2MBase::MessageType type); +static void large_res_sent_cb(const M2MBase &base, const M2MBase::MessageDeliveryStatus status, const M2MBase::MessageType type); +static coap_response_code_e large_res_read_requested(const M2MResourceBase &resource, uint8_t *&buffer, size_t &buffer_size, size_t &total_size, const size_t offset, void *client_args); + +// PDMC callback functions +static void pdmc_error_handler(int error_code); +static void pdmc_status_handler(int status); + +#ifdef MBED_CLOUD_CLIENT_SUPPORT_MULTICAST_UPDATE +static void pdmc_external_update_cb(uint32_t start_address, uint32_t size); +#endif // MBED_CLOUD_CLIENT_SUPPORT_MULTICAST_UPDATE + +// Helper methods +static void reboot_if_threshold_value(int threshold); + +// Global variables +#ifndef PDMC_EXAMPLE_MINIMAL +#include "blinky.h" +static Blinky blinky; +#endif + +static MbedCloudClient pdmc_client; +static M2MObjectList object_list; +static bool register_called = false; +static bool registered = false; +static int error_count = 0; +volatile bool paused = false; +static uint8_t *large_res_data = NULL; +const static int16_t large_res_size = 2049; + +// Pointers to the resources that will be created in main_application(). +static M2MResource *button_res; +static M2MResource *pattern_res; +static M2MResource *blink_res; +static M2MResource *factory_reset_res; +static M2MResource *large_res; + +void pdmc_init() +{ + pdmc_client.init(); +} + +void pdmc_close() +{ + pdmc_client.close(); +} + +void pdmc_resume() +{ + paused = false; + int timeout_ms = 5000; + while (-1 == mcc_platform_interface_connect()) { + // Will try to connect using mcc_platform_interface_connect until error count and then does reboot if + // not successful. Wait timeout is always doubled + printf("Network did not recover after pause. Try again after %d milliseconds.\n", timeout_ms); + mcc_platform_do_wait(timeout_ms); + timeout_ms *= 2; + reboot_if_threshold_value(MAX_PDMC_CLIENT_CONNECTION_ERROR_COUNT); + } + + pdmc_client.resume(mcc_platform_get_network_interface()); +} + +bool pdmc_connect() +{ +#if defined (MEMORY_TESTS_HEAP) && !defined(PDMC_EXAMPLE_MINIMAL) + // Add some test resources to measure memory consumption. + // This code is activated only if MEMORY_TESTS_HEAP is defined. + create_m2mobject_test_set(object_list); +#endif + + pdmc_client.add_objects(object_list); + + pdmc_client.on_error(&pdmc_error_handler); + pdmc_client.on_status_changed(&pdmc_status_handler); + +#ifdef MBED_CLOUD_CLIENT_SUPPORT_MULTICAST_UPDATE + pdmc_client.on_external_update(pdmc_external_update_cb); +#endif + +#ifndef MBED_CONF_MBED_CLOUD_CLIENT_DISABLE_CERTIFICATE_ENROLLMENT + pdmc_client.on_certificate_renewal(certificate_renewal_cb); +#endif + +#ifdef MBED_CLOUD_CLIENT_SUPPORT_UPDATE + /* Set callback functions for authorizing updates and monitoring progress. + Code is implemented in update_ui_example.cpp + Both callbacks are completely optional. If no authorization callback + is set, the update process will procede immediately in each step. + */ + update_ui_set_cloud_client(&pdmc_client); + pdmc_client.set_update_authorize_priority_handler(update_authorize_priority_handler); + pdmc_client.set_update_progress_handler(update_progress); +#endif + + bool setup = pdmc_client.setup(mcc_platform_get_network_interface()); + register_called = true; + if (!setup) { + printf("PDMC setup failed\n"); + return false; + } + +#ifndef PDMC_EXAMPLE_MINIMAL + blinky.init(button_res); + blinky.request_next_loop_event(); + blinky.request_automatic_increment_event(); +#endif + +#ifdef MEMORY_TESTS_HEAP + printf("Register being called\r\n"); + print_heap_stats(); +#endif + + return true; +} + +M2MObjectList *pdmc_get_object_list() +{ + return &object_list; +} + +bool pdmc_registered() +{ + return registered; +} + +bool pdmc_paused() +{ + return paused; +} + +bool pdmc_register_called() +{ + return register_called; +} + +/** PDMC callback functions --> **/ + +static void pdmc_status_handler(int status) +{ + switch (status) { + case MbedCloudClient::Registered: + printf("Client registered\r\n"); + registered = true; + error_count = 0; + static const ConnectorClientEndpointInfo *endpoint = NULL; + if (endpoint == NULL) { + endpoint = pdmc_client.endpoint_info(); + if (endpoint) { +#if MBED_CONF_APP_DEVELOPER_MODE == 1 + printf("Endpoint Name: %s\r\n", endpoint->internal_endpoint_name.c_str()); +#else + printf("Endpoint Name: %s\r\n", endpoint->endpoint_name.c_str()); +#endif + printf("Device ID: %s\r\n", endpoint->internal_endpoint_name.c_str()); + } + } +#ifdef MEMORY_TESTS_HEAP + print_heap_stats(); +#endif + break; + + case MbedCloudClient::Unregistered: + paused = false; + registered = false; + register_called = false; + printf("Client unregistered - Exiting application\n"); +#ifdef MEMORY_TESTS_HEAP + print_heap_stats(); +#endif + break; + + case MbedCloudClient::RegistrationUpdated: + printf("Client registration updated\n"); + error_count = 0; + break; + + case MbedCloudClient::Paused: + break; + + case MbedCloudClient::AlertMode: + break; + + case MbedCloudClient::Sleep: + printf("Pelion client is going to sleep - Pausing the client\r\n"); + pdmc_client.pause(); + mcc_platform_interface_close(); + paused = true; + default: + break; + } +} + +static void pdmc_error_handler(int error_code) +{ + const char *error; + switch (error_code) { + case MbedCloudClient::ConnectErrorNone: + error = "MbedCloudClient::ConnectErrorNone"; + break; + case MbedCloudClient::ConnectAlreadyExists: + error = "MbedCloudClient::ConnectAlreadyExists"; + break; + case MbedCloudClient::ConnectBootstrapFailed: + error = "MbedCloudClient::ConnectBootstrapFailed"; + break; + case MbedCloudClient::ConnectInvalidParameters: + error = "MbedCloudClient::ConnectInvalidParameters"; + break; + case MbedCloudClient::ConnectNotRegistered: + error = "MbedCloudClient::ConnectNotRegistered"; + break; + case MbedCloudClient::ConnectTimeout: + error = "MbedCloudClient::ConnectTimeout"; + break; + case MbedCloudClient::ConnectNetworkError: + error = "MbedCloudClient::ConnectNetworkError"; + break; + case MbedCloudClient::ConnectResponseParseFailed: + error = "MbedCloudClient::ConnectResponseParseFailed"; + break; + case MbedCloudClient::ConnectUnknownError: + error = "MbedCloudClient::ConnectUnknownError"; + break; + case MbedCloudClient::ConnectMemoryConnectFail: + error = "MbedCloudClient::ConnectMemoryConnectFail"; + break; + case MbedCloudClient::ConnectNotAllowed: + error = "MbedCloudClient::ConnectNotAllowed"; + break; + case MbedCloudClient::ConnectSecureConnectionFailed: + error = "MbedCloudClient::ConnectSecureConnectionFailed"; + break; + case MbedCloudClient::ConnectDnsResolvingFailed: + error = "MbedCloudClient::ConnectDnsResolvingFailed"; + break; + case MbedCloudClient::ConnectorFailedToStoreCredentials: + error = "MbedCloudClient::ConnectorFailedToStoreCredentials"; + break; + case MbedCloudClient::ConnectorFailedToReadCredentials: + error = "MbedCloudClient::ConnectorFailedToReadCredentials"; + break; +#ifdef MBED_CLOUD_CLIENT_SUPPORT_UPDATE + case MbedCloudClient::UpdateWarningCertificateNotFound: + error = "MbedCloudClient::UpdateWarningCertificateNotFound"; + break; + case MbedCloudClient::UpdateWarningIdentityNotFound: + error = "MbedCloudClient::UpdateWarningIdentityNotFound"; + break; + case MbedCloudClient::UpdateWarningCertificateInvalid: + error = "MbedCloudClient::UpdateWarningCertificateInvalid"; + break; + case MbedCloudClient::UpdateWarningSignatureInvalid: + error = "MbedCloudClient::UpdateWarningSignatureInvalid"; + break; + case MbedCloudClient::UpdateWarningVendorMismatch: + error = "MbedCloudClient::UpdateWarningVendorMismatch"; + break; + case MbedCloudClient::UpdateWarningClassMismatch: + error = "MbedCloudClient::UpdateWarningClassMismatch"; + break; + case MbedCloudClient::UpdateWarningDeviceMismatch: + error = "MbedCloudClient::UpdateWarningDeviceMismatch"; + break; + case MbedCloudClient::UpdateWarningURINotFound: + error = "MbedCloudClient::UpdateWarningURINotFound"; + break; + case MbedCloudClient::UpdateWarningRollbackProtection: + error = "MbedCloudClient::UpdateWarningRollbackProtection"; + break; + case MbedCloudClient::UpdateWarningUnknown: + error = "MbedCloudClient::UpdateWarningUnknown"; + break; + case MbedCloudClient::UpdateErrorWriteToStorage: + error = "MbedCloudClient::UpdateErrorWriteToStorage"; + break; + case MbedCloudClient::UpdateErrorInvalidHash: + error = "MbedCloudClient::UpdateErrorInvalidHash"; + break; + case MbedCloudClient::UpdateErrorConnection: + error = "MbedCloudClient::UpdateErrorConnection"; + break; + case MbedCloudClient::UpdateWarningAuthorizationRejected: + error = "MbedCloudClient::UpdateWarningAuthorizationRejected"; + break; + case MbedCloudClient::UpdateWarningAuthorizationUnavailable: + error = "MbedCloudClient::UpdateWarningAuthorizationUnavailable"; + break; + case MbedCloudClient::UpdateCertificateInsertion: + error = "MbedCloudClient::UpdateCertificateInsertion"; + break; +#endif +#ifndef MBED_CONF_MBED_CLOUD_CLIENT_DISABLE_CERTIFICATE_ENROLLMENT + case CE_STATUS_INIT_FAILED: + error = "CE_STATUS_INIT_FAILED"; + break; +#endif // !MBED_CONF_MBED_CLOUD_CLIENT_DISABLE_CERTIFICATE_ENROLLMENT + + default: + error = "UNKNOWN"; + } + printf("\nError occurred : %s\r\n", error); + printf("Error code : %d\r\n", error_code); + printf("Error details : %s\r\n", pdmc_client.error_description()); + +#if defined(MAX_ERROR_COUNT) && (MAX_ERROR_COUNT > 0) + if (error_code == MbedCloudClient::ConnectNetworkError || + error_code == MbedCloudClient::ConnectDnsResolvingFailed || + error_code == MbedCloudClient::ConnectSecureConnectionFailed || + error_code == MbedCloudClient::ConnectTimeout) { + reboot_if_threshold_value(MAX_ERROR_COUNT); + } +#endif +} + +#ifdef MBED_CLOUD_CLIENT_SUPPORT_MULTICAST_UPDATE +static void pdmc_external_update_cb(uint32_t start_address, uint32_t size) +{ + printf("Application received external update, start address: %" PRIX32 ", size: %" PRIu32 " bytes\n", start_address, size); +} +#endif // MBED_CLOUD_CLIENT_SUPPORT_MULTICAST_UPDATE + +/** Helper methods --> **/ + +bool create_pdmc_resources() +{ + // Create resource for button count. Path of this resource will be: 3200/0/5501. + button_res = M2MInterfaceFactory::create_resource(object_list, 3200, 0, 5501, M2MResourceInstance::INTEGER, M2MBase::GET_PUT_ALLOWED); + if (button_res == NULL) { + return false; + } + button_res->set_value(0); + button_res->set_observable(true); + button_res->set_message_delivery_status_cb((void(*)(const M2MBase &, const M2MBase::MessageDeliveryStatus, const M2MBase::MessageType, void *))delivery_status_cb, NULL); + button_res->set_value_updated_function(button_counter_updated); + + // Create resource for led blinking pattern. Path of this resource will be: 3201/0/5853. + pattern_res = M2MInterfaceFactory::create_resource(object_list, 3201, 0, 5853, M2MResourceInstance::STRING, M2MBase::GET_PUT_ALLOWED); + if (!pattern_res) { + return false; + } + pattern_res->set_value((const unsigned char *)"500:500:500:500", 15); + pattern_res->set_observable(true); + pattern_res->set_value_updated_function(blink_pattern_updated); + pattern_res->set_message_delivery_status_cb((void(*)(const M2MBase &, const M2MBase::MessageDeliveryStatus, const M2MBase::MessageType, void *))delivery_status_cb, NULL); + + // Create resource for starting the led blinking. Path of this resource will be: 3201/0/5850. + blink_res = M2MInterfaceFactory::create_resource(object_list, 3201, 0, 5850, M2MResourceInstance::STRING, M2MBase::POST_ALLOWED); + if (!blink_res) { + return false; + } + + blink_res->set_execute_function(blink_cb); + blink_res->set_message_delivery_status_cb((void(*)(const M2MBase &, const M2MBase::MessageDeliveryStatus, const M2MBase::MessageType, void *))delivery_status_cb, NULL); + blink_res->set_delayed_response(true); + + // Create optional Device resource for running factory reset for the device. Path of this resource will be: 3/0/5. + factory_reset_res = M2MInterfaceFactory::create_device()->create_resource(M2MDevice::FactoryReset); + if (factory_reset_res) { + factory_reset_res->set_execute_function(factory_reset_cb); + } else { + return false; + } + + // Create an example resource for handling large resource payloads. Path of this resource will be: 5000/0/2. + large_res = M2MInterfaceFactory::create_resource(object_list, 5000, 0, 2, M2MResourceInstance::STRING, M2MBase::GET_ALLOWED); + if (!large_res) { + return false; + } + + large_res->set_message_delivery_status_cb((void(*)(const M2MBase &, const M2MBase::MessageDeliveryStatus, const M2MBase::MessageType, void *))large_res_sent_cb, NULL); + large_res->set_read_resource_function(large_res_read_requested, NULL); + +#ifdef MBED_CLOUD_CLIENT_TRANSPORT_MODE_UDP_QUEUE + button_res->set_auto_observable(true); + pattern_res->set_auto_observable(true); + blink_res->set_auto_observable(true); + factory_reset_res->set_auto_observable(true); +#endif + + return true; +} + +static void reboot_if_threshold_value(int threshold) +{ + if (++error_count == threshold) { + printf("Max error count %d reached, rebooting.\n\n", threshold); + mcc_platform_do_wait(1 * 1000); + mcc_platform_reboot(); + } +} + +/** Resource callback functions --> **/ + +static void button_counter_updated(const char *) +{ + // Converts uint64_t to a string to remove the dependency for int64 printf implementation. + char buffer[20 + 1]; + (void) m2m::itoa_c(button_res->get_value_int(), buffer); + printf("Counter resource set to %s\r\n", buffer); +} + +static void blink_pattern_updated(const char *) +{ + printf("PUT received, new value: %s\r\n", pattern_res->get_value_string().c_str()); +} + +static void blink_cb(void *) +{ + String pattern_string = pattern_res->get_value_string(); + printf("POST executed\r\n"); + + // The pattern is something like 500:200:500, so parse that. + // LED blinking is done while parsing. +#ifndef PDMC_EXAMPLE_MINIMAL + const bool restart_pattern = false; + if (blinky.start((char *)pattern_res->value(), pattern_res->value_length(), restart_pattern) == false) { + printf("out of memory error\r\n"); + } +#endif + blink_res->send_delayed_post_response(); +} + +static void delivery_status_cb(const M2MBase &object, + const M2MBase::MessageDeliveryStatus status, + const M2MBase::MessageType /*type*/) +{ + switch (status) { + case M2MBase::MESSAGE_STATUS_BUILD_ERROR: + printf("Message status callback: (%s) error when building CoAP message\r\n", object.uri_path()); + break; + case M2MBase::MESSAGE_STATUS_RESEND_QUEUE_FULL: + printf("Message status callback: (%s) CoAP resend queue full\r\n", object.uri_path()); + break; + case M2MBase::MESSAGE_STATUS_SENT: + printf("Message status callback: (%s) Message sent to server\r\n", object.uri_path()); + break; + case M2MBase::MESSAGE_STATUS_DELIVERED: + printf("Message status callback: (%s) Message delivered\r\n", object.uri_path()); + break; + case M2MBase::MESSAGE_STATUS_SEND_FAILED: + printf("Message status callback: (%s) Message sending failed\r\n", object.uri_path()); + break; + case M2MBase::MESSAGE_STATUS_SUBSCRIBED: + printf("Message status callback: (%s) subscribed\r\n", object.uri_path()); + break; + case M2MBase::MESSAGE_STATUS_UNSUBSCRIBED: + printf("Message status callback: (%s) subscription removed\r\n", object.uri_path()); + break; + case M2MBase::MESSAGE_STATUS_REJECTED: + printf("Message status callback: (%s) server has rejected the message\r\n", object.uri_path()); + break; + default: + break; + } +} + +static void large_res_sent_cb(const M2MBase &base, + const M2MBase::MessageDeliveryStatus status, + const M2MBase::MessageType /*type*/) +{ + switch (status) { + case M2MBase::MESSAGE_STATUS_DELIVERED: + free(large_res_data); + printf("5000/0/2 data sent to server, memory can be now released\r\n"); + break; + + case M2MBase::MESSAGE_STATUS_SEND_FAILED: + printf("Failed to send 5000/0/2 data!\r\n"); + free(large_res_data); + break; + + default: + break; + } +} + +static void factory_reset_cb(void *) +{ + printf("Factory reset resource triggered\r\n"); + + // First send response, so server won't be left waiting. + // Factory reset resource is by default expecting explicit + // delayed response sending. + factory_reset_res->send_delayed_post_response(); + + // Then run potentially long-taking factory reset routines. + kcm_factory_reset(); +} + +static coap_response_code_e large_res_read_requested(const M2MResourceBase &resource, + uint8_t *&buffer, + size_t &buffer_size, + size_t &total_size, + const size_t offset, + void */*client_args*/) +{ + printf("GET request received for resource: %s\r\n", resource.uri_path()); + + // Allocate buffer when first request comes in + if (offset == 0) { + large_res_data = (uint8_t *)malloc(large_res_size); + memset(large_res_data, 0, large_res_size); + } + + if (!large_res_data) { + return COAP_RESPONSE_INTERNAL_SERVER_ERROR; + } + + total_size = large_res_size; + + // Adjust last package size + if (offset + buffer_size > total_size) { + buffer_size = total_size - offset; + } + + // Read data from offset + buffer = (uint8_t *)large_res_data + offset; + + return COAP_RESPONSE_CONTENT; +} diff --git a/source/pdmc_example.h b/source/pdmc_example.h new file mode 100644 index 0000000..7677772 --- /dev/null +++ b/source/pdmc_example.h @@ -0,0 +1,46 @@ +// ---------------------------------------------------------------------------- +// Copyright 2016-2021 Pelion. +// +// SPDX-License-Identifier: Apache-2.0 +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// ---------------------------------------------------------------------------- + +#ifndef PDMC_EXAMPLE_H +#define PDMC_EXAMPLE_H + +#include "m2minterface.h" + +// Starting with 5s, after every iteration waiting time is multiplied by 2 -> max waiting time is with 9 is 1280s (~21min) +// it is this long as with bad cellular rssi register and plmn selection might take 5mins so we wan't to give it a few tries. +#define MAX_PDMC_CLIENT_CONNECTION_ERROR_COUNT 9 + +void pdmc_init(); + +void pdmc_close(); + +bool pdmc_connect(); + +void pdmc_resume(); + +bool pdmc_registered(); + +bool pdmc_paused(); + +bool pdmc_register_called(); + +M2MObjectList *pdmc_get_object_list(); + +bool create_pdmc_resources(); + +#endif // PDMC_EXAMPLE_H diff --git a/source/platform/KEIL/mcc_common_setup.c b/source/platform/KEIL/mcc_common_setup.c index cd2120b..5925ba6 100644 --- a/source/platform/KEIL/mcc_common_setup.c +++ b/source/platform/KEIL/mcc_common_setup.c @@ -18,6 +18,7 @@ #include "RTE_Components.h" #include "cmsis_os2.h" #include "pal.h" +#include "MbedCloudClientConfig.h" #ifdef RTE_Compiler_EventRecorder #include "EventRecorder.h" @@ -38,8 +39,8 @@ uint64_t app_main_stk[APP_MAIN_STK_SZ / 8]; const osThreadAttr_t app_main_attr = { - .stack_mem = &app_main_stk[0], - .stack_size = sizeof(app_main_stk) + .stack_mem = &app_main_stk[0], + .stack_size = sizeof(app_main_stk) }; static void *network_interface = NULL; @@ -66,7 +67,7 @@ int mcc_platform_init_connection(void) #ifdef RTE_IoT_Socket_WiFi printf("Connecting to WiFi ...\r\n"); - if (Driver_WiFi0.Initialize (NULL) != ARM_DRIVER_OK) { + if (Driver_WiFi0.Initialize(NULL) != ARM_DRIVER_OK) { printf("Failed to initialize wifi!\n"); return -1; } @@ -98,20 +99,20 @@ int mcc_platform_init_connection(void) // Loop until link is up uint32_t addr; do { - osDelay(1000U); - netIF_GetOption(NET_IF_CLASS_ETH | 0, - netIF_OptionIP4_Address, - (uint8_t *)&addr, sizeof (addr)); + osDelay(1000U); + netIF_GetOption(NET_IF_CLASS_ETH | 0, + netIF_OptionIP4_Address, + (uint8_t *)&addr, sizeof(addr)); } while (addr == 0U); uint8_t ip4_addr[NET_ADDR_IP4_LEN]; char ip4_ascii[16]; - if (netIF_GetOption (NET_IF_CLASS_ETH | 0, netIF_OptionIP4_Address, - ip4_addr, sizeof(ip4_addr)) == netOK) { + if (netIF_GetOption(NET_IF_CLASS_ETH | 0, netIF_OptionIP4_Address, + ip4_addr, sizeof(ip4_addr)) == netOK) { - netIP_ntoa (NET_ADDR_IP4, ip4_addr, ip4_ascii, sizeof(ip4_ascii)); + netIP_ntoa(NET_ADDR_IP4, ip4_addr, ip4_ascii, sizeof(ip4_ascii)); printf("IP4=%s\n", ip4_ascii); } #endif @@ -131,7 +132,7 @@ int mcc_platform_close_connection(void) return 0; } -void* mcc_platform_get_network_interface(void) +void *mcc_platform_get_network_interface(void) { return network_interface; } @@ -187,6 +188,7 @@ int mcc_platform_run_program(main_t mainFunc) void mcc_platform_sw_build_info(void) { printf("Application ready. Build at: " __DATE__ " " __TIME__ "\n"); + printf("PDMC version %d.%d.%d\n", PDMC_MAJOR_VERSION, PDMC_MINOR_VERSION, PDMC_PATCH_VERSION); } void mcc_platform_reboot(void) diff --git a/source/platform/Linux/mcc_common_setup.c b/source/platform/Linux/mcc_common_setup.c index 7078ab2..44a4e33 100644 --- a/source/platform/Linux/mcc_common_setup.c +++ b/source/platform/Linux/mcc_common_setup.c @@ -29,8 +29,8 @@ #include "mcc_common_setup.h" #include "mcc_common_config.h" #include "pal.h" - #include "mcc_common_button_and_led.h" +#include "MbedCloudClientConfig.h" //////////////////////////////////////// // PLATFORM SPECIFIC DEFINES & FUNCTIONS @@ -38,35 +38,41 @@ static void *network_interface; // PAL_NET_DEFAULT_INTERFACE 0xFFFFFFFF -static unsigned int network=0xFFFFFFFF; +static unsigned int network = 0xFFFFFFFF; //////////////////////////////// // SETUP_COMMON.H IMPLEMENTATION //////////////////////////////// -int mcc_platform_init_connection(void) { +int mcc_platform_init_connection(void) +{ return mcc_platform_interface_connect(); } -void* mcc_platform_get_network_interface(void) { +void *mcc_platform_get_network_interface(void) +{ return mcc_platform_interface_get(); } -int mcc_platform_close_connection(void) { +int mcc_platform_close_connection(void) +{ return mcc_platform_interface_close(); } -int mcc_platform_interface_connect() { +int mcc_platform_interface_connect() +{ network_interface = &network; return 0; } -int mcc_platform_interface_close() { +int mcc_platform_interface_close() +{ network_interface = NULL; return 0; } -void* mcc_platform_interface_get() { +void *mcc_platform_interface_get() +{ return network_interface; } @@ -92,20 +98,17 @@ int mcc_platform_storage_init(void) // Get default mount point. status = pal_fsGetMountPoint(PAL_FS_PARTITION_PRIMARY, PAL_MAX_FILE_AND_FOLDER_LENGTH, path); - if(status != PAL_SUCCESS) - { + if (status != PAL_SUCCESS) { printf("Fetching of PAL_FS_PARTITION_PRIMARY path %s failed.\n", path); return -1; } // Make the sub-path printf("Creating path %s\n", path); - int res = mkdir(path,0744); - if(res) - { + int res = mkdir(path, 0744); + if (res) { // Ignore error if it exists - if( errno != EEXIST) - { + if (errno != EEXIST) { printf("Creation of PAL_FS_PARTITION_PRIMARY path %s failed.\n", path); return -1; } @@ -115,19 +118,16 @@ int mcc_platform_storage_init(void) // Get default mount point. status = pal_fsGetMountPoint(PAL_FS_PARTITION_SECONDARY, PAL_MAX_FILE_AND_FOLDER_LENGTH, path); - if(status != PAL_SUCCESS) - { + if (status != PAL_SUCCESS) { return -1; } // Make the sub-path printf("Creating path %s\n", path); - res = mkdir(path,0744); - if(res) - { + res = mkdir(path, 0744); + if (res) { // Ignore error if it exists - if( errno != EEXIST) - { + if (errno != EEXIST) { printf("Creation of PAL_FS_PARTITION_SECONDARY path %s failed.\n", path); return -1; } @@ -198,11 +198,14 @@ int mcc_platform_run_program(main_t mainFunc) return 1; } -void mcc_platform_sw_build_info() { +void mcc_platform_sw_build_info() +{ printf("Application ready. Build at: " __DATE__ " " __TIME__ "\n"); + printf("PDMC version %d.%d.%d\n", PDMC_MAJOR_VERSION, PDMC_MINOR_VERSION, PDMC_PATCH_VERSION); } -void mcc_platform_reboot() { +void mcc_platform_reboot() +{ pal_osReboot(); } diff --git a/source/platform/NXP/mcc_common_setup.c b/source/platform/NXP/mcc_common_setup.c index 9d7ecad..3cf9ede 100644 --- a/source/platform/NXP/mcc_common_setup.c +++ b/source/platform/NXP/mcc_common_setup.c @@ -21,6 +21,7 @@ /////////// #include "mcc_common_setup.h" #include "pal.h" +#include "MbedCloudClientConfig.h" #include "FreeRTOS.h" #include "task.h" @@ -46,7 +47,8 @@ extern struct netif network_interface; // SETUP_COMMON.H IMPLEMENTATION //////////////////////////////// -int mcc_platform_init_connection(void) { +int mcc_platform_init_connection(void) +{ DEBUG_PRINT("mcc_platform_init_connection\r\n"); return 0; @@ -61,37 +63,43 @@ int mcc_platform_run_program(main_t mainFunc) return 0; } -void* mcc_platform_get_network_interface(void) { +void *mcc_platform_get_network_interface(void) +{ DEBUG_PRINT("mcc_platform_get_network_interface\r\n"); return &network_interface; } -int mcc_platform_close_connection(void) { +int mcc_platform_close_connection(void) +{ DEBUG_PRINT("mcc_platform_close_connection\r\n"); return 0; } -int mcc_platform_interface_connect(void) { +int mcc_platform_interface_connect(void) +{ DEBUG_PRINT("mcc_platform_interface_connect\r\n"); return 0; } -int mcc_platform_interface_close(void) { +int mcc_platform_interface_close(void) +{ DEBUG_PRINT("mcc_platform_interface_close\r\n"); return 0; } -void* mcc_platform_interface_get(void) { +void *mcc_platform_interface_get(void) +{ DEBUG_PRINT("mcc_platform_interface_get\r\n"); return &network_interface; } -void mcc_platform_interface_init(void) { +void mcc_platform_interface_init(void) +{ DEBUG_PRINT("mcc_platform_interface_init\r\n"); } @@ -124,10 +132,13 @@ void mcc_platform_do_wait(int timeout_ms) vTaskDelay(pdMS_TO_TICKS(timeout_ms)); } -void mcc_platform_sw_build_info(void) { +void mcc_platform_sw_build_info(void) +{ printf("Application ready. Build at: " __DATE__ " " __TIME__ "\r\n"); + printf("PDMC version %d.%d.%d\r\n", PDMC_MAJOR_VERSION, PDMC_MINOR_VERSION, PDMC_PATCH_VERSION); } -void mcc_platform_reboot(void) { +void mcc_platform_reboot(void) +{ pal_osReboot(); } diff --git a/source/platform/Renesas_EK_RA6M3/mcc_common_setup.c b/source/platform/Renesas_EK_RA6M3/mcc_common_setup.c index 200f969..07d3b20 100644 --- a/source/platform/Renesas_EK_RA6M3/mcc_common_setup.c +++ b/source/platform/Renesas_EK_RA6M3/mcc_common_setup.c @@ -21,6 +21,7 @@ /////////// #include "mcc_common_setup.h" #include "pal.h" +#include "MbedCloudClientConfig.h" #include "FreeRTOS.h" #include "task.h" @@ -31,7 +32,7 @@ // PLATFORM SPECIFIC DEFINES & FUNCTIONS //////////////////////////////////////// static void *network_interface = 0; -extern void* mcc_platform_GetNetWorkInterfaceContext(); +extern void *mcc_platform_GetNetWorkInterfaceContext(); static int init_FreeRTOS = 0; extern int mcc_platform_initFreeRTOSPlatform(); @@ -50,29 +51,35 @@ extern int fileSystemMountDrive(); // SETUP_COMMON.H IMPLEMENTATION //////////////////////////////// -int mcc_platform_init_connection(void) { +int mcc_platform_init_connection(void) +{ return mcc_platform_interface_connect(); } -void* mcc_platform_get_network_interface(void) { +void *mcc_platform_get_network_interface(void) +{ return mcc_platform_interface_get(); } -int mcc_platform_close_connection(void) { +int mcc_platform_close_connection(void) +{ return mcc_platform_interface_close(); } -int mcc_platform_interface_connect(void) { +int mcc_platform_interface_connect(void) +{ network_interface = mcc_platform_GetNetWorkInterfaceContext(); return networkInit(); } -int mcc_platform_interface_close(void) { +int mcc_platform_interface_close(void) +{ // XXX: Ignore the fact that this is not implemented. return 0; } -void* mcc_platform_interface_get(void) { +void *mcc_platform_interface_get(void) +{ return network_interface; } @@ -105,14 +112,13 @@ int mcc_platform_storage_init(void) int mcc_platform_init(void) { - if(init_FreeRTOS) { + if (init_FreeRTOS) { return 0; } init_FreeRTOS = 1; - if(mcc_platform_initFreeRTOSPlatform()) { + if (mcc_platform_initFreeRTOSPlatform()) { return 0; - } - else { + } else { return -1; } } @@ -122,10 +128,13 @@ void mcc_platform_do_wait(int timeout_ms) vTaskDelay(pdMS_TO_TICKS(timeout_ms)); } -void mcc_platform_sw_build_info(void) { +void mcc_platform_sw_build_info(void) +{ printf("Application ready. Build at: " __DATE__ " " __TIME__ "\n"); + printf("PDMC version %d.%d.%d\n", PDMC_MAJOR_VERSION, PDMC_MINOR_VERSION, PDMC_PATCH_VERSION); } -void mcc_platform_reboot(void) { +void mcc_platform_reboot(void) +{ pal_osReboot(); } diff --git a/source/platform/Renesas_RX65N-CK/mcc_common_setup.c b/source/platform/Renesas_RX65N-CK/mcc_common_setup.c index f7fcc67..3ddc4cc 100644 --- a/source/platform/Renesas_RX65N-CK/mcc_common_setup.c +++ b/source/platform/Renesas_RX65N-CK/mcc_common_setup.c @@ -21,14 +21,13 @@ #include "task.h" #include "pal_plat_rtos.h" #include "mcc_common_setup.h" - +#include "MbedCloudClientConfig.h" int mcc_platform_run_program(main_t mainFunc) { - BaseType_t status = xTaskCreate((TaskFunction_t)mainFunc, "_main_", (uint32_t)1024*8, NULL, tskIDLE_PRIORITY + 1, NULL); + BaseType_t status = xTaskCreate((TaskFunction_t)mainFunc, "_main_", (uint32_t)1024 * 8, NULL, tskIDLE_PRIORITY + 1, NULL); - if (status == pdPASS) - { + if (status == pdPASS) { vTaskStartScheduler(); } return 1; @@ -42,6 +41,7 @@ void mcc_platform_do_wait(int timeout_ms) void mcc_platform_sw_build_info(void) { printf("Application ready. Build at: " __DATE__ " " __TIME__ "\r\n"); + printf("PDMC version %d.%d.%d\r\n", PDMC_MAJOR_VERSION, PDMC_MINOR_VERSION, PDMC_PATCH_VERSION); } int mcc_platform_reformat_storage(void) @@ -57,7 +57,7 @@ int mcc_platform_reformat_storage(void) int mcc_platform_storage_init(void) { // printf("mcc_platform_storage_init()\n"); - + // XXX: some of the existing users of this module actually call mcc_platform_storage_init() // BEFORE mcc_platform_init(). // diff --git a/source/platform/ZephyrOS/mcc_common_setup.c b/source/platform/ZephyrOS/mcc_common_setup.c index 2a19754..73f12a8 100644 --- a/source/platform/ZephyrOS/mcc_common_setup.c +++ b/source/platform/ZephyrOS/mcc_common_setup.c @@ -20,16 +20,18 @@ // INCLUDES /////////// #include "mcc_common_setup.h" +#include "MbedCloudClientConfig.h" +#include #include +#include + //////////////////////////////////////// // PLATFORM SPECIFIC DEFINES & FUNCTIONS //////////////////////////////////////// #if 0 -#include - #undef DEBUG_PRINT #define DEBUG_PRINT(...) printf(__VA_ARGS__) #else @@ -42,7 +44,8 @@ // SETUP_COMMON.H IMPLEMENTATION //////////////////////////////// -int mcc_platform_init_connection(void) { +int mcc_platform_init_connection(void) +{ DEBUG_PRINT("mcc_platform_init_connection\r\n"); return 0; @@ -57,37 +60,64 @@ int mcc_platform_run_program(main_t mainFunc) return 0; } -void* mcc_platform_get_network_interface(void) { +void *mcc_platform_get_network_interface(void) +{ DEBUG_PRINT("mcc_platform_get_network_interface\r\n"); return NULL; } -int mcc_platform_close_connection(void) { +int mcc_platform_close_connection(void) +{ DEBUG_PRINT("mcc_platform_close_connection\r\n"); return 0; } -int mcc_platform_interface_connect(void) { +int mcc_platform_interface_connect(void) +{ DEBUG_PRINT("mcc_platform_interface_connect\r\n"); + char ip_output[NET_IPV4_ADDR_LEN]; + char mac_output[3 * NET_LINK_ADDR_MAX_LENGTH]; + + struct net_if *iface = net_if_get_default(); + + /* copy IP address to string */ + net_addr_ntop(AF_INET, &iface->config.ip.ipv4->unicast[0].address.in_addr, ip_output, sizeof(ip_output)); + + /* copy MAC address to string (last call clips ':' for '\0') */ + struct net_linkaddr * mac = net_if_get_link_addr(iface); + for (size_t index = 0; index < mac->len; index++) { + snprintf(mac_output + (3 * index), + (3 * NET_LINK_ADDR_MAX_LENGTH) - (3 * index), + "%02X:", + mac->addr[index]); + } + + /* print out addresses */ + printf("IP: %s\r\n", ip_output); + printf("MAC address: %s\r\n", mac_output); + return 0; } -int mcc_platform_interface_close(void) { +int mcc_platform_interface_close(void) +{ DEBUG_PRINT("mcc_platform_interface_close\r\n"); return 0; } -void* mcc_platform_interface_get(void) { +void *mcc_platform_interface_get(void) +{ DEBUG_PRINT("mcc_platform_interface_get\r\n"); return NULL; } -void mcc_platform_interface_init(void) { +void mcc_platform_interface_init(void) +{ DEBUG_PRINT("mcc_platform_interface_init\r\n"); } @@ -118,10 +148,15 @@ void mcc_platform_do_wait(int timeout_ms) k_msleep(timeout_ms); } -void mcc_platform_sw_build_info(void) { - DEBUG_PRINT("Application ready. Build at: " __DATE__ " " __TIME__ "\r\n"); +void mcc_platform_sw_build_info(void) +{ + DEBUG_PRINT("mcc_platform_sw_build_info\r\n"); + + printf("Application ready. Build at: " __DATE__ " " __TIME__ "\r\n"); + printf("PDMC version %d.%d.%d\r\n", PDMC_MAJOR_VERSION, PDMC_MINOR_VERSION, PDMC_PATCH_VERSION); } -void mcc_platform_reboot(void) { +void mcc_platform_reboot(void) +{ NVIC_SystemReset(); } diff --git a/source/platform/mbed-os/mcc_common_setup.cpp b/source/platform/mbed-os/mcc_common_setup.cpp index fba363d..8fd5fe5 100644 --- a/source/platform/mbed-os/mcc_common_setup.cpp +++ b/source/platform/mbed-os/mcc_common_setup.cpp @@ -31,6 +31,7 @@ #include "mcc_common_config.h" #include "kv_config.h" #include "mbed_trace.h" +#include "MbedCloudClientConfig.h" #if MBED_MAJOR_VERSION > 5 #include "DeviceKey.h" @@ -398,6 +399,7 @@ int mcc_platform_run_program(main_t mainFunc) void mcc_platform_sw_build_info(void) { printf("Application ready. Build at: " __DATE__ " " __TIME__ "\n"); + printf("PDMC version %d.%d.%d\n", PDMC_MAJOR_VERSION, PDMC_MINOR_VERSION, PDMC_PATCH_VERSION); // The Mbed OS' master branch does not define the version numbers at all, so we need // some ifdeffery to keep compilations running. @@ -414,8 +416,15 @@ int mcc_platform_storage_init(void) mcc_platform_do_wait(MCC_PLATFORM_WAIT_BEFORE_BD_INIT * SECONDS_TO_MS); int status = kv_init_storage_config(); if (status != MBED_SUCCESS) { - printf("kv_init_storage_config() - failed, status %d\n", status); - return status; +#ifdef MBED_CONF_MBED_CLOUD_CLIENT_PSA_SUPPORT + if (status == MBED_ERROR_UNSUPPORTED) { + printf("PSA enabled, ignore kv_init_storage_config() is not supported\n"); + } else +#endif + { + printf("kv_init_storage_config() - failed, status %d\n", status); + return status; + } } return 0; } diff --git a/source/resource.cpp b/source/resource.cpp deleted file mode 100644 index 38a50bc..0000000 --- a/source/resource.cpp +++ /dev/null @@ -1,84 +0,0 @@ -// ---------------------------------------------------------------------------- -// Copyright 2016-2017 ARM Ltd. -// -// SPDX-License-Identifier: Apache-2.0 -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -// ---------------------------------------------------------------------------- - -#include "mbed-cloud-client/MbedCloudClient.h" -#include "m2mresource.h" -#include "mbed-client/m2minterface.h" -#include -#include - -M2MResource* add_resource(M2MObjectList *list, uint16_t object_id, uint16_t instance_id, - uint16_t resource_id, const char *resource_type, M2MResourceInstance::ResourceType data_type, - M2MBase::Operation allowed, const char *value, bool observable, void *cb, - void *message_status_cb) -{ - M2MObject *object = NULL; - M2MObjectInstance* object_instance = NULL; - M2MResource* resource = NULL; - char name[6]; - - //check if object already exists. - if (!list->empty()) { - M2MObjectList::const_iterator it; - it = list->begin(); - for ( ; it != list->end(); it++ ) { - if ((*it)->name_id() == object_id) { - object = (*it); - break; - } - } - } - //Create new object if needed. - if (!object) { - snprintf(name, 6, "%d", object_id); - object = M2MInterfaceFactory::create_object(name); - list->push_back(object); - } else { - //check if instance already exists. - object_instance = object->object_instance(instance_id); - } - //Create new instance if needed. - if (!object_instance) { - object_instance = object->create_object_instance(instance_id); - } - //create the recource. - snprintf(name, 6, "%d", resource_id); - resource = object_instance->create_dynamic_resource(name, resource_type, data_type, observable); - //Set value if available. - if (value) { - resource->set_value((const unsigned char*)value, strlen(value)); - } - //Set allowed operations for accessing the resource. - resource->set_operation(allowed); - - resource->set_message_delivery_status_cb( - (void(*)(const M2MBase&, - const M2MBase::MessageDeliveryStatus, - const M2MBase::MessageType, - void*))message_status_cb, NULL); - - //Set callback of PUT or POST operation is enabled. - //NOTE: This function does not support setting them both. - if(allowed & M2MResourceInstance::PUT_ALLOWED) { - resource->set_value_updated_function((void(*)(const char*))cb); - } else if (allowed & M2MResourceInstance::POST_ALLOWED){ - resource->set_execute_function((void(*)(void*))cb); - } - - return resource; -} diff --git a/source/resource.h b/source/resource.h deleted file mode 100644 index 4aad8c1..0000000 --- a/source/resource.h +++ /dev/null @@ -1,64 +0,0 @@ -// ---------------------------------------------------------------------------- -// Copyright 2016-2017 ARM Ltd. -// -// SPDX-License-Identifier: Apache-2.0 -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -// ---------------------------------------------------------------------------- - - -#ifndef RESOURCE_H -#define RESOURCE_H - - -/** - * \brief Helper function for creating different kind of resources. - * The path of the resource will be "object_id/instance_id/resource_id" - * For example if object_id = 1, instance_id = 2, resource_id = 3 - * the path would be 1/2/3 - * - * \param list Pointer to the object list, - * contains objects to be registered to the server. - * \param object_id Name of the object in integer format. - * \param instance_id Name of the instance in integer format. - * \param resource_id Name of the resource in integer format. - * \param resource_type Resource type name. - * \param data_type Data type of the resource value. - * \param allowed Methods allowed for accessing this resource. - * \param value Resource value as a null terminated string. - * May be set as NULL. - * \param observable Resource set observable if true. - * \param cb Function pointer to either: - * value_updated_callback2 if allowed & GET_PUT_ALLOWED - * OR - * execute_callback_2 in if allowed & POST_ALLOWED. - * In other cases this parameter is ignored. - * - * NOTE: This function is not designed to support setting both - * GET_PUT_ALLOWED and POST_ALLOWED for parameter allowed - * at the same time. - * \param message_status_cb Function pointer to message_status_cb - */ -M2MResource* add_resource(M2MObjectList *list, - uint16_t object_id, - uint16_t instance_id, - uint16_t resource_id, - const char *resource_type, - M2MResourceInstance::ResourceType data_type, - M2MBase::Operation allowed, - const char *value, - bool observable, - void *cb, - void *message_status_cb); - -#endif //RESOURCE_H diff --git a/source/simplem2mclient.h b/source/simplem2mclient.h deleted file mode 100644 index 8f2afbc..0000000 --- a/source/simplem2mclient.h +++ /dev/null @@ -1,395 +0,0 @@ -// ---------------------------------------------------------------------------- -// Copyright 2016-2020 ARM Ltd. -// -// SPDX-License-Identifier: Apache-2.0 -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -// ---------------------------------------------------------------------------- - - -#ifndef SIMPLEM2MCLIENT_H -#define SIMPLEM2MCLIENT_H -#include -#include - -#include "mbed-cloud-client/MbedCloudClient.h" -#include "m2mdevice.h" -#include "mcc_common_setup.h" -#include "m2mresource.h" -#include "mbed-client/m2minterface.h" -#include "key_config_manager.h" -#include "resource.h" -#include "application_init.h" -#include "factory_configurator_client.h" - -#ifdef MBED_CLOUD_CLIENT_USER_CONFIG_FILE -#include MBED_CLOUD_CLIENT_USER_CONFIG_FILE -#endif - -#ifdef MBED_CLOUD_CLIENT_SUPPORT_UPDATE -#include "update_ui_example.h" -#endif - -#if defined (MEMORY_TESTS_HEAP) -#include "memory_tests.h" -#endif - -// This defines how many consecutive errors can occur before application will perform reboot as recovery. -// Set to 0 to disable the feature. -#ifndef MAX_ERROR_COUNT -#define MAX_ERROR_COUNT 5 -#endif - -// starting with 5s, after every iteration waiting time is multiplied by 2 -> max waiting time is with 9 is 1280s (~21min) -// it is this long as with bad cellular rssi register and plmn selection might take 5mins so we wan't to give it a few tries. -#define MAX_PDMC_CLIENT_CONNECTION_ERROR_COUNT 9 - -#ifdef MBED_CLOUD_CLIENT_SUPPORT_MULTICAST_UPDATE -static void external_update(uint32_t start_address, uint32_t size) -{ - printf("Application received external update, start address: %" PRIX32 ", size: %" PRIu32 " bytes\n", start_address, size); -} -#endif // MBED_CLOUD_CLIENT_SUPPORT_MULTICAST_UPDATE - -class SimpleM2MClient { - -public: - - SimpleM2MClient() : - _registered(false), - _register_called(false), - _error_count(0) -#ifdef MBED_CLOUD_CLIENT_TRANSPORT_MODE_UDP_QUEUE - , _paused(false) -#endif - { - } - - void reboot_if_threshold_value(int threshold) { - if (++_error_count == threshold) { - printf("Max error count %d reached, rebooting.\n\n", threshold); - mcc_platform_do_wait(1 * 1000); - mcc_platform_reboot(); - } - } - - bool call_register() - { - - _cloud_client.on_registered(this, &SimpleM2MClient::client_registered); - _cloud_client.on_registration_updated(this, &SimpleM2MClient::client_registration_updated); - _cloud_client.on_unregistered(this, &SimpleM2MClient::client_unregistered); - _cloud_client.on_error(this, &SimpleM2MClient::error); - -#ifdef MBED_CLOUD_CLIENT_SUPPORT_MULTICAST_UPDATE - _cloud_client.on_external_update(external_update); -#endif - - bool setup = _cloud_client.setup(mcc_platform_get_network_interface()); - _register_called = true; - if (!setup) { - printf("Client setup failed\n"); - return false; - } - -#ifdef MBED_CLOUD_CLIENT_TRANSPORT_MODE_UDP_QUEUE - callback_handler cb(this, &SimpleM2MClient::sleep_callback_function); - _cloud_client.set_queue_sleep_handler(cb); -#endif - -#ifdef MBED_CLOUD_CLIENT_SUPPORT_UPDATE - /* Set callback functions for authorizing updates and monitoring progress. - Code is implemented in update_ui_example.cpp - Both callbacks are completely optional. If no authorization callback - is set, the update process will procede immediately in each step. - */ - update_ui_set_cloud_client(&_cloud_client); - _cloud_client.set_update_authorize_priority_handler(update_authorize_priority_handler); - _cloud_client.set_update_progress_handler(update_progress); -#endif - return true; - } - - void init() - { - _cloud_client.init(); - } - void close() - { - _cloud_client.close(); - } - - void register_update() - { - _cloud_client.register_update(); - } - - void client_registered() - { - _registered = true; - printf("Client registered\r\n"); - _error_count = 0; - static const ConnectorClientEndpointInfo *endpoint = NULL; - if (endpoint == NULL) { - endpoint = _cloud_client.endpoint_info(); - if (endpoint) { -#if MBED_CONF_APP_DEVELOPER_MODE == 1 - printf("Endpoint Name: %s\r\n", endpoint->internal_endpoint_name.c_str()); -#else - printf("Endpoint Name: %s\r\n", endpoint->endpoint_name.c_str()); -#endif - printf("Device ID: %s\r\n", endpoint->internal_endpoint_name.c_str()); - } - } -#ifdef MEMORY_TESTS_HEAP - print_heap_stats(); -#endif - } - - void client_registration_updated() - { - printf("Client registration updated\n"); - _error_count = 0; - } - - void client_unregistered() - { -#ifdef MBED_CLOUD_CLIENT_TRANSPORT_MODE_UDP_QUEUE - _paused = false; -#endif - _registered = false; - _register_called = false; - printf("Client unregistered - Exiting application\n"); -#ifdef MEMORY_TESTS_HEAP - print_heap_stats(); -#endif - } - - void error(int error_code) - { - const char *error; - switch (error_code) { - case MbedCloudClient::ConnectErrorNone: - error = "MbedCloudClient::ConnectErrorNone"; - break; - case MbedCloudClient::ConnectAlreadyExists: - error = "MbedCloudClient::ConnectAlreadyExists"; - break; - case MbedCloudClient::ConnectBootstrapFailed: - error = "MbedCloudClient::ConnectBootstrapFailed"; - break; - case MbedCloudClient::ConnectInvalidParameters: - error = "MbedCloudClient::ConnectInvalidParameters"; - break; - case MbedCloudClient::ConnectNotRegistered: - error = "MbedCloudClient::ConnectNotRegistered"; - break; - case MbedCloudClient::ConnectTimeout: - error = "MbedCloudClient::ConnectTimeout"; - break; - case MbedCloudClient::ConnectNetworkError: - error = "MbedCloudClient::ConnectNetworkError"; - break; - case MbedCloudClient::ConnectResponseParseFailed: - error = "MbedCloudClient::ConnectResponseParseFailed"; - break; - case MbedCloudClient::ConnectUnknownError: - error = "MbedCloudClient::ConnectUnknownError"; - break; - case MbedCloudClient::ConnectMemoryConnectFail: - error = "MbedCloudClient::ConnectMemoryConnectFail"; - break; - case MbedCloudClient::ConnectNotAllowed: - error = "MbedCloudClient::ConnectNotAllowed"; - break; - case MbedCloudClient::ConnectSecureConnectionFailed: - error = "MbedCloudClient::ConnectSecureConnectionFailed"; - break; - case MbedCloudClient::ConnectDnsResolvingFailed: - error = "MbedCloudClient::ConnectDnsResolvingFailed"; - break; - case MbedCloudClient::ConnectorFailedToStoreCredentials: - error = "MbedCloudClient::ConnectorFailedToStoreCredentials"; - break; - case MbedCloudClient::ConnectorFailedToReadCredentials: - error = "MbedCloudClient::ConnectorFailedToReadCredentials"; - break; -#ifdef MBED_CLOUD_CLIENT_SUPPORT_UPDATE - case MbedCloudClient::UpdateWarningCertificateNotFound: - error = "MbedCloudClient::UpdateWarningCertificateNotFound"; - break; - case MbedCloudClient::UpdateWarningIdentityNotFound: - error = "MbedCloudClient::UpdateWarningIdentityNotFound"; - break; - case MbedCloudClient::UpdateWarningCertificateInvalid: - error = "MbedCloudClient::UpdateWarningCertificateInvalid"; - break; - case MbedCloudClient::UpdateWarningSignatureInvalid: - error = "MbedCloudClient::UpdateWarningSignatureInvalid"; - break; - case MbedCloudClient::UpdateWarningVendorMismatch: - error = "MbedCloudClient::UpdateWarningVendorMismatch"; - break; - case MbedCloudClient::UpdateWarningClassMismatch: - error = "MbedCloudClient::UpdateWarningClassMismatch"; - break; - case MbedCloudClient::UpdateWarningDeviceMismatch: - error = "MbedCloudClient::UpdateWarningDeviceMismatch"; - break; - case MbedCloudClient::UpdateWarningURINotFound: - error = "MbedCloudClient::UpdateWarningURINotFound"; - break; - case MbedCloudClient::UpdateWarningRollbackProtection: - error = "MbedCloudClient::UpdateWarningRollbackProtection"; - break; - case MbedCloudClient::UpdateWarningUnknown: - error = "MbedCloudClient::UpdateWarningUnknown"; - break; - case MbedCloudClient::UpdateErrorWriteToStorage: - error = "MbedCloudClient::UpdateErrorWriteToStorage"; - break; - case MbedCloudClient::UpdateErrorInvalidHash: - error = "MbedCloudClient::UpdateErrorInvalidHash"; - break; - case MbedCloudClient::UpdateErrorConnection: - error = "MbedCloudClient::UpdateErrorConnection"; - break; - case MbedCloudClient::UpdateWarningAuthorizationRejected: - error = "MbedCloudClient::UpdateWarningAuthorizationRejected"; - break; - case MbedCloudClient::UpdateWarningAuthorizationUnavailable: - error = "MbedCloudClient::UpdateWarningAuthorizationUnavailable"; - break; - case MbedCloudClient::UpdateCertificateInsertion: - error = "MbedCloudClient::UpdateCertificateInsertion"; - break; -#endif -#ifndef MBED_CONF_MBED_CLOUD_CLIENT_DISABLE_CERTIFICATE_ENROLLMENT - case CE_STATUS_INIT_FAILED: - error = "CE_STATUS_INIT_FAILED"; - break; -#endif // !MBED_CONF_MBED_CLOUD_CLIENT_DISABLE_CERTIFICATE_ENROLLMENT - - default: - error = "UNKNOWN"; - } - printf("\nError occurred : %s\r\n", error); - printf("Error code : %d\r\n", error_code); - printf("Error details : %s\r\n", _cloud_client.error_description()); - -// Feature is disabled if MAX_ERROR_COUNT is 0. -#if (MAX_ERROR_COUNT > 0) - if ( error_code == MbedCloudClient::ConnectNetworkError || - error_code == MbedCloudClient::ConnectDnsResolvingFailed || - error_code == MbedCloudClient::ConnectSecureConnectionFailed || - error_code == MbedCloudClient::ConnectTimeout) { - reboot_if_threshold_value(MAX_ERROR_COUNT); - } -#endif - } - - bool is_client_registered() - { - return _registered; - } - - bool is_register_called() - { - return _register_called; - } - - void register_and_connect() - { -#if defined (MEMORY_TESTS_HEAP) && !defined(MCC_MINIMAL) - // Add some test resources to measure memory consumption. - // This code is activated only if MEMORY_TESTS_HEAP is defined. - create_m2mobject_test_set(_obj_list); -#endif - _cloud_client.add_objects(_obj_list); - - // Start registering to the cloud. - call_register(); - - // Print memory statistics if the MEMORY_TESTS_HEAP is defined. -#ifdef MEMORY_TESTS_HEAP - printf("Register being called\r\n"); - print_heap_stats(); -#endif - } - - MbedCloudClient &get_cloud_client() - { - return _cloud_client; - } - - M2MObjectList *get_m2m_obj_list() - { - return &_obj_list; - } - -#ifdef MBED_CLOUD_CLIENT_TRANSPORT_MODE_UDP_QUEUE - void sleep_callback_function() - { - printf("Pelion client is going to sleep - Pausing the client\r\n"); - _cloud_client.pause(); - mcc_platform_interface_close(); - _paused = true; - } - - bool is_client_paused() - { - return _paused; - } - - void client_resumed() - { - _paused = false; - int timeout_ms = 5000; - while (-1 == mcc_platform_interface_connect()){ - // Will try to connect using mcc_platform_interface_connect until error count and then does reboot if - // not successful. Wait timeout is always doubled - printf("Network did not recover after pause. Try again after %d milliseconds.\n", timeout_ms); - mcc_platform_do_wait(timeout_ms); - timeout_ms *= 2; - reboot_if_threshold_value(MAX_PDMC_CLIENT_CONNECTION_ERROR_COUNT); - } - _cloud_client.resume(mcc_platform_get_network_interface()); - - } - -#endif - - M2MResource *add_cloud_resource(uint16_t object_id, uint16_t instance_id, - uint16_t resource_id, const char *resource_type, - M2MResourceInstance::ResourceType data_type, - M2MBase::Operation allowed, const char *value, - bool observable, void *cb, void *message_status_cb) - { - return add_resource(&_obj_list, object_id, instance_id, resource_id, resource_type, data_type, - allowed, value, observable, cb, message_status_cb); - - } - -private: - M2MObjectList _obj_list; - MbedCloudClient _cloud_client; - bool _registered; - bool _register_called; - int _error_count; -#ifdef MBED_CLOUD_CLIENT_TRANSPORT_MODE_UDP_QUEUE - volatile bool _paused; -#endif - -}; - -#endif // SIMPLEM2MCLIENT_H diff --git a/west.yml b/west.yml index c150f19..88be4c8 100644 --- a/west.yml +++ b/west.yml @@ -10,7 +10,7 @@ manifest: - name: pelion-dm repo-path: mbed-cloud-client remote: PelionIoT - revision: d7edc529ed3722c811ff401440ef58ea980bf543 + revision: 105a1846277c80e5eb15ad74de7e4d7b15e57c26 path: modules/lib/pelion-dm - name: zephyr remote: zephyrproject-rtos