Merge pull request #240 from Ko-/development
Enable 64-bit bignum limbs and add optimized multiplication for Aarch64
diff --git a/include/mbedtls/config.h b/include/mbedtls/config.h
index 95ab1f2..3c1430c 100644
--- a/include/mbedtls/config.h
+++ b/include/mbedtls/config.h
@@ -1007,6 +1007,16 @@
//#define MBEDTLS_SHA256_SMALLER
/**
+ * \def MBEDTLS_SHA512_SMALLER
+ *
+ * Enable an implementation of SHA-512 that has lower ROM footprint but also
+ * lower performance.
+ *
+ * Uncomment to enable the smaller implementation of SHA512.
+ */
+//#define MBEDTLS_SHA512_SMALLER
+
+/**
* \def MBEDTLS_THREADING_ALT
*
* Provide your own alternate threading implementation.
diff --git a/library/bignum.c b/library/bignum.c
index 30757df..5f5df78 100644
--- a/library/bignum.c
+++ b/library/bignum.c
@@ -2426,7 +2426,8 @@
}
if (count++ > 30) {
- return MBEDTLS_ERR_MPI_NOT_ACCEPTABLE;
+ ret = MBEDTLS_ERR_MPI_NOT_ACCEPTABLE;
+ goto cleanup;
}
} while ( mbedtls_mpi_cmp_mpi( &A, &W ) >= 0 ||
diff --git a/library/sha512.c b/library/sha512.c
index bdd20b2..2e2b797 100644
--- a/library/sha512.c
+++ b/library/sha512.c
@@ -92,6 +92,15 @@
}
#endif /* PUT_UINT64_BE */
+#if defined(MBEDTLS_SHA512_SMALLER)
+static void sha512_put_uint64_be( uint64_t n, unsigned char *b, uint8_t i )
+{
+ PUT_UINT64_BE(n, b, i);
+}
+#else
+#define sha512_put_uint64_be PUT_UINT64_BE
+#endif /* MBEDTLS_SHA512_SMALLER */
+
void mbedtls_sha512_init( mbedtls_sha512_context *ctx )
{
SHA512_VALIDATE( ctx != NULL );
@@ -219,7 +228,7 @@
{
int i;
uint64_t temp1, temp2, W[80];
- uint64_t A, B, C, D, E, F, G, H;
+ uint64_t A[8];
SHA512_VALIDATE_RET( ctx != NULL );
SHA512_VALIDATE_RET( (const unsigned char *)data != NULL );
@@ -244,6 +253,28 @@
(d) += temp1; (h) = temp1 + temp2; \
} while( 0 )
+ for( i = 0; i < 8; i++ )
+ A[i] = ctx->state[i];
+
+#if defined(MBEDTLS_SHA512_SMALLER)
+ for( i = 0; i < 80; i++ )
+ {
+ if( i < 16 )
+ {
+ GET_UINT64_BE( W[i], data, i << 3 );
+ }
+ else
+ {
+ W[i] = S1(W[i - 2]) + W[i - 7] +
+ S0(W[i - 15]) + W[i - 16];
+ }
+
+ P( A[0], A[1], A[2], A[3], A[4], A[5], A[6], A[7], W[i], K[i] );
+
+ temp1 = A[7]; A[7] = A[6]; A[6] = A[5]; A[5] = A[4]; A[4] = A[3];
+ A[3] = A[2]; A[2] = A[1]; A[1] = A[0]; A[0] = temp1;
+ }
+#else /* MBEDTLS_SHA512_SMALLER */
for( i = 0; i < 16; i++ )
{
GET_UINT64_BE( W[i], data, i << 3 );
@@ -255,37 +286,23 @@
S0(W[i - 15]) + W[i - 16];
}
- A = ctx->state[0];
- B = ctx->state[1];
- C = ctx->state[2];
- D = ctx->state[3];
- E = ctx->state[4];
- F = ctx->state[5];
- G = ctx->state[6];
- H = ctx->state[7];
i = 0;
-
do
{
- P( A, B, C, D, E, F, G, H, W[i], K[i] ); i++;
- P( H, A, B, C, D, E, F, G, W[i], K[i] ); i++;
- P( G, H, A, B, C, D, E, F, W[i], K[i] ); i++;
- P( F, G, H, A, B, C, D, E, W[i], K[i] ); i++;
- P( E, F, G, H, A, B, C, D, W[i], K[i] ); i++;
- P( D, E, F, G, H, A, B, C, W[i], K[i] ); i++;
- P( C, D, E, F, G, H, A, B, W[i], K[i] ); i++;
- P( B, C, D, E, F, G, H, A, W[i], K[i] ); i++;
+ P( A[0], A[1], A[2], A[3], A[4], A[5], A[6], A[7], W[i], K[i] ); i++;
+ P( A[7], A[0], A[1], A[2], A[3], A[4], A[5], A[6], W[i], K[i] ); i++;
+ P( A[6], A[7], A[0], A[1], A[2], A[3], A[4], A[5], W[i], K[i] ); i++;
+ P( A[5], A[6], A[7], A[0], A[1], A[2], A[3], A[4], W[i], K[i] ); i++;
+ P( A[4], A[5], A[6], A[7], A[0], A[1], A[2], A[3], W[i], K[i] ); i++;
+ P( A[3], A[4], A[5], A[6], A[7], A[0], A[1], A[2], W[i], K[i] ); i++;
+ P( A[2], A[3], A[4], A[5], A[6], A[7], A[0], A[1], W[i], K[i] ); i++;
+ P( A[1], A[2], A[3], A[4], A[5], A[6], A[7], A[0], W[i], K[i] ); i++;
}
while( i < 80 );
+#endif /* MBEDTLS_SHA512_SMALLER */
- ctx->state[0] += A;
- ctx->state[1] += B;
- ctx->state[2] += C;
- ctx->state[3] += D;
- ctx->state[4] += E;
- ctx->state[5] += F;
- ctx->state[6] += G;
- ctx->state[7] += H;
+ for( i = 0; i < 8; i++ )
+ ctx->state[i] += A[i];
return( 0 );
}
@@ -403,8 +420,8 @@
| ( ctx->total[1] << 3 );
low = ( ctx->total[0] << 3 );
- PUT_UINT64_BE( high, ctx->buffer, 112 );
- PUT_UINT64_BE( low, ctx->buffer, 120 );
+ sha512_put_uint64_be( high, ctx->buffer, 112 );
+ sha512_put_uint64_be( low, ctx->buffer, 120 );
if( ( ret = mbedtls_internal_sha512_process( ctx, ctx->buffer ) ) != 0 )
return( ret );
@@ -412,17 +429,17 @@
/*
* Output final state
*/
- PUT_UINT64_BE( ctx->state[0], output, 0 );
- PUT_UINT64_BE( ctx->state[1], output, 8 );
- PUT_UINT64_BE( ctx->state[2], output, 16 );
- PUT_UINT64_BE( ctx->state[3], output, 24 );
- PUT_UINT64_BE( ctx->state[4], output, 32 );
- PUT_UINT64_BE( ctx->state[5], output, 40 );
+ sha512_put_uint64_be( ctx->state[0], output, 0 );
+ sha512_put_uint64_be( ctx->state[1], output, 8 );
+ sha512_put_uint64_be( ctx->state[2], output, 16 );
+ sha512_put_uint64_be( ctx->state[3], output, 24 );
+ sha512_put_uint64_be( ctx->state[4], output, 32 );
+ sha512_put_uint64_be( ctx->state[5], output, 40 );
if( ctx->is384 == 0 )
{
- PUT_UINT64_BE( ctx->state[6], output, 48 );
- PUT_UINT64_BE( ctx->state[7], output, 56 );
+ sha512_put_uint64_be( ctx->state[6], output, 48 );
+ sha512_put_uint64_be( ctx->state[7], output, 56 );
}
return( 0 );
diff --git a/library/version_features.c b/library/version_features.c
index cd75cc0..5404d79 100644
--- a/library/version_features.c
+++ b/library/version_features.c
@@ -408,6 +408,9 @@
#if defined(MBEDTLS_SHA256_SMALLER)
"MBEDTLS_SHA256_SMALLER",
#endif /* MBEDTLS_SHA256_SMALLER */
+#if defined(MBEDTLS_SHA512_SMALLER)
+ "MBEDTLS_SHA512_SMALLER",
+#endif /* MBEDTLS_SHA512_SMALLER */
#if defined(MBEDTLS_THREADING_ALT)
"MBEDTLS_THREADING_ALT",
#endif /* MBEDTLS_THREADING_ALT */
diff --git a/programs/test/query_config.c b/programs/test/query_config.c
index 4f28009..da3dfb0 100644
--- a/programs/test/query_config.c
+++ b/programs/test/query_config.c
@@ -1116,6 +1116,14 @@
}
#endif /* MBEDTLS_SHA256_SMALLER */
+#if defined(MBEDTLS_SHA512_SMALLER)
+ if( strcmp( "MBEDTLS_SHA512_SMALLER", config ) == 0 )
+ {
+ MACRO_EXPANSION_TO_STR( MBEDTLS_SHA512_SMALLER );
+ return( 0 );
+ }
+#endif /* MBEDTLS_SHA512_SMALLER */
+
#if defined(MBEDTLS_THREADING_ALT)
if( strcmp( "MBEDTLS_THREADING_ALT", config ) == 0 )
{
diff --git a/tests/suites/test_suite_cipher.aes.data b/tests/suites/test_suite_cipher.aes.data
index c42fc79..6293408 100644
--- a/tests/suites/test_suite_cipher.aes.data
+++ b/tests/suites/test_suite_cipher.aes.data
@@ -1,6 +1,10 @@
-Decrypt empty buffer
+AES-128 CBC - Decrypt empty buffer
depends_on:MBEDTLS_AES_C:MBEDTLS_CIPHER_MODE_CBC:MBEDTLS_CIPHER_PADDING_PKCS7
-dec_empty_buf:MBEDTLS_CIPHER_AES_128_CBC
+dec_empty_buf:MBEDTLS_CIPHER_AES_128_CBC:0:0
+
+AES-128 XTS - Decrypt empty buffer
+depends_on:MBEDTLS_AES_C:MBEDTLS_CIPHER_MODE_XTS
+dec_empty_buf:MBEDTLS_CIPHER_AES_128_XTS:MBEDTLS_ERR_AES_INVALID_INPUT_LENGTH:0
AES-128 CBC - Encrypt and decrypt 0 bytes with PKCS7 padding
depends_on:MBEDTLS_AES_C:MBEDTLS_CIPHER_MODE_CBC:MBEDTLS_CIPHER_PADDING_PKCS7
diff --git a/tests/suites/test_suite_cipher.arc4.data b/tests/suites/test_suite_cipher.arc4.data
index 6e69b81..adeed83 100644
--- a/tests/suites/test_suite_cipher.arc4.data
+++ b/tests/suites/test_suite_cipher.arc4.data
@@ -1,3 +1,7 @@
+ARC4 Decrypt empty buffer
+depends_on:MBEDTLS_ARC4_C
+dec_empty_buf:MBEDTLS_CIPHER_ARC4_128:0:0
+
ARC4 Encrypt and decrypt 0 bytes
depends_on:MBEDTLS_ARC4_C
enc_dec_buf:MBEDTLS_CIPHER_ARC4_128:"ARC4-128":128:0:-1
diff --git a/tests/suites/test_suite_cipher.aria.data b/tests/suites/test_suite_cipher.aria.data
new file mode 100644
index 0000000..2c50a21
--- /dev/null
+++ b/tests/suites/test_suite_cipher.aria.data
@@ -0,0 +1,3 @@
+Aria CBC Decrypt empty buffer
+depends_on:MBEDTLS_ARIA_C:MBEDTLS_CIPHER_MODE_CBC
+dec_empty_buf:MBEDTLS_CIPHER_ARIA_128_CBC:0:0
diff --git a/tests/suites/test_suite_cipher.blowfish.data b/tests/suites/test_suite_cipher.blowfish.data
index b94bc47..bbb3934 100644
--- a/tests/suites/test_suite_cipher.blowfish.data
+++ b/tests/suites/test_suite_cipher.blowfish.data
@@ -1,3 +1,7 @@
+BLOWFISH CBC Decrypt empty buffer
+depends_on:MBEDTLS_BLOWFISH_C:MBEDTLS_CIPHER_MODE_CBC:MBEDTLS_CIPHER_PADDING_PKCS7
+dec_empty_buf:MBEDTLS_CIPHER_BLOWFISH_CBC:0:0
+
BLOWFISH Encrypt and decrypt 0 bytes
depends_on:MBEDTLS_BLOWFISH_C:MBEDTLS_CIPHER_MODE_CBC:MBEDTLS_CIPHER_PADDING_PKCS7
enc_dec_buf:MBEDTLS_CIPHER_BLOWFISH_CBC:"BLOWFISH-CBC":128:0:-1
diff --git a/tests/suites/test_suite_cipher.camellia.data b/tests/suites/test_suite_cipher.camellia.data
index e6342da..8fbbbe9 100644
--- a/tests/suites/test_suite_cipher.camellia.data
+++ b/tests/suites/test_suite_cipher.camellia.data
@@ -1,3 +1,7 @@
+CAMELLIA CBC Decrypt empty buffer
+depends_on:MBEDTLS_CAMELLIA_C:MBEDTLS_CIPHER_MODE_CBC:MBEDTLS_CIPHER_PADDING_PKCS7
+dec_empty_buf:MBEDTLS_CIPHER_CAMELLIA_128_CBC:0:0
+
CAMELLIA Encrypt and decrypt 0 bytes
depends_on:MBEDTLS_CAMELLIA_C:MBEDTLS_CIPHER_MODE_CBC:MBEDTLS_CIPHER_PADDING_PKCS7
enc_dec_buf:MBEDTLS_CIPHER_CAMELLIA_128_CBC:"CAMELLIA-128-CBC":128:0:-1
diff --git a/tests/suites/test_suite_cipher.chachapoly.data b/tests/suites/test_suite_cipher.chachapoly.data
index ccd0dfb..8c246ad 100644
--- a/tests/suites/test_suite_cipher.chachapoly.data
+++ b/tests/suites/test_suite_cipher.chachapoly.data
@@ -1,6 +1,6 @@
Decrypt empty buffer
depends_on:MBEDTLS_CHACHAPOLY_C
-dec_empty_buf:MBEDTLS_CIPHER_CHACHA20_POLY1305
+dec_empty_buf:MBEDTLS_CIPHER_CHACHA20_POLY1305:0:0
ChaCha20+Poly1305 Encrypt and decrypt 0 bytes
depends_on:MBEDTLS_CHACHAPOLY_C
diff --git a/tests/suites/test_suite_cipher.des.data b/tests/suites/test_suite_cipher.des.data
index ba9020e..c272a3e 100644
--- a/tests/suites/test_suite_cipher.des.data
+++ b/tests/suites/test_suite_cipher.des.data
@@ -1,3 +1,15 @@
+DES CBC Decrypt empty buffer
+depends_on:MBEDTLS_DES_C:MBEDTLS_CIPHER_MODE_CBC:MBEDTLS_CIPHER_PADDING_PKCS7
+dec_empty_buf:MBEDTLS_CIPHER_DES_CBC:0:0
+
+DES EDE CBC Decrypt empty buffer
+depends_on:MBEDTLS_DES_C:MBEDTLS_CIPHER_MODE_CBC:MBEDTLS_CIPHER_PADDING_PKCS7
+dec_empty_buf:MBEDTLS_CIPHER_DES_EDE_CBC:0:0
+
+DES EDE3 CBC Decrypt empty buffer
+depends_on:MBEDTLS_DES_C:MBEDTLS_CIPHER_MODE_CBC:MBEDTLS_CIPHER_PADDING_PKCS7
+dec_empty_buf:MBEDTLS_CIPHER_DES_EDE3_CBC:0:0
+
DES Encrypt and decrypt 0 bytes
depends_on:MBEDTLS_DES_C:MBEDTLS_CIPHER_MODE_CBC:MBEDTLS_CIPHER_PADDING_PKCS7
enc_dec_buf:MBEDTLS_CIPHER_DES_CBC:"DES-CBC":64:0:-1
diff --git a/tests/suites/test_suite_cipher.function b/tests/suites/test_suite_cipher.function
index f6367f1..8405f69 100644
--- a/tests/suites/test_suite_cipher.function
+++ b/tests/suites/test_suite_cipher.function
@@ -1,6 +1,10 @@
/* BEGIN_HEADER */
#include "mbedtls/cipher.h"
+#if defined(MBEDTLS_AES_C)
+#include "mbedtls/aes.h"
+#endif
+
#if defined(MBEDTLS_GCM_C)
#include "mbedtls/gcm.h"
#endif
@@ -715,7 +719,9 @@
/* END_CASE */
/* BEGIN_CASE */
-void dec_empty_buf( int cipher )
+void dec_empty_buf( int cipher,
+ int expected_update_ret,
+ int expected_finish_ret )
{
unsigned char key[32];
unsigned char iv[16];
@@ -728,8 +734,6 @@
size_t outlen = 0;
- int expected_ret;
-
memset( key, 0, 32 );
memset( iv , 0, 16 );
@@ -758,25 +762,24 @@
#endif
/* decode 0-byte string */
- TEST_ASSERT( 0 == mbedtls_cipher_update( &ctx_dec, encbuf, 0, decbuf, &outlen ) );
+ TEST_ASSERT( expected_update_ret ==
+ mbedtls_cipher_update( &ctx_dec, encbuf, 0, decbuf, &outlen ) );
TEST_ASSERT( 0 == outlen );
- if ( cipher_info->mode == MBEDTLS_MODE_CBC ||
- cipher_info->mode == MBEDTLS_MODE_ECB )
- {
- /* CBC and ECB ciphers need a full block of input. */
- expected_ret = MBEDTLS_ERR_CIPHER_FULL_BLOCK_EXPECTED;
- }
- else
+ if ( expected_finish_ret == 0 &&
+ ( cipher_info->mode == MBEDTLS_MODE_CBC ||
+ cipher_info->mode == MBEDTLS_MODE_ECB ) )
{
/* Non-CBC and non-ECB ciphers are OK with decrypting empty buffers and
* return success, not MBEDTLS_ERR_CIPHER_FULL_BLOCK_EXPECTED, when
- * decrypting an empty buffer. */
- expected_ret = 0;
+ * decrypting an empty buffer.
+ * On the other hand, CBC and ECB ciphers need a full block of input.
+ */
+ expected_finish_ret = MBEDTLS_ERR_CIPHER_FULL_BLOCK_EXPECTED;
}
- TEST_ASSERT( expected_ret == mbedtls_cipher_finish(
- &ctx_dec, decbuf + outlen, &outlen ) );
+ TEST_ASSERT( expected_finish_ret == mbedtls_cipher_finish(
+ &ctx_dec, decbuf + outlen, &outlen ) );
TEST_ASSERT( 0 == outlen );
exit:
diff --git a/tests/suites/test_suite_cipher.gcm.data b/tests/suites/test_suite_cipher.gcm.data
index 03d08ce..83889de 100644
--- a/tests/suites/test_suite_cipher.gcm.data
+++ b/tests/suites/test_suite_cipher.gcm.data
@@ -1,3 +1,11 @@
+CAMELLIA GCM Decrypt empty buffer
+depends_on:MBEDTLS_CAMELLIA_C:MBEDTLS_GCM_C
+dec_empty_buf:MBEDTLS_CIPHER_CAMELLIA_128_GCM:0:0
+
+Aria GCM Decrypt empty buffer
+depends_on:MBEDTLS_ARIA_C:MBEDTLS_GCM_C
+dec_empty_buf:MBEDTLS_CIPHER_ARIA_128_GCM:0:0
+
AES 128 GCM Encrypt and decrypt 0 bytes
depends_on:MBEDTLS_AES_C:MBEDTLS_GCM_C
enc_dec_buf:MBEDTLS_CIPHER_AES_128_GCM:"AES-128-GCM":128:0:-1
diff --git a/tests/suites/test_suite_cipher.nist_kw.data b/tests/suites/test_suite_cipher.nist_kw.data
index 59ef931..8201891 100644
--- a/tests/suites/test_suite_cipher.nist_kw.data
+++ b/tests/suites/test_suite_cipher.nist_kw.data
@@ -1,3 +1,11 @@
+KW AES-128 wrap - Decrypt empty buffer
+depends_on:MBEDTLS_AES_C:MBEDTLS_NIST_KW_C
+dec_empty_buf:MBEDTLS_CIPHER_AES_128_KW:MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE:MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE
+
+KWP AES-128 wrap - Decrypt empty buffer
+depends_on:MBEDTLS_AES_C:MBEDTLS_NIST_KW_C
+dec_empty_buf:MBEDTLS_CIPHER_AES_128_KWP:MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE:MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE
+
KW AES-128 wrap rfc 3394
depends_on:MBEDTLS_AES_C:MBEDTLS_NIST_KW_C
auth_crypt_tv:MBEDTLS_CIPHER_AES_128_KW:"000102030405060708090A0B0C0D0E0F":"":"":"1FA68B0A8112B447AEF34BD8FB5A7B829D3E862371D2CFE5":"":"":"00112233445566778899AABBCCDDEEFF":0
@@ -268,4 +276,3 @@
KWP AES-256 wrap CAVS 17.4 FAIL COUNT 4 CLEN 32
depends_on:MBEDTLS_AES_C:MBEDTLS_NIST_KW_C
auth_crypt_tv:MBEDTLS_CIPHER_AES_256_KWP:"c32cb3e1e41a4b9f4de79989957866f5dd48dba38c22a6ebb80e14c84bdd9534":"":"":"c29b05c2619a58ecc1d239e7a34273cd":"":"FAIL":"":0
-