"Fossies" - the Fresh Open Source Software Archive

Member "tin-2.4.2/libcanlock/src/sha1.c" (11 Mar 2017, 12539 Bytes) of package /linux/misc/tin-2.4.2.tar.xz:


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 "sha1.c" see the Fossies "Dox" file reference documentation and the latest Fossies "Diffs" side-by-side code changes report: 2.4.1_vs_2.4.2.

    1 /**************************** sha1.c ***************************/
    2 /***************** See RFC 6234 for details. *******************/
    3 /* Copyright (c) 2011 IETF Trust and the persons identified as */
    4 /* authors of the code.  All rights reserved.                  */
    5 /* See sha.h for terms of use and redistribution.              */
    6 
    7 /*
    8  *  Description:
    9  *      This file implements the Secure Hash Algorithm SHA-1
   10  *      as defined in the U.S. National Institute of Standards
   11  *      and Technology Federal Information Processing Standards
   12  *      Publication (FIPS PUB) 180-3 published in October 2008
   13  *      and formerly defined in its predecessors, FIPS PUB 180-1
   14  *      and FIP PUB 180-2.
   15  *
   16  *      A combined document showing all algorithms is available at
   17  *              http://csrc.nist.gov/publications/fips/
   18  *                     fips180-3/fips180-3_final.pdf
   19  *
   20  *      The SHA-1 algorithm produces a 160-bit message digest for a
   21  *      given data stream that can serve as a means of providing a
   22  *      "fingerprint" for a message.
   23  *
   24  *  Portability Issues:
   25  *      SHA-1 is defined in terms of 32-bit "words".  This code
   26  *      uses <stdint.h> (included via "sha.h") to define 32- and
   27  *      8-bit unsigned integer types.  If your C compiler does
   28  *      not support 32-bit unsigned integers, this code is not
   29  *      appropriate.
   30  *
   31  *  Caveats:
   32  *      SHA-1 is designed to work with messages less than 2^64 bits
   33  *      long.  This implementation uses SHA1Input() to hash the bits
   34  *      that are a multiple of the size of an 8-bit octet, and then
   35  *      optionally uses SHA1FinalBits() to hash the final few bits of
   36  *      the input.
   37  */
   38 
   39 #include "sha.h"
   40 #include "sha-private.h"
   41 
   42 /*
   43  *  Define the SHA1 circular left shift macro
   44  */
   45 #define SHA1_ROTL(bits,word) \
   46                 (((word) << (bits)) | ((word) >> (32-(bits))))
   47 
   48 /*
   49  * Add "length" to the length.
   50  * Set Corrupted when overflow has occurred.
   51  */
   52 static uint32_t addTemp;
   53 #define SHA1AddLength(context, length)                     \
   54     (addTemp = (context)->Length_Low,                      \
   55      (context)->Corrupted =                                \
   56         (((context)->Length_Low += (length)) < addTemp) && \
   57         (++(context)->Length_High == 0) ? shaInputTooLong  \
   58                                         : (context)->Corrupted )
   59 
   60 /* Local Function Prototypes */
   61 static void SHA1ProcessMessageBlock(SHA1Context *context);
   62 static void SHA1Finalize(SHA1Context *context, uint8_t Pad_Byte);
   63 static void SHA1PadMessage(SHA1Context *context, uint8_t Pad_Byte);
   64 
   65 /*
   66  *  SHA1Reset
   67  *
   68  *  Description:
   69  *      This function will initialize the SHA1Context in preparation
   70  *      for computing a new SHA1 message digest.
   71  *
   72  *  Parameters:
   73  *      context: [in/out]
   74  *          The context to reset.
   75  *
   76  *  Returns:
   77  *      sha Error Code.
   78  *
   79  */
   80 int SHA1Reset(SHA1Context *context)
   81 {
   82   if (!context) return shaNull;
   83 
   84   context->Length_High = context->Length_Low = 0;
   85   context->Message_Block_Index = 0;
   86 
   87   /* Initial Hash Values: FIPS 180-3 section 5.3.1 */
   88   context->Intermediate_Hash[0]   = 0x67452301;
   89   context->Intermediate_Hash[1]   = 0xEFCDAB89;
   90   context->Intermediate_Hash[2]   = 0x98BADCFE;
   91   context->Intermediate_Hash[3]   = 0x10325476;
   92   context->Intermediate_Hash[4]   = 0xC3D2E1F0;
   93 
   94   context->Computed   = 0;
   95   context->Corrupted  = shaSuccess;
   96 
   97   return shaSuccess;
   98 }
   99 
  100 /*
  101  *  SHA1Input
  102  *
  103  *  Description:
  104  *      This function accepts an array of octets as the next portion
  105  *      of the message.
  106  *
  107  *  Parameters:
  108  *      context: [in/out]
  109  *          The SHA context to update.
  110  *      message_array[ ]: [in]
  111  *          An array of octets representing the next portion of
  112  *          the message.
  113  *      length: [in]
  114  *          The length of the message in message_array.
  115  *
  116  *  Returns:
  117  *      sha Error Code.
  118  *
  119  */
  120 int SHA1Input(SHA1Context *context,
  121     const uint8_t *message_array, unsigned length)
  122 {
  123   if (!context) return shaNull;
  124   if (!length) return shaSuccess;
  125   if (!message_array) return shaNull;
  126   if (context->Computed) return context->Corrupted = shaStateError;
  127   if (context->Corrupted) return context->Corrupted;
  128 
  129   while (length--) {
  130     context->Message_Block[context->Message_Block_Index++] =
  131       *message_array;
  132 
  133     if ((SHA1AddLength(context, 8) == shaSuccess) &&
  134       (context->Message_Block_Index == SHA1_Message_Block_Size))
  135       SHA1ProcessMessageBlock(context);
  136 
  137     message_array++;
  138   }
  139 
  140   return context->Corrupted;
  141 }
  142 
  143 /*
  144  * SHA1FinalBits
  145  *
  146  * Description:
  147  *   This function will add in any final bits of the message.
  148  *
  149  * Parameters:
  150  *   context: [in/out]
  151  *     The SHA context to update.
  152  *   message_bits: [in]
  153  *     The final bits of the message, in the upper portion of the
  154  *     byte.  (Use 0b###00000 instead of 0b00000### to input the
  155  *     three bits ###.)
  156  *   length: [in]
  157  *     The number of bits in message_bits, between 1 and 7.
  158  *
  159  * Returns:
  160  *   sha Error Code.
  161  */
  162 int SHA1FinalBits(SHA1Context *context, uint8_t message_bits,
  163     unsigned int length)
  164 {
  165   static uint8_t masks[8] = {
  166       /* 0 0b00000000 */ 0x00, /* 1 0b10000000 */ 0x80,
  167       /* 2 0b11000000 */ 0xC0, /* 3 0b11100000 */ 0xE0,
  168       /* 4 0b11110000 */ 0xF0, /* 5 0b11111000 */ 0xF8,
  169       /* 6 0b11111100 */ 0xFC, /* 7 0b11111110 */ 0xFE
  170   };
  171 
  172   static uint8_t markbit[8] = {
  173       /* 0 0b10000000 */ 0x80, /* 1 0b01000000 */ 0x40,
  174       /* 2 0b00100000 */ 0x20, /* 3 0b00010000 */ 0x10,
  175       /* 4 0b00001000 */ 0x08, /* 5 0b00000100 */ 0x04,
  176       /* 6 0b00000010 */ 0x02, /* 7 0b00000001 */ 0x01
  177   };
  178 
  179   if (!context) return shaNull;
  180   if (!length) return shaSuccess;
  181   if (context->Corrupted) return context->Corrupted;
  182   if (context->Computed) return context->Corrupted = shaStateError;
  183   if (length >= 8) return context->Corrupted = shaBadParam;
  184 
  185   SHA1AddLength(context, length);
  186   SHA1Finalize(context,
  187     (uint8_t) ((message_bits & masks[length]) | markbit[length]));
  188 
  189   return context->Corrupted;
  190 }
  191 
  192 /*
  193  * SHA1Result
  194  *
  195  * Description:
  196  *   This function will return the 160-bit message digest
  197  *   into the Message_Digest array provided by the caller.
  198  *   NOTE:
  199  *    The first octet of hash is stored in the element with index 0,
  200  *      the last octet of hash in the element with index 19.
  201  *
  202  * Parameters:
  203  *   context: [in/out]
  204  *     The context to use to calculate the SHA-1 hash.
  205  *   Message_Digest[ ]: [out]
  206  *     Where the digest is returned.
  207  *
  208  * Returns:
  209  *   sha Error Code.
  210  *
  211  */
  212 int SHA1Result(SHA1Context *context,
  213     uint8_t Message_Digest[SHA1HashSize])
  214 {
  215   int i;
  216 
  217   if (!context) return shaNull;
  218   if (!Message_Digest) return shaNull;
  219   if (context->Corrupted) return context->Corrupted;
  220 
  221   if (!context->Computed)
  222     SHA1Finalize(context, 0x80);
  223 
  224   for (i = 0; i < SHA1HashSize; ++i)
  225     Message_Digest[i] = (uint8_t) (context->Intermediate_Hash[i>>2]
  226                                    >> (8 * ( 3 - ( i & 0x03 ) )));
  227 
  228   return shaSuccess;
  229 }
  230 
  231 /*
  232  * SHA1ProcessMessageBlock
  233  *
  234  * Description:
  235  *   This helper function will process the next 512 bits of the
  236  *   message stored in the Message_Block array.
  237  *
  238  * Parameters:
  239  *   context: [in/out]
  240  *     The SHA context to update.
  241  *
  242  * Returns:
  243  *   Nothing.
  244  *
  245  * Comments:
  246  *   Many of the variable names in this code, especially the
  247  *   single character names, were used because those were the
  248  *   names used in the Secure Hash Standard.
  249  */
  250 static void SHA1ProcessMessageBlock(SHA1Context *context)
  251 {
  252   /* Constants defined in FIPS 180-3, section 4.2.1 */
  253   const uint32_t K[4] = {
  254       0x5A827999, 0x6ED9EBA1, 0x8F1BBCDC, 0xCA62C1D6
  255   };
  256   int        t;               /* Loop counter */
  257   uint32_t   temp;            /* Temporary word value */
  258   uint32_t   W[80];           /* Word sequence */
  259   uint32_t   A, B, C, D, E;   /* Word buffers */
  260 
  261   /*
  262    * Initialize the first 16 words in the array W
  263    */
  264   for (t = 0; t < 16; t++) {
  265     W[t]  = ((uint32_t)context->Message_Block[t * 4]) << 24;
  266     W[t] |= ((uint32_t)context->Message_Block[t * 4 + 1]) << 16;
  267     W[t] |= ((uint32_t)context->Message_Block[t * 4 + 2]) << 8;
  268     W[t] |= ((uint32_t)context->Message_Block[t * 4 + 3]);
  269   }
  270 
  271   for (t = 16; t < 80; t++)
  272     W[t] = SHA1_ROTL(1, W[t-3] ^ W[t-8] ^ W[t-14] ^ W[t-16]);
  273 
  274   A = context->Intermediate_Hash[0];
  275   B = context->Intermediate_Hash[1];
  276   C = context->Intermediate_Hash[2];
  277   D = context->Intermediate_Hash[3];
  278   E = context->Intermediate_Hash[4];
  279 
  280   for (t = 0; t < 20; t++) {
  281     temp = SHA1_ROTL(5,A) + SHA_Ch(B, C, D) + E + W[t] + K[0];
  282     E = D;
  283     D = C;
  284     C = SHA1_ROTL(30,B);
  285     B = A;
  286     A = temp;
  287   }
  288 
  289   for (t = 20; t < 40; t++) {
  290     temp = SHA1_ROTL(5,A) + SHA_Parity(B, C, D) + E + W[t] + K[1];
  291     E = D;
  292     D = C;
  293     C = SHA1_ROTL(30,B);
  294     B = A;
  295     A = temp;
  296   }
  297 
  298   for (t = 40; t < 60; t++) {
  299     temp = SHA1_ROTL(5,A) + SHA_Maj(B, C, D) + E + W[t] + K[2];
  300     E = D;
  301     D = C;
  302     C = SHA1_ROTL(30,B);
  303     B = A;
  304     A = temp;
  305   }
  306 
  307   for (t = 60; t < 80; t++) {
  308     temp = SHA1_ROTL(5,A) + SHA_Parity(B, C, D) + E + W[t] + K[3];
  309     E = D;
  310     D = C;
  311     C = SHA1_ROTL(30,B);
  312     B = A;
  313     A = temp;
  314   }
  315 
  316   context->Intermediate_Hash[0] += A;
  317   context->Intermediate_Hash[1] += B;
  318   context->Intermediate_Hash[2] += C;
  319   context->Intermediate_Hash[3] += D;
  320   context->Intermediate_Hash[4] += E;
  321   context->Message_Block_Index = 0;
  322 }
  323 
  324 /*
  325  * SHA1Finalize
  326  *
  327  * Description:
  328  *   This helper function finishes off the digest calculations.
  329  *
  330  * Parameters:
  331  *   context: [in/out]
  332  *     The SHA context to update.
  333  *   Pad_Byte: [in]
  334  *     The last byte to add to the message block before the 0-padding
  335  *     and length.  This will contain the last bits of the message
  336  *     followed by another single bit.  If the message was an
  337  *     exact multiple of 8-bits long, Pad_Byte will be 0x80.
  338  *
  339  * Returns:
  340  *   sha Error Code.
  341  *
  342  */
  343 static void SHA1Finalize(SHA1Context *context, uint8_t Pad_Byte)
  344 {
  345   int i;
  346   SHA1PadMessage(context, Pad_Byte);
  347   /* message may be sensitive, clear it out */
  348   for (i = 0; i < SHA1_Message_Block_Size; ++i)
  349     context->Message_Block[i] = 0;
  350   context->Length_High = 0;     /* and clear length */
  351   context->Length_Low = 0;
  352   context->Computed = 1;
  353 }
  354 
  355 /*
  356  * SHA1PadMessage
  357  *
  358  * Description:
  359  *   According to the standard, the message must be padded to the next
  360  *   even multiple of 512 bits.  The first padding bit must be a '1'.
  361  *   The last 64 bits represent the length of the original message.
  362  *   All bits in between should be 0.  This helper function will pad
  363  *   the message according to those rules by filling the Message_Block
  364  *   array accordingly.  When it returns, it can be assumed that the
  365  *   message digest has been computed.
  366  *
  367  * Parameters:
  368  *   context: [in/out]
  369  *     The context to pad.
  370  *   Pad_Byte: [in]
  371  *     The last byte to add to the message block before the 0-padding
  372  *     and length.  This will contain the last bits of the message
  373  *     followed by another single bit.  If the message was an
  374  *     exact multiple of 8-bits long, Pad_Byte will be 0x80.
  375  *
  376  * Returns:
  377  *   Nothing.
  378  */
  379 static void SHA1PadMessage(SHA1Context *context, uint8_t Pad_Byte)
  380 {
  381   /*
  382    * Check to see if the current message block is too small to hold
  383    * the initial padding bits and length.  If so, we will pad the
  384    * block, process it, and then continue padding into a second
  385    * block.
  386    */
  387   if (context->Message_Block_Index >= (SHA1_Message_Block_Size - 8)) {
  388     context->Message_Block[context->Message_Block_Index++] = Pad_Byte;
  389     while (context->Message_Block_Index < SHA1_Message_Block_Size)
  390       context->Message_Block[context->Message_Block_Index++] = 0;
  391 
  392     SHA1ProcessMessageBlock(context);
  393   } else
  394     context->Message_Block[context->Message_Block_Index++] = Pad_Byte;
  395 
  396   while (context->Message_Block_Index < (SHA1_Message_Block_Size - 8))
  397     context->Message_Block[context->Message_Block_Index++] = 0;
  398 
  399   /*
  400    * Store the message length as the last 8 octets
  401    */
  402   context->Message_Block[56] = (uint8_t) (context->Length_High >> 24);
  403   context->Message_Block[57] = (uint8_t) (context->Length_High >> 16);
  404   context->Message_Block[58] = (uint8_t) (context->Length_High >> 8);
  405   context->Message_Block[59] = (uint8_t) (context->Length_High);
  406   context->Message_Block[60] = (uint8_t) (context->Length_Low >> 24);
  407   context->Message_Block[61] = (uint8_t) (context->Length_Low >> 16);
  408   context->Message_Block[62] = (uint8_t) (context->Length_Low >> 8);
  409   context->Message_Block[63] = (uint8_t) (context->Length_Low);
  410 
  411   SHA1ProcessMessageBlock(context);
  412 }