Merge branch 'mbedtls-2.1'
diff --git a/ChangeLog b/ChangeLog
index 374c6aa..87b8185 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,21 +1,32 @@
 mbed TLS ChangeLog (Sorted per branch, date)
 
-= mbed TLS 2.1.x
+= mbed TLS 2.1.x branch released 2016-xx-xx
+
+Security
+   * Removed the MBEDTLS_SSL_AEAD_RANDOM_IV option, because it was not compliant
+     with RFC-5116 and could lead to session key recovery in very long TLS
+     sessions. "Nonce-Disrespecting Adversaries Practical Forgery Attacks on GCM in
+     TLS" - H. Bock, A. Zauner, S. Devlin, J. Somorovsky, P. Jovanovic.
+     https://eprint.iacr.org/2016/475.pdf
+   * Fixed potential stack corruption in mbedtls_x509write_crt_der() and
+     mbedtls_x509write_csr_der() when the signature is copied to the buffer
+     without checking whether there is enough space in the destination. The
+     issue cannot be triggered remotely. Found by Jethro Beekman.
 
 Bugfix
    * Fix an issue that caused valid certificates being rejected whenever an
      expired or not yet valid version of the trusted certificate was before the
      valid version in the trusted certificate list.
-   * Fix incorrect handling of block lengths in crypt_and_hash sample program,
-     when GCM is used. #441
+   * Fix incorrect handling of block lengths in crypt_and_hash.c sample program,
+     when GCM is used. Found by udf2457. #441
    * Fix for key exchanges based on ECDH-RSA or ECDH-ECDSA which weren't
      enabled unless others were also present. Found by David Fernandez. #428
-   * Fixed cert_app sample program for debug output and for use when no root
+   * Fixed cert_app.c sample program for debug output and for use when no root
      certificates are provided.
    * Fix conditional statement that would cause a 1 byte overread in
      mbedtls_asn1_get_int(). Found and fixed by Guido Vranken. #599
    * Fixed pthread implementation to avoid unintended double initialisations
-     and double frees. (found by Niklas Amnebratt)
+     and double frees. Found by Niklas Amnebratt.
    * Fixed the sample applications gen_key.c, cert_req.c and cert_write.c for
      builds where the configuration MBEDTLS_PEM_WRITE_C is not defined. Found
      by inestlerode. #559.
@@ -25,6 +36,10 @@
    * Fix documentation and implementation missmatch for function arguments of
      mbedtls_gcm_finish(). Found by cmiatpaar. #602
    * Guarantee that P>Q at RSA key generation. Found by inestlerode. #558
+   * Fix missing return code check after call to mbedtls_md_setup() that could
+     result in usage of invalid md_ctx in mbedtls_rsa_rsaes_oaep_encrypt(),
+     mbedtls_rsa_rsaes_oaep_decrypt(), mbedtls_rsa_rsassa_pss_sign() and
+     mbedtls_rsa_rsassa_pss_verify_ext(). Fixed by Brian J. Murray. #502
    * Fix potential byte overread when verifying malformed SERVER_HELLO in
      ssl_parse_hello_verify_request() for DTLS. Found by Guido Vranken.
    * Fix check for validity of date when parsing in mbedtls_x509_get_time().
diff --git a/include/mbedtls/config.h b/include/mbedtls/config.h
index 5147ec6..e77cf26 100644
--- a/include/mbedtls/config.h
+++ b/include/mbedtls/config.h
@@ -869,18 +869,6 @@
 //#define MBEDTLS_SHA256_SMALLER
 
 /**
- * \def MBEDTLS_SSL_AEAD_RANDOM_IV
- *
- * Generate a random IV rather than using the record sequence number as a
- * nonce for ciphersuites using and AEAD algorithm (GCM or CCM).
- *
- * Using the sequence number is generally recommended.
- *
- * Uncomment this macro to always use random IVs with AEAD ciphersuites.
- */
-//#define MBEDTLS_SSL_AEAD_RANDOM_IV
-
-/**
  * \def MBEDTLS_SSL_ALL_ALERT_MESSAGES
  *
  * Enable sending of alert messages in case of encountered errors as per RFC.
diff --git a/library/rsa.c b/library/rsa.c
index 76e35de..e831875 100644
--- a/library/rsa.c
+++ b/library/rsa.c
@@ -551,7 +551,11 @@
     memcpy( p, input, ilen );
 
     mbedtls_md_init( &md_ctx );
-    mbedtls_md_setup( &md_ctx, md_info, 0 );
+    if( ( ret = mbedtls_md_setup( &md_ctx, md_info, 0 ) ) != 0 )
+    {
+        mbedtls_md_free( &md_ctx );
+        return( ret );
+    }
 
     // maskedDB: Apply dbMask to DB
     //
@@ -726,7 +730,12 @@
      * Unmask data and generate lHash
      */
     mbedtls_md_init( &md_ctx );
