]> Git Repo - linux.git/commitdiff
Merge tag 'random_for_linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tytso...
authorLinus Torvalds <[email protected]>
Fri, 24 Oct 2014 19:33:32 +0000 (12:33 -0700)
committerLinus Torvalds <[email protected]>
Fri, 24 Oct 2014 19:33:32 +0000 (12:33 -0700)
Pull /dev/random updates from Ted Ts'o:
 "This adds a memzero_explicit() call which is guaranteed not to be
  optimized away by GCC.  This is important when we are wiping
  cryptographically sensitive material"

* tag 'random_for_linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tytso/random:
  crypto: memzero_explicit - make sure to clear out sensitive data
  random: add and use memzero_explicit() for clearing data

1  2 
crypto/sha256_generic.c
crypto/sha512_generic.c
drivers/char/random.c
include/linux/string.h
lib/string.c

diff --combined crypto/sha256_generic.c
index 0bb5583446993aae173c0b7c015b0db9214f723f,32c5e5ea205a7e71f758a65336ac141158ad977d..65e7b76b057fcddc8f88a04d54b678df245a8c85
@@@ -24,7 -24,6 +24,7 @@@
  #include <linux/types.h>
  #include <crypto/sha.h>
  #include <asm/byteorder.h>
 +#include <asm/unaligned.h>
  
  static inline u32 Ch(u32 x, u32 y, u32 z)
  {
@@@ -43,7 -42,7 +43,7 @@@ static inline u32 Maj(u32 x, u32 y, u3
  
  static inline void LOAD_OP(int I, u32 *W, const u8 *input)
  {
 -      W[I] = __be32_to_cpu( ((__be32*)(input))[I] );
 +      W[I] = get_unaligned_be32((__u32 *)input + I);
  }
  
  static inline void BLEND_OP(int I, u32 *W)
@@@ -211,10 -210,9 +211,9 @@@ static void sha256_transform(u32 *state
  
        /* clear any sensitive info... */
        a = b = c = d = e = f = g = h = t1 = t2 = 0;
-       memset(W, 0, 64 * sizeof(u32));
+       memzero_explicit(W, 64 * sizeof(u32));
  }
  
  static int sha224_init(struct shash_desc *desc)
  {
        struct sha256_state *sctx = shash_desc_ctx(desc);
@@@ -317,7 -315,7 +316,7 @@@ static int sha224_final(struct shash_de
        sha256_final(desc, D);
  
        memcpy(hash, D, SHA224_DIGEST_SIZE);
-       memset(D, 0, SHA256_DIGEST_SIZE);
+       memzero_explicit(D, SHA256_DIGEST_SIZE);
  
        return 0;
  }
diff --combined crypto/sha512_generic.c
index 6dde57dc511bab6c0068837356c7992f47b298cf,04d295a8bc08b15592040731b5f59f40b7d7014d..95db67197cd99dd1fd0cd538311f6e3f2202e7f3
@@@ -20,7 -20,6 +20,7 @@@
  #include <crypto/sha.h>
  #include <linux/percpu.h>
  #include <asm/byteorder.h>
 +#include <asm/unaligned.h>
  
  static inline u64 Ch(u64 x, u64 y, u64 z)
  {
@@@ -69,7 -68,7 +69,7 @@@ static const u64 sha512_K[80] = 
  
  static inline void LOAD_OP(int I, u64 *W, const u8 *input)
  {
 -      W[I] = __be64_to_cpu( ((__be64*)(input))[I] );
 +      W[I] = get_unaligned_be64((__u64 *)input + I);
  }
  
  static inline void BLEND_OP(int I, u64 *W)
@@@ -239,7 -238,7 +239,7 @@@ static int sha384_final(struct shash_de
        sha512_final(desc, D);
  
        memcpy(hash, D, 48);
-       memset(D, 0, 64);
+       memzero_explicit(D, 64);
  
        return 0;
  }
diff --combined drivers/char/random.c
index 82759cef904332cbe6800d4be9c4e08aa420f19c,8c86a95203a058814e80a6879a3236db0ec90c65..04645c09fe5e5eee7f6699c451e9e4f6f8368958
@@@ -874,7 -874,7 +874,7 @@@ static __u32 get_reg(struct fast_pool *
  void add_interrupt_randomness(int irq, int irq_flags)
  {
        struct entropy_store    *r;
 -      struct fast_pool        *fast_pool = &__get_cpu_var(irq_randomness);
 +      struct fast_pool        *fast_pool = this_cpu_ptr(&irq_randomness);
        struct pt_regs          *regs = get_irq_regs();
        unsigned long           now = jiffies;
        cycles_t                cycles = random_get_entropy();
@@@ -1106,7 -1106,7 +1106,7 @@@ static void extract_buf(struct entropy_
        __mix_pool_bytes(r, hash.w, sizeof(hash.w));
        spin_unlock_irqrestore(&r->lock, flags);
  
-       memset(workspace, 0, sizeof(workspace));
+       memzero_explicit(workspace, sizeof(workspace));
  
        /*
         * In case the hash function has some recognizable output
        hash.w[2] ^= rol32(hash.w[2], 16);
  
        memcpy(out, &hash, EXTRACT_SIZE);
-       memset(&hash, 0, sizeof(hash));
+       memzero_explicit(&hash, sizeof(hash));
  }
  
  /*
@@@ -1175,7 -1175,7 +1175,7 @@@ static ssize_t extract_entropy(struct e
        }
  
        /* Wipe data just returned from memory */
-       memset(tmp, 0, sizeof(tmp));
+       memzero_explicit(tmp, sizeof(tmp));
  
        return ret;
  }
@@@ -1218,7 -1218,7 +1218,7 @@@ static ssize_t extract_entropy_user(str
        }
  
        /* Wipe data just returned from memory */
-       memset(tmp, 0, sizeof(tmp));
+       memzero_explicit(tmp, sizeof(tmp));
  
        return ret;
  }
diff --combined include/linux/string.h
index e6edfe51575a6f5a452e937376add0afdb7c5d48,3b42b3732da655a969a1b3d6d316e266311f47c9..2e22a2e58f3af56018c0e68cda2603211ecc3aca
@@@ -41,7 -41,7 +41,7 @@@ extern int strcmp(const char *,const ch
  extern int strncmp(const char *,const char *,__kernel_size_t);
  #endif
  #ifndef __HAVE_ARCH_STRNICMP
 -extern int strnicmp(const char *, const char *, __kernel_size_t);
 +#define strnicmp strncasecmp
  #endif
  #ifndef __HAVE_ARCH_STRCASECMP
  extern int strcasecmp(const char *s1, const char *s2);
@@@ -132,7 -132,7 +132,7 @@@ int bprintf(u32 *bin_buf, size_t size, 
  #endif
  
  extern ssize_t memory_read_from_buffer(void *to, size_t count, loff_t *ppos,
-                       const void *from, size_t available);
+                                      const void *from, size_t available);
  
  /**
   * strstarts - does @str start with @prefix?
@@@ -144,7 -144,8 +144,8 @@@ static inline bool strstarts(const cha
        return strncmp(str, prefix, strlen(prefix)) == 0;
  }
  
- extern size_t memweight(const void *ptr, size_t bytes);
+ size_t memweight(const void *ptr, size_t bytes);
+ void memzero_explicit(void *s, size_t count);
  
  /**
   * kbasename - return the last part of a pathname.
diff --combined lib/string.c
index 2fc20aa06f848fcebd8aa30d238942f5ec399690,3a3120452a1d51d5247b298cb8cc56f64e38f7b8..10063300b83009dfcdc08988d640fc191481dde5
  #include <linux/bug.h>
  #include <linux/errno.h>
  
 -#ifndef __HAVE_ARCH_STRNICMP
 +#ifndef __HAVE_ARCH_STRNCASECMP
  /**
 - * strnicmp - Case insensitive, length-limited string comparison
 + * strncasecmp - Case insensitive, length-limited string comparison
   * @s1: One string
   * @s2: The other string
   * @len: the maximum number of characters to compare
   */
 -int strnicmp(const char *s1, const char *s2, size_t len)
 +int strncasecmp(const char *s1, const char *s2, size_t len)
  {
        /* Yes, Virginia, it had better be unsigned */
        unsigned char c1, c2;
        } while (--len);
        return (int)c1 - (int)c2;
  }
 +EXPORT_SYMBOL(strncasecmp);
 +#endif
 +#ifndef __HAVE_ARCH_STRNICMP
 +#undef strnicmp
 +int strnicmp(const char *s1, const char *s2, size_t len)
 +{
 +      return strncasecmp(s1, s2, len);
 +}
  EXPORT_SYMBOL(strnicmp);
  #endif
  
@@@ -81,6 -73,20 +81,6 @@@ int strcasecmp(const char *s1, const ch
  EXPORT_SYMBOL(strcasecmp);
  #endif
  
 -#ifndef __HAVE_ARCH_STRNCASECMP
 -int strncasecmp(const char *s1, const char *s2, size_t n)
 -{
 -      int c1, c2;
 -
 -      do {
 -              c1 = tolower(*s1++);
 -              c2 = tolower(*s2++);
 -      } while ((--n > 0) && c1 == c2 && c1 != 0);
 -      return c1 - c2;
 -}
 -EXPORT_SYMBOL(strncasecmp);
 -#endif
 -
  #ifndef __HAVE_ARCH_STRCPY
  /**
   * strcpy - Copy a %NUL terminated string
@@@ -598,6 -604,22 +598,22 @@@ void *memset(void *s, int c, size_t cou
  EXPORT_SYMBOL(memset);
  #endif
  
+ /**
+  * memzero_explicit - Fill a region of memory (e.g. sensitive
+  *                  keying data) with 0s.
+  * @s: Pointer to the start of the area.
+  * @count: The size of the area.
+  *
+  * memzero_explicit() doesn't need an arch-specific version as
+  * it just invokes the one of memset() implicitly.
+  */
+ void memzero_explicit(void *s, size_t count)
+ {
+       memset(s, 0, count);
+       OPTIMIZER_HIDE_VAR(s);
+ }
+ EXPORT_SYMBOL(memzero_explicit);
  #ifndef __HAVE_ARCH_MEMCPY
  /**
   * memcpy - Copy one area of memory to another
@@@ -801,9 -823,9 +817,9 @@@ void *memchr_inv(const void *start, in
                return check_bytes8(start, value, bytes);
  
        value64 = value;
 -#if defined(ARCH_HAS_FAST_MULTIPLIER) && BITS_PER_LONG == 64
 +#if defined(CONFIG_ARCH_HAS_FAST_MULTIPLIER) && BITS_PER_LONG == 64
        value64 *= 0x0101010101010101;
 -#elif defined(ARCH_HAS_FAST_MULTIPLIER)
 +#elif defined(CONFIG_ARCH_HAS_FAST_MULTIPLIER)
        value64 *= 0x01010101;
        value64 |= value64 << 32;
  #else
This page took 0.087354 seconds and 4 git commands to generate.