Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependencies: FXAS21002 FXOS8700Q
arm_uc_crypto_pal.c
00001 // ---------------------------------------------------------------------------- 00002 // Copyright 2016-2017 ARM Ltd. 00003 // 00004 // SPDX-License-Identifier: Apache-2.0 00005 // 00006 // Licensed under the Apache License, Version 2.0 (the "License"); 00007 // you may not use this file except in compliance with the License. 00008 // You may obtain a copy of the License at 00009 // 00010 // http://www.apache.org/licenses/LICENSE-2.0 00011 // 00012 // Unless required by applicable law or agreed to in writing, software 00013 // distributed under the License is distributed on an "AS IS" BASIS, 00014 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00015 // See the License for the specific language governing permissions and 00016 // limitations under the License. 00017 // ---------------------------------------------------------------------------- 00018 00019 #include "update-client-common/arm_uc_config.h" 00020 #include "update-client-common/arm_uc_error.h" 00021 #include "update-client-common/arm_uc_crypto.h" 00022 00023 #include <string.h> 00024 00025 #if defined(ARM_UC_FEATURE_CRYPTO_PAL) && (ARM_UC_FEATURE_CRYPTO_PAL == 1) 00026 #include "pal.h" 00027 #include "sotp.h" 00028 #ifndef palMDHandle_t 00029 #include "pal_Crypto.h" 00030 #include "pal_plat_rot.h" 00031 #else 00032 #include "mbedtls/md.h" 00033 #endif 00034 00035 arm_uc_error_t ARM_UC_cryptoHashSetup(arm_uc_mdHandle_t *hDigest, arm_uc_mdType_t mdType) 00036 { 00037 arm_uc_error_t result = (arm_uc_error_t) { ARM_UC_CU_ERR_INVALID_PARAMETER }; 00038 if (hDigest) { 00039 palStatus_t rc = pal_mdInit(hDigest, mdType); 00040 if (rc == PAL_SUCCESS) { 00041 result.code = ERR_NONE; 00042 } 00043 } 00044 return result; 00045 } 00046 00047 arm_uc_error_t ARM_UC_cryptoHashUpdate(arm_uc_mdHandle_t *hDigest, arm_uc_buffer_t *input) 00048 { 00049 arm_uc_error_t result = (arm_uc_error_t) { ARM_UC_CU_ERR_INVALID_PARAMETER }; 00050 if (hDigest && input) { 00051 palStatus_t rc = pal_mdUpdate(*hDigest, input->ptr, input->size); 00052 if (rc == PAL_SUCCESS) { 00053 result = (arm_uc_error_t) { ERR_NONE }; 00054 } 00055 } 00056 return result; 00057 } 00058 00059 arm_uc_error_t ARM_UC_cryptoHashFinish(arm_uc_mdHandle_t *hDigest, arm_uc_buffer_t *output) 00060 { 00061 arm_uc_error_t result = (arm_uc_error_t) { ARM_UC_CU_ERR_INVALID_PARAMETER }; 00062 00063 // TODO: validate buffer size? I guess we just hope for the best! 00064 if (hDigest && output && output->size_max >= 256 / 8) { // FIXME:PAL does not provide a method to extract this 00065 palStatus_t rc = pal_mdFinal(*hDigest, output->ptr); 00066 00067 if (rc == PAL_SUCCESS) { 00068 result = (arm_uc_error_t) { ERR_NONE }; 00069 output->size = 256 / 8; // FIXME:PAL does not provide a method to extract this 00070 } 00071 } 00072 if (hDigest) { 00073 palStatus_t rc = pal_mdFree(hDigest); 00074 if (rc != PAL_SUCCESS && result.error == ERR_NONE) { 00075 result.module = TWO_CC('P', 'A'); 00076 result.error = rc; 00077 } 00078 } 00079 return result; 00080 } 00081 00082 arm_uc_error_t ARM_UC_cryptoDecryptSetup(arm_uc_cipherHandle_t *hCipher, arm_uc_buffer_t *key, arm_uc_buffer_t *iv, 00083 int32_t aesKeySize) 00084 { 00085 arm_uc_error_t result = (arm_uc_error_t) { ARM_UC_CU_ERR_INVALID_PARAMETER }; 00086 00087 if (key && key->ptr && iv && iv->ptr) { 00088 palStatus_t rc = 1; 00089 00090 switch (aesKeySize) { 00091 case 128: 00092 case 256: { 00093 rc = pal_initAes(&hCipher->aes_context); 00094 /* NOTE: From the mbedtls documentation: 00095 * Due to the nature of CTR you should use the same key schedule for 00096 * both encryption and decryption. So a context initialized with 00097 * mbedtls_aes_setkey_enc() for both MBEDTLS_AES_ENCRYPT and MBEDTLS_AES_DECRYPT. 00098 */ 00099 if (rc == PAL_SUCCESS) { 00100 rc = pal_setAesKey(hCipher->aes_context, key->ptr, aesKeySize, PAL_KEY_TARGET_ENCRYPTION); 00101 } 00102 hCipher->aes_iv = iv->ptr; 00103 break; 00104 } 00105 default: 00106 // rc is still 1, this means the function returns Invalid Parameter 00107 break; 00108 } 00109 00110 if (rc == PAL_SUCCESS) { 00111 result = (arm_uc_error_t) { ERR_NONE }; 00112 } 00113 } 00114 00115 return result; 00116 } 00117 00118 arm_uc_error_t ARM_UC_cryptoDecryptUpdate(arm_uc_cipherHandle_t *hCipher, const uint8_t *input_ptr, uint32_t input_size, 00119 arm_uc_buffer_t *output) 00120 { 00121 arm_uc_error_t result = (arm_uc_error_t) { ARM_UC_CU_ERR_INVALID_PARAMETER }; 00122 size_t data_size = input_size < output->size_max ? input_size : output->size_max; 00123 output->size = 0; 00124 palStatus_t rc = pal_aesCTR( 00125 hCipher->aes_context, 00126 input_ptr, 00127 output->ptr, 00128 data_size, 00129 hCipher->aes_iv 00130 ); 00131 if (rc == PAL_SUCCESS) { 00132 result = (arm_uc_error_t) { ERR_NONE }; 00133 output->size = data_size; 00134 } 00135 return result; 00136 } 00137 00138 arm_uc_error_t ARM_UC_cryptoDecryptFinish(arm_uc_cipherHandle_t *hCipher, arm_uc_buffer_t *output) 00139 { 00140 pal_freeAes(&hCipher->aes_context); 00141 (void) output; 00142 return (arm_uc_error_t) {ERR_NONE}; 00143 } 00144 00145 arm_uc_error_t ARM_UC_cryptoHMACSHA256(arm_uc_buffer_t *key, 00146 arm_uc_buffer_t *input, 00147 arm_uc_buffer_t *output) 00148 { 00149 arm_uc_error_t result = (arm_uc_error_t) { ARM_UC_CU_ERR_INVALID_PARAMETER }; 00150 00151 00152 size_t outPutSize = 0; 00153 palStatus_t pal_st = pal_mdHmacSha256(key->ptr, key->size, 00154 input->ptr, input->size, 00155 output->ptr, &outPutSize); 00156 00157 output->size = (uint32_t) outPutSize; // we lose here some bits in 64 bit systems, 00158 // but as long as we are under u32 MAX size it does not matter 00159 // and as input size is read from u32 this should be safe 00160 00161 00162 if ((pal_st == PAL_SUCCESS) && (output->size == ARM_UC_SHA256_SIZE)) { 00163 result = (arm_uc_error_t) { ERR_NONE }; 00164 } 00165 00166 return result; 00167 } 00168 00169 int8_t mbed_cloud_client_get_rot_128bit(uint8_t *key_buf, uint32_t length) 00170 { 00171 int8_t rv = -1; 00172 palStatus_t status = PAL_ERR_GENERIC_FAILURE ; 00173 00174 if (length < ARM_UC_ROT_SIZE) { 00175 return -1; 00176 } 00177 //Get RoT 00178 status = pal_plat_osGetRoT(key_buf, ARM_UC_ROT_SIZE); 00179 00180 if (status == PAL_SUCCESS) { 00181 rv = 0; 00182 } else { 00183 /* clear buffer on failure so we don't leak the rot */ 00184 memset(key_buf, 0, length); 00185 } 00186 00187 return rv; 00188 } 00189 00190 #endif
Generated on Tue Jul 12 2022 20:20:57 by
