From 8c6daf31ef0177f860e5c1686be537e0a3f6a7ad Mon Sep 17 00:00:00 2001 From: Robert Brown Date: Tue, 26 Mar 2024 16:00:34 +0000 Subject: [PATCH 1/6] [nasa/Cryptolib#230] WIP: TM Apply Refactoring --- src/core/crypto_tm.c | 336 +++++++++++++++++++++++++------------------ 1 file changed, 198 insertions(+), 138 deletions(-) diff --git a/src/core/crypto_tm.c b/src/core/crypto_tm.c index 63545d5c..7719f861 100644 --- a/src/core/crypto_tm.c +++ b/src/core/crypto_tm.c @@ -23,6 +23,190 @@ #include // memcpy/memset +int32_t Crypto_TM_Sanity_Check(uint8_t* pTfBuffer) +{ + int32_t status = CRYPTO_LIB_SUCCESS; + // Passed a null, return an error + if (!pTfBuffer) + { + return CRYPTO_LIB_ERR_NULL_BUFFER; + return status; + } + + if ((crypto_config.init_status == UNITIALIZED) || (mc_if == NULL) || (sa_if == NULL)) + { + printf(KRED "ERROR: CryptoLib Configuration Not Set! -- CRYPTO_LIB_ERR_NO_CONFIG, Will Exit\n" RESET); + status = CRYPTO_LIB_ERR_NO_CONFIG; + // Can't mc_log since it's not configured + return status; // return immediately so a NULL crypto_config is not dereferenced later + } + return status; +} + +int32_t Crypto_TM_Determine_SA_Service_Type(uint8_t* sa_service_type, SecurityAssociation_t* sa_ptr) +{ + int32_t status = CRYPTO_LIB_SUCCESS; + if ((sa_ptr->est == 0) && (sa_ptr->ast == 0)) + { + *sa_service_type = SA_PLAINTEXT; + } + else if ((sa_ptr->est == 0) && (sa_ptr->ast == 1)) + { + *sa_service_type = SA_AUTHENTICATION; + } + else if ((sa_ptr->est == 1) && (sa_ptr->ast == 0)) + { + *sa_service_type = SA_ENCRYPTION; + } + else if ((sa_ptr->est == 1) && (sa_ptr->ast == 1)) + { + *sa_service_type = SA_AUTHENTICATED_ENCRYPTION; + } + else + { + // Probably unnecessary check + // Leaving for now as it would be cleaner in SA to have an association enum returned I believe + printf(KRED "Error: SA Service Type is not defined! \n" RESET); + status = CRYPTO_LIB_ERROR; + mc_if->mc_log(status); + return status; + } + return status; +} + +void Crypto_TM_Check_For_Secondary_Header(uint8_t* pTfBuffer, uint16_t* idx) +{ + *idx = 4; + if((pTfBuffer[*idx] & 0x80) == 0x80) + { +#ifdef TM_DEBUG + printf(KYEL "A TM Secondary Header flag is set!\n"); +#endif + // Secondary header is present + *idx = 6; + // Determine length of secondary header + // Length coded as total length of secondary header - 1 + // Reference CCSDS 132.0-B-2 4.1.3.2.3 + uint8_t secondary_hdr_len = (pTfBuffer[*idx] & 0x3F); +#ifdef TM_DEBUG + printf(KYEL "Secondary Header Length is decoded as: %d\n", secondary_hdr_len); +#endif + // Increment from current byte (1st byte of secondary header), + // to where the SPI would start + *idx += secondary_hdr_len + 1; + } + else + { + // No Secondary header, carry on as usual and increment to SPI start + *idx = 6; + } +} + +int32_t Crypto_TM_IV_Sanity_Check(uint8_t* sa_service_type, SecurityAssociation_t* sa_ptr) +{ + int32_t status = CRYPTO_LIB_SUCCESS; + #ifdef SA_DEBUG + if (sa_ptr->shivf_len > 0 && sa_ptr->iv != NULL) + { + printf(KYEL "Using IV value:\n\t"); + for (int i = 0; i < sa_ptr->iv_len; i++) + { + printf("%02x", *(sa_ptr->iv + i)); + } + printf("\n" RESET); + printf(KYEL "Transmitted IV value:\n\t"); + for (int i = sa_ptr->iv_len - sa_ptr->shivf_len; i < sa_ptr->iv_len; i++) + { + printf("%02x", *(sa_ptr->iv + i)); + } + printf("\n" RESET); + } +#endif + if(*sa_service_type != SA_PLAINTEXT && sa_ptr->ecs_len == 0 && sa_ptr->acs_len ==0) + { + status = CRYPTO_LIB_ERR_NULL_CIPHERS; +#ifdef TM_DEBUG + printf(KRED "CRYPTO_LIB_ERR_NULL_CIPHERS, Invalid cipher lengths, %d\n" RESET, CRYPTO_LIB_ERR_NULL_CIPHERS); +#endif + mc_if->mc_log(status); + return status; + } + + if(sa_ptr->est == 0 && sa_ptr->ast == 1) + { + if(sa_ptr->acs_len != 0) + { + if((sa_ptr->acs == CRYPTO_MAC_CMAC_AES256 || sa_ptr->acs == CRYPTO_MAC_HMAC_SHA256 || sa_ptr->acs == CRYPTO_MAC_HMAC_SHA512) && + sa_ptr->iv_len > 0 ) + { + status = CRYPTO_LIB_ERR_IV_NOT_SUPPORTED_FOR_ACS_ALGO; + mc_if->mc_log(status); + return status; + } + } + } + return status; +} + +void Crypto_TM_PKCS_Padding(uint32_t* pkcs_padding, SecurityAssociation_t* sa_ptr, uint8_t* pTfBuffer, uint16_t* idx_p) +{ + uint16_t idx = *idx_p; + if(*pkcs_padding) + { + uint8_t hex_padding[3] = {0}; //TODO: Create #Define for the 3 + *pkcs_padding = *pkcs_padding & 0x00FFFFFF; // Truncate to be maxiumum of 3 bytes in size + + // Byte Magic + hex_padding[0] = (*pkcs_padding >> 16) & 0xFF; + hex_padding[1] = (*pkcs_padding >> 8) & 0xFF; + hex_padding[2] = (*pkcs_padding) & 0xFF; + + uint8_t padding_start = 0; + padding_start = 3 - sa_ptr->shplf_len; + + for (int i = 0; i < sa_ptr->shplf_len; i++) + { + pTfBuffer[idx] = hex_padding[padding_start++]; + idx++; + } + } + *idx_p = idx; +} + +void Crypto_TM_Handle_Managed_Parameter_Flags(uint16_t* pdu_len) +{ + if(current_managed_parameters->has_ocf == TM_HAS_OCF) + { + *pdu_len -= 4; + } + if(current_managed_parameters->has_fecf == TM_HAS_FECF) + { + *pdu_len -= 2; + } +} + +int32_t Crypto_TM_Get_Keys(crypto_key_t** ekp, crypto_key_t** akp, SecurityAssociation_t* sa_ptr) +{ + int32_t status = CRYPTO_LIB_SUCCESS; + *ekp = key_if->get_key(sa_ptr->ekid); + if (ekp == NULL) + { + status = CRYPTO_LIB_ERR_KEY_ID_ERROR; + mc_if->mc_log(status); + return status; + } + + + *akp = key_if->get_key(sa_ptr->akid); + if (akp == NULL) + { + status = CRYPTO_LIB_ERR_KEY_ID_ERROR; + mc_if->mc_log(status); + return status; + } + return status; +} + /** * @brief Function: Crypto_TM_ApplySecurity * @param ingest: uint8_t* @@ -60,18 +244,10 @@ int32_t Crypto_TM_ApplySecurity(uint8_t* pTfBuffer) uint16_t scid = 0; uint16_t vcid = 0; - // Passed a null, return an error - if (!pTfBuffer) + status = Crypto_TM_Sanity_Check(pTfBuffer); + if(status != CRYPTO_LIB_SUCCESS) { - return CRYPTO_LIB_ERR_NULL_BUFFER; - } - - if ((crypto_config.init_status == UNITIALIZED) || (mc_if == NULL) || (sa_if == NULL)) - { - printf(KRED "ERROR: CryptoLib Configuration Not Set! -- CRYPTO_LIB_ERR_NO_CONFIG, Will Exit\n" RESET); - status = CRYPTO_LIB_ERR_NO_CONFIG; - // Can't mc_log since it's not configured - return status; // return immediately so a NULL crypto_config is not dereferenced later + return status; } tfvn = ((uint8_t)pTfBuffer[0] & 0xC0) >> 6; @@ -132,31 +308,8 @@ int32_t Crypto_TM_ApplySecurity(uint8_t* pTfBuffer) #endif // Determine SA Service Type - if ((sa_ptr->est == 0) && (sa_ptr->ast == 0)) - { - sa_service_type = SA_PLAINTEXT; - } - else if ((sa_ptr->est == 0) && (sa_ptr->ast == 1)) - { - sa_service_type = SA_AUTHENTICATION; - } - else if ((sa_ptr->est == 1) && (sa_ptr->ast == 0)) - { - sa_service_type = SA_ENCRYPTION; - } - else if ((sa_ptr->est == 1) && (sa_ptr->ast == 1)) - { - sa_service_type = SA_AUTHENTICATED_ENCRYPTION; - } - else - { - // Probably unnecessary check - // Leaving for now as it would be cleaner in SA to have an association enum returned I believe - printf(KRED "Error: SA Service Type is not defined! \n" RESET); - status = CRYPTO_LIB_ERROR; - mc_if->mc_log(status); - return status; - } + status = Crypto_TM_Determine_SA_Service_Type(&sa_service_type, sa_ptr); + if(status != CRYPTO_LIB_SUCCESS) return status; // Determine Algorithm cipher & mode. // TODO - Parse authentication_cipher, and handle AEAD cases properly if (sa_service_type != SA_PLAINTEXT) @@ -186,30 +339,9 @@ int32_t Crypto_TM_ApplySecurity(uint8_t* pTfBuffer) // Note: Secondary headers are static only for a mission phase, not guaranteed static // over the life of a mission Per CCSDS 132.0-B.3 Section 4.1.2.7.2.3 // Secondary Header flag is 1st bit of 5th byte (index 4) - idx = 4; - if((pTfBuffer[idx] & 0x80) == 0x80) - { -#ifdef TM_DEBUG - printf(KYEL "A TM Secondary Header flag is set!\n"); -#endif - // Secondary header is present - idx = 6; - // Determine length of secondary header - // Length coded as total length of secondary header - 1 - // Reference CCSDS 132.0-B-2 4.1.3.2.3 - uint8_t secondary_hdr_len = (pTfBuffer[idx] & 0x3F); -#ifdef TM_DEBUG - printf(KYEL "Secondary Header Length is decoded as: %d\n", secondary_hdr_len); -#endif - // Increment from current byte (1st byte of secondary header), - // to where the SPI would start - idx += secondary_hdr_len + 1; - } - else - { - // No Secondary header, carry on as usual and increment to SPI start - idx = 6; - } + + Crypto_TM_Check_For_Secondary_Header(pTfBuffer, &idx); + /** * Begin Security Header Fields * Reference CCSDS SDLP 3550b1 4.1.1.1.3 @@ -221,46 +353,9 @@ int32_t Crypto_TM_ApplySecurity(uint8_t* pTfBuffer) idx += 2; // Set initialization vector if specified -#ifdef SA_DEBUG - if (sa_ptr->shivf_len > 0 && sa_ptr->iv != NULL) - { - printf(KYEL "Using IV value:\n\t"); - for (i = 0; i < sa_ptr->iv_len; i++) - { - printf("%02x", *(sa_ptr->iv + i)); - } - printf("\n" RESET); - printf(KYEL "Transmitted IV value:\n\t"); - for (i = sa_ptr->iv_len - sa_ptr->shivf_len; i < sa_ptr->iv_len; i++) - { - printf("%02x", *(sa_ptr->iv + i)); - } - printf("\n" RESET); - } -#endif - if(sa_service_type != SA_PLAINTEXT && sa_ptr->ecs_len == 0 && sa_ptr->acs_len ==0) - { - status = CRYPTO_LIB_ERR_NULL_CIPHERS; -#ifdef TM_DEBUG - printf(KRED "CRYPTO_LIB_ERR_NULL_CIPHERS, Invalid cipher lengths, %d\n" RESET, CRYPTO_LIB_ERR_NULL_CIPHERS); -#endif - mc_if->mc_log(status); - return status; - } + status = Crypto_TM_IV_Sanity_Check(&sa_service_type, sa_ptr); + if(status != CRYPTO_LIB_SUCCESS) return status; - if(sa_ptr->est == 0 && sa_ptr->ast == 1) - { - if(sa_ptr->acs_len != 0) - { - if((sa_ptr->acs == CRYPTO_MAC_CMAC_AES256 || sa_ptr->acs == CRYPTO_MAC_HMAC_SHA256 || sa_ptr->acs == CRYPTO_MAC_HMAC_SHA512) && - sa_ptr->iv_len > 0 ) - { - status = CRYPTO_LIB_ERR_IV_NOT_SUPPORTED_FOR_ACS_ALGO; - mc_if->mc_log(status); - return status; - } - } - } // Start index from the transmitted portion for (i = sa_ptr->iv_len - sa_ptr->shivf_len; i < sa_ptr->iv_len; i++) { @@ -295,26 +390,8 @@ int32_t Crypto_TM_ApplySecurity(uint8_t* pTfBuffer) * cryptographic process, consisting of an integral number of octets. - CCSDS 3550b1 **/ // TODO: Set this depending on crypto cipher used + Crypto_TM_PKCS_Padding(&pkcs_padding, sa_ptr, pTfBuffer, &idx); - if(pkcs_padding) - { - uint8_t hex_padding[3] = {0}; //TODO: Create #Define for the 3 - pkcs_padding = pkcs_padding & 0x00FFFFFF; // Truncate to be maxiumum of 3 bytes in size - - // Byte Magic - hex_padding[0] = (pkcs_padding >> 16) & 0xFF; - hex_padding[1] = (pkcs_padding >> 8) & 0xFF; - hex_padding[2] = (pkcs_padding) & 0xFF; - - uint8_t padding_start = 0; - padding_start = 3 - sa_ptr->shplf_len; - - for (i = 0; i < sa_ptr->shplf_len; i++) - { - pTfBuffer[idx] = hex_padding[padding_start++]; - idx++; - } - } /** * End Security Header Fields @@ -338,14 +415,7 @@ int32_t Crypto_TM_ApplySecurity(uint8_t* pTfBuffer) // Calculate size of data to be encrypted pdu_len = current_managed_parameters->max_frame_size - idx - sa_ptr->stmacf_len; // Check other managed parameter flags, subtract their lengths from data field if present - if(current_managed_parameters->has_ocf == TM_HAS_OCF) - { - pdu_len -= 4; - } - if(current_managed_parameters->has_fecf == TM_HAS_FECF) - { - pdu_len -= 2; - } + Crypto_TM_Handle_Managed_Parameter_Flags(&pdu_len); #ifdef TM_DEBUG printf(KYEL "Data location starts at: %d\n" RESET, idx); @@ -365,20 +435,10 @@ int32_t Crypto_TM_ApplySecurity(uint8_t* pTfBuffer) // Get Key crypto_key_t* ekp = NULL; - ekp = key_if->get_key(sa_ptr->ekid); - if (ekp == NULL) - { - status = CRYPTO_LIB_ERR_KEY_ID_ERROR; - mc_if->mc_log(status); - return status; - } - crypto_key_t* akp = NULL; - akp = key_if->get_key(sa_ptr->akid); - if (akp == NULL) + status = Crypto_TM_Get_Keys(&ekp, &akp, sa_ptr); + if(status != CRYPTO_LIB_SUCCESS) { - status = CRYPTO_LIB_ERR_KEY_ID_ERROR; - mc_if->mc_log(status); return status; } From c5a4e46fc12d0757952ad7e15ce2d35c62939814 Mon Sep 17 00:00:00 2001 From: Robert Brown Date: Mon, 1 Apr 2024 19:52:17 +0000 Subject: [PATCH 2/6] [nasa/cryptolib#230] WIP: Refactoring of TM Apply --- src/core/crypto_tm.c | 580 +++++++++++++++++++++++-------------------- 1 file changed, 313 insertions(+), 267 deletions(-) diff --git a/src/core/crypto_tm.c b/src/core/crypto_tm.c index 7719f861..799cb25b 100644 --- a/src/core/crypto_tm.c +++ b/src/core/crypto_tm.c @@ -193,20 +193,325 @@ int32_t Crypto_TM_Get_Keys(crypto_key_t** ekp, crypto_key_t** akp, SecurityAssoc { status = CRYPTO_LIB_ERR_KEY_ID_ERROR; mc_if->mc_log(status); - return status; } - *akp = key_if->get_key(sa_ptr->akid); - if (akp == NULL) + if (akp == NULL && status == CRYPTO_LIB_SUCCESS) { status = CRYPTO_LIB_ERR_KEY_ID_ERROR; mc_if->mc_log(status); - return status; } return status; } +int32_t Crypto_TM_Do_Encrypt_NONPLAINTEXT(uint8_t sa_service_type, uint16_t* aad_len, int* mac_loc, uint16_t* idx_p, uint16_t pdu_len, uint8_t* pTfBuffer, uint8_t* aad, SecurityAssociation_t* sa_ptr) +{ + int32_t status = CRYPTO_LIB_SUCCESS; + int16_t idx = *idx_p; + + if (sa_service_type != SA_PLAINTEXT) + { + *aad_len = 0; + + if (sa_service_type == SA_AUTHENTICATED_ENCRYPTION || sa_service_type == SA_AUTHENTICATION) + { + *mac_loc = idx + pdu_len; +#ifdef MAC_DEBUG + printf(KYEL "MAC location is: %d\n" RESET, *mac_loc); + printf(KYEL "MAC size is: %d\n" RESET, sa_ptr->stmacf_len); +#endif + + // Prepare the Header AAD (CCSDS 335.0-B-2 4.2.3.4) + *aad_len = idx; // At the very least AAD includes the header + if (sa_service_type == SA_AUTHENTICATION) // auth only, we authenticate the payload as part of the AEAD encrypt call here + { + *aad_len += pdu_len; + } +#ifdef TM_DEBUG + printf("Calculated AAD Length: %d\n",*aad_len); +#endif + if (sa_ptr->abm_len < *aad_len) + { + status = CRYPTO_LIB_ERR_ABM_TOO_SHORT_FOR_AAD; + printf(KRED "Error: abm_len of %d < *aad_len of %d\n" RESET, sa_ptr->abm_len, *aad_len); + mc_if->mc_log(status); + } + if (status == CRYPTO_LIB_SUCCESS) + { + status = Crypto_Prepare_TM_AAD(pTfBuffer, *aad_len, sa_ptr->abm, aad); + } + } + } + + *idx_p = idx; + return status; +} + +int32_t Crypto_TM_Do_Encrypt_NONPLAINTEXT_AEAD_Logic(uint8_t sa_service_type, uint8_t ecs_is_aead_algorithm, uint8_t* pTfBuffer, uint16_t pdu_len, uint16_t data_loc, crypto_key_t* ekp, crypto_key_t* akp, uint32_t pkcs_padding, int* mac_loc, uint16_t* aad_len, uint8_t* aad, SecurityAssociation_t* sa_ptr) +{ + int32_t status = CRYPTO_LIB_SUCCESS; + + if(sa_service_type != SA_PLAINTEXT && ecs_is_aead_algorithm == CRYPTO_TRUE) + { + if(sa_service_type == SA_ENCRYPTION) + { + status = cryptography_if->cryptography_encrypt(//Stub out data in/out as this is done in place and want to save cycles + (uint8_t*)(&pTfBuffer[data_loc]), // ciphertext output + (size_t) pdu_len, // length of data + (uint8_t*)(&pTfBuffer[data_loc]), // plaintext input + (size_t) pdu_len, // in data length - from start of frame to end of data + &(ekp->value[0]), // Key + Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs), + sa_ptr, // SA (for key reference) + sa_ptr->iv, // IV + sa_ptr->iv_len, // IV Length + &sa_ptr->ecs, // encryption cipher + pkcs_padding, // authentication cipher + NULL); + } + if(sa_service_type == SA_AUTHENTICATED_ENCRYPTION) + { + status = cryptography_if->cryptography_aead_encrypt((uint8_t*)(&pTfBuffer[data_loc]), // ciphertext output + (size_t) pdu_len, // length of data + (uint8_t*)(&pTfBuffer[data_loc]), // plaintext input + (size_t) pdu_len, // in data length + &(ekp->value[0]), // Key + Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs), // Length of key derived from sa_ptr key_ref + sa_ptr, // SA (for key reference) + sa_ptr->iv, // IV + sa_ptr->iv_len, // IV Length + &pTfBuffer[*mac_loc], // tag output + sa_ptr->stmacf_len, // tag size + aad, // AAD Input + *aad_len, // Length of AAD + (sa_ptr->est==1), + (sa_ptr->ast==1), + (sa_ptr->ast==1), + &sa_ptr->ecs, // encryption cipher + &sa_ptr->acs, // authentication cipher + NULL); + } + } + + else if (sa_service_type != SA_PLAINTEXT && ecs_is_aead_algorithm == CRYPTO_FALSE) // Non aead algorithm + { + // TODO - implement non-AEAD algorithm logic + if(sa_service_type == SA_AUTHENTICATION) + { + status = cryptography_if->cryptography_authenticate(//Stub out data in/out as this is done in place and want to save cycles + (uint8_t*)(&pTfBuffer[0]), // ciphertext output + (size_t) 0, // length of data + (uint8_t*)(&pTfBuffer[0]), // plaintext input + (size_t)0, // in data length - from start of frame to end of data + &(akp->value[0]), // Key + Crypto_Get_ACS_Algo_Keylen(sa_ptr->acs), + sa_ptr, // SA (for key reference) + sa_ptr->iv, // IV + sa_ptr->iv_len, // IV Length + &pTfBuffer[*mac_loc], // tag output + sa_ptr->stmacf_len, // tag size + aad, // AAD Input + *aad_len, // Length of AAD + sa_ptr->ecs, // encryption cipher + sa_ptr->acs, // authentication cipher + NULL); + } + else if(sa_service_type == SA_ENCRYPTION || sa_service_type == SA_AUTHENTICATED_ENCRYPTION) + { + if (sa_service_type == SA_ENCRYPTION) + { + status = cryptography_if->cryptography_encrypt(//Stub out data in/out as this is done in place and want to save cycles + (uint8_t*)(&pTfBuffer[data_loc]), // ciphertext output + (size_t) pdu_len, // length of data + (uint8_t*)(&pTfBuffer[data_loc]), // plaintext input + (size_t) pdu_len, // in data length - from start of frame to end of data + &(ekp->value[0]), // Key + Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs), + sa_ptr, // SA (for key reference) + sa_ptr->iv, // IV + sa_ptr->iv_len, // IV Length + &sa_ptr->ecs, // encryption cipher + pkcs_padding, // authentication cipher + NULL); + } + } + else if(sa_service_type == SA_PLAINTEXT) + { + // Do nothing, SDLS fields were already copied into static frame in memory + } + else{ +#ifdef TM_DEBUG + printf(KRED "Service type reported as: %d\n" RESET, sa_service_type); + printf(KRED "ECS IS AEAD Value: %d\n" RESET, ecs_is_aead_algorithm); +#endif + status = CRYPTO_LIB_ERR_UNSUPPORTED_MODE; + } + } + return status; +} + +int32_t Crypto_TM_Do_Encrypt_Handle_Increment(uint8_t sa_service_type, SecurityAssociation_t* sa_ptr) +{ + int32_t status = CRYPTO_LIB_SUCCESS; + if (sa_service_type != SA_PLAINTEXT) + { +#ifdef INCREMENT + if (crypto_config.crypto_increment_nontransmitted_iv == SA_INCREMENT_NONTRANSMITTED_IV_TRUE) + { + if (sa_ptr->shivf_len > 0 && sa_ptr->iv_len != 0) + { + status = Crypto_increment(sa_ptr->iv, sa_ptr->iv_len); + } + } + else // SA_INCREMENT_NONTRANSMITTED_IV_FALSE + { + // Only increment the transmitted portion + if (sa_ptr->shivf_len > 0 && sa_ptr->iv_len != 0) + { + status = Crypto_increment(sa_ptr->iv + (sa_ptr->iv_len - sa_ptr->shivf_len), sa_ptr->shivf_len); + } + } + if (sa_ptr->shsnf_len > 0 && status == CRYPTO_LIB_SUCCESS) + { + status = Crypto_increment(sa_ptr->arsn, sa_ptr->arsn_len); + } + +#ifdef SA_DEBUG + if (sa_ptr->iv_len > 0) + { + printf(KYEL "Next IV value is:\n\t"); + for (int i = 0; i < sa_ptr->iv_len; i++) + { + printf("%02x", *(sa_ptr->iv + i)); + } + printf("\n" RESET); + printf(KYEL "Next transmitted IV value is:\n\t"); + for (int i = sa_ptr->iv_len - sa_ptr->shivf_len; i < sa_ptr->iv_len; i++) + { + printf("%02x", *(sa_ptr->iv + i)); + } + printf("\n" RESET); + } + printf(KYEL "Next ARSN value is:\n\t"); + for (int i = 0; i < sa_ptr->arsn_len; i++) + { + printf("%02x", *(sa_ptr->arsn + i)); + } + printf("\n" RESET); + printf(KYEL "Next transmitted ARSN value is:\n\t"); + for (int i = sa_ptr->arsn_len - sa_ptr->shsnf_len; i < sa_ptr->arsn_len; i++) + { + printf("%02x", *(sa_ptr->arsn + i)); + } + printf("\n" RESET); +#endif +#endif + } + return status; +} + +int32_t Crypto_TM_Do_Encrypt(uint8_t sa_service_type, SecurityAssociation_t* sa_ptr, uint16_t* aad_len, int* mac_loc, uint16_t* idx_p, uint16_t pdu_len, uint8_t* pTfBuffer, uint8_t* aad, uint8_t ecs_is_aead_algorithm, uint16_t data_loc, crypto_key_t* ekp, crypto_key_t* akp, uint32_t pkcs_padding, uint16_t* new_fecf) +{ +/** + * Begin Authentication / Encryption + **/ + uint16_t idx = *idx_p; + int32_t status = CRYPTO_LIB_SUCCESS; + status = Crypto_TM_Do_Encrypt_NONPLAINTEXT(sa_service_type, aad_len, mac_loc, idx_p, pdu_len, pTfBuffer, aad, sa_ptr); + +// AEAD Algorithm Logic + if (status == CRYPTO_LIB_SUCCESS) + { + status = Crypto_TM_Do_Encrypt_NONPLAINTEXT_AEAD_Logic(sa_service_type, ecs_is_aead_algorithm, pTfBuffer, pdu_len, data_loc, ekp, akp, pkcs_padding, mac_loc, aad_len, aad, sa_ptr); + } + + + if (status != CRYPTO_LIB_SUCCESS) + { + status = Crypto_TM_Do_Encrypt_Handle_Increment(sa_service_type, sa_ptr); + } + + + // Move idx to mac location + idx += pdu_len; +#ifdef TM_DEBUG + if (sa_ptr->stmacf_len > 0) + { + printf(KYEL "Data length is %d\n" RESET, pdu_len); + printf(KYEL "MAC location starts at: %d\n" RESET, idx); + printf(KYEL "MAC length of %d\n" RESET, sa_ptr->stmacf_len); + } + else + { + printf(KYEL "MAC NOT SET TO BE USED IN SA - LENGTH IS 0\n"); + } +#endif + +//TODO OCF - ? Here, elsewhere? + + /** + * End Authentication / Encryption + **/ + + // Only calculate & insert FECF if CryptoLib is configured to do so & gvcid includes FECF. + if (current_managed_parameters->has_fecf == TM_HAS_FECF) + { +#ifdef FECF_DEBUG + printf(KCYN "Calcing FECF over %d bytes\n" RESET, current_managed_parameters->max_frame_size - 2); +#endif + if (crypto_config.crypto_create_fecf == CRYPTO_TM_CREATE_FECF_TRUE) + { + *new_fecf = Crypto_Calc_FECF((uint8_t*)pTfBuffer, current_managed_parameters->max_frame_size - 2); + pTfBuffer[current_managed_parameters->max_frame_size - 2] = (uint8_t)((*new_fecf & 0xFF00) >> 8); + pTfBuffer[current_managed_parameters->max_frame_size - 1] = (uint8_t)(*new_fecf & 0x00FF); + } + else // CRYPTO_TC_CREATE_FECF_FALSE + { + pTfBuffer[current_managed_parameters->max_frame_size - 2] = (uint8_t)0x00; + pTfBuffer[current_managed_parameters->max_frame_size - 1] = (uint8_t)0x00; + } + idx += 2; + } + +#ifdef TM_DEBUG + printf(KYEL "Printing new TM frame:\n\t"); + for(int i = 0; i < current_managed_parameters->max_frame_size; i++) + { + printf("%02X", pTfBuffer[i]); + } + printf("\n"); +#endif + + status = sa_if->sa_save_sa(sa_ptr); + +#ifdef DEBUG + printf(KYEL "----- Crypto_TM_ApplySecurity END -----\n" RESET); +#endif + + *idx_p = idx; + + return status; +} + +void Crypto_TM_ApplySecurity_Debug_Print(uint16_t idx, uint16_t pdu_len, SecurityAssociation_t* sa_ptr) +{ + #ifdef TM_DEBUG + printf(KYEL "Data location starts at: %d\n" RESET, idx); + printf(KYEL "Data size is: %d\n" RESET, pdu_len); + printf(KYEL "Index at end of SPI is: %d\n", idx); + if(current_managed_parameters->has_ocf == TM_HAS_OCF) + { + // If OCF exists, comes immediately after MAC + printf(KYEL "OCF Location is: %d" RESET, idx + pdu_len + sa_ptr->stmacf_len); + } + if(current_managed_parameters->has_fecf == TM_HAS_FECF) + { + // If FECF exists, comes just before end of the frame + printf(KYEL "FECF Location is: %d\n" RESET, current_managed_parameters->max_frame_size - 2); + } +#endif +} + /** * @brief Function: Crypto_TM_ApplySecurity * @param ingest: uint8_t* @@ -416,22 +721,7 @@ int32_t Crypto_TM_ApplySecurity(uint8_t* pTfBuffer) pdu_len = current_managed_parameters->max_frame_size - idx - sa_ptr->stmacf_len; // Check other managed parameter flags, subtract their lengths from data field if present Crypto_TM_Handle_Managed_Parameter_Flags(&pdu_len); - -#ifdef TM_DEBUG - printf(KYEL "Data location starts at: %d\n" RESET, idx); - printf(KYEL "Data size is: %d\n" RESET, pdu_len); - printf(KYEL "Index at end of SPI is: %d\n", idx); - if(current_managed_parameters->has_ocf == TM_HAS_OCF) - { - // If OCF exists, comes immediately after MAC - printf(KYEL "OCF Location is: %d" RESET, idx + pdu_len + sa_ptr->stmacf_len); - } - if(current_managed_parameters->has_fecf == TM_HAS_FECF) - { - // If FECF exists, comes just before end of the frame - printf(KYEL "FECF Location is: %d\n" RESET, current_managed_parameters->max_frame_size - 2); - } -#endif + Crypto_TM_ApplySecurity_Debug_Print(idx, pdu_len, sa_ptr); // Get Key crypto_key_t* ekp = NULL; @@ -442,255 +732,11 @@ int32_t Crypto_TM_ApplySecurity(uint8_t* pTfBuffer) return status; } - /** - * Begin Authentication / Encryption - **/ - - if (sa_service_type != SA_PLAINTEXT) - { - aad_len = 0; - - if (sa_service_type == SA_AUTHENTICATED_ENCRYPTION || sa_service_type == SA_AUTHENTICATION) - { - mac_loc = idx+pdu_len; -#ifdef MAC_DEBUG - printf(KYEL "MAC location is: %d\n" RESET, mac_loc); - printf(KYEL "MAC size is: %d\n" RESET, sa_ptr->stmacf_len); -#endif - - // Prepare the Header AAD (CCSDS 335.0-B-2 4.2.3.4) - aad_len = idx; // At the very least AAD includes the header - if (sa_service_type == SA_AUTHENTICATION) // auth only, we authenticate the payload as part of the AEAD encrypt call here - { - aad_len += pdu_len; - } -#ifdef TM_DEBUG - printf("Calculated AAD Length: %d\n",aad_len); -#endif - if (sa_ptr->abm_len < aad_len) - { - status = CRYPTO_LIB_ERR_ABM_TOO_SHORT_FOR_AAD; - printf(KRED "Error: abm_len of %d < aad_len of %d\n" RESET, sa_ptr->abm_len, aad_len); - mc_if->mc_log(status); - return status; - } - status = Crypto_Prepare_TM_AAD(&pTfBuffer[0], aad_len, sa_ptr->abm, &aad[0]); - } - } - - // AEAD Algorithm Logic - if(sa_service_type != SA_PLAINTEXT && ecs_is_aead_algorithm == CRYPTO_TRUE) - { - if(sa_service_type == SA_ENCRYPTION) - { - status = cryptography_if->cryptography_encrypt(//Stub out data in/out as this is done in place and want to save cycles - (uint8_t*)(&pTfBuffer[data_loc]), // ciphertext output - (size_t) pdu_len, // length of data - (uint8_t*)(&pTfBuffer[data_loc]), // plaintext input - (size_t) pdu_len, // in data length - from start of frame to end of data - &(ekp->value[0]), // Key - Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs), - sa_ptr, // SA (for key reference) - sa_ptr->iv, // IV - sa_ptr->iv_len, // IV Length - &sa_ptr->ecs, // encryption cipher - pkcs_padding, // authentication cipher - NULL); - } - if(sa_service_type == SA_AUTHENTICATED_ENCRYPTION) - { - status = cryptography_if->cryptography_aead_encrypt((uint8_t*)(&pTfBuffer[data_loc]), // ciphertext output - (size_t) pdu_len, // length of data - (uint8_t*)(&pTfBuffer[data_loc]), // plaintext input - (size_t) pdu_len, // in data length - &(ekp->value[0]), // Key - Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs), // Length of key derived from sa_ptr key_ref - sa_ptr, // SA (for key reference) - sa_ptr->iv, // IV - sa_ptr->iv_len, // IV Length - &pTfBuffer[mac_loc], // tag output - sa_ptr->stmacf_len, // tag size - aad, // AAD Input - aad_len, // Length of AAD - (sa_ptr->est==1), - (sa_ptr->ast==1), - (sa_ptr->ast==1), - &sa_ptr->ecs, // encryption cipher - &sa_ptr->acs, // authentication cipher - NULL); - } - } - - else if (sa_service_type != SA_PLAINTEXT && ecs_is_aead_algorithm == CRYPTO_FALSE) // Non aead algorithm - { - // TODO - implement non-AEAD algorithm logic - if(sa_service_type == SA_AUTHENTICATION) - { - status = cryptography_if->cryptography_authenticate(//Stub out data in/out as this is done in place and want to save cycles - (uint8_t*)(&pTfBuffer[0]), // ciphertext output - (size_t) 0, // length of data - (uint8_t*)(&pTfBuffer[0]), // plaintext input - (size_t)0, // in data length - from start of frame to end of data - &(akp->value[0]), // Key - Crypto_Get_ACS_Algo_Keylen(sa_ptr->acs), - sa_ptr, // SA (for key reference) - sa_ptr->iv, // IV - sa_ptr->iv_len, // IV Length - &pTfBuffer[mac_loc], // tag output - sa_ptr->stmacf_len, // tag size - aad, // AAD Input - aad_len, // Length of AAD - sa_ptr->ecs, // encryption cipher - sa_ptr->acs, // authentication cipher - NULL); - } - else if(sa_service_type == SA_ENCRYPTION || sa_service_type == SA_AUTHENTICATED_ENCRYPTION) - { - if (sa_service_type == SA_ENCRYPTION) - { - status = cryptography_if->cryptography_encrypt(//Stub out data in/out as this is done in place and want to save cycles - (uint8_t*)(&pTfBuffer[data_loc]), // ciphertext output - (size_t) pdu_len, // length of data - (uint8_t*)(&pTfBuffer[data_loc]), // plaintext input - (size_t) pdu_len, // in data length - from start of frame to end of data - &(ekp->value[0]), // Key - Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs), - sa_ptr, // SA (for key reference) - sa_ptr->iv, // IV - sa_ptr->iv_len, // IV Length - &sa_ptr->ecs, // encryption cipher - pkcs_padding, // authentication cipher - NULL); - } - } - else if(sa_service_type == SA_PLAINTEXT) - { - // Do nothing, SDLS fields were already copied into static frame in memory - } - else{ -#ifdef TM_DEBUG - printf(KRED "Service type reported as: %d\n" RESET, sa_service_type); - printf(KRED "ECS IS AEAD Value: %d\n" RESET, ecs_is_aead_algorithm); -#endif - status = CRYPTO_LIB_ERR_UNSUPPORTED_MODE; - } - } - - if (status != CRYPTO_LIB_SUCCESS) - { - return status; // Cryptography IF call failed, return. - } - - if (sa_service_type != SA_PLAINTEXT) - { -#ifdef INCREMENT - if (crypto_config.crypto_increment_nontransmitted_iv == SA_INCREMENT_NONTRANSMITTED_IV_TRUE) - { - if (sa_ptr->shivf_len > 0 && sa_ptr->iv_len != 0) - { - Crypto_increment(sa_ptr->iv, sa_ptr->iv_len); - } - } - else // SA_INCREMENT_NONTRANSMITTED_IV_FALSE - { - // Only increment the transmitted portion - if (sa_ptr->shivf_len > 0 && sa_ptr->iv_len != 0) - { - Crypto_increment(sa_ptr->iv + (sa_ptr->iv_len - sa_ptr->shivf_len), sa_ptr->shivf_len); - } - } - if (sa_ptr->shsnf_len > 0) - { - Crypto_increment(sa_ptr->arsn, sa_ptr->arsn_len); - } - -#ifdef SA_DEBUG - if (sa_ptr->iv_len > 0) - { - printf(KYEL "Next IV value is:\n\t"); - for (i = 0; i < sa_ptr->iv_len; i++) - { - printf("%02x", *(sa_ptr->iv + i)); - } - printf("\n" RESET); - printf(KYEL "Next transmitted IV value is:\n\t"); - for (i = sa_ptr->iv_len - sa_ptr->shivf_len; i < sa_ptr->iv_len; i++) - { - printf("%02x", *(sa_ptr->iv + i)); - } - printf("\n" RESET); - } - printf(KYEL "Next ARSN value is:\n\t"); - for (i = 0; i < sa_ptr->arsn_len; i++) - { - printf("%02x", *(sa_ptr->arsn + i)); - } - printf("\n" RESET); - printf(KYEL "Next transmitted ARSN value is:\n\t"); - for (i = sa_ptr->arsn_len - sa_ptr->shsnf_len; i < sa_ptr->arsn_len; i++) - { - printf("%02x", *(sa_ptr->arsn + i)); - } - printf("\n" RESET); -#endif -#endif - } - - // Move idx to mac location - idx += pdu_len; -#ifdef TM_DEBUG - if (sa_ptr->stmacf_len > 0) - { - printf(KYEL "Data length is %d\n" RESET, pdu_len); - printf(KYEL "MAC location starts at: %d\n" RESET, idx); - printf(KYEL "MAC length of %d\n" RESET, sa_ptr->stmacf_len); - } - else - { - printf(KYEL "MAC NOT SET TO BE USED IN SA - LENGTH IS 0\n"); - } -#endif - -//TODO OCF - ? Here, elsewhere? - - /** - * End Authentication / Encryption - **/ - - // Only calculate & insert FECF if CryptoLib is configured to do so & gvcid includes FECF. - if (current_managed_parameters->has_fecf == TM_HAS_FECF) - { -#ifdef FECF_DEBUG - printf(KCYN "Calcing FECF over %d bytes\n" RESET, current_managed_parameters->max_frame_size - 2); -#endif - if (crypto_config.crypto_create_fecf == CRYPTO_TM_CREATE_FECF_TRUE) - { - new_fecf = Crypto_Calc_FECF((uint8_t*)pTfBuffer, current_managed_parameters->max_frame_size - 2); - pTfBuffer[current_managed_parameters->max_frame_size - 2] = (uint8_t)((new_fecf & 0xFF00) >> 8); - pTfBuffer[current_managed_parameters->max_frame_size - 1] = (uint8_t)(new_fecf & 0x00FF); - } - else // CRYPTO_TC_CREATE_FECF_FALSE - { - pTfBuffer[current_managed_parameters->max_frame_size - 2] = (uint8_t)0x00; - pTfBuffer[current_managed_parameters->max_frame_size - 1] = (uint8_t)0x00; - } - idx += 2; - } - -#ifdef TM_DEBUG - printf(KYEL "Printing new TM frame:\n\t"); - for(int i = 0; i < current_managed_parameters->max_frame_size; i++) + status = Crypto_TM_Do_Encrypt(sa_service_type, sa_ptr, &aad_len, &mac_loc, &idx, pdu_len, pTfBuffer, aad, ecs_is_aead_algorithm, data_loc, ekp, akp, pkcs_padding, &new_fecf); + if(status != CRYPTO_LIB_SUCCESS) { - printf("%02X", pTfBuffer[i]); + return status; } - printf("\n"); -#endif - - status = sa_if->sa_save_sa(sa_ptr); - -#ifdef DEBUG - printf(KYEL "----- Crypto_TM_ApplySecurity END -----\n" RESET); -#endif mc_if->mc_log(status); return status; From 29cd1b430f820790fe3810730176e414938a80d6 Mon Sep 17 00:00:00 2001 From: Robert Brown Date: Tue, 2 Apr 2024 20:05:13 +0000 Subject: [PATCH 3/6] [nasa/cryptolib#231][nasa/cryptolib#230] WIP: TM Refactor, single return, TODO: Headers --- src/core/crypto_tm.c | 727 +++++++++++++++++++++++-------------------- 1 file changed, 388 insertions(+), 339 deletions(-) diff --git a/src/core/crypto_tm.c b/src/core/crypto_tm.c index 799cb25b..cb7ec962 100644 --- a/src/core/crypto_tm.c +++ b/src/core/crypto_tm.c @@ -986,36 +986,9 @@ int32_t Crypto_TM_ApplySecurity(uint8_t* pTfBuffer) return status; } **/ -/** - * @brief Function: Crypto_TM_ProcessSecurity - * @param ingest: uint8_t* - * @param len_ingest: int* - * @return int32: Success/Failure - **/ -int32_t Crypto_TM_ProcessSecurity(uint8_t* p_ingest, uint16_t len_ingest, uint8_t** pp_processed_frame, uint16_t* p_decrypted_length) +int32_t Crypto_TM_Process_Setup(uint16_t len_ingest, uint16_t* byte_idx, uint8_t* p_ingest, uint8_t* secondary_hdr_len) { - // Local Variables int32_t status = CRYPTO_LIB_SUCCESS; - uint8_t aad[1786]; - uint16_t aad_len = 0; - uint16_t byte_idx = 0; - uint8_t ecs_is_aead_algorithm; - uint32_t encryption_cipher = 0; - uint8_t iv_loc; - int mac_loc = 0; - uint16_t pdu_len = 1; - uint8_t* p_new_dec_frame = NULL; - SecurityAssociation_t* sa_ptr = NULL; - uint8_t sa_service_type = -1; - uint8_t secondary_hdr_len = 0; - uint8_t spi = -1; - - - // Bit math to give concise access to values in the ingest - tm_frame_pri_hdr.tfvn = ((uint8_t)p_ingest[0] & 0xC0) >> 6; - tm_frame_pri_hdr.scid = (((uint16_t)p_ingest[0] & 0x3F) << 4) | (((uint16_t)p_ingest[1] & 0xF0) >> 4); - tm_frame_pri_hdr.vcid = ((uint8_t)p_ingest[1] & 0x0E) >> 1; - #ifdef DEBUG printf(KYEL "\n----- Crypto_TM_ProcessSecurity START -----\n" RESET); #endif @@ -1024,10 +997,9 @@ int32_t Crypto_TM_ProcessSecurity(uint8_t* p_ingest, uint16_t len_ingest, uint8_ { status = CRYPTO_LIB_ERR_INPUT_FRAME_TOO_SHORT_FOR_TM_STANDARD; mc_if->mc_log(status); - return status; } - if ((crypto_config.init_status == UNITIALIZED) || (mc_if == NULL) || (sa_if == NULL)) + if ((status == CRYPTO_LIB_SUCCESS) && ((crypto_config.init_status == UNITIALIZED) || (mc_if == NULL) || (sa_if == NULL))) { #ifdef TM_DEBUG printf(KRED "ERROR: CryptoLib Configuration Not Set! -- CRYPTO_LIB_ERR_NO_CONFIG, Will Exit\n" RESET); @@ -1038,15 +1010,13 @@ int32_t Crypto_TM_ProcessSecurity(uint8_t* p_ingest, uint16_t len_ingest, uint8_ { mc_if->mc_log(status); } - return status; } // Query SA DB for active SA / SDLS parameters - if (sa_if == NULL) // This should not happen, but tested here for safety + if ((sa_if == NULL) && (status == CRYPTO_LIB_SUCCESS)) // This should not happen, but tested here for safety { printf(KRED "ERROR: SA DB Not initalized! -- CRYPTO_LIB_ERR_NO_INIT, Will Exit\n" RESET); status = CRYPTO_LIB_ERR_NO_INIT; - return status; } #ifdef TM_DEBUG @@ -1055,141 +1025,95 @@ int32_t Crypto_TM_ProcessSecurity(uint8_t* p_ingest, uint16_t len_ingest, uint8_ #endif // Lookup-retrieve managed parameters for frame via gvcid: - status = Crypto_Get_Managed_Parameters_For_Gvcid( + if (status == CRYPTO_LIB_SUCCESS) + { + status = Crypto_Get_Managed_Parameters_For_Gvcid( tm_frame_pri_hdr.tfvn, tm_frame_pri_hdr.scid, tm_frame_pri_hdr.vcid, gvcid_managed_parameters, ¤t_managed_parameters); - + } + if (status != CRYPTO_LIB_SUCCESS) { #ifdef TM_DEBUG printf(KRED "**NO LUCK WITH GVCID!\n" RESET); #endif - mc_if->mc_log(status); - return status; + // Can't mc_log if it's not configured + if (mc_if != NULL) + { + mc_if->mc_log(status); + } } // Unable to get necessary Managed Parameters for TM TF -- return with error. // Check if secondary header is present within frame // Note: Secondary headers are static only for a mission phase, not guaranteed static // over the life of a mission Per CCSDS 132.0-B.3 Section 4.1.2.7.2.3 - // Secondary Header flag is 1st bit of 5th byte (index 4) - byte_idx = 4; - if((p_ingest[byte_idx] & 0x80) == 0x80) + if(status == CRYPTO_LIB_SUCCESS) { -#ifdef TM_DEBUG - printf(KYEL "A TM Secondary Header flag is set!\n"); -#endif - // Secondary header is present - byte_idx = 6; - // Determine length of secondary header - // Length coded as total length of secondary header - 1 - // Reference CCSDS 132.0-B-2 4.1.3.2.3 - secondary_hdr_len = (p_ingest[byte_idx] & 0x3F) + 1; -#ifdef TM_DEBUG - printf(KYEL "Secondary Header Length is decoded as: %d\n", secondary_hdr_len); -#endif - // Increment from current byte (1st byte of secondary header), - // to where the SPI would start - byte_idx += secondary_hdr_len; - } - else - { - // No Secondary header, carry on as usual and increment to SPI start - byte_idx = 6; + // Secondary Header flag is 1st bit of 5th byte (index 4) + *byte_idx = 4; + if((p_ingest[*byte_idx] & 0x80) == 0x80) + { + #ifdef TM_DEBUG + printf(KYEL "A TM Secondary Header flag is set!\n"); + #endif + // Secondary header is present + *byte_idx = 6; + // Determine length of secondary header + // Length coded as total length of secondary header - 1 + // Reference CCSDS 132.0-B-2 4.1.3.2.3 + *secondary_hdr_len = (p_ingest[*byte_idx] & 0x3F) + 1; + #ifdef TM_DEBUG + printf(KYEL "Secondary Header Length is decoded as: %d\n", *secondary_hdr_len); + #endif + // Increment from current byte (1st byte of secondary header), + // to where the SPI would start + *byte_idx += *secondary_hdr_len; + } + else + { + // No Secondary header, carry on as usual and increment to SPI start + *byte_idx = 6; + } } - /** - * Begin Security Header Fields - * Reference CCSDS SDLP 3550b1 4.1.1.1.3 - **/ - // Get SPI - spi = (uint8_t)p_ingest[byte_idx] << 8 | (uint8_t)p_ingest[byte_idx + 1]; - // Move index to past the SPI - byte_idx += 2; - - status = sa_if->sa_get_from_spi(spi, &sa_ptr); - // If no valid SPI, return - if (status != CRYPTO_LIB_SUCCESS) - { - mc_if->mc_log(status); - return status; - } + return status; +} -#ifdef SA_DEBUG - printf(KYEL "DEBUG - Printing SA Entry for current frame.\n" RESET); - Crypto_saPrint(sa_ptr); -#endif - // Determine SA Service Type - if ((sa_ptr->est == 0) && (sa_ptr->ast == 0)) - { - sa_service_type = SA_PLAINTEXT; - } - else if ((sa_ptr->est == 0) && (sa_ptr->ast == 1)) - { - sa_service_type = SA_AUTHENTICATION; - } - else if ((sa_ptr->est == 1) && (sa_ptr->ast == 0)) - { - sa_service_type = SA_ENCRYPTION; - } - else if ((sa_ptr->est == 1) && (sa_ptr->ast == 1)) - { - sa_service_type = SA_AUTHENTICATED_ENCRYPTION; - } - else - { - // Probably unnecessary check - // Leaving for now as it would be cleaner in SA to have an association enum returned I believe - printf(KRED "Error: SA Service Type is not defined! \n" RESET); - status = CRYPTO_LIB_ERROR; - mc_if->mc_log(status); - return status; - } +int32_t Crypto_TM_Determine_Cipher_Mode(uint8_t sa_service_type, SecurityAssociation_t* sa_ptr, uint32_t* encryption_cipher, uint8_t* ecs_is_aead_algorithm) +{ + int32_t status = CRYPTO_LIB_SUCCESS; - // Determine Algorithm cipher & mode. // TODO - Parse authentication_cipher, and handle AEAD cases properly if (sa_service_type != SA_PLAINTEXT) { if (sa_ptr->ecs != CRYPTO_CIPHER_NONE) { - encryption_cipher = sa_ptr->ecs; + *encryption_cipher = sa_ptr->ecs; #ifdef TC_DEBUG - printf(KYEL "SA Encryption Cipher: %d\n", encryption_cipher); + printf(KYEL "SA Encryption Cipher: %d\n", *encryption_cipher); #endif } // If no pointer, must not be using ECS at all else { - encryption_cipher = CRYPTO_CIPHER_NONE; + *encryption_cipher = CRYPTO_CIPHER_NONE; } - ecs_is_aead_algorithm = Crypto_Is_AEAD_Algorithm(encryption_cipher); + *ecs_is_aead_algorithm = Crypto_Is_AEAD_Algorithm(*encryption_cipher); } - if ( encryption_cipher == CRYPTO_CIPHER_NONE && sa_ptr->est == 1) + if ( *encryption_cipher == CRYPTO_CIPHER_NONE && sa_ptr->est == 1) { status = CRYPTO_LIB_ERR_NO_ECS_SET_FOR_ENCRYPTION_MODE; mc_if->mc_log(status); - return status; } -#ifdef TM_DEBUG - switch (sa_service_type) - { - case SA_PLAINTEXT: - printf(KBLU "Processing a TM - CLEAR!\n" RESET); - break; - case SA_AUTHENTICATION: - printf(KBLU "Processing a TM - AUTHENTICATED!\n" RESET); - break; - case SA_ENCRYPTION: - printf(KBLU "Processing a TM - ENCRYPTED!\n" RESET); - break; - case SA_AUTHENTICATED_ENCRYPTION: - printf(KBLU "Processing a TM - AUTHENTICATED ENCRYPTION!\n" RESET); - break; - } -#endif + return status; +} + +int32_t Crypto_TM_FECF_Setup(uint8_t* p_ingest, uint16_t len_ingest) +{ + int32_t status = CRYPTO_LIB_SUCCESS; - // Parse & Check FECF, if present, and update fecf length if (current_managed_parameters->has_fecf == TM_HAS_FECF) { uint16_t received_fecf = (((p_ingest[current_managed_parameters->max_frame_size - 2] << 8) & 0xFF00) | @@ -1210,7 +1134,6 @@ int32_t Crypto_TM_ProcessSecurity(uint8_t* p_ingest, uint16_t len_ingest, uint8_ #endif status = CRYPTO_LIB_ERR_INVALID_FECF; mc_if->mc_log(status); - return status; } // Valid FECF, zero out the field else @@ -1232,114 +1155,13 @@ int32_t Crypto_TM_ProcessSecurity(uint8_t* p_ingest, uint16_t len_ingest, uint8_ #endif status = CRYPTO_LIB_ERR_TC_ENUM_USED_FOR_TM_CONFIG; mc_if->mc_log(status); - return status; - } - - // Accio buffer - p_new_dec_frame = (uint8_t*)calloc(1, (len_ingest) * sizeof(uint8_t)); - if (!p_new_dec_frame) - { - printf(KRED "Error: Calloc for decrypted output buffer failed! \n" RESET); - status = CRYPTO_LIB_ERROR; - mc_if->mc_log(status); - return status; - } - - // Copy over TM Primary Header (6 bytes),Secondary (if present) - // If present, the TF Secondary Header will follow the TF PriHdr - memcpy(p_new_dec_frame, &p_ingest[0], 6 + secondary_hdr_len); - - // Byte_idx is still set to just past the SPI - // If IV is present, note location - if (sa_ptr->iv_len > 0) - { - iv_loc = byte_idx; - } - // Increment byte_idx past Security Header Fields based on SA values - byte_idx += sa_ptr->shivf_len; - byte_idx += (sa_ptr->arsn_len - sa_ptr->shsnf_len); - byte_idx += sa_ptr->shplf_len; - -#ifdef SA_DEBUG - printf(KYEL "IV length of %d bytes\n" RESET, sa_ptr->shivf_len); - printf(KYEL "ARSN length of %d bytes\n" RESET, sa_ptr->arsn_len - sa_ptr->shsnf_len); - printf(KYEL "PAD length field of %d bytes\n" RESET, sa_ptr->shplf_len); - printf(KYEL "First byte past Security Header is at index %d\n" RESET, byte_idx); -#endif - - /** - * End Security Header Fields - * byte_idx is now at start of pdu / encrypted data - **/ - - // Calculate size of the protocol data unit - // NOTE: This size itself is not the length for authentication - pdu_len = current_managed_parameters->max_frame_size - (byte_idx) - sa_ptr->stmacf_len; - if(current_managed_parameters->has_ocf == TM_HAS_OCF) - { - pdu_len -= 4; - } - if(current_managed_parameters->has_fecf == TM_HAS_FECF) - { - pdu_len -= 2; - } - - // If MAC exists, comes immediately after pdu - if (sa_ptr->stmacf_len > 0) - { - mac_loc = byte_idx + pdu_len; - } - -#ifdef TM_DEBUG - printf(KYEL "Index / data location starts at: %d\n" RESET, byte_idx); - printf(KYEL "Data size is: %d\n" RESET, pdu_len); - if(current_managed_parameters->has_ocf == TM_HAS_OCF) - { - // If OCF exists, comes immediately after MAC - printf(KYEL "OCF Location is: %d" RESET, byte_idx + pdu_len + sa_ptr->stmacf_len); - } - if(current_managed_parameters->has_fecf == TM_HAS_FECF) - { - // If FECF exists, comes just before end of the frame - printf(KYEL "FECF Location is: %d\n" RESET, current_managed_parameters->max_frame_size - 2); - } -#endif - - // Copy pdu into output frame - // this will be over-written by decryption functions if necessary, - // but not by authentication which requires - - // Get Key - crypto_key_t* ekp = NULL; - ekp = key_if->get_key(sa_ptr->ekid); - if (ekp == NULL) - { - status = CRYPTO_LIB_ERR_KEY_ID_ERROR; - mc_if->mc_log(status); - return status; - } - - crypto_key_t* akp = NULL; - akp = key_if->get_key(sa_ptr->akid); - if (akp == NULL) - { - status = CRYPTO_LIB_ERR_KEY_ID_ERROR; - mc_if->mc_log(status); - return status; } + return status; +} - /** - * Begin Authentication / Encryption - **/ - - // if(sa_service_type != SA_PLAINTEXT) - // { - // status = CRYPTO_LIB_ERR_NULL_CIPHERS; - // mc_if->mc_log(status); - // return status; - // } - - // Parse MAC, prepare AAD +int32_t Crypto_TM_Parse_Mac_Prep_AAD(uint8_t sa_service_type, uint8_t* p_ingest, int mac_loc, SecurityAssociation_t* sa_ptr, uint16_t* aad_len, uint16_t byte_idx, uint8_t* aad) +{ + int32_t status = CRYPTO_LIB_SUCCESS; if ((sa_service_type == SA_AUTHENTICATION) || (sa_service_type == SA_AUTHENTICATED_ENCRYPTION)) { #ifdef MAC_DEBUG @@ -1348,134 +1170,179 @@ int32_t Crypto_TM_ProcessSecurity(uint8_t* p_ingest, uint16_t len_ingest, uint8_ #endif if (sa_service_type == SA_AUTHENTICATED_ENCRYPTION) { - aad_len = byte_idx; + *aad_len = byte_idx; } else { - aad_len = mac_loc; + *aad_len = mac_loc; } - if (sa_ptr->abm_len < aad_len) + if (sa_ptr->abm_len < *aad_len) { status = CRYPTO_LIB_ERR_ABM_TOO_SHORT_FOR_AAD; mc_if->mc_log(status); - return status; } // Use ingest and abm to create aad - Crypto_Prepare_TM_AAD(p_ingest, aad_len, sa_ptr->abm, &aad[0]); + if(status == CRYPTO_LIB_SUCCESS) + { + status = Crypto_Prepare_TM_AAD(p_ingest, *aad_len, sa_ptr->abm, aad); + } #ifdef MAC_DEBUG - printf("AAD Debug:\n\tAAD Length is %d\n\t AAD is: ", aad_len); - for (int i = 0; icryptography_decrypt(p_new_dec_frame+byte_idx, // plaintext output + pdu_len, // length of data + p_ingest+byte_idx, // ciphertext input + pdu_len, // in data length + &(ekp->value[0]), // Key + Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs), + sa_ptr, // SA for key reference + p_ingest+iv_loc, // IV + sa_ptr->iv_len, // IV Length + &sa_ptr->ecs, // encryption cipher + &sa_ptr->acs, // authentication cipher + NULL); + } + if(sa_service_type == SA_AUTHENTICATED_ENCRYPTION) + { + status = cryptography_if->cryptography_aead_decrypt(p_new_dec_frame+byte_idx, // plaintext output + pdu_len, // length of data + p_ingest+byte_idx, // ciphertext input + pdu_len, // in data length + &(ekp->value[0]), // Key + Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs), + sa_ptr, // SA for key reference + p_ingest+iv_loc, // IV + sa_ptr->iv_len, // IV Length + p_ingest+mac_loc, // Frame Expected Tag + sa_ptr->stmacf_len, // tag size + aad, // additional authenticated data + aad_len, // length of AAD + (sa_ptr->est), // Decryption Bool + (sa_ptr->ast), // Authentication Bool + (sa_ptr->ast), // AAD Bool + &sa_ptr->ecs, // encryption cipher + &sa_ptr->acs, // authentication cipher + NULL); + } + return status; +} - if(sa_service_type == SA_ENCRYPTION) +int32_t Crypto_TM_Do_Decrypt_NONAEAD(uint8_t sa_service_type, uint16_t pdu_len, uint8_t* p_new_dec_frame, uint16_t byte_idx, uint8_t* p_ingest, crypto_key_t* akp, crypto_key_t* ekp, SecurityAssociation_t* sa_ptr, uint8_t iv_loc, int mac_loc, uint16_t aad_len, uint8_t* aad) +{ + int32_t status = CRYPTO_LIB_SUCCESS; + if(sa_service_type == SA_AUTHENTICATION || sa_service_type == SA_AUTHENTICATED_ENCRYPTION) + { + status = cryptography_if->cryptography_validate_authentication(p_new_dec_frame+byte_idx, // plaintext output + pdu_len, // length of data + p_ingest+byte_idx, // ciphertext input + pdu_len, // in data length + &(akp->value[0]), // Key + Crypto_Get_ACS_Algo_Keylen(sa_ptr->acs), + sa_ptr, // SA for key reference + p_ingest+iv_loc, // IV + sa_ptr->iv_len, // IV Length + p_ingest+mac_loc, // Frame Expected Tag + sa_ptr->stmacf_len, // tag size + aad, // additional authenticated data + aad_len, // length of AAD + CRYPTO_CIPHER_NONE, // encryption cipher + sa_ptr->acs, // authentication cipher + NULL); // cam cookies + + } + if(sa_service_type == SA_ENCRYPTION || sa_service_type == SA_AUTHENTICATED_ENCRYPTION) + { + // Check that key length to be used meets the algorithm requirement + if((int32_t) ekp->key_len != Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs)) { - status = cryptography_if->cryptography_decrypt(p_new_dec_frame+byte_idx, // plaintext output - pdu_len, // length of data - p_ingest+byte_idx, // ciphertext input - pdu_len, // in data length - &(ekp->value[0]), // Key - Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs), - sa_ptr, // SA for key reference - p_ingest+iv_loc, // IV - sa_ptr->iv_len, // IV Length - &sa_ptr->ecs, // encryption cipher - &sa_ptr->acs, // authentication cipher - NULL); + // free(aad); - non-heap object + status = CRYPTO_LIB_ERR_KEY_LENGTH_ERROR; + mc_if->mc_log(status); + //return status; } - if(sa_service_type == SA_AUTHENTICATED_ENCRYPTION) + + if(status == CRYPTO_LIB_SUCCESS) { - status = cryptography_if->cryptography_aead_decrypt(p_new_dec_frame+byte_idx, // plaintext output - pdu_len, // length of data - p_ingest+byte_idx, // ciphertext input - pdu_len, // in data length - &(ekp->value[0]), // Key - Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs), - sa_ptr, // SA for key reference - p_ingest+iv_loc, // IV - sa_ptr->iv_len, // IV Length - p_ingest+mac_loc, // Frame Expected Tag - sa_ptr->stmacf_len, // tag size - aad, // additional authenticated data - aad_len, // length of AAD - (sa_ptr->est), // Decryption Bool - (sa_ptr->ast), // Authentication Bool - (sa_ptr->ast), // AAD Bool - &sa_ptr->ecs, // encryption cipher - &sa_ptr->acs, // authentication cipher - NULL); + status = cryptography_if->cryptography_decrypt(p_new_dec_frame+byte_idx, // plaintext output + pdu_len, // length of data + p_ingest+byte_idx, // ciphertext input + pdu_len, // in data length + &(ekp->value[0]), // Key + Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs), + sa_ptr, // SA for key reference + p_ingest+iv_loc, // IV + sa_ptr->iv_len, // IV Length + &sa_ptr->ecs, // encryption cipher + &sa_ptr->acs, // authentication cipher + NULL); } + + // //Handle Padding Removal + // if(sa_ptr->shplf_len != 0) + // { + // int padding_location = TC_FRAME_HEADER_SIZE + segment_hdr_len + SPI_LEN + sa_ptr->shivf_len + + // sa_ptr->shsnf_len; + // uint16_t padding_amount = 0; + // // Get Padding Amount from ingest frame + // padding_amount = (int)ingest[padding_location]; + // // Remove Padding from final decrypted portion + // tc_sdls_processed_frame->tc_pdu_len -= padding_amount; + // } } + return status; +} - else if (sa_service_type != SA_PLAINTEXT && ecs_is_aead_algorithm == CRYPTO_FALSE) +void Crypto_TM_Calc_PDU_MAC(uint16_t* pdu_len, uint16_t byte_idx, SecurityAssociation_t* sa_ptr, int* mac_loc) +{ + *pdu_len = current_managed_parameters->max_frame_size - (byte_idx) - sa_ptr->stmacf_len; + if(current_managed_parameters->has_ocf == TM_HAS_OCF) { - // TODO - implement non-AEAD algorithm logic - if(sa_service_type == SA_AUTHENTICATION || sa_service_type == SA_AUTHENTICATED_ENCRYPTION) - { - status = cryptography_if->cryptography_validate_authentication(p_new_dec_frame+byte_idx, // plaintext output - pdu_len, // length of data - p_ingest+byte_idx, // ciphertext input - pdu_len, // in data length - &(akp->value[0]), // Key - Crypto_Get_ACS_Algo_Keylen(sa_ptr->acs), - sa_ptr, // SA for key reference - p_ingest+iv_loc, // IV - sa_ptr->iv_len, // IV Length - p_ingest+mac_loc, // Frame Expected Tag - sa_ptr->stmacf_len, // tag size - aad, // additional authenticated data - aad_len, // length of AAD - CRYPTO_CIPHER_NONE, // encryption cipher - sa_ptr->acs, // authentication cipher - NULL); // cam cookies + *pdu_len -= 4; + } + if(current_managed_parameters->has_fecf == TM_HAS_FECF) + { + *pdu_len -= 2; + } - } - if(sa_service_type == SA_ENCRYPTION || sa_service_type == SA_AUTHENTICATED_ENCRYPTION) - { - // Check that key length to be used emets the algorithm requirement - if((int32_t) ekp->key_len != Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs)) - { - // free(aad); - non-heap object - status = CRYPTO_LIB_ERR_KEY_LENGTH_ERROR; - mc_if->mc_log(status); - return status; - } + // If MAC exists, comes immediately after pdu + if (sa_ptr->stmacf_len > 0) + { + *mac_loc = byte_idx + *pdu_len; + } +} - status = cryptography_if->cryptography_decrypt(p_new_dec_frame+byte_idx, // plaintext output - pdu_len, // length of data - p_ingest+byte_idx, // ciphertext input - pdu_len, // in data length - &(ekp->value[0]), // Key - Crypto_Get_ECS_Algo_Keylen(sa_ptr->ecs), - sa_ptr, // SA for key reference - p_ingest+iv_loc, // IV - sa_ptr->iv_len, // IV Length - &sa_ptr->ecs, // encryption cipher - &sa_ptr->acs, // authentication cipher - NULL); +int32_t Crypto_TM_Do_Decrypt(uint8_t sa_service_type, SecurityAssociation_t* sa_ptr, uint8_t ecs_is_aead_algorithm, uint16_t byte_idx, uint8_t* p_new_dec_frame, uint16_t pdu_len, uint8_t* p_ingest, crypto_key_t* ekp, crypto_key_t* akp, uint8_t iv_loc, int mac_loc, uint16_t aad_len, uint8_t* aad, uint8_t** pp_processed_frame, uint16_t* p_decrypted_length) +{ + int32_t status = CRYPTO_LIB_SUCCESS; + if(sa_service_type != SA_PLAINTEXT && ecs_is_aead_algorithm == CRYPTO_TRUE) + { + status = Crypto_TM_Do_Decrypt_AEAD(sa_service_type, p_ingest, p_new_dec_frame, byte_idx, pdu_len, ekp, sa_ptr, iv_loc, mac_loc, aad_len, aad); + } - // //Handle Padding Removal - // if(sa_ptr->shplf_len != 0) - // { - // int padding_location = TC_FRAME_HEADER_SIZE + segment_hdr_len + SPI_LEN + sa_ptr->shivf_len + - // sa_ptr->shsnf_len; - // uint16_t padding_amount = 0; - // // Get Padding Amount from ingest frame - // padding_amount = (int)ingest[padding_location]; - // // Remove Padding from final decrypted portion - // tc_sdls_processed_frame->tc_pdu_len -= padding_amount; - // } - } + else if (sa_service_type != SA_PLAINTEXT && ecs_is_aead_algorithm == CRYPTO_FALSE) + { + status = Crypto_TM_Do_Decrypt_NONAEAD(sa_service_type, pdu_len, p_new_dec_frame, byte_idx, p_ingest, akp, ekp, sa_ptr, iv_loc, mac_loc, aad_len, aad); + // TODO - implement non-AEAD algorithm logic } // If plaintext, copy byte by byte @@ -1506,10 +1373,192 @@ int32_t Crypto_TM_ProcessSecurity(uint8_t* p_ingest, uint16_t len_ingest, uint8_ #ifdef DEBUG printf(KYEL "----- Crypto_TM_ProcessSecurity END -----\n" RESET); #endif - + if(status != CRYPTO_LIB_SUCCESS) + { mc_if->mc_log(status); - return status; } + + return status; +} + +void Crypto_TM_Process_Debug_Print(uint16_t byte_idx, uint16_t pdu_len, SecurityAssociation_t* sa_ptr) +{ + #ifdef TM_DEBUG + printf(KYEL "Index / data location starts at: %d\n" RESET, byte_idx); + printf(KYEL "Data size is: %d\n" RESET, pdu_len); + if(current_managed_parameters->has_ocf == TM_HAS_OCF) + { + // If OCF exists, comes immediately after MAC + printf(KYEL "OCF Location is: %d" RESET, byte_idx + pdu_len + sa_ptr->stmacf_len); + } + if(current_managed_parameters->has_fecf == TM_HAS_FECF) + { + // If FECF exists, comes just before end of the frame + printf(KYEL "FECF Location is: %d\n" RESET, current_managed_parameters->max_frame_size - 2); + } + #endif +} + +/** + * @brief Function: Crypto_TM_ProcessSecurity + * @param ingest: uint8_t* + * @param len_ingest: int* + * @return int32: Success/Failure + **/ +int32_t Crypto_TM_ProcessSecurity(uint8_t* p_ingest, uint16_t len_ingest, uint8_t** pp_processed_frame, uint16_t* p_decrypted_length) +{ + // Local Variables + int32_t status = CRYPTO_LIB_SUCCESS; + uint8_t aad[1786]; + uint16_t aad_len = 0; + uint16_t byte_idx = 0; + uint8_t ecs_is_aead_algorithm; + uint32_t encryption_cipher = 0; + uint8_t iv_loc; + int mac_loc = 0; + uint16_t pdu_len = 1; + uint8_t* p_new_dec_frame = NULL; + SecurityAssociation_t* sa_ptr = NULL; + uint8_t sa_service_type = -1; + uint8_t secondary_hdr_len = 0; + uint8_t spi = -1; + crypto_key_t* ekp = NULL; + crypto_key_t* akp = NULL; + + // Bit math to give concise access to values in the ingest + tm_frame_pri_hdr.tfvn = ((uint8_t)p_ingest[0] & 0xC0) >> 6; + tm_frame_pri_hdr.scid = (((uint16_t)p_ingest[0] & 0x3F) << 4) | (((uint16_t)p_ingest[1] & 0xF0) >> 4); + tm_frame_pri_hdr.vcid = ((uint8_t)p_ingest[1] & 0x0E) >> 1; + + status = Crypto_TM_Process_Setup(len_ingest, &byte_idx, p_ingest, &secondary_hdr_len); + if (status == CRYPTO_LIB_SUCCESS) + { + /** + * Begin Security Header Fields + * Reference CCSDS SDLP 3550b1 4.1.1.1.3 + **/ + // Get SPI + spi = (uint8_t)p_ingest[byte_idx] << 8 | (uint8_t)p_ingest[byte_idx + 1]; + // Move index to past the SPI + byte_idx += 2; + + status = sa_if->sa_get_from_spi(spi, &sa_ptr); + } + + // If no valid SPI, return + if (status == CRYPTO_LIB_SUCCESS) + { +#ifdef SA_DEBUG + printf(KYEL "DEBUG - Printing SA Entry for current frame.\n" RESET); + Crypto_saPrint(sa_ptr); +#endif + // Determine SA Service Type + status = Crypto_TM_Determine_SA_Service_Type(&sa_service_type, sa_ptr); + } + if (status == CRYPTO_LIB_SUCCESS) + { + // Determine Algorithm cipher & mode. // TODO - Parse authentication_cipher, and handle AEAD cases properly + status = Crypto_TM_Determine_Cipher_Mode(sa_service_type, sa_ptr, &encryption_cipher, &ecs_is_aead_algorithm); + } + if (status == CRYPTO_LIB_SUCCESS) + { + #ifdef TM_DEBUG + switch (sa_service_type) + { + case SA_PLAINTEXT: + printf(KBLU "Processing a TM - CLEAR!\n" RESET); + break; + case SA_AUTHENTICATION: + printf(KBLU "Processing a TM - AUTHENTICATED!\n" RESET); + break; + case SA_ENCRYPTION: + printf(KBLU "Processing a TM - ENCRYPTED!\n" RESET); + break; + case SA_AUTHENTICATED_ENCRYPTION: + printf(KBLU "Processing a TM - AUTHENTICATED ENCRYPTION!\n" RESET); + break; + } + #endif + + // Parse & Check FECF, if present, and update fecf length + status = Crypto_TM_FECF_Setup(p_ingest, len_ingest); + } + + if (status == CRYPTO_LIB_SUCCESS) + { + // Accio buffer + p_new_dec_frame = (uint8_t*)calloc(1, (len_ingest) * sizeof(uint8_t)); + if (!p_new_dec_frame) + { + printf(KRED "Error: Calloc for decrypted output buffer failed! \n" RESET); + status = CRYPTO_LIB_ERROR; + } + } + + if (status == CRYPTO_LIB_SUCCESS) + { + // Copy over TM Primary Header (6 bytes),Secondary (if present) + // If present, the TF Secondary Header will follow the TF PriHdr + memcpy(p_new_dec_frame, &p_ingest[0], 6 + secondary_hdr_len); + + // Byte_idx is still set to just past the SPI + // If IV is present, note location + if (sa_ptr->iv_len > 0) + { + iv_loc = byte_idx; + } + // Increment byte_idx past Security Header Fields based on SA values + byte_idx += sa_ptr->shivf_len; + byte_idx += (sa_ptr->arsn_len - sa_ptr->shsnf_len); + byte_idx += sa_ptr->shplf_len; + + #ifdef SA_DEBUG + printf(KYEL "IV length of %d bytes\n" RESET, sa_ptr->shivf_len); + printf(KYEL "ARSN length of %d bytes\n" RESET, sa_ptr->arsn_len - sa_ptr->shsnf_len); + printf(KYEL "PAD length field of %d bytes\n" RESET, sa_ptr->shplf_len); + printf(KYEL "First byte past Security Header is at index %d\n" RESET, byte_idx); + #endif + + /** + * End Security Header Fields + * byte_idx is now at start of pdu / encrypted data + **/ + + // Calculate size of the protocol data unit + // NOTE: This size itself is not the length for authentication + Crypto_TM_Calc_PDU_MAC(&pdu_len, byte_idx, sa_ptr, &mac_loc); + + Crypto_TM_Process_Debug_Print(byte_idx, pdu_len, sa_ptr); + + // Copy pdu into output frame + // this will be over-written by decryption functions if necessary, + // but not by authentication which requires + + // Get Key + status = Crypto_TM_Get_Keys(&ekp, &akp, sa_ptr); + } + + if (status == CRYPTO_LIB_SUCCESS) + { + /** + * Begin Authentication / Encryption + **/ + + // if(sa_service_type != SA_PLAINTEXT) + // { + // status = CRYPTO_LIB_ERR_NULL_CIPHERS; + // mc_if->mc_log(status); + // return status; + // } + + // Parse MAC, prepare AAD + Crypto_TM_Parse_Mac_Prep_AAD(sa_service_type, p_ingest, mac_loc, sa_ptr, &aad_len, byte_idx, aad); + + status = Crypto_TM_Do_Decrypt(sa_service_type, sa_ptr, ecs_is_aead_algorithm, byte_idx, p_new_dec_frame, pdu_len, p_ingest, ekp, akp, iv_loc, mac_loc, aad_len, aad, pp_processed_frame, p_decrypted_length); + } + + return status; +} /** * @brief Function: Crypto_Get_tmLength From b960619cab59999f7db26dcbd9f692a7302b87d1 Mon Sep 17 00:00:00 2001 From: Robert Brown Date: Wed, 3 Apr 2024 17:30:03 +0000 Subject: [PATCH 4/6] [nasa/cryptolib#231][nasa/cryptolib#230] TM Refactor Headers and Doxygen --- include/crypto.h | 24 +++++ src/core/crypto_tm.c | 221 +++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 245 insertions(+) diff --git a/include/crypto.h b/include/crypto.h index a153b774..680570d2 100644 --- a/include/crypto.h +++ b/include/crypto.h @@ -115,6 +115,30 @@ extern char* Crypto_Get_Error_Code_Enum_String(int32_t crypto_error_code); /* ** Internal Prototypes */ +// Telemetry (TM) +int32_t Crypto_TM_Sanity_Check(uint8_t* pTfBuffer); +int32_t Crypto_TM_Determine_SA_Service_Type(uint8_t* sa_service_type, SecurityAssociation_t* sa_ptr); +void Crypto_TM_Check_For_Secondary_Header(uint8_t* pTfBuffer, uint16_t* idx); +int32_t Crypto_TM_IV_Sanity_Check(uint8_t* sa_service_type, SecurityAssociation_t* sa_ptr); +void Crypto_TM_PKCS_Padding(uint32_t* pkcs_padding, SecurityAssociation_t* sa_ptr, uint8_t* pTfBuffer, uint16_t* idx_p); +void Crypto_TM_Handle_Managed_Parameter_Flags(uint16_t* pdu_len); +int32_t Crypto_TM_Get_Keys(crypto_key_t** ekp, crypto_key_t** akp, SecurityAssociation_t* sa_ptr); +int32_t Crypto_TM_Do_Encrypt_NONPLAINTEXT(uint8_t sa_service_type, uint16_t* aad_len, int* mac_loc, uint16_t* idx_p, uint16_t pdu_len, uint8_t* pTfBuffer, uint8_t* aad, SecurityAssociation_t* sa_ptr); +int32_t Crypto_TM_Do_Encrypt_NONPLAINTEXT_AEAD_Logic(uint8_t sa_service_type, uint8_t ecs_is_aead_algorithm, uint8_t* pTfBuffer, uint16_t pdu_len, uint16_t data_loc, crypto_key_t* ekp, crypto_key_t* akp, uint32_t pkcs_padding, int* mac_loc, uint16_t* aad_len, uint8_t* aad, SecurityAssociation_t* sa_ptr); +int32_t Crypto_TM_Do_Encrypt_Handle_Increment(uint8_t sa_service_type, SecurityAssociation_t* sa_ptr); +int32_t Crypto_TM_Do_Encrypt(uint8_t sa_service_type, SecurityAssociation_t* sa_ptr, uint16_t* aad_len, int* mac_loc, uint16_t* idx_p, uint16_t pdu_len, uint8_t* pTfBuffer, uint8_t* aad, uint8_t ecs_is_aead_algorithm, uint16_t data_loc, crypto_key_t* ekp, crypto_key_t* akp, uint32_t pkcs_padding, uint16_t* new_fecf); +void Crypto_TM_ApplySecurity_Debug_Print(uint16_t idx, uint16_t pdu_len, SecurityAssociation_t* sa_ptr); +int32_t Crypto_TM_Process_Setup(uint16_t len_ingest, uint16_t* byte_idx, uint8_t* p_ingest, uint8_t* secondary_hdr_len); +int32_t Crypto_TM_Determine_Cipher_Mode(uint8_t sa_service_type, SecurityAssociation_t* sa_ptr, uint32_t* encryption_cipher, uint8_t* ecs_is_aead_algorithm); +int32_t Crypto_TM_FECF_Setup(uint8_t* p_ingest, uint16_t len_ingest); +int32_t Crypto_TM_Parse_Mac_Prep_AAD(uint8_t sa_service_type, uint8_t* p_ingest, int mac_loc, SecurityAssociation_t* sa_ptr, uint16_t* aad_len, uint16_t byte_idx, uint8_t* aad); +int32_t Crypto_TM_Do_Decrypt_AEAD(uint8_t sa_service_type, uint8_t* p_ingest, uint8_t* p_new_dec_frame, uint16_t byte_idx, uint16_t pdu_len, crypto_key_t* ekp, SecurityAssociation_t* sa_ptr, uint8_t iv_loc, int mac_loc, uint16_t aad_len, uint8_t* aad); +int32_t Crypto_TM_Do_Decrypt_NONAEAD(uint8_t sa_service_type, uint16_t pdu_len, uint8_t* p_new_dec_frame, uint16_t byte_idx, uint8_t* p_ingest, crypto_key_t* akp, crypto_key_t* ekp, SecurityAssociation_t* sa_ptr, uint8_t iv_loc, int mac_loc, uint16_t aad_len, uint8_t* aad); +void Crypto_TM_Calc_PDU_MAC(uint16_t* pdu_len, uint16_t byte_idx, SecurityAssociation_t* sa_ptr, int* mac_loc); +int32_t Crypto_TM_Do_Decrypt(uint8_t sa_service_type, SecurityAssociation_t* sa_ptr, uint8_t ecs_is_aead_algorithm, uint16_t byte_idx, uint8_t* p_new_dec_frame, uint16_t pdu_len, uint8_t* p_ingest, crypto_key_t* ekp, crypto_key_t* akp, uint8_t iv_loc, int mac_loc, uint16_t aad_len, uint8_t* aad, uint8_t** pp_processed_frame, uint16_t* p_decrypted_length); +void Crypto_TM_Process_Debug_Print(uint16_t byte_idx, uint16_t pdu_len, SecurityAssociation_t* sa_ptr); + + extern uint8_t Crypto_Prep_Reply(uint8_t* ingest, uint8_t appID); extern int32_t Crypto_increment(uint8_t* num, int length); // int32_t Crypto_Get_tcPayloadLength(TC_t* tc_frame, SecurityAssociation_t* sa_ptr); diff --git a/src/core/crypto_tm.c b/src/core/crypto_tm.c index cb7ec962..4f63c44f 100644 --- a/src/core/crypto_tm.c +++ b/src/core/crypto_tm.c @@ -23,6 +23,12 @@ #include // memcpy/memset +/** + * @brief Function: Crypto_TM_Sanity_Check + * Verify that needed buffers and settings are not null + * @param pTfBuffer: uint8_t* + * @return int32: Success/Failure +**/ int32_t Crypto_TM_Sanity_Check(uint8_t* pTfBuffer) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -43,6 +49,13 @@ int32_t Crypto_TM_Sanity_Check(uint8_t* pTfBuffer) return status; } +/** + * @brief Function: Crypto_TM_Determine_SA_Service_Type + * Determines the service type for Security Association + * @param sa_service_type: uint8_t* + * @param sa_ptr: SecurityAssociation_t* + * @return int32_t: Success/Failure +**/ int32_t Crypto_TM_Determine_SA_Service_Type(uint8_t* sa_service_type, SecurityAssociation_t* sa_ptr) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -74,6 +87,12 @@ int32_t Crypto_TM_Determine_SA_Service_Type(uint8_t* sa_service_type, SecurityAs return status; } +/** + * @brief Function: Crypto_TM_Check_For_Secondary_Header + * Determines if a secondary header exists + * @param pTfBuffer: uint8_t* + * @param idx: uint16_t* +**/ void Crypto_TM_Check_For_Secondary_Header(uint8_t* pTfBuffer, uint16_t* idx) { *idx = 4; @@ -102,6 +121,13 @@ void Crypto_TM_Check_For_Secondary_Header(uint8_t* pTfBuffer, uint16_t* idx) } } +/** + * @brief Function: Crypto_TM_IV_Sanity_Check + * Verifies sanity of IV. Validates IV Values, Ciphers, and Algorithms + * @param sa_service_type: uint8_t* + * @param sa_ptr: SecurityAssociation_t* + * @return int32_t: Success/Failure +**/ int32_t Crypto_TM_IV_Sanity_Check(uint8_t* sa_service_type, SecurityAssociation_t* sa_ptr) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -148,6 +174,14 @@ int32_t Crypto_TM_IV_Sanity_Check(uint8_t* sa_service_type, SecurityAssociation_ return status; } +/** + * @brief Function: Crypto_TM_PKCS_Padding + * Handles pkcs padding as necessary + * @param pkcs_padding: uint32_t* + * @param sa_ptr: SecurityAssociation_t* + * @param pTfBuffer: uint8_t* + * @param idx_p: uint16_t* +**/ void Crypto_TM_PKCS_Padding(uint32_t* pkcs_padding, SecurityAssociation_t* sa_ptr, uint8_t* pTfBuffer, uint16_t* idx_p) { uint16_t idx = *idx_p; @@ -173,6 +207,11 @@ void Crypto_TM_PKCS_Padding(uint32_t* pkcs_padding, SecurityAssociation_t* sa_pt *idx_p = idx; } +/** + * @brief Function: Crypto_TM_Handle_Managed_Parameter_Flags + * Handles pdu length while dealing with ocf/fecf + * @param pdu_len: uint16_t* +**/ void Crypto_TM_Handle_Managed_Parameter_Flags(uint16_t* pdu_len) { if(current_managed_parameters->has_ocf == TM_HAS_OCF) @@ -185,6 +224,14 @@ void Crypto_TM_Handle_Managed_Parameter_Flags(uint16_t* pdu_len) } } +/** + * @brief Function: Crypto_TM_Get_Keys + * Retrieves keys from SA based on ekid/akid. + * @param ekp: crypto_key_t** + * @param akp: crypto_key_t** + * @param sa_ptr: SecurityAssociation_t* + * @return int32_t: Success/Failure +**/ int32_t Crypto_TM_Get_Keys(crypto_key_t** ekp, crypto_key_t** akp, SecurityAssociation_t* sa_ptr) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -204,6 +251,19 @@ int32_t Crypto_TM_Get_Keys(crypto_key_t** ekp, crypto_key_t** akp, SecurityAssoc return status; } +/** + * @brief Function: Crypto_TM_Do_Encrypt_NONPLAINTEXT + * Preps Encryption for Non-plain-text Authentication and Authenticated Encryption + * @param sa_service_type: uint8_t + * @param aad_len: uint16_t* + * @param mac_loc: int* + * @param idx_p: uint16_t* + * @param pdu_len: uint16_t + * @param pTfBuffer: uint8_t* + * @param aad: uint8_t* + * @param sa_ptr: SecurityAssociation_t* + * @return int32_t: Success/Failure +**/ int32_t Crypto_TM_Do_Encrypt_NONPLAINTEXT(uint8_t sa_service_type, uint16_t* aad_len, int* mac_loc, uint16_t* idx_p, uint16_t pdu_len, uint8_t* pTfBuffer, uint8_t* aad, SecurityAssociation_t* sa_ptr) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -247,6 +307,23 @@ int32_t Crypto_TM_Do_Encrypt_NONPLAINTEXT(uint8_t sa_service_type, uint16_t* aad return status; } +/** + * @brief Function: Crypto_TM_Do_Encrypt_NONPLAINTEXT_AEAD_Logic + * Preps Encryption for Non-plain-text Encryption and Authenticated Encryption for AEAD Algorithms + * @param sa_service_type: uint8_t + * @param ecs_is_aead_algorithm: uint8_t + * @param pTfBuffer: uint8_t* + * @param pdu_len: uint16_t + * @param data_loc: uint16_t + * @param ekp: crypto_key_t* + * @param akp: crypto_key_t* + * @param pkcs_padding: uint32_t + * @param mac_loc: int* + * @param aad_len: uint16_t* + * @param aad: uint8_t* + * @param sa_ptr: SecurityAssociation_t* + * @return int32_t: Success/Failure +**/ int32_t Crypto_TM_Do_Encrypt_NONPLAINTEXT_AEAD_Logic(uint8_t sa_service_type, uint8_t ecs_is_aead_algorithm, uint8_t* pTfBuffer, uint16_t pdu_len, uint16_t data_loc, crypto_key_t* ekp, crypto_key_t* akp, uint32_t pkcs_padding, int* mac_loc, uint16_t* aad_len, uint8_t* aad, SecurityAssociation_t* sa_ptr) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -350,6 +427,13 @@ int32_t Crypto_TM_Do_Encrypt_NONPLAINTEXT_AEAD_Logic(uint8_t sa_service_type, ui return status; } +/** + * @brief Function: Crypto_TM_Do_Encrypt_Handle_Increment + * Handles the incrementing of IV and ARSN as necessary + * @param sa_service_type: uint8_t + * @param sa_ptr: SecurityAssociation_t* + * @return int32_t: Success/Failure +**/ int32_t Crypto_TM_Do_Encrypt_Handle_Increment(uint8_t sa_service_type, SecurityAssociation_t* sa_ptr) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -410,6 +494,25 @@ int32_t Crypto_TM_Do_Encrypt_Handle_Increment(uint8_t sa_service_type, SecurityA return status; } +/** + * @brief Function: Crypto_TM_Do_Encrypt + * Parent function for performing TM Encryption + * @param sa_service_type: uint8_t + * @param sa_ptr: SecurityAssociation_t* + * @param aad_len: uint16_t* + * @param mac_loc: int* + * @param idx_p: uint16_t* + * @param pdu_len: uint16_t + * @param pTfBuffer: uint8_t* + * @param aad: uint8_t* + * @param ecs_is_aead_algorithm: uint8_t + * @param data_loc: uint16_t + * @param ekp: crypto_key_t* + * @param akp: crypto_key_t* + * @param pkcs_padding: uint32_t + * @param new_fecf: uint16_t* + * @return int32_t: Success/Failure +**/ int32_t Crypto_TM_Do_Encrypt(uint8_t sa_service_type, SecurityAssociation_t* sa_ptr, uint16_t* aad_len, int* mac_loc, uint16_t* idx_p, uint16_t pdu_len, uint8_t* pTfBuffer, uint8_t* aad, uint8_t ecs_is_aead_algorithm, uint16_t data_loc, crypto_key_t* ekp, crypto_key_t* akp, uint32_t pkcs_padding, uint16_t* new_fecf) { /** @@ -493,6 +596,15 @@ int32_t Crypto_TM_Do_Encrypt(uint8_t sa_service_type, SecurityAssociation_t* sa_ return status; } + +/** + * @brief Function: Crypto_TM_ApplySecurity_Debug_Print + * Simple Debug Print function for TM. Displays + * Data Location, size, and index at end of SPI. OCF Location, FECF Location + * @param idx: uint16_t + * @param pdu_len: uint16_t + * @param sa_ptr: SecurityAssociation_t* +**/ void Crypto_TM_ApplySecurity_Debug_Print(uint16_t idx, uint16_t pdu_len, SecurityAssociation_t* sa_ptr) { #ifdef TM_DEBUG @@ -986,6 +1098,17 @@ int32_t Crypto_TM_ApplySecurity(uint8_t* pTfBuffer) return status; } **/ + +/** + * @brief Function: Crypto_TM_Process_Setup + * Sets up TM Process Security. Verifies ingest length, verifies pointers are not null, + * Retreives managed parameters, validates GVCID, and verifies the presence of Secondary Header + * @param len_ingest: uint16_t + * @param byte_idx: uint16_t* + * @param p_ingest: uint8_t* + * @param secondary_hdr_len: uint8_t* + * @return int32_t: Success/Failure +**/ int32_t Crypto_TM_Process_Setup(uint16_t len_ingest, uint16_t* byte_idx, uint8_t* p_ingest, uint8_t* secondary_hdr_len) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -1080,6 +1203,15 @@ int32_t Crypto_TM_Process_Setup(uint16_t len_ingest, uint16_t* byte_idx, uint8_t return status; } +/** + * @brief Function: Crypto_TM_Determine_Cipher_Mode + * Determines Cipher mode and Algorithm type + * @param sa_service_type: uint8_t + * @param sa_ptr: SecurityAssociation_t* + * @param encryption_cipher: uint32_t* + * @param ecs_is_aead_algorithm: uint8_t* + * @return int32_t: Success/Failure +**/ int32_t Crypto_TM_Determine_Cipher_Mode(uint8_t sa_service_type, SecurityAssociation_t* sa_ptr, uint32_t* encryption_cipher, uint8_t* ecs_is_aead_algorithm) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -1110,6 +1242,13 @@ int32_t Crypto_TM_Determine_Cipher_Mode(uint8_t sa_service_type, SecurityAssocia return status; } +/** + * @brief Function: Crypto_TM_FECF_Setup + * Handles FECF Calculations, Verification, and Setup + * @param p_ingest: uint8_t* + * @param len_ingest: uint16_t + * @return int32_t: Success/Failure +**/ int32_t Crypto_TM_FECF_Setup(uint8_t* p_ingest, uint16_t len_ingest) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -1159,6 +1298,18 @@ int32_t Crypto_TM_FECF_Setup(uint8_t* p_ingest, uint16_t len_ingest) return status; } +/** + * @brief Function: Crypto_TM_Parse_Mac_Prep_AAD + * Parses TM MAC, and calls AAD Prep functionality + * @param sa_service_type: uint8_t + * @param p_ingest: uint8_t* + * @param mac_loc: int + * @param sa_ptr: SecurityAssociation_t* + * @param aad_len: uint16_t* + * @param byte_idx: uint16_t + * @param aad: uint8_t* + * @return int32_t: Success/Failure +**/ int32_t Crypto_TM_Parse_Mac_Prep_AAD(uint8_t sa_service_type, uint8_t* p_ingest, int mac_loc, SecurityAssociation_t* sa_ptr, uint16_t* aad_len, uint16_t byte_idx, uint8_t* aad) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -1203,6 +1354,22 @@ int32_t Crypto_TM_Parse_Mac_Prep_AAD(uint8_t sa_service_type, uint8_t* p_ingest, return status; } +/** + * @brief Function: Crypto_TM_Do_Decrypt_AEAD + * Performs decryption on AEAD Authentication, Encryption, and Authenticated Encryption + * @param sa_service_type: uint8_t + * @param p_ingest: uint8_t* + * @param p_new_dec_frame: uint8_t* + * @param byte_idx: uint16_t + * @param pdu_len: uint16_t + * @param ekp: crypto_key_t* + * @param sa_ptr: SecurityAssociation_t* + * @param iv_loc: uint8_t + * @param mac_loc: int + * @param aad_len: uint16_t + * @param aad: uint8_t* + * @return int32_t: Success/Failure +*/ int32_t Crypto_TM_Do_Decrypt_AEAD(uint8_t sa_service_type, uint8_t* p_ingest, uint8_t* p_new_dec_frame, uint16_t byte_idx, uint16_t pdu_len, crypto_key_t* ekp, SecurityAssociation_t* sa_ptr, uint8_t iv_loc, int mac_loc, uint16_t aad_len, uint8_t* aad) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -1246,6 +1413,23 @@ int32_t Crypto_TM_Do_Decrypt_AEAD(uint8_t sa_service_type, uint8_t* p_ingest, ui return status; } +/** + * @brief Function: Crypto_TM_Do_Decrypt_NONAEAD + * Performs decryption on NON AEAD Encryption and Authenticated Encryption + * @param sa_service_type: uint8_t + * @param pdu_len: uint16_t + * @param p_new_dec_frame: uint8_t* + * @param byte_idx: uint16_t + * @param p_ingest: uint8_t* + * @param akp: crypto_key_t* + * @param ekp: crypto_key_t* + * @param sa_ptr: SecurityAssociation_t* + * @param iv_loc: uint8_t + * @param mac_loc: int + * @param aad_len: uint16_t + * @param aad: uint8_t + * @return int32_t: Success/Failure +*/ int32_t Crypto_TM_Do_Decrypt_NONAEAD(uint8_t sa_service_type, uint16_t pdu_len, uint8_t* p_new_dec_frame, uint16_t byte_idx, uint8_t* p_ingest, crypto_key_t* akp, crypto_key_t* ekp, SecurityAssociation_t* sa_ptr, uint8_t iv_loc, int mac_loc, uint16_t aad_len, uint8_t* aad) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -1312,6 +1496,15 @@ int32_t Crypto_TM_Do_Decrypt_NONAEAD(uint8_t sa_service_type, uint16_t pdu_len, return status; } +/** + * @brief Function: Crypto_TM_Calc_PDU_MAC + * Calculates the PDU MAC + * @param pdu_len: uint16_t* + * @param byte_idx: uint16_t + * @param sa_ptr: SecurityAssociation_t* + * @param mac_loc: int* + * @return int32_t: Success/Failure +*/ void Crypto_TM_Calc_PDU_MAC(uint16_t* pdu_len, uint16_t byte_idx, SecurityAssociation_t* sa_ptr, int* mac_loc) { *pdu_len = current_managed_parameters->max_frame_size - (byte_idx) - sa_ptr->stmacf_len; @@ -1331,6 +1524,26 @@ void Crypto_TM_Calc_PDU_MAC(uint16_t* pdu_len, uint16_t byte_idx, SecurityAssoci } } +/** + * @brief Function: Crypto_TM_Do_Decrypt + * Parent TM Decryption Functionality + * @param sa_service_type: uint8_t + * @param sa_ptr: SecurityAssociation_t* + * @param ecs_is_aead_algorithm: uint8_t + * @param byte_idx: uint16_t + * @param p_new_dec_frame: uint8_t* + * @param pdu_len: uint16_t + * @param p_ingest: uint8_t* + * @param ekp: crypto_key_t* + * @param akp: crypto_key_t* + * @param iv_loc: uint8_t + * @param mac_loc: int + * @param aad_len: uint16_t + * @param aad: uint8_t* + * @param pp_processed_frame: uint8_t** + * @param p_decrypted_length: uint16_t* + * @return int32_t: Success/Failure +*/ int32_t Crypto_TM_Do_Decrypt(uint8_t sa_service_type, SecurityAssociation_t* sa_ptr, uint8_t ecs_is_aead_algorithm, uint16_t byte_idx, uint8_t* p_new_dec_frame, uint16_t pdu_len, uint8_t* p_ingest, crypto_key_t* ekp, crypto_key_t* akp, uint8_t iv_loc, int mac_loc, uint16_t aad_len, uint8_t* aad, uint8_t** pp_processed_frame, uint16_t* p_decrypted_length) { int32_t status = CRYPTO_LIB_SUCCESS; @@ -1381,6 +1594,14 @@ int32_t Crypto_TM_Do_Decrypt(uint8_t sa_service_type, SecurityAssociation_t* sa_ return status; } +/** + * @brief Function: Crypto_TM_Process_Debug_Print + * TM Process Helper Debug Print + * Displays Index/data location start, Data Size, OCF Location, FECF Location + * @param byte_idx: uint16_t + * @param pdu_len: uint16_t + * @param sa_ptr: SecurityAssociation_t* +*/ void Crypto_TM_Process_Debug_Print(uint16_t byte_idx, uint16_t pdu_len, SecurityAssociation_t* sa_ptr) { #ifdef TM_DEBUG From 826c275a15472b63f3a90d573acc93984213814b Mon Sep 17 00:00:00 2001 From: Robert Brown Date: Wed, 3 Apr 2024 17:44:44 +0000 Subject: [PATCH 5/6] [nasa/cryptolib#231][nasa/cryptolib#230] Unused Variable Fix --- src/core/crypto_tm.c | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/src/core/crypto_tm.c b/src/core/crypto_tm.c index 4f63c44f..9dd592b1 100644 --- a/src/core/crypto_tm.c +++ b/src/core/crypto_tm.c @@ -607,6 +607,11 @@ int32_t Crypto_TM_Do_Encrypt(uint8_t sa_service_type, SecurityAssociation_t* sa_ **/ void Crypto_TM_ApplySecurity_Debug_Print(uint16_t idx, uint16_t pdu_len, SecurityAssociation_t* sa_ptr) { + // Fix to ignore warnings + idx = idx; + pdu_len = pdu_len; + sa_ptr = sa_ptr; + #ifdef TM_DEBUG printf(KYEL "Data location starts at: %d\n" RESET, idx); printf(KYEL "Data size is: %d\n" RESET, pdu_len); @@ -1604,6 +1609,10 @@ int32_t Crypto_TM_Do_Decrypt(uint8_t sa_service_type, SecurityAssociation_t* sa_ */ void Crypto_TM_Process_Debug_Print(uint16_t byte_idx, uint16_t pdu_len, SecurityAssociation_t* sa_ptr) { + // Fix for variable warnings + byte_idx = byte_idx; + pdu_len = pdu_len; + sa_ptr = sa_ptr; #ifdef TM_DEBUG printf(KYEL "Index / data location starts at: %d\n" RESET, byte_idx); printf(KYEL "Data size is: %d\n" RESET, pdu_len); From 6588b7985baf4b20bde38929724166112f40224d Mon Sep 17 00:00:00 2001 From: Robert Brown Date: Thu, 4 Apr 2024 15:56:21 +0000 Subject: [PATCH 6/6] [nasa/cryptolib#230] Pull request fixes. Single return statements. --- src/core/crypto_tm.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/core/crypto_tm.c b/src/core/crypto_tm.c index 9dd592b1..e7598ed1 100644 --- a/src/core/crypto_tm.c +++ b/src/core/crypto_tm.c @@ -35,16 +35,14 @@ int32_t Crypto_TM_Sanity_Check(uint8_t* pTfBuffer) // Passed a null, return an error if (!pTfBuffer) { - return CRYPTO_LIB_ERR_NULL_BUFFER; - return status; + status = CRYPTO_LIB_ERR_NULL_BUFFER; } - if ((crypto_config.init_status == UNITIALIZED) || (mc_if == NULL) || (sa_if == NULL)) + if ((status == CRYPTO_LIB_SUCCESS) && ((crypto_config.init_status == UNITIALIZED) || (mc_if == NULL) || (sa_if == NULL))) { printf(KRED "ERROR: CryptoLib Configuration Not Set! -- CRYPTO_LIB_ERR_NO_CONFIG, Will Exit\n" RESET); status = CRYPTO_LIB_ERR_NO_CONFIG; // Can't mc_log since it's not configured - return status; // return immediately so a NULL crypto_config is not dereferenced later } return status; } @@ -81,8 +79,10 @@ int32_t Crypto_TM_Determine_SA_Service_Type(uint8_t* sa_service_type, SecurityAs // Leaving for now as it would be cleaner in SA to have an association enum returned I believe printf(KRED "Error: SA Service Type is not defined! \n" RESET); status = CRYPTO_LIB_ERROR; + } + if(status != CRYPTO_LIB_SUCCESS) + { mc_if->mc_log(status); - return status; } return status; }