1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <string.h>
4 #include <assert.h>
5 #include "aes_core.h"
6
7 #define UL64(x) x##ULL
8 #ifndef uint64_t
9 #define uint64_t unsigned long long int
10 #endif
11
12 enum {
13 SHA_384 = 0,
14 SHA_512,
15 SHA_512_224,
16 SHA_512_256
17 };
18
19 /**
20 * \brief SHA-512 context structure
21 */
22 typedef struct
23 {
24 uint64_t total[2]; /*!< number of bytes processed */
25 uint64_t state[8]; /*!< intermediate digest state */
26 unsigned char buffer[128]; /*!< data block being processed */
27 int is384; /*!< 0 => SHA-512, else SHA-384 */
28 }
29 RK_SHA512_CTX;
30
31 /* Implementation that should never be optimized out by the compiler */
mbedtls_zeroize(void * v,size_t n)32 static void mbedtls_zeroize( void *v, size_t n ) {
33 volatile unsigned char *p = v; while( n-- ) *p++ = 0;
34 }
35
36 /*
37 * 64-bit integer manipulation macros (big endian)
38 */
39 #ifndef GET_UINT64_BE
40 #define GET_UINT64_BE(n,b,i) \
41 { \
42 (n) = ( (uint64_t) (b)[(i) ] << 56 ) \
43 | ( (uint64_t) (b)[(i) + 1] << 48 ) \
44 | ( (uint64_t) (b)[(i) + 2] << 40 ) \
45 | ( (uint64_t) (b)[(i) + 3] << 32 ) \
46 | ( (uint64_t) (b)[(i) + 4] << 24 ) \
47 | ( (uint64_t) (b)[(i) + 5] << 16 ) \
48 | ( (uint64_t) (b)[(i) + 6] << 8 ) \
49 | ( (uint64_t) (b)[(i) + 7] ); \
50 }
51 #endif /* GET_UINT64_BE */
52
53 #ifndef PUT_UINT64_BE
54 #define PUT_UINT64_BE(n,b,i) \
55 { \
56 (b)[(i) ] = (unsigned char) ( (n) >> 56 ); \
57 (b)[(i) + 1] = (unsigned char) ( (n) >> 48 ); \
58 (b)[(i) + 2] = (unsigned char) ( (n) >> 40 ); \
59 (b)[(i) + 3] = (unsigned char) ( (n) >> 32 ); \
60 (b)[(i) + 4] = (unsigned char) ( (n) >> 24 ); \
61 (b)[(i) + 5] = (unsigned char) ( (n) >> 16 ); \
62 (b)[(i) + 6] = (unsigned char) ( (n) >> 8 ); \
63 (b)[(i) + 7] = (unsigned char) ( (n) ); \
64 }
65 #endif /* PUT_UINT64_BE */
66
mbedtls_sha512_init(RK_SHA512_CTX * ctx)67 void mbedtls_sha512_init( RK_SHA512_CTX *ctx )
68 {
69 memset( ctx, 0, sizeof( RK_SHA512_CTX ) );
70 }
71
mbedtls_sha512_free(RK_SHA512_CTX * ctx)72 void mbedtls_sha512_free( RK_SHA512_CTX *ctx )
73 {
74 if( ctx == NULL )
75 return;
76
77 mbedtls_zeroize( ctx, sizeof( RK_SHA512_CTX ) );
78 }
79
mbedtls_sha512_clone(RK_SHA512_CTX * dst,const RK_SHA512_CTX * src)80 void mbedtls_sha512_clone( RK_SHA512_CTX *dst,
81 const RK_SHA512_CTX *src )
82 {
83 *dst = *src;
84 }
85
86 /*
87 * SHA-512 context setup
88 */
mbedtls_sha512_starts(RK_SHA512_CTX * ctx,int type)89 void mbedtls_sha512_starts( RK_SHA512_CTX *ctx, int type)
90 {
91 ctx->total[0] = 0;
92 ctx->total[1] = 0;
93
94 if( type == SHA_512)
95 {
96 /* SHA-512 */
97 ctx->state[0] = UL64(0x6A09E667F3BCC908);
98 ctx->state[1] = UL64(0xBB67AE8584CAA73B);
99 ctx->state[2] = UL64(0x3C6EF372FE94F82B);
100 ctx->state[3] = UL64(0xA54FF53A5F1D36F1);
101 ctx->state[4] = UL64(0x510E527FADE682D1);
102 ctx->state[5] = UL64(0x9B05688C2B3E6C1F);
103 ctx->state[6] = UL64(0x1F83D9ABFB41BD6B);
104 ctx->state[7] = UL64(0x5BE0CD19137E2179);
105 }
106 else if (type == SHA_384)
107 {
108 /* SHA-384 */
109 ctx->state[0] = UL64(0xCBBB9D5DC1059ED8);
110 ctx->state[1] = UL64(0x629A292A367CD507);
111 ctx->state[2] = UL64(0x9159015A3070DD17);
112 ctx->state[3] = UL64(0x152FECD8F70E5939);
113 ctx->state[4] = UL64(0x67332667FFC00B31);
114 ctx->state[5] = UL64(0x8EB44A8768581511);
115 ctx->state[6] = UL64(0xDB0C2E0D64F98FA7);
116 ctx->state[7] = UL64(0x47B5481DBEFA4FA4);
117 ctx->is384 = 1;
118 }
119 else if (type == SHA_512_224)
120 {
121 ctx->state[0] = UL64(0x8C3D37C819544DA2);
122 ctx->state[1] = UL64(0x73E1996689DCD4D6);
123 ctx->state[2] = UL64(0x1DFAB7AE32FF9C82);
124 ctx->state[3] = UL64(0x679DD514582F9FCF);
125 ctx->state[4] = UL64(0x0F6D2B697BD44DA8);
126 ctx->state[5] = UL64(0x77E36F7304C48942);
127 ctx->state[6] = UL64(0x3F9D85A86A1D36C8);
128 ctx->state[7] = UL64(0x1112E6AD91D692A1);
129 }
130 else if (type == SHA_512_256)
131 {
132 ctx->state[0] = UL64(0x22312194FC2BF72C);
133 ctx->state[1] = UL64(0x9F555FA3C84C64C2);
134 ctx->state[2] = UL64(0x2393B86B6F53B151);
135 ctx->state[3] = UL64(0x963877195940EABD);
136 ctx->state[4] = UL64(0x96283EE2A88EFFE3);
137 ctx->state[5] = UL64(0xBE5E1E2553863992);
138 ctx->state[6] = UL64(0x2B0199FC2C85B8AA);
139 ctx->state[7] = UL64(0x0EB72DDC81C52CA2);
140 }
141 else
142 {
143 ;
144 }
145 }
146
147 /*
148 * Round constants
149 */
150 static const uint64_t K[80] =
151 {
152 UL64(0x428A2F98D728AE22), UL64(0x7137449123EF65CD),
153 UL64(0xB5C0FBCFEC4D3B2F), UL64(0xE9B5DBA58189DBBC),
154 UL64(0x3956C25BF348B538), UL64(0x59F111F1B605D019),
155 UL64(0x923F82A4AF194F9B), UL64(0xAB1C5ED5DA6D8118),
156 UL64(0xD807AA98A3030242), UL64(0x12835B0145706FBE),
157 UL64(0x243185BE4EE4B28C), UL64(0x550C7DC3D5FFB4E2),
158 UL64(0x72BE5D74F27B896F), UL64(0x80DEB1FE3B1696B1),
159 UL64(0x9BDC06A725C71235), UL64(0xC19BF174CF692694),
160 UL64(0xE49B69C19EF14AD2), UL64(0xEFBE4786384F25E3),
161 UL64(0x0FC19DC68B8CD5B5), UL64(0x240CA1CC77AC9C65),
162 UL64(0x2DE92C6F592B0275), UL64(0x4A7484AA6EA6E483),
163 UL64(0x5CB0A9DCBD41FBD4), UL64(0x76F988DA831153B5),
164 UL64(0x983E5152EE66DFAB), UL64(0xA831C66D2DB43210),
165 UL64(0xB00327C898FB213F), UL64(0xBF597FC7BEEF0EE4),
166 UL64(0xC6E00BF33DA88FC2), UL64(0xD5A79147930AA725),
167 UL64(0x06CA6351E003826F), UL64(0x142929670A0E6E70),
168 UL64(0x27B70A8546D22FFC), UL64(0x2E1B21385C26C926),
169 UL64(0x4D2C6DFC5AC42AED), UL64(0x53380D139D95B3DF),
170 UL64(0x650A73548BAF63DE), UL64(0x766A0ABB3C77B2A8),
171 UL64(0x81C2C92E47EDAEE6), UL64(0x92722C851482353B),
172 UL64(0xA2BFE8A14CF10364), UL64(0xA81A664BBC423001),
173 UL64(0xC24B8B70D0F89791), UL64(0xC76C51A30654BE30),
174 UL64(0xD192E819D6EF5218), UL64(0xD69906245565A910),
175 UL64(0xF40E35855771202A), UL64(0x106AA07032BBD1B8),
176 UL64(0x19A4C116B8D2D0C8), UL64(0x1E376C085141AB53),
177 UL64(0x2748774CDF8EEB99), UL64(0x34B0BCB5E19B48A8),
178 UL64(0x391C0CB3C5C95A63), UL64(0x4ED8AA4AE3418ACB),
179 UL64(0x5B9CCA4F7763E373), UL64(0x682E6FF3D6B2B8A3),
180 UL64(0x748F82EE5DEFB2FC), UL64(0x78A5636F43172F60),
181 UL64(0x84C87814A1F0AB72), UL64(0x8CC702081A6439EC),
182 UL64(0x90BEFFFA23631E28), UL64(0xA4506CEBDE82BDE9),
183 UL64(0xBEF9A3F7B2C67915), UL64(0xC67178F2E372532B),
184 UL64(0xCA273ECEEA26619C), UL64(0xD186B8C721C0C207),
185 UL64(0xEADA7DD6CDE0EB1E), UL64(0xF57D4F7FEE6ED178),
186 UL64(0x06F067AA72176FBA), UL64(0x0A637DC5A2C898A6),
187 UL64(0x113F9804BEF90DAE), UL64(0x1B710B35131C471B),
188 UL64(0x28DB77F523047D84), UL64(0x32CAAB7B40C72493),
189 UL64(0x3C9EBE0A15C9BEBC), UL64(0x431D67C49C100D4C),
190 UL64(0x4CC5D4BECB3E42B6), UL64(0x597F299CFC657E2A),
191 UL64(0x5FCB6FAB3AD6FAEC), UL64(0x6C44198C4A475817)
192 };
193
mbedtls_sha512_process(RK_SHA512_CTX * ctx,const unsigned char data[128])194 void mbedtls_sha512_process( RK_SHA512_CTX *ctx, const unsigned char data[128] )
195 {
196 int i;
197 uint64_t temp1, temp2, W[80];
198 uint64_t A, B, C, D, E, F, G, H;
199
200 #define SHR(x,n) (x >> n)
201 #define ROTR(x,n) (SHR(x,n) | (x << (64 - n)))
202
203 #define S0(x) (ROTR(x, 1) ^ ROTR(x, 8) ^ SHR(x, 7))
204 #define S1(x) (ROTR(x,19) ^ ROTR(x,61) ^ SHR(x, 6))
205
206 #define S2(x) (ROTR(x,28) ^ ROTR(x,34) ^ ROTR(x,39))
207 #define S3(x) (ROTR(x,14) ^ ROTR(x,18) ^ ROTR(x,41))
208
209 #define F0(x,y,z) ((x & y) | (z & (x | y)))
210 #define F1(x,y,z) (z ^ (x & (y ^ z)))
211
212 #define P(a,b,c,d,e,f,g,h,x,K) \
213 { \
214 temp1 = h + S3(e) + F1(e,f,g) + K + x; \
215 temp2 = S2(a) + F0(a,b,c); \
216 d += temp1; h = temp1 + temp2; \
217 }
218
219 for( i = 0; i < 16; i++ )
220 {
221 GET_UINT64_BE( W[i], data, i << 3 );
222 }
223
224 for( ; i < 80; i++ )
225 {
226 W[i] = S1(W[i - 2]) + W[i - 7] +
227 S0(W[i - 15]) + W[i - 16];
228 }
229
230 A = ctx->state[0];
231 B = ctx->state[1];
232 C = ctx->state[2];
233 D = ctx->state[3];
234 E = ctx->state[4];
235 F = ctx->state[5];
236 G = ctx->state[6];
237 H = ctx->state[7];
238 i = 0;
239
240 do
241 {
242 P( A, B, C, D, E, F, G, H, W[i], K[i] ); i++;
243 P( H, A, B, C, D, E, F, G, W[i], K[i] ); i++;
244 P( G, H, A, B, C, D, E, F, W[i], K[i] ); i++;
245 P( F, G, H, A, B, C, D, E, W[i], K[i] ); i++;
246 P( E, F, G, H, A, B, C, D, W[i], K[i] ); i++;
247 P( D, E, F, G, H, A, B, C, W[i], K[i] ); i++;
248 P( C, D, E, F, G, H, A, B, W[i], K[i] ); i++;
249 P( B, C, D, E, F, G, H, A, W[i], K[i] ); i++;
250 }
251 while( i < 80 );
252
253 ctx->state[0] += A;
254 ctx->state[1] += B;
255 ctx->state[2] += C;
256 ctx->state[3] += D;
257 ctx->state[4] += E;
258 ctx->state[5] += F;
259 ctx->state[6] += G;
260 ctx->state[7] += H;
261 }
262
263 /*
264 * SHA-512 process buffer
265 */
mbedtls_sha512_update(RK_SHA512_CTX * ctx,const unsigned char * input,size_t ilen)266 void mbedtls_sha512_update( RK_SHA512_CTX *ctx, const unsigned char *input,
267 size_t ilen )
268 {
269 size_t fill;
270 unsigned int left;
271
272 if( ilen == 0 )
273 return;
274
275 left = (unsigned int) (ctx->total[0] & 0x7F);
276 fill = 128 - left;
277
278 ctx->total[0] += (uint64_t) ilen;
279
280 if( ctx->total[0] < (uint64_t) ilen )
281 ctx->total[1]++;
282
283 if( left && ilen >= fill )
284 {
285 memcpy( (void *) (ctx->buffer + left), input, fill );
286 mbedtls_sha512_process( ctx, ctx->buffer );
287 input += fill;
288 ilen -= fill;
289 left = 0;
290 }
291
292 while( ilen >= 128 )
293 {
294 mbedtls_sha512_process( ctx, input );
295 input += 128;
296 ilen -= 128;
297 }
298
299 if( ilen > 0 )
300 memcpy( (void *) (ctx->buffer + left), input, ilen );
301 }
302
303 static const unsigned char sha512_padding[128] =
304 {
305 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
306 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
307 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
308 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
309 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
310 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
311 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
312 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
313 };
314
315 /*
316 * SHA-512 final digest
317 */
mbedtls_sha512_finish(RK_SHA512_CTX * ctx,unsigned char output[64])318 void mbedtls_sha512_finish( RK_SHA512_CTX *ctx, unsigned char output[64] )
319 {
320 size_t last, padn;
321 uint64_t high, low;
322 unsigned char msglen[16];
323
324 high = ( ctx->total[0] >> 61 )
325 | ( ctx->total[1] << 3 );
326 low = ( ctx->total[0] << 3 );
327
328 PUT_UINT64_BE( high, msglen, 0 );
329 PUT_UINT64_BE( low, msglen, 8 );
330
331 last = (size_t)( ctx->total[0] & 0x7F );
332 padn = ( last < 112 ) ? ( 112 - last ) : ( 240 - last );
333
334 mbedtls_sha512_update( ctx, sha512_padding, padn );
335 mbedtls_sha512_update( ctx, msglen, 16 );
336
337 PUT_UINT64_BE( ctx->state[0], output, 0 );
338 PUT_UINT64_BE( ctx->state[1], output, 8 );
339 PUT_UINT64_BE( ctx->state[2], output, 16 );
340 PUT_UINT64_BE( ctx->state[3], output, 24 );
341 PUT_UINT64_BE( ctx->state[4], output, 32 );
342 PUT_UINT64_BE( ctx->state[5], output, 40 );
343
344 if( ctx->is384 == 0 )
345 {
346 PUT_UINT64_BE( ctx->state[6], output, 48 );
347 PUT_UINT64_BE( ctx->state[7], output, 56 );
348 }
349 }
350
351
352 /*
353 * output = SHA-512( input buffer )
354 */
rk_hash_sha512(const unsigned char * in,unsigned int in_len,unsigned char * out,unsigned int * out_len)355 int rk_hash_sha512(const unsigned char *in, unsigned int in_len,
356 unsigned char *out, unsigned int *out_len)
357 {
358 RK_SHA512_CTX ctx;
359
360 if (in == NULL && in_len != 0)
361 return -1;
362
363 if(out == NULL || out_len == NULL)
364 return -1;
365
366 mbedtls_sha512_init( &ctx );
367 mbedtls_sha512_starts( &ctx, SHA_512);
368 mbedtls_sha512_update( &ctx, in, in_len );
369 mbedtls_sha512_finish( &ctx, out );
370 mbedtls_sha512_free( &ctx );
371 *out_len = 64;
372 return 0;
373 }
374
rk_hash_sha384(const unsigned char * in,unsigned int in_len,unsigned char * out,unsigned int * out_len)375 int rk_hash_sha384(const unsigned char *in, unsigned int in_len,
376 unsigned char *out, unsigned int *out_len)
377 {
378 RK_SHA512_CTX ctx;
379
380 if (in == NULL && in_len != 0)
381 return -1;
382
383 if(out == NULL || out_len == NULL)
384 return -1;
385
386 mbedtls_sha512_init( &ctx );
387 mbedtls_sha512_starts( &ctx, SHA_384);
388 mbedtls_sha512_update( &ctx, in, in_len );
389 mbedtls_sha512_finish( &ctx, out );
390 mbedtls_sha512_free( &ctx );
391 *out_len = 48;
392 return 0;
393 }
394
rk_hash_sha512_224(const unsigned char * in,unsigned int in_len,unsigned char * out,unsigned int * out_len)395 int rk_hash_sha512_224(const unsigned char *in, unsigned int in_len,
396 unsigned char *out, unsigned int *out_len)
397 {
398 RK_SHA512_CTX ctx;
399
400 if (in == NULL && in_len != 0)
401 return -1;
402
403 if(out == NULL || out_len == NULL)
404 return -1;
405
406 mbedtls_sha512_init( &ctx );
407 mbedtls_sha512_starts( &ctx, SHA_512_224);
408 mbedtls_sha512_update( &ctx, in, in_len );
409 mbedtls_sha512_finish( &ctx, out );
410 mbedtls_sha512_free( &ctx );
411 *out_len = 28;
412 return 0;
413 }
414
rk_hash_sha512_256(const unsigned char * in,unsigned int in_len,unsigned char * out,unsigned int * out_len)415 int rk_hash_sha512_256(const unsigned char *in, unsigned int in_len,
416 unsigned char *out, unsigned int *out_len)
417 {
418 RK_SHA512_CTX ctx;
419
420 if (in == NULL && in_len != 0)
421 return -1;
422
423 if(out == NULL || out_len == NULL)
424 return -1;
425
426 mbedtls_sha512_init( &ctx );
427 mbedtls_sha512_starts( &ctx, SHA_512_256);
428 mbedtls_sha512_update( &ctx, in, in_len );
429 mbedtls_sha512_finish( &ctx, out );
430 mbedtls_sha512_free( &ctx );
431 *out_len = 32;
432 return 0;
433 }
434
435