Bug Summary

File:rpmio/digest_openssl.c
Warning:line 552, column 9
Value stored to 'rc' is never read

Annotated Source Code

1#include "system.h"
2
3#include <openssl/evp.h>
4#include <openssl/rsa.h>
5#include <openssl/dsa.h>
6#include <rpm/rpmpgp.h>
7
8#include "rpmio/digest.h"
9
10
11/* Compatibility functions for OpenSSL 1.0.2 */
12
13#ifndef HAVE_EVP_MD_CTX_NEW1
14# define EVP_MD_CTX_new EVP_MD_CTX_create
15# define EVP_MD_CTX_free EVP_MD_CTX_destroy
16#endif
17
18#ifndef HAVE_RSA_SET0_KEY1
19int RSA_set0_key(RSA *r, BIGNUM *n, BIGNUM *e, BIGNUM *d);
20int RSA_set0_key(RSA *r, BIGNUM *n, BIGNUM *e, BIGNUM *d)
21{
22 if (!r) return 0;
23
24 if (n) {
25 r->n = n;
26 }
27
28 if (e) {
29 r->e = e;
30 }
31
32 if (d) {
33 r->d = d;
34 }
35
36 return 1;
37}
38#endif /* HAVE_RSA_SET0_KEY */
39
40#ifndef HAVE_DSA_SET0_KEY1
41int DSA_set0_key(DSA *d, BIGNUM *pub_key, BIGNUM *priv_key);
42
43int DSA_set0_key(DSA *d, BIGNUM *pub_key, BIGNUM *priv_key)
44{
45 if (!d) return 0;
46
47 if (pub_key) {
48 d->pub_key = pub_key;
49 }
50
51 if (priv_key) {
52 d->priv_key = priv_key;
53 }
54
55 return 1;
56}
57#endif /* HAVE_DSA_SET0_KEY */
58
59#ifndef HAVE_DSA_SET0_PQG1
60int DSA_set0_pqg(DSA *d, BIGNUM *p, BIGNUM *q, BIGNUM *g);
61
62int DSA_set0_pqg(DSA *d, BIGNUM *p, BIGNUM *q, BIGNUM *g)
63{
64 if (!d) return 0;
65
66 if (p) {
67 d->p = p;
68 }
69
70 if (q) {
71 d->q = q;
72 }
73
74 if (g) {
75 d->g = g;
76 }
77
78 return 1;
79}
80#endif /* HAVE_DSA_SET0_PQG */
81
82#ifndef HAVE_DSA_SIG_SET01
83int DSA_SIG_set0(DSA_SIG *sig, BIGNUM *r, BIGNUM *s);
84
85int DSA_SIG_set0(DSA_SIG *sig, BIGNUM *r, BIGNUM *s)
86{
87 if (!sig) return 0;
88
89 if (r) {
90 sig->r = r;
91 }
92
93 if (s) {
94 sig->s = s;
95 }
96
97 return 1;
98}
99#endif /* HAVE_DSA_SIG_SET0 */
100
101#ifndef HAVE_BN2BINPAD1
102static int BN_bn2binpad(const BIGNUM *a, unsigned char *to, int tolen)
103{
104 int i;
105
106 i = BN_num_bytes(a)((BN_num_bits(a)+7)/8);
107 if (tolen < i)
108 return -1;
109
110 /* Add leading zeroes if necessary */
111 if (tolen > i) {
112 memset(to, 0, tolen - i);
113 to += tolen - i;
114 }
115
116 BN_bn2bin(a, to);
117
118 return tolen;
119}
120#endif /* HAVE_BN2BINPAD */
121
122struct DIGEST_CTX_s {
123 rpmDigestFlags flags; /*!< Bit(s) to control digest operation. */
124 int algo; /*!< Used hash algorithm */
125
126 EVP_MD_CTX *md_ctx; /* Digest context (opaque) */
127
128};
129
130/**************************** init ************************************/
131
132int rpmInitCrypto(void) {
133 return 0;
134}
135
136int rpmFreeCrypto(void) {
137 return 0;
138}
139
140/**************************** digest ************************************/
141
142DIGEST_CTX rpmDigestDup(DIGEST_CTX octx)
143{
144 if (!octx) return NULL((void*)0);
145
146 DIGEST_CTX nctx = NULL((void*)0);
147 nctx = xcalloc(1, sizeof(*nctx))rcalloc((1), (sizeof(*nctx)));
148
149 nctx->flags = octx->flags;
150 nctx->algo = octx->algo;
151 nctx->md_ctx = EVP_MD_CTX_new();
152 if (!nctx->md_ctx) {
153 free(nctx);
154 return NULL((void*)0);
155 }
156
157 if (!EVP_MD_CTX_copy(nctx->md_ctx, octx->md_ctx)) {
158 free(nctx);
159 return NULL((void*)0);
160 }
161
162 return nctx;
163}
164
165static const EVP_MD *getEVPMD(int hashalgo)
166{
167 switch (hashalgo) {
168
169 case PGPHASHALGO_MD5:
170 return EVP_md5();
171
172 case PGPHASHALGO_SHA1:
173 return EVP_sha1();
174
175 case PGPHASHALGO_RIPEMD160:
176 return EVP_ripemd160();
177
178 case PGPHASHALGO_MD2:
179 return EVP_md2();
180
181 case PGPHASHALGO_SHA256:
182 return EVP_sha256();
183
184 case PGPHASHALGO_SHA384:
185 return EVP_sha384();
186
187 case PGPHASHALGO_SHA512:
188 return EVP_sha512();
189
190 case PGPHASHALGO_SHA224:
191 return EVP_sha224();
192
193 default:
194 return EVP_md_null();
195 }
196}
197
198size_t rpmDigestLength(int hashalgo)
199{
200 return EVP_MD_size(getEVPMD(hashalgo));
201}
202
203DIGEST_CTX rpmDigestInit(int hashalgo, rpmDigestFlags flags)
204{
205 DIGEST_CTX ctx = xcalloc(1, sizeof(*ctx))rcalloc((1), (sizeof(*ctx)));
206
207 ctx->md_ctx = EVP_MD_CTX_new();
208 if (!ctx->md_ctx) {
209 free(ctx);
210 return NULL((void*)0);
211 }
212
213 const EVP_MD *md = getEVPMD(hashalgo);
214 if (md == EVP_md_null()) {
215 free(ctx->md_ctx);
216 free(ctx);
217 return NULL((void*)0);
218 }
219
220 ctx->algo = hashalgo;
221 ctx->flags = flags;
222 if (!EVP_DigestInit_ex(ctx->md_ctx, md, NULL((void*)0))) {
223 free(ctx->md_ctx);
224 free(ctx);
225 return NULL((void*)0);
226 }
227
228 return ctx;
229}
230
231int rpmDigestUpdate(DIGEST_CTX ctx, const void *data, size_t len)
232{
233 if (ctx == NULL((void*)0)) return -1;
234
235 EVP_DigestUpdate(ctx->md_ctx, data, len);
236
237 return 0;
238}
239
240int rpmDigestFinal(DIGEST_CTX ctx, void ** datap, size_t *lenp, int asAscii)
241{
242 int ret;
243 unsigned char *digest = NULL((void*)0);
244 unsigned int digestlen;
245
246 if (ctx == NULL((void*)0)) return -1;
247
248 digestlen = EVP_MD_CTX_size(ctx->md_ctx)EVP_MD_size(EVP_MD_CTX_md(ctx->md_ctx));
249 digest = xcalloc(digestlen, sizeof(*digest))rcalloc((digestlen), (sizeof(*digest)));
250
251 ret = EVP_DigestFinal_ex(ctx->md_ctx, digest, &digestlen);
252 if (ret != 1) goto done;
253
254 if (!asAscii) {
255 /* Raw data requested */
256 if (lenp) *lenp = digestlen;
257 if (datap) {
258 *datap = digest;
259 digest = NULL((void*)0);
260 }
261 }
262
263 else {
264 /* ASCII requested */
265 if (lenp) *lenp = (2*digestlen) + 1;
266 if (datap) {
267 const uint8_t * s = (const uint8_t *) digest;
268 *datap = pgpHexStr(s, digestlen);
269 }
270 }
271
272 ret = 1;
273
274done:
275 if (digest) {
276 /* Zero the digest, just in case it's sensitive */
277 memset(digest, 0, digestlen);
278 free(digest);
279 }
280
281 EVP_MD_CTX_free(ctx->md_ctx);
282 free(ctx);
283
284 if (ret != 1) {
285 return -1;
286 }
287
288 return 0;
289}
290
291
292/****************************** RSA **************************************/
293
294/* Key */
295
296struct pgpDigKeyRSA_s {
297 size_t nbytes; /* Size of modulus */
298
299 BIGNUM *n; /* Common Modulus */
300 BIGNUM *e; /* Public Exponent */
301
302 EVP_PKEY *evp_pkey; /* Fully constructed key */
303};
304
305static int constructRSASigningKey(struct pgpDigKeyRSA_s *key)
306{
307 if (key->evp_pkey) {
308 /* We've already constructed it, so just reuse it */
309 return 1;
310 }
311
312 /* Create the RSA key */
313 RSA *rsa = RSA_new();
314 if (!rsa) return 0;
315
316 if (!RSA_set0_key(rsa, key->n, key->e, NULL((void*)0))) {
317 RSA_free(rsa);
318 return 0;
319 }
320
321 /* Create an EVP_PKEY container to abstract the key-type. */
322 key->evp_pkey = EVP_PKEY_new();
323 if (!key->evp_pkey) {
324 RSA_free(rsa);
325 return 0;
326 }
327
328 /* Assign the RSA key to the EVP_PKEY structure.
329 This will take over memory management of the RSA key */
330 if (!EVP_PKEY_assign_RSA(key->evp_pkey, rsa)EVP_PKEY_assign((key->evp_pkey),6, (char *)(rsa))) {
331 EVP_PKEY_free(key->evp_pkey);
332 key->evp_pkey = NULL((void*)0);
333 RSA_free(rsa);
334 }
335
336 return 1;
337}
338
339static int pgpSetKeyMpiRSA(pgpDigAlg pgpkey, int num, const uint8_t *p)
340{
341 size_t mlen = pgpMpiLen(p) - 2;
342 struct pgpDigKeyRSA_s *key = pgpkey->data;
343
344 if (!key) {
345 key = pgpkey->data = xcalloc(1, sizeof(*key))rcalloc((1), (sizeof(*key)));
346 }
347
348 switch (num) {
349 case 0:
350 /* Modulus */
351 if (key->n) {
352 /* This should only ever happen once per key */
353 return 1;
354 }
355
356 key->nbytes = mlen;
357 /* Create a BIGNUM from the pointer.
358 Note: this assumes big-endian data as required by PGP */
359 key->n = BN_bin2bn(p+2, mlen, NULL((void*)0));
360 if (!key->n) return 1;
361 break;
362
363 case 1:
364 /* Exponent */
365 if (key->e) {
366 /* This should only ever happen once per key */
367 return 1;
368 }
369
370 /* Create a BIGNUM from the pointer.
371 Note: this assumes big-endian data as required by PGP */
372 key->e = BN_bin2bn(p+2, mlen, NULL((void*)0));
373 if (!key->e) return 1;
374 break;
375 }
376
377 return 0;
378}
379
380static void pgpFreeKeyRSA(pgpDigAlg pgpkey)
381{
382 struct pgpDigKeyRSA_s *key = pgpkey->data;
383 if (key) {
384 if (key->evp_pkey) {
385 EVP_PKEY_free(key->evp_pkey);
386 } else {
387 /* If key->evp_pkey was constructed,
388 * the memory management of these BNs
389 * are freed with it. */
390 BN_clear_free(key->n);
391 BN_clear_free(key->e);
392 }
393
394 free(key);
395 }
396}
397
398/* Signature */
399
400struct pgpDigSigRSA_s {
401 BIGNUM *bn;
402 size_t len;
403};
404
405static int pgpSetSigMpiRSA(pgpDigAlg pgpsig, int num, const uint8_t *p)
406{
407 BIGNUM *bn = NULL((void*)0);
408
409 int mlen = pgpMpiLen(p) - 2;
410 int rc = 1;
411
412 struct pgpDigSigRSA_s *sig = pgpsig->data;
413 if (!sig) {
414 sig = xcalloc(1, sizeof(*sig))rcalloc((1), (sizeof(*sig)));
415 }
416
417 switch (num) {
418 case 0:
419 if (sig->bn) {
420 /* This should only ever happen once per signature */
421 return 1;
422 }
423
424 bn = sig->bn = BN_new();
425 if (!bn) return 1;
426
427 /* Create a BIGNUM from the signature pointer.
428 Note: this assumes big-endian data as required
429 by the PGP multiprecision integer format
430 (RFC4880, Section 3.2)
431 This will be useful later, as we can
432 retrieve this value with appropriate
433 padding. */
434 bn = BN_bin2bn(p+2, mlen, bn);
435 if (!bn) return 1;
436
437 sig->bn = bn;
438 sig->len = mlen;
439
440 pgpsig->data = sig;
441 rc = 0;
442 break;
443 }
444 return rc;
445}
446
447static void pgpFreeSigRSA(pgpDigAlg pgpsig)
448{
449 struct pgpDigSigRSA_s *sig = pgpsig->data;
450 if (sig) {
451 BN_clear_free(sig->bn);
452 free(pgpsig->data);
453 }
454}
455
456static int pgpVerifySigRSA(pgpDigAlg pgpkey, pgpDigAlg pgpsig,
457 uint8_t *hash, size_t hashlen, int hash_algo)
458{
459 int rc, ret;
460 EVP_PKEY_CTX *pkey_ctx = NULL((void*)0);
461 struct pgpDigSigRSA_s *sig = pgpsig->data;
462
463 void *padded_sig = NULL((void*)0);
464
465 struct pgpDigKeyRSA_s *key = pgpkey->data;
466
467 if (!constructRSASigningKey(key)) {
468 rc = 1;
469 goto done;
470 }
471
472 pkey_ctx = EVP_PKEY_CTX_new(key->evp_pkey, NULL((void*)0));
473 if (!pkey_ctx) {
474 rc = 1;
475 goto done;
476 }
477
478 ret = EVP_PKEY_verify_init(pkey_ctx);
479 if (ret < 0) {
480 rc = 1;
481 goto done;
482 }
483
484 ret = EVP_PKEY_CTX_set_rsa_padding(pkey_ctx, RSA_PKCS1_PADDING)EVP_PKEY_CTX_ctrl(pkey_ctx, 6, -1, (0x1000 + 1), 1, ((void*)0
))
;
485 if (ret < 0) {
486 rc = 1;
487 goto done;
488 }
489
490 ret = EVP_PKEY_CTX_set_signature_md(pkey_ctx, getEVPMD(hash_algo))EVP_PKEY_CTX_ctrl(pkey_ctx, -1, ((1<<3) | (1<<4) |
(1<<5) | (1<<6) | (1<<7)), 1, 0, (void *)getEVPMD
(hash_algo))
;
491 if (ret < 0) {
492 rc = 1;
493 goto done;
494 }
495
496 int pkey_len = EVP_PKEY_size(key->evp_pkey);
497 padded_sig = xcalloc(1, pkey_len)rcalloc((1), (pkey_len));
498 if (!BN_bn2binpad(sig->bn, padded_sig, pkey_len)) {
499 rc = 1;
500 goto done;
501 }
502
503 ret = EVP_PKEY_verify(pkey_ctx, padded_sig, pkey_len, hash, hashlen);
504 if (ret == 1)
505 {
506 /* Success */
507 rc = 0;
508 }
509 else
510 {
511 /* Failure */
512 rc = 1;
513 }
514
515done:
516 EVP_PKEY_CTX_free(pkey_ctx);
517 free(padded_sig);
518 return rc;
519}
520
521/****************************** DSA ***************************************/
522/* Key */
523
524struct pgpDigKeyDSA_s {
525 BIGNUM *p; /* Prime */
526 BIGNUM *q; /* Subprime */
527 BIGNUM *g; /* Base */
528 BIGNUM *y; /* Public Key */
529
530 DSA *dsa_key; /* Fully constructed key */
531};
532
533static int constructDSASigningKey(struct pgpDigKeyDSA_s *key)
534{
535 int rc;
536
537 if (key->dsa_key) {
538 /* We've already constructed it, so just reuse it */
539 return 1;
540 }
541
542 /* Create the DSA key */
543 DSA *dsa = DSA_new();
544 if (!dsa) return 0;
545
546 if (!DSA_set0_pqg(dsa, key->p, key->q, key->g)) {
547 rc = 0;
548 goto done;
549 }
550
551 if (!DSA_set0_key(dsa, key->y, NULL((void*)0))) {
552 rc = 0;
Value stored to 'rc' is never read
553 }
554
555 key->dsa_key = dsa;
556
557 rc = 1;
558done:
559 if (rc == 0) {
560 DSA_free(dsa);
561 }
562 return rc;
563}
564
565
566static int pgpSetKeyMpiDSA(pgpDigAlg pgpkey, int num, const uint8_t *p)
567{
568 BIGNUM *bn;
569 size_t mlen = pgpMpiLen(p) - 2;
570 struct pgpDigKeyDSA_s *key = pgpkey->data;
571
572 if (!key) {
573 key = pgpkey->data = xcalloc(1, sizeof(*key))rcalloc((1), (sizeof(*key)));
574 }
575
576 /* Create a BIGNUM from the key pointer.
577 Note: this assumes big-endian data as required
578 by the PGP multiprecision integer format
579 (RFC4880, Section 3.2) */
580 bn = BN_bin2bn(p+2, mlen, NULL((void*)0));
581 if (!bn) return 1;
582
583 switch (num) {
584 case 0:
585 /* Prime */
586 if (key->p) {
587 /* This should only ever happen once per key */
588 return 1;
589 }
590 key->p = bn;
591 break;
592
593 case 1:
594 /* Subprime */
595 if (key->q) {
596 /* This should only ever happen once per key */
597 return 1;
598 }
599 key->q = bn;
600 break;
601 case 2:
602 /* Base */
603 if (key->g) {
604 /* This should only ever happen once per key */
605 return 1;
606 }
607 key->g = bn;
608 break;
609 case 3:
610 /* Public */
611 if (key->y) {
612 /* This should only ever happen once per key */
613 return 1;
614 }
615 key->y = bn;
616 break;
617 }
618
619 return 0;
620}
621
622static void pgpFreeKeyDSA(pgpDigAlg pgpkey)
623{
624 struct pgpDigKeyDSA_s *key = pgpkey->data;
625 if (key) {
626 if (key->dsa_key) {
627 DSA_free(key->dsa_key);
628 } else {
629 /* If sig->dsa_key was constructed,
630 * the memory management of these BNs
631 * are freed with it. */
632 BN_clear_free(key->p);
633 BN_clear_free(key->q);
634 BN_clear_free(key->g);
635 BN_clear_free(key->y);
636 }
637 free(key);
638 }
639}
640
641/* Signature */
642
643struct pgpDigSigDSA_s {
644 BIGNUM *r;
645 BIGNUM *s;
646
647 DSA_SIG *dsa_sig;
648};
649
650static int constructDSASignature(struct pgpDigSigDSA_s *sig)
651{
652 int rc;
653
654 if (sig->dsa_sig) {
655 /* We've already constructed it, so just reuse it */
656 return 1;
657 }
658
659 /* Create the DSA signature */
660 DSA_SIG *dsa_sig = DSA_SIG_new();
661 if (!dsa_sig) return 0;
662
663 if (!DSA_SIG_set0(dsa_sig, sig->r, sig->s)) {
664 rc = 0;
665 goto done;
666 }
667
668 sig->dsa_sig = dsa_sig;
669
670 rc = 1;
671done:
672 if (rc == 0) {
673 DSA_SIG_free(sig->dsa_sig);
674 }
675 return rc;
676}
677
678static int pgpSetSigMpiDSA(pgpDigAlg pgpsig, int num, const uint8_t *p)
679{
680 BIGNUM *bn = NULL((void*)0);
681
682 int mlen = pgpMpiLen(p) - 2;
683 int rc = 1;
684
685 struct pgpDigSigDSA_s *sig = pgpsig->data;
686 if (!sig) {
687 sig = xcalloc(1, sizeof(*sig))rcalloc((1), (sizeof(*sig)));
688 }
689
690 /* Create a BIGNUM from the signature pointer.
691 Note: this assumes big-endian data as required
692 by the PGP multiprecision integer format
693 (RFC4880, Section 3.2) */
694 bn = BN_bin2bn(p+2, mlen, NULL((void*)0));
695 if (!bn) return 1;
696
697 switch (num) {
698 case 0:
699 if (sig->r) {
700 /* This should only ever happen once per signature */
701 BN_free(bn);
702 return 1;
703 }
704 sig->r = bn;
705 rc = 0;
706 break;
707 case 1:
708 if (sig->s) {
709 /* This should only ever happen once per signature */
710 BN_free(bn);
711 return 1;
712 }
713 sig->s = bn;
714 rc = 0;
715 break;
716 }
717
718 pgpsig->data = sig;
719
720 return rc;
721}
722
723static void pgpFreeSigDSA(pgpDigAlg pgpsig)
724{
725 struct pgpDigSigDSA_s *sig = pgpsig->data;
726 if (sig) {
727 if (sig->dsa_sig) {
728 DSA_SIG_free(sig->dsa_sig);
729 } else {
730 /* If sig->dsa_sig was constructed,
731 * the memory management of these BNs
732 * are freed with it. */
733 BN_clear_free(sig->r);
734 BN_clear_free(sig->s);
735 }
736 free(pgpsig->data);
737 }
738}
739
740static int pgpVerifySigDSA(pgpDigAlg pgpkey, pgpDigAlg pgpsig,
741 uint8_t *hash, size_t hashlen, int hash_algo)
742{
743 int rc, ret;
744 struct pgpDigSigDSA_s *sig = pgpsig->data;
745
746 struct pgpDigKeyDSA_s *key = pgpkey->data;
747
748 if (!constructDSASigningKey(key)) {
749 rc = 1;
750 goto done;
751 }
752
753 if (!constructDSASignature(sig)) {
754 rc = 1;
755 goto done;
756 }
757
758 ret = DSA_do_verify(hash, hashlen, sig->dsa_sig, key->dsa_key);
759 if (ret == 1)
760 {
761 /* Success */
762 rc = 0;
763 }
764 else
765 {
766 /* Failure */
767 rc = 1;
768 }
769
770done:
771 return rc;
772}
773
774/****************************** NULL **************************************/
775
776static int pgpSetMpiNULL(pgpDigAlg pgpkey, int num, const uint8_t *p)
777{
778 return 1;
779}
780
781static int pgpVerifyNULL(pgpDigAlg pgpkey, pgpDigAlg pgpsig,
782 uint8_t *hash, size_t hashlen, int hash_algo)
783{
784 return 1;
785}
786
787/****************************** PGP **************************************/
788pgpDigAlg pgpPubkeyNew(int algo)
789{
790 pgpDigAlg ka = xcalloc(1, sizeof(*ka))rcalloc((1), (sizeof(*ka)));;
791
792 switch (algo) {
793 case PGPPUBKEYALGO_RSA:
794 ka->setmpi = pgpSetKeyMpiRSA;
795 ka->free = pgpFreeKeyRSA;
796 ka->mpis = 2;
797 break;
798 case PGPPUBKEYALGO_DSA:
799 ka->setmpi = pgpSetKeyMpiDSA;
800 ka->free = pgpFreeKeyDSA;
801 ka->mpis = 4;
802 break;
803 default:
804 ka->setmpi = pgpSetMpiNULL;
805 ka->mpis = -1;
806 break;
807 }
808
809 ka->verify = pgpVerifyNULL; /* keys can't be verified */
810
811 return ka;
812}
813
814pgpDigAlg pgpSignatureNew(int algo)
815{
816 pgpDigAlg sa = xcalloc(1, sizeof(*sa))rcalloc((1), (sizeof(*sa)));
817
818 switch (algo) {
819 case PGPPUBKEYALGO_RSA:
820 sa->setmpi = pgpSetSigMpiRSA;
821 sa->free = pgpFreeSigRSA;
822 sa->verify = pgpVerifySigRSA;
823 sa->mpis = 1;
824 break;
825 case PGPPUBKEYALGO_DSA:
826 sa->setmpi = pgpSetSigMpiDSA;
827 sa->free = pgpFreeSigDSA;
828 sa->verify = pgpVerifySigDSA;
829 sa->mpis = 2;
830 break;
831 default:
832 sa->setmpi = pgpSetMpiNULL;
833 sa->verify = pgpVerifyNULL;
834 sa->mpis = -1;
835 break;
836 }
837 return sa;
838}