-    mbedtls_md_setup( &md_ctx, md_info, 0 );
+    if( ( ret = mbedtls_md_setup( &md_ctx, md_info, 0 ) ) != 0 )
+    {
+        mbedtls_md_free( &md_ctx );
+        return( ret );
+    }
+
 
     /* Generate lHash */
     mbedtls_md( md_info, label, label_len, lhash );
@@ -972,7 +981,11 @@
     p += slen;
 
     mbedtls_md_init( &md_ctx );
-    mbedtls_md_setup( &md_ctx, md_info, 0 );
+    if( ( ret = mbedtls_md_setup( &md_ctx, md_info, 0 ) ) != 0 )
+    {
+        mbedtls_md_free( &md_ctx );
+        return( ret );
+    }
 
     // Generate H = Hash( M' )
     //
@@ -1245,7 +1258,11 @@
         return( MBEDTLS_ERR_RSA_BAD_INPUT_DATA );
 
     mbedtls_md_init( &md_ctx );
-    mbedtls_md_setup( &md_ctx, md_info, 0 );
+    if( ( ret = mbedtls_md_setup( &md_ctx, md_info, 0 ) ) != 0 )
+    {
+        mbedtls_md_free( &md_ctx );
+        return( ret );
+    }
 
     mgf_mask( p, siglen - hlen - 1, p + siglen - hlen - 1, hlen, &md_ctx );
 
diff --git a/library/ssl_tls.c b/library/ssl_tls.c
index bf60941..d442642 100644
--- a/library/ssl_tls.c
+++ b/library/ssl_tls.c
@@ -1364,17 +1364,6 @@
         /*
          * Generate IV
          */
