00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071 #include "sha256.h"
00072 #include <memory.h>
00073
00074 #ifdef HAS_STDINT
00075 #include <stdint.h>
00076 #endif
00077 #ifndef HAS_STDINT
00078 typedef unsigned int uint32_t;
00079 #endif
00080
00081 #define SHA256_BLOCK_SIZE (512 / 8)
00082
00084 class SHA256Context
00085 {
00086 public:
00087 unsigned int tot_len;
00088 unsigned int len;
00089 unsigned char block[2 * SHA256_BLOCK_SIZE];
00090 uint32_t h[8];
00091 };
00092
00093 #define SHA256_DIGEST_SIZE (256 / 8)
00094
00095 #define SHFR(x, n) (x >> n)
00096 #define ROTR(x, n) ((x >> n) | (x << ((sizeof(x) << 3) - n)))
00097 #define ROTL(x, n) ((x << n) | (x >> ((sizeof(x) << 3) - n)))
00098 #define CH(x, y, z) ((x & y) ^ (~x & z))
00099 #define MAJ(x, y, z) ((x & y) ^ (x & z) ^ (y & z))
00100
00101 #define SHA256_F1(x) (ROTR(x, 2) ^ ROTR(x, 13) ^ ROTR(x, 22))
00102 #define SHA256_F2(x) (ROTR(x, 6) ^ ROTR(x, 11) ^ ROTR(x, 25))
00103 #define SHA256_F3(x) (ROTR(x, 7) ^ ROTR(x, 18) ^ SHFR(x, 3))
00104 #define SHA256_F4(x) (ROTR(x, 17) ^ ROTR(x, 19) ^ SHFR(x, 10))
00105
00106 #define UNPACK32(x, str) \
00107 { \
00108 *((str) + 3) = (uint8_t) ((x) ); \
00109 *((str) + 2) = (uint8_t) ((x) >> 8); \
00110 *((str) + 1) = (uint8_t) ((x) >> 16); \
00111 *((str) + 0) = (uint8_t) ((x) >> 24); \
00112 }
00113
00114 #define PACK32(str, x) \
00115 { \
00116 *(x) = ((uint32_t) *((str) + 3) ) \
00117 | ((uint32_t) *((str) + 2) << 8) \
00118 | ((uint32_t) *((str) + 1) << 16) \
00119 | ((uint32_t) *((str) + 0) << 24); \
00120 }
00121
00122
00123
00124 #define SHA256_SCR(i) \
00125 { \
00126 w[i] = SHA256_F4(w[i - 2]) + w[i - 7] \
00127 + SHA256_F3(w[i - 15]) + w[i - 16]; \
00128 }
00129
00130 const unsigned int sha256_h0[8] =
00131 {
00132 0x6a09e667, 0xbb67ae85, 0x3c6ef372, 0xa54ff53a,
00133 0x510e527f, 0x9b05688c, 0x1f83d9ab, 0x5be0cd19
00134 };
00135
00136 uint32_t sha256_k[64] =
00137 {
00138 0x428a2f98, 0x71374491, 0xb5c0fbcf, 0xe9b5dba5,
00139 0x3956c25b, 0x59f111f1, 0x923f82a4, 0xab1c5ed5,
00140 0xd807aa98, 0x12835b01, 0x243185be, 0x550c7dc3,
00141 0x72be5d74, 0x80deb1fe, 0x9bdc06a7, 0xc19bf174,
00142 0xe49b69c1, 0xefbe4786, 0x0fc19dc6, 0x240ca1cc,
00143 0x2de92c6f, 0x4a7484aa, 0x5cb0a9dc, 0x76f988da,
00144 0x983e5152, 0xa831c66d, 0xb00327c8, 0xbf597fc7,
00145 0xc6e00bf3, 0xd5a79147, 0x06ca6351, 0x14292967,
00146 0x27b70a85, 0x2e1b2138, 0x4d2c6dfc, 0x53380d13,
00147 0x650a7354, 0x766a0abb, 0x81c2c92e, 0x92722c85,
00148 0xa2bfe8a1, 0xa81a664b, 0xc24b8b70, 0xc76c51a3,
00149 0xd192e819, 0xd6990624, 0xf40e3585, 0x106aa070,
00150 0x19a4c116, 0x1e376c08, 0x2748774c, 0x34b0bcb5,
00151 0x391c0cb3, 0x4ed8aa4a, 0x5b9cca4f, 0x682e6ff3,
00152 0x748f82ee, 0x78a5636f, 0x84c87814, 0x8cc70208,
00153 0x90befffa, 0xa4506ceb, 0xbef9a3f7, 0xc67178f2
00154 };
00155
00156 void SHA256Init(SHA256Context *ctx)
00157 {
00158 for (int i = 0; i < 8; i++)
00159 ctx->h[i] = sha256_h0[i];
00160 ctx->len = 0;
00161 ctx->tot_len = 0;
00162 }
00163
00164 void SHA256Transform(SHA256Context *ctx,
00165 unsigned char *message,
00166 unsigned int block_nb)
00167 {
00168 uint32_t w[64];
00169 uint32_t wv[8];
00170 unsigned char *sub_block;
00171 for (unsigned int i = 1; i <= block_nb; i++)
00172 {
00173 int j;
00174 sub_block = message + ((i - 1) << 6);
00175
00176 for (j = 0; j < 16; j++)
00177 PACK32(&sub_block[j << 2], &w[j]);
00178 for (j = 16; j < 64; j++)
00179 SHA256_SCR(j);
00180 for (j = 0; j < 8; j++)
00181 wv[j] = ctx->h[j];
00182 for (j = 0; j < 64; j++)
00183 {
00184 uint32_t t1 = wv[7] + SHA256_F2(wv[4]) + CH(wv[4], wv[5], wv[6]) + sha256_k[j] + w[j];
00185 uint32_t t2 = SHA256_F1(wv[0]) + MAJ(wv[0], wv[1], wv[2]);
00186 wv[7] = wv[6];
00187 wv[6] = wv[5];
00188 wv[5] = wv[4];
00189 wv[4] = wv[3] + t1;
00190 wv[3] = wv[2];
00191 wv[2] = wv[1];
00192 wv[1] = wv[0];
00193 wv[0] = t1 + t2;
00194 }
00195 for (j = 0; j < 8; j++)
00196 ctx->h[j] += wv[j];
00197 }
00198 }
00199
00200 void SHA256Update(SHA256Context *ctx,
00201 unsigned char *message,
00202 unsigned int len)
00203 {
00204
00205
00206
00207
00208
00209
00210
00211
00212
00213
00214
00215
00216
00217
00218
00219
00220 unsigned int tmp_len = SHA256_BLOCK_SIZE - ctx->len;
00221 unsigned int rem_len = len < tmp_len ? len : tmp_len;
00222
00223 memcpy(&ctx->block[ctx->len], message, rem_len);
00224 if (ctx->len + len < SHA256_BLOCK_SIZE)
00225 {
00226 ctx->len += len;
00227 return;
00228 }
00229 unsigned int new_len = len - rem_len;
00230 unsigned int block_nb = new_len / SHA256_BLOCK_SIZE;
00231 unsigned char *shifted_message = message + rem_len;
00232 SHA256Transform(ctx, ctx->block, 1);
00233 SHA256Transform(ctx, shifted_message, block_nb);
00234 rem_len = new_len % SHA256_BLOCK_SIZE;
00235 memcpy(ctx->block, &shifted_message[block_nb << 6],rem_len);
00236 ctx->len = rem_len;
00237 ctx->tot_len += (block_nb + 1) << 6;
00238 }
00239
00240 void SHA256Final(SHA256Context *ctx, unsigned char *digest)
00241 {
00242 unsigned int block_nb = (1 + ((SHA256_BLOCK_SIZE - 9) < (ctx->len % SHA256_BLOCK_SIZE)));
00243 unsigned int len_b = (ctx->tot_len + ctx->len) << 3;
00244 unsigned int pm_len = block_nb << 6;
00245 memset(ctx->block + ctx->len, 0, pm_len - ctx->len);
00246 ctx->block[ctx->len] = 0x80;
00247 UNPACK32(len_b, ctx->block + pm_len - 4);
00248 SHA256Transform(ctx, ctx->block, block_nb);
00249 for (int i = 0 ; i < 8; i++)
00250 UNPACK32(ctx->h[i], &digest[i << 2]);
00251 }
00252
00253 std::string SHA256Hash(const char *src, int len)
00254 {
00255
00256 unsigned char bytehash[SHA256_DIGEST_SIZE];
00257 SHA256Context ctx;
00258 SHA256Init(&ctx);
00259 SHA256Update(&ctx, (unsigned char *)src, (unsigned int)len);
00260 SHA256Final(&ctx, bytehash);
00261
00262 const char* hxc = "0123456789abcdef";
00263 std::string hash = "";
00264 for (int i = 0; i < SHA256_DIGEST_SIZE; i++)
00265 {
00266 hash += hxc[bytehash[i] / 16];
00267 hash += hxc[bytehash[i] % 16];
00268 }
00269 return hash;
00270 }
00271
00272 std::string sha256(const std::string& string)
00273 {
00274 return SHA256Hash(string.c_str(), string.length());
00275 }