1 /* This file is distributed under the following terms: 2 3 * Copyright 2005-2014 Colin Percival. All rights reserved. 4 * Copyright 2014 Sean Kelly. All rights reserved. 5 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 16 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 18 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 19 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 20 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 21 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 23 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 24 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 25 * SUCH DAMAGE. 26 */ 27 28 #include <assert.h> 29 #include <stdint.h> 30 #include <string.h> 31 #include <ByteOrder.h> 32 #include "pbkdf2.h" 33 34 /* Function which does the zeroing. */ 35 static void 36 insecure_memzero_func(volatile void * buf, size_t len) 37 { 38 volatile uint8_t * _buf = (volatile uint8_t *)buf; 39 size_t i; 40 41 for (i = 0; i < len; i++) 42 _buf[i] = 0; 43 } 44 45 /* Pointer to memory-zeroing function. */ 46 void (* volatile insecure_memzero_ptr)(volatile void *, size_t) = 47 insecure_memzero_func; 48 49 /** 50 * HMAC_SHA256_Init(ctx, K, Klen): 51 * Initialize the HMAC-SHA256 context ${ctx} with ${Klen} bytes of key from 52 * ${K}. 53 */ 54 void 55 HMAC_SHA256_Init(HMAC_SHA256_CTX * ctx, const void * _K, size_t Klen) 56 { 57 uint8_t pad[64]; 58 uint8_t khash[32]; 59 const uint8_t * K = (const uint8_t *)_K; 60 size_t i; 61 62 /* If Klen > 64, the key is really SHA256(K). */ 63 if (Klen > 64) { 64 ctx->ictx.Init(); 65 ctx->ictx.Update(K, Klen); 66 memcpy(khash, ctx->ictx.Digest(), 32); 67 K = khash; 68 Klen = 32; 69 } 70 71 /* Inner SHA256 operation is SHA256(K xor [block of 0x36] || data). */ 72 ctx->ictx.Init(); 73 memset(pad, 0x36, 64); 74 for (i = 0; i < Klen; i++) 75 pad[i] ^= K[i]; 76 ctx->ictx.Update(pad, 64); 77 78 /* Outer SHA256 operation is SHA256(K xor [block of 0x5c] || hash). */ 79 ctx->octx.Init(); 80 memset(pad, 0x5c, 64); 81 for (i = 0; i < Klen; i++) 82 pad[i] ^= K[i]; 83 ctx->octx.Update(pad, 64); 84 85 /* Clean the stack. */ 86 insecure_memzero(khash, 32); 87 insecure_memzero(pad, 64); 88 } 89 90 /** 91 * HMAC_SHA256_Update(ctx, in, len): 92 * Input ${len} bytes from ${in} into the HMAC-SHA256 context ${ctx}. 93 */ 94 void 95 HMAC_SHA256_Update(HMAC_SHA256_CTX * ctx, const void * in, size_t len) 96 { 97 98 /* Feed data to the inner SHA256 operation. */ 99 ctx->ictx.Update(in, len); 100 } 101 102 /** 103 * HMAC_SHA256_Final(digest, ctx): 104 * Output the HMAC-SHA256 of the data input to the context ${ctx} into the 105 * buffer ${digest}. 106 */ 107 void 108 HMAC_SHA256_Final(uint8_t digest[32], HMAC_SHA256_CTX * ctx) 109 { 110 uint8_t ihash[32]; 111 112 /* Finish the inner SHA256 operation. */ 113 memcpy(ihash, ctx->ictx.Digest(), 32); 114 115 /* Feed the inner hash to the outer SHA256 operation. */ 116 ctx->octx.Update(ihash, 32); 117 118 /* Finish the outer SHA256 operation. */ 119 memcpy(digest, ctx->octx.Digest(), 32); 120 121 /* Clean the stack. */ 122 insecure_memzero(ihash, 32); 123 } 124 125 /** 126 * PBKDF2_SHA256(passwd, passwdlen, salt, saltlen, c, buf, dkLen): 127 * Compute PBKDF2(passwd, salt, c, dkLen) using HMAC-SHA256 as the PRF, and 128 * write the output to buf. The value dkLen must be at most 32 * (2^32 - 1). 129 */ 130 void 131 PBKDF2_SHA256(const uint8_t * passwd, size_t passwdlen, const uint8_t * salt, 132 size_t saltlen, uint64_t c, uint8_t * buf, size_t dkLen) 133 { 134 HMAC_SHA256_CTX PShctx, hctx; 135 size_t i; 136 uint32_t ivec; 137 uint8_t U[32]; 138 uint8_t T[32]; 139 uint64_t j; 140 int k; 141 size_t clen; 142 143 /* Sanity-check. */ 144 assert(dkLen <= 32 * (size_t)(UINT32_MAX)); 145 146 /* Compute HMAC state after processing P and S. */ 147 HMAC_SHA256_Init(&PShctx, passwd, passwdlen); 148 HMAC_SHA256_Update(&PShctx, salt, saltlen); 149 150 /* Iterate through the blocks. */ 151 for (i = 0; i * 32 < dkLen; i++) { 152 /* Generate INT(i + 1). */ 153 ivec = B_HOST_TO_BENDIAN_INT32((uint32_t)(i + 1)); 154 155 /* Compute U_1 = PRF(P, S || INT(i)). */ 156 memcpy(&hctx, &PShctx, sizeof(HMAC_SHA256_CTX)); 157 HMAC_SHA256_Update(&hctx, &ivec, 4); 158 HMAC_SHA256_Final(U, &hctx); 159 160 /* T_i = U_1 ... */ 161 memcpy(T, U, 32); 162 163 for (j = 2; j <= c; j++) { 164 /* Compute U_j. */ 165 HMAC_SHA256_Init(&hctx, passwd, passwdlen); 166 HMAC_SHA256_Update(&hctx, U, 32); 167 HMAC_SHA256_Final(U, &hctx); 168 169 /* ... xor U_j ... */ 170 for (k = 0; k < 32; k++) 171 T[k] ^= U[k]; 172 } 173 174 /* Copy as many bytes as necessary into buf. */ 175 clen = dkLen - i * 32; 176 if (clen > 32) 177 clen = 32; 178 memcpy(&buf[i * 32], T, clen); 179 } 180 181 /* Clean PShctx, since we never called _Final on it. */ 182 insecure_memzero(&PShctx, sizeof(HMAC_SHA256_CTX)); 183 } 184