-#if defined(MBEDTLS_SSL_AEAD_RANDOM_IV)
-        ret = ssl->conf->f_rng( ssl->conf->p_rng,
-                ssl->transform_out->iv_enc + ssl->transform_out->fixed_ivlen,
-                ssl->transform_out->ivlen - ssl->transform_out->fixed_ivlen );
-        if( ret != 0 )
-            return( ret );
-
-        memcpy( ssl->out_iv,
-                ssl->transform_out->iv_enc + ssl->transform_out->fixed_ivlen,
-                ssl->transform_out->ivlen - ssl->transform_out->fixed_ivlen );
-#else
         if( ssl->transform_out->ivlen - ssl->transform_out->fixed_ivlen != 8 )
         {
             /* Reminder if we ever add an AEAD mode with a different size */
@@ -1385,7 +1374,6 @@
         memcpy( ssl->transform_out->iv_enc + ssl->transform_out->fixed_ivlen,
                              ssl->out_ctr, 8 );
         memcpy( ssl->out_iv, ssl->out_ctr, 8 );
-#endif
 
         MBEDTLS_SSL_DEBUG_BUF( 4, "IV used", ssl->out_iv,
                 ssl->transform_out->ivlen - ssl->transform_out->fixed_ivlen );
diff --git a/library/version_features.c b/library/version_features.c
index 196b93c..f9d99af 100644
--- a/library/version_features.c
+++ b/library/version_features.c
@@ -309,9 +309,6 @@
 #if defined(MBEDTLS_SHA256_SMALLER)
     "MBEDTLS_SHA256_SMALLER",
 #endif /* MBEDTLS_SHA256_SMALLER */
-#if defined(MBEDTLS_SSL_AEAD_RANDOM_IV)
-    "MBEDTLS_SSL_AEAD_RANDOM_IV",
-#endif /* MBEDTLS_SSL_AEAD_RANDOM_IV */
 #if defined(MBEDTLS_SSL_ALL_ALERT_MESSAGES)
     "MBEDTLS_SSL_ALL_ALERT_MESSAGES",
 #endif /* MBEDTLS_SSL_ALL_ALERT_MESSAGES */
diff --git a/library/x509write_crt.c b/library/x509write_crt.c
index 9041d44..d1d9a22 100644
--- a/library/x509write_crt.c
+++ b/library/x509write_crt.c
@@ -413,6 +413,9 @@
     MBEDTLS_ASN1_CHK_ADD( sig_and_oid_len, mbedtls_x509_write_sig( &c2, buf,
                                         sig_oid, sig_oid_len, sig, sig_len ) );
 
+    if( len > (size_t)( c2 - buf ) )
+        return( MBEDTLS_ERR_ASN1_BUF_TOO_SMALL );
+
     c2 -= len;
     memcpy( c2, c, len );
 
diff --git a/library/x509write_csr.c b/library/x509write_csr.c
index 0b9a285..8fd856b 100644
--- a/library/x509write_csr.c
+++ b/library/x509write_csr.c
@@ -213,6 +213,9 @@
     MBEDTLS_ASN1_CHK_ADD( sig_and_oid_len, mbedtls_x509_write_sig( &c2, buf,
                                         sig_oid, sig_oid_len, sig, sig_len ) );
 
+    if( len > (size_t)( c2 - buf ) )
+        return( MBEDTLS_ERR_ASN1_BUF_TOO_SMALL );
+
     c2 -= len;
     memcpy( c2, c, len );
 
diff --git a/tests/scripts/all.sh b/tests/scripts/all.sh
index 5ef74cd..a2eff08 100755
--- a/tests/scripts/all.sh
+++ b/tests/scripts/all.sh
@@ -1,19 +1,29 @@
 #!/bin/sh
 
-# Run all available tests (mostly).
+# all.sh
 #
-# Warning: includes various build modes, so it will mess with the current
-# CMake configuration. After this script is run, the CMake cache is lost and
-# CMake is not initialised any more!
+# This file is part of mbed TLS (https://tls.mbed.org)
 #
-# Assumes gcc and clang (recent enough for using ASan with gcc and MemSan with
-# clang, or valgrind) are available, as well as cmake and a "good" find.
+# Copyright (c) 2014-2016, ARM Limited, All Rights Reserved
+#
+# Purpose
+#
+# To run all tests possible or available on the platform.
+#
+# Warning: the test is destructive. It includes various build modes and
+# configurations, and can and will arbitrarily change the current CMake
+# configuration. After this script has been run, the CMake cache will be lost
+# and CMake will no longer be initialised.
+#
+# The script assumes the presence of gcc and clang (recent enough for using
+# ASan with gcc and MemSan with clang, or valgrind) are available, as well as
+# cmake and a "good" find.
 
-# Abort on errors (and uninitiliased variables)
+# Abort on errors (and uninitialised variables)
 set -eu
 
 if [ -d library -a -d include -a -d tests ]; then :; else
-    echo "Must be run from mbed TLS root" >&2
+    err_msg "Must be run from mbed TLS root"
     exit 1
 fi
 
@@ -21,20 +31,34 @@
 CONFIG_BAK="$CONFIG_H.bak"
 
 MEMORY=0
+FORCE=0
+RELEASE=0
 
-while [ $# -gt 0 ]; do
-    case "$1" in
-        -m*)
-            MEMORY=${1#-m}
-            ;;
-        *)
-            echo "Unknown argument: '$1'" >&2
-            echo "Use the source, Luke!" >&2
-            exit 1
-            ;;
-    esac
-    shift
-done
+# Default commands, can be overriden by the environment
+: ${OPENSSL:="openssl"}
+: ${OPENSSL_LEGACY:="$OPENSSL"}
+: ${GNUTLS_CLI:="gnutls-cli"}
+: ${GNUTLS_SERV:="gnutls-serv"}
+: ${GNUTLS_LEGACY_CLI:="$GNUTLS_CLI"}
+: ${GNUTLS_LEGACY_SERV:="$GNUTLS_SERV"}
+: ${OUT_OF_SOURCE_DIR:=./mbedtls_out_of_source_build}
+
+usage()
+{
+    printf "Usage: $0\n"
+    printf "  -h|--help\t\tPrint this help.\n"
+    printf "  -m|--memory\t\tAdditional optional memory tests.\n"
+    printf "  -f|--force\t\tForce the tests to overwrite any modified files.\n"
+    printf "  -s|--seed\t\tInteger seed value to use for this test run.\n"
+    printf "  -r|--release-test\t\tRun this script in release mode. This fixes the seed value to 1.\n"
+    printf "     --out-of-source-dir=<path>\t\tDirectory used for CMake out-of-source build tests."
+    printf "     --openssl=<OpenSSL_path>\t\tPath to OpenSSL executable to use for most tests.\n"
+    printf "     --openssl-legacy=<OpenSSL_path>\t\tPath to OpenSSL executable to use for legacy tests e.g. SSLv3.\n"
+    printf "     --gnutls-cli=<GnuTLS_cli_path>\t\tPath to GnuTLS client executable to use for most tests.\n"
+    printf "     --gnutls-serv=<GnuTLS_serv_path>\t\tPath to GnuTLS server executable to use for most tests.\n"
+    printf "     --gnutls-legacy-cli=<GnuTLS_cli_path>\t\tPath to GnuTLS client executable to use for legacy tests.\n"
+    printf "     --gnutls-legacy-serv=<GnuTLS_serv_path>\t\tPath to GnuTLS server executable to use for legacy tests.\n"
+}
 
 # remove built files as well as the cmake cache/config
 cleanup()
@@ -62,6 +86,134 @@
     echo "******************************************************************"
 }
 
