diff options
author | Nikos Mavrogiannopoulos <nmav@redhat.com> | 2014-04-18 15:55:37 +0200 |
---|---|---|
committer | Nikos Mavrogiannopoulos <nmav@redhat.com> | 2014-04-18 16:24:19 +0200 |
commit | 5bbd3cbf5fa469998debea7aa8b3096be52aeedc (patch) | |
tree | 2eac9ead7393498e83df85e3a0cea7a2323b9461 /lib | |
parent | c1f2fe5c56da2f4fb6d61b4f8f0b117e5e6f8962 (diff) | |
download | gnutls-5bbd3cbf5fa469998debea7aa8b3096be52aeedc.tar.gz |
Use a harder to optimize out memset().
Diffstat (limited to 'lib')
-rw-r--r-- | lib/Makefile.am | 5 | ||||
-rw-r--r-- | lib/gnutls_mem.c | 10 | ||||
-rw-r--r-- | lib/gnutls_mem.h | 6 | ||||
-rw-r--r-- | lib/safe-memset.c | 52 |
4 files changed, 58 insertions, 15 deletions
diff --git a/lib/Makefile.am b/lib/Makefile.am index 817db30488..e39c7c45bf 100644 --- a/lib/Makefile.am +++ b/lib/Makefile.am @@ -81,7 +81,8 @@ COBJECTS = gnutls_range.c gnutls_record.c \ gnutls_rsa_export.c gnutls_helper.c gnutls_supplemental.c \ random.c crypto-api.c gnutls_privkey.c gnutls_pcert.c \ gnutls_pubkey.c locks.c gnutls_dtls.c system_override.c \ - crypto-backend.c verify-tofu.c pin.c tpm.c fips.c + crypto-backend.c verify-tofu.c pin.c tpm.c fips.c \ + safe-memset.c if ENABLE_SELF_CHECKS COBJECTS += crypto-selftests.c crypto-selftests-pk.c @@ -109,7 +110,7 @@ HFILES = abstract_int.h debug.h gnutls_compress.h gnutls_cipher.h \ gnutls_srp.h auth/srp.h auth/srp_passwd.h \ gnutls_helper.h gnutls_supplemental.h crypto.h random.h system.h\ locks.h gnutls_mbuffers.h gnutls_ecc.h pin.h fips.h \ - priority_options.h + priority_options.h safe-memset.h if ENABLE_PKCS11 HFILES += pkcs11_int.h diff --git a/lib/gnutls_mem.c b/lib/gnutls_mem.c index 01638745c3..b82c392bbf 100644 --- a/lib/gnutls_mem.c +++ b/lib/gnutls_mem.c @@ -82,16 +82,6 @@ char *_gnutls_strdup(const char *str) return ret; } -void _gnutls_bzero(void *mem, size_t size) -{ - /* The reason we use that function instead of directly - * calling memset is to prevent the compiler - * optimizing out certain calls that may look - * pointless to him, but needed to erase - * private keys. */ - memset(mem, 0, size); -} - #if 0 /* don't use them. They are included for documentation. */ diff --git a/lib/gnutls_mem.h b/lib/gnutls_mem.h index 2dc4200a35..1f1da609cd 100644 --- a/lib/gnutls_mem.h +++ b/lib/gnutls_mem.h @@ -37,14 +37,14 @@ svoid *gnutls_secure_calloc(size_t nmemb, size_t size); void *_gnutls_calloc(size_t nmemb, size_t size); char *_gnutls_strdup(const char *); -void _gnutls_bzero(void *v, size_t n); - #define zrelease_mpi_key(mpi) if (*mpi!=NULL) { \ _gnutls_mpi_clear(*mpi); \ _gnutls_mpi_release(mpi); \ } -#define zeroize_key(x, size) _gnutls_bzero(x, size) +void _gnutls_safe_memset(void *data, int c, size_t size); + +#define zeroize_key(x, size) _gnutls_safe_memset(x, 0, size) #define zeroize_temp_key zeroize_key #define zrelease_temp_mpi_key zrelease_mpi_key diff --git a/lib/safe-memset.c b/lib/safe-memset.c new file mode 100644 index 0000000000..2cf2cb8cd6 --- /dev/null +++ b/lib/safe-memset.c @@ -0,0 +1,52 @@ +/* + * Copyright (C) 2014 Red Hat + * + * This file is part of GnuTLS. + * + * The GnuTLS is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public License + * as published by the Free Software Foundation; either version 2.1 of + * the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/> + * + */ + +#ifdef TEST_SAFE_MEMSET +# include <string.h> +#else +# include <gnutls_int.h> +#endif + +/* This is based on a nice trick for safe memset, + * sent by David Jacobson in the openssl-dev mailing list. + */ + +void _gnutls_safe_memset(void *data, int c, size_t size) +{ + volatile unsigned volatile_zero = 0; + volatile char *vdata = (volatile char*)data; + + do { + memset(data, c, size); + } while(vdata[volatile_zero] != c); +} + +#ifdef TEST_SAFE_MEMSET +int main() +{ + char x[64]; + + safe_memset(x, 0, sizeof(x)); + + return 0; + +} + +#endif |