1 /*- 2 * Copyright (c) 2009 The NetBSD Foundation, Inc. 3 * All rights reserved. 4 * 5 * This code is derived from software contributed to The NetBSD Foundation 6 * by Alistair Crooks (agc@NetBSD.org) 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 1. Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * 2. Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in the 15 * documentation and/or other materials provided with the distribution. 16 * 17 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 18 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 19 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 20 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 21 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 22 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 23 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 24 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 25 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 26 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 27 * POSSIBILITY OF SUCH DAMAGE. 28 */ 29 /* 30 * Copyright (c) 2005-2008 Nominet UK (www.nic.uk) 31 * All rights reserved. 32 * Contributors: Ben Laurie, Rachel Willmer. The Contributors have asserted 33 * their moral rights under the UK Copyright Design and Patents Act 1988 to 34 * be recorded as the authors of this copyright work. 35 * 36 * Licensed under the Apache License, Version 2.0 (the "License"); you may not 37 * use this file except in compliance with the License. 38 * 39 * You may obtain a copy of the License at 40 * http://www.apache.org/licenses/LICENSE-2.0 41 * 42 * Unless required by applicable law or agreed to in writing, software 43 * distributed under the License is distributed on an "AS IS" BASIS, 44 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 45 * 46 * See the License for the specific language governing permissions and 47 * limitations under the License. 48 */ 49 50 /** \file 51 */ 52 #include "config.h" 53 54 #ifdef HAVE_OPENSSL_MD5_H 55 #include <openssl/md5.h> 56 #endif 57 58 #ifdef HAVE_OPENSSL_SHA_H 59 #include <openssl/sha.h> 60 #endif 61 62 #ifdef HAVE_OPENSSL_DSA_H 63 #include <openssl/dsa.h> 64 #endif 65 66 #ifdef HAVE_OPENSSL_RSA_H 67 #include <openssl/rsa.h> 68 #endif 69 70 #ifdef HAVE_OPENSSL_ERR_H 71 #include <openssl/err.h> 72 #endif 73 74 75 #include <stdlib.h> 76 77 /* Apple */ 78 #ifdef HAVE_COMMONCRYPTO_COMMONDIGEST_H 79 #undef MD5_DIGEST_LENGTH 80 #undef SHA_DIGEST_LENGTH 81 #define COMMON_DIGEST_FOR_OPENSSL 1 82 #include <CommonCrypto/CommonDigest.h> 83 #endif 84 85 #include "crypto.h" 86 #include "keyring.h" 87 #include "readerwriter.h" 88 #include "netpgpdefs.h" 89 #include "keyring_local.h" 90 91 92 static void 93 test_seckey(const __ops_seckey_t * seckey) 94 { 95 RSA *test = RSA_new(); 96 97 test->n = BN_dup(seckey->pubkey.key.rsa.n); 98 test->e = BN_dup(seckey->pubkey.key.rsa.e); 99 100 test->d = BN_dup(seckey->key.rsa.d); 101 test->p = BN_dup(seckey->key.rsa.p); 102 test->q = BN_dup(seckey->key.rsa.q); 103 104 if (RSA_check_key(test) != 1) { 105 (void) fprintf(stderr, 106 "test_seckey: RSA_check_key failed\n"); 107 } 108 RSA_free(test); 109 } 110 111 static void 112 md5_init(__ops_hash_t * hash) 113 { 114 if (hash->data) { 115 (void) fprintf(stderr, "md5_init: hash data non-null\n"); 116 } 117 hash->data = calloc(1, sizeof(MD5_CTX)); 118 MD5_Init(hash->data); 119 } 120 121 static void 122 md5_add(__ops_hash_t * hash, const unsigned char *data, unsigned length) 123 { 124 MD5_Update(hash->data, data, length); 125 } 126 127 static unsigned 128 md5_finish(__ops_hash_t * hash, unsigned char *out) 129 { 130 MD5_Final(out, hash->data); 131 free(hash->data); 132 hash->data = NULL; 133 return 16; 134 } 135 136 static __ops_hash_t md5 = { 137 OPS_HASH_MD5, 138 MD5_DIGEST_LENGTH, 139 "MD5", 140 md5_init, 141 md5_add, 142 md5_finish, 143 NULL 144 }; 145 146 /** 147 \ingroup Core_Crypto 148 \brief Initialise to MD5 149 \param hash Hash to initialise 150 */ 151 void 152 __ops_hash_md5(__ops_hash_t * hash) 153 { 154 *hash = md5; 155 } 156 157 static void 158 sha1_init(__ops_hash_t * hash) 159 { 160 if (__ops_get_debug_level(__FILE__)) { 161 fprintf(stderr, "***\n***\nsha1_init\n***\n"); 162 } 163 if (hash->data) { 164 (void) fprintf(stderr, "sha1_init: hash data non-null\n"); 165 } 166 hash->data = calloc(1, sizeof(SHA_CTX)); 167 SHA1_Init(hash->data); 168 } 169 170 static void 171 sha1_add(__ops_hash_t * hash, const unsigned char *data, unsigned length) 172 { 173 if (__ops_get_debug_level(__FILE__)) { 174 unsigned int i; 175 176 (void) fprintf(stderr, "adding %d to hash:\n ", length); 177 for (i = 0; i < length; i++) { 178 (void) fprintf(stderr, "0x%02x ", data[i]); 179 if (!((i + 1) % 16)) { 180 (void) fprintf(stderr, "\n"); 181 } else if (!((i + 1) % 8)) { 182 (void) fprintf(stderr, " "); 183 } 184 } 185 (void) fprintf(stderr, "\n"); 186 } 187 SHA1_Update(hash->data, data, length); 188 } 189 190 static unsigned 191 sha1_finish(__ops_hash_t * hash, unsigned char *out) 192 { 193 SHA1_Final(out, hash->data); 194 if (__ops_get_debug_level(__FILE__)) { 195 unsigned i; 196 197 (void) fprintf(stderr, "***\n***\nsha1_finish\n***\n"); 198 for (i = 0; i < OPS_SHA1_HASH_SIZE; i++) 199 (void) fprintf(stderr, "0x%02x ", out[i]); 200 (void) fprintf(stderr, "\n"); 201 } 202 (void) free(hash->data); 203 hash->data = NULL; 204 return OPS_SHA1_HASH_SIZE; 205 } 206 207 static __ops_hash_t sha1 = { 208 OPS_HASH_SHA1, 209 OPS_SHA1_HASH_SIZE, 210 "SHA1", 211 sha1_init, 212 sha1_add, 213 sha1_finish, 214 NULL 215 }; 216 217 /** 218 \ingroup Core_Crypto 219 \brief Initialise to SHA1 220 \param hash Hash to initialise 221 */ 222 void 223 __ops_hash_sha1(__ops_hash_t * hash) 224 { 225 *hash = sha1; 226 } 227 228 static void 229 sha256_init(__ops_hash_t * hash) 230 { 231 if (__ops_get_debug_level(__FILE__)) { 232 fprintf(stderr, "***\n***\nsha256_init\n***\n"); 233 } 234 if (hash->data) { 235 (void) fprintf(stderr, "sha256_init: hash data non-null\n"); 236 } 237 hash->data = calloc(1, sizeof(SHA256_CTX)); 238 SHA256_Init(hash->data); 239 } 240 241 static void 242 sha256_add(__ops_hash_t * hash, const unsigned char *data, unsigned length) 243 { 244 if (__ops_get_debug_level(__FILE__)) { 245 unsigned int i; 246 247 (void) fprintf(stderr, "adding %d to hash:\n ", length); 248 for (i = 0; i < length; i++) { 249 (void) fprintf(stderr, "0x%02x ", data[i]); 250 if (!((i + 1) % 16)) 251 (void) fprintf(stderr, "\n"); 252 else if (!((i + 1) % 8)) 253 (void) fprintf(stderr, " "); 254 } 255 (void) fprintf(stderr, "\n"); 256 } 257 SHA256_Update(hash->data, data, length); 258 } 259 260 static unsigned 261 sha256_finish(__ops_hash_t * hash, unsigned char *out) 262 { 263 SHA256_Final(out, hash->data); 264 if (__ops_get_debug_level(__FILE__)) { 265 unsigned i; 266 267 (void) fprintf(stderr, "***\n***\nsha1_finish\n***\n"); 268 for (i = 0; i < SHA256_DIGEST_LENGTH; i++) 269 (void) fprintf(stderr, "0x%02x ", out[i]); 270 (void) fprintf(stderr, "\n"); 271 } 272 (void) free(hash->data); 273 hash->data = NULL; 274 return SHA256_DIGEST_LENGTH; 275 } 276 277 static __ops_hash_t sha256 = { 278 OPS_HASH_SHA256, 279 SHA256_DIGEST_LENGTH, 280 "SHA256", 281 sha256_init, 282 sha256_add, 283 sha256_finish, 284 NULL 285 }; 286 287 void 288 __ops_hash_sha256(__ops_hash_t *hash) 289 { 290 *hash = sha256; 291 } 292 293 /* 294 * SHA384 295 */ 296 static void 297 sha384_init(__ops_hash_t *hash) 298 { 299 if (__ops_get_debug_level(__FILE__)) { 300 (void) fprintf(stderr, "***\n***\nsha384_init\n***\n"); 301 } 302 if (hash->data) { 303 (void) fprintf(stderr, "sha384_init: hash data non-null\n"); 304 } 305 hash->data = calloc(1, sizeof(SHA512_CTX)); 306 SHA384_Init(hash->data); 307 } 308 309 static void 310 sha384_add(__ops_hash_t * hash, const unsigned char *data, unsigned length) 311 { 312 if (__ops_get_debug_level(__FILE__)) { 313 unsigned int i; 314 315 (void) fprintf(stderr, "adding %d to hash:\n ", length); 316 for (i = 0; i < length; i++) { 317 (void) fprintf(stderr, "0x%02x ", data[i]); 318 if (!((i + 1) % 16)) 319 (void) fprintf(stderr, "\n"); 320 else if (!((i + 1) % 8)) 321 (void) fprintf(stderr, " "); 322 } 323 (void) fprintf(stderr, "\n"); 324 } 325 SHA384_Update(hash->data, data, length); 326 } 327 328 static unsigned 329 sha384_finish(__ops_hash_t * hash, unsigned char *out) 330 { 331 SHA384_Final(out, hash->data); 332 if (__ops_get_debug_level(__FILE__)) { 333 unsigned i; 334 335 (void) fprintf(stderr, "***\n***\nsha1_finish\n***\n"); 336 for (i = 0; i < SHA384_DIGEST_LENGTH; i++) 337 (void) fprintf(stderr, "0x%02x ", out[i]); 338 (void) fprintf(stderr, "\n"); 339 } 340 (void) free(hash->data); 341 hash->data = NULL; 342 return SHA384_DIGEST_LENGTH; 343 } 344 345 static __ops_hash_t sha384 = { 346 OPS_HASH_SHA384, 347 SHA384_DIGEST_LENGTH, 348 "SHA384", 349 sha384_init, 350 sha384_add, 351 sha384_finish, 352 NULL 353 }; 354 355 void 356 __ops_hash_sha384(__ops_hash_t *hash) 357 { 358 *hash = sha384; 359 } 360 361 /* 362 * SHA512 363 */ 364 static void 365 sha512_init(__ops_hash_t * hash) 366 { 367 if (__ops_get_debug_level(__FILE__)) { 368 (void) fprintf(stderr, "***\n***\nsha512_init\n***\n"); 369 } 370 if (hash->data) { 371 (void) fprintf(stderr, "sha512_init: hash data non-null\n"); 372 } 373 hash->data = calloc(1, sizeof(SHA512_CTX)); 374 SHA512_Init(hash->data); 375 } 376 377 static void 378 sha512_add(__ops_hash_t * hash, const unsigned char *data, unsigned length) 379 { 380 if (__ops_get_debug_level(__FILE__)) { 381 unsigned int i; 382 383 (void) fprintf(stderr, "adding %d to hash:\n ", length); 384 for (i = 0; i < length; i++) { 385 (void) fprintf(stderr, "0x%02x ", data[i]); 386 if (!((i + 1) % 16)) 387 (void) fprintf(stderr, "\n"); 388 else if (!((i + 1) % 8)) 389 (void) fprintf(stderr, " "); 390 } 391 (void) fprintf(stderr, "\n"); 392 } 393 SHA512_Update(hash->data, data, length); 394 } 395 396 static unsigned 397 sha512_finish(__ops_hash_t * hash, unsigned char *out) 398 { 399 SHA512_Final(out, hash->data); 400 if (__ops_get_debug_level(__FILE__)) { 401 unsigned i; 402 403 (void) fprintf(stderr, "***\n***\nsha1_finish\n***\n"); 404 for (i = 0; i < SHA512_DIGEST_LENGTH; i++) 405 (void) fprintf(stderr, "0x%02x ", out[i]); 406 (void) fprintf(stderr, "\n"); 407 } 408 (void) free(hash->data); 409 hash->data = NULL; 410 return SHA512_DIGEST_LENGTH; 411 } 412 413 static __ops_hash_t sha512 = { 414 OPS_HASH_SHA512, 415 SHA512_DIGEST_LENGTH, 416 "SHA512", 417 sha512_init, 418 sha512_add, 419 sha512_finish, 420 NULL 421 }; 422 423 void 424 __ops_hash_sha512(__ops_hash_t * hash) 425 { 426 *hash = sha512; 427 } 428 429 /* 430 * SHA224 431 */ 432 433 static void 434 sha224_init(__ops_hash_t * hash) 435 { 436 if (__ops_get_debug_level(__FILE__)) { 437 (void) fprintf(stderr, "***\n***\nsha1_init\n***\n"); 438 } 439 if (hash->data) { 440 (void) fprintf(stderr, "sha224_init: hash data non-null\n"); 441 } 442 hash->data = calloc(1, sizeof(SHA256_CTX)); 443 SHA224_Init(hash->data); 444 } 445 446 static void 447 sha224_add(__ops_hash_t * hash, const unsigned char *data, unsigned length) 448 { 449 if (__ops_get_debug_level(__FILE__)) { 450 unsigned int i; 451 452 (void) fprintf(stderr, "adding %d to hash:\n ", length); 453 for (i = 0; i < length; i++) { 454 (void) fprintf(stderr, "0x%02x ", data[i]); 455 if (!((i + 1) % 16)) 456 (void) fprintf(stderr, "\n"); 457 else if (!((i + 1) % 8)) 458 (void) fprintf(stderr, " "); 459 } 460 (void) fprintf(stderr, "\n"); 461 } 462 SHA224_Update(hash->data, data, length); 463 } 464 465 static unsigned 466 sha224_finish(__ops_hash_t * hash, unsigned char *out) 467 { 468 SHA224_Final(out, hash->data); 469 if (__ops_get_debug_level(__FILE__)) { 470 unsigned i; 471 472 (void) fprintf(stderr, "***\n***\nsha1_finish\n***\n"); 473 for (i = 0; i < SHA224_DIGEST_LENGTH; i++) 474 (void) fprintf(stderr, "0x%02x ", out[i]); 475 (void) fprintf(stderr, "\n"); 476 } 477 (void) free(hash->data); 478 hash->data = NULL; 479 return SHA224_DIGEST_LENGTH; 480 } 481 482 static __ops_hash_t sha224 = { 483 OPS_HASH_SHA224, 484 SHA224_DIGEST_LENGTH, 485 "SHA224", 486 sha224_init, 487 sha224_add, 488 sha224_finish, 489 NULL 490 }; 491 492 void 493 __ops_hash_sha224(__ops_hash_t * hash) 494 { 495 *hash = sha224; 496 } 497 498 bool 499 __ops_dsa_verify(const unsigned char *hash, size_t hash_length, 500 const __ops_dsa_sig_t * sig, 501 const __ops_dsa_pubkey_t * dsa) 502 { 503 DSA_SIG *osig; 504 DSA *odsa; 505 int ret; 506 unsigned int qlen; 507 508 osig = DSA_SIG_new(); 509 osig->r = sig->r; 510 osig->s = sig->s; 511 512 odsa = DSA_new(); 513 odsa->p = dsa->p; 514 odsa->q = dsa->q; 515 odsa->g = dsa->g; 516 odsa->pub_key = dsa->y; 517 518 if (__ops_get_debug_level(__FILE__)) { 519 unsigned i; 520 521 (void) fprintf(stderr, "hash passed in:\n"); 522 for (i = 0; i < hash_length; i++) { 523 (void) fprintf(stderr, "%02x ", hash[i]); 524 } 525 (void) fprintf(stderr, "\n"); 526 printf("hash_length=%" PRIsize "d\n", hash_length); 527 } 528 /* printf("Q=%d\n", BN_num_bytes(odsa->q)); */ 529 if ((qlen = BN_num_bytes(odsa->q)) < hash_length) { 530 hash_length = qlen; 531 } 532 ret = DSA_do_verify(hash, (int)hash_length, osig, odsa); 533 if (__ops_get_debug_level(__FILE__)) { 534 (void) fprintf(stderr, "ret=%d\n", ret); 535 } 536 if (ret < 0) { 537 (void) fprintf(stderr, 538 "__ops_do_verify: DSA_do_verify failed\n"); 539 return 0; 540 } 541 542 odsa->p = odsa->q = odsa->g = odsa->pub_key = NULL; 543 DSA_free(odsa); 544 545 osig->r = osig->s = NULL; 546 DSA_SIG_free(osig); 547 548 return ret != 0; 549 } 550 551 /** 552 \ingroup Core_Crypto 553 \brief Recovers message digest from the signature 554 \param out Where to write decrypted data to 555 \param in Encrypted data 556 \param length Length of encrypted data 557 \param rsa RSA public key 558 \return size of recovered message digest 559 */ 560 int 561 __ops_rsa_public_decrypt(unsigned char *out, const unsigned char *in, 562 size_t length, const __ops_rsa_pubkey_t * rsa) 563 { 564 RSA *orsa; 565 int n; 566 567 orsa = RSA_new(); 568 orsa->n = rsa->n; 569 orsa->e = rsa->e; 570 571 n = RSA_public_decrypt((int)length, in, out, orsa, RSA_NO_PADDING); 572 573 orsa->n = orsa->e = NULL; 574 RSA_free(orsa); 575 576 return n; 577 } 578 579 /** 580 \ingroup Core_Crypto 581 \brief Signs data with RSA 582 \param out Where to write signature 583 \param in Data to sign 584 \param length Length of data 585 \param srsa RSA secret key 586 \param rsa RSA public key 587 \return number of bytes decrypted 588 */ 589 int 590 __ops_rsa_private_encrypt(unsigned char *out, 591 const unsigned char *in, 592 size_t length, 593 const __ops_rsa_seckey_t *srsa, 594 const __ops_rsa_pubkey_t *rsa) 595 { 596 RSA *orsa; 597 int n; 598 599 orsa = RSA_new(); 600 orsa->n = rsa->n; /* XXX: do we need n? */ 601 orsa->d = srsa->d; 602 orsa->p = srsa->q; 603 orsa->q = srsa->p; 604 605 /* debug */ 606 orsa->e = rsa->e; 607 /* If this isn't set, it's very likely that the programmer hasn't */ 608 /* decrypted the secret key. RSA_check_key segfaults in that case. */ 609 /* Use __ops_decrypt_seckey() to do that. */ 610 if (orsa->d == NULL) { 611 (void) fprintf(stderr, "orsa is not set\n"); 612 return 0; 613 } 614 if (RSA_check_key(orsa) != 1) { 615 (void) fprintf(stderr, "RSA_check_key is not set\n"); 616 return 0; 617 } 618 /* end debug */ 619 620 n = RSA_private_encrypt((int)length, in, out, orsa, RSA_NO_PADDING); 621 622 orsa->n = orsa->d = orsa->p = orsa->q = NULL; 623 RSA_free(orsa); 624 625 return n; 626 } 627 628 /** 629 \ingroup Core_Crypto 630 \brief Decrypts RSA-encrypted data 631 \param out Where to write the plaintext 632 \param in Encrypted data 633 \param length Length of encrypted data 634 \param srsa RSA secret key 635 \param rsa RSA public key 636 \return size of recovered plaintext 637 */ 638 int 639 __ops_rsa_private_decrypt(unsigned char *out, const unsigned char *in, 640 size_t length, const __ops_rsa_seckey_t * srsa, 641 const __ops_rsa_pubkey_t * rsa) 642 { 643 RSA *orsa; 644 int n; 645 char errbuf[1024]; 646 647 orsa = RSA_new(); 648 orsa->n = rsa->n; /* XXX: do we need n? */ 649 orsa->d = srsa->d; 650 orsa->p = srsa->q; 651 orsa->q = srsa->p; 652 653 /* debug */ 654 orsa->e = rsa->e; 655 if (RSA_check_key(orsa) != 1) { 656 (void) fprintf(stderr, "RSA_check_key is not set\n"); 657 return 0; 658 } 659 /* end debug */ 660 661 n = RSA_private_decrypt((int)length, in, out, orsa, RSA_NO_PADDING); 662 663 if (__ops_get_debug_level(__FILE__)) { 664 printf("__ops_rsa_private_decrypt: n=%d\n",n); 665 } 666 667 errbuf[0] = '\0'; 668 if (n == -1) { 669 unsigned long err = ERR_get_error(); 670 ERR_error_string(err, &errbuf[0]); 671 fprintf(stderr, "openssl error : %s\n", errbuf); 672 } 673 orsa->n = orsa->d = orsa->p = orsa->q = NULL; 674 RSA_free(orsa); 675 676 return n; 677 } 678 679 /** 680 \ingroup Core_Crypto 681 \brief RSA-encrypts data 682 \param out Where to write the encrypted data 683 \param in Plaintext 684 \param length Size of plaintext 685 \param rsa RSA Public Key 686 */ 687 int 688 __ops_rsa_public_encrypt(unsigned char *out, 689 const unsigned char *in, 690 size_t length, 691 const __ops_rsa_pubkey_t *rsa) 692 { 693 RSA *orsa; 694 int n; 695 696 /* printf("__ops_rsa_public_encrypt: length=%ld\n", length); */ 697 698 orsa = RSA_new(); 699 orsa->n = rsa->n; 700 orsa->e = rsa->e; 701 702 /* printf("len: %ld\n", length); */ 703 /* __ops_print_bn("n: ", orsa->n); */ 704 /* __ops_print_bn("e: ", orsa->e); */ 705 n = RSA_public_encrypt((int)length, in, out, orsa, RSA_NO_PADDING); 706 707 if (n == -1) { 708 BIO *fd_out; 709 710 fd_out = BIO_new_fd(fileno(stderr), BIO_NOCLOSE); 711 ERR_print_errors(fd_out); 712 } 713 orsa->n = orsa->e = NULL; 714 RSA_free(orsa); 715 716 return n; 717 } 718 719 /** 720 \ingroup Core_Crypto 721 \brief initialises openssl 722 \note Would usually call __ops_init() instead 723 \sa __ops_init() 724 */ 725 void 726 __ops_crypto_init() 727 { 728 #ifdef DMALLOC 729 CRYPTO_malloc_debug_init(); 730 CRYPTO_dbg_set_options(V_CRYPTO_MDEBUG_ALL); 731 CRYPTO_mem_ctrl(CRYPTO_MEM_CHECK_ON); 732 #endif 733 } 734 735 /** 736 \ingroup Core_Crypto 737 \brief Finalise openssl 738 \note Would usually call __ops_finish() instead 739 \sa __ops_finish() 740 */ 741 void 742 __ops_crypto_finish() 743 { 744 CRYPTO_cleanup_all_ex_data(); 745 ERR_remove_state((unsigned long)0); 746 #ifdef DMALLOC 747 CRYPTO_mem_leaks_fp(stderr); 748 #endif 749 } 750 751 /** 752 \ingroup Core_Hashes 753 \brief Get Hash name 754 \param hash Hash struct 755 \return Hash name 756 */ 757 const char * 758 __ops_text_from_hash(__ops_hash_t * hash) 759 { 760 return hash->name; 761 } 762 763 /** 764 \ingroup HighLevel_KeyGenerate 765 \brief Generates an RSA keypair 766 \param numbits Modulus size 767 \param e Public Exponent 768 \param keydata Pointer to keydata struct to hold new key 769 \return true if key generated successfully; otherwise false 770 \note It is the caller's responsibility to call __ops_keydata_free(keydata) 771 */ 772 bool 773 __ops_rsa_generate_keypair(const int numbits, 774 const unsigned long e, 775 __ops_keydata_t *keydata) 776 { 777 __ops_seckey_t *seckey = NULL; 778 RSA *rsa = NULL; 779 BN_CTX *ctx = BN_CTX_new(); 780 __ops_createinfo_t *cinfo; 781 __ops_memory_t *mem; 782 783 __ops_keydata_init(keydata, OPS_PTAG_CT_SECRET_KEY); 784 seckey = __ops_get_writable_seckey(keydata); 785 786 /* generate the key pair */ 787 788 rsa = RSA_generate_key(numbits, e, NULL, NULL); 789 790 /* populate __ops key from ssl key */ 791 792 seckey->pubkey.version = 4; 793 seckey->pubkey.birthtime = time(NULL); 794 seckey->pubkey.days_valid = 0; 795 seckey->pubkey.alg = OPS_PKA_RSA; 796 797 seckey->pubkey.key.rsa.n = BN_dup(rsa->n); 798 seckey->pubkey.key.rsa.e = BN_dup(rsa->e); 799 800 seckey->s2k_usage = OPS_S2KU_ENCRYPTED_AND_HASHED; 801 seckey->s2k_specifier = OPS_S2KS_SALTED; 802 /* seckey->s2k_specifier=OPS_S2KS_SIMPLE; */ 803 seckey->alg = OPS_SA_CAST5; /* \todo make param */ 804 seckey->hash_alg = OPS_HASH_SHA1; /* \todo make param */ 805 seckey->octetc = 0; 806 seckey->checksum = 0; 807 808 seckey->key.rsa.d = BN_dup(rsa->d); 809 seckey->key.rsa.p = BN_dup(rsa->p); 810 seckey->key.rsa.q = BN_dup(rsa->q); 811 seckey->key.rsa.u = BN_mod_inverse(NULL, rsa->p, rsa->q, ctx); 812 if (seckey->key.rsa.u == NULL) { 813 (void) fprintf(stderr, "seckey->key.rsa.u is NULL\n"); 814 return 0; 815 } 816 BN_CTX_free(ctx); 817 818 RSA_free(rsa); 819 820 __ops_keyid(keydata->key_id, OPS_KEY_ID_SIZE, OPS_KEY_ID_SIZE, 821 &keydata->key.seckey.pubkey); 822 __ops_fingerprint(&keydata->fingerprint, &keydata->key.seckey.pubkey); 823 824 /* Generate checksum */ 825 826 cinfo = NULL; 827 mem = NULL; 828 829 __ops_setup_memory_write(&cinfo, &mem, 128); 830 831 __ops_push_skey_checksum_writer(cinfo, seckey); 832 833 switch (seckey->pubkey.alg) { 834 /* case OPS_PKA_DSA: */ 835 /* return __ops_write_mpi(key->key.dsa.x,info); */ 836 837 case OPS_PKA_RSA: 838 case OPS_PKA_RSA_ENCRYPT_ONLY: 839 case OPS_PKA_RSA_SIGN_ONLY: 840 if (!__ops_write_mpi(seckey->key.rsa.d, cinfo) || 841 !__ops_write_mpi(seckey->key.rsa.p, cinfo) || 842 !__ops_write_mpi(seckey->key.rsa.q, cinfo) || 843 !__ops_write_mpi(seckey->key.rsa.u, cinfo)) { 844 return false; 845 } 846 break; 847 848 /* case OPS_PKA_ELGAMAL: */ 849 /* return __ops_write_mpi(key->key.elgamal.x,info); */ 850 851 default: 852 (void) fprintf(stderr, "Bad seckey->pubkey.alg\n"); 853 return false; 854 } 855 856 /* close rather than pop, since its the only one on the stack */ 857 __ops_writer_close(cinfo); 858 __ops_teardown_memory_write(cinfo, mem); 859 860 /* should now have checksum in seckey struct */ 861 862 /* test */ 863 if (__ops_get_debug_level(__FILE__)) { 864 test_seckey(seckey); 865 } 866 867 return true; 868 } 869 870 /** 871 \ingroup HighLevel_KeyGenerate 872 \brief Creates a self-signed RSA keypair 873 \param numbits Modulus size 874 \param e Public Exponent 875 \param userid User ID 876 \return The new keypair or NULL 877 878 \note It is the caller's responsibility to call __ops_keydata_free(keydata) 879 \sa __ops_rsa_generate_keypair() 880 \sa __ops_keydata_free() 881 */ 882 __ops_keydata_t * 883 __ops_rsa_create_selfsigned_keypair(const int numbits, 884 const unsigned long e, 885 __ops_user_id_t *userid) 886 { 887 __ops_keydata_t *keydata = NULL; 888 889 keydata = __ops_keydata_new(); 890 if (__ops_rsa_generate_keypair(numbits, e, keydata) != true || 891 __ops_add_selfsigned_userid_to_keydata(keydata, userid) != true) { 892 __ops_keydata_free(keydata); 893 return NULL; 894 } 895 return keydata; 896 } 897 898 DSA_SIG * 899 __ops_dsa_sign(unsigned char *hashbuf, 900 unsigned hashsize, 901 const __ops_dsa_seckey_t *sdsa, 902 const __ops_dsa_pubkey_t *dsa) 903 { 904 DSA_SIG *dsasig; 905 DSA *odsa; 906 907 odsa = DSA_new(); 908 odsa->p = dsa->p; 909 odsa->q = dsa->q; 910 odsa->g = dsa->g; 911 odsa->pub_key = dsa->y; 912 odsa->priv_key = sdsa->x; 913 914 dsasig = DSA_do_sign(hashbuf, (int)hashsize, odsa); 915 916 odsa->p = odsa->q = odsa->g = odsa->pub_key = odsa->priv_key = NULL; 917 DSA_free(odsa); 918 919 return dsasig; 920 } 921