1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License, Version 1.0 only 6 * (the "License"). You may not use this file except in compliance 7 * with the License. 8 * 9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 10 * or http://www.opensolaris.org/os/licensing. 11 * See the License for the specific language governing permissions 12 * and limitations under the License. 13 * 14 * When distributing Covered Code, include this CDDL HEADER in each 15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 16 * If applicable, add the following below this CDDL HEADER, with the 17 * fields enclosed by brackets "[]" replaced with your own identifying 18 * information: Portions Copyright [yyyy] [name of copyright owner] 19 * 20 * CDDL HEADER END 21 */ 22 /* 23 * Copyright 2005 Sun Microsystems, Inc. All rights reserved. 24 * Use is subject to license terms. 25 */ 26 27 #pragma ident "%Z%%M% %I% %E% SMI" 28 29 #include <stdlib.h> 30 #include <strings.h> 31 #include <sys/types.h> 32 #include <security/cryptoki.h> 33 #include "softObject.h" 34 #include "softOps.h" 35 #include "softSession.h" 36 #include "softMAC.h" 37 #include "softRSA.h" 38 #include "softDSA.h" 39 #include "softCrypt.h" 40 41 /* 42 * soft_sign_init() 43 * 44 * Arguments: 45 * session_p: pointer to soft_session_t struct 46 * pMechanism: pointer to CK_MECHANISM struct provided by application 47 * key_p: pointer to key soft_object_t struct 48 * 49 * Description: 50 * called by C_SignInit(). This function calls the corresponding 51 * sign init routine based on the mechanism. 52 * 53 */ 54 CK_RV 55 soft_sign_init(soft_session_t *session_p, CK_MECHANISM_PTR pMechanism, 56 soft_object_t *key_p) 57 { 58 59 switch (pMechanism->mechanism) { 60 61 case CKM_SSL3_MD5_MAC: 62 case CKM_SSL3_SHA1_MAC: 63 case CKM_MD5_HMAC_GENERAL: 64 case CKM_MD5_HMAC: 65 case CKM_SHA_1_HMAC_GENERAL: 66 case CKM_SHA_1_HMAC: 67 case CKM_SHA256_HMAC_GENERAL: 68 case CKM_SHA256_HMAC: 69 case CKM_SHA384_HMAC_GENERAL: 70 case CKM_SHA384_HMAC: 71 case CKM_SHA512_HMAC_GENERAL: 72 case CKM_SHA512_HMAC: 73 74 return (soft_hmac_sign_verify_init_common(session_p, 75 pMechanism, key_p, B_TRUE)); 76 77 case CKM_RSA_X_509: 78 case CKM_RSA_PKCS: 79 case CKM_MD5_RSA_PKCS: 80 case CKM_SHA1_RSA_PKCS: 81 case CKM_SHA256_RSA_PKCS: 82 case CKM_SHA384_RSA_PKCS: 83 case CKM_SHA512_RSA_PKCS: 84 85 return (soft_rsa_sign_verify_init_common(session_p, pMechanism, 86 key_p, B_TRUE)); 87 88 case CKM_DSA: 89 case CKM_DSA_SHA1: 90 91 return (soft_dsa_sign_verify_init_common(session_p, pMechanism, 92 key_p, B_TRUE)); 93 94 case CKM_DES_MAC_GENERAL: 95 case CKM_DES_MAC: 96 97 return (soft_des_sign_verify_init_common(session_p, pMechanism, 98 key_p, B_TRUE)); 99 100 default: 101 return (CKR_MECHANISM_INVALID); 102 } 103 104 } 105 106 107 /* 108 * soft_sign() 109 * 110 * Arguments: 111 * session_p: pointer to soft_session_t struct 112 * pData: pointer to the input data to be signed 113 * ulDataLen: length of the input data 114 * pSignature: pointer to the signature after signing 115 * pulSignatureLen: pointer to the length of the signature 116 * 117 * Description: 118 * called by C_Sign(). This function calls the corresponding 119 * sign routine based on the mechanism. 120 * 121 */ 122 CK_RV 123 soft_sign(soft_session_t *session_p, CK_BYTE_PTR pData, 124 CK_ULONG ulDataLen, CK_BYTE_PTR pSignature, 125 CK_ULONG_PTR pulSignatureLen) 126 { 127 128 CK_MECHANISM_TYPE mechanism = session_p->sign.mech.mechanism; 129 CK_RV rv = CKR_OK; 130 131 switch (mechanism) { 132 133 case CKM_SSL3_MD5_MAC: 134 case CKM_SSL3_SHA1_MAC: 135 case CKM_MD5_HMAC_GENERAL: 136 case CKM_MD5_HMAC: 137 case CKM_SHA_1_HMAC_GENERAL: 138 case CKM_SHA_1_HMAC: 139 case CKM_SHA256_HMAC_GENERAL: 140 case CKM_SHA256_HMAC: 141 case CKM_SHA384_HMAC_GENERAL: 142 case CKM_SHA384_HMAC: 143 case CKM_SHA512_HMAC_GENERAL: 144 case CKM_SHA512_HMAC: 145 { 146 CK_BYTE hmac[SHA512_DIGEST_LENGTH]; /* use the maximum size */ 147 148 if (pSignature != NULL) { 149 /* Pass local buffer to avoid overflow. */ 150 rv = soft_hmac_sign_verify_common(session_p, pData, 151 ulDataLen, hmac, pulSignatureLen, B_TRUE); 152 } else { 153 /* Pass original pSignature, let callee to handle it. */ 154 rv = soft_hmac_sign_verify_common(session_p, pData, 155 ulDataLen, pSignature, pulSignatureLen, B_TRUE); 156 } 157 158 if ((rv == CKR_OK) && (pSignature != NULL)) 159 (void) memcpy(pSignature, hmac, *pulSignatureLen); 160 161 return (rv); 162 } 163 case CKM_DES_MAC_GENERAL: 164 case CKM_DES_MAC: 165 { 166 CK_BYTE signature[DES_BLOCK_LEN]; /* use the maximum size */ 167 168 if (pSignature != NULL) { 169 /* Pass local buffer to avoid overflow. */ 170 rv = soft_des_sign_verify_common(session_p, pData, 171 ulDataLen, signature, pulSignatureLen, B_TRUE, 172 B_FALSE); 173 } else { 174 /* Pass NULL, let callee to handle it. */ 175 rv = soft_des_sign_verify_common(session_p, pData, 176 ulDataLen, NULL, pulSignatureLen, B_TRUE, 177 B_FALSE); 178 } 179 180 if ((rv == CKR_OK) && (pSignature != NULL)) 181 (void) memcpy(pSignature, signature, *pulSignatureLen); 182 183 return (rv); 184 } 185 case CKM_RSA_X_509: 186 case CKM_RSA_PKCS: 187 188 return (soft_rsa_sign_common(session_p, pData, ulDataLen, 189 pSignature, pulSignatureLen, mechanism)); 190 191 case CKM_MD5_RSA_PKCS: 192 case CKM_SHA1_RSA_PKCS: 193 case CKM_SHA256_RSA_PKCS: 194 case CKM_SHA384_RSA_PKCS: 195 case CKM_SHA512_RSA_PKCS: 196 197 return (soft_rsa_digest_sign_common(session_p, pData, ulDataLen, 198 pSignature, pulSignatureLen, mechanism, B_FALSE)); 199 200 case CKM_DSA: 201 202 return (soft_dsa_sign(session_p, pData, ulDataLen, 203 pSignature, pulSignatureLen)); 204 205 case CKM_DSA_SHA1: 206 207 return (soft_dsa_digest_sign_common(session_p, pData, ulDataLen, 208 pSignature, pulSignatureLen, B_FALSE)); 209 210 default: 211 return (CKR_MECHANISM_INVALID); 212 } 213 } 214 215 216 /* 217 * soft_sign_update() 218 * 219 * Arguments: 220 * session_p: pointer to soft_session_t struct 221 * pPart: pointer to the input data to be signed 222 * ulPartLen: length of the input data 223 * 224 * Description: 225 * called by C_SignUpdate(). This function calls the corresponding 226 * sign update routine based on the mechanism. 227 * 228 */ 229 CK_RV 230 soft_sign_update(soft_session_t *session_p, CK_BYTE_PTR pPart, 231 CK_ULONG ulPartLen) 232 { 233 CK_MECHANISM_TYPE mechanism = session_p->sign.mech.mechanism; 234 235 switch (mechanism) { 236 237 case CKM_SSL3_MD5_MAC: 238 case CKM_SSL3_SHA1_MAC: 239 case CKM_MD5_HMAC_GENERAL: 240 case CKM_MD5_HMAC: 241 case CKM_SHA_1_HMAC_GENERAL: 242 case CKM_SHA_1_HMAC: 243 case CKM_SHA256_HMAC_GENERAL: 244 case CKM_SHA256_HMAC: 245 case CKM_SHA384_HMAC_GENERAL: 246 case CKM_SHA384_HMAC: 247 case CKM_SHA512_HMAC_GENERAL: 248 case CKM_SHA512_HMAC: 249 250 return (soft_hmac_sign_verify_update(session_p, pPart, 251 ulPartLen, B_TRUE)); 252 253 case CKM_DES_MAC_GENERAL: 254 case CKM_DES_MAC: 255 256 return (soft_des_mac_sign_verify_update(session_p, pPart, 257 ulPartLen)); 258 259 case CKM_MD5_RSA_PKCS: 260 case CKM_SHA1_RSA_PKCS: 261 case CKM_SHA256_RSA_PKCS: 262 case CKM_SHA384_RSA_PKCS: 263 case CKM_SHA512_RSA_PKCS: 264 /* 265 * The MD5/SHA1 digest value is accumulated in the context 266 * of the multiple-part digesting operation. In the final 267 * operation, the digest is encoded and then perform RSA 268 * signing. 269 */ 270 case CKM_DSA_SHA1: 271 272 return (soft_digest_update(session_p, pPart, ulPartLen)); 273 274 default: 275 /* PKCS11: The mechanism only supports single-part operation. */ 276 return (CKR_MECHANISM_INVALID); 277 } 278 } 279 280 281 /* 282 * soft_sign_final() 283 * 284 * Arguments: 285 * session_p: pointer to soft_session_t struct 286 * pSignature: pointer to the signature after signing 287 * pulSignatureLen: pointer to the length of the signature 288 * 289 * Description: 290 * called by C_SignFinal(). This function calls the corresponding 291 * sign final routine based on the mechanism. 292 * 293 */ 294 CK_RV 295 soft_sign_final(soft_session_t *session_p, CK_BYTE_PTR pSignature, 296 CK_ULONG_PTR pulSignatureLen) 297 { 298 299 CK_MECHANISM_TYPE mechanism = session_p->sign.mech.mechanism; 300 CK_RV rv = CKR_OK; 301 302 switch (mechanism) { 303 304 case CKM_SSL3_MD5_MAC: 305 case CKM_SSL3_SHA1_MAC: 306 case CKM_MD5_HMAC_GENERAL: 307 case CKM_MD5_HMAC: 308 case CKM_SHA_1_HMAC_GENERAL: 309 case CKM_SHA_1_HMAC: 310 case CKM_SHA256_HMAC_GENERAL: 311 case CKM_SHA256_HMAC: 312 case CKM_SHA384_HMAC_GENERAL: 313 case CKM_SHA384_HMAC: 314 case CKM_SHA512_HMAC_GENERAL: 315 case CKM_SHA512_HMAC: 316 { 317 CK_BYTE hmac[SHA512_DIGEST_LENGTH]; /* use the maximum size */ 318 319 if (pSignature != NULL) { 320 /* Pass local buffer to avoid overflow */ 321 rv = soft_hmac_sign_verify_common(session_p, NULL, 322 0, hmac, pulSignatureLen, B_TRUE); 323 } else { 324 /* Pass original pSignature, let callee to handle it. */ 325 rv = soft_hmac_sign_verify_common(session_p, NULL, 326 0, pSignature, pulSignatureLen, B_TRUE); 327 } 328 329 if ((rv == CKR_OK) && (pSignature != NULL)) 330 (void) memcpy(pSignature, hmac, *pulSignatureLen); 331 332 return (rv); 333 } 334 case CKM_DES_MAC_GENERAL: 335 case CKM_DES_MAC: 336 { 337 CK_BYTE signature[DES_BLOCK_LEN]; /* use the maximum size */ 338 339 if (pSignature != NULL) { 340 /* Pass local buffer to avoid overflow. */ 341 rv = soft_des_sign_verify_common(session_p, NULL, 0, 342 signature, pulSignatureLen, B_TRUE, B_TRUE); 343 } else { 344 /* Pass NULL, let callee to handle it. */ 345 rv = soft_des_sign_verify_common(session_p, NULL, 0, 346 NULL, pulSignatureLen, B_TRUE, B_TRUE); 347 } 348 349 if ((rv == CKR_OK) && (pSignature != NULL)) 350 (void) memcpy(pSignature, signature, *pulSignatureLen); 351 352 return (rv); 353 } 354 case CKM_MD5_RSA_PKCS: 355 case CKM_SHA1_RSA_PKCS: 356 case CKM_SHA256_RSA_PKCS: 357 case CKM_SHA384_RSA_PKCS: 358 case CKM_SHA512_RSA_PKCS: 359 360 return (soft_rsa_digest_sign_common(session_p, NULL, 0, 361 pSignature, pulSignatureLen, mechanism, B_TRUE)); 362 363 case CKM_DSA_SHA1: 364 365 return (soft_dsa_digest_sign_common(session_p, NULL, 0, 366 pSignature, pulSignatureLen, B_TRUE)); 367 368 default: 369 /* PKCS11: The mechanism only supports single-part operation. */ 370 return (CKR_MECHANISM_INVALID); 371 } 372 } 373 374 375 CK_RV 376 soft_sign_recover_init(soft_session_t *session_p, CK_MECHANISM_PTR pMechanism, 377 soft_object_t *key_p) 378 { 379 380 switch (pMechanism->mechanism) { 381 382 case CKM_RSA_X_509: 383 case CKM_RSA_PKCS: 384 385 return (soft_rsa_sign_verify_init_common(session_p, pMechanism, 386 key_p, B_TRUE)); 387 388 default: 389 return (CKR_MECHANISM_INVALID); 390 } 391 } 392 393 394 CK_RV 395 soft_sign_recover(soft_session_t *session_p, CK_BYTE_PTR pData, 396 CK_ULONG ulDataLen, CK_BYTE_PTR pSignature, 397 CK_ULONG_PTR pulSignatureLen) 398 { 399 400 CK_MECHANISM_TYPE mechanism = session_p->sign.mech.mechanism; 401 402 switch (mechanism) { 403 404 case CKM_RSA_X_509: 405 case CKM_RSA_PKCS: 406 407 return (soft_rsa_sign_common(session_p, pData, ulDataLen, 408 pSignature, pulSignatureLen, mechanism)); 409 410 default: 411 return (CKR_MECHANISM_INVALID); 412 } 413 } 414 415 /* 416 * This function frees the allocated active crypto context. 417 * It is only called by the first tier of sign/verify routines 418 * and the caller of this function may or may not hold the session mutex. 419 */ 420 void 421 soft_sign_verify_cleanup(soft_session_t *session_p, boolean_t sign, 422 boolean_t lock_held) 423 { 424 425 crypto_active_op_t *active_op; 426 boolean_t lock_true = B_TRUE; 427 428 if (!lock_held) 429 (void) pthread_mutex_lock(&session_p->session_mutex); 430 431 active_op = (sign) ? &(session_p->sign) : &(session_p->verify); 432 433 switch (active_op->mech.mechanism) { 434 435 case CKM_MD5_RSA_PKCS: 436 case CKM_SHA1_RSA_PKCS: 437 case CKM_SHA256_RSA_PKCS: 438 case CKM_SHA384_RSA_PKCS: 439 case CKM_SHA512_RSA_PKCS: 440 case CKM_DSA_SHA1: 441 if (session_p->digest.context != NULL) { 442 free(session_p->digest.context); 443 session_p->digest.context = NULL; 444 session_p->digest.flags = 0; 445 } 446 break; 447 448 case CKM_RSA_PKCS: 449 case CKM_RSA_X_509: 450 case CKM_DSA: 451 break; 452 453 case CKM_SSL3_MD5_MAC: 454 case CKM_SSL3_SHA1_MAC: 455 case CKM_MD5_HMAC_GENERAL: 456 case CKM_MD5_HMAC: 457 case CKM_SHA_1_HMAC_GENERAL: 458 case CKM_SHA_1_HMAC: 459 case CKM_SHA256_HMAC_GENERAL: 460 case CKM_SHA256_HMAC: 461 case CKM_SHA384_HMAC_GENERAL: 462 case CKM_SHA384_HMAC: 463 case CKM_SHA512_HMAC_GENERAL: 464 case CKM_SHA512_HMAC: 465 if (active_op->context != NULL) 466 bzero(active_op->context, sizeof (soft_hmac_ctx_t)); 467 break; 468 case CKM_DES_MAC_GENERAL: 469 case CKM_DES_MAC: 470 if (session_p->encrypt.context != NULL) { 471 free(session_p->encrypt.context); 472 session_p->encrypt.context = NULL; 473 session_p->encrypt.flags = 0; 474 } 475 if (active_op->context != NULL) 476 bzero(active_op->context, sizeof (soft_des_ctx_t)); 477 break; 478 479 } 480 481 if (active_op->context != NULL) { 482 free(active_op->context); 483 active_op->context = NULL; 484 } 485 486 active_op->flags = 0; 487 488 if (!lock_held) 489 SES_REFRELE(session_p, lock_true); 490 } 491