1 /* 2 * Copyright 2017-2022 NXP 3 * All rights reserved. 4 * 5 * SPDX-License-Identifier: BSD-3-Clause 6 */ 7 #ifndef _FSL_HASHCRYPT_H_ 8 #define _FSL_HASHCRYPT_H_ 9 10 #include "fsl_common.h" 11 12 /*! @brief HASHCRYPT status return codes. */ 13 enum _hashcrypt_status 14 { 15 kStatus_HASHCRYPT_Again = 16 MAKE_STATUS(kStatusGroup_HASHCRYPT, 0), /*!< Non-blocking function shall be called again. */ 17 }; 18 19 /******************************************************************************* 20 * Definitions 21 *******************************************************************************/ 22 23 /*! 24 * @addtogroup hashcrypt_driver 25 * @{ 26 */ 27 /*! @name Driver version */ 28 /*@{*/ 29 /*! @brief HASHCRYPT driver version. Version 2.2.11. 30 * 31 * Current version: 2.2.11 32 * 33 * Change log: 34 * - Version 2.0.0 35 * - Initial version 36 * - Version 2.0.1 37 * - Support loading AES key from unaligned address 38 * - Version 2.0.2 39 * - Support loading AES key from unaligned address for different compiler and core variants 40 * - Version 2.0.3 41 * - Remove SHA512 and AES ICB algorithm definitions 42 * - Version 2.0.4 43 * - Add SHA context switch support 44 * - Version 2.1.0 45 * - Update the register name and macro to align with new header. 46 * - Version 2.1.1 47 * - Fix MISRA C-2012. 48 * - Version 2.1.2 49 * - Support loading AES input data from unaligned address. 50 * - Version 2.1.3 51 * - Fix MISRA C-2012. 52 * - Version 2.1.4 53 * - Fix context switch cannot work when switching from AES. 54 * - Version 2.1.5 55 * - Add data synchronization barrier inside hashcrypt_sha_ldm_stm_16_words() 56 * to prevent possible optimization issue. 57 * - Version 2.2.0 58 * - Add AES-OFB and AES-CFB mixed IP/SW modes. 59 * - Version 2.2.1 60 * - Add data synchronization barrier inside hashcrypt_sha_ldm_stm_16_words() 61 * prevent compiler from reordering memory write when -O2 or higher is used. 62 * - Version 2.2.2 63 * - Add data synchronization barrier inside hashcrypt_sha_ldm_stm_16_words() 64 * to fix optimization issue 65 * - Version 2.2.3 66 * - Added check for size in hashcrypt_aes_one_block to prevent overflowing COUNT field in MEMCTRL register, if its 67 * bigger than COUNT field do a multiple runs. 68 * - Version 2.2.4 69 * - In all HASHCRYPT_AES_xx functions have been added setting CTRL_MODE bitfield to 0 after processing data, which 70 * decreases power consumption. 71 * - Version 2.2.5 72 * - Add data synchronization barrier and instruction synchronization barrier inside 73 * hashcrypt_sha_process_message_data() to fix optimization issue 74 * - Version 2.2.6 75 * - Add data synchronization barrier inside HASHCRYPT_SHA_Update() and hashcrypt_get_data() function to fix 76 * optimization issue on MDK and ARMGCC release targets 77 * - Version 2.2.7 78 * - Add data synchronization barrier inside HASHCRYPT_SHA_Update() to fix optimization issue on MCUX IDE release 79 * target 80 * - Version 2.2.8 81 * - Unify hashcrypt hashing behavior between aligned and unaligned input data 82 * - Version 2.2.9 83 * - Add handling of set ERROR bit in the STATUS register 84 * - Version 2.2.10 85 * - Fix missing error statement in hashcrypt_save_running_hash() 86 * - Version 2.2.11 87 * - Fix incorrect SHA-256 calculation for long messages with reload 88 */ 89 #define FSL_HASHCRYPT_DRIVER_VERSION (MAKE_VERSION(2, 2, 11)) 90 /*@}*/ 91 92 /*! @brief Algorithm definitions correspond with the values for Mode field in Control register !*/ 93 #define HASHCRYPT_MODE_SHA1 0x1 94 #define HASHCRYPT_MODE_SHA256 0x2 95 #define HASHCRYPT_MODE_AES 0x4 96 97 /*! @brief Algorithm used for Hashcrypt operation */ 98 typedef enum _hashcrypt_algo_t 99 { 100 kHASHCRYPT_Sha1 = HASHCRYPT_MODE_SHA1, /*!< SHA_1 */ 101 kHASHCRYPT_Sha256 = HASHCRYPT_MODE_SHA256, /*!< SHA_256 */ 102 kHASHCRYPT_Aes = HASHCRYPT_MODE_AES, /*!< AES */ 103 } hashcrypt_algo_t; 104 105 /*! @} */ 106 107 /******************************************************************************* 108 * AES Definitions 109 *******************************************************************************/ 110 111 /*! 112 * @addtogroup hashcrypt_driver_aes 113 * @{ 114 */ 115 116 /*! AES block size in bytes */ 117 #define HASHCRYPT_AES_BLOCK_SIZE 16U 118 #define AES_ENCRYPT 0 119 #define AES_DECRYPT 1 120 121 /*! @brief AES mode */ 122 typedef enum _hashcrypt_aes_mode_t 123 { 124 kHASHCRYPT_AesEcb = 0U, /*!< AES ECB mode */ 125 kHASHCRYPT_AesCbc = 1U, /*!< AES CBC mode */ 126 kHASHCRYPT_AesCtr = 2U, /*!< AES CTR mode */ 127 } hashcrypt_aes_mode_t; 128 129 /*! @brief Size of AES key */ 130 typedef enum _hashcrypt_aes_keysize_t 131 { 132 kHASHCRYPT_Aes128 = 0U, /*!< AES 128 bit key */ 133 kHASHCRYPT_Aes192 = 1U, /*!< AES 192 bit key */ 134 kHASHCRYPT_Aes256 = 2U, /*!< AES 256 bit key */ 135 kHASHCRYPT_InvalidKey = 3U, /*!< AES invalid key */ 136 } hashcrypt_aes_keysize_t; 137 138 /*! @brief HASHCRYPT key source selection. 139 * 140 */ 141 typedef enum _hashcrypt_key 142 { 143 kHASHCRYPT_UserKey = 0xc3c3U, /*!< HASHCRYPT user key */ 144 kHASHCRYPT_SecretKey = 0x3c3cU, /*!< HASHCRYPT secret key (dedicated hw bus from PUF) */ 145 } hashcrypt_key_t; 146 147 /*! @brief Specify HASHCRYPT's key resource. */ 148 struct _hashcrypt_handle 149 { 150 uint32_t keyWord[8]; /*!< Copy of user key (set by HASHCRYPT_AES_SetKey(). */ 151 hashcrypt_aes_keysize_t keySize; 152 hashcrypt_key_t keyType; /*!< For operations with key (such as AES encryption/decryption), specify key type. */ 153 } __attribute__((aligned)); 154 155 typedef struct _hashcrypt_handle hashcrypt_handle_t; 156 157 /*! 158 *@} 159 */ /* end of hashcrypt_driver_aes */ 160 161 /******************************************************************************* 162 * HASH Definitions 163 ******************************************************************************/ 164 /*! 165 * @addtogroup hashcrypt_driver_hash 166 * @{ 167 */ 168 169 /*! @brief HASHCRYPT HASH Context size. */ 170 #if defined(FSL_FEATURE_HASHCRYPT_HAS_RELOAD_FEATURE) && (FSL_FEATURE_HASHCRYPT_HAS_RELOAD_FEATURE > 0) 171 #define HASHCRYPT_HASH_CTX_SIZE 30 172 #else 173 #define HASHCRYPT_HASH_CTX_SIZE 22 174 #endif 175 176 /*! @brief Storage type used to save hash context. */ 177 typedef struct _hashcrypt_hash_ctx_t 178 { 179 uint32_t x[HASHCRYPT_HASH_CTX_SIZE]; /*!< storage */ 180 } hashcrypt_hash_ctx_t; 181 182 /*! @brief HASHCRYPT background hash callback function. */ 183 typedef void (*hashcrypt_callback_t)(HASHCRYPT_Type *base, hashcrypt_hash_ctx_t *ctx, status_t status, void *userData); 184 185 /*! 186 *@} 187 */ /* end of hashcrypt_driver_hash */ 188 189 /******************************************************************************* 190 * API 191 ******************************************************************************/ 192 #if defined(__cplusplus) 193 extern "C" { 194 #endif 195 196 /*! 197 * @addtogroup hashcrypt_driver 198 * @{ 199 */ 200 201 /*! 202 * @brief Enables clock and disables reset for HASHCRYPT peripheral. 203 * 204 * Enable clock and disable reset for HASHCRYPT. 205 * 206 * @param base HASHCRYPT base address 207 */ 208 void HASHCRYPT_Init(HASHCRYPT_Type *base); 209 210 /*! 211 * @brief Disables clock for HASHCRYPT peripheral. 212 * 213 * Disable clock and enable reset. 214 * 215 * @param base HASHCRYPT base address 216 */ 217 void HASHCRYPT_Deinit(HASHCRYPT_Type *base); 218 219 /*! 220 *@} 221 */ /* end of hashcrypt_driver */ 222 223 /******************************************************************************* 224 * AES API 225 ******************************************************************************/ 226 227 /*! 228 * @addtogroup hashcrypt_driver_aes 229 * @{ 230 */ 231 232 /*! 233 * @brief Set AES key to hashcrypt_handle_t struct and optionally to HASHCRYPT. 234 * 235 * Sets the AES key for encryption/decryption with the hashcrypt_handle_t structure. 236 * The hashcrypt_handle_t input argument specifies key source. 237 * 238 * @param base HASHCRYPT peripheral base address. 239 * @param handle Handle used for the request. 240 * @param key 0-mod-4 aligned pointer to AES key. 241 * @param keySize AES key size in bytes. Shall equal 16, 24 or 32. 242 * @return status from set key operation 243 */ 244 status_t HASHCRYPT_AES_SetKey(HASHCRYPT_Type *base, hashcrypt_handle_t *handle, const uint8_t *key, size_t keySize); 245 246 /*! 247 * @brief Encrypts AES on one or multiple 128-bit block(s). 248 * 249 * Encrypts AES. 250 * The source plaintext and destination ciphertext can overlap in system memory. 251 * 252 * @param base HASHCRYPT peripheral base address 253 * @param handle Handle used for this request. 254 * @param plaintext Input plain text to encrypt 255 * @param[out] ciphertext Output cipher text 256 * @param size Size of input and output data in bytes. Must be multiple of 16 bytes. 257 * @return Status from encrypt operation 258 */ 259 status_t HASHCRYPT_AES_EncryptEcb( 260 HASHCRYPT_Type *base, hashcrypt_handle_t *handle, const uint8_t *plaintext, uint8_t *ciphertext, size_t size); 261 262 /*! 263 * @brief Decrypts AES on one or multiple 128-bit block(s). 264 * 265 * Decrypts AES. 266 * The source ciphertext and destination plaintext can overlap in system memory. 267 * 268 * @param base HASHCRYPT peripheral base address 269 * @param handle Handle used for this request. 270 * @param ciphertext Input plain text to encrypt 271 * @param[out] plaintext Output cipher text 272 * @param size Size of input and output data in bytes. Must be multiple of 16 bytes. 273 * @return Status from decrypt operation 274 */ 275 status_t HASHCRYPT_AES_DecryptEcb( 276 HASHCRYPT_Type *base, hashcrypt_handle_t *handle, const uint8_t *ciphertext, uint8_t *plaintext, size_t size); 277 278 /*! 279 * @brief Encrypts AES using CBC block mode. 280 * 281 * @param base HASHCRYPT peripheral base address 282 * @param handle Handle used for this request. 283 * @param plaintext Input plain text to encrypt 284 * @param[out] ciphertext Output cipher text 285 * @param size Size of input and output data in bytes. Must be multiple of 16 bytes. 286 * @param iv Input initial vector to combine with the first input block. 287 * @return Status from encrypt operation 288 */ 289 status_t HASHCRYPT_AES_EncryptCbc(HASHCRYPT_Type *base, 290 hashcrypt_handle_t *handle, 291 const uint8_t *plaintext, 292 uint8_t *ciphertext, 293 size_t size, 294 const uint8_t iv[16]); 295 296 /*! 297 * @brief Decrypts AES using CBC block mode. 298 * 299 * @param base HASHCRYPT peripheral base address 300 * @param handle Handle used for this request. 301 * @param ciphertext Input cipher text to decrypt 302 * @param[out] plaintext Output plain text 303 * @param size Size of input and output data in bytes. Must be multiple of 16 bytes. 304 * @param iv Input initial vector to combine with the first input block. 305 * @return Status from decrypt operation 306 */ 307 status_t HASHCRYPT_AES_DecryptCbc(HASHCRYPT_Type *base, 308 hashcrypt_handle_t *handle, 309 const uint8_t *ciphertext, 310 uint8_t *plaintext, 311 size_t size, 312 const uint8_t iv[16]); 313 314 /*! 315 * @brief Encrypts or decrypts AES using CTR block mode. 316 * 317 * Encrypts or decrypts AES using CTR block mode. 318 * AES CTR mode uses only forward AES cipher and same algorithm for encryption and decryption. 319 * The only difference between encryption and decryption is that, for encryption, the input argument 320 * is plain text and the output argument is cipher text. For decryption, the input argument is cipher text 321 * and the output argument is plain text. 322 * 323 * @param base HASHCRYPT peripheral base address 324 * @param handle Handle used for this request. 325 * @param input Input data for CTR block mode 326 * @param[out] output Output data for CTR block mode 327 * @param size Size of input and output data in bytes 328 * @param[in,out] counter Input counter (updates on return) 329 * @param[out] counterlast Output cipher of last counter, for chained CTR calls (statefull encryption). NULL can be 330 * passed if chained calls are 331 * not used. 332 * @param[out] szLeft Output number of bytes in left unused in counterlast block. NULL can be passed if chained calls 333 * are not used. 334 * @return Status from encrypt operation 335 */ 336 status_t HASHCRYPT_AES_CryptCtr(HASHCRYPT_Type *base, 337 hashcrypt_handle_t *handle, 338 const uint8_t *input, 339 uint8_t *output, 340 size_t size, 341 uint8_t counter[HASHCRYPT_AES_BLOCK_SIZE], 342 uint8_t counterlast[HASHCRYPT_AES_BLOCK_SIZE], 343 size_t *szLeft); 344 345 /*! 346 * @brief Encrypts or decrypts AES using OFB block mode. 347 * 348 * Encrypts or decrypts AES using OFB block mode. 349 * AES OFB mode uses only forward AES cipher and same algorithm for encryption and decryption. 350 * The only difference between encryption and decryption is that, for encryption, the input argument 351 * is plain text and the output argument is cipher text. For decryption, the input argument is cipher text 352 * and the output argument is plain text. 353 * 354 * @param base HASHCRYPT peripheral base address 355 * @param handle Handle used for this request. 356 * @param input Input data for OFB block mode 357 * @param[out] output Output data for OFB block mode 358 * @param size Size of input and output data in bytes 359 * @param iv Input initial vector to combine with the first input block. 360 * @return Status from encrypt operation 361 */ 362 363 status_t HASHCRYPT_AES_CryptOfb(HASHCRYPT_Type *base, 364 hashcrypt_handle_t *handle, 365 const uint8_t *input, 366 uint8_t *output, 367 size_t size, 368 const uint8_t iv[HASHCRYPT_AES_BLOCK_SIZE]); 369 370 /*! 371 * @brief Encrypts AES using CFB block mode. 372 * 373 * @param base HASHCRYPT peripheral base address 374 * @param handle Handle used for this request. 375 * @param plaintext Input plain text to encrypt 376 * @param[out] ciphertext Output cipher text 377 * @param size Size of input and output data in bytes. Must be multiple of 16 bytes. 378 * @param iv Input initial vector to combine with the first input block. 379 * @return Status from encrypt operation 380 */ 381 382 status_t HASHCRYPT_AES_EncryptCfb(HASHCRYPT_Type *base, 383 hashcrypt_handle_t *handle, 384 const uint8_t *plaintext, 385 uint8_t *ciphertext, 386 size_t size, 387 const uint8_t iv[16]); 388 389 /*! 390 * @brief Decrypts AES using CFB block mode. 391 * 392 * @param base HASHCRYPT peripheral base address 393 * @param handle Handle used for this request. 394 * @param ciphertext Input cipher text to decrypt 395 * @param[out] plaintext Output plaintext text 396 * @param size Size of input and output data in bytes. Must be multiple of 16 bytes. 397 * @param iv Input initial vector to combine with the first input block. 398 * @return Status from encrypt operation 399 */ 400 401 status_t HASHCRYPT_AES_DecryptCfb(HASHCRYPT_Type *base, 402 hashcrypt_handle_t *handle, 403 const uint8_t *ciphertext, 404 uint8_t *plaintext, 405 size_t size, 406 const uint8_t iv[16]); 407 /*! 408 *@} 409 */ /* end of hashcrypt_driver_aes */ 410 411 /******************************************************************************* 412 * HASH API 413 ******************************************************************************/ 414 415 /*! 416 * @addtogroup hashcrypt_driver_hash 417 * @{ 418 */ 419 420 /*! 421 * @brief Create HASH on given data 422 * 423 * Perform the full SHA in one function call. The function is blocking. 424 * 425 * @param base HASHCRYPT peripheral base address 426 * @param algo Underlaying algorithm to use for hash computation. 427 * @param input Input data 428 * @param inputSize Size of input data in bytes 429 * @param[out] output Output hash data 430 * @param[out] outputSize Output parameter storing the size of the output hash in bytes 431 * @return Status of the one call hash operation. 432 */ 433 status_t HASHCRYPT_SHA(HASHCRYPT_Type *base, 434 hashcrypt_algo_t algo, 435 const uint8_t *input, 436 size_t inputSize, 437 uint8_t *output, 438 size_t *outputSize); 439 440 /*! 441 * @brief Initialize HASH context 442 * 443 * This function initializes the HASH. 444 * 445 * @param base HASHCRYPT peripheral base address 446 * @param[out] ctx Output hash context 447 * @param algo Underlaying algorithm to use for hash computation. 448 * @return Status of initialization 449 */ 450 status_t HASHCRYPT_SHA_Init(HASHCRYPT_Type *base, hashcrypt_hash_ctx_t *ctx, hashcrypt_algo_t algo); 451 452 /*! 453 * @brief Add data to current HASH 454 * 455 * Add data to current HASH. This can be called repeatedly with an arbitrary amount of data to be 456 * hashed. The functions blocks. If it returns kStatus_Success, the running hash 457 * has been updated (HASHCRYPT has processed the input data), so the memory at \p input pointer 458 * can be released back to system. The HASHCRYPT context buffer is updated with the running hash 459 * and with all necessary information to support possible context switch. 460 * 461 * @param base HASHCRYPT peripheral base address 462 * @param[in,out] ctx HASH context 463 * @param input Input data 464 * @param inputSize Size of input data in bytes 465 * @return Status of the hash update operation 466 */ 467 status_t HASHCRYPT_SHA_Update(HASHCRYPT_Type *base, hashcrypt_hash_ctx_t *ctx, const uint8_t *input, size_t inputSize); 468 469 /*! 470 * @brief Finalize hashing 471 * 472 * Outputs the final hash (computed by HASHCRYPT_HASH_Update()) and erases the context. 473 * 474 * @param base HASHCRYPT peripheral base address 475 * @param[in,out] ctx Input hash context 476 * @param[out] output Output hash data 477 * @param[in,out] outputSize Optional parameter (can be passed as NULL). On function entry, it specifies the size of 478 * output[] buffer. On function return, it stores the number of updated output bytes. 479 * @return Status of the hash finish operation 480 */ 481 status_t HASHCRYPT_SHA_Finish(HASHCRYPT_Type *base, hashcrypt_hash_ctx_t *ctx, uint8_t *output, size_t *outputSize); 482 483 /*! 484 *@} 485 */ /* end of hashcrypt_driver_hash */ 486 487 /*! 488 * @addtogroup hashcrypt_background_driver_hash 489 * @{ 490 */ 491 492 /*! 493 * @brief Initializes the HASHCRYPT handle for background hashing. 494 * 495 * This function initializes the hash context for background hashing 496 * (Non-blocking) APIs. This is less typical interface to hash function, but can be used 497 * for parallel processing, when main CPU has something else to do. 498 * Example is digital signature RSASSA-PKCS1-V1_5-VERIFY((n,e),M,S) algorithm, where 499 * background hashing of M can be started, then CPU can compute S^e mod n 500 * (in parallel with background hashing) and once the digest becomes available, 501 * CPU can proceed to comparison of EM with EM'. 502 * 503 * @param base HASHCRYPT peripheral base address. 504 * @param[out] ctx Hash context. 505 * @param callback Callback function. 506 * @param userData User data (to be passed as an argument to callback function, once callback is invoked from isr). 507 */ 508 void HASHCRYPT_SHA_SetCallback(HASHCRYPT_Type *base, 509 hashcrypt_hash_ctx_t *ctx, 510 hashcrypt_callback_t callback, 511 void *userData); 512 513 /*! 514 * @brief Create running hash on given data. 515 * 516 * Configures the HASHCRYPT to compute new running hash as AHB master 517 * and returns immediately. HASHCRYPT AHB Master mode supports only aligned \p input 518 * address and can be called only once per continuous block of data. Every call to this function 519 * must be preceded with HASHCRYPT_SHA_Init() and finished with HASHCRYPT_SHA_Finish(). 520 * Once callback function is invoked by HASHCRYPT isr, it should set a flag 521 * for the main application to finalize the hashing (padding) and to read out the final digest 522 * by calling HASHCRYPT_SHA_Finish(). 523 * 524 * @param base HASHCRYPT peripheral base address 525 * @param ctx Specifies callback. Last incomplete 512-bit block of the input is copied into clear buffer for padding. 526 * @param input 32-bit word aligned pointer to Input data. 527 * @param inputSize Size of input data in bytes (must be word aligned) 528 * @return Status of the hash update operation. 529 */ 530 status_t HASHCRYPT_SHA_UpdateNonBlocking(HASHCRYPT_Type *base, 531 hashcrypt_hash_ctx_t *ctx, 532 const uint8_t *input, 533 size_t inputSize); 534 /*! 535 *@} 536 */ /* end of hashcrypt_background_driver_hash */ 537 538 #if defined(__cplusplus) 539 } 540 #endif 541 542 #endif /* _FSL_HASHCRYPT_H_ */ 543