13#if defined(__x86_64__) || defined(__amd64__) || defined(__i386__)
15namespace sha256_sse4 {
16void Transform(uint32_t *s,
const uint8_t *chunk,
size_t blocks);
34void Transform(uint32_t *s,
const uint8_t *chunk,
size_t blocks);
41 inline uint32_t
Ch(uint32_t x, uint32_t y, uint32_t z) {
42 return z ^ (x & (y ^ z));
44 inline uint32_t
Maj(uint32_t x, uint32_t y, uint32_t z) {
45 return (x & y) | (z & (x | y));
47 inline uint32_t
Sigma0(uint32_t x) {
48 return (x >> 2 | x << 30) ^ (x >> 13 | x << 19) ^ (x >> 22 | x << 10);
50 inline uint32_t
Sigma1(uint32_t x) {
51 return (x >> 6 | x << 26) ^ (x >> 11 | x << 21) ^ (x >> 25 | x << 7);
53 inline uint32_t
sigma0(uint32_t x) {
54 return (x >> 7 | x << 25) ^ (x >> 18 | x << 14) ^ (x >> 3);
56 inline uint32_t
sigma1(uint32_t x) {
57 return (x >> 17 | x << 15) ^ (x >> 19 | x << 13) ^ (x >> 10);
61 inline void Round(uint32_t a, uint32_t b, uint32_t c, uint32_t &d,
62 uint32_t e, uint32_t f, uint32_t g, uint32_t &h,
64 uint32_t t1 = h +
Sigma1(e) +
Ch(e, f, g) + k;
71 inline void Initialize(uint32_t *s) {
85 void Transform(uint32_t *s,
const uint8_t *chunk,
size_t blocks) {
87 uint32_t a = s[0], b = s[1], c = s[2], d = s[3], e = s[4], f = s[5],
89 uint32_t w0, w1, w2, w3, w4, w5, w6, w7, w8, w9, w10, w11, w12, w13,
92 Round(a, b, c, d, e, f, g, h,
93 0x428a2f98 + (w0 =
ReadBE32(chunk + 0)));
94 Round(h, a, b, c, d, e, f, g,
95 0x71374491 + (w1 =
ReadBE32(chunk + 4)));
96 Round(g, h, a, b, c, d, e, f,
97 0xb5c0fbcf + (w2 =
ReadBE32(chunk + 8)));
98 Round(f, g, h, a, b, c, d, e,
99 0xe9b5dba5 + (w3 =
ReadBE32(chunk + 12)));
100 Round(e, f, g, h, a, b, c, d,
101 0x3956c25b + (w4 =
ReadBE32(chunk + 16)));
102 Round(d, e, f, g, h, a, b, c,
103 0x59f111f1 + (w5 =
ReadBE32(chunk + 20)));
104 Round(c, d, e, f, g, h, a, b,
105 0x923f82a4 + (w6 =
ReadBE32(chunk + 24)));
106 Round(b, c, d, e, f, g, h, a,
107 0xab1c5ed5 + (w7 =
ReadBE32(chunk + 28)));
108 Round(a, b, c, d, e, f, g, h,
109 0xd807aa98 + (w8 =
ReadBE32(chunk + 32)));
110 Round(h, a, b, c, d, e, f, g,
111 0x12835b01 + (w9 =
ReadBE32(chunk + 36)));
112 Round(g, h, a, b, c, d, e, f,
113 0x243185be + (w10 =
ReadBE32(chunk + 40)));
114 Round(f, g, h, a, b, c, d, e,
115 0x550c7dc3 + (w11 =
ReadBE32(chunk + 44)));
116 Round(e, f, g, h, a, b, c, d,
117 0x72be5d74 + (w12 =
ReadBE32(chunk + 48)));
118 Round(d, e, f, g, h, a, b, c,
119 0x80deb1fe + (w13 =
ReadBE32(chunk + 52)));
120 Round(c, d, e, f, g, h, a, b,
121 0x9bdc06a7 + (w14 =
ReadBE32(chunk + 56)));
122 Round(b, c, d, e, f, g, h, a,
123 0xc19bf174 + (w15 =
ReadBE32(chunk + 60)));
125 Round(a, b, c, d, e, f, g, h,
127 Round(h, a, b, c, d, e, f, g,
129 Round(g, h, a, b, c, d, e, f,
131 Round(f, g, h, a, b, c, d, e,
133 Round(e, f, g, h, a, b, c, d,
135 Round(d, e, f, g, h, a, b, c,
137 Round(c, d, e, f, g, h, a, b,
139 Round(b, c, d, e, f, g, h, a,
141 Round(a, b, c, d, e, f, g, h,
143 Round(h, a, b, c, d, e, f, g,
145 Round(g, h, a, b, c, d, e, f,
147 Round(f, g, h, a, b, c, d, e,
149 Round(e, f, g, h, a, b, c, d,
151 Round(d, e, f, g, h, a, b, c,
153 Round(c, d, e, f, g, h, a, b,
155 Round(b, c, d, e, f, g, h, a,
158 Round(a, b, c, d, e, f, g, h,
160 Round(h, a, b, c, d, e, f, g,
162 Round(g, h, a, b, c, d, e, f,
164 Round(f, g, h, a, b, c, d, e,
166 Round(e, f, g, h, a, b, c, d,
168 Round(d, e, f, g, h, a, b, c,
170 Round(c, d, e, f, g, h, a, b,
172 Round(b, c, d, e, f, g, h, a,
174 Round(a, b, c, d, e, f, g, h,
176 Round(h, a, b, c, d, e, f, g,
178 Round(g, h, a, b, c, d, e, f,
180 Round(f, g, h, a, b, c, d, e,
182 Round(e, f, g, h, a, b, c, d,
184 Round(d, e, f, g, h, a, b, c,
186 Round(c, d, e, f, g, h, a, b,
188 Round(b, c, d, e, f, g, h, a,
191 Round(a, b, c, d, e, f, g, h,
193 Round(h, a, b, c, d, e, f, g,
195 Round(g, h, a, b, c, d, e, f,
197 Round(f, g, h, a, b, c, d, e,
199 Round(e, f, g, h, a, b, c, d,
201 Round(d, e, f, g, h, a, b, c,
203 Round(c, d, e, f, g, h, a, b,
205 Round(b, c, d, e, f, g, h, a,
207 Round(a, b, c, d, e, f, g, h,
209 Round(h, a, b, c, d, e, f, g,
211 Round(g, h, a, b, c, d, e, f,
213 Round(f, g, h, a, b, c, d, e,
215 Round(e, f, g, h, a, b, c, d,
217 Round(d, e, f, g, h, a, b, c,
219 Round(c, d, e, f, g, h, a, b,
221 Round(b, c, d, e, f, g, h, a,
236 void TransformD64(uint8_t *out,
const uint8_t *in) {
238 uint32_t a = 0x6a09e667ul;
239 uint32_t b = 0xbb67ae85ul;
240 uint32_t c = 0x3c6ef372ul;
241 uint32_t d = 0xa54ff53aul;
242 uint32_t e = 0x510e527ful;
243 uint32_t f = 0x9b05688cul;
244 uint32_t g = 0x1f83d9abul;
245 uint32_t h = 0x5be0cd19ul;
247 uint32_t w0, w1, w2, w3, w4, w5, w6, w7, w8, w9, w10, w11, w12, w13,
250 Round(a, b, c, d, e, f, g, h, 0x428a2f98ul + (w0 =
ReadBE32(in + 0)));
251 Round(h, a, b, c, d, e, f, g, 0x71374491ul + (w1 =
ReadBE32(in + 4)));
252 Round(g, h, a, b, c, d, e, f, 0xb5c0fbcful + (w2 =
ReadBE32(in + 8)));
253 Round(f, g, h, a, b, c, d, e, 0xe9b5dba5ul + (w3 =
ReadBE32(in + 12)));
254 Round(e, f, g, h, a, b, c, d, 0x3956c25bul + (w4 =
ReadBE32(in + 16)));
255 Round(d, e, f, g, h, a, b, c, 0x59f111f1ul + (w5 =
ReadBE32(in + 20)));
256 Round(c, d, e, f, g, h, a, b, 0x923f82a4ul + (w6 =
ReadBE32(in + 24)));
257 Round(b, c, d, e, f, g, h, a, 0xab1c5ed5ul + (w7 =
ReadBE32(in + 28)));
258 Round(a, b, c, d, e, f, g, h, 0xd807aa98ul + (w8 =
ReadBE32(in + 32)));
259 Round(h, a, b, c, d, e, f, g, 0x12835b01ul + (w9 =
ReadBE32(in + 36)));
260 Round(g, h, a, b, c, d, e, f, 0x243185beul + (w10 =
ReadBE32(in + 40)));
261 Round(f, g, h, a, b, c, d, e, 0x550c7dc3ul + (w11 =
ReadBE32(in + 44)));
262 Round(e, f, g, h, a, b, c, d, 0x72be5d74ul + (w12 =
ReadBE32(in + 48)));
263 Round(d, e, f, g, h, a, b, c, 0x80deb1feul + (w13 =
ReadBE32(in + 52)));
264 Round(c, d, e, f, g, h, a, b, 0x9bdc06a7ul + (w14 =
ReadBE32(in + 56)));
265 Round(b, c, d, e, f, g, h, a, 0xc19bf174ul + (w15 =
ReadBE32(in + 60)));
266 Round(a, b, c, d, e, f, g, h,
268 Round(h, a, b, c, d, e, f, g,
270 Round(g, h, a, b, c, d, e, f,
272 Round(f, g, h, a, b, c, d, e,
274 Round(e, f, g, h, a, b, c, d,
276 Round(d, e, f, g, h, a, b, c,
278 Round(c, d, e, f, g, h, a, b,
280 Round(b, c, d, e, f, g, h, a,
282 Round(a, b, c, d, e, f, g, h,
284 Round(h, a, b, c, d, e, f, g,
286 Round(g, h, a, b, c, d, e, f,
288 Round(f, g, h, a, b, c, d, e,
290 Round(e, f, g, h, a, b, c, d,
291 0xc6e00bf3ul + (w12 +=
sigma1(w10) + w5 +
sigma0(w13)));
292 Round(d, e, f, g, h, a, b, c,
293 0xd5a79147ul + (w13 +=
sigma1(w11) + w6 +
sigma0(w14)));
294 Round(c, d, e, f, g, h, a, b,
295 0x06ca6351ul + (w14 +=
sigma1(w12) + w7 +
sigma0(w15)));
296 Round(b, c, d, e, f, g, h, a,
298 Round(a, b, c, d, e, f, g, h,
300 Round(h, a, b, c, d, e, f, g,
302 Round(g, h, a, b, c, d, e, f,
304 Round(f, g, h, a, b, c, d, e,
306 Round(e, f, g, h, a, b, c, d,
308 Round(d, e, f, g, h, a, b, c,
310 Round(c, d, e, f, g, h, a, b,
312 Round(b, c, d, e, f, g, h, a,
314 Round(a, b, c, d, e, f, g, h,
316 Round(h, a, b, c, d, e, f, g,
318 Round(g, h, a, b, c, d, e, f,
320 Round(f, g, h, a, b, c, d, e,
322 Round(e, f, g, h, a, b, c, d,
323 0xd192e819ul + (w12 +=
sigma1(w10) + w5 +
sigma0(w13)));
324 Round(d, e, f, g, h, a, b, c,
325 0xd6990624ul + (w13 +=
sigma1(w11) + w6 +
sigma0(w14)));
326 Round(c, d, e, f, g, h, a, b,
327 0xf40e3585ul + (w14 +=
sigma1(w12) + w7 +
sigma0(w15)));
328 Round(b, c, d, e, f, g, h, a,
330 Round(a, b, c, d, e, f, g, h,
332 Round(h, a, b, c, d, e, f, g,
334 Round(g, h, a, b, c, d, e, f,
336 Round(f, g, h, a, b, c, d, e,
338 Round(e, f, g, h, a, b, c, d,
340 Round(d, e, f, g, h, a, b, c,
342 Round(c, d, e, f, g, h, a, b,
344 Round(b, c, d, e, f, g, h, a,
346 Round(a, b, c, d, e, f, g, h,
348 Round(h, a, b, c, d, e, f, g,
350 Round(g, h, a, b, c, d, e, f,
352 Round(f, g, h, a, b, c, d, e,
354 Round(e, f, g, h, a, b, c, d,
355 0x90befffaul + (w12 +=
sigma1(w10) + w5 +
sigma0(w13)));
356 Round(d, e, f, g, h, a, b, c,
357 0xa4506cebul + (w13 +=
sigma1(w11) + w6 +
sigma0(w14)));
358 Round(c, d, e, f, g, h, a, b,
360 Round(b, c, d, e, f, g, h, a,
372 uint32_t t0 = a, t1 = b, t2 = c, t3 = d, t4 = e, t5 = f, t6 = g, t7 = h;
375 Round(a, b, c, d, e, f, g, h, 0xc28a2f98ul);
376 Round(h, a, b, c, d, e, f, g, 0x71374491ul);
377 Round(g, h, a, b, c, d, e, f, 0xb5c0fbcful);
378 Round(f, g, h, a, b, c, d, e, 0xe9b5dba5ul);
379 Round(e, f, g, h, a, b, c, d, 0x3956c25bul);
380 Round(d, e, f, g, h, a, b, c, 0x59f111f1ul);
381 Round(c, d, e, f, g, h, a, b, 0x923f82a4ul);
382 Round(b, c, d, e, f, g, h, a, 0xab1c5ed5ul);
383 Round(a, b, c, d, e, f, g, h, 0xd807aa98ul);
384 Round(h, a, b, c, d, e, f, g, 0x12835b01ul);
385 Round(g, h, a, b, c, d, e, f, 0x243185beul);
386 Round(f, g, h, a, b, c, d, e, 0x550c7dc3ul);
387 Round(e, f, g, h, a, b, c, d, 0x72be5d74ul);
388 Round(d, e, f, g, h, a, b, c, 0x80deb1feul);
389 Round(c, d, e, f, g, h, a, b, 0x9bdc06a7ul);
390 Round(b, c, d, e, f, g, h, a, 0xc19bf374ul);
391 Round(a, b, c, d, e, f, g, h, 0x649b69c1ul);
392 Round(h, a, b, c, d, e, f, g, 0xf0fe4786ul);
393 Round(g, h, a, b, c, d, e, f, 0x0fe1edc6ul);
394 Round(f, g, h, a, b, c, d, e, 0x240cf254ul);
395 Round(e, f, g, h, a, b, c, d, 0x4fe9346ful);
396 Round(d, e, f, g, h, a, b, c, 0x6cc984beul);
397 Round(c, d, e, f, g, h, a, b, 0x61b9411eul);
398 Round(b, c, d, e, f, g, h, a, 0x16f988faul);
399 Round(a, b, c, d, e, f, g, h, 0xf2c65152ul);
400 Round(h, a, b, c, d, e, f, g, 0xa88e5a6dul);
401 Round(g, h, a, b, c, d, e, f, 0xb019fc65ul);
402 Round(f, g, h, a, b, c, d, e, 0xb9d99ec7ul);
403 Round(e, f, g, h, a, b, c, d, 0x9a1231c3ul);
404 Round(d, e, f, g, h, a, b, c, 0xe70eeaa0ul);
405 Round(c, d, e, f, g, h, a, b, 0xfdb1232bul);
406 Round(b, c, d, e, f, g, h, a, 0xc7353eb0ul);
407 Round(a, b, c, d, e, f, g, h, 0x3069bad5ul);
408 Round(h, a, b, c, d, e, f, g, 0xcb976d5ful);
409 Round(g, h, a, b, c, d, e, f, 0x5a0f118ful);
410 Round(f, g, h, a, b, c, d, e, 0xdc1eeefdul);
411 Round(e, f, g, h, a, b, c, d, 0x0a35b689ul);
412 Round(d, e, f, g, h, a, b, c, 0xde0b7a04ul);
413 Round(c, d, e, f, g, h, a, b, 0x58f4ca9dul);
414 Round(b, c, d, e, f, g, h, a, 0xe15d5b16ul);
415 Round(a, b, c, d, e, f, g, h, 0x007f3e86ul);
416 Round(h, a, b, c, d, e, f, g, 0x37088980ul);
417 Round(g, h, a, b, c, d, e, f, 0xa507ea32ul);
418 Round(f, g, h, a, b, c, d, e, 0x6fab9537ul);
419 Round(e, f, g, h, a, b, c, d, 0x17406110ul);
420 Round(d, e, f, g, h, a, b, c, 0x0d8cd6f1ul);
421 Round(c, d, e, f, g, h, a, b, 0xcdaa3b6dul);
422 Round(b, c, d, e, f, g, h, a, 0xc0bbbe37ul);
423 Round(a, b, c, d, e, f, g, h, 0x83613bdaul);
424 Round(h, a, b, c, d, e, f, g, 0xdb48a363ul);
425 Round(g, h, a, b, c, d, e, f, 0x0b02e931ul);
426 Round(f, g, h, a, b, c, d, e, 0x6fd15ca7ul);
427 Round(e, f, g, h, a, b, c, d, 0x521afacaul);
428 Round(d, e, f, g, h, a, b, c, 0x31338431ul);
429 Round(c, d, e, f, g, h, a, b, 0x6ed41a95ul);
430 Round(b, c, d, e, f, g, h, a, 0x6d437890ul);
431 Round(a, b, c, d, e, f, g, h, 0xc39c91f2ul);
432 Round(h, a, b, c, d, e, f, g, 0x9eccabbdul);
433 Round(g, h, a, b, c, d, e, f, 0xb5c9a0e6ul);
434 Round(f, g, h, a, b, c, d, e, 0x532fb63cul);
435 Round(e, f, g, h, a, b, c, d, 0xd2c741c6ul);
436 Round(d, e, f, g, h, a, b, c, 0x07237ea3ul);
437 Round(c, d, e, f, g, h, a, b, 0xa4954b68ul);
438 Round(b, c, d, e, f, g, h, a, 0x4c191d76ul);
459 Round(a, b, c, d, e, f, g, h, 0x428a2f98ul + w0);
460 Round(h, a, b, c, d, e, f, g, 0x71374491ul + w1);
461 Round(g, h, a, b, c, d, e, f, 0xb5c0fbcful + w2);
462 Round(f, g, h, a, b, c, d, e, 0xe9b5dba5ul + w3);
463 Round(e, f, g, h, a, b, c, d, 0x3956c25bul + w4);
464 Round(d, e, f, g, h, a, b, c, 0x59f111f1ul + w5);
465 Round(c, d, e, f, g, h, a, b, 0x923f82a4ul + w6);
466 Round(b, c, d, e, f, g, h, a, 0xab1c5ed5ul + w7);
467 Round(a, b, c, d, e, f, g, h, 0x5807aa98ul);
468 Round(h, a, b, c, d, e, f, g, 0x12835b01ul);
469 Round(g, h, a, b, c, d, e, f, 0x243185beul);
470 Round(f, g, h, a, b, c, d, e, 0x550c7dc3ul);
471 Round(e, f, g, h, a, b, c, d, 0x72be5d74ul);
472 Round(d, e, f, g, h, a, b, c, 0x80deb1feul);
473 Round(c, d, e, f, g, h, a, b, 0x9bdc06a7ul);
474 Round(b, c, d, e, f, g, h, a, 0xc19bf274ul);
475 Round(a, b, c, d, e, f, g, h, 0xe49b69c1ul + (w0 +=
sigma0(w1)));
476 Round(h, a, b, c, d, e, f, g,
477 0xefbe4786ul + (w1 += 0xa00000ul +
sigma0(w2)));
478 Round(g, h, a, b, c, d, e, f,
480 Round(f, g, h, a, b, c, d, e,
482 Round(e, f, g, h, a, b, c, d,
484 Round(d, e, f, g, h, a, b, c,
486 Round(c, d, e, f, g, h, a, b,
487 0x5cb0a9dcul + (w6 +=
sigma1(w4) + 0x100ul +
sigma0(w7)));
488 Round(b, c, d, e, f, g, h, a,
489 0x76f988daul + (w7 +=
sigma1(w5) + w0 + 0x11002000ul));
490 Round(a, b, c, d, e, f, g, h,
491 0x983e5152ul + (w8 = 0x80000000ul +
sigma1(w6) + w1));
492 Round(h, a, b, c, d, e, f, g, 0xa831c66dul + (w9 =
sigma1(w7) + w2));
493 Round(g, h, a, b, c, d, e, f, 0xb00327c8ul + (w10 =
sigma1(w8) + w3));
494 Round(f, g, h, a, b, c, d, e, 0xbf597fc7ul + (w11 =
sigma1(w9) + w4));
495 Round(e, f, g, h, a, b, c, d, 0xc6e00bf3ul + (w12 =
sigma1(w10) + w5));
496 Round(d, e, f, g, h, a, b, c, 0xd5a79147ul + (w13 =
sigma1(w11) + w6));
497 Round(c, d, e, f, g, h, a, b,
498 0x06ca6351ul + (w14 =
sigma1(w12) + w7 + 0x400022ul));
499 Round(b, c, d, e, f, g, h, a,
500 0x14292967ul + (w15 = 0x100ul +
sigma1(w13) + w8 +
sigma0(w0)));
501 Round(a, b, c, d, e, f, g, h,
503 Round(h, a, b, c, d, e, f, g,
505 Round(g, h, a, b, c, d, e, f,
507 Round(f, g, h, a, b, c, d, e,
509 Round(e, f, g, h, a, b, c, d,
511 Round(d, e, f, g, h, a, b, c,
513 Round(c, d, e, f, g, h, a, b,
515 Round(b, c, d, e, f, g, h, a,
517 Round(a, b, c, d, e, f, g, h,
519 Round(h, a, b, c, d, e, f, g,
521 Round(g, h, a, b, c, d, e, f,
523 Round(f, g, h, a, b, c, d, e,
525 Round(e, f, g, h, a, b, c, d,
526 0xd192e819ul + (w12 +=
sigma1(w10) + w5 +
sigma0(w13)));
527 Round(d, e, f, g, h, a, b, c,
528 0xd6990624ul + (w13 +=
sigma1(w11) + w6 +
sigma0(w14)));
529 Round(c, d, e, f, g, h, a, b,
530 0xf40e3585ul + (w14 +=
sigma1(w12) + w7 +
sigma0(w15)));
531 Round(b, c, d, e, f, g, h, a,
533 Round(a, b, c, d, e, f, g, h,
535 Round(h, a, b, c, d, e, f, g,
537 Round(g, h, a, b, c, d, e, f,
539 Round(f, g, h, a, b, c, d, e,
541 Round(e, f, g, h, a, b, c, d,
543 Round(d, e, f, g, h, a, b, c,
545 Round(c, d, e, f, g, h, a, b,
547 Round(b, c, d, e, f, g, h, a,
549 Round(a, b, c, d, e, f, g, h,
551 Round(h, a, b, c, d, e, f, g,
553 Round(g, h, a, b, c, d, e, f,
555 Round(f, g, h, a, b, c, d, e,
557 Round(e, f, g, h, a, b, c, d,
558 0x90befffaul + (w12 +=
sigma1(w10) + w5 +
sigma0(w13)));
559 Round(d, e, f, g, h, a, b, c,
560 0xa4506cebul + (w13 +=
sigma1(w11) + w6 +
sigma0(w14)));
561 Round(c, d, e, f, g, h, a, b,
563 Round(b, c, d, e, f, g, h, a,
579typedef void (*TransformType)(uint32_t *,
const uint8_t *, size_t);
580typedef void (*TransformD64Type)(uint8_t *,
const uint8_t *);
582template <TransformType tr>
583void TransformD64Wrapper(uint8_t *out,
const uint8_t *in) {
585 static const uint8_t padding1[64] = {
586 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
587 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
588 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0};
589 uint8_t buffer2[64] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
590 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
591 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
592 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0};
593 sha256::Initialize(s);
604 sha256::Initialize(s);
617TransformD64Type TransformD64 = sha256::TransformD64;
618TransformD64Type TransformD64_2way =
nullptr;
619TransformD64Type TransformD64_4way =
nullptr;
620TransformD64Type TransformD64_8way =
nullptr;
624 static const uint32_t
init[8] = {0x6a09e667ul, 0xbb67ae85ul, 0x3c6ef372ul,
625 0xa54ff53aul, 0x510e527ful, 0x9b05688cul,
626 0x1f83d9abul, 0x5be0cd19ul};
628 static const uint8_t data[641] =
630 "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do "
631 "eiusmod tempor incididunt ut labore et dolore magna aliqua. Et m"
632 "olestie ac feugiat sed lectus vestibulum mattis ullamcorper. Mor"
633 "bi blandit cursus risus at ultrices mi tempus imperdiet nulla. N"
634 "unc congue nisi vita suscipit tellus mauris. Imperdiet proin fer"
635 "mentum leo vel orci. Massa tempor nec feugiat nisl pretium fusce"
636 " id velit. Telus in metus vulputate eu scelerisque felis. Mi tem"
637 "pus imperdiet nulla malesuada pellentesque. Tristique magna sit.";
640 static const uint32_t result[9][8] = {
641 {0x6a09e667ul, 0xbb67ae85ul, 0x3c6ef372ul, 0xa54ff53aul, 0x510e527ful,
642 0x9b05688cul, 0x1f83d9abul, 0x5be0cd19ul},
643 {0x91f8ec6bul, 0x4da10fe3ul, 0x1c9c292cul, 0x45e18185ul, 0x435cc111ul,
644 0x3ca26f09ul, 0xeb954caeul, 0x402a7069ul},
645 {0xcabea5acul, 0x374fb97cul, 0x182ad996ul, 0x7bd69cbful, 0x450ff900ul,
646 0xc1d2be8aul, 0x6a41d505ul, 0xe6212dc3ul},
647 {0xbcff09d6ul, 0x3e76f36eul, 0x3ecb2501ul, 0x78866e97ul, 0xe1c1e2fdul,
648 0x32f4eafful, 0x8aa6c4e5ul, 0xdfc024bcul},
649 {0xa08c5d94ul, 0x0a862f93ul, 0x6b7f2f40ul, 0x8f9fae76ul, 0x6d40439ful,
650 0x79dcee0cul, 0x3e39ff3aul, 0xdc3bdbb1ul},
651 {0x216a0895ul, 0x9f1a3662ul, 0xe99946f9ul, 0x87ba4364ul, 0x0fb5db2cul,
652 0x12bed3d3ul, 0x6689c0c7ul, 0x292f1b04ul},
653 {0xca3067f8ul, 0xbc8c2656ul, 0x37cb7e0dul, 0x9b6b8b0ful, 0x46dc380bul,
654 0xf1287f57ul, 0xc42e4b23ul, 0x3fefe94dul},
655 {0x3e4c4039ul, 0xbb6fca8cul, 0x6f27d2f7ul, 0x301e44a4ul, 0x8352ba14ul,
656 0x5769ce37ul, 0x48a1155ful, 0xc0e1c4c6ul},
657 {0xfe2fa9ddul, 0x69d0862bul, 0x1ae0db23ul, 0x471f9244ul, 0xf55c0145ul,
658 0xc30f9c3bul, 0x40a84ea0ul, 0x5b8a266cul},
662 static const uint8_t result_d64[256] = {
663 0x09, 0x3a, 0xc4, 0xd0, 0x0f, 0xf7, 0x57, 0xe1, 0x72, 0x85, 0x79, 0x42,
664 0xfe, 0xe7, 0xe0, 0xa0, 0xfc, 0x52, 0xd7, 0xdb, 0x07, 0x63, 0x45, 0xfb,
665 0x53, 0x14, 0x7d, 0x17, 0x22, 0x86, 0xf0, 0x52, 0x48, 0xb6, 0x11, 0x9e,
666 0x6e, 0x48, 0x81, 0x6d, 0xcc, 0x57, 0x1f, 0xb2, 0x97, 0xa8, 0xd5, 0x25,
667 0x9b, 0x82, 0xaa, 0x89, 0xe2, 0xfd, 0x2d, 0x56, 0xe8, 0x28, 0x83, 0x0b,
668 0xe2, 0xfa, 0x53, 0xb7, 0xd6, 0x6b, 0x07, 0x85, 0x83, 0xb0, 0x10, 0xa2,
669 0xf5, 0x51, 0x3c, 0xf9, 0x60, 0x03, 0xab, 0x45, 0x6c, 0x15, 0x6e, 0xef,
670 0xb5, 0xac, 0x3e, 0x6c, 0xdf, 0xb4, 0x92, 0x22, 0x2d, 0xce, 0xbf, 0x3e,
671 0xe9, 0xe5, 0xf6, 0x29, 0x0e, 0x01, 0x4f, 0xd2, 0xd4, 0x45, 0x65, 0xb3,
672 0xbb, 0xf2, 0x4c, 0x16, 0x37, 0x50, 0x3c, 0x6e, 0x49, 0x8c, 0x5a, 0x89,
673 0x2b, 0x1b, 0xab, 0xc4, 0x37, 0xd1, 0x46, 0xe9, 0x3d, 0x0e, 0x85, 0xa2,
674 0x50, 0x73, 0xa1, 0x5e, 0x54, 0x37, 0xd7, 0x94, 0x17, 0x56, 0xc2, 0xd8,
675 0xe5, 0x9f, 0xed, 0x4e, 0xae, 0x15, 0x42, 0x06, 0x0d, 0x74, 0x74, 0x5e,
676 0x24, 0x30, 0xce, 0xd1, 0x9e, 0x50, 0xa3, 0x9a, 0xb8, 0xf0, 0x4a, 0x57,
677 0x69, 0x78, 0x67, 0x12, 0x84, 0x58, 0xbe, 0xc7, 0x36, 0xaa, 0xee, 0x7c,
678 0x64, 0xa3, 0x76, 0xec, 0xff, 0x55, 0x41, 0x00, 0x2a, 0x44, 0x68, 0x4d,
679 0xb6, 0x53, 0x9e, 0x1c, 0x95, 0xb7, 0xca, 0xdc, 0x7f, 0x7d, 0x74, 0x27,
680 0x5c, 0x8e, 0xa6, 0x84, 0xb5, 0xac, 0x87, 0xa9, 0xf3, 0xff, 0x75, 0xf2,
681 0x34, 0xcd, 0x1a, 0x3b, 0x82, 0x2c, 0x2b, 0x4e, 0x6a, 0x46, 0x30, 0xa6,
682 0x89, 0x86, 0x23, 0xac, 0xf8, 0xa5, 0x15, 0xe9, 0x0a, 0xaa, 0x1e, 0x9a,
683 0xd7, 0x93, 0x6b, 0x28, 0xe4, 0x3b, 0xfd, 0x59, 0xc6, 0xed, 0x7c, 0x5f,
684 0xa5, 0x41, 0xcb, 0x51};
687 for (
size_t i = 0; i <= 8; ++i) {
691 if (!std::equal(state, state + 8, result[i])) {
699 TransformD64(out, data + 1);
700 if (!std::equal(out, out + 32, result_d64)) {
706 if (TransformD64_2way) {
708 TransformD64_2way(out, data + 1);
709 if (!std::equal(out, out + 64, result_d64)) {
715 if (TransformD64_4way) {
717 TransformD64_4way(out, data + 1);
718 if (!std::equal(out, out + 128, result_d64)) {
724 if (TransformD64_8way) {
726 TransformD64_8way(out, data + 1);
727 if (!std::equal(out, out + 256, result_d64)) {
735#if defined(USE_ASM) && \
736 (defined(__x86_64__) || defined(__amd64__) || defined(__i386__))
740 __asm__(
"xgetbv" :
"=a"(a),
"=d"(d) :
"c"(0));
747 std::string ret =
"standard";
748#if defined(USE_ASM) && defined(HAVE_GETCPUID)
749 bool have_sse4 =
false;
750 bool have_xsave =
false;
751 bool have_avx =
false;
752 bool have_avx2 =
false;
753 bool have_shani =
false;
754 bool enabled_avx =
false;
764 uint32_t eax, ebx, ecx, edx;
765 GetCPUID(1, 0, eax, ebx, ecx, edx);
766 have_sse4 = (ecx >> 19) & 1;
767 have_xsave = (ecx >> 27) & 1;
768 have_avx = (ecx >> 28) & 1;
769 if (have_xsave && have_avx) {
770 enabled_avx = AVXEnabled();
773 GetCPUID(7, 0, eax, ebx, ecx, edx);
774 have_avx2 = (ebx >> 5) & 1;
775 have_shani = (ebx >> 29) & 1;
778#if defined(ENABLE_SHANI) && !defined(BUILD_BITCOIN_INTERNAL)
781 TransformD64 = TransformD64Wrapper<sha256_shani::Transform>;
783 ret =
"shani(1way,2way)";
790#if defined(__x86_64__) || defined(__amd64__)
792 TransformD64 = TransformD64Wrapper<sha256_sse4::Transform>;
795#if defined(ENABLE_SSE41) && !defined(BUILD_BITCOIN_INTERNAL)
797 ret +=
",sse41(4way)";
801#if defined(ENABLE_AVX2) && !defined(BUILD_BITCOIN_INTERNAL)
802 if (have_avx2 && have_avx && enabled_avx) {
804 ret +=
",avx2(8way)";
816 sha256::Initialize(
s);
820 const uint8_t *end = data + len;
821 size_t bufsize =
bytes % 64;
822 if (bufsize && bufsize + len >= 64) {
824 memcpy(
buf + bufsize, data, 64 - bufsize);
825 bytes += 64 - bufsize;
826 data += 64 - bufsize;
830 if (end - data >= 64) {
831 size_t blocks = (end - data) / 64;
834 bytes += 64 * blocks;
838 memcpy(
buf + bufsize, data, end - data);
845 static const uint8_t pad[64] = {0x80};
862 sha256::Initialize(
s);
866void SHA256D64(uint8_t *out,
const uint8_t *in,
size_t blocks) {
867 if (TransformD64_8way) {
868 while (blocks >= 8) {
869 TransformD64_8way(out, in);
875 if (TransformD64_4way) {
876 while (blocks >= 4) {
877 TransformD64_4way(out, in);
883 if (TransformD64_2way) {
884 while (blocks >= 2) {
885 TransformD64_2way(out, in);
892 TransformD64(out, in);
A hasher class for SHA-256.
CSHA256 & Write(const uint8_t *data, size_t len)
void Finalize(uint8_t hash[OUTPUT_SIZE])
static void WriteBE64(uint8_t *ptr, uint64_t x)
static void WriteBE32(uint8_t *ptr, uint32_t x)
static uint32_t ReadBE32(const uint8_t *ptr)
#define Round(a, b, c, d, e, f, g, h, k, w)
void Transform(uint32_t *s, const uint8_t *chunk, size_t blocks)
Internal SHA-256 implementation.
void Transform_8way(uint8_t *out, const uint8_t *in)
void Transform_2way(uint8_t *out, const uint8_t *in)
void Transform_4way(uint8_t *out, const uint8_t *in)
void SHA256D64(uint8_t *out, const uint8_t *in, size_t blocks)
Compute multiple double-SHA256's of 64-byte blobs.
std::string SHA256AutoDetect()
Autodetect the best available SHA256 implementation.