Merge pull request #7173 from daverodgman/zeroize-platform

Use platform-provided secure zeroization
This commit is contained in:
Dave Rodgman 2023-03-06 09:16:12 +00:00 committed by GitHub
commit 4693fd9e9e
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 107 additions and 5 deletions

View file

@ -0,0 +1,3 @@
Security
* Use platform-provided secure zeroization function where possible, such as
explicit_bzero().

View file

@ -26,6 +26,11 @@
#define _POSIX_C_SOURCE 200112L
#endif
#if !defined(_GNU_SOURCE)
/* Clang requires this to get support for explicit_bzero */
#define _GNU_SOURCE
#endif
#include "common.h"
#include "mbedtls/platform_util.h"
@ -33,11 +38,31 @@
#include "mbedtls/threading.h"
#include <stddef.h>
#ifndef __STDC_WANT_LIB_EXT1__
#define __STDC_WANT_LIB_EXT1__ 1 /* Ask for the C11 gmtime_s() and memset_s() if available */
#endif
#include <string.h>
#if defined(_WIN32)
#include <windows.h>
#endif
// Detect platforms known to support explicit_bzero()
#if defined(__GLIBC__) && (__GLIBC__ >= 2) && (__GLIBC_MINOR__ >= 25)
#define MBEDTLS_PLATFORM_HAS_EXPLICIT_BZERO 1
#elif defined(__FreeBSD__) && (__FreeBSD_version >= 1100037)
#define MBEDTLS_PLATFORM_HAS_EXPLICIT_BZERO 1
#endif
#if !defined(MBEDTLS_PLATFORM_ZEROIZE_ALT)
/*
* This implementation should never be optimized out by the compiler
* Where possible, we try to detect the presence of a platform-provided
* secure memset, such as explicit_bzero(), that is safe against being optimized
* out, and use that.
*
* For other platforms, we provide an implementation that aims not to be
* optimized out by the compiler.
*
* This implementation for mbedtls_platform_zeroize() was inspired from Colin
* Percival's blog article at:
@ -52,30 +77,40 @@
* (refer to http://www.daemonology.net/blog/2014-09-05-erratum.html for
* details), optimizations of the following form are still possible:
*
* if( memset_func != memset )
* memset_func( buf, 0, len );
* if (memset_func != memset)
* memset_func(buf, 0, len);
*
* Note that it is extremely difficult to guarantee that
* mbedtls_platform_zeroize() will not be optimized out by aggressive compilers
* the memset() call will not be optimized out by aggressive compilers
* in a portable way. For this reason, Mbed TLS also provides the configuration
* option MBEDTLS_PLATFORM_ZEROIZE_ALT, which allows users to configure
* mbedtls_platform_zeroize() to use a suitable implementation for their
* platform and needs.
*/
#if !defined(MBEDTLS_PLATFORM_HAS_EXPLICIT_BZERO) && !defined(__STDC_LIB_EXT1__) \
&& !defined(_WIN32)
static void *(*const volatile memset_func)(void *, int, size_t) = memset;
#endif
void mbedtls_platform_zeroize(void *buf, size_t len)
{
MBEDTLS_INTERNAL_VALIDATE(len == 0 || buf != NULL);
if (len > 0) {
#if defined(MBEDTLS_PLATFORM_HAS_EXPLICIT_BZERO)
explicit_bzero(buf, len);
#elif defined(__STDC_LIB_EXT1__)
memset_s(buf, len, 0, len);
#elif defined(_WIN32)
SecureZeroMemory(buf, len);
#else
memset_func(buf, 0, len);
#endif
}
}
#endif /* MBEDTLS_PLATFORM_ZEROIZE_ALT */
#if defined(MBEDTLS_HAVE_TIME_DATE) && !defined(MBEDTLS_PLATFORM_GMTIME_R_ALT)
#define __STDC_WANT_LIB_EXT1__ 1 /* Ask for the C11 gmtime_s() if it's available */
#include <time.h>
#if !defined(_WIN32) && (defined(unix) || \
defined(__unix) || defined(__unix__) || (defined(__APPLE__) && \

View file

@ -0,0 +1,23 @@
Zeroize len 0, null
mbedtls_platform_zeroize:0:1
Zeroize len 0, non-null
mbedtls_platform_zeroize:0:0
Zeroize len 1
mbedtls_platform_zeroize:1:0
Zeroize len 4
mbedtls_platform_zeroize:1:0
Zeroize len 5
mbedtls_platform_zeroize:1:0
Zeroize len 32
mbedtls_platform_zeroize:32:0
Zeroize len 127
mbedtls_platform_zeroize:127:0
Zeroize len 128
mbedtls_platform_zeroize:128:0

View file

@ -0,0 +1,41 @@
/* BEGIN_HEADER */
#include "mbedtls/platform_util.h"
/* END_HEADER */
/* BEGIN_CASE */
void mbedtls_platform_zeroize(int len, int null)
{
char buf[130];
char *p = NULL;
TEST_ASSERT(len <= 128);
/* Write sentinel values */
buf[0] = 2;
buf[len + 1] = 2;
/* Write non-zero content */
if (!null) {
p = &buf[1];
for (int i = 0; i < len; i++) {
p[i] = 1;
}
}
/* Check content is non-zero */
TEST_EQUAL(buf[0], 2);
for (int i = 0; i < len; i++) {
TEST_ASSERT(p[i] == 1);
}
TEST_EQUAL(buf[len + 1], 2);
mbedtls_platform_zeroize(p, len);
/* Check content is zero and sentinels un-changed */
TEST_EQUAL(buf[0], 2);
for (int i = 0; i < len; i++) {
TEST_ASSERT(p[i] == 0);
}
TEST_EQUAL(buf[len + 1], 2);
}
/* END_CASE */