+err_msg()
+{
+    echo "$1" >&2
+}
+
+check_tools()
+{
+    for TOOL in "$@"; do
+        if ! `hash "$TOOL" >/dev/null 2>&1`; then
+            err_msg "$TOOL not found!"
+            exit 1
+        fi
+    done
+}
+
+while [ $# -gt 0 ]; do
+    case "$1" in
+        --memory|-m*)
+            MEMORY=${1#-m}
+            ;;
+        --force|-f)
+            FORCE=1
+            ;;
+        --seed|-s)
+            shift
+            SEED="$1"
+            ;;
+        --release-test|-r)
+            RELEASE=1
+            ;;
+        --out-of-source-dir)
+            shift
+            OUT_OF_SOURCE_DIR="$1"
+            ;;
+        --openssl)
+            shift
+            OPENSSL="$1"
+            ;;
+        --openssl-legacy)
+            shift
+            OPENSSL_LEGACY="$1"
+            ;;
+        --gnutls-cli)
+            shift
+            GNUTLS_CLI="$1"
+            ;;
+        --gnutls-serv)
+            shift
+            GNUTLS_SERV="$1"
+            ;;
+        --gnutls-legacy-cli)
+            shift
+            GNUTLS_LEGACY_CLI="$1"
+            ;;
+        --gnutls-legacy-serv)
+            shift
+            GNUTLS_LEGACY_SERV="$1"
+            ;;
+        --help|-h|*)
+            usage
+            exit 1
+            ;;
+    esac
+    shift
+done
+
+if [ $FORCE -eq 1 ]; then
+    rm -rf yotta/module "$OUT_OF_SOURCE_DIR"
+    git checkout-index -f -q $CONFIG_H
+    cleanup
+else
+
+    if [ -d yotta/module ]; then
+        err_msg "Warning - there is an existing yotta module in the directory 'yotta/module'"
+        echo "You can either delete your work and retry, or force the test to overwrite the"
+        echo "test by rerunning the script as: $0 --force"
+        exit 1
+    fi
+
+    if [ -d "$OUT_OF_SOURCE_DIR" ]; then
+        echo "Warning - there is an existing directory at '$OUT_OF_SOURCE_DIR'" >&2
+        echo "You can either delete this directory manually, or force the test by rerunning"
+        echo "the script as: $0 --force --out-of-source-dir $OUT_OF_SOURCE_DIR"
+        exit 1
+    fi
+
+    if ! git diff-files --quiet include/mbedtls/config.h; then
+        echo $?
+        err_msg "Warning - the configuration file 'include/mbedtls/config.h' has been edited. "
+        echo "You can either delete or preserve your work, or force the test by rerunning the"
+        echo "script as: $0 --force"
+        exit 1
+    fi
+fi
+
+if [ $RELEASE -eq 1 ]; then
+    # Fix the seed value to 1 to ensure that the tests are deterministic.
+    SEED=1
+fi
+
+msg "info: $0 configuration"
+echo "MEMORY: $MEMORY"
+echo "FORCE: $FORCE"
+echo "SEED: ${SEED-"UNSET"}"
+echo "OPENSSL: $OPENSSL"
+echo "OPENSSL_LEGACY: $OPENSSL_LEGACY"
+echo "GNUTLS_CLI: $GNUTLS_CLI"
+echo "GNUTLS_SERV: $GNUTLS_SERV"
+echo "GNUTLS_LEGACY_CLI: $GNUTLS_LEGACY_CLI"
+echo "GNUTLS_LEGACY_SERV: $GNUTLS_LEGACY_SERV"
+
+# To avoid setting OpenSSL and GnuTLS for each call to compat.sh and ssl-opt.sh
+# we just export the variables they require
+export OPENSSL_CMD="$OPENSSL"
+export GNUTLS_CLI="$GNUTLS_CLI"
+export GNUTLS_SERV="$GNUTLS_SERV"
+
+# Avoid passing --seed flag in every call to ssl-opt.sh
+[ ! -z ${SEED+set} ] && export SEED
+
+# Make sure the tools we need are available.
+check_tools "$OPENSSL" "$OPENSSL_LEGACY" "$GNUTLS_CLI" "$GNUTLS_SERV" \
+    "$GNUTLS_LEGACY_CLI" "$GNUTLS_LEGACY_SERV" "doxygen" "dot" \
+    "arm-none-eabi-gcc" "armcc"
+
+#
+# Test Suites to be executed
+#
 # The test ordering tries to optimize for the following criteria:
 # 1. Catch possible problems early, by running first tests that run quickly
 #    and/or are more likely to fail than others (eg I use Clang most of the
