1 /* 2 * Common Public License Version 0.5 3 * 4 * THE ACCOMPANYING PROGRAM IS PROVIDED UNDER THE TERMS OF 5 * THIS COMMON PUBLIC LICENSE ("AGREEMENT"). ANY USE, 6 * REPRODUCTION OR DISTRIBUTION OF THE PROGRAM CONSTITUTES 7 * RECIPIENT'S ACCEPTANCE OF THIS AGREEMENT. 8 * 9 * 1. DEFINITIONS 10 * 11 * "Contribution" means: 12 * a) in the case of the initial Contributor, the 13 * initial code and documentation distributed under 14 * this Agreement, and 15 * 16 * b) in the case of each subsequent Contributor: 17 * i) changes to the Program, and 18 * ii) additions to the Program; 19 * 20 * where such changes and/or additions to the Program 21 * originate from and are distributed by that 22 * particular Contributor. A Contribution 'originates' 23 * from a Contributor if it was added to the Program 24 * by such Contributor itself or anyone acting on such 25 * Contributor's behalf. Contributions do not include 26 * additions to the Program which: (i) are separate 27 * modules of software distributed in conjunction with 28 * the Program under their own license agreement, and 29 * (ii) are not derivative works of the Program. 30 * 31 * 32 * "Contributor" means any person or entity that distributes 33 * the Program. 34 * 35 * "Licensed Patents " mean patent claims licensable by a 36 * Contributor which are necessarily infringed by the use or 37 * sale of its Contribution alone or when combined with the 38 * Program. 39 * 40 * "Program" means the Contributions distributed in 41 * accordance with this Agreement. 42 * 43 * "Recipient" means anyone who receives the Program under 44 * this Agreement, including all Contributors. 45 * 46 * 2. GRANT OF RIGHTS 47 * 48 * a) Subject to the terms of this Agreement, each 49 * Contributor hereby grants Recipient a 50 * no - exclusive, worldwide, royalt - free copyright 51 * license to reproduce, prepare derivative works of, 52 * publicly display, publicly perform, distribute and 53 * sublicense the Contribution of such Contributor, if 54 * any, and such derivative works, in source code and 55 * object code form. 56 * 57 * b) Subject to the terms of this Agreement, each 58 * Contributor hereby grants Recipient a 59 * no - exclusive, worldwide, royalt - free patent 60 * license under Licensed Patents to make, use, sell, 61 * offer to sell, import and otherwise transfer the 62 * Contribution of such Contributor, if any, in source 63 * code and object code form. This patent license 64 * shall apply to the combination of the Contribution 65 * and the Program if, at the time the Contribution is 66 * added by the Contributor, such addition of the 67 * Contribution causes such combination to be covered 68 * by the Licensed Patents. The patent license shall 69 * not apply to any other combinations which include 70 * the Contribution. No hardware per se is licensed 71 * hereunder. 72 * 73 * c) Recipient understands that although each 74 * Contributor grants the licenses to its 75 * Contributions set forth herein, no assurances are 76 * provided by any Contributor that the Program does 77 * not infringe the patent or other intellectual 78 * property rights of any other entity. Each 79 * Contributor disclaims any liability to Recipient 80 * for claims brought by any other entity based on 81 * infringement of intellectual property rights or 82 * otherwise. As a condition to exercising the rights 83 * and licenses granted hereunder, each Recipient 84 * hereby assumes sole responsibility to secure any 85 * other intellectual property rights needed, if any. 86 * 87 * For example, if a third party patent license is 88 * required to allow Recipient to distribute the 89 * Program, it is Recipient's responsibility to 90 * acquire that license before distributing the 91 * Program. 92 * 93 * d) Each Contributor represents that to its 94 * knowledge it has sufficient copyright rights in its 95 * Contribution, if any, to grant the copyright 96 * license set forth in this Agreement. 97 * 98 * 3. REQUIREMENTS 99 * 100 * A Contributor may choose to distribute the Program in 101 * object code form under its own license agreement, provided 102 * that: 103 * a) it complies with the terms and conditions of 104 * this Agreement; and 105 * 106 * b) its license agreement: 107 * i) effectively disclaims on behalf of all 108 * Contributors all warranties and conditions, express 109 * and implied, including warranties or conditions of 110 * title and no - infringement, and implied warranties 111 * or conditions of merchantability and fitness for a 112 * particular purpose; 113 * 114 * ii) effectively excludes on behalf of all 115 * Contributors all liability for damages, including 116 * direct, indirect, special, incidental and 117 * consequential damages, such as lost profits; 118 * 119 * iii) states that any provisions which differ from 120 * this Agreement are offered by that Contributor 121 * alone and not by any other party; and 122 * 123 * iv) states that source code for the Program is 124 * available from such Contributor, and informs 125 * licensees how to obtain it in a reasonable manner 126 * on or through a medium customarily used for 127 * software exchange. 128 * 129 * When the Program is made available in source code form: 130 * a) it must be made available under this Agreement; 131 * and 132 * b) a copy of this Agreement must be included with 133 * each copy of the Program. 134 * 135 * Contributors may not remove or alter any copyright notices 136 * contained within the Program. 137 * 138 * Each Contributor must identify itself as the originator of 139 * its Contribution, if any, in a manner that reasonably 140 * allows subsequent Recipients to identify the originator of 141 * the Contribution. 142 * 143 * 144 * 4. COMMERCIAL DISTRIBUTION 145 * 146 * Commercial distributors of software may accept certain 147 * responsibilities with respect to end users, business 148 * partners and the like. While this license is intended to 149 * facilitate the commercial use of the Program, the 150 * Contributor who includes the Program in a commercial 151 * product offering should do so in a manner which does not 152 * create potential liability for other Contributors. 153 * Therefore, if a Contributor includes the Program in a 154 * commercial product offering, such Contributor ("Commercial 155 * Contributor") hereby agrees to defend and indemnify every 156 * other Contributor ("Indemnified Contributor") against any 157 * losses, damages and costs (collectively "Losses") arising 158 * from claims, lawsuits and other legal actions brought by a 159 * third party against the Indemnified Contributor to the 160 * extent caused by the acts or omissions of such Commercial 161 * Contributor in connection with its distribution of the 162 * Program in a commercial product offering. The obligations 163 * in this section do not apply to any claims or Losses 164 * relating to any actual or alleged intellectual property 165 * infringement. In order to qualify, an Indemnified 166 * Contributor must: a) promptly notify the Commercial 167 * Contributor in writing of such claim, and b) allow the 168 * Commercial Contributor to control, and cooperate with the 169 * Commercial Contributor in, the defense and any related 170 * settlement negotiations. The Indemnified Contributor may 171 * participate in any such claim at its own expense. 172 * 173 * 174 * For example, a Contributor might include the Program in a 175 * commercial product offering, Product X. That Contributor 176 * is then a Commercial Contributor. If that Commercial 177 * Contributor then makes performance claims, or offers 178 * warranties related to Product X, those performance claims 179 * and warranties are such Commercial Contributor's 180 * responsibility alone. Under this section, the Commercial 181 * Contributor would have to defend claims against the other 182 * Contributors related to those performance claims and 183 * warranties, and if a court requires any other Contributor 184 * to pay any damages as a result, the Commercial Contributor 185 * must pay those damages. 186 * 187 * 188 * 5. NO WARRANTY 189 * 190 * EXCEPT AS EXPRESSLY SET FORTH IN THIS AGREEMENT, THE 191 * PROGRAM IS PROVIDED ON AN "AS IS" BASIS, WITHOUT 192 * WARRANTIES OR CONDITIONS OF ANY KIND, EITHER EXPRESS OR 193 * IMPLIED INCLUDING, WITHOUT LIMITATION, ANY WARRANTIES OR 194 * CONDITIONS OF TITLE, NO - INFRINGEMENT, MERCHANTABILITY OR 195 * FITNESS FOR A PARTICULAR PURPOSE. Each Recipient is solely 196 * responsible for determining the appropriateness of using 197 * and distributing the Program and assumes all risks 198 * associated with its exercise of rights under this 199 * Agreement, including but not limited to the risks and 200 * costs of program errors, compliance with applicable laws, 201 * damage to or loss of data, programs or equipment, and 202 * unavailability or interruption of operations. 203 * 204 * 6. DISCLAIMER OF LIABILITY 205 * EXCEPT AS EXPRESSLY SET FORTH IN THIS AGREEMENT, NEITHER 206 * RECIPIENT NOR ANY CONTRIBUTORS SHALL HAVE ANY LIABILITY 207 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, 208 * OR CONSEQUENTIAL DAMAGES (INCLUDING WITHOUT LIMITATION 209 * LOST PROFITS), HOWEVER CAUSED AND ON ANY THEORY OF 210 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 211 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT 212 * OF THE USE OR DISTRIBUTION OF THE PROGRAM OR THE EXERCISE 213 * OF ANY RIGHTS GRANTED HEREUNDER, EVEN IF ADVISED OF THE 214 * POSSIBILITY OF SUCH DAMAGES. 215 * 216 * 7. GENERAL 217 * 218 * If any provision of this Agreement is invalid or 219 * unenforceable under applicable law, it shall not affect 220 * the validity or enforceability of the remainder of the 221 * terms of this Agreement, and without further action by the 222 * parties hereto, such provision shall be reformed to the 223 * minimum extent necessary to make such provision valid and 224 * enforceable. 225 * 226 * 227 * If Recipient institutes patent litigation against a 228 * Contributor with respect to a patent applicable to 229 * software (including a cros - claim or counterclaim in a 230 * lawsuit), then any patent licenses granted by that 231 * Contributor to such Recipient under this Agreement shall 232 * terminate as of the date such litigation is filed. In 233 * addition, If Recipient institutes patent litigation 234 * against any entity (including a cros - claim or 235 * counterclaim in a lawsuit) alleging that the Program 236 * itself (excluding combinations of the Program with other 237 * software or hardware) infringes such Recipient's 238 * patent(s), then such Recipient's rights granted under 239 * Section 2(b) shall terminate as of the date such 240 * litigation is filed. 241 * 242 * All Recipient's rights under this Agreement shall 243 * terminate if it fails to comply with any of the material 244 * terms or conditions of this Agreement and does not cure 245 * such failure in a reasonable period of time after becoming 246 * aware of such noncompliance. If all Recipient's rights 247 * under this Agreement terminate, Recipient agrees to cease 248 * use and distribution of the Program as soon as reasonably 249 * practicable. However, Recipient's obligations under this 250 * Agreement and any licenses granted by Recipient relating 251 * to the Program shall continue and survive. 252 * 253 * Everyone is permitted to copy and distribute copies of 254 * this Agreement, but in order to avoid inconsistency the 255 * Agreement is copyrighted and may only be modified in the 256 * following manner. The Agreement Steward reserves the right 257 * to publish new versions (including revisions) of this 258 * Agreement from time to time. No one other than the 259 * Agreement Steward has the right to modify this Agreement. 260 * 261 * IBM is the initial Agreement Steward. IBM may assign the 262 * responsibility to serve as the Agreement Steward to a 263 * suitable separate entity. Each new version of the 264 * Agreement will be given a distinguishing version number. 265 * The Program (including Contributions) may always be 266 * distributed subject to the version of the Agreement under 267 * which it was received. In addition, after a new version of 268 * the Agreement is published, Contributor may elect to 269 * distribute the Program (including its Contributions) under 270 * the new version. Except as expressly stated in Sections 271 * 2(a) and 2(b) above, Recipient receives no rights or 272 * licenses to the intellectual property of any Contributor 273 * under this Agreement, whether expressly, by implication, 274 * estoppel or otherwise. All rights in the Program not 275 * expressly granted under this Agreement are reserved. 276 * 277 * 278 * This Agreement is governed by the laws of the State of New 279 * York and the intellectual property laws of the United 280 * States of America. No party to this Agreement will bring a 281 * legal action under this Agreement more than one year after 282 * the cause of action arose. Each party waives its rights to 283 * a jury trial in any resulting litigation. 284 * 285 * 286 * 287 * (C) COPYRIGHT International Business Machines Corp. 2001, 2002 288 */ 289 /* 290 * Copyright 2009 Sun Microsystems, Inc. All rights reserved. 291 * Use is subject to license terms. 292 */ 293 294 #include "tpmtok_int.h" 295 296 // template_add_attributes() 297 // 298 // blindly add the given attributes to the template. do no sanity checking 299 // at this point. sanity checking will occur later. 300 // 301 CK_RV 302 template_add_attributes(TEMPLATE * tmpl, 303 CK_ATTRIBUTE * pTemplate, 304 CK_ULONG ulCount) 305 { 306 CK_ATTRIBUTE * attr = NULL; 307 CK_RV rc; 308 unsigned int i; 309 310 for (i = 0; i < ulCount; i++) { 311 if (! is_attribute_defined(pTemplate[i].type)) { 312 return (CKR_ATTRIBUTE_TYPE_INVALID); 313 } 314 attr = (CK_ATTRIBUTE *)malloc(sizeof (CK_ATTRIBUTE) + 315 pTemplate[i].ulValueLen); 316 if (! attr) { 317 return (CKR_HOST_MEMORY); 318 } 319 attr->type = pTemplate[i].type; 320 attr->ulValueLen = pTemplate[i].ulValueLen; 321 322 if (attr->ulValueLen != 0) { 323 attr->pValue = (CK_BYTE *)attr + sizeof (CK_ATTRIBUTE); 324 (void) memcpy(attr->pValue, pTemplate[i].pValue, 325 attr->ulValueLen); 326 } else 327 attr->pValue = NULL; 328 329 rc = template_update_attribute(tmpl, attr); 330 if (rc != CKR_OK) { 331 free(attr); 332 return (rc); 333 } 334 } 335 336 return (CKR_OK); 337 } 338 339 340 // template_add_default_attributes() 341 // 342 CK_RV 343 template_add_default_attributes(TEMPLATE * tmpl, 344 CK_ULONG class, 345 CK_ULONG subclass, 346 CK_ULONG mode) 347 { 348 CK_RV rc; 349 350 // first add the default common attributes 351 // 352 rc = template_set_default_common_attributes(tmpl); 353 if (rc != CKR_OK) { 354 return (rc); 355 } 356 // set the template class - specific default attributes 357 // 358 switch (class) { 359 case CKO_DATA: 360 return (data_object_set_default_attributes(tmpl, mode)); 361 case CKO_CERTIFICATE: 362 if (subclass == CKC_X_509) 363 return (cert_x509_set_default_attributes(tmpl, mode)); 364 else 365 return (CKR_OK); 366 case CKO_PUBLIC_KEY: 367 switch (subclass) { 368 case CKK_RSA: 369 return (rsa_publ_set_default_attributes( 370 tmpl, mode)); 371 default: 372 return (CKR_ATTRIBUTE_VALUE_INVALID); 373 } 374 375 case CKO_PRIVATE_KEY: 376 switch (subclass) { 377 case CKK_RSA: 378 return (rsa_priv_set_default_attributes( 379 tmpl, mode)); 380 default: 381 return (CKR_ATTRIBUTE_VALUE_INVALID); 382 } 383 384 case CKO_SECRET_KEY: 385 switch (subclass) { 386 case CKK_GENERIC_SECRET: 387 return (generic_secret_set_default_attributes( 388 tmpl, mode)); 389 default: 390 return (CKR_ATTRIBUTE_VALUE_INVALID); 391 } 392 393 case CKO_HW_FEATURE: 394 switch (subclass) { 395 case CKH_CLOCK: 396 return (clock_set_default_attributes( 397 tmpl)); 398 case CKH_MONOTONIC_COUNTER: 399 return (counter_set_default_attributes( 400 tmpl)); 401 default: 402 return (CKR_ATTRIBUTE_VALUE_INVALID); 403 } 404 405 case CKO_DOMAIN_PARAMETERS: 406 switch (subclass) { 407 default: 408 return (CKR_ATTRIBUTE_VALUE_INVALID); 409 } 410 411 default: 412 return (CKR_ATTRIBUTE_VALUE_INVALID); 413 } 414 } 415 416 // template_attribute_find() 417 // 418 // find the attribute in the list and return (its value 419 // 420 CK_BBOOL 421 template_attribute_find(TEMPLATE * tmpl, 422 CK_ATTRIBUTE_TYPE type, 423 CK_ATTRIBUTE ** attr) 424 { 425 DL_NODE * node = NULL; 426 CK_ATTRIBUTE * a = NULL; 427 428 if (! tmpl || ! attr) 429 return (FALSE); 430 node = tmpl->attribute_list; 431 432 while (node != NULL) { 433 a = (CK_ATTRIBUTE *)node->data; 434 435 if (type == a->type) { 436 *attr = a; 437 return (TRUE); 438 } 439 440 node = node->next; 441 } 442 443 *attr = NULL; 444 return (FALSE); 445 } 446 447 // template_attribute_find_multiple() 448 // 449 // find the attributes in the list and return (their values 450 // 451 void 452 template_attribute_find_multiple(TEMPLATE * tmpl, 453 ATTRIBUTE_PARSE_LIST * parselist, 454 CK_ULONG plcount) 455 { 456 CK_ATTRIBUTE * attr = NULL; 457 CK_ULONG i; 458 459 for (i = 0; i < plcount; i++) { 460 parselist[i].found = template_attribute_find( 461 tmpl, parselist[i].type, &attr); 462 463 if (parselist[i].found && parselist[i].ptr != NULL) 464 (void) memcpy(parselist[i].ptr, attr->pValue, 465 parselist[i].len); 466 } 467 } 468 469 CK_RV 470 template_check_required_attributes(TEMPLATE * tmpl, 471 CK_ULONG class, 472 CK_ULONG subclass, 473 CK_ULONG mode) 474 { 475 if (class == CKO_DATA) 476 return (data_object_check_required_attributes( 477 tmpl, mode)); 478 else if (class == CKO_CERTIFICATE) { 479 if (subclass == CKC_X_509) 480 return (cert_x509_check_required_attributes( 481 tmpl, mode)); 482 else 483 return (cert_vendor_check_required_attributes( 484 tmpl, mode)); 485 } else if (class == CKO_PUBLIC_KEY) { 486 switch (subclass) { 487 case CKK_RSA: 488 return (rsa_publ_check_required_attributes( 489 tmpl, mode)); 490 default: 491 return (CKR_ATTRIBUTE_VALUE_INVALID); 492 } 493 } else if (class == CKO_PRIVATE_KEY) { 494 switch (subclass) { 495 case CKK_RSA: 496 return (rsa_priv_check_required_attributes( 497 tmpl, mode)); 498 default: 499 return (CKR_ATTRIBUTE_VALUE_INVALID); 500 } 501 } else if (class == CKO_SECRET_KEY) { 502 switch (subclass) { 503 case CKK_GENERIC_SECRET: 504 return ( 505 generic_secret_check_required_attributes( 506 tmpl, mode)); 507 default: 508 return (CKR_ATTRIBUTE_VALUE_INVALID); 509 } 510 } else if (class == CKO_HW_FEATURE) { 511 512 switch (subclass) { 513 case CKH_CLOCK: 514 return ( 515 clock_check_required_attributes( 516 tmpl, mode)); 517 case CKH_MONOTONIC_COUNTER: 518 return ( 519 counter_check_required_attributes( 520 tmpl, mode)); 521 default: 522 return (CKR_ATTRIBUTE_VALUE_INVALID); 523 } 524 } else if (class == CKO_DOMAIN_PARAMETERS) { 525 switch (subclass) { 526 default: 527 return (CKR_ATTRIBUTE_VALUE_INVALID); 528 } 529 } 530 return (CKR_ATTRIBUTE_VALUE_INVALID); 531 } 532 533 534 // template_check_required_base_attributes() 535 // 536 // check to make sure that attributes required by Cryptoki are 537 // present. does not check to see if the attribute makes sense 538 // for the particular object (that is done in the 'validate' routines) 539 // 540 CK_RV 541 template_check_required_base_attributes(TEMPLATE * tmpl, 542 CK_ULONG mode) 543 { 544 CK_ATTRIBUTE * attr; 545 CK_BBOOL found; 546 547 found = template_attribute_find(tmpl, CKA_CLASS, &attr); 548 if (mode == MODE_CREATE && found == FALSE) 549 return (CKR_TEMPLATE_INCOMPLETE); 550 return (CKR_OK); 551 } 552 553 554 // template_compare() 555 // 556 CK_BBOOL 557 template_compare(CK_ATTRIBUTE * t1, 558 CK_ULONG ulCount, 559 TEMPLATE * t2) { 560 CK_ATTRIBUTE * attr1 = NULL; 561 CK_ATTRIBUTE * attr2 = NULL; 562 CK_ULONG i; 563 CK_RV rc; 564 565 if (! t1 || ! t2) 566 return (FALSE); 567 attr1 = t1; 568 569 for (i = 0; i < ulCount; i++) { 570 rc = template_attribute_find(t2, attr1->type, &attr2); 571 if (rc == FALSE) 572 return (FALSE); 573 if (attr1->ulValueLen != attr2->ulValueLen) 574 return (FALSE); 575 if (memcmp(attr1->pValue, attr2->pValue, attr1->ulValueLen) 576 != 0) 577 return (FALSE); 578 attr1++; 579 } 580 581 return (TRUE); 582 } 583 584 // template_copy() 585 // 586 // This doesn't copy the template items verbatim. The new template is in 587 // the reverse order of the old one. This should not have any effect. 588 // 589 // This is very similar to template_merge(). template_merge() can also 590 // be used to copy a list (of unique attributes) but is slower because for 591 // each attribute, it must search through the list. 592 // 593 CK_RV 594 template_copy(TEMPLATE *dest, TEMPLATE *src) { 595 DL_NODE *node; 596 597 if (! dest || ! src) { 598 return (CKR_FUNCTION_FAILED); 599 } 600 node = src->attribute_list; 601 602 while (node) { 603 CK_ATTRIBUTE *attr = (CK_ATTRIBUTE *)node->data; 604 CK_ATTRIBUTE *new_attr = NULL; 605 CK_ULONG len; 606 607 len = sizeof (CK_ATTRIBUTE) + attr->ulValueLen; 608 609 new_attr = (CK_ATTRIBUTE *)malloc(len); 610 if (! new_attr) { 611 return (CKR_HOST_MEMORY); 612 } 613 (void) memcpy(new_attr, attr, len); 614 615 new_attr->pValue = (CK_BYTE *)new_attr + sizeof (CK_ATTRIBUTE); 616 617 dest->attribute_list = dlist_add_as_first(dest->attribute_list, 618 new_attr); 619 620 node = node->next; 621 } 622 623 return (CKR_OK); 624 } 625 626 627 // template_flatten() - this still gets used when saving token objects to disk 628 // 629 CK_RV 630 template_flatten(TEMPLATE * tmpl, 631 CK_BYTE * dest) 632 { 633 DL_NODE * node = NULL; 634 CK_BYTE * ptr = NULL; 635 CK_ULONG_32 long_len; 636 CK_ATTRIBUTE_32 *attr_32; 637 CK_ULONG Val; 638 CK_ULONG_32 Val_32; 639 CK_ULONG * pVal; 640 long_len = sizeof (CK_ULONG); 641 642 if (! tmpl || ! dest) { 643 return (CKR_FUNCTION_FAILED); 644 } 645 ptr = dest; 646 node = tmpl->attribute_list; 647 while (node) { 648 CK_ATTRIBUTE *attr = (CK_ATTRIBUTE *)node->data; 649 650 if (long_len == 4) { 651 (void) memcpy(ptr, attr, sizeof (CK_ATTRIBUTE) + 652 attr->ulValueLen); 653 ptr += sizeof (CK_ATTRIBUTE) + attr->ulValueLen; 654 } else { 655 attr_32 = malloc(sizeof (CK_ATTRIBUTE_32)); 656 if (! attr_32) { 657 return (CKR_HOST_MEMORY); 658 } 659 attr_32->type = attr->type; 660 attr_32->pValue = 0x00; 661 if ((attr->type == CKA_CLASS || 662 attr->type == CKA_KEY_TYPE || 663 attr->type == CKA_MODULUS_BITS || 664 attr->type == CKA_VALUE_BITS || 665 attr->type == CKA_CERTIFICATE_TYPE || 666 attr->type == CKA_VALUE_LEN) && 667 attr->ulValueLen != 0) { 668 669 attr_32->ulValueLen = sizeof (CK_ULONG_32); 670 671 (void) memcpy(ptr, attr_32, 672 sizeof (CK_ATTRIBUTE_32)); 673 ptr += sizeof (CK_ATTRIBUTE_32); 674 675 pVal = (CK_ULONG *)attr->pValue; 676 Val = *pVal; 677 Val_32 = (CK_ULONG_32)Val; 678 (void) memcpy(ptr, &Val_32, 679 sizeof (CK_ULONG_32)); 680 ptr += sizeof (CK_ULONG_32); 681 } else { 682 attr_32->ulValueLen = attr->ulValueLen; 683 (void) memcpy(ptr, attr_32, 684 sizeof (CK_ATTRIBUTE_32)); 685 ptr += sizeof (CK_ATTRIBUTE_32); 686 if (attr->ulValueLen != 0) { 687 (void) memcpy(ptr, attr->pValue, 688 attr->ulValueLen); 689 ptr += attr->ulValueLen; 690 } 691 } 692 free(attr_32); 693 } 694 node = node->next; 695 } 696 697 return (CKR_OK); 698 } 699 700 CK_RV 701 template_unflatten(TEMPLATE ** new_tmpl, 702 CK_BYTE * buf, 703 CK_ULONG count) 704 { 705 TEMPLATE * tmpl = NULL; 706 CK_ATTRIBUTE * a2 = NULL; 707 CK_BYTE *ptr = NULL; 708 CK_ULONG i, len; 709 CK_RV rc; 710 CK_ULONG_32 long_len = sizeof (CK_ULONG); 711 CK_ULONG_32 attr_ulong_32; 712 CK_ULONG attr_ulong; 713 CK_ATTRIBUTE * a1_64 = NULL; 714 CK_ATTRIBUTE_32 * a1 = NULL; 715 716 if (! new_tmpl || ! buf) { 717 return (CKR_FUNCTION_FAILED); 718 } 719 tmpl = (TEMPLATE *)malloc(sizeof (TEMPLATE)); 720 if (! tmpl) { 721 return (CKR_HOST_MEMORY); 722 } 723 (void) memset(tmpl, 0x0, sizeof (TEMPLATE)); 724 725 ptr = buf; 726 for (i = 0; i < count; i++) { 727 if (long_len == 4) { 728 void *aptr = ptr; 729 a1_64 = (CK_ATTRIBUTE *)aptr; 730 731 len = sizeof (CK_ATTRIBUTE) + a1_64->ulValueLen; 732 a2 = (CK_ATTRIBUTE *)malloc(len); 733 if (! a2) { 734 (void) template_free(tmpl); 735 return (CKR_HOST_MEMORY); 736 } 737 738 (void) memcpy(a2, a1_64, len); 739 } else { 740 void *aptr = ptr; 741 a1 = (CK_ATTRIBUTE_32 *)aptr; 742 743 if ((a1->type == CKA_CLASS || 744 a1->type == CKA_KEY_TYPE || 745 a1->type == CKA_MODULUS_BITS || 746 a1->type == CKA_VALUE_BITS || 747 a1->type == CKA_CERTIFICATE_TYPE || 748 a1->type == CKA_VALUE_LEN) && 749 a1->ulValueLen != 0) { 750 len = sizeof (CK_ATTRIBUTE) + sizeof (CK_ULONG); 751 } else { 752 len = sizeof (CK_ATTRIBUTE) + a1->ulValueLen; 753 } 754 755 a2 = (CK_ATTRIBUTE *)malloc(len); 756 if (! a2) { 757 return (CKR_HOST_MEMORY); 758 } 759 a2->type = a1->type; 760 761 if ((a1->type == CKA_CLASS || 762 a1->type == CKA_KEY_TYPE || 763 a1->type == CKA_MODULUS_BITS || 764 a1->type == CKA_VALUE_BITS || 765 a1->type == CKA_CERTIFICATE_TYPE || 766 a1->type == CKA_VALUE_LEN) && 767 a1->ulValueLen != 0) { 768 a2->ulValueLen = sizeof (CK_ULONG); 769 { 770 CK_ULONG_32 *p32; 771 CK_BYTE *pb2; 772 void *aptr = a1; 773 void *bptr; 774 775 pb2 = (CK_BYTE *)aptr; 776 pb2 += sizeof (CK_ATTRIBUTE_32); 777 bptr = pb2; 778 p32 = (CK_ULONG_32 *)bptr; 779 attr_ulong_32 = *p32; 780 } 781 782 attr_ulong = attr_ulong_32; 783 784 { 785 CK_BYTE *pb2; 786 pb2 = (CK_BYTE *)a2; 787 pb2 += sizeof (CK_ATTRIBUTE); 788 (void) memcpy(pb2, 789 (CK_BYTE *)&attr_ulong, 790 sizeof (CK_ULONG)); 791 } 792 } else { 793 CK_BYTE *pb2, *pb; 794 795 a2->ulValueLen = a1->ulValueLen; 796 pb2 = (CK_BYTE *)a2; 797 pb2 += sizeof (CK_ATTRIBUTE); 798 pb = (CK_BYTE *)a1; 799 pb += sizeof (CK_ATTRIBUTE_32); 800 (void) memcpy(pb2, pb, a1->ulValueLen); 801 } 802 } 803 804 805 if (a2->ulValueLen != 0) 806 a2->pValue = (CK_BYTE *)a2 + sizeof (CK_ATTRIBUTE); 807 else 808 a2->pValue = NULL; 809 810 rc = template_update_attribute(tmpl, a2); 811 if (rc != CKR_OK) { 812 free(a2); 813 (void) template_free(tmpl); 814 return (rc); 815 } 816 if (long_len == 4) 817 ptr += len; 818 else 819 ptr += sizeof (CK_ATTRIBUTE_32) + a1->ulValueLen; 820 821 822 } 823 824 *new_tmpl = tmpl; 825 return (CKR_OK); 826 } 827 828 CK_RV 829 template_free(TEMPLATE *tmpl) { 830 if (! tmpl) 831 return (CKR_OK); 832 while (tmpl->attribute_list) { 833 CK_ATTRIBUTE *attr = (CK_ATTRIBUTE *)tmpl->attribute_list->data; 834 835 if (attr) 836 free(attr); 837 838 tmpl->attribute_list = dlist_remove_node(tmpl->attribute_list, 839 tmpl->attribute_list); 840 } 841 842 free(tmpl); 843 return (CKR_OK); 844 } 845 846 CK_BBOOL 847 template_get_class(TEMPLATE * tmpl, 848 CK_ULONG * class, 849 CK_ULONG * subclass) 850 { 851 DL_NODE * node; 852 CK_BBOOL found; 853 854 if (! tmpl || ! class || ! subclass) 855 return (FALSE); 856 node = tmpl->attribute_list; 857 858 while (node) { 859 CK_ATTRIBUTE *attr = (CK_ATTRIBUTE *)node->data; 860 861 if (attr->type == CKA_CLASS) { 862 *class = *(CK_OBJECT_CLASS *)attr->pValue; 863 found = TRUE; 864 } 865 866 if (attr->type == CKA_CERTIFICATE_TYPE) 867 *subclass = *(CK_CERTIFICATE_TYPE *)attr->pValue; 868 869 if (attr->type == CKA_KEY_TYPE) 870 *subclass = *(CK_KEY_TYPE *)attr->pValue; 871 872 node = node->next; 873 } 874 875 return (found); 876 } 877 878 CK_ULONG 879 template_get_count(TEMPLATE *tmpl) 880 { 881 if (tmpl == NULL) 882 return (0); 883 return (dlist_length(tmpl->attribute_list)); 884 } 885 886 CK_ULONG 887 template_get_size(TEMPLATE *tmpl) 888 { 889 DL_NODE * node; 890 CK_ULONG size = 0; 891 892 if (tmpl == NULL) 893 return (0); 894 node = tmpl->attribute_list; 895 while (node) { 896 CK_ATTRIBUTE *attr = (CK_ATTRIBUTE *)node->data; 897 898 size += sizeof (CK_ATTRIBUTE) + attr->ulValueLen; 899 900 node = node->next; 901 } 902 903 return (size); 904 } 905 906 CK_ULONG 907 template_get_compressed_size(TEMPLATE *tmpl) 908 { 909 DL_NODE * node; 910 CK_ULONG size = 0; 911 912 if (tmpl == NULL) 913 return (0); 914 node = tmpl->attribute_list; 915 while (node) { 916 CK_ATTRIBUTE *attr = (CK_ATTRIBUTE *)node->data; 917 918 size += sizeof (CK_ATTRIBUTE_32); 919 if ((attr->type == CKA_CLASS || 920 attr->type == CKA_KEY_TYPE || 921 attr->type == CKA_MODULUS_BITS || 922 attr->type == CKA_VALUE_BITS || 923 attr->type == CKA_CERTIFICATE_TYPE || 924 attr->type == CKA_VALUE_LEN) && 925 attr->ulValueLen != 0) { 926 size += sizeof (CK_ULONG_32); 927 } else { 928 size += attr->ulValueLen; 929 } 930 931 node = node->next; 932 } 933 934 return (size); 935 } 936 937 /* 938 * template_is_okay_to_reveal_attribute() 939 * 940 * determines whether the specified CK_ATTRIBUTE_TYPE is allowed to 941 * be leave the card in the clear. note: the specified template doesn't need 942 * to actually posess an attribute of type 'type'. The template is 943 * provided mainly to determine the object class and subclass 944 * 945 * this routine is called by C_GetAttributeValue which exports the attributes 946 * in the clear. this routine is NOT called when wrapping a key. 947 */ 948 CK_BBOOL 949 template_check_exportability(TEMPLATE *tmpl, CK_ATTRIBUTE_TYPE type) 950 { 951 CK_ATTRIBUTE * attr = NULL; 952 CK_ULONG class; 953 CK_ULONG subclass; 954 CK_BBOOL val; 955 956 if (! tmpl) 957 return (FALSE); 958 (void) template_get_class(tmpl, &class, &subclass); 959 960 if (class != CKO_PRIVATE_KEY && class != CKO_SECRET_KEY) 961 return (TRUE); 962 val = template_attribute_find(tmpl, CKA_SENSITIVE, &attr); 963 if (val) { 964 val = *(CK_BBOOL *)attr->pValue; 965 if (val == FALSE) 966 return (TRUE); 967 } else { 968 return (FALSE); 969 } 970 971 if (class == CKO_PRIVATE_KEY) { 972 switch (subclass) { 973 case CKK_RSA: 974 return (rsa_priv_check_exportability(type)); 975 default: 976 return (CKR_ATTRIBUTE_VALUE_INVALID); 977 } 978 } else if (class == CKO_SECRET_KEY) { 979 return (secret_key_check_exportability(type)); 980 } 981 982 return (CKR_ATTRIBUTE_VALUE_INVALID); 983 } 984 985 CK_RV 986 template_merge(TEMPLATE *dest, TEMPLATE **src) 987 { 988 DL_NODE *node; 989 CK_RV rc; 990 991 if (! dest || ! src) { 992 return (CKR_FUNCTION_FAILED); 993 } 994 node = (*src)->attribute_list; 995 996 while (node) { 997 CK_ATTRIBUTE *attr = (CK_ATTRIBUTE *)node->data; 998 999 rc = template_update_attribute(dest, attr); 1000 if (rc != CKR_OK) { 1001 return (rc); 1002 } 1003 node->data = NULL; 1004 node = node->next; 1005 } 1006 1007 (void) template_free(*src); 1008 *src = NULL; 1009 1010 return (CKR_OK); 1011 } 1012 1013 /* 1014 * template_set_default_common_attributes() 1015 * 1016 * Set the default attributes common to all objects: 1017 * 1018 * CKA_TOKEN : FALSE 1019 * CKA_PRIVATE : TRUE -- Cryptoki leaves this up to the token to decide 1020 * CKA_MODIFIABLE : TRUE 1021 * CKA_LABEL : empty string 1022 */ 1023 CK_RV 1024 template_set_default_common_attributes(TEMPLATE *tmpl) 1025 { 1026 CK_ATTRIBUTE * token_attr; 1027 CK_ATTRIBUTE * priv_attr; 1028 CK_ATTRIBUTE * mod_attr; 1029 CK_ATTRIBUTE * label_attr; 1030 1031 token_attr = (CK_ATTRIBUTE *)malloc(sizeof (CK_ATTRIBUTE) + 1032 sizeof (CK_BBOOL)); 1033 priv_attr = (CK_ATTRIBUTE *)malloc(sizeof (CK_ATTRIBUTE) + 1034 sizeof (CK_BBOOL)); 1035 mod_attr = (CK_ATTRIBUTE *)malloc(sizeof (CK_ATTRIBUTE) + 1036 sizeof (CK_BBOOL)); 1037 label_attr = (CK_ATTRIBUTE *)malloc(sizeof (CK_ATTRIBUTE) + 0); 1038 1039 if (! token_attr || ! priv_attr || ! mod_attr || ! label_attr) { 1040 if (token_attr) free(token_attr); 1041 if (priv_attr) free(priv_attr); 1042 if (mod_attr) free(mod_attr); 1043 if (label_attr) free(label_attr); 1044 1045 return (CKR_HOST_MEMORY); 1046 } 1047 1048 token_attr->type = CKA_TOKEN; 1049 token_attr->ulValueLen = sizeof (CK_BBOOL); 1050 token_attr->pValue = (CK_BYTE *)token_attr + sizeof (CK_ATTRIBUTE); 1051 *(CK_BBOOL *)token_attr->pValue = FALSE; 1052 1053 priv_attr->type = CKA_PRIVATE; 1054 priv_attr->ulValueLen = sizeof (CK_BBOOL); 1055 priv_attr->pValue = (CK_BYTE *)priv_attr + sizeof (CK_ATTRIBUTE); 1056 *(CK_BBOOL *)priv_attr->pValue = FALSE; 1057 1058 mod_attr->type = CKA_MODIFIABLE; 1059 mod_attr->ulValueLen = sizeof (CK_BBOOL); 1060 mod_attr->pValue = (CK_BYTE *)mod_attr + sizeof (CK_ATTRIBUTE); 1061 *(CK_BBOOL *)mod_attr->pValue = TRUE; 1062 1063 label_attr->type = CKA_LABEL; 1064 label_attr->ulValueLen = 0; // empty string 1065 label_attr->pValue = NULL; 1066 1067 (void) template_update_attribute(tmpl, token_attr); 1068 (void) template_update_attribute(tmpl, priv_attr); 1069 (void) template_update_attribute(tmpl, mod_attr); 1070 (void) template_update_attribute(tmpl, label_attr); 1071 1072 return (CKR_OK); 1073 } 1074 1075 CK_RV 1076 template_update_attribute(TEMPLATE *tmpl, CK_ATTRIBUTE *new_attr) { 1077 DL_NODE * node = NULL; 1078 CK_ATTRIBUTE * attr = NULL; 1079 1080 if (! tmpl || ! new_attr) { 1081 return (CKR_FUNCTION_FAILED); 1082 } 1083 node = tmpl->attribute_list; 1084 1085 while (node != NULL) { 1086 attr = (CK_ATTRIBUTE *)node->data; 1087 1088 if (new_attr->type == attr->type) { 1089 free(attr); 1090 tmpl->attribute_list = dlist_remove_node( 1091 tmpl->attribute_list, node); 1092 break; 1093 } 1094 1095 node = node->next; 1096 } 1097 1098 tmpl->attribute_list = dlist_add_as_first( 1099 tmpl->attribute_list, new_attr); 1100 1101 return (CKR_OK); 1102 } 1103 1104 CK_RV 1105 template_validate_attribute(TEMPLATE * tmpl, 1106 CK_ATTRIBUTE * attr, 1107 CK_ULONG class, 1108 CK_ULONG subclass, 1109 CK_ULONG mode) 1110 { 1111 if (class == CKO_DATA) 1112 return (data_object_validate_attribute(tmpl, attr, mode)); 1113 else if (class == CKO_CERTIFICATE) { 1114 if (subclass == CKC_X_509) 1115 return (cert_x509_validate_attribute(tmpl, attr, mode)); 1116 else 1117 return (cert_vendor_validate_attribute(tmpl, 1118 attr, mode)); 1119 } else if (class == CKO_PUBLIC_KEY) { 1120 1121 switch (subclass) { 1122 case CKK_RSA: 1123 return (rsa_publ_validate_attribute(tmpl, 1124 attr, mode)); 1125 default: 1126 return (CKR_ATTRIBUTE_VALUE_INVALID); 1127 } 1128 } else if (class == CKO_PRIVATE_KEY) { 1129 1130 switch (subclass) { 1131 case CKK_RSA: 1132 return (rsa_priv_validate_attribute(tmpl, 1133 attr, mode)); 1134 default: 1135 return (CKR_ATTRIBUTE_VALUE_INVALID); 1136 } 1137 } else if (class == CKO_SECRET_KEY) { 1138 switch (subclass) { 1139 case CKK_GENERIC_SECRET: 1140 return (generic_secret_validate_attribute(tmpl, 1141 attr, mode)); 1142 default: 1143 return (CKR_ATTRIBUTE_VALUE_INVALID); 1144 } 1145 } else if (class == CKO_HW_FEATURE) { 1146 1147 switch (subclass) { 1148 case CKH_CLOCK: 1149 return (clock_validate_attribute(tmpl, 1150 attr, mode)); 1151 case CKH_MONOTONIC_COUNTER: 1152 return (counter_validate_attribute(tmpl, 1153 attr, mode)); 1154 default: 1155 return (CKR_ATTRIBUTE_VALUE_INVALID); 1156 } 1157 } else if (class == CKO_DOMAIN_PARAMETERS) { 1158 switch (subclass) { 1159 default: 1160 return (CKR_ATTRIBUTE_VALUE_INVALID); 1161 } 1162 } 1163 return (CKR_ATTRIBUTE_VALUE_INVALID); 1164 } 1165 1166 CK_RV 1167 template_validate_attributes(TEMPLATE * tmpl, 1168 CK_ULONG class, 1169 CK_ULONG subclass, 1170 CK_ULONG mode) 1171 { 1172 DL_NODE *node; 1173 CK_RV rc = CKR_OK; 1174 1175 node = tmpl->attribute_list; 1176 1177 while (node) { 1178 CK_ATTRIBUTE *attr = (CK_ATTRIBUTE *)node->data; 1179 1180 rc = template_validate_attribute(tmpl, attr, class, 1181 subclass, mode); 1182 if (rc != CKR_OK) { 1183 return (rc); 1184 } 1185 node = node->next; 1186 } 1187 1188 return (CKR_OK); 1189 } 1190 1191 CK_RV 1192 template_validate_base_attribute(TEMPLATE * tmpl, 1193 CK_ATTRIBUTE * attr, 1194 CK_ULONG mode) 1195 { 1196 if (! tmpl || ! attr) { 1197 return (CKR_FUNCTION_FAILED); 1198 } 1199 switch (attr->type) { 1200 case CKA_CLASS: 1201 if ((mode & (MODE_CREATE | MODE_DERIVE | 1202 MODE_KEYGEN | MODE_UNWRAP)) != 0) 1203 return (CKR_OK); 1204 break; 1205 1206 case CKA_TOKEN: 1207 if ((mode & (MODE_CREATE | MODE_COPY | 1208 MODE_DERIVE | MODE_KEYGEN | MODE_UNWRAP)) != 0) 1209 return (CKR_OK); 1210 break; 1211 1212 case CKA_PRIVATE: 1213 if ((mode & (MODE_CREATE | MODE_COPY | 1214 MODE_DERIVE | MODE_KEYGEN | MODE_UNWRAP)) != 0) 1215 return (CKR_OK); 1216 break; 1217 1218 case CKA_LABEL: 1219 return (CKR_OK); 1220 case CKA_MODIFIABLE: 1221 if ((mode & (MODE_CREATE | MODE_COPY | 1222 MODE_DERIVE | MODE_KEYGEN | MODE_UNWRAP)) != 0) 1223 return (CKR_OK); 1224 break; 1225 1226 default: 1227 return (CKR_TEMPLATE_INCONSISTENT); 1228 } 1229 1230 return (CKR_ATTRIBUTE_READ_ONLY); 1231 } 1232