Skip to content

Commit

Permalink
Merge pull request #52 from ARMmbed/release-3.4.0
Browse files Browse the repository at this point in the history
mbed-cloud-client 3.4.0
  • Loading branch information
teetak01 authored Aug 28, 2019
2 parents 1a16ef2 + 0f0f4e1 commit 3212529
Show file tree
Hide file tree
Showing 281 changed files with 24,772 additions and 5,454 deletions.
46 changes: 45 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,12 +1,56 @@
## Changelog for Pelion Device Management Client

### Release 3.4.0 (28.08.2019)

#### Device Management Connect client

* Added the `max-age` option to be part of the notification message construction. This fixes the issue that the resource cache was not being updated due to value changes from notification messages.
* Added a Secure Device Access (SDA) client library.
* A new feature flag that enables SDA - `MBED_CLOUD_CLIENT_ENABLE_SDA` (disabled by default).
* A new feature flag, `MBED_CONF_MBED_CLIENT_ENABLE_OBSERVATION_PARAMETERS`, controls the usage of LwM2M Write attributes for LwM2M resources. Disabling this feature will allow you to save RAM used by observation parameters per resource. Disabled by setting the flag to 0.
* New API for managing update priority and rejecting optional firmware updates.
- Added `set_update_authorize_priority_handler()`.
- Added `update_reject()`.
- New error enums for update authorization rejection, `UpdateWarningAuthorizationRejected`, `UpdateWarningAuthorizationUnavailable`.
* Support for certificate renewal with Platform Security Architecture (PSA).
* Extended `MbedCloudClient()` constructor to allow callback registration to client.
* A new API for creating `M2MResource` directly without first creating `M2MObject` and `M2MObjectInstance`.
* Bug fix: Requests sent from Device Management Client using the same URI and method were determined duplicates even if the context parameter was different.

#### Factory configurator client

* Replaced CBOR implementation library with tinycbor.
* Bug fix: Working with a file name length of `KCM_MAX_FILENAME_SIZE` in KCM APIs resulted in a `KCM_STATUS_FILE_NAME_TOO_LONG` error.

#### Secure Device Access client

* Initial Secure Device Access (SDA) release.
* SDA implements the ACE-OAuth standard, which specifies a framework for authenticating and authorizing in constrained IoT environments.
* The [full SDA documentation](../device-management/secure-device-access.html) is available on our documentation site.

#### Device Management Update client

* New update authorization API:
* Deprecated `ARM_UC_SetAuthorizeHandler()` in favor of `ARM_UC_SetAuthorizePriorityHandler()`.
* Added `ARM_UC_Reject()` to the application authorization callback to deliver the rejection reason to the service.
* Added a priority field to the manifest.
* Propagated update priority from the manifest to the application authorization callback.
* Writing of the update candidate metadata is postponed to a later phase. The metadata is written when the download has completed and the client application has authorized the installation.

#### Platform Adaptation Layer (PAL)

* [Linux] Read the source entropy from the target machine system environment if available; otherwise, use the user default source entropy file path.
* Read the entropy file name from the system environment entry `ENTROPYSOURCE=<path-to-entropy-file-name>`.
* [TLS] Fixed potential double free issue in `pal_initTLS()`.
* [Tests] Do not try to execute filesystem tests if there is no filesystem.

### Release 3.3.0 (02.07.2019)

#### Device Management Connect client

* Updated Mbed CoAP to 4.8.0.
* A fix to accommodate a null terminator space for managing a common name parameter (max 64 characters) in an `X.509` certificate.
* A fix to clear a stored SSL session when the device rebootstraps. Without clearing, a bootstrap loop may render the device unusable.
* Fix to clear stored SSL session when the device re-bootstraps otherwise the device is going into eternal re-bootstrap loop thus bricking up the device.

#### Factory configurator client

Expand Down
19 changes: 15 additions & 4 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,7 @@ ADD_GLOBALDIR(${CMAKE_CURRENT_SOURCE_DIR}/nanostack-libservice/mbed-client-libse
ADD_GLOBALDIR(${CMAKE_CURRENT_SOURCE_DIR}/sal-stack-nanostack-eventloop)
ADD_GLOBALDIR(${CMAKE_CURRENT_SOURCE_DIR}/sal-stack-nanostack-eventloop/nanostack-event-loop)
ADD_GLOBALDIR(${CMAKE_CURRENT_SOURCE_DIR}/ns-hal-pal)
ADD_GLOBALDIR(${CMAKE_CURRENT_SOURCE_DIR}/tinycbor/src)

# factory-client

Expand All @@ -85,7 +86,6 @@ SET(FCC_MODULES
key-config-manager
factory-configurator-client
fcc-bundle-handler
secsrv-cbor
logger
storage
utils
Expand Down Expand Up @@ -121,7 +121,6 @@ include_directories(${FACTORY_CLIENT_SOURCE_DIR}/mbed-client-esfs/source-pal/api
include_directories(${FACTORY_CLIENT_SOURCE_DIR}/mbed-client-esfs/source-pal/linux)
include_directories(${FACTORY_CLIENT_SOURCE_DIR}/crypto-service/crypto-service)
include_directories(${FACTORY_CLIENT_SOURCE_DIR}/crypto-service/source/include)
include_directories(${FACTORY_CLIENT_SOURCE_DIR}/secsrv-cbor/secsrv-cbor)
include_directories(${FACTORY_CLIENT_SOURCE_DIR}/fcc-bundle-handler/fcc-bundle-handler)
include_directories(${FACTORY_CLIENT_SOURCE_DIR}/fcc-bundle-handler/source/include)
include_directories(${FACTORY_CLIENT_SOURCE_DIR}/fcc-output-info-handler/fcc-output-info-handler)
Expand All @@ -132,6 +131,18 @@ ADD_GLOBALDIR(${CERTIFICATE_ENROLLMENT_CLIENT_SOURCE_DIR}/certificate-enrollment
include_directories(${CERTIFICATE_ENROLLMENT_CLIENT_SOURCE_DIR}/certificate-enrollment-client)
include_directories(${CERTIFICATE_ENROLLMENT_CLIENT_SOURCE_DIR}/source/include)

# Secure Device Access Client
SET(SECURE_DEVICE_ACCESS_CLIENT_SOURCE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/secure-device-access-client)
ADD_GLOBALDIR(${SECURE_DEVICE_ACCESS_CLIENT_SOURCE_DIR}/secure-device-access/secure-device-access)
include_directories(${SECURE_DEVICE_ACCESS_CLIENT_SOURCE_DIR}/logger/logger)
include_directories(${SECURE_DEVICE_ACCESS_CLIENT_SOURCE_DIR}/helpers/helpers)
include_directories(${SECURE_DEVICE_ACCESS_CLIENT_SOURCE_DIR}/mem/mem)
include_directories(${SECURE_DEVICE_ACCESS_CLIENT_SOURCE_DIR}/platform/platform)
include_directories(${SECURE_DEVICE_ACCESS_CLIENT_SOURCE_DIR}/sda-bundle-parser/sda-bundle-parser)
include_directories(${SECURE_DEVICE_ACCESS_CLIENT_SOURCE_DIR}/secure-device-access/secure-device-access)
include_directories(${SECURE_DEVICE_ACCESS_CLIENT_SOURCE_DIR}/sda-cose/sda-cose)
include_directories(${SECURE_DEVICE_ACCESS_CLIENT_SOURCE_DIR}/cose-c/cose-c)

# Update client

SET(UPDATE_SOURCE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/update-client-hub)
Expand Down Expand Up @@ -241,12 +252,12 @@ target_link_libraries(mbedclient nanostacklibservice nanostackeventloop mbedcoap
CREATE_LIBRARY(mbedCloudClient "${MBED_CLOUD_CLIENT_SRC}" "")

# Create buld dependencies to ensure all the needed parts get build
add_dependencies(mbedCloudClient pal factory-configurator-client esfs mbedTrace nanostacklibservice nanostackeventloop mbedclient certificate-enrollment-client update-client)
add_dependencies(mbedCloudClient pal factory-configurator-client mbedTrace nanostacklibservice nanostackeventloop mbedclient certificate-enrollment-client update-client)

# Add linking dependency for all the subcomponents of mbedCloudClient. This allows one to
# just have "target_link_libraries(<client-application> mbedCloudClient)" and cmake will
# automatically build all the submodules.
target_link_libraries(mbedCloudClient pal factory-configurator-client esfs mbedTrace nanostacklibservice nanostackeventloop mbedclient certificate-enrollment-client update-client)
target_link_libraries(mbedCloudClient pal factory-configurator-client mbedTrace nanostacklibservice nanostackeventloop mbedclient certificate-enrollment-client update-client)

ADDSUBDIRS()

11 changes: 9 additions & 2 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,9 @@ LOCAL_ADD_INCLUDE += \
LOCAL_ADD_INCLUDE += \
${LOCAL_NAME}/certificate-enrollment-client/certificate-enrollment-client

# Tinycbor
LOCAL_ADD_INCLUDE += ${LOCAL_NAME}/tinycbor/src

# Compile the sub-modules, except when the "service" must be used as a library.
# list all the modules that need to be compiled prior to using this module
LOCAL_MODULE_DEPENDS += ${MBED_CLOUD_SERVICE}/mbed-cloud-client/mbed-client-pal
Expand All @@ -116,12 +119,13 @@ LOCAL_EXPORT_FLAG += "NS_EXCLUDE_HIGHRES_TIMER=1"
LOCAL_EXPORT_FLAG += "MBED_CONF_NANOSTACK_EVENTLOOP_USE_PLATFORM_TICK_TIMER"
LOCAL_EXPORT_FLAG += "NS_EVENTLOOP_USE_TICK_TIMER"



# Disable code using STL as it not available on SDK
LOCAL_EXPORT_FLAG += "MBED_CLOUD_CLIENT_STL_API=0"
LOCAL_EXPORT_FLAG += "MBED_CLOUD_CLIENT_STD_NAMESPACE_POLLUTION=0"

# Disable code using ldexp as it not available on SDK
LOCAL_EXPORT_FLAG += "CBOR_NO_FLOATING_POINT"

# Update client
LOCAL_EXPORT_FLAG += "ATOMIC_QUEUE_USE_PAL=1"
LOCAL_EXPORT_FLAG += "ARM_UC_PROFILE_MBED_CLOUD_CLIENT=1"
Expand Down Expand Up @@ -181,6 +185,9 @@ C_SRC += ${wildcard update-client-hub/modules/pal-filesystem/source/*.c}
C_SRC += ${wildcard certificate-enrollment-client/source/*.c}
C++_SRC += ${wildcard certificate-enrollment-client/source/*.cpp}

# Tinycbor
C_SRC += ${wildcard tinycbor/src/*.c}

# mbed-trace and its dependency. This might deserver a separate lib, but the mbed-trace
# already has a makefile and mixing this system with generic make takes a bit more work
# than deemed necessary for two C-files.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@ namespace CertificateEnrollmentClient {
* Zero current_cert pointer, then release the semaphore. Note that when the semaphore is released - new device renewals may be made.
* Then call renewal_data->finish() and delete renewal_data.
*
* \param renewal_data the data of the certificate to be renewed.
* \param renewal_data the data of the certificate to be renewed.
* It is important that this is passed to the function because after releasing the semaphore - the global pointer may be replaced.
* \param exit_status the status of the renewal process
*/
Expand Down Expand Up @@ -158,7 +158,7 @@ namespace CertificateEnrollmentClient {
* \brief Start the renewal process.
* Parse the certificate name, generate keys and CSR. Then call the EST client so the new certificate may be retrieved
*
* \param renewal_data the data of the certificate to be renewed
* \param renewal_data the data of the certificate to be renewed
*/
static void certificate_renewal_start(CertificateRenewalDataBase *renewal_data);

Expand Down Expand Up @@ -197,7 +197,7 @@ void CertificateEnrollmentClient::call_user_cb_send_response(const uint8_t *tlv,
void CertificateEnrollmentClient::certificate_renewal_post(void *arg)
{
palStatus_t pal_status;
ce_status_e status;
ce_status_e status;
SA_PV_LOG_INFO_FUNC_ENTER_NO_ARGS();

M2MResource::M2MExecuteParameter *args = (M2MResource::M2MExecuteParameter *)arg;
Expand All @@ -219,7 +219,7 @@ void CertificateEnrollmentClient::certificate_renewal_post(void *arg)
}

call_user_cb_send_response(data, data_size, status);
return;
return;
}

// Enqueue the event
Expand Down Expand Up @@ -279,7 +279,7 @@ ce_status_e CertificateEnrollmentClient::certificate_renew(const char *cert_name
} else {
status = CE_STATUS_ERROR;
}

}

SA_PV_LOG_INFO_FUNC_EXIT_NO_ARGS();
Expand Down Expand Up @@ -376,7 +376,7 @@ ce_status_e CertificateEnrollmentClient::init(M2MBaseList& list, const EstClient

#ifdef CERT_ENROLLMENT_EST_MOCK
PV_UNUSED_PARAM(est_client);
g_est_client = new EstClientMock();
g_est_client = new EstClientMock();
SA_PV_ERR_RECOVERABLE_RETURN_IF((!g_est_client), CE_STATUS_ERROR, "Error creating mock EST");
#else
g_est_client = est_client;
Expand Down Expand Up @@ -406,7 +406,7 @@ void CertificateEnrollmentClient::finalize()

// LWM2M objects, instances, and resources are deleted when MbedCloudClient is unregistered and ServiceClient::state_unregister() is called
// Currently nothing to finalize for CE core module except for KCM. However we do not wish to finalize it it may be used by other resources

// Release our resources
release_objects();
}
Expand Down Expand Up @@ -449,20 +449,19 @@ void CertificateEnrollmentClient::certificate_renewal_start(CertificateRenewalDa
SA_PV_ERR_RECOVERABLE_RETURN_IF((ce_status != CE_STATUS_SUCCESS), certificate_renewal_finish(renewal_data, ce_status), "Parse error");

// Create CSR's key handle
kcm_status = cs_ec_key_new(&renewal_data->key_handle);

kcm_status = cs_key_pair_new(&(renewal_data->key_handle), true);
// translate error to some CE native error
ce_status = ce_error_handler(kcm_status);
SA_PV_ERR_RECOVERABLE_RETURN_IF((ce_status != CE_STATUS_SUCCESS), certificate_renewal_finish(renewal_data, ce_status), "Failed creating new key handle");

// key handle is initialized in the base constructor
ce_status = ce_generate_keys_and_create_csr_from_certificate(renewal_data->cert_name, renewal_data->key_handle, &renewal_data->csr, &renewal_data->csr_size);
ce_status = ce_generate_keys_and_create_csr_from_certificate(renewal_data->cert_name, &(renewal_data->renewal_items_names), renewal_data->key_handle, &renewal_data->csr, &renewal_data->csr_size);
SA_PV_ERR_RECOVERABLE_RETURN_IF((ce_status != CE_STATUS_SUCCESS), certificate_renewal_finish(renewal_data, ce_status), "Keys/CSR generation error");

// Call the EST client

// If lwm2m device certificate - set cert name to NULL and request EST enrollment
if (pv_str_equals(g_lwm2m_name, renewal_data->cert_name,(uint32_t)(strlen(g_lwm2m_name) + 1))) {
if (pv_str_equals(g_lwm2m_name, renewal_data->cert_name, (uint32_t)(strlen(g_lwm2m_name) + 1))) {
SA_PV_LOG_INFO("Attempting to renew LwM2M device certificate\n");
cert_name = NULL;
cert_name_size = 0;
Expand Down Expand Up @@ -511,7 +510,7 @@ void CertificateEnrollmentClient::est_cb(est_enrollment_result_e result,
ce_status_e status;
SA_PV_LOG_INFO_FUNC_ENTER("result = %d", result);

PV_UNUSED_PARAM(context);
PV_UNUSED_PARAM(context);
if (result != EST_ENROLLMENT_SUCCESS || cert_chain == NULL) {
return certificate_renewal_finish(current_cert, CE_STATUS_EST_ERROR);
}
Expand All @@ -523,7 +522,7 @@ void CertificateEnrollmentClient::est_cb(est_enrollment_result_e result,
if (status != CE_STATUS_SUCCESS) { // If event scheduling fails - free the chain context and finish the process
SA_PV_LOG_INFO("Error scheduling event");
g_est_client->free_cert_chain_context(current_cert->est_data);

// Make sure we do not keep an invalid pointer
current_cert->est_data = NULL;
certificate_renewal_finish(current_cert, status);
Expand All @@ -543,7 +542,7 @@ void CertificateEnrollmentClient::est_response_process(CertificateRenewalDataBas
params.crypto_handle = renewal_data->key_handle;

// Perform a safe renewal
ce_status = ce_safe_renewal(renewal_data->cert_name, &params);
ce_status = ce_safe_renewal(renewal_data->cert_name, &renewal_data->renewal_items_names, &params);

// Free the est chain. Do not free in the destructor, we'd rather free it as soon as possible
g_est_client->free_cert_chain_context(renewal_data->est_data);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,11 +32,12 @@ namespace CertificateEnrollmentClient {
{
_raw_data_size = raw_data_size;
cert_name = NULL;
memset((void*)&renewal_items_names, 0, sizeof(renewal_items_names));
csr = NULL;
csr_size = 0;
est_data = NULL;
key_handle = 0;
_raw_data = (uint8_t *)malloc(raw_data_size);
_raw_data = (uint8_t *)malloc(raw_data_size);
memcpy(_raw_data, raw_data, _raw_data_size);
}

Expand All @@ -50,7 +51,7 @@ namespace CertificateEnrollmentClient {
free(csr);

// Release the key handle, this shouldn't fail...
kcm_status = cs_ec_key_free(&key_handle);
kcm_status = cs_key_pair_free(&key_handle);
ce_status = ce_error_handler(kcm_status);

if (ce_status != CE_STATUS_SUCCESS) {
Expand All @@ -75,7 +76,7 @@ namespace CertificateEnrollmentClient {

ce_tlv_status_e status;
ce_tlv_element_s element;

cert_name = NULL;

if (ce_tlv_parser_init(_raw_data, _raw_data_size, &element) != CE_TLV_STATUS_SUCCESS) {
Expand Down
Loading

0 comments on commit 3212529

Please sign in to comment.