Merge pull request #6264 from hannestschofenig/rfc9146_2
CID update to RFC 9146
diff --git a/.travis.yml b/.travis.yml
index 67cb3ca..eaf817a 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -25,8 +25,40 @@
- tests/scripts/all.sh -k build_arm_linux_gnueabi_gcc_arm5vte build_arm_none_eabi_gcc_m0plus
- name: full configuration
+ os: linux
+ dist: focal
+ addons:
+ apt:
+ packages:
+ - clang-10
+ - gnutls-bin
script:
- - tests/scripts/all.sh -k test_full_cmake_gcc_asan
+ # Do a manual build+test sequence rather than using all.sh,
+ # because there's no all.sh component that does what we want,
+ # which is a build with Clang >= 10 and ASan, running all the SSL
+ # testing.
+ # - The clang executable in the default PATH is Clang 7 on
+ # Travis's focal instances, but we want Clang >= 10.
+ # - Running all the SSL testing requires a specific set of
+ # OpenSSL and GnuTLS versions and we don't want to bother
+ # with those on Travis.
+ # So we explicitly select clang-10 as the compiler, and we
+ # have ad hoc restrictions on SSL testing based on what is
+ # passing at the time of writing. We will remove these limitations
+ # gradually.
+ - make generated_files
+ - make CC=clang-10 CFLAGS='-Werror -Wall -Wextra -fsanitize=address,undefined -fno-sanitize-recover=all -O2' LDFLAGS='-Werror -Wall -Wextra -fsanitize=address,undefined -fno-sanitize-recover=all'
+ - make test
+ - programs/test/selftest
+ - tests/scripts/test_psa_constant_names.py
+ - tests/ssl-opt.sh
+ # Modern OpenSSL does not support fixed ECDH or null ciphers.
+ - tests/compat.sh -p OpenSSL -e 'NULL\|ECDH-'
+ - tests/scripts/travis-log-failure.sh
+ # GnuTLS supports CAMELLIA but compat.sh doesn't properly enable it.
+ - tests/compat.sh -p GnuTLS -e 'CAMELLIA'
+ - tests/scripts/travis-log-failure.sh
+ - tests/context-info.sh
- name: Windows
os: windows
diff --git a/ChangeLog.d/driver-only-hashes.txt b/ChangeLog.d/driver-only-hashes.txt
index 2062bcb..6ccd199 100644
--- a/ChangeLog.d/driver-only-hashes.txt
+++ b/ChangeLog.d/driver-only-hashes.txt
@@ -1,20 +1,19 @@
Features
- * Some crypto modules that previously depended on MD or a low-level hash
- module, either unconditionally (RSA, PK, PKCS5, PKCS12, EC J-PAKE), or
- for some features (PEM for encrypted files), are now able to use PSA
- Crypto instead when the legacy API is not available. This means it is
- now possible to use all features from those modules in configurations
- where the built-in implementations of hashes are excluded and the hashes
- are only provided by PSA drivers. In these configurations, you need to
- call `psa_crypto_init()` before you call any function from those
- modules; this is not required in configurations where the built-in
- implementation is still available. Note that some crypto modules and
- features still depend on the built-in implementation of hashes:
- MBEDTLS_HKDF_C (but the PSA HKDF function do not depend on it),
- MBEDTLS_ENTROPY_C, MBEDTLS_HMAC_DRBG_C and MBEDTLS_ECDSA_DETERMINISTIC.
- In particular, for now, compiling without built-in hashes requires use
- of MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG.
- * When MBEDTLS_USE_PSA_CRYPTO is enabled, X.509, TLS 1.2 and TLS 1.3 no
- longer depend on MD. This means it is now possible to use them in
- configurations where the built-in implementations of hashes are excluded
- and the hashes are only provided by PSA drivers.
+ * Some modules can now use PSA drivers for hashes, including with no
+ built-in implementation present, but only in some configurations.
+ - RSA OAEP and PSS (PKCS#1 v2.1), PKCS5, PKCS12 and EC J-PAKE now use
+ hashes from PSA when (and only when) MBEDTLS_MD_C is disabled.
+ - PEM parsing of encrypted files now uses MD-5 from PSA when (and only
+ when) MBEDTLS_MD5_C is disabled.
+ See the documentation of the corresponding macros in mbedtls_config.h for
+ details.
+ Note that some modules are not able to use hashes from PSA yet, including
+ the entropy module. As a consequence, for now the only way to build with
+ all hashes only provided by drivers (no built-in hash) is to use
+ MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG.
+ * When MBEDTLS_USE_PSA_CRYPTO is enabled, X.509, TLS 1.2 and TLS 1.3 now
+ properly negotiate/accept hashes based on their availability in PSA.
+ As a consequence, they now work in configurations where the built-in
+ implementations of (some) hashes are excluded and those hashes are only
+ provided by PSA drivers. (See previous entry for limitation on RSA-PSS
+ though: that module only use hashes from PSA when MBEDTLS_MD_C is off).
diff --git a/ChangeLog.d/ecjpake-in-tls.txt b/ChangeLog.d/ecjpake-in-tls.txt
new file mode 100644
index 0000000..b84caab
--- /dev/null
+++ b/ChangeLog.d/ecjpake-in-tls.txt
@@ -0,0 +1,5 @@
+Features
+ * The TLS 1.2 EC J-PAKE key exchange can now use the PSA Crypto API.
+ Additional PSA key slots will be allocated in the process of such key
+ exchange for builds that enable MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED and
+ MBEDTLS_USE_PSA_CRYPTO.
diff --git a/ChangeLog.d/fix-possible-false-success-in-mbedtls_cipher_check_tag.txt b/ChangeLog.d/fix-possible-false-success-in-mbedtls_cipher_check_tag.txt
new file mode 100644
index 0000000..1f9e0aa
--- /dev/null
+++ b/ChangeLog.d/fix-possible-false-success-in-mbedtls_cipher_check_tag.txt
@@ -0,0 +1,5 @@
+Changes
+ * Calling AEAD tag-specific functions for non-AEAD algorithms (which
+ should not be done - they are documented for use only by AES-GCM and
+ ChaCha20+Poly1305) now returns MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE
+ instead of success (0).
diff --git a/ChangeLog.d/fix-tls12server-sent-sigalgs.txt b/ChangeLog.d/fix-tls12server-sent-sigalgs.txt
new file mode 100644
index 0000000..9abde2b
--- /dev/null
+++ b/ChangeLog.d/fix-tls12server-sent-sigalgs.txt
@@ -0,0 +1,5 @@
+Bugfix
+ * Fix a bug whereby the the list of signature algorithms sent as part of the
+ TLS 1.2 server certificate request would get corrupted, meaning the first
+ algorithm would not get sent and an entry consisting of two random bytes
+ would be sent instead. Found by Serban Bejan and Dudek Sebastian.
diff --git a/ChangeLog.d/fix_dh_genprime_error_reporting.txt b/ChangeLog.d/fix_dh_genprime_error_reporting.txt
new file mode 100644
index 0000000..1c98947
--- /dev/null
+++ b/ChangeLog.d/fix_dh_genprime_error_reporting.txt
@@ -0,0 +1,4 @@
+Bugfix
+ * Fix bug in error reporting in dh_genprime.c where upon failure,
+ the error code returned by mbedtls_mpi_write_file() is overwritten
+ and therefore not printed.
diff --git a/ChangeLog.d/move-ssl-modules.txt b/ChangeLog.d/move-ssl-modules.txt
new file mode 100644
index 0000000..f00e5ad
--- /dev/null
+++ b/ChangeLog.d/move-ssl-modules.txt
@@ -0,0 +1,3 @@
+Bugfix
+ * Move some SSL-specific code out of libmbedcrypto where it had been placed
+ accidentally.
diff --git a/ChangeLog.d/mpi-add-0-ub.txt b/ChangeLog.d/mpi-add-0-ub.txt
new file mode 100644
index 0000000..9f131a4
--- /dev/null
+++ b/ChangeLog.d/mpi-add-0-ub.txt
@@ -0,0 +1,4 @@
+Bugfix
+ * Fix undefined behavior (typically harmless in practice) of
+ mbedtls_mpi_add_mpi(), mbedtls_mpi_add_abs() and mbedtls_mpi_add_int()
+ when both operands are 0 and the left operand is represented with 0 limbs.
diff --git a/ChangeLog.d/mpi-most-negative-sint.txt b/ChangeLog.d/mpi-most-negative-sint.txt
new file mode 100644
index 0000000..5e775c4
--- /dev/null
+++ b/ChangeLog.d/mpi-most-negative-sint.txt
@@ -0,0 +1,4 @@
+Bugfix
+ * Fix undefined behavior (typically harmless in practice) when some bignum
+ functions receive the most negative value of mbedtls_mpi_sint. Credit
+ to OSS-Fuzz. Fixes #6597.
diff --git a/ChangeLog.d/negative-zero-from-add.txt b/ChangeLog.d/negative-zero-from-add.txt
new file mode 100644
index 0000000..107d858
--- /dev/null
+++ b/ChangeLog.d/negative-zero-from-add.txt
@@ -0,0 +1,6 @@
+Bugfix
+ * In the bignum module, operations of the form (-A) - (+A) or (-A) - (-A)
+ with A > 0 created an unintended representation of the value 0 which was
+ not processed correctly by some bignum operations. Fix this. This had no
+ consequence on cryptography code, but might affect applications that call
+ bignum directly and use negative numbers.
diff --git a/ChangeLog.d/pkcs7-parser.txt b/ChangeLog.d/pkcs7-parser.txt
new file mode 100644
index 0000000..7f85f0c
--- /dev/null
+++ b/ChangeLog.d/pkcs7-parser.txt
@@ -0,0 +1,13 @@
+Features
+ * Added partial support for parsing the PKCS7 cryptographic message syntax,
+ as defined in RFC 2315. Currently, support is limited to the following:
+ - Only the signed data content type, version 1 is supported.
+ - Only DER encoding is supported.
+ - Only a single digest algorithm per message is supported.
+ - Only 0 or 1, certificate is supported per message, which must be in
+ X509 format.
+ - There is no support for certificate-revocation lists.
+ - The authenticated and unauthenticated attribute fields of SignerInfo
+ must be empty.
+ Many thanks to Daniel Axtens, Nayna Jain, and Nick Child from IBM for
+ contributing this feature.
diff --git a/ChangeLog.d/psa-ecb-ub.txt b/ChangeLog.d/psa-ecb-ub.txt
new file mode 100644
index 0000000..9d725ac
--- /dev/null
+++ b/ChangeLog.d/psa-ecb-ub.txt
@@ -0,0 +1,3 @@
+Bugfix
+ * Fix undefined behavior (typically harmless in practice) in PSA ECB
+ encryption and decryption.
diff --git a/docs/architecture/psa-migration/outcome-analysis.sh b/docs/architecture/psa-migration/outcome-analysis.sh
index 81ab691..9084685 100755
--- a/docs/architecture/psa-migration/outcome-analysis.sh
+++ b/docs/architecture/psa-migration/outcome-analysis.sh
@@ -13,6 +13,7 @@
# - the set of tests skipped in the driver-only build is the same as in an
# equivalent software-based configuration, or the difference is small enough,
# justified, and a github issue is created to track it.
+# This part is verified by tests/scripts/analyze_outcomes.py
#
# WARNING: this script checks out a commit other than the head of the current
# branch; it checks out the current branch again when running successfully,
@@ -26,30 +27,12 @@
# re-running this script (for example "get numbers before this PR").
# ----- BEGIN edit this -----
-# The component in all.sh that builds and tests with drivers.
-DRIVER_COMPONENT=test_psa_crypto_config_accel_hash_use_psa
-# A similar configuration to that of the component, except without drivers,
-# for comparison.
-reference_config () {
- # start with full
- scripts/config.py full
- # use PSA config and disable driver-less algs as in the component
- scripts/config.py set MBEDTLS_PSA_CRYPTO_CONFIG
- scripts/config.py -f include/psa/crypto_config.h unset PSA_WANT_ALG_STREAM_CIPHER
- scripts/config.py -f include/psa/crypto_config.h unset PSA_WANT_ALG_ECB_NO_PADDING
- # disable options as in the component
- # (no need to disable whole modules, we'll just skip their test suite)
- scripts/config.py unset MBEDTLS_ECDSA_DETERMINISTIC
- scripts/config.py -f include/psa/crypto_config.h unset PSA_WANT_ALG_DETERMINISTIC_ECDSA
-}
# Space-separated list of test suites to ignore:
# if SSS is in that list, test_suite_SSS and test_suite_SSS.* are ignored.
IGNORE="md mdx shax" # accelerated
IGNORE="$IGNORE entropy hmac_drbg random" # disabled (ext. RNG)
IGNORE="$IGNORE psa_crypto_init" # needs internal RNG
IGNORE="$IGNORE hkdf" # disabled in the all.sh component tested
-# Compare only "reference vs driver" or also "before vs after"?
-BEFORE_AFTER=1 # 0 or 1
# ----- END edit this -----
set -eu
@@ -65,38 +48,27 @@
make check
}
-if [ "$BEFORE_AFTER" -eq 1 ]; then
- # save current HEAD
- HEAD=$(git branch --show-current)
+# save current HEAD
+HEAD=$(git branch --show-current)
- # get the numbers before this PR for default and full
- cleanup
- git checkout $(git merge-base HEAD development)
- record "before-default"
-
- cleanup
- scripts/config.py full
- record "before-full"
-
- # get the numbers now for default and full
- cleanup
- git checkout $HEAD
- record "after-default"
-
- cleanup
- scripts/config.py full
- record "after-full"
-fi
-
-# get the numbers now for driver-only and reference
+# get the numbers before this PR for default and full
cleanup
-reference_config
-record "reference"
+git checkout $(git merge-base HEAD development)
+record "before-default"
cleanup
-export MBEDTLS_TEST_OUTCOME_FILE="$PWD/outcome-drivers.csv"
-export SKIP_SSL_OPT_COMPAT_SH=1
-tests/scripts/all.sh -k test_psa_crypto_config_accel_hash_use_psa
+scripts/config.py full
+record "before-full"
+
+# get the numbers now for default and full
+cleanup
+git checkout $HEAD
+record "after-default"
+
+cleanup
+scripts/config.py full
+record "after-full"
+
# analysis
@@ -156,8 +128,5 @@
}
populate_suites
-if [ "$BEFORE_AFTER" -eq 1 ]; then
- compare_builds before-default after-default
- compare_builds before-full after-full
-fi
-compare_builds reference drivers
+compare_builds before-default after-default
+compare_builds before-full after-full
diff --git a/docs/architecture/tls13-support.md b/docs/architecture/tls13-support.md
index f30590b..85482ba 100644
--- a/docs/architecture/tls13-support.md
+++ b/docs/architecture/tls13-support.md
@@ -478,3 +478,175 @@
* state change: the state change is done in the main state handler to ease
the navigation of the state machine transitions.
+
+
+Writing and reading early or 0-RTT data
+---------------------------------------
+
+An application function to write and send a buffer of data to a server through
+TLS may plausibly look like:
+
+```
+int write_data( mbedtls_ssl_context *ssl,
+ const unsigned char *data_to_write,
+ size_t data_to_write_len,
+ size_t *data_written )
+{
+ *data_written = 0;
+
+ while( *data_written < data_to_write_len )
+ {
+ ret = mbedtls_ssl_write( ssl, data_to_write + *data_written,
+ data_to_write_len - *data_written );
+
+ if( ret < 0 &&
+ ret != MBEDTLS_ERR_SSL_WANT_READ &&
+ ret != MBEDTLS_ERR_SSL_WANT_WRITE )
+ {
+ return( ret );
+ }
+
+ *data_written += ret;
+ }
+
+ return( 0 );
+}
+```
+where ssl is the SSL context to use, data_to_write the address of the data
+buffer and data_to_write_len the number of data bytes. The handshake may
+not be completed, not even started for the SSL context ssl when the function is
+called and in that case the mbedtls_ssl_write() API takes care transparently of
+completing the handshake before to write and send data to the server. The
+mbedtls_ssl_write() may not been able to write and send all data in one go thus
+the need for a loop calling it as long as there are still data to write and
+send.
+
+An application function to write and send early data and only early data,
+data sent during the first flight of client messages while the handshake is in
+its initial phase, would look completely similar but the call to
+mbedtls_ssl_write_early_data() instead of mbedtls_ssl_write().
+```
+int write_early_data( mbedtls_ssl_context *ssl,
+ const unsigned char *data_to_write,
+ size_t data_to_write_len,
+ size_t *data_written )
+{
+ *data_written = 0;
+
+ while( *data_written < data_to_write_len )
+ {
+ ret = mbedtls_ssl_write_early_data( ssl, data_to_write + *data_written,
+ data_to_write_len - *data_written );
+
+ if( ret < 0 &&
+ ret != MBEDTLS_ERR_SSL_WANT_READ &&
+ ret != MBEDTLS_ERR_SSL_WANT_WRITE )
+ {
+ return( ret );
+ }
+
+ *data_written += ret;
+ }
+
+ return( 0 );
+}
+```
+Note that compared to write_data(), write_early_data() can also return
+MBEDTLS_ERR_SSL_CANNOT_WRITE_EARLY_DATA and that should be handled
+specifically by the user of write_early_data(). A fresh SSL context (typically
+just after a call to mbedtls_ssl_setup() or mbedtls_ssl_session_reset()) would
+be expected when calling `write_early_data`.
+
+All together, code to write and send a buffer of data as long as possible as
+early data and then as standard post-handshake application data could
+plausibly look like:
+
+```
+ret = write_early_data( ssl, data_to_write, data_to_write_len,
+ &early_data_written );
+if( ret < 0 &&
+ ret != MBEDTLS_ERR_SSL_CANNOT_WRITE_EARLY_DATA )
+{
+ goto error;
+}
+
+ret = write_data( ssl, data_to_write + early_data_written,
+ data_to_write_len - early_data_written, &data_written );
+if( ret < 0 )
+ goto error;
+
+data_written += early_data_written;
+```
+
+Finally, taking into account that the server may reject early data, application
+code to write and send a buffer of data could plausibly look like:
+```
+ret = write_early_data( ssl, data_to_write, data_to_write_len,
+ &early_data_written );
+if( ret < 0 &&
+ ret != MBEDTLS_ERR_SSL_CANNOT_WRITE_EARLY_DATA )
+{
+ goto error;
+}
+
+/*
+ * Make sure the handshake is completed as it is a requisite to
+ * mbedtls_ssl_get_early_data_status().
+ */
+while( !mbedtls_ssl_is_handshake_over( ssl ) )
+{
+ ret = mbedtls_ssl_handshake( ssl );
+ if( ret < 0 &&
+ ret != MBEDTLS_ERR_SSL_WANT_READ &&
+ ret != MBEDTLS_ERR_SSL_WANT_WRITE )
+ {
+ goto error;
+ }
+}
+
+ret = mbedtls_ssl_get_early_data_status( ssl );
+if( ret < 0 )
+ goto error;
+
+if( ret == MBEDTLS_SSL_EARLY_DATA_STATUS_REJECTED )
+ early_data_written = 0;
+
+ret = write_data( ssl, data_to_write + early_data_written,
+ data_to_write_len - early_data_written, &data_written );
+if( ret < 0 )
+ goto error;
+
+data_written += early_data_written;
+```
+
+Basically, the same holds for reading early data on the server side without the
+complication of possible rejection. An application function to read early data
+into a given buffer could plausibly look like:
+```
+int read_early_data( mbedtls_ssl_context *ssl,
+ unsigned char *buffer,
+ size_t buffer_size,
+ size_t *data_len )
+{
+ *data_len = 0;
+
+ while( *data_len < buffer_size )
+ {
+ ret = mbedtls_ssl_read_early_data( ssl, buffer + *data_len,
+ buffer_size - *data_len );
+
+ if( ret < 0 &&
+ ret != MBEDTLS_ERR_SSL_WANT_READ &&
+ ret != MBEDTLS_ERR_SSL_WANT_WRITE )
+ {
+ return( ret );
+ }
+
+ *data_len += ret;
+ }
+
+ return( 0 );
+}
+```
+with again calls to read_early_data() expected to be done with a fresh SSL
+context.
diff --git a/docs/use-psa-crypto.md b/docs/use-psa-crypto.md
index b22d37f..11442ed 100644
--- a/docs/use-psa-crypto.md
+++ b/docs/use-psa-crypto.md
@@ -86,7 +86,6 @@
Current exceptions:
-- EC J-PAKE (when `MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED` is defined)
- finite-field (non-EC) Diffie-Hellman (used in key exchanges: DHE-RSA,
DHE-PSK)
diff --git a/include/mbedtls/aes.h b/include/mbedtls/aes.h
index c359011..1cd20fe 100644
--- a/include/mbedtls/aes.h
+++ b/include/mbedtls/aes.h
@@ -61,11 +61,6 @@
/** Invalid input data. */
#define MBEDTLS_ERR_AES_BAD_INPUT_DATA -0x0021
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
#ifdef __cplusplus
extern "C" {
#endif
diff --git a/include/mbedtls/asn1.h b/include/mbedtls/asn1.h
index 8b66ee2..5e3f387 100644
--- a/include/mbedtls/asn1.h
+++ b/include/mbedtls/asn1.h
@@ -39,8 +39,9 @@
/**
* \name ASN1 Error codes
- * These error codes are OR'ed to X509 error codes for
+ * These error codes are combined with other error codes for
* higher error granularity.
+ * e.g. X.509 and PKCS #7 error codes
* ASN1 is a standard to specify data structures.
* \{
*/
diff --git a/include/mbedtls/bignum.h b/include/mbedtls/bignum.h
index 9d15955..877fbc7 100644
--- a/include/mbedtls/bignum.h
+++ b/include/mbedtls/bignum.h
@@ -179,6 +179,20 @@
#endif /* !MBEDTLS_NO_UDBL_DIVISION */
#endif /* !MBEDTLS_HAVE_INT64 */
+/** \typedef mbedtls_mpi_uint
+ * \brief The type of machine digits in a bignum, called _limbs_.
+ *
+ * This is always an unsigned integer type with no padding bits. The size
+ * is platform-dependent.
+ */
+
+/** \typedef mbedtls_mpi_sint
+ * \brief The signed type corresponding to #mbedtls_mpi_uint.
+ *
+ * This is always an signed integer type with no padding bits. The size
+ * is platform-dependent.
+ */
+
#ifdef __cplusplus
extern "C" {
#endif
@@ -188,9 +202,27 @@
*/
typedef struct mbedtls_mpi
{
- int MBEDTLS_PRIVATE(s); /*!< Sign: -1 if the mpi is negative, 1 otherwise */
- size_t MBEDTLS_PRIVATE(n); /*!< total # of limbs */
- mbedtls_mpi_uint *MBEDTLS_PRIVATE(p); /*!< pointer to limbs */
+ /** Sign: -1 if the mpi is negative, 1 otherwise.
+ *
+ * The number 0 must be represented with `s = +1`. Although many library
+ * functions treat all-limbs-zero as equivalent to a valid representation
+ * of 0 regardless of the sign bit, there are exceptions, so bignum
+ * functions and external callers must always set \c s to +1 for the
+ * number zero.
+ *
+ * Note that this implies that calloc() or `... = {0}` does not create
+ * a valid MPI representation. You must call mbedtls_mpi_init().
+ */
+ int MBEDTLS_PRIVATE(s);
+
+ /** Total number of limbs in \c p. */
+ size_t MBEDTLS_PRIVATE(n);
+
+ /** Pointer to limbs.
+ *
+ * This may be \c NULL if \c n is 0.
+ */
+ mbedtls_mpi_uint *MBEDTLS_PRIVATE(p);
}
mbedtls_mpi;
diff --git a/include/mbedtls/build_info.h b/include/mbedtls/build_info.h
index 170cbeb..362ce2f 100644
--- a/include/mbedtls/build_info.h
+++ b/include/mbedtls/build_info.h
@@ -53,6 +53,12 @@
#define _CRT_SECURE_NO_DEPRECATE 1
#endif
+/* Define `inline` on some non-C99-compliant compilers. */
+#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
+ !defined(inline) && !defined(__cplusplus)
+#define inline __inline
+#endif
+
#if !defined(MBEDTLS_CONFIG_FILE)
#include "mbedtls/mbedtls_config.h"
#else
diff --git a/include/mbedtls/check_config.h b/include/mbedtls/check_config.h
index 6bfb9fa..7f55580 100644
--- a/include/mbedtls/check_config.h
+++ b/include/mbedtls/check_config.h
@@ -842,10 +842,10 @@
"but no key exchange methods defined with MBEDTLS_KEY_EXCHANGE_xxxx"
#endif
-/* Early data requires PSK related mode defined */
#if defined(MBEDTLS_SSL_EARLY_DATA) && \
- ( !defined(MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_ENABLED) && \
- !defined(MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_EPHEMERAL_ENABLED))
+ ( !defined(MBEDTLS_SSL_SESSION_TICKETS) || \
+ ( !defined(MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_ENABLED) && \
+ !defined(MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_EPHEMERAL_ENABLED) ) )
#error "MBEDTLS_SSL_EARLY_DATA defined, but not all prerequisites"
#endif
@@ -1075,6 +1075,14 @@
#error "MBEDTLS_SSL_TRUNCATED_HMAC was removed in Mbed TLS 3.0. See https://github.com/Mbed-TLS/mbedtls/issues/4341"
#endif
+#if defined(MBEDTLS_PKCS7_C) && ( ( !defined(MBEDTLS_ASN1_PARSE_C) ) || \
+ ( !defined(MBEDTLS_OID_C) ) || ( !defined(MBEDTLS_PK_PARSE_C) ) || \
+ ( !defined(MBEDTLS_X509_CRT_PARSE_C) ) ||\
+ ( !defined(MBEDTLS_X509_CRL_PARSE_C) ) || ( !defined(MBEDTLS_BIGNUM_C) ) || \
+ ( !defined(MBEDTLS_MD_C) ) )
+#error "MBEDTLS_PKCS7_C is defined, but not all prerequisites"
+#endif
+
/*
* Avoid warning from -pedantic. This is a convenient place for this
* workaround since this is included by every single file before the
diff --git a/include/mbedtls/cipher.h b/include/mbedtls/cipher.h
index a3f52ea..151da1d 100644
--- a/include/mbedtls/cipher.h
+++ b/include/mbedtls/cipher.h
@@ -46,11 +46,6 @@
#define MBEDTLS_CIPHER_MODE_STREAM
#endif
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
/** The selected feature is not available. */
#define MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE -0x6080
/** Bad input parameters. */
diff --git a/include/mbedtls/ecjpake.h b/include/mbedtls/ecjpake.h
index e7ca1b2..3dd3361 100644
--- a/include/mbedtls/ecjpake.h
+++ b/include/mbedtls/ecjpake.h
@@ -113,7 +113,7 @@
* \param curve The identifier of the elliptic curve to use,
* for example #MBEDTLS_ECP_DP_SECP256R1.
* \param secret The pre-shared secret (passphrase). This must be
- * a readable buffer of length \p len Bytes. It need
+ * a readable not empty buffer of length \p len Bytes. It need
* only be valid for the duration of this call.
* \param len The length of the pre-shared secret \p secret.
*
diff --git a/include/mbedtls/error.h b/include/mbedtls/error.h
index eb83913..4a97d65 100644
--- a/include/mbedtls/error.h
+++ b/include/mbedtls/error.h
@@ -26,11 +26,6 @@
#include <stddef.h>
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
/**
* Error code layout.
*
@@ -96,6 +91,7 @@
* ECP 4 10 (Started from top)
* MD 5 5
* HKDF 5 1 (Started from top)
+ * PKCS7 5 12 (Started from 0x5300)
* SSL 5 2 (Started from 0x5F00)
* CIPHER 6 8 (Started from 0x6080)
* SSL 6 22 (Started from top, plus 0x6000)
diff --git a/include/mbedtls/mbedtls_config.h b/include/mbedtls/mbedtls_config.h
index 8f45236..c719073 100644
--- a/include/mbedtls/mbedtls_config.h
+++ b/include/mbedtls/mbedtls_config.h
@@ -1146,6 +1146,11 @@
* \warning If building without MBEDTLS_MD_C, you must call psa_crypto_init()
* before doing any PKCS#1 v2.1 operation.
*
+ * \warning When building with MBEDTLS_MD_C, all hashes used with this
+ * need to be available as built-ins (that is, for SHA-256, MBEDTLS_SHA256_C,
+ * etc.) as opposed to just PSA drivers. So far, PSA drivers are only used by
+ * this module in builds where MBEDTLS_MD_C is disabled.
+ *
* This enables support for RSAES-OAEP and RSASSA-PSS operations.
*/
#define MBEDTLS_PKCS1_V21
@@ -1655,7 +1660,8 @@
*
* Enable support for RFC 8446 TLS 1.3 early data.
*
-* Requires: MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_ENABLED or
+* Requires: MBEDTLS_SSL_SESSION_TICKETS and either
+* MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_ENABLED or
* MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_EPHEMERAL_ENABLED
*
* Comment this to disable support for early data. If MBEDTLS_SSL_PROTO_TLS1_3
@@ -2450,6 +2456,11 @@
*
* \warning If building without MBEDTLS_MD_C, you must call psa_crypto_init()
* before doing any EC J-PAKE operations.
+ *
+ * \warning When building with MBEDTLS_MD_C, all hashes used with this
+ * need to be available as built-ins (that is, for SHA-256, MBEDTLS_SHA256_C,
+ * etc.) as opposed to just PSA drivers. So far, PSA drivers are only used by
+ * this module in builds where MBEDTLS_MD_C is disabled.
*/
#define MBEDTLS_ECJPAKE_C
@@ -2794,11 +2805,32 @@
* \warning If building without MBEDTLS_MD_C, you must call psa_crypto_init()
* before doing any PKCS5 operation.
*
+ * \warning When building with MBEDTLS_MD_C, all hashes used with this
+ * need to be available as built-ins (that is, for SHA-256, MBEDTLS_SHA256_C,
+ * etc.) as opposed to just PSA drivers. So far, PSA drivers are only used by
+ * this module in builds where MBEDTLS_MD_C is disabled.
+ *
* This module adds support for the PKCS#5 functions.
*/
#define MBEDTLS_PKCS5_C
/**
+ * \def MBEDTLS_PKCS7_C
+ *
+ * Enable PKCS7 core for using PKCS7 formatted signatures.
+ * RFC Link - https://tools.ietf.org/html/rfc2315
+ *
+ * Module: library/pkcs7.c
+ *
+ * Requires: MBEDTLS_ASN1_PARSE_C, MBEDTLS_OID_C, MBEDTLS_PK_PARSE_C,
+ * MBEDTLS_X509_CRT_PARSE_C MBEDTLS_X509_CRL_PARSE_C,
+ * MBEDTLS_BIGNUM_C, MBEDTLS_MD_C
+ *
+ * This module is required for the PKCS7 parsing modules.
+ */
+#define MBEDTLS_PKCS7_C
+
+/**
* \def MBEDTLS_PKCS12_C
*
* Enable PKCS#12 PBE functions.
@@ -2813,6 +2845,11 @@
* \warning If building without MBEDTLS_MD_C, you must call psa_crypto_init()
* before doing any PKCS12 operation.
*
+ * \warning When building with MBEDTLS_MD_C, all hashes used with this
+ * need to be available as built-ins (that is, for SHA-256, MBEDTLS_SHA256_C,
+ * etc.) as opposed to just PSA drivers. So far, PSA drivers are only used by
+ * this module in builds where MBEDTLS_MD_C is disabled.
+ *
* This module enables PKCS#12 functions.
*/
#define MBEDTLS_PKCS12_C
diff --git a/include/mbedtls/oid.h b/include/mbedtls/oid.h
index 4ee3f93..e5c4b92 100644
--- a/include/mbedtls/oid.h
+++ b/include/mbedtls/oid.h
@@ -220,6 +220,7 @@
#define MBEDTLS_OID_PKCS MBEDTLS_OID_RSA_COMPANY "\x01" /**< pkcs OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) rsadsi(113549) 1 } */
#define MBEDTLS_OID_PKCS1 MBEDTLS_OID_PKCS "\x01" /**< pkcs-1 OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) rsadsi(113549) pkcs(1) 1 } */
#define MBEDTLS_OID_PKCS5 MBEDTLS_OID_PKCS "\x05" /**< pkcs-5 OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) rsadsi(113549) pkcs(1) 5 } */
+#define MBEDTLS_OID_PKCS7 MBEDTLS_OID_PKCS "\x07" /**< pkcs-7 OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) rsadsi(113549) pkcs(1) 7 } */
#define MBEDTLS_OID_PKCS9 MBEDTLS_OID_PKCS "\x09" /**< pkcs-9 OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) rsadsi(113549) pkcs(1) 9 } */
#define MBEDTLS_OID_PKCS12 MBEDTLS_OID_PKCS "\x0c" /**< pkcs-12 OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) rsadsi(113549) pkcs(1) 12 } */
@@ -301,6 +302,16 @@
#define MBEDTLS_OID_PKCS5_PBE_SHA1_RC2_CBC MBEDTLS_OID_PKCS5 "\x0b" /**< pbeWithSHA1AndRC2-CBC OBJECT IDENTIFIER ::= {pkcs-5 11} */
/*
+ * PKCS#7 OIDs
+ */
+#define MBEDTLS_OID_PKCS7_DATA MBEDTLS_OID_PKCS7 "\x01" /**< Content type is Data OBJECT IDENTIFIER ::= {pkcs-7 1} */
+#define MBEDTLS_OID_PKCS7_SIGNED_DATA MBEDTLS_OID_PKCS7 "\x02" /**< Content type is Signed Data OBJECT IDENTIFIER ::= {pkcs-7 2} */
+#define MBEDTLS_OID_PKCS7_ENVELOPED_DATA MBEDTLS_OID_PKCS7 "\x03" /**< Content type is Enveloped Data OBJECT IDENTIFIER ::= {pkcs-7 3} */
+#define MBEDTLS_OID_PKCS7_SIGNED_AND_ENVELOPED_DATA MBEDTLS_OID_PKCS7 "\x04" /**< Content type is Signed and Enveloped Data OBJECT IDENTIFIER ::= {pkcs-7 4} */
+#define MBEDTLS_OID_PKCS7_DIGESTED_DATA MBEDTLS_OID_PKCS7 "\x05" /**< Content type is Digested Data OBJECT IDENTIFIER ::= {pkcs-7 5} */
+#define MBEDTLS_OID_PKCS7_ENCRYPTED_DATA MBEDTLS_OID_PKCS7 "\x06" /**< Content type is Encrypted Data OBJECT IDENTIFIER ::= {pkcs-7 6} */
+
+/*
* PKCS#8 OIDs
*/
#define MBEDTLS_OID_PKCS9_CSR_EXT_REQ MBEDTLS_OID_PKCS9 "\x0e" /**< extensionRequest OBJECT IDENTIFIER ::= {pkcs-9 14} */
diff --git a/include/mbedtls/pem.h b/include/mbedtls/pem.h
index c75a124..a4c6fb8 100644
--- a/include/mbedtls/pem.h
+++ b/include/mbedtls/pem.h
@@ -27,11 +27,6 @@
#include <stddef.h>
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
/**
* \name PEM Error codes
* These error codes are returned in case of errors reading the
diff --git a/include/mbedtls/pk.h b/include/mbedtls/pk.h
index 867961d..db0bfac 100644
--- a/include/mbedtls/pk.h
+++ b/include/mbedtls/pk.h
@@ -44,11 +44,6 @@
#include "psa/crypto.h"
#endif
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
/** Memory allocation failed. */
#define MBEDTLS_ERR_PK_ALLOC_FAILED -0x3F80
/** Type mismatch, eg attempt to encrypt with an ECDSA key */
diff --git a/include/mbedtls/pkcs7.h b/include/mbedtls/pkcs7.h
new file mode 100644
index 0000000..52895ac
--- /dev/null
+++ b/include/mbedtls/pkcs7.h
@@ -0,0 +1,241 @@
+/**
+ * \file pkcs7.h
+ *
+ * \brief PKCS7 generic defines and structures
+ * https://tools.ietf.org/html/rfc2315
+ */
+/*
+ * Copyright The Mbed TLS Contributors
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may
+ * not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * Note: For the time being, this implementation of the PKCS7 cryptographic
+ * message syntax is a partial implementation of RFC 2315.
+ * Differences include:
+ * - The RFC specifies 6 different content types. The only type currently
+ * supported in Mbed TLS is the signed data content type.
+ * - The only supported PKCS7 Signed Data syntax version is version 1
+ * - The RFC specifies support for BER. This implementation is limited to
+ * DER only.
+ * - The RFC specifies that multiple digest algorithms can be specified
+ * in the Signed Data type. Only one digest algorithm is supported in Mbed TLS.
+ * - The RFC specifies the Signed Data type can contain multiple X509 or PKCS6
+ * certificates. In Mbed TLS, this list can only contain 0 or 1 certificates
+ * and they must be in X509 format.
+ * - The RFC specifies the Signed Data type can contain
+ * certificate-revocation lists (crls). This implementation has no support
+ * for crls so it is assumed to be an empty list.
+ * - The RFC allows for SignerInfo structure to optionally contain
+ * unauthenticatedAttributes and authenticatedAttributes. In Mbed TLS it is
+ * assumed these fields are empty.
+ */
+
+#ifndef MBEDTLS_PKCS7_H
+#define MBEDTLS_PKCS7_H
+
+#include "mbedtls/private_access.h"
+
+#include "mbedtls/build_info.h"
+
+#include "mbedtls/asn1.h"
+#include "mbedtls/x509.h"
+#include "mbedtls/x509_crt.h"
+
+/**
+ * \name PKCS7 Module Error codes
+ * \{
+ */
+#define MBEDTLS_ERR_PKCS7_INVALID_FORMAT -0x5300 /**< The format is invalid, e.g. different type expected. */
+#define MBEDTLS_ERR_PKCS7_FEATURE_UNAVAILABLE -0x5380 /**< Unavailable feature, e.g. anything other than signed data. */
+#define MBEDTLS_ERR_PKCS7_INVALID_VERSION -0x5400 /**< The PKCS7 version element is invalid or cannot be parsed. */
+#define MBEDTLS_ERR_PKCS7_INVALID_CONTENT_INFO -0x5480 /**< The PKCS7 content info invalid or cannot be parsed. */
+#define MBEDTLS_ERR_PKCS7_INVALID_ALG -0x5500 /**< The algorithm tag or value is invalid or cannot be parsed. */
+#define MBEDTLS_ERR_PKCS7_INVALID_CERT -0x5580 /**< The certificate tag or value is invalid or cannot be parsed. */
+#define MBEDTLS_ERR_PKCS7_INVALID_SIGNATURE -0x5600 /**< Error parsing the signature */
+#define MBEDTLS_ERR_PKCS7_INVALID_SIGNER_INFO -0x5680 /**< Error parsing the signer's info */
+#define MBEDTLS_ERR_PKCS7_BAD_INPUT_DATA -0x5700 /**< Input invalid. */
+#define MBEDTLS_ERR_PKCS7_ALLOC_FAILED -0x5780 /**< Allocation of memory failed. */
+#define MBEDTLS_ERR_PKCS7_VERIFY_FAIL -0x5800 /**< Verification Failed */
+#define MBEDTLS_ERR_PKCS7_CERT_DATE_INVALID -0x5880 /**< The PKCS7 date issued/expired dates are invalid */
+/* \} name */
+
+/**
+ * \name PKCS7 Supported Version
+ * \{
+ */
+#define MBEDTLS_PKCS7_SUPPORTED_VERSION 0x01
+/* \} name */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * Type-length-value structure that allows for ASN1 using DER.
+ */
+typedef mbedtls_asn1_buf mbedtls_pkcs7_buf;
+
+/**
+ * Container for ASN1 named information objects.
+ * It allows for Relative Distinguished Names (e.g. cn=localhost,ou=code,etc.).
+ */
+typedef mbedtls_asn1_named_data mbedtls_pkcs7_name;
+
+/**
+ * Container for a sequence of ASN.1 items
+ */
+typedef mbedtls_asn1_sequence mbedtls_pkcs7_sequence;
+
+/**
+ * PKCS7 types
+ */
+typedef enum {
+ MBEDTLS_PKCS7_NONE=0,
+ MBEDTLS_PKCS7_DATA,
+ MBEDTLS_PKCS7_SIGNED_DATA,
+ MBEDTLS_PKCS7_ENVELOPED_DATA,
+ MBEDTLS_PKCS7_SIGNED_AND_ENVELOPED_DATA,
+ MBEDTLS_PKCS7_DIGESTED_DATA,
+ MBEDTLS_PKCS7_ENCRYPTED_DATA,
+}
+mbedtls_pkcs7_type;
+
+/**
+ * Structure holding PKCS7 signer info
+ */
+typedef struct mbedtls_pkcs7_signer_info
+{
+ int MBEDTLS_PRIVATE(version);
+ mbedtls_x509_buf MBEDTLS_PRIVATE(serial);
+ mbedtls_x509_name MBEDTLS_PRIVATE(issuer);
+ mbedtls_x509_buf MBEDTLS_PRIVATE(issuer_raw);
+ mbedtls_x509_buf MBEDTLS_PRIVATE(alg_identifier);
+ mbedtls_x509_buf MBEDTLS_PRIVATE(sig_alg_identifier);
+ mbedtls_x509_buf MBEDTLS_PRIVATE(sig);
+ struct mbedtls_pkcs7_signer_info *MBEDTLS_PRIVATE(next);
+}
+mbedtls_pkcs7_signer_info;
+
+/**
+ * Structure holding attached data as part of PKCS7 signed data format
+ */
+typedef struct mbedtls_pkcs7_data
+{
+ mbedtls_pkcs7_buf MBEDTLS_PRIVATE(oid);
+ mbedtls_pkcs7_buf MBEDTLS_PRIVATE(data);
+}
+mbedtls_pkcs7_data;
+
+/**
+ * Structure holding the signed data section
+ */
+typedef struct mbedtls_pkcs7_signed_data
+{
+ int MBEDTLS_PRIVATE(version);
+ mbedtls_pkcs7_buf MBEDTLS_PRIVATE(digest_alg_identifiers);
+ struct mbedtls_pkcs7_data MBEDTLS_PRIVATE(content);
+ int MBEDTLS_PRIVATE(no_of_certs);
+ mbedtls_x509_crt MBEDTLS_PRIVATE(certs);
+ int MBEDTLS_PRIVATE(no_of_crls);
+ mbedtls_x509_crl MBEDTLS_PRIVATE(crl);
+ int MBEDTLS_PRIVATE(no_of_signers);
+ mbedtls_pkcs7_signer_info MBEDTLS_PRIVATE(signers);
+}
+mbedtls_pkcs7_signed_data;
+
+/**
+ * Structure holding PKCS7 structure, only signed data for now
+ */
+typedef struct mbedtls_pkcs7
+{
+ mbedtls_pkcs7_buf MBEDTLS_PRIVATE(raw);
+ mbedtls_pkcs7_buf MBEDTLS_PRIVATE(content_type_oid);
+ mbedtls_pkcs7_signed_data MBEDTLS_PRIVATE(signed_data);
+}
+mbedtls_pkcs7;
+
+/**
+ * \brief Initialize pkcs7 structure.
+ *
+ * \param pkcs7 pkcs7 structure.
+ */
+void mbedtls_pkcs7_init( mbedtls_pkcs7 *pkcs7 );
+
+/**
+ * \brief Parse a single DER formatted pkcs7 content.
+ *
+ * \param pkcs7 The pkcs7 structure to be filled by parser for the output.
+ * \param buf The buffer holding the DER encoded pkcs7.
+ * \param buflen The size in Bytes of \p buf.
+ *
+ * \note This function makes an internal copy of the PKCS7 buffer
+ * \p buf. In particular, \p buf may be destroyed or reused
+ * after this call returns.
+ *
+ * \return The \c mbedtls_pkcs7_type of \p buf, if successful.
+ * \return A negative error code on failure.
+ */
+int mbedtls_pkcs7_parse_der( mbedtls_pkcs7 *pkcs7, const unsigned char *buf,
+ const size_t buflen );
+
+/**
+ * \brief Verification of PKCS7 signature.
+ *
+ * \param pkcs7 PKCS7 structure containing signature.
+ * \param cert Certificate containing key to verify signature.
+ * \param data Plain data on which signature has to be verified.
+ * \param datalen Length of the data.
+ *
+ * \note This function internally calculates the hash on the supplied
+ * plain data for signature verification.
+ *
+ * \return A negative error code on failure.
+ */
+int mbedtls_pkcs7_signed_data_verify( mbedtls_pkcs7 *pkcs7,
+ const mbedtls_x509_crt *cert,
+ const unsigned char *data,
+ size_t datalen );
+
+/**
+ * \brief Verification of PKCS7 signature.
+ *
+ * \param pkcs7 PKCS7 structure containing signature.
+ * \param cert Certificate containing key to verify signature.
+ * \param hash Hash of the plain data on which signature has to be verified.
+ * \param hashlen Length of the hash.
+ *
+ * \note This function is different from mbedtls_pkcs7_signed_data_verify()
+ * in a way that it directly recieves the hash of the data.
+ *
+ * \return A negative error code on failure.
+ */
+int mbedtls_pkcs7_signed_hash_verify( mbedtls_pkcs7 *pkcs7,
+ const mbedtls_x509_crt *cert,
+ const unsigned char *hash, size_t hashlen);
+
+/**
+ * \brief Unallocate all PKCS7 data and zeroize the memory.
+ * It doesn't free pkcs7 itself. It should be done by the caller.
+ *
+ * \param pkcs7 PKCS7 structure to free.
+ */
+void mbedtls_pkcs7_free( mbedtls_pkcs7 *pkcs7 );
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* pkcs7.h */
diff --git a/include/mbedtls/ssl.h b/include/mbedtls/ssl.h
index 3a4d660..3165cd5 100644
--- a/include/mbedtls/ssl.h
+++ b/include/mbedtls/ssl.h
@@ -96,12 +96,16 @@
/* Error space gap */
/** Processing of the Certificate handshake message failed. */
#define MBEDTLS_ERR_SSL_BAD_CERTIFICATE -0x7A00
-/** Received NewSessionTicket Post Handshake Message */
+/* Error space gap */
+/**
+ * Received NewSessionTicket Post Handshake Message.
+ * This error code is experimental and may be changed or removed without notice.
+ */
#define MBEDTLS_ERR_SSL_RECEIVED_NEW_SESSION_TICKET -0x7B00
-/* Error space gap */
-/* Error space gap */
-/* Error space gap */
-/* Error space gap */
+/** Not possible to read early data */
+#define MBEDTLS_ERR_SSL_CANNOT_READ_EARLY_DATA -0x7B80
+/** Not possible to write early data */
+#define MBEDTLS_ERR_SSL_CANNOT_WRITE_EARLY_DATA -0x7C00
/* Error space gap */
/* Error space gap */
/* Error space gap */
@@ -664,7 +668,7 @@
MBEDTLS_SSL_SERVER_FINISHED,
MBEDTLS_SSL_FLUSH_BUFFERS,
MBEDTLS_SSL_HANDSHAKE_WRAPUP,
- MBEDTLS_SSL_HANDSHAKE_OVER,
+
MBEDTLS_SSL_NEW_SESSION_TICKET,
MBEDTLS_SSL_SERVER_HELLO_VERIFY_REQUEST_SENT,
MBEDTLS_SSL_HELLO_RETRY_REQUEST,
@@ -674,7 +678,9 @@
MBEDTLS_SSL_CLIENT_CCS_BEFORE_2ND_CLIENT_HELLO,
MBEDTLS_SSL_SERVER_CCS_AFTER_SERVER_HELLO,
MBEDTLS_SSL_SERVER_CCS_AFTER_HELLO_RETRY_REQUEST,
- MBEDTLS_SSL_NEW_SESSION_TICKET_FLUSH,
+ MBEDTLS_SSL_HANDSHAKE_OVER,
+ MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET,
+ MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET_FLUSH,
}
mbedtls_ssl_states;
@@ -804,6 +810,21 @@
typedef struct mbedtls_ssl_flight_item mbedtls_ssl_flight_item;
#endif
+#if defined(MBEDTLS_SSL_PROTO_TLS1_3) && defined(MBEDTLS_SSL_SESSION_TICKETS)
+typedef uint8_t mbedtls_ssl_tls13_ticket_flags;
+
+#define MBEDTLS_SSL_TLS1_3_TICKET_ALLOW_PSK_RESUMPTION \
+ MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK /* 1U << 0 */
+#define MBEDTLS_SSL_TLS1_3_TICKET_ALLOW_PSK_EPHEMERAL_RESUMPTION \
+ MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_EPHEMERAL /* 1U << 2 */
+#define MBEDTLS_SSL_TLS1_3_TICKET_ALLOW_EARLY_DATA ( 1U << 3 )
+
+#define MBEDTLS_SSL_TLS1_3_TICKET_FLAGS_MASK \
+ ( MBEDTLS_SSL_TLS1_3_TICKET_ALLOW_PSK_RESUMPTION | \
+ MBEDTLS_SSL_TLS1_3_TICKET_ALLOW_PSK_EPHEMERAL_RESUMPTION | \
+ MBEDTLS_SSL_TLS1_3_TICKET_ALLOW_EARLY_DATA )
+#endif /* MBEDTLS_SSL_PROTO_TLS1_3 && MBEDTLS_SSL_SESSION_TICKETS */
+
/**
* \brief Callback type: server-side session cache getter
*
@@ -1786,6 +1807,10 @@
* and #MBEDTLS_SSL_CID_DISABLED. */
#endif /* MBEDTLS_SSL_DTLS_CONNECTION_ID */
+#if defined(MBEDTLS_SSL_EARLY_DATA) && defined(MBEDTLS_SSL_CLI_C)
+ int MBEDTLS_PRIVATE(early_data_status);
+#endif /* MBEDTLS_SSL_EARLY_DATA && MBEDTLS_SSL_CLI_C */
+
/** Callback to export key block and master secret */
mbedtls_ssl_export_keys_t *MBEDTLS_PRIVATE(f_export_keys);
void *MBEDTLS_PRIVATE(p_export_keys); /*!< context for key export callback */
@@ -3828,9 +3853,10 @@
* \note The SSL context needs to be already set up. The right place
* to call this function is between \c mbedtls_ssl_setup() or
* \c mbedtls_ssl_reset() and \c mbedtls_ssl_handshake().
+ * Password cannot be empty (see RFC 8236).
*
* \param ssl SSL context
- * \param pw EC J-PAKE password (pre-shared secret)
+ * \param pw EC J-PAKE password (pre-shared secret). It cannot be empty
* \param pw_len length of pw in bytes
*
* \return 0 on success, or a negative error code.
@@ -4628,7 +4654,7 @@
*/
static inline int mbedtls_ssl_is_handshake_over( mbedtls_ssl_context *ssl )
{
- return( ssl->MBEDTLS_PRIVATE( state ) == MBEDTLS_SSL_HANDSHAKE_OVER );
+ return( ssl->MBEDTLS_PRIVATE( state ) >= MBEDTLS_SSL_HANDSHAKE_OVER );
}
/**
@@ -4868,6 +4894,151 @@
*/
int mbedtls_ssl_close_notify( mbedtls_ssl_context *ssl );
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+
+#if defined(MBEDTLS_SSL_SRV_C)
+/**
+ * \brief Read at most 'len' application data bytes while performing
+ * the handshake (early data).
+ *
+ * \note This function behaves mainly as mbedtls_ssl_read(). The
+ * specification of mbedtls_ssl_read() relevant to TLS 1.3
+ * (thus not the parts specific to (D)TLS 1.2) applies to this
+ * function and the present documentation is restricted to the
+ * differences with mbedtls_ssl_read().
+ *
+ * \param ssl SSL context
+ * \param buf buffer that will hold the data
+ * \param len maximum number of bytes to read
+ *
+ * \return One additional specific return value:
+ * #MBEDTLS_ERR_SSL_CANNOT_READ_EARLY_DATA.
+ *
+ * #MBEDTLS_ERR_SSL_CANNOT_READ_EARLY_DATA is returned when it
+ * is not possible to read early data for the SSL context
+ * \p ssl.
+ *
+ * It may have been possible and it is not possible
+ * anymore because the server received the End of Early Data
+ * message or the maximum number of allowed early data for the
+ * PSK in use has been reached.
+ *
+ * It may never have been possible and will never be possible
+ * for the SSL context \p ssl because the use of early data
+ * is disabled for that context or more generally the context
+ * is not suitably configured to enable early data or the
+ * client does not use early data or the first call to the
+ * function was done while the handshake was already too
+ * advanced to gather and accept early data.
+ *
+ * It is not possible to read early data for the SSL context
+ * \p ssl but this does not preclude for using it with
+ * mbedtls_ssl_write(), mbedtls_ssl_read() or
+ * mbedtls_ssl_handshake().
+ *
+ * \note When a server wants to retrieve early data, it is expected
+ * that this function starts the handshake for the SSL context
+ * \p ssl. But this is not mandatory.
+ *
+ */
+int mbedtls_ssl_read_early_data( mbedtls_ssl_context *ssl,
+ unsigned char *buf, size_t len );
+#endif /* MBEDTLS_SSL_SRV_C */
+
+#if defined(MBEDTLS_SSL_CLI_C)
+/**
+ * \brief Try to write exactly 'len' application data bytes while
+ * performing the handshake (early data).
+ *
+ * \note This function behaves mainly as mbedtls_ssl_write(). The
+ * specification of mbedtls_ssl_write() relevant to TLS 1.3
+ * (thus not the parts specific to (D)TLS1.2) applies to this
+ * function and the present documentation is restricted to the
+ * differences with mbedtls_ssl_write().
+ *
+ * \param ssl SSL context
+ * \param buf buffer holding the data
+ * \param len how many bytes must be written
+ *
+ * \return One additional specific return value:
+ * #MBEDTLS_ERR_SSL_CANNOT_WRITE_EARLY_DATA.
+ *
+ * #MBEDTLS_ERR_SSL_CANNOT_WRITE_EARLY_DATA is returned when it
+ * is not possible to write early data for the SSL context
+ * \p ssl.
+ *
+ * It may have been possible and it is not possible
+ * anymore because the client received the server Finished
+ * message, the server rejected early data or the maximum
+ * number of allowed early data for the PSK in use has been
+ * reached.
+ *
+ * It may never have been possible and will never be possible
+ * for the SSL context \p ssl because the use of early data
+ * is disabled for that context or more generally the context
+ * is not suitably configured to enable early data or the first
+ * call to the function was done while the handshake was
+ * already completed.
+ *
+ * It is not possible to write early data for the SSL context
+ * \p ssl but this does not preclude for using it with
+ * mbedtls_ssl_write(), mbedtls_ssl_read() or
+ * mbedtls_ssl_handshake().
+ *
+ * \note This function may write early data only if the SSL context
+ * has been configured for the handshake with a PSK for which
+ * early data is allowed.
+ *
+ * \note To maximize the number of early data that can be written in
+ * the course of the handshake, it is expected that this
+ * function starts the handshake for the SSL context \p ssl.
+ * But this is not mandatory.
+ *
+ * \note This function does not provide any information on whether
+ * the server has accepted or will accept early data or not.
+ * When it returns a positive value, it just means that it
+ * has written early data to the server. To know whether the
+ * server has accepted early data or not, you should call
+ * mbedtls_ssl_get_early_data_status() with the handshake
+ * completed.
+ */
+int mbedtls_ssl_write_early_data( mbedtls_ssl_context *ssl,
+ const unsigned char *buf, size_t len );
+
+#define MBEDTLS_SSL_EARLY_DATA_STATUS_NOT_SENT 0
+#define MBEDTLS_SSL_EARLY_DATA_STATUS_ACCEPTED 1
+#define MBEDTLS_SSL_EARLY_DATA_STATUS_REJECTED 2
+/**
+ * \brief Get the status of the negotiation of the use of early data.
+ *
+ * \param ssl The SSL context to query
+ *
+ * \return #MBEDTLS_ERR_SSL_BAD_INPUT_DATA if this function is called
+ * from the server-side.
+ *
+ * \return #MBEDTLS_ERR_SSL_BAD_INPUT_DATA if this function is called
+ * prior to completion of the handshake.
+ *
+ * \return #MBEDTLS_SSL_EARLY_DATA_STATUS_NOT_SENT if the client has
+ * not indicated the use of early data to the server.
+ *
+ * \return #MBEDTLS_SSL_EARLY_DATA_STATUS_ACCEPTED if the client has
+ * indicated the use of early data and the server has accepted
+ * it.
+ *
+ * \return #MBEDTLS_SSL_EARLY_DATA_STATUS_REJECTED if the client has
+ * indicated the use of early data but the server has rejected
+ * it. In this situation, the client may want to re-send the
+ * early data it may have tried to send by calling
+ * mbedtls_ssl_write_early_data() as ordinary post-handshake
+ * application data by calling mbedtls_ssl_write().
+ *
+ */
+int mbedtls_ssl_get_early_data_status( mbedtls_ssl_context *ssl );
+#endif /* MBEDTLS_SSL_CLI_C */
+
+#endif /* MBEDTLS_SSL_EARLY_DATA */
+
/**
* \brief Free referenced items in an SSL context and clear memory
*
diff --git a/include/psa/crypto_extra.h b/include/psa/crypto_extra.h
index 4f65398..33e2e77 100644
--- a/include/psa/crypto_extra.h
+++ b/include/psa/crypto_extra.h
@@ -1829,7 +1829,7 @@
*/
#if defined(MBEDTLS_PSA_BUILTIN_PAKE)
#define PSA_PAKE_OPERATION_INIT {PSA_ALG_NONE, 0, 0, 0, 0, \
- MBEDTLS_SVC_KEY_ID_INIT, \
+ NULL, 0 , \
PSA_PAKE_ROLE_NONE, {0}, 0, 0, \
{.dummy = 0}}
#else
@@ -1920,7 +1920,8 @@
#if defined(MBEDTLS_PSA_BUILTIN_PAKE)
unsigned int MBEDTLS_PRIVATE(input_step);
unsigned int MBEDTLS_PRIVATE(output_step);
- mbedtls_svc_key_id_t MBEDTLS_PRIVATE(password);
+ uint8_t* MBEDTLS_PRIVATE(password);
+ size_t MBEDTLS_PRIVATE(password_len);
psa_pake_role_t MBEDTLS_PRIVATE(role);
uint8_t MBEDTLS_PRIVATE(buffer[MBEDTLS_PSA_PAKE_BUFFER_SIZE]);
size_t MBEDTLS_PRIVATE(buffer_length);
diff --git a/include/psa/crypto_platform.h b/include/psa/crypto_platform.h
index 47ab1cf..573b33c 100644
--- a/include/psa/crypto_platform.h
+++ b/include/psa/crypto_platform.h
@@ -45,11 +45,6 @@
/* PSA requires several types which C99 provides in stdint.h. */
#include <stdint.h>
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
#if defined(MBEDTLS_PSA_CRYPTO_KEY_ID_ENCODES_OWNER)
/* Building for the PSA Crypto service on a PSA platform, a key owner is a PSA
diff --git a/library/CMakeLists.txt b/library/CMakeLists.txt
index 7c325f7..8106dab 100644
--- a/library/CMakeLists.txt
+++ b/library/CMakeLists.txt
@@ -49,8 +49,6 @@
md.c
md5.c
memory_buffer_alloc.c
- mps_reader.c
- mps_trace.c
nist_kw.c
oid.c
padlock.c
@@ -84,7 +82,6 @@
sha1.c
sha256.c
sha512.c
- ssl_debug_helpers_generated.c
threading.c
timing.c
version.c
@@ -92,6 +89,7 @@
)
set(src_x509
+ pkcs7.c
x509.c
x509_create.c
x509_crl.c
@@ -103,11 +101,14 @@
set(src_tls
debug.c
+ mps_reader.c
+ mps_trace.c
net_sockets.c
ssl_cache.c
ssl_ciphersuites.c
ssl_client.c
ssl_cookie.c
+ ssl_debug_helpers_generated.c
ssl_msg.c
ssl_ticket.c
ssl_tls.c
diff --git a/library/Makefile b/library/Makefile
index b1cdc7f..5073517 100644
--- a/library/Makefile
+++ b/library/Makefile
@@ -114,8 +114,6 @@
md.o \
md5.o \
memory_buffer_alloc.o \
- mps_reader.o \
- mps_trace.o \
nist_kw.o \
oid.o \
padlock.o \
@@ -149,7 +147,6 @@
sha1.o \
sha256.o \
sha512.o \
- ssl_debug_helpers_generated.o \
threading.o \
timing.o \
version.o \
@@ -168,15 +165,19 @@
x509_csr.o \
x509write_crt.o \
x509write_csr.o \
+ pkcs7.o \
# This line is intentionally left blank
OBJS_TLS= \
debug.o \
+ mps_reader.o \
+ mps_trace.o \
net_sockets.o \
ssl_cache.o \
ssl_ciphersuites.o \
ssl_client.o \
ssl_cookie.o \
+ ssl_debug_helpers_generated.o \
ssl_msg.o \
ssl_ticket.o \
ssl_tls.o \
diff --git a/library/aria.c b/library/aria.c
index 924f952..5e52eea 100644
--- a/library/aria.c
+++ b/library/aria.c
@@ -37,11 +37,6 @@
#include "mbedtls/platform_util.h"
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
/* Parameter validation macros */
#define ARIA_VALIDATE_RET( cond ) \
MBEDTLS_INTERNAL_VALIDATE_RET( cond, MBEDTLS_ERR_ARIA_BAD_INPUT_DATA )
diff --git a/library/bignum.c b/library/bignum.c
index 521787d..a68957a 100644
--- a/library/bignum.c
+++ b/library/bignum.c
@@ -252,6 +252,17 @@
memcpy( Y, &T, sizeof( mbedtls_mpi ) );
}
+static inline mbedtls_mpi_uint mpi_sint_abs( mbedtls_mpi_sint z )
+{
+ if( z >= 0 )
+ return( z );
+ /* Take care to handle the most negative value (-2^(biL-1)) correctly.
+ * A naive -z would have undefined behavior.
+ * Write this in a way that makes popular compilers happy (GCC, Clang,
+ * MSVC). */
+ return( (mbedtls_mpi_uint) 0 - (mbedtls_mpi_uint) z );
+}
+
/*
* Set value from integer
*/
@@ -263,7 +274,7 @@
MBEDTLS_MPI_CHK( mbedtls_mpi_grow( X, 1 ) );
memset( X->p, 0, X->n * ciL );
- X->p[0] = ( z < 0 ) ? -z : z;
+ X->p[0] = mpi_sint_abs( z );
X->s = ( z < 0 ) ? -1 : 1;
cleanup:
@@ -853,7 +864,7 @@
mbedtls_mpi_uint p[1];
MPI_VALIDATE_RET( X != NULL );
- *p = ( z < 0 ) ? -z : z;
+ *p = mpi_sint_abs( z );
Y.s = ( z < 0 ) ? -1 : 1;
Y.n = 1;
Y.p = p;
@@ -889,6 +900,11 @@
if( B->p[j - 1] != 0 )
break;
+ /* Exit early to avoid undefined behavior on NULL+0 when X->n == 0
+ * and B is 0 (of any size). */
+ if( j == 0 )
+ return( 0 );
+
MBEDTLS_MPI_CHK( mbedtls_mpi_grow( X, j ) );
/* j is the number of non-zero limbs of B. Add those to X. */
@@ -952,17 +968,15 @@
carry = mbedtls_mpi_core_sub( X->p, A->p, B->p, n );
if( carry != 0 )
{
- /* Propagate the carry to the first nonzero limb of X. */
- for( ; n < X->n && X->p[n] == 0; n++ )
- --X->p[n];
- /* If we ran out of space for the carry, it means that the result
- * is negative. */
- if( n == X->n )
+ /* Propagate the carry through the rest of X. */
+ carry = mbedtls_mpi_core_sub_int( X->p + n, X->p + n, carry, X->n - n );
+
+ /* If we have further carry/borrow, the result is negative. */
+ if( carry != 0 )
{
ret = MBEDTLS_ERR_MPI_NEGATIVE_VALUE;
goto cleanup;
}
- --X->p[n];
}
/* X should always be positive as a result of unsigned subtractions. */
@@ -972,10 +986,12 @@
return( ret );
}
-/*
- * Signed addition: X = A + B
+/* Common function for signed addition and subtraction.
+ * Calculate A + B * flip_B where flip_B is 1 or -1.
*/
-int mbedtls_mpi_add_mpi( mbedtls_mpi *X, const mbedtls_mpi *A, const mbedtls_mpi *B )
+static int add_sub_mpi( mbedtls_mpi *X,
+ const mbedtls_mpi *A, const mbedtls_mpi *B,
+ int flip_B )
{
int ret, s;
MPI_VALIDATE_RET( X != NULL );
@@ -983,16 +999,21 @@
MPI_VALIDATE_RET( B != NULL );
s = A->s;
- if( A->s * B->s < 0 )
+ if( A->s * B->s * flip_B < 0 )
{
- if( mbedtls_mpi_cmp_abs( A, B ) >= 0 )
+ int cmp = mbedtls_mpi_cmp_abs( A, B );
+ if( cmp >= 0 )
{
MBEDTLS_MPI_CHK( mbedtls_mpi_sub_abs( X, A, B ) );
- X->s = s;
+ /* If |A| = |B|, the result is 0 and we must set the sign bit
+ * to +1 regardless of which of A or B was negative. Otherwise,
+ * since |A| > |B|, the sign is the sign of A. */
+ X->s = cmp == 0 ? 1 : s;
}
else
{
MBEDTLS_MPI_CHK( mbedtls_mpi_sub_abs( X, B, A ) );
+ /* Since |A| < |B|, the sign is the opposite of A. */
X->s = -s;
}
}
@@ -1008,38 +1029,19 @@
}
/*
+ * Signed addition: X = A + B
+ */
+int mbedtls_mpi_add_mpi( mbedtls_mpi *X, const mbedtls_mpi *A, const mbedtls_mpi *B )
+{
+ return( add_sub_mpi( X, A, B, 1 ) );
+}
+
+/*
* Signed subtraction: X = A - B
*/
int mbedtls_mpi_sub_mpi( mbedtls_mpi *X, const mbedtls_mpi *A, const mbedtls_mpi *B )
{
- int ret, s;
- MPI_VALIDATE_RET( X != NULL );
- MPI_VALIDATE_RET( A != NULL );
- MPI_VALIDATE_RET( B != NULL );
-
- s = A->s;
- if( A->s * B->s > 0 )
- {
- if( mbedtls_mpi_cmp_abs( A, B ) >= 0 )
- {
- MBEDTLS_MPI_CHK( mbedtls_mpi_sub_abs( X, A, B ) );
- X->s = s;
- }
- else
- {
- MBEDTLS_MPI_CHK( mbedtls_mpi_sub_abs( X, B, A ) );
- X->s = -s;
- }
- }
- else
- {
- MBEDTLS_MPI_CHK( mbedtls_mpi_add_abs( X, A, B ) );
- X->s = s;
- }
-
-cleanup:
-
- return( ret );
+ return( add_sub_mpi( X, A, B, -1 ) );
}
/*
@@ -1052,7 +1054,7 @@
MPI_VALIDATE_RET( X != NULL );
MPI_VALIDATE_RET( A != NULL );
- p[0] = ( b < 0 ) ? -b : b;
+ p[0] = mpi_sint_abs( b );
B.s = ( b < 0 ) ? -1 : 1;
B.n = 1;
B.p = p;
@@ -1070,7 +1072,7 @@
MPI_VALIDATE_RET( X != NULL );
MPI_VALIDATE_RET( A != NULL );
- p[0] = ( b < 0 ) ? -b : b;
+ p[0] = mpi_sint_abs( b );
B.s = ( b < 0 ) ? -1 : 1;
B.n = 1;
B.p = p;
@@ -1408,7 +1410,7 @@
mbedtls_mpi_uint p[1];
MPI_VALIDATE_RET( A != NULL );
- p[0] = ( b < 0 ) ? -b : b;
+ p[0] = mpi_sint_abs( b );
B.s = ( b < 0 ) ? -1 : 1;
B.n = 1;
B.p = p;
diff --git a/library/bignum_core.c b/library/bignum_core.c
index 34aecda..41d3239 100644
--- a/library/bignum_core.c
+++ b/library/bignum_core.c
@@ -590,6 +590,22 @@
/* BEGIN MERGE SLOT 3 */
+mbedtls_mpi_uint mbedtls_mpi_core_sub_int( mbedtls_mpi_uint *X,
+ const mbedtls_mpi_uint *A,
+ mbedtls_mpi_uint c, /* doubles as carry */
+ size_t limbs )
+{
+ for( size_t i = 0; i < limbs; i++ )
+ {
+ mbedtls_mpi_uint s = A[i];
+ mbedtls_mpi_uint t = s - c;
+ c = ( t > s );
+ X[i] = t;
+ }
+
+ return( c );
+}
+
/* END MERGE SLOT 3 */
/* BEGIN MERGE SLOT 4 */
diff --git a/library/bignum_core.h b/library/bignum_core.h
index ad04e08..d48e705 100644
--- a/library/bignum_core.h
+++ b/library/bignum_core.h
@@ -504,6 +504,23 @@
/* BEGIN MERGE SLOT 3 */
+/**
+ * \brief Subtract unsigned integer from known-size large unsigned integers.
+ * Return the borrow.
+ *
+ * \param[out] X The result of the subtraction.
+ * \param[in] A The left operand.
+ * \param b The unsigned scalar to subtract.
+ * \param limbs Number of limbs of \p X and \p A.
+ *
+ * \return 1 if `A < b`.
+ * 0 if `A >= b`.
+ */
+mbedtls_mpi_uint mbedtls_mpi_core_sub_int( mbedtls_mpi_uint *X,
+ const mbedtls_mpi_uint *A,
+ mbedtls_mpi_uint b,
+ size_t limbs );
+
/* END MERGE SLOT 3 */
/* BEGIN MERGE SLOT 4 */
diff --git a/library/bignum_mod.c b/library/bignum_mod.c
index 13108c5..7a5539d 100644
--- a/library/bignum_mod.c
+++ b/library/bignum_mod.c
@@ -39,7 +39,7 @@
mbedtls_mpi_uint *p,
size_t p_limbs )
{
- if( p_limbs < m->limbs || !mbedtls_mpi_core_lt_ct( m->p, p, p_limbs ) )
+ if( p_limbs != m->limbs || !mbedtls_mpi_core_lt_ct( p, m->p, m->limbs ) )
return( MBEDTLS_ERR_MPI_BAD_INPUT_DATA );
r->limbs = m->limbs;
@@ -50,7 +50,7 @@
void mbedtls_mpi_mod_residue_release( mbedtls_mpi_mod_residue *r )
{
- if ( r == NULL )
+ if( r == NULL )
return;
r->limbs = 0;
@@ -59,19 +59,18 @@
void mbedtls_mpi_mod_modulus_init( mbedtls_mpi_mod_modulus *m )
{
- if ( m == NULL )
+ if( m == NULL )
return;
m->p = NULL;
m->limbs = 0;
m->bits = 0;
- m->ext_rep = MBEDTLS_MPI_MOD_EXT_REP_INVALID;
m->int_rep = MBEDTLS_MPI_MOD_REP_INVALID;
}
void mbedtls_mpi_mod_modulus_free( mbedtls_mpi_mod_modulus *m )
{
- if ( m == NULL )
+ if( m == NULL )
return;
switch( m->int_rep )
@@ -96,7 +95,6 @@
m->p = NULL;
m->limbs = 0;
m->bits = 0;
- m->ext_rep = MBEDTLS_MPI_MOD_EXT_REP_INVALID;
m->int_rep = MBEDTLS_MPI_MOD_REP_INVALID;
}
@@ -112,17 +110,17 @@
mbedtls_mpi_init( &N );
mbedtls_mpi_init( &RR );
- if ( A == NULL || limbs == 0 || limbs >= ( MBEDTLS_MPI_MAX_LIMBS / 2 ) - 2 )
+ if( A == NULL || limbs == 0 || limbs >= ( MBEDTLS_MPI_MAX_LIMBS / 2 ) - 2 )
goto cleanup;
- if ( mbedtls_mpi_grow( &N, limbs ) )
+ if( mbedtls_mpi_grow( &N, limbs ) )
goto cleanup;
memcpy( N.p, A, sizeof(mbedtls_mpi_uint) * limbs );
ret = mbedtls_mpi_core_get_mont_r2_unsafe(&RR, &N);
- if ( ret == 0 )
+ if( ret == 0 )
{
*X = RR.p;
RR.p = NULL;
@@ -138,7 +136,6 @@
int mbedtls_mpi_mod_modulus_setup( mbedtls_mpi_mod_modulus *m,
const mbedtls_mpi_uint *p,
size_t p_limbs,
- mbedtls_mpi_mod_ext_rep ext_rep,
mbedtls_mpi_mod_rep_selector int_rep )
{
int ret = 0;
@@ -147,17 +144,6 @@
m->limbs = p_limbs;
m->bits = mbedtls_mpi_core_bitlen( p, p_limbs );
- switch( ext_rep )
- {
- case MBEDTLS_MPI_MOD_EXT_REP_LE:
- case MBEDTLS_MPI_MOD_EXT_REP_BE:
- m->ext_rep = ext_rep;
- break;
- default:
- ret = MBEDTLS_ERR_MPI_BAD_INPUT_DATA;
- goto exit;
- }
-
switch( int_rep )
{
case MBEDTLS_MPI_MOD_REP_MONTGOMERY:
@@ -209,7 +195,71 @@
/* END MERGE SLOT 6 */
/* BEGIN MERGE SLOT 7 */
+int mbedtls_mpi_mod_read( mbedtls_mpi_mod_residue *r,
+ const mbedtls_mpi_mod_modulus *m,
+ const unsigned char *buf,
+ size_t buflen,
+ mbedtls_mpi_mod_ext_rep ext_rep )
+{
+ int ret = MBEDTLS_ERR_MPI_BAD_INPUT_DATA;
+ /* Do our best to check if r and m have been set up */
+ if( r->limbs == 0 || m->limbs == 0 )
+ goto cleanup;
+ if( r->limbs != m->limbs )
+ goto cleanup;
+
+ ret = mbedtls_mpi_mod_raw_read( r->p, m, buf, buflen, ext_rep );
+ if( ret != 0 )
+ goto cleanup;
+
+ r->limbs = m->limbs;
+
+ if( m->int_rep == MBEDTLS_MPI_MOD_REP_MONTGOMERY )
+ ret = mbedtls_mpi_mod_raw_to_mont_rep( r->p, m );
+
+cleanup:
+ return ( ret );
+}
+
+int mbedtls_mpi_mod_write( const mbedtls_mpi_mod_residue *r,
+ const mbedtls_mpi_mod_modulus *m,
+ unsigned char *buf,
+ size_t buflen,
+ mbedtls_mpi_mod_ext_rep ext_rep )
+{
+ int ret = MBEDTLS_ERR_MPI_BAD_INPUT_DATA;
+
+ /* Do our best to check if r and m have been set up */
+ if( r->limbs == 0 || m->limbs == 0 )
+ goto cleanup;
+ if( r->limbs != m->limbs )
+ goto cleanup;
+
+ if( m->int_rep == MBEDTLS_MPI_MOD_REP_MONTGOMERY )
+ {
+ ret = mbedtls_mpi_mod_raw_from_mont_rep( r->p, m );
+ if( ret != 0 )
+ goto cleanup;
+ }
+
+ ret = mbedtls_mpi_mod_raw_write( r->p, m, buf, buflen, ext_rep );
+
+ if( m->int_rep == MBEDTLS_MPI_MOD_REP_MONTGOMERY )
+ {
+ /* If this fails, the value of r is corrupted and we want to return
+ * this error (as opposed to the error code from the write above) to
+ * let the caller know. If it succeeds, we want to return the error
+ * code from write above. */
+ int conv_ret = mbedtls_mpi_mod_raw_to_mont_rep( r->p, m );
+ if( ret == 0 )
+ ret = conv_ret;
+ }
+
+cleanup:
+
+ return ( ret );
+}
/* END MERGE SLOT 7 */
/* BEGIN MERGE SLOT 8 */
diff --git a/library/bignum_mod.h b/library/bignum_mod.h
index 29c26f2..d92f21e 100644
--- a/library/bignum_mod.h
+++ b/library/bignum_mod.h
@@ -64,7 +64,6 @@
const mbedtls_mpi_uint *p;
size_t limbs; // number of limbs
size_t bits; // bitlen of p
- mbedtls_mpi_mod_ext_rep ext_rep; // signals external representation (eg. byte order)
mbedtls_mpi_mod_rep_selector int_rep; // selector to signal the active member of the union
union rep
{
@@ -75,16 +74,27 @@
/** Setup a residue structure.
*
- * \param[out] r The address of residue to setup. The size is determined by
- * \p m.
- * (In particular, it must have at least as many limbs as the
- * modulus \p m.)
+ * The residue will be set up with the buffer \p p and modulus \p m.
+ *
+ * The memory pointed to by \p p will be used by the resulting residue structure.
+ * The value at the pointed-to memory will be the initial value of \p r and must
+ * hold a value that is less than the modulus. This value will be used as-is
+ * and interpreted according to the value of the `m->int_rep` field.
+ *
+ * The modulus \p m will be the modulus associated with \p r. The residue \p r
+ * should only be used in operations where the modulus is \p m.
+ *
+ * \param[out] r The address of the residue to setup.
* \param[in] m The address of the modulus related to \p r.
- * \param[in] p The address of the limb array storing the value of \p r.
+ * \param[in] p The address of the limb array containing the value of \p r.
* The memory pointed to by \p p will be used by \p r and must
* not be modified in any way until after
- * mbedtls_mpi_mod_residue_release() is called.
- * \param p_limbs The number of limbs of \p p.
+ * mbedtls_mpi_mod_residue_release() is called. The data
+ * pointed to by \p p must be less than the modulus (the value
+ * pointed to by `m->p`) and already in the representation
+ * indicated by `m->int_rep`.
+ * \param p_limbs The number of limbs of \p p. Must be the same as the number
+ * of limbs in the modulus \p m.
*
* \return \c 0 if successful.
* \return #MBEDTLS_ERR_MPI_BAD_INPUT_DATA if \p p_limbs is less than the
@@ -121,19 +131,15 @@
* not be modified in any way until after
* mbedtls_mpi_mod_modulus_free() is called.
* \param p_limbs The number of limbs of \p p.
- * \param ext_rep The external representation to be used for residues
- * associated with \p m (see #mbedtls_mpi_mod_ext_rep).
* \param int_rep The internal representation to be used for residues
* associated with \p m (see #mbedtls_mpi_mod_rep_selector).
*
* \return \c 0 if successful.
- * \return #MBEDTLS_ERR_MPI_BAD_INPUT_DATA if \p ext_rep or \p int_rep is
- * invalid.
+ * \return #MBEDTLS_ERR_MPI_BAD_INPUT_DATA if \p int_rep is invalid.
*/
int mbedtls_mpi_mod_modulus_setup( mbedtls_mpi_mod_modulus *m,
const mbedtls_mpi_uint *p,
size_t p_limbs,
- mbedtls_mpi_mod_ext_rep ext_rep,
mbedtls_mpi_mod_rep_selector int_rep );
/** Free elements of a modulus structure.
@@ -173,7 +179,72 @@
/* END MERGE SLOT 6 */
/* BEGIN MERGE SLOT 7 */
+/** Read a residue from a byte buffer.
+ *
+ * The residue will be automatically converted to the internal representation
+ * based on the value of the `m->int_rep` field.
+ *
+ * The modulus \p m will be the modulus associated with \p r. The residue \p r
+ * should only be used in operations where the modulus is \p m or a modulus
+ * equivalent to \p m (in the sense that all their fields or memory pointed by
+ * their fields hold the same value).
+ *
+ * \param[out] r The address of the residue. It must have exactly the same
+ * number of limbs as the modulus \p m.
+ * \param[in] m The address of the modulus.
+ * \param[in] buf The input buffer to import from.
+ * \param buflen The length in bytes of \p buf.
+ * \param ext_rep The endianness of the number in the input buffer.
+ *
+ * \return \c 0 if successful.
+ * \return #MBEDTLS_ERR_MPI_BUFFER_TOO_SMALL if \p r isn't
+ * large enough to hold the value in \p buf.
+ * \return #MBEDTLS_ERR_MPI_BAD_INPUT_DATA if \p ext_rep
+ * is invalid or the value in the buffer is not less than \p m.
+ */
+int mbedtls_mpi_mod_read( mbedtls_mpi_mod_residue *r,
+ const mbedtls_mpi_mod_modulus *m,
+ const unsigned char *buf,
+ size_t buflen,
+ mbedtls_mpi_mod_ext_rep ext_rep );
+/** Write a residue into a byte buffer.
+ *
+ * The modulus \p m must be the modulus associated with \p r (see
+ * mbedtls_mpi_mod_residue_setup() and mbedtls_mpi_mod_read()).
+ *
+ * The residue will be automatically converted from the internal representation
+ * based on the value of `m->int_rep` field.
+ *
+ * \warning If the buffer is smaller than `m->bits`, the number of
+ * leading zeroes is leaked through timing. If \p r is
+ * secret, the caller must ensure that \p buflen is at least
+ * (`m->bits`+7)/8.
+ *
+ * \param[in] r The address of the residue. It must have the same number of
+ * limbs as the modulus \p m. (\p r is an input parameter, but
+ * its value will be modified during execution and restored
+ * before the function returns.)
+ * \param[in] m The address of the modulus associated with \r.
+ * \param[out] buf The output buffer to export to.
+ * \param buflen The length in bytes of \p buf.
+ * \param ext_rep The endianness in which the number should be written into
+ * the output buffer.
+ *
+ * \return \c 0 if successful.
+ * \return #MBEDTLS_ERR_MPI_BUFFER_TOO_SMALL if \p buf isn't
+ * large enough to hold the value of \p r (without leading
+ * zeroes).
+ * \return #MBEDTLS_ERR_MPI_BAD_INPUT_DATA if \p ext_rep is invalid.
+ * \return #MBEDTLS_ERR_MPI_ALLOC_FAILED if couldn't allocate enough
+ * memory for conversion. Can occur only for moduli with
+ * MBEDTLS_MPI_MOD_REP_MONTGOMERY.
+ */
+int mbedtls_mpi_mod_write( const mbedtls_mpi_mod_residue *r,
+ const mbedtls_mpi_mod_modulus *m,
+ unsigned char *buf,
+ size_t buflen,
+ mbedtls_mpi_mod_ext_rep ext_rep );
/* END MERGE SLOT 7 */
/* BEGIN MERGE SLOT 8 */
diff --git a/library/bignum_mod_raw.c b/library/bignum_mod_raw.c
index b43add7..22e56b7 100644
--- a/library/bignum_mod_raw.c
+++ b/library/bignum_mod_raw.c
@@ -52,11 +52,12 @@
int mbedtls_mpi_mod_raw_read( mbedtls_mpi_uint *X,
const mbedtls_mpi_mod_modulus *m,
const unsigned char *input,
- size_t input_length )
+ size_t input_length,
+ mbedtls_mpi_mod_ext_rep ext_rep )
{
int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
- switch( m->ext_rep )
+ switch( ext_rep )
{
case MBEDTLS_MPI_MOD_EXT_REP_LE:
ret = mbedtls_mpi_core_read_le( X, m->limbs,
@@ -87,9 +88,10 @@
int mbedtls_mpi_mod_raw_write( const mbedtls_mpi_uint *A,
const mbedtls_mpi_mod_modulus *m,
unsigned char *output,
- size_t output_length )
+ size_t output_length,
+ mbedtls_mpi_mod_ext_rep ext_rep )
{
- switch( m->ext_rep )
+ switch( ext_rep )
{
case MBEDTLS_MPI_MOD_EXT_REP_LE:
return( mbedtls_mpi_core_write_le( A, m->limbs,
@@ -108,6 +110,16 @@
/* BEGIN MERGE SLOT 2 */
+void mbedtls_mpi_mod_raw_sub( mbedtls_mpi_uint *X,
+ const mbedtls_mpi_uint *A,
+ const mbedtls_mpi_uint *B,
+ const mbedtls_mpi_mod_modulus *N )
+{
+ mbedtls_mpi_uint c = mbedtls_mpi_core_sub( X, A, B, N->limbs );
+
+ (void) mbedtls_mpi_core_add_if( X, N->p, N->limbs, (unsigned) c );
+}
+
/* END MERGE SLOT 2 */
/* BEGIN MERGE SLOT 3 */
@@ -119,7 +131,16 @@
/* END MERGE SLOT 4 */
/* BEGIN MERGE SLOT 5 */
-
+void mbedtls_mpi_mod_raw_add( mbedtls_mpi_uint *X,
+ const mbedtls_mpi_uint *A,
+ const mbedtls_mpi_uint *B,
+ const mbedtls_mpi_mod_modulus *N )
+{
+ mbedtls_mpi_uint carry, borrow;
+ carry = mbedtls_mpi_core_add( X, A, B, N->limbs );
+ borrow = mbedtls_mpi_core_sub( X, X, N->p, N->limbs );
+ (void) mbedtls_mpi_core_add_if( X, N->p, N->limbs, (unsigned) ( carry ^ borrow ) );
+}
/* END MERGE SLOT 5 */
/* BEGIN MERGE SLOT 6 */
diff --git a/library/bignum_mod_raw.h b/library/bignum_mod_raw.h
index f738e91..d7b6dd1 100644
--- a/library/bignum_mod_raw.h
+++ b/library/bignum_mod_raw.h
@@ -106,6 +106,7 @@
* \param[in] m The address of the modulus related to \p X.
* \param[in] input The input buffer to import from.
* \param input_length The length in bytes of \p input.
+ * \param ext_rep The endianness of the number in the input buffer.
*
* \return \c 0 if successful.
* \return #MBEDTLS_ERR_MPI_BUFFER_TOO_SMALL if \p X isn't
@@ -116,7 +117,8 @@
int mbedtls_mpi_mod_raw_read( mbedtls_mpi_uint *X,
const mbedtls_mpi_mod_modulus *m,
const unsigned char *input,
- size_t input_length );
+ size_t input_length,
+ mbedtls_mpi_mod_ext_rep ext_rep );
/** Export A into unsigned binary data.
*
@@ -126,6 +128,7 @@
* \param[in] m The address of the modulus related to \p A.
* \param[out] output The output buffer to export to.
* \param output_length The length in bytes of \p output.
+ * \param ext_rep The endianness in which the number should be written into the output buffer.
*
* \return \c 0 if successful.
* \return #MBEDTLS_ERR_MPI_BUFFER_TOO_SMALL if \p output isn't
@@ -136,7 +139,8 @@
int mbedtls_mpi_mod_raw_write( const mbedtls_mpi_uint *A,
const mbedtls_mpi_mod_modulus *m,
unsigned char *output,
- size_t output_length );
+ size_t output_length,
+ mbedtls_mpi_mod_ext_rep ext_rep );
/* BEGIN MERGE SLOT 1 */
@@ -144,6 +148,28 @@
/* BEGIN MERGE SLOT 2 */
+/** \brief Subtract two MPIs, returning the residue modulo the specified
+ * modulus.
+ *
+ * The size of the operation is determined by \p N. \p A and \p B must have
+ * the same number of limbs as \p N.
+ *
+ * \p X may be aliased to \p A or \p B, or even both, but may not overlap
+ * either otherwise.
+ *
+ * \param[out] X The address of the result MPI.
+ * This must be initialized. Must have enough limbs to
+ * store the full value of the result.
+ * \param[in] A The address of the first MPI. This must be initialized.
+ * \param[in] B The address of the second MPI. This must be initialized.
+ * \param[in] N The address of the modulus. Used to perform a modulo
+ * operation on the result of the subtraction.
+ */
+void mbedtls_mpi_mod_raw_sub( mbedtls_mpi_uint *X,
+ const mbedtls_mpi_uint *A,
+ const mbedtls_mpi_uint *B,
+ const mbedtls_mpi_mod_modulus *N );
+
/* END MERGE SLOT 2 */
/* BEGIN MERGE SLOT 3 */
@@ -155,7 +181,28 @@
/* END MERGE SLOT 4 */
/* BEGIN MERGE SLOT 5 */
-
+/**
+ * \brief Perform a known-size modular addition.
+ *
+ * Calculate `A + B modulo N`.
+ *
+ * The number of limbs in each operand, and the result, is given by the
+ * modulus \p N.
+ *
+ * \p X may be aliased to \p A or \p B, or even both, but may not overlap
+ * either otherwise.
+ *
+ * \param[out] X The result of the modular addition.
+ * \param[in] A Little-endian presentation of the left operand. This
+ * must be smaller than \p N.
+ * \param[in] B Little-endian presentation of the right operand. This
+ * must be smaller than \p N.
+ * \param[in] N The address of the modulus.
+ */
+void mbedtls_mpi_mod_raw_add( mbedtls_mpi_uint *X,
+ const mbedtls_mpi_uint *A,
+ const mbedtls_mpi_uint *B,
+ const mbedtls_mpi_mod_modulus *N );
/* END MERGE SLOT 5 */
/* BEGIN MERGE SLOT 6 */
diff --git a/library/chacha20.c b/library/chacha20.c
index e53eb82..85d7461 100644
--- a/library/chacha20.c
+++ b/library/chacha20.c
@@ -36,11 +36,6 @@
#if !defined(MBEDTLS_CHACHA20_ALT)
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
#define ROTL32( value, amount ) \
( (uint32_t) ( (value) << (amount) ) | ( (value) >> ( 32 - (amount) ) ) )
diff --git a/library/cipher.c b/library/cipher.c
index dfb7329..dffe3ad 100644
--- a/library/cipher.c
+++ b/library/cipher.c
@@ -500,7 +500,7 @@
}
#endif
- return( 0 );
+ return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE );
}
#endif /* MBEDTLS_GCM_C || MBEDTLS_CHACHAPOLY_C */
@@ -1129,7 +1129,7 @@
}
#endif
- return( 0 );
+ return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE );
}
int mbedtls_cipher_check_tag( mbedtls_cipher_context_t *ctx,
@@ -1156,11 +1156,8 @@
}
#endif /* MBEDTLS_USE_PSA_CRYPTO */
- /* Status to return on a non-authenticated algorithm. It would make sense
- * to return MBEDTLS_ERR_CIPHER_INVALID_CONTEXT or perhaps
- * MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA, but at the time I write this our
- * unit tests assume 0. */
- ret = 0;
+ /* Status to return on a non-authenticated algorithm. */
+ ret = MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE;
#if defined(MBEDTLS_GCM_C)
if( MBEDTLS_MODE_GCM == ctx->cipher_info->mode )
diff --git a/library/common.h b/library/common.h
index a630fcc..25d5294 100644
--- a/library/common.h
+++ b/library/common.h
@@ -25,6 +25,7 @@
#include "mbedtls/build_info.h"
+#include <stddef.h>
#include <stdint.h>
/** Helper to define a function as static except when building invasive tests.
@@ -68,6 +69,44 @@
*/
#define MBEDTLS_ALLOW_PRIVATE_ACCESS
+/** Return an offset into a buffer.
+ *
+ * This is just the addition of an offset to a pointer, except that this
+ * function also accepts an offset of 0 into a buffer whose pointer is null.
+ * (`p + n` has undefined behavior when `p` is null, even when `n == 0`.
+ * A null pointer is a valid buffer pointer when the size is 0, for example
+ * as the result of `malloc(0)` on some platforms.)
+ *
+ * \param p Pointer to a buffer of at least n bytes.
+ * This may be \p NULL if \p n is zero.
+ * \param n An offset in bytes.
+ * \return Pointer to offset \p n in the buffer \p p.
+ * Note that this is only a valid pointer if the size of the
+ * buffer is at least \p n + 1.
+ */
+static inline unsigned char *mbedtls_buffer_offset(
+ unsigned char *p, size_t n )
+{
+ return( p == NULL ? NULL : p + n );
+}
+
+/** Return an offset into a read-only buffer.
+ *
+ * Similar to mbedtls_buffer_offset(), but for const pointers.
+ *
+ * \param p Pointer to a buffer of at least n bytes.
+ * This may be \p NULL if \p n is zero.
+ * \param n An offset in bytes.
+ * \return Pointer to offset \p n in the buffer \p p.
+ * Note that this is only a valid pointer if the size of the
+ * buffer is at least \p n + 1.
+ */
+static inline const unsigned char *mbedtls_buffer_offset_const(
+ const unsigned char *p, size_t n )
+{
+ return( p == NULL ? NULL : p + n );
+}
+
/** Byte Reading Macros
*
* Given a multi-byte integer \p x, MBEDTLS_BYTE_n retrieves the n-th
diff --git a/library/debug.c b/library/debug.c
index bdbf6dd..6114a46 100644
--- a/library/debug.c
+++ b/library/debug.c
@@ -30,11 +30,6 @@
#include <stdio.h>
#include <string.h>
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
#define DEBUG_BUF_SIZE 512
static int debug_threshold = 0;
diff --git a/library/ecp.c b/library/ecp.c
index 37f6090..cd7d554 100644
--- a/library/ecp.c
+++ b/library/ecp.c
@@ -88,11 +88,6 @@
#include "ecp_internal_alt.h"
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
#if defined(MBEDTLS_SELF_TEST)
/*
* Counts of point addition and doubling, and field multiplications.
diff --git a/library/ecp_curves.c b/library/ecp_curves.c
index 7b14237..5cd2828 100644
--- a/library/ecp_curves.c
+++ b/library/ecp_curves.c
@@ -39,11 +39,6 @@
#define ECP_VALIDATE( cond ) \
MBEDTLS_INTERNAL_VALIDATE( cond )
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
#define ECP_MPI_INIT(s, n, p) {s, (n), (mbedtls_mpi_uint *)(p)}
#define ECP_MPI_INIT_ARRAY(x) \
diff --git a/library/mps_reader.c b/library/mps_reader.c
index 36958b4..6f823bd 100644
--- a/library/mps_reader.c
+++ b/library/mps_reader.c
@@ -29,11 +29,6 @@
#include <string.h>
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
#if defined(MBEDTLS_MPS_ENABLE_TRACE)
static int mbedtls_mps_trace_id = MBEDTLS_MPS_TRACE_BIT_READER;
#endif /* MBEDTLS_MPS_ENABLE_TRACE */
diff --git a/library/pkcs7.c b/library/pkcs7.c
new file mode 100644
index 0000000..ca0170a
--- /dev/null
+++ b/library/pkcs7.c
@@ -0,0 +1,753 @@
+/*
+ * Copyright The Mbed TLS Contributors
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may
+ * not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#include "common.h"
+
+#include "mbedtls/build_info.h"
+#if defined(MBEDTLS_PKCS7_C)
+#include "mbedtls/pkcs7.h"
+#include "mbedtls/x509.h"
+#include "mbedtls/asn1.h"
+#include "mbedtls/x509_crt.h"
+#include "mbedtls/x509_crl.h"
+#include "mbedtls/oid.h"
+#include "mbedtls/error.h"
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#if defined(MBEDTLS_FS_IO)
+#include <sys/types.h>
+#include <sys/stat.h>
+#endif
+
+#include "mbedtls/platform.h"
+#include "mbedtls/platform_util.h"
+
+#if defined(MBEDTLS_HAVE_TIME)
+#include "mbedtls/platform_time.h"
+#endif
+#if defined(MBEDTLS_HAVE_TIME_DATE)
+#include <time.h>
+#endif
+
+/**
+ * Initializes the pkcs7 structure.
+ */
+void mbedtls_pkcs7_init( mbedtls_pkcs7 *pkcs7 )
+{
+ memset( pkcs7, 0, sizeof( *pkcs7 ) );
+}
+
+static int pkcs7_get_next_content_len( unsigned char **p, unsigned char *end,
+ size_t *len )
+{
+ int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+
+ ret = mbedtls_asn1_get_tag( p, end, len, MBEDTLS_ASN1_CONSTRUCTED
+ | MBEDTLS_ASN1_CONTEXT_SPECIFIC );
+ if( ret != 0 )
+ {
+ ret = MBEDTLS_ERROR_ADD( MBEDTLS_ERR_PKCS7_INVALID_FORMAT, ret );
+ }
+
+ return( ret );
+}
+
+/**
+ * version Version
+ * Version ::= INTEGER
+ **/
+static int pkcs7_get_version( unsigned char **p, unsigned char *end, int *ver )
+{
+ int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+
+ ret = mbedtls_asn1_get_int( p, end, ver );
+ if( ret != 0 )
+ ret = MBEDTLS_ERROR_ADD( MBEDTLS_ERR_PKCS7_INVALID_VERSION, ret );
+
+ /* If version != 1, return invalid version */
+ if( *ver != MBEDTLS_PKCS7_SUPPORTED_VERSION )
+ ret = MBEDTLS_ERR_PKCS7_INVALID_VERSION;
+
+ return( ret );
+}
+
+/**
+ * ContentInfo ::= SEQUENCE {
+ * contentType ContentType,
+ * content
+ * [0] EXPLICIT ANY DEFINED BY contentType OPTIONAL }
+ **/
+static int pkcs7_get_content_info_type( unsigned char **p, unsigned char *end,
+ mbedtls_pkcs7_buf *pkcs7 )
+{
+ size_t len = 0;
+ int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+ unsigned char *start = *p;
+
+ ret = mbedtls_asn1_get_tag( p, end, &len, MBEDTLS_ASN1_CONSTRUCTED
+ | MBEDTLS_ASN1_SEQUENCE );
+ if( ret != 0 ) {
+ *p = start;
+ ret = MBEDTLS_ERROR_ADD( MBEDTLS_ERR_PKCS7_INVALID_CONTENT_INFO, ret );
+ goto out;
+ }
+
+ ret = mbedtls_asn1_get_tag( p, end, &len, MBEDTLS_ASN1_OID );
+ if( ret != 0 ) {
+ *p = start;
+ ret = MBEDTLS_ERROR_ADD( MBEDTLS_ERR_PKCS7_INVALID_CONTENT_INFO, ret );
+ goto out;
+ }
+
+ pkcs7->tag = MBEDTLS_ASN1_OID;
+ pkcs7->len = len;
+ pkcs7->p = *p;
+ *p += len;
+
+out:
+ return( ret );
+}
+
+/**
+ * DigestAlgorithmIdentifier ::= AlgorithmIdentifier
+ *
+ * This is from x509.h
+ **/
+static int pkcs7_get_digest_algorithm( unsigned char **p, unsigned char *end,
+ mbedtls_x509_buf *alg )
+{
+ int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+
+ if( ( ret = mbedtls_asn1_get_alg_null( p, end, alg ) ) != 0 )
+ ret = MBEDTLS_ERROR_ADD( MBEDTLS_ERR_PKCS7_INVALID_ALG, ret );
+
+ return( ret );
+}
+
+/**
+ * DigestAlgorithmIdentifiers :: SET of DigestAlgorithmIdentifier
+ **/
+static int pkcs7_get_digest_algorithm_set( unsigned char **p,
+ unsigned char *end,
+ mbedtls_x509_buf *alg )
+{
+ size_t len = 0;
+ int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+
+ ret = mbedtls_asn1_get_tag( p, end, &len, MBEDTLS_ASN1_CONSTRUCTED
+ | MBEDTLS_ASN1_SET );
+ if( ret != 0 )
+ {
+ ret = MBEDTLS_ERROR_ADD( MBEDTLS_ERR_PKCS7_INVALID_ALG, ret );
+ goto out;
+ }
+
+ end = *p + len;
+
+ ret = mbedtls_asn1_get_alg_null( p, end, alg );
+ if( ret != 0 )
+ {
+ ret = MBEDTLS_ERROR_ADD( MBEDTLS_ERR_PKCS7_INVALID_ALG, ret );
+ goto out;
+ }
+
+ /** For now, it assumes there is only one digest algorithm specified **/
+ if ( *p != end )
+ ret = MBEDTLS_ERR_PKCS7_FEATURE_UNAVAILABLE;
+
+out:
+ return( ret );
+}
+
+/**
+ * certificates :: SET OF ExtendedCertificateOrCertificate,
+ * ExtendedCertificateOrCertificate ::= CHOICE {
+ * certificate Certificate -- x509,
+ * extendedCertificate[0] IMPLICIT ExtendedCertificate }
+ * Return number of certificates added to the signed data,
+ * 0 or higher is valid.
+ * Return negative error code for failure.
+ **/
+static int pkcs7_get_certificates( unsigned char **p, unsigned char *end,
+ mbedtls_x509_crt *certs )
+{
+ int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+ size_t len1 = 0;
+ size_t len2 = 0;
+ unsigned char *end_set, *end_cert, *start;
+
+ if( ( ret = mbedtls_asn1_get_tag( p, end, &len1, MBEDTLS_ASN1_CONSTRUCTED
+ | MBEDTLS_ASN1_CONTEXT_SPECIFIC ) ) != 0 )
+ {
+ if( ret == MBEDTLS_ERR_ASN1_UNEXPECTED_TAG )
+ ret = 0;
+ else
+ ret = MBEDTLS_ERROR_ADD( MBEDTLS_ERR_PKCS7_INVALID_FORMAT, ret );
+ goto out;
+ }
+ start = *p;
+ end_set = *p + len1;
+
+ ret = mbedtls_asn1_get_tag( p, end_set, &len2, MBEDTLS_ASN1_CONSTRUCTED
+ | MBEDTLS_ASN1_SEQUENCE );
+ if( ret != 0 )
+ {
+ ret = MBEDTLS_ERROR_ADD( MBEDTLS_ERR_PKCS7_INVALID_CERT, ret );
+ goto out;
+ }
+
+ end_cert = *p + len2;
+
+ /*
+ * This is to verify that there is only one signer certificate. It seems it is
+ * not easy to differentiate between the chain vs different signer's certificate.
+ * So, we support only the root certificate and the single signer.
+ * The behaviour would be improved with addition of multiple signer support.
+ */
+ if ( end_cert != end_set )
+ {
+ ret = MBEDTLS_ERR_PKCS7_FEATURE_UNAVAILABLE;
+ goto out;
+ }
+
+ *p = start;
+ if( ( ret = mbedtls_x509_crt_parse_der( certs, *p, len1 ) ) < 0 )
+ {
+ ret = MBEDTLS_ERR_PKCS7_INVALID_CERT;
+ goto out;
+ }
+
+ *p = *p + len1;
+
+ /*
+ * Since in this version we strictly support single certificate, and reaching
+ * here implies we have parsed successfully, we return 1.
+ */
+ ret = 1;
+
+out:
+ return( ret );
+}
+
+/**
+ * EncryptedDigest ::= OCTET STRING
+ **/
+static int pkcs7_get_signature( unsigned char **p, unsigned char *end,
+ mbedtls_pkcs7_buf *signature )
+{
+ int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+ size_t len = 0;
+
+ ret = mbedtls_asn1_get_tag( p, end, &len, MBEDTLS_ASN1_OCTET_STRING );
+ if( ret != 0 )
+ goto out;
+
+ signature->tag = MBEDTLS_ASN1_OCTET_STRING;
+ signature->len = len;
+ signature->p = *p;
+
+ *p = *p + len;
+
+out:
+ return( ret );
+}
+
+/**
+ * SignerInfo ::= SEQUENCE {
+ * version Version;
+ * issuerAndSerialNumber IssuerAndSerialNumber,
+ * digestAlgorithm DigestAlgorithmIdentifier,
+ * authenticatedAttributes
+ * [0] IMPLICIT Attributes OPTIONAL,
+ * digestEncryptionAlgorithm DigestEncryptionAlgorithmIdentifier,
+ * encryptedDigest EncryptedDigest,
+ * unauthenticatedAttributes
+ * [1] IMPLICIT Attributes OPTIONAL,
+ * Returns 0 if the signerInfo is valid.
+ * Return negative error code for failure.
+ * Structure must not contain vales for authenticatedAttributes
+ * and unauthenticatedAttributes.
+ **/
+static int pkcs7_get_signer_info( unsigned char **p, unsigned char *end,
+ mbedtls_pkcs7_signer_info *signer )
+{
+ unsigned char *end_signer;
+ int asn1_ret = 0, ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+ size_t len = 0;
+
+ asn1_ret = mbedtls_asn1_get_tag( p, end, &len, MBEDTLS_ASN1_CONSTRUCTED
+ | MBEDTLS_ASN1_SEQUENCE );
+ if( asn1_ret != 0 )
+ goto out;
+
+ end_signer = *p + len;
+
+ ret = pkcs7_get_version( p, end_signer, &signer->version );
+ if( ret != 0 )
+ goto out;
+
+ asn1_ret = mbedtls_asn1_get_tag( p, end_signer, &len,
+ MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE );
+ if( asn1_ret != 0 )
+ goto out;
+
+ /* Parsing IssuerAndSerialNumber */
+ signer->issuer_raw.p = *p;
+
+ asn1_ret = mbedtls_asn1_get_tag( p, end_signer, &len,
+ MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE );
+ if( asn1_ret != 0 )
+ goto out;
+
+ ret = mbedtls_x509_get_name( p, *p + len, &signer->issuer );
+ if( ret != 0 )
+ goto out;
+
+ signer->issuer_raw.len = *p - signer->issuer_raw.p;
+
+ ret = mbedtls_x509_get_serial( p, end_signer, &signer->serial );
+ if( ret != 0 )
+ goto out;
+
+ ret = pkcs7_get_digest_algorithm( p, end_signer, &signer->alg_identifier );
+ if( ret != 0 )
+ goto out;
+
+ /* Asssume authenticatedAttributes is nonexistent */
+
+ ret = pkcs7_get_digest_algorithm( p, end_signer, &signer->sig_alg_identifier );
+ if( ret != 0 )
+ goto out;
+
+ ret = pkcs7_get_signature( p, end_signer, &signer->sig );
+ if( ret != 0 )
+ goto out;
+
+ /* Do not permit any unauthenticated attributes */
+ if( *p != end_signer )
+ ret = MBEDTLS_ERR_PKCS7_INVALID_SIGNER_INFO;
+
+out:
+ if( asn1_ret != 0 )
+ ret = MBEDTLS_ERROR_ADD( MBEDTLS_ERR_PKCS7_INVALID_SIGNER_INFO,
+ asn1_ret );
+ else if( ret != 0 )
+ ret = MBEDTLS_ERR_PKCS7_INVALID_SIGNER_INFO;
+
+ return( ret );
+}
+
+static void pkcs7_free_signer_info( mbedtls_pkcs7_signer_info *signer )
+{
+ mbedtls_x509_name *name_cur;
+ mbedtls_x509_name *name_prv;
+
+ if( signer == NULL )
+ return;
+
+ name_cur = signer->issuer.next;
+ while( name_cur != NULL )
+ {
+ name_prv = name_cur;
+ name_cur = name_cur->next;
+ mbedtls_free( name_prv );
+ }
+}
+
+/**
+ * SignerInfos ::= SET of SignerInfo
+ * Return number of signers added to the signed data,
+ * 0 or higher is valid.
+ * Return negative error code for failure.
+ **/
+static int pkcs7_get_signers_info_set( unsigned char **p, unsigned char *end,
+ mbedtls_pkcs7_signer_info *signers_set )
+{
+ unsigned char *end_set;
+ int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+ int count = 0;
+ size_t len = 0;
+ mbedtls_pkcs7_signer_info *signer, *prev;
+
+ ret = mbedtls_asn1_get_tag( p, end, &len, MBEDTLS_ASN1_CONSTRUCTED
+ | MBEDTLS_ASN1_SET );
+ if( ret != 0 )
+ {
+ ret = MBEDTLS_ERROR_ADD( MBEDTLS_ERR_PKCS7_INVALID_SIGNER_INFO, ret );
+ goto out;
+ }
+
+ /* Detect zero signers */
+ if( len == 0 )
+ {
+ ret = 0;
+ goto out;
+ }
+
+ end_set = *p + len;
+
+ ret = pkcs7_get_signer_info( p, end_set, signers_set );
+ if( ret != 0 )
+ goto out;
+ count++;
+
+ prev = signers_set;
+ while( *p != end_set )
+ {
+ signer = mbedtls_calloc( 1, sizeof( mbedtls_pkcs7_signer_info ) );
+ if( !signer )
+ {
+ ret = MBEDTLS_ERR_PKCS7_ALLOC_FAILED;
+ goto cleanup;
+ }
+
+ ret = pkcs7_get_signer_info( p, end_set, signer );
+ if( ret != 0 ) {
+ mbedtls_free( signer );
+ goto cleanup;
+ }
+ prev->next = signer;
+ prev = signer;
+ count++;
+ }
+
+ ret = count;
+ goto out;
+
+cleanup:
+ signer = signers_set->next;
+ pkcs7_free_signer_info( signers_set );
+ while( signer )
+ {
+ prev = signer;
+ signer = signer->next;
+ pkcs7_free_signer_info( prev );
+ mbedtls_free( prev );
+ }
+
+out:
+ return( ret );
+}
+
+/**
+ * SignedData ::= SEQUENCE {
+ * version Version,
+ * digestAlgorithms DigestAlgorithmIdentifiers,
+ * contentInfo ContentInfo,
+ * certificates
+ * [0] IMPLICIT ExtendedCertificatesAndCertificates
+ * OPTIONAL,
+ * crls
+ * [0] IMPLICIT CertificateRevocationLists OPTIONAL,
+ * signerInfos SignerInfos }
+ */
+static int pkcs7_get_signed_data( unsigned char *buf, size_t buflen,
+ mbedtls_pkcs7_signed_data *signed_data )
+{
+ unsigned char *p = buf;
+ unsigned char *end = buf + buflen;
+ unsigned char *end_set;
+ size_t len = 0;
+ int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+ mbedtls_md_type_t md_alg;
+
+ ret = mbedtls_asn1_get_tag( &p, end, &len, MBEDTLS_ASN1_CONSTRUCTED
+ | MBEDTLS_ASN1_SEQUENCE );
+ if( ret != 0 )
+ {
+ ret = MBEDTLS_ERROR_ADD( MBEDTLS_ERR_PKCS7_INVALID_FORMAT, ret );
+ goto out;
+ }
+
+ end_set = p + len;
+
+ /* Get version of signed data */
+ ret = pkcs7_get_version( &p, end_set, &signed_data->version );
+ if( ret != 0 )
+ goto out;
+
+ /* Get digest algorithm */
+ ret = pkcs7_get_digest_algorithm_set( &p, end_set,
+ &signed_data->digest_alg_identifiers );
+ if( ret != 0 )
+ goto out;
+
+ ret = mbedtls_oid_get_md_alg( &signed_data->digest_alg_identifiers, &md_alg );
+ if( ret != 0 )
+ {
+ ret = MBEDTLS_ERR_PKCS7_INVALID_ALG;
+ goto out;
+ }
+
+ /* Do not expect any content */
+ ret = pkcs7_get_content_info_type( &p, end_set, &signed_data->content.oid );
+ if( ret != 0 )
+ goto out;
+
+ if( MBEDTLS_OID_CMP( MBEDTLS_OID_PKCS7_DATA, &signed_data->content.oid ) )
+ {
+ ret = MBEDTLS_ERR_PKCS7_INVALID_CONTENT_INFO;
+ goto out;
+ }
+
+ /* Look for certificates, there may or may not be any */
+ mbedtls_x509_crt_init( &signed_data->certs );
+ ret = pkcs7_get_certificates( &p, end_set, &signed_data->certs );
+ if( ret < 0 )
+ goto out;
+
+ signed_data->no_of_certs = ret;
+
+ /*
+ * Currently CRLs are not supported. If CRL exist, the parsing will fail
+ * at next step of getting signers info and return error as invalid
+ * signer info.
+ */
+
+ signed_data->no_of_crls = 0;
+
+ /* Get signers info */
+ ret = pkcs7_get_signers_info_set( &p, end_set, &signed_data->signers );
+ if( ret < 0 )
+ goto out;
+
+ signed_data->no_of_signers = ret;
+
+ /* Don't permit trailing data */
+ if ( p != end )
+ ret = MBEDTLS_ERR_PKCS7_INVALID_FORMAT;
+ else
+ ret = 0;
+
+out:
+ return( ret );
+}
+
+int mbedtls_pkcs7_parse_der( mbedtls_pkcs7 *pkcs7, const unsigned char *buf,
+ const size_t buflen )
+{
+ unsigned char *p;
+ unsigned char *end;
+ size_t len = 0;
+ int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+ int isoidset = 0;
+
+ if( !pkcs7 )
+ {
+ ret = MBEDTLS_ERR_PKCS7_BAD_INPUT_DATA;
+ goto out;
+ }
+
+ /* make an internal copy of the buffer for parsing */
+ pkcs7->raw.p = p = mbedtls_calloc( 1, buflen );
+ if( pkcs7->raw.p == NULL )
+ {
+ ret = MBEDTLS_ERR_PKCS7_ALLOC_FAILED;
+ goto out;
+ }
+ memcpy( p, buf, buflen );
+ pkcs7->raw.len = buflen;
+ end = p + buflen;
+
+ ret = pkcs7_get_content_info_type( &p, end, &pkcs7->content_type_oid );
+ if( ret != 0 )
+ {
+ len = buflen;
+ goto try_data;
+ }
+
+ if( ! MBEDTLS_OID_CMP( MBEDTLS_OID_PKCS7_DATA, &pkcs7->content_type_oid )
+ || ! MBEDTLS_OID_CMP( MBEDTLS_OID_PKCS7_ENCRYPTED_DATA, &pkcs7->content_type_oid )
+ || ! MBEDTLS_OID_CMP( MBEDTLS_OID_PKCS7_ENVELOPED_DATA, &pkcs7->content_type_oid )
+ || ! MBEDTLS_OID_CMP( MBEDTLS_OID_PKCS7_SIGNED_AND_ENVELOPED_DATA, &pkcs7->content_type_oid )
+ || ! MBEDTLS_OID_CMP( MBEDTLS_OID_PKCS7_DIGESTED_DATA, &pkcs7->content_type_oid )
+ || ! MBEDTLS_OID_CMP( MBEDTLS_OID_PKCS7_ENCRYPTED_DATA, &pkcs7->content_type_oid ) )
+ {
+ ret = MBEDTLS_ERR_PKCS7_FEATURE_UNAVAILABLE;
+ goto out;
+ }
+
+ if( MBEDTLS_OID_CMP( MBEDTLS_OID_PKCS7_SIGNED_DATA, &pkcs7->content_type_oid ) )
+ {
+ ret = MBEDTLS_ERR_PKCS7_BAD_INPUT_DATA;
+ goto out;
+ }
+
+ isoidset = 1;
+
+ ret = pkcs7_get_next_content_len( &p, end, &len );
+ if( ret != 0 )
+ goto out;
+
+try_data:
+ ret = pkcs7_get_signed_data( p, len, &pkcs7->signed_data );
+ if ( ret != 0 )
+ goto out;
+
+ if ( !isoidset )
+ {
+ pkcs7->content_type_oid.tag = MBEDTLS_ASN1_OID;
+ pkcs7->content_type_oid.len = MBEDTLS_OID_SIZE( MBEDTLS_OID_PKCS7_SIGNED_DATA );
+ pkcs7->content_type_oid.p = (unsigned char *)MBEDTLS_OID_PKCS7_SIGNED_DATA;
+ }
+
+ ret = MBEDTLS_PKCS7_SIGNED_DATA;
+
+out:
+ if ( ret < 0 )
+ mbedtls_pkcs7_free( pkcs7 );
+
+ return( ret );
+}
+
+static int mbedtls_pkcs7_data_or_hash_verify( mbedtls_pkcs7 *pkcs7,
+ const mbedtls_x509_crt *cert,
+ const unsigned char *data,
+ size_t datalen,
+ const int is_data_hash )
+{
+ int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+ unsigned char *hash;
+ mbedtls_pk_context pk_cxt = cert->pk;
+ const mbedtls_md_info_t *md_info;
+ mbedtls_md_type_t md_alg;
+ mbedtls_pkcs7_signer_info *signer;
+
+ if( pkcs7->signed_data.no_of_signers == 0 )
+ {
+ ret = MBEDTLS_ERR_PKCS7_INVALID_CERT;
+ goto out;
+ }
+
+ if( mbedtls_x509_time_is_past( &cert->valid_to ) ||
+ mbedtls_x509_time_is_future( &cert->valid_from ))
+ {
+ ret = MBEDTLS_ERR_PKCS7_CERT_DATE_INVALID;
+ goto out;
+ }
+
+ /*
+ * Potential TODOs
+ * Currently we iterate over all signers and return success if any of them
+ * verify.
+ *
+ * However, we could make this better by checking against the certificate's
+ * identification and SignerIdentifier fields first. That would also allow
+ * us to distinguish between 'no signature for key' and 'signature for key
+ * failed to validate'.
+ *
+ * We could also cache hashes by md, so if there are several sigs all using
+ * the same algo we don't recalculate the hash each time.
+ */
+ for( signer = &pkcs7->signed_data.signers; signer; signer = signer->next )
+ {
+ ret = mbedtls_oid_get_md_alg( &signer->alg_identifier, &md_alg );
+ if( ret != 0 )
+ {
+ ret = MBEDTLS_ERR_PKCS7_VERIFY_FAIL;
+ continue;
+ }
+
+ md_info = mbedtls_md_info_from_type( md_alg );
+ if( md_info == NULL )
+ {
+ ret = MBEDTLS_ERR_PKCS7_VERIFY_FAIL;
+ continue;
+ }
+
+ hash = mbedtls_calloc( mbedtls_md_get_size( md_info ), 1 );
+ if( hash == NULL ) {
+ ret = MBEDTLS_ERR_PKCS7_ALLOC_FAILED;
+ goto out;
+ }
+ if( is_data_hash )
+ {
+ if( datalen != mbedtls_md_get_size( md_info ))
+ ret = MBEDTLS_ERR_PKCS7_VERIFY_FAIL;
+ else
+ memcpy(hash, data, datalen);
+ }
+ else
+ {
+ ret = mbedtls_md( md_info, data, datalen, hash );
+ }
+ if( ret != 0 )
+ {
+ ret = MBEDTLS_ERR_PKCS7_VERIFY_FAIL;
+ mbedtls_free( hash );
+ continue;
+ }
+
+ ret = mbedtls_pk_verify( &pk_cxt, md_alg, hash,
+ mbedtls_md_get_size( md_info ),
+ signer->sig.p, signer->sig.len );
+ mbedtls_free( hash );
+
+ if( ret == 0 )
+ break;
+ }
+
+out:
+ return( ret );
+}
+int mbedtls_pkcs7_signed_data_verify( mbedtls_pkcs7 *pkcs7,
+ const mbedtls_x509_crt *cert,
+ const unsigned char *data,
+ size_t datalen )
+{
+ return( mbedtls_pkcs7_data_or_hash_verify( pkcs7, cert, data, datalen, 0 ) );
+}
+
+int mbedtls_pkcs7_signed_hash_verify( mbedtls_pkcs7 *pkcs7,
+ const mbedtls_x509_crt *cert,
+ const unsigned char *hash,
+ size_t hashlen )
+{
+ return( mbedtls_pkcs7_data_or_hash_verify( pkcs7, cert, hash, hashlen, 1 ) );
+}
+
+/*
+ * Unallocate all pkcs7 data
+ */
+void mbedtls_pkcs7_free( mbedtls_pkcs7 *pkcs7 )
+{
+ mbedtls_pkcs7_signer_info *signer_cur;
+ mbedtls_pkcs7_signer_info *signer_prev;
+
+ if( pkcs7 == NULL || pkcs7->raw.p == NULL )
+ return;
+
+ mbedtls_free( pkcs7->raw.p );
+
+ mbedtls_x509_crt_free( &pkcs7->signed_data.certs );
+ mbedtls_x509_crl_free( &pkcs7->signed_data.crl );
+
+ signer_cur = pkcs7->signed_data.signers.next;
+ pkcs7_free_signer_info( &pkcs7->signed_data.signers );
+ while( signer_cur != NULL )
+ {
+ signer_prev = signer_cur;
+ signer_cur = signer_prev->next;
+ pkcs7_free_signer_info( signer_prev );
+ mbedtls_free( signer_prev );
+ }
+
+ pkcs7->raw.p = NULL;
+}
+
+#endif
diff --git a/library/poly1305.c b/library/poly1305.c
index 0850f66..4d0cdee 100644
--- a/library/poly1305.c
+++ b/library/poly1305.c
@@ -32,11 +32,6 @@
#if !defined(MBEDTLS_POLY1305_ALT)
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
#define POLY1305_BLOCK_SIZE_BYTES ( 16U )
/*
diff --git a/library/psa_crypto.c b/library/psa_crypto.c
index 2ce5e43..e881f2f 100644
--- a/library/psa_crypto.c
+++ b/library/psa_crypto.c
@@ -877,20 +877,7 @@
return( PSA_SUCCESS );
}
-/** Get the description of a key given its identifier and policy constraints
- * and lock it.
- *
- * The key must have allow all the usage flags set in \p usage. If \p alg is
- * nonzero, the key must allow operations with this algorithm. If \p alg is
- * zero, the algorithm is not checked.
- *
- * In case of a persistent key, the function loads the description of the key
- * into a key slot if not already done.
- *
- * On success, the returned key slot is locked. It is the responsibility of
- * the caller to unlock the key slot when it does not access it anymore.
- */
-static psa_status_t psa_get_and_lock_key_slot_with_policy(
+psa_status_t psa_get_and_lock_key_slot_with_policy(
mbedtls_svc_key_id_t key,
psa_key_slot_t **p_slot,
psa_key_usage_t usage,
@@ -3467,8 +3454,8 @@
status = psa_driver_wrapper_cipher_encrypt(
&attributes, slot->key.data, slot->key.bytes,
alg, local_iv, default_iv_length, input, input_length,
- output + default_iv_length, output_size - default_iv_length,
- output_length );
+ mbedtls_buffer_offset( output, default_iv_length ),
+ output_size - default_iv_length, output_length );
exit:
unlock_status = psa_unlock_key_slot( slot );
diff --git a/library/psa_crypto_cipher.c b/library/psa_crypto_cipher.c
index 70dc74d..91a0e3b 100644
--- a/library/psa_crypto_cipher.c
+++ b/library/psa_crypto_cipher.c
@@ -516,10 +516,10 @@
if( status != PSA_SUCCESS )
goto exit;
- status = mbedtls_psa_cipher_finish( &operation,
- output + update_output_length,
- output_size - update_output_length,
- &finish_output_length );
+ status = mbedtls_psa_cipher_finish(
+ &operation,
+ mbedtls_buffer_offset( output, update_output_length ),
+ output_size - update_output_length, &finish_output_length );
if( status != PSA_SUCCESS )
goto exit;
@@ -563,17 +563,20 @@
goto exit;
}
- status = mbedtls_psa_cipher_update( &operation, input + operation.iv_length,
- input_length - operation.iv_length,
- output, output_size, &olength );
+ status = mbedtls_psa_cipher_update(
+ &operation,
+ mbedtls_buffer_offset_const( input, operation.iv_length ),
+ input_length - operation.iv_length,
+ output, output_size, &olength );
if( status != PSA_SUCCESS )
goto exit;
accumulated_length = olength;
- status = mbedtls_psa_cipher_finish( &operation, output + accumulated_length,
- output_size - accumulated_length,
- &olength );
+ status = mbedtls_psa_cipher_finish(
+ &operation,
+ mbedtls_buffer_offset( output, accumulated_length ),
+ output_size - accumulated_length, &olength );
if( status != PSA_SUCCESS )
goto exit;
diff --git a/library/psa_crypto_core.h b/library/psa_crypto_core.h
index 9863848..5cefa27 100644
--- a/library/psa_crypto_core.h
+++ b/library/psa_crypto_core.h
@@ -183,6 +183,24 @@
}
#endif
+/** Get the description of a key given its identifier and policy constraints
+ * and lock it.
+ *
+ * The key must have allow all the usage flags set in \p usage. If \p alg is
+ * nonzero, the key must allow operations with this algorithm. If \p alg is
+ * zero, the algorithm is not checked.
+ *
+ * In case of a persistent key, the function loads the description of the key
+ * into a key slot if not already done.
+ *
+ * On success, the returned key slot is locked. It is the responsibility of
+ * the caller to unlock the key slot when it does not access it anymore.
+ */
+psa_status_t psa_get_and_lock_key_slot_with_policy( mbedtls_svc_key_id_t key,
+ psa_key_slot_t **p_slot,
+ psa_key_usage_t usage,
+ psa_algorithm_t alg );
+
/** Completely wipe a slot in memory, including its policy.
*
* Persistent storage is not affected.
diff --git a/library/psa_crypto_pake.c b/library/psa_crypto_pake.c
index 870b5b5..659b712 100644
--- a/library/psa_crypto_pake.c
+++ b/library/psa_crypto_pake.c
@@ -248,6 +248,7 @@
psa_key_attributes_t attributes = psa_key_attributes_init();
psa_key_type_t type;
psa_key_usage_t usage;
+ psa_key_slot_t *slot = NULL;
if( operation->alg == PSA_ALG_NONE ||
operation->state != PSA_PAKE_STATE_SETUP )
@@ -273,7 +274,27 @@
if( ( usage & PSA_KEY_USAGE_DERIVE ) == 0 )
return( PSA_ERROR_NOT_PERMITTED );
- operation->password = password;
+ if( operation->password != NULL )
+ return( PSA_ERROR_BAD_STATE );
+
+ status = psa_get_and_lock_key_slot_with_policy( password, &slot,
+ PSA_KEY_USAGE_DERIVE,
+ PSA_ALG_JPAKE );
+ if( status != PSA_SUCCESS )
+ return( status );
+
+ operation->password = mbedtls_calloc( 1, slot->key.bytes );
+ if( operation->password == NULL )
+ {
+ psa_unlock_key_slot( slot );
+ return( PSA_ERROR_INSUFFICIENT_MEMORY );
+ }
+ memcpy( operation->password, slot->key.data, slot->key.bytes );
+ operation->password_len = slot->key.bytes;
+
+ status = psa_unlock_key_slot( slot );
+ if( status != PSA_SUCCESS )
+ return( status );
return( PSA_SUCCESS );
}
@@ -348,9 +369,7 @@
static psa_status_t psa_pake_ecjpake_setup( psa_pake_operation_t *operation )
{
int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
- psa_status_t status = PSA_ERROR_CORRUPTION_DETECTED;
mbedtls_ecjpake_role role;
- psa_key_slot_t *slot = NULL;
if( operation->role == PSA_PAKE_ROLE_CLIENT )
role = MBEDTLS_ECJPAKE_CLIENT;
@@ -359,22 +378,20 @@
else
return( PSA_ERROR_BAD_STATE );
- if( psa_is_valid_key_id( operation->password, 1 ) == 0 )
+ if( operation->password_len == 0 )
return( PSA_ERROR_BAD_STATE );
- status = psa_get_and_lock_key_slot( operation->password, &slot );
- if( status != PSA_SUCCESS )
- return( status );
-
-
ret = mbedtls_ecjpake_setup( &operation->ctx.ecjpake,
role,
MBEDTLS_MD_SHA256,
MBEDTLS_ECP_DP_SECP256R1,
- slot->key.data, slot->key.bytes );
+ operation->password,
+ operation->password_len );
- psa_unlock_key_slot( slot );
- slot = NULL;
+ mbedtls_platform_zeroize( operation->password, operation->password_len );
+ mbedtls_free( operation->password );
+ operation->password = NULL;
+ operation->password_len = 0;
if( ret != 0 )
return( mbedtls_ecjpake_to_psa_error( ret ) );
@@ -840,7 +857,11 @@
{
operation->input_step = PSA_PAKE_STEP_INVALID;
operation->output_step = PSA_PAKE_STEP_INVALID;
- operation->password = MBEDTLS_SVC_KEY_ID_INIT;
+ if( operation->password_len > 0 )
+ mbedtls_platform_zeroize( operation->password, operation->password_len );
+ mbedtls_free( operation->password );
+ operation->password = NULL;
+ operation->password_len = 0;
operation->role = PSA_PAKE_ROLE_NONE;
mbedtls_platform_zeroize( operation->buffer, MBEDTLS_PSA_PAKE_BUFFER_SIZE );
operation->buffer_length = 0;
diff --git a/library/ssl_misc.h b/library/ssl_misc.h
index ad8754c..1902d71 100644
--- a/library/ssl_misc.h
+++ b/library/ssl_misc.h
@@ -50,17 +50,13 @@
#include "mbedtls/sha512.h"
#endif
-#if defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED)
+#if defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED) && \
+ !defined(MBEDTLS_USE_PSA_CRYPTO)
#include "mbedtls/ecjpake.h"
#endif
#include "common.h"
-#if ( defined(__ARMCC_VERSION) || defined(_MSC_VER) ) && \
- !defined(inline) && !defined(__cplusplus)
-#define inline __inline
-#endif
-
/* Shorthand for restartable ECC */
#if defined(MBEDTLS_ECP_RESTARTABLE) && \
defined(MBEDTLS_SSL_CLI_C) && \
@@ -776,7 +772,13 @@
#endif /* MBEDTLS_ECDH_C || MBEDTLS_ECDSA_C */
#if defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED)
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ psa_pake_operation_t psa_pake_ctx; /*!< EC J-PAKE key exchange */
+ mbedtls_svc_key_id_t psa_pake_password;
+ uint8_t psa_pake_ctx_is_ok;
+#else
mbedtls_ecjpake_context ecjpake_ctx; /*!< EC J-PAKE key exchange */
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
#if defined(MBEDTLS_SSL_CLI_C)
unsigned char *ecjpake_cache; /*!< Cache for ClientHello ext */
size_t ecjpake_cache_len; /*!< Length of cached data */
@@ -2046,6 +2048,12 @@
size_t *out_len );
#endif /* MBEDTLS_ECDH_C */
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+int mbedtls_ssl_tls13_write_early_data_ext( mbedtls_ssl_context *ssl,
+ unsigned char *buf,
+ const unsigned char *end,
+ size_t *out_len );
+#endif /* MBEDTLS_SSL_EARLY_DATA */
#endif /* MBEDTLS_SSL_PROTO_TLS1_3 */
@@ -2487,6 +2495,52 @@
}
#endif /* MBEDTLS_USE_PSA_CRYPTO || MBEDTLS_SSL_PROTO_TLS1_3 */
+#if defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED) && \
+ defined(MBEDTLS_USE_PSA_CRYPTO)
+
+typedef enum {
+ MBEDTLS_ECJPAKE_ROUND_ONE,
+ MBEDTLS_ECJPAKE_ROUND_TWO
+} mbedtls_ecjpake_rounds_t;
+
+/**
+ * \brief Parse the provided input buffer for getting the first round
+ * of key exchange. This code is common between server and client
+ *
+ * \param pake_ctx [in] the PAKE's operation/context structure
+ * \param buf [in] input buffer to parse
+ * \param len [in] length of the input buffer
+ * \param round [in] either MBEDTLS_ECJPAKE_ROUND_ONE or
+ * MBEDTLS_ECJPAKE_ROUND_TWO
+ *
+ * \return 0 on success or a negative error code in case of failure
+ */
+int mbedtls_psa_ecjpake_read_round(
+ psa_pake_operation_t *pake_ctx,
+ const unsigned char *buf,
+ size_t len, mbedtls_ecjpake_rounds_t round );
+
+/**
+ * \brief Write the first round of key exchange into the provided output
+ * buffer. This code is common between server and client
+ *
+ * \param pake_ctx [in] the PAKE's operation/context structure
+ * \param buf [out] the output buffer in which data will be written to
+ * \param len [in] length of the output buffer
+ * \param olen [out] the length of the data really written on the buffer
+ * \param round [in] either MBEDTLS_ECJPAKE_ROUND_ONE or
+ * MBEDTLS_ECJPAKE_ROUND_TWO
+ *
+ * \return 0 on success or a negative error code in case of failure
+ */
+int mbedtls_psa_ecjpake_write_round(
+ psa_pake_operation_t *pake_ctx,
+ unsigned char *buf,
+ size_t len, size_t *olen,
+ mbedtls_ecjpake_rounds_t round );
+
+#endif //MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED && MBEDTLS_USE_PSA_CRYPTO
+
/**
* \brief TLS record protection modes
*/
diff --git a/library/ssl_msg.c b/library/ssl_msg.c
index c523b82..040dc80 100644
--- a/library/ssl_msg.c
+++ b/library/ssl_msg.c
@@ -2073,7 +2073,7 @@
MBEDTLS_SSL_DEBUG_MSG( 2, ( "timeout" ) );
mbedtls_ssl_set_timer( ssl, 0 );
- if( mbedtls_ssl_is_handshake_over( ssl ) == 0 )
+ if( ssl->state != MBEDTLS_SSL_HANDSHAKE_OVER )
{
if( ssl_double_retransmit_timeout( ssl ) != 0 )
{
@@ -5465,7 +5465,7 @@
MBEDTLS_SSL_DEBUG_MSG( 3, ( "NewSessionTicket received" ) );
mbedtls_ssl_handshake_set_state( ssl,
- MBEDTLS_SSL_NEW_SESSION_TICKET );
+ MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET );
return( MBEDTLS_ERR_SSL_WANT_READ );
}
@@ -5668,7 +5668,7 @@
}
#endif
- if( mbedtls_ssl_is_handshake_over( ssl ) == 0 )
+ if( ssl->state != MBEDTLS_SSL_HANDSHAKE_OVER )
{
ret = mbedtls_ssl_handshake( ssl );
if( ret != MBEDTLS_ERR_SSL_WAITING_SERVER_HELLO_RENEGO &&
@@ -5924,7 +5924,7 @@
}
#endif
- if( mbedtls_ssl_is_handshake_over( ssl ) == 0 )
+ if( ssl->state != MBEDTLS_SSL_HANDSHAKE_OVER )
{
if( ( ret = mbedtls_ssl_handshake( ssl ) ) != 0 )
{
diff --git a/library/ssl_tls.c b/library/ssl_tls.c
index da90b23..3d3491b 100644
--- a/library/ssl_tls.c
+++ b/library/ssl_tls.c
@@ -907,7 +907,12 @@
mbedtls_ecdh_init( &handshake->ecdh_ctx );
#endif
#if defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED)
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ handshake->psa_pake_ctx = psa_pake_operation_init();
+ handshake->psa_pake_password = MBEDTLS_SVC_KEY_ID_INIT;
+#else
mbedtls_ecjpake_init( &handshake->ecjpake_ctx );
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
#if defined(MBEDTLS_SSL_CLI_C)
handshake->ecjpake_cache = NULL;
handshake->ecjpake_cache_len = 0;
@@ -1850,6 +1855,73 @@
/*
* Set EC J-PAKE password for current handshake
*/
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+int mbedtls_ssl_set_hs_ecjpake_password( mbedtls_ssl_context *ssl,
+ const unsigned char *pw,
+ size_t pw_len )
+{
+ psa_pake_cipher_suite_t cipher_suite = psa_pake_cipher_suite_init();
+ psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
+ psa_pake_role_t psa_role;
+ psa_status_t status;
+
+ if( ssl->handshake == NULL || ssl->conf == NULL )
+ return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
+
+ if( ssl->conf->endpoint == MBEDTLS_SSL_IS_SERVER )
+ psa_role = PSA_PAKE_ROLE_SERVER;
+ else
+ psa_role = PSA_PAKE_ROLE_CLIENT;
+
+ /* Empty password is not valid */
+ if( ( pw == NULL) || ( pw_len == 0 ) )
+ return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
+
+ psa_set_key_usage_flags( &attributes, PSA_KEY_USAGE_DERIVE );
+ psa_set_key_algorithm( &attributes, PSA_ALG_JPAKE );
+ psa_set_key_type( &attributes, PSA_KEY_TYPE_PASSWORD );
+
+ status = psa_import_key( &attributes, pw, pw_len,
+ &ssl->handshake->psa_pake_password );
+ if( status != PSA_SUCCESS )
+ return( MBEDTLS_ERR_SSL_HW_ACCEL_FAILED );
+
+ psa_pake_cs_set_algorithm( &cipher_suite, PSA_ALG_JPAKE );
+ psa_pake_cs_set_primitive( &cipher_suite,
+ PSA_PAKE_PRIMITIVE( PSA_PAKE_PRIMITIVE_TYPE_ECC,
+ PSA_ECC_FAMILY_SECP_R1,
+ 256) );
+ psa_pake_cs_set_hash( &cipher_suite, PSA_ALG_SHA_256 );
+
+ status = psa_pake_setup( &ssl->handshake->psa_pake_ctx, &cipher_suite );
+ if( status != PSA_SUCCESS )
+ {
+ psa_destroy_key( ssl->handshake->psa_pake_password );
+ return( MBEDTLS_ERR_SSL_HW_ACCEL_FAILED );
+ }
+
+ status = psa_pake_set_role( &ssl->handshake->psa_pake_ctx, psa_role );
+ if( status != PSA_SUCCESS )
+ {
+ psa_destroy_key( ssl->handshake->psa_pake_password );
+ psa_pake_abort( &ssl->handshake->psa_pake_ctx );
+ return( MBEDTLS_ERR_SSL_HW_ACCEL_FAILED );
+ }
+
+ psa_pake_set_password_key( &ssl->handshake->psa_pake_ctx,
+ ssl->handshake->psa_pake_password );
+ if( status != PSA_SUCCESS )
+ {
+ psa_destroy_key( ssl->handshake->psa_pake_password );
+ psa_pake_abort( &ssl->handshake->psa_pake_ctx );
+ return( MBEDTLS_ERR_SSL_HW_ACCEL_FAILED );
+ }
+
+ ssl->handshake->psa_pake_ctx_is_ok = 1;
+
+ return( 0 );
+}
+#else /* MBEDTLS_USE_PSA_CRYPTO */
int mbedtls_ssl_set_hs_ecjpake_password( mbedtls_ssl_context *ssl,
const unsigned char *pw,
size_t pw_len )
@@ -1870,6 +1942,7 @@
MBEDTLS_ECP_DP_SECP256R1,
pw, pw_len ) );
}
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
#endif /* MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED */
#if defined(MBEDTLS_SSL_HANDSHAKE_WITH_PSK_ENABLED)
@@ -3602,7 +3675,7 @@
if( ssl == NULL ||
ssl->conf == NULL ||
ssl->handshake == NULL ||
- mbedtls_ssl_is_handshake_over( ssl ) == 1 )
+ ssl->state == MBEDTLS_SSL_HANDSHAKE_OVER )
{
return( MBEDTLS_ERR_SSL_BAD_INPUT_DATA );
}
@@ -3706,7 +3779,7 @@
MBEDTLS_SSL_DEBUG_MSG( 2, ( "=> handshake" ) );
/* Main handshake loop */
- while( mbedtls_ssl_is_handshake_over( ssl ) == 0 )
+ while( ssl->state != MBEDTLS_SSL_HANDSHAKE_OVER )
{
ret = mbedtls_ssl_handshake_step( ssl );
@@ -3908,8 +3981,15 @@
#if !defined(MBEDTLS_USE_PSA_CRYPTO) && defined(MBEDTLS_ECDH_C)
mbedtls_ecdh_free( &handshake->ecdh_ctx );
#endif
+
#if defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED)
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ psa_pake_abort( &handshake->psa_pake_ctx );
+ psa_destroy_key( handshake->psa_pake_password );
+ handshake->psa_pake_password = MBEDTLS_SVC_KEY_ID_INIT;
+#else
mbedtls_ecjpake_free( &handshake->ecjpake_ctx );
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
#if defined(MBEDTLS_SSL_CLI_C)
mbedtls_free( handshake->ecjpake_cache );
handshake->ecjpake_cache = NULL;
@@ -6123,6 +6203,55 @@
else
#endif
{
+#if defined(MBEDTLS_USE_PSA_CRYPTO) && \
+ defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED)
+ if( handshake->ciphersuite_info->key_exchange == MBEDTLS_KEY_EXCHANGE_ECJPAKE )
+ {
+ psa_status_t status;
+ psa_algorithm_t alg = PSA_ALG_TLS12_ECJPAKE_TO_PMS;
+ psa_key_derivation_operation_t derivation =
+ PSA_KEY_DERIVATION_OPERATION_INIT;
+
+ MBEDTLS_SSL_DEBUG_MSG( 2, ( "perform PSA-based PMS KDF for ECJPAKE" ) );
+
+ handshake->pmslen = PSA_TLS12_ECJPAKE_TO_PMS_DATA_SIZE;
+
+ status = psa_key_derivation_setup( &derivation, alg );
+ if( status != PSA_SUCCESS )
+ return( MBEDTLS_ERR_SSL_HW_ACCEL_FAILED );
+
+ status = psa_key_derivation_set_capacity( &derivation,
+ PSA_TLS12_ECJPAKE_TO_PMS_DATA_SIZE );
+ if( status != PSA_SUCCESS )
+ {
+ psa_key_derivation_abort( &derivation );
+ return( MBEDTLS_ERR_SSL_HW_ACCEL_FAILED );
+ }
+
+ status = psa_pake_get_implicit_key( &handshake->psa_pake_ctx,
+ &derivation );
+ if( status != PSA_SUCCESS )
+ {
+ psa_key_derivation_abort( &derivation );
+ return( MBEDTLS_ERR_SSL_HW_ACCEL_FAILED );
+ }
+
+ status = psa_key_derivation_output_bytes( &derivation,
+ handshake->premaster,
+ handshake->pmslen );
+ if( status != PSA_SUCCESS )
+ {
+ psa_key_derivation_abort( &derivation );
+ return( MBEDTLS_ERR_SSL_HW_ACCEL_FAILED );
+ }
+
+ status = psa_key_derivation_abort( &derivation );
+ if( status != PSA_SUCCESS )
+ {
+ return( MBEDTLS_ERR_SSL_HW_ACCEL_FAILED );
+ }
+ }
+#endif
ret = handshake->tls_prf( handshake->premaster, handshake->pmslen,
lbl, seed, seed_len,
master,
@@ -7544,7 +7673,7 @@
#endif
mbedtls_ssl_handshake_wrapup_free_hs_transform( ssl );
- ssl->state++;
+ ssl->state = MBEDTLS_SSL_HANDSHAKE_OVER;
MBEDTLS_SSL_DEBUG_MSG( 3, ( "<= handshake wrapup" ) );
}
@@ -8306,6 +8435,99 @@
return( ret );
}
+#if defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED) && \
+ defined(MBEDTLS_USE_PSA_CRYPTO)
+int mbedtls_psa_ecjpake_read_round(
+ psa_pake_operation_t *pake_ctx,
+ const unsigned char *buf,
+ size_t len, mbedtls_ecjpake_rounds_t round )
+{
+ psa_status_t status;
+ size_t input_offset = 0;
+ /*
+ * At round one repeat the KEY_SHARE, ZK_PUBLIC & ZF_PROOF twice
+ * At round two perform a single cycle
+ */
+ unsigned int remaining_steps = ( round == MBEDTLS_ECJPAKE_ROUND_ONE) ? 2 : 1;
+
+ for( ; remaining_steps > 0; remaining_steps-- )
+ {
+ for( psa_pake_step_t step = PSA_PAKE_STEP_KEY_SHARE;
+ step <= PSA_PAKE_STEP_ZK_PROOF;
+ ++step )
+ {
+ /* Length is stored at the first byte */
+ size_t length = buf[input_offset];
+ input_offset += 1;
+
+ if( input_offset + length > len )
+ {
+ return MBEDTLS_ERR_SSL_HANDSHAKE_FAILURE;
+ }
+
+ status = psa_pake_input( pake_ctx, step,
+ buf + input_offset, length );
+ if( status != PSA_SUCCESS)
+ {
+ return psa_ssl_status_to_mbedtls( status );
+ }
+
+ input_offset += length;
+ }
+ }
+
+ if( input_offset != len )
+ return MBEDTLS_ERR_SSL_HANDSHAKE_FAILURE;
+
+ return( 0 );
+}
+
+int mbedtls_psa_ecjpake_write_round(
+ psa_pake_operation_t *pake_ctx,
+ unsigned char *buf,
+ size_t len, size_t *olen,
+ mbedtls_ecjpake_rounds_t round )
+{
+ psa_status_t status;
+ size_t output_offset = 0;
+ size_t output_len;
+ /*
+ * At round one repeat the KEY_SHARE, ZK_PUBLIC & ZF_PROOF twice
+ * At round two perform a single cycle
+ */
+ unsigned int remaining_steps = ( round == MBEDTLS_ECJPAKE_ROUND_ONE) ? 2 : 1;
+
+ for( ; remaining_steps > 0; remaining_steps-- )
+ {
+ for( psa_pake_step_t step = PSA_PAKE_STEP_KEY_SHARE;
+ step <= PSA_PAKE_STEP_ZK_PROOF;
+ ++step )
+ {
+ /*
+ * For each step, prepend 1 byte with the length of the data as
+ * given by psa_pake_output().
+ */
+ status = psa_pake_output( pake_ctx, step,
+ buf + output_offset + 1,
+ len - output_offset - 1,
+ &output_len );
+ if( status != PSA_SUCCESS )
+ {
+ return( psa_ssl_status_to_mbedtls( status ) );
+ }
+
+ *(buf + output_offset) = (uint8_t) output_len;
+
+ output_offset += output_len + 1;
+ }
+ }
+
+ *olen = output_offset;
+
+ return( 0 );
+}
+#endif //MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED && MBEDTLS_USE_PSA_CRYPTO
+
#if defined(MBEDTLS_USE_PSA_CRYPTO)
int mbedtls_ssl_get_key_exchange_md_tls1_2( mbedtls_ssl_context *ssl,
unsigned char *hash, size_t *hashlen,
@@ -8864,8 +9086,13 @@
#if defined(MBEDTLS_SSL_PROTO_TLS1_2) && defined(MBEDTLS_SSL_CLI_C)
#if defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED)
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ if( suite_info->key_exchange == MBEDTLS_KEY_EXCHANGE_ECJPAKE &&
+ ssl->handshake->psa_pake_ctx_is_ok != 1 )
+#else
if( suite_info->key_exchange == MBEDTLS_KEY_EXCHANGE_ECJPAKE &&
mbedtls_ecjpake_check( &ssl->handshake->ecjpake_ctx ) != 0 )
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
{
return( -1 );
}
diff --git a/library/ssl_tls12_client.c b/library/ssl_tls12_client.c
index 941b58b..5def8b6 100644
--- a/library/ssl_tls12_client.c
+++ b/library/ssl_tls12_client.c
@@ -132,13 +132,18 @@
{
int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
unsigned char *p = buf;
- size_t kkpp_len;
+ size_t kkpp_len = 0;
*olen = 0;
/* Skip costly extension if we can't use EC J-PAKE anyway */
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ if( ssl->handshake->psa_pake_ctx_is_ok != 1 )
+ return( 0 );
+#else
if( mbedtls_ecjpake_check( &ssl->handshake->ecjpake_ctx ) != 0 )
return( 0 );
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
MBEDTLS_SSL_DEBUG_MSG( 3,
( "client hello, adding ecjpake_kkpp extension" ) );
@@ -158,6 +163,18 @@
{
MBEDTLS_SSL_DEBUG_MSG( 3, ( "generating new ecjpake parameters" ) );
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ ret = mbedtls_psa_ecjpake_write_round(&ssl->handshake->psa_pake_ctx,
+ p + 2, end - p - 2, &kkpp_len,
+ MBEDTLS_ECJPAKE_ROUND_ONE );
+ if ( ret != 0 )
+ {
+ psa_destroy_key( ssl->handshake->psa_pake_password );
+ psa_pake_abort( &ssl->handshake->psa_pake_ctx );
+ MBEDTLS_SSL_DEBUG_RET( 1 , "psa_pake_output", ret );
+ return( ret );
+ }
+#else
ret = mbedtls_ecjpake_write_round_one( &ssl->handshake->ecjpake_ctx,
p + 2, end - p - 2, &kkpp_len,
ssl->conf->f_rng, ssl->conf->p_rng );
@@ -167,6 +184,7 @@
"mbedtls_ecjpake_write_round_one", ret );
return( ret );
}
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
ssl->handshake->ecjpake_cache = mbedtls_calloc( 1, kkpp_len );
if( ssl->handshake->ecjpake_cache == NULL )
@@ -846,10 +864,11 @@
ssl->handshake->ecdh_ctx.point_format = p[0];
#endif /* !MBEDTLS_USE_PSA_CRYPTO &&
( MBEDTLS_ECDH_C || MBEDTLS_ECDSA_C ) */
-#if defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED)
+#if !defined(MBEDTLS_USE_PSA_CRYPTO) && \
+ defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED)
mbedtls_ecjpake_set_point_format( &ssl->handshake->ecjpake_ctx,
p[0] );
-#endif
+#endif /* !MBEDTLS_USE_PSA_CRYPTO && MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED */
MBEDTLS_SSL_DEBUG_MSG( 4, ( "point format selected: %d", p[0] ) );
return( 0 );
}
@@ -886,6 +905,24 @@
ssl->handshake->ecjpake_cache = NULL;
ssl->handshake->ecjpake_cache_len = 0;
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ if( ( ret = mbedtls_psa_ecjpake_read_round(
+ &ssl->handshake->psa_pake_ctx, buf, len,
+ MBEDTLS_ECJPAKE_ROUND_ONE ) ) != 0 )
+ {
+ psa_destroy_key( ssl->handshake->psa_pake_password );
+ psa_pake_abort( &ssl->handshake->psa_pake_ctx );
+
+ MBEDTLS_SSL_DEBUG_RET( 1, "psa_pake_input round one", ret );
+ mbedtls_ssl_send_alert_message(
+ ssl,
+ MBEDTLS_SSL_ALERT_LEVEL_FATAL,
+ MBEDTLS_SSL_ALERT_MSG_HANDSHAKE_FAILURE );
+ return( ret );
+ }
+
+ return( 0 );
+#else
if( ( ret = mbedtls_ecjpake_read_round_one( &ssl->handshake->ecjpake_ctx,
buf, len ) ) != 0 )
{
@@ -898,6 +935,7 @@
}
return( 0 );
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
}
#endif /* MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED */
@@ -2293,6 +2331,47 @@
#if defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED)
if( ciphersuite_info->key_exchange == MBEDTLS_KEY_EXCHANGE_ECJPAKE )
{
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ /*
+ * The first 3 bytes are:
+ * [0] MBEDTLS_ECP_TLS_NAMED_CURVE
+ * [1, 2] elliptic curve's TLS ID
+ *
+ * However since we only support secp256r1 for now, we check only
+ * that TLS ID here
+ */
+ uint16_t read_tls_id = MBEDTLS_GET_UINT16_BE( p, 1 );
+ const mbedtls_ecp_curve_info *curve_info;
+
+ if( ( curve_info = mbedtls_ecp_curve_info_from_grp_id(
+ MBEDTLS_ECP_DP_SECP256R1 ) ) == NULL )
+ {
+ return( MBEDTLS_ERR_SSL_FEATURE_UNAVAILABLE );
+ }
+
+ if( ( *p != MBEDTLS_ECP_TLS_NAMED_CURVE ) ||
+ ( read_tls_id != curve_info->tls_id ) )
+ {
+ return( MBEDTLS_ERR_SSL_ILLEGAL_PARAMETER );
+ }
+
+ p += 3;
+
+ if( ( ret = mbedtls_psa_ecjpake_read_round(
+ &ssl->handshake->psa_pake_ctx, p, end - p,
+ MBEDTLS_ECJPAKE_ROUND_TWO ) ) != 0 )
+ {
+ psa_destroy_key( ssl->handshake->psa_pake_password );
+ psa_pake_abort( &ssl->handshake->psa_pake_ctx );
+
+ MBEDTLS_SSL_DEBUG_RET( 1, "psa_pake_input round two", ret );
+ mbedtls_ssl_send_alert_message(
+ ssl,
+ MBEDTLS_SSL_ALERT_LEVEL_FATAL,
+ MBEDTLS_SSL_ALERT_MSG_HANDSHAKE_FAILURE );
+ return( MBEDTLS_ERR_SSL_HANDSHAKE_FAILURE );
+ }
+#else
ret = mbedtls_ecjpake_read_round_two( &ssl->handshake->ecjpake_ctx,
p, end - p );
if( ret != 0 )
@@ -2304,6 +2383,7 @@
MBEDTLS_SSL_ALERT_MSG_HANDSHAKE_FAILURE );
return( MBEDTLS_ERR_SSL_HANDSHAKE_FAILURE );
}
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
}
else
#endif /* MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED */
@@ -2651,7 +2731,7 @@
for( size_t i = 0; i < sig_alg_len; i += 2 )
{
MBEDTLS_SSL_DEBUG_MSG( 3,
- ( "Supported Signature Algorithm found: %d,%d",
+ ( "Supported Signature Algorithm found: %02x %02x",
sig_alg[i], sig_alg[i + 1] ) );
}
#endif
@@ -3224,6 +3304,21 @@
{
header_len = 4;
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ unsigned char *out_p = ssl->out_msg + header_len;
+ unsigned char *end_p = ssl->out_msg + MBEDTLS_SSL_OUT_CONTENT_LEN -
+ header_len;
+ ret = mbedtls_psa_ecjpake_write_round( &ssl->handshake->psa_pake_ctx,
+ out_p, end_p - out_p, &content_len,
+ MBEDTLS_ECJPAKE_ROUND_TWO );
+ if ( ret != 0 )
+ {
+ psa_destroy_key( ssl->handshake->psa_pake_password );
+ psa_pake_abort( &ssl->handshake->psa_pake_ctx );
+ MBEDTLS_SSL_DEBUG_RET( 1 , "psa_pake_output", ret );
+ return( ret );
+ }
+#else
ret = mbedtls_ecjpake_write_round_two( &ssl->handshake->ecjpake_ctx,
ssl->out_msg + header_len,
MBEDTLS_SSL_OUT_CONTENT_LEN - header_len,
@@ -3243,6 +3338,7 @@
MBEDTLS_SSL_DEBUG_RET( 1, "mbedtls_ecjpake_derive_secret", ret );
return( ret );
}
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
}
else
#endif /* MBEDTLS_KEY_EXCHANGE_RSA_ENABLED */
diff --git a/library/ssl_tls12_server.c b/library/ssl_tls12_server.c
index 8ad1667..eeb579a 100644
--- a/library/ssl_tls12_server.c
+++ b/library/ssl_tls12_server.c
@@ -268,10 +268,11 @@
ssl->handshake->ecdh_ctx.point_format = p[0];
#endif /* !MBEDTLS_USE_PSA_CRYPTO &&
( MBEDTLS_ECDH_C || MBEDTLS_ECDSA_C ) */
-#if defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED)
+#if !defined(MBEDTLS_USE_PSA_CRYPTO) && \
+ defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED)
mbedtls_ecjpake_set_point_format( &ssl->handshake->ecjpake_ctx,
p[0] );
-#endif
+#endif /* !MBEDTLS_USE_PSA_CRYPTO && MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED */
MBEDTLS_SSL_DEBUG_MSG( 4, ( "point format selected: %d", p[0] ) );
return( 0 );
}
@@ -289,16 +290,37 @@
MBEDTLS_CHECK_RETURN_CRITICAL
static int ssl_parse_ecjpake_kkpp( mbedtls_ssl_context *ssl,
const unsigned char *buf,
- size_t len )
+ size_t len)
{
int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ if( ssl->handshake->psa_pake_ctx_is_ok != 1 )
+#else
if( mbedtls_ecjpake_check( &ssl->handshake->ecjpake_ctx ) != 0 )
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
{
MBEDTLS_SSL_DEBUG_MSG( 3, ( "skip ecjpake kkpp extension" ) );
return( 0 );
}
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ if( ( ret = mbedtls_psa_ecjpake_read_round(
+ &ssl->handshake->psa_pake_ctx, buf, len,
+ MBEDTLS_ECJPAKE_ROUND_ONE ) ) != 0 )
+ {
+ psa_destroy_key( ssl->handshake->psa_pake_password );
+ psa_pake_abort( &ssl->handshake->psa_pake_ctx );
+
+ MBEDTLS_SSL_DEBUG_RET( 1, "psa_pake_input round one", ret );
+ mbedtls_ssl_send_alert_message(
+ ssl,
+ MBEDTLS_SSL_ALERT_LEVEL_FATAL,
+ MBEDTLS_SSL_ALERT_MSG_HANDSHAKE_FAILURE );
+
+ return( ret );
+ }
+#else
if( ( ret = mbedtls_ecjpake_read_round_one( &ssl->handshake->ecjpake_ctx,
buf, len ) ) != 0 )
{
@@ -307,6 +329,7 @@
MBEDTLS_SSL_ALERT_MSG_ILLEGAL_PARAMETER );
return( ret );
}
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
/* Only mark the extension as OK when we're sure it is */
ssl->handshake->cli_exts |= MBEDTLS_TLS_EXT_ECJPAKE_KKPP_OK;
@@ -1990,6 +2013,18 @@
MBEDTLS_PUT_UINT16_BE( MBEDTLS_TLS_EXT_ECJPAKE_KKPP, p, 0 );
p += 2;
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ ret = mbedtls_psa_ecjpake_write_round( &ssl->handshake->psa_pake_ctx,
+ p + 2, end - p - 2, &kkpp_len,
+ MBEDTLS_ECJPAKE_ROUND_ONE );
+ if ( ret != 0 )
+ {
+ psa_destroy_key( ssl->handshake->psa_pake_password );
+ psa_pake_abort( &ssl->handshake->psa_pake_ctx );
+ MBEDTLS_SSL_DEBUG_RET( 1 , "psa_pake_output", ret );
+ return;
+ }
+#else
ret = mbedtls_ecjpake_write_round_one( &ssl->handshake->ecjpake_ctx,
p + 2, end - p - 2, &kkpp_len,
ssl->conf->f_rng, ssl->conf->p_rng );
@@ -1998,6 +2033,7 @@
MBEDTLS_SSL_DEBUG_RET( 1 , "mbedtls_ecjpake_write_round_one", ret );
return;
}
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
MBEDTLS_PUT_UINT16_BE( kkpp_len, p, 0 );
p += 2;
@@ -2525,10 +2561,15 @@
if( ! mbedtls_ssl_sig_alg_is_supported( ssl, *sig_alg ) )
continue;
- MBEDTLS_PUT_UINT16_BE( *sig_alg, p, sa_len );
+ /* Write elements at offsets starting from 1 (offset 0 is for the
+ * length). Thus the offset of each element is the length of the
+ * partial list including that element. */
sa_len += 2;
+ MBEDTLS_PUT_UINT16_BE( *sig_alg, p, sa_len );
+
}
+ /* Fill in list length. */
MBEDTLS_PUT_UINT16_BE( sa_len, p, 0 );
sa_len += 2;
p += sa_len;
@@ -2802,6 +2843,46 @@
if( ciphersuite_info->key_exchange == MBEDTLS_KEY_EXCHANGE_ECJPAKE )
{
int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ unsigned char *out_p = ssl->out_msg + ssl->out_msglen;
+ unsigned char *end_p = ssl->out_msg + MBEDTLS_SSL_OUT_CONTENT_LEN -
+ ssl->out_msglen;
+ size_t output_offset = 0;
+ size_t output_len = 0;
+ const mbedtls_ecp_curve_info *curve_info;
+
+ /*
+ * The first 3 bytes are:
+ * [0] MBEDTLS_ECP_TLS_NAMED_CURVE
+ * [1, 2] elliptic curve's TLS ID
+ *
+ * However since we only support secp256r1 for now, we hardcode its
+ * TLS ID here
+ */
+ if( ( curve_info = mbedtls_ecp_curve_info_from_grp_id(
+ MBEDTLS_ECP_DP_SECP256R1 ) ) == NULL )
+ {
+ return( MBEDTLS_ERR_SSL_FEATURE_UNAVAILABLE );
+ }
+ *out_p = MBEDTLS_ECP_TLS_NAMED_CURVE;
+ MBEDTLS_PUT_UINT16_BE( curve_info->tls_id, out_p, 1 );
+ output_offset += 3;
+
+ ret = mbedtls_psa_ecjpake_write_round( &ssl->handshake->psa_pake_ctx,
+ out_p + output_offset,
+ end_p - out_p - output_offset, &output_len,
+ MBEDTLS_ECJPAKE_ROUND_TWO );
+ if( ret != 0 )
+ {
+ psa_destroy_key( ssl->handshake->psa_pake_password );
+ psa_pake_abort( &ssl->handshake->psa_pake_ctx );
+ MBEDTLS_SSL_DEBUG_RET( 1 , "psa_pake_output", ret );
+ return( ret );
+ }
+
+ output_offset += output_len;
+ ssl->out_msglen += output_offset;
+#else
size_t len = 0;
ret = mbedtls_ecjpake_write_round_two(
@@ -2816,6 +2897,7 @@
}
ssl->out_msglen += len;
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
}
#endif /* MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED */
@@ -4033,6 +4115,18 @@
#if defined(MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED)
if( ciphersuite_info->key_exchange == MBEDTLS_KEY_EXCHANGE_ECJPAKE )
{
+#if defined(MBEDTLS_USE_PSA_CRYPTO)
+ if( ( ret = mbedtls_psa_ecjpake_read_round(
+ &ssl->handshake->psa_pake_ctx, p, end - p,
+ MBEDTLS_ECJPAKE_ROUND_TWO ) ) != 0 )
+ {
+ psa_destroy_key( ssl->handshake->psa_pake_password );
+ psa_pake_abort( &ssl->handshake->psa_pake_ctx );
+
+ MBEDTLS_SSL_DEBUG_RET( 1, "psa_pake_input round two", ret );
+ return( ret );
+ }
+#else
ret = mbedtls_ecjpake_read_round_two( &ssl->handshake->ecjpake_ctx,
p, end - p );
if( ret != 0 )
@@ -4049,6 +4143,7 @@
MBEDTLS_SSL_DEBUG_RET( 1, "mbedtls_ecjpake_derive_secret", ret );
return( ret );
}
+#endif /* MBEDTLS_USE_PSA_CRYPTO */
}
else
#endif /* MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED */
diff --git a/library/ssl_tls13_client.c b/library/ssl_tls13_client.c
index 9940a0e..0109f77 100644
--- a/library/ssl_tls13_client.c
+++ b/library/ssl_tls13_client.c
@@ -700,6 +700,19 @@
session != NULL && session->ticket != NULL );
}
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+static int ssl_tls13_early_data_has_valid_ticket( mbedtls_ssl_context *ssl )
+{
+ mbedtls_ssl_session *session = ssl->session_negotiate;
+ return( ssl->handshake->resume &&
+ session->tls_version == MBEDTLS_SSL_VERSION_TLS1_3 &&
+ ( session->ticket_flags &
+ MBEDTLS_SSL_TLS1_3_TICKET_ALLOW_EARLY_DATA ) &&
+ mbedtls_ssl_tls13_cipher_suite_is_offered(
+ ssl, session->ciphersuite ) );
+}
+#endif
+
MBEDTLS_CHECK_RETURN_CRITICAL
static int ssl_tls13_ticket_get_identity( mbedtls_ssl_context *ssl,
psa_algorithm_t *hash_alg,
@@ -1160,6 +1173,29 @@
}
#endif
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+ if( mbedtls_ssl_conf_tls13_some_psk_enabled( ssl ) &&
+ ssl_tls13_early_data_has_valid_ticket( ssl ) &&
+ ssl->conf->early_data_enabled == MBEDTLS_SSL_EARLY_DATA_ENABLED )
+ {
+ ret = mbedtls_ssl_tls13_write_early_data_ext( ssl, p, end, &ext_len );
+ if( ret != 0 )
+ return( ret );
+ p += ext_len;
+
+ /* Initializes the status to `rejected`. It will be updated to
+ * `accepted` if the EncryptedExtension message contain an early data
+ * indication extension.
+ */
+ ssl->early_data_status = MBEDTLS_SSL_EARLY_DATA_STATUS_REJECTED;
+ }
+ else
+ {
+ MBEDTLS_SSL_DEBUG_MSG( 2, ( "<= skip write early_data extension" ) );
+ ssl->early_data_status = MBEDTLS_SSL_EARLY_DATA_STATUS_NOT_SENT;
+ }
+#endif /* MBEDTLS_SSL_EARLY_DATA */
+
#if defined(MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_SOME_PSK_ENABLED)
/* For PSK-based key exchange we need the pre_shared_key extension
* and the psk_key_exchange_modes extension.
@@ -2024,6 +2060,21 @@
break;
#endif /* MBEDTLS_SSL_ALPN */
+
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+ case MBEDTLS_TLS_EXT_EARLY_DATA:
+
+ if( extension_data_len != 0 )
+ {
+ /* The message must be empty. */
+ MBEDTLS_SSL_PEND_FATAL_ALERT( MBEDTLS_SSL_ALERT_MSG_DECODE_ERROR,
+ MBEDTLS_ERR_SSL_DECODE_ERROR );
+ return( MBEDTLS_ERR_SSL_DECODE_ERROR );
+ }
+
+ break;
+#endif /* MBEDTLS_SSL_EARLY_DATA */
+
default:
MBEDTLS_SSL_PRINT_EXT(
3, MBEDTLS_SSL_HS_ENCRYPTED_EXTENSIONS,
@@ -2066,6 +2117,14 @@
MBEDTLS_SSL_PROC_CHK(
ssl_tls13_parse_encrypted_extensions( ssl, buf, buf + buf_len ) );
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+ if( ssl->handshake->received_extensions &
+ MBEDTLS_SSL_EXT_MASK( EARLY_DATA ) )
+ {
+ ssl->early_data_status = MBEDTLS_SSL_EARLY_DATA_STATUS_ACCEPTED;
+ }
+#endif
+
mbedtls_ssl_add_hs_msg_to_checksum( ssl, MBEDTLS_SSL_HS_ENCRYPTED_EXTENSIONS,
buf, buf_len );
@@ -2505,6 +2564,23 @@
switch( extension_type )
{
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+ case MBEDTLS_TLS_EXT_EARLY_DATA:
+ if( extension_data_len != 4 )
+ {
+ MBEDTLS_SSL_PEND_FATAL_ALERT(
+ MBEDTLS_SSL_ALERT_MSG_DECODE_ERROR,
+ MBEDTLS_ERR_SSL_DECODE_ERROR );
+ return( MBEDTLS_ERR_SSL_DECODE_ERROR );
+ }
+ if( ssl->session != NULL )
+ {
+ ssl->session->ticket_flags |=
+ MBEDTLS_SSL_TLS1_3_TICKET_ALLOW_EARLY_DATA;
+ }
+ break;
+#endif /* MBEDTLS_SSL_EARLY_DATA */
+
default:
MBEDTLS_SSL_PRINT_EXT(
3, MBEDTLS_SSL_HS_NEW_SESSION_TICKET,
@@ -2690,7 +2766,7 @@
}
/*
- * Handler for MBEDTLS_SSL_NEW_SESSION_TICKET
+ * Handler for MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET
*/
MBEDTLS_CHECK_RETURN_CRITICAL
static int ssl_tls13_process_new_session_ticket( mbedtls_ssl_context *ssl )
@@ -2804,7 +2880,7 @@
#endif /* MBEDTLS_SSL_TLS1_3_COMPATIBILITY_MODE */
#if defined(MBEDTLS_SSL_SESSION_TICKETS)
- case MBEDTLS_SSL_NEW_SESSION_TICKET:
+ case MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET:
ret = ssl_tls13_process_new_session_ticket( ssl );
if( ret != 0 )
break;
diff --git a/library/ssl_tls13_generic.c b/library/ssl_tls13_generic.c
index f854998..761c00e 100644
--- a/library/ssl_tls13_generic.c
+++ b/library/ssl_tls13_generic.c
@@ -1374,6 +1374,39 @@
#endif /* MBEDTLS_SSL_TLS1_3_COMPATIBILITY_MODE */
+/* Early Data Indication Extension
+ *
+ * struct {
+ * select ( Handshake.msg_type ) {
+ * ...
+ * case client_hello: Empty;
+ * case encrypted_extensions: Empty;
+ * };
+ * } EarlyDataIndication;
+ */
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+int mbedtls_ssl_tls13_write_early_data_ext( mbedtls_ssl_context *ssl,
+ unsigned char *buf,
+ const unsigned char *end,
+ size_t *out_len )
+{
+ unsigned char *p = buf;
+ *out_len = 0;
+ ((void) ssl);
+
+ MBEDTLS_SSL_CHK_BUF_PTR( p, end, 4 );
+
+ MBEDTLS_PUT_UINT16_BE( MBEDTLS_TLS_EXT_EARLY_DATA, p, 0 );
+ MBEDTLS_PUT_UINT16_BE( 0, p, 2 );
+
+ *out_len = 4;
+
+ mbedtls_ssl_tls13_set_hs_sent_ext_mask( ssl, MBEDTLS_TLS_EXT_EARLY_DATA );
+
+ return( 0 );
+}
+#endif /* MBEDTLS_SSL_EARLY_DATA */
+
/* Reset SSL context and update hash for handling HRR.
*
* Replace Transcript-Hash(X) by
diff --git a/library/ssl_tls13_server.c b/library/ssl_tls13_server.c
index 3cd0310..ce8767c 100644
--- a/library/ssl_tls13_server.c
+++ b/library/ssl_tls13_server.c
@@ -2628,7 +2628,7 @@
mbedtls_ssl_tls13_handshake_wrapup( ssl );
#if defined(MBEDTLS_SSL_SESSION_TICKETS)
- mbedtls_ssl_handshake_set_state( ssl, MBEDTLS_SSL_NEW_SESSION_TICKET );
+ mbedtls_ssl_handshake_set_state( ssl, MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET );
#else
mbedtls_ssl_handshake_set_state( ssl, MBEDTLS_SSL_HANDSHAKE_OVER );
#endif
@@ -2636,7 +2636,7 @@
}
/*
- * Handler for MBEDTLS_SSL_NEW_SESSION_TICKET
+ * Handler for MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET
*/
#define SSL_NEW_SESSION_TICKET_SKIP 0
#define SSL_NEW_SESSION_TICKET_WRITE 1
@@ -2872,7 +2872,7 @@
}
/*
- * Handler for MBEDTLS_SSL_NEW_SESSION_TICKET
+ * Handler for MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET
*/
static int ssl_tls13_write_new_session_ticket( mbedtls_ssl_context *ssl )
{
@@ -2908,8 +2908,8 @@
else
ssl->handshake->new_session_tickets_count--;
- mbedtls_ssl_handshake_set_state( ssl,
- MBEDTLS_SSL_NEW_SESSION_TICKET_FLUSH );
+ mbedtls_ssl_handshake_set_state(
+ ssl, MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET_FLUSH );
}
else
{
@@ -3045,7 +3045,7 @@
#endif /* MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_EPHEMERAL_ENABLED */
#if defined(MBEDTLS_SSL_SESSION_TICKETS)
- case MBEDTLS_SSL_NEW_SESSION_TICKET:
+ case MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET:
ret = ssl_tls13_write_new_session_ticket( ssl );
if( ret != 0 )
{
@@ -3054,9 +3054,9 @@
ret );
}
break;
- case MBEDTLS_SSL_NEW_SESSION_TICKET_FLUSH:
+ case MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET_FLUSH:
/* This state is necessary to do the flush of the New Session
- * Ticket message written in MBEDTLS_SSL_NEW_SESSION_TICKET
+ * Ticket message written in MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET
* as part of ssl_prepare_handshake_step.
*/
ret = 0;
@@ -3064,7 +3064,7 @@
if( ssl->handshake->new_session_tickets_count == 0 )
mbedtls_ssl_handshake_set_state( ssl, MBEDTLS_SSL_HANDSHAKE_OVER );
else
- mbedtls_ssl_handshake_set_state( ssl, MBEDTLS_SSL_NEW_SESSION_TICKET );
+ mbedtls_ssl_handshake_set_state( ssl, MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET );
break;
#endif /* MBEDTLS_SSL_SESSION_TICKETS */
diff --git a/programs/fuzz/.gitignore b/programs/fuzz/.gitignore
index 5dc0960..34e3ed0 100644
--- a/programs/fuzz/.gitignore
+++ b/programs/fuzz/.gitignore
@@ -1,6 +1,7 @@
fuzz_client
fuzz_dtlsclient
fuzz_dtlsserver
+fuzz_pkcs7
fuzz_privkey
fuzz_pubkey
fuzz_server
diff --git a/programs/fuzz/CMakeLists.txt b/programs/fuzz/CMakeLists.txt
index c7fcd35..7747744 100644
--- a/programs/fuzz/CMakeLists.txt
+++ b/programs/fuzz/CMakeLists.txt
@@ -12,6 +12,7 @@
fuzz_x509crl
fuzz_x509crt
fuzz_x509csr
+ fuzz_pkcs7
)
set(executables_with_common_c
diff --git a/programs/fuzz/fuzz_pkcs7.c b/programs/fuzz/fuzz_pkcs7.c
new file mode 100644
index 0000000..960007d
--- /dev/null
+++ b/programs/fuzz/fuzz_pkcs7.c
@@ -0,0 +1,19 @@
+#include <stdint.h>
+#include "mbedtls/pkcs7.h"
+
+int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) {
+#ifdef MBEDTLS_PKCS7_C
+ mbedtls_pkcs7 pkcs7;
+
+ mbedtls_pkcs7_init( &pkcs7 );
+
+ mbedtls_pkcs7_parse_der( &pkcs7, Data, Size );
+
+ mbedtls_pkcs7_free( &pkcs7 );
+#else
+ (void) Data;
+ (void) Size;
+#endif
+
+ return 0;
+}
diff --git a/programs/fuzz/fuzz_pkcs7.options b/programs/fuzz/fuzz_pkcs7.options
new file mode 100644
index 0000000..0824b19
--- /dev/null
+++ b/programs/fuzz/fuzz_pkcs7.options
@@ -0,0 +1,2 @@
+[libfuzzer]
+max_len = 65535
diff --git a/programs/pkey/dh_genprime.c b/programs/pkey/dh_genprime.c
index 2e696e5..331838b 100644
--- a/programs/pkey/dh_genprime.c
+++ b/programs/pkey/dh_genprime.c
@@ -157,8 +157,8 @@
goto exit;
}
- if( ( ret = mbedtls_mpi_write_file( "P = ", &P, 16, fout ) != 0 ) ||
- ( ret = mbedtls_mpi_write_file( "G = ", &G, 16, fout ) != 0 ) )
+ if( ( ( ret = mbedtls_mpi_write_file( "P = ", &P, 16, fout ) ) != 0 ) ||
+ ( ( ret = mbedtls_mpi_write_file( "G = ", &G, 16, fout ) ) != 0 ) )
{
mbedtls_printf( " failed\n ! mbedtls_mpi_write_file returned %d\n\n", ret );
fclose( fout );
diff --git a/programs/ssl/ssl_client2.c b/programs/ssl/ssl_client2.c
index 56efb3c..6aa295d 100644
--- a/programs/ssl/ssl_client2.c
+++ b/programs/ssl/ssl_client2.c
@@ -64,6 +64,7 @@
#define DFL_KEY_OPAQUE 0
#define DFL_KEY_PWD ""
#define DFL_PSK ""
+#define DFL_EARLY_DATA MBEDTLS_SSL_EARLY_DATA_DISABLED
#define DFL_PSK_OPAQUE 0
#define DFL_PSK_IDENTITY "Client_identity"
#define DFL_ECJPAKE_PW NULL
@@ -344,6 +345,14 @@
#define USAGE_SERIALIZATION ""
#endif
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+#define USAGE_EARLY_DATA \
+ " early_data=%%d default: 0 (disabled)\n" \
+ " options: 0 (disabled), 1 (enabled)\n"
+#else
+#define USAGE_EARLY_DATA ""
+#endif /* MBEDTLS_SSL_EARLY_DATA && MBEDTLS_SSL_PROTO_TLS1_3 */
+
#define USAGE_KEY_OPAQUE_ALGS \
" key_opaque_algs=%%s Allowed opaque key algorithms.\n" \
" comma-separated pair of values among the following:\n" \
@@ -422,6 +431,7 @@
USAGE_REPRODUCIBLE \
USAGE_CURVES \
USAGE_SIG_ALGS \
+ USAGE_EARLY_DATA \
USAGE_DHMLEN \
USAGE_KEY_OPAQUE_ALGS \
"\n"
@@ -533,6 +543,9 @@
* after renegotiation */
int reproducible; /* make communication reproducible */
int skip_close_notify; /* skip sending the close_notify alert */
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+ int early_data; /* support for early data */
+#endif
int query_config_mode; /* whether to read config */
int use_srtp; /* Support SRTP */
int force_srtp_profile; /* SRTP protection profile to use or all */
@@ -932,6 +945,9 @@
opt.alpn_string = DFL_ALPN_STRING;
opt.curves = DFL_CURVES;
opt.sig_algs = DFL_SIG_ALGS;
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+ opt.early_data = DFL_EARLY_DATA;
+#endif
opt.transport = DFL_TRANSPORT;
opt.hs_to_min = DFL_HS_TO_MIN;
opt.hs_to_max = DFL_HS_TO_MAX;
@@ -1189,7 +1205,24 @@
default: goto usage;
}
}
+
#if defined(MBEDTLS_SSL_PROTO_TLS1_3)
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+ else if( strcmp( p, "early_data" ) == 0 )
+ {
+ switch( atoi( q ) )
+ {
+ case 0:
+ opt.early_data = MBEDTLS_SSL_EARLY_DATA_DISABLED;
+ break;
+ case 1:
+ opt.early_data = MBEDTLS_SSL_EARLY_DATA_ENABLED;
+ break;
+ default: goto usage;
+ }
+ }
+#endif /* MBEDTLS_SSL_EARLY_DATA */
+
else if( strcmp( p, "tls13_kex_modes" ) == 0 )
{
if( strcmp( q, "psk" ) == 0 )
@@ -2091,6 +2124,10 @@
if( opt.max_version != DFL_MAX_VERSION )
mbedtls_ssl_conf_max_tls_version( &conf, opt.max_version );
+#if defined(MBEDTLS_SSL_EARLY_DATA)
+ mbedtls_ssl_tls13_conf_early_data( &conf, opt.early_data );
+#endif /* MBEDTLS_SSL_EARLY_DATA */
+
if( ( ret = mbedtls_ssl_setup( &ssl, &conf ) ) != 0 )
{
mbedtls_printf( " failed\n ! mbedtls_ssl_setup returned -0x%x\n\n",
diff --git a/scripts/config.py b/scripts/config.py
index 470c63d..7e58acd 100755
--- a/scripts/config.py
+++ b/scripts/config.py
@@ -311,6 +311,7 @@
if name in [
'MBEDTLS_DEBUG_C', # part of libmbedtls
'MBEDTLS_NET_C', # part of libmbedtls
+ 'MBEDTLS_PKCS7_C', # part of libmbedx509
]:
return False
return True
diff --git a/scripts/generate_errors.pl b/scripts/generate_errors.pl
index 41b0337..5395abf 100755
--- a/scripts/generate_errors.pl
+++ b/scripts/generate_errors.pl
@@ -52,7 +52,7 @@
SHA1 SHA256 SHA512 THREADING );
my @high_level_modules = qw( CIPHER DHM ECP MD
PEM PK PKCS12 PKCS5
- RSA SSL X509 );
+ RSA SSL X509 PKCS7 );
undef $/;
@@ -136,6 +136,7 @@
$define_name = "ASN1_PARSE" if ($define_name eq "ASN1");
$define_name = "SSL_TLS" if ($define_name eq "SSL");
$define_name = "PEM_PARSE,PEM_WRITE" if ($define_name eq "PEM");
+ $define_name = "PKCS7" if ($define_name eq "PKCS7");
my $include_name = $module_name;
$include_name =~ tr/A-Z/a-z/;
diff --git a/scripts/mbedtls_dev/bignum_common.py b/scripts/mbedtls_dev/bignum_common.py
index 279668f..67ea78d 100644
--- a/scripts/mbedtls_dev/bignum_common.py
+++ b/scripts/mbedtls_dev/bignum_common.py
@@ -14,11 +14,13 @@
# See the License for the specific language governing permissions and
# limitations under the License.
-import itertools
-import typing
-
from abc import abstractmethod
-from typing import Iterator, List, Tuple, TypeVar
+from typing import Iterator, List, Tuple, TypeVar, Any
+from itertools import chain
+
+from . import test_case
+from . import test_data_generation
+from .bignum_data import INPUTS_DEFAULT, MODULI_DEFAULT
T = TypeVar('T') #pylint: disable=invalid-name
@@ -38,7 +40,13 @@
raise ValueError("Not invertible")
def hex_to_int(val: str) -> int:
- return int(val, 16) if val else 0
+ """Implement the syntax accepted by mbedtls_test_read_mpi().
+
+ This is a superset of what is accepted by mbedtls_test_read_mpi_core().
+ """
+ if val in ['', '-']:
+ return 0
+ return int(val, 16)
def quote_str(val) -> str:
return "\"{}\"".format(val)
@@ -57,18 +65,10 @@
return (val.bit_length() + bits_in_limb - 1) // bits_in_limb
def combination_pairs(values: List[T]) -> List[Tuple[T, T]]:
- """Return all pair combinations from input values.
+ """Return all pair combinations from input values."""
+ return [(x, y) for x in values for y in values]
- The return value is cast, as older versions of mypy are unable to derive
- the specific type returned by itertools.combinations_with_replacement.
- """
- return typing.cast(
- List[Tuple[T, T]],
- list(itertools.combinations_with_replacement(values, 2))
- )
-
-
-class OperationCommon:
+class OperationCommon(test_data_generation.BaseTest):
"""Common features for bignum binary operations.
This adds functionality common in binary operation tests.
@@ -82,22 +82,106 @@
unique_combinations_only: Boolean to select if test case combinations
must be unique. If True, only A,B or B,A would be included as a test
case. If False, both A,B and B,A would be included.
+ input_style: Controls the way how test data is passed to the functions
+ in the generated test cases. "variable" passes them as they are
+ defined in the python source. "arch_split" pads the values with
+ zeroes depending on the architecture/limb size. If this is set,
+ test cases are generated for all architectures.
+ arity: the number of operands for the operation. Currently supported
+ values are 1 and 2.
"""
symbol = ""
- input_values = [] # type: List[str]
- input_cases = [] # type: List[Tuple[str, str]]
- unique_combinations_only = True
+ input_values = INPUTS_DEFAULT # type: List[str]
+ input_cases = [] # type: List[Any]
+ unique_combinations_only = False
+ input_styles = ["variable", "fixed", "arch_split"] # type: List[str]
+ input_style = "variable" # type: str
+ limb_sizes = [32, 64] # type: List[int]
+ arities = [1, 2]
+ arity = 2
- def __init__(self, val_a: str, val_b: str) -> None:
- self.arg_a = val_a
- self.arg_b = val_b
+ def __init__(self, val_a: str, val_b: str = "0", bits_in_limb: int = 32) -> None:
+ self.val_a = val_a
+ self.val_b = val_b
+ # Setting the int versions here as opposed to making them @properties
+ # provides earlier/more robust input validation.
self.int_a = hex_to_int(val_a)
self.int_b = hex_to_int(val_b)
+ if bits_in_limb not in self.limb_sizes:
+ raise ValueError("Invalid number of bits in limb!")
+ if self.input_style == "arch_split":
+ self.dependencies = ["MBEDTLS_HAVE_INT{:d}".format(bits_in_limb)]
+ self.bits_in_limb = bits_in_limb
+
+ @property
+ def boundary(self) -> int:
+ if self.arity == 1:
+ return self.int_a
+ elif self.arity == 2:
+ return max(self.int_a, self.int_b)
+ raise ValueError("Unsupported number of operands!")
+
+ @property
+ def limb_boundary(self) -> int:
+ return bound_mpi(self.boundary, self.bits_in_limb)
+
+ @property
+ def limbs(self) -> int:
+ return limbs_mpi(self.boundary, self.bits_in_limb)
+
+ @property
+ def hex_digits(self) -> int:
+ return 2 * (self.limbs * self.bits_in_limb // 8)
+
+ def format_arg(self, val) -> str:
+ if self.input_style not in self.input_styles:
+ raise ValueError("Unknown input style!")
+ if self.input_style == "variable":
+ return val
+ else:
+ return val.zfill(self.hex_digits)
+
+ def format_result(self, res) -> str:
+ res_str = '{:x}'.format(res)
+ return quote_str(self.format_arg(res_str))
+
+ @property
+ def arg_a(self) -> str:
+ return self.format_arg(self.val_a)
+
+ @property
+ def arg_b(self) -> str:
+ if self.arity == 1:
+ raise AttributeError("Operation is unary and doesn't have arg_b!")
+ return self.format_arg(self.val_b)
def arguments(self) -> List[str]:
- return [
- quote_str(self.arg_a), quote_str(self.arg_b)
- ] + self.result()
+ args = [quote_str(self.arg_a)]
+ if self.arity == 2:
+ args.append(quote_str(self.arg_b))
+ return args + self.result()
+
+ def description(self) -> str:
+ """Generate a description for the test case.
+
+ If not set, case_description uses the form A `symbol` B, where symbol
+ is used to represent the operation. Descriptions of each value are
+ generated to provide some context to the test case.
+ """
+ if not self.case_description:
+ if self.arity == 1:
+ self.case_description = "{} {:x}".format(
+ self.symbol, self.int_a
+ )
+ elif self.arity == 2:
+ self.case_description = "{:x} {} {:x}".format(
+ self.int_a, self.symbol, self.int_b
+ )
+ return super().description()
+
+ @property
+ def is_valid(self) -> bool:
+ return True
@abstractmethod
def result(self) -> List[str]:
@@ -115,15 +199,134 @@
Combinations are first generated from all input values, and then
specific cases provided.
"""
- if cls.unique_combinations_only:
- yield from combination_pairs(cls.input_values)
+ if cls.arity == 1:
+ yield from ((a, "0") for a in cls.input_values)
+ elif cls.arity == 2:
+ if cls.unique_combinations_only:
+ yield from combination_pairs(cls.input_values)
+ else:
+ yield from (
+ (a, b)
+ for a in cls.input_values
+ for b in cls.input_values
+ )
else:
- yield from (
- (a, b)
- for a in cls.input_values
- for b in cls.input_values
- )
- yield from cls.input_cases
+ raise ValueError("Unsupported number of operands!")
+
+ @classmethod
+ def generate_function_tests(cls) -> Iterator[test_case.TestCase]:
+ if cls.input_style not in cls.input_styles:
+ raise ValueError("Unknown input style!")
+ if cls.arity not in cls.arities:
+ raise ValueError("Unsupported number of operands!")
+ if cls.input_style == "arch_split":
+ test_objects = (cls(a, b, bits_in_limb=bil)
+ for a, b in cls.get_value_pairs()
+ for bil in cls.limb_sizes)
+ special_cases = (cls(*args, bits_in_limb=bil) # type: ignore
+ for args in cls.input_cases
+ for bil in cls.limb_sizes)
+ else:
+ test_objects = (cls(a, b)
+ for a, b in cls.get_value_pairs())
+ special_cases = (cls(*args) for args in cls.input_cases)
+ yield from (valid_test_object.create_test_case()
+ for valid_test_object in filter(
+ lambda test_object: test_object.is_valid,
+ chain(test_objects, special_cases)
+ )
+ )
+
+
+class ModOperationCommon(OperationCommon):
+ #pylint: disable=abstract-method
+ """Target for bignum mod_raw test case generation."""
+ moduli = MODULI_DEFAULT # type: List[str]
+
+ def __init__(self, val_n: str, val_a: str, val_b: str = "0",
+ bits_in_limb: int = 64) -> None:
+ super().__init__(val_a=val_a, val_b=val_b, bits_in_limb=bits_in_limb)
+ self.val_n = val_n
+ # Setting the int versions here as opposed to making them @properties
+ # provides earlier/more robust input validation.
+ self.int_n = hex_to_int(val_n)
+
+ @property
+ def boundary(self) -> int:
+ return self.int_n
+
+ @property
+ def arg_n(self) -> str:
+ return self.format_arg(self.val_n)
+
+ def arguments(self) -> List[str]:
+ return [quote_str(self.arg_n)] + super().arguments()
+
+ @property
+ def r(self) -> int: # pylint: disable=invalid-name
+ l = limbs_mpi(self.int_n, self.bits_in_limb)
+ return bound_mpi_limbs(l, self.bits_in_limb)
+
+ @property
+ def r_inv(self) -> int:
+ return invmod(self.r, self.int_n)
+
+ @property
+ def r2(self) -> int: # pylint: disable=invalid-name
+ return pow(self.r, 2)
+
+ @property
+ def is_valid(self) -> bool:
+ if self.int_a >= self.int_n:
+ return False
+ if self.arity == 2 and self.int_b >= self.int_n:
+ return False
+ return True
+
+ def description(self) -> str:
+ """Generate a description for the test case.
+
+ It uses the form A `symbol` B mod N, where symbol is used to represent
+ the operation.
+ """
+
+ if not self.case_description:
+ return super().description() + " mod {:x}".format(self.int_n)
+ return super().description()
+
+ @classmethod
+ def input_cases_args(cls) -> Iterator[Tuple[Any, Any, Any]]:
+ if cls.arity == 1:
+ yield from ((n, a, "0") for a, n in cls.input_cases)
+ elif cls.arity == 2:
+ yield from ((n, a, b) for a, b, n in cls.input_cases)
+ else:
+ raise ValueError("Unsupported number of operands!")
+
+ @classmethod
+ def generate_function_tests(cls) -> Iterator[test_case.TestCase]:
+ if cls.input_style not in cls.input_styles:
+ raise ValueError("Unknown input style!")
+ if cls.arity not in cls.arities:
+ raise ValueError("Unsupported number of operands!")
+ if cls.input_style == "arch_split":
+ test_objects = (cls(n, a, b, bits_in_limb=bil)
+ for n in cls.moduli
+ for a, b in cls.get_value_pairs()
+ for bil in cls.limb_sizes)
+ special_cases = (cls(*args, bits_in_limb=bil)
+ for args in cls.input_cases_args()
+ for bil in cls.limb_sizes)
+ else:
+ test_objects = (cls(n, a, b)
+ for n in cls.moduli
+ for a, b in cls.get_value_pairs())
+ special_cases = (cls(*args) for args in cls.input_cases_args())
+ yield from (valid_test_object.create_test_case()
+ for valid_test_object in filter(
+ lambda test_object: test_object.is_valid,
+ chain(test_objects, special_cases)
+ ))
# BEGIN MERGE SLOT 1
diff --git a/scripts/mbedtls_dev/bignum_core.py b/scripts/mbedtls_dev/bignum_core.py
index 0cc86b8..b8e2a31 100644
--- a/scripts/mbedtls_dev/bignum_core.py
+++ b/scripts/mbedtls_dev/bignum_core.py
@@ -16,20 +16,19 @@
import random
-from abc import ABCMeta
from typing import Dict, Iterator, List, Tuple
from . import test_case
from . import test_data_generation
from . import bignum_common
-class BignumCoreTarget(test_data_generation.BaseTarget, metaclass=ABCMeta):
- #pylint: disable=abstract-method
+class BignumCoreTarget(test_data_generation.BaseTarget):
+ #pylint: disable=abstract-method, too-few-public-methods
"""Target for bignum core test case generation."""
target_basename = 'test_suite_bignum_core.generated'
-class BignumCoreShiftR(BignumCoreTarget, metaclass=ABCMeta):
+class BignumCoreShiftR(BignumCoreTarget, test_data_generation.BaseTest):
"""Test cases for mbedtls_bignum_core_shift_r()."""
count = 0
test_function = "mpi_core_shift_r"
@@ -69,7 +68,7 @@
for count in counts:
yield cls(input_hex, descr, count).create_test_case()
-class BignumCoreCTLookup(BignumCoreTarget, metaclass=ABCMeta):
+class BignumCoreCTLookup(BignumCoreTarget, test_data_generation.BaseTest):
"""Test cases for mbedtls_mpi_core_ct_uint_table_lookup()."""
test_function = "mpi_core_ct_uint_table_lookup"
test_name = "Constant time MPI table lookup"
@@ -107,104 +106,33 @@
yield (cls(bitsize, bitsize_description, window_size)
.create_test_case())
-class BignumCoreOperation(bignum_common.OperationCommon, BignumCoreTarget, metaclass=ABCMeta):
- #pylint: disable=abstract-method
- """Common features for bignum core operations."""
- input_values = [
- "0", "1", "3", "f", "fe", "ff", "100", "ff00", "fffe", "ffff", "10000",
- "fffffffe", "ffffffff", "100000000", "1f7f7f7f7f7f7f",
- "8000000000000000", "fefefefefefefefe", "fffffffffffffffe",
- "ffffffffffffffff", "10000000000000000", "1234567890abcdef0",
- "fffffffffffffffffefefefefefefefe", "fffffffffffffffffffffffffffffffe",
- "ffffffffffffffffffffffffffffffff", "100000000000000000000000000000000",
- "1234567890abcdef01234567890abcdef0",
- "fffffffffffffffffffffffffffffffffffffffffffffffffefefefefefefefe",
- "fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe",
- "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff",
- "10000000000000000000000000000000000000000000000000000000000000000",
- "1234567890abcdef01234567890abcdef01234567890abcdef01234567890abcdef0",
- (
- "4df72d07b4b71c8dacb6cffa954f8d88254b6277099308baf003fab73227f34029"
- "643b5a263f66e0d3c3fa297ef71755efd53b8fb6cb812c6bbf7bcf179298bd9947"
- "c4c8b14324140a2c0f5fad7958a69050a987a6096e9f055fb38edf0c5889eca4a0"
- "cfa99b45fbdeee4c696b328ddceae4723945901ec025076b12b"
- )
- ]
- def description(self) -> str:
- """Generate a description for the test case.
-
- If not set, case_description uses the form A `symbol` B, where symbol
- is used to represent the operation. Descriptions of each value are
- generated to provide some context to the test case.
- """
- if not self.case_description:
- self.case_description = "{:x} {} {:x}".format(
- self.int_a, self.symbol, self.int_b
- )
- return super().description()
-
- @classmethod
- def generate_function_tests(cls) -> Iterator[test_case.TestCase]:
- for a_value, b_value in cls.get_value_pairs():
- yield cls(a_value, b_value).create_test_case()
-
-
-class BignumCoreOperationArchSplit(BignumCoreOperation):
- #pylint: disable=abstract-method
- """Common features for bignum core operations where the result depends on
- the limb size."""
-
- def __init__(self, val_a: str, val_b: str, bits_in_limb: int) -> None:
- super().__init__(val_a, val_b)
- bound_val = max(self.int_a, self.int_b)
- self.bits_in_limb = bits_in_limb
- self.bound = bignum_common.bound_mpi(bound_val, self.bits_in_limb)
- limbs = bignum_common.limbs_mpi(bound_val, self.bits_in_limb)
- byte_len = limbs * self.bits_in_limb // 8
- self.hex_digits = 2 * byte_len
- if self.bits_in_limb == 32:
- self.dependencies = ["MBEDTLS_HAVE_INT32"]
- elif self.bits_in_limb == 64:
- self.dependencies = ["MBEDTLS_HAVE_INT64"]
- else:
- raise ValueError("Invalid number of bits in limb!")
- self.arg_a = self.arg_a.zfill(self.hex_digits)
- self.arg_b = self.arg_b.zfill(self.hex_digits)
-
- def pad_to_limbs(self, val) -> str:
- return "{:x}".format(val).zfill(self.hex_digits)
-
- @classmethod
- def generate_function_tests(cls) -> Iterator[test_case.TestCase]:
- for a_value, b_value in cls.get_value_pairs():
- yield cls(a_value, b_value, 32).create_test_case()
- yield cls(a_value, b_value, 64).create_test_case()
-
-class BignumCoreAddAndAddIf(BignumCoreOperationArchSplit):
+class BignumCoreAddAndAddIf(BignumCoreTarget, bignum_common.OperationCommon):
"""Test cases for bignum core add and add-if."""
count = 0
symbol = "+"
test_function = "mpi_core_add_and_add_if"
test_name = "mpi_core_add_and_add_if"
+ input_style = "arch_split"
+ unique_combinations_only = True
def result(self) -> List[str]:
result = self.int_a + self.int_b
- carry, result = divmod(result, self.bound)
+ carry, result = divmod(result, self.limb_boundary)
return [
- bignum_common.quote_str(self.pad_to_limbs(result)),
+ self.format_result(result),
str(carry)
]
-class BignumCoreSub(BignumCoreOperation):
+
+class BignumCoreSub(BignumCoreTarget, bignum_common.OperationCommon):
"""Test cases for bignum core sub."""
count = 0
symbol = "-"
test_function = "mpi_core_sub"
test_name = "mbedtls_mpi_core_sub"
- unique_combinations_only = False
def result(self) -> List[str]:
if self.int_a >= self.int_b:
@@ -224,12 +152,11 @@
]
-class BignumCoreMLA(BignumCoreOperation):
+class BignumCoreMLA(BignumCoreTarget, bignum_common.OperationCommon):
"""Test cases for fixed-size multiply accumulate."""
count = 0
test_function = "mpi_core_mla"
test_name = "mbedtls_mpi_core_mla"
- unique_combinations_only = False
input_values = [
"0", "1", "fffe", "ffffffff", "100000000", "20000000000000",
@@ -289,6 +216,16 @@
]
@classmethod
+ def get_value_pairs(cls) -> Iterator[Tuple[str, str]]:
+ """Generator to yield pairs of inputs.
+
+ Combinations are first generated from all input values, and then
+ specific cases provided.
+ """
+ yield from super().get_value_pairs()
+ yield from cls.input_cases
+
+ @classmethod
def generate_function_tests(cls) -> Iterator[test_case.TestCase]:
"""Override for additional scalar input."""
for a_value, b_value in cls.get_value_pairs():
@@ -297,7 +234,7 @@
yield cur_op.create_test_case()
-class BignumCoreMontmul(BignumCoreTarget):
+class BignumCoreMontmul(BignumCoreTarget, test_data_generation.BaseTest):
"""Test cases for Montgomery multiplication."""
count = 0
test_function = "mpi_core_montmul"
@@ -826,6 +763,37 @@
# BEGIN MERGE SLOT 3
+class BignumCoreSubInt(BignumCoreTarget, bignum_common.OperationCommon):
+ """Test cases for bignum core sub int."""
+ count = 0
+ symbol = "-"
+ test_function = "mpi_core_sub_int"
+ test_name = "mpi_core_sub_int"
+ input_style = "arch_split"
+
+ @property
+ def is_valid(self) -> bool:
+ # This is "sub int", so b is only one limb
+ if bignum_common.limbs_mpi(self.int_b, self.bits_in_limb) > 1:
+ return False
+ return True
+
+ # Overriding because we don't want leading zeros on b
+ @property
+ def arg_b(self) -> str:
+ return self.val_b
+
+ def result(self) -> List[str]:
+ result = self.int_a - self.int_b
+
+ borrow, result = divmod(result, self.limb_boundary)
+
+ # Borrow will be -1 if non-zero, but we want it to be 1 in the test data
+ return [
+ self.format_result(result),
+ str(-borrow)
+ ]
+
# END MERGE SLOT 3
# BEGIN MERGE SLOT 4
diff --git a/scripts/mbedtls_dev/bignum_data.py b/scripts/mbedtls_dev/bignum_data.py
new file mode 100644
index 0000000..74d21d0
--- /dev/null
+++ b/scripts/mbedtls_dev/bignum_data.py
@@ -0,0 +1,136 @@
+"""Base values and datasets for bignum generated tests and helper functions that
+produced them."""
+# Copyright The Mbed TLS Contributors
+# SPDX-License-Identifier: Apache-2.0
+#
+# Licensed under the Apache License, Version 2.0 (the "License"); you may
+# not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+import random
+
+# Functions calling these were used to produce test data and are here only for
+# reproducability, they are not used by the test generation framework/classes
+try:
+ from Cryptodome.Util.number import isPrime, getPrime #type: ignore #pylint: disable=import-error
+except ImportError:
+ pass
+
+# Generated by bignum_common.gen_safe_prime(192,1)
+SAFE_PRIME_192_BIT_SEED_1 = "d1c127a667786703830500038ebaef20e5a3e2dc378fb75b"
+
+# First number generated by random.getrandbits(192) - seed(2,2), not a prime
+RANDOM_192_BIT_SEED_2_NO1 = "177219d30e7a269fd95bafc8f2a4d27bdcf4bb99f4bea973"
+
+# Second number generated by random.getrandbits(192) - seed(2,2), not a prime
+RANDOM_192_BIT_SEED_2_NO2 = "cf1822ffbc6887782b491044d5e341245c6e433715ba2bdd"
+
+# Third number generated by random.getrandbits(192) - seed(2,2), not a prime
+RANDOM_192_BIT_SEED_2_NO3 = "3653f8dd9b1f282e4067c3584ee207f8da94e3e8ab73738f"
+
+# Fourth number generated by random.getrandbits(192) - seed(2,2), not a prime
+RANDOM_192_BIT_SEED_2_NO4 = "ffed9235288bc781ae66267594c9c9500925e4749b575bd1"
+
+# Ninth number generated by random.getrandbits(192) - seed(2,2), not a prime
+RANDOM_192_BIT_SEED_2_NO9 = "2a1be9cd8697bbd0e2520e33e44c50556c71c4a66148a86f"
+
+# Generated by bignum_common.gen_safe_prime(1024,3)
+SAFE_PRIME_1024_BIT_SEED_3 = ("c93ba7ec74d96f411ba008bdb78e63ff11bb5df46a51e16b"
+ "2c9d156f8e4e18abf5e052cb01f47d0d1925a77f60991577"
+ "e128fb6f52f34a27950a594baadd3d8057abeb222cf3cca9"
+ "62db16abf79f2ada5bd29ab2f51244bf295eff9f6aaba130"
+ "2efc449b128be75eeaca04bc3c1a155d11d14e8be32a2c82"
+ "87b3996cf6ad5223")
+
+# First number generated by random.getrandbits(1024) - seed(4,2), not a prime
+RANDOM_1024_BIT_SEED_4_NO1 = ("6905269ed6f0b09f165c8ce36e2f24b43000de01b2ed40ed"
+ "3addccb2c33be0ac79d679346d4ac7a5c3902b38963dc6e8"
+ "534f45738d048ec0f1099c6c3e1b258fd724452ccea71ff4"
+ "a14876aeaff1a098ca5996666ceab360512bd13110722311"
+ "710cf5327ac435a7a97c643656412a9b8a1abcd1a6916c74"
+ "da4f9fc3c6da5d7")
+
+# Second number generated by random.getrandbits(1024) - seed(4,2), not a prime
+RANDOM_1024_BIT_SEED_4_NO2 = ("f1cfd99216df648647adec26793d0e453f5082492d83a823"
+ "3fb62d2c81862fc9634f806fabf4a07c566002249b191bf4"
+ "d8441b5616332aca5f552773e14b0190d93936e1daca3c06"
+ "f5ff0c03bb5d7385de08caa1a08179104a25e4664f5253a0"
+ "2a3187853184ff27459142deccea264542a00403ce80c4b0"
+ "a4042bb3d4341aad")
+
+# Third number generated by random.getrandbits(1024) - seed(4,2), not a prime
+RANDOM_1024_BIT_SEED_4_NO3 = ("14c15c910b11ad28cc21ce88d0060cc54278c2614e1bcb38"
+ "3bb4a570294c4ea3738d243a6e58d5ca49c7b59b995253fd"
+ "6c79a3de69f85e3131f3b9238224b122c3e4a892d9196ada"
+ "4fcfa583e1df8af9b474c7e89286a1754abcb06ae8abb93f"
+ "01d89a024cdce7a6d7288ff68c320f89f1347e0cdd905ecf"
+ "d160c5d0ef412ed6")
+
+# Fourth number generated by random.getrandbits(1024) - seed(4,2), not a prime
+RANDOM_1024_BIT_SEED_4_NO4 = ("32decd6b8efbc170a26a25c852175b7a96b98b5fbf37a2be"
+ "6f98bca35b17b9662f0733c846bbe9e870ef55b1a1f65507"
+ "a2909cb633e238b4e9dd38b869ace91311021c9e32111ac1"
+ "ac7cc4a4ff4dab102522d53857c49391b36cc9aa78a330a1"
+ "a5e333cb88dcf94384d4cd1f47ca7883ff5a52f1a05885ac"
+ "7671863c0bdbc23a")
+
+# Fifth number generated by random.getrandbits(1024) - seed(4,2), not a prime
+RANDOM_1024_BIT_SEED_4_NO5 = ("53be4721f5b9e1f5acdac615bc20f6264922b9ccf469aef8"
+ "f6e7d078e55b85dd1525f363b281b8885b69dc230af5ac87"
+ "0692b534758240df4a7a03052d733dcdef40af2e54c0ce68"
+ "1f44ebd13cc75f3edcb285f89d8cf4d4950b16ffc3e1ac3b"
+ "4708d9893a973000b54a23020fc5b043d6e4a51519d9c9cc"
+ "52d32377e78131c1")
+
+# Adding 192 bit and 1024 bit numbers because these are the shortest required
+# for ECC and RSA respectively.
+INPUTS_DEFAULT = [
+ "0", "1", # corner cases
+ "2", "3", # small primes
+ "4", # non-prime even
+ "38", # small random
+ SAFE_PRIME_192_BIT_SEED_1, # prime
+ RANDOM_192_BIT_SEED_2_NO1, # not a prime
+ RANDOM_192_BIT_SEED_2_NO2, # not a prime
+ SAFE_PRIME_1024_BIT_SEED_3, # prime
+ RANDOM_1024_BIT_SEED_4_NO1, # not a prime
+ RANDOM_1024_BIT_SEED_4_NO3, # not a prime
+ RANDOM_1024_BIT_SEED_4_NO2, # largest (not a prime)
+ ]
+
+# Only odd moduli are present as in the new bignum code only odd moduli are
+# supported for now.
+MODULI_DEFAULT = [
+ "53", # safe prime
+ "45", # non-prime
+ SAFE_PRIME_192_BIT_SEED_1, # safe prime
+ RANDOM_192_BIT_SEED_2_NO4, # not a prime
+ SAFE_PRIME_1024_BIT_SEED_3, # safe prime
+ RANDOM_1024_BIT_SEED_4_NO5, # not a prime
+ ]
+
+def __gen_safe_prime(bits, seed):
+ '''
+ Generate a safe prime.
+
+ This function is intended for generating constants offline and shouldn't be
+ used in test generation classes.
+
+ Requires pycryptodomex for getPrime and isPrime and python 3.9 or later for
+ randbytes.
+ '''
+ rng = random.Random()
+ # We want reproducability across python versions
+ rng.seed(seed, version=2)
+ while True:
+ prime = 2*getPrime(bits-1, rng.randbytes)+1 #pylint: disable=no-member
+ if isPrime(prime, 1e-30):
+ return prime
diff --git a/scripts/mbedtls_dev/bignum_mod.py b/scripts/mbedtls_dev/bignum_mod.py
index 2bd7fbb..a604cc0 100644
--- a/scripts/mbedtls_dev/bignum_mod.py
+++ b/scripts/mbedtls_dev/bignum_mod.py
@@ -14,12 +14,10 @@
# See the License for the specific language governing permissions and
# limitations under the License.
-from abc import ABCMeta
-
from . import test_data_generation
-class BignumModTarget(test_data_generation.BaseTarget, metaclass=ABCMeta):
- #pylint: disable=abstract-method
+class BignumModTarget(test_data_generation.BaseTarget):
+ #pylint: disable=abstract-method, too-few-public-methods
"""Target for bignum mod test case generation."""
target_basename = 'test_suite_bignum_mod.generated'
diff --git a/scripts/mbedtls_dev/bignum_mod_raw.py b/scripts/mbedtls_dev/bignum_mod_raw.py
index bd694a6..0bbad5d 100644
--- a/scripts/mbedtls_dev/bignum_mod_raw.py
+++ b/scripts/mbedtls_dev/bignum_mod_raw.py
@@ -14,95 +14,41 @@
# See the License for the specific language governing permissions and
# limitations under the License.
-from abc import ABCMeta
-from typing import Dict, Iterator, List
+from typing import Dict, List
-from . import test_case
from . import test_data_generation
from . import bignum_common
-class BignumModRawTarget(test_data_generation.BaseTarget, metaclass=ABCMeta):
- #pylint: disable=abstract-method
+class BignumModRawTarget(test_data_generation.BaseTarget):
+ #pylint: disable=abstract-method, too-few-public-methods
"""Target for bignum mod_raw test case generation."""
target_basename = 'test_suite_bignum_mod_raw.generated'
-class BignumModRawOperation(bignum_common.OperationCommon, BignumModRawTarget, metaclass=ABCMeta):
- #pylint: disable=abstract-method
- """Target for bignum mod_raw test case generation."""
-
- def __init__(self, val_n: str, val_a: str, val_b: str = "0", bits_in_limb: int = 64) -> None:
- super().__init__(val_a=val_a, val_b=val_b)
- self.val_n = val_n
- self.bits_in_limb = bits_in_limb
-
- @property
- def int_n(self) -> int:
- return bignum_common.hex_to_int(self.val_n)
-
- @property
- def boundary(self) -> int:
- data_in = [self.int_a, self.int_b, self.int_n]
- return max([n for n in data_in if n is not None])
-
- @property
- def limbs(self) -> int:
- return bignum_common.limbs_mpi(self.boundary, self.bits_in_limb)
-
- @property
- def hex_digits(self) -> int:
- return 2 * (self.limbs * self.bits_in_limb // 8)
-
- @property
- def hex_n(self) -> str:
- return "{:x}".format(self.int_n).zfill(self.hex_digits)
-
- @property
- def hex_a(self) -> str:
- return "{:x}".format(self.int_a).zfill(self.hex_digits)
-
- @property
- def hex_b(self) -> str:
- return "{:x}".format(self.int_b).zfill(self.hex_digits)
-
- @property
- def r(self) -> int: # pylint: disable=invalid-name
- l = bignum_common.limbs_mpi(self.int_n, self.bits_in_limb)
- return bignum_common.bound_mpi_limbs(l, self.bits_in_limb)
-
- @property
- def r_inv(self) -> int:
- return bignum_common.invmod(self.r, self.int_n)
-
- @property
- def r2(self) -> int: # pylint: disable=invalid-name
- return pow(self.r, 2)
-
-class BignumModRawOperationArchSplit(BignumModRawOperation):
- #pylint: disable=abstract-method
- """Common features for bignum mod raw operations where the result depends on
- the limb size."""
-
- limb_sizes = [32, 64] # type: List[int]
-
- def __init__(self, val_n: str, val_a: str, val_b: str = "0", bits_in_limb: int = 64) -> None:
- super().__init__(val_n=val_n, val_a=val_a, val_b=val_b, bits_in_limb=bits_in_limb)
-
- if bits_in_limb not in self.limb_sizes:
- raise ValueError("Invalid number of bits in limb!")
-
- self.dependencies = ["MBEDTLS_HAVE_INT{:d}".format(bits_in_limb)]
-
- @classmethod
- def generate_function_tests(cls) -> Iterator[test_case.TestCase]:
- for a_value, b_value in cls.get_value_pairs():
- for bil in cls.limb_sizes:
- yield cls(a_value, b_value, bits_in_limb=bil).create_test_case()
# BEGIN MERGE SLOT 1
# END MERGE SLOT 1
# BEGIN MERGE SLOT 2
+class BignumModRawSub(bignum_common.ModOperationCommon,
+ BignumModRawTarget):
+ """Test cases for bignum mpi_mod_raw_sub()."""
+ symbol = "-"
+ test_function = "mpi_mod_raw_sub"
+ test_name = "mbedtls_mpi_mod_raw_sub"
+ input_style = "fixed"
+ arity = 2
+
+ def arguments(self) -> List[str]:
+ return [bignum_common.quote_str(n) for n in [self.arg_a,
+ self.arg_b,
+ self.arg_n]
+ ] + self.result()
+
+ def result(self) -> List[str]:
+ result = (self.int_a - self.int_b) % self.int_n
+ return [self.format_result(result)]
+
# END MERGE SLOT 2
# BEGIN MERGE SLOT 3
@@ -115,6 +61,19 @@
# BEGIN MERGE SLOT 5
+class BignumModRawAdd(bignum_common.ModOperationCommon,
+ BignumModRawTarget):
+ """Test cases for bignum mpi_mod_raw_add()."""
+ symbol = "+"
+ test_function = "mpi_mod_raw_add"
+ test_name = "mbedtls_mpi_mod_raw_add"
+ input_style = "fixed"
+ arity = 2
+
+ def result(self) -> List[str]:
+ result = (self.int_a + self.int_b) % self.int_n
+ return [self.format_result(result)]
+
# END MERGE SLOT 5
# BEGIN MERGE SLOT 6
@@ -122,126 +81,35 @@
# END MERGE SLOT 6
# BEGIN MERGE SLOT 7
-class BignumModRawConvertToMont(BignumModRawOperationArchSplit):
- """ Test cases for mpi_mod_raw_to_mont_rep(). """
+class BignumModRawConvertToMont(bignum_common.ModOperationCommon,
+ BignumModRawTarget):
+ """ Test cases for mpi_mod_raw_to_mont_rep(). """
test_function = "mpi_mod_raw_to_mont_rep"
test_name = "Convert into Mont: "
-
- test_data_moduli = ["b",
- "fd",
- "eeff99aa37",
- "eeff99aa11",
- "800000000005",
- "7fffffffffffffff",
- "80fe000a10000001",
- "25a55a46e5da99c71c7",
- "1058ad82120c3a10196bb36229c1",
- "7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f"
- "18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a"
- "98df75154f8c914a282f8b",
- "8335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63",
- "ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f"
- "2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a6"
- "4d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2"
- "deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d"
- "6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a0"
- "7e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d389"
- "8c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6"
- "bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3a"
- "d4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181d"
- "b8896f33bb12e6ef73f12ec5c5ea7a8a337"
- ]
-
- test_input_numbers = ["0",
- "1",
- "97",
- "f5",
- "6f5c3",
- "745bfe50f7",
- "ffa1f9924123",
- "334a8b983c79bd",
- "5b84f632b58f3461",
- "19acd15bc38008e1",
- "ffffffffffffffff",
- "54ce6a6bb8247fa0427cfc75a6b0599",
- "fecafe8eca052f154ce6a6bb8247fa019558bfeecce9bb9",
- "a87d7a56fa4bfdc7da42ef798b9cf6843d4c54794698cb14d72"
- "851dec9586a319f4bb6d5695acbd7c92e7a42a5ede6972adcbc"
- "f68425265887f2d721f462b7f1b91531bac29fa648facb8e3c6"
- "1bd5ae42d5a59ba1c89a95897bfe541a8ce1d633b98f379c481"
- "6f25e21f6ac49286b261adb4b78274fe5f61c187581f213e84b"
- "2a821e341ef956ecd5de89e6c1a35418cd74a549379d2d4594a"
- "577543147f8e35b3514e62cf3e89d1156cdc91ab5f4c928fbd6"
- "9148c35df5962fed381f4d8a62852a36823d5425f7487c13a12"
- "523473fb823aa9d6ea5f42e794e15f2c1a8785cf6b7d51a4617"
- "947fb3baf674f74a673cf1d38126983a19ed52c7439fab42c2185"
- ]
-
- descr_tpl = '{} #{} N: \"{}\" A: \"{}\".'
+ symbol = "R *"
+ input_style = "arch_split"
+ arity = 1
def result(self) -> List[str]:
- return [self.hex_x]
+ result = (self.int_a * self.r) % self.int_n
+ return [self.format_result(result)]
- def arguments(self) -> List[str]:
- return [bignum_common.quote_str(n) for n in [self.hex_n,
- self.hex_a,
- self.hex_x]]
- def description(self) -> str:
- return self.descr_tpl.format(self.test_name,
- self.count,
- self.int_n,
- self.int_a)
-
- @classmethod
- def generate_function_tests(cls) -> Iterator[test_case.TestCase]:
- for bil in [32, 64]:
- for n in cls.test_data_moduli:
- for i in cls.test_input_numbers:
- # Skip invalid combinations where A.limbs > N.limbs
- if bignum_common.hex_to_int(i) > bignum_common.hex_to_int(n):
- continue
- yield cls(n, i, bits_in_limb=bil).create_test_case()
-
- @property
- def x(self) -> int: # pylint: disable=invalid-name
- return (self.int_a * self.r) % self.int_n
-
- @property
- def hex_x(self) -> str:
- return "{:x}".format(self.x).zfill(self.hex_digits)
-
-class BignumModRawConvertFromMont(BignumModRawConvertToMont):
+class BignumModRawConvertFromMont(bignum_common.ModOperationCommon,
+ BignumModRawTarget):
""" Test cases for mpi_mod_raw_from_mont_rep(). """
-
test_function = "mpi_mod_raw_from_mont_rep"
test_name = "Convert from Mont: "
+ symbol = "1/R *"
+ input_style = "arch_split"
+ arity = 1
- test_input_numbers = ["0",
- "1",
- "3ca",
- "539ed428",
- "7dfe5c6beb35a2d6",
- "dca8de1c2adfc6d7aafb9b48e",
- "a7d17b6c4be72f3d5c16bf9c1af6fc933",
- "2fec97beec546f9553142ed52f147845463f579",
- "378dc83b8bc5a7b62cba495af4919578dce6d4f175cadc4f",
- "b6415f2a1a8e48a518345db11f56db3829c8f2c6415ab4a395a"
- "b3ac2ea4cbef4af86eb18a84eb6ded4c6ecbfc4b59c2879a675"
- "487f687adea9d197a84a5242a5cf6125ce19a6ad2e7341f1c57"
- "d43ea4f4c852a51cb63dabcd1c9de2b827a3146a3d175b35bea"
- "41ae75d2a286a3e9d43623152ac513dcdea1d72a7da846a8ab3"
- "58d9be4926c79cfb287cf1cf25b689de3b912176be5dcaf4d4c"
- "6e7cb839a4a3243a6c47c1e2c99d65c59d6fa3672575c2f1ca8"
- "de6a32e854ec9d8ec635c96af7679fce26d7d159e4a9da3bd74"
- "e1272c376cd926d74fe3fb164a5935cff3d5cdb92b35fe2cea32"
- "138a7e6bfbc319ebd1725dacb9a359cbf693f2ecb785efb9d627"
- ]
+ def result(self) -> List[str]:
+ result = (self.int_a * self.r_inv) % self.int_n
+ return [self.format_result(result)]
- @property
- def x(self): # pylint: disable=invalid-name
- return (self.int_a * self.r_inv) % self.int_n
+
# END MERGE SLOT 7
# BEGIN MERGE SLOT 8
diff --git a/scripts/mbedtls_dev/test_data_generation.py b/scripts/mbedtls_dev/test_data_generation.py
index eec0f9d..02aa510 100644
--- a/scripts/mbedtls_dev/test_data_generation.py
+++ b/scripts/mbedtls_dev/test_data_generation.py
@@ -25,6 +25,7 @@
import os
import posixpath
import re
+import inspect
from abc import ABCMeta, abstractmethod
from typing import Callable, Dict, Iterable, Iterator, List, Type, TypeVar
@@ -35,12 +36,8 @@
T = TypeVar('T') #pylint: disable=invalid-name
-class BaseTarget(metaclass=ABCMeta):
- """Base target for test case generation.
-
- Child classes of this class represent an output file, and can be referred
- to as file targets. These indicate where test cases will be written to for
- all subclasses of the file target, which is set by `target_basename`.
+class BaseTest(metaclass=ABCMeta):
+ """Base class for test case generation.
Attributes:
count: Counter for test cases from this class.
@@ -48,8 +45,6 @@
automatically generated using the class, or manually set.
dependencies: A list of dependencies required for the test case.
show_test_count: Toggle for inclusion of `count` in the test description.
- target_basename: Basename of file to write generated tests to. This
- should be specified in a child class of BaseTarget.
test_function: Test function which the class generates cases for.
test_name: A common name or description of the test function. This can
be `test_function`, a clearer equivalent, or a short summary of the
@@ -59,7 +54,6 @@
case_description = ""
dependencies = [] # type: List[str]
show_test_count = True
- target_basename = ""
test_function = ""
test_name = ""
@@ -121,6 +115,21 @@
"""
raise NotImplementedError
+
+class BaseTarget:
+ #pylint: disable=too-few-public-methods
+ """Base target for test case generation.
+
+ Child classes of this class represent an output file, and can be referred
+ to as file targets. These indicate where test cases will be written to for
+ all subclasses of the file target, which is set by `target_basename`.
+
+ Attributes:
+ target_basename: Basename of file to write generated tests to. This
+ should be specified in a child class of BaseTarget.
+ """
+ target_basename = ""
+
@classmethod
def generate_tests(cls) -> Iterator[test_case.TestCase]:
"""Generate test cases for the class and its subclasses.
@@ -132,7 +141,8 @@
yield from `generate_tests()` in each. Calling this method on a class X
will yield test cases from all classes derived from X.
"""
- if cls.test_function:
+ if issubclass(cls, BaseTest) and not inspect.isabstract(cls):
+ #pylint: disable=no-member
yield from cls.generate_function_tests()
for subclass in sorted(cls.__subclasses__(), key=lambda c: c.__name__):
yield from subclass.generate_tests()
diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt
index c23cb6b..0ef6fdb 100644
--- a/tests/CMakeLists.txt
+++ b/tests/CMakeLists.txt
@@ -70,6 +70,7 @@
${CMAKE_CURRENT_SOURCE_DIR}/../tests/scripts/generate_bignum_tests.py
${CMAKE_CURRENT_SOURCE_DIR}/../scripts/mbedtls_dev/bignum_common.py
${CMAKE_CURRENT_SOURCE_DIR}/../scripts/mbedtls_dev/bignum_core.py
+ ${CMAKE_CURRENT_SOURCE_DIR}/../scripts/mbedtls_dev/bignum_mod_raw.py
${CMAKE_CURRENT_SOURCE_DIR}/../scripts/mbedtls_dev/test_case.py
${CMAKE_CURRENT_SOURCE_DIR}/../scripts/mbedtls_dev/test_data_generation.py
)
diff --git a/tests/Makefile b/tests/Makefile
index 7c08f54..0b31cdd 100644
--- a/tests/Makefile
+++ b/tests/Makefile
@@ -94,6 +94,7 @@
generated_bignum_test_data: scripts/generate_bignum_tests.py
generated_bignum_test_data: ../scripts/mbedtls_dev/bignum_common.py
generated_bignum_test_data: ../scripts/mbedtls_dev/bignum_core.py
+generated_bignum_test_data: ../scripts/mbedtls_dev/bignum_mod_raw.py
generated_bignum_test_data: ../scripts/mbedtls_dev/test_case.py
generated_bignum_test_data: ../scripts/mbedtls_dev/test_data_generation.py
generated_bignum_test_data:
diff --git a/tests/compat.sh b/tests/compat.sh
index d681217..529c2c5 100755
--- a/tests/compat.sh
+++ b/tests/compat.sh
@@ -595,6 +595,20 @@
G_CLIENT_ARGS="-p $PORT --debug 3 $G_MODE"
G_CLIENT_PRIO="NONE:$G_PRIO_MODE:+COMP-NULL:+CURVE-ALL:+SIGN-ALL"
+ # Newer versions of OpenSSL have a syntax to enable all "ciphers", even
+ # low-security ones. This covers not just cipher suites but also protocol
+ # versions. It is necessary, for example, to use (D)TLS 1.0/1.1 on
+ # OpenSSL 1.1.1f from Ubuntu 20.04. The syntax was only introduced in
+ # OpenSSL 1.1.0 (21e0c1d23afff48601eb93135defddae51f7e2e3) and I can't find
+ # a way to discover it from -help, so check the openssl version.
+ case $($OPENSSL_CMD version) in
+ "OpenSSL 0"*|"OpenSSL 1.0"*) :;;
+ *)
+ O_CLIENT_ARGS="$O_CLIENT_ARGS -cipher ALL@SECLEVEL=0"
+ O_SERVER_ARGS="$O_SERVER_ARGS -cipher ALL@SECLEVEL=0"
+ ;;
+ esac
+
if [ "X$VERIFY" = "XYES" ];
then
M_SERVER_ARGS="$M_SERVER_ARGS ca_file=data_files/test-ca_cat12.crt auth_mode=required"
diff --git a/tests/data_files/Makefile b/tests/data_files/Makefile
index 09a0689..5591669 100644
--- a/tests/data_files/Makefile
+++ b/tests/data_files/Makefile
@@ -884,6 +884,11 @@
$(MBEDTLS_CERT_REQ) output_file=$@ filename=$< subject_name="C=NL,O=PolarSSL,CN=PolarSSL Server 1" md=SHA256
all_final += server1.req.sha256
+server1.req.sha256.ext: server1.key
+ # Generating this with OpenSSL as a comparison point to test we're getting the same result
+ openssl req -new -out $@ -key $< -subj '/C=NL/O=PolarSSL/CN=PolarSSL Server 1' -sha256 -addext "extendedKeyUsage=serverAuth"
+all_final += server1.req.sha256.ext
+
server1.req.sha384: server1.key
$(MBEDTLS_CERT_REQ) output_file=$@ filename=$< subject_name="C=NL,O=PolarSSL,CN=PolarSSL Server 1" md=SHA384
all_final += server1.req.sha384
@@ -1134,6 +1139,108 @@
all_final += ecdsa_secp521r1.crt ecdsa_secp521r1.key
tls13_certs: ecdsa_secp521r1.crt ecdsa_secp521r1.key
+# PKCS7 test data
+pkcs7_test_cert_1 = pkcs7-rsa-sha256-1.crt
+pkcs7_test_cert_2 = pkcs7-rsa-sha256-2.crt
+pkcs7_test_file = pkcs7_data.bin
+
+$(pkcs7_test_file):
+ echo -e "Hello\xd" > $@
+all_final += $(pkcs7_test_file)
+
+pkcs7_data_1.bin:
+ echo -e "2\xd" > $@
+all_final += pkcs7_data_1.bin
+
+# Generate signing cert
+pkcs7-rsa-sha256-1.crt:
+ $(OPENSSL) req -x509 -subj="/C=NL/O=PKCS7/CN=PKCS7 Cert 1" -sha256 -nodes -days 365 -newkey rsa:2048 -keyout pkcs7-rsa-sha256-1.key -out pkcs7-rsa-sha256-1.crt
+ cat pkcs7-rsa-sha256-1.crt pkcs7-rsa-sha256-1.key > pkcs7-rsa-sha256-1.pem
+all_final += pkcs7-rsa-sha256-1.crt
+
+pkcs7-rsa-sha256-2.crt:
+ $(OPENSSL) req -x509 -subj="/C=NL/O=PKCS7/CN=PKCS7 Cert 2" -sha256 -nodes -days 365 -newkey rsa:2048 -keyout pkcs7-rsa-sha256-2.key -out pkcs7-rsa-sha256-2.crt
+ cat pkcs7-rsa-sha256-2.crt pkcs7-rsa-sha256-2.key > pkcs7-rsa-sha256-2.pem
+all_final += pkcs7-rsa-sha256-2.crt
+
+# Convert signing certs to DER for testing PEM-free builds
+pkcs7-rsa-sha256-1.der: $(pkcs7_test_cert_1)
+ $(OPENSSL) x509 -in pkcs7-rsa-sha256-1.crt -out $@ -outform DER
+all_final += pkcs7-rsa-sha256-1.der
+
+pkcs7-rsa-sha256-2.der: $(pkcs7_test_cert_2)
+ $(OPENSSL) x509 -in pkcs7-rsa-sha256-2.crt -out $@ -outform DER
+all_final += pkcs7-rsa-sha256-2.der
+
+# pkcs7 signature file with CERT
+pkcs7_data_cert_signed_sha256.der: $(pkcs7_test_file) $(pkcs7_test_cert_1)
+ $(OPENSSL) smime -sign -binary -in pkcs7_data.bin -out $@ -md sha256 -signer pkcs7-rsa-sha256-1.pem -noattr -outform DER -out $@
+all_final += pkcs7_data_cert_signed_sha256.der
+
+# pkcs7 signature file with CERT and sha1
+pkcs7_data_cert_signed_sha1.der: $(pkcs7_test_file) $(pkcs7_test_cert_1)
+ $(OPENSSL) smime -sign -binary -in pkcs7_data.bin -out $@ -md sha1 -signer pkcs7-rsa-sha256-1.pem -noattr -outform DER -out $@
+all_final += pkcs7_data_cert_signed_sha1.der
+
+# pkcs7 signature file with CERT and sha512
+pkcs7_data_cert_signed_sha512.der: $(pkcs7_test_file) $(pkcs7_test_cert_1)
+ $(OPENSSL) smime -sign -binary -in pkcs7_data.bin -out $@ -md sha512 -signer pkcs7-rsa-sha256-1.pem -noattr -outform DER -out $@
+all_final += pkcs7_data_cert_signed_sha512.der
+
+# pkcs7 signature file without CERT
+pkcs7_data_without_cert_signed.der: $(pkcs7_test_file) $(pkcs7_test_cert_1)
+ $(OPENSSL) smime -sign -binary -in pkcs7_data.bin -out $@ -md sha256 -signer pkcs7-rsa-sha256-1.pem -nocerts -noattr -outform DER -out $@
+all_final += pkcs7_data_without_cert_signed.der
+
+# pkcs7 signature file with multiple signers
+pkcs7_data_multiple_signed.der: $(pkcs7_test_file) $(pkcs7_test_cert_1) $(pkcs7_test_cert_2)
+ $(OPENSSL) smime -sign -binary -in pkcs7_data.bin -out $@ -md sha256 -signer pkcs7-rsa-sha256-1.pem -signer pkcs7-rsa-sha256-2.pem -nocerts -noattr -outform DER -out $@
+all_final += pkcs7_data_multiple_signed.der
+
+# pkcs7 signature file with multiple certificates
+pkcs7_data_multiple_certs_signed.der: $(pkcs7_test_file) $(pkcs7_test_cert_1) $(pkcs7_test_cert_2)
+ $(OPENSSL) smime -sign -binary -in pkcs7_data.bin -out $@ -md sha256 -signer pkcs7-rsa-sha256-1.pem -signer pkcs7-rsa-sha256-2.pem -noattr -outform DER -out $@
+all_final += pkcs7_data_multiple_certs_signed.der
+
+# pkcs7 signature file with corrupted CERT
+pkcs7_data_signed_badcert.der: pkcs7_data_cert_signed_sha256.der
+ cp pkcs7_data_cert_signed_sha256.der $@
+ echo -en '\xa1' | dd of=$@ bs=1 seek=547 conv=notrunc
+all_final += pkcs7_data_signed_badcert.der
+
+# pkcs7 signature file with corrupted signer info
+pkcs7_data_signed_badsigner.der: pkcs7_data_cert_signed_sha256.der
+ cp pkcs7_data_cert_signed_sha256.der $@
+ echo -en '\xa1' | dd of=$@ bs=1 seek=918 conv=notrunc
+all_final += pkcs7_data_signed_badsigner.der
+
+# pkcs7 file with version 2
+pkcs7_data_cert_signed_v2.der: pkcs7_data_cert_signed_sha256.der
+ cp pkcs7_data_cert_signed_sha256.der $@
+ echo -en '\x02' | dd of=$@ bs=1 seek=25 conv=notrunc
+all_final += pkcs7_data_cert_signed_v2.der
+
+pkcs7_data_cert_encrypted.der: $(pkcs7_test_file) $(pkcs7_test_cert_1)
+ $(OPENSSL) smime -encrypt -aes256 -in pkcs7_data.bin -binary -outform DER -out $@ pkcs7-rsa-sha256-1.crt
+all_final += pkcs7_data_cert_encrypted.der
+
+## Negative tests
+# For some interesting sizes, what happens if we make them off-by-one?
+pkcs7_signerInfo_issuer_invalid_size.der: pkcs7_data_cert_signed_sha256.der
+ cp $< $@
+ echo -en '\x35' | dd of=$@ seek=919 bs=1 conv=notrunc
+all_final += pkcs7_signerInfo_issuer_invalid_size.der
+
+pkcs7_signerInfo_serial_invalid_size.der: pkcs7_data_cert_signed_sha256.der
+ cp $< $@
+ echo -en '\x15' | dd of=$@ seek=973 bs=1 conv=notrunc
+all_final += pkcs7_signerInfo_serial_invalid_size.der
+
+# pkcs7 signature file just with signed data
+pkcs7_data_cert_signeddata_sha256.der: pkcs7_data_cert_signed_sha256.der
+ dd if=pkcs7_data_cert_signed_sha256.der of=$@ skip=19 bs=1
+all_final += pkcs7_data_cert_signeddata_sha256.der
+
################################################################
#### Diffie-Hellman parameters
################################################################
diff --git a/tests/data_files/pkcs7-rsa-sha256-1.crt b/tests/data_files/pkcs7-rsa-sha256-1.crt
new file mode 100644
index 0000000..9e461cd
--- /dev/null
+++ b/tests/data_files/pkcs7-rsa-sha256-1.crt
@@ -0,0 +1,20 @@
+-----BEGIN CERTIFICATE-----
+MIIDSTCCAjGgAwIBAgIUe97d0kRM0c3+XEGoECyJt98ubL8wDQYJKoZIhvcNAQEL
+BQAwNDELMAkGA1UEBhMCTkwxDjAMBgNVBAoMBVBLQ1M3MRUwEwYDVQQDDAxQS0NT
+NyBDZXJ0IDEwHhcNMjIxMDI4MTYxMDU2WhcNMjMxMDI4MTYxMDU2WjA0MQswCQYD
+VQQGEwJOTDEOMAwGA1UECgwFUEtDUzcxFTATBgNVBAMMDFBLQ1M3IENlcnQgMTCC
+ASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMi2z2mJnNHw67TKZFwF5w4N
+Lv7dzGHQicvVFaOaNXm5I0O2HsdQBg+07TeHYzJADkJfHTdsfnXClzMU7fS7MMj4
+3QO5/P+VWiRdSRN61uYAVsrBlVKoZdUhhxh8wELJxJ4+OpwXpTS0U82rwMsRO09j
+9bMXS57pkCsZENEUlqJ5p0Mmrc/uEL/Z5+uvuzd76bY5WRZdE91XURccra08HTra
+xovIAR1htUz2AXi+NoOaiayRq0GePKN9a6iB0lUYxNtovKb3yDYC9pmoaxf7Hnc7
+y+dLuTpJslGuhkKLV0Dhhoux1vq54ocS6Y7DGa2Pyk1zAQxLCcS4BFiWHnzwg1MC
+AwEAAaNTMFEwHQYDVR0OBBYEFIru5ZR8xnxd1RWnbip+zTHuUv3IMB8GA1UdIwQY
+MBaAFIru5ZR8xnxd1RWnbip+zTHuUv3IMA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZI
+hvcNAQELBQADggEBAIIda5jNRX3r0rCBrKJ+vs1Pk6zIKEQ7Oeq/+p+k6eRUO0b8
+wx4rW0gXeQPeppaaxKLMZXBlA5DxsI1DpML5dcfti/M1bHIYOAISRRqPEd5GVTy8
+1ltCVN249mg06yHdoqjzO1geFIRVesoblO6JMd3xYDe3pxcTIakZNq/Cf/zjld51
+1fcMuLWu4F/1BwiNZa8eQ5Zs1Cy+b3+s+NrgVd2CIrFpZSFyP4EkUXhZXJha6Rf9
+SzmYdz4al7e9EAhURvQlm8wJpFSSkoLBuJtx7Vh6d14KPUU2NB9F2ulp6AbJb+/H
+EGd3bAK6IhIrkZmxTAwowESHUJBwuX890tbZcnM=
+-----END CERTIFICATE-----
diff --git a/tests/data_files/pkcs7-rsa-sha256-1.der b/tests/data_files/pkcs7-rsa-sha256-1.der
new file mode 100644
index 0000000..0d799ea
--- /dev/null
+++ b/tests/data_files/pkcs7-rsa-sha256-1.der
Binary files differ
diff --git a/tests/data_files/pkcs7-rsa-sha256-1.key b/tests/data_files/pkcs7-rsa-sha256-1.key
new file mode 100644
index 0000000..e31159d
--- /dev/null
+++ b/tests/data_files/pkcs7-rsa-sha256-1.key
@@ -0,0 +1,28 @@
+-----BEGIN PRIVATE KEY-----
+MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDIts9piZzR8Ou0
+ymRcBecODS7+3cxh0InL1RWjmjV5uSNDth7HUAYPtO03h2MyQA5CXx03bH51wpcz
+FO30uzDI+N0Dufz/lVokXUkTetbmAFbKwZVSqGXVIYcYfMBCycSePjqcF6U0tFPN
+q8DLETtPY/WzF0ue6ZArGRDRFJaieadDJq3P7hC/2efrr7s3e+m2OVkWXRPdV1EX
+HK2tPB062saLyAEdYbVM9gF4vjaDmomskatBnjyjfWuogdJVGMTbaLym98g2AvaZ
+qGsX+x53O8vnS7k6SbJRroZCi1dA4YaLsdb6ueKHEumOwxmtj8pNcwEMSwnEuARY
+lh588INTAgMBAAECggEBAIg+P1B+TurbRMQ11iX5A7wwCsSKPh/vdHneLJAfL0lu
++JcP2piko1iqEZPt3NHRVVyMP8LNbJH3Ardz74p+PkFNXIkZCLlc4hFpGR+V9KWv
+eTqsaPXwxR8FYTSoCcHMQCDCUPp/um6qMXCcs4OkMMRVMATfPT+jf28h1p52AUJL
+aAoBJfn7gP3WiB0FWq0bRZgSZzNYowE/MhGAQ+DuBGTSASSK3YJcxE94044fBVE8
+EqYKrxoY/x56li5cZ0v9kaURCrvhqCeq2+U5kIkgtvp2l6wF0Mm1du3BLxo2LQEI
+Y2j+6BFEV74Mtv48GTwrZcyit787zyo9vVGcviSD5VECgYEA/mgLc5KfF/cQLmM/
+20T4k0edvktkRIJHFUBphowt5Hb0a0wM5C1VM4z3yN3b9ikQK+ZaQXETdPATBXIe
+LntX1D1xtbMxdcAfd1FSq8QxAuaPknJZBgtzlpCsx3ZvMnNuzKZN/TU8kR1biwPE
+9HaeEG3bouUu+CI/l/DqrBbQRacCgYEAyfiqsLWGhXQ7e3pLk47PDYlMOsjDWPjs
+SGcatH1/lIMWyZue4W2IUcFMbpbjA6QWibo3VnOavIRSTn97JNUWYvgc5MmaQ7iX
+Iss4m3vJ1LIqx30iUgw3EfDoWdpufEEYssZ/VxJPs3sdmZGALgd3CaqxHJuhuS+U
+eVhWzD6LonUCgYBRCbt8GRxsedrBrAPPSO0VnR52W3WZDRavglEa9tQ3jlzVQOhq
+VrZpMWJMrb8/bl0kXsApUGeuPDsS5QMQM2IKzXfHNUlwBL8BNvpqlJg4IFFjiOEq
+t8MeFv+ymdtZ6sNElUUKf0bHwt5CLfUzGgXHnfb0sKSBjgdL0wYtwyacyQKBgQDJ
+NcyG4zEy/srLhtiIFnu8Fo40+hFzL/nlX6JBMc3KHJa1Hy43krF+ET6d5gAffndd
+moDKxbzgFksRHPuHhCobSucuHpJq6RjYdvDcJYS7OwxXVRi9+KFcZE52RaBQdWGv
+qQTvr7RrMDoa5dN3B8TVgpGT2JBTN02JXjKKo7zkiQKBgCZwKDiXl7qsGidvlFZc
+4CEtFsCgnNgdRTzsTL/Pr8q9CBK3BhjZjNzQALF1iGFDC1FdFYFOwI1E3j+MRHJB
+rQMF8zbmmlZ6SC5QtqatCSCCKUyrUjD5J+4UfJqWFjiBBdwz+5VJojHw1yijEwl4
+LrS/V2yBrDJVczQQM4psonLF
+-----END PRIVATE KEY-----
diff --git a/tests/data_files/pkcs7-rsa-sha256-1.pem b/tests/data_files/pkcs7-rsa-sha256-1.pem
new file mode 100644
index 0000000..3795b71
--- /dev/null
+++ b/tests/data_files/pkcs7-rsa-sha256-1.pem
@@ -0,0 +1,48 @@
+-----BEGIN CERTIFICATE-----
+MIIDSTCCAjGgAwIBAgIUe97d0kRM0c3+XEGoECyJt98ubL8wDQYJKoZIhvcNAQEL
+BQAwNDELMAkGA1UEBhMCTkwxDjAMBgNVBAoMBVBLQ1M3MRUwEwYDVQQDDAxQS0NT
+NyBDZXJ0IDEwHhcNMjIxMDI4MTYxMDU2WhcNMjMxMDI4MTYxMDU2WjA0MQswCQYD
+VQQGEwJOTDEOMAwGA1UECgwFUEtDUzcxFTATBgNVBAMMDFBLQ1M3IENlcnQgMTCC
+ASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMi2z2mJnNHw67TKZFwF5w4N
+Lv7dzGHQicvVFaOaNXm5I0O2HsdQBg+07TeHYzJADkJfHTdsfnXClzMU7fS7MMj4
+3QO5/P+VWiRdSRN61uYAVsrBlVKoZdUhhxh8wELJxJ4+OpwXpTS0U82rwMsRO09j
+9bMXS57pkCsZENEUlqJ5p0Mmrc/uEL/Z5+uvuzd76bY5WRZdE91XURccra08HTra
+xovIAR1htUz2AXi+NoOaiayRq0GePKN9a6iB0lUYxNtovKb3yDYC9pmoaxf7Hnc7
+y+dLuTpJslGuhkKLV0Dhhoux1vq54ocS6Y7DGa2Pyk1zAQxLCcS4BFiWHnzwg1MC
+AwEAAaNTMFEwHQYDVR0OBBYEFIru5ZR8xnxd1RWnbip+zTHuUv3IMB8GA1UdIwQY
+MBaAFIru5ZR8xnxd1RWnbip+zTHuUv3IMA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZI
+hvcNAQELBQADggEBAIIda5jNRX3r0rCBrKJ+vs1Pk6zIKEQ7Oeq/+p+k6eRUO0b8
+wx4rW0gXeQPeppaaxKLMZXBlA5DxsI1DpML5dcfti/M1bHIYOAISRRqPEd5GVTy8
+1ltCVN249mg06yHdoqjzO1geFIRVesoblO6JMd3xYDe3pxcTIakZNq/Cf/zjld51
+1fcMuLWu4F/1BwiNZa8eQ5Zs1Cy+b3+s+NrgVd2CIrFpZSFyP4EkUXhZXJha6Rf9
+SzmYdz4al7e9EAhURvQlm8wJpFSSkoLBuJtx7Vh6d14KPUU2NB9F2ulp6AbJb+/H
+EGd3bAK6IhIrkZmxTAwowESHUJBwuX890tbZcnM=
+-----END CERTIFICATE-----
+-----BEGIN PRIVATE KEY-----
+MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDIts9piZzR8Ou0
+ymRcBecODS7+3cxh0InL1RWjmjV5uSNDth7HUAYPtO03h2MyQA5CXx03bH51wpcz
+FO30uzDI+N0Dufz/lVokXUkTetbmAFbKwZVSqGXVIYcYfMBCycSePjqcF6U0tFPN
+q8DLETtPY/WzF0ue6ZArGRDRFJaieadDJq3P7hC/2efrr7s3e+m2OVkWXRPdV1EX
+HK2tPB062saLyAEdYbVM9gF4vjaDmomskatBnjyjfWuogdJVGMTbaLym98g2AvaZ
+qGsX+x53O8vnS7k6SbJRroZCi1dA4YaLsdb6ueKHEumOwxmtj8pNcwEMSwnEuARY
+lh588INTAgMBAAECggEBAIg+P1B+TurbRMQ11iX5A7wwCsSKPh/vdHneLJAfL0lu
++JcP2piko1iqEZPt3NHRVVyMP8LNbJH3Ardz74p+PkFNXIkZCLlc4hFpGR+V9KWv
+eTqsaPXwxR8FYTSoCcHMQCDCUPp/um6qMXCcs4OkMMRVMATfPT+jf28h1p52AUJL
+aAoBJfn7gP3WiB0FWq0bRZgSZzNYowE/MhGAQ+DuBGTSASSK3YJcxE94044fBVE8
+EqYKrxoY/x56li5cZ0v9kaURCrvhqCeq2+U5kIkgtvp2l6wF0Mm1du3BLxo2LQEI
+Y2j+6BFEV74Mtv48GTwrZcyit787zyo9vVGcviSD5VECgYEA/mgLc5KfF/cQLmM/
+20T4k0edvktkRIJHFUBphowt5Hb0a0wM5C1VM4z3yN3b9ikQK+ZaQXETdPATBXIe
+LntX1D1xtbMxdcAfd1FSq8QxAuaPknJZBgtzlpCsx3ZvMnNuzKZN/TU8kR1biwPE
+9HaeEG3bouUu+CI/l/DqrBbQRacCgYEAyfiqsLWGhXQ7e3pLk47PDYlMOsjDWPjs
+SGcatH1/lIMWyZue4W2IUcFMbpbjA6QWibo3VnOavIRSTn97JNUWYvgc5MmaQ7iX
+Iss4m3vJ1LIqx30iUgw3EfDoWdpufEEYssZ/VxJPs3sdmZGALgd3CaqxHJuhuS+U
+eVhWzD6LonUCgYBRCbt8GRxsedrBrAPPSO0VnR52W3WZDRavglEa9tQ3jlzVQOhq
+VrZpMWJMrb8/bl0kXsApUGeuPDsS5QMQM2IKzXfHNUlwBL8BNvpqlJg4IFFjiOEq
+t8MeFv+ymdtZ6sNElUUKf0bHwt5CLfUzGgXHnfb0sKSBjgdL0wYtwyacyQKBgQDJ
+NcyG4zEy/srLhtiIFnu8Fo40+hFzL/nlX6JBMc3KHJa1Hy43krF+ET6d5gAffndd
+moDKxbzgFksRHPuHhCobSucuHpJq6RjYdvDcJYS7OwxXVRi9+KFcZE52RaBQdWGv
+qQTvr7RrMDoa5dN3B8TVgpGT2JBTN02JXjKKo7zkiQKBgCZwKDiXl7qsGidvlFZc
+4CEtFsCgnNgdRTzsTL/Pr8q9CBK3BhjZjNzQALF1iGFDC1FdFYFOwI1E3j+MRHJB
+rQMF8zbmmlZ6SC5QtqatCSCCKUyrUjD5J+4UfJqWFjiBBdwz+5VJojHw1yijEwl4
+LrS/V2yBrDJVczQQM4psonLF
+-----END PRIVATE KEY-----
diff --git a/tests/data_files/pkcs7-rsa-sha256-2.crt b/tests/data_files/pkcs7-rsa-sha256-2.crt
new file mode 100644
index 0000000..a0df7d9
--- /dev/null
+++ b/tests/data_files/pkcs7-rsa-sha256-2.crt
@@ -0,0 +1,20 @@
+-----BEGIN CERTIFICATE-----
+MIIDSTCCAjGgAwIBAgIUVk1VQCWvWZ4ycHmycg7wDfN8+3wwDQYJKoZIhvcNAQEL
+BQAwNDELMAkGA1UEBhMCTkwxDjAMBgNVBAoMBVBLQ1M3MRUwEwYDVQQDDAxQS0NT
+NyBDZXJ0IDIwHhcNMjIxMDI4MTYxMDU2WhcNMjMxMDI4MTYxMDU2WjA0MQswCQYD
+VQQGEwJOTDEOMAwGA1UECgwFUEtDUzcxFTATBgNVBAMMDFBLQ1M3IENlcnQgMjCC
+ASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMmVNZZ0/qcT+h/lVNO+gP65
+lERTTudQ15h8QTLjaKhx5SSTLnuUhD0jLbR+ng8PMqdJ8ePkZEh1+7mi9MHzID4Y
+c47jH8M+Jc/JdBr6cSjbFd23QHESUjKKmV1IjSHc6Llbxe962z4gEXYjJAMkfr6B
+g1iecK3AlnEI4F0BsQfC5dgA4Qce2okvcTuhYgvHtLZ+UN4ca50Kw0o4u5FYdl89
+KDCE4zNp8MaaxGC83xcM4A9XqjHyZ7a2wvACTlmLQ2q/E+RN/8THEel4Y+yv82Uj
+j2LqqEaA06dvSdOPdaGz9jUZauqBw7TcuGGVzrrsZ0g/sHXKng9TppehAV/HrJUC
+AwEAAaNTMFEwHQYDVR0OBBYEFI5FVrtfLwPXRERcyVX6qBVvfoduMB8GA1UdIwQY
+MBaAFI5FVrtfLwPXRERcyVX6qBVvfoduMA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZI
+hvcNAQELBQADggEBAKRl0wgREe6eAduJSV5fs+Ec0s2qs2lHQqt/0JGEIbZBBtka
+q1UH9CIMMAd6Kb0kh5GlJT2shg/EAYWoitMwntkeRYTln2k2/B5jux+U5Ph4HyC+
+ad2GqmsoXWDru79rltT7Pv1hS1ofJyQ4Jv88vQA/SuIIRGdTC24VAVgg00JxvDRB
+xeqsQ9Pld4ebg4VvqsInnSpmKCcxfWxFhJk/Ax8bK/tV/GnrPiwsvry1j9nZyebS
+IyI01/6DwJS2ZhFnsLGyPHFOAFNtomjIdQ6gf2L1wq0qiGOKj/K9IzFNCpCz82a+
+gMgqFzCT5TCZC16kUG2NA2pXAx9O4uppKjRk97U=
+-----END CERTIFICATE-----
diff --git a/tests/data_files/pkcs7-rsa-sha256-2.der b/tests/data_files/pkcs7-rsa-sha256-2.der
new file mode 100644
index 0000000..fc7a3ea
--- /dev/null
+++ b/tests/data_files/pkcs7-rsa-sha256-2.der
Binary files differ
diff --git a/tests/data_files/pkcs7-rsa-sha256-2.key b/tests/data_files/pkcs7-rsa-sha256-2.key
new file mode 100644
index 0000000..659c015
--- /dev/null
+++ b/tests/data_files/pkcs7-rsa-sha256-2.key
@@ -0,0 +1,28 @@
+-----BEGIN PRIVATE KEY-----
+MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDJlTWWdP6nE/of
+5VTTvoD+uZREU07nUNeYfEEy42ioceUkky57lIQ9Iy20fp4PDzKnSfHj5GRIdfu5
+ovTB8yA+GHOO4x/DPiXPyXQa+nEo2xXdt0BxElIyipldSI0h3Oi5W8Xvets+IBF2
+IyQDJH6+gYNYnnCtwJZxCOBdAbEHwuXYAOEHHtqJL3E7oWILx7S2flDeHGudCsNK
+OLuRWHZfPSgwhOMzafDGmsRgvN8XDOAPV6ox8me2tsLwAk5Zi0NqvxPkTf/ExxHp
+eGPsr/NlI49i6qhGgNOnb0nTj3Whs/Y1GWrqgcO03Lhhlc667GdIP7B1yp4PU6aX
+oQFfx6yVAgMBAAECggEBAMVHm3w134qQCHfyroPTqtaftDTx+wRyn6yB3iT5XdGM
+NZ8H07Pp80kKBo7gY7uFOiNyQKKxQFuR69sPWc3+LI3YzC8IpGslhUfHdjN46gn7
+73hfAVgnf/4qmlEq0cRUOAY/hIUMjUhNhglB9tqEeu3iPjMaTFgfZJwW/czH/QMD
+w4zj5XoLgwRkqVvUceu/dBgV8KP5DpON+q8wpfWtjunv7rg5Nc3BVBrpb5SadJ7T
+i5TsS+pZQyp+mTvyCI3A1hkr2Vw5tULWO8SPhuEQkdtC/CL+luCUO7L16lU6KhFB
+qP5Fduik5skyLCVvAMUkjKcrC22k0gkhOHvfmMhjaAECgYEA68+hAQIiV9ErZGk9
+ZLu+VJHBSPmEQCkUcbviwzoRo8YSyka12TZERy+NJcvmD9deNgFbp8GyZf01XJWH
+slSYt6LyInrJrTpv+3q2Vl5GQp0f+39i7MHnwGGKbWsDbSAm+L9yKTJzYJz1O5fo
+in06AiyyGPwnXd1cm5bTXVX+dQECgYEA2tdi6DXF8awE23pv4HphPBhXS5hmYP/D
+NC7CtP8wQsxjPdiIxkBFFVEaFCC2njq1VhTyJb5noJM4kOIwcoaQ/zgyyxQa0u7w
++CqvAh1WwG+sT/B7vivrtDmmYeyGQapFo5DRIz+MflKAhzDhtnEyT9vLuCdn8J95
+0YvxZJ9+k5UCgYEAh+e7SER9nJUt6AoLWyIlGMKEXlWIFh5W7RG3KIMwJW6D59aG
++fAfu9M5Cx6PsnOSlZeExpOJCOS9O2Xmti2xcqzT1nFkCJWUcqCPtAlTfxLlmuIZ
+FpDOy36r9FHnwJ32OAjGd93ex0DOyZDMcfyoURaHcoTo/10UAYwUt0dXhwECgYAI
+xad2TWmA1XdgYNkJM36gTQ16v0IjUz084z70yGHj25OC0CIzaDIct6KG+gS39Px9
+1dsa/jXjLuOOkzKD9LbtNBB9KXIl0GQiXnujZw+qKQ/MKISdS99n2wO7WyLKkQu3
+kb+AXTTBf4cdZC04BfORVesll5bIA2x7pNNpSCdnvQKBgG7VXYcPlIV7iAyi2xFa
+uN1jccu/AK7xA0G1jz2SHNlpet74LmWR8XsTujJeo8WG1IRFxSky4h/pAP0XWIFO
+0LPK7eeDtnFq6y1/DXpI+/9BWX5T/8+4Yk93p37YrBVWKfd21dhrAklQs11m3rlQ
+Qn6c/zyvMKSyrCVxo5pTd5Il
+-----END PRIVATE KEY-----
diff --git a/tests/data_files/pkcs7-rsa-sha256-2.pem b/tests/data_files/pkcs7-rsa-sha256-2.pem
new file mode 100644
index 0000000..b11a00a
--- /dev/null
+++ b/tests/data_files/pkcs7-rsa-sha256-2.pem
@@ -0,0 +1,48 @@
+-----BEGIN CERTIFICATE-----
+MIIDSTCCAjGgAwIBAgIUVk1VQCWvWZ4ycHmycg7wDfN8+3wwDQYJKoZIhvcNAQEL
+BQAwNDELMAkGA1UEBhMCTkwxDjAMBgNVBAoMBVBLQ1M3MRUwEwYDVQQDDAxQS0NT
+NyBDZXJ0IDIwHhcNMjIxMDI4MTYxMDU2WhcNMjMxMDI4MTYxMDU2WjA0MQswCQYD
+VQQGEwJOTDEOMAwGA1UECgwFUEtDUzcxFTATBgNVBAMMDFBLQ1M3IENlcnQgMjCC
+ASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMmVNZZ0/qcT+h/lVNO+gP65
+lERTTudQ15h8QTLjaKhx5SSTLnuUhD0jLbR+ng8PMqdJ8ePkZEh1+7mi9MHzID4Y
+c47jH8M+Jc/JdBr6cSjbFd23QHESUjKKmV1IjSHc6Llbxe962z4gEXYjJAMkfr6B
+g1iecK3AlnEI4F0BsQfC5dgA4Qce2okvcTuhYgvHtLZ+UN4ca50Kw0o4u5FYdl89
+KDCE4zNp8MaaxGC83xcM4A9XqjHyZ7a2wvACTlmLQ2q/E+RN/8THEel4Y+yv82Uj
+j2LqqEaA06dvSdOPdaGz9jUZauqBw7TcuGGVzrrsZ0g/sHXKng9TppehAV/HrJUC
+AwEAAaNTMFEwHQYDVR0OBBYEFI5FVrtfLwPXRERcyVX6qBVvfoduMB8GA1UdIwQY
+MBaAFI5FVrtfLwPXRERcyVX6qBVvfoduMA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZI
+hvcNAQELBQADggEBAKRl0wgREe6eAduJSV5fs+Ec0s2qs2lHQqt/0JGEIbZBBtka
+q1UH9CIMMAd6Kb0kh5GlJT2shg/EAYWoitMwntkeRYTln2k2/B5jux+U5Ph4HyC+
+ad2GqmsoXWDru79rltT7Pv1hS1ofJyQ4Jv88vQA/SuIIRGdTC24VAVgg00JxvDRB
+xeqsQ9Pld4ebg4VvqsInnSpmKCcxfWxFhJk/Ax8bK/tV/GnrPiwsvry1j9nZyebS
+IyI01/6DwJS2ZhFnsLGyPHFOAFNtomjIdQ6gf2L1wq0qiGOKj/K9IzFNCpCz82a+
+gMgqFzCT5TCZC16kUG2NA2pXAx9O4uppKjRk97U=
+-----END CERTIFICATE-----
+-----BEGIN PRIVATE KEY-----
+MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDJlTWWdP6nE/of
+5VTTvoD+uZREU07nUNeYfEEy42ioceUkky57lIQ9Iy20fp4PDzKnSfHj5GRIdfu5
+ovTB8yA+GHOO4x/DPiXPyXQa+nEo2xXdt0BxElIyipldSI0h3Oi5W8Xvets+IBF2
+IyQDJH6+gYNYnnCtwJZxCOBdAbEHwuXYAOEHHtqJL3E7oWILx7S2flDeHGudCsNK
+OLuRWHZfPSgwhOMzafDGmsRgvN8XDOAPV6ox8me2tsLwAk5Zi0NqvxPkTf/ExxHp
+eGPsr/NlI49i6qhGgNOnb0nTj3Whs/Y1GWrqgcO03Lhhlc667GdIP7B1yp4PU6aX
+oQFfx6yVAgMBAAECggEBAMVHm3w134qQCHfyroPTqtaftDTx+wRyn6yB3iT5XdGM
+NZ8H07Pp80kKBo7gY7uFOiNyQKKxQFuR69sPWc3+LI3YzC8IpGslhUfHdjN46gn7
+73hfAVgnf/4qmlEq0cRUOAY/hIUMjUhNhglB9tqEeu3iPjMaTFgfZJwW/czH/QMD
+w4zj5XoLgwRkqVvUceu/dBgV8KP5DpON+q8wpfWtjunv7rg5Nc3BVBrpb5SadJ7T
+i5TsS+pZQyp+mTvyCI3A1hkr2Vw5tULWO8SPhuEQkdtC/CL+luCUO7L16lU6KhFB
+qP5Fduik5skyLCVvAMUkjKcrC22k0gkhOHvfmMhjaAECgYEA68+hAQIiV9ErZGk9
+ZLu+VJHBSPmEQCkUcbviwzoRo8YSyka12TZERy+NJcvmD9deNgFbp8GyZf01XJWH
+slSYt6LyInrJrTpv+3q2Vl5GQp0f+39i7MHnwGGKbWsDbSAm+L9yKTJzYJz1O5fo
+in06AiyyGPwnXd1cm5bTXVX+dQECgYEA2tdi6DXF8awE23pv4HphPBhXS5hmYP/D
+NC7CtP8wQsxjPdiIxkBFFVEaFCC2njq1VhTyJb5noJM4kOIwcoaQ/zgyyxQa0u7w
++CqvAh1WwG+sT/B7vivrtDmmYeyGQapFo5DRIz+MflKAhzDhtnEyT9vLuCdn8J95
+0YvxZJ9+k5UCgYEAh+e7SER9nJUt6AoLWyIlGMKEXlWIFh5W7RG3KIMwJW6D59aG
++fAfu9M5Cx6PsnOSlZeExpOJCOS9O2Xmti2xcqzT1nFkCJWUcqCPtAlTfxLlmuIZ
+FpDOy36r9FHnwJ32OAjGd93ex0DOyZDMcfyoURaHcoTo/10UAYwUt0dXhwECgYAI
+xad2TWmA1XdgYNkJM36gTQ16v0IjUz084z70yGHj25OC0CIzaDIct6KG+gS39Px9
+1dsa/jXjLuOOkzKD9LbtNBB9KXIl0GQiXnujZw+qKQ/MKISdS99n2wO7WyLKkQu3
+kb+AXTTBf4cdZC04BfORVesll5bIA2x7pNNpSCdnvQKBgG7VXYcPlIV7iAyi2xFa
+uN1jccu/AK7xA0G1jz2SHNlpet74LmWR8XsTujJeo8WG1IRFxSky4h/pAP0XWIFO
+0LPK7eeDtnFq6y1/DXpI+/9BWX5T/8+4Yk93p37YrBVWKfd21dhrAklQs11m3rlQ
+Qn6c/zyvMKSyrCVxo5pTd5Il
+-----END PRIVATE KEY-----
diff --git a/tests/data_files/pkcs7_data.bin b/tests/data_files/pkcs7_data.bin
new file mode 100644
index 0000000..40ee264
--- /dev/null
+++ b/tests/data_files/pkcs7_data.bin
@@ -0,0 +1 @@
+Hello
diff --git a/tests/data_files/pkcs7_data_1.bin b/tests/data_files/pkcs7_data_1.bin
new file mode 100644
index 0000000..78c6bae
--- /dev/null
+++ b/tests/data_files/pkcs7_data_1.bin
@@ -0,0 +1 @@
+2
diff --git a/tests/data_files/pkcs7_data_cert_encrypted.der b/tests/data_files/pkcs7_data_cert_encrypted.der
new file mode 100644
index 0000000..b7b1c83
--- /dev/null
+++ b/tests/data_files/pkcs7_data_cert_encrypted.der
Binary files differ
diff --git a/tests/data_files/pkcs7_data_cert_signed_sha1.der b/tests/data_files/pkcs7_data_cert_signed_sha1.der
new file mode 100644
index 0000000..fb1deb0
--- /dev/null
+++ b/tests/data_files/pkcs7_data_cert_signed_sha1.der
Binary files differ
diff --git a/tests/data_files/pkcs7_data_cert_signed_sha256.der b/tests/data_files/pkcs7_data_cert_signed_sha256.der
new file mode 100644
index 0000000..8dc2f4c
--- /dev/null
+++ b/tests/data_files/pkcs7_data_cert_signed_sha256.der
Binary files differ
diff --git a/tests/data_files/pkcs7_data_cert_signed_sha512.der b/tests/data_files/pkcs7_data_cert_signed_sha512.der
new file mode 100644
index 0000000..a4aa587
--- /dev/null
+++ b/tests/data_files/pkcs7_data_cert_signed_sha512.der
Binary files differ
diff --git a/tests/data_files/pkcs7_data_cert_signed_v2.der b/tests/data_files/pkcs7_data_cert_signed_v2.der
new file mode 100644
index 0000000..4f4cb04
--- /dev/null
+++ b/tests/data_files/pkcs7_data_cert_signed_v2.der
Binary files differ
diff --git a/tests/data_files/pkcs7_data_cert_signeddata_sha256.der b/tests/data_files/pkcs7_data_cert_signeddata_sha256.der
new file mode 100644
index 0000000..cb7d751
--- /dev/null
+++ b/tests/data_files/pkcs7_data_cert_signeddata_sha256.der
Binary files differ
diff --git a/tests/data_files/pkcs7_data_multiple_certs_signed.der b/tests/data_files/pkcs7_data_multiple_certs_signed.der
new file mode 100644
index 0000000..4a237e9
--- /dev/null
+++ b/tests/data_files/pkcs7_data_multiple_certs_signed.der
Binary files differ
diff --git a/tests/data_files/pkcs7_data_multiple_signed.der b/tests/data_files/pkcs7_data_multiple_signed.der
new file mode 100644
index 0000000..095b80c
--- /dev/null
+++ b/tests/data_files/pkcs7_data_multiple_signed.der
Binary files differ
diff --git a/tests/data_files/pkcs7_data_signed_badcert.der b/tests/data_files/pkcs7_data_signed_badcert.der
new file mode 100644
index 0000000..ed00f65
--- /dev/null
+++ b/tests/data_files/pkcs7_data_signed_badcert.der
Binary files differ
diff --git a/tests/data_files/pkcs7_data_signed_badsigner.der b/tests/data_files/pkcs7_data_signed_badsigner.der
new file mode 100644
index 0000000..aa5447c
--- /dev/null
+++ b/tests/data_files/pkcs7_data_signed_badsigner.der
Binary files differ
diff --git a/tests/data_files/pkcs7_data_without_cert_signed.der b/tests/data_files/pkcs7_data_without_cert_signed.der
new file mode 100644
index 0000000..b47fe92
--- /dev/null
+++ b/tests/data_files/pkcs7_data_without_cert_signed.der
Binary files differ
diff --git a/tests/data_files/pkcs7_signerInfo_issuer_invalid_size.der b/tests/data_files/pkcs7_signerInfo_issuer_invalid_size.der
new file mode 100644
index 0000000..898ca67
--- /dev/null
+++ b/tests/data_files/pkcs7_signerInfo_issuer_invalid_size.der
Binary files differ
diff --git a/tests/data_files/pkcs7_signerInfo_serial_invalid_size.der b/tests/data_files/pkcs7_signerInfo_serial_invalid_size.der
new file mode 100644
index 0000000..f4b4e38
--- /dev/null
+++ b/tests/data_files/pkcs7_signerInfo_serial_invalid_size.der
Binary files differ
diff --git a/tests/data_files/server1.req.sha256.ext b/tests/data_files/server1.req.sha256.ext
new file mode 100644
index 0000000..3f26f09
--- /dev/null
+++ b/tests/data_files/server1.req.sha256.ext
@@ -0,0 +1,17 @@
+-----BEGIN CERTIFICATE REQUEST-----
+MIICpzCCAY8CAQAwPDELMAkGA1UEBhMCTkwxETAPBgNVBAoMCFBvbGFyU1NMMRow
+GAYDVQQDDBFQb2xhclNTTCBTZXJ2ZXIgMTCCASIwDQYJKoZIhvcNAQEBBQADggEP
+ADCCAQoCggEBAKkCHz1AatVVU4v9Nu6CZS4VYV6Jv7joRZDb7ogWUtPxQ1BHlhJZ
+ZIdr/SvgRvlzvt3PkuGRW+1moG+JKXlFgNCDatVBQ3dfOXwJBEeCsFc5cO2j7BUZ
+HqgzCEfBBUKp/UzDtN/dBh9NEFFAZ3MTD0D4bYElXwqxU8YwfhU5rPla7n+SnqYF
+W+cTl4W1I5LZ1CQG1QkliXUH3aYajz8JGb6tZSxk65Wb3P5BXhem2mxbacwCuhQs
+FiScStzN0PdSZ3PxLaAj/X70McotcMqJCwTbLqZPcG6ezr1YieJTWZ5uWpJl4og/
+DJQZo93l6J2VE+0p26twEtxaymsXq1KCVLECAwEAAaAmMCQGCSqGSIb3DQEJDjEX
+MBUwEwYDVR0lBAwwCgYIKwYBBQUHAwEwDQYJKoZIhvcNAQELBQADggEBAHi0yEGu
+Fh5tuLiLuT95UrRnly55+lTY9xchFiKtlcoEdSheybYxqk3JHuSSqojOFKZBlRdk
+oG6Azg56/aMHPWyvtCMSRQX4b+FgjeQsm9IfhYNMquQOxyPxm62vjuU3MfZIofXH
+hKdI6Ci2CDF4Fyvw50KBWniV38eE9+kjsvDLdXD3ESZJGhjjuFl8ReUiA2wdBTcP
+XEZaXUIc6B4tUnlPeqn/2zp4GBqqWzNZx6TXBpApASGG3BEJnM52FVPC7E9p+8YZ
+qIGuiF5Cz/rYZkpwffBWIfS2zZakHLm5TB8FgZkWlyReJU9Ihk2Tl/sZ1kllFdYa
+xLPnLCL82KFL1Co=
+-----END CERTIFICATE REQUEST-----
diff --git a/tests/include/test/helpers.h b/tests/include/test/helpers.h
index e0e6fd2..5f9bde6 100644
--- a/tests/include/test/helpers.h
+++ b/tests/include/test/helpers.h
@@ -295,13 +295,19 @@
/** Read an MPI from a hexadecimal string.
*
- * Like mbedtls_mpi_read_string(), but size the resulting bignum based
- * on the number of digits in the string. In particular, construct a
- * bignum with 0 limbs for an empty string, and a bignum with leading 0
- * limbs if the string has sufficiently many leading 0 digits.
+ * Like mbedtls_mpi_read_string(), but with tighter guarantees around
+ * edge cases.
*
- * This is important so that the "0 (null)" and "0 (1 limb)" and
- * "leading zeros" test cases do what they claim.
+ * - This function guarantees that if \p s begins with '-' then the sign
+ * bit of the result will be negative, even if the value is 0.
+ * When this function encounters such a "negative 0", it
+ * increments #mbedtls_test_case_uses_negative_0.
+ * - The size of the result is exactly the minimum number of limbs needed
+ * to fit the digits in the input. In particular, this function constructs
+ * a bignum with 0 limbs for an empty string, and a bignum with leading 0
+ * limbs if the string has sufficiently many leading 0 digits.
+ * This is important so that the "0 (null)" and "0 (1 limb)" and
+ * "leading zeros" test cases do what they claim.
*
* \param[out] X The MPI object to populate. It must be initialized.
* \param[in] s The null-terminated hexadecimal string to read from.
@@ -309,6 +315,14 @@
* \return \c 0 on success, an \c MBEDTLS_ERR_MPI_xxx error code otherwise.
*/
int mbedtls_test_read_mpi( mbedtls_mpi *X, const char *s );
+
+/** Nonzero if the current test case had an input parsed with
+ * mbedtls_test_read_mpi() that is a negative 0 (`"-"`, `"-0"`, `"-00"`, etc.,
+ * constructing a result with the sign bit set to -1 and the value being
+ * all-limbs-0, which is not a valid representation in #mbedtls_mpi but is
+ * tested for robustness).
+ */
+extern unsigned mbedtls_test_case_uses_negative_0;
#endif /* MBEDTLS_BIGNUM_C */
#endif /* TEST_HELPERS_H */
diff --git a/tests/opt-testcases/tls13-misc.sh b/tests/opt-testcases/tls13-misc.sh
index 4ad6faa..ed42848 100755
--- a/tests/opt-testcases/tls13-misc.sh
+++ b/tests/opt-testcases/tls13-misc.sh
@@ -282,3 +282,65 @@
0 \
-s "key exchange mode: ephemeral$"
+# skip the basic check now cause it will randomly trigger the anti-replay protection in gnutls_server
+# Add it back once we fix the issue
+skip_next_test
+requires_gnutls_tls1_3
+requires_config_enabled MBEDTLS_DEBUG_C
+requires_config_enabled MBEDTLS_SSL_CLI_C
+requires_all_configs_enabled MBEDTLS_SSL_TLS1_3_COMPATIBILITY_MODE \
+ MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_EPHEMERAL_ENABLED \
+ MBEDTLS_SSL_EARLY_DATA
+requires_any_configs_enabled MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_EPHEMERAL_ENABLED \
+ MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_ENABLED
+run_test "TLS 1.3 m->G: EarlyData: basic check, good" \
+ "$G_NEXT_SRV -d 10 --priority=NORMAL:-VERS-ALL:+VERS-TLS1.3:+CIPHER-ALL:+ECDHE-PSK:+PSK --earlydata --disable-client-cert" \
+ "$P_CLI debug_level=4 early_data=1 reco_mode=1 reconnect=1 reco_delay=2" \
+ 1 \
+ -c "Reconnecting with saved session" \
+ -c "NewSessionTicket: early_data(42) extension received." \
+ -c "ClientHello: early_data(42) extension exists." \
+ -c "EncryptedExtensions: early_data(42) extension received." \
+ -c "EncryptedExtensions: early_data(42) extension exists." \
+ -s "Parsing extension 'Early Data/42' (0 bytes)" \
+ -s "Sending extension Early Data/42 (0 bytes)" \
+ -s "early data accepted"
+
+requires_gnutls_tls1_3
+requires_config_enabled MBEDTLS_DEBUG_C
+requires_config_enabled MBEDTLS_SSL_CLI_C
+requires_all_configs_enabled MBEDTLS_SSL_TLS1_3_COMPATIBILITY_MODE \
+ MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_EPHEMERAL_ENABLED \
+ MBEDTLS_SSL_EARLY_DATA
+requires_any_configs_enabled MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_EPHEMERAL_ENABLED \
+ MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_ENABLED
+run_test "TLS 1.3 m->G: EarlyData: no early_data in NewSessionTicket, good" \
+ "$G_NEXT_SRV -d 10 --priority=NORMAL:-VERS-ALL:+VERS-TLS1.3:+CIPHER-ALL:+ECDHE-PSK:+PSK --disable-client-cert" \
+ "$P_CLI debug_level=4 early_data=1 reco_mode=1 reconnect=1 reco_delay=2" \
+ 0 \
+ -c "Reconnecting with saved session" \
+ -C "NewSessionTicket: early_data(42) extension received." \
+ -c "ClientHello: early_data(42) extension does not exist." \
+ -C "EncryptedExtensions: early_data(42) extension received." \
+ -C "EncryptedExtensions: early_data(42) extension exists."
+
+#TODO: OpenSSL tests don't work now. It might be openssl options issue, cause GnuTLS has worked.
+skip_next_test
+requires_openssl_tls1_3
+requires_config_enabled MBEDTLS_DEBUG_C
+requires_config_enabled MBEDTLS_SSL_CLI_C
+requires_all_configs_enabled MBEDTLS_SSL_TLS1_3_COMPATIBILITY_MODE \
+ MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_EPHEMERAL_ENABLED \
+ MBEDTLS_SSL_EARLY_DATA
+requires_any_configs_enabled MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_EPHEMERAL_ENABLED \
+ MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_ENABLED
+run_test "TLS 1.3, ext PSK, early data" \
+ "$O_NEXT_SRV_EARLY_DATA -msg -debug -tls1_3 -psk_identity 0a0b0c -psk 010203 -allow_no_dhe_kex -nocert" \
+ "$P_CLI debug_level=5 force_version=tls13 tls13_kex_modes=psk early_data=1 psk=010203 psk_identity=0a0b0c" \
+ 1 \
+ -c "Reconnecting with saved session" \
+ -c "NewSessionTicket: early_data(42) extension received." \
+ -c "ClientHello: early_data(42) extension exists." \
+ -c "EncryptedExtensions: early_data(42) extension received." \
+ -c "EncryptedExtensions: early_data(42) extension ( ignored )."
+
diff --git a/tests/scripts/all.sh b/tests/scripts/all.sh
index 397e765..b99b6cc 100755
--- a/tests/scripts/all.sh
+++ b/tests/scripts/all.sh
@@ -1217,6 +1217,7 @@
# Direct dependencies
scripts/config.py unset MBEDTLS_HKDF_C
scripts/config.py unset MBEDTLS_HMAC_DRBG_C
+ scripts/config.py unset MBEDTLS_PKCS7_C
# Indirect dependencies
scripts/config.py unset MBEDTLS_ECDSA_DETERMINISTIC
make
@@ -1438,6 +1439,31 @@
tests/ssl-opt.sh -f "TLS 1.2"
}
+# We're not aware of any other (open source) implementation of EC J-PAKE in TLS
+# that we could use for interop testing. However, we now have sort of two
+# implementations ourselves: one using PSA, the other not. At least test that
+# these two interoperate with each other.
+component_test_tls1_2_ecjpake_compatibility() {
+ msg "build: TLS1.2 server+client w/ EC-JPAKE w/o USE_PSA"
+ scripts/config.py set MBEDTLS_KEY_EXCHANGE_ECJPAKE_ENABLED
+ make -C programs ssl/ssl_server2 ssl/ssl_client2
+ cp programs/ssl/ssl_server2 s2_no_use_psa
+ cp programs/ssl/ssl_client2 c2_no_use_psa
+
+ msg "build: TLS1.2 server+client w/ EC-JPAKE w/ USE_PSA"
+ scripts/config.py set MBEDTLS_USE_PSA_CRYPTO
+ make clean
+ make -C programs ssl/ssl_server2 ssl/ssl_client2
+ make -C programs test/udp_proxy test/query_compile_time_config
+
+ msg "test: server w/o USE_PSA - client w/ USE_PSA"
+ P_SRV=../s2_no_use_psa tests/ssl-opt.sh -f ECJPAKE
+ msg "test: client w/o USE_PSA - server w/ USE_PSA"
+ P_CLI=../c2_no_use_psa tests/ssl-opt.sh -f ECJPAKE
+
+ rm s2_no_use_psa c2_no_use_psa
+}
+
component_test_psa_external_rng_use_psa_crypto () {
msg "build: full + PSA_CRYPTO_EXTERNAL_RNG + USE_PSA_CRYPTO minus CTR_DRBG"
scripts/config.py full
@@ -2066,6 +2092,48 @@
make test
}
+# Auxiliary function to build config for hashes with and without drivers
+config_psa_crypto_hash_use_psa () {
+ DRIVER_ONLY="$1"
+ # start with config full for maximum coverage (also enables USE_PSA)
+ scripts/config.py full
+ # enable support for drivers and configuring PSA-only algorithms
+ scripts/config.py set MBEDTLS_PSA_CRYPTO_CONFIG
+ scripts/config.py set MBEDTLS_PSA_CRYPTO_DRIVERS
+ if [ "$DRIVER_ONLY" -eq 1 ]; then
+ # disable the built-in implementation of hashes
+ scripts/config.py unset MBEDTLS_MD5_C
+ scripts/config.py unset MBEDTLS_RIPEMD160_C
+ scripts/config.py unset MBEDTLS_SHA1_C
+ scripts/config.py unset MBEDTLS_SHA224_C
+ scripts/config.py unset MBEDTLS_SHA256_C # see external RNG below
+ scripts/config.py unset MBEDTLS_SHA256_USE_A64_CRYPTO_IF_PRESENT
+ scripts/config.py unset MBEDTLS_SHA384_C
+ scripts/config.py unset MBEDTLS_SHA512_C
+ scripts/config.py unset MBEDTLS_SHA512_USE_A64_CRYPTO_IF_PRESENT
+ fi
+ # Use an external RNG as currently internal RNGs depend on entropy.c
+ # which in turn hard-depends on SHA256_C (or SHA512_C).
+ # See component_test_psa_external_rng_no_drbg_use_psa.
+ scripts/config.py set MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG
+ scripts/config.py unset MBEDTLS_ENTROPY_C
+ scripts/config.py unset MBEDTLS_ENTROPY_NV_SEED # depends on ENTROPY_C
+ scripts/config.py unset MBEDTLS_PLATFORM_NV_SEED_ALT # depends on former
+ # Also unset MD_C and things that depend on it;
+ # see component_test_crypto_full_no_md.
+ if [ "$DRIVER_ONLY" -eq 1 ]; then
+ scripts/config.py unset MBEDTLS_MD_C
+ fi
+ scripts/config.py unset MBEDTLS_HKDF_C # has independent PSA implementation
+ scripts/config.py unset MBEDTLS_HMAC_DRBG_C
+ scripts/config.py unset MBEDTLS_PKCS7_C
+ scripts/config.py unset MBEDTLS_ECDSA_DETERMINISTIC
+ scripts/config.py -f include/psa/crypto_config.h unset PSA_WANT_ALG_DETERMINISTIC_ECDSA
+}
+
+# Note that component_test_psa_crypto_config_reference_hash_use_psa
+# is related to this component and both components need to be kept in sync.
+# For details please see comments for component_test_psa_crypto_config_reference_hash_use_psa.
component_test_psa_crypto_config_accel_hash_use_psa () {
msg "test: MBEDTLS_PSA_CRYPTO_CONFIG with accelerated hash and USE_PSA"
@@ -2078,35 +2146,7 @@
loc_accel_flags=$( echo "$loc_accel_list" | sed 's/[^ ]* */-DLIBTESTDRIVER1_MBEDTLS_PSA_ACCEL_&/g' )
make -C tests libtestdriver1.a CFLAGS="$ASAN_CFLAGS $loc_accel_flags" LDFLAGS="$ASAN_CFLAGS"
- # start with config full for maximum coverage (also enables USE_PSA)
- scripts/config.py full
- # enable support for drivers and configuring PSA-only algorithms
- scripts/config.py set MBEDTLS_PSA_CRYPTO_DRIVERS
- scripts/config.py set MBEDTLS_PSA_CRYPTO_CONFIG
- # disable the built-in implementation of hashes
- scripts/config.py unset MBEDTLS_MD5_C
- scripts/config.py unset MBEDTLS_RIPEMD160_C
- scripts/config.py unset MBEDTLS_SHA1_C
- scripts/config.py unset MBEDTLS_SHA224_C
- scripts/config.py unset MBEDTLS_SHA256_C # see external RNG below
- scripts/config.py unset MBEDTLS_SHA256_USE_A64_CRYPTO_IF_PRESENT
- scripts/config.py unset MBEDTLS_SHA384_C
- scripts/config.py unset MBEDTLS_SHA512_C
- scripts/config.py unset MBEDTLS_SHA512_USE_A64_CRYPTO_IF_PRESENT
- # Use an external RNG as currently internal RNGs depend on entropy.c
- # which in turn hard-depends on SHA256_C (or SHA512_C).
- # See component_test_psa_external_rng_no_drbg_use_psa.
- scripts/config.py set MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG
- scripts/config.py unset MBEDTLS_ENTROPY_C
- scripts/config.py unset MBEDTLS_ENTROPY_NV_SEED # depends on ENTROPY_C
- scripts/config.py unset MBEDTLS_PLATFORM_NV_SEED_ALT # depends on former
- # Also unset MD_C and things that depend on it;
- # see component_test_crypto_full_no_md.
- scripts/config.py unset MBEDTLS_MD_C
- scripts/config.py unset MBEDTLS_HKDF_C # has independent PSA implementation
- scripts/config.py unset MBEDTLS_HMAC_DRBG_C
- scripts/config.py unset MBEDTLS_ECDSA_DETERMINISTIC
- scripts/config.py -f include/psa/crypto_config.h unset PSA_WANT_ALG_DETERMINISTIC_ECDSA
+ config_psa_crypto_hash_use_psa 1
loc_accel_flags="$loc_accel_flags $( echo "$loc_accel_list" | sed 's/[^ ]* */-DMBEDTLS_PSA_ACCEL_&/g' )"
make CFLAGS="$ASAN_CFLAGS -Werror -I../tests/include -I../tests -I../../tests -DPSA_CRYPTO_DRIVER_TEST -DMBEDTLS_TEST_LIBTESTDRIVER1 $loc_accel_flags" LDFLAGS="-ltestdriver1 $ASAN_CFLAGS" all
@@ -2123,16 +2163,32 @@
msg "test: MBEDTLS_PSA_CRYPTO_CONFIG with accelerated hash and USE_PSA"
make test
- # hidden option: when running outcome-analysis.sh, we can skip this
- if [ "${SKIP_SSL_OPT_COMPAT_SH-unset}" = "unset" ]; then
- msg "test: ssl-opt.sh, MBEDTLS_PSA_CRYPTO_CONFIG with accelerated hash and USE_PSA"
- tests/ssl-opt.sh
+ msg "test: ssl-opt.sh, MBEDTLS_PSA_CRYPTO_CONFIG with accelerated hash and USE_PSA"
+ tests/ssl-opt.sh
- msg "test: compat.sh, MBEDTLS_PSA_CRYPTO_CONFIG with accelerated hash and USE_PSA"
- tests/compat.sh
- else
- echo "skip ssl-opt.sh and compat.sh"
- fi
+ msg "test: compat.sh, MBEDTLS_PSA_CRYPTO_CONFIG without accelerated hash and USE_PSA"
+ tests/compat.sh
+}
+
+# This component provides reference configuration for test_psa_crypto_config_accel_hash_use_psa
+# without accelerated hash. The outcome from both components are used by the analyze_outcomes.py
+# script to find regression in test coverage when accelerated hash is used (tests and ssl-opt).
+# Both components need to be kept in sync.
+component_test_psa_crypto_config_reference_hash_use_psa() {
+ msg "test: MBEDTLS_PSA_CRYPTO_CONFIG without accelerated hash and USE_PSA"
+
+ scripts/config.py -f include/psa/crypto_config.h unset PSA_WANT_ALG_STREAM_CIPHER
+ scripts/config.py -f include/psa/crypto_config.h unset PSA_WANT_ALG_ECB_NO_PADDING
+
+ config_psa_crypto_hash_use_psa 0
+
+ make
+
+ msg "test: MBEDTLS_PSA_CRYPTO_CONFIG without accelerated hash and USE_PSA"
+ make test
+
+ msg "test: ssl-opt.sh, MBEDTLS_PSA_CRYPTO_CONFIG without accelerated hash and USE_PSA"
+ tests/ssl-opt.sh
}
component_test_psa_crypto_config_accel_cipher () {
@@ -3221,6 +3277,7 @@
component_test_tls13_only () {
msg "build: default config with MBEDTLS_SSL_PROTO_TLS1_3, without MBEDTLS_SSL_PROTO_TLS1_2"
+ scripts/config.py set MBEDTLS_SSL_EARLY_DATA
make CFLAGS="'-DMBEDTLS_USER_CONFIG_FILE=\"../tests/configs/tls13-only.h\"'"
msg "test: TLS 1.3 only, all key exchange modes enabled"
@@ -3240,6 +3297,8 @@
scripts/config.py unset MBEDTLS_SSL_SERVER_NAME_INDICATION
scripts/config.py unset MBEDTLS_ECDSA_C
scripts/config.py unset MBEDTLS_PKCS1_V21
+ scripts/config.py unset MBEDTLS_PKCS7_C
+ scripts/config.py set MBEDTLS_SSL_EARLY_DATA
make CFLAGS="'-DMBEDTLS_USER_CONFIG_FILE=\"../tests/configs/tls13-only.h\"'"
msg "test_suite_ssl: TLS 1.3 only, only PSK key exchange mode enabled"
@@ -3253,6 +3312,7 @@
msg "build: TLS 1.3 only from default, only ephemeral key exchange mode"
scripts/config.py unset MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_ENABLED
scripts/config.py unset MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_EPHEMERAL_ENABLED
+ scripts/config.py unset MBEDTLS_SSL_EARLY_DATA
make CFLAGS="'-DMBEDTLS_USER_CONFIG_FILE=\"../tests/configs/tls13-only.h\"'"
msg "test_suite_ssl: TLS 1.3 only, only ephemeral key exchange mode"
@@ -3271,6 +3331,8 @@
scripts/config.py unset MBEDTLS_SSL_SERVER_NAME_INDICATION
scripts/config.py unset MBEDTLS_ECDSA_C
scripts/config.py unset MBEDTLS_PKCS1_V21
+ scripts/config.py unset MBEDTLS_PKCS7_C
+ scripts/config.py set MBEDTLS_SSL_EARLY_DATA
make CFLAGS="'-DMBEDTLS_USER_CONFIG_FILE=\"../tests/configs/tls13-only.h\"'"
msg "test_suite_ssl: TLS 1.3 only, only PSK ephemeral key exchange mode"
@@ -3288,6 +3350,8 @@
scripts/config.py unset MBEDTLS_SSL_SERVER_NAME_INDICATION
scripts/config.py unset MBEDTLS_ECDSA_C
scripts/config.py unset MBEDTLS_PKCS1_V21
+ scripts/config.py unset MBEDTLS_PKCS7_C
+ scripts/config.py set MBEDTLS_SSL_EARLY_DATA
make CFLAGS="'-DMBEDTLS_USER_CONFIG_FILE=\"../tests/configs/tls13-only.h\"'"
msg "test_suite_ssl: TLS 1.3 only, PSK and PSK ephemeral key exchange modes"
@@ -3300,6 +3364,7 @@
component_test_tls13_only_ephemeral_all () {
msg "build: TLS 1.3 only from default, without PSK key exchange mode"
scripts/config.py unset MBEDTLS_SSL_TLS1_3_KEY_EXCHANGE_MODE_PSK_ENABLED
+ scripts/config.py set MBEDTLS_SSL_EARLY_DATA
make CFLAGS="'-DMBEDTLS_USER_CONFIG_FILE=\"../tests/configs/tls13-only.h\"'"
msg "test_suite_ssl: TLS 1.3 only, ephemeral and PSK ephemeral key exchange modes"
@@ -3314,6 +3379,7 @@
scripts/config.py set MBEDTLS_SSL_PROTO_TLS1_3
scripts/config.py set MBEDTLS_SSL_TLS1_3_COMPATIBILITY_MODE
scripts/config.py set MBEDTLS_SSL_CID_TLS1_3_PADDING_GRANULARITY 1
+ scripts/config.py set MBEDTLS_SSL_EARLY_DATA
CC=gcc cmake -D CMAKE_BUILD_TYPE:String=Asan .
make
msg "test: default config with MBEDTLS_SSL_PROTO_TLS1_3 enabled, without padding"
@@ -3327,6 +3393,7 @@
scripts/config.py set MBEDTLS_SSL_PROTO_TLS1_3
scripts/config.py unset MBEDTLS_SSL_TLS1_3_COMPATIBILITY_MODE
scripts/config.py set MBEDTLS_SSL_CID_TLS1_3_PADDING_GRANULARITY 1
+ scripts/config.py set MBEDTLS_SSL_EARLY_DATA
CC=gcc cmake -D CMAKE_BUILD_TYPE:String=Asan .
make
msg "test: default config with MBEDTLS_SSL_PROTO_TLS1_3 enabled, without padding"
diff --git a/tests/scripts/analyze_outcomes.py b/tests/scripts/analyze_outcomes.py
index d06a059..bb44396 100755
--- a/tests/scripts/analyze_outcomes.py
+++ b/tests/scripts/analyze_outcomes.py
@@ -9,6 +9,7 @@
import argparse
import sys
import traceback
+import re
import check_test_cases
@@ -60,6 +61,37 @@
# fixed this branch to have full coverage of test cases.
results.warning('Test case not executed: {}', key)
+def analyze_driver_vs_reference(outcomes, component_ref, component_driver, ignored_tests):
+ """Check that all tests executed in the reference component are also
+ executed in the corresponding driver component.
+ Skip test suites provided in ignored_tests list.
+ """
+ available = check_test_cases.collect_available_test_cases()
+ result = True
+
+ for key in available:
+ # Skip ignored test suites
+ test_suite = key.split(';')[0] # retrieve test suit name
+ test_suite = test_suite.split('.')[0] # retrieve main part of test suit name
+ if test_suite in ignored_tests:
+ continue
+ # Continue if test was not executed by any component
+ hits = outcomes[key].hits() if key in outcomes else 0
+ if hits == 0:
+ continue
+ # Search for tests that run in reference component and not in driver component
+ driver_test_passed = False
+ reference_test_passed = False
+ for entry in outcomes[key].successes:
+ if component_driver in entry:
+ driver_test_passed = True
+ if component_ref in entry:
+ reference_test_passed = True
+ if(driver_test_passed is False and reference_test_passed is True):
+ print('{}: driver: skipped/failed; reference: passed'.format(key))
+ result = False
+ return result
+
def analyze_outcomes(outcomes):
"""Run all analyses on the given outcome collection."""
results = Results()
@@ -87,20 +119,75 @@
outcomes[key].failures.append(setup)
return outcomes
-def analyze_outcome_file(outcome_file):
- """Analyze the given outcome file."""
+def do_analyze_coverage(outcome_file, args):
+ """Perform coverage analysis."""
+ del args # unused
outcomes = read_outcome_file(outcome_file)
- return analyze_outcomes(outcomes)
+ results = analyze_outcomes(outcomes)
+ return results.error_count == 0
+
+def do_analyze_driver_vs_reference(outcome_file, args):
+ """Perform driver vs reference analyze."""
+ ignored_tests = ['test_suite_' + x for x in args['ignored_suites']]
+
+ outcomes = read_outcome_file(outcome_file)
+ return analyze_driver_vs_reference(outcomes, args['component_ref'],
+ args['component_driver'], ignored_tests)
+
+# List of tasks with a function that can handle this task and additional arguments if required
+TASKS = {
+ 'analyze_coverage': {
+ 'test_function': do_analyze_coverage,
+ 'args': {}},
+ 'analyze_driver_vs_reference_hash': {
+ 'test_function': do_analyze_driver_vs_reference,
+ 'args': {
+ 'component_ref': 'test_psa_crypto_config_reference_hash_use_psa',
+ 'component_driver': 'test_psa_crypto_config_accel_hash_use_psa',
+ 'ignored_suites': ['shax', 'mdx', # the software implementations that are being excluded
+ 'md', # the legacy abstraction layer that's being excluded
+ ]}}
+}
def main():
try:
parser = argparse.ArgumentParser(description=__doc__)
parser.add_argument('outcomes', metavar='OUTCOMES.CSV',
help='Outcome file to analyze')
+ parser.add_argument('task', default='all', nargs='?',
+ help='Analysis to be done. By default, run all tasks. '
+ 'With one or more TASK, run only those. '
+ 'TASK can be the name of a single task or '
+ 'comma/space-separated list of tasks. ')
+ parser.add_argument('--list', action='store_true',
+ help='List all available tasks and exit.')
options = parser.parse_args()
- results = analyze_outcome_file(options.outcomes)
- if results.error_count > 0:
+
+ if options.list:
+ for task in TASKS:
+ print(task)
+ sys.exit(0)
+
+ result = True
+
+ if options.task == 'all':
+ tasks = TASKS.keys()
+ else:
+ tasks = re.split(r'[, ]+', options.task)
+
+ for task in tasks:
+ if task not in TASKS:
+ print('Error: invalid task: {}'.format(task))
+ sys.exit(1)
+
+ for task in TASKS:
+ if task in tasks:
+ if not TASKS[task]['test_function'](options.outcomes, TASKS[task]['args']):
+ result = False
+
+ if result is False:
sys.exit(1)
+ print("SUCCESS :-)")
except Exception: # pylint: disable=broad-except
# Print the backtrace and exit explicitly with our chosen status.
traceback.print_exc()
diff --git a/tests/scripts/check_files.py b/tests/scripts/check_files.py
index 5c18702..42f2e82 100755
--- a/tests/scripts/check_files.py
+++ b/tests/scripts/check_files.py
@@ -122,6 +122,7 @@
r'tests/data_files/.*\.req\.[^/]+\Z',
r'tests/data_files/.*malformed[^/]+\Z',
r'tests/data_files/format_pkcs12\.fmt\Z',
+ r'tests/data_files/pkcs7_data.*\.bin\Z',
]
BINARY_FILE_PATH_RE = re.compile('|'.join(BINARY_FILE_PATH_RE_LIST))
diff --git a/tests/scripts/generate_bignum_tests.py b/tests/scripts/generate_bignum_tests.py
index a105203..c3058e9 100755
--- a/tests/scripts/generate_bignum_tests.py
+++ b/tests/scripts/generate_bignum_tests.py
@@ -57,7 +57,7 @@
import sys
from abc import ABCMeta
-from typing import Iterator, List
+from typing import List
import scripts_path # pylint: disable=unused-import
from mbedtls_dev import test_case
@@ -68,21 +68,29 @@
# the framework
from mbedtls_dev import bignum_core, bignum_mod_raw # pylint: disable=unused-import
-class BignumTarget(test_data_generation.BaseTarget, metaclass=ABCMeta):
- #pylint: disable=abstract-method
+class BignumTarget(test_data_generation.BaseTarget):
+ #pylint: disable=too-few-public-methods
"""Target for bignum (legacy) test case generation."""
target_basename = 'test_suite_bignum.generated'
-class BignumOperation(bignum_common.OperationCommon, BignumTarget, metaclass=ABCMeta):
+class BignumOperation(bignum_common.OperationCommon, BignumTarget,
+ metaclass=ABCMeta):
#pylint: disable=abstract-method
"""Common features for bignum operations in legacy tests."""
+ unique_combinations_only = True
input_values = [
- "", "0", "7b", "-7b",
+ "", "0", "-", "-0",
+ "7b", "-7b",
"0000000000000000123", "-0000000000000000123",
"1230000000000000000", "-1230000000000000000"
]
+ def description_suffix(self) -> str:
+ #pylint: disable=no-self-use # derived classes need self
+ """Text to add at the end of the test case description."""
+ return ""
+
def description(self) -> str:
"""Generate a description for the test case.
@@ -96,6 +104,9 @@
self.symbol,
self.value_description(self.arg_b)
)
+ description_suffix = self.description_suffix()
+ if description_suffix:
+ self.case_description += " " + description_suffix
return super().description()
@staticmethod
@@ -107,6 +118,8 @@
"""
if val == "":
return "0 (null)"
+ if val == "-":
+ return "negative 0 (null)"
if val == "0":
return "0 (1 limb)"
@@ -121,11 +134,6 @@
tmp = "large " + tmp
return tmp
- @classmethod
- def generate_function_tests(cls) -> Iterator[test_case.TestCase]:
- for a_value, b_value in cls.get_value_pairs():
- yield cls(a_value, b_value).create_test_case()
-
class BignumCmp(BignumOperation):
"""Test cases for bignum value comparison."""
@@ -171,9 +179,21 @@
]
)
- def result(self) -> List[str]:
- return [bignum_common.quote_str("{:x}").format(self.int_a + self.int_b)]
+ def __init__(self, val_a: str, val_b: str) -> None:
+ super().__init__(val_a, val_b)
+ self._result = self.int_a + self.int_b
+ def description_suffix(self) -> str:
+ if (self.int_a >= 0 and self.int_b >= 0):
+ return "" # obviously positive result or 0
+ if (self.int_a <= 0 and self.int_b <= 0):
+ return "" # obviously negative result or 0
+ # The sign of the result is not obvious, so indicate it
+ return ", result{}0".format('>' if self._result > 0 else
+ '<' if self._result < 0 else '=')
+
+ def result(self) -> List[str]:
+ return [bignum_common.quote_str("{:x}".format(self._result))]
if __name__ == '__main__':
# Use the section of the docstring relevant to the CLI as description
diff --git a/tests/scripts/run-test-suites.pl b/tests/scripts/run-test-suites.pl
index 8a5bb93..cedc0bf 100755
--- a/tests/scripts/run-test-suites.pl
+++ b/tests/scripts/run-test-suites.pl
@@ -50,10 +50,10 @@
'verbose|v:1' => \$verbose,
) or die;
-# All test suites = executable files derived from a .data file.
+# All test suites = executable files with a .datax file.
my @suites = ();
-for my $data_file (glob 'suites/test_suite_*.data') {
- (my $base = $data_file) =~ s#^suites/(.*)\.data$#$1#;
+for my $data_file (glob 'test_suite_*.datax') {
+ (my $base = $data_file) =~ s/\.datax$//;
push @suites, $base if -x $base;
push @suites, "$base.exe" if -e "$base.exe";
}
diff --git a/tests/src/helpers.c b/tests/src/helpers.c
index cc23fd7..7c83714 100644
--- a/tests/src/helpers.c
+++ b/tests/src/helpers.c
@@ -89,6 +89,10 @@
mbedtls_test_info.step = step;
}
+#if defined(MBEDTLS_BIGNUM_C)
+unsigned mbedtls_test_case_uses_negative_0 = 0;
+#endif
+
void mbedtls_test_info_reset( void )
{
mbedtls_test_info.result = MBEDTLS_TEST_RESULT_SUCCESS;
@@ -98,6 +102,9 @@
mbedtls_test_info.filename = 0;
memset( mbedtls_test_info.line1, 0, sizeof( mbedtls_test_info.line1 ) );
memset( mbedtls_test_info.line2, 0, sizeof( mbedtls_test_info.line2 ) );
+#if defined(MBEDTLS_BIGNUM_C)
+ mbedtls_test_case_uses_negative_0 = 0;
+#endif
}
int mbedtls_test_equal( const char *test, int line_no, const char* filename,
@@ -396,6 +403,15 @@
int mbedtls_test_read_mpi( mbedtls_mpi *X, const char *s )
{
+ int negative = 0;
+ /* Always set the sign bit to -1 if the input has a minus sign, even for 0.
+ * This creates an invalid representation, which mbedtls_mpi_read_string()
+ * avoids but we want to be able to create that in test data. */
+ if( s[0] == '-' )
+ {
+ ++s;
+ negative = 1;
+ }
/* mbedtls_mpi_read_string() currently retains leading zeros.
* It always allocates at least one limb for the value 0. */
if( s[0] == 0 )
@@ -403,7 +419,15 @@
mbedtls_mpi_free( X );
return( 0 );
}
- else
- return( mbedtls_mpi_read_string( X, 16, s ) );
+ int ret = mbedtls_mpi_read_string( X, 16, s );
+ if( ret != 0 )
+ return( ret );
+ if( negative )
+ {
+ if( mbedtls_mpi_cmp_int( X, 0 ) == 0 )
+ ++mbedtls_test_case_uses_negative_0;
+ X->s = -1;
+ }
+ return( 0 );
}
#endif
diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh
index de94983..1fe8bae 100755
--- a/tests/ssl-opt.sh
+++ b/tests/ssl-opt.sh
@@ -80,12 +80,14 @@
if [ -n "${OPENSSL_NEXT:-}" ]; then
O_NEXT_SRV="$OPENSSL_NEXT s_server -www -cert data_files/server5.crt -key data_files/server5.key"
+ O_NEXT_SRV_EARLY_DATA="$OPENSSL_NEXT s_server -early_data -cert data_files/server5.crt -key data_files/server5.key"
O_NEXT_SRV_NO_CERT="$OPENSSL_NEXT s_server -www "
O_NEXT_CLI="echo 'GET / HTTP/1.0' | $OPENSSL_NEXT s_client -CAfile data_files/test-ca_cat12.crt"
O_NEXT_CLI_NO_CERT="echo 'GET / HTTP/1.0' | $OPENSSL_NEXT s_client"
else
O_NEXT_SRV=false
O_NEXT_SRV_NO_CERT=false
+ O_NEXT_SRV_EARLY_DATA=false
O_NEXT_CLI_NO_CERT=false
O_NEXT_CLI=false
fi
@@ -1360,7 +1362,7 @@
if [ -n "$PXY_CMD" ]; then
kill $PXY_PID >/dev/null 2>&1
- wait $PXY_PID
+ wait $PXY_PID >> $PXY_OUT 2>&1
fi
}
@@ -1687,9 +1689,24 @@
O_LEGACY_CLI="$O_LEGACY_CLI -connect 127.0.0.1:+SRV_PORT"
fi
+# Newer versions of OpenSSL have a syntax to enable all "ciphers", even
+# low-security ones. This covers not just cipher suites but also protocol
+# versions. It is necessary, for example, to use (D)TLS 1.0/1.1 on
+# OpenSSL 1.1.1f from Ubuntu 20.04. The syntax was only introduced in
+# OpenSSL 1.1.0 (21e0c1d23afff48601eb93135defddae51f7e2e3) and I can't find
+# a way to discover it from -help, so check the openssl version.
+case $($OPENSSL_CMD version) in
+ "OpenSSL 0"*|"OpenSSL 1.0"*) :;;
+ *)
+ O_CLI="$O_CLI -cipher ALL@SECLEVEL=0"
+ O_SRV="$O_SRV -cipher ALL@SECLEVEL=0"
+ ;;
+esac
+
if [ -n "${OPENSSL_NEXT:-}" ]; then
O_NEXT_SRV="$O_NEXT_SRV -accept $SRV_PORT"
O_NEXT_SRV_NO_CERT="$O_NEXT_SRV_NO_CERT -accept $SRV_PORT"
+ O_NEXT_SRV_EARLY_DATA="$O_NEXT_SRV_EARLY_DATA -accept $SRV_PORT"
O_NEXT_CLI="$O_NEXT_CLI -connect 127.0.0.1:+SRV_PORT"
O_NEXT_CLI_NO_CERT="$O_NEXT_CLI_NO_CERT -connect 127.0.0.1:+SRV_PORT"
fi
@@ -2381,6 +2398,31 @@
-u "IV used" \
-U "IV used"
+# Test for correctness of sent single supported algorithm
+requires_config_enabled MBEDTLS_ECP_DP_SECP256R1_ENABLED
+requires_config_enabled MBEDTLS_SSL_PROTO_TLS1_2
+requires_config_enabled MBEDTLS_DEBUG_C
+requires_config_enabled MBEDTLS_SSL_CLI_C
+requires_config_enabled MBEDTLS_SSL_SRV_C
+requires_config_enabled MBEDTLS_ECDSA_C
+requires_hash_alg SHA_256
+run_test "Single supported algorithm sending: mbedtls client" \
+ "$P_SRV sig_algs=ecdsa_secp256r1_sha256 auth_mode=required" \
+ "$P_CLI sig_algs=ecdsa_secp256r1_sha256 debug_level=3" \
+ 0 \
+ -c "Supported Signature Algorithm found: 04 03"
+
+requires_config_enabled MBEDTLS_SSL_PROTO_TLS1_2
+requires_config_enabled MBEDTLS_SSL_SRV_C
+requires_config_enabled MBEDTLS_ECDSA_C
+requires_config_enabled MBEDTLS_ECP_DP_SECP256R1_ENABLED
+requires_hash_alg SHA_256
+run_test "Single supported algorithm sending: openssl client" \
+ "$P_SRV sig_algs=ecdsa_secp256r1_sha256 auth_mode=required" \
+ "$O_CLI -cert data_files/server6.crt \
+ -key data_files/server6.key" \
+ 0
+
# Tests for certificate verification callback
requires_config_enabled MBEDTLS_SSL_PROTO_TLS1_2
run_test "Configuration-specific CRT verification callback" \
@@ -5281,8 +5323,8 @@
key_file=data_files/server6.key \
force_ciphersuite=TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384" \
0 \
- -c "Supported Signature Algorithm found: 4," \
- -c "Supported Signature Algorithm found: 5,"
+ -c "Supported Signature Algorithm found: 04 " \
+ -c "Supported Signature Algorithm found: 05 "
requires_config_enabled MBEDTLS_SSL_PROTO_TLS1_2
requires_any_configs_enabled $TLS1_2_KEY_EXCHANGES_WITH_CERT
@@ -5292,8 +5334,8 @@
key_file=data_files/server6.key \
force_ciphersuite=TLS-ECDHE-ECDSA-WITH-AES-128-GCM-SHA256" \
0 \
- -c "Supported Signature Algorithm found: 4," \
- -c "Supported Signature Algorithm found: 5,"
+ -c "Supported Signature Algorithm found: 04 " \
+ -c "Supported Signature Algorithm found: 05 "
requires_key_exchange_with_cert_in_tls12_or_tls13_enabled
run_test "Authentication: client has no cert, server required (TLS)" \
@@ -5694,8 +5736,8 @@
force_ciphersuite=TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384" \
0 \
-s "use CA callback for X.509 CRT verification" \
- -c "Supported Signature Algorithm found: 4," \
- -c "Supported Signature Algorithm found: 5,"
+ -c "Supported Signature Algorithm found: 04 " \
+ -c "Supported Signature Algorithm found: 05 "
requires_config_enabled MBEDTLS_X509_TRUSTED_CERTIFICATE_CALLBACK
requires_config_enabled MBEDTLS_SSL_PROTO_TLS1_2
@@ -5707,8 +5749,8 @@
force_ciphersuite=TLS-ECDHE-ECDSA-WITH-AES-128-GCM-SHA256" \
0 \
-s "use CA callback for X.509 CRT verification" \
- -c "Supported Signature Algorithm found: 4," \
- -c "Supported Signature Algorithm found: 5,"
+ -c "Supported Signature Algorithm found: 04 " \
+ -c "Supported Signature Algorithm found: 05 "
requires_config_enabled MBEDTLS_X509_TRUSTED_CERTIFICATE_CALLBACK
requires_config_enabled MBEDTLS_SSL_PROTO_TLS1_2
@@ -12914,8 +12956,8 @@
"$O_NEXT_CLI -msg -debug -tls1_3 -reconnect" \
0 \
-s "=> write NewSessionTicket msg" \
- -s "server state: MBEDTLS_SSL_NEW_SESSION_TICKET" \
- -s "server state: MBEDTLS_SSL_NEW_SESSION_TICKET_FLUSH"
+ -s "server state: MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET" \
+ -s "server state: MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET_FLUSH"
requires_gnutls_tls1_3
requires_config_enabled MBEDTLS_SSL_SESSION_TICKETS
@@ -12931,8 +12973,8 @@
-c "Connecting again- trying to resume previous session" \
-c "NEW SESSION TICKET (4) was received" \
-s "=> write NewSessionTicket msg" \
- -s "server state: MBEDTLS_SSL_NEW_SESSION_TICKET" \
- -s "server state: MBEDTLS_SSL_NEW_SESSION_TICKET_FLUSH" \
+ -s "server state: MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET" \
+ -s "server state: MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET_FLUSH" \
-s "key exchange mode: ephemeral" \
-s "key exchange mode: psk_ephemeral" \
-s "found pre_shared_key extension"
@@ -12954,8 +12996,8 @@
-c "Reconnecting with saved session" \
-c "HTTP/1.0 200 OK" \
-s "=> write NewSessionTicket msg" \
- -s "server state: MBEDTLS_SSL_NEW_SESSION_TICKET" \
- -s "server state: MBEDTLS_SSL_NEW_SESSION_TICKET_FLUSH" \
+ -s "server state: MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET" \
+ -s "server state: MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET_FLUSH" \
-s "key exchange mode: ephemeral" \
-s "key exchange mode: psk_ephemeral" \
-s "found pre_shared_key extension"
@@ -13009,8 +13051,8 @@
-c "Reconnecting with saved session" \
-c "HTTP/1.0 200 OK" \
-s "=> write NewSessionTicket msg" \
- -s "server state: MBEDTLS_SSL_NEW_SESSION_TICKET" \
- -s "server state: MBEDTLS_SSL_NEW_SESSION_TICKET_FLUSH" \
+ -s "server state: MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET" \
+ -s "server state: MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET_FLUSH" \
-s "key exchange mode: ephemeral" \
-s "key exchange mode: psk_ephemeral" \
-s "found pre_shared_key extension"
@@ -13033,8 +13075,8 @@
-c "Reconnecting with saved session" \
-c "Hostname mismatch the session ticket, disable session resumption." \
-s "=> write NewSessionTicket msg" \
- -s "server state: MBEDTLS_SSL_NEW_SESSION_TICKET" \
- -s "server state: MBEDTLS_SSL_NEW_SESSION_TICKET_FLUSH"
+ -s "server state: MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET" \
+ -s "server state: MBEDTLS_SSL_TLS1_3_NEW_SESSION_TICKET_FLUSH"
# Test heap memory usage after handshake
requires_config_enabled MBEDTLS_SSL_PROTO_TLS1_2
diff --git a/tests/suites/test_suite_bignum.function b/tests/suites/test_suite_bignum.function
index 5c3d776..55bb2f5 100644
--- a/tests/suites/test_suite_bignum.function
+++ b/tests/suites/test_suite_bignum.function
@@ -13,10 +13,21 @@
* constructing the value. */
static int sign_is_valid( const mbedtls_mpi *X )
{
+ /* Only +1 and -1 are valid sign bits, not e.g. 0 */
if( X->s != 1 && X->s != -1 )
- return( 0 ); // invalid sign bit, e.g. 0
- if( mbedtls_mpi_bitlen( X ) == 0 && X->s != 1 )
- return( 0 ); // negative zero
+ return( 0 );
+
+ /* The value 0 must be represented with the sign +1. A "negative zero"
+ * with s=-1 is an invalid representation. Forbid that. As an exception,
+ * we sometimes test the robustness of library functions when given
+ * a negative zero input. If a test case has a negative zero as input,
+ * we don't mind if the function has a negative zero output. */
+ if( ! mbedtls_test_case_uses_negative_0 &&
+ mbedtls_mpi_bitlen( X ) == 0 && X->s != 1 )
+ {
+ return( 0 );
+ }
+
return( 1 );
}
@@ -1447,6 +1458,150 @@
}
/* END_CASE */
+/* BEGIN_CASE */
+void most_negative_mpi_sint( )
+{
+ /* Ad hoc tests for n = -p = -2^(biL-1) as a mbedtls_mpi_sint. We
+ * guarantee that mbedtls_mpi_sint is a two's complement type, so this
+ * is a valid value. However, negating it (`-n`) has undefined behavior
+ * (although in practice `-n` evaluates to the value n).
+ *
+ * This function has ad hoc tests for this value. It's separated from other
+ * functions because the test framework makes it hard to pass this value
+ * into test cases.
+ *
+ * In the comments here:
+ * - biL = number of bits in limbs
+ * - p = 2^(biL-1) (smallest positive value not in mbedtls_mpi_sint range)
+ * - n = -2^(biL-1) (largest negative value in mbedtls_mpi_sint range)
+ */
+
+ mbedtls_mpi A, R, X;
+ mbedtls_mpi_init( &A );
+ mbedtls_mpi_init( &R );
+ mbedtls_mpi_init( &X );
+
+ const size_t biL = 8 * sizeof( mbedtls_mpi_sint );
+ mbedtls_mpi_uint most_positive_plus_1 = (mbedtls_mpi_uint) 1 << ( biL - 1 );
+ const mbedtls_mpi_sint most_positive = most_positive_plus_1 - 1;
+ const mbedtls_mpi_sint most_negative = - most_positive - 1;
+ TEST_EQUAL( (mbedtls_mpi_uint) most_negative,
+ (mbedtls_mpi_uint) 1 << ( biL - 1 ) );
+ TEST_EQUAL( (mbedtls_mpi_uint) most_negative << 1, 0 );
+
+ /* Test mbedtls_mpi_lset() */
+ TEST_EQUAL( mbedtls_mpi_lset( &A, most_negative ), 0 );
+ TEST_EQUAL( A.s, -1 );
+ TEST_EQUAL( A.n, 1 );
+ TEST_EQUAL( A.p[0], most_positive_plus_1 );
+
+ /* Test mbedtls_mpi_cmp_int(): -p == -p */
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &A, most_negative ), 0 );
+
+ /* Test mbedtls_mpi_cmp_int(): -(p+1) < -p */
+ A.p[0] = most_positive_plus_1 + 1;
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &A, most_negative ), -1 );
+
+ /* Test mbedtls_mpi_cmp_int(): -(p-1) > -p */
+ A.p[0] = most_positive_plus_1 - 1;
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &A, most_negative ), 1 );
+
+ /* Test mbedtls_mpi_add_int(): (p-1) + (-p) */
+ TEST_EQUAL( mbedtls_mpi_lset( &A, most_positive ), 0 );
+ TEST_EQUAL( mbedtls_mpi_add_int( &X, &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &X, -1 ), 0 );
+
+ /* Test mbedtls_mpi_add_int(): (0) + (-p) */
+ TEST_EQUAL( mbedtls_mpi_lset( &A, 0 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_add_int( &X, &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &X, most_negative ), 0 );
+
+ /* Test mbedtls_mpi_add_int(): (-p) + (-p) */
+ TEST_EQUAL( mbedtls_mpi_lset( &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_add_int( &X, &A, most_negative ), 0 );
+ TEST_EQUAL( X.s, -1 );
+ TEST_EQUAL( X.n, 2 );
+ TEST_EQUAL( X.p[0], 0 );
+ TEST_EQUAL( X.p[1], 1 );
+
+ /* Test mbedtls_mpi_sub_int(): (p) - (-p) */
+ mbedtls_mpi_free( &X );
+ TEST_EQUAL( mbedtls_mpi_lset( &A, most_positive ), 0 );
+ TEST_EQUAL( mbedtls_mpi_sub_int( &X, &A, most_negative ), 0 );
+ TEST_EQUAL( X.s, 1 );
+ TEST_EQUAL( X.n, 1 );
+ TEST_EQUAL( X.p[0], ~(mbedtls_mpi_uint)0 );
+
+ /* Test mbedtls_mpi_sub_int(): (0) - (-p) */
+ TEST_EQUAL( mbedtls_mpi_lset( &A, 0 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_sub_int( &X, &A, most_negative ), 0 );
+ TEST_EQUAL( X.s, 1 );
+ TEST_EQUAL( X.n, 1 );
+ TEST_EQUAL( X.p[0], most_positive_plus_1 );
+
+ /* Test mbedtls_mpi_sub_int(): (-p) - (-p) */
+ TEST_EQUAL( mbedtls_mpi_lset( &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_sub_int( &X, &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &X, 0 ), 0 );
+
+ /* Test mbedtls_mpi_div_int(): (-p+1) / (-p) */
+ TEST_EQUAL( mbedtls_mpi_lset( &A, -most_positive ), 0 );
+ TEST_EQUAL( mbedtls_mpi_div_int( &X, &R, &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &X, 0 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &R, -most_positive ), 0 );
+
+ /* Test mbedtls_mpi_div_int(): (-p) / (-p) */
+ TEST_EQUAL( mbedtls_mpi_lset( &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_div_int( &X, &R, &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &X, 1 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &R, 0 ), 0 );
+
+ /* Test mbedtls_mpi_div_int(): (-2*p) / (-p) */
+ TEST_EQUAL( mbedtls_mpi_shift_l( &A, 1 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_div_int( &X, &R, &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &X, 2 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &R, 0 ), 0 );
+
+ /* Test mbedtls_mpi_div_int(): (-2*p+1) / (-p) */
+ TEST_EQUAL( mbedtls_mpi_add_int( &A, &A, 1 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_div_int( &X, &R, &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &X, 1 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &R, -most_positive ), 0 );
+
+ /* Test mbedtls_mpi_div_int(): (p-1) / (-p) */
+ TEST_EQUAL( mbedtls_mpi_lset( &A, most_positive ), 0 );
+ TEST_EQUAL( mbedtls_mpi_div_int( &X, &R, &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &X, 0 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &R, most_positive ), 0 );
+
+ /* Test mbedtls_mpi_div_int(): (p) / (-p) */
+ TEST_EQUAL( mbedtls_mpi_add_int( &A, &A, 1 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_div_int( &X, &R, &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &X, -1 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &R, 0 ), 0 );
+
+ /* Test mbedtls_mpi_div_int(): (2*p) / (-p) */
+ TEST_EQUAL( mbedtls_mpi_shift_l( &A, 1 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_div_int( &X, &R, &A, most_negative ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &X, -2 ), 0 );
+ TEST_EQUAL( mbedtls_mpi_cmp_int( &R, 0 ), 0 );
+
+ /* Test mbedtls_mpi_mod_int(): never valid */
+ TEST_EQUAL( mbedtls_mpi_mod_int( X.p, &A, most_negative ),
+ MBEDTLS_ERR_MPI_NEGATIVE_VALUE );
+
+ /* Test mbedtls_mpi_random(): never valid */
+ TEST_EQUAL( mbedtls_mpi_random( &X, most_negative, &A,
+ mbedtls_test_rnd_std_rand, NULL ),
+ MBEDTLS_ERR_MPI_BAD_INPUT_DATA );
+
+exit:
+ mbedtls_mpi_free( &A );
+ mbedtls_mpi_free( &R );
+ mbedtls_mpi_free( &X );
+}
+/* END_CASE */
+
/* BEGIN_CASE depends_on:MBEDTLS_SELF_TEST */
void mpi_selftest( )
{
diff --git a/tests/suites/test_suite_bignum.misc.data b/tests/suites/test_suite_bignum.misc.data
index 0b8aa33..dc6830e 100644
--- a/tests/suites/test_suite_bignum.misc.data
+++ b/tests/suites/test_suite_bignum.misc.data
@@ -1144,6 +1144,18 @@
Test mbedtls_mpi_div_mpi: 0 (null) / -1
mpi_div_mpi:"":"-1":"":"":0
+Test mbedtls_mpi_div_mpi: -0 (null) / 1
+mpi_div_mpi:"-":"1":"":"":0
+
+Test mbedtls_mpi_div_mpi: -0 (null) / -1
+mpi_div_mpi:"-":"-1":"":"":0
+
+Test mbedtls_mpi_div_mpi: -0 (null) / 42
+mpi_div_mpi:"-":"2a":"":"":0
+
+Test mbedtls_mpi_div_mpi: -0 (null) / -42
+mpi_div_mpi:"-":"-2a":"":"":0
+
Test mbedtls_mpi_div_mpi #1
mpi_div_mpi:"9e22d6da18a33d1ef28d2a82242b3f6e9c9742f63e5d440f58a190bfaf23a7866e67589adb80":"22":"4a6abf75b13dc268ea9cc8b5b6aaf0ac85ecd437a4e0987fb13cf8d2acc57c0306c738c1583":"1a":0
@@ -1204,6 +1216,18 @@
Test mbedtls_mpi_mod_mpi: 0 (null) % -1
mpi_mod_mpi:"":"-1":"":MBEDTLS_ERR_MPI_NEGATIVE_VALUE
+Test mbedtls_mpi_mod_mpi: -0 (null) % 1
+mpi_mod_mpi:"-":"1":"":0
+
+Test mbedtls_mpi_mod_mpi: -0 (null) % -1
+mpi_mod_mpi:"-":"-1":"":MBEDTLS_ERR_MPI_NEGATIVE_VALUE
+
+Test mbedtls_mpi_mod_mpi: -0 (null) % 42
+mpi_mod_mpi:"-":"2a":"":0
+
+Test mbedtls_mpi_mod_mpi: -0 (null) % -42
+mpi_mod_mpi:"-":"-2a":"":MBEDTLS_ERR_MPI_NEGATIVE_VALUE
+
Base test mbedtls_mpi_mod_int #1
mpi_mod_int:"3e8":"d":"c":0
@@ -1934,6 +1958,9 @@
MPI random bad arguments: min > N = 1, 0 limb in upper bound
mpi_random_fail:2:"000000000000000001":MBEDTLS_ERR_MPI_BAD_INPUT_DATA
+Most negative mbedtls_mpi_sint
+most_negative_mpi_sint:
+
MPI Selftest
depends_on:MBEDTLS_SELF_TEST
mpi_selftest:
diff --git a/tests/suites/test_suite_bignum_core.function b/tests/suites/test_suite_bignum_core.function
index 612a7c6..d5bb420 100644
--- a/tests/suites/test_suite_bignum_core.function
+++ b/tests/suites/test_suite_bignum_core.function
@@ -1049,6 +1049,52 @@
/* BEGIN MERGE SLOT 3 */
+/* BEGIN_CASE */
+void mpi_core_sub_int( char * input_A, char * input_B,
+ char * input_X, int borrow )
+{
+ /* We are testing A - b, where A is an MPI and b is a scalar, expecting
+ * result X with borrow borrow. However, for ease of handling we encode b
+ * as a 1-limb MPI (B) in the .data file. */
+
+ mbedtls_mpi_uint *A = NULL;
+ mbedtls_mpi_uint *B = NULL;
+ mbedtls_mpi_uint *X = NULL;
+ mbedtls_mpi_uint *R = NULL;
+ size_t A_limbs, B_limbs, X_limbs;
+
+ TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &A, &A_limbs, input_A ) );
+ TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &B, &B_limbs, input_B ) );
+ TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &X, &X_limbs, input_X ) );
+
+ /* The MPI encoding of scalar b must be only 1 limb */
+ TEST_EQUAL( B_limbs, 1 );
+
+ /* The subtraction is fixed-width, so A and X must have the same number of limbs */
+ TEST_EQUAL( A_limbs, X_limbs );
+ size_t limbs = A_limbs;
+
+ ASSERT_ALLOC( R, limbs );
+
+#define TEST_COMPARE_CORE_MPIS( A, B, limbs ) \
+ ASSERT_COMPARE( A, (limbs) * sizeof(mbedtls_mpi_uint), B, (limbs) * sizeof(mbedtls_mpi_uint) )
+
+ /* 1. R = A - b. Result and borrow should be correct */
+ TEST_EQUAL( mbedtls_mpi_core_sub_int( R, A, B[0], limbs ), borrow );
+ TEST_COMPARE_CORE_MPIS( R, X, limbs );
+
+ /* 2. A = A - b. Result and borrow should be correct */
+ TEST_EQUAL( mbedtls_mpi_core_sub_int( A, A, B[0], limbs ), borrow );
+ TEST_COMPARE_CORE_MPIS( A, X, limbs );
+
+exit:
+ mbedtls_free( A );
+ mbedtls_free( B );
+ mbedtls_free( X );
+ mbedtls_free( R );
+}
+/* END_CASE */
+
/* END MERGE SLOT 3 */
/* BEGIN MERGE SLOT 4 */
diff --git a/tests/suites/test_suite_bignum_mod.data b/tests/suites/test_suite_bignum_mod.data
index 95faa53..2ea4a58 100644
--- a/tests/suites/test_suite_bignum_mod.data
+++ b/tests/suites/test_suite_bignum_mod.data
@@ -1,29 +1,11 @@
-Test mbedtls_mpi_mod_setup #1 (Both representations invalid)
-mpi_mod_setup:MBEDTLS_MPI_MOD_EXT_REP_INVALID:MBEDTLS_MPI_MOD_REP_INVALID:MBEDTLS_ERR_MPI_BAD_INPUT_DATA
+Test mbedtls_mpi_mod_setup #1 (Internal representation invalid)
+mpi_mod_setup:MBEDTLS_MPI_MOD_REP_INVALID:MBEDTLS_ERR_MPI_BAD_INPUT_DATA
-Test mbedtls_mpi_mod_setup #2 (Internal representation invalid)
-mpi_mod_setup:MBEDTLS_MPI_MOD_EXT_REP_LE:MBEDTLS_MPI_MOD_REP_INVALID:MBEDTLS_ERR_MPI_BAD_INPUT_DATA
+Test mbedtls_mpi_mod_setup #6 (Optimised reduction)
+mpi_mod_setup:MBEDTLS_MPI_MOD_REP_OPT_RED:0
-Test mbedtls_mpi_mod_setup #3 (Internal representation invalid)
-mpi_mod_setup:MBEDTLS_MPI_MOD_EXT_REP_BE:MBEDTLS_MPI_MOD_REP_INVALID:MBEDTLS_ERR_MPI_BAD_INPUT_DATA
-
-Test mbedtls_mpi_mod_setup #4 (External representation invalid)
-mpi_mod_setup:MBEDTLS_MPI_MOD_EXT_REP_INVALID:MBEDTLS_MPI_MOD_REP_MONTGOMERY:MBEDTLS_ERR_MPI_BAD_INPUT_DATA
-
-Test mbedtls_mpi_mod_setup #5 (External representation invalid)
-mpi_mod_setup:MBEDTLS_MPI_MOD_EXT_REP_INVALID:MBEDTLS_MPI_MOD_REP_OPT_RED:MBEDTLS_ERR_MPI_BAD_INPUT_DATA
-
-Test mbedtls_mpi_mod_setup #6 (Both representations valid)
-mpi_mod_setup:MBEDTLS_MPI_MOD_EXT_REP_BE:MBEDTLS_MPI_MOD_REP_OPT_RED:0
-
-Test mbedtls_mpi_mod_setup #7 (Both representations valid)
-mpi_mod_setup:MBEDTLS_MPI_MOD_EXT_REP_BE:MBEDTLS_MPI_MOD_REP_MONTGOMERY:0
-
-Test mbedtls_mpi_mod_setup #8 (Both representations valid)
-mpi_mod_setup:MBEDTLS_MPI_MOD_EXT_REP_LE:MBEDTLS_MPI_MOD_REP_OPT_RED:0
-
-Test mbedtls_mpi_mod_setup #9 (Both representations valid)
-mpi_mod_setup:MBEDTLS_MPI_MOD_EXT_REP_LE:MBEDTLS_MPI_MOD_REP_MONTGOMERY:0
+Test mbedtls_mpi_mod_setup #7 (Montgomery representation)
+mpi_mod_setup:MBEDTLS_MPI_MOD_REP_MONTGOMERY:0
# BEGIN MERGE SLOT 1
@@ -50,17 +32,269 @@
# END MERGE SLOT 6
# BEGIN MERGE SLOT 7
+Test mbedtls_mpi_residue_setup #1 m > r
+mpi_residue_setup:"fe":"01":0
-# END MERGE SLOT 7
+Test mbedtls_mpi_residue_setup #2 r == m - 1
+mpi_residue_setup:"ff":"fe":0
-# BEGIN MERGE SLOT 8
+Test mbedtls_mpi_residue_setup #3 m->limbs = r-> limbs && m > r
+mpi_residue_setup:"7dfe5c6":"fe":0
-# END MERGE SLOT 8
+Test mbedtls_mpi_residue_setup #4 m->limbs = r-> limbs && m > r
+mpi_residue_setup:"7ffffffffffffffffffffffffffffffffffffffffffffff1":"0000000000000000000000000000000000000000000000fe":0
-# BEGIN MERGE SLOT 9
+Test mbedtls_mpi_residue_setup #5 m->limbs > r-> limbs && m > r
+mpi_residue_setup:"7ffffffff00000000":"fe":MBEDTLS_ERR_MPI_BAD_INPUT_DATA
-# END MERGE SLOT 9
+Test mbedtls_mpi_residue_setup #6 m->limbs < r-> limbs && m > r
+mpi_residue_setup:"ff":"000000000000000000000000000000000000000000000001":MBEDTLS_ERR_MPI_BAD_INPUT_DATA
-# BEGIN MERGE SLOT 10
+Test mbedtls_mpi_residue_setup #7 r == m
+mpi_residue_setup:"fe":"fe":-4
-# END MERGE SLOT 10
+Test mbedtls_mpi_residue_setup #8 r > m
+mpi_residue_setup:"fe":"ff":-4
+
+Test mbedtls_mpi_mod_io_neg #1 input_r < modulo m
+mpi_mod_io_neg:"fe":"fd":0
+
+Test mbedtls_mpi_mod_io_neg #2 input_r == modulo m
+mpi_mod_io_neg:"fe":"fe":MBEDTLS_ERR_MPI_BAD_INPUT_DATA
+
+Test mbedtls_mpi_mod_io_neg #3 input_r > modulo m
+mpi_mod_io_neg:"fe":"ff":MBEDTLS_ERR_MPI_BAD_INPUT_DATA
+
+Test mbedtls_mpi_mod_io_neg #4 input_r too large to fit
+mpi_mod_io_neg:"fe":"ffffffffffffffffff":MBEDTLS_ERR_MPI_BUFFER_TOO_SMALL
+
+Test mbedtls_mpi_mod_io_neg #5 Sucesfull read / output buffer too small
+mpi_mod_io_neg:"7ffffffffffffffffffffffffffffff1":"ffff":0
+
+Test mbedtls_mpi_mod_io #1 N: "11" A: "119".
+mpi_mod_io:"000000000000000b":"0000000000000000":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #2 N: "11" A: "136".
+mpi_mod_io:"000000000000000b":"0000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #3 N: "11" A: "119".
+mpi_mod_io:"000000000000000b":"0000000000000001":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #4 N: "11" A: "136".
+mpi_mod_io:"000000000000000b":"0100000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #5 N: "140737488355333" A: "119".
+mpi_mod_io:"0000800000000005":"0000000000000000":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #6 N: "140737488355333" A: "136".
+mpi_mod_io:"0000800000000005":"0000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #7 N: "140737488355333" A: "119".
+mpi_mod_io:"0000800000000005":"0000000000000001":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #8 N: "140737488355333" A: "136".
+mpi_mod_io:"0000800000000005":"0100000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #9 N: "140737488355333" A: "119".
+mpi_mod_io:"0000800000000005":"00000000000003ca":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #10 N: "140737488355333" A: "136".
+mpi_mod_io:"0000800000000005":"ca03000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #11 N: "140737488355333" A: "119".
+mpi_mod_io:"0000800000000005":"00000000539ed428":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #12 N: "140737488355333" A: "136".
+mpi_mod_io:"0000800000000005":"28d49e5300000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #13 N: "9223372036854775807" A: "119".
+mpi_mod_io:"7fffffffffffffff":"0000000000000000":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #14 N: "9223372036854775807" A: "136".
+mpi_mod_io:"7fffffffffffffff":"0000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #15 N: "9223372036854775807" A: "119".
+mpi_mod_io:"7fffffffffffffff":"0000000000000001":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #16 N: "9223372036854775807" A: "136".
+mpi_mod_io:"7fffffffffffffff":"0100000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #17 N: "9223372036854775807" A: "119".
+mpi_mod_io:"7fffffffffffffff":"00000000000003ca":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #18 N: "9223372036854775807" A: "136".
+mpi_mod_io:"7fffffffffffffff":"ca03000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #19 N: "9223372036854775807" A: "119".
+mpi_mod_io:"7fffffffffffffff":"00000000539ed428":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #20 N: "9223372036854775807" A: "136".
+mpi_mod_io:"7fffffffffffffff":"28d49e5300000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #21 N: "9223372036854775807" A: "119".
+mpi_mod_io:"7fffffffffffffff":"7dfe5c6beb35a2d6":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #22 N: "9223372036854775807" A: "136".
+mpi_mod_io:"7fffffffffffffff":"d6a235eb6b5cfe7d":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #23 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "119".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #24 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "136".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #25 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "119".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #26 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "136".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"01000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #27 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "119".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000003ca":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #28 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "136".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"ca030000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #29 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "119".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000539ed428":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #30 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "136".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"28d49e53000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #31 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "119".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000007dfe5c6beb35a2d6":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #32 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "136".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"d6a235eb6b5cfe7d0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #33 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "119".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000dca8de1c2adfc6d7aafb9b48e":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #34 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "136".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"8eb4b9af7a6dfcadc2e18dca0d000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #35 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "119".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000a7d17b6c4be72f3d5c16bf9c1af6fc933":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #36 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "136".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"33c96fafc1f96bc1d5f372bec4b6177d0a0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #37 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "119".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002fec97beec546f9553142ed52f147845463f579":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #38 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "136".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"79f563548447f152ed423155f946c5ee7bc9fe020000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #39 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "119".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"00000000000000000000000000000000000000000000000000000000000000000000000000000000378dc83b8bc5a7b62cba495af4919578dce6d4f175cadc4f":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #40 N: "6610145858169835373800827072568987987787972943497619105736762797475099959212160692262984293277166612477845864397201463825139894315919781838969391314120587" A: "136".
+mpi_mod_io:"7e35b84cb19ea5bc57ec37f5e431462fa962d98c1e63738d4657f18ad6532e6adc3eafe67f1e5fa262af94cee8d3e7268593942a2a98df75154f8c914a282f8b":"4fdcca75f1d4e6dc789591f45a49ba2cb6a7c58b3bc88d3700000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #41 N: "201076468338594879614802819276237850336264827391977454179" A: "119".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #42 N: "201076468338594879614802819276237850336264827391977454179" A: "136".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #43 N: "201076468338594879614802819276237850336264827391977454179" A: "119".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"000000000000000000000000000000000000000000000001":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #44 N: "201076468338594879614802819276237850336264827391977454179" A: "136".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"010000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #45 N: "201076468338594879614802819276237850336264827391977454179" A: "119".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"0000000000000000000000000000000000000000000003ca":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #46 N: "201076468338594879614802819276237850336264827391977454179" A: "136".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"ca0300000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #47 N: "201076468338594879614802819276237850336264827391977454179" A: "119".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"0000000000000000000000000000000000000000539ed428":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #48 N: "201076468338594879614802819276237850336264827391977454179" A: "136".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"28d49e530000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #49 N: "201076468338594879614802819276237850336264827391977454179" A: "119".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"000000000000000000000000000000007dfe5c6beb35a2d6":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #50 N: "201076468338594879614802819276237850336264827391977454179" A: "136".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"d6a235eb6b5cfe7d00000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #51 N: "201076468338594879614802819276237850336264827391977454179" A: "119".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"00000000000000000000000dca8de1c2adfc6d7aafb9b48e":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #52 N: "201076468338594879614802819276237850336264827391977454179" A: "136".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"8eb4b9af7a6dfcadc2e18dca0d0000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #53 N: "201076468338594879614802819276237850336264827391977454179" A: "119".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"000000000000000a7d17b6c4be72f3d5c16bf9c1af6fc933":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #54 N: "201076468338594879614802819276237850336264827391977454179" A: "136".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"33c96fafc1f96bc1d5f372bec4b6177d0a00000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #55 N: "201076468338594879614802819276237850336264827391977454179" A: "119".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"0000000002fec97beec546f9553142ed52f147845463f579":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #56 N: "201076468338594879614802819276237850336264827391977454179" A: "136".
+mpi_mod_io:"08335616aed761f1f7f44e6bd49e807b82e3bf2bf11bfa63":"79f563548447f152ed423155f946c5ee7bc9fe0200000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #57 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "119".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #58 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "136".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #59 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "119".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #60 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "136".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"01000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #61 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "119".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000003ca":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #62 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "136".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"ca030000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #63 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "119".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000539ed428":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #64 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "136".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"28d49e53000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #65 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "119".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000007dfe5c6beb35a2d6":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #66 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "136".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"d6a235eb6b5cfe7d0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #67 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "119".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000dca8de1c2adfc6d7aafb9b48e":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #68 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "136".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"8eb4b9af7a6dfcadc2e18dca0d000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #69 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "119".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000a7d17b6c4be72f3d5c16bf9c1af6fc933":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #70 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "136".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"33c96fafc1f96bc1d5f372bec4b6177d0a0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #71 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "119".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002fec97beec546f9553142ed52f147845463f579":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #72 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "136".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"79f563548447f152ed423155f946c5ee7bc9fe020000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #73 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "119".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000378dc83b8bc5a7b62cba495af4919578dce6d4f175cadc4f":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #74 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "136".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"4fdcca75f1d4e6dc789591f45a49ba2cb6a7c58b3bc88d3700000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000":MBEDTLS_MPI_MOD_EXT_REP_LE
+
+Test mbedtls_mpi_mod_io #75 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "119".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"b6415f2a1a8e48a518345db11f56db3829c8f2c6415ab4a395ab3ac2ea4cbef4af86eb18a84eb6ded4c6ecbfc4b59c2879a675487f687adea9d197a84a5242a5cf6125ce19a6ad2e7341f1c57d43ea4f4c852a51cb63dabcd1c9de2b827a3146a3d175b35bea41ae75d2a286a3e9d43623152ac513dcdea1d72a7da846a8ab358d9be4926c79cfb287cf1cf25b689de3b912176be5dcaf4d4c6e7cb839a4a3243a6c47c1e2c99d65c59d6fa3672575c2f1ca8de6a32e854ec9d8ec635c96af7679fce26d7d159e4a9da3bd74e1272c376cd926d74fe3fb164a5935cff3d5cdb92b35fe2cea32138a7e6bfbc319ebd1725dacb9a359cbf693f2ecb785efb9d627":MBEDTLS_MPI_MOD_EXT_REP_BE
+
+Test mbedtls_mpi_mod_io #76 N: "32292747613635961694771916499883650667878589411552643628627186850993060141490368296439843252993342320145797691611646027435006878234727648863911408777308953382400333083852585109256846643097239747078406546553406955958288616728627292699264194880486908744773379992784153004816057528456043920098334713005039494478693892693017304730883448003944721685094014669042959451482141781404822386404101555113742346277194830729517252154824958327000717338180410404929239489607893939166712107274943411892079802406181464789204374234653633818543559183821503846194953493439237710780169796543565449952151334229364816621060143650318299210551" A: "136".
+mpi_mod_io:"ffcece570f2f991013f26dd5b03c4c5b65f97be5905f36cb4664f2c78ff80aa8135a4aaf57ccb8a0aca2f394909a74cef1ef6758a64d11e2c149c393659d124bfc94196f0ce88f7d7d567efa5a649e2deefaa6e10fdc3deac60d606bf63fc540ac95294347031aefd73d6a9ee10188aaeb7a90d920894553cb196881691cadc51808715a07e8b24fcb1a63df047c7cdf084dd177ba368c806f3d51ddb5d3898c863e687ecaf7d649a57a46264a582f94d3c8f2edaf59f77a7f6bdaf83c991e8f06abe220ec8507386fce8c3da84c6c3903ab8f3ad4630a204196a7dbcbd9bcca4e40ec5cc5c09938d49f5e1e6181db8896f33bb12e6ef73f12ec5c5ea7a8a337":"27d6b9ef85b7ecf293f6cb59a3b9ac5d72d1eb19c3fb6b7e8a1332ea2cfe352bb9cdd5f3cf35594a16fbe34fd726d96c372c27e174bda39d4a9e157d6de2fc7976af965c63ecd8c94e852ea3e68dcaf1c2752567a36f9dc5659dc9e2c1476c3a24a3a439b87c6e4c4dafdce56b1712b9e39d685bf21ccf87b2cf796c92e49b8d35aba846a87d2ad7a1dedc13c52a152336d4e9a386a2d275ae41ea5bb375d1a346317a822bdec9d1bcda63cb512a854c4fea437dc5f141732eada619ce2561cfa542524aa897d1a9de7a687f4875a679289cb5c4bfecc6d4deb64ea818eb86aff4be4ceac23aab95a3b45a41c6f2c82938db561fb15d3418a5488e1a2a5f41b6":MBEDTLS_MPI_MOD_EXT_REP_LE
diff --git a/tests/suites/test_suite_bignum_mod.function b/tests/suites/test_suite_bignum_mod.function
index 1a2d0c1..a941cb6 100644
--- a/tests/suites/test_suite_bignum_mod.function
+++ b/tests/suites/test_suite_bignum_mod.function
@@ -12,7 +12,7 @@
*/
/* BEGIN_CASE */
-void mpi_mod_setup( int ext_rep, int int_rep, int iret )
+void mpi_mod_setup( int int_rep, int iret )
{
#define MLIMBS 8
mbedtls_mpi_uint mp[MLIMBS];
@@ -22,7 +22,7 @@
memset( mp, 0xFF, sizeof(mp) );
mbedtls_mpi_mod_modulus_init( &m );
- ret = mbedtls_mpi_mod_modulus_setup( &m, mp, MLIMBS, ext_rep, int_rep );
+ ret = mbedtls_mpi_mod_modulus_setup( &m, mp, MLIMBS, int_rep );
TEST_EQUAL( ret, iret );
/* Only test if the constants have been set-up */
@@ -80,7 +80,214 @@
/* END MERGE SLOT 6 */
/* BEGIN MERGE SLOT 7 */
+/* BEGIN_CASE */
+void mpi_residue_setup( char * input_N, char * input_R, int ret )
+{
+ mbedtls_mpi_uint *N = NULL;
+ mbedtls_mpi_uint *R = NULL;
+ size_t n_limbs, r_limbs;
+ mbedtls_mpi_mod_modulus m;
+ mbedtls_mpi_mod_residue r;
+ mbedtls_mpi_mod_modulus_init( &m );
+
+ /* Allocate the memory for intermediate data structures */
+ TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &N, &n_limbs, input_N ) );
+ TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &R, &r_limbs, input_R ) );
+
+ TEST_EQUAL( 0, mbedtls_mpi_mod_modulus_setup( &m, N, n_limbs,
+ MBEDTLS_MPI_MOD_REP_MONTGOMERY ) );
+
+ TEST_EQUAL( ret, mbedtls_mpi_mod_residue_setup( &r, &m, R , r_limbs ) );
+
+ if ( ret == 0 )
+ {
+ TEST_EQUAL( r.limbs, r_limbs );
+ TEST_ASSERT( r.p == R );
+ }
+
+exit:
+ mbedtls_mpi_mod_modulus_free( &m );
+ mbedtls_free( N );
+ mbedtls_free( R );
+}
+/* END_CASE */
+
+/* BEGIN_CASE */
+void mpi_mod_io_neg( char * input_N, data_t * buf, int ret )
+{
+ mbedtls_mpi_uint *N = NULL;
+ mbedtls_mpi_uint *R = NULL;
+
+ mbedtls_mpi_mod_modulus m;
+ mbedtls_mpi_mod_residue r = { NULL, 0 };
+ mbedtls_mpi_mod_ext_rep endian = MBEDTLS_MPI_MOD_EXT_REP_LE;
+
+ mbedtls_mpi_mod_modulus_init( &m );
+
+ size_t n_limbs;
+ TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &N, &n_limbs, input_N ) );
+ size_t r_limbs = n_limbs;
+ ASSERT_ALLOC( R, r_limbs );
+
+ /* modulus->p == NULL || residue->p == NULL ( m has not been set-up ) */
+ TEST_EQUAL( MBEDTLS_ERR_MPI_BAD_INPUT_DATA,
+ mbedtls_mpi_mod_read( &r, &m, buf->x, buf->len, endian ) );
+
+ TEST_EQUAL( MBEDTLS_ERR_MPI_BAD_INPUT_DATA,
+ mbedtls_mpi_mod_write( &r, &m, buf->x, buf->len, endian ) );
+
+ /* Set up modulus and test with residue->p == NULL */
+ TEST_EQUAL( 0, mbedtls_mpi_mod_modulus_setup( &m, N, n_limbs,
+ MBEDTLS_MPI_MOD_REP_MONTGOMERY ) );
+
+ TEST_EQUAL( MBEDTLS_ERR_MPI_BAD_INPUT_DATA,
+ mbedtls_mpi_mod_read( &r, &m, buf->x, buf->len, endian ) );
+ TEST_EQUAL( MBEDTLS_ERR_MPI_BAD_INPUT_DATA,
+ mbedtls_mpi_mod_write( &r, &m, buf->x, buf->len, endian ) );
+
+ /* Do the rest of the tests with a residue set up with the input data */
+ TEST_EQUAL( 0, mbedtls_mpi_mod_residue_setup( &r, &m, R , r_limbs ) );
+
+ /* Fail for r_limbs < m->limbs */
+ r.limbs--;
+ TEST_ASSERT( r.limbs < m.limbs );
+ TEST_EQUAL( MBEDTLS_ERR_MPI_BAD_INPUT_DATA,
+ mbedtls_mpi_mod_read( &r, &m, buf->x, buf->len, endian ) );
+ TEST_EQUAL( MBEDTLS_ERR_MPI_BAD_INPUT_DATA,
+ mbedtls_mpi_mod_write( &r, &m, buf->x, buf->len, endian ) );
+ r.limbs++;
+
+ /* Fail for r_limbs > m->limbs */
+ m.limbs--;
+ TEST_ASSERT( r.limbs > m.limbs );
+ TEST_EQUAL( MBEDTLS_ERR_MPI_BAD_INPUT_DATA,
+ mbedtls_mpi_mod_read( &r, &m, buf->x, buf->len, endian ) );
+ TEST_EQUAL( MBEDTLS_ERR_MPI_BAD_INPUT_DATA,
+ mbedtls_mpi_mod_write( &r, &m, buf->x, buf->len, endian ) );
+ m.limbs++;
+
+ /* Test the read */
+ TEST_EQUAL( ret, mbedtls_mpi_mod_read( &r, &m, buf->x, buf->len, endian ) );
+
+ /* Test write overflow only when the representation is large and read is successful */
+ if ( r.limbs > 1 && ret == 0 )
+ TEST_EQUAL( MBEDTLS_ERR_MPI_BUFFER_TOO_SMALL,
+ mbedtls_mpi_mod_write( &r, &m, buf->x, 1, endian ) );
+
+exit:
+ mbedtls_mpi_mod_residue_release( &r );
+ mbedtls_mpi_mod_modulus_free( &m );
+ mbedtls_free( N );
+ mbedtls_free( R );
+}
+/* END_CASE */
+
+/* BEGIN_CASE */
+void mpi_mod_io( char * input_N, data_t * input_A, int endian )
+{
+ mbedtls_mpi_uint *N = NULL;
+ mbedtls_mpi_uint *R = NULL;
+ mbedtls_mpi_uint *R_COPY = NULL;
+ unsigned char *obuf = NULL;
+ unsigned char *ref_buf = NULL;
+ mbedtls_mpi_mod_modulus m;
+ mbedtls_mpi_mod_residue r;
+ mbedtls_mpi_mod_residue r_copy;
+ size_t n_limbs, n_bytes, a_bytes;
+
+ mbedtls_mpi_mod_modulus_init( &m );
+
+ /* Read inputs */
+ TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &N, &n_limbs, input_N ) );
+ n_bytes = n_limbs * sizeof( mbedtls_mpi_uint );
+ a_bytes = input_A->len;
+
+ /* Allocate the memory for intermediate data structures */
+ ASSERT_ALLOC( R, n_bytes );
+ ASSERT_ALLOC( R_COPY, n_bytes );
+
+ /* Test that input's size is not greater to modulo's */
+ TEST_LE_U( a_bytes, n_bytes );
+
+ /* Init Structures */
+ TEST_EQUAL( 0, mbedtls_mpi_mod_modulus_setup( &m, N, n_limbs,
+ MBEDTLS_MPI_MOD_REP_MONTGOMERY ) );
+
+ /* Enforcing p_limbs >= m->limbs */
+ TEST_EQUAL( 0, mbedtls_mpi_mod_residue_setup( &r, &m, R, n_limbs ) );
+
+ TEST_EQUAL( 0, mbedtls_mpi_mod_read( &r, &m, input_A->x, input_A->len,
+ endian ) );
+
+ /* Read a copy for checking that writing didn't change the value of r */
+ TEST_EQUAL( 0, mbedtls_mpi_mod_residue_setup( &r_copy, &m,
+ R_COPY, n_limbs ) );
+ TEST_EQUAL( 0, mbedtls_mpi_mod_read( &r_copy, &m, input_A->x, input_A->len,
+ endian ) );
+
+ /* Get number of bytes without leading zeroes */
+ size_t a_bytes_trimmed = a_bytes;
+ while( a_bytes_trimmed > 0 )
+ {
+ unsigned char* r_byte_array = (unsigned char*) r.p;
+ if( r_byte_array[--a_bytes_trimmed] != 0 )
+ break;
+ }
+ a_bytes_trimmed++;
+
+ /* Test write with three output buffer sizes: tight, same as input and
+ * longer than the input */
+ size_t obuf_sizes[3];
+ const size_t obuf_sizes_len = sizeof( obuf_sizes ) / sizeof( obuf_sizes[0] );
+ obuf_sizes[0] = a_bytes_trimmed;
+ obuf_sizes[1] = a_bytes;
+ obuf_sizes[2] = a_bytes + 8;
+
+ for( size_t i = 0; i < obuf_sizes_len; i++ )
+ {
+ ASSERT_ALLOC( obuf, obuf_sizes[i] );
+ TEST_EQUAL( 0, mbedtls_mpi_mod_write( &r, &m, obuf, obuf_sizes[i], endian ) );
+
+ /* Make sure that writing didn't corrupt the value of r */
+ ASSERT_COMPARE( r.p, r.limbs, r_copy.p, r_copy.limbs );
+
+ /* Set up reference output for checking the result */
+ ASSERT_ALLOC( ref_buf, obuf_sizes[i] );
+ switch( endian )
+ {
+ case MBEDTLS_MPI_MOD_EXT_REP_LE:
+ memcpy( ref_buf, input_A->x, a_bytes_trimmed );
+ break;
+ case MBEDTLS_MPI_MOD_EXT_REP_BE:
+ {
+ size_t a_offset = input_A->len - a_bytes_trimmed;
+ size_t ref_offset = obuf_sizes[i] - a_bytes_trimmed;
+ memcpy( ref_buf + ref_offset, input_A->x + a_offset,
+ a_bytes_trimmed );
+ }
+ break;
+ default:
+ TEST_ASSERT( 0 );
+ }
+
+ /* Check the result */
+ ASSERT_COMPARE( obuf, obuf_sizes[i], ref_buf, obuf_sizes[i] );
+
+ mbedtls_free( ref_buf );
+ ref_buf = NULL;
+ mbedtls_free( obuf );
+ obuf = NULL;
+ }
+
+exit:
+ mbedtls_mpi_mod_modulus_free( &m );
+ mbedtls_free( N );
+ mbedtls_free( R );
+ mbedtls_free( R_COPY );
+ mbedtls_free( obuf );
+}
+/* END_CASE */
/* END MERGE SLOT 7 */
/* BEGIN MERGE SLOT 8 */
diff --git a/tests/suites/test_suite_bignum_mod_raw.function b/tests/suites/test_suite_bignum_mod_raw.function
index d0ffd27..c7decf0 100644
--- a/tests/suites/test_suite_bignum_mod_raw.function
+++ b/tests/suites/test_suite_bignum_mod_raw.function
@@ -49,22 +49,22 @@
mbedtls_mpi_uint init[sizeof( X ) / sizeof( X[0] )];
memset( init, 0xFF, sizeof( init ) );
- int ret = mbedtls_mpi_mod_modulus_setup( &m, init, nx, endian,
+ int ret = mbedtls_mpi_mod_modulus_setup( &m, init, nx,
MBEDTLS_MPI_MOD_REP_MONTGOMERY );
TEST_EQUAL( ret, 0 );
if( iendian == MBEDTLS_MPI_MOD_EXT_REP_INVALID && iret != 0 )
- m.ext_rep = MBEDTLS_MPI_MOD_EXT_REP_INVALID;
+ endian = MBEDTLS_MPI_MOD_EXT_REP_INVALID;
- ret = mbedtls_mpi_mod_raw_read( X, &m, input->x, input->len );
+ ret = mbedtls_mpi_mod_raw_read( X, &m, input->x, input->len, endian );
TEST_EQUAL( ret, iret );
if( iret == 0 )
{
if( iendian == MBEDTLS_MPI_MOD_EXT_REP_INVALID && oret != 0 )
- m.ext_rep = MBEDTLS_MPI_MOD_EXT_REP_INVALID;
+ endian = MBEDTLS_MPI_MOD_EXT_REP_INVALID;
- ret = mbedtls_mpi_mod_raw_write( X, &m, buf, nb );
+ ret = mbedtls_mpi_mod_raw_write( X, &m, buf, nb, endian );
TEST_EQUAL( ret, oret );
}
@@ -117,10 +117,12 @@
mbedtls_mpi_uint *X = NULL;
mbedtls_mpi_uint *Y = NULL;
mbedtls_mpi_uint *buff_m = NULL;
- mbedtls_mpi_mod_modulus m;
size_t limbs_X;
size_t limbs_Y;
+ mbedtls_mpi_mod_modulus m;
+ mbedtls_mpi_mod_modulus_init( &m );
+
TEST_EQUAL( mbedtls_test_read_mpi_core( &X, &limbs_X, input_X ), 0 );
TEST_EQUAL( mbedtls_test_read_mpi_core( &Y, &limbs_Y, input_Y ), 0 );
@@ -129,8 +131,6 @@
size_t bytes = limbs * sizeof( mbedtls_mpi_uint );
size_t copy_bytes = copy_limbs * sizeof( mbedtls_mpi_uint );
- mbedtls_mpi_mod_modulus_init( &m );
-
TEST_EQUAL( limbs_X, limbs_Y );
TEST_ASSERT( copy_limbs <= limbs );
@@ -138,7 +138,6 @@
memset( buff_m, 0xFF, copy_limbs );
TEST_EQUAL( mbedtls_mpi_mod_modulus_setup(
&m, buff_m, copy_limbs,
- MBEDTLS_MPI_MOD_EXT_REP_BE,
MBEDTLS_MPI_MOD_REP_MONTGOMERY ), 0 );
/* condition is false */
@@ -190,10 +189,12 @@
mbedtls_mpi_uint *X = NULL;
mbedtls_mpi_uint *Y = NULL;
mbedtls_mpi_uint *buff_m = NULL;
- mbedtls_mpi_mod_modulus m;
size_t limbs_X;
size_t limbs_Y;
+ mbedtls_mpi_mod_modulus m;
+ mbedtls_mpi_mod_modulus_init( &m );
+
TEST_EQUAL( mbedtls_test_read_mpi_core( &tmp_X, &limbs_X, input_X ), 0 );
TEST_EQUAL( mbedtls_test_read_mpi_core( &tmp_Y, &limbs_Y, input_Y ), 0 );
@@ -202,8 +203,6 @@
size_t bytes = limbs * sizeof( mbedtls_mpi_uint );
size_t copy_bytes = copy_limbs * sizeof( mbedtls_mpi_uint );
- mbedtls_mpi_mod_modulus_init( &m );
-
TEST_EQUAL( limbs_X, limbs_Y );
TEST_ASSERT( copy_limbs <= limbs );
@@ -211,7 +210,6 @@
memset( buff_m, 0xFF, copy_limbs );
TEST_EQUAL( mbedtls_mpi_mod_modulus_setup(
&m, buff_m, copy_limbs,
- MBEDTLS_MPI_MOD_EXT_REP_BE,
MBEDTLS_MPI_MOD_REP_MONTGOMERY ), 0 );
ASSERT_ALLOC( X, limbs );
@@ -275,6 +273,78 @@
/* BEGIN MERGE SLOT 2 */
+/* BEGIN_CASE */
+void mpi_mod_raw_sub( char * input_A,
+ char * input_B,
+ char * input_N,
+ char * result )
+{
+ mbedtls_mpi_uint *A = NULL;
+ mbedtls_mpi_uint *B = NULL;
+ mbedtls_mpi_uint *N = NULL;
+ mbedtls_mpi_uint *X = NULL;
+ mbedtls_mpi_uint *res = NULL;
+ size_t limbs_A;
+ size_t limbs_B;
+ size_t limbs_N;
+ size_t limbs_res;
+
+ mbedtls_mpi_mod_modulus m;
+ mbedtls_mpi_mod_modulus_init( &m );
+
+ TEST_EQUAL( mbedtls_test_read_mpi_core( &A, &limbs_A, input_A ), 0 );
+ TEST_EQUAL( mbedtls_test_read_mpi_core( &B, &limbs_B, input_B ), 0 );
+ TEST_EQUAL( mbedtls_test_read_mpi_core( &N, &limbs_N, input_N ), 0 );
+ TEST_EQUAL( mbedtls_test_read_mpi_core( &res, &limbs_res, result ), 0 );
+
+ size_t limbs = limbs_N;
+ size_t bytes = limbs * sizeof( mbedtls_mpi_uint );
+
+ TEST_EQUAL( limbs_A, limbs );
+ TEST_EQUAL( limbs_B, limbs );
+ TEST_EQUAL( limbs_res, limbs );
+
+ ASSERT_ALLOC( X, limbs );
+
+ TEST_EQUAL( mbedtls_mpi_mod_modulus_setup(
+ &m, N, limbs,
+ MBEDTLS_MPI_MOD_REP_MONTGOMERY ), 0 );
+
+ mbedtls_mpi_mod_raw_sub( X, A, B, &m );
+ ASSERT_COMPARE( X, bytes, res, bytes );
+
+ /* alias X to A */
+ memcpy( X, A, bytes );
+ mbedtls_mpi_mod_raw_sub( X, X, B, &m );
+ ASSERT_COMPARE( X, bytes, res, bytes );
+
+ /* alias X to B */
+ memcpy( X, B, bytes );
+ mbedtls_mpi_mod_raw_sub( X, A, X, &m );
+ ASSERT_COMPARE( X, bytes, res, bytes );
+
+ /* A == B: alias A and B */
+ if( memcmp( A, B, bytes ) == 0 )
+ {
+ mbedtls_mpi_mod_raw_sub( X, A, A, &m );
+ ASSERT_COMPARE( X, bytes, res, bytes );
+
+ /* X, A, B all aliased together */
+ memcpy( X, A, bytes );
+ mbedtls_mpi_mod_raw_sub( X, X, X, &m );
+ ASSERT_COMPARE( X, bytes, res, bytes );
+ }
+exit:
+ mbedtls_free( A );
+ mbedtls_free( B );
+ mbedtls_free( X );
+ mbedtls_free( res );
+
+ mbedtls_mpi_mod_modulus_free( &m );
+ mbedtls_free( N );
+}
+/* END_CASE */
+
/* END MERGE SLOT 2 */
/* BEGIN MERGE SLOT 3 */
@@ -287,6 +357,97 @@
/* BEGIN MERGE SLOT 5 */
+/* BEGIN_CASE */
+void mpi_mod_raw_add( char * input_N,
+ char * input_A, char * input_B,
+ char * input_S )
+{
+ mbedtls_mpi_uint *A = NULL;
+ mbedtls_mpi_uint *B = NULL;
+ mbedtls_mpi_uint *S = NULL;
+ mbedtls_mpi_uint *N = NULL;
+ mbedtls_mpi_uint *X = NULL;
+ size_t A_limbs, B_limbs, N_limbs, S_limbs;
+
+ mbedtls_mpi_mod_modulus m;
+ mbedtls_mpi_mod_modulus_init( &m );
+
+ TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &A, &A_limbs, input_A ) );
+ TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &B, &B_limbs, input_B ) );
+ TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &N, &N_limbs, input_N ) );
+ TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &S, &S_limbs, input_S ) );
+
+ /* Modulus gives the number of limbs; all inputs must have the same. */
+ size_t limbs = N_limbs;
+ size_t bytes = limbs * sizeof( *A );
+
+ TEST_EQUAL( A_limbs, limbs );
+ TEST_EQUAL( B_limbs, limbs );
+ TEST_EQUAL( S_limbs, limbs );
+
+ ASSERT_ALLOC( X, limbs );
+
+ TEST_EQUAL( mbedtls_mpi_mod_modulus_setup(
+ &m, N, limbs,
+ MBEDTLS_MPI_MOD_REP_MONTGOMERY
+ ), 0 );
+
+ /* A + B => Correct result */
+ mbedtls_mpi_mod_raw_add( X, A, B, &m );
+ ASSERT_COMPARE( X, bytes, S, bytes );
+
+ /* A + B: alias X to A => Correct result */
+ memcpy( X, A, bytes );
+ mbedtls_mpi_mod_raw_add( X, X, B, &m );
+ ASSERT_COMPARE( X, bytes, S, bytes );
+
+ /* A + B: alias X to B => Correct result */
+ memcpy( X, B, bytes );
+ mbedtls_mpi_mod_raw_add( X, A, X, &m );
+ ASSERT_COMPARE( X, bytes, S, bytes );
+
+ if ( memcmp(A, B, bytes ) == 0 )
+ {
+ /* A == B: alias A and B */
+
+ /* A + A => Correct result */
+ mbedtls_mpi_mod_raw_add( X, A, A, &m );
+ ASSERT_COMPARE( X, bytes, S, bytes );
+
+ /* A + A: X, A, B all aliased together => Correct result */
+ memcpy( X, A, bytes );
+ mbedtls_mpi_mod_raw_add( X, X, X, &m );
+ ASSERT_COMPARE( X, bytes, S, bytes );
+ }
+ else
+ {
+ /* A != B: test B + A */
+
+ /* B + A => Correct result */
+ mbedtls_mpi_mod_raw_add( X, B, A, &m );
+ ASSERT_COMPARE( X, bytes, S, bytes );
+
+ /* B + A: alias X to A => Correct result */
+ memcpy( X, A, bytes );
+ mbedtls_mpi_mod_raw_add( X, B, X, &m );
+ ASSERT_COMPARE( X, bytes, S, bytes );
+
+ /* B + A: alias X to B => Correct result */
+ memcpy( X, B, bytes );
+ mbedtls_mpi_mod_raw_add( X, X, A, &m );
+ ASSERT_COMPARE( X, bytes, S, bytes );
+ }
+
+exit:
+ mbedtls_mpi_mod_modulus_free( &m );
+
+ mbedtls_free( A );
+ mbedtls_free( B );
+ mbedtls_free( S );
+ mbedtls_free( N );
+ mbedtls_free( X );
+}
+/* END_CASE */
/* END MERGE SLOT 5 */
/* BEGIN MERGE SLOT 6 */
@@ -300,9 +461,11 @@
mbedtls_mpi_uint *N = NULL;
mbedtls_mpi_uint *A = NULL;
mbedtls_mpi_uint *X = NULL;
- mbedtls_mpi_mod_modulus m;
size_t n_limbs, a_limbs, x_limbs, x_bytes;
+ mbedtls_mpi_mod_modulus m;
+ mbedtls_mpi_mod_modulus_init( &m );
+
/* Read inputs */
TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &N, &n_limbs, input_N ) );
TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &A, &a_limbs, input_A ) );
@@ -312,9 +475,8 @@
/* Test that input does not require more limbs than modulo */
TEST_LE_U(a_limbs, n_limbs);
- mbedtls_mpi_mod_modulus_init( &m );
TEST_EQUAL( 0, mbedtls_mpi_mod_modulus_setup( &m, N, n_limbs,
- MBEDTLS_MPI_MOD_EXT_REP_BE, MBEDTLS_MPI_MOD_REP_MONTGOMERY ) );
+ MBEDTLS_MPI_MOD_REP_MONTGOMERY ) );
/* Convert from cannonical into Montgomery representation */
TEST_EQUAL(0, mbedtls_mpi_mod_raw_to_mont_rep( A, &m ) );
@@ -335,9 +497,11 @@
mbedtls_mpi_uint *N = NULL;
mbedtls_mpi_uint *A = NULL;
mbedtls_mpi_uint *X = NULL;
- mbedtls_mpi_mod_modulus m;
size_t n_limbs, a_limbs, x_limbs, x_bytes;
+ mbedtls_mpi_mod_modulus m;
+ mbedtls_mpi_mod_modulus_init( &m );
+
/* Read inputs */
TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &N, &n_limbs, input_N ) );
TEST_EQUAL( 0, mbedtls_test_read_mpi_core( &A, &a_limbs, input_A ) );
@@ -347,9 +511,8 @@
/* Test that input does not require more limbs than modulo */
TEST_LE_U(a_limbs, n_limbs);
- mbedtls_mpi_mod_modulus_init( &m );
TEST_EQUAL( 0, mbedtls_mpi_mod_modulus_setup( &m, N, n_limbs,
- MBEDTLS_MPI_MOD_EXT_REP_BE, MBEDTLS_MPI_MOD_REP_MONTGOMERY ) );
+ MBEDTLS_MPI_MOD_REP_MONTGOMERY ) );
/* Convert from Montgomery into cannonical representation */
TEST_EQUAL(0, mbedtls_mpi_mod_raw_from_mont_rep( A, &m ) );
diff --git a/tests/suites/test_suite_cipher.function b/tests/suites/test_suite_cipher.function
index b7c3b51..ff936df 100644
--- a/tests/suites/test_suite_cipher.function
+++ b/tests/suites/test_suite_cipher.function
@@ -450,8 +450,12 @@
TEST_ASSERT( 0 == mbedtls_cipher_reset( &ctx_enc ) );
#if defined(MBEDTLS_GCM_C) || defined(MBEDTLS_CHACHAPOLY_C)
- TEST_ASSERT( 0 == mbedtls_cipher_update_ad( &ctx_dec, ad, sizeof( ad ) - i ) );
- TEST_ASSERT( 0 == mbedtls_cipher_update_ad( &ctx_enc, ad, sizeof( ad ) - i ) );
+ int expected = ( cipher_info->mode == MBEDTLS_MODE_GCM ||
+ cipher_info->type == MBEDTLS_CIPHER_CHACHA20_POLY1305 ) ?
+ 0 : MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE;
+
+ TEST_EQUAL( expected, mbedtls_cipher_update_ad( &ctx_dec, ad, sizeof(ad) - i ) );
+ TEST_EQUAL( expected, mbedtls_cipher_update_ad( &ctx_enc, ad, sizeof(ad) - i ) );
#endif
block_size = mbedtls_cipher_get_block_size( &ctx_enc );
@@ -470,7 +474,7 @@
total_len += outlen;
#if defined(MBEDTLS_GCM_C) || defined(MBEDTLS_CHACHAPOLY_C)
- TEST_ASSERT( 0 == mbedtls_cipher_write_tag( &ctx_enc, tag, sizeof( tag ) ) );
+ TEST_EQUAL( expected, mbedtls_cipher_write_tag( &ctx_enc, tag, sizeof(tag) ) );
#endif
TEST_ASSERT( total_len == length ||
@@ -491,7 +495,7 @@
total_len += outlen;
#if defined(MBEDTLS_GCM_C) || defined(MBEDTLS_CHACHAPOLY_C)
- TEST_ASSERT( 0 == mbedtls_cipher_check_tag( &ctx_dec, tag, sizeof( tag ) ) );
+ TEST_EQUAL( expected, mbedtls_cipher_check_tag( &ctx_dec, tag, sizeof(tag) ) );
#endif
/* check result */
@@ -547,7 +551,11 @@
TEST_ASSERT( 0 == mbedtls_cipher_set_iv( &ctx, iv, 16 ) );
TEST_ASSERT( 0 == mbedtls_cipher_reset( &ctx ) );
#if defined(MBEDTLS_GCM_C) || defined(MBEDTLS_CHACHAPOLY_C)
- TEST_ASSERT( 0 == mbedtls_cipher_update_ad( &ctx, NULL, 0 ) );
+ int expected = ( cipher_info->mode == MBEDTLS_MODE_GCM ||
+ cipher_info->type == MBEDTLS_CIPHER_CHACHA20_POLY1305 ) ?
+ 0 : MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE;
+
+ TEST_EQUAL( expected, mbedtls_cipher_update_ad( &ctx, NULL, 0 ) );
#endif
/* encode length number of bytes from inbuf */
@@ -609,7 +617,11 @@
TEST_ASSERT( 0 == mbedtls_cipher_reset( &ctx_dec ) );
#if defined(MBEDTLS_GCM_C) || defined(MBEDTLS_CHACHAPOLY_C)
- TEST_ASSERT( 0 == mbedtls_cipher_update_ad( &ctx_dec, NULL, 0 ) );
+ int expected = ( cipher_info->mode == MBEDTLS_MODE_GCM ||
+ cipher_info->type == MBEDTLS_CIPHER_CHACHA20_POLY1305 ) ?
+ 0 : MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE;
+
+ TEST_EQUAL( expected, mbedtls_cipher_update_ad( &ctx_dec, NULL, 0 ) );
#endif
/* decode 0-byte string */
@@ -710,8 +722,12 @@
TEST_ASSERT( 0 == mbedtls_cipher_reset( &ctx_enc ) );
#if defined(MBEDTLS_GCM_C) || defined(MBEDTLS_CHACHAPOLY_C)
- TEST_ASSERT( 0 == mbedtls_cipher_update_ad( &ctx_dec, NULL, 0 ) );
- TEST_ASSERT( 0 == mbedtls_cipher_update_ad( &ctx_enc, NULL, 0 ) );
+ int expected = ( cipher_info->mode == MBEDTLS_MODE_GCM ||
+ cipher_info->type == MBEDTLS_CIPHER_CHACHA20_POLY1305 ) ?
+ 0 : MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE;
+
+ TEST_EQUAL( expected, mbedtls_cipher_update_ad( &ctx_dec, NULL, 0 ) );
+ TEST_EQUAL( expected, mbedtls_cipher_update_ad( &ctx_enc, NULL, 0 ) );
#endif
block_size = mbedtls_cipher_get_block_size( &ctx_enc );
@@ -795,7 +811,11 @@
TEST_ASSERT( 0 == mbedtls_cipher_set_iv( &ctx, iv->x, iv->len ) );
TEST_ASSERT( 0 == mbedtls_cipher_reset( &ctx ) );
#if defined(MBEDTLS_GCM_C) || defined(MBEDTLS_CHACHAPOLY_C)
- TEST_ASSERT( 0 == mbedtls_cipher_update_ad( &ctx, ad->x, ad->len ) );
+ int expected = ( ctx.cipher_info->mode == MBEDTLS_MODE_GCM ||
+ ctx.cipher_info->type == MBEDTLS_CIPHER_CHACHA20_POLY1305 ) ?
+ 0 : MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE;
+
+ TEST_EQUAL( expected, mbedtls_cipher_update_ad( &ctx, ad->x, ad->len ) );
#endif
/* decode buffer and check tag->x */
@@ -806,7 +826,11 @@
&outlen ) );
total_len += outlen;
#if defined(MBEDTLS_GCM_C) || defined(MBEDTLS_CHACHAPOLY_C)
- TEST_ASSERT( tag_result == mbedtls_cipher_check_tag( &ctx, tag->x, tag->len ) );
+ int tag_expected = ( ctx.cipher_info->mode == MBEDTLS_MODE_GCM ||
+ ctx.cipher_info->type == MBEDTLS_CIPHER_CHACHA20_POLY1305 ) ?
+ tag_result : MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE;
+
+ TEST_EQUAL( tag_expected, mbedtls_cipher_check_tag( &ctx, tag->x, tag->len ) );
#endif
/* check plaintext only if everything went fine */
diff --git a/tests/suites/test_suite_pkcs7.data b/tests/suites/test_suite_pkcs7.data
new file mode 100644
index 0000000..4f81b6f
--- /dev/null
+++ b/tests/suites/test_suite_pkcs7.data
@@ -0,0 +1,75 @@
+PKCS7 Signed Data Parse Pass SHA256 #1
+depends_on:MBEDTLS_SHA256_C:MBEDTLS_RSA_C
+pkcs7_parse:"data_files/pkcs7_data_cert_signed_sha256.der":MBEDTLS_PKCS7_SIGNED_DATA
+
+PKCS7 Signed Data Parse Pass SHA1 #2
+depends_on:MBEDTLS_SHA1_C:MBEDTLS_SHA256_C:MBEDTLS_RSA_C
+pkcs7_parse:"data_files/pkcs7_data_cert_signed_sha1.der":MBEDTLS_PKCS7_SIGNED_DATA
+
+PKCS7 Signed Data Parse Pass Without CERT #3
+depends_on:MBEDTLS_SHA256_C
+pkcs7_parse:"data_files/pkcs7_data_without_cert_signed.der":MBEDTLS_PKCS7_SIGNED_DATA
+
+PKCS7 Signed Data Parse Fail with multiple certs #4
+depends_on:MBEDTLS_SHA256_C:MBEDTLS_RSA_C
+pkcs7_parse:"data_files/pkcs7_data_multiple_certs_signed.der":MBEDTLS_ERR_PKCS7_FEATURE_UNAVAILABLE
+
+PKCS7 Signed Data Parse Fail with corrupted cert #5
+depends_on:MBEDTLS_SHA256_C:MBEDTLS_RSA_C
+pkcs7_parse:"data_files/pkcs7_data_signed_badcert.der":MBEDTLS_ERR_PKCS7_INVALID_CERT
+
+PKCS7 Signed Data Parse Fail with corrupted signer info #6
+depends_on:MBEDTLS_SHA256_C:MBEDTLS_RSA_C
+pkcs7_parse:"data_files/pkcs7_data_signed_badsigner.der":MBEDTLS_ERROR_ADD(MBEDTLS_ERR_PKCS7_INVALID_SIGNER_INFO,MBEDTLS_ERR_ASN1_UNEXPECTED_TAG)
+
+PKCS7 Signed Data Parse Fail Version other than 1 #7
+depends_on:MBEDTLS_SHA256_C
+pkcs7_parse:"data_files/pkcs7_data_cert_signed_v2.der":MBEDTLS_ERR_PKCS7_INVALID_VERSION
+
+PKCS7 Signed Data Parse Fail Encrypted Content #8
+depends_on:MBEDTLS_SHA256_C
+pkcs7_parse:"data_files/pkcs7_data_cert_encrypted.der":MBEDTLS_ERR_PKCS7_FEATURE_UNAVAILABLE
+
+PKCS7 Signed Data Verification Pass SHA256 #9
+depends_on:MBEDTLS_SHA256_C
+pkcs7_verify:"data_files/pkcs7_data_cert_signed_sha256.der":"data_files/pkcs7-rsa-sha256-1.der":"data_files/pkcs7_data.bin":0:0
+
+PKCS7 Signed Data Verification Pass SHA256 #9.1
+depends_on:MBEDTLS_SHA256_C
+pkcs7_verify:"data_files/pkcs7_data_cert_signed_sha256.der":"data_files/pkcs7-rsa-sha256-1.der":"data_files/pkcs7_data.bin":MBEDTLS_MD_SHA256:0
+
+PKCS7 Signed Data Verification Pass SHA1 #10
+depends_on:MBEDTLS_SHA1_C:MBEDTLS_SHA256_C
+pkcs7_verify:"data_files/pkcs7_data_cert_signed_sha1.der":"data_files/pkcs7-rsa-sha256-1.der":"data_files/pkcs7_data.bin":0:0
+
+PKCS7 Signed Data Verification Pass SHA512 #11
+depends_on:MBEDTLS_SHA512_C:MBEDTLS_SHA256_C
+pkcs7_verify:"data_files/pkcs7_data_cert_signed_sha512.der":"data_files/pkcs7-rsa-sha256-1.der":"data_files/pkcs7_data.bin":0:0
+
+PKCS7 Signed Data Verification Fail because of different certificate #12
+depends_on:MBEDTLS_SHA256_C
+pkcs7_verify:"data_files/pkcs7_data_cert_signed_sha256.der":"data_files/pkcs7-rsa-sha256-2.der":"data_files/pkcs7_data.bin":0:MBEDTLS_ERR_RSA_VERIFY_FAILED
+
+PKCS7 Signed Data Verification Fail because of different data hash #13
+depends_on:MBEDTLS_SHA256_C
+pkcs7_verify:"data_files/pkcs7_data_cert_signed_sha256.der":"data_files/pkcs7-rsa-sha256-1.der":"data_files/pkcs7_data_1.bin":0:MBEDTLS_ERR_RSA_VERIFY_FAILED
+
+PKCS7 Signed Data Parse Failure Corrupt signerInfo.issuer #15.1
+depends_on:MBEDTLS_SHA256_C
+pkcs7_parse:"data_files/pkcs7_signerInfo_issuer_invalid_size.der":MBEDTLS_ERR_PKCS7_INVALID_SIGNER_INFO
+
+PKCS7 Signed Data Parse Failure Corrupt signerInfo.serial #15.2
+depends_on:MBEDTLS_SHA256_C
+pkcs7_parse:"data_files/pkcs7_signerInfo_serial_invalid_size.der":MBEDTLS_ERR_PKCS7_INVALID_SIGNER_INFO
+
+PKCS7 Only Signed Data Parse Pass #15
+depends_on:MBEDTLS_SHA256_C:MBEDTLS_RSA_C
+pkcs7_parse:"data_files/pkcs7_data_cert_signeddata_sha256.der":MBEDTLS_PKCS7_SIGNED_DATA
+
+PKCS7 Signed Data Verify with multiple signers #16
+depends_on:MBEDTLS_SHA256_C
+pkcs7_verify_multiple_signers:"data_files/pkcs7_data_multiple_signed.der":"data_files/pkcs7-rsa-sha256-1.crt":"data_files/pkcs7-rsa-sha256-2.crt":"data_files/pkcs7_data.bin":0:0
+
+PKCS7 Signed Data Hash Verify with multiple signers #17
+depends_on:MBEDTLS_SHA256_C
+pkcs7_verify_multiple_signers:"data_files/pkcs7_data_multiple_signed.der":"data_files/pkcs7-rsa-sha256-1.crt":"data_files/pkcs7-rsa-sha256-2.crt":"data_files/pkcs7_data.bin":MBEDTLS_MD_SHA256:0
diff --git a/tests/suites/test_suite_pkcs7.function b/tests/suites/test_suite_pkcs7.function
new file mode 100644
index 0000000..e396140
--- /dev/null
+++ b/tests/suites/test_suite_pkcs7.function
@@ -0,0 +1,194 @@
+/* BEGIN_HEADER */
+#include "mbedtls/bignum.h"
+#include "mbedtls/pkcs7.h"
+#include "mbedtls/x509.h"
+#include "mbedtls/x509_crt.h"
+#include "mbedtls/x509_crl.h"
+#include "mbedtls/oid.h"
+#include "sys/types.h"
+#include "sys/stat.h"
+/* END_HEADER */
+
+/* BEGIN_DEPENDENCIES
+ * depends_on:MBEDTLS_PKCS7_C:MBEDTLS_RSA_C
+ * END_DEPENDENCIES
+ */
+
+/* BEGIN_CASE depends_on:MBEDTLS_FS_IO */
+void pkcs7_parse( char *pkcs7_file, int res_expect )
+{
+ unsigned char *pkcs7_buf = NULL;
+ size_t buflen;
+ int res;
+
+ mbedtls_pkcs7 pkcs7;
+
+ mbedtls_pkcs7_init( &pkcs7 );
+
+ res = mbedtls_pk_load_file( pkcs7_file, &pkcs7_buf, &buflen );
+ TEST_ASSERT( res == 0 );
+
+ res = mbedtls_pkcs7_parse_der( &pkcs7, pkcs7_buf, buflen );
+ TEST_ASSERT( res == res_expect );
+
+exit:
+ mbedtls_free( pkcs7_buf );
+ mbedtls_pkcs7_free( &pkcs7 );
+}
+/* END_CASE */
+
+/* BEGIN_CASE depends_on:MBEDTLS_FS_IO:MBEDTLS_X509_CRT_PARSE_C:MBEDTLS_PKCS1_V15:MBEDTLS_RSA_C */
+void pkcs7_verify( char *pkcs7_file, char *crt, char *filetobesigned, int do_hash_alg, int res_expect )
+{
+ unsigned char *pkcs7_buf = NULL;
+ size_t buflen;
+ unsigned char *data = NULL;
+ unsigned char hash[32];
+ struct stat st;
+ size_t datalen;
+ int res;
+ FILE *file;
+ const mbedtls_md_info_t *md_info;
+ mbedtls_md_type_t md_alg;
+
+ mbedtls_pkcs7 pkcs7;
+ mbedtls_x509_crt x509;
+
+ USE_PSA_INIT();
+
+ mbedtls_pkcs7_init( &pkcs7 );
+ mbedtls_x509_crt_init( &x509 );
+
+ res = mbedtls_x509_crt_parse_file( &x509, crt );
+ TEST_ASSERT( res == 0 );
+
+ res = mbedtls_pk_load_file( pkcs7_file, &pkcs7_buf, &buflen );
+ TEST_ASSERT( res == 0 );
+
+ res = mbedtls_pkcs7_parse_der( &pkcs7, pkcs7_buf, buflen );
+ TEST_ASSERT( res == MBEDTLS_PKCS7_SIGNED_DATA );
+
+ res = stat( filetobesigned, &st );
+ TEST_ASSERT( res == 0 );
+
+ file = fopen( filetobesigned, "rb" );
+ TEST_ASSERT( file != NULL );
+
+ datalen = st.st_size;
+ ASSERT_ALLOC( data, datalen );
+ TEST_ASSERT( data != NULL );
+
+ buflen = fread( (void *)data , sizeof( unsigned char ), datalen, file );
+ TEST_ASSERT( buflen == datalen );
+ fclose( file );
+
+ if( do_hash_alg )
+ {
+ res = mbedtls_oid_get_md_alg( &pkcs7.signed_data.digest_alg_identifiers, &md_alg );
+ TEST_ASSERT( res == 0 );
+ TEST_ASSERT( md_alg == (mbedtls_md_type_t) do_hash_alg );
+ md_info = mbedtls_md_info_from_type( md_alg );
+
+ res = mbedtls_md( md_info, data, datalen, hash );
+ TEST_ASSERT( res == 0 );
+
+ res = mbedtls_pkcs7_signed_hash_verify( &pkcs7, &x509, hash, sizeof(hash) );
+ }
+ else
+ {
+ res = mbedtls_pkcs7_signed_data_verify( &pkcs7, &x509, data, datalen );
+ }
+ TEST_ASSERT( res == res_expect );
+
+exit:
+ mbedtls_x509_crt_free( &x509 );
+ mbedtls_free( data );
+ mbedtls_pkcs7_free( &pkcs7 );
+ mbedtls_free( pkcs7_buf );
+ USE_PSA_DONE();
+}
+/* END_CASE */
+
+/* BEGIN_CASE depends_on:MBEDTLS_FS_IO:MBEDTLS_X509_CRT_PARSE_C:MBEDTLS_PKCS1_V15:MBEDTLS_RSA_C */
+void pkcs7_verify_multiple_signers( char *pkcs7_file, char *crt1, char *crt2, char *filetobesigned, int do_hash_alg, int res_expect )
+{
+ unsigned char *pkcs7_buf = NULL;
+ size_t buflen;
+ unsigned char *data = NULL;
+ unsigned char hash[32];
+ struct stat st;
+ size_t datalen;
+ int res;
+ FILE *file;
+ const mbedtls_md_info_t *md_info;
+ mbedtls_md_type_t md_alg;
+
+ mbedtls_pkcs7 pkcs7;
+ mbedtls_x509_crt x509_1;
+ mbedtls_x509_crt x509_2;
+
+ USE_PSA_INIT();
+
+ mbedtls_pkcs7_init( &pkcs7 );
+ mbedtls_x509_crt_init( &x509_1 );
+ mbedtls_x509_crt_init( &x509_2 );
+
+ res = mbedtls_pk_load_file( pkcs7_file, &pkcs7_buf, &buflen );
+ TEST_ASSERT( res == 0 );
+
+ res = mbedtls_pkcs7_parse_der( &pkcs7, pkcs7_buf, buflen );
+ TEST_ASSERT( res == MBEDTLS_PKCS7_SIGNED_DATA );
+
+ TEST_ASSERT( pkcs7.signed_data.no_of_signers == 2 );
+
+ res = mbedtls_x509_crt_parse_file( &x509_1, crt1 );
+ TEST_ASSERT( res == 0 );
+
+ res = mbedtls_x509_crt_parse_file( &x509_2, crt2 );
+ TEST_ASSERT( res == 0 );
+
+ res = stat( filetobesigned, &st );
+ TEST_ASSERT( res == 0 );
+
+ file = fopen( filetobesigned, "rb" );
+ TEST_ASSERT( file != NULL );
+
+ datalen = st.st_size;
+ ASSERT_ALLOC( data, datalen );
+ buflen = fread( ( void * )data , sizeof( unsigned char ), datalen, file );
+ TEST_ASSERT( buflen == datalen );
+
+ fclose( file );
+
+ if( do_hash_alg )
+ {
+ res = mbedtls_oid_get_md_alg( &pkcs7.signed_data.digest_alg_identifiers, &md_alg );
+ TEST_ASSERT( res == 0 );
+ TEST_ASSERT( md_alg == MBEDTLS_MD_SHA256 );
+
+ md_info = mbedtls_md_info_from_type( md_alg );
+
+ res = mbedtls_md( md_info, data, datalen, hash );
+ TEST_ASSERT( res == 0 );
+
+ res = mbedtls_pkcs7_signed_hash_verify( &pkcs7, &x509_1, hash, sizeof(hash) );
+ TEST_ASSERT( res == res_expect );
+ }
+ else
+ {
+ res = mbedtls_pkcs7_signed_data_verify( &pkcs7, &x509_1, data, datalen );
+ TEST_ASSERT( res == res_expect );
+ }
+
+ res = mbedtls_pkcs7_signed_data_verify( &pkcs7, &x509_2, data, datalen );
+ TEST_ASSERT( res == res_expect );
+
+exit:
+ mbedtls_x509_crt_free( &x509_1 );
+ mbedtls_x509_crt_free( &x509_2 );
+ mbedtls_pkcs7_free( &pkcs7 );
+ mbedtls_free( data );
+ mbedtls_free( pkcs7_buf );
+ USE_PSA_DONE();
+}
+/* END_CASE */
diff --git a/tests/suites/test_suite_psa_crypto.data b/tests/suites/test_suite_psa_crypto.data
index cce3fd0..659205d 100644
--- a/tests/suites/test_suite_psa_crypto.data
+++ b/tests/suites/test_suite_psa_crypto.data
@@ -6549,11 +6549,16 @@
PSA PAKE: ecjpake rounds
depends_on:PSA_WANT_KEY_TYPE_ECC_KEY_PAIR:PSA_WANT_ECC_SECP_R1_256:PSA_WANT_ALG_SHA_256:PSA_WANT_ALG_TLS12_PSK_TO_MS
-ecjpake_rounds:PSA_ALG_JPAKE:PSA_PAKE_PRIMITIVE(PSA_PAKE_PRIMITIVE_TYPE_ECC, PSA_ECC_FAMILY_SECP_R1, 256):PSA_ALG_SHA_256:PSA_ALG_TLS12_PSK_TO_MS(PSA_ALG_SHA_256):"abcdef":0
+ecjpake_rounds:PSA_ALG_JPAKE:PSA_PAKE_PRIMITIVE(PSA_PAKE_PRIMITIVE_TYPE_ECC, PSA_ECC_FAMILY_SECP_R1, 256):PSA_ALG_SHA_256:PSA_ALG_TLS12_PSK_TO_MS(PSA_ALG_SHA_256):"abcdef":0:0
PSA PAKE: ecjpake rounds, client input first
depends_on:PSA_WANT_KEY_TYPE_ECC_KEY_PAIR:PSA_WANT_ECC_SECP_R1_256:PSA_WANT_ALG_SHA_256:PSA_WANT_ALG_TLS12_PSK_TO_MS
-ecjpake_rounds:PSA_ALG_JPAKE:PSA_PAKE_PRIMITIVE(PSA_PAKE_PRIMITIVE_TYPE_ECC, PSA_ECC_FAMILY_SECP_R1, 256):PSA_ALG_SHA_256:PSA_ALG_TLS12_PSK_TO_MS(PSA_ALG_SHA_256):"abcdef":1
+ecjpake_rounds:PSA_ALG_JPAKE:PSA_PAKE_PRIMITIVE(PSA_PAKE_PRIMITIVE_TYPE_ECC, PSA_ECC_FAMILY_SECP_R1, 256):PSA_ALG_SHA_256:PSA_ALG_TLS12_PSK_TO_MS(PSA_ALG_SHA_256):"abcdef":1:0
+
+# This test case relies on implementation (it may need to be adjusted in the future)
+PSA PAKE: ecjpake rounds - key is destroyed after being passed to set_password_key
+depends_on:PSA_WANT_KEY_TYPE_ECC_KEY_PAIR:PSA_WANT_ECC_SECP_R1_256:PSA_WANT_ALG_SHA_256:PSA_WANT_ALG_TLS12_PSK_TO_MS
+ecjpake_rounds:PSA_ALG_JPAKE:PSA_PAKE_PRIMITIVE(PSA_PAKE_PRIMITIVE_TYPE_ECC, PSA_ECC_FAMILY_SECP_R1, 256):PSA_ALG_SHA_256:PSA_ALG_TLS12_PSK_TO_MS(PSA_ALG_SHA_256):"abcdef":0:1
PSA PAKE: ecjpake no input errors
depends_on:PSA_WANT_KEY_TYPE_ECC_KEY_PAIR:PSA_WANT_ECC_SECP_R1_256:PSA_WANT_ALG_SHA_256
diff --git a/tests/suites/test_suite_psa_crypto.function b/tests/suites/test_suite_psa_crypto.function
index 779f594..1f3b3b6 100644
--- a/tests/suites/test_suite_psa_crypto.function
+++ b/tests/suites/test_suite_psa_crypto.function
@@ -4,6 +4,7 @@
#include "mbedtls/asn1.h"
#include "mbedtls/asn1write.h"
#include "mbedtls/oid.h"
+#include "common.h"
/* For MBEDTLS_CTR_DRBG_MAX_REQUEST, knowing that psa_generate_random()
* uses mbedtls_ctr_drbg internally. */
@@ -31,6 +32,27 @@
#define ASSERT_OPERATION_IS_ACTIVE( operation ) TEST_ASSERT( operation.id != 0 )
#define ASSERT_OPERATION_IS_INACTIVE( operation ) TEST_ASSERT( operation.id == 0 )
+#if defined(PSA_WANT_ALG_JPAKE)
+int ecjpake_operation_setup( psa_pake_operation_t *operation,
+ psa_pake_cipher_suite_t *cipher_suite,
+ psa_pake_role_t role,
+ mbedtls_svc_key_id_t key,
+ size_t key_available )
+{
+ PSA_ASSERT( psa_pake_abort( operation ) );
+
+ PSA_ASSERT( psa_pake_setup( operation, cipher_suite ) );
+
+ PSA_ASSERT( psa_pake_set_role( operation, role) );
+
+ if( key_available )
+ PSA_ASSERT( psa_pake_set_password_key( operation, key ) );
+ return 0;
+exit:
+ return 1;
+}
+#endif
+
/** An invalid export length that will never be set by psa_export_key(). */
static const size_t INVALID_EXPORT_LENGTH = ~0U;
@@ -3962,7 +3984,7 @@
TEST_LE_U( length, output_buffer_size );
output_length += length;
PSA_ASSERT( psa_cipher_finish( &operation,
- output + output_length,
+ mbedtls_buffer_offset( output, output_length ),
output_buffer_size - output_length,
&length ) );
output_length += length;
@@ -3980,7 +4002,7 @@
TEST_LE_U( length, output_buffer_size );
output_length += length;
PSA_ASSERT( psa_cipher_finish( &operation,
- output + output_length,
+ mbedtls_buffer_offset( output, output_length ),
output_buffer_size - output_length,
&length ) );
output_length += length;
@@ -8740,7 +8762,6 @@
{
psa_pake_cipher_suite_t cipher_suite = psa_pake_cipher_suite_init();
psa_pake_operation_t operation = psa_pake_operation_init();
- psa_pake_operation_t op_copy = psa_pake_operation_init();
psa_algorithm_t alg = alg_arg;
psa_pake_primitive_t primitive = primitive_arg;
psa_key_type_t key_type_pw = key_type_pw_arg;
@@ -8839,22 +8860,25 @@
if( input_first )
{
/* Invalid parameters (input) */
- op_copy = operation;
- TEST_EQUAL( psa_pake_input( &op_copy, PSA_PAKE_STEP_ZK_PROOF,
+ TEST_EQUAL( psa_pake_input( &operation, PSA_PAKE_STEP_ZK_PROOF,
NULL, 0 ),
PSA_ERROR_INVALID_ARGUMENT );
/* Invalid parameters (step) */
- op_copy = operation;
- TEST_EQUAL( psa_pake_input( &op_copy, PSA_PAKE_STEP_ZK_PROOF + 10,
+ TEST_EQUAL( ecjpake_operation_setup( &operation, &cipher_suite, role,
+ key, pw_data->len ) , 0 );
+ TEST_EQUAL( psa_pake_input( &operation, PSA_PAKE_STEP_ZK_PROOF + 10,
output_buffer, size_zk_proof ),
PSA_ERROR_INVALID_ARGUMENT );
/* Invalid first step */
- op_copy = operation;
- TEST_EQUAL( psa_pake_input( &op_copy, PSA_PAKE_STEP_ZK_PROOF,
+ TEST_EQUAL( ecjpake_operation_setup( &operation, &cipher_suite, role,
+ key, pw_data->len ), 0 );
+ TEST_EQUAL( psa_pake_input( &operation, PSA_PAKE_STEP_ZK_PROOF,
output_buffer, size_zk_proof ),
PSA_ERROR_BAD_STATE );
/* Possibly valid */
+ TEST_EQUAL( ecjpake_operation_setup( &operation, &cipher_suite, role,
+ key, pw_data->len ), 0 );
TEST_EQUAL( psa_pake_input( &operation, PSA_PAKE_STEP_KEY_SHARE,
output_buffer, size_key_share ),
expected_status_input_output);
@@ -8875,22 +8899,25 @@
else
{
/* Invalid parameters (output) */
- op_copy = operation;
- TEST_EQUAL( psa_pake_output( &op_copy, PSA_PAKE_STEP_ZK_PROOF,
+ TEST_EQUAL( psa_pake_output( &operation, PSA_PAKE_STEP_ZK_PROOF,
NULL, 0, NULL ),
PSA_ERROR_INVALID_ARGUMENT );
- op_copy = operation;
/* Invalid parameters (step) */
- TEST_EQUAL( psa_pake_output( &op_copy, PSA_PAKE_STEP_ZK_PROOF + 10,
+ TEST_EQUAL( ecjpake_operation_setup( &operation, &cipher_suite, role,
+ key, pw_data->len ), 0 );
+ TEST_EQUAL( psa_pake_output( &operation, PSA_PAKE_STEP_ZK_PROOF + 10,
output_buffer, buf_size, &output_len ),
PSA_ERROR_INVALID_ARGUMENT );
/* Invalid first step */
- op_copy = operation;
- TEST_EQUAL( psa_pake_output( &op_copy, PSA_PAKE_STEP_ZK_PROOF,
+ TEST_EQUAL( ecjpake_operation_setup( &operation, &cipher_suite, role,
+ key, pw_data->len ), 0 );
+ TEST_EQUAL( psa_pake_output( &operation, PSA_PAKE_STEP_ZK_PROOF,
output_buffer, buf_size, &output_len ),
PSA_ERROR_BAD_STATE );
/* Possibly valid */
+ TEST_EQUAL( ecjpake_operation_setup( &operation, &cipher_suite, role,
+ key, pw_data->len ), 0 );
TEST_EQUAL( psa_pake_output( &operation, PSA_PAKE_STEP_KEY_SHARE,
output_buffer, buf_size, &output_len ),
expected_status_input_output );
@@ -8974,7 +9001,7 @@
/* BEGIN_CASE depends_on:PSA_WANT_ALG_JPAKE */
void ecjpake_rounds( int alg_arg, int primitive_arg, int hash_arg,
int derive_alg_arg, data_t *pw_data,
- int client_input_first )
+ int client_input_first, int destroy_key )
{
psa_pake_cipher_suite_t cipher_suite = psa_pake_cipher_suite_init();
psa_pake_operation_t server = psa_pake_operation_init();
@@ -9025,6 +9052,9 @@
PSA_ASSERT( psa_pake_set_password_key( &server, key ) );
PSA_ASSERT( psa_pake_set_password_key( &client, key ) );
+ if( destroy_key == 1 )
+ psa_destroy_key( key );
+
TEST_EQUAL( psa_pake_get_implicit_key( &server, &server_derive ),
PSA_ERROR_BAD_STATE );
TEST_EQUAL( psa_pake_get_implicit_key( &client, &client_derive ),
diff --git a/tests/suites/test_suite_x509write.data b/tests/suites/test_suite_x509write.data
index 8411557..c55c9d1 100644
--- a/tests/suites/test_suite_x509write.data
+++ b/tests/suites/test_suite_x509write.data
@@ -1,30 +1,30 @@
Certificate Request check Server1 SHA1
depends_on:MBEDTLS_HAS_ALG_SHA_1_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
-x509_csr_check:"data_files/server1.key":"data_files/server1.req.sha1":MBEDTLS_MD_SHA1:0:0:0:0
+x509_csr_check:"data_files/server1.key":"data_files/server1.req.sha1":MBEDTLS_MD_SHA1:0:0:0:0:0
Certificate Request check Server1 SHA224
depends_on:MBEDTLS_HAS_ALG_SHA_224_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
-x509_csr_check:"data_files/server1.key":"data_files/server1.req.sha224":MBEDTLS_MD_SHA224:0:0:0:0
+x509_csr_check:"data_files/server1.key":"data_files/server1.req.sha224":MBEDTLS_MD_SHA224:0:0:0:0:0
Certificate Request check Server1 SHA256
depends_on:MBEDTLS_HAS_ALG_SHA_256_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
-x509_csr_check:"data_files/server1.key":"data_files/server1.req.sha256":MBEDTLS_MD_SHA256:0:0:0:0
+x509_csr_check:"data_files/server1.key":"data_files/server1.req.sha256":MBEDTLS_MD_SHA256:0:0:0:0:0
Certificate Request check Server1 SHA384
depends_on:MBEDTLS_HAS_ALG_SHA_384_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
-x509_csr_check:"data_files/server1.key":"data_files/server1.req.sha384":MBEDTLS_MD_SHA384:0:0:0:0
+x509_csr_check:"data_files/server1.key":"data_files/server1.req.sha384":MBEDTLS_MD_SHA384:0:0:0:0:0
Certificate Request check Server1 SHA512
depends_on:MBEDTLS_HAS_ALG_SHA_512_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
-x509_csr_check:"data_files/server1.key":"data_files/server1.req.sha512":MBEDTLS_MD_SHA512:0:0:0:0
+x509_csr_check:"data_files/server1.key":"data_files/server1.req.sha512":MBEDTLS_MD_SHA512:0:0:0:0:0
Certificate Request check Server1 MD5
depends_on:MBEDTLS_HAS_ALG_MD5_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
-x509_csr_check:"data_files/server1.key":"data_files/server1.req.md5":MBEDTLS_MD_MD5:0:0:0:0
+x509_csr_check:"data_files/server1.key":"data_files/server1.req.md5":MBEDTLS_MD_MD5:0:0:0:0:0
Certificate Request check Server1 key_usage
depends_on:MBEDTLS_HAS_ALG_SHA_1_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
-x509_csr_check:"data_files/server1.key":"data_files/server1.req.key_usage":MBEDTLS_MD_SHA1:MBEDTLS_X509_KU_DIGITAL_SIGNATURE | MBEDTLS_X509_KU_NON_REPUDIATION | MBEDTLS_X509_KU_KEY_ENCIPHERMENT:1:0:0
+x509_csr_check:"data_files/server1.key":"data_files/server1.req.key_usage":MBEDTLS_MD_SHA1:MBEDTLS_X509_KU_DIGITAL_SIGNATURE | MBEDTLS_X509_KU_NON_REPUDIATION | MBEDTLS_X509_KU_KEY_ENCIPHERMENT:1:0:0:0
Certificate Request check opaque Server1 key_usage
depends_on:MBEDTLS_HAS_ALG_SHA_1_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
@@ -32,23 +32,27 @@
Certificate Request check Server1 key_usage empty
depends_on:MBEDTLS_HAS_ALG_SHA_1_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
-x509_csr_check:"data_files/server1.key":"data_files/server1.req.key_usage_empty":MBEDTLS_MD_SHA1:0:1:0:0
+x509_csr_check:"data_files/server1.key":"data_files/server1.req.key_usage_empty":MBEDTLS_MD_SHA1:0:1:0:0:0
Certificate Request check Server1 ns_cert_type
depends_on:MBEDTLS_HAS_ALG_SHA_1_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
-x509_csr_check:"data_files/server1.key":"data_files/server1.req.cert_type":MBEDTLS_MD_SHA1:0:0:MBEDTLS_X509_NS_CERT_TYPE_SSL_SERVER:1
+x509_csr_check:"data_files/server1.key":"data_files/server1.req.cert_type":MBEDTLS_MD_SHA1:0:0:MBEDTLS_X509_NS_CERT_TYPE_SSL_SERVER:1:0
Certificate Request check Server1 ns_cert_type empty
depends_on:MBEDTLS_HAS_ALG_SHA_1_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
-x509_csr_check:"data_files/server1.key":"data_files/server1.req.cert_type_empty":MBEDTLS_MD_SHA1:0:0:0:1
+x509_csr_check:"data_files/server1.key":"data_files/server1.req.cert_type_empty":MBEDTLS_MD_SHA1:0:0:0:1:0
Certificate Request check Server1 key_usage + ns_cert_type
depends_on:MBEDTLS_HAS_ALG_SHA_1_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
-x509_csr_check:"data_files/server1.key":"data_files/server1.req.ku-ct":MBEDTLS_MD_SHA1:MBEDTLS_X509_KU_DIGITAL_SIGNATURE | MBEDTLS_X509_KU_NON_REPUDIATION | MBEDTLS_X509_KU_KEY_ENCIPHERMENT:1:MBEDTLS_X509_NS_CERT_TYPE_SSL_SERVER:1
+x509_csr_check:"data_files/server1.key":"data_files/server1.req.ku-ct":MBEDTLS_MD_SHA1:MBEDTLS_X509_KU_DIGITAL_SIGNATURE | MBEDTLS_X509_KU_NON_REPUDIATION | MBEDTLS_X509_KU_KEY_ENCIPHERMENT:1:MBEDTLS_X509_NS_CERT_TYPE_SSL_SERVER:1:0
Certificate Request check Server5 ECDSA, key_usage
depends_on:MBEDTLS_HAS_ALG_SHA_1_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_ECDSA_C:MBEDTLS_ECDSA_DETERMINISTIC:MBEDTLS_ECP_DP_SECP256R1_ENABLED
-x509_csr_check:"data_files/server5.key":"data_files/server5.req.ku.sha1":MBEDTLS_MD_SHA1:MBEDTLS_X509_KU_DIGITAL_SIGNATURE | MBEDTLS_X509_KU_NON_REPUDIATION:1:0:0
+x509_csr_check:"data_files/server5.key":"data_files/server5.req.ku.sha1":MBEDTLS_MD_SHA1:MBEDTLS_X509_KU_DIGITAL_SIGNATURE | MBEDTLS_X509_KU_NON_REPUDIATION:1:0:0:0
+
+Certificate Request check Server1, set_extension
+depends_on:MBEDTLS_HAS_ALG_SHA_256_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_RSA_C:MBEDTLS_PKCS1_V15
+x509_csr_check:"data_files/server1.key":"data_files/server1.req.sha256.ext":MBEDTLS_MD_SHA256:0:0:0:0:1
Certificate Request check opaque Server5 ECDSA, key_usage
depends_on:MBEDTLS_HAS_ALG_SHA_256_VIA_MD_OR_PSA_BASED_ON_USE_PSA:MBEDTLS_ECDSA_C:MBEDTLS_ECP_DP_SECP256R1_ENABLED
diff --git a/tests/suites/test_suite_x509write.function b/tests/suites/test_suite_x509write.function
index aa54072..5bd814a 100644
--- a/tests/suites/test_suite_x509write.function
+++ b/tests/suites/test_suite_x509write.function
@@ -5,6 +5,7 @@
#include "mbedtls/pem.h"
#include "mbedtls/oid.h"
#include "mbedtls/rsa.h"
+#include "mbedtls/asn1write.h"
#include "hash_info.h"
#include "mbedtls/legacy_or_psa.h"
@@ -74,6 +75,56 @@
}
#endif /* MBEDTLS_USE_PSA_CRYPTO && MBEDTLS_PEM_WRITE_C && MBEDTLS_X509_CSR_WRITE_C */
+#if defined(MBEDTLS_X509_CSR_WRITE_C)
+
+/*
+ * The size of this temporary buffer is given by the sequence of functions
+ * called hereinafter:
+ * - mbedtls_asn1_write_oid()
+ * - 8 bytes for MBEDTLS_OID_EXTENDED_KEY_USAGE raw value
+ * - 1 byte for MBEDTLS_OID_EXTENDED_KEY_USAGE length
+ * - 1 byte for MBEDTLS_ASN1_OID tag
+ * - mbedtls_asn1_write_len()
+ * - 1 byte since we're dealing with sizes which are less than 0x80
+ * - mbedtls_asn1_write_tag()
+ * - 1 byte
+ *
+ * This length is fine as long as this function is called using the
+ * MBEDTLS_OID_SERVER_AUTH OID. If this is changed in the future, then this
+ * buffer's length should be adjusted accordingly.
+ * Unfortunately there's no predefined max size for OIDs which can be used
+ * to set an overall upper boundary which is always guaranteed.
+ */
+#define EXT_KEY_USAGE_TMP_BUF_MAX_LENGTH 12
+
+static int csr_set_extended_key_usage( mbedtls_x509write_csr *ctx,
+ const char *oid, size_t oid_len )
+{
+ unsigned char buf[EXT_KEY_USAGE_TMP_BUF_MAX_LENGTH] = { 0 };
+ unsigned char *p = buf + sizeof( buf );
+ int ret;
+ size_t len = 0;
+
+ /*
+ * Following functions fail anyway if the temporary buffer is not large,
+ * but we set an extra check here to emphasize a possible source of errors
+ */
+ if ( oid_len > EXT_KEY_USAGE_TMP_BUF_MAX_LENGTH )
+ {
+ return MBEDTLS_ERR_X509_BAD_INPUT_DATA;
+ }
+
+ MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_oid( &p, buf, oid, oid_len ) );
+ MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_len( &p, buf, ret ) );
+ MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_tag( &p, buf,
+ MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE ) );
+
+ ret = mbedtls_x509write_csr_set_extension( ctx, MBEDTLS_OID_EXTENDED_KEY_USAGE,
+ MBEDTLS_OID_SIZE( MBEDTLS_OID_EXTENDED_KEY_USAGE ), 0, p, len );
+
+ return ret;
+}
+#endif /* MBEDTLS_X509_CSR_WRITE_C */
/* END_HEADER */
/* BEGIN_DEPENDENCIES
@@ -84,7 +135,7 @@
/* BEGIN_CASE depends_on:MBEDTLS_PEM_WRITE_C:MBEDTLS_X509_CSR_WRITE_C */
void x509_csr_check( char * key_file, char * cert_req_check_file, int md_type,
int key_usage, int set_key_usage, int cert_type,
- int set_cert_type )
+ int set_cert_type, int set_extension )
{
mbedtls_pk_context key;
mbedtls_x509write_csr req;
@@ -117,6 +168,9 @@
TEST_ASSERT( mbedtls_x509write_csr_set_key_usage( &req, key_usage ) == 0 );
if( set_cert_type != 0 )
TEST_ASSERT( mbedtls_x509write_csr_set_ns_cert_type( &req, cert_type ) == 0 );
+ if ( set_extension != 0 )
+ TEST_ASSERT( csr_set_extended_key_usage( &req, MBEDTLS_OID_SERVER_AUTH,
+ MBEDTLS_OID_SIZE( MBEDTLS_OID_SERVER_AUTH ) ) == 0 );
ret = mbedtls_x509write_csr_pem( &req, buf, sizeof( buf ),
mbedtls_test_rnd_pseudo_rand, &rnd_info );