|  | /* BEGIN_HEADER */ | 
|  | #include "mbedtls/ccm.h" | 
|  | /* END_HEADER */ | 
|  |  | 
|  | /* BEGIN_DEPENDENCIES | 
|  | * depends_on:MBEDTLS_CCM_C | 
|  | * END_DEPENDENCIES | 
|  | */ | 
|  |  | 
|  | /* BEGIN_CASE depends_on:MBEDTLS_SELF_TEST:MBEDTLS_AES_C */ | 
|  | void mbedtls_ccm_self_test( ) | 
|  | { | 
|  | TEST_ASSERT( mbedtls_ccm_self_test( 1 ) == 0 ); | 
|  | } | 
|  | /* END_CASE */ | 
|  |  | 
|  | /* BEGIN_CASE */ | 
|  | void mbedtls_ccm_setkey( int cipher_id, int key_size, int result ) | 
|  | { | 
|  | mbedtls_ccm_context ctx; | 
|  | unsigned char key[32]; | 
|  | int ret; | 
|  |  | 
|  | mbedtls_ccm_init( &ctx ); | 
|  |  | 
|  | memset( key, 0x2A, sizeof( key ) ); | 
|  | TEST_ASSERT( (unsigned) key_size <= 8 * sizeof( key ) ); | 
|  |  | 
|  | ret = mbedtls_ccm_setkey( &ctx, cipher_id, key, key_size ); | 
|  | TEST_ASSERT( ret == result ); | 
|  |  | 
|  | exit: | 
|  | mbedtls_ccm_free( &ctx ); | 
|  | } | 
|  | /* END_CASE */ | 
|  |  | 
|  | /* BEGIN_CASE depends_on:MBEDTLS_AES_C */ | 
|  | void ccm_lengths( int msg_len, int iv_len, int add_len, int tag_len, int res ) | 
|  | { | 
|  | mbedtls_ccm_context ctx; | 
|  | unsigned char key[16]; | 
|  | unsigned char msg[10]; | 
|  | unsigned char iv[14]; | 
|  | unsigned char add[10]; | 
|  | unsigned char out[10]; | 
|  | unsigned char tag[18]; | 
|  | int decrypt_ret; | 
|  |  | 
|  | mbedtls_ccm_init( &ctx ); | 
|  |  | 
|  | memset( key, 0, sizeof( key ) ); | 
|  | memset( msg, 0, sizeof( msg ) ); | 
|  | memset( iv, 0, sizeof( iv ) ); | 
|  | memset( add, 0, sizeof( add ) ); | 
|  | memset( out, 0, sizeof( out ) ); | 
|  | memset( tag, 0, sizeof( tag ) ); | 
|  |  | 
|  | TEST_ASSERT( mbedtls_ccm_setkey( &ctx, MBEDTLS_CIPHER_ID_AES, | 
|  | key, 8 * sizeof( key ) ) == 0 ); | 
|  |  | 
|  | TEST_ASSERT( mbedtls_ccm_encrypt_and_tag( &ctx, msg_len, iv, iv_len, add, add_len, | 
|  | msg, out, tag, tag_len ) == res ); | 
|  |  | 
|  | decrypt_ret = mbedtls_ccm_auth_decrypt( &ctx, msg_len, iv, iv_len, add, add_len, | 
|  | msg, out, tag, tag_len ); | 
|  |  | 
|  | if( res == 0 ) | 
|  | TEST_ASSERT( decrypt_ret == MBEDTLS_ERR_CCM_AUTH_FAILED ); | 
|  | else | 
|  | TEST_ASSERT( decrypt_ret == res ); | 
|  |  | 
|  | exit: | 
|  | mbedtls_ccm_free( &ctx ); | 
|  | } | 
|  | /* END_CASE */ | 
|  |  | 
|  | /* BEGIN_CASE */ | 
|  | void mbedtls_ccm_encrypt_and_tag( int cipher_id, | 
|  | char *key_hex, char *msg_hex, | 
|  | char *iv_hex, char *add_hex, | 
|  | char *result_hex ) | 
|  | { | 
|  | unsigned char key[32]; | 
|  | unsigned char msg[50]; | 
|  | unsigned char iv[13]; | 
|  | unsigned char add[32]; | 
|  | unsigned char result[50]; | 
|  | mbedtls_ccm_context ctx; | 
|  | size_t key_len, msg_len, iv_len, add_len, tag_len, result_len; | 
|  |  | 
|  | mbedtls_ccm_init( &ctx ); | 
|  |  | 
|  | memset( key, 0x00, sizeof( key ) ); | 
|  | memset( msg, 0x00, sizeof( msg ) ); | 
|  | memset( iv, 0x00, sizeof( iv ) ); | 
|  | memset( add, 0x00, sizeof( add ) ); | 
|  | memset( result, 0x00, sizeof( result ) ); | 
|  |  | 
|  | key_len = unhexify( key, key_hex ); | 
|  | msg_len = unhexify( msg, msg_hex ); | 
|  | iv_len = unhexify( iv, iv_hex ); | 
|  | add_len = unhexify( add, add_hex ); | 
|  | result_len = unhexify( result, result_hex ); | 
|  | tag_len = result_len - msg_len; | 
|  |  | 
|  | TEST_ASSERT( mbedtls_ccm_setkey( &ctx, cipher_id, key, key_len * 8 ) == 0 ); | 
|  |  | 
|  | /* Test with input == output */ | 
|  | TEST_ASSERT( mbedtls_ccm_encrypt_and_tag( &ctx, msg_len, iv, iv_len, add, add_len, | 
|  | msg, msg, msg + msg_len, tag_len ) == 0 ); | 
|  |  | 
|  | TEST_ASSERT( memcmp( msg, result, result_len ) == 0 ); | 
|  |  | 
|  | /* Check we didn't write past the end */ | 
|  | TEST_ASSERT( msg[result_len] == 0 && msg[result_len + 1] == 0 ); | 
|  |  | 
|  | exit: | 
|  | mbedtls_ccm_free( &ctx ); | 
|  | } | 
|  | /* END_CASE */ | 
|  |  | 
|  | /* BEGIN_CASE */ | 
|  | void mbedtls_ccm_auth_decrypt( int cipher_id, | 
|  | char *key_hex, char *msg_hex, | 
|  | char *iv_hex, char *add_hex, | 
|  | int tag_len, char *result_hex ) | 
|  | { | 
|  | unsigned char key[32]; | 
|  | unsigned char msg[50]; | 
|  | unsigned char iv[13]; | 
|  | unsigned char add[32]; | 
|  | unsigned char tag[16]; | 
|  | unsigned char result[50]; | 
|  | mbedtls_ccm_context ctx; | 
|  | size_t key_len, msg_len, iv_len, add_len, result_len; | 
|  | int ret; | 
|  |  | 
|  | mbedtls_ccm_init( &ctx ); | 
|  |  | 
|  | memset( key, 0x00, sizeof( key ) ); | 
|  | memset( msg, 0x00, sizeof( msg ) ); | 
|  | memset( iv, 0x00, sizeof( iv ) ); | 
|  | memset( add, 0x00, sizeof( add ) ); | 
|  | memset( tag, 0x00, sizeof( tag ) ); | 
|  | memset( result, 0x00, sizeof( result ) ); | 
|  |  | 
|  | key_len = unhexify( key, key_hex ); | 
|  | msg_len = unhexify( msg, msg_hex ); | 
|  | iv_len = unhexify( iv, iv_hex ); | 
|  | add_len = unhexify( add, add_hex ); | 
|  | msg_len -= tag_len; | 
|  | memcpy( tag, msg + msg_len, tag_len ); | 
|  |  | 
|  | if( strcmp( "FAIL", result_hex ) == 0 ) | 
|  | { | 
|  | ret = MBEDTLS_ERR_CCM_AUTH_FAILED; | 
|  | result_len = -1; | 
|  | } | 
|  | else | 
|  | { | 
|  | ret = 0; | 
|  | result_len = unhexify( result, result_hex ); | 
|  | } | 
|  |  | 
|  | TEST_ASSERT( mbedtls_ccm_setkey( &ctx, cipher_id, key, key_len * 8 ) == 0 ); | 
|  |  | 
|  | /* Test with input == output */ | 
|  | TEST_ASSERT( mbedtls_ccm_auth_decrypt( &ctx, msg_len, iv, iv_len, add, add_len, | 
|  | msg, msg, msg + msg_len, tag_len ) == ret ); | 
|  |  | 
|  | if( ret == 0 ) | 
|  | { | 
|  | TEST_ASSERT( memcmp( msg, result, result_len ) == 0 ); | 
|  | } | 
|  | else | 
|  | { | 
|  | size_t i; | 
|  |  | 
|  | for( i = 0; i < msg_len; i++ ) | 
|  | TEST_ASSERT( msg[i] == 0 ); | 
|  | } | 
|  |  | 
|  | /* Check we didn't write past the end (where the original tag is) */ | 
|  | TEST_ASSERT( memcmp( msg + msg_len, tag, tag_len ) == 0 ); | 
|  |  | 
|  | exit: | 
|  | mbedtls_ccm_free( &ctx ); | 
|  | } | 
|  | /* END_CASE */ |