Print this page
9642 PKCS#11 softtoken should use explicit_bzero
Reviewed by: Dan McDonald <danmcd@joyent.com>
Reviewed by: Alex Wilson <alex.wilson@joyent.com>


   5  * Common Development and Distribution License (the "License").
   6  * You may not use this file except in compliance with the License.
   7  *
   8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
   9  * or http://www.opensolaris.org/os/licensing.
  10  * See the License for the specific language governing permissions
  11  * and limitations under the License.
  12  *
  13  * When distributing Covered Code, include this CDDL HEADER in each
  14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15  * If applicable, add the following below this CDDL HEADER, with the
  16  * fields enclosed by brackets "[]" replaced with your own identifying
  17  * information: Portions Copyright [yyyy] [name of copyright owner]
  18  *
  19  * CDDL HEADER END
  20  */
  21 
  22 /*
  23  * Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved.
  24  * Copyright 2015 Nexenta Systems, Inc.  All rights reserved.

  25  */
  26 
  27 #include <pthread.h>
  28 #include <stdlib.h>
  29 #include <string.h>
  30 #include <strings.h>
  31 #include <sys/types.h>
  32 #include <security/cryptoki.h>
  33 #include <modes/modes.h>
  34 #include <arcfour.h>
  35 #include "softSession.h"
  36 #include "softObject.h"
  37 #include "softOps.h"
  38 #include "softCrypt.h"
  39 #include "softRSA.h"
  40 
  41 /*
  42  * Add padding bytes with the value of length of padding.
  43  */
  44 void


 158 
 159                 rv = soft_des_crypt_init_common(session_p, pMechanism,
 160                     key_p, B_TRUE);
 161 
 162                 if (rv != CKR_OK)
 163                         return (rv);
 164 
 165                 (void) pthread_mutex_lock(&session_p->session_mutex);
 166 
 167                 soft_des_ctx = (soft_des_ctx_t *)session_p->encrypt.context;
 168                 /* Copy Initialization Vector (IV) into the context. */
 169                 (void) memcpy(soft_des_ctx->ivec, pMechanism->pParameter,
 170                     DES_BLOCK_LEN);
 171 
 172                 /* Allocate a context for DES cipher-block chaining. */
 173                 soft_des_ctx->des_cbc = (void *)des_cbc_ctx_init(
 174                     soft_des_ctx->key_sched, soft_des_ctx->keysched_len,
 175                     soft_des_ctx->ivec, key_p->key_type);
 176 
 177                 if (soft_des_ctx->des_cbc == NULL) {
 178                         bzero(soft_des_ctx->key_sched,
 179                             soft_des_ctx->keysched_len);
 180                         free(soft_des_ctx->key_sched);
 181                         free(session_p->encrypt.context);
 182                         session_p->encrypt.context = NULL;
 183                         rv = CKR_HOST_MEMORY;
 184                 }
 185 
 186                 (void) pthread_mutex_unlock(&session_p->session_mutex);
 187 
 188                 return (rv);
 189         }
 190         case CKM_AES_ECB:
 191 
 192                 if (key_p->key_type != CKK_AES) {
 193                         return (CKR_KEY_TYPE_INCONSISTENT);
 194                 }
 195 
 196                 return (soft_aes_crypt_init_common(session_p, pMechanism,
 197                     key_p, B_TRUE));
 198 
 199         case CKM_AES_CBC:
 200         case CKM_AES_CBC_PAD:
 201                 if ((pMechanism->pParameter == NULL) ||


 222 
 223                 soft_aes_ctx = (soft_aes_ctx_t *)session_p->encrypt.context;
 224                 /* Copy Initialization Vector (IV) into the context. */
 225                 if (pMechanism->mechanism == CKM_AES_CMAC) {
 226                         (void) bzero(soft_aes_ctx->ivec, AES_BLOCK_LEN);
 227                         /* Allocate a context for AES cipher-block chaining. */
 228                         soft_aes_ctx->aes_cbc = (void *)aes_cmac_ctx_init(
 229                             soft_aes_ctx->key_sched,
 230                             soft_aes_ctx->keysched_len);
 231                 } else {
 232                         (void) memcpy(soft_aes_ctx->ivec,
 233                             pMechanism->pParameter,
 234                             AES_BLOCK_LEN);
 235                         /* Allocate a context for AES cipher-block chaining. */
 236                         soft_aes_ctx->aes_cbc = (void *)aes_cbc_ctx_init(
 237                             soft_aes_ctx->key_sched,
 238                             soft_aes_ctx->keysched_len,
 239                             soft_aes_ctx->ivec);
 240                 }
 241                 if (soft_aes_ctx->aes_cbc == NULL) {
 242                         bzero(soft_aes_ctx->key_sched,
 243                             soft_aes_ctx->keysched_len);
 244                         free(soft_aes_ctx->key_sched);
 245                         free(session_p->encrypt.context);
 246                         session_p->encrypt.context = NULL;
 247                         rv = CKR_HOST_MEMORY;
 248                 }
 249 
 250                 (void) pthread_mutex_unlock(&session_p->session_mutex);
 251 
 252                 return (rv);
 253         }
 254         case CKM_AES_CTR:
 255         {
 256                 soft_aes_ctx_t *soft_aes_ctx;
 257 
 258                 if (key_p->key_type != CKK_AES) {
 259                         return (CKR_KEY_TYPE_INCONSISTENT);
 260                 }
 261 
 262                 if (pMechanism->pParameter == NULL ||
 263                     pMechanism->ulParameterLen != sizeof (CK_AES_CTR_PARAMS)) {
 264                         return (CKR_MECHANISM_PARAM_INVALID);
 265                 }
 266 
 267                 rv = soft_aes_crypt_init_common(session_p, pMechanism,
 268                     key_p, B_TRUE);
 269 
 270                 if (rv != CKR_OK)
 271                         return (rv);
 272 
 273                 (void) pthread_mutex_lock(&session_p->session_mutex);
 274 
 275                 soft_aes_ctx = (soft_aes_ctx_t *)session_p->encrypt.context;
 276                 soft_aes_ctx->aes_cbc = aes_ctr_ctx_init(
 277                     soft_aes_ctx->key_sched, soft_aes_ctx->keysched_len,
 278                     pMechanism->pParameter);
 279 
 280                 if (soft_aes_ctx->aes_cbc == NULL) {
 281                         bzero(soft_aes_ctx->key_sched,
 282                             soft_aes_ctx->keysched_len);
 283                         free(soft_aes_ctx->key_sched);
 284                         free(session_p->encrypt.context);
 285                         session_p->encrypt.context = NULL;
 286                         rv = CKR_HOST_MEMORY;
 287                 }
 288 
 289                 (void) pthread_mutex_unlock(&session_p->session_mutex);
 290 
 291                 return (rv);
 292         }
 293         case CKM_RC4:
 294 
 295                 if (key_p->key_type != CKK_RC4) {
 296                         return (CKR_KEY_TYPE_INCONSISTENT);
 297                 }
 298 
 299                 return (soft_arcfour_crypt_init(session_p, pMechanism, key_p,
 300                     B_TRUE));
 301 
 302         case CKM_RSA_X_509:
 303         case CKM_RSA_PKCS:
 304 


 324                     key_p, B_TRUE);
 325 
 326                 if (rv != CKR_OK)
 327                         return (rv);
 328 
 329                 (void) pthread_mutex_lock(&session_p->session_mutex);
 330 
 331                 soft_blowfish_ctx =
 332                     (soft_blowfish_ctx_t *)session_p->encrypt.context;
 333                 /* Copy Initialization Vector (IV) into the context. */
 334                 (void) memcpy(soft_blowfish_ctx->ivec, pMechanism->pParameter,
 335                     BLOWFISH_BLOCK_LEN);
 336 
 337                 /* Allocate a context for Blowfish cipher-block chaining */
 338                 soft_blowfish_ctx->blowfish_cbc =
 339                     (void *)blowfish_cbc_ctx_init(soft_blowfish_ctx->key_sched,
 340                     soft_blowfish_ctx->keysched_len,
 341                     soft_blowfish_ctx->ivec);
 342 
 343                 if (soft_blowfish_ctx->blowfish_cbc == NULL) {
 344                         bzero(soft_blowfish_ctx->key_sched,
 345                             soft_blowfish_ctx->keysched_len);
 346                         free(soft_blowfish_ctx->key_sched);
 347                         free(session_p->encrypt.context);
 348                         session_p->encrypt.context = NULL;
 349                         rv = CKR_HOST_MEMORY;
 350                 }
 351 
 352                 (void) pthread_mutex_unlock(&session_p->session_mutex);
 353 
 354                 return (rv);
 355         }
 356         default:
 357                 return (CKR_MECHANISM_INVALID);
 358         }
 359 }
 360 
 361 
 362 /*
 363  * soft_encrypt_common()
 364  *
 365  * Arguments:
 366  *      session_p:      pointer to soft_session_t struct
 367  *      pData:          pointer to the input data to be encrypted


 611                         out.cd_format = CRYPTO_DATA_RAW;
 612                         out.cd_offset = 0;
 613                         out.cd_length = out_len;
 614                         out.cd_raw.iov_base = (char *)pLastEncryptedPart;
 615                         out.cd_raw.iov_len = out_len;
 616 
 617                         /* Encrypt multiple blocks of data. */
 618                         rc = des_encrypt_contiguous_blocks(
 619                             (des_ctx_t *)soft_des_ctx->des_cbc,
 620                             (char *)pLastEncryptedPart, out_len, &out);
 621 
 622                         if (rc == 0) {
 623                                 *pulLastEncryptedPartLen = out_len;
 624                         } else {
 625                                 *pulLastEncryptedPartLen = 0;
 626                                 rv = CKR_FUNCTION_FAILED;
 627                         }
 628 
 629                         /* Cleanup memory space. */
 630                         free(soft_des_ctx->des_cbc);
 631                         bzero(soft_des_ctx->key_sched,
 632                             soft_des_ctx->keysched_len);
 633                         free(soft_des_ctx->key_sched);
 634                 }
 635 
 636                 break;
 637         }
 638         case CKM_DES_CBC:
 639         case CKM_DES_ECB:
 640         case CKM_DES3_CBC:
 641         case CKM_DES3_ECB:
 642         {
 643 
 644                 soft_des_ctx_t *soft_des_ctx;
 645 
 646                 soft_des_ctx = (soft_des_ctx_t *)session_p->encrypt.context;
 647                 /*
 648                  * CKM_DES_CBC and CKM_DES_ECB does not do any padding,
 649                  * so when the final is called, the remaining buffer
 650                  * should not contain any more data.
 651                  */
 652                 *pulLastEncryptedPartLen = 0;
 653                 if (soft_des_ctx->remain_len != 0) {
 654                         rv = CKR_DATA_LEN_RANGE;
 655                 } else {
 656                         if (pLastEncryptedPart == NULL)
 657                                 goto clean1;
 658                 }
 659 
 660                 /* Cleanup memory space. */
 661                 free(soft_des_ctx->des_cbc);
 662                 bzero(soft_des_ctx->key_sched, soft_des_ctx->keysched_len);
 663                 free(soft_des_ctx->key_sched);
 664 
 665                 break;
 666         }
 667         case CKM_AES_CBC_PAD:
 668         {
 669                 soft_aes_ctx_t *soft_aes_ctx;
 670 
 671                 soft_aes_ctx = (soft_aes_ctx_t *)session_p->encrypt.context;
 672                 /*
 673                  * For CKM_AES_CBC_PAD, compute output length with
 674                  * padding. If the remaining buffer has one block
 675                  * of data, then output length will be two blocksize of
 676                  * ciphertext. If the remaining buffer has less than
 677                  * one block of data, then output length will be
 678                  * one blocksize.
 679                  */
 680                 if (soft_aes_ctx->remain_len == AES_BLOCK_LEN)
 681                         out_len = 2 * AES_BLOCK_LEN;
 682                 else
 683                         out_len = AES_BLOCK_LEN;


 706                         out.cd_format = CRYPTO_DATA_RAW;
 707                         out.cd_offset = 0;
 708                         out.cd_length = out_len;
 709                         out.cd_raw.iov_base = (char *)pLastEncryptedPart;
 710                         out.cd_raw.iov_len = out_len;
 711 
 712                         /* Encrypt multiple blocks of data. */
 713                         rc = aes_encrypt_contiguous_blocks(
 714                             (aes_ctx_t *)soft_aes_ctx->aes_cbc,
 715                             (char *)pLastEncryptedPart, out_len, &out);
 716 
 717                         if (rc == 0) {
 718                                 *pulLastEncryptedPartLen = out_len;
 719                         } else {
 720                                 *pulLastEncryptedPartLen = 0;
 721                                 rv = CKR_FUNCTION_FAILED;
 722                         }
 723 
 724                         /* Cleanup memory space. */
 725                         free(soft_aes_ctx->aes_cbc);
 726                         bzero(soft_aes_ctx->key_sched,
 727                             soft_aes_ctx->keysched_len);
 728                         free(soft_aes_ctx->key_sched);
 729                 }
 730 
 731                 break;
 732         }
 733         case CKM_AES_CMAC:
 734         {
 735                 soft_aes_ctx_t *soft_aes_ctx;
 736                 soft_aes_ctx = (soft_aes_ctx_t *)session_p->encrypt.context;
 737 
 738                 if (pLastEncryptedPart == NULL) {
 739                         /*
 740                          * Application asks for the length of the output
 741                          * buffer to hold the ciphertext.
 742                          */
 743                         *pulLastEncryptedPartLen = AES_BLOCK_LEN;
 744                         goto clean1;
 745                 } else {
 746                         crypto_data_t out;
 747 
 748                         out.cd_format = CRYPTO_DATA_RAW;
 749                         out.cd_offset = 0;
 750                         out.cd_length = AES_BLOCK_LEN;
 751                         out.cd_raw.iov_base = (char *)pLastEncryptedPart;
 752                         out.cd_raw.iov_len = AES_BLOCK_LEN;
 753 
 754                         rc = cmac_mode_final(soft_aes_ctx->aes_cbc, &out,
 755                             aes_encrypt_block, aes_xor_block);
 756 
 757                         if (rc == 0) {
 758                                 *pulLastEncryptedPartLen = AES_BLOCK_LEN;
 759                         } else {
 760                                 *pulLastEncryptedPartLen = 0;
 761                                 rv = CKR_FUNCTION_FAILED;
 762                         }
 763 
 764                         /* Cleanup memory space. */
 765                         free(soft_aes_ctx->aes_cbc);
 766                         bzero(soft_aes_ctx->key_sched,
 767                             soft_aes_ctx->keysched_len);
 768                         free(soft_aes_ctx->key_sched);
 769                 }
 770 
 771                 break;
 772         }
 773         case CKM_AES_CBC:
 774         case CKM_AES_ECB:
 775         {
 776                 soft_aes_ctx_t *soft_aes_ctx;
 777 
 778                 soft_aes_ctx = (soft_aes_ctx_t *)session_p->encrypt.context;
 779                 /*
 780                  * CKM_AES_CBC and CKM_AES_ECB does not do any padding,
 781                  * so when the final is called, the remaining buffer
 782                  * should not contain any more data.
 783                  */
 784                 *pulLastEncryptedPartLen = 0;
 785                 if (soft_aes_ctx->remain_len != 0) {
 786                         rv = CKR_DATA_LEN_RANGE;
 787                 } else {
 788                         if (pLastEncryptedPart == NULL)
 789                                 goto clean1;
 790                 }
 791 
 792                 /* Cleanup memory space. */
 793                 free(soft_aes_ctx->aes_cbc);
 794                 bzero(soft_aes_ctx->key_sched, soft_aes_ctx->keysched_len);
 795                 free(soft_aes_ctx->key_sched);
 796 
 797                 break;
 798         }
 799         case CKM_AES_CTR:
 800         {
 801                 crypto_data_t out;
 802                 soft_aes_ctx_t *soft_aes_ctx;
 803                 ctr_ctx_t *ctr_ctx;
 804                 size_t len;
 805 
 806                 soft_aes_ctx = (soft_aes_ctx_t *)session_p->encrypt.context;
 807                 ctr_ctx = soft_aes_ctx->aes_cbc;
 808                 len = ctr_ctx->ctr_remainder_len;
 809 
 810                 if (pLastEncryptedPart == NULL) {
 811                         *pulLastEncryptedPartLen = len;
 812                         goto clean1;
 813                 }
 814                 if (len > 0) {
 815                         out.cd_format = CRYPTO_DATA_RAW;
 816                         out.cd_offset = 0;
 817                         out.cd_length = len;
 818                         out.cd_raw.iov_base = (char *)pLastEncryptedPart;
 819                         out.cd_raw.iov_len = len;
 820 
 821                         rv = ctr_mode_final(ctr_ctx, &out, aes_encrypt_block);
 822                 }
 823                 if (rv == CRYPTO_BUFFER_TOO_SMALL) {
 824                         *pulLastEncryptedPartLen = len;
 825                         goto clean1;
 826                 }
 827 
 828                 /* Cleanup memory space. */
 829                 free(ctr_ctx);
 830                 bzero(soft_aes_ctx->key_sched, soft_aes_ctx->keysched_len);
 831                 free(soft_aes_ctx->key_sched);
 832 
 833                 break;
 834         }
 835         case CKM_BLOWFISH_CBC:
 836         {
 837                 soft_blowfish_ctx_t *soft_blowfish_ctx;
 838 
 839                 soft_blowfish_ctx =
 840                     (soft_blowfish_ctx_t *)session_p->encrypt.context;
 841                 /*
 842                  * CKM_BLOWFISH_CBC does not do any padding, so when the
 843                  * final is called, the remaining buffer should not contain
 844                  * any more data
 845                  */
 846                 *pulLastEncryptedPartLen = 0;
 847                 if (soft_blowfish_ctx->remain_len != 0)
 848                         rv = CKR_DATA_LEN_RANGE;
 849                 else {
 850                         if (pLastEncryptedPart == NULL)
 851                                 goto clean1;
 852                 }
 853 
 854                 free(soft_blowfish_ctx->blowfish_cbc);
 855                 bzero(soft_blowfish_ctx->key_sched,
 856                     soft_blowfish_ctx->keysched_len);
 857                 free(soft_blowfish_ctx->key_sched);
 858                 break;
 859         }
 860 
 861         case CKM_RC4:
 862         {
 863                 ARCFour_key *key = (ARCFour_key *)session_p->encrypt.context;
 864                 /* Remaining data size is always zero for RC4. */
 865                 *pulLastEncryptedPartLen = 0;
 866                 if (pLastEncryptedPart == NULL)
 867                         goto clean1;
 868                 bzero(key, sizeof (*key));
 869                 break;
 870         }
 871         default:
 872                 /* PKCS11: The mechanism only supports single-part operation. */
 873                 rv = CKR_MECHANISM_INVALID;
 874                 break;
 875         }
 876 
 877         free(session_p->encrypt.context);
 878         session_p->encrypt.context = NULL;
 879 clean1:
 880         (void) pthread_mutex_unlock(&session_p->session_mutex);
 881 
 882         return (rv);
 883 }
 884 
 885 /*
 886  * This function frees the allocated active crypto context and the
 887  * lower level of allocated struct as needed.
 888  * This function is called by the 1st tier of encrypt/decrypt routines


 904 
 905         active_op = (encrypt) ? &(session_p->encrypt) : &(session_p->decrypt);
 906 
 907         switch (active_op->mech.mechanism) {
 908 
 909         case CKM_DES_CBC_PAD:
 910         case CKM_DES3_CBC_PAD:
 911         case CKM_DES_CBC:
 912         case CKM_DES_ECB:
 913         case CKM_DES3_CBC:
 914         case CKM_DES3_ECB:
 915         {
 916 
 917                 soft_des_ctx_t *soft_des_ctx =
 918                     (soft_des_ctx_t *)active_op->context;
 919                 des_ctx_t *des_ctx;
 920 
 921                 if (soft_des_ctx != NULL) {
 922                         des_ctx = (des_ctx_t *)soft_des_ctx->des_cbc;
 923                         if (des_ctx != NULL) {
 924                                 bzero(des_ctx->dc_keysched,
 925                                     des_ctx->dc_keysched_len);
 926                                 free(soft_des_ctx->des_cbc);
 927                         }
 928                         bzero(soft_des_ctx->key_sched,
 929                             soft_des_ctx->keysched_len);
 930                         free(soft_des_ctx->key_sched);
 931                 }
 932                 break;
 933         }
 934 
 935         case CKM_AES_CBC_PAD:
 936         case CKM_AES_CBC:
 937         case CKM_AES_CMAC:
 938         case CKM_AES_ECB:
 939         {
 940                 soft_aes_ctx_t *soft_aes_ctx =
 941                     (soft_aes_ctx_t *)active_op->context;
 942                 aes_ctx_t *aes_ctx;
 943 
 944                 if (soft_aes_ctx != NULL) {
 945                         aes_ctx = (aes_ctx_t *)soft_aes_ctx->aes_cbc;
 946                         if (aes_ctx != NULL) {
 947                                 bzero(aes_ctx->ac_keysched,
 948                                     aes_ctx->ac_keysched_len);
 949                                 free(soft_aes_ctx->aes_cbc);
 950                         }
 951                         bzero(soft_aes_ctx->key_sched,
 952                             soft_aes_ctx->keysched_len);
 953                         free(soft_aes_ctx->key_sched);
 954                 }
 955                 break;
 956         }
 957 
 958         case CKM_BLOWFISH_CBC:
 959         {
 960                 soft_blowfish_ctx_t *soft_blowfish_ctx =
 961                     (soft_blowfish_ctx_t *)active_op->context;
 962                 blowfish_ctx_t *blowfish_ctx;
 963 
 964                 if (soft_blowfish_ctx != NULL) {
 965                         blowfish_ctx =
 966                             (blowfish_ctx_t *)soft_blowfish_ctx->blowfish_cbc;
 967                         if (blowfish_ctx != NULL) {
 968                                 bzero(blowfish_ctx->bc_keysched,
 969                                     blowfish_ctx->bc_keysched_len);
 970                                 free(soft_blowfish_ctx->blowfish_cbc);
 971                         }
 972 
 973                         bzero(soft_blowfish_ctx->key_sched,
 974                             soft_blowfish_ctx->keysched_len);
 975                         free(soft_blowfish_ctx->key_sched);
 976                 }
 977                 break;
 978         }
 979 
 980         case CKM_RC4:
 981         {
 982                 ARCFour_key *key = (ARCFour_key *)active_op->context;
 983 
 984                 if (key != NULL)
 985                         bzero(key, sizeof (*key));
 986                 break;
 987         }
 988 
 989         case CKM_RSA_X_509:
 990         case CKM_RSA_PKCS:
 991         {
 992                 soft_rsa_ctx_t *rsa_ctx =
 993                     (soft_rsa_ctx_t *)active_op->context;
 994 
 995                 if (rsa_ctx != NULL)
 996                         if (rsa_ctx->key != NULL) {
 997                                 soft_cleanup_object(rsa_ctx->key);
 998                                 free(rsa_ctx->key);
 999                         }
1000 
1001                 break;
1002         }
1003 
1004         } /* switch */
1005 


   5  * Common Development and Distribution License (the "License").
   6  * You may not use this file except in compliance with the License.
   7  *
   8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
   9  * or http://www.opensolaris.org/os/licensing.
  10  * See the License for the specific language governing permissions
  11  * and limitations under the License.
  12  *
  13  * When distributing Covered Code, include this CDDL HEADER in each
  14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15  * If applicable, add the following below this CDDL HEADER, with the
  16  * fields enclosed by brackets "[]" replaced with your own identifying
  17  * information: Portions Copyright [yyyy] [name of copyright owner]
  18  *
  19  * CDDL HEADER END
  20  */
  21 
  22 /*
  23  * Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved.
  24  * Copyright 2015 Nexenta Systems, Inc.  All rights reserved.
  25  * Copyright (c) 2018, Joyent, Inc.
  26  */
  27 
  28 #include <pthread.h>
  29 #include <stdlib.h>
  30 #include <string.h>
  31 #include <strings.h>
  32 #include <sys/types.h>
  33 #include <security/cryptoki.h>
  34 #include <modes/modes.h>
  35 #include <arcfour.h>
  36 #include "softSession.h"
  37 #include "softObject.h"
  38 #include "softOps.h"
  39 #include "softCrypt.h"
  40 #include "softRSA.h"
  41 
  42 /*
  43  * Add padding bytes with the value of length of padding.
  44  */
  45 void


 159 
 160                 rv = soft_des_crypt_init_common(session_p, pMechanism,
 161                     key_p, B_TRUE);
 162 
 163                 if (rv != CKR_OK)
 164                         return (rv);
 165 
 166                 (void) pthread_mutex_lock(&session_p->session_mutex);
 167 
 168                 soft_des_ctx = (soft_des_ctx_t *)session_p->encrypt.context;
 169                 /* Copy Initialization Vector (IV) into the context. */
 170                 (void) memcpy(soft_des_ctx->ivec, pMechanism->pParameter,
 171                     DES_BLOCK_LEN);
 172 
 173                 /* Allocate a context for DES cipher-block chaining. */
 174                 soft_des_ctx->des_cbc = (void *)des_cbc_ctx_init(
 175                     soft_des_ctx->key_sched, soft_des_ctx->keysched_len,
 176                     soft_des_ctx->ivec, key_p->key_type);
 177 
 178                 if (soft_des_ctx->des_cbc == NULL) {
 179                         freezero(soft_des_ctx->key_sched,
 180                             soft_des_ctx->keysched_len);
 181                         freezero(session_p->encrypt.context,
 182                             sizeof (soft_des_ctx_t));
 183                         session_p->encrypt.context = NULL;
 184                         rv = CKR_HOST_MEMORY;
 185                 }
 186 
 187                 (void) pthread_mutex_unlock(&session_p->session_mutex);
 188 
 189                 return (rv);
 190         }
 191         case CKM_AES_ECB:
 192 
 193                 if (key_p->key_type != CKK_AES) {
 194                         return (CKR_KEY_TYPE_INCONSISTENT);
 195                 }
 196 
 197                 return (soft_aes_crypt_init_common(session_p, pMechanism,
 198                     key_p, B_TRUE));
 199 
 200         case CKM_AES_CBC:
 201         case CKM_AES_CBC_PAD:
 202                 if ((pMechanism->pParameter == NULL) ||


 223 
 224                 soft_aes_ctx = (soft_aes_ctx_t *)session_p->encrypt.context;
 225                 /* Copy Initialization Vector (IV) into the context. */
 226                 if (pMechanism->mechanism == CKM_AES_CMAC) {
 227                         (void) bzero(soft_aes_ctx->ivec, AES_BLOCK_LEN);
 228                         /* Allocate a context for AES cipher-block chaining. */
 229                         soft_aes_ctx->aes_cbc = (void *)aes_cmac_ctx_init(
 230                             soft_aes_ctx->key_sched,
 231                             soft_aes_ctx->keysched_len);
 232                 } else {
 233                         (void) memcpy(soft_aes_ctx->ivec,
 234                             pMechanism->pParameter,
 235                             AES_BLOCK_LEN);
 236                         /* Allocate a context for AES cipher-block chaining. */
 237                         soft_aes_ctx->aes_cbc = (void *)aes_cbc_ctx_init(
 238                             soft_aes_ctx->key_sched,
 239                             soft_aes_ctx->keysched_len,
 240                             soft_aes_ctx->ivec);
 241                 }
 242                 if (soft_aes_ctx->aes_cbc == NULL) {
 243                         freezero(soft_aes_ctx->key_sched,
 244                             soft_aes_ctx->keysched_len);
 245                         freezero(session_p->encrypt.context,
 246                             sizeof (soft_aes_ctx_t));
 247                         session_p->encrypt.context = NULL;
 248                         rv = CKR_HOST_MEMORY;
 249                 }
 250 
 251                 (void) pthread_mutex_unlock(&session_p->session_mutex);
 252 
 253                 return (rv);
 254         }
 255         case CKM_AES_CTR:
 256         {
 257                 soft_aes_ctx_t *soft_aes_ctx;
 258 
 259                 if (key_p->key_type != CKK_AES) {
 260                         return (CKR_KEY_TYPE_INCONSISTENT);
 261                 }
 262 
 263                 if (pMechanism->pParameter == NULL ||
 264                     pMechanism->ulParameterLen != sizeof (CK_AES_CTR_PARAMS)) {
 265                         return (CKR_MECHANISM_PARAM_INVALID);
 266                 }
 267 
 268                 rv = soft_aes_crypt_init_common(session_p, pMechanism,
 269                     key_p, B_TRUE);
 270 
 271                 if (rv != CKR_OK)
 272                         return (rv);
 273 
 274                 (void) pthread_mutex_lock(&session_p->session_mutex);
 275 
 276                 soft_aes_ctx = (soft_aes_ctx_t *)session_p->encrypt.context;
 277                 soft_aes_ctx->aes_cbc = aes_ctr_ctx_init(
 278                     soft_aes_ctx->key_sched, soft_aes_ctx->keysched_len,
 279                     pMechanism->pParameter);
 280 
 281                 if (soft_aes_ctx->aes_cbc == NULL) {
 282                         freezero(soft_aes_ctx->key_sched,
 283                             soft_aes_ctx->keysched_len);
 284                         freezero(session_p->encrypt.context,
 285                             sizeof (soft_aes_ctx_t));
 286                         session_p->encrypt.context = NULL;
 287                         rv = CKR_HOST_MEMORY;
 288                 }
 289 
 290                 (void) pthread_mutex_unlock(&session_p->session_mutex);
 291 
 292                 return (rv);
 293         }
 294         case CKM_RC4:
 295 
 296                 if (key_p->key_type != CKK_RC4) {
 297                         return (CKR_KEY_TYPE_INCONSISTENT);
 298                 }
 299 
 300                 return (soft_arcfour_crypt_init(session_p, pMechanism, key_p,
 301                     B_TRUE));
 302 
 303         case CKM_RSA_X_509:
 304         case CKM_RSA_PKCS:
 305 


 325                     key_p, B_TRUE);
 326 
 327                 if (rv != CKR_OK)
 328                         return (rv);
 329 
 330                 (void) pthread_mutex_lock(&session_p->session_mutex);
 331 
 332                 soft_blowfish_ctx =
 333                     (soft_blowfish_ctx_t *)session_p->encrypt.context;
 334                 /* Copy Initialization Vector (IV) into the context. */
 335                 (void) memcpy(soft_blowfish_ctx->ivec, pMechanism->pParameter,
 336                     BLOWFISH_BLOCK_LEN);
 337 
 338                 /* Allocate a context for Blowfish cipher-block chaining */
 339                 soft_blowfish_ctx->blowfish_cbc =
 340                     (void *)blowfish_cbc_ctx_init(soft_blowfish_ctx->key_sched,
 341                     soft_blowfish_ctx->keysched_len,
 342                     soft_blowfish_ctx->ivec);
 343 
 344                 if (soft_blowfish_ctx->blowfish_cbc == NULL) {
 345                         freezero(soft_blowfish_ctx->key_sched,
 346                             soft_blowfish_ctx->keysched_len);
 347                         freezero(session_p->encrypt.context,
 348                             sizeof (soft_blowfish_ctx_t));
 349                         session_p->encrypt.context = NULL;
 350                         rv = CKR_HOST_MEMORY;
 351                 }
 352 
 353                 (void) pthread_mutex_unlock(&session_p->session_mutex);
 354 
 355                 return (rv);
 356         }
 357         default:
 358                 return (CKR_MECHANISM_INVALID);
 359         }
 360 }
 361 
 362 
 363 /*
 364  * soft_encrypt_common()
 365  *
 366  * Arguments:
 367  *      session_p:      pointer to soft_session_t struct
 368  *      pData:          pointer to the input data to be encrypted


 612                         out.cd_format = CRYPTO_DATA_RAW;
 613                         out.cd_offset = 0;
 614                         out.cd_length = out_len;
 615                         out.cd_raw.iov_base = (char *)pLastEncryptedPart;
 616                         out.cd_raw.iov_len = out_len;
 617 
 618                         /* Encrypt multiple blocks of data. */
 619                         rc = des_encrypt_contiguous_blocks(
 620                             (des_ctx_t *)soft_des_ctx->des_cbc,
 621                             (char *)pLastEncryptedPart, out_len, &out);
 622 
 623                         if (rc == 0) {
 624                                 *pulLastEncryptedPartLen = out_len;
 625                         } else {
 626                                 *pulLastEncryptedPartLen = 0;
 627                                 rv = CKR_FUNCTION_FAILED;
 628                         }
 629 
 630                         /* Cleanup memory space. */
 631                         free(soft_des_ctx->des_cbc);
 632                         freezero(soft_des_ctx->key_sched,
 633                             soft_des_ctx->keysched_len);

 634                 }
 635 
 636                 break;
 637         }
 638         case CKM_DES_CBC:
 639         case CKM_DES_ECB:
 640         case CKM_DES3_CBC:
 641         case CKM_DES3_ECB:
 642         {
 643 
 644                 soft_des_ctx_t *soft_des_ctx;
 645 
 646                 soft_des_ctx = (soft_des_ctx_t *)session_p->encrypt.context;
 647                 /*
 648                  * CKM_DES_CBC and CKM_DES_ECB does not do any padding,
 649                  * so when the final is called, the remaining buffer
 650                  * should not contain any more data.
 651                  */
 652                 *pulLastEncryptedPartLen = 0;
 653                 if (soft_des_ctx->remain_len != 0) {
 654                         rv = CKR_DATA_LEN_RANGE;
 655                 } else {
 656                         if (pLastEncryptedPart == NULL)
 657                                 goto clean1;
 658                 }
 659 
 660                 /* Cleanup memory space. */
 661                 free(soft_des_ctx->des_cbc);
 662                 freezero(soft_des_ctx->key_sched,
 663                     soft_des_ctx->keysched_len);
 664 
 665                 break;
 666         }
 667         case CKM_AES_CBC_PAD:
 668         {
 669                 soft_aes_ctx_t *soft_aes_ctx;
 670 
 671                 soft_aes_ctx = (soft_aes_ctx_t *)session_p->encrypt.context;
 672                 /*
 673                  * For CKM_AES_CBC_PAD, compute output length with
 674                  * padding. If the remaining buffer has one block
 675                  * of data, then output length will be two blocksize of
 676                  * ciphertext. If the remaining buffer has less than
 677                  * one block of data, then output length will be
 678                  * one blocksize.
 679                  */
 680                 if (soft_aes_ctx->remain_len == AES_BLOCK_LEN)
 681                         out_len = 2 * AES_BLOCK_LEN;
 682                 else
 683                         out_len = AES_BLOCK_LEN;


 706                         out.cd_format = CRYPTO_DATA_RAW;
 707                         out.cd_offset = 0;
 708                         out.cd_length = out_len;
 709                         out.cd_raw.iov_base = (char *)pLastEncryptedPart;
 710                         out.cd_raw.iov_len = out_len;
 711 
 712                         /* Encrypt multiple blocks of data. */
 713                         rc = aes_encrypt_contiguous_blocks(
 714                             (aes_ctx_t *)soft_aes_ctx->aes_cbc,
 715                             (char *)pLastEncryptedPart, out_len, &out);
 716 
 717                         if (rc == 0) {
 718                                 *pulLastEncryptedPartLen = out_len;
 719                         } else {
 720                                 *pulLastEncryptedPartLen = 0;
 721                                 rv = CKR_FUNCTION_FAILED;
 722                         }
 723 
 724                         /* Cleanup memory space. */
 725                         free(soft_aes_ctx->aes_cbc);
 726                         freezero(soft_aes_ctx->key_sched,
 727                             soft_aes_ctx->keysched_len);

 728                 }
 729 
 730                 break;
 731         }
 732         case CKM_AES_CMAC:
 733         {
 734                 soft_aes_ctx_t *soft_aes_ctx;
 735                 soft_aes_ctx = (soft_aes_ctx_t *)session_p->encrypt.context;
 736 
 737                 if (pLastEncryptedPart == NULL) {
 738                         /*
 739                          * Application asks for the length of the output
 740                          * buffer to hold the ciphertext.
 741                          */
 742                         *pulLastEncryptedPartLen = AES_BLOCK_LEN;
 743                         goto clean1;
 744                 } else {
 745                         crypto_data_t out;
 746 
 747                         out.cd_format = CRYPTO_DATA_RAW;
 748                         out.cd_offset = 0;
 749                         out.cd_length = AES_BLOCK_LEN;
 750                         out.cd_raw.iov_base = (char *)pLastEncryptedPart;
 751                         out.cd_raw.iov_len = AES_BLOCK_LEN;
 752 
 753                         rc = cmac_mode_final(soft_aes_ctx->aes_cbc, &out,
 754                             aes_encrypt_block, aes_xor_block);
 755 
 756                         if (rc == 0) {
 757                                 *pulLastEncryptedPartLen = AES_BLOCK_LEN;
 758                         } else {
 759                                 *pulLastEncryptedPartLen = 0;
 760                                 rv = CKR_FUNCTION_FAILED;
 761                         }
 762 
 763                         /* Cleanup memory space. */
 764                         free(soft_aes_ctx->aes_cbc);
 765                         freezero(soft_aes_ctx->key_sched,
 766                             soft_aes_ctx->keysched_len);

 767                 }
 768 
 769                 break;
 770         }
 771         case CKM_AES_CBC:
 772         case CKM_AES_ECB:
 773         {
 774                 soft_aes_ctx_t *soft_aes_ctx;
 775 
 776                 soft_aes_ctx = (soft_aes_ctx_t *)session_p->encrypt.context;
 777                 /*
 778                  * CKM_AES_CBC and CKM_AES_ECB does not do any padding,
 779                  * so when the final is called, the remaining buffer
 780                  * should not contain any more data.
 781                  */
 782                 *pulLastEncryptedPartLen = 0;
 783                 if (soft_aes_ctx->remain_len != 0) {
 784                         rv = CKR_DATA_LEN_RANGE;
 785                 } else {
 786                         if (pLastEncryptedPart == NULL)
 787                                 goto clean1;
 788                 }
 789 
 790                 /* Cleanup memory space. */
 791                 free(soft_aes_ctx->aes_cbc);
 792                 freezero(soft_aes_ctx->key_sched,
 793                     soft_aes_ctx->keysched_len);
 794 
 795                 break;
 796         }
 797         case CKM_AES_CTR:
 798         {
 799                 crypto_data_t out;
 800                 soft_aes_ctx_t *soft_aes_ctx;
 801                 ctr_ctx_t *ctr_ctx;
 802                 size_t len;
 803 
 804                 soft_aes_ctx = (soft_aes_ctx_t *)session_p->encrypt.context;
 805                 ctr_ctx = soft_aes_ctx->aes_cbc;
 806                 len = ctr_ctx->ctr_remainder_len;
 807 
 808                 if (pLastEncryptedPart == NULL) {
 809                         *pulLastEncryptedPartLen = len;
 810                         goto clean1;
 811                 }
 812                 if (len > 0) {
 813                         out.cd_format = CRYPTO_DATA_RAW;
 814                         out.cd_offset = 0;
 815                         out.cd_length = len;
 816                         out.cd_raw.iov_base = (char *)pLastEncryptedPart;
 817                         out.cd_raw.iov_len = len;
 818 
 819                         rv = ctr_mode_final(ctr_ctx, &out, aes_encrypt_block);
 820                 }
 821                 if (rv == CRYPTO_BUFFER_TOO_SMALL) {
 822                         *pulLastEncryptedPartLen = len;
 823                         goto clean1;
 824                 }
 825 
 826                 /* Cleanup memory space. */
 827                 free(ctr_ctx);
 828                 freezero(soft_aes_ctx->key_sched,
 829                     soft_aes_ctx->keysched_len);
 830 
 831                 break;
 832         }
 833         case CKM_BLOWFISH_CBC:
 834         {
 835                 soft_blowfish_ctx_t *soft_blowfish_ctx;
 836 
 837                 soft_blowfish_ctx =
 838                     (soft_blowfish_ctx_t *)session_p->encrypt.context;
 839                 /*
 840                  * CKM_BLOWFISH_CBC does not do any padding, so when the
 841                  * final is called, the remaining buffer should not contain
 842                  * any more data
 843                  */
 844                 *pulLastEncryptedPartLen = 0;
 845                 if (soft_blowfish_ctx->remain_len != 0)
 846                         rv = CKR_DATA_LEN_RANGE;
 847                 else {
 848                         if (pLastEncryptedPart == NULL)
 849                                 goto clean1;
 850                 }
 851 
 852                 free(soft_blowfish_ctx->blowfish_cbc);
 853                 freezero(soft_blowfish_ctx->key_sched,
 854                     soft_blowfish_ctx->keysched_len);

 855                 break;
 856         }
 857 
 858         case CKM_RC4:
 859         {
 860                 ARCFour_key *key = (ARCFour_key *)session_p->encrypt.context;
 861                 /* Remaining data size is always zero for RC4. */
 862                 *pulLastEncryptedPartLen = 0;
 863                 if (pLastEncryptedPart == NULL)
 864                         goto clean1;
 865                 explicit_bzero(key, sizeof (*key));
 866                 break;
 867         }
 868         default:
 869                 /* PKCS11: The mechanism only supports single-part operation. */
 870                 rv = CKR_MECHANISM_INVALID;
 871                 break;
 872         }
 873 
 874         free(session_p->encrypt.context);
 875         session_p->encrypt.context = NULL;
 876 clean1:
 877         (void) pthread_mutex_unlock(&session_p->session_mutex);
 878 
 879         return (rv);
 880 }
 881 
 882 /*
 883  * This function frees the allocated active crypto context and the
 884  * lower level of allocated struct as needed.
 885  * This function is called by the 1st tier of encrypt/decrypt routines


 901 
 902         active_op = (encrypt) ? &(session_p->encrypt) : &(session_p->decrypt);
 903 
 904         switch (active_op->mech.mechanism) {
 905 
 906         case CKM_DES_CBC_PAD:
 907         case CKM_DES3_CBC_PAD:
 908         case CKM_DES_CBC:
 909         case CKM_DES_ECB:
 910         case CKM_DES3_CBC:
 911         case CKM_DES3_ECB:
 912         {
 913 
 914                 soft_des_ctx_t *soft_des_ctx =
 915                     (soft_des_ctx_t *)active_op->context;
 916                 des_ctx_t *des_ctx;
 917 
 918                 if (soft_des_ctx != NULL) {
 919                         des_ctx = (des_ctx_t *)soft_des_ctx->des_cbc;
 920                         if (des_ctx != NULL) {
 921                                 explicit_bzero(des_ctx->dc_keysched,
 922                                     des_ctx->dc_keysched_len);
 923                                 free(soft_des_ctx->des_cbc);
 924                         }
 925                         freezero(soft_des_ctx->key_sched,
 926                             soft_des_ctx->keysched_len);

 927                 }
 928                 break;
 929         }
 930 
 931         case CKM_AES_CBC_PAD:
 932         case CKM_AES_CBC:
 933         case CKM_AES_CMAC:
 934         case CKM_AES_ECB:
 935         {
 936                 soft_aes_ctx_t *soft_aes_ctx =
 937                     (soft_aes_ctx_t *)active_op->context;
 938                 aes_ctx_t *aes_ctx;
 939 
 940                 if (soft_aes_ctx != NULL) {
 941                         aes_ctx = (aes_ctx_t *)soft_aes_ctx->aes_cbc;
 942                         if (aes_ctx != NULL) {
 943                                 explicit_bzero(aes_ctx->ac_keysched,
 944                                     aes_ctx->ac_keysched_len);
 945                                 free(soft_aes_ctx->aes_cbc);
 946                         }
 947                         freezero(soft_aes_ctx->key_sched,
 948                             soft_aes_ctx->keysched_len);

 949                 }
 950                 break;
 951         }
 952 
 953         case CKM_BLOWFISH_CBC:
 954         {
 955                 soft_blowfish_ctx_t *soft_blowfish_ctx =
 956                     (soft_blowfish_ctx_t *)active_op->context;
 957                 blowfish_ctx_t *blowfish_ctx;
 958 
 959                 if (soft_blowfish_ctx != NULL) {
 960                         blowfish_ctx =
 961                             (blowfish_ctx_t *)soft_blowfish_ctx->blowfish_cbc;
 962                         if (blowfish_ctx != NULL) {
 963                                 explicit_bzero(blowfish_ctx->bc_keysched,
 964                                     blowfish_ctx->bc_keysched_len);
 965                                 free(soft_blowfish_ctx->blowfish_cbc);
 966                         }
 967 
 968                         freezero(soft_blowfish_ctx->key_sched,
 969                             soft_blowfish_ctx->keysched_len);

 970                 }
 971                 break;
 972         }
 973 
 974         case CKM_RC4:
 975         {
 976                 ARCFour_key *key = (ARCFour_key *)active_op->context;
 977 
 978                 if (key != NULL)
 979                         explicit_bzero(key, sizeof (*key));
 980                 break;
 981         }
 982 
 983         case CKM_RSA_X_509:
 984         case CKM_RSA_PKCS:
 985         {
 986                 soft_rsa_ctx_t *rsa_ctx =
 987                     (soft_rsa_ctx_t *)active_op->context;
 988 
 989                 if (rsa_ctx != NULL)
 990                         if (rsa_ctx->key != NULL) {
 991                                 soft_cleanup_object(rsa_ctx->key);
 992                                 free(rsa_ctx->key);
 993                         }
 994 
 995                 break;
 996         }
 997 
 998         } /* switch */
 999