@@ -93,7 +245,7 @@
 CC=gcc cmake -D CMAKE_BUILD_TYPE:String=Asan .
 make
 
-msg "test: main suites and selftest (ASan build)" # ~ 50s
+msg "test: main suites (inc. selftests) (ASan build)" # ~ 50s
 make test
 programs/test/selftest
 
@@ -103,8 +255,6 @@
 msg "test/build: ref-configs (ASan build)" # ~ 6 min 20s
 tests/scripts/test-ref-configs.pl
 
-# Most frequent issues are likely to be caught at this point
-
 msg "build: with ASan (rebuild after ref-configs)" # ~ 1 min
 make
 
@@ -118,12 +268,13 @@
 CC=gcc cmake -D CMAKE_BUILD_TYPE:String=Asan .
 make
 
-msg "test: SSLv3 - main suites and selftest (ASan build)" # ~ 50s
+msg "test: SSLv3 - main suites (inc. selftests) (ASan build)" # ~ 50s
 make test
 programs/test/selftest
 
 msg "build: SSLv3 - compat.sh (ASan build)" # ~ 6 min
-tests/compat.sh -m 'ssl3 tls1 tls1_1 tls1_2 dtls1 dtls1_2'
+tests/compat.sh -m 'tls1 tls1_1 tls1_2 dtls1 dtls1_2'
+OPENSSL_CMD="$OPENSSL_LEGACY" tests/compat.sh -m 'ssl3'
 
 msg "build: SSLv3 - ssl-opt.sh (ASan build)" # ~ 6 min
 tests/ssl-opt.sh
@@ -143,7 +294,7 @@
 tests/ssl-opt.sh -f Default
 
 msg "test: compat.sh RC4, DES & NULL (full config)" # ~ 2 min
-tests/compat.sh -e '3DES\|DES-CBC3' -f 'NULL\|DES\|RC4\|ARCFOUR'
+OPENSSL_CMD="$OPENSSL_LEGACY" GNUTLS_CLI="$GNUTLS_LEGACY_CLI" GNUTLS_SERV="$GNUTLS_LEGACY_SERV" tests/compat.sh -e '3DES\|DES-CBC3' -f 'NULL\|DES\|RC4\|ARCFOUR'
 
 msg "test/build: curves.pl (gcc)" # ~ 4 min
 cleanup
@@ -217,7 +368,6 @@
 CC=gcc CFLAGS='-Werror -m32' make
 fi # x86_64
 
