Home | History | Annotate | Download | only in zfs
      1    789   ahrens /*
      2    789   ahrens  * CDDL HEADER START
      3    789   ahrens  *
      4    789   ahrens  * The contents of this file are subject to the terms of the
      5   5688  bonwick  * Common Development and Distribution License (the "License").
      6   5688  bonwick  * You may not use this file except in compliance with the License.
      7    789   ahrens  *
      8    789   ahrens  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
      9    789   ahrens  * or http://www.opensolaris.org/os/licensing.
     10    789   ahrens  * See the License for the specific language governing permissions
     11    789   ahrens  * and limitations under the License.
     12    789   ahrens  *
     13    789   ahrens  * When distributing Covered Code, include this CDDL HEADER in each
     14    789   ahrens  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
     15    789   ahrens  * If applicable, add the following below this CDDL HEADER, with the
     16    789   ahrens  * fields enclosed by brackets "[]" replaced with your own identifying
     17    789   ahrens  * information: Portions Copyright [yyyy] [name of copyright owner]
     18    789   ahrens  *
     19    789   ahrens  * CDDL HEADER END
     20    789   ahrens  */
     21    789   ahrens /*
     22  10922     Jeff  * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
     23    789   ahrens  * Use is subject to license terms.
     24    789   ahrens  */
     25    789   ahrens 
     26    789   ahrens #include <sys/zfs_context.h>
     27    789   ahrens #include <sys/zio.h>
     28    789   ahrens 
     29    789   ahrens /*
     30   5688  bonwick  * SHA-256 checksum, as specified in FIPS 180-3, available at:
     31   5688  bonwick  * http://csrc.nist.gov/publications/PubsFIPS.html
     32    789   ahrens  *
     33    789   ahrens  * This is a very compact implementation of SHA-256.
     34    789   ahrens  * It is designed to be simple and portable, not to be fast.
     35    789   ahrens  */
     36    789   ahrens 
     37    789   ahrens /*
     38   5688  bonwick  * The literal definitions of Ch() and Maj() according to FIPS 180-3 are:
     39    789   ahrens  *
     40   5688  bonwick  * 	Ch(x, y, z)     (x & y) ^ (~x & z)
     41   5688  bonwick  * 	Maj(x, y, z)    (x & y) ^ (x & z) ^ (y & z)
     42    789   ahrens  *
     43   5688  bonwick  * We use equivalent logical reductions here that require one less op.
     44    789   ahrens  */
     45    789   ahrens #define	Ch(x, y, z)	((z) ^ ((x) & ((y) ^ (z))))
     46    789   ahrens #define	Maj(x, y, z)	(((x) & (y)) ^ ((z) & ((x) ^ (y))))
     47    789   ahrens #define	Rot32(x, s)	(((x) >> s) | ((x) << (32 - s)))
     48    789   ahrens #define	SIGMA0(x)	(Rot32(x, 2) ^ Rot32(x, 13) ^ Rot32(x, 22))
     49    789   ahrens #define	SIGMA1(x)	(Rot32(x, 6) ^ Rot32(x, 11) ^ Rot32(x, 25))
     50    789   ahrens #define	sigma0(x)	(Rot32(x, 7) ^ Rot32(x, 18) ^ ((x) >> 3))
     51    789   ahrens #define	sigma1(x)	(Rot32(x, 17) ^ Rot32(x, 19) ^ ((x) >> 10))
     52    789   ahrens 
     53    789   ahrens static const uint32_t SHA256_K[64] = {
     54    789   ahrens 	0x428a2f98, 0x71374491, 0xb5c0fbcf, 0xe9b5dba5,
     55    789   ahrens 	0x3956c25b, 0x59f111f1, 0x923f82a4, 0xab1c5ed5,
     56    789   ahrens 	0xd807aa98, 0x12835b01, 0x243185be, 0x550c7dc3,
     57    789   ahrens 	0x72be5d74, 0x80deb1fe, 0x9bdc06a7, 0xc19bf174,
     58    789   ahrens 	0xe49b69c1, 0xefbe4786, 0x0fc19dc6, 0x240ca1cc,
     59    789   ahrens 	0x2de92c6f, 0x4a7484aa, 0x5cb0a9dc, 0x76f988da,
     60    789   ahrens 	0x983e5152, 0xa831c66d, 0xb00327c8, 0xbf597fc7,
     61    789   ahrens 	0xc6e00bf3, 0xd5a79147, 0x06ca6351, 0x14292967,
     62    789   ahrens 	0x27b70a85, 0x2e1b2138, 0x4d2c6dfc, 0x53380d13,
     63    789   ahrens 	0x650a7354, 0x766a0abb, 0x81c2c92e, 0x92722c85,
     64    789   ahrens 	0xa2bfe8a1, 0xa81a664b, 0xc24b8b70, 0xc76c51a3,
     65    789   ahrens 	0xd192e819, 0xd6990624, 0xf40e3585, 0x106aa070,
     66    789   ahrens 	0x19a4c116, 0x1e376c08, 0x2748774c, 0x34b0bcb5,
     67    789   ahrens 	0x391c0cb3, 0x4ed8aa4a, 0x5b9cca4f, 0x682e6ff3,
     68    789   ahrens 	0x748f82ee, 0x78a5636f, 0x84c87814, 0x8cc70208,
     69    789   ahrens 	0x90befffa, 0xa4506ceb, 0xbef9a3f7, 0xc67178f2
     70    789   ahrens };
     71    789   ahrens 
     72    789   ahrens static void
     73    789   ahrens SHA256Transform(uint32_t *H, const uint8_t *cp)
     74    789   ahrens {
     75    789   ahrens 	uint32_t a, b, c, d, e, f, g, h, t, T1, T2, W[64];
     76    789   ahrens 
     77    789   ahrens 	for (t = 0; t < 16; t++, cp += 4)
     78    789   ahrens 		W[t] = (cp[0] << 24) | (cp[1] << 16) | (cp[2] << 8) | cp[3];
     79    789   ahrens 
     80    789   ahrens 	for (t = 16; t < 64; t++)
     81    789   ahrens 		W[t] = sigma1(W[t - 2]) + W[t - 7] +
     82    789   ahrens 		    sigma0(W[t - 15]) + W[t - 16];
     83    789   ahrens 
     84    789   ahrens 	a = H[0]; b = H[1]; c = H[2]; d = H[3];
     85    789   ahrens 	e = H[4]; f = H[5]; g = H[6]; h = H[7];
     86    789   ahrens 
     87    789   ahrens 	for (t = 0; t < 64; t++) {
     88    789   ahrens 		T1 = h + SIGMA1(e) + Ch(e, f, g) + SHA256_K[t] + W[t];
     89    789   ahrens 		T2 = SIGMA0(a) + Maj(a, b, c);
     90    789   ahrens 		h = g; g = f; f = e; e = d + T1;
     91    789   ahrens 		d = c; c = b; b = a; a = T1 + T2;
     92    789   ahrens 	}
     93    789   ahrens 
     94    789   ahrens 	H[0] += a; H[1] += b; H[2] += c; H[3] += d;
     95    789   ahrens 	H[4] += e; H[5] += f; H[6] += g; H[7] += h;
     96    789   ahrens }
     97    789   ahrens 
     98    789   ahrens void
     99    789   ahrens zio_checksum_SHA256(const void *buf, uint64_t size, zio_cksum_t *zcp)
    100    789   ahrens {
    101    789   ahrens 	uint32_t H[8] = { 0x6a09e667, 0xbb67ae85, 0x3c6ef372, 0xa54ff53a,
    102    789   ahrens 	    0x510e527f, 0x9b05688c, 0x1f83d9ab, 0x5be0cd19 };
    103    789   ahrens 	uint8_t pad[128];
    104   5688  bonwick 	int i, padsize;
    105    789   ahrens 
    106   5688  bonwick 	for (i = 0; i < (size & ~63ULL); i += 64)
    107    789   ahrens 		SHA256Transform(H, (uint8_t *)buf + i);
    108    789   ahrens 
    109   5688  bonwick 	for (padsize = 0; i < size; i++)
    110   5688  bonwick 		pad[padsize++] = *((uint8_t *)buf + i);
    111    789   ahrens 
    112    789   ahrens 	for (pad[padsize++] = 0x80; (padsize & 63) != 56; padsize++)
    113    789   ahrens 		pad[padsize] = 0;
    114    789   ahrens 
    115   5688  bonwick 	for (i = 56; i >= 0; i -= 8)
    116   5688  bonwick 		pad[padsize++] = (size << 3) >> i;
    117    789   ahrens 
    118    789   ahrens 	for (i = 0; i < padsize; i += 64)
    119    789   ahrens 		SHA256Transform(H, pad + i);
    120    789   ahrens 
    121    789   ahrens 	ZIO_SET_CHECKSUM(zcp,
    122    789   ahrens 	    (uint64_t)H[0] << 32 | H[1],
    123    789   ahrens 	    (uint64_t)H[2] << 32 | H[3],
    124    789   ahrens 	    (uint64_t)H[4] << 32 | H[5],
    125    789   ahrens 	    (uint64_t)H[6] << 32 | H[7]);
    126    789   ahrens }
    127