1 #include "lib9.h" 2 #include "kernel.h" 3 #include <isa.h> 4 #include "interp.h" 5 #include "runt.h" 6 #include "keyring.h" 7 #include <mp.h> 8 #include <libsec.h> 9 #include "pool.h" 10 #include "raise.h" 11 #include "../libkeyring/keys.h" 12 13 14 enum { 15 PSEUDO=0, 16 REALLY, 17 }; 18 19 Type *TSigAlg; 20 Type *TCertificate; 21 Type *TSK; 22 Type *TPK; 23 Type *TDigestState; 24 Type *TAuthinfo; 25 Type *TAESstate; 26 Type *TDESstate; 27 Type *TIDEAstate; 28 Type *TBFstate; 29 Type *TRC4state; 30 Type *TIPint; 31 Type *TDSAsk; 32 Type *TDSApk; 33 Type *TDSAsig; 34 Type *TEGsk; 35 Type *TEGpk; 36 Type *TEGsig; 37 Type *TRSAsk; 38 Type *TRSApk; 39 Type *TRSAsig; 40 41 enum { 42 Maxmsg= 4096 43 }; 44 45 uchar IPintmap[] = Keyring_IPint_map; 46 uchar SigAlgmap[] = Keyring_SigAlg_map; 47 uchar SKmap[] = Keyring_SK_map; 48 uchar PKmap[] = Keyring_PK_map; 49 uchar Certificatemap[] = Keyring_Certificate_map; 50 uchar DigestStatemap[] = Keyring_DigestState_map; 51 uchar Authinfomap[] = Keyring_Authinfo_map; 52 uchar AESstatemap[] = Keyring_AESstate_map; 53 uchar DESstatemap[] = Keyring_DESstate_map; 54 uchar IDEAstatemap[] = Keyring_IDEAstate_map; 55 uchar BFstatemap[] = Keyring_BFstate_map; 56 uchar RC4statemap[] = Keyring_RC4state_map; 57 uchar DSAskmap[] = Keyring_DSAsk_map; 58 uchar DSApkmap[] = Keyring_DSApk_map; 59 uchar DSAsigmap[] = Keyring_DSAsig_map; 60 uchar EGskmap[] = Keyring_EGsk_map; 61 uchar EGpkmap[] = Keyring_EGpk_map; 62 uchar EGsigmap[] = Keyring_EGsig_map; 63 uchar RSAskmap[] = Keyring_RSAsk_map; 64 uchar RSApkmap[] = Keyring_RSApk_map; 65 uchar RSAsigmap[] = Keyring_RSAsig_map; 66 67 PK* checkPK(Keyring_PK *k); 68 69 extern void setid(char*, int); 70 extern vlong osusectime(void); 71 extern Keyring_IPint* newIPint(mpint*); 72 extern mpint* checkIPint(Keyring_IPint*); 73 extern void freeIPint(Heap*, int); 74 75 static char exBadSA[] = "bad signature algorithm"; 76 static char exBadSK[] = "bad secret key"; 77 static char exBadPK[] = "bad public key"; 78 static char exBadCert[] = "bad certificate"; 79 80 typedef struct XBFstate XBFstate; 81 82 /* BF state */ 83 struct XBFstate 84 { 85 Keyring_BFstate x; 86 BFstate state; 87 }; 88 89 /* 90 * Infinite (actually kind of big) precision integers 91 */ 92 93 /* convert a Big to base64 ascii */ 94 int 95 bigtobase64(mpint* b, char *buf, int len) 96 { 97 uchar *p; 98 int n, rv, o; 99 100 n = (b->top+1)*Dbytes; 101 p = malloc(n+1); 102 if(p == nil) 103 goto Err; 104 n = mptobe(b, p+1, n, nil); 105 if(n < 0) 106 goto Err; 107 p[0] = 0; 108 if(n != 0 && (p[1]&0x80)){ 109 /* force leading 0 byte for compatibility with older representation */ 110 /* TO DO: if b->sign < 0, complement bits and add one */ 111 o = 0; 112 n++; 113 }else 114 o = 1; 115 rv = enc64(buf, len, p+o, n); 116 free(p); 117 return rv; 118 119 Err: 120 free(p); 121 if(len > 0){ 122 *buf = '*'; 123 return 1; 124 } 125 return 0; 126 } 127 128 /* convert a Big to base64 ascii for %U */ 129 int 130 big64conv(Fmt *f) 131 { 132 mpint *b; 133 char *buf; 134 int n; 135 136 b = va_arg(f->args, mpint*); 137 n = (b->top+1)*Dbytes + 1; 138 n = ((n+3)/3)*4 + 1; 139 buf = malloc(n); 140 bigtobase64(b, buf, n); 141 n = fmtstrcpy(f, buf); 142 free(buf); 143 return n; 144 } 145 146 static void* 147 newthing(Type *t, int add) 148 { 149 Heap *h; 150 151 h = heap(t); 152 if(add) 153 ptradd(h); 154 return H2D(void*, h); 155 } 156 157 static Keyring_IPint* 158 ipcopymp(mpint* b) 159 { 160 if(b == nil) 161 return H; 162 return newIPint(mpcopy(b)); 163 } 164 165 /* convert a base64 string to a big */ 166 mpint* 167 base64tobig(char *str, char **strp) 168 { 169 int n; 170 char *p; 171 mpint *b; 172 uchar hex[(MaxBigBytes*6 + 7)/8]; 173 174 for(p = str; *p && *p != '\n'; p++) 175 ; 176 n = dec64(hex, sizeof(hex), str, p - str); 177 b = betomp(hex, n, nil); 178 if(strp){ 179 if(*p) 180 p++; 181 *strp = p; 182 } 183 return b; 184 } 185 186 /* 187 * signature algorithms 188 */ 189 enum 190 { 191 Maxalg = 8 192 }; 193 static SigAlgVec *algs[Maxalg]; 194 static int nalg; 195 196 static SigAlg* 197 newSigAlg(SigAlgVec *vec) 198 { 199 Heap *h; 200 SigAlg *sa; 201 202 h = heap(TSigAlg); 203 sa = H2D(SigAlg*, h); 204 retstr(vec->name, &sa->x.name); 205 sa->vec = vec; 206 return sa; 207 } 208 209 static void 210 freeSigAlg(Heap *h, int swept) 211 { 212 if(!swept) 213 freeheap(h, 0); 214 } 215 216 SigAlgVec* 217 findsigalg(char *name) 218 { 219 SigAlgVec **sap; 220 221 for(sap = algs; sap < &algs[nalg]; sap++) 222 if(strcmp(name, (*sap)->name) == 0) 223 return *sap; 224 return nil; 225 } 226 227 SigAlg* 228 strtoalg(char *str, char **strp) 229 { 230 int n; 231 char *p, name[20]; 232 SigAlgVec *sa; 233 234 235 p = strchr(str, '\n'); 236 if(p == 0){ 237 p = str + strlen(str); 238 if(strp) 239 *strp = p; 240 } else { 241 if(strp) 242 *strp = p+1; 243 } 244 245 n = p - str; 246 if(n < sizeof(name)){ 247 strncpy(name, str, n); 248 name[n] = 0; 249 sa = findsigalg(name); 250 if(sa != nil) 251 return newSigAlg(sa); 252 } 253 return nil; 254 } 255 256 static SigAlg* 257 checkSigAlg(Keyring_SigAlg *ksa) 258 { 259 SigAlgVec **sap; 260 SigAlg *sa; 261 262 sa = (SigAlg*)ksa; 263 264 for(sap = algs; sap < &algs[Maxalg]; sap++) 265 if(sa->vec == *sap) 266 return sa; 267 errorf("%s: %s", exType, exBadSA); 268 return nil; 269 } 270 271 /* 272 * parse next new line terminated string into a String 273 */ 274 String* 275 strtostring(char *str, char **strp) 276 { 277 char *p; 278 String *s; 279 280 p = strchr(str, '\n'); 281 if(p == 0) 282 p = str + strlen(str); 283 s = H; 284 retnstr(str, p - str, &s); 285 286 if(strp){ 287 if(*p) 288 p++; 289 *strp = p; 290 } 291 292 return s; 293 } 294 295 /* 296 * private part of a key 297 */ 298 static SK* 299 newSK(SigAlg *sa, String *owner, int increfsa) 300 { 301 Heap *h; 302 SK *k; 303 304 h = heap(TSK); 305 k = H2D(SK*, h); 306 k->x.sa = (Keyring_SigAlg*)sa; 307 if(increfsa) { 308 h = D2H(sa); 309 h->ref++; 310 Setmark(h); 311 } 312 k->x.owner = owner; 313 k->key = 0; 314 return k; 315 } 316 317 static void 318 freeSK(Heap *h, int swept) 319 { 320 SK *k; 321 SigAlg *sa; 322 323 k = H2D(SK*, h); 324 sa = checkSigAlg(k->x.sa); 325 if(k->key) 326 (*sa->vec->skfree)(k->key); 327 freeheap(h, swept); 328 } 329 330 static SK* 331 checkSK(Keyring_SK *k) 332 { 333 SK *sk; 334 335 sk = (SK*)k; 336 if(sk == H || sk == nil || sk->key == 0 || D2H(sk)->t != TSK){ 337 errorf("%s: %s", exType, exBadSK); 338 return nil; 339 } 340 return sk; 341 } 342 343 void 344 Keyring_genSK(void *fp) 345 { 346 F_Keyring_genSK *f; 347 SK *sk; 348 SigAlg *sa; 349 void *v; 350 351 f = fp; 352 v = *f->ret; 353 *f->ret = H; 354 destroy(v); 355 356 sa = strtoalg(string2c(f->algname), 0); 357 if(sa == nil) 358 return; 359 360 sk = newSK(sa, stringdup(f->owner), 0); 361 *f->ret = (Keyring_SK*)sk; 362 release(); 363 sk->key = (*sa->vec->gensk)(f->length); 364 acquire(); 365 } 366 367 void 368 Keyring_genSKfromPK(void *fp) 369 { 370 F_Keyring_genSKfromPK *f; 371 SigAlg *sa; 372 PK *pk; 373 SK *sk; 374 void *v; 375 376 f = fp; 377 v = *f->ret; 378 *f->ret = H; 379 destroy(v); 380 381 pk = checkPK(f->pk); 382 sa = checkSigAlg(pk->x.sa); 383 sk = newSK(sa, stringdup(f->owner), 1); 384 *f->ret = (Keyring_SK*)sk; 385 release(); 386 sk->key = (*sa->vec->genskfrompk)(pk->key); 387 acquire(); 388 } 389 390 /* converts a sequence of newline-separated base64-encoded mpints to attr=hexval ... in f */ 391 static char* 392 bigs2attr(Fmt *f, char *bigs, char **names) 393 { 394 int i, n, nd; 395 char *b16, *vals[20]; 396 uchar data[(MaxBigBytes*6 + 7)/8]; 397 398 b16 = malloc(2*MaxBigBytes+1); 399 if(b16 == nil) 400 return nil; 401 n = getfields(bigs, vals, nelem(vals), 0, "\n"); 402 for(i = 0; i < n-1; i++){ 403 if(names == nil || names[i] == nil) 404 break; /* shouldn't happen */ 405 nd = dec64(data, sizeof(data), vals[i], strlen(vals[i])); 406 if(nd < 0) 407 break; 408 enc16(b16, 2*MaxBigBytes+1, data, nd); 409 fmtprint(f, " %s=%s", names[i], b16); 410 } 411 free(b16); 412 return fmtstrflush(f); 413 } 414 415 void 416 Keyring_sktoattr(void *fp) 417 { 418 F_Keyring_sktoattr *f; 419 char *val, *buf, *owner; 420 SigAlg *sa; 421 Fmt o; 422 SK *sk; 423 424 f = fp; 425 sk = checkSK(f->sk); 426 sa = checkSigAlg(sk->x.sa); 427 buf = malloc(Maxbuf); 428 if(buf == nil){ 429 retstr(nil, f->ret); 430 return; 431 } 432 (*sa->vec->sk2str)(sk->key, buf, Maxbuf); 433 fmtstrinit(&o); 434 fmtprint(&o, "alg=%q", string2c(sa->x.name)); 435 owner = string2c(sk->x.owner); 436 if(*owner) 437 fmtprint(&o, " owner=%q", owner); 438 val = bigs2attr(&o, buf, sa->vec->skattr); 439 free(buf); 440 retstr(val, f->ret); 441 free(val); 442 } 443 444 static int 445 sktostr(SK *sk, char *buf, int len) 446 { 447 int n; 448 SigAlg *sa; 449 450 sa = checkSigAlg(sk->x.sa); 451 n = snprint(buf, len, "%s\n%s\n", string2c(sa->x.name), 452 string2c(sk->x.owner)); 453 return n + (*sa->vec->sk2str)(sk->key, buf+n, len - n); 454 } 455 456 void 457 Keyring_sktostr(void *fp) 458 { 459 F_Keyring_sktostr *f; 460 char *buf; 461 462 f = fp; 463 buf = malloc(Maxbuf); 464 465 if(buf) 466 sktostr(checkSK(f->sk), buf, Maxbuf); 467 retstr(buf, f->ret); 468 469 free(buf); 470 } 471 472 static SK* 473 strtosk(char *buf) 474 { 475 SK *sk; 476 char *p; 477 SigAlg *sa; 478 String *owner; 479 void *key; 480 481 sa = strtoalg(buf, &p); 482 if(sa == nil) 483 return H; 484 owner = strtostring(p, &p); 485 if(owner == H){ 486 destroy(sa); 487 return H; 488 } 489 490 key = (*sa->vec->str2sk)(p, &p); 491 if(key == nil){ 492 destroy(sa); 493 destroy(owner); 494 return H; 495 } 496 sk = newSK(sa, owner, 0); 497 sk->key = key; 498 499 return sk; 500 } 501 502 void 503 Keyring_strtosk(void *fp) 504 { 505 F_Keyring_strtosk *f; 506 void *v; 507 508 f = fp; 509 v = *f->ret; 510 *f->ret = H; 511 destroy(v); 512 *f->ret = (Keyring_SK*)strtosk(string2c(f->s)); 513 } 514 515 /* 516 * public part of a key 517 */ 518 PK* 519 newPK(SigAlg *sa, String *owner, int increfsa) 520 { 521 Heap *h; 522 PK *k; 523 524 h = heap(TPK); 525 k = H2D(PK*, h); 526 k->x.sa = (Keyring_SigAlg*)sa; 527 if(increfsa) { 528 h = D2H(sa); 529 h->ref++; 530 Setmark(h); 531 } 532 k->x.owner = owner; 533 k->key = 0; 534 return k; 535 } 536 537 void 538 pkimmutable(PK *k) 539 { 540 poolimmutable(D2H(k)); 541 poolimmutable(D2H(k->x.sa)); 542 poolimmutable(D2H(k->x.sa->name)); 543 poolimmutable(D2H(k->x.owner)); 544 } 545 546 void 547 pkmutable(PK *k) 548 { 549 poolmutable(D2H(k)); 550 poolmutable(D2H(k->x.sa)); 551 poolmutable(D2H(k->x.sa->name)); 552 poolmutable(D2H(k->x.owner)); 553 } 554 555 void 556 freePK(Heap *h, int swept) 557 { 558 PK *k; 559 SigAlg *sa; 560 561 k = H2D(PK*, h); 562 sa = checkSigAlg(k->x.sa); 563 if(k->key) 564 (*sa->vec->pkfree)(k->key); 565 freeheap(h, swept); 566 } 567 568 PK* 569 checkPK(Keyring_PK *k) 570 { 571 PK *pk; 572 573 pk = (PK*)k; 574 if(pk == H || pk == nil || pk->key == 0 || D2H(pk)->t != TPK){ 575 errorf("%s: %s", exType, exBadPK); 576 return nil; 577 } 578 return pk; 579 } 580 581 void 582 Keyring_sktopk(void *fp) 583 { 584 F_Keyring_sktopk *f; 585 PK *pk; 586 SigAlg *sa; 587 SK *sk; 588 589 f = fp; 590 destroy(*f->ret); 591 *f->ret = H; 592 593 sk = checkSK(f->sk); 594 sa = checkSigAlg(sk->x.sa); 595 pk = newPK(sa, stringdup(sk->x.owner), 1); 596 pk->key = (*sa->vec->sk2pk)(sk->key); 597 *f->ret = (Keyring_PK*)pk; 598 } 599 600 static int 601 pktostr(PK *pk, char *buf, int len) 602 { 603 int n; 604 SigAlg *sa; 605 606 sa = checkSigAlg(pk->x.sa); 607 n = snprint(buf, len, "%s\n%s\n", string2c(sa->x.name), string2c(pk->x.owner)); 608 return n + (*sa->vec->pk2str)(pk->key, buf+n, len - n); 609 } 610 611 void 612 Keyring_pktostr(void *fp) 613 { 614 F_Keyring_pktostr *f; 615 char *buf; 616 617 f = fp; 618 buf = malloc(Maxbuf); 619 620 if(buf) 621 pktostr(checkPK(f->pk), buf, Maxbuf); 622 retstr(buf, f->ret); 623 624 free(buf); 625 } 626 627 void 628 Keyring_pktoattr(void *fp) 629 { 630 F_Keyring_pktoattr *f; 631 char *val, *buf, *owner; 632 SigAlg *sa; 633 Fmt o; 634 PK *pk; 635 636 f = fp; 637 pk = checkPK(f->pk); 638 sa = checkSigAlg(pk->x.sa); 639 buf = malloc(Maxbuf); 640 if(buf == nil){ 641 retstr(nil, f->ret); 642 return; 643 } 644 (*sa->vec->pk2str)(pk->key, buf, Maxbuf); 645 fmtstrinit(&o); 646 fmtprint(&o, "alg=%q", string2c(sa->x.name)); 647 owner = string2c(pk->x.owner); 648 if(*owner) 649 fmtprint(&o, " owner=%q", owner); 650 val = bigs2attr(&o, buf, sa->vec->pkattr); 651 free(buf); 652 retstr(val, f->ret); 653 free(val); 654 } 655 656 static PK* 657 strtopk(char *buf) 658 { 659 PK *pk; 660 char *p; 661 SigAlg *sa; 662 String *owner; 663 void *key; 664 665 sa = strtoalg(buf, &p); 666 if(sa == nil) 667 return H; 668 owner = strtostring(p, &p); 669 if(owner == H){ 670 destroy(sa); 671 return H; 672 } 673 674 key = (*sa->vec->str2pk)(p, &p); 675 if(key == nil){ 676 destroy(sa); 677 destroy(owner); 678 return H; 679 } 680 pk = newPK(sa, owner, 0); 681 pk->key = key; 682 683 return pk; 684 } 685 686 void 687 Keyring_strtopk(void *fp) 688 { 689 F_Keyring_strtopk *f; 690 void *v; 691 692 f = fp; 693 v = *f->ret; 694 *f->ret = H; 695 destroy(v); 696 *f->ret = (Keyring_PK*)strtopk(string2c(f->s)); 697 } 698 699 /* 700 * Certificates/signatures 701 */ 702 703 void 704 certimmutable(Certificate *c) 705 { 706 poolimmutable(D2H(c)); 707 poolimmutable(D2H(c->x.signer)); 708 poolimmutable(D2H(c->x.ha)); 709 poolimmutable(D2H(c->x.sa)); 710 poolimmutable(D2H(c->x.sa->name)); 711 } 712 713 void 714 certmutable(Certificate *c) 715 { 716 poolmutable(D2H(c)); 717 poolmutable(D2H(c->x.signer)); 718 poolmutable(D2H(c->x.ha)); 719 Setmark(D2H(c->x.sa)); 720 poolmutable(D2H(c->x.sa)); 721 Setmark(D2H(c->x.sa->name)); 722 poolmutable(D2H(c->x.sa->name)); 723 } 724 725 Certificate* 726 newCertificate(SigAlg *sa, String *ha, String *signer, long exp, int increfsa) 727 { 728 Heap *h; 729 Certificate *c; 730 731 h = heap(TCertificate); 732 c = H2D(Certificate*, h); 733 c->x.sa = (Keyring_SigAlg*)sa; 734 if(increfsa) { 735 h = D2H(sa); 736 h->ref++; 737 Setmark(h); 738 } 739 c->x.signer = signer; 740 c->x.ha = ha; 741 c->x.exp = exp; 742 c->signa = 0; 743 744 return c; 745 } 746 747 void 748 freeCertificate(Heap *h, int swept) 749 { 750 Certificate *c; 751 SigAlg *sa; 752 753 c = H2D(Certificate*, h); 754 sa = checkSigAlg(c->x.sa); 755 if(c->signa) 756 (*sa->vec->sigfree)(c->signa); 757 freeheap(h, swept); 758 } 759 760 Certificate* 761 checkCertificate(Keyring_Certificate *c) 762 { 763 Certificate *cert; 764 765 cert = (Certificate*)c; 766 if(cert == H || cert == nil || cert->signa == 0 || D2H(cert)->t != TCertificate){ 767 errorf("%s: %s", exType, exBadCert); 768 return nil; 769 } 770 return cert; 771 } 772 773 static int 774 certtostr(Certificate *c, char *buf, int len) 775 { 776 SigAlg *sa; 777 int n; 778 779 sa = checkSigAlg(c->x.sa); 780 n = snprint(buf, len, "%s\n%s\n%s\n%d\n", string2c(sa->x.name), 781 string2c(c->x.ha), string2c(c->x.signer), c->x.exp); 782 return n + (*sa->vec->sig2str)(c->signa, buf+n, len - n); 783 } 784 785 void 786 Keyring_certtostr(void *fp) 787 { 788 F_Keyring_certtostr *f; 789 char *buf; 790 791 f = fp; 792 buf = malloc(Maxbuf); 793 794 if(buf) 795 certtostr(checkCertificate(f->c), buf, Maxbuf); 796 retstr(buf, f->ret); 797 798 free(buf); 799 } 800 801 void 802 Keyring_certtoattr(void *fp) 803 { 804 F_Keyring_certtoattr *f; 805 char *val, *buf, *ha; 806 SigAlg *sa; 807 Fmt o; 808 Certificate *c; 809 810 f = fp; 811 c = checkCertificate(f->c); 812 sa = checkSigAlg(c->x.sa); 813 buf = malloc(Maxbuf); 814 if(buf == nil){ 815 retstr(nil, f->ret); 816 return; 817 } 818 (*sa->vec->sig2str)(c->signa, buf, Maxbuf); 819 ha = string2c(c->x.ha); 820 if(strcmp(ha, "sha") == 0) 821 ha = "sha1"; /* normalise */ 822 fmtstrinit(&o); 823 fmtprint(&o, "sigalg=%q-%q signer=%q expires=%ud", string2c(sa->x.name), ha, 824 string2c(c->x.signer), c->x.exp); 825 val = bigs2attr(&o, buf, sa->vec->sigattr); 826 free(buf); 827 retstr(val, f->ret); 828 free(val); 829 } 830 831 static Certificate* 832 strtocert(char *buf) 833 { 834 Certificate *c; 835 char *p; 836 SigAlg *sa; 837 String *signer, *ha; 838 long exp; 839 void *signa; 840 841 sa = strtoalg(buf, &p); 842 if(sa == 0) 843 return H; 844 845 ha = strtostring(p, &p); 846 if(ha == H){ 847 destroy(sa); 848 return H; 849 } 850 851 signer = strtostring(p, &p); 852 if(signer == H){ 853 destroy(sa); 854 destroy(ha); 855 return H; 856 } 857 858 exp = strtoul(p, &p, 10); 859 if(*p) 860 p++; 861 signa = (*sa->vec->str2sig)(p, &p); 862 if(signa == nil){ 863 destroy(sa); 864 destroy(ha); 865 destroy(signer); 866 return H; 867 } 868 869 c = newCertificate(sa, ha, signer, exp, 0); 870 c->signa = signa; 871 872 return c; 873 } 874 875 void 876 Keyring_strtocert(void *fp) 877 { 878 F_Keyring_strtocert *f; 879 880 f = fp; 881 destroy(*f->ret); 882 *f->ret = H; 883 *f->ret = (Keyring_Certificate*)strtocert(string2c(f->s)); 884 } 885 886 static Certificate* 887 sign(SK *sk, char *ha, ulong exp, uchar *a, int len) 888 { 889 Certificate *c; 890 mpint *b; 891 int n; 892 SigAlg *sa; 893 DigestState *ds; 894 uchar digest[SHA1dlen]; 895 char *buf; 896 String *hastr; 897 898 hastr = H; 899 sa = checkSigAlg(sk->x.sa); 900 buf = malloc(Maxbuf); 901 if(buf == nil) 902 return nil; 903 904 /* add signer name and expiration time to hash */ 905 n = snprint(buf, Maxbuf, "%s %lud", string2c(sk->x.owner), exp); 906 if(strcmp(ha, "sha") == 0 || strcmp(ha, "sha1") == 0){ 907 ds = sha1(a, len, 0, 0); 908 sha1((uchar*)buf, n, digest, ds); 909 n = Keyring_SHA1dlen; 910 } else if(strcmp(ha, "md5") == 0){ 911 ds = md5(a, len, 0, 0); 912 md5((uchar*)buf, n, digest, ds); 913 n = Keyring_MD5dlen; 914 } else if(strcmp(ha, "md4") == 0){ 915 ds = md4(a, len, 0, 0); 916 md4((uchar*)buf, n, digest, ds); 917 n = Keyring_MD5dlen; 918 } else { 919 free(buf); 920 return nil; 921 } 922 free(buf); 923 924 /* turn message into a big integer */ 925 b = betomp(digest, n, nil); 926 if(b == nil) 927 return nil; 928 929 /* sign */ 930 retstr(ha, &hastr); 931 c = newCertificate(sa, hastr, stringdup(sk->x.owner), exp, 1); 932 certimmutable(c); /* hide from the garbage collector */ 933 release(); 934 c->signa = (*sa->vec->sign)(b, sk->key); 935 acquire(); 936 mpfree(b); 937 938 return c; 939 } 940 941 void 942 Keyring_sign(void *fp) 943 { 944 F_Keyring_sign *f; 945 Certificate *c; 946 mpint *b; 947 int n; 948 SigAlg *sa; 949 SK *sk; 950 XDigestState *ds; 951 uchar digest[SHA1dlen]; 952 char *buf; 953 void *v; 954 955 f = fp; 956 v = *f->ret; 957 *f->ret = H; 958 destroy(v); 959 960 sk = checkSK(f->sk); 961 sa = checkSigAlg(sk->x.sa); 962 963 /* add signer name and expiration time to hash */ 964 if(f->state == H) 965 return; 966 buf = malloc(Maxbuf); 967 if(buf == nil) 968 return; 969 ds = (XDigestState*)f->state; 970 n = snprint(buf, Maxbuf, "%s %d", string2c(sk->x.owner), f->exp); 971 if(strcmp(string2c(f->ha), "sha") == 0 || strcmp(string2c(f->ha), "sha1") == 0){ 972 sha1((uchar*)buf, n, digest, &ds->state); 973 n = Keyring_SHA1dlen; 974 } else if(strcmp(string2c(f->ha), "md5") == 0){ 975 md5((uchar*)buf, n, digest, &ds->state); 976 n = Keyring_MD5dlen; 977 } else if(strcmp(string2c(f->ha), "md4") == 0){ 978 md4((uchar*)buf, n, digest, &ds->state); 979 n = Keyring_MD5dlen; 980 } else { 981 free(buf); 982 return; 983 } 984 free(buf); 985 986 /* turn message into a big integer */ 987 b = betomp(digest, n, nil); 988 if(b == nil) 989 return; 990 991 /* sign */ 992 c = newCertificate(sa, stringdup(f->ha), stringdup(sk->x.owner), f->exp, 1); 993 *f->ret = (Keyring_Certificate*)c; 994 release(); 995 c->signa = (*sa->vec->sign)(b, sk->key); 996 acquire(); 997 mpfree(b); 998 } 999 1000 void 1001 Keyring_signm(void *fp) 1002 { 1003 F_Keyring_signm *f; 1004 Certificate *c; 1005 mpint *b; 1006 SigAlg *sa; 1007 SK *sk; 1008 void *v; 1009 1010 f = fp; 1011 v = *f->ret; 1012 *f->ret = H; 1013 destroy(v); 1014 1015 sk = checkSK(f->sk); 1016 sa = checkSigAlg(sk->x.sa); 1017 1018 if(f->m == H) 1019 return; 1020 b = checkIPint(f->m); 1021 1022 /* sign */ 1023 c = newCertificate(sa, stringdup(f->ha), stringdup(sk->x.owner), 0, 1); 1024 *f->ret = (Keyring_Certificate*)c; 1025 release(); 1026 c->signa = (*sa->vec->sign)(b, sk->key); 1027 acquire(); 1028 } 1029 1030 static int 1031 verify(PK *pk, Certificate *c, char *a, int len) 1032 { 1033 mpint *b; 1034 int n; 1035 SigAlg *sa, *pksa; 1036 DigestState *ds; 1037 uchar digest[SHA1dlen]; 1038 char *buf; 1039 1040 sa = checkSigAlg(c->x.sa); 1041 pksa = checkSigAlg(pk->x.sa); 1042 if(sa->vec != pksa->vec) 1043 return 0; 1044 1045 /* add signer name and expiration time to hash */ 1046 buf = malloc(Maxbuf); 1047 if(buf == nil) 1048 return 0; 1049 n = snprint(buf, Maxbuf, "%s %d", string2c(c->x.signer), c->x.exp); 1050 if(strcmp(string2c(c->x.ha), "sha") == 0 || strcmp(string2c(c->x.ha), "sha1") == 0){ 1051 ds = sha1((uchar*)a, len, 0, 0); 1052 sha1((uchar*)buf, n, digest, ds); 1053 n = Keyring_SHA1dlen; 1054 } else if(strcmp(string2c(c->x.ha), "md5") == 0){ 1055 ds = md5((uchar*)a, len, 0, 0); 1056 md5((uchar*)buf, n, digest, ds); 1057 n = Keyring_MD5dlen; 1058 } else if(strcmp(string2c(c->x.ha), "md4") == 0){ 1059 ds = md4((uchar*)a, len, 0, 0); 1060 md4((uchar*)buf, n, digest, ds); 1061 n = Keyring_MD5dlen; 1062 } else { 1063 free(buf); 1064 return 0; 1065 } 1066 free(buf); 1067 1068 /* turn message into a big integer */ 1069 b = betomp(digest, n, nil); 1070 if(b == nil) 1071 return 0; 1072 /* verify */ 1073 release(); 1074 n = (*sa->vec->verify)(b, c->signa, pk->key); 1075 acquire(); 1076 1077 mpfree(b); 1078 return n; 1079 } 1080 1081 void 1082 Keyring_verify(void *fp) 1083 { 1084 F_Keyring_verify *f; 1085 Certificate *c; 1086 mpint *b; 1087 int n; 1088 SigAlg *sa, *pksa; 1089 PK *pk; 1090 XDigestState *ds; 1091 uchar digest[SHA1dlen]; 1092 char *buf; 1093 1094 f = fp; 1095 *f->ret = 0; 1096 1097 c = checkCertificate(f->cert); 1098 sa = checkSigAlg(c->x.sa); 1099 pk = checkPK(f->pk); 1100 pksa = checkSigAlg(pk->x.sa); 1101 if(sa->vec != pksa->vec) 1102 return; 1103 1104 /* add signer name and expiration time to hash */ 1105 if(f->state == H) 1106 return; 1107 buf = malloc(Maxbuf); 1108 if(buf == nil) 1109 return; 1110 n = snprint(buf, Maxbuf, "%s %d", string2c(c->x.signer), c->x.exp); 1111 ds = (XDigestState*)f->state; 1112 1113 if(strcmp(string2c(c->x.ha), "sha") == 0 || strcmp(string2c(c->x.ha), "sha1") == 0){ 1114 sha1((uchar*)buf, n, digest, &ds->state); 1115 n = Keyring_SHA1dlen; 1116 } else if(strcmp(string2c(c->x.ha), "md5") == 0){ 1117 md5((uchar*)buf, n, digest, &ds->state); 1118 n = Keyring_MD5dlen; 1119 } else if(strcmp(string2c(c->x.ha), "md4") == 0){ 1120 md4((uchar*)buf, n, digest, &ds->state); 1121 n = Keyring_MD5dlen; 1122 } else { 1123 free(buf); 1124 return; 1125 } 1126 free(buf); 1127 1128 /* turn message into a big integer */ 1129 b = betomp(digest, n, nil); 1130 if(b == nil) 1131 return; 1132 1133 /* verify */ 1134 release(); 1135 *f->ret = (*sa->vec->verify)(b, c->signa, pk->key); 1136 acquire(); 1137 1138 mpfree(b); 1139 } 1140 1141 void 1142 Keyring_verifym(void *fp) 1143 { 1144 F_Keyring_verifym *f; 1145 Certificate *c; 1146 SigAlg *sa, *pksa; 1147 PK *pk; 1148 1149 f = fp; 1150 *f->ret = 0; 1151 1152 c = checkCertificate(f->cert); 1153 sa = checkSigAlg(c->x.sa); 1154 pk = checkPK(f->pk); 1155 pksa = checkSigAlg(pk->x.sa); 1156 if(sa->vec != pksa->vec) 1157 return; 1158 1159 if(f->m == H) 1160 return; 1161 1162 release(); 1163 *f->ret = (*sa->vec->verify)(checkIPint(f->m), c->signa, pk->key); 1164 acquire(); 1165 } 1166 1167 /* 1168 * digests 1169 */ 1170 void 1171 DigestState_copy(void *fp) 1172 { 1173 F_DigestState_copy *f; 1174 Heap *h; 1175 XDigestState *ds; 1176 void *r; 1177 1178 f = fp; 1179 r = *f->ret; 1180 *f->ret = H; 1181 destroy(r); 1182 1183 if(f->d != H){ 1184 h = heap(TDigestState); 1185 ds = H2D(XDigestState*, h); 1186 memmove(&ds->state, &((XDigestState*)f->d)->state, sizeof(ds->state)); 1187 *f->ret = (Keyring_DigestState*)ds; 1188 } 1189 } 1190 1191 static Keyring_DigestState* 1192 keyring_digest_x(Array *buf, int n, Array *digest, int dlen, Keyring_DigestState *state, DigestState* (*fn)(uchar*, ulong, uchar*, DigestState*)) 1193 { 1194 Heap *h; 1195 XDigestState *ds; 1196 uchar *cbuf, *cdigest; 1197 1198 if(buf != H){ 1199 if(n > buf->len) 1200 n = buf->len; 1201 cbuf = buf->data; 1202 }else{ 1203 if(n != 0) 1204 return H; 1205 cbuf = nil; 1206 } 1207 1208 if(digest != H){ 1209 if(digest->len < dlen) 1210 return H; 1211 cdigest = digest->data; 1212 } else 1213 cdigest = nil; 1214 1215 if(state == H){ 1216 h = heap(TDigestState); 1217 ds = H2D(XDigestState*, h); 1218 memset(&ds->state, 0, sizeof(ds->state)); 1219 } else { 1220 D2H(state)->ref++; 1221 ds = (XDigestState*)state; 1222 } 1223 1224 (*fn)(cbuf, n, cdigest, &ds->state); 1225 1226 return (Keyring_DigestState*)ds; 1227 } 1228 1229 void 1230 Keyring_sha1(void *fp) 1231 { 1232 F_Keyring_sha1 *f; 1233 void *r; 1234 1235 f = fp; 1236 r = *f->ret; 1237 *f->ret = H; 1238 destroy(r); 1239 1240 *f->ret = keyring_digest_x(f->buf, f->n, f->digest, SHA1dlen, f->state, sha1); 1241 } 1242 1243 void 1244 Keyring_md5(void *fp) 1245 { 1246 F_Keyring_md5 *f; 1247 void *r; 1248 1249 f = fp; 1250 r = *f->ret; 1251 *f->ret = H; 1252 destroy(r); 1253 1254 *f->ret = keyring_digest_x(f->buf, f->n, f->digest, MD5dlen, f->state, md5); 1255 } 1256 1257 void 1258 Keyring_md4(void *fp) 1259 { 1260 F_Keyring_md4 *f; 1261 void *r; 1262 1263 f = fp; 1264 r = *f->ret; 1265 *f->ret = H; 1266 destroy(r); 1267 1268 *f->ret = keyring_digest_x(f->buf, f->n, f->digest, MD4dlen, f->state, md4); 1269 } 1270 1271 static Keyring_DigestState* 1272 keyring_hmac_x(Array *data, int n, Array *key, Array *digest, int dlen, Keyring_DigestState *state, DigestState* (*fn)(uchar*, ulong, uchar*, ulong, uchar*, DigestState*)) 1273 { 1274 Heap *h; 1275 XDigestState *ds; 1276 uchar *cdata, *cdigest; 1277 1278 if(data != H){ 1279 if(n > data->len) 1280 n = data->len; 1281 cdata = data->data; 1282 }else{ 1283 if(n != 0) 1284 return H; 1285 cdata = nil; 1286 } 1287 1288 if(key == H || key->len > 64) 1289 return H; 1290 1291 if(digest != H){ 1292 if(digest->len < dlen) 1293 return H; 1294 cdigest = digest->data; 1295 } else 1296 cdigest = nil; 1297 1298 if(state == H){ 1299 h = heap(TDigestState); 1300 ds = H2D(XDigestState*, h); 1301 memset(&ds->state, 0, sizeof(ds->state)); 1302 } else { 1303 D2H(state)->ref++; 1304 ds = (XDigestState*)state; 1305 } 1306 1307 (*fn)(cdata, n, key->data, key->len, cdigest, &ds->state); 1308 1309 return (Keyring_DigestState*)ds; 1310 } 1311 1312 void 1313 Keyring_hmac_sha1(void *fp) 1314 { 1315 F_Keyring_hmac_sha1 *f; 1316 void *r; 1317 1318 f = fp; 1319 r = *f->ret; 1320 *f->ret = H; 1321 destroy(r); 1322 *f->ret = keyring_hmac_x(f->data, f->n, f->key, f->digest, SHA1dlen, f->state, hmac_sha1); 1323 } 1324 1325 void 1326 Keyring_hmac_md5(void *fp) 1327 { 1328 F_Keyring_hmac_md5 *f; 1329 void *r; 1330 1331 f = fp; 1332 r = *f->ret; 1333 *f->ret = H; 1334 destroy(r); 1335 *f->ret = keyring_hmac_x(f->data, f->n, f->key, f->digest, MD5dlen, f->state, hmac_md5); 1336 } 1337 1338 void 1339 Keyring_dhparams(void *fp) 1340 { 1341 F_Keyring_dhparams *f; 1342 mpint *p, *alpha; 1343 void *v; 1344 1345 f = fp; 1346 v = f->ret->t0; 1347 f->ret->t0 = H; 1348 destroy(v); 1349 v = f->ret->t1; 1350 f->ret->t1 = H; 1351 destroy(v); 1352 1353 p = mpnew(0); 1354 alpha = mpnew(0); 1355 release(); 1356 if(f->nbits == 1024) 1357 DSAprimes(alpha, p, nil); 1358 else 1359 gensafeprime(p, alpha, f->nbits, 0); 1360 acquire(); 1361 f->ret->t0 = newIPint(alpha); 1362 f->ret->t1 = newIPint(p); 1363 } 1364 1365 static int 1366 sendmsg(int fd, void *buf, int n) 1367 { 1368 char num[10]; 1369 1370 release(); 1371 snprint(num, sizeof(num), "%4.4d\n", n); 1372 if(kwrite(fd, num, 5) != 5){ 1373 acquire(); 1374 return -1; 1375 } 1376 n = kwrite(fd, buf, n); 1377 acquire(); 1378 return n; 1379 } 1380 1381 void 1382 Keyring_sendmsg(void *fp) 1383 { 1384 F_Keyring_sendmsg *f; 1385 int n; 1386 1387 f = fp; 1388 *f->ret = -1; 1389 if(f->fd == H || f->buf == H || f->n < 0) 1390 return; 1391 n = f->buf->len; 1392 if(n > f->n) 1393 n = f->n; 1394 *f->ret = sendmsg(f->fd->fd, f->buf->data, n); 1395 } 1396 1397 static int 1398 senderr(int fd, char *err, int addrmt) 1399 { 1400 char num[10]; 1401 int n, m; 1402 1403 release(); 1404 n = strlen(err); 1405 m = 0; 1406 if(addrmt) 1407 m = strlen("remote: "); 1408 snprint(num, sizeof(num), "!%3.3d\n", n+m); 1409 if(kwrite(fd, num, 5) != 5){ 1410 acquire(); 1411 return -1; 1412 } 1413 if(addrmt) 1414 kwrite(fd, "remote: ", m); 1415 n = kwrite(fd, err, n); 1416 acquire(); 1417 return n; 1418 } 1419 1420 void 1421 Keyring_senderrmsg(void *fp) 1422 { 1423 F_Keyring_senderrmsg *f; 1424 char *s; 1425 1426 f = fp; 1427 *f->ret = -1; 1428 if(f->fd == H) 1429 return; 1430 s = string2c(f->s); 1431 if(senderr(f->fd->fd, s, 0) > 0) 1432 *f->ret = 0; 1433 } 1434 1435 static int 1436 nreadn(int fd, void *av, int n) 1437 { 1438 1439 char *a; 1440 long m, t; 1441 1442 a = av; 1443 t = 0; 1444 while(t < n){ 1445 m = kread(fd, a+t, n-t); 1446 if(m <= 0){ 1447 if(t == 0) 1448 return m; 1449 break; 1450 } 1451 t += m; 1452 } 1453 return t; 1454 } 1455 1456 #define MSG "input or format error" 1457 1458 static void 1459 getmsgerr(char *buf, int n, int r) 1460 { 1461 char *e; 1462 int l; 1463 1464 e = r>0? MSG: "hungup"; 1465 l = strlen(e)+1; 1466 if(n > l) 1467 n = l; 1468 memmove(buf, e, n-1); 1469 buf[n-1] = 0; 1470 } 1471 1472 static int 1473 getmsg(int fd, char *buf, int n) 1474 { 1475 char num[6]; 1476 int len, r; 1477 1478 release(); 1479 if((r = nreadn(fd, num, 5)) != 5){ 1480 getmsgerr(buf, n, r); 1481 acquire(); 1482 return -1; 1483 } 1484 num[5] = 0; 1485 1486 if(num[0] == '!') 1487 len = strtoul(num+1, 0, 10); 1488 else 1489 len = strtoul(num, 0, 10); 1490 1491 r = -1; 1492 if(len < 0 || len >= n || (r = nreadn(fd, buf, len)) != len){ 1493 getmsgerr(buf, n, r); 1494 acquire(); 1495 return -1; 1496 } 1497 1498 buf[len] = 0; 1499 acquire(); 1500 if(num[0] == '!') 1501 return -len; 1502 1503 return len; 1504 } 1505 1506 void 1507 Keyring_getmsg(void *fp) 1508 { 1509 F_Keyring_getmsg *f; 1510 char *buf; 1511 int n; 1512 1513 f = fp; 1514 destroy(*f->ret); 1515 *f->ret = H; 1516 if(f->fd == H){ 1517 kwerrstr("nil fd"); 1518 return; 1519 } 1520 1521 buf = malloc(Maxmsg); 1522 if(buf == nil){ 1523 kwerrstr(exNomem); 1524 return; 1525 } 1526 1527 n = getmsg(f->fd->fd, buf, Maxmsg); 1528 if(n < 0){ 1529 kwerrstr("%s", buf); 1530 free(buf); 1531 return; 1532 } 1533 1534 *f->ret = mem2array(buf, n); 1535 free(buf); 1536 } 1537 1538 void 1539 Keyring_auth(void *fp) 1540 { 1541 F_Keyring_auth *f; 1542 mpint *r0, *r1, *p, *alpha, *alphar0, *alphar1, *alphar0r1; 1543 SK *mysk; 1544 PK *mypk, *spk, *hispk; 1545 Certificate *cert, *hiscert, *alphacert; 1546 char *buf, *err; 1547 uchar *cvb; 1548 int n, fd, version; 1549 long now; 1550 1551 hispk = H; 1552 hiscert = H; 1553 alphacert = H; 1554 err = nil; 1555 1556 /* null out the return values */ 1557 f = fp; 1558 destroy(f->ret->t0); 1559 f->ret->t0 = H; 1560 destroy(f->ret->t1); 1561 f->ret->t1 = H; 1562 r0 = r1 = alphar0 = alphar1 = alphar0r1 = nil; 1563 1564 /* check args */ 1565 if(f->fd == H || f->fd->fd < 0){ 1566 retstr("bad fd", &f->ret->t0); 1567 return; 1568 } 1569 fd = f->fd->fd; 1570 1571 buf = malloc(Maxbuf); 1572 if(buf == nil){ 1573 retstr(exNomem, &f->ret->t0); 1574 return; 1575 } 1576 1577 /* send auth protocol version number */ 1578 if(sendmsg(fd, "1", 1) <= 0){ 1579 err = MSG; 1580 goto out; 1581 } 1582 1583 /* get auth protocol version number */ 1584 n = getmsg(fd, buf, Maxbuf-1); 1585 if(n < 0){ 1586 err = buf; 1587 goto out; 1588 } 1589 buf[n] = 0; 1590 version = atoi(buf); 1591 if(version != 1 || n > 4){ 1592 err = "incompatible authentication protocol"; 1593 goto out; 1594 } 1595 1596 if(f->info == H){ 1597 err = "no authentication information"; 1598 goto out; 1599 } 1600 if(f->info->p == H){ 1601 err = "missing diffie hellman mod"; 1602 goto out; 1603 } 1604 if(f->info->alpha == H){ 1605 err = "missing diffie hellman base"; 1606 goto out; 1607 } 1608 mysk = checkSK(f->info->mysk); 1609 if(mysk == H){ 1610 err = "bad sk arg"; 1611 goto out; 1612 } 1613 mypk = checkPK(f->info->mypk); 1614 if(mypk == H){ 1615 err = "bad pk arg"; 1616 goto out; 1617 } 1618 cert = checkCertificate(f->info->cert); 1619 if(cert == H){ 1620 err = "bad certificate arg"; 1621 goto out; 1622 } 1623 spk = checkPK(f->info->spk); 1624 if(spk == H){ 1625 err = "bad signer key arg"; 1626 goto out; 1627 } 1628 1629 /* get alpha and p */ 1630 p = checkIPint(f->info->p); 1631 alpha = checkIPint(f->info->alpha); 1632 1633 if(p->sign == -1) { 1634 err = "-ve modulus"; 1635 goto out; 1636 } 1637 1638 r0 = mpnew(0); 1639 r1 = mpnew(0); 1640 alphar0 = mpnew(0); 1641 alphar0r1 = mpnew(0); 1642 1643 /* generate alpha**r0 */ 1644 if(0)print("X"); 1645 release(); 1646 mprand(mpsignif(p), genrandom, r0); 1647 mpexp(alpha, r0, p, alphar0); 1648 acquire(); 1649 if(0)print("Y"); 1650 1651 /* send alpha**r0 mod p, mycert, and mypk */ 1652 n = bigtobase64(alphar0, buf, Maxbuf); 1653 if(sendmsg(fd, buf, n) <= 0){ 1654 err = MSG; 1655 goto out; 1656 } 1657 1658 n = certtostr(cert, buf, Maxbuf); 1659 if(sendmsg(fd, buf, n) <= 0){ 1660 err = MSG; 1661 goto out; 1662 } 1663 1664 n = pktostr(mypk, buf, Maxbuf); 1665 if(sendmsg(fd, buf, n) <= 0){ 1666 err = MSG; 1667 goto out; 1668 } 1669 1670 /* get alpha**r1 mod p, hiscert, hispk */ 1671 n = getmsg(fd, buf, Maxbuf-1); 1672 if(n < 0){ 1673 err = buf; 1674 goto out; 1675 } 1676 buf[n] = 0; 1677 alphar1 = strtomp(buf, nil, 64, nil); 1678 1679 /* trying a fast one */ 1680 if(mpcmp(p, alphar1) <= 0){ 1681 err = "implausible parameter value"; 1682 goto out; 1683 } 1684 1685 /* if alpha**r1 == alpha**r0, someone may be trying a replay */ 1686 if(mpcmp(alphar0, alphar1) == 0){ 1687 err = "possible replay attack"; 1688 goto out; 1689 } 1690 1691 n = getmsg(fd, buf, Maxbuf-1); 1692 if(n < 0){ 1693 err = buf; 1694 goto out; 1695 } 1696 buf[n] = 0; 1697 hiscert = strtocert(buf); 1698 if(hiscert == H){ 1699 err = "bad certificate syntax"; 1700 goto out; 1701 } 1702 certimmutable(hiscert); /* hide from the garbage collector */ 1703 1704 n = getmsg(fd, buf, Maxbuf-1); 1705 if(n < 0){ 1706 err = buf; 1707 goto out; 1708 } 1709 buf[n] = 0; 1710 hispk = strtopk(buf); 1711 if(hispk == H){ 1712 err = "bad public key"; 1713 goto out; 1714 } 1715 pkimmutable(hispk); /* hide from the garbage collector */ 1716 1717 /* verify his public key */ 1718 if(verify(spk, hiscert, buf, n) == 0){ 1719 err = "pk doesn't match certificate"; 1720 goto out; 1721 } 1722 1723 /* check expiration date - in seconds of epoch */ 1724 1725 now = osusectime()/1000000; 1726 if(hiscert->x.exp != 0 && hiscert->x.exp <= now){ 1727 err = "certificate expired"; 1728 goto out; 1729 } 1730 1731 /* sign alpha**r0 and alpha**r1 and send */ 1732 n = bigtobase64(alphar0, buf, Maxbuf); 1733 n += bigtobase64(alphar1, buf+n, Maxbuf-n); 1734 alphacert = sign(mysk, "sha1", 0, (uchar*)buf, n); 1735 n = certtostr(alphacert, buf, Maxbuf); 1736 if(sendmsg(fd, buf, n) <= 0){ 1737 err = MSG; 1738 goto out; 1739 } 1740 certmutable(alphacert); 1741 destroy(alphacert); 1742 alphacert = H; 1743 1744 /* get signature of alpha**r1 and alpha**r0 and verify */ 1745 n = getmsg(fd, buf, Maxbuf-1); 1746 if(n < 0){ 1747 err = buf; 1748 goto out; 1749 } 1750 buf[n] = 0; 1751 alphacert = strtocert(buf); 1752 if(alphacert == H){ 1753 err = "alpha**r1 doesn't match certificate"; 1754 goto out; 1755 } 1756 certimmutable(alphacert); /* hide from the garbage collector */ 1757 n = bigtobase64(alphar1, buf, Maxbuf); 1758 n += bigtobase64(alphar0, buf+n, Maxbuf-n); 1759 if(verify(hispk, alphacert, buf, n) == 0){ 1760 err = "bad certificate"; 1761 goto out; 1762 } 1763 1764 /* we are now authenticated and have a common secret, alpha**(r0*r1) */ 1765 f->ret->t0 = stringdup(hispk->x.owner); 1766 mpexp(alphar1, r0, p, alphar0r1); 1767 n = mptobe(alphar0r1, nil, Maxbuf, &cvb); 1768 if(n < 0){ 1769 err = "bad conversion"; 1770 goto out; 1771 } 1772 f->ret->t1 = mem2array(cvb, n); 1773 free(cvb); 1774 1775 out: 1776 /* return status */ 1777 if(f->ret->t0 == H){ 1778 if(err == buf) 1779 senderr(fd, "missing your authentication data", 1); 1780 else 1781 senderr(fd, err, 1); 1782 }else 1783 sendmsg(fd, "OK", 2); 1784 1785 /* read responses */ 1786 if(err != buf){ 1787 for(;;){ 1788 n = getmsg(fd, buf, Maxbuf-1); 1789 if(n < 0){ 1790 destroy(f->ret->t0); 1791 f->ret->t0 = H; 1792 destroy(f->ret->t1); 1793 f->ret->t1 = H; 1794 if(err == nil){ 1795 if(n < -1) 1796 err = buf; 1797 else 1798 err = MSG; 1799 } 1800 break; 1801 } 1802 if(n == 2 && buf[0] == 'O' && buf[1] == 'K') 1803 break; 1804 } 1805 } 1806 1807 /* set error and id to nobody */ 1808 if(f->ret->t0 == H){ 1809 if(err == nil) 1810 err = MSG; 1811 retstr(err, &f->ret->t0); 1812 if(f->setid) 1813 setid("nobody", 1); 1814 } else { 1815 /* change user id */ 1816 if(f->setid) 1817 setid(string2c(f->ret->t0), 1); 1818 } 1819 1820 /* free resources */ 1821 if(hispk != H){ 1822 pkmutable(hispk); 1823 destroy(hispk); 1824 } 1825 if(hiscert != H){ 1826 certmutable(hiscert); 1827 destroy(hiscert); 1828 } 1829 if(alphacert != H){ 1830 certmutable(alphacert); 1831 destroy(alphacert); 1832 } 1833 free(buf); 1834 if(r0 != nil){ 1835 mpfree(r0); 1836 mpfree(r1); 1837 mpfree(alphar0); 1838 mpfree(alphar1); 1839 mpfree(alphar0r1); 1840 } 1841 } 1842 1843 static Keyring_Authinfo* 1844 newAuthinfo(void) 1845 { 1846 return H2D(Keyring_Authinfo*, heap(TAuthinfo)); 1847 } 1848 1849 void 1850 Keyring_writeauthinfo(void *fp) 1851 { 1852 F_Keyring_writeauthinfo *f; 1853 int n, fd; 1854 char *buf; 1855 PK *spk; 1856 SK *mysk; 1857 Certificate *c; 1858 1859 f = fp; 1860 *f->ret = -1; 1861 1862 if(f->filename == H) 1863 return; 1864 if(f->info == H) 1865 return; 1866 if(f->info->alpha == H || f->info->p == H) 1867 return; 1868 if(((IPint*)f->info->alpha)->b == 0 || ((IPint*)f->info->p)->b == H) 1869 return; 1870 spk = checkPK(f->info->spk); 1871 mysk = checkSK(f->info->mysk); 1872 c = checkCertificate(f->info->cert); 1873 1874 buf = malloc(Maxbuf); 1875 if(buf == nil) 1876 return; 1877 1878 /* 1879 * The file may already exist or be a file2chan file so first 1880 * try opening with truncation since create will change the 1881 * permissions of the file and create doesn't work with a 1882 * file2chan. 1883 */ 1884 release(); 1885 fd = kopen(string2c(f->filename), OTRUNC|OWRITE); 1886 if(fd < 0) 1887 fd = kcreate(string2c(f->filename), OWRITE, 0600); 1888 if(fd < 0) 1889 fd = kopen(string2c(f->filename), OWRITE); 1890 acquire(); 1891 if(fd < 0) 1892 goto out; 1893 1894 /* signer's public key */ 1895 n = pktostr(spk, buf, Maxmsg); 1896 if(sendmsg(fd, buf, n) <= 0) 1897 goto out; 1898 1899 /* certificate for my public key */ 1900 n = certtostr(c, buf, Maxmsg); 1901 if(sendmsg(fd, buf, n) <= 0) 1902 goto out; 1903 1904 /* my secret/public key */ 1905 n = sktostr(mysk, buf, Maxmsg); 1906 if(sendmsg(fd, buf, n) <= 0) 1907 goto out; 1908 1909 /* diffie hellman base */ 1910 n = bigtobase64(((IPint*)f->info->alpha)->b, buf, Maxbuf); 1911 if(sendmsg(fd, buf, n) <= 0) 1912 goto out; 1913 1914 /* diffie hellman modulus */ 1915 n = bigtobase64(((IPint*)f->info->p)->b, buf, Maxbuf); 1916 if(sendmsg(fd, buf, n) <= 0) 1917 goto out; 1918 1919 *f->ret = 0; 1920 out: 1921 free(buf); 1922 if(fd >= 0){ 1923 release(); 1924 kclose(fd); 1925 acquire(); 1926 } 1927 } 1928 1929 void 1930 Keyring_readauthinfo(void *fp) 1931 { 1932 F_Keyring_readauthinfo *f; 1933 int fd; 1934 char *buf; 1935 int n, ok; 1936 PK *mypk; 1937 SK *mysk; 1938 SigAlg *sa; 1939 Keyring_Authinfo *ai; 1940 mpint *b; 1941 1942 f = fp; 1943 destroy(*f->ret); 1944 *f->ret = H; 1945 1946 ok = 0; 1947 1948 if(f->filename == H) 1949 return; 1950 1951 buf = malloc(Maxbuf); 1952 if(buf == nil) 1953 return; 1954 1955 ai = newAuthinfo(); 1956 *f->ret = ai; 1957 1958 release(); 1959 fd = kopen(string2c(f->filename), OREAD); 1960 acquire(); 1961 if(fd < 0) 1962 goto out; 1963 1964 /* signer's public key */ 1965 n = getmsg(fd, buf, Maxmsg); 1966 if(n < 0) 1967 goto out; 1968 1969 ai->spk = (Keyring_PK*)strtopk(buf); 1970 if(ai->spk == H) 1971 goto out; 1972 1973 /* certificate for my public key */ 1974 n = getmsg(fd, buf, Maxmsg); 1975 if(n < 0) 1976 goto out; 1977 ai->cert = (Keyring_Certificate*)strtocert(buf); 1978 if(ai->cert == H) 1979 goto out; 1980 1981 /* my secret/public key */ 1982 n = getmsg(fd, buf, Maxmsg); 1983 if(n < 0) 1984 goto out; 1985 mysk = strtosk(buf); 1986 ai->mysk = (Keyring_SK*)mysk; 1987 if(mysk == H) 1988 goto out; 1989 sa = checkSigAlg(mysk->x.sa); 1990 mypk = newPK(sa, stringdup(mysk->x.owner), 1); 1991 mypk->key = (*sa->vec->sk2pk)(mysk->key); 1992 ai->mypk = (Keyring_PK*)mypk; 1993 1994 /* diffie hellman base */ 1995 n = getmsg(fd, buf, Maxmsg); 1996 if(n < 0) 1997 goto out; 1998 b = strtomp(buf, nil, 64, nil); 1999 ai->alpha = newIPint(b); 2000 2001 /* diffie hellman modulus */ 2002 n = getmsg(fd, buf, Maxmsg); 2003 if(n < 0) 2004 goto out; 2005 b = strtomp(buf, nil, 64, nil); 2006 ai->p = newIPint(b); 2007 ok = 1; 2008 out: 2009 if(!ok){ 2010 destroy(*f->ret); 2011 *f->ret = H; 2012 } 2013 free(buf); 2014 if(fd >= 0){ 2015 release(); 2016 kclose(fd); 2017 acquire(); 2018 kwerrstr("%q: %s", string2c(f->filename), MSG); 2019 } 2020 } 2021 2022 void 2023 keyringmodinit(void) 2024 { 2025 SigAlgVec *sav; 2026 extern SigAlgVec* elgamalinit(void); 2027 extern SigAlgVec* rsainit(void); 2028 extern SigAlgVec* dsainit(void); 2029 2030 TIPint = dtype(freeIPint, sizeof(IPint), IPintmap, sizeof(IPintmap)); 2031 TSigAlg = dtype(freeSigAlg, sizeof(SigAlg), SigAlgmap, sizeof(SigAlgmap)); 2032 TSK = dtype(freeSK, sizeof(SK), SKmap, sizeof(SKmap)); 2033 TPK = dtype(freePK, sizeof(PK), PKmap, sizeof(PKmap)); 2034 TCertificate = dtype(freeCertificate, sizeof(Certificate), Certificatemap, 2035 sizeof(Certificatemap)); 2036 TDigestState = dtype(freeheap, sizeof(XDigestState), DigestStatemap, 2037 sizeof(DigestStatemap)); 2038 TAESstate = dtype(freeheap, sizeof(XAESstate), AESstatemap, 2039 sizeof(AESstatemap)); 2040 TDESstate = dtype(freeheap, sizeof(XDESstate), DESstatemap, 2041 sizeof(DESstatemap)); 2042 TIDEAstate = dtype(freeheap, sizeof(XIDEAstate), IDEAstatemap, 2043 sizeof(IDEAstatemap)); 2044 TBFstate = dtype(freeheap, sizeof(XBFstate), BFstatemap, 2045 sizeof(BFstatemap)); 2046 TRC4state = dtype(freeheap, sizeof(XRC4state), RC4statemap, 2047 sizeof(RC4statemap)); 2048 TAuthinfo = dtype(freeheap, sizeof(Keyring_Authinfo), Authinfomap, sizeof(Authinfomap)); 2049 TDSAsk = dtype(freeheap, sizeof(Keyring_DSAsk), DSAskmap, sizeof(DSAskmap)); 2050 TDSApk = dtype(freeheap, sizeof(Keyring_DSApk), DSApkmap, sizeof(DSApkmap)); 2051 TDSAsig = dtype(freeheap, sizeof(Keyring_DSAsig), DSAsigmap, sizeof(DSAsigmap)); 2052 TEGsk = dtype(freeheap, sizeof(Keyring_EGsk), EGskmap, sizeof(EGskmap)); 2053 TEGpk = dtype(freeheap, sizeof(Keyring_EGpk), EGpkmap, sizeof(EGpkmap)); 2054 TEGsig = dtype(freeheap, sizeof(Keyring_EGsig), EGsigmap, sizeof(EGsigmap)); 2055 TRSAsk = dtype(freeheap, sizeof(Keyring_RSAsk), RSAskmap, sizeof(RSAskmap)); 2056 TRSApk = dtype(freeheap, sizeof(Keyring_RSApk), RSApkmap, sizeof(RSApkmap)); 2057 TRSAsig = dtype(freeheap, sizeof(Keyring_RSAsig), RSAsigmap, sizeof(RSAsigmap)); 2058 2059 if((sav = elgamalinit()) != nil) 2060 algs[nalg++] = sav; 2061 if((sav = rsainit()) != nil) 2062 algs[nalg++] = sav; 2063 if((sav = dsainit()) != nil) 2064 algs[nalg++] = sav; 2065 2066 fmtinstall('U', big64conv); 2067 builtinmod("$Keyring", Keyringmodtab, Keyringmodlen); 2068 } 2069 2070 /* 2071 * IO on a delimited channel. A message starting with 0x00 is a normal 2072 * message. One starting with 0xff is an error string. 2073 * 2074 * return negative number for error messages (including hangup) 2075 */ 2076 static int 2077 getbuf(int fd, uchar *buf, int n, char *err, int nerr) 2078 { 2079 int len; 2080 2081 release(); 2082 len = kread(fd, buf, n); 2083 acquire(); 2084 if(len <= 0){ 2085 strncpy(err, "hungup", nerr); 2086 buf[nerr-1] = 0; 2087 return -1; 2088 } 2089 if(buf[0] == 0) 2090 return len-1; 2091 if(buf[0] != 0xff){ 2092 /* 2093 * this happens when the client's password is wrong: both sides use a digest of the 2094 * password as a crypt key for devssl. When they don't match decryption garbles 2095 * messages 2096 */ 2097 strncpy(err, "failure", nerr); 2098 err[nerr-1] = 0; 2099 return -1; 2100 } 2101 2102 /* error string */ 2103 len--; 2104 if(len < 1){ 2105 strncpy(err, "unknown", nerr); 2106 err[nerr-1] = 0; 2107 } else { 2108 if(len >= nerr) 2109 len = nerr-1; 2110 memmove(err, buf+1, len); 2111 err[len] = 0; 2112 } 2113 return -1; 2114 } 2115 2116 void 2117 Keyring_getstring(void *fp) 2118 { 2119 F_Keyring_getstring *f; 2120 uchar *buf; 2121 char err[64]; 2122 int n; 2123 2124 f = fp; 2125 destroy(f->ret->t0); 2126 f->ret->t0 = H; 2127 destroy(f->ret->t1); 2128 f->ret->t1 = H; 2129 2130 if(f->fd == H) 2131 return; 2132 2133 buf = malloc(Maxmsg); 2134 if(buf == nil) 2135 return; 2136 2137 n = getbuf(f->fd->fd, buf, Maxmsg, err, sizeof(err)); 2138 if(n < 0) 2139 retnstr(err, strlen(err), &f->ret->t1); 2140 else 2141 retnstr(((char*)buf)+1, n, &f->ret->t0); 2142 2143 free(buf); 2144 } 2145 2146 void 2147 Keyring_getbytearray(void *fp) 2148 { 2149 F_Keyring_getbytearray *f; 2150 uchar *buf; 2151 char err[64]; 2152 int n; 2153 2154 f = fp; 2155 destroy(f->ret->t0); 2156 f->ret->t0 = H; 2157 destroy(f->ret->t1); 2158 f->ret->t1 = H; 2159 2160 if(f->fd == H) 2161 return; 2162 2163 buf = malloc(Maxmsg); 2164 if(buf == nil) 2165 return; 2166 2167 n = getbuf(f->fd->fd, buf, Maxmsg, err, sizeof(err)); 2168 if(n < 0) 2169 retnstr(err, strlen(err), &f->ret->t1); 2170 else 2171 f->ret->t0 = mem2array(buf+1, n); 2172 2173 free(buf); 2174 } 2175 2176 static int 2177 putbuf(int fd, void *p, int n) 2178 { 2179 char *buf; 2180 2181 buf = malloc(Maxmsg); 2182 if(buf == nil) 2183 return -1; 2184 2185 release(); 2186 buf[0] = 0; 2187 if(n < 0){ 2188 buf[0] = 0xff; 2189 n = -n; 2190 } 2191 if(n >= Maxmsg) 2192 n = Maxmsg - 1; 2193 memmove(buf+1, p, n); 2194 n = kwrite(fd, buf, n+1); 2195 acquire(); 2196 2197 free(buf); 2198 return n; 2199 } 2200 2201 void 2202 Keyring_putstring(void *fp) 2203 { 2204 F_Keyring_putstring *f; 2205 2206 f = fp; 2207 *f->ret = -1; 2208 if(f->fd == H || f->s == H) 2209 return; 2210 *f->ret = putbuf(f->fd->fd, string2c(f->s), strlen(string2c(f->s))); 2211 } 2212 2213 void 2214 Keyring_puterror(void *fp) 2215 { 2216 F_Keyring_puterror *f; 2217 2218 f = fp; 2219 *f->ret = -1; 2220 if(f->fd == H || f->s == H) 2221 return; 2222 *f->ret = putbuf(f->fd->fd, string2c(f->s), -strlen(string2c(f->s))); 2223 } 2224 2225 void 2226 Keyring_putbytearray(void *fp) 2227 { 2228 F_Keyring_putbytearray *f; 2229 int n; 2230 2231 f = fp; 2232 *f->ret = -1; 2233 if(f->fd == H || f->a == H) 2234 return; 2235 n = f->n; 2236 if(n > f->a->len) 2237 n = f->a->len; 2238 *f->ret = putbuf(f->fd->fd, f->a->data, n); 2239 } 2240 2241 void 2242 Keyring_dessetup(void *fp) 2243 { 2244 F_Keyring_dessetup *f; 2245 Heap *h; 2246 XDESstate *ds; 2247 uchar *ivec; 2248 2249 f = fp; 2250 destroy(*f->ret); 2251 *f->ret = H; 2252 2253 if(f->key == H) 2254 return; 2255 if(f->ivec == H) 2256 ivec = 0; 2257 else 2258 ivec = f->ivec->data; 2259 2260 if(f->key->len < 8 || (ivec && f->ivec->len < 8)) 2261 return; 2262 2263 h = heap(TDESstate); 2264 ds = H2D(XDESstate*, h); 2265 setupDESstate(&ds->state, f->key->data, ivec); 2266 2267 *f->ret = (Keyring_DESstate*)ds; 2268 } 2269 2270 void 2271 Keyring_desecb(void *fp) 2272 { 2273 F_Keyring_desecb *f; 2274 XDESstate *ds; 2275 int i; 2276 uchar *p; 2277 /* uchar tmp[8]; */ 2278 2279 f = fp; 2280 2281 if(f->state == (Keyring_DESstate*)H) 2282 return; 2283 if(f->buf == H) 2284 return; 2285 if(f->buf->len < f->n) 2286 f->n = f->buf->len; 2287 if(f->n & 7) 2288 return; 2289 2290 ds = (XDESstate*)f->state; 2291 p = f->buf->data; 2292 2293 for(i = 8; i <= f->n; i += 8, p += 8) 2294 block_cipher(ds->state.expanded, p, f->direction); 2295 } 2296 2297 void 2298 Keyring_descbc(void *fp) 2299 { 2300 F_Keyring_descbc *f; 2301 XDESstate *ds; 2302 uchar *p, *ep, *ip, *p2, *eip; 2303 uchar tmp[8]; 2304 2305 f = fp; 2306 2307 if(f->state == H) 2308 return; 2309 if(f->buf == H) 2310 return; 2311 if(f->buf->len < f->n) 2312 f->n = f->buf->len; 2313 if(f->n & 7) 2314 return; 2315 2316 ds = (XDESstate*)f->state; 2317 p = f->buf->data; 2318 2319 if(f->direction == 0){ 2320 for(ep = p + f->n; p < ep; p += 8){ 2321 p2 = p; 2322 ip = ds->state.ivec; 2323 for(eip = ip+8; ip < eip; ) 2324 *p2++ ^= *ip++; 2325 block_cipher(ds->state.expanded, p, 0); 2326 memmove(ds->state.ivec, p, 8); 2327 } 2328 } else { 2329 for(ep = p + f->n; p < ep; ){ 2330 memmove(tmp, p, 8); 2331 block_cipher(ds->state.expanded, p, 1); 2332 p2 = tmp; 2333 ip = ds->state.ivec; 2334 for(eip = ip+8; ip < eip; ){ 2335 *p++ ^= *ip; 2336 *ip++ = *p2++; 2337 } 2338 } 2339 } 2340 } 2341 2342 void 2343 Keyring_ideasetup(void *fp) 2344 { 2345 F_Keyring_ideasetup *f; 2346 Heap *h; 2347 XIDEAstate *is; 2348 uchar *ivec; 2349 2350 f = fp; 2351 destroy(*f->ret); 2352 *f->ret = H; 2353 2354 if(f->key == (Array*)H) 2355 return; 2356 if(f->ivec == (Array*)H) 2357 ivec = 0; 2358 else 2359 ivec = f->ivec->data; 2360 2361 if(f->key->len < 16 || (ivec && f->ivec->len < 8)) 2362 return; 2363 2364 h = heap(TIDEAstate); 2365 is = H2D(XIDEAstate*, h); 2366 2367 setupIDEAstate(&is->state, f->key->data, ivec); 2368 2369 *f->ret = (Keyring_IDEAstate*)is; 2370 } 2371 2372 void 2373 Keyring_ideaecb(void *fp) 2374 { 2375 F_Keyring_ideaecb *f; 2376 XIDEAstate *is; 2377 int i; 2378 uchar *p; 2379 /* uchar tmp[8]; */ 2380 2381 f = fp; 2382 2383 if(f->state == (Keyring_IDEAstate*)H) 2384 return; 2385 if(f->buf == (Array*)H) 2386 return; 2387 if(f->buf->len < f->n) 2388 f->n = f->buf->len; 2389 if(f->n & 7) 2390 return; 2391 2392 is = (XIDEAstate*)f->state; 2393 p = f->buf->data; 2394 2395 for(i = 8; i <= f->n; i += 8, p += 8) 2396 idea_cipher(is->state.edkey, p, f->direction); 2397 } 2398 2399 void 2400 Keyring_ideacbc(void *fp) 2401 { 2402 F_Keyring_ideacbc *f; 2403 XIDEAstate *is; 2404 uchar *p, *ep, *ip, *p2, *eip; 2405 uchar tmp[8]; 2406 2407 f = fp; 2408 2409 if(f->state == (Keyring_IDEAstate*)H) 2410 return; 2411 if(f->buf == (Array*)H) 2412 return; 2413 if(f->buf->len < f->n) 2414 f->n = f->buf->len; 2415 if(f->n & 7) 2416 return; 2417 2418 is = (XIDEAstate*)f->state; 2419 p = f->buf->data; 2420 2421 if(f->direction == 0){ 2422 for(ep = p + f->n; p < ep; p += 8){ 2423 p2 = p; 2424 ip = is->state.ivec; 2425 for(eip = ip+8; ip < eip; ) 2426 *p2++ ^= *ip++; 2427 idea_cipher(is->state.edkey, p, 0); 2428 memmove(is->state.ivec, p, 8); 2429 } 2430 } else { 2431 for(ep = p + f->n; p < ep; ){ 2432 memmove(tmp, p, 8); 2433 idea_cipher(is->state.edkey, p, 1); 2434 p2 = tmp; 2435 ip = is->state.ivec; 2436 for(eip = ip+8; ip < eip; ){ 2437 *p++ ^= *ip; 2438 *ip++ = *p2++; 2439 } 2440 } 2441 } 2442 } 2443 2444 void 2445 Keyring_aessetup(void *fp) 2446 { 2447 F_Keyring_aessetup *f; 2448 Heap *h; 2449 XAESstate *is; 2450 uchar *ivec; 2451 2452 f = fp; 2453 destroy(*f->ret); 2454 *f->ret = H; 2455 2456 if(f->key == (Array*)H) 2457 return; 2458 if(f->ivec == (Array*)H) 2459 ivec = nil; 2460 else 2461 ivec = f->ivec->data; 2462 2463 if(f->key->len != 16 && f->key->len != 24 && f->key->len != 32) 2464 return; 2465 if(ivec && f->ivec->len < AESbsize) 2466 return; 2467 2468 h = heap(TAESstate); 2469 is = H2D(XAESstate*, h); 2470 2471 setupAESstate(&is->state, f->key->data, f->key->len, ivec); 2472 2473 *f->ret = (Keyring_AESstate*)is; 2474 } 2475 2476 void 2477 Keyring_aescbc(void *fp) 2478 { 2479 F_Keyring_aescbc *f; 2480 XAESstate *is; 2481 uchar *p; 2482 2483 f = fp; 2484 2485 if(f->state == (Keyring_AESstate*)H) 2486 return; 2487 if(f->buf == (Array*)H) 2488 return; 2489 if(f->buf->len < f->n) 2490 f->n = f->buf->len; 2491 2492 is = (XAESstate*)f->state; 2493 p = f->buf->data; 2494 2495 if(f->direction == 0) 2496 aesCBCencrypt(p, f->n, &is->state); 2497 else 2498 aesCBCdecrypt(p, f->n, &is->state); 2499 } 2500 2501 void 2502 Keyring_blowfishsetup(void *fp) 2503 { 2504 F_Keyring_blowfishsetup *f; 2505 Heap *h; 2506 XBFstate *is; 2507 uchar *ivec; 2508 2509 f = fp; 2510 destroy(*f->ret); 2511 *f->ret = H; 2512 2513 if(f->key == (Array*)H) 2514 return; 2515 if(f->ivec == (Array*)H) 2516 ivec = nil; 2517 else 2518 ivec = f->ivec->data; 2519 2520 if(f->key->len <= 0) 2521 return; 2522 if(ivec && f->ivec->len != BFbsize) 2523 return; 2524 2525 h = heap(TBFstate); 2526 is = H2D(XBFstate*, h); 2527 2528 setupBFstate(&is->state, f->key->data, f->key->len, ivec); 2529 2530 *f->ret = (Keyring_BFstate*)is; 2531 } 2532 2533 void 2534 Keyring_blowfishcbc(void *fp) 2535 { 2536 F_Keyring_blowfishcbc *f; 2537 XBFstate *is; 2538 uchar *p; 2539 2540 f = fp; 2541 2542 if(f->state == (Keyring_BFstate*)H) 2543 return; 2544 if(f->buf == (Array*)H) 2545 return; 2546 if(f->buf->len < f->n) 2547 f->n = f->buf->len; 2548 2549 is = (XBFstate*)f->state; 2550 p = f->buf->data; 2551 2552 if(f->direction == 0) 2553 bfCBCencrypt(p, f->n, &is->state); 2554 else 2555 bfCBCdecrypt(p, f->n, &is->state); 2556 } 2557 2558 void 2559 Keyring_rc4setup(void *fp) 2560 { 2561 F_Keyring_rc4setup *f; 2562 Heap *h; 2563 XRC4state *is; 2564 2565 f = fp; 2566 destroy(*f->ret); 2567 *f->ret = H; 2568 2569 if(f->seed == (Array*)H) 2570 return; 2571 2572 h = heap(TRC4state); 2573 is = H2D(XRC4state*, h); 2574 2575 setupRC4state(&is->state, f->seed->data, f->seed->len); 2576 2577 *f->ret = (Keyring_RC4state*)is; 2578 } 2579 2580 void 2581 Keyring_rc4(void *fp) 2582 { 2583 F_Keyring_rc4 *f; 2584 XRC4state *is; 2585 uchar *p; 2586 2587 f = fp; 2588 if(f->state == (Keyring_RC4state*)H) 2589 return; 2590 if(f->buf == (Array*)H) 2591 return; 2592 if(f->buf->len < f->n) 2593 f->n = f->buf->len; 2594 is = (XRC4state*)f->state; 2595 p = f->buf->data; 2596 rc4(&is->state, p, f->n); 2597 } 2598 2599 void 2600 Keyring_rc4skip(void *fp) 2601 { 2602 F_Keyring_rc4skip *f; 2603 XRC4state *is; 2604 2605 f = fp; 2606 if(f->state == (Keyring_RC4state*)H) 2607 return; 2608 is = (XRC4state*)f->state; 2609 rc4skip(&is->state, f->n); 2610 } 2611 2612 void 2613 Keyring_rc4back(void *fp) 2614 { 2615 F_Keyring_rc4back *f; 2616 XRC4state *is; 2617 2618 f = fp; 2619 if(f->state == (Keyring_RC4state*)H) 2620 return; 2621 is = (XRC4state*)f->state; 2622 rc4back(&is->state, f->n); 2623 } 2624 2625 /* 2626 * public/secret keys, signing and verifying 2627 */ 2628 2629 static void 2630 dsapk2pub(DSApub* p, Keyring_DSApk* pk) 2631 { 2632 if(pk == H) 2633 error(exNilref); 2634 p->p = checkIPint(pk->p); 2635 p->q = checkIPint(pk->q); 2636 p->alpha = checkIPint(pk->alpha); 2637 p->key = checkIPint(pk->key); 2638 } 2639 2640 static void 2641 dsask2priv(DSApriv* p, Keyring_DSAsk* sk) 2642 { 2643 if(sk == H || sk->pk == H) 2644 error(exNilref); 2645 dsapk2pub(&p->pub, sk->pk); 2646 p->secret = checkIPint(sk->secret); 2647 } 2648 2649 static void 2650 dsapriv2sk(Keyring_DSAsk* sk, DSApriv* p) 2651 { 2652 Keyring_DSApk* pk; 2653 2654 pk = sk->pk; 2655 pk->p = ipcopymp(p->pub.p); 2656 pk->q = ipcopymp(p->pub.q); 2657 pk->alpha = ipcopymp(p->pub.alpha); 2658 pk->key = ipcopymp(p->pub.key); 2659 sk->secret = ipcopymp(p->secret); 2660 } 2661 2662 void 2663 DSAsk_gen(void *fp) 2664 { 2665 F_DSAsk_gen *f; 2666 Keyring_DSAsk *sk; 2667 DSApriv *p; 2668 DSApub pub, *oldpk; 2669 void *v; 2670 2671 f = fp; 2672 v = *f->ret; 2673 sk = newthing(TDSAsk, 0); 2674 sk->pk = newthing(TDSApk, 0); 2675 *f->ret = sk; 2676 destroy(v); 2677 oldpk = nil; 2678 if(f->oldpk != H){ 2679 dsapk2pub(&pub, f->oldpk); 2680 oldpk = &pub; 2681 } 2682 release(); 2683 p = dsagen(oldpk); 2684 acquire(); 2685 dsapriv2sk(sk, p); 2686 dsaprivfree(p); 2687 } 2688 2689 void 2690 DSAsk_sign(void *fp) 2691 { 2692 F_DSAsk_sign *f; 2693 Keyring_DSAsig *sig; 2694 DSApriv p; 2695 mpint *m; 2696 DSAsig *s; 2697 void *v; 2698 2699 f = fp; 2700 v = *f->ret; 2701 sig = newthing(TDSAsig, 0); 2702 *f->ret = sig; 2703 destroy(v); 2704 2705 dsask2priv(&p, f->k); 2706 m = checkIPint(f->m); 2707 release(); 2708 s = dsasign(&p, m); 2709 acquire(); 2710 sig->r = ipcopymp(s->r); 2711 sig->s = ipcopymp(s->s); 2712 dsasigfree(s); 2713 } 2714 2715 void 2716 DSApk_verify(void *fp) 2717 { 2718 F_DSApk_verify *f; 2719 DSApub p; 2720 DSAsig sig; 2721 mpint *m; 2722 2723 f = fp; 2724 *f->ret = 0; 2725 if(f->m == H || f->sig == H) 2726 return; 2727 dsapk2pub(&p, f->k); 2728 sig.r = checkIPint(f->sig->r); 2729 sig.s = checkIPint(f->sig->s); 2730 m = checkIPint(f->m); 2731 release(); 2732 *f->ret = dsaverify(&p, &sig, m) == 0; 2733 acquire(); 2734 } 2735 2736 static void 2737 egpk2pub(EGpub* p, Keyring_EGpk* pk) 2738 { 2739 if(pk == H) 2740 error(exNilref); 2741 p->p = checkIPint(pk->p); 2742 p->alpha = checkIPint(pk->alpha); 2743 p->key = checkIPint(pk->key); 2744 } 2745 2746 static void 2747 egsk2priv(EGpriv* p, Keyring_EGsk* sk) 2748 { 2749 if(sk == H || sk->pk == H) 2750 error(exNilref); 2751 egpk2pub(&p->pub, sk->pk); 2752 p->secret = checkIPint(sk->secret); 2753 } 2754 2755 static void 2756 egpriv2sk(Keyring_EGsk* sk, EGpriv* p) 2757 { 2758 Keyring_EGpk* pk; 2759 2760 pk = sk->pk; 2761 pk->p = ipcopymp(p->pub.p); 2762 pk->alpha = ipcopymp(p->pub.alpha); 2763 pk->key = ipcopymp(p->pub.key); 2764 sk->secret = ipcopymp(p->secret); 2765 } 2766 2767 void 2768 EGsk_gen(void *fp) 2769 { 2770 F_EGsk_gen *f; 2771 Keyring_EGsk *sk; 2772 EGpriv *p; 2773 void *v; 2774 2775 f = fp; 2776 v = *f->ret; 2777 sk = newthing(TEGsk, 0); 2778 sk->pk = newthing(TEGpk, 0); 2779 *f->ret = sk; 2780 destroy(v); 2781 release(); 2782 for(;;){ 2783 p = eggen(f->nlen, f->nrep); 2784 if(mpsignif(p->pub.p) == f->nlen) 2785 break; 2786 egprivfree(p); 2787 } 2788 acquire(); 2789 egpriv2sk(sk, p); 2790 egprivfree(p); 2791 } 2792 2793 void 2794 EGsk_sign(void *fp) 2795 { 2796 F_EGsk_sign *f; 2797 Keyring_EGsig *sig; 2798 EGpriv p; 2799 mpint *m; 2800 EGsig *s; 2801 void *v; 2802 2803 f = fp; 2804 v = *f->ret; 2805 sig = newthing(TEGsig, 0); 2806 *f->ret = sig; 2807 destroy(v); 2808 2809 egsk2priv(&p, f->k); 2810 m = checkIPint(f->m); 2811 release(); 2812 s = egsign(&p, m); 2813 acquire(); 2814 sig->r = ipcopymp(s->r); 2815 sig->s = ipcopymp(s->s); 2816 egsigfree(s); 2817 } 2818 2819 void 2820 EGpk_verify(void *fp) 2821 { 2822 F_EGpk_verify *f; 2823 EGpub p; 2824 EGsig sig; 2825 mpint *m; 2826 2827 f = fp; 2828 *f->ret = 0; 2829 if(f->m == H || f->sig == H) 2830 return; 2831 egpk2pub(&p, f->k); 2832 sig.r = checkIPint(f->sig->r); 2833 sig.s = checkIPint(f->sig->s); 2834 m = checkIPint(f->m); 2835 release(); 2836 *f->ret = egverify(&p, &sig, m) == 0; 2837 acquire(); 2838 } 2839 2840 static void 2841 rsapk2pub(RSApub* p, Keyring_RSApk* pk) 2842 { 2843 if(pk == H) 2844 error(exNilref); 2845 memset(p, 0, sizeof(*p)); 2846 p->n = checkIPint(pk->n); 2847 p->ek = checkIPint(pk->ek); 2848 } 2849 2850 static void 2851 rsask2priv(RSApriv* p, Keyring_RSAsk* sk) 2852 { 2853 if(sk == H || sk->pk == H) 2854 error(exNilref); 2855 rsapk2pub(&p->pub, sk->pk); 2856 p->dk = checkIPint(sk->dk); 2857 p->p = checkIPint(sk->p); 2858 p->q = checkIPint(sk->q); 2859 p->kp = checkIPint(sk->kp); 2860 p->kq = checkIPint(sk->kq); 2861 p->c2 = checkIPint(sk->c2); 2862 } 2863 2864 static void 2865 rsapriv2sk(Keyring_RSAsk* sk, RSApriv* p) 2866 { 2867 Keyring_RSApk* pk; 2868 2869 pk = sk->pk; 2870 pk->n = ipcopymp(p->pub.n); 2871 pk->ek = ipcopymp(p->pub.ek); 2872 sk->dk = ipcopymp(p->dk); 2873 sk->p = ipcopymp(p->p); 2874 sk->q = ipcopymp(p->q); 2875 sk->kp = ipcopymp(p->kp); 2876 sk->kq = ipcopymp(p->kq); 2877 sk->c2 = ipcopymp(p->c2); 2878 } 2879 2880 void 2881 RSApk_encrypt(void *fp) 2882 { 2883 F_RSApk_encrypt *f; 2884 RSApub p; 2885 mpint *m, *o; 2886 void *v; 2887 2888 f = fp; 2889 v = *f->ret; 2890 *f->ret = H; 2891 destroy(v); 2892 2893 rsapk2pub(&p, f->k); 2894 m = checkIPint(f->m); 2895 release(); 2896 o = rsaencrypt(&p, m, nil); 2897 acquire(); 2898 *f->ret = newIPint(o); 2899 } 2900 2901 void 2902 RSAsk_gen(void *fp) 2903 { 2904 F_RSAsk_gen *f; 2905 Keyring_RSAsk *sk; 2906 RSApriv *p; 2907 void *v; 2908 2909 f = fp; 2910 v = *f->ret; 2911 sk = newthing(TRSAsk, 0); 2912 sk->pk = newthing(TRSApk, 0); 2913 *f->ret = sk; 2914 destroy(v); 2915 release(); 2916 for(;;){ 2917 p = rsagen(f->nlen, f->elen, f->nrep); 2918 if(mpsignif(p->pub.n) == f->nlen) 2919 break; 2920 rsaprivfree(p); 2921 } 2922 acquire(); 2923 rsapriv2sk(sk, p); 2924 rsaprivfree(p); 2925 } 2926 2927 void 2928 RSAsk_fill(void *fp) 2929 { 2930 F_RSAsk_fill *f; 2931 Keyring_RSAsk *sk; 2932 RSApriv *p; 2933 void *v; 2934 2935 f = fp; 2936 v = *f->ret; 2937 sk = newthing(TRSAsk, 0); 2938 sk->pk = newthing(TRSApk, 0); 2939 *f->ret = sk; 2940 destroy(v); 2941 release(); 2942 p = rsafill(checkIPint(f->n), checkIPint(f->e), checkIPint(f->d), 2943 checkIPint(f->p), checkIPint(f->q)); 2944 acquire(); 2945 if(p == nil) { 2946 *f->ret = H; 2947 destroy(sk); 2948 }else{ 2949 rsapriv2sk(sk, p); 2950 rsaprivfree(p); 2951 } 2952 } 2953 2954 void 2955 RSAsk_decrypt(void *fp) 2956 { 2957 F_RSAsk_decrypt *f; 2958 RSApriv p; 2959 mpint *m, *o; 2960 void *v; 2961 2962 f = fp; 2963 v = *f->ret; 2964 *f->ret = H; 2965 destroy(v); 2966 2967 rsask2priv(&p, f->k); 2968 m = checkIPint(f->m); 2969 release(); 2970 o = rsadecrypt(&p, m, nil); 2971 acquire(); 2972 *f->ret = newIPint(o); 2973 } 2974 2975 void 2976 RSAsk_sign(void *fp) 2977 { 2978 F_RSAsk_sign *f; 2979 Keyring_RSAsig *sig; 2980 RSApriv p; 2981 mpint *m, *s; 2982 void *v; 2983 2984 f = fp; 2985 v = *f->ret; 2986 sig = newthing(TRSAsig, 0); 2987 *f->ret = sig; 2988 destroy(v); 2989 2990 rsask2priv(&p, f->k); 2991 m = checkIPint(f->m); 2992 release(); 2993 s = rsadecrypt(&p, m, nil); 2994 acquire(); 2995 sig->n = newIPint(s); 2996 } 2997 2998 void 2999 RSApk_verify(void *fp) 3000 { 3001 F_RSApk_verify *f; 3002 RSApub p; 3003 mpint *sig, *m, *t; 3004 3005 f = fp; 3006 *f->ret = 0; 3007 if(f->m == H || f->sig == H) 3008 return; 3009 rsapk2pub(&p, f->k); 3010 sig = checkIPint(f->sig->n); 3011 m = checkIPint(f->m); 3012 release(); 3013 t = rsaencrypt(&p, sig, nil); 3014 *f->ret = mpcmp(t, m) == 0; 3015 mpfree(t); 3016 acquire(); 3017 } 3018