-if which arm-none-eabi-gcc >/dev/null; then
 msg "build: arm-none-eabi-gcc, make" # ~ 10s
 cleanup
 cp "$CONFIG_H" "$CONFIG_BAK"
@@ -225,6 +375,7 @@
 scripts/config.pl unset MBEDTLS_NET_C
 scripts/config.pl unset MBEDTLS_TIMING_C
 scripts/config.pl unset MBEDTLS_FS_IO
+scripts/config.pl set MBEDTLS_NO_PLATFORM_ENTROPY
 # following things are not in the default config
 scripts/config.pl unset MBEDTLS_HAVEGE_C # depends on timing.c
 scripts/config.pl unset MBEDTLS_THREADING_PTHREAD
@@ -232,9 +383,7 @@
 scripts/config.pl unset MBEDTLS_MEMORY_BACKTRACE # execinfo.h
 scripts/config.pl unset MBEDTLS_MEMORY_BUFFER_ALLOC_C # calls exit
 CC=arm-none-eabi-gcc AR=arm-none-eabi-ar LD=arm-none-eabi-ld CFLAGS=-Werror make lib
-fi # arm-gcc
 
-if which armcc >/dev/null && armcc --help >/dev/null 2>&1; then
 msg "build: armcc, make"
 cleanup
 cp "$CONFIG_H" "$CONFIG_BAK"
@@ -244,6 +393,7 @@
 scripts/config.pl unset MBEDTLS_FS_IO
 scripts/config.pl unset MBEDTLS_HAVE_TIME
 scripts/config.pl unset MBEDTLS_HAVE_TIME_DATE
+scripts/config.pl set MBEDTLS_NO_PLATFORM_ENTROPY
 # following things are not in the default config
 scripts/config.pl unset MBEDTLS_DEPRECATED_WARNING
 scripts/config.pl unset MBEDTLS_HAVEGE_C # depends on timing.c
@@ -251,13 +401,7 @@
 scripts/config.pl unset MBEDTLS_THREADING_C
 scripts/config.pl unset MBEDTLS_MEMORY_BACKTRACE # execinfo.h
 scripts/config.pl unset MBEDTLS_MEMORY_BUFFER_ALLOC_C # calls exit
-CC=armcc AR=armar WARNING_CFLAGS= make lib 2> armcc.stderr
-if [ -s armcc.stderr ]; then
-    cat armcc.stderr
-    exit 1;
-fi
-rm armcc.stderr
-fi # armcc
+CC=armcc AR=armar WARNING_CFLAGS= make lib
 
 if which i686-w64-mingw32-gcc >/dev/null; then
 msg "build: cross-mingw64, make" # ~ 30s
@@ -317,6 +461,19 @@
 
 fi # MemSan
 
+msg "build: cmake 'out-of-source' build"
+cleanup
+MBEDTLS_ROOT_DIR="$PWD"
+mkdir "$OUT_OF_SOURCE_DIR"
+cd "$OUT_OF_SOURCE_DIR"
+cmake "$MBEDTLS_ROOT_DIR"
+make
+
+msg "test: cmake 'out-of-source' build"
+make test
+cd "$MBEDTLS_ROOT_DIR"
+rm -rf "$OUT_OF_SOURCE_DIR"
+
 msg "Done, cleaning up"
 cleanup
 
diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh
index d184d85..e73d011 100755
--- a/tests/ssl-opt.sh
+++ b/tests/ssl-opt.sh
@@ -286,8 +286,10 @@
 # Usage: run_test name [-p proxy_cmd] srv_cmd cli_cmd cli_exit [option [...]]
 # Options:  -s pattern  pattern that must be present in server output
 #           -c pattern  pattern that must be present in client output
+#           -u pattern  lines after pattern must be unique in client output
 #           -S pattern  pattern that must be absent in server output
 #           -C pattern  pattern that must be absent in client output
+#           -U pattern  lines after pattern must be unique in server output
 run_test() {
     NAME="$1"
     shift 1
@@ -419,29 +421,50 @@
     do
         case $1 in
             "-s")
-                if grep -v '^==' $SRV_OUT | grep "$2" >/dev/null; then :; else
-                    fail "-s $2"
+                if grep -v '^==' $SRV_OUT | grep -v 'Serious error when reading debug info' | grep "$2" >/dev/null; then :; else
+                    fail "pattern '$2' MUST be present in the Server output"
                     return
                 fi
                 ;;
 
             "-c")
-                if grep -v '^==' $CLI_OUT | grep "$2" >/dev/null; then :; else
-                    fail "-c $2"
+                if grep -v '^==' $CLI_OUT | grep -v 'Serious error when reading debug info' | grep "$2" >/dev/null; then :; else
+                    fail "pattern '$2' MUST be present in the Client output"
                     return
                 fi
                 ;;
 
             "-S")
-                if grep -v '^==' $SRV_OUT | grep "$2" >/dev/null; then
-                    fail "-S $2"
+                if grep -v '^==' $SRV_OUT | grep -v 'Serious error when reading debug info' | grep "$2" >/dev/null; then
+                    fail "pattern '$2' MUST NOT be present in the Server output"
                     return
                 fi
                 ;;
 
             "-C")
-                if grep -v '^==' $CLI_OUT | grep "$2" >/dev/null; then
-                    fail "-C $2"
+                if grep -v '^==' $CLI_OUT | grep -v 'Serious error when reading debug info' | grep "$2" >/dev/null; then
+                    fail "pattern '$2' MUST NOT be present in the Client output"
+                    return
+                fi
+                ;;
+
+                # The filtering in the following two options (-u and -U) do the following
+                #   - ignore valgrind output
+                #   - filter out everything but lines right after the pattern occurances
+                #   - keep one of each non-unique line
+                #   - count how many lines remain
+                # A line with '--' will remain in the result from previous outputs, so the number of lines in the result will be 1
+                # if there were no duplicates.
+            "-U")
+                if [ $(grep -v '^==' $SRV_OUT | grep -v 'Serious error when reading debug info' | grep -A1 "$2" | grep -v "$2" | sort | uniq -d | wc -l) -gt 1 ]; then
+                    fail "lines following pattern '$2' must be unique in Server output"
+                    return
+                fi
+                ;;
+
+            "-u")
+                if [ $(grep -v '^==' $CLI_OUT | grep -v 'Serious error when reading debug info' | grep -A1 "$2" | grep -v "$2" | sort | uniq -d | wc -l) -gt 1 ]; then
+                    fail "lines following pattern '$2' must be unique in Client output"
                     return
                 fi
                 ;;
@@ -572,6 +595,14 @@
             -s "Protocol is DTLSv1.2" \
             -s "Ciphersuite is TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384"
 
+# Test for uniqueness of IVs in AEAD ciphersuites
+run_test    "Unique IV in GCM" \
+            "$P_SRV exchanges=20 debug_level=4" \
+            "$P_CLI exchanges=20 debug_level=4 force_ciphersuite=TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384" \
+            0 \
+            -u "IV used" \
+            -U "IV used"
+
 # Tests for rc4 option
 
 requires_config_enabled MBEDTLS_REMOVE_ARC4_CIPHERSUITES
diff --git a/tests/suites/test_suite_x509write.function b/tests/suites/test_suite_x509write.function
index c3773ba..5120837 100644
--- a/tests/suites/test_suite_x509write.function
+++ b/tests/suites/test_suite_x509write.function
@@ -52,6 +52,10 @@
     TEST_ASSERT( olen >= pem_len - 1 );
     TEST_ASSERT( memcmp( buf, check_buf, pem_len - 1 ) == 0 );
 
+    ret = mbedtls_x509write_csr_der( &req, buf, pem_len / 2,
+                            rnd_pseudo_rand, &rnd_info );
+    TEST_ASSERT( ret == MBEDTLS_ERR_ASN1_BUF_TOO_SMALL );
+
 exit:
     mbedtls_x509write_csr_free( &req );
     mbedtls_pk_free( &key );
@@ -125,6 +129,10 @@
     TEST_ASSERT( olen >= pem_len - 1 );
     TEST_ASSERT( memcmp( buf, check_buf, pem_len - 1 ) == 0 );
 
+    ret = mbedtls_x509write_crt_der( &crt, buf, pem_len / 2,
+                            rnd_pseudo_rand, &rnd_info );
+    TEST_ASSERT( ret == MBEDTLS_ERR_ASN1_BUF_TOO_SMALL );
+
 exit:
     mbedtls_x509write_crt_free( &crt );
     mbedtls_pk_free( &issuer_key );