rpm 5.3.12
|
00001 00005 #include "system.h" 00006 #include <rpmlog.h> 00007 00008 #include <rpmiotypes.h> 00009 #define _RPMPGP_INTERNAL 00010 #if defined(WITH_SSL) 00011 00012 #if defined(__LCLINT__) && !defined(__i386__) 00013 #define __i386__ 00014 #endif 00015 00016 #define _RPMSSL_INTERNAL 00017 #include <rpmssl.h> 00018 #endif 00019 00020 #include "debug.h" 00021 00022 #if defined(WITH_SSL) 00023 00024 /*@access pgpDig @*/ 00025 /*@access pgpDigParams @*/ 00026 00027 /*@-redecl@*/ 00028 /*@unchecked@*/ 00029 extern int _pgp_debug; 00030 00031 /*@unchecked@*/ 00032 extern int _pgp_print; 00033 /*@=redecl@*/ 00034 00035 /*@unchecked@*/ 00036 static int _rpmssl_debug; 00037 00038 #define SPEW(_t, _rc, _dig) \ 00039 { if ((_t) || _rpmssl_debug || _pgp_debug < 0) \ 00040 fprintf(stderr, "<-- %s(%p) %s\t%s\n", __FUNCTION__, (_dig), \ 00041 ((_rc) ? "OK" : "BAD"), (_dig)->pubkey_algoN); \ 00042 } 00043 00044 static const char * rpmsslHashAlgo2Name(uint32_t algo) 00045 { 00046 return pgpValStr(pgpHashTbl, (rpmuint8_t)algo); 00047 } 00048 00049 static const char * rpmsslPubkeyAlgo2Name(uint32_t algo) 00050 { 00051 return pgpValStr(pgpPubkeyTbl, (rpmuint8_t)algo); 00052 } 00053 00059 static 00060 unsigned char nibble(char c) 00061 /*@*/ 00062 { 00063 if (c >= '0' && c <= '9') 00064 return (unsigned char) (c - '0'); 00065 if (c >= 'A' && c <= 'F') 00066 return (unsigned char)((int)(c - 'A') + 10); 00067 if (c >= 'a' && c <= 'f') 00068 return (unsigned char)((int)(c - 'a') + 10); 00069 return (unsigned char) '\0'; 00070 } 00071 00072 static unsigned char * rpmsslBN2bin(const char * msg, const BIGNUM * s, size_t maxn) 00073 { 00074 unsigned char * t = xcalloc(1, maxn); 00075 /*@-modunconnomods@*/ 00076 size_t nt = BN_bn2bin(s, t); 00077 /*@=modunconnomods@*/ 00078 00079 if (nt < maxn) { 00080 size_t pad = (maxn - nt); 00081 memmove(t+pad, t, nt); 00082 memset(t, 0, pad); 00083 } 00084 return t; 00085 } 00086 00087 static 00088 int rpmsslSetRSA(/*@only@*/ DIGEST_CTX ctx, pgpDig dig, pgpDigParams sigp) 00089 /*@modifies dig @*/ 00090 { 00091 rpmssl ssl = dig->impl; 00092 unsigned int nb = RSA_size(ssl->rsa); 00093 const char * prefix = rpmDigestASN1(ctx); 00094 const char * hexstr; 00095 const char * s; 00096 rpmuint8_t signhash16[2]; 00097 char * tt; 00098 int rc; 00099 int xx; 00100 pgpDigParams pubp = pgpGetPubkey(dig); 00101 dig->pubkey_algoN = rpmsslPubkeyAlgo2Name(pubp->pubkey_algo); 00102 dig->hash_algoN = rpmsslHashAlgo2Name(sigp->hash_algo); 00103 00104 assert(sigp->hash_algo == rpmDigestAlgo(ctx)); 00105 if (prefix == NULL) 00106 return 1; 00107 00108 /* XXX FIXME: do PKCS1 padding in binary not hex */ 00109 /* XXX FIXME: should this lazy free be done elsewhere? */ 00110 ssl->digest = _free(ssl->digest); 00111 ssl->digestlen = 0; 00112 xx = rpmDigestFinal(ctx, (void **)&ssl->digest, &ssl->digestlen, 1); 00113 00114 hexstr = tt = xmalloc(2 * nb + 1); 00115 memset(tt, (int) 'f', (2 * nb)); 00116 tt[0] = '0'; tt[1] = '0'; 00117 tt[2] = '0'; tt[3] = '1'; 00118 tt += (2 * nb) - strlen(prefix) - strlen(ssl->digest) - 2; 00119 *tt++ = '0'; *tt++ = '0'; 00120 tt = stpcpy(tt, prefix); 00121 tt = stpcpy(tt, ssl->digest); 00122 00123 /* Set RSA hash. */ 00124 /*@-moduncon -noeffectuncon @*/ 00125 xx = BN_hex2bn(&ssl->hm, hexstr); 00126 /*@=moduncon =noeffectuncon @*/ 00127 00128 /*@-modfilesys@*/ 00129 if (_pgp_debug < 0) fprintf(stderr, "*** hm: %s\n", hexstr); 00130 hexstr = _free(hexstr); 00131 /*@=modfilesys@*/ 00132 00133 /* Compare leading 16 bits of digest for quick check. */ 00134 s = ssl->digest; 00135 /*@-type@*/ 00136 signhash16[0] = (rpmuint8_t) (nibble(s[0]) << 4) | nibble(s[1]); 00137 signhash16[1] = (rpmuint8_t) (nibble(s[2]) << 4) | nibble(s[3]); 00138 /*@=type@*/ 00139 rc = memcmp(signhash16, sigp->signhash16, sizeof(sigp->signhash16)); 00140 SPEW(0, !rc, dig); 00141 return rc; 00142 } 00143 00144 static 00145 int rpmsslVerifyRSA(pgpDig dig) 00146 /*@*/ 00147 { 00148 rpmssl ssl = dig->impl; 00149 /*@-moduncon@*/ 00150 size_t maxn; 00151 unsigned char * hm; 00152 unsigned char * c; 00153 size_t nb; 00154 /*@=moduncon@*/ 00155 size_t i; 00156 int rc = 0; 00157 int xx; 00158 00159 assert(ssl->rsa); /* XXX ensure lazy malloc with parameter set. */ 00160 maxn = BN_num_bytes(ssl->rsa->n); 00161 hm = rpmsslBN2bin("hm", ssl->hm, maxn); 00162 c = rpmsslBN2bin(" c", ssl->c, maxn); 00163 nb = RSA_public_decrypt((int)maxn, c, c, ssl->rsa, RSA_PKCS1_PADDING); 00164 00165 /*@=moduncon@*/ 00166 /* Verify RSA signature. */ 00167 /* XXX This is _NOT_ the correct openssl function to use: 00168 * rc = RSA_verify(type, m, m_len, sigbuf, siglen, ssl->rsa) 00169 * 00170 * Here's what needs doing (from OpenPGP reference sources in 1999): 00171 * static u32_t checkrsa(BIGNUM * a, RSA * key, u8_t * hash, int hlen) 00172 * { 00173 * u8_t dbuf[MAXSIGM]; 00174 * int j, ll; 00175 * 00176 * j = BN_bn2bin(a, dbuf); 00177 * ll = BN_num_bytes(key->n); 00178 * while (j < ll) 00179 * memmove(&dbuf[1], dbuf, j++), dbuf[0] = 0; 00180 * j = RSA_public_decrypt(ll, dbuf, dbuf, key, RSA_PKCS1_PADDING); 00181 * RSA_free(key); 00182 * return (j != hlen || memcmp(dbuf, hash, j)); 00183 * } 00184 */ 00185 for (i = 2; i < maxn; i++) { 00186 if (hm[i] == 0xff) 00187 continue; 00188 i++; 00189 break; 00190 } 00191 00192 rc = ((maxn - i) == nb && (xx = memcmp(hm+i, c, nb)) == 0); 00193 00194 c = _free(c); 00195 hm = _free(hm); 00196 00197 SPEW(!rc, rc, dig); 00198 return rc; 00199 } 00200 00201 static 00202 int rpmsslSignRSA(pgpDig dig) 00203 /*@*/ 00204 { 00205 rpmssl ssl = dig->impl; 00206 int rc = 0; /* assume failure. */ 00207 unsigned char * c = NULL; 00208 unsigned char * hm = NULL; 00209 size_t maxn; 00210 int xx; 00211 00212 #ifdef DYING 00213 assert(ssl->rsa); /* XXX ensure lazy malloc with parameter set. */ 00214 #else 00215 if (ssl->rsa == NULL) return rc; 00216 #endif 00217 00218 maxn = RSA_size(ssl->rsa); 00219 assert(ssl->hm); 00220 hm = rpmsslBN2bin("hm", ssl->hm, maxn); 00221 00222 c = xmalloc(maxn); 00223 xx = RSA_private_encrypt((int)maxn, hm, c, ssl->rsa, RSA_NO_PADDING); 00224 ssl->c = BN_bin2bn(c, maxn, NULL); 00225 00226 c = _free(c); 00227 hm = _free(hm); 00228 00229 rc = (ssl->c != NULL); 00230 00231 SPEW(!rc, rc, dig); 00232 00233 return rc; 00234 } 00235 00236 static 00237 int rpmsslGenerateRSA(pgpDig dig) 00238 /*@*/ 00239 { 00240 rpmssl ssl = dig->impl; 00241 int rc = 0; /* assume failure. */ 00242 static unsigned long _e = 0x10001; 00243 00244 if (ssl->nbits == 0) ssl->nbits = 1024; /* XXX FIXME */ 00245 assert(ssl->nbits); 00246 00247 #if defined(HAVE_RSA_GENERATE_KEY_EX) 00248 { BIGNUM * bn = BN_new(); 00249 assert(bn); 00250 if ((ssl->rsa = RSA_new()) != NULL 00251 && BN_set_word(bn, _e) 00252 && RSA_generate_key_ex(ssl->rsa, ssl->nbits, bn, NULL)) 00253 rc = 1; 00254 if (bn) BN_free(bn); 00255 } 00256 #else 00257 /* XXX older & deprecated API in openssl-0.97a (Centos4/s390x) */ 00258 if ((ssl->rsa = RSA_generate_key(ssl->nbits, _e, NULL, NULL)) != NULL) 00259 rc = 1; 00260 #endif 00261 00262 if (!rc && ssl->rsa) { 00263 RSA_free(ssl->rsa); 00264 ssl->rsa = NULL; 00265 } 00266 00267 SPEW(!rc, rc, dig); 00268 00269 return rc; 00270 } 00271 00272 static 00273 int rpmsslSetDSA(/*@only@*/ DIGEST_CTX ctx, pgpDig dig, pgpDigParams sigp) 00274 /*@modifies dig @*/ 00275 { 00276 rpmssl ssl = dig->impl; 00277 int rc; 00278 int xx; 00279 pgpDigParams pubp = pgpGetPubkey(dig); 00280 dig->pubkey_algoN = rpmsslPubkeyAlgo2Name(pubp->pubkey_algo); 00281 dig->hash_algoN = rpmsslHashAlgo2Name(sigp->hash_algo); 00282 00283 assert(sigp->hash_algo == rpmDigestAlgo(ctx)); 00284 /* Set DSA hash. */ 00285 /* XXX FIXME: should this lazy free be done elsewhere? */ 00286 ssl->digest = _free(ssl->digest); 00287 ssl->digestlen = 0; 00288 xx = rpmDigestFinal(ctx, (void **)&ssl->digest, &ssl->digestlen, 0); 00289 00290 /* Compare leading 16 bits of digest for quick check. */ 00291 rc = memcmp(ssl->digest, sigp->signhash16, sizeof(sigp->signhash16)); 00292 SPEW(0, !rc, dig); 00293 return rc; 00294 } 00295 00296 static 00297 int rpmsslVerifyDSA(pgpDig dig) 00298 /*@*/ 00299 { 00300 rpmssl ssl = dig->impl; 00301 int rc; 00302 00303 assert(ssl->dsa); /* XXX ensure lazy malloc with parameter set. */ 00304 /* Verify DSA signature. */ 00305 rc = DSA_do_verify(ssl->digest, (int)ssl->digestlen, ssl->dsasig, ssl->dsa); 00306 rc = (rc == 1); 00307 00308 SPEW(!rc, rc, dig); 00309 return rc; 00310 } 00311 00312 static 00313 int rpmsslSignDSA(pgpDig dig) 00314 /*@*/ 00315 { 00316 rpmssl ssl = dig->impl; 00317 int rc = 0; /* assume failure */ 00318 00319 #ifdef DYING 00320 assert(ssl->dsa); /* XXX ensure lazy malloc with parameter set. */ 00321 #else 00322 if (ssl->dsa == NULL) return rc; 00323 #endif 00324 00325 ssl->dsasig = DSA_do_sign(ssl->digest, ssl->digestlen, ssl->dsa); 00326 rc = (ssl->dsasig != NULL); 00327 00328 SPEW(!rc, rc, dig); 00329 00330 return rc; 00331 } 00332 00333 static 00334 int rpmsslGenerateDSA(pgpDig dig) 00335 /*@*/ 00336 { 00337 rpmssl ssl = dig->impl; 00338 int rc = 0; /* assume failure. */ 00339 00340 if (ssl->nbits == 0) ssl->nbits = 1024; /* XXX FIXME */ 00341 assert(ssl->nbits); 00342 00343 #if defined(HAVE_DSA_GENERATE_PARAMETERS_EX) 00344 if ((ssl->dsa = DSA_new()) != NULL 00345 && DSA_generate_parameters_ex(ssl->dsa, ssl->nbits, 00346 NULL, 0, NULL, NULL, NULL) 00347 && DSA_generate_key(ssl->dsa)) 00348 rc = 1; 00349 #else 00350 /* XXX older & deprecated API in openssl-0.97a (Centos4/s390x) */ 00351 if ((ssl->dsa = DSA_generate_parameters(ssl->nbits, 00352 NULL, 0, NULL, NULL, NULL, NULL)) != NULL 00353 && DSA_generate_key(ssl->dsa)) 00354 rc = 1; 00355 #endif 00356 00357 if (!rc && ssl->dsa) { 00358 DSA_free(ssl->dsa); 00359 ssl->dsa = NULL; 00360 } 00361 00362 SPEW(!rc, rc, dig); 00363 00364 return rc; 00365 } 00366 00367 static 00368 int rpmsslSetELG(/*@only@*/ DIGEST_CTX ctx, /*@unused@*/pgpDig dig, pgpDigParams sigp) 00369 /*@*/ 00370 { 00371 rpmssl ssl = dig->impl; 00372 int rc = 1; /* XXX always fail. */ 00373 int xx; 00374 00375 assert(sigp->hash_algo == rpmDigestAlgo(ctx)); 00376 00377 /* XXX FIXME: should this lazy free be done elsewhere? */ 00378 ssl->digest = _free(ssl->digest); 00379 ssl->digestlen = 0; 00380 xx = rpmDigestFinal(ctx, (void **)&ssl->digest, &ssl->digestlen, 0); 00381 00382 /* Compare leading 16 bits of digest for quick check. */ 00383 rc = 0; 00384 00385 SPEW(rc, !rc, dig); 00386 return rc; 00387 } 00388 00389 static 00390 int rpmsslSetECDSA(/*@only@*/ DIGEST_CTX ctx, /*@unused@*/pgpDig dig, pgpDigParams sigp) 00391 /*@*/ 00392 { 00393 rpmssl ssl = dig->impl; 00394 int rc = 1; /* assume failure. */ 00395 int xx; 00396 00397 assert(sigp->hash_algo == rpmDigestAlgo(ctx)); 00398 00399 /* XXX FIXME: should this lazy free be done elsewhere? */ 00400 ssl->digest = _free(ssl->digest); 00401 ssl->digestlen = 0; 00402 xx = rpmDigestFinal(ctx, &ssl->digest, &ssl->digestlen, 0); 00403 00404 /* Compare leading 16 bits of digest for quick check. */ 00405 rc = 0; 00406 00407 SPEW(rc, !rc, dig); 00408 return rc; 00409 } 00410 00411 static 00412 int rpmsslVerifyECDSA(pgpDig dig) 00413 /*@*/ 00414 { 00415 int rc = 0; /* assume failure. */ 00416 00417 #if !defined(OPENSSL_NO_ECDSA) 00418 rpmssl ssl = dig->impl; 00419 rc = ECDSA_do_verify(ssl->digest, ssl->digestlen, ssl->ecdsasig, ssl->ecdsakey); 00420 #endif 00421 rc = (rc == 1); 00422 00423 SPEW(!rc, rc, dig); 00424 return rc; 00425 } 00426 00427 static 00428 int rpmsslSignECDSA(pgpDig dig) 00429 /*@*/ 00430 { 00431 int rc = 0; /* assume failure. */ 00432 00433 #if !defined(OPENSSL_NO_ECDSA) 00434 rpmssl ssl = dig->impl; 00435 ssl->ecdsasig = ECDSA_do_sign(ssl->digest, ssl->digestlen, ssl->ecdsakey); 00436 rc = (ssl->ecdsasig != NULL); 00437 #endif 00438 00439 SPEW(!rc, rc, dig); 00440 return rc; 00441 } 00442 00443 static 00444 int rpmsslGenerateECDSA(pgpDig dig) 00445 /*@*/ 00446 { 00447 int rc = 0; /* assume failure. */ 00448 00449 #if !defined(OPENSSL_NO_ECDSA) 00450 rpmssl ssl = dig->impl; 00451 00452 if (ssl->nid == 0) { /* XXX FIXME */ 00453 ssl->nid = NID_X9_62_prime256v1; 00454 ssl->nbits = 256; 00455 } 00456 00457 if ((ssl->ecdsakey = EC_KEY_new_by_curve_name(ssl->nid)) != NULL 00458 && EC_KEY_generate_key(ssl->ecdsakey)) 00459 rc = 1; 00460 #endif 00461 00462 SPEW(!rc, rc, dig); 00463 return rc; 00464 } 00465 00466 static int rpmsslErrChk(pgpDig dig, const char * msg, int rc, unsigned expected) 00467 { 00468 #ifdef NOTYET 00469 rpmgc gc = dig->impl; 00470 /* Was the return code the expected result? */ 00471 rc = (gcry_err_code(gc->err) != expected); 00472 if (rc) 00473 fail("%s failed: %s\n", msg, gpg_strerror(gc->err)); 00474 /* XXX FIXME: rpmsslStrerror */ 00475 #else 00476 rc = (rc == 0); /* XXX impedance match 1 -> 0 on success */ 00477 #endif 00478 return rc; /* XXX 0 on success */ 00479 } 00480 00481 static int rpmsslAvailableCipher(pgpDig dig, int algo) 00482 { 00483 int rc = 0; /* assume available */ 00484 #ifdef NOTYET 00485 rc = rpmgsslvailable(dig->impl, algo, 00486 (gcry_md_test_algo(algo) || algo == PGPHASHALGO_MD5)); 00487 #endif /* _RPMGC_INTERNAL */ 00488 return rc; 00489 } 00490 00491 static int rpmsslAvailableDigest(pgpDig dig, int algo) 00492 { 00493 int rc = 0; /* assume available */ 00494 #ifdef NOTYET 00495 rc = rpmgsslvailable(dig->impl, algo, 00496 (gcry_md_test_algo(algo) || algo == PGPHASHALGO_MD5)); 00497 #endif /* _RPMGC_INTERNAL */ 00498 return rc; 00499 } 00500 00501 static int rpmsslAvailablePubkey(pgpDig dig, int algo) 00502 { 00503 int rc = 0; /* assume available */ 00504 #ifdef NOTYET 00505 rc = rpmsslAvailable(dig->impl, algo, gcry_pk_test_algo(algo)); 00506 #endif /* _RPMGC_INTERNAL */ 00507 return rc; 00508 } 00509 00510 static int rpmsslVerify(pgpDig dig) 00511 { 00512 int rc = 0; /* assume failure */ 00513 pgpDigParams pubp = pgpGetPubkey(dig); 00514 pgpDigParams sigp = pgpGetSignature(dig); 00515 dig->pubkey_algoN = rpmsslPubkeyAlgo2Name(pubp->pubkey_algo); 00516 dig->hash_algoN = rpmsslHashAlgo2Name(sigp->hash_algo); 00517 00518 switch (pubp->pubkey_algo) { 00519 default: 00520 break; 00521 case PGPPUBKEYALGO_RSA: 00522 rc = rpmsslVerifyRSA(dig); 00523 break; 00524 case PGPPUBKEYALGO_DSA: 00525 rc = rpmsslVerifyDSA(dig); 00526 break; 00527 case PGPPUBKEYALGO_ELGAMAL: 00528 #ifdef NOTYET 00529 rc = rpmsslVerifyELG(dig); 00530 #endif 00531 break; 00532 case PGPPUBKEYALGO_ECDSA: 00533 rc = rpmsslVerifyECDSA(dig); 00534 break; 00535 } 00536 SPEW(!rc, rc, dig); 00537 return rc; 00538 } 00539 00540 static int rpmsslSign(pgpDig dig) 00541 { 00542 int rc = 0; /* assume failure */ 00543 pgpDigParams pubp = pgpGetPubkey(dig); 00544 dig->pubkey_algoN = rpmsslPubkeyAlgo2Name(pubp->pubkey_algo); 00545 00546 switch (pubp->pubkey_algo) { 00547 default: 00548 break; 00549 case PGPPUBKEYALGO_RSA: 00550 rc = rpmsslSignRSA(dig); 00551 break; 00552 case PGPPUBKEYALGO_DSA: 00553 rc = rpmsslSignDSA(dig); 00554 break; 00555 case PGPPUBKEYALGO_ELGAMAL: 00556 #ifdef NOTYET 00557 rc = rpmsslSignELG(dig); 00558 #endif 00559 break; 00560 case PGPPUBKEYALGO_ECDSA: 00561 rc = rpmsslSignECDSA(dig); 00562 break; 00563 } 00564 SPEW(!rc, rc, dig); 00565 return rc; 00566 } 00567 00568 static int rpmsslGenerate(pgpDig dig) 00569 { 00570 int rc = 0; /* assume failure */ 00571 pgpDigParams pubp = pgpGetPubkey(dig); 00572 dig->pubkey_algoN = rpmsslPubkeyAlgo2Name(pubp->pubkey_algo); 00573 00574 switch (pubp->pubkey_algo) { 00575 default: 00576 break; 00577 case PGPPUBKEYALGO_RSA: 00578 rc = rpmsslGenerateRSA(dig); 00579 break; 00580 case PGPPUBKEYALGO_DSA: 00581 rc = rpmsslGenerateDSA(dig); 00582 break; 00583 case PGPPUBKEYALGO_ELGAMAL: 00584 #ifdef NOTYET 00585 rc = rpmsslGenerateELG(dig); 00586 #endif 00587 break; 00588 case PGPPUBKEYALGO_ECDSA: 00589 rc = rpmsslGenerateECDSA(dig); 00590 break; 00591 } 00592 SPEW(!rc, rc, dig); 00593 return rc; 00594 } 00595 00596 static 00597 int rpmsslMpiItem(/*@unused@*/ const char * pre, pgpDig dig, int itemno, 00598 const rpmuint8_t * p, 00599 /*@unused@*/ /*@null@*/ const rpmuint8_t * pend) 00600 /*@*/ 00601 { 00602 rpmssl ssl = dig->impl; 00603 unsigned int nb = ((pgpMpiBits(p) + 7) >> 3); 00604 int rc = 0; 00605 00606 /*@-moduncon@*/ 00607 switch (itemno) { 00608 default: 00609 assert(0); 00610 case 50: /* ECDSA r */ 00611 case 51: /* ECDSA s */ 00612 case 60: /* ECDSA curve OID */ 00613 case 61: /* ECDSA Q */ 00614 break; 00615 case 10: /* RSA m**d */ 00616 ssl->c = BN_bin2bn(p+2, nb, ssl->c); 00617 break; 00618 case 20: /* DSA r */ 00619 if (ssl->dsasig == NULL) ssl->dsasig = DSA_SIG_new(); 00620 ssl->dsasig->r = BN_bin2bn(p+2, nb, ssl->dsasig->r); 00621 break; 00622 case 21: /* DSA s */ 00623 if (ssl->dsasig == NULL) ssl->dsasig = DSA_SIG_new(); 00624 ssl->dsasig->s = BN_bin2bn(p+2, nb, ssl->dsasig->s); 00625 break; 00626 case 30: /* RSA n */ 00627 if (ssl->rsa == NULL) ssl->rsa = RSA_new(); 00628 ssl->rsa->n = BN_bin2bn(p+2, nb, ssl->rsa->n); 00629 break; 00630 case 31: /* RSA e */ 00631 if (ssl->rsa == NULL) ssl->rsa = RSA_new(); 00632 ssl->rsa->e = BN_bin2bn(p+2, nb, ssl->rsa->e); 00633 break; 00634 case 40: /* DSA p */ 00635 if (ssl->dsa == NULL) ssl->dsa = DSA_new(); 00636 ssl->dsa->p = BN_bin2bn(p+2, nb, ssl->dsa->p); 00637 break; 00638 case 41: /* DSA q */ 00639 if (ssl->dsa == NULL) ssl->dsa = DSA_new(); 00640 ssl->dsa->q = BN_bin2bn(p+2, nb, ssl->dsa->q); 00641 break; 00642 case 42: /* DSA g */ 00643 if (ssl->dsa == NULL) ssl->dsa = DSA_new(); 00644 ssl->dsa->g = BN_bin2bn(p+2, nb, ssl->dsa->g); 00645 break; 00646 case 43: /* DSA y */ 00647 if (ssl->dsa == NULL) ssl->dsa = DSA_new(); 00648 ssl->dsa->pub_key = BN_bin2bn(p+2, nb, ssl->dsa->pub_key); 00649 break; 00650 } 00651 /*@=moduncon@*/ 00652 return rc; 00653 } 00654 00655 /*@-mustmod@*/ 00656 static 00657 void rpmsslClean(void * impl) 00658 /*@modifies impl @*/ 00659 { 00660 rpmssl ssl = impl; 00661 /*@-moduncon@*/ 00662 if (ssl != NULL) { 00663 ssl->nbits = 0; 00664 ssl->err = 0; 00665 ssl->badok = 0; 00666 ssl->digest = _free(ssl->digest); 00667 ssl->digestlen = 0; 00668 00669 if (ssl->dsa) 00670 DSA_free(ssl->dsa); 00671 ssl->dsa = NULL; 00672 if (ssl->dsasig) 00673 DSA_SIG_free(ssl->dsasig); 00674 ssl->dsasig = NULL; 00675 00676 if (ssl->rsa) 00677 RSA_free(ssl->rsa); 00678 ssl->rsa = NULL; 00679 if (ssl->hm) 00680 BN_free(ssl->hm); 00681 ssl->hm = NULL; 00682 if (ssl->c) 00683 BN_free(ssl->c); 00684 ssl->c = NULL; 00685 00686 #if !defined(OPENSSL_NO_ECDSA) 00687 if (ssl->ecdsakey) 00688 EC_KEY_free(ssl->ecdsakey); 00689 ssl->ecdsakey = NULL; 00690 if (ssl->ecdsasig) 00691 ECDSA_SIG_free(ssl->ecdsasig); 00692 ssl->ecdsasig = NULL; 00693 00694 if (ssl->ecdsakey_bad) 00695 EC_KEY_free(ssl->ecdsakey_bad); 00696 ssl->ecdsakey_bad = NULL; 00697 #endif 00698 00699 } 00700 /*@=moduncon@*/ 00701 } 00702 /*@=mustmod@*/ 00703 00704 static /*@null@*/ 00705 void * rpmsslFree(/*@only@*/ void * impl) 00706 /*@modifies impl @*/ 00707 { 00708 rpmsslClean(impl); 00709 impl = _free(impl); 00710 return NULL; 00711 } 00712 00713 static 00714 void * rpmsslInit(void) 00715 /*@*/ 00716 { 00717 rpmssl ssl = xcalloc(1, sizeof(*ssl)); 00718 /*@-moduncon@*/ 00719 ERR_load_crypto_strings(); 00720 /*@=moduncon@*/ 00721 return (void *) ssl; 00722 } 00723 00724 struct pgpImplVecs_s rpmsslImplVecs = { 00725 rpmsslSetRSA, 00726 rpmsslSetDSA, 00727 rpmsslSetELG, 00728 rpmsslSetECDSA, 00729 00730 rpmsslErrChk, 00731 rpmsslAvailableCipher, rpmsslAvailableDigest, rpmsslAvailablePubkey, 00732 rpmsslVerify, rpmsslSign, rpmsslGenerate, 00733 00734 rpmsslMpiItem, rpmsslClean, 00735 rpmsslFree, rpmsslInit 00736 }; 00737 00738 #endif 00739