xref: /OK3568_Linux_fs/external/security/librkcrypto/test/c_mode/hash_md5.c (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <string.h>
4 #include <assert.h>
5 #include "aes_core.h"
6 
7 #ifndef uint32_t
8 #define uint32_t unsigned int
9 #endif
10 
11 /**
12  * \brief          MD5 context structure
13  */
14 typedef struct
15 {
16     uint32_t total[2];          /*!< number of bytes processed  */
17     uint32_t state[4];          /*!< intermediate digest state  */
18     unsigned char buffer[64];   /*!< data block being processed */
19 }
20 RK_MD5_CTX;
21 
22 /* Implementation that should never be optimized out by the compiler */
mbedtls_zeroize(void * v,size_t n)23 static void mbedtls_zeroize( void *v, size_t n ) {
24     volatile unsigned char *p = v; while( n-- ) *p++ = 0;
25 }
26 
27 /*
28  * 32-bit integer manipulation macros (little endian)
29  */
30 #ifndef GET_UINT32_LE
31 #define GET_UINT32_LE(n,b,i)                            \
32 {                                                       \
33     (n) = ( (uint32_t) (b)[(i)    ]       )             \
34         | ( (uint32_t) (b)[(i) + 1] <<  8 )             \
35         | ( (uint32_t) (b)[(i) + 2] << 16 )             \
36         | ( (uint32_t) (b)[(i) + 3] << 24 );            \
37 }
38 #endif
39 
40 #ifndef PUT_UINT32_LE
41 #define PUT_UINT32_LE(n,b,i)                                    \
42 {                                                               \
43     (b)[(i)    ] = (unsigned char) ( ( (n)       ) & 0xFF );    \
44     (b)[(i) + 1] = (unsigned char) ( ( (n) >>  8 ) & 0xFF );    \
45     (b)[(i) + 2] = (unsigned char) ( ( (n) >> 16 ) & 0xFF );    \
46     (b)[(i) + 3] = (unsigned char) ( ( (n) >> 24 ) & 0xFF );    \
47 }
48 #endif
49 
mbedtls_md5_init(RK_MD5_CTX * ctx)50 void mbedtls_md5_init( RK_MD5_CTX *ctx )
51 {
52     memset( ctx, 0, sizeof( RK_MD5_CTX ) );
53 }
54 
mbedtls_md5_free(RK_MD5_CTX * ctx)55 void mbedtls_md5_free( RK_MD5_CTX *ctx )
56 {
57     if( ctx == NULL )
58         return;
59 
60     mbedtls_zeroize( ctx, sizeof( RK_MD5_CTX ) );
61 }
62 
mbedtls_md5_clone(RK_MD5_CTX * dst,const RK_MD5_CTX * src)63 void mbedtls_md5_clone( RK_MD5_CTX *dst,
64                         const RK_MD5_CTX *src )
65 {
66     *dst = *src;
67 }
68 
69 /*
70  * MD5 context setup
71  */
mbedtls_md5_starts(RK_MD5_CTX * ctx)72 void mbedtls_md5_starts( RK_MD5_CTX *ctx )
73 {
74     ctx->total[0] = 0;
75     ctx->total[1] = 0;
76 
77     ctx->state[0] = 0x67452301;
78     ctx->state[1] = 0xEFCDAB89;
79     ctx->state[2] = 0x98BADCFE;
80     ctx->state[3] = 0x10325476;
81 }
82 
83 #if !defined(MBEDTLS_MD5_PROCESS_ALT)
mbedtls_md5_process(RK_MD5_CTX * ctx,const unsigned char data[64])84 void mbedtls_md5_process( RK_MD5_CTX *ctx, const unsigned char data[64] )
85 {
86     uint32_t X[16], A, B, C, D;
87 
88     GET_UINT32_LE( X[ 0], data,  0 );
89     GET_UINT32_LE( X[ 1], data,  4 );
90     GET_UINT32_LE( X[ 2], data,  8 );
91     GET_UINT32_LE( X[ 3], data, 12 );
92     GET_UINT32_LE( X[ 4], data, 16 );
93     GET_UINT32_LE( X[ 5], data, 20 );
94     GET_UINT32_LE( X[ 6], data, 24 );
95     GET_UINT32_LE( X[ 7], data, 28 );
96     GET_UINT32_LE( X[ 8], data, 32 );
97     GET_UINT32_LE( X[ 9], data, 36 );
98     GET_UINT32_LE( X[10], data, 40 );
99     GET_UINT32_LE( X[11], data, 44 );
100     GET_UINT32_LE( X[12], data, 48 );
101     GET_UINT32_LE( X[13], data, 52 );
102     GET_UINT32_LE( X[14], data, 56 );
103     GET_UINT32_LE( X[15], data, 60 );
104 
105 #define S(x,n) ((x << n) | ((x & 0xFFFFFFFF) >> (32 - n)))
106 
107 #define P(a,b,c,d,k,s,t)                                \
108 {                                                       \
109     a += F(b,c,d) + X[k] + t; a = S(a,s) + b;           \
110 }
111 
112     A = ctx->state[0];
113     B = ctx->state[1];
114     C = ctx->state[2];
115     D = ctx->state[3];
116 
117 #define F(x,y,z) (z ^ (x & (y ^ z)))
118 
119     P( A, B, C, D,  0,  7, 0xD76AA478 );
120     P( D, A, B, C,  1, 12, 0xE8C7B756 );
121     P( C, D, A, B,  2, 17, 0x242070DB );
122     P( B, C, D, A,  3, 22, 0xC1BDCEEE );
123     P( A, B, C, D,  4,  7, 0xF57C0FAF );
124     P( D, A, B, C,  5, 12, 0x4787C62A );
125     P( C, D, A, B,  6, 17, 0xA8304613 );
126     P( B, C, D, A,  7, 22, 0xFD469501 );
127     P( A, B, C, D,  8,  7, 0x698098D8 );
128     P( D, A, B, C,  9, 12, 0x8B44F7AF );
129     P( C, D, A, B, 10, 17, 0xFFFF5BB1 );
130     P( B, C, D, A, 11, 22, 0x895CD7BE );
131     P( A, B, C, D, 12,  7, 0x6B901122 );
132     P( D, A, B, C, 13, 12, 0xFD987193 );
133     P( C, D, A, B, 14, 17, 0xA679438E );
134     P( B, C, D, A, 15, 22, 0x49B40821 );
135 
136 #undef F
137 
138 #define F(x,y,z) (y ^ (z & (x ^ y)))
139 
140     P( A, B, C, D,  1,  5, 0xF61E2562 );
141     P( D, A, B, C,  6,  9, 0xC040B340 );
142     P( C, D, A, B, 11, 14, 0x265E5A51 );
143     P( B, C, D, A,  0, 20, 0xE9B6C7AA );
144     P( A, B, C, D,  5,  5, 0xD62F105D );
145     P( D, A, B, C, 10,  9, 0x02441453 );
146     P( C, D, A, B, 15, 14, 0xD8A1E681 );
147     P( B, C, D, A,  4, 20, 0xE7D3FBC8 );
148     P( A, B, C, D,  9,  5, 0x21E1CDE6 );
149     P( D, A, B, C, 14,  9, 0xC33707D6 );
150     P( C, D, A, B,  3, 14, 0xF4D50D87 );
151     P( B, C, D, A,  8, 20, 0x455A14ED );
152     P( A, B, C, D, 13,  5, 0xA9E3E905 );
153     P( D, A, B, C,  2,  9, 0xFCEFA3F8 );
154     P( C, D, A, B,  7, 14, 0x676F02D9 );
155     P( B, C, D, A, 12, 20, 0x8D2A4C8A );
156 
157 #undef F
158 
159 #define F(x,y,z) (x ^ y ^ z)
160 
161     P( A, B, C, D,  5,  4, 0xFFFA3942 );
162     P( D, A, B, C,  8, 11, 0x8771F681 );
163     P( C, D, A, B, 11, 16, 0x6D9D6122 );
164     P( B, C, D, A, 14, 23, 0xFDE5380C );
165     P( A, B, C, D,  1,  4, 0xA4BEEA44 );
166     P( D, A, B, C,  4, 11, 0x4BDECFA9 );
167     P( C, D, A, B,  7, 16, 0xF6BB4B60 );
168     P( B, C, D, A, 10, 23, 0xBEBFBC70 );
169     P( A, B, C, D, 13,  4, 0x289B7EC6 );
170     P( D, A, B, C,  0, 11, 0xEAA127FA );
171     P( C, D, A, B,  3, 16, 0xD4EF3085 );
172     P( B, C, D, A,  6, 23, 0x04881D05 );
173     P( A, B, C, D,  9,  4, 0xD9D4D039 );
174     P( D, A, B, C, 12, 11, 0xE6DB99E5 );
175     P( C, D, A, B, 15, 16, 0x1FA27CF8 );
176     P( B, C, D, A,  2, 23, 0xC4AC5665 );
177 
178 #undef F
179 
180 #define F(x,y,z) (y ^ (x | ~z))
181 
182     P( A, B, C, D,  0,  6, 0xF4292244 );
183     P( D, A, B, C,  7, 10, 0x432AFF97 );
184     P( C, D, A, B, 14, 15, 0xAB9423A7 );
185     P( B, C, D, A,  5, 21, 0xFC93A039 );
186     P( A, B, C, D, 12,  6, 0x655B59C3 );
187     P( D, A, B, C,  3, 10, 0x8F0CCC92 );
188     P( C, D, A, B, 10, 15, 0xFFEFF47D );
189     P( B, C, D, A,  1, 21, 0x85845DD1 );
190     P( A, B, C, D,  8,  6, 0x6FA87E4F );
191     P( D, A, B, C, 15, 10, 0xFE2CE6E0 );
192     P( C, D, A, B,  6, 15, 0xA3014314 );
193     P( B, C, D, A, 13, 21, 0x4E0811A1 );
194     P( A, B, C, D,  4,  6, 0xF7537E82 );
195     P( D, A, B, C, 11, 10, 0xBD3AF235 );
196     P( C, D, A, B,  2, 15, 0x2AD7D2BB );
197     P( B, C, D, A,  9, 21, 0xEB86D391 );
198 
199 #undef F
200 
201     ctx->state[0] += A;
202     ctx->state[1] += B;
203     ctx->state[2] += C;
204     ctx->state[3] += D;
205 }
206 
207 /*
208  * MD5 process buffer
209  */
mbedtls_md5_update(RK_MD5_CTX * ctx,const unsigned char * input,size_t ilen)210 void mbedtls_md5_update( RK_MD5_CTX *ctx, const unsigned char *input, size_t ilen )
211 {
212     size_t fill;
213     uint32_t left;
214 
215     if( ilen == 0 )
216         return;
217 
218     left = ctx->total[0] & 0x3F;
219     fill = 64 - left;
220 
221     ctx->total[0] += (uint32_t) ilen;
222     ctx->total[0] &= 0xFFFFFFFF;
223 
224     if( ctx->total[0] < (uint32_t) ilen )
225         ctx->total[1]++;
226 
227     if( left && ilen >= fill )
228     {
229         memcpy( (void *) (ctx->buffer + left), input, fill );
230         mbedtls_md5_process( ctx, ctx->buffer );
231         input += fill;
232         ilen  -= fill;
233         left = 0;
234     }
235 
236     while( ilen >= 64 )
237     {
238         mbedtls_md5_process( ctx, input );
239         input += 64;
240         ilen  -= 64;
241     }
242 
243     if( ilen > 0 )
244     {
245         memcpy( (void *) (ctx->buffer + left), input, ilen );
246     }
247 }
248 
249 static const unsigned char md5_padding[64] =
250 {
251  0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
252     0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
253     0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
254     0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
255 };
256 
257 /*
258  * MD5 final digest
259  */
mbedtls_md5_finish(RK_MD5_CTX * ctx,unsigned char output[16])260 void mbedtls_md5_finish( RK_MD5_CTX *ctx, unsigned char output[16] )
261 {
262     uint32_t last, padn;
263     uint32_t high, low;
264     unsigned char msglen[8];
265 
266     high = ( ctx->total[0] >> 29 )
267          | ( ctx->total[1] <<  3 );
268     low  = ( ctx->total[0] <<  3 );
269 
270     PUT_UINT32_LE( low,  msglen, 0 );
271     PUT_UINT32_LE( high, msglen, 4 );
272 
273     last = ctx->total[0] & 0x3F;
274     padn = ( last < 56 ) ? ( 56 - last ) : ( 120 - last );
275 
276     mbedtls_md5_update( ctx, md5_padding, padn );
277     mbedtls_md5_update( ctx, msglen, 8 );
278 
279     PUT_UINT32_LE( ctx->state[0], output,  0 );
280     PUT_UINT32_LE( ctx->state[1], output,  4 );
281     PUT_UINT32_LE( ctx->state[2], output,  8 );
282     PUT_UINT32_LE( ctx->state[3], output, 12 );
283 }
284 
285 #endif /* !MBEDTLS_MD5_ALT */
286 
287 /*
288  * output = MD5( input buffer )
289  */
rk_hash_md5(const unsigned char * in,unsigned int in_len,unsigned char * out,unsigned int * out_len)290  int rk_hash_md5(const unsigned char *in, unsigned int in_len,
291 							unsigned char *out, unsigned int *out_len)
292 {
293     RK_MD5_CTX ctx;
294 
295 	if (in == NULL && in_len != 0)
296 		return -1;
297 
298 	if(out == NULL || out_len == NULL)
299 		return -1;
300 
301     mbedtls_md5_init( &ctx );
302     mbedtls_md5_starts( &ctx );
303     mbedtls_md5_update( &ctx, in, in_len );
304     mbedtls_md5_finish( &ctx, out );
305     mbedtls_md5_free( &ctx );
306 	*out_len = 16;
307 	return 0;
308 }
309 
310 
311