Nigel Rantor / azure_c_shared_utility

Fork of azure_c_shared_utility by Azure IoT

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers sha.h Source File

sha.h

00001 // Copyright (c) Microsoft. All rights reserved.
00002 // Licensed under the MIT license. See LICENSE file in the project root for full license information.
00003 
00004 /**************************** sha.h ****************************/
00005 /******************* See RFC 4634 for details ******************/
00006 #ifndef _SHA_H_
00007 #define _SHA_H_
00008 
00009 #ifdef __cplusplus
00010 extern "C"
00011 {
00012 #endif
00013 
00014 /*
00015  *  Description:
00016  *      This file implements the Secure Hash Signature Standard
00017  *      algorithms as defined in the National Institute of Standards
00018  *      and Technology Federal Information Processing Standards
00019  *      Publication (FIPS PUB) 180-1 published on April 17, 1995, 180-2
00020  *      published on August 1, 2002, and the FIPS PUB 180-2 Change
00021  *      Notice published on February 28, 2004.
00022  *
00023  *      A combined document showing all algorithms is available at
00024  *              http://csrc.nist.gov/publications/fips/
00025  *              fips180-2/fips180-2withchangenotice.pdf
00026  *
00027  *      The five hashes are defined in these sizes:
00028  *              SHA-1           20 byte / 160 bit
00029  *              SHA-224         28 byte / 224 bit
00030  *              SHA-256         32 byte / 256 bit
00031  *              SHA-384         48 byte / 384 bit
00032  *              SHA-512         64 byte / 512 bit
00033  */
00034 
00035 #include <stdint.h>
00036 /*
00037  * If you do not have the ISO standard stdint.h header file, then you
00038  * must typedef the following:
00039  *    name              meaning
00040  *  uint64_t         unsigned 64 bit integer
00041  *  uint32_t         unsigned 32 bit integer
00042  *  uint8_t          unsigned 8 bit integer (i.e., unsigned char)
00043  *  int_least16_t    integer of >= 16 bits
00044  *
00045  */
00046 
00047 #ifndef _SHA_enum_
00048 #define _SHA_enum_
00049 /*
00050  *  All SHA functions return one of these values.
00051  */
00052 enum {
00053     shaSuccess = 0,
00054     shaNull,            /* Null pointer parameter */
00055     shaInputTooLong,    /* input data too long */
00056     shaStateError,      /* called Input after FinalBits or Result */
00057     shaBadParam         /* passed a bad parameter */
00058 };
00059 #endif /* _SHA_enum_ */
00060 
00061 /*
00062  *  These constants hold size information for each of the SHA
00063  *  hashing operations
00064  */
00065 enum {
00066     SHA1_Message_Block_Size = 64, SHA224_Message_Block_Size = 64,
00067     SHA256_Message_Block_Size = 64, SHA384_Message_Block_Size = 128,
00068     SHA512_Message_Block_Size = 128,
00069     USHA_Max_Message_Block_Size = SHA512_Message_Block_Size,
00070 
00071     SHA1HashSize = 20, SHA224HashSize = 28, SHA256HashSize = 32,
00072     SHA384HashSize = 48, SHA512HashSize = 64,
00073     USHAMaxHashSize = SHA512HashSize,
00074 
00075     SHA1HashSizeBits = 160, SHA224HashSizeBits = 224,
00076     SHA256HashSizeBits = 256, SHA384HashSizeBits = 384,
00077     SHA512HashSizeBits = 512, USHAMaxHashSizeBits = SHA512HashSizeBits
00078 };
00079 
00080 /*
00081  *  These constants are used in the USHA (unified sha) functions.
00082  */
00083 typedef enum SHAversion {
00084     SHA1, SHA224, SHA256, SHA384, SHA512
00085 } SHAversion;
00086 
00087 /*
00088  *  This structure will hold context information for the SHA-1
00089  *  hashing operation.
00090  */
00091 typedef struct SHA1Context {
00092     uint32_t Intermediate_Hash[SHA1HashSize/4]; /* Message Digest */
00093 
00094     uint32_t Length_Low;                /* Message length in bits */
00095     uint32_t Length_High;               /* Message length in bits */
00096 
00097     int_least16_t Message_Block_Index;  /* Message_Block array index */
00098                                         /* 512-bit message blocks */
00099     uint8_t Message_Block[SHA1_Message_Block_Size];
00100 
00101     int Computed;                       /* Is the digest computed? */
00102     int Corrupted;                      /* Is the digest corrupted? */
00103 } SHA1Context;
00104 
00105 /*
00106  *  This structure will hold context information for the SHA-256
00107  *  hashing operation.
00108  */
00109 typedef struct SHA256Context {
00110     uint32_t Intermediate_Hash[SHA256HashSize/4]; /* Message Digest */
00111 
00112     uint32_t Length_Low;                /* Message length in bits */
00113     uint32_t Length_High;               /* Message length in bits */
00114 
00115     int_least16_t Message_Block_Index;  /* Message_Block array index */
00116                                         /* 512-bit message blocks */
00117     uint8_t Message_Block[SHA256_Message_Block_Size];
00118 
00119     int Computed;                       /* Is the digest computed? */
00120     int Corrupted;                      /* Is the digest corrupted? */
00121 } SHA256Context;
00122 
00123 /*
00124  *  This structure will hold context information for the SHA-512
00125  *  hashing operation.
00126  */
00127 typedef struct SHA512Context {
00128 #ifdef USE_32BIT_ONLY
00129     uint32_t Intermediate_Hash[SHA512HashSize/4]; /* Message Digest  */
00130     uint32_t Length[4];                 /* Message length in bits */
00131 #else /* !USE_32BIT_ONLY */
00132     uint64_t Intermediate_Hash[SHA512HashSize/8]; /* Message Digest */
00133     uint64_t Length_Low, Length_High;   /* Message length in bits */
00134 #endif /* USE_32BIT_ONLY */
00135 
00136     int_least16_t Message_Block_Index;  /* Message_Block array index */
00137                                         /* 1024-bit message blocks */
00138     uint8_t Message_Block[SHA512_Message_Block_Size];
00139 
00140     int Computed;                       /* Is the digest computed?*/
00141     int Corrupted;                      /* Is the digest corrupted? */
00142 } SHA512Context;
00143 
00144 /*
00145  *  This structure will hold context information for the SHA-224
00146  *  hashing operation. It uses the SHA-256 structure for computation.
00147  */
00148 typedef struct SHA256Context SHA224Context;
00149 
00150 /*
00151  *  This structure will hold context information for the SHA-384
00152  *  hashing operation. It uses the SHA-512 structure for computation.
00153  */
00154 typedef struct SHA512Context SHA384Context;
00155 
00156 /*
00157  *  This structure holds context information for all SHA
00158  *  hashing operations.
00159  */
00160 typedef struct USHAContext {
00161     int whichSha;               /* which SHA is being used */
00162     union {
00163       SHA1Context sha1Context;
00164       SHA224Context sha224Context; SHA256Context sha256Context;
00165       SHA384Context sha384Context; SHA512Context sha512Context;
00166     } ctx;
00167 } USHAContext;
00168 
00169 /*
00170  *  This structure will hold context information for the HMAC
00171  *  keyed hashing operation.
00172  */
00173 typedef struct HMACContext {
00174     int whichSha;               /* which SHA is being used */
00175     int hashSize;               /* hash size of SHA being used */
00176     int blockSize;              /* block size of SHA being used */
00177     USHAContext shaContext;     /* SHA context */
00178     unsigned char k_opad[USHA_Max_Message_Block_Size];
00179                         /* outer padding - key XORd with opad */
00180 } HMACContext;
00181 
00182 
00183 /*
00184  *  Function Prototypes
00185  */
00186 
00187 /* SHA-1 */
00188 extern int SHA1Reset(SHA1Context *);
00189 extern int SHA1Input(SHA1Context *, const uint8_t *bytes,
00190                      unsigned int bytecount);
00191 extern int SHA1FinalBits(SHA1Context *, const uint8_t bits,
00192                          unsigned int bitcount);
00193 extern int SHA1Result(SHA1Context *,
00194                       uint8_t Message_Digest[SHA1HashSize]);
00195 
00196 /* SHA-224 */
00197 extern int SHA224Reset(SHA224Context *);
00198 extern int SHA224Input(SHA224Context *, const uint8_t *bytes,
00199                        unsigned int bytecount);
00200 extern int SHA224FinalBits(SHA224Context *, const uint8_t bits,
00201                            unsigned int bitcount);
00202 extern int SHA224Result(SHA224Context *,
00203                         uint8_t Message_Digest[SHA224HashSize]);
00204 
00205 /* SHA-256 */
00206 extern int SHA256Reset(SHA256Context *);
00207 extern int SHA256Input(SHA256Context *, const uint8_t *bytes,
00208                        unsigned int bytecount);
00209 extern int SHA256FinalBits(SHA256Context *, const uint8_t bits,
00210                            unsigned int bitcount);
00211 extern int SHA256Result(SHA256Context *,
00212                         uint8_t Message_Digest[SHA256HashSize]);
00213 
00214 /* SHA-384 */
00215 extern int SHA384Reset(SHA384Context *);
00216 extern int SHA384Input(SHA384Context *, const uint8_t *bytes,
00217                        unsigned int bytecount);
00218 extern int SHA384FinalBits(SHA384Context *, const uint8_t bits,
00219                            unsigned int bitcount);
00220 extern int SHA384Result(SHA384Context *,
00221                         uint8_t Message_Digest[SHA384HashSize]);
00222 
00223 /* SHA-512 */
00224 extern int SHA512Reset(SHA512Context *);
00225 extern int SHA512Input(SHA512Context *, const uint8_t *bytes,
00226                        unsigned int bytecount);
00227 extern int SHA512FinalBits(SHA512Context *, const uint8_t bits,
00228                            unsigned int bitcount);
00229 extern int SHA512Result(SHA512Context *,
00230                         uint8_t Message_Digest[SHA512HashSize]);
00231 
00232 /* Unified SHA functions, chosen by whichSha */
00233 extern int USHAReset(USHAContext *, SHAversion whichSha);
00234 extern int USHAInput(USHAContext *,
00235                      const uint8_t *bytes, unsigned int bytecount);
00236 extern int USHAFinalBits(USHAContext *,
00237                          const uint8_t bits, unsigned int bitcount);
00238 extern int USHAResult(USHAContext *,
00239                       uint8_t Message_Digest[USHAMaxHashSize]);
00240 extern int USHABlockSize(enum SHAversion whichSha);
00241 extern int USHAHashSize(enum SHAversion whichSha);
00242 extern int USHAHashSizeBits(enum SHAversion whichSha);
00243 
00244 /*
00245  * HMAC Keyed-Hashing for Message Authentication, RFC2104,
00246  * for all SHAs.
00247  * This interface allows a fixed-length text input to be used.
00248  */
00249 extern int hmac(SHAversion whichSha, /* which SHA algorithm to use */
00250     const unsigned char *text,     /* pointer to data stream */
00251     int text_len,                  /* length of data stream */
00252     const unsigned char *key,      /* pointer to authentication key */
00253     int key_len,                   /* length of authentication key */
00254     uint8_t digest[USHAMaxHashSize]); /* caller digest to fill in */
00255 
00256 /*
00257  * HMAC Keyed-Hashing for Message Authentication, RFC2104,
00258  * for all SHAs.
00259  * This interface allows any length of text input to be used.
00260  */
00261 extern int hmacReset(HMACContext *ctx, enum SHAversion whichSha,
00262                      const unsigned char *key, int key_len);
00263 extern int hmacInput(HMACContext *ctx, const unsigned char *text,
00264                      int text_len);
00265 
00266 extern int hmacFinalBits(HMACContext *ctx, const uint8_t bits,
00267                          unsigned int bitcount);
00268 extern int hmacResult(HMACContext *ctx,
00269                       uint8_t digest[USHAMaxHashSize]);
00270 
00271 
00272 #ifdef __cplusplus
00273 }
00274 #endif
00275 
00276 #endif /* _SHA_H_ */
00277