1 /*-
2 * Copyright 2005 Colin Percival
3 * Copyright (c) 2015 Allan Jude <allanjude@FreeBSD.org>
4 * Copyright 2021, 2022 Alexander Peslyak
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
17 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
20 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
24 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26 * SUCH DAMAGE.
27 */
28
29 #include "crypt-port.h"
30
31 #if INCLUDE_sha512crypt
32
33 #include "alg-sha512.h"
34 #include "byteorder.h"
35
36 /* SHA512 round constants. */
37 static const uint64_t K[80] = {
38 0x428a2f98d728ae22ULL, 0x7137449123ef65cdULL,
39 0xb5c0fbcfec4d3b2fULL, 0xe9b5dba58189dbbcULL,
40 0x3956c25bf348b538ULL, 0x59f111f1b605d019ULL,
41 0x923f82a4af194f9bULL, 0xab1c5ed5da6d8118ULL,
42 0xd807aa98a3030242ULL, 0x12835b0145706fbeULL,
43 0x243185be4ee4b28cULL, 0x550c7dc3d5ffb4e2ULL,
44 0x72be5d74f27b896fULL, 0x80deb1fe3b1696b1ULL,
45 0x9bdc06a725c71235ULL, 0xc19bf174cf692694ULL,
46 0xe49b69c19ef14ad2ULL, 0xefbe4786384f25e3ULL,
47 0x0fc19dc68b8cd5b5ULL, 0x240ca1cc77ac9c65ULL,
48 0x2de92c6f592b0275ULL, 0x4a7484aa6ea6e483ULL,
49 0x5cb0a9dcbd41fbd4ULL, 0x76f988da831153b5ULL,
50 0x983e5152ee66dfabULL, 0xa831c66d2db43210ULL,
51 0xb00327c898fb213fULL, 0xbf597fc7beef0ee4ULL,
52 0xc6e00bf33da88fc2ULL, 0xd5a79147930aa725ULL,
53 0x06ca6351e003826fULL, 0x142929670a0e6e70ULL,
54 0x27b70a8546d22ffcULL, 0x2e1b21385c26c926ULL,
55 0x4d2c6dfc5ac42aedULL, 0x53380d139d95b3dfULL,
56 0x650a73548baf63deULL, 0x766a0abb3c77b2a8ULL,
57 0x81c2c92e47edaee6ULL, 0x92722c851482353bULL,
58 0xa2bfe8a14cf10364ULL, 0xa81a664bbc423001ULL,
59 0xc24b8b70d0f89791ULL, 0xc76c51a30654be30ULL,
60 0xd192e819d6ef5218ULL, 0xd69906245565a910ULL,
61 0xf40e35855771202aULL, 0x106aa07032bbd1b8ULL,
62 0x19a4c116b8d2d0c8ULL, 0x1e376c085141ab53ULL,
63 0x2748774cdf8eeb99ULL, 0x34b0bcb5e19b48a8ULL,
64 0x391c0cb3c5c95a63ULL, 0x4ed8aa4ae3418acbULL,
65 0x5b9cca4f7763e373ULL, 0x682e6ff3d6b2b8a3ULL,
66 0x748f82ee5defb2fcULL, 0x78a5636f43172f60ULL,
67 0x84c87814a1f0ab72ULL, 0x8cc702081a6439ecULL,
68 0x90befffa23631e28ULL, 0xa4506cebde82bde9ULL,
69 0xbef9a3f7b2c67915ULL, 0xc67178f2e372532bULL,
70 0xca273eceea26619cULL, 0xd186b8c721c0c207ULL,
71 0xeada7dd6cde0eb1eULL, 0xf57d4f7fee6ed178ULL,
72 0x06f067aa72176fbaULL, 0x0a637dc5a2c898a6ULL,
73 0x113f9804bef90daeULL, 0x1b710b35131c471bULL,
74 0x28db77f523047d84ULL, 0x32caab7b40c72493ULL,
75 0x3c9ebe0a15c9bebcULL, 0x431d67c49c100d4cULL,
76 0x4cc5d4becb3e42b6ULL, 0x597f299cfc657e2aULL,
77 0x5fcb6fab3ad6faecULL, 0x6c44198c4a475817ULL
78 };
79
80 /* Elementary functions used by SHA512 */
81 #define Ch(x, y, z) ((x & (y ^ z)) ^ z)
82 #if 1 /* Explicit caching/reuse of common subexpression between rounds */
83 #define Maj(x, y, z) (y ^ ((x_xor_y = x ^ y) & y_xor_z))
84 #else /* Let the compiler cache/reuse or not */
85 #define Maj(x, y, z) (y ^ ((x ^ y) & (y ^ z)))
86 #endif
87 #define SHR(x, n) (x >> n)
88 #define ROTR(x, n) ((x >> n) | (x << (64 - n)))
89 #define S0(x) (ROTR(x, 28) ^ ROTR(x, 34) ^ ROTR(x, 39))
90 #define S1(x) (ROTR(x, 14) ^ ROTR(x, 18) ^ ROTR(x, 41))
91 #define s0(x) (ROTR(x, 1) ^ ROTR(x, 8) ^ SHR(x, 7))
92 #define s1(x) (ROTR(x, 19) ^ ROTR(x, 61) ^ SHR(x, 6))
93
94 /* SHA512 round function */
95 #define RND(a, b, c, d, e, f, g, h, k) \
96 h += S1(e) + Ch(e, f, g) + k; \
97 d += h; \
98 h += S0(a) + Maj(a, b, c); \
99 y_xor_z = x_xor_y;
100
101 /* Adjusted round function for rotating state */
102 #define RNDr(S, W, i, ii) \
103 RND(S[(80 - i) % 8], S[(81 - i) % 8], \
104 S[(82 - i) % 8], S[(83 - i) % 8], \
105 S[(84 - i) % 8], S[(85 - i) % 8], \
106 S[(86 - i) % 8], S[(87 - i) % 8], \
107 W[i + ii] + K[i + ii])
108
109 /* Message schedule computation */
110 #define MSCH(W, ii, i) \
111 W[i + ii + 16] = s1(W[i + ii + 14]) + W[i + ii + 9] + s0(W[i + ii + 1]) + W[i + ii]
112
113 /*
114 * SHA512 block compression function. The 512-bit state is transformed via
115 * the 512-bit input block to produce a new state.
116 */
117 static void
118 SHA512_Transform(uint64_t * state, const unsigned char block[SHA512_BLOCK_LENGTH])
119 {
120 uint64_t W[80];
121 uint64_t S[8];
122 int i;
123
124 /* 1. Prepare the first part of the message schedule W. */
125 be64dec_vect(W, block, SHA512_BLOCK_LENGTH/8);
126
127 /* 2. Initialize working variables. */
128 memcpy(S, state, SHA512_DIGEST_LENGTH);
129
130 /* 3. Mix. */
131 for (i = 0; i < 80; i += 16) {
132 uint64_t x_xor_y, y_xor_z = S[(65 - i) % 8] ^ S[(66 - i) % 8];
133 RNDr(S, W, 0, i);
134 RNDr(S, W, 1, i);
135 RNDr(S, W, 2, i);
136 RNDr(S, W, 3, i);
137 RNDr(S, W, 4, i);
138 RNDr(S, W, 5, i);
139 RNDr(S, W, 6, i);
140 RNDr(S, W, 7, i);
141 RNDr(S, W, 8, i);
142 RNDr(S, W, 9, i);
143 RNDr(S, W, 10, i);
144 RNDr(S, W, 11, i);
145 RNDr(S, W, 12, i);
146 RNDr(S, W, 13, i);
147 RNDr(S, W, 14, i);
148 RNDr(S, W, 15, i);
149
150 if (i == 64)
151 break;
152 MSCH(W, 0, i);
153 MSCH(W, 1, i);
154 MSCH(W, 2, i);
155 MSCH(W, 3, i);
156 MSCH(W, 4, i);
157 MSCH(W, 5, i);
158 MSCH(W, 6, i);
159 MSCH(W, 7, i);
160 MSCH(W, 8, i);
161 MSCH(W, 9, i);
162 MSCH(W, 10, i);
163 MSCH(W, 11, i);
164 MSCH(W, 12, i);
165 MSCH(W, 13, i);
166 MSCH(W, 14, i);
167 MSCH(W, 15, i);
168 }
169
170 /* 4. Mix local working variables into global state */
171 for (i = 0; i < 8; i++)
172 state[i] += S[i];
173 }
174
175 static const unsigned char PAD[SHA512_BLOCK_LENGTH] = {
176 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
177 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
178 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
179 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
180 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
181 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
182 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
183 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
184 };
185
186 /* Add padding and terminating bit-count. */
187 static void
188 SHA512_Pad(SHA512_CTX * ctx)
189 {
190 size_t r;
191
192 /* Figure out how many bytes we have buffered. */
193 r = (ctx->count[1] >> 3) & 0x7f;
194
195 /* Pad to 112 mod 128, transforming if we finish a block en route. */
196 if (r < 112) {
197 /* Pad to 112 mod 128. */
198 memcpy(&ctx->buf[r], PAD, 112 - r);
199 } else {
200 /* Finish the current block and mix. */
201 memcpy(&ctx->buf[r], PAD, 128 - r);
202 SHA512_Transform(ctx->state, ctx->buf);
203
204 /* The start of the final block is all zeroes. */
205 memset(&ctx->buf[0], 0, 112);
206 }
207
208 /* Add the terminating bit-count. */
209 be64enc_vect(&ctx->buf[112], ctx->count, 2);
210
211 /* Mix in the final block. */
212 SHA512_Transform(ctx->state, ctx->buf);
213 }
214
215 /* SHA-512 initialization. Begins a SHA-512 operation. */
216 void
217 SHA512_Init(SHA512_CTX * ctx)
218 {
219
220 /* Zero bits processed so far */
221 ctx->count[0] = ctx->count[1] = 0;
222
223 /* Magic initialization constants */
224 ctx->state[0] = 0x6a09e667f3bcc908ULL;
225 ctx->state[1] = 0xbb67ae8584caa73bULL;
226 ctx->state[2] = 0x3c6ef372fe94f82bULL;
227 ctx->state[3] = 0xa54ff53a5f1d36f1ULL;
228 ctx->state[4] = 0x510e527fade682d1ULL;
229 ctx->state[5] = 0x9b05688c2b3e6c1fULL;
230 ctx->state[6] = 0x1f83d9abfb41bd6bULL;
231 ctx->state[7] = 0x5be0cd19137e2179ULL;
232 }
233
234 /* Add bytes into the hash */
235 void
236 SHA512_Update(SHA512_CTX * ctx, const void *in, size_t len)
237 {
238 uint64_t bitlen[2];
239 size_t r;
240 const unsigned char *src = in;
241
242 /* Number of bytes left in the buffer from previous updates */
243 r = (ctx->count[1] >> 3) & 0x7f;
244
245 /* Convert the length into a number of bits */
246 bitlen[1] = ((uint64_t)len) << 3;
247 bitlen[0] = ((uint64_t)len) >> 61;
248
249 /* Update number of bits */
250 if ((ctx->count[1] += bitlen[1]) < bitlen[1])
251 ctx->count[0]++;
252 ctx->count[0] += bitlen[0];
253
254 /* Handle the case where we don't need to perform any transforms */
255 if (len < SHA512_BLOCK_LENGTH - r) {
256 memcpy(&ctx->buf[r], src, len);
257 return;
258 }
259
260 /* Finish the current block */
261 memcpy(&ctx->buf[r], src, SHA512_BLOCK_LENGTH - r);
262 SHA512_Transform(ctx->state, ctx->buf);
263 src += SHA512_BLOCK_LENGTH - r;
264 len -= SHA512_BLOCK_LENGTH - r;
265
266 /* Perform complete blocks */
267 while (len >= SHA512_BLOCK_LENGTH) {
268 SHA512_Transform(ctx->state, src);
269 src += SHA512_BLOCK_LENGTH;
270 len -= SHA512_BLOCK_LENGTH;
271 }
272
273 /* Copy left over data into buffer */
274 memcpy(ctx->buf, src, len);
275 }
276
277 /*
278 * SHA-512 finalization. Pads the input data, exports the hash value,
279 * and clears the context state.
280 */
281 void
282 SHA512_Final(unsigned char digest[MIN_SIZE(SHA512_DIGEST_LENGTH)],
283 SHA512_CTX *ctx)
284 {
285
286 /* Add padding */
287 SHA512_Pad(ctx);
288
289 /* Write the hash */
290 be64enc_vect(digest, ctx->state, SHA512_DIGEST_LENGTH/8);
291
292 /* Clear the context state */
293 explicit_bzero(ctx, sizeof(*ctx));
294 }
295
296 /**
297 * SHA512_Buf(in, len, digest):
298 * Compute the SHA512 hash of ${len} bytes from ${in} and write it to ${digest}.
299 */
300 void
301 SHA512_Buf(const void * in, size_t len,
302 unsigned char digest[MIN_SIZE(SHA512_DIGEST_LENGTH)])
303 {
304 SHA512_CTX ctx;
305
306 SHA512_Init(&ctx);
307 SHA512_Update(&ctx, in, len);
308 SHA512_Final(digest, &ctx);
309 }
310
311 #endif