xref: /lighttpd1.4/src/sys-crypto-md.h (revision 4933a225)
1 /* sys-crypto-md.h - message digest (MD) wrapper
2  *
3  * message digest (MD) algorithms are not necessarily cryptographically secure
4  * (often provided by crypto libraries, hence this file named sys-crypto-md.h)
5  *
6  * Copyright(c) 2020 Glenn Strauss gstrauss()gluelogic.com  All rights reserved
7  * License: BSD 3-clause (same as lighttpd)
8  */
9 #ifndef LI_SYS_CRYPTO_MD_H
10 #define LI_SYS_CRYPTO_MD_H
11 #include "first.h"
12 
13 #include "sys-crypto.h" /* USE_LIB_CRYPTO */
14 #ifdef USE_LIB_CRYPTO
15 
16 #if defined(USE_NETTLE_CRYPTO)
17 
18 #include <nettle/md4.h>
19 #include <nettle/md5.h>
20 #include <nettle/sha.h>
21 
22 #define USE_LIB_CRYPTO_MD4
23 typedef struct md4_ctx MD4_CTX;
24 static inline int
25 MD4_Init(MD4_CTX *ctx)
26 {
27     nettle_md4_init(ctx);
28     return 1;
29 }
30 static inline int
31 MD4_Final(unsigned char *digest, MD4_CTX *ctx)
32 {
33     nettle_md4_digest(ctx, MD4_DIGEST_SIZE, digest);
34     return 1;
35 }
36 static inline int
37 MD4_Update(MD4_CTX *ctx, const void *data, size_t length)
38 {
39     nettle_md4_update(ctx, length, data);
40     return 1;
41 }
42 
43 #define USE_LIB_CRYPTO_MD5
44 typedef struct md5_ctx MD5_CTX;
45 static inline int
46 MD5_Init(MD5_CTX *ctx)
47 {
48     nettle_md5_init(ctx);
49     return 1;
50 }
51 static inline int
52 MD5_Final(unsigned char *digest, MD5_CTX *ctx)
53 {
54     nettle_md5_digest(ctx, MD5_DIGEST_SIZE, digest);
55     return 1;
56 }
57 static inline int
58 MD5_Update(MD5_CTX *ctx, const void *data, size_t length)
59 {
60     nettle_md5_update(ctx, length, data);
61     return 1;
62 }
63 
64 #define USE_LIB_CRYPTO_SHA1
65 typedef struct sha1_ctx SHA_CTX;
66 static inline int
67 SHA1_Init(SHA_CTX *ctx)
68 {
69     nettle_sha1_init(ctx);
70     return 1;
71 }
72 static inline int
73 SHA1_Final(unsigned char *digest, SHA_CTX *ctx)
74 {
75     nettle_sha1_digest(ctx, SHA1_DIGEST_SIZE, digest);
76     return 1;
77 }
78 static inline int
79 SHA1_Update(SHA_CTX *ctx, const void *data, size_t length)
80 {
81     nettle_sha1_update(ctx, length, data);
82     return 1;
83 }
84 
85 #define USE_LIB_CRYPTO_SHA256
86 typedef struct sha256_ctx SHA256_CTX;
87 static inline int
88 SHA256_Init(SHA256_CTX *ctx)
89 {
90     nettle_sha256_init(ctx);
91     return 1;
92 }
93 static inline int
94 SHA256_Final(unsigned char *digest, SHA256_CTX *ctx)
95 {
96     nettle_sha256_digest(ctx, SHA256_DIGEST_SIZE, digest);
97     return 1;
98 }
99 static inline int
100 SHA256_Update(SHA256_CTX *ctx, const void *data, size_t length)
101 {
102     nettle_sha256_update(ctx, length, data);
103     return 1;
104 }
105 
106 #define USE_LIB_CRYPTO_SHA512_256
107 typedef struct sha512_256_ctx SHA512_CTX;    /*(yes, SHA512_CTX)*/
108 static inline int
109 SHA512_256_Init(SHA512_CTX *ctx)
110 {
111     nettle_sha512_256_init(ctx);
112     return 1;
113 }
114 static inline int
115 SHA512_256_Final(unsigned char *digest, SHA512_CTX *ctx)
116 {
117     nettle_sha512_256_digest(ctx, SHA256_DIGEST_SIZE, digest);
118     return 1;
119 }
120 static inline int
121 SHA512_256_Update(SHA512_CTX *ctx, const void *data, size_t length)
122 {
123     nettle_sha512_update(ctx, length, data); /*(yes, nettle_sha512_update())*/
124     return 1;
125 }
126 
127 #define USE_LIB_CRYPTO_SHA512
128 typedef struct sha512_ctx SHA512_CTX;
129 static inline int
130 SHA512_Init(SHA512_CTX *ctx)
131 {
132     nettle_sha512_init(ctx);
133     return 1;
134 }
135 static inline int
136 SHA512_Final(unsigned char *digest, SHA512_CTX *ctx)
137 {
138     nettle_sha512_digest(ctx, SHA512_DIGEST_SIZE, digest);
139     return 1;
140 }
141 static inline int
142 SHA512_Update(SHA512_CTX *ctx, const void *data, size_t length)
143 {
144     nettle_sha512_update(ctx, length, data);
145     return 1;
146 }
147 
148 #elif defined(USE_MBEDTLS_CRYPTO)
149 
150 #include <mbedtls/config.h>
151 
152 #ifdef MBEDTLS_MD4_C
153 #define USE_LIB_CRYPTO_MD4
154 #include <mbedtls/md4.h>
155 typedef struct mbedtls_md4_context MD4_CTX;
156 static inline int
157 MD4_Init(MD4_CTX *ctx)
158 {
159     mbedtls_md4_init(ctx);
160     return (0 == mbedtls_md4_starts_ret(ctx));
161 }
162 static inline int
163 MD4_Final(unsigned char *digest, MD4_CTX *ctx)
164 {
165     int rc = mbedtls_md4_finish_ret(ctx, digest);
166     mbedtls_md4_free(ctx);
167     return (0 == rc);
168 }
169 static inline int
170 MD4_Update(MD4_CTX *ctx, const void *data, size_t length)
171 {
172     return (0 == mbedtls_md4_update_ret(ctx, data, length));
173 }
174 #endif
175 
176 #ifdef MBEDTLS_MD5_C
177 #define USE_LIB_CRYPTO_MD5
178 #include <mbedtls/md5.h>
179 typedef struct mbedtls_md5_context MD5_CTX;
180 static inline int
181 MD5_Init(MD5_CTX *ctx)
182 {
183     mbedtls_md5_init(ctx);
184     return (0 == mbedtls_md5_starts_ret(ctx));
185 }
186 static inline int
187 MD5_Final(unsigned char *digest, MD5_CTX *ctx)
188 {
189     int rc = mbedtls_md5_finish_ret(ctx, digest);
190     mbedtls_md5_free(ctx);
191     return (0 == rc);
192 }
193 static inline int
194 MD5_Update(MD5_CTX *ctx, const void *data, size_t length)
195 {
196     return (0 == mbedtls_md5_update_ret(ctx, data, length));
197 }
198 #endif
199 
200 #ifdef MBEDTLS_SHA1_C
201 #define USE_LIB_CRYPTO_SHA1
202 #include <mbedtls/sha1.h>
203 typedef struct mbedtls_sha1_context SHA_CTX;
204 static inline int
205 SHA1_Init(SHA_CTX *ctx)
206 {
207     mbedtls_sha1_init(ctx);
208     return (0 == mbedtls_sha1_starts_ret(ctx));
209 }
210 static inline int
211 SHA1_Final(unsigned char *digest, SHA_CTX *ctx)
212 {
213     int rc = mbedtls_sha1_finish_ret(ctx, digest);
214     mbedtls_sha1_free(ctx);
215     return (0 == rc);
216 }
217 static inline int
218 SHA1_Update(SHA_CTX *ctx, const void *data, size_t length)
219 {
220     return (0 == mbedtls_sha1_update_ret(ctx, data, length));
221 }
222 #endif
223 
224 #ifdef MBEDTLS_SHA256_C
225 #define USE_LIB_CRYPTO_SHA256
226 #include <mbedtls/sha256.h>
227 typedef struct mbedtls_sha256_context SHA256_CTX;
228 static inline int
229 SHA256_Init(SHA256_CTX *ctx)
230 {
231     mbedtls_sha256_init(ctx);
232     return (0 == mbedtls_sha256_starts_ret(ctx, 0));
233 }
234 static inline int
235 SHA256_Final(unsigned char *digest, SHA256_CTX *ctx)
236 {
237     int rc = mbedtls_sha256_finish_ret(ctx, digest);
238     mbedtls_sha256_free(ctx);
239     return (0 == rc);
240 }
241 static inline int
242 SHA256_Update(SHA256_CTX *ctx, const void *data, size_t length)
243 {
244     return (0 == mbedtls_sha256_update_ret(ctx, data, length));
245 }
246 #endif
247 
248 #ifdef MBEDTLS_SHA512_C
249 #define USE_LIB_CRYPTO_SHA512
250 #include <mbedtls/sha512.h>
251 typedef struct mbedtls_sha512_context SHA512_CTX;
252 static inline int
253 SHA512_Init(SHA512_CTX *ctx)
254 {
255     mbedtls_sha512_init(ctx);
256     return (0 == mbedtls_sha512_starts_ret(ctx, 0));
257 }
258 static inline int
259 SHA512_Final(unsigned char *digest, SHA512_CTX *ctx)
260 {
261     int rc = mbedtls_sha512_finish_ret(ctx, digest);
262     mbedtls_sha512_free(ctx);
263     return (0 == rc);
264 }
265 static inline int
266 SHA512_Update(SHA512_CTX *ctx, const void *data, size_t length)
267 {
268     return (0 == mbedtls_sha512_update_ret(ctx, data, length));
269 }
270 #endif
271 
272 #elif defined(USE_WOLFSSL_CRYPTO)
273 
274 /* WolfSSL compatibility API for OpenSSL unnecessarily bounces through an extra
275  * layer of indirection.  However, to avoid conflicting typedefs when includers
276  * also include headers from the WolfSSL compatibility API for OpenSSL, we
277  * include those headers here, as well, and use the compatibility API typedefs.
278  * (undef of OPENSSL_EXTRA and NO_OLD_WC_NAMES not sufficient, and not friendly
279  *  to do in a header when others might rely on them) */
280 
281 /* workaround fragile code in wolfssl/wolfcrypto/types.h */
282 #if !defined(SIZEOF_LONG) || !defined(SIZEOF_LONG_LONG)
283 #undef SIZEOF_LONG
284 #undef SIZEOF_LONG_LONG
285 #endif
286 
287 #ifndef NO_MD4
288 #include <wolfssl/wolfcrypt/md4.h>
289 #include <wolfssl/openssl/md4.h>
290 #undef MD4_Init
291 #undef MD4_Final
292 #undef MD4_Update
293 #define USE_LIB_CRYPTO_MD4
294 /*typedef Md4 MD4_CTX;*/
295 static inline int
296 MD4_Init(MD4_CTX *ctx)
297 {
298     wc_InitMd4((Md4 *)ctx);
299     return 1;
300 }
301 static inline int
302 MD4_Final(unsigned char *digest, MD4_CTX *ctx)
303 {
304     wc_Md4Final((Md4 *)ctx, digest);
305     return 1;
306 }
307 static inline int
308 MD4_Update(MD4_CTX *ctx, const void *data, size_t length)
309 {
310     wc_Md4Update((Md4 *)ctx, data, length);
311     return 1;
312 }
313 #endif
314 
315 #ifndef NO_MD5
316 #include <wolfssl/wolfcrypt/md5.h>
317 #include <wolfssl/openssl/md5.h>
318 #undef MD5_Init
319 #undef MD5_Final
320 #undef MD5_Update
321 #define USE_LIB_CRYPTO_MD5
322 /*typedef wc_Md5 MD5_CTX;*/
323 static inline int
324 MD5_Init(MD5_CTX *ctx)
325 {
326     return (0 == wc_InitMd5((wc_Md5 *)ctx));
327 }
328 static inline int
329 MD5_Final(unsigned char *digest, MD5_CTX *ctx)
330 {
331     return (0 == wc_Md5Final((wc_Md5 *)ctx, digest));
332 }
333 static inline int
334 MD5_Update(MD5_CTX *ctx, const void *data, size_t length)
335 {
336     wc_Md5Update((wc_Md5 *)ctx, data, length);
337     return 1;
338 }
339 #endif
340 
341 #ifndef NO_SHA
342 #include <wolfssl/wolfcrypt/sha.h>
343 #include <wolfssl/openssl/sha.h>
344 #undef SHA1_Init
345 #undef SHA1_Final
346 #undef SHA1_Update
347 #define USE_LIB_CRYPTO_SHA1
348 /*typedef wc_Sha SHA_CTX;*/
349 static inline int
350 SHA1_Init(SHA_CTX *ctx)
351 {
352     return (0 == wc_InitSha((wc_Sha *)ctx));
353 }
354 static inline int
355 SHA1_Final(unsigned char *digest, SHA_CTX *ctx)
356 {
357     return (0 == wc_ShaFinal((wc_Sha *)ctx, digest));
358 }
359 static inline int
360 SHA1_Update(SHA_CTX *ctx, const void *data, size_t length)
361 {
362     wc_ShaUpdate((wc_Sha *)ctx, data, length);
363     return 1;
364 }
365 #endif
366 
367 #ifndef NO_SHA256
368 #include <wolfssl/wolfcrypt/sha256.h>
369 #include <wolfssl/openssl/sha.h>
370 #undef SHA256_Init
371 #undef SHA256_Final
372 #undef SHA256_Update
373 #define USE_LIB_CRYPTO_SHA256
374 /*typedef wc_Sha256 SHA256_CTX;*/
375 static inline int
376 SHA256_Init(SHA256_CTX *ctx)
377 {
378     return (0 == wc_InitSha256((wc_Sha256 *)ctx));
379 }
380 static inline int
381 SHA256_Final(unsigned char *digest, SHA256_CTX *ctx)
382 {
383     return (0 == wc_Sha256Final((wc_Sha256 *)ctx, digest));
384 }
385 static inline int
386 SHA256_Update(SHA256_CTX *ctx, const void *data, size_t length)
387 {
388     wc_Sha256Update((wc_Sha256 *)ctx, data, length);
389     return 1;
390 }
391 #endif
392 
393 #ifndef NO_SHA512
394 #include <wolfssl/wolfcrypt/sha512.h>
395 #include <wolfssl/openssl/sha.h>
396 #undef SHA512_Init
397 #undef SHA512_Final
398 #undef SHA512_Update
399 #define USE_LIB_CRYPTO_SHA512
400 /*typedef wc_Sha512 SHA512_CTX;*/
401 static inline int
402 SHA512_Init(SHA512_CTX *ctx)
403 {
404     return (0 == wc_InitSha512((wc_Sha512 *)ctx));
405 }
406 static inline int
407 SHA512_Final(unsigned char *digest, SHA512_CTX *ctx)
408 {
409     return (0 == wc_Sha512Final((wc_Sha512 *)ctx, digest));
410 }
411 static inline int
412 SHA512_Update(SHA512_CTX *ctx, const void *data, size_t length)
413 {
414     wc_Sha512Update((wc_Sha512 *)ctx, data, length);
415     return 1;
416 }
417 #endif
418 
419 #elif defined(USE_OPENSSL_CRYPTO)
420 
421 #include <openssl/md4.h>
422 #include <openssl/md5.h>
423 #include <openssl/sha.h>
424 #ifndef OPENSSL_NO_MD4
425 #define USE_LIB_CRYPTO_MD4
426 #endif
427 #ifndef OPENSSL_NO_MD5
428 #define USE_LIB_CRYPTO_MD5
429 #endif
430 #define USE_LIB_CRYPTO_SHA1
431 #define USE_LIB_CRYPTO_SHA256
432 #ifdef SHA512_256_DIGEST_LENGTH
433 #define USE_LIB_CRYPTO_SHA512_256
434 #endif
435 #ifdef SHA512_DIGEST_LENGTH
436 #define USE_LIB_CRYPTO_SHA512
437 #endif
438 
439 #include <openssl/opensslv.h>
440 #if OPENSSL_VERSION_NUMBER >= 0x30000000L
441 #include <openssl/evp.h>
442 
443 #ifdef USE_LIB_CRYPTO_MD4
444 #define MD4_CTX EVP_MD4_CTX
445 #define MD4_Init EVP_MD4_Init
446 #define MD4_Final EVP_MD4_Final
447 #define MD4_Update EVP_MD4_Update
448 typedef EVP_MD_CTX * MD4_CTX;
449 static inline int
450 EVP_MD4_Init(EVP_MD4_CTX *ctx)
451 {
452     return ((*ctx = EVP_MD_CTX_new()) != NULL
453             && 1 == EVP_DigestInit_ex(*ctx, EVP_md4(), NULL));
454 }
455 static inline int
456 EVP_MD4_Final(unsigned char *digest, EVP_MD4_CTX *ctx)
457 {
458     /* MD4_DIGEST_LENGTH; EVP_MD_size(EVP_md4()) */
459     int rc = EVP_DigestFinal_ex(*ctx, digest, NULL);
460     EVP_MD_CTX_free(*ctx);
461     return (1 == rc);
462 }
463 static inline int
464 EVP_MD4_Update(EVP_MD4_CTX *ctx, const void *data, size_t length)
465 {
466     return (1 == EVP_DigestUpdate(*ctx, data, length));
467 }
468 #endif
469 
470 #ifdef USE_LIB_CRYPTO_MD5
471 #define MD5_CTX EVP_MD5_CTX
472 #define MD5_Init EVP_MD5_Init
473 #define MD5_Final EVP_MD5_Final
474 #define MD5_Update EVP_MD5_Update
475 typedef EVP_MD_CTX * EVP_MD5_CTX;
476 static inline int
477 EVP_MD5_Init(EVP_MD5_CTX *ctx)
478 {
479     return ((*ctx = EVP_MD_CTX_new()) != NULL
480             && 1 == EVP_DigestInit_ex(*ctx, EVP_md5(), NULL));
481 }
482 static inline int
483 EVP_MD5_Final(unsigned char *digest, EVP_MD5_CTX *ctx)
484 {
485     /* MD5_DIGEST_LENGTH; EVP_MD_size(EVP_md5()) */
486     int rc = EVP_DigestFinal_ex(*ctx, digest, NULL);
487     EVP_MD_CTX_free(*ctx);
488     return (1 == rc);
489 }
490 static inline int
491 EVP_MD5_Update(EVP_MD5_CTX *ctx, const void *data, size_t length)
492 {
493     return (1 == EVP_DigestUpdate(*ctx, data, length));
494 }
495 #endif
496 
497 #ifdef USE_LIB_CRYPTO_SHA1
498 #define SHA_CTX EVP_SHA1_CTX
499 #define SHA1_Init EVP_SHA1_Init
500 #define SHA1_Final EVP_SHA1_Final
501 #define SHA1_Update EVP_SHA1_Update
502 typedef EVP_MD_CTX * EVP_SHA1_CTX;
503 static inline int
504 EVP_SHA1_Init(EVP_SHA1_CTX *ctx)
505 {
506     return ((*ctx = EVP_MD_CTX_new()) != NULL
507             && 1 == EVP_DigestInit_ex(*ctx, EVP_sha1(), NULL));
508 }
509 static inline int
510 EVP_SHA1_Final(unsigned char *digest, EVP_SHA1_CTX *ctx)
511 {
512     /* SHA_DIGEST_LENGTH; EVP_MD_size(EVP_sha1()) */
513     int rc = EVP_DigestFinal_ex(*ctx, digest, NULL);
514     EVP_MD_CTX_free(*ctx);
515     return (1 == rc);
516 }
517 static inline int
518 EVP_SHA1_Update(EVP_SHA1_CTX *ctx, const void *data, size_t length)
519 {
520     return (1 == EVP_DigestUpdate(*ctx, data, length));
521 }
522 #endif
523 
524 #ifdef USE_LIB_CRYPTO_SHA256
525 #define SHA256_CTX EVP_SHA256_CTX
526 #define SHA256_Init EVP_SHA256_Init
527 #define SHA256_Final EVP_SHA256_Final
528 #define SHA256_Update EVP_SHA256_Update
529 typedef EVP_MD_CTX * EVP_SHA256_CTX;
530 static inline int
531 EVP_SHA256_Init(EVP_SHA256_CTX *ctx)
532 {
533     return ((*ctx = EVP_MD_CTX_new()) != NULL
534             && 1 == EVP_DigestInit_ex(*ctx, EVP_sha256(), NULL));
535 }
536 static inline int
537 EVP_SHA256_Final(unsigned char *digest, EVP_SHA256_CTX *ctx)
538 {
539     /* SHA256_DIGEST_LENGTH; EVP_MD_size(EVP_sha256()) */
540     int rc = EVP_DigestFinal_ex(*ctx, digest, NULL);
541     EVP_MD_CTX_free(*ctx);
542     return (1 == rc);
543 }
544 static inline int
545 EVP_SHA256_Update(EVP_SHA256_CTX *ctx, const void *data, size_t length)
546 {
547     return (1 == EVP_DigestUpdate(*ctx, data, length));
548 }
549 #endif
550 
551 #ifdef USE_LIB_CRYPTO_SHA512_256
552 #define SHA512_256_CTX EVP_SHA512_256_CTX
553 #define SHA512_256_Init EVP_SHA512_256_Init
554 #define SHA512_256_Final EVP_SHA512_256_Final
555 #define SHA512_256_Update EVP_SHA512_256_Update
556 typedef EVP_MD_CTX * EVP_SHA512_256_CTX;
557 static inline int
558 EVP_SHA512_256_Init(EVP_SHA512_256_CTX *ctx)
559 {
560     return ((*ctx = EVP_MD_CTX_new()) != NULL
561             && 1 == EVP_DigestInit_ex(*ctx, EVP_sha512_256(), NULL));
562 }
563 static inline int
564 EVP_SHA512_256_Final(unsigned char *digest, EVP_SHA512_256_CTX *ctx)
565 {
566     /* SHA256_DIGEST_LENGTH; EVP_MD_size(EVP_sha512_256()) */
567     int rc = EVP_DigestFinal_ex(*ctx, digest, NULL);
568     EVP_MD_CTX_free(*ctx);
569     return (1 == rc);
570 }
571 static inline int
572 EVP_SHA512_256_Update(EVP_SHA512_256_CTX *ctx, const void *data, size_t length)
573 {
574     return (1 == EVP_DigestUpdate(*ctx, data, length));
575 }
576 #endif
577 
578 #ifdef USE_LIB_CRYPTO_SHA512
579 #define SHA512_CTX EVP_SHA512_CTX
580 #define SHA512_Init EVP_SHA512_Init
581 #define SHA512_Final EVP_SHA512_Final
582 #define SHA512_Update EVP_SHA512_Update
583 typedef EVP_MD_CTX * EVP_SHA512_CTX;
584 static inline int
585 EVP_SHA512_Init(EVP_SHA512_CTX *ctx)
586 {
587     return ((*ctx = EVP_MD_CTX_new()) != NULL
588             && 1 == EVP_DigestInit_ex(*ctx, EVP_sha512(), NULL));
589 }
590 static inline int
591 EVP_SHA512_Final(unsigned char *digest, EVP_SHA512_CTX *ctx)
592 {
593     /* SHA512_DIGEST_LENGTH; EVP_MD_size(EVP_sha512()) */
594     int rc = EVP_DigestFinal_ex(*ctx, digest, NULL);
595     EVP_MD_CTX_free(*ctx);
596     return (1 == rc);
597 }
598 static inline int
599 EVP_SHA512_Update(EVP_SHA512_CTX *ctx, const void *data, size_t length)
600 {
601     return (1 == EVP_DigestUpdate(*ctx, data, length));
602 }
603 #endif
604 
605 #endif /* OPENSSL_VERSION_NUMBER >= 0x30000000L */
606 
607 #elif defined(USE_GNUTLS_CRYPTO)
608 
609 #include <gnutls/crypto.h>
610 #include "buffer.h"     /* SEGFAULT() */
611 
612 #define USE_LIB_CRYPTO_MD5
613 typedef gnutls_hash_hd_t MD5_CTX;
614 static inline int
615 MD5_Init(MD5_CTX *ctx)
616 {
617     if (gnutls_hash_init(ctx, GNUTLS_DIG_MD5) < 0)
618         SEGFAULT();
619     return 1;
620 }
621 static inline int
622 MD5_Final(unsigned char *digest, MD5_CTX *ctx)
623 {
624     gnutls_hash_deinit(*ctx, digest);
625     return 1;
626 }
627 static inline int
628 MD5_Update(MD5_CTX *ctx, const void *data, size_t length)
629 {
630     gnutls_hash(*ctx, data, length);
631     return 1;
632 }
633 
634 #define USE_LIB_CRYPTO_SHA1
635 typedef gnutls_hash_hd_t SHA_CTX;
636 static inline int
637 SHA1_Init(SHA_CTX *ctx)
638 {
639     if (gnutls_hash_init(ctx, GNUTLS_DIG_SHA1) < 0)
640         SEGFAULT();
641     return 1;
642 }
643 static inline int
644 SHA1_Final(unsigned char *digest, SHA_CTX *ctx)
645 {
646     gnutls_hash_deinit(*ctx, digest);
647     return 1;
648 }
649 static inline int
650 SHA1_Update(SHA_CTX *ctx, const void *data, size_t length)
651 {
652     gnutls_hash(*ctx, data, length);
653     return 1;
654 }
655 
656 #define USE_LIB_CRYPTO_SHA256
657 typedef gnutls_hash_hd_t SHA256_CTX;
658 static inline int
659 SHA256_Init(SHA256_CTX *ctx)
660 {
661     if (gnutls_hash_init(ctx, GNUTLS_DIG_SHA256) < 0)
662         SEGFAULT();
663     return 1;
664 }
665 static inline int
666 SHA256_Final(unsigned char *digest, SHA256_CTX *ctx)
667 {
668     gnutls_hash_deinit(*ctx, digest);
669     return 1;
670 }
671 static inline int
672 SHA256_Update(SHA256_CTX *ctx, const void *data, size_t length)
673 {
674     gnutls_hash(*ctx, data, length);
675     return 1;
676 }
677 
678 #define USE_LIB_CRYPTO_SHA512
679 typedef gnutls_hash_hd_t SHA512_CTX;
680 static inline int
681 SHA512_Init(SHA512_CTX *ctx)
682 {
683     if (gnutls_hash_init(ctx, GNUTLS_DIG_SHA512) < 0)
684         SEGFAULT();
685     return 1;
686 }
687 static inline int
688 SHA512_Final(unsigned char *digest, SHA512_CTX *ctx)
689 {
690     gnutls_hash_deinit(*ctx, digest);
691     return 1;
692 }
693 static inline int
694 SHA512_Update(SHA512_CTX *ctx, const void *data, size_t length)
695 {
696     gnutls_hash(*ctx, data, length);
697     return 1;
698 }
699 
700 #elif defined(USE_NSS_CRYPTO)
701 
702 #ifdef __has_include
703 #if __has_include(<nss3/nss.h>)
704 #define NSS_VER_INCLUDE
705 #endif
706 #endif
707 
708 /* basic algorithms fail if NSS library has not been init'd (WTH).
709  * lighttpd defers initialization of rand and crypto until first use
710  * to attempt to avoid long, blocking init at startup while waiting
711  * for sufficient system entropy to become available */
712 #ifdef NSS_VER_INCLUDE
713 #include <nss3/nss.h>   /* NSS_IsInitialized() NSS_NoDB_Init() */
714 #else
715 #include <nss/nss.h>    /* NSS_IsInitialized() NSS_NoDB_Init() */
716 #endif
717 #include <stdlib.h>     /* abort() */
718 __attribute_cold__
719 static inline void
720 nss_requires_explicit_init_for_basic_crypto_wth(void)
721 {
722     if (NSS_NoDB_Init(NULL) < 0)
723         abort();
724 }
725 
726 #ifdef NSS_VER_INCLUDE
727 #include <nss3/sechash.h>
728 #else
729 #include <nss/sechash.h>
730 #endif
731 
732 #define NSS_gen_hashfuncs(name, typ)                                          \
733 static inline int                                                             \
734 name##_Init(void **ctx)                                                       \
735 {                                                                             \
736     if (!NSS_IsInitialized())                                                 \
737         nss_requires_explicit_init_for_basic_crypto_wth();                    \
738     const SECHashObject * const hashObj = HASH_GetHashObject(typ);            \
739     return ((*ctx=hashObj->create()) != NULL) ? (hashObj->begin(*ctx),1) : 0; \
740 }                                                                             \
741 static inline int                                                             \
742 name##_Final(unsigned char *dest, void **ctx)                                 \
743 {                                                                             \
744     const SECHashObject * const hashObj = HASH_GetHashObject(typ);            \
745     unsigned int retLen;                                                      \
746     hashObj->end(*ctx, dest, &retLen, hashObj->length);                       \
747     hashObj->destroy(*ctx, PR_TRUE);                                          \
748     return 1;                                                                 \
749 }                                                                             \
750 static inline int                                                             \
751 name##_Update(void **ctx, const void *src, size_t len)                        \
752 {                                                                             \
753     const SECHashObject * const hashObj = HASH_GetHashObject(typ);            \
754     hashObj->update(*ctx, src, (int)len);                                     \
755     return 1;                                                                 \
756 }                                                                             \
757 typedef void * name##_CTX
758 typedef void * SHA_CTX;
759 
760 #define USE_LIB_CRYPTO_MD5
761 /* MD5_Init()
762  * MD5_Update()
763  * MD5_Final() */
764 NSS_gen_hashfuncs(MD5, HASH_AlgMD5);
765 
766 #define USE_LIB_CRYPTO_SHA1
767 /* SHA1_Init()
768  * SHA1_Update()
769  * SHA1_Final() */
770 NSS_gen_hashfuncs(SHA1, HASH_AlgSHA1);
771 
772 #define USE_LIB_CRYPTO_SHA256
773 /* SHA256_Init()
774  * SHA256_Update()
775  * SHA256_Final() */
776 NSS_gen_hashfuncs(SHA256, HASH_AlgSHA256);
777 
778 #define USE_LIB_CRYPTO_SHA512
779 /* SHA512_Init()
780  * SHA512_Update()
781  * SHA512_Final() */
782 NSS_gen_hashfuncs(SHA512, HASH_AlgSHA512);
783 
784 #endif
785 
786 #endif /* USE_LIB_CRYPTO */
787 
788 
789 #ifdef USE_LIB_CRYPTO_MD5
790 #ifndef MD5_DIGEST_LENGTH
791 #define MD5_DIGEST_LENGTH 16
792 #endif
793 #include "algo_md5.h" /*(for legacy li_MD5_*() name mangling)*/
794 #else
795 #include "algo_md5.h"
796 #endif
797 
798 
799 #ifdef USE_LIB_CRYPTO_SHA1
800 #ifndef SHA_DIGEST_LENGTH
801 #define SHA_DIGEST_LENGTH 20
802 #endif
803 #else
804 #include "algo_sha1.h"
805 #endif
806 
807 
808 #ifdef USE_LIB_CRYPTO_SHA256
809 #ifndef SHA256_DIGEST_LENGTH
810 #define SHA256_DIGEST_LENGTH 32
811 #endif
812 #endif
813 
814 
815 #ifdef USE_LIB_CRYPTO_SHA512_256
816 #ifndef SHA512_256_DIGEST_LENGTH
817 #define SHA512_256_DIGEST_LENGTH 32
818 #endif
819 #endif
820 
821 
822 #ifdef USE_LIB_CRYPTO_SHA512
823 #ifndef SHA512_DIGEST_LENGTH
824 #define SHA512_DIGEST_LENGTH 64
825 #endif
826 #endif
827 
828 
829 #endif /* LI_SYS_CRYPTO_MD_H */
830