libmoost
/home/mhx/git/github/libmoost/src/digest/rfc6234/sha.h
Go to the documentation of this file.
00001 /**************************** sha.h ****************************/
00002 /***************** See RFC 6234 for details. *******************/
00003 /*
00004    Copyright (c) 2011 IETF Trust and the persons identified as
00005    authors of the code.  All rights reserved.
00006 
00007    Redistribution and use in source and binary forms, with or
00008    without modification, are permitted provided that the following
00009    conditions are met:
00010 
00011    - Redistributions of source code must retain the above
00012      copyright notice, this list of conditions and
00013      the following disclaimer.
00014 
00015    - Redistributions in binary form must reproduce the above
00016      copyright notice, this list of conditions and the following
00017      disclaimer in the documentation and/or other materials provided
00018      with the distribution.
00019 
00020    - Neither the name of Internet Society, IETF or IETF Trust, nor
00021      the names of specific contributors, may be used to endorse or
00022      promote products derived from this software without specific
00023      prior written permission.
00024 
00025    THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
00026    CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
00027    INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
00028    MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
00029    DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
00030    CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
00031    SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
00032    NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
00033    LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
00034    HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
00035    CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
00036    OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
00037    EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00038 */
00039 #ifndef _SHA_H_
00040 #define _SHA_H_
00041 
00042 /*
00043  *  Description:
00044  *      This file implements the Secure Hash Algorithms
00045  *      as defined in the U.S. National Institute of Standards
00046  *      and Technology Federal Information Processing Standards
00047  *      Publication (FIPS PUB) 180-3 published in October 2008
00048  *      and formerly defined in its predecessors, FIPS PUB 180-1
00049  *      and FIP PUB 180-2.
00050  *
00051  *      A combined document showing all algorithms is available at
00052  *              http://csrc.nist.gov/publications/fips/
00053  *                     fips180-3/fips180-3_final.pdf
00054  *
00055  *      The five hashes are defined in these sizes:
00056  *              SHA-1           20 byte / 160 bit
00057  *              SHA-224         28 byte / 224 bit
00058  *              SHA-256         32 byte / 256 bit
00059  *              SHA-384         48 byte / 384 bit
00060  *              SHA-512         64 byte / 512 bit
00061  *
00062  *  Compilation Note:
00063  *    These files may be compiled with two options:
00064  *        USE_32BIT_ONLY - use 32-bit arithmetic only, for systems
00065  *                         without 64-bit integers
00066  *
00067  *        USE_MODIFIED_MACROS - use alternate form of the SHA_Ch()
00068  *                         and SHA_Maj() macros that are equivalent
00069  *                         and potentially faster on many systems
00070  *
00071  */
00072 
00073 #include <stdint.h>
00074 /*
00075  * If you do not have the ISO standard stdint.h header file, then you
00076  * must typedef the following:
00077  *    name              meaning
00078  *  uint64_t         unsigned 64-bit integer
00079  *  uint32_t         unsigned 32-bit integer
00080  *  uint8_t          unsigned 8-bit integer (i.e., unsigned char)
00081  *  int_least16_t    integer of >= 16 bits
00082  *
00083  * See stdint-example.h
00084  */
00085 
00086 #ifndef _SHA_enum_
00087 #define _SHA_enum_
00088 /*
00089  *  All SHA functions return one of these values.
00090  */
00091 enum {
00092     shaSuccess = 0,
00093     shaNull,            /* Null pointer parameter */
00094     shaInputTooLong,    /* input data too long */
00095     shaStateError,      /* called Input after FinalBits or Result */
00096     shaBadParam         /* passed a bad parameter */
00097 };
00098 #endif /* _SHA_enum_ */
00099 
00100 /*
00101  *  These constants hold size information for each of the SHA
00102  *  hashing operations
00103  */
00104 enum {
00105     SHA1_Message_Block_Size = 64, SHA224_Message_Block_Size = 64,
00106     SHA256_Message_Block_Size = 64, SHA384_Message_Block_Size = 128,
00107     SHA512_Message_Block_Size = 128,
00108     USHA_Max_Message_Block_Size = SHA512_Message_Block_Size,
00109 
00110     SHA1HashSize = 20, SHA224HashSize = 28, SHA256HashSize = 32,
00111     SHA384HashSize = 48, SHA512HashSize = 64,
00112     USHAMaxHashSize = SHA512HashSize,
00113 
00114     SHA1HashSizeBits = 160, SHA224HashSizeBits = 224,
00115     SHA256HashSizeBits = 256, SHA384HashSizeBits = 384,
00116     SHA512HashSizeBits = 512, USHAMaxHashSizeBits = SHA512HashSizeBits
00117 };
00118 
00119 /*
00120  *  These constants are used in the USHA (Unified SHA) functions.
00121  */
00122 typedef enum SHAversion {
00123     SHA1, SHA224, SHA256, SHA384, SHA512
00124 } SHAversion;
00125 
00126 /*
00127  *  This structure will hold context information for the SHA-1
00128  *  hashing operation.
00129  */
00130 typedef struct SHA1Context {
00131     uint32_t Intermediate_Hash[SHA1HashSize/4]; /* Message Digest */
00132 
00133     uint32_t Length_High;               /* Message length in bits */
00134     uint32_t Length_Low;                /* Message length in bits */
00135 
00136     int_least16_t Message_Block_Index;  /* Message_Block array index */
00137                                         /* 512-bit message blocks */
00138     uint8_t Message_Block[SHA1_Message_Block_Size];
00139 
00140     int Computed;                   /* Is the hash computed? */
00141     int Corrupted;                  /* Cumulative corruption code */
00142 } SHA1Context;
00143 
00144 /*
00145  *  This structure will hold context information for the SHA-256
00146  *  hashing operation.
00147  */
00148 typedef struct SHA256Context {
00149     uint32_t Intermediate_Hash[SHA256HashSize/4]; /* Message Digest */
00150 
00151     uint32_t Length_High;               /* Message length in bits */
00152     uint32_t Length_Low;                /* Message length in bits */
00153 
00154     int_least16_t Message_Block_Index;  /* Message_Block array index */
00155                                         /* 512-bit message blocks */
00156     uint8_t Message_Block[SHA256_Message_Block_Size];
00157 
00158     int Computed;                   /* Is the hash computed? */
00159     int Corrupted;                  /* Cumulative corruption code */
00160 } SHA256Context;
00161 
00162 /*
00163  *  This structure will hold context information for the SHA-512
00164  *  hashing operation.
00165  */
00166 typedef struct SHA512Context {
00167 #ifdef USE_32BIT_ONLY
00168     uint32_t Intermediate_Hash[SHA512HashSize/4]; /* Message Digest  */
00169     uint32_t Length[4];                 /* Message length in bits */
00170 #else /* !USE_32BIT_ONLY */
00171     uint64_t Intermediate_Hash[SHA512HashSize/8]; /* Message Digest */
00172     uint64_t Length_High, Length_Low;   /* Message length in bits */
00173 #endif /* USE_32BIT_ONLY */
00174 
00175     int_least16_t Message_Block_Index;  /* Message_Block array index */
00176                                         /* 1024-bit message blocks */
00177     uint8_t Message_Block[SHA512_Message_Block_Size];
00178 
00179     int Computed;                   /* Is the hash computed?*/
00180     int Corrupted;                  /* Cumulative corruption code */
00181 } SHA512Context;
00182 
00183 /*
00184  *  This structure will hold context information for the SHA-224
00185  *  hashing operation.  It uses the SHA-256 structure for computation.
00186  */
00187 typedef struct SHA256Context SHA224Context;
00188 
00189 /*
00190  *  This structure will hold context information for the SHA-384
00191  *  hashing operation.  It uses the SHA-512 structure for computation.
00192  */
00193 typedef struct SHA512Context SHA384Context;
00194 
00195 /*
00196  *  This structure holds context information for all SHA
00197  *  hashing operations.
00198  */
00199 typedef struct USHAContext {
00200     int whichSha;               /* which SHA is being used */
00201     union {
00202       SHA1Context sha1Context;
00203       SHA224Context sha224Context; SHA256Context sha256Context;
00204       SHA384Context sha384Context; SHA512Context sha512Context;
00205     } ctx;
00206 
00207 } USHAContext;
00208 
00209 /*
00210  *  This structure will hold context information for the HMAC
00211  *  keyed-hashing operation.
00212  */
00213 typedef struct HMACContext {
00214     int whichSha;               /* which SHA is being used */
00215     int hashSize;               /* hash size of SHA being used */
00216     int blockSize;              /* block size of SHA being used */
00217     USHAContext shaContext;     /* SHA context */
00218     unsigned char k_opad[USHA_Max_Message_Block_Size];
00219                         /* outer padding - key XORd with opad */
00220     int Computed;               /* Is the MAC computed? */
00221     int Corrupted;              /* Cumulative corruption code */
00222 
00223 } HMACContext;
00224 
00225 /*
00226  *  This structure will hold context information for the HKDF
00227  *  extract-and-expand Key Derivation Functions.
00228  */
00229 typedef struct HKDFContext {
00230     int whichSha;               /* which SHA is being used */
00231     HMACContext hmacContext;
00232     int hashSize;               /* hash size of SHA being used */
00233     unsigned char prk[USHAMaxHashSize];
00234                         /* pseudo-random key - output of hkdfInput */
00235     int Computed;               /* Is the key material computed? */
00236     int Corrupted;              /* Cumulative corruption code */
00237 } HKDFContext;
00238 
00239 /*
00240  *  Function Prototypes
00241  */
00242 
00243 #ifdef __cplusplus
00244 extern "C" {
00245 #endif
00246 
00247 /* SHA-1 */
00248 extern int SHA1Reset(SHA1Context *);
00249 extern int SHA1Input(SHA1Context *, const uint8_t *bytes,
00250                      unsigned int bytecount);
00251 extern int SHA1FinalBits(SHA1Context *, uint8_t bits,
00252                          unsigned int bit_count);
00253 extern int SHA1Result(SHA1Context *,
00254                       uint8_t Message_Digest[SHA1HashSize]);
00255 
00256 /* SHA-224 */
00257 extern int SHA224Reset(SHA224Context *);
00258 extern int SHA224Input(SHA224Context *, const uint8_t *bytes,
00259                        unsigned int bytecount);
00260 extern int SHA224FinalBits(SHA224Context *, uint8_t bits,
00261                            unsigned int bit_count);
00262 extern int SHA224Result(SHA224Context *,
00263                         uint8_t Message_Digest[SHA224HashSize]);
00264 
00265 /* SHA-256 */
00266 extern int SHA256Reset(SHA256Context *);
00267 extern int SHA256Input(SHA256Context *, const uint8_t *bytes,
00268                        unsigned int bytecount);
00269 extern int SHA256FinalBits(SHA256Context *, uint8_t bits,
00270                            unsigned int bit_count);
00271 extern int SHA256Result(SHA256Context *,
00272                         uint8_t Message_Digest[SHA256HashSize]);
00273 
00274 /* SHA-384 */
00275 extern int SHA384Reset(SHA384Context *);
00276 extern int SHA384Input(SHA384Context *, const uint8_t *bytes,
00277                        unsigned int bytecount);
00278 extern int SHA384FinalBits(SHA384Context *, uint8_t bits,
00279                            unsigned int bit_count);
00280 extern int SHA384Result(SHA384Context *,
00281                         uint8_t Message_Digest[SHA384HashSize]);
00282 
00283 /* SHA-512 */
00284 extern int SHA512Reset(SHA512Context *);
00285 extern int SHA512Input(SHA512Context *, const uint8_t *bytes,
00286                        unsigned int bytecount);
00287 extern int SHA512FinalBits(SHA512Context *, uint8_t bits,
00288                            unsigned int bit_count);
00289 extern int SHA512Result(SHA512Context *,
00290                         uint8_t Message_Digest[SHA512HashSize]);
00291 
00292 /* Unified SHA functions, chosen by whichSha */
00293 extern int USHAReset(USHAContext *context, SHAversion whichSha);
00294 extern int USHAInput(USHAContext *context,
00295                      const uint8_t *bytes, unsigned int bytecount);
00296 extern int USHAFinalBits(USHAContext *context,
00297                          uint8_t bits, unsigned int bit_count);
00298 extern int USHAResult(USHAContext *context,
00299                       uint8_t Message_Digest[USHAMaxHashSize]);
00300 extern int USHABlockSize(enum SHAversion whichSha);
00301 extern int USHAHashSize(enum SHAversion whichSha);
00302 extern int USHAHashSizeBits(enum SHAversion whichSha);
00303 extern const char *USHAHashName(enum SHAversion whichSha);
00304 
00305 /*
00306  * HMAC Keyed-Hashing for Message Authentication, RFC 2104,
00307  * for all SHAs.
00308  * This interface allows a fixed-length text input to be used.
00309  */
00310 extern int hmac(SHAversion whichSha, /* which SHA algorithm to use */
00311     const unsigned char *text,     /* pointer to data stream */
00312     int text_len,                  /* length of data stream */
00313     const unsigned char *key,      /* pointer to authentication key */
00314     int key_len,                   /* length of authentication key */
00315     uint8_t digest[USHAMaxHashSize]); /* caller digest to fill in */
00316 
00317 /*
00318  * HMAC Keyed-Hashing for Message Authentication, RFC 2104,
00319  * for all SHAs.
00320  * This interface allows any length of text input to be used.
00321  */
00322 extern int hmacReset(HMACContext *context, enum SHAversion whichSha,
00323                      const unsigned char *key, int key_len);
00324 extern int hmacInput(HMACContext *context, const unsigned char *text,
00325                      int text_len);
00326 extern int hmacFinalBits(HMACContext *context, uint8_t bits,
00327                          unsigned int bit_count);
00328 extern int hmacResult(HMACContext *context,
00329                       uint8_t digest[USHAMaxHashSize]);
00330 
00331 /*
00332  * HKDF HMAC-based Extract-and-Expand Key Derivation Function,
00333  * RFC 5869, for all SHAs.
00334  */
00335 extern int hkdf(SHAversion whichSha, const unsigned char *salt,
00336                 int salt_len, const unsigned char *ikm, int ikm_len,
00337                 const unsigned char *info, int info_len,
00338                 uint8_t okm[ ], int okm_len);
00339 extern int hkdfExtract(SHAversion whichSha, const unsigned char *salt,
00340                        int salt_len, const unsigned char *ikm,
00341                        int ikm_len, uint8_t prk[USHAMaxHashSize]);
00342 extern int hkdfExpand(SHAversion whichSha, const uint8_t prk[ ],
00343                       int prk_len, const unsigned char *info,
00344                       int info_len, uint8_t okm[ ], int okm_len);
00345 
00346 /*
00347  * HKDF HMAC-based Extract-and-Expand Key Derivation Function,
00348  * RFC 5869, for all SHAs.
00349  * This interface allows any length of text input to be used.
00350  */
00351 extern int hkdfReset(HKDFContext *context, enum SHAversion whichSha,
00352                      const unsigned char *salt, int salt_len);
00353 extern int hkdfInput(HKDFContext *context, const unsigned char *ikm,
00354                      int ikm_len);
00355 extern int hkdfFinalBits(HKDFContext *context, uint8_t ikm_bits,
00356                          unsigned int ikm_bit_count);
00357 extern int hkdfResult(HKDFContext *context,
00358                       uint8_t prk[USHAMaxHashSize],
00359                       const unsigned char *info, int info_len,
00360                       uint8_t okm[USHAMaxHashSize], int okm_len);
00361 
00362 #ifdef __cplusplus
00363 }
00364 #endif
00365 
00366 #endif /* _SHA_H_ */