From 3899eb22e0f32b5d1811e7495f0e6cbe6fc68245 Mon Sep 17 00:00:00 2001 From: "D. Cody Cutright" Date: Mon, 7 Mar 2022 13:44:43 -0500 Subject: [PATCH 1/6] Adjust IV memcpy block to be reliant on SA configuration --- src/src_main/crypto_tc.c | 26 ++++++++++++-------------- 1 file changed, 12 insertions(+), 14 deletions(-) diff --git a/src/src_main/crypto_tc.c b/src/src_main/crypto_tc.c index f7ca974a..6f476637 100644 --- a/src/src_main/crypto_tc.c +++ b/src/src_main/crypto_tc.c @@ -318,24 +318,22 @@ int32_t Crypto_TC_ApplySecurity(const uint8_t* p_in_frame, const uint16_t in_fra index += 2; // Set initialization vector if specified - if ((sa_service_type == SA_AUTHENTICATION) || (sa_service_type == SA_AUTHENTICATED_ENCRYPTION) || - (sa_service_type == SA_ENCRYPTION)) - { #ifdef SA_DEBUG - printf(KYEL "Using IV value:\n\t"); - for (i = 0; i < sa_ptr->shivf_len; i++) + if (sa_ptr->shivf_len > 0) { - printf("%02x", *(sa_ptr->iv + i)); + printf(KYEL "Using IV value:\n\t"); + for (i = 0; i < sa_ptr->shivf_len; i++) + { + printf("%02x", *(sa_ptr->iv + i)); + } + printf("\n" RESET); } - printf("\n" RESET); #endif - - for (i = 0; i < sa_ptr->shivf_len; i++) - { - // Copy in IV from SA - *(p_new_enc_frame + index) = *(sa_ptr->iv + i); - index++; - } + for (i = 0; i < sa_ptr->shivf_len; i++) + { + // Copy in IV from SA + *(p_new_enc_frame + index) = *(sa_ptr->iv + i); + index++; } // Set anti-replay sequence number if specified From 7388cf79db5cc6b406b752eb4b2c3f69f8b344c3 Mon Sep 17 00:00:00 2001 From: "D. Cody Cutright" Date: Mon, 7 Mar 2022 15:44:34 -0500 Subject: [PATCH 2/6] Fix SA to have 2 byte ARSN, not an IV; Add encrypt/decrypt UT for plaintext --- src/src_main/crypto_tc.c | 23 ------------- src/src_main/sadb_routine_inmemory.template.c | 7 ++-- util/src_util/et_dt_validation.c | 32 +++++++++++++++++++ 3 files changed, 36 insertions(+), 26 deletions(-) diff --git a/src/src_main/crypto_tc.c b/src/src_main/crypto_tc.c index 6f476637..1da48989 100644 --- a/src/src_main/crypto_tc.c +++ b/src/src_main/crypto_tc.c @@ -343,8 +343,6 @@ int32_t Crypto_TC_ApplySecurity(const uint8_t* p_in_frame, const uint16_t in_fra ** for an SA, the Sequence Number field shall be zero octets in length. ** Reference CCSDS 3550b1 */ - // TODO: Workout ARSN vs SN and when they may - // or may not be the same or different field for (i = 0; i < sa_ptr->shsnf_len; i++) { // Copy in ARSN from SA @@ -386,27 +384,6 @@ int32_t Crypto_TC_ApplySecurity(const uint8_t* p_in_frame, const uint16_t in_fra tf_payload_len = temp_tc_header.fl - TC_FRAME_HEADER_SIZE - segment_hdr_len - fecf_len + 1; memcpy((p_new_enc_frame + index), (p_in_frame + TC_FRAME_HEADER_SIZE + segment_hdr_len), tf_payload_len); - /* - ** Begin Security Trailer Fields - */ - - // Set MAC Field if present - /* - ** May be present and unused if switching between clear and authenticated - ** CCSDS 3550b1 4.1.2.3 - */ - // By leaving MAC as zeros, can use index for encryption output - // for (i=0; i < temp_SA.stmacf_len; i++) - // { - // // Temp fill MAC - // *(p_new_enc_frame + index) = 0x00; - // index++; - // } - - /* - ** End Security Trailer Fields - */ - /* ** Begin Authentication / Encryption */ diff --git a/src/src_main/sadb_routine_inmemory.template.c b/src/src_main/sadb_routine_inmemory.template.c index 9cb63a5f..d21e9dd5 100644 --- a/src/src_main/sadb_routine_inmemory.template.c +++ b/src/src_main/sadb_routine_inmemory.template.c @@ -79,9 +79,10 @@ int32_t sadb_config(void) sa[1].sa_state = SA_OPERATIONAL; sa[1].est = 0; sa[1].ast = 0; - sa[1].shivf_len = 2; - sa[1].iv = (uint8_t*) calloc(1, sa[1].shivf_len * sizeof(uint8_t)); - sa[1].arsn_len = 1; + sa[1].shivf_len = 0; + sa[1].shsnf_len = 2; + sa[1].arsn_len = 2; + sa[1].arsn = (uint8_t*) calloc(1, sa[1].arsn_len * sizeof(uint8_t)); sa[1].arsnw_len = 1; sa[1].arsnw = 5; sa[1].gvcid_tc_blk.tfvn = 0; diff --git a/util/src_util/et_dt_validation.c b/util/src_util/et_dt_validation.c index 34355092..b91f0527 100644 --- a/util/src_util/et_dt_validation.c +++ b/util/src_util/et_dt_validation.c @@ -1913,4 +1913,36 @@ UTEST(NIST_DEC_CMAC_VALIDATION, AES_CMAC_256_PT_128_TEST_1) // sadb_routine->sadb_close(); } +UTEST(PLAINTEXT, ENCRYPT_DECRYPT) +{ + int32_t status = CRYPTO_LIB_ERROR; + uint8_t* ptr_enc_frame = NULL; + uint16_t enc_frame_len = 0; + // Setup & Initialize CryptoLib + Crypto_Config_CryptoLib(SADB_TYPE_INMEMORY, CRYPTOGRAPHY_TYPE_LIBGCRYPT, CRYPTO_TC_CREATE_FECF_TRUE, TC_PROCESS_SDLS_PDUS_TRUE, TC_HAS_PUS_HDR, + TC_IGNORE_SA_STATE_TRUE, TC_IGNORE_ANTI_REPLAY_TRUE, TC_UNIQUE_SA_PER_MAP_ID_FALSE, + TC_CHECK_FECF_TRUE, 0x3F); + Crypto_Config_Add_Gvcid_Managed_Parameter(0, 0x0003, 0, TC_HAS_FECF, TC_NO_SEGMENT_HDRS); + Crypto_Config_Add_Gvcid_Managed_Parameter(0, 0x0003, 1, TC_HAS_FECF, TC_NO_SEGMENT_HDRS); + Crypto_Init(); + + char* jpl_frame_pt_h = "2003001c00ff000100001880d03e000a197f0b000300020093d4ba21c4555555555555"; + uint8_t* jpl_frame_pt_b = NULL; + int jpl_frame_pt_len = 0; + TC_t* tc_sdls_processed_frame; + tc_sdls_processed_frame = calloc(1, sizeof(uint8_t) * TC_SIZE); + + // Convert input jpl frame + hex_conversion(jpl_frame_pt_h, (char**) &jpl_frame_pt_b, &jpl_frame_pt_len); + + // Apply, save the generated frame + status = Crypto_TC_ApplySecurity(jpl_frame_pt_b, jpl_frame_pt_len, &ptr_enc_frame, &enc_frame_len); + ASSERT_EQ(status, CRYPTO_LIB_SUCCESS); + + // // Process the generated frame + int len = (int)enc_frame_len; + status = Crypto_TC_ProcessSecurity(ptr_enc_frame, &len, tc_sdls_processed_frame); + ASSERT_EQ(status, CRYPTO_LIB_SUCCESS); +} + UTEST_MAIN(); \ No newline at end of file From 2d26c544818276506b132a75775c02731e7aec9f Mon Sep 17 00:00:00 2001 From: "D. Cody Cutright" Date: Tue, 8 Mar 2022 14:06:50 -0500 Subject: [PATCH 3/6] Add Encrypt_decrypt test description --- util/src_util/et_dt_validation.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/util/src_util/et_dt_validation.c b/util/src_util/et_dt_validation.c index b91f0527..ddec39e8 100644 --- a/util/src_util/et_dt_validation.c +++ b/util/src_util/et_dt_validation.c @@ -1913,6 +1913,9 @@ UTEST(NIST_DEC_CMAC_VALIDATION, AES_CMAC_256_PT_128_TEST_1) // sadb_routine->sadb_close(); } +/** + * @brief Unit Test: Encrypts a frame, then decrypts the output to ensure the reverse doesn't error + **/ UTEST(PLAINTEXT, ENCRYPT_DECRYPT) { int32_t status = CRYPTO_LIB_ERROR; From 3b2c0ef5c12c61de1821a13a45443d4f694b2fa3 Mon Sep 17 00:00:00 2001 From: "D. Cody Cutright" Date: Tue, 8 Mar 2022 16:42:56 -0500 Subject: [PATCH 4/6] Add additional checks for invalid SA that do not cause segfault, UTs for same --- include/crypto_error.h | 1 + src/src_main/crypto_tc.c | 32 ++++++++++++++++++++--------- util/src_util/ut_crypto.c | 42 +++++++++++++++++++++++++++++++++++++++ 3 files changed, 66 insertions(+), 9 deletions(-) diff --git a/include/crypto_error.h b/include/crypto_error.h index 1c771098..e7da9c32 100644 --- a/include/crypto_error.h +++ b/include/crypto_error.h @@ -76,5 +76,6 @@ #define CRYPTO_LIB_ERR_IV_OUTSIDE_WINDOW (-23) #define CRYPTO_LIB_ERR_NULL_ARSN (-24) #define CRYPTO_LIB_ERR_NULL_SA (-25) +#define CRYPTO_ERR_INVALID_SA_CONFIGURATION (-26) #endif //_crypto_error_h_ diff --git a/src/src_main/crypto_tc.c b/src/src_main/crypto_tc.c index 1da48989..6e213cfc 100644 --- a/src/src_main/crypto_tc.c +++ b/src/src_main/crypto_tc.c @@ -319,7 +319,7 @@ int32_t Crypto_TC_ApplySecurity(const uint8_t* p_in_frame, const uint16_t in_fra // Set initialization vector if specified #ifdef SA_DEBUG - if (sa_ptr->shivf_len > 0) + if (sa_ptr->shivf_len > 0 && sa_ptr->iv != NULL) { printf(KYEL "Using IV value:\n\t"); for (i = 0; i < sa_ptr->shivf_len; i++) @@ -329,11 +329,18 @@ int32_t Crypto_TC_ApplySecurity(const uint8_t* p_in_frame, const uint16_t in_fra printf("\n" RESET); } #endif - for (i = 0; i < sa_ptr->shivf_len; i++) + if (sa_ptr->shivf_len > 0 && sa_ptr->iv == NULL) { - // Copy in IV from SA - *(p_new_enc_frame + index) = *(sa_ptr->iv + i); - index++; + return CRYPTO_ERR_INVALID_SA_CONFIGURATION; + } + else + { + for (i = 0; i < sa_ptr->shivf_len; i++) + { + // Copy in IV from SA + *(p_new_enc_frame + index) = *(sa_ptr->iv + i); + index++; + } } // Set anti-replay sequence number if specified @@ -343,11 +350,18 @@ int32_t Crypto_TC_ApplySecurity(const uint8_t* p_in_frame, const uint16_t in_fra ** for an SA, the Sequence Number field shall be zero octets in length. ** Reference CCSDS 3550b1 */ - for (i = 0; i < sa_ptr->shsnf_len; i++) + if ((sa_ptr->shsnf_len > 0 || sa_ptr->arsn_len > 0) && sa_ptr->arsn == NULL) { - // Copy in ARSN from SA - *(p_new_enc_frame + index) = *(sa_ptr->arsn + i); - index++; + return CRYPTO_ERR_INVALID_SA_CONFIGURATION; + } + else + { + for (i = 0; i < sa_ptr->shsnf_len; i++) + { + // Copy in ARSN from SA + *(p_new_enc_frame + index) = *(sa_ptr->arsn + i); + index++; + } } // Set security header padding if specified diff --git a/util/src_util/ut_crypto.c b/util/src_util/ut_crypto.c index ff5d6dcf..318426e8 100644 --- a/util/src_util/ut_crypto.c +++ b/util/src_util/ut_crypto.c @@ -263,4 +263,46 @@ UTEST(CRYPTO_C, EXT_PROC_PDU) ASSERT_EQ(status, CRYPTO_LIB_SUCCESS); } +/** + * @brief Unit Test: Test that an SA set to use IV/ARSN without mallocing doesn't segfault and returns an error + **/ +UTEST(INVALID_SA_CONFIGS, INVALID_IV_ARSN) +{ + int32_t status = CRYPTO_LIB_ERROR; + uint8_t* ptr_enc_frame = NULL; + uint16_t enc_frame_len = 0; + // Setup & Initialize CryptoLib + Crypto_Config_CryptoLib(SADB_TYPE_INMEMORY, CRYPTOGRAPHY_TYPE_LIBGCRYPT, CRYPTO_TC_CREATE_FECF_TRUE, TC_PROCESS_SDLS_PDUS_TRUE, TC_HAS_PUS_HDR, + TC_IGNORE_SA_STATE_TRUE, TC_IGNORE_ANTI_REPLAY_TRUE, TC_UNIQUE_SA_PER_MAP_ID_FALSE, + TC_CHECK_FECF_TRUE, 0x3F); + Crypto_Config_Add_Gvcid_Managed_Parameter(0, 0x0003, 0, TC_HAS_FECF, TC_NO_SEGMENT_HDRS); + Crypto_Config_Add_Gvcid_Managed_Parameter(0, 0x0003, 1, TC_HAS_FECF, TC_NO_SEGMENT_HDRS); + Crypto_Init(); + + char* jpl_frame_pt_h = "2003001c00ff000100001880d03e000a197f0b000300020093d4ba21c4555555555555"; + uint8_t* jpl_frame_pt_b = NULL; + int jpl_frame_pt_len = 0; + + // Expose/setup SAs for testing + SecurityAssociation_t* test_association = NULL; + test_association = malloc(sizeof(SecurityAssociation_t) * sizeof(uint8_t)); + sadb_routine->sadb_get_sa_from_spi(1, &test_association); + + // Convert input jpl frame + hex_conversion(jpl_frame_pt_h, (char**) &jpl_frame_pt_b, &jpl_frame_pt_len); + + // Should fail, as SA will be set to use ARSN, but ARSN pointer is NULL + free(test_association->arsn); + test_association->arsn = NULL; + status = Crypto_TC_ApplySecurity(jpl_frame_pt_b, jpl_frame_pt_len, &ptr_enc_frame, &enc_frame_len); + ASSERT_EQ(CRYPTO_ERR_INVALID_SA_CONFIGURATION, status); + + // Should fail, as SA will be set to use IV, but IV pointer is NULL + free(test_association->iv); + test_association->iv = NULL; + test_association->shivf_len = 12; + status = Crypto_TC_ApplySecurity(jpl_frame_pt_b, jpl_frame_pt_len, &ptr_enc_frame, &enc_frame_len); + ASSERT_EQ(CRYPTO_ERR_INVALID_SA_CONFIGURATION, status); +} + UTEST_MAIN(); \ No newline at end of file From 34ab0206c33a3206f74d88104b1d8f51ec8d2aaa Mon Sep 17 00:00:00 2001 From: "D. Cody Cutright" Date: Tue, 8 Mar 2022 16:47:20 -0500 Subject: [PATCH 5/6] Fix incorrect return code --- src/src_main/crypto_tc.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/src_main/crypto_tc.c b/src/src_main/crypto_tc.c index 2b42d8e7..c81bf212 100644 --- a/src/src_main/crypto_tc.c +++ b/src/src_main/crypto_tc.c @@ -331,7 +331,7 @@ int32_t Crypto_TC_ApplySecurity(const uint8_t* p_in_frame, const uint16_t in_fra #endif if (sa_ptr->shivf_len > 0 && sa_ptr->iv == NULL) { - return CRYPTO_ERR_INVALID_SA_CONFIGURATION; + return CRYPTO_LIB_ERR_INVALID_SA_CONFIGURATION; } else { @@ -352,7 +352,7 @@ int32_t Crypto_TC_ApplySecurity(const uint8_t* p_in_frame, const uint16_t in_fra */ if ((sa_ptr->shsnf_len > 0 || sa_ptr->arsn_len > 0) && sa_ptr->arsn == NULL) { - return CRYPTO_ERR_INVALID_SA_CONFIGURATION; + return CRYPTO_LIB_ERR_INVALID_SA_CONFIGURATION; } else { From 9fec5698548beab7e4c7314dfff81b26a44f816a Mon Sep 17 00:00:00 2001 From: "D. Cody Cutright" Date: Tue, 8 Mar 2022 16:51:14 -0500 Subject: [PATCH 6/6] Missing parenthesis --- util/src_util/ut_crypto.c | 1 + 1 file changed, 1 insertion(+) diff --git a/util/src_util/ut_crypto.c b/util/src_util/ut_crypto.c index 3779c3cf..e1a23bb4 100644 --- a/util/src_util/ut_crypto.c +++ b/util/src_util/ut_crypto.c @@ -320,5 +320,6 @@ UTEST(INVALID_SA_CONFIGS, INVALID_IV_ARSN) test_association->shivf_len = 12; status = Crypto_TC_ApplySecurity(jpl_frame_pt_b, jpl_frame_pt_len, &ptr_enc_frame, &enc_frame_len); ASSERT_EQ(CRYPTO_LIB_ERR_INVALID_SA_CONFIGURATION, status); +} UTEST_MAIN(); \ No newline at end of file