xref: /openbsd/lib/libcrypto/ripemd/ripemd.c (revision 4bdff4be)
1 /* $OpenBSD: ripemd.c,v 1.7 2023/08/10 12:27:35 jsing Exp $ */
2 /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
3  * All rights reserved.
4  *
5  * This package is an SSL implementation written
6  * by Eric Young (eay@cryptsoft.com).
7  * The implementation was written so as to conform with Netscapes SSL.
8  *
9  * This library is free for commercial and non-commercial use as long as
10  * the following conditions are aheared to.  The following conditions
11  * apply to all code found in this distribution, be it the RC4, RSA,
12  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
13  * included with this distribution is covered by the same copyright terms
14  * except that the holder is Tim Hudson (tjh@cryptsoft.com).
15  *
16  * Copyright remains Eric Young's, and as such any Copyright notices in
17  * the code are not to be removed.
18  * If this package is used in a product, Eric Young should be given attribution
19  * as the author of the parts of the library used.
20  * This can be in the form of a textual message at program startup or
21  * in documentation (online or textual) provided with the package.
22  *
23  * Redistribution and use in source and binary forms, with or without
24  * modification, are permitted provided that the following conditions
25  * are met:
26  * 1. Redistributions of source code must retain the copyright
27  *    notice, this list of conditions and the following disclaimer.
28  * 2. Redistributions in binary form must reproduce the above copyright
29  *    notice, this list of conditions and the following disclaimer in the
30  *    documentation and/or other materials provided with the distribution.
31  * 3. All advertising materials mentioning features or use of this software
32  *    must display the following acknowledgement:
33  *    "This product includes cryptographic software written by
34  *     Eric Young (eay@cryptsoft.com)"
35  *    The word 'cryptographic' can be left out if the rouines from the library
36  *    being used are not cryptographic related :-).
37  * 4. If you include any Windows specific code (or a derivative thereof) from
38  *    the apps directory (application code) you must include an acknowledgement:
39  *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
40  *
41  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
42  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
43  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
44  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
45  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
46  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
47  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
48  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
49  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
50  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
51  * SUCH DAMAGE.
52  *
53  * The licence and distribution terms for any publically available version or
54  * derivative of this code cannot be changed.  i.e. this code cannot simply be
55  * copied and put under another distribution licence
56  * [including the GNU Public Licence.]
57  */
58 
59 #include <stdio.h>
60 #include <openssl/opensslv.h>
61 #include <openssl/crypto.h>
62 
63 #include <stdlib.h>
64 #include <string.h>
65 #include <openssl/opensslconf.h>
66 #include <openssl/ripemd.h>
67 
68 /*
69  * DO EXAMINE COMMENTS IN crypto/md5/md5_locl.h & crypto/md5/md5_dgst.c
70  * FOR EXPLANATIONS ON FOLLOWING "CODE."
71  *					<appro@fy.chalmers.se>
72  */
73 #ifdef RMD160_ASM
74 # if defined(__i386) || defined(__i386__) || defined(_M_IX86) || defined(__INTEL__)
75 #  define ripemd160_block_data_order ripemd160_block_asm_data_order
76 # endif
77 #endif
78 
79 __BEGIN_HIDDEN_DECLS
80 
81 void ripemd160_block_data_order (RIPEMD160_CTX *c, const void *p, size_t num);
82 
83 __END_HIDDEN_DECLS
84 
85 #define DATA_ORDER_IS_LITTLE_ENDIAN
86 
87 #define HASH_LONG               RIPEMD160_LONG
88 #define HASH_CTX                RIPEMD160_CTX
89 #define HASH_CBLOCK             RIPEMD160_CBLOCK
90 #define HASH_UPDATE             RIPEMD160_Update
91 #define HASH_TRANSFORM          RIPEMD160_Transform
92 #define HASH_FINAL              RIPEMD160_Final
93 #define	HASH_MAKE_STRING(c,s)	do {	\
94 	unsigned long ll;		\
95 	ll=(c)->A; HOST_l2c(ll,(s));	\
96 	ll=(c)->B; HOST_l2c(ll,(s));	\
97 	ll=(c)->C; HOST_l2c(ll,(s));	\
98 	ll=(c)->D; HOST_l2c(ll,(s));	\
99 	ll=(c)->E; HOST_l2c(ll,(s));	\
100 	} while (0)
101 #define HASH_BLOCK_DATA_ORDER   ripemd160_block_data_order
102 
103 #include "md32_common.h"
104 
105 #if 0
106 #define F1(x,y,z)	 ((x)^(y)^(z))
107 #define F2(x,y,z)	(((x)&(y))|((~x)&z))
108 #define F3(x,y,z)	(((x)|(~y))^(z))
109 #define F4(x,y,z)	(((x)&(z))|((y)&(~(z))))
110 #define F5(x,y,z)	 ((x)^((y)|(~(z))))
111 #else
112 /*
113  * Transformed F2 and F4 are courtesy of Wei Dai <weidai@eskimo.com>
114  */
115 #define F1(x,y,z)	((x) ^ (y) ^ (z))
116 #define F2(x,y,z)	((((y) ^ (z)) & (x)) ^ (z))
117 #define F3(x,y,z)	(((~(y)) | (x)) ^ (z))
118 #define F4(x,y,z)	((((x) ^ (y)) & (z)) ^ (y))
119 #define F5(x,y,z)	(((~(z)) | (y)) ^ (x))
120 #endif
121 
122 #define RIPEMD160_A	0x67452301L
123 #define RIPEMD160_B	0xEFCDAB89L
124 #define RIPEMD160_C	0x98BADCFEL
125 #define RIPEMD160_D	0x10325476L
126 #define RIPEMD160_E	0xC3D2E1F0L
127 
128 #define KL0 0x00000000L
129 #define KL1 0x5A827999L
130 #define KL2 0x6ED9EBA1L
131 #define KL3 0x8F1BBCDCL
132 #define KL4 0xA953FD4EL
133 
134 #define KR0 0x50A28BE6L
135 #define KR1 0x5C4DD124L
136 #define KR2 0x6D703EF3L
137 #define KR3 0x7A6D76E9L
138 #define KR4 0x00000000L
139 
140 #define RIP1(a,b,c,d,e,w,s) { \
141 	a+=F1(b,c,d)+w; \
142         a=ROTATE(a,s)+e; \
143         c=ROTATE(c,10); }
144 
145 #define RIP2(a,b,c,d,e,w,s,K) { \
146 	a+=F2(b,c,d)+w+K; \
147         a=ROTATE(a,s)+e; \
148         c=ROTATE(c,10); }
149 
150 #define RIP3(a,b,c,d,e,w,s,K) { \
151 	a+=F3(b,c,d)+w+K; \
152         a=ROTATE(a,s)+e; \
153         c=ROTATE(c,10); }
154 
155 #define RIP4(a,b,c,d,e,w,s,K) { \
156 	a+=F4(b,c,d)+w+K; \
157         a=ROTATE(a,s)+e; \
158         c=ROTATE(c,10); }
159 
160 #define RIP5(a,b,c,d,e,w,s,K) { \
161 	a+=F5(b,c,d)+w+K; \
162         a=ROTATE(a,s)+e; \
163         c=ROTATE(c,10); }
164 
165 #  ifdef RMD160_ASM
166 void ripemd160_block_x86(RIPEMD160_CTX *c, unsigned long *p, size_t num);
167 #    define ripemd160_block ripemd160_block_x86
168 #  else
169 void ripemd160_block(RIPEMD160_CTX *c, unsigned long *p, size_t num);
170 #  endif
171 
172 int
173 RIPEMD160_Init(RIPEMD160_CTX *c)
174 {
175 	memset (c, 0, sizeof(*c));
176 	c->A = RIPEMD160_A;
177 	c->B = RIPEMD160_B;
178 	c->C = RIPEMD160_C;
179 	c->D = RIPEMD160_D;
180 	c->E = RIPEMD160_E;
181 	return 1;
182 }
183 
184 #ifndef ripemd160_block_data_order
185 void
186 ripemd160_block_data_order(RIPEMD160_CTX *ctx, const void *p, size_t num)
187 {
188 	const unsigned char *data = p;
189 	unsigned int A, B, C, D, E;
190 	unsigned int a, b, c, d, e, l;
191 	unsigned int X0, X1, X2, X3, X4, X5, X6, X7,
192 	    X8, X9, X10, X11, X12, X13, X14, X15;
193 
194 	for (; num--; ) {
195 
196 		A = ctx->A;
197 		B = ctx->B;
198 		C = ctx->C;
199 		D = ctx->D;
200 		E = ctx->E;
201 
202 		HOST_c2l(data, l);
203 		X0 = l;
204 		HOST_c2l(data, l);
205 		X1 = l;
206 		RIP1(A, B, C, D, E, X0, 11);
207 		HOST_c2l(data, l);
208 		X2 = l;
209 		RIP1(E, A, B, C, D, X1, 14);
210 		HOST_c2l(data, l);
211 		X3 = l;
212 		RIP1(D, E, A, B, C, X2, 15);
213 		HOST_c2l(data, l);
214 		X4 = l;
215 		RIP1(C, D, E, A, B, X3, 12);
216 		HOST_c2l(data, l);
217 		X5 = l;
218 		RIP1(B, C, D, E, A, X4, 5);
219 		HOST_c2l(data, l);
220 		X6 = l;
221 		RIP1(A, B, C, D, E, X5, 8);
222 		HOST_c2l(data, l);
223 		X7 = l;
224 		RIP1(E, A, B, C, D, X6, 7);
225 		HOST_c2l(data, l);
226 		X8 = l;
227 		RIP1(D, E, A, B, C, X7, 9);
228 		HOST_c2l(data, l);
229 		X9 = l;
230 		RIP1(C, D, E, A, B, X8, 11);
231 		HOST_c2l(data, l);
232 		X10 = l;
233 		RIP1(B, C, D, E, A, X9, 13);
234 		HOST_c2l(data, l);
235 		X11 = l;
236 		RIP1(A, B, C, D, E, X10, 14);
237 		HOST_c2l(data, l);
238 		X12 = l;
239 		RIP1(E, A, B, C, D, X11, 15);
240 		HOST_c2l(data, l);
241 		X13 = l;
242 		RIP1(D, E, A, B, C, X12, 6);
243 		HOST_c2l(data, l);
244 		X14 = l;
245 		RIP1(C, D, E, A, B, X13, 7);
246 		HOST_c2l(data, l);
247 		X15 = l;
248 		RIP1(B, C, D, E, A, X14, 9);
249 		RIP1(A, B, C, D, E, X15, 8);
250 
251 		RIP2(E, A, B, C, D, X7, 7, KL1);
252 		RIP2(D, E, A, B, C, X4, 6, KL1);
253 		RIP2(C, D, E, A, B, X13, 8, KL1);
254 		RIP2(B, C, D, E, A, X1, 13, KL1);
255 		RIP2(A, B, C, D, E, X10, 11, KL1);
256 		RIP2(E, A, B, C, D, X6, 9, KL1);
257 		RIP2(D, E, A, B, C, X15, 7, KL1);
258 		RIP2(C, D, E, A, B, X3, 15, KL1);
259 		RIP2(B, C, D, E, A, X12, 7, KL1);
260 		RIP2(A, B, C, D, E, X0, 12, KL1);
261 		RIP2(E, A, B, C, D, X9, 15, KL1);
262 		RIP2(D, E, A, B, C, X5, 9, KL1);
263 		RIP2(C, D, E, A, B, X2, 11, KL1);
264 		RIP2(B, C, D, E, A, X14, 7, KL1);
265 		RIP2(A, B, C, D, E, X11, 13, KL1);
266 		RIP2(E, A, B, C, D, X8, 12, KL1);
267 
268 		RIP3(D, E, A, B, C, X3, 11, KL2);
269 		RIP3(C, D, E, A, B, X10, 13, KL2);
270 		RIP3(B, C, D, E, A, X14, 6, KL2);
271 		RIP3(A, B, C, D, E, X4, 7, KL2);
272 		RIP3(E, A, B, C, D, X9, 14, KL2);
273 		RIP3(D, E, A, B, C, X15, 9, KL2);
274 		RIP3(C, D, E, A, B, X8, 13, KL2);
275 		RIP3(B, C, D, E, A, X1, 15, KL2);
276 		RIP3(A, B, C, D, E, X2, 14, KL2);
277 		RIP3(E, A, B, C, D, X7, 8, KL2);
278 		RIP3(D, E, A, B, C, X0, 13, KL2);
279 		RIP3(C, D, E, A, B, X6, 6, KL2);
280 		RIP3(B, C, D, E, A, X13, 5, KL2);
281 		RIP3(A, B, C, D, E, X11, 12, KL2);
282 		RIP3(E, A, B, C, D, X5, 7, KL2);
283 		RIP3(D, E, A, B, C, X12, 5, KL2);
284 
285 		RIP4(C, D, E, A, B, X1, 11, KL3);
286 		RIP4(B, C, D, E, A, X9, 12, KL3);
287 		RIP4(A, B, C, D, E, X11, 14, KL3);
288 		RIP4(E, A, B, C, D, X10, 15, KL3);
289 		RIP4(D, E, A, B, C, X0, 14, KL3);
290 		RIP4(C, D, E, A, B, X8, 15, KL3);
291 		RIP4(B, C, D, E, A, X12, 9, KL3);
292 		RIP4(A, B, C, D, E, X4, 8, KL3);
293 		RIP4(E, A, B, C, D, X13, 9, KL3);
294 		RIP4(D, E, A, B, C, X3, 14, KL3);
295 		RIP4(C, D, E, A, B, X7, 5, KL3);
296 		RIP4(B, C, D, E, A, X15, 6, KL3);
297 		RIP4(A, B, C, D, E, X14, 8, KL3);
298 		RIP4(E, A, B, C, D, X5, 6, KL3);
299 		RIP4(D, E, A, B, C, X6, 5, KL3);
300 		RIP4(C, D, E, A, B, X2, 12, KL3);
301 
302 		RIP5(B, C, D, E, A, X4, 9, KL4);
303 		RIP5(A, B, C, D, E, X0, 15, KL4);
304 		RIP5(E, A, B, C, D, X5, 5, KL4);
305 		RIP5(D, E, A, B, C, X9, 11, KL4);
306 		RIP5(C, D, E, A, B, X7, 6, KL4);
307 		RIP5(B, C, D, E, A, X12, 8, KL4);
308 		RIP5(A, B, C, D, E, X2, 13, KL4);
309 		RIP5(E, A, B, C, D, X10, 12, KL4);
310 		RIP5(D, E, A, B, C, X14, 5, KL4);
311 		RIP5(C, D, E, A, B, X1, 12, KL4);
312 		RIP5(B, C, D, E, A, X3, 13, KL4);
313 		RIP5(A, B, C, D, E, X8, 14, KL4);
314 		RIP5(E, A, B, C, D, X11, 11, KL4);
315 		RIP5(D, E, A, B, C, X6, 8, KL4);
316 		RIP5(C, D, E, A, B, X15, 5, KL4);
317 		RIP5(B, C, D, E, A, X13, 6, KL4);
318 
319 		a = A;
320 		b = B;
321 		c = C;
322 		d = D;
323 		e = E;
324 		/* Do other half */
325 		A = ctx->A;
326 		B = ctx->B;
327 		C = ctx->C;
328 		D = ctx->D;
329 		E = ctx->E;
330 
331 		RIP5(A, B, C, D, E, X5, 8, KR0);
332 		RIP5(E, A, B, C, D, X14, 9, KR0);
333 		RIP5(D, E, A, B, C, X7, 9, KR0);
334 		RIP5(C, D, E, A, B, X0, 11, KR0);
335 		RIP5(B, C, D, E, A, X9, 13, KR0);
336 		RIP5(A, B, C, D, E, X2, 15, KR0);
337 		RIP5(E, A, B, C, D, X11, 15, KR0);
338 		RIP5(D, E, A, B, C, X4, 5, KR0);
339 		RIP5(C, D, E, A, B, X13, 7, KR0);
340 		RIP5(B, C, D, E, A, X6, 7, KR0);
341 		RIP5(A, B, C, D, E, X15, 8, KR0);
342 		RIP5(E, A, B, C, D, X8, 11, KR0);
343 		RIP5(D, E, A, B, C, X1, 14, KR0);
344 		RIP5(C, D, E, A, B, X10, 14, KR0);
345 		RIP5(B, C, D, E, A, X3, 12, KR0);
346 		RIP5(A, B, C, D, E, X12, 6, KR0);
347 
348 		RIP4(E, A, B, C, D, X6, 9, KR1);
349 		RIP4(D, E, A, B, C, X11, 13, KR1);
350 		RIP4(C, D, E, A, B, X3, 15, KR1);
351 		RIP4(B, C, D, E, A, X7, 7, KR1);
352 		RIP4(A, B, C, D, E, X0, 12, KR1);
353 		RIP4(E, A, B, C, D, X13, 8, KR1);
354 		RIP4(D, E, A, B, C, X5, 9, KR1);
355 		RIP4(C, D, E, A, B, X10, 11, KR1);
356 		RIP4(B, C, D, E, A, X14, 7, KR1);
357 		RIP4(A, B, C, D, E, X15, 7, KR1);
358 		RIP4(E, A, B, C, D, X8, 12, KR1);
359 		RIP4(D, E, A, B, C, X12, 7, KR1);
360 		RIP4(C, D, E, A, B, X4, 6, KR1);
361 		RIP4(B, C, D, E, A, X9, 15, KR1);
362 		RIP4(A, B, C, D, E, X1, 13, KR1);
363 		RIP4(E, A, B, C, D, X2, 11, KR1);
364 
365 		RIP3(D, E, A, B, C, X15, 9, KR2);
366 		RIP3(C, D, E, A, B, X5, 7, KR2);
367 		RIP3(B, C, D, E, A, X1, 15, KR2);
368 		RIP3(A, B, C, D, E, X3, 11, KR2);
369 		RIP3(E, A, B, C, D, X7, 8, KR2);
370 		RIP3(D, E, A, B, C, X14, 6, KR2);
371 		RIP3(C, D, E, A, B, X6, 6, KR2);
372 		RIP3(B, C, D, E, A, X9, 14, KR2);
373 		RIP3(A, B, C, D, E, X11, 12, KR2);
374 		RIP3(E, A, B, C, D, X8, 13, KR2);
375 		RIP3(D, E, A, B, C, X12, 5, KR2);
376 		RIP3(C, D, E, A, B, X2, 14, KR2);
377 		RIP3(B, C, D, E, A, X10, 13, KR2);
378 		RIP3(A, B, C, D, E, X0, 13, KR2);
379 		RIP3(E, A, B, C, D, X4, 7, KR2);
380 		RIP3(D, E, A, B, C, X13, 5, KR2);
381 
382 		RIP2(C, D, E, A, B, X8, 15, KR3);
383 		RIP2(B, C, D, E, A, X6, 5, KR3);
384 		RIP2(A, B, C, D, E, X4, 8, KR3);
385 		RIP2(E, A, B, C, D, X1, 11, KR3);
386 		RIP2(D, E, A, B, C, X3, 14, KR3);
387 		RIP2(C, D, E, A, B, X11, 14, KR3);
388 		RIP2(B, C, D, E, A, X15, 6, KR3);
389 		RIP2(A, B, C, D, E, X0, 14, KR3);
390 		RIP2(E, A, B, C, D, X5, 6, KR3);
391 		RIP2(D, E, A, B, C, X12, 9, KR3);
392 		RIP2(C, D, E, A, B, X2, 12, KR3);
393 		RIP2(B, C, D, E, A, X13, 9, KR3);
394 		RIP2(A, B, C, D, E, X9, 12, KR3);
395 		RIP2(E, A, B, C, D, X7, 5, KR3);
396 		RIP2(D, E, A, B, C, X10, 15, KR3);
397 		RIP2(C, D, E, A, B, X14, 8, KR3);
398 
399 		RIP1(B, C, D, E, A, X12, 8);
400 		RIP1(A, B, C, D, E, X15, 5);
401 		RIP1(E, A, B, C, D, X10, 12);
402 		RIP1(D, E, A, B, C, X4, 9);
403 		RIP1(C, D, E, A, B, X1, 12);
404 		RIP1(B, C, D, E, A, X5, 5);
405 		RIP1(A, B, C, D, E, X8, 14);
406 		RIP1(E, A, B, C, D, X7, 6);
407 		RIP1(D, E, A, B, C, X6, 8);
408 		RIP1(C, D, E, A, B, X2, 13);
409 		RIP1(B, C, D, E, A, X13, 6);
410 		RIP1(A, B, C, D, E, X14, 5);
411 		RIP1(E, A, B, C, D, X0, 15);
412 		RIP1(D, E, A, B, C, X3, 13);
413 		RIP1(C, D, E, A, B, X9, 11);
414 		RIP1(B, C, D, E, A, X11, 11);
415 
416 		D = ctx->B + c + D;
417 		ctx->B = ctx->C + d + E;
418 		ctx->C = ctx->D + e + A;
419 		ctx->D = ctx->E + a + B;
420 		ctx->E = ctx->A + b + C;
421 		ctx->A = D;
422 
423 	}
424 }
425 #endif
426 
427 unsigned char *
428 RIPEMD160(const unsigned char *d, size_t n,
429     unsigned char *md)
430 {
431 	RIPEMD160_CTX c;
432 	static unsigned char m[RIPEMD160_DIGEST_LENGTH];
433 
434 	if (md == NULL)
435 		md = m;
436 	if (!RIPEMD160_Init(&c))
437 		return NULL;
438 	RIPEMD160_Update(&c, d, n);
439 	RIPEMD160_Final(md, &c);
440 	explicit_bzero(&c, sizeof(c));
441 	return (md);
442 }
443