"Fossies" - the Fresh Open Source Software Archive

Member "src/Crypto/Sha2Small.c" (10 Oct 2018, 5636 Bytes) of package /windows/misc/VeraCrypt_1.23-Hotfix-2_Source.zip:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "Sha2Small.c" see the Fossies "Dox" file reference documentation.

    1 /* LibTomCrypt, modular cryptographic library -- Tom St Denis
    2  *
    3  * LibTomCrypt is a library that provides various cryptographic
    4  * algorithms in a highly modular and flexible manner.
    5  *
    6  * The library is free for all purposes without any express
    7  * guarantee it works.
    8  *
    9  * Tom St Denis, tomstdenis@gmail.com, http://libtom.org
   10  *
   11  */
   12 
   13 /* Adapted for VeraCrypt */
   14 
   15 #include <memory.h>
   16 #include "Common/Tcdefs.h"
   17 #include "Common/Endian.h"
   18 #include "Sha2Small.h"
   19 
   20 #pragma optimize ("tl", on)
   21 
   22 typedef unsigned __int32 uint32;
   23 typedef unsigned __int8 byte;
   24 
   25 #include <stdlib.h>
   26 #pragma intrinsic(_lrotr)
   27 #define RORc(x,n) _lrotr(x,n)
   28 
   29 /******************************************************************************/
   30 
   31 /*
   32     The K array
   33  */
   34 
   35 static const uint32 K[64] = {
   36     0x428a2f98UL, 0x71374491UL, 0xb5c0fbcfUL, 0xe9b5dba5UL, 0x3956c25bUL,
   37     0x59f111f1UL, 0x923f82a4UL, 0xab1c5ed5UL, 0xd807aa98UL, 0x12835b01UL,
   38     0x243185beUL, 0x550c7dc3UL, 0x72be5d74UL, 0x80deb1feUL, 0x9bdc06a7UL,
   39     0xc19bf174UL, 0xe49b69c1UL, 0xefbe4786UL, 0x0fc19dc6UL, 0x240ca1ccUL,
   40     0x2de92c6fUL, 0x4a7484aaUL, 0x5cb0a9dcUL, 0x76f988daUL, 0x983e5152UL,
   41     0xa831c66dUL, 0xb00327c8UL, 0xbf597fc7UL, 0xc6e00bf3UL, 0xd5a79147UL,
   42     0x06ca6351UL, 0x14292967UL, 0x27b70a85UL, 0x2e1b2138UL, 0x4d2c6dfcUL,
   43     0x53380d13UL, 0x650a7354UL, 0x766a0abbUL, 0x81c2c92eUL, 0x92722c85UL,
   44     0xa2bfe8a1UL, 0xa81a664bUL, 0xc24b8b70UL, 0xc76c51a3UL, 0xd192e819UL,
   45     0xd6990624UL, 0xf40e3585UL, 0x106aa070UL, 0x19a4c116UL, 0x1e376c08UL,
   46     0x2748774cUL, 0x34b0bcb5UL, 0x391c0cb3UL, 0x4ed8aa4aUL, 0x5b9cca4fUL,
   47     0x682e6ff3UL, 0x748f82eeUL, 0x78a5636fUL, 0x84c87814UL, 0x8cc70208UL,
   48     0x90befffaUL, 0xa4506cebUL, 0xbef9a3f7UL, 0xc67178f2UL
   49 };
   50 
   51 /*
   52     Various logical functions
   53  */
   54 #define Ch(x,y,z)           (z ^ (x & (y ^ z)))
   55 #define Maj(x,y,z)      (((x | y) & z) | (x & y))
   56 #define S(x, n)         RORc((x),(n))
   57 #define R(x, n)         ((x)>>(n))
   58 #define Sigma0(x)           (S(x, 2) ^ S(x, 13) ^ S(x, 22))
   59 #define Sigma1(x)           (S(x, 6) ^ S(x, 11) ^ S(x, 25))
   60 #define Gamma0(x)           (S(x, 7) ^ S(x, 18) ^ R(x, 3))
   61 #define Gamma1(x)           (S(x, 17) ^ S(x, 19) ^ R(x, 10))
   62 
   63 #define STORE32H(x, y, i) { \
   64 (y)[i] = (unsigned char)(((x)>>24)); \
   65 (y)[i+1] = (unsigned char)(((x)>>16)); \
   66 (y)[i+2] = (unsigned char)(((x)>>8)); \
   67 (y)[i+3] = (unsigned char)((x)); \
   68 }
   69 
   70 #define LOAD32H(x, y, i) { \
   71 x = ((unsigned long)((y)[i])<<24) | \
   72 ((unsigned long)((y)[i+1])<<16) | \
   73 ((unsigned long)((y)[i+2])<<8)  | \
   74 ((unsigned long)((y)[i+3])); \
   75 }
   76 
   77 /*
   78     compress 512-bits
   79  */
   80 static void sha256_compress(sha256_ctx * ctx, unsigned char *buf)
   81 {
   82 
   83     uint32 S[8], W[64], t0, t1;
   84     uint32 t, w2, w15;
   85     int i;
   86 
   87 /*
   88     copy state into S
   89  */
   90     for (i = 0; i < 8; i++) {
   91         S[i] = ctx->state[i];
   92     }
   93 
   94 /*
   95     copy the state into 512-bits into W[0..15]
   96  */
   97     for (i = 0; i < 16; i++) {
   98         LOAD32H(W[i], buf , (4*i));
   99     }
  100 
  101 /*
  102     fill W[16..63]
  103  */
  104     for (i = 16; i < 64; i++) {
  105         w2 = W[i - 2];
  106         w15 = W[i - 15];
  107         W[i] = Gamma1(w2) + W[i - 7] + Gamma0(w15) + W[i - 16];
  108     }
  109 
  110 /*
  111     Compress
  112  */
  113 
  114 #define RND(a,b,c,d,e,f,g,h,i)                          \
  115     t0 = h + Sigma1(e) + Ch(e, f, g) + K[i] + W[i]; \
  116     t1 = Sigma0(a) + Maj(a, b, c);                      \
  117     d += t0;                                            \
  118     h  = t0 + t1;
  119 
  120     for (i = 0; i < 64; ++i) {
  121         RND(S[0],S[1],S[2],S[3],S[4],S[5],S[6],S[7],i);
  122         t = S[7]; S[7] = S[6]; S[6] = S[5]; S[5] = S[4];
  123         S[4] = S[3]; S[3] = S[2]; S[2] = S[1]; S[1] = S[0]; S[0] = t;
  124     }
  125 
  126 /*
  127     feedback
  128  */
  129     for (i = 0; i < 8; i++) {
  130         ctx->state[i] += S[i];
  131     }
  132 
  133 }
  134 
  135 /*
  136     init the sha256 state
  137  */
  138 VOID_RETURN sha256_begin(sha256_ctx* ctx)
  139 {
  140     ctx->curlen = 0;
  141     ctx->state[0] = 0x6A09E667UL;
  142     ctx->state[1] = 0xBB67AE85UL;
  143     ctx->state[2] = 0x3C6EF372UL;
  144     ctx->state[3] = 0xA54FF53AUL;
  145     ctx->state[4] = 0x510E527FUL;
  146     ctx->state[5] = 0x9B05688CUL;
  147     ctx->state[6] = 0x1F83D9ABUL;
  148     ctx->state[7] = 0x5BE0CD19UL;
  149     ctx->highLength = 0;
  150     ctx->lowLength = 0;
  151 }
  152 
  153 VOID_RETURN sha256_hash(unsigned char* data, unsigned int len, sha256_ctx* ctx)
  154 {
  155     uint32 n;
  156     while (len > 0) {
  157         if (ctx->curlen == 0 && len >= 64) {
  158             sha256_compress(ctx, (unsigned char *)data);
  159 
  160             n = ctx->lowLength + 512;
  161             if (n < ctx->lowLength) {
  162                 ctx->highLength++;
  163             }
  164             ctx->lowLength = n;
  165             data        += 64;
  166             len     -= 64;
  167         } else {
  168             n = min(len, 64 - ctx->curlen);
  169             memcpy(ctx->buf + ctx->curlen, data, (size_t)n);
  170             ctx->curlen += (unsigned int) n;
  171             data            += (unsigned int) n;
  172             len         -= (unsigned int) n;
  173 
  174             if (ctx->curlen == 64) {
  175                 sha256_compress (ctx, ctx->buf);
  176 
  177                 n = ctx->lowLength + 512;
  178                 if (n < ctx->lowLength) {
  179                     ctx->highLength++;
  180                 }
  181                 ctx->lowLength = n;
  182                 ctx->curlen = 0;
  183             }
  184         }
  185     }
  186     return;
  187 }
  188 
  189 VOID_RETURN sha256_end(unsigned char* hval, sha256_ctx* ctx)
  190 {
  191     int i;
  192     uint32  n;
  193 
  194 /*
  195     increase the length of the message
  196  */
  197 
  198     n = ctx->lowLength + (ctx->curlen << 3);
  199     if (n < ctx->lowLength) {
  200         ctx->highLength++;
  201     }
  202     ctx->highLength += (ctx->curlen >> 29);
  203     ctx->lowLength = n;
  204 
  205 /*
  206     append the '1' bit
  207  */
  208     ctx->buf[ctx->curlen++] = (unsigned char)0x80;
  209 
  210 /*
  211     if the length is currently above 56 bytes we append zeros then compress.
  212     Then we can fall back to padding zeros and length encoding like normal.
  213  */
  214     if (ctx->curlen > 56) {
  215         while (ctx->curlen < 64) {
  216             ctx->buf[ctx->curlen++] = (unsigned char)0;
  217         }
  218         sha256_compress(ctx, ctx->buf);
  219         ctx->curlen = 0;
  220     }
  221 
  222 /*
  223     pad upto 56 bytes of zeroes
  224  */
  225     while (ctx->curlen < 56) {
  226         ctx->buf[ctx->curlen++] = (unsigned char)0;
  227     }
  228 
  229 /*
  230     store length
  231  */
  232 
  233     STORE32H(ctx->highLength, ctx->buf, 56);
  234     STORE32H(ctx->lowLength, ctx->buf, 60);
  235 
  236     sha256_compress(ctx, ctx->buf);
  237 
  238 /*
  239     copy output
  240  */
  241     for (i = 0; i < 8; i++) {
  242         STORE32H(ctx->state[i], hval, (4*i));
  243     }
  244 }
  245 
  246 /******************************************************************************/