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 (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 * Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved. 23 */ 24 25 #include <sys/errno.h> 26 #include <sys/types.h> 27 #include <sys/kmem.h> 28 #include <sys/sysmacros.h> 29 #include <sys/crypto/common.h> 30 #include <sys/crypto/impl.h> 31 #include <sys/crypto/api.h> 32 #include <sys/crypto/spi.h> 33 #include <sys/crypto/sched_impl.h> 34 35 #define CRYPTO_OPS_OFFSET(f) offsetof(crypto_ops_t, co_##f) 36 #define CRYPTO_CIPHER_MAC_OFFSET(f) offsetof(crypto_dual_cipher_mac_ops_t, f) 37 38 static int crypto_mac_decrypt_common(crypto_mechanism_t *, 39 crypto_mechanism_t *, crypto_dual_data_t *, crypto_key_t *, crypto_key_t *, 40 crypto_ctx_template_t, crypto_ctx_template_t, crypto_data_t *, 41 crypto_data_t *, crypto_call_req_t *, boolean_t); 42 43 static int crypto_mac_decrypt_common_prov(crypto_provider_t provider, 44 crypto_session_id_t sid, crypto_mechanism_t *, crypto_mechanism_t *, 45 crypto_dual_data_t *, crypto_key_t *, crypto_key_t *, 46 crypto_ctx_template_t, crypto_ctx_template_t, crypto_data_t *, 47 crypto_data_t *, crypto_call_req_t *, boolean_t); 48 49 int 50 crypto_encrypt_mac_prov(crypto_provider_t provider, crypto_session_id_t sid, 51 crypto_mechanism_t *encr_mech, crypto_mechanism_t *mac_mech, 52 crypto_data_t *pt, crypto_key_t *encr_key, crypto_key_t *mac_key, 53 crypto_ctx_template_t encr_tmpl, crypto_ctx_template_t mac_tmpl, 54 crypto_dual_data_t *ct, crypto_data_t *mac, crypto_call_req_t *crq) 55 { 56 /* 57 * First try to find a provider for the encryption mechanism, that 58 * is also capable of the MAC mechanism. 59 */ 60 int rv; 61 kcf_mech_entry_t *me; 62 kcf_provider_desc_t *pd = provider; 63 kcf_provider_desc_t *real_provider = pd; 64 kcf_ctx_template_t *ctx_encr_tmpl, *ctx_mac_tmpl; 65 kcf_req_params_t params; 66 kcf_encrypt_mac_ops_params_t *cmops; 67 crypto_spi_ctx_template_t spi_encr_tmpl = NULL, spi_mac_tmpl = NULL; 68 69 ASSERT(KCF_PROV_REFHELD(pd)); 70 71 if (pd->pd_prov_type == CRYPTO_LOGICAL_PROVIDER) { 72 rv = kcf_get_hardware_provider(encr_mech->cm_type, encr_key, 73 mac_mech->cm_type, mac_key, pd, &real_provider, 74 CRYPTO_FG_ENCRYPT_MAC_ATOMIC); 75 76 if (rv != CRYPTO_SUCCESS) 77 return (rv); 78 } 79 80 /* 81 * For SW providers, check the validity of the context template 82 * It is very rare that the generation number mis-matches, so 83 * is acceptable to fail here, and let the consumer recover by 84 * freeing this tmpl and create a new one for the key and new SW 85 * provider 86 * Warning! will need to change when multiple software providers 87 * per mechanism are supported. 88 */ 89 90 if (real_provider->pd_prov_type == CRYPTO_SW_PROVIDER) { 91 if (encr_tmpl != NULL) { 92 if (kcf_get_mech_entry(encr_mech->cm_type, &me) != 93 KCF_SUCCESS) { 94 rv = CRYPTO_MECHANISM_INVALID; 95 goto out; 96 } 97 ctx_encr_tmpl = (kcf_ctx_template_t *)encr_tmpl; 98 if (ctx_encr_tmpl->ct_generation != me->me_gen_swprov) { 99 rv = CRYPTO_OLD_CTX_TEMPLATE; 100 goto out; 101 } 102 spi_encr_tmpl = ctx_encr_tmpl->ct_prov_tmpl; 103 } 104 105 if (mac_tmpl != NULL) { 106 if (kcf_get_mech_entry(mac_mech->cm_type, &me) != 107 KCF_SUCCESS) { 108 rv = CRYPTO_MECHANISM_INVALID; 109 goto out; 110 } 111 ctx_mac_tmpl = (kcf_ctx_template_t *)mac_tmpl; 112 if (ctx_mac_tmpl->ct_generation != me->me_gen_swprov) { 113 rv = CRYPTO_OLD_CTX_TEMPLATE; 114 goto out; 115 } 116 spi_mac_tmpl = ctx_mac_tmpl->ct_prov_tmpl; 117 } 118 } 119 120 /* The fast path for SW providers. */ 121 if (CHECK_FASTPATH(crq, real_provider)) { 122 crypto_mechanism_t lencr_mech; 123 crypto_mechanism_t lmac_mech; 124 125 /* careful! structs assignments */ 126 lencr_mech = *encr_mech; 127 KCF_SET_PROVIDER_MECHNUM(encr_mech->cm_type, real_provider, 128 &lencr_mech); 129 130 lmac_mech = *mac_mech; 131 KCF_SET_PROVIDER_MECHNUM(mac_mech->cm_type, real_provider, 132 &lmac_mech); 133 134 rv = KCF_PROV_ENCRYPT_MAC_ATOMIC(real_provider, sid, 135 &lencr_mech, encr_key, &lmac_mech, mac_key, pt, ct, 136 mac, spi_encr_tmpl, spi_mac_tmpl, KCF_SWFP_RHNDL(crq)); 137 138 KCF_PROV_INCRSTATS(pd, rv); 139 } else { 140 KCF_WRAP_ENCRYPT_MAC_OPS_PARAMS(¶ms, KCF_OP_ATOMIC, 141 sid, encr_key, mac_key, pt, ct, mac, spi_encr_tmpl, 142 spi_mac_tmpl); 143 144 cmops = &(params.rp_u.encrypt_mac_params); 145 146 /* careful! structs assignments */ 147 cmops->em_encr_mech = *encr_mech; 148 KCF_SET_PROVIDER_MECHNUM(encr_mech->cm_type, real_provider, 149 &cmops->em_encr_mech); 150 cmops->em_framework_encr_mechtype = encr_mech->cm_type; 151 152 cmops->em_mac_mech = *mac_mech; 153 KCF_SET_PROVIDER_MECHNUM(mac_mech->cm_type, real_provider, 154 &cmops->em_mac_mech); 155 cmops->em_framework_mac_mechtype = mac_mech->cm_type; 156 157 rv = kcf_submit_request(real_provider, NULL, crq, ¶ms, 158 B_FALSE); 159 } 160 161 out: 162 if (pd->pd_prov_type == CRYPTO_LOGICAL_PROVIDER) 163 KCF_PROV_REFRELE(real_provider); 164 return (rv); 165 } 166 167 /* 168 * Performs a dual encrypt/mac atomic operation. The provider and session 169 * to use are determined by the KCF dispatcher. 170 */ 171 int 172 crypto_encrypt_mac(crypto_mechanism_t *encr_mech, 173 crypto_mechanism_t *mac_mech, crypto_data_t *pt, 174 crypto_key_t *encr_key, crypto_key_t *mac_key, 175 crypto_ctx_template_t encr_tmpl, crypto_ctx_template_t mac_tmpl, 176 crypto_dual_data_t *ct, crypto_data_t *mac, crypto_call_req_t *crq) 177 { 178 /* 179 * First try to find a provider for the encryption mechanism, that 180 * is also capable of the MAC mechanism. 181 */ 182 int error; 183 kcf_mech_entry_t *me; 184 kcf_provider_desc_t *pd; 185 kcf_ctx_template_t *ctx_encr_tmpl, *ctx_mac_tmpl; 186 kcf_req_params_t params; 187 kcf_encrypt_mac_ops_params_t *cmops; 188 crypto_spi_ctx_template_t spi_encr_tmpl = NULL, spi_mac_tmpl = NULL; 189 crypto_mech_type_t prov_encr_mechid, prov_mac_mechid; 190 kcf_prov_tried_t *list = NULL; 191 boolean_t encr_tmpl_checked = B_FALSE; 192 boolean_t mac_tmpl_checked = B_FALSE; 193 kcf_dual_req_t *next_req = NULL; 194 195 retry: 196 /* pd is returned held on success */ 197 pd = kcf_get_dual_provider(encr_mech, encr_key, mac_mech, mac_key, 198 &me, &prov_encr_mechid, 199 &prov_mac_mechid, &error, list, 200 CRYPTO_FG_ENCRYPT_ATOMIC | CRYPTO_FG_ENCRYPT_MAC_ATOMIC, 201 CRYPTO_FG_MAC_ATOMIC | CRYPTO_FG_ENCRYPT_MAC_ATOMIC, 202 ct->dd_len1); 203 if (pd == NULL) { 204 if (list != NULL) 205 kcf_free_triedlist(list); 206 if (next_req != NULL) 207 kmem_free(next_req, sizeof (kcf_dual_req_t)); 208 return (error); 209 } 210 211 /* 212 * For SW providers, check the validity of the context template 213 * It is very rare that the generation number mis-matches, so 214 * is acceptable to fail here, and let the consumer recover by 215 * freeing this tmpl and create a new one for the key and new SW 216 * provider 217 * Warning! will need to change when multiple software providers 218 * per mechanism are supported. 219 */ 220 221 if ((!encr_tmpl_checked) && (pd->pd_prov_type == CRYPTO_SW_PROVIDER)) { 222 if (encr_tmpl != NULL) { 223 ctx_encr_tmpl = (kcf_ctx_template_t *)encr_tmpl; 224 if (ctx_encr_tmpl->ct_generation != me->me_gen_swprov) { 225 226 if (next_req != NULL) 227 kmem_free(next_req, 228 sizeof (kcf_dual_req_t)); 229 if (list != NULL) 230 kcf_free_triedlist(list); 231 232 KCF_PROV_REFRELE(pd); 233 /* Which one is the the old one ? */ 234 return (CRYPTO_OLD_CTX_TEMPLATE); 235 } 236 spi_encr_tmpl = ctx_encr_tmpl->ct_prov_tmpl; 237 } 238 encr_tmpl_checked = B_TRUE; 239 } 240 241 if (prov_mac_mechid == CRYPTO_MECH_INVALID) { 242 crypto_call_req_t encr_req; 243 244 /* Need to emulate with 2 internal calls */ 245 /* Allocate and initialize the MAC req for the callback */ 246 247 if (crq != NULL) { 248 if (next_req == NULL) { 249 next_req = kcf_alloc_req(crq); 250 251 if (next_req == NULL) { 252 KCF_PROV_REFRELE(pd); 253 if (list != NULL) 254 kcf_free_triedlist(list); 255 return (CRYPTO_HOST_MEMORY); 256 } 257 /* 258 * Careful! we're wrapping-in mac_tmpl instead 259 * of an spi_mac_tmpl. The callback routine will 260 * have to validate mac_tmpl, and use the 261 * mac_ctx_tmpl, once it picks a MAC provider. 262 */ 263 KCF_WRAP_MAC_OPS_PARAMS(&(next_req->kr_params), 264 KCF_OP_ATOMIC, 0, mac_mech, mac_key, 265 (crypto_data_t *)ct, mac, mac_tmpl); 266 } 267 268 encr_req.cr_flag = crq->cr_flag; 269 encr_req.cr_callback_func = kcf_next_req; 270 encr_req.cr_callback_arg = next_req; 271 } 272 273 if (pt == NULL) { 274 KCF_WRAP_ENCRYPT_OPS_PARAMS(¶ms, KCF_OP_ATOMIC, 275 pd->pd_sid, encr_mech, encr_key, 276 (crypto_data_t *)ct, NULL, spi_encr_tmpl); 277 } else { 278 KCF_WRAP_ENCRYPT_OPS_PARAMS(¶ms, KCF_OP_ATOMIC, 279 pd->pd_sid, encr_mech, encr_key, pt, 280 (crypto_data_t *)ct, spi_encr_tmpl); 281 } 282 283 error = kcf_submit_request(pd, NULL, (crq == NULL) ? NULL : 284 &encr_req, ¶ms, B_TRUE); 285 286 switch (error) { 287 case CRYPTO_SUCCESS: { 288 off_t saveoffset; 289 size_t savelen; 290 291 /* 292 * The encryption step is done. Reuse the encr_req 293 * for submitting the MAC step. 294 */ 295 if (next_req == NULL) { 296 saveoffset = ct->dd_offset1; 297 savelen = ct->dd_len1; 298 } else { 299 saveoffset = next_req->kr_saveoffset = 300 ct->dd_offset1; 301 savelen = next_req->kr_savelen = ct->dd_len1; 302 encr_req.cr_callback_func = kcf_last_req; 303 } 304 305 ct->dd_offset1 = ct->dd_offset2; 306 ct->dd_len1 = ct->dd_len2; 307 308 error = crypto_mac(mac_mech, (crypto_data_t *)ct, 309 mac_key, mac_tmpl, mac, (crq == NULL) ? NULL : 310 &encr_req); 311 312 if (error != CRYPTO_QUEUED) { 313 ct->dd_offset1 = saveoffset; 314 ct->dd_len1 = savelen; 315 } 316 break; 317 } 318 319 case CRYPTO_QUEUED: 320 if ((crq != NULL) && 321 !(crq->cr_flag & CRYPTO_SKIP_REQID)) 322 crq->cr_reqid = encr_req.cr_reqid; 323 break; 324 325 default: 326 327 /* Add pd to the linked list of providers tried. */ 328 if (IS_RECOVERABLE(error)) { 329 if (kcf_insert_triedlist(&list, pd, 330 KCF_KMFLAG(crq)) != NULL) 331 goto retry; 332 } 333 } 334 if (error != CRYPTO_QUEUED && next_req != NULL) 335 kmem_free(next_req, sizeof (kcf_dual_req_t)); 336 if (list != NULL) 337 kcf_free_triedlist(list); 338 KCF_PROV_REFRELE(pd); 339 return (error); 340 } 341 if ((!mac_tmpl_checked) && (pd->pd_prov_type == CRYPTO_SW_PROVIDER)) { 342 if ((mac_tmpl != NULL) && 343 (prov_mac_mechid != CRYPTO_MECH_INVALID)) { 344 ctx_mac_tmpl = (kcf_ctx_template_t *)mac_tmpl; 345 if (ctx_mac_tmpl->ct_generation != me->me_gen_swprov) { 346 347 if (next_req != NULL) 348 kmem_free(next_req, 349 sizeof (kcf_dual_req_t)); 350 if (list != NULL) 351 kcf_free_triedlist(list); 352 353 KCF_PROV_REFRELE(pd); 354 /* Which one is the the old one ? */ 355 return (CRYPTO_OLD_CTX_TEMPLATE); 356 } 357 spi_mac_tmpl = ctx_mac_tmpl->ct_prov_tmpl; 358 } 359 mac_tmpl_checked = B_TRUE; 360 } 361 362 /* The fast path for SW providers. */ 363 if (CHECK_FASTPATH(crq, pd)) { 364 crypto_mechanism_t lencr_mech; 365 crypto_mechanism_t lmac_mech; 366 367 /* careful! structs assignments */ 368 lencr_mech = *encr_mech; 369 lencr_mech.cm_type = prov_encr_mechid; 370 lmac_mech = *mac_mech; 371 lmac_mech.cm_type = prov_mac_mechid; 372 373 error = KCF_PROV_ENCRYPT_MAC_ATOMIC(pd, pd->pd_sid, 374 &lencr_mech, encr_key, &lmac_mech, mac_key, pt, ct, 375 mac, spi_encr_tmpl, spi_mac_tmpl, KCF_SWFP_RHNDL(crq)); 376 377 KCF_PROV_INCRSTATS(pd, error); 378 } else { 379 KCF_WRAP_ENCRYPT_MAC_OPS_PARAMS(¶ms, KCF_OP_ATOMIC, 380 pd->pd_sid, encr_key, mac_key, pt, ct, mac, spi_encr_tmpl, 381 spi_mac_tmpl); 382 383 cmops = &(params.rp_u.encrypt_mac_params); 384 385 /* careful! structs assignments */ 386 cmops->em_encr_mech = *encr_mech; 387 cmops->em_encr_mech.cm_type = prov_encr_mechid; 388 cmops->em_framework_encr_mechtype = encr_mech->cm_type; 389 cmops->em_mac_mech = *mac_mech; 390 cmops->em_mac_mech.cm_type = prov_mac_mechid; 391 cmops->em_framework_mac_mechtype = mac_mech->cm_type; 392 393 error = kcf_submit_request(pd, NULL, crq, ¶ms, B_FALSE); 394 } 395 396 if (error != CRYPTO_SUCCESS && error != CRYPTO_QUEUED && 397 IS_RECOVERABLE(error)) { 398 /* Add pd to the linked list of providers tried. */ 399 if (kcf_insert_triedlist(&list, pd, KCF_KMFLAG(crq)) != NULL) 400 goto retry; 401 } 402 403 if (next_req != NULL) 404 kmem_free(next_req, sizeof (kcf_dual_req_t)); 405 406 if (list != NULL) 407 kcf_free_triedlist(list); 408 409 KCF_PROV_REFRELE(pd); 410 return (error); 411 } 412 413 int 414 crypto_encrypt_mac_init_prov(crypto_provider_t provider, 415 crypto_session_id_t sid, crypto_mechanism_t *encr_mech, 416 crypto_mechanism_t *mac_mech, crypto_key_t *encr_key, 417 crypto_key_t *mac_key, crypto_ctx_template_t encr_tmpl, 418 crypto_ctx_template_t mac_tmpl, crypto_context_t *ctxp, 419 crypto_call_req_t *cr) 420 { 421 /* 422 * First try to find a provider for the encryption mechanism, that 423 * is also capable of the MAC mechanism. 424 */ 425 int rv; 426 kcf_mech_entry_t *me; 427 kcf_provider_desc_t *pd = provider; 428 kcf_provider_desc_t *real_provider = pd; 429 kcf_ctx_template_t *ctx_encr_tmpl, *ctx_mac_tmpl; 430 kcf_req_params_t params; 431 kcf_encrypt_mac_ops_params_t *cmops; 432 crypto_spi_ctx_template_t spi_encr_tmpl = NULL, spi_mac_tmpl = NULL; 433 crypto_ctx_t *ctx; 434 kcf_context_t *encr_kcf_context = NULL; 435 436 ASSERT(KCF_PROV_REFHELD(pd)); 437 438 if (pd->pd_prov_type == CRYPTO_LOGICAL_PROVIDER) { 439 rv = kcf_get_hardware_provider(encr_mech->cm_type, encr_key, 440 mac_mech->cm_type, mac_key, pd, &real_provider, 441 CRYPTO_FG_ENCRYPT_MAC); 442 443 if (rv != CRYPTO_SUCCESS) 444 return (rv); 445 } 446 447 /* 448 * For SW providers, check the validity of the context template 449 * It is very rare that the generation number mis-matches, so 450 * is acceptable to fail here, and let the consumer recover by 451 * freeing this tmpl and create a new one for the key and new SW 452 * provider 453 * Warning! will need to change when multiple software providers 454 * per mechanism are supported. 455 */ 456 457 if (real_provider->pd_prov_type == CRYPTO_SW_PROVIDER) { 458 if (encr_tmpl != NULL) { 459 if (kcf_get_mech_entry(encr_mech->cm_type, &me) != 460 KCF_SUCCESS) { 461 rv = CRYPTO_MECHANISM_INVALID; 462 goto out; 463 } 464 ctx_encr_tmpl = (kcf_ctx_template_t *)encr_tmpl; 465 if (ctx_encr_tmpl->ct_generation != me->me_gen_swprov) { 466 rv = CRYPTO_OLD_CTX_TEMPLATE; 467 goto out; 468 } 469 spi_encr_tmpl = ctx_encr_tmpl->ct_prov_tmpl; 470 } 471 472 if (mac_tmpl != NULL) { 473 if (kcf_get_mech_entry(mac_mech->cm_type, &me) != 474 KCF_SUCCESS) { 475 rv = CRYPTO_MECHANISM_INVALID; 476 goto out; 477 } 478 ctx_mac_tmpl = (kcf_ctx_template_t *)mac_tmpl; 479 if (ctx_mac_tmpl->ct_generation != me->me_gen_swprov) { 480 rv = CRYPTO_OLD_CTX_TEMPLATE; 481 goto out; 482 } 483 spi_mac_tmpl = ctx_mac_tmpl->ct_prov_tmpl; 484 } 485 } 486 487 ctx = kcf_new_ctx(cr, real_provider, sid); 488 if (ctx == NULL) { 489 rv = CRYPTO_HOST_MEMORY; 490 goto out; 491 } 492 encr_kcf_context = (kcf_context_t *)ctx->cc_framework_private; 493 494 /* The fast path for SW providers. */ 495 if (CHECK_FASTPATH(cr, real_provider)) { 496 crypto_mechanism_t lencr_mech; 497 crypto_mechanism_t lmac_mech; 498 499 /* careful! structs assignments */ 500 lencr_mech = *encr_mech; 501 KCF_SET_PROVIDER_MECHNUM(encr_mech->cm_type, real_provider, 502 &lencr_mech); 503 504 lmac_mech = *mac_mech; 505 KCF_SET_PROVIDER_MECHNUM(mac_mech->cm_type, real_provider, 506 &lmac_mech); 507 508 rv = KCF_PROV_ENCRYPT_MAC_INIT(real_provider, ctx, &lencr_mech, 509 encr_key, &lmac_mech, mac_key, spi_encr_tmpl, spi_mac_tmpl, 510 KCF_SWFP_RHNDL(cr)); 511 512 KCF_PROV_INCRSTATS(pd, rv); 513 } else { 514 KCF_WRAP_ENCRYPT_MAC_OPS_PARAMS(¶ms, KCF_OP_INIT, 515 sid, encr_key, mac_key, NULL, NULL, NULL, 516 spi_encr_tmpl, spi_mac_tmpl); 517 518 cmops = &(params.rp_u.encrypt_mac_params); 519 520 /* careful! structs assignments */ 521 cmops->em_encr_mech = *encr_mech; 522 KCF_SET_PROVIDER_MECHNUM(encr_mech->cm_type, real_provider, 523 &cmops->em_encr_mech); 524 cmops->em_framework_encr_mechtype = encr_mech->cm_type; 525 526 cmops->em_mac_mech = *mac_mech; 527 KCF_SET_PROVIDER_MECHNUM(mac_mech->cm_type, real_provider, 528 &cmops->em_mac_mech); 529 cmops->em_framework_mac_mechtype = mac_mech->cm_type; 530 531 rv = kcf_submit_request(real_provider, ctx, cr, ¶ms, 532 B_FALSE); 533 } 534 535 if (rv != CRYPTO_SUCCESS && rv != CRYPTO_QUEUED) { 536 KCF_CONTEXT_REFRELE(encr_kcf_context); 537 } else 538 *ctxp = (crypto_context_t)ctx; 539 540 out: 541 if (pd->pd_prov_type == CRYPTO_LOGICAL_PROVIDER) 542 KCF_PROV_REFRELE(real_provider); 543 return (rv); 544 } 545 546 /* 547 * Starts a multi-part dual encrypt/mac operation. The provider and session 548 * to use are determined by the KCF dispatcher. 549 */ 550 /* ARGSUSED */ 551 int 552 crypto_encrypt_mac_init(crypto_mechanism_t *encr_mech, 553 crypto_mechanism_t *mac_mech, crypto_key_t *encr_key, 554 crypto_key_t *mac_key, crypto_ctx_template_t encr_tmpl, 555 crypto_ctx_template_t mac_tmpl, crypto_context_t *ctxp, 556 crypto_call_req_t *cr) 557 { 558 /* 559 * First try to find a provider for the encryption mechanism, that 560 * is also capable of the MAC mechanism. 561 */ 562 int error; 563 kcf_mech_entry_t *me; 564 kcf_provider_desc_t *pd; 565 kcf_ctx_template_t *ctx_encr_tmpl, *ctx_mac_tmpl; 566 kcf_req_params_t params; 567 kcf_encrypt_mac_ops_params_t *cmops; 568 crypto_spi_ctx_template_t spi_encr_tmpl = NULL, spi_mac_tmpl = NULL; 569 crypto_mech_type_t prov_encr_mechid, prov_mac_mechid; 570 kcf_prov_tried_t *list = NULL; 571 boolean_t encr_tmpl_checked = B_FALSE; 572 boolean_t mac_tmpl_checked = B_FALSE; 573 crypto_ctx_t *ctx = NULL; 574 kcf_context_t *encr_kcf_context = NULL, *mac_kcf_context; 575 crypto_call_flag_t save_flag; 576 577 retry: 578 /* pd is returned held on success */ 579 pd = kcf_get_dual_provider(encr_mech, encr_key, mac_mech, mac_key, 580 &me, &prov_encr_mechid, 581 &prov_mac_mechid, &error, list, 582 CRYPTO_FG_ENCRYPT | CRYPTO_FG_ENCRYPT_MAC, CRYPTO_FG_MAC, 0); 583 if (pd == NULL) { 584 if (list != NULL) 585 kcf_free_triedlist(list); 586 return (error); 587 } 588 589 /* 590 * For SW providers, check the validity of the context template 591 * It is very rare that the generation number mis-matches, so 592 * is acceptable to fail here, and let the consumer recover by 593 * freeing this tmpl and create a new one for the key and new SW 594 * provider 595 * Warning! will need to change when multiple software providers 596 * per mechanism are supported. 597 */ 598 599 if ((!encr_tmpl_checked) && (pd->pd_prov_type == CRYPTO_SW_PROVIDER)) { 600 if (encr_tmpl != NULL) { 601 ctx_encr_tmpl = (kcf_ctx_template_t *)encr_tmpl; 602 if (ctx_encr_tmpl->ct_generation != me->me_gen_swprov) { 603 604 if (list != NULL) 605 kcf_free_triedlist(list); 606 if (encr_kcf_context != NULL) 607 KCF_CONTEXT_REFRELE(encr_kcf_context); 608 609 KCF_PROV_REFRELE(pd); 610 /* Which one is the the old one ? */ 611 return (CRYPTO_OLD_CTX_TEMPLATE); 612 } 613 spi_encr_tmpl = ctx_encr_tmpl->ct_prov_tmpl; 614 } 615 encr_tmpl_checked = B_TRUE; 616 } 617 618 if (prov_mac_mechid == CRYPTO_MECH_INVALID) { 619 /* Need to emulate with 2 internal calls */ 620 621 /* 622 * We avoid code complexity by limiting the pure async. 623 * case to be done using only a SW provider. 624 * XXX - Redo the emulation code below so that we can 625 * remove this limitation. 626 */ 627 if (cr != NULL && pd->pd_prov_type == CRYPTO_HW_PROVIDER) { 628 if ((kcf_insert_triedlist(&list, pd, KCF_KMFLAG(cr)) 629 != NULL)) 630 goto retry; 631 if (list != NULL) 632 kcf_free_triedlist(list); 633 if (encr_kcf_context != NULL) 634 KCF_CONTEXT_REFRELE(encr_kcf_context); 635 KCF_PROV_REFRELE(pd); 636 return (CRYPTO_HOST_MEMORY); 637 } 638 639 if (ctx == NULL && pd->pd_prov_type == CRYPTO_SW_PROVIDER) { 640 ctx = kcf_new_ctx(cr, pd, pd->pd_sid); 641 if (ctx == NULL) { 642 if (list != NULL) 643 kcf_free_triedlist(list); 644 if (encr_kcf_context != NULL) 645 KCF_CONTEXT_REFRELE(encr_kcf_context); 646 KCF_PROV_REFRELE(pd); 647 return (CRYPTO_HOST_MEMORY); 648 } 649 encr_kcf_context = (kcf_context_t *) 650 ctx->cc_framework_private; 651 } 652 /* 653 * Trade-off speed vs avoidance of code complexity and 654 * duplication: 655 * Could do all the combinations of fastpath / synch / asynch 656 * for the encryption and the mac steps. Early attempts 657 * showed the code grew wild and bug-prone, for little gain. 658 * Therefore, the adaptative asynch case is not implemented. 659 * It's either pure synchronous, or pure asynchronous. 660 * We still preserve a fastpath for the pure synchronous 661 * requests to SW providers. 662 */ 663 if (cr == NULL) { 664 crypto_context_t mac_context; 665 666 if (pd->pd_prov_type == CRYPTO_SW_PROVIDER) { 667 crypto_mechanism_t lmech = *encr_mech; 668 669 lmech.cm_type = prov_encr_mechid; 670 671 error = KCF_PROV_ENCRYPT_INIT(pd, ctx, &lmech, 672 encr_key, spi_encr_tmpl, 673 KCF_RHNDL(KM_SLEEP)); 674 } else { 675 /* 676 * If we did the 'goto retry' then ctx may not 677 * be NULL. In general, we can't reuse another 678 * provider's context, so we free it now so 679 * we don't leak it. 680 */ 681 if (ctx != NULL) { 682 KCF_CONTEXT_REFRELE((kcf_context_t *) 683 ctx->cc_framework_private); 684 encr_kcf_context = NULL; 685 } 686 error = crypto_encrypt_init_prov(pd, pd->pd_sid, 687 encr_mech, encr_key, &encr_tmpl, 688 (crypto_context_t *)&ctx, NULL); 689 690 if (error == CRYPTO_SUCCESS) { 691 encr_kcf_context = (kcf_context_t *) 692 ctx->cc_framework_private; 693 } 694 } 695 KCF_PROV_INCRSTATS(pd, error); 696 697 KCF_PROV_REFRELE(pd); 698 699 if (error != CRYPTO_SUCCESS) { 700 /* Can't be CRYPTO_QUEUED. return the failure */ 701 if (list != NULL) 702 kcf_free_triedlist(list); 703 if (encr_kcf_context != NULL) 704 KCF_CONTEXT_REFRELE(encr_kcf_context); 705 706 return (error); 707 } 708 error = crypto_mac_init(mac_mech, mac_key, mac_tmpl, 709 &mac_context, NULL); 710 711 if (list != NULL) 712 kcf_free_triedlist(list); 713 714 if (error != CRYPTO_SUCCESS) { 715 /* Should this be an ASSERT() ? */ 716 717 KCF_CONTEXT_REFRELE(encr_kcf_context); 718 } else { 719 encr_kcf_context = (kcf_context_t *) 720 ctx->cc_framework_private; 721 mac_kcf_context = (kcf_context_t *) 722 ((crypto_ctx_t *)mac_context)-> 723 cc_framework_private; 724 725 encr_kcf_context->kc_secondctx = 726 mac_kcf_context; 727 KCF_CONTEXT_REFHOLD(mac_kcf_context); 728 729 *ctxp = (crypto_context_t)ctx; 730 } 731 732 return (error); 733 } 734 735 /* submit a pure asynchronous request. */ 736 save_flag = cr->cr_flag; 737 cr->cr_flag |= CRYPTO_ALWAYS_QUEUE; 738 739 KCF_WRAP_ENCRYPT_MAC_OPS_PARAMS(¶ms, KCF_OP_INIT, 740 pd->pd_sid, encr_key, mac_key, NULL, NULL, NULL, 741 spi_encr_tmpl, spi_mac_tmpl); 742 743 cmops = &(params.rp_u.encrypt_mac_params); 744 745 /* careful! structs assignments */ 746 cmops->em_encr_mech = *encr_mech; 747 /* 748 * cmops->em_encr_mech.cm_type will be set when we get to 749 * kcf_emulate_dual() routine. 750 */ 751 cmops->em_framework_encr_mechtype = encr_mech->cm_type; 752 cmops->em_mac_mech = *mac_mech; 753 754 /* 755 * cmops->em_mac_mech.cm_type will be set when we know the 756 * MAC provider. 757 */ 758 cmops->em_framework_mac_mechtype = mac_mech->cm_type; 759 760 /* 761 * non-NULL ctx->kc_secondctx tells common_submit_request 762 * that this request uses separate cipher and MAC contexts. 763 * That function will set ctx->kc_secondctx to the new 764 * MAC context, once it gets one. 765 */ 766 encr_kcf_context->kc_secondctx = encr_kcf_context; 767 768 error = kcf_submit_request(pd, ctx, cr, ¶ms, B_FALSE); 769 770 cr->cr_flag = save_flag; 771 772 if (error != CRYPTO_SUCCESS && error != CRYPTO_QUEUED) { 773 KCF_CONTEXT_REFRELE(encr_kcf_context); 774 } 775 if (list != NULL) 776 kcf_free_triedlist(list); 777 *ctxp = (crypto_context_t)ctx; 778 KCF_PROV_REFRELE(pd); 779 return (error); 780 } 781 782 if ((!mac_tmpl_checked) && (pd->pd_prov_type == CRYPTO_SW_PROVIDER)) { 783 if ((mac_tmpl != NULL) && 784 (prov_mac_mechid != CRYPTO_MECH_INVALID)) { 785 ctx_mac_tmpl = (kcf_ctx_template_t *)mac_tmpl; 786 if (ctx_mac_tmpl->ct_generation != me->me_gen_swprov) { 787 788 if (list != NULL) 789 kcf_free_triedlist(list); 790 791 KCF_PROV_REFRELE(pd); 792 /* Which one is the the old one ? */ 793 return (CRYPTO_OLD_CTX_TEMPLATE); 794 } 795 spi_mac_tmpl = ctx_mac_tmpl->ct_prov_tmpl; 796 } 797 mac_tmpl_checked = B_TRUE; 798 } 799 800 if (ctx == NULL) { 801 ctx = kcf_new_ctx(cr, pd, pd->pd_sid); 802 if (ctx == NULL) { 803 if (list != NULL) 804 kcf_free_triedlist(list); 805 806 KCF_PROV_REFRELE(pd); 807 return (CRYPTO_HOST_MEMORY); 808 } 809 encr_kcf_context = (kcf_context_t *)ctx->cc_framework_private; 810 } 811 812 /* The fast path for SW providers. */ 813 if (CHECK_FASTPATH(cr, pd)) { 814 crypto_mechanism_t lencr_mech; 815 crypto_mechanism_t lmac_mech; 816 817 /* careful! structs assignments */ 818 lencr_mech = *encr_mech; 819 lencr_mech.cm_type = prov_encr_mechid; 820 lmac_mech = *mac_mech; 821 lmac_mech.cm_type = prov_mac_mechid; 822 823 error = KCF_PROV_ENCRYPT_MAC_INIT(pd, ctx, &lencr_mech, 824 encr_key, &lmac_mech, mac_key, spi_encr_tmpl, spi_mac_tmpl, 825 KCF_SWFP_RHNDL(cr)); 826 827 KCF_PROV_INCRSTATS(pd, error); 828 } else { 829 KCF_WRAP_ENCRYPT_MAC_OPS_PARAMS(¶ms, KCF_OP_INIT, 830 pd->pd_sid, encr_key, mac_key, NULL, NULL, NULL, 831 spi_encr_tmpl, spi_mac_tmpl); 832 833 cmops = &(params.rp_u.encrypt_mac_params); 834 835 /* careful! structs assignments */ 836 cmops->em_encr_mech = *encr_mech; 837 cmops->em_encr_mech.cm_type = prov_encr_mechid; 838 cmops->em_framework_encr_mechtype = encr_mech->cm_type; 839 cmops->em_mac_mech = *mac_mech; 840 cmops->em_mac_mech.cm_type = prov_mac_mechid; 841 cmops->em_framework_mac_mechtype = mac_mech->cm_type; 842 843 error = kcf_submit_request(pd, ctx, cr, ¶ms, B_FALSE); 844 } 845 846 if (error != CRYPTO_SUCCESS && error != CRYPTO_QUEUED) { 847 if ((IS_RECOVERABLE(error)) && 848 (kcf_insert_triedlist(&list, pd, KCF_KMFLAG(cr)) != NULL)) 849 goto retry; 850 851 KCF_CONTEXT_REFRELE(encr_kcf_context); 852 } else 853 *ctxp = (crypto_context_t)ctx; 854 855 if (list != NULL) 856 kcf_free_triedlist(list); 857 858 KCF_PROV_REFRELE(pd); 859 return (error); 860 } 861 862 /* 863 * Continues a multi-part dual encrypt/mac operation. 864 */ 865 /* ARGSUSED */ 866 int 867 crypto_encrypt_mac_update(crypto_context_t context, 868 crypto_data_t *pt, crypto_dual_data_t *ct, crypto_call_req_t *cr) 869 { 870 crypto_ctx_t *ctx = (crypto_ctx_t *)context, *mac_ctx; 871 kcf_context_t *kcf_ctx, *kcf_mac_ctx; 872 kcf_provider_desc_t *pd; 873 int error; 874 kcf_req_params_t params; 875 876 if ((ctx == NULL) || 877 ((kcf_ctx = (kcf_context_t *)ctx->cc_framework_private) == NULL) || 878 ((pd = kcf_ctx->kc_prov_desc) == NULL)) { 879 return (CRYPTO_INVALID_CONTEXT); 880 } 881 882 ASSERT(pd->pd_prov_type != CRYPTO_LOGICAL_PROVIDER); 883 884 if ((kcf_mac_ctx = kcf_ctx->kc_secondctx) != NULL) { 885 off_t save_offset; 886 size_t save_len; 887 crypto_call_flag_t save_flag; 888 889 if (kcf_mac_ctx->kc_prov_desc == NULL) { 890 error = CRYPTO_INVALID_CONTEXT; 891 goto out; 892 } 893 mac_ctx = &kcf_mac_ctx->kc_glbl_ctx; 894 895 /* First we submit the encryption request */ 896 if (cr == NULL) { 897 /* 898 * 'ct' is always not NULL. 899 * A NULL 'pt' means in-place. 900 */ 901 if (pt == NULL) 902 error = crypto_encrypt_update(context, 903 (crypto_data_t *)ct, NULL, NULL); 904 else 905 error = crypto_encrypt_update(context, pt, 906 (crypto_data_t *)ct, NULL); 907 908 if (error != CRYPTO_SUCCESS) 909 goto out; 910 911 /* 912 * call mac_update when there is data to throw in 913 * the mix. Either an explicitly non-zero ct->dd_len2, 914 * or the last ciphertext portion. 915 */ 916 save_offset = ct->dd_offset1; 917 save_len = ct->dd_len1; 918 if (ct->dd_len2 == 0) { 919 /* 920 * The previous encrypt step was an 921 * accumulation only and didn't produce any 922 * partial output 923 */ 924 if (ct->dd_len1 == 0) 925 goto out; 926 } else { 927 ct->dd_offset1 = ct->dd_offset2; 928 ct->dd_len1 = ct->dd_len2; 929 } 930 error = crypto_mac_update((crypto_context_t)mac_ctx, 931 (crypto_data_t *)ct, NULL); 932 933 ct->dd_offset1 = save_offset; 934 ct->dd_len1 = save_len; 935 936 goto out; 937 } 938 /* submit a pure asynchronous request. */ 939 save_flag = cr->cr_flag; 940 cr->cr_flag |= CRYPTO_ALWAYS_QUEUE; 941 942 KCF_WRAP_ENCRYPT_MAC_OPS_PARAMS(¶ms, KCF_OP_UPDATE, 943 pd->pd_sid, NULL, NULL, pt, ct, NULL, NULL, NULL) 944 945 946 error = kcf_submit_request(pd, ctx, cr, ¶ms, B_FALSE); 947 948 cr->cr_flag = save_flag; 949 goto out; 950 } 951 952 /* The fast path for SW providers. */ 953 if (CHECK_FASTPATH(cr, pd)) { 954 error = KCF_PROV_ENCRYPT_MAC_UPDATE(pd, ctx, pt, ct, NULL); 955 KCF_PROV_INCRSTATS(pd, error); 956 } else { 957 KCF_WRAP_ENCRYPT_MAC_OPS_PARAMS(¶ms, KCF_OP_UPDATE, 958 ctx->cc_session, NULL, NULL, pt, ct, NULL, NULL, NULL); 959 960 error = kcf_submit_request(pd, ctx, cr, ¶ms, B_FALSE); 961 } 962 out: 963 return (error); 964 } 965 966 /* 967 * Terminates a multi-part dual encrypt/mac operation. 968 */ 969 /* ARGSUSED */ 970 int crypto_encrypt_mac_final(crypto_context_t context, crypto_dual_data_t *ct, 971 crypto_data_t *mac, crypto_call_req_t *cr) 972 { 973 crypto_ctx_t *ctx = (crypto_ctx_t *)context, *mac_ctx; 974 kcf_context_t *kcf_ctx, *kcf_mac_ctx; 975 kcf_provider_desc_t *pd; 976 int error; 977 kcf_req_params_t params; 978 979 if ((ctx == NULL) || 980 ((kcf_ctx = (kcf_context_t *)ctx->cc_framework_private) == NULL) || 981 ((pd = kcf_ctx->kc_prov_desc) == NULL)) { 982 return (CRYPTO_INVALID_CONTEXT); 983 } 984 985 ASSERT(pd->pd_prov_type != CRYPTO_LOGICAL_PROVIDER); 986 987 if ((kcf_mac_ctx = kcf_ctx->kc_secondctx) != NULL) { 988 off_t save_offset; 989 size_t save_len; 990 crypto_context_t mac_context; 991 crypto_call_flag_t save_flag; 992 993 if (kcf_mac_ctx->kc_prov_desc == NULL) { 994 return (CRYPTO_INVALID_CONTEXT); 995 } 996 mac_ctx = &kcf_mac_ctx->kc_glbl_ctx; 997 mac_context = (crypto_context_t)mac_ctx; 998 999 if (cr == NULL) { 1000 /* Get the last chunk of ciphertext */ 1001 error = crypto_encrypt_final(context, 1002 (crypto_data_t *)ct, NULL); 1003 1004 if (error != CRYPTO_SUCCESS) { 1005 /* 1006 * Needed here, because the caller of 1007 * crypto_encrypt_mac_final() lost all 1008 * refs to the mac_ctx. 1009 */ 1010 crypto_cancel_ctx(mac_context); 1011 return (error); 1012 } 1013 if (ct->dd_len2 > 0) { 1014 save_offset = ct->dd_offset1; 1015 save_len = ct->dd_len1; 1016 ct->dd_offset1 = ct->dd_offset2; 1017 ct->dd_len1 = ct->dd_len2; 1018 1019 error = crypto_mac_update(mac_context, 1020 (crypto_data_t *)ct, NULL); 1021 1022 ct->dd_offset1 = save_offset; 1023 ct->dd_len1 = save_len; 1024 1025 if (error != CRYPTO_SUCCESS) { 1026 crypto_cancel_ctx(mac_context); 1027 return (error); 1028 } 1029 } 1030 1031 /* and finally, collect the MAC */ 1032 error = crypto_mac_final(mac_context, mac, NULL); 1033 1034 return (error); 1035 } 1036 /* submit a pure asynchronous request. */ 1037 save_flag = cr->cr_flag; 1038 cr->cr_flag |= CRYPTO_ALWAYS_QUEUE; 1039 1040 KCF_WRAP_ENCRYPT_MAC_OPS_PARAMS(¶ms, KCF_OP_FINAL, 1041 pd->pd_sid, NULL, NULL, NULL, ct, mac, NULL, NULL) 1042 1043 1044 error = kcf_submit_request(pd, ctx, cr, ¶ms, B_FALSE); 1045 1046 cr->cr_flag = save_flag; 1047 return (error); 1048 } 1049 /* The fast path for SW providers. */ 1050 if (CHECK_FASTPATH(cr, pd)) { 1051 error = KCF_PROV_ENCRYPT_MAC_FINAL(pd, ctx, ct, mac, NULL); 1052 KCF_PROV_INCRSTATS(pd, error); 1053 } else { 1054 KCF_WRAP_ENCRYPT_MAC_OPS_PARAMS(¶ms, KCF_OP_FINAL, 1055 ctx->cc_session, NULL, NULL, NULL, ct, mac, NULL, NULL); 1056 error = kcf_submit_request(pd, ctx, cr, ¶ms, B_FALSE); 1057 } 1058 out: 1059 /* Release the hold done in kcf_new_ctx() during init step. */ 1060 KCF_CONTEXT_COND_RELEASE(error, kcf_ctx); 1061 return (error); 1062 } 1063 1064 /* 1065 * Performs an atomic dual mac/decrypt operation. The provider to use 1066 * is determined by the KCF dispatcher. 1067 */ 1068 int 1069 crypto_mac_decrypt(crypto_mechanism_t *mac_mech, 1070 crypto_mechanism_t *decr_mech, crypto_dual_data_t *ct, 1071 crypto_key_t *mac_key, crypto_key_t *decr_key, 1072 crypto_ctx_template_t mac_tmpl, crypto_ctx_template_t decr_tmpl, 1073 crypto_data_t *mac, crypto_data_t *pt, crypto_call_req_t *crq) 1074 { 1075 return (crypto_mac_decrypt_common(mac_mech, decr_mech, ct, mac_key, 1076 decr_key, mac_tmpl, decr_tmpl, mac, pt, crq, B_FALSE)); 1077 } 1078 1079 int 1080 crypto_mac_decrypt_prov(crypto_provider_t provider, crypto_session_id_t sid, 1081 crypto_mechanism_t *mac_mech, crypto_mechanism_t *decr_mech, 1082 crypto_dual_data_t *ct, crypto_key_t *mac_key, crypto_key_t *decr_key, 1083 crypto_ctx_template_t mac_tmpl, crypto_ctx_template_t decr_tmpl, 1084 crypto_data_t *mac, crypto_data_t *pt, crypto_call_req_t *crq) 1085 { 1086 return (crypto_mac_decrypt_common_prov(provider, sid, mac_mech, 1087 decr_mech, ct, mac_key, decr_key, mac_tmpl, decr_tmpl, mac, pt, 1088 crq, B_FALSE)); 1089 } 1090 1091 /* 1092 * Performs an atomic dual mac/decrypt operation. The provider to use 1093 * is determined by the KCF dispatcher. 'mac' specifies the expected 1094 * value for the MAC. The decryption is not performed if the computed 1095 * MAC does not match the expected MAC. 1096 */ 1097 int 1098 crypto_mac_verify_decrypt(crypto_mechanism_t *mac_mech, 1099 crypto_mechanism_t *decr_mech, crypto_dual_data_t *ct, 1100 crypto_key_t *mac_key, crypto_key_t *decr_key, 1101 crypto_ctx_template_t mac_tmpl, crypto_ctx_template_t decr_tmpl, 1102 crypto_data_t *mac, crypto_data_t *pt, crypto_call_req_t *crq) 1103 { 1104 return (crypto_mac_decrypt_common(mac_mech, decr_mech, ct, mac_key, 1105 decr_key, mac_tmpl, decr_tmpl, mac, pt, crq, B_TRUE)); 1106 } 1107 1108 int 1109 crypto_mac_verify_decrypt_prov(crypto_provider_t provider, 1110 crypto_session_id_t sid, crypto_mechanism_t *mac_mech, 1111 crypto_mechanism_t *decr_mech, crypto_dual_data_t *ct, 1112 crypto_key_t *mac_key, crypto_key_t *decr_key, 1113 crypto_ctx_template_t mac_tmpl, crypto_ctx_template_t decr_tmpl, 1114 crypto_data_t *mac, crypto_data_t *pt, crypto_call_req_t *crq) 1115 { 1116 return (crypto_mac_decrypt_common_prov(provider, sid, mac_mech, 1117 decr_mech, ct, mac_key, decr_key, mac_tmpl, decr_tmpl, mac, pt, 1118 crq, B_TRUE)); 1119 } 1120 1121 /* 1122 * Called by both crypto_mac_decrypt() and crypto_mac_verify_decrypt(). 1123 * optionally verified if the MACs match before calling the decryption step. 1124 */ 1125 static int 1126 crypto_mac_decrypt_common(crypto_mechanism_t *mac_mech, 1127 crypto_mechanism_t *decr_mech, crypto_dual_data_t *ct, 1128 crypto_key_t *mac_key, crypto_key_t *decr_key, 1129 crypto_ctx_template_t mac_tmpl, crypto_ctx_template_t decr_tmpl, 1130 crypto_data_t *mac, crypto_data_t *pt, crypto_call_req_t *crq, 1131 boolean_t do_verify) 1132 { 1133 /* 1134 * First try to find a provider for the decryption mechanism, that 1135 * is also capable of the MAC mechanism. 1136 * We still favor optimizing the costlier decryption. 1137 */ 1138 int error; 1139 kcf_mech_entry_t *me; 1140 kcf_provider_desc_t *pd; 1141 kcf_ctx_template_t *ctx_decr_tmpl, *ctx_mac_tmpl; 1142 kcf_req_params_t params; 1143 kcf_mac_decrypt_ops_params_t *cmops; 1144 crypto_spi_ctx_template_t spi_decr_tmpl = NULL, spi_mac_tmpl = NULL; 1145 crypto_mech_type_t prov_decr_mechid, prov_mac_mechid; 1146 kcf_prov_tried_t *list = NULL; 1147 boolean_t decr_tmpl_checked = B_FALSE; 1148 boolean_t mac_tmpl_checked = B_FALSE; 1149 kcf_dual_req_t *next_req = NULL; 1150 crypto_call_req_t mac_req, *mac_reqp = NULL; 1151 1152 retry: 1153 /* pd is returned held on success */ 1154 pd = kcf_get_dual_provider(decr_mech, decr_key, mac_mech, mac_key, 1155 &me, &prov_decr_mechid, 1156 &prov_mac_mechid, &error, list, 1157 CRYPTO_FG_DECRYPT_ATOMIC | CRYPTO_FG_MAC_DECRYPT_ATOMIC, 1158 CRYPTO_FG_MAC_ATOMIC | CRYPTO_FG_MAC_DECRYPT_ATOMIC, ct->dd_len2); 1159 if (pd == NULL) { 1160 if (list != NULL) 1161 kcf_free_triedlist(list); 1162 if (next_req != NULL) 1163 kmem_free(next_req, sizeof (kcf_dual_req_t)); 1164 return (CRYPTO_MECH_NOT_SUPPORTED); 1165 } 1166 1167 /* 1168 * For SW providers, check the validity of the context template 1169 * It is very rare that the generation number mis-matches, so 1170 * is acceptable to fail here, and let the consumer recover by 1171 * freeing this tmpl and create a new one for the key and new SW 1172 * provider 1173 */ 1174 1175 if ((!decr_tmpl_checked) && (pd->pd_prov_type == CRYPTO_SW_PROVIDER)) { 1176 if (decr_tmpl != NULL) { 1177 ctx_decr_tmpl = (kcf_ctx_template_t *)decr_tmpl; 1178 if (ctx_decr_tmpl->ct_generation != me->me_gen_swprov) { 1179 if (next_req != NULL) 1180 kmem_free(next_req, 1181 sizeof (kcf_dual_req_t)); 1182 if (list != NULL) 1183 kcf_free_triedlist(list); 1184 KCF_PROV_REFRELE(pd); 1185 1186 /* Which one is the the old one ? */ 1187 return (CRYPTO_OLD_CTX_TEMPLATE); 1188 } 1189 spi_decr_tmpl = ctx_decr_tmpl->ct_prov_tmpl; 1190 } 1191 decr_tmpl_checked = B_TRUE; 1192 } 1193 if (prov_mac_mechid == CRYPTO_MECH_INVALID) { 1194 /* Need to emulate with 2 internal calls */ 1195 1196 /* Prepare the call_req to be submitted for the MAC step */ 1197 1198 if (crq != NULL) { 1199 1200 if (next_req == NULL) { 1201 /* 1202 * allocate, initialize and prepare the 1203 * params for the next step only in the 1204 * first pass (not on every retry). 1205 */ 1206 next_req = kcf_alloc_req(crq); 1207 1208 if (next_req == NULL) { 1209 KCF_PROV_REFRELE(pd); 1210 if (list != NULL) 1211 kcf_free_triedlist(list); 1212 return (CRYPTO_HOST_MEMORY); 1213 } 1214 KCF_WRAP_DECRYPT_OPS_PARAMS( 1215 &(next_req->kr_params), KCF_OP_ATOMIC, 1216 0, decr_mech, decr_key, 1217 (crypto_data_t *)ct, pt, spi_decr_tmpl); 1218 } 1219 1220 mac_req.cr_flag = (crq != NULL) ? crq->cr_flag : 0; 1221 mac_req.cr_flag |= CRYPTO_SETDUAL; 1222 mac_req.cr_callback_func = kcf_next_req; 1223 mac_req.cr_callback_arg = next_req; 1224 mac_reqp = &mac_req; 1225 } 1226 1227 /* 'pd' is the decryption provider. */ 1228 1229 if (do_verify) 1230 error = crypto_mac_verify(mac_mech, (crypto_data_t *)ct, 1231 mac_key, mac_tmpl, mac, 1232 (crq == NULL) ? NULL : mac_reqp); 1233 else 1234 error = crypto_mac(mac_mech, (crypto_data_t *)ct, 1235 mac_key, mac_tmpl, mac, 1236 (crq == NULL) ? NULL : mac_reqp); 1237 1238 switch (error) { 1239 case CRYPTO_SUCCESS: { 1240 off_t saveoffset; 1241 size_t savelen; 1242 1243 if (next_req == NULL) { 1244 saveoffset = ct->dd_offset1; 1245 savelen = ct->dd_len1; 1246 } else { 1247 saveoffset = next_req->kr_saveoffset = 1248 ct->dd_offset1; 1249 savelen = next_req->kr_savelen = ct->dd_len1; 1250 1251 ASSERT(mac_reqp != NULL); 1252 mac_req.cr_flag &= ~CRYPTO_SETDUAL; 1253 mac_req.cr_callback_func = kcf_last_req; 1254 } 1255 ct->dd_offset1 = ct->dd_offset2; 1256 ct->dd_len1 = ct->dd_len2; 1257 1258 if (CHECK_FASTPATH(crq, pd)) { 1259 crypto_mechanism_t lmech; 1260 1261 lmech = *decr_mech; 1262 KCF_SET_PROVIDER_MECHNUM(decr_mech->cm_type, 1263 pd, &lmech); 1264 1265 error = KCF_PROV_DECRYPT_ATOMIC(pd, pd->pd_sid, 1266 &lmech, decr_key, (crypto_data_t *)ct, 1267 (crypto_data_t *)pt, spi_decr_tmpl, 1268 KCF_SWFP_RHNDL(mac_reqp)); 1269 1270 KCF_PROV_INCRSTATS(pd, error); 1271 } else { 1272 KCF_WRAP_DECRYPT_OPS_PARAMS(¶ms, 1273 KCF_OP_ATOMIC, pd->pd_sid, decr_mech, 1274 decr_key, (crypto_data_t *)ct, pt, 1275 spi_decr_tmpl); 1276 1277 error = kcf_submit_request(pd, NULL, 1278 (crq == NULL) ? NULL : mac_reqp, 1279 ¶ms, B_FALSE); 1280 } 1281 if (error != CRYPTO_QUEUED) { 1282 KCF_PROV_INCRSTATS(pd, error); 1283 ct->dd_offset1 = saveoffset; 1284 ct->dd_len1 = savelen; 1285 } 1286 break; 1287 } 1288 1289 case CRYPTO_QUEUED: 1290 if ((crq != NULL) && (crq->cr_flag & CRYPTO_SKIP_REQID)) 1291 crq->cr_reqid = mac_req.cr_reqid; 1292 break; 1293 1294 default: 1295 if (IS_RECOVERABLE(error)) { 1296 if (kcf_insert_triedlist(&list, pd, 1297 KCF_KMFLAG(crq)) != NULL) 1298 goto retry; 1299 } 1300 } 1301 if (error != CRYPTO_QUEUED && next_req != NULL) 1302 kmem_free(next_req, sizeof (kcf_dual_req_t)); 1303 if (list != NULL) 1304 kcf_free_triedlist(list); 1305 KCF_PROV_REFRELE(pd); 1306 return (error); 1307 } 1308 1309 if ((!mac_tmpl_checked) && (pd->pd_prov_type == CRYPTO_SW_PROVIDER)) { 1310 if ((mac_tmpl != NULL) && 1311 (prov_mac_mechid != CRYPTO_MECH_INVALID)) { 1312 ctx_mac_tmpl = (kcf_ctx_template_t *)mac_tmpl; 1313 if (ctx_mac_tmpl->ct_generation != me->me_gen_swprov) { 1314 if (next_req != NULL) 1315 kmem_free(next_req, 1316 sizeof (kcf_dual_req_t)); 1317 if (list != NULL) 1318 kcf_free_triedlist(list); 1319 KCF_PROV_REFRELE(pd); 1320 1321 /* Which one is the the old one ? */ 1322 return (CRYPTO_OLD_CTX_TEMPLATE); 1323 } 1324 spi_mac_tmpl = ctx_mac_tmpl->ct_prov_tmpl; 1325 } 1326 mac_tmpl_checked = B_TRUE; 1327 } 1328 1329 /* The fast path for SW providers. */ 1330 if (CHECK_FASTPATH(crq, pd)) { 1331 crypto_mechanism_t lmac_mech; 1332 crypto_mechanism_t ldecr_mech; 1333 1334 /* careful! structs assignments */ 1335 ldecr_mech = *decr_mech; 1336 ldecr_mech.cm_type = prov_decr_mechid; 1337 lmac_mech = *mac_mech; 1338 lmac_mech.cm_type = prov_mac_mechid; 1339 1340 if (do_verify) 1341 error = KCF_PROV_MAC_VERIFY_DECRYPT_ATOMIC(pd, 1342 pd->pd_sid, &lmac_mech, mac_key, &ldecr_mech, 1343 decr_key, ct, mac, pt, spi_mac_tmpl, spi_decr_tmpl, 1344 KCF_SWFP_RHNDL(crq)); 1345 else 1346 error = KCF_PROV_MAC_DECRYPT_ATOMIC(pd, pd->pd_sid, 1347 &lmac_mech, mac_key, &ldecr_mech, decr_key, 1348 ct, mac, pt, spi_mac_tmpl, spi_decr_tmpl, 1349 KCF_SWFP_RHNDL(crq)); 1350 1351 KCF_PROV_INCRSTATS(pd, error); 1352 } else { 1353 KCF_WRAP_MAC_DECRYPT_OPS_PARAMS(¶ms, 1354 (do_verify) ? KCF_OP_MAC_VERIFY_DECRYPT_ATOMIC : 1355 KCF_OP_ATOMIC, pd->pd_sid, mac_key, decr_key, ct, mac, pt, 1356 spi_mac_tmpl, spi_decr_tmpl); 1357 1358 cmops = &(params.rp_u.mac_decrypt_params); 1359 1360 /* careful! structs assignments */ 1361 cmops->md_decr_mech = *decr_mech; 1362 cmops->md_decr_mech.cm_type = prov_decr_mechid; 1363 cmops->md_framework_decr_mechtype = decr_mech->cm_type; 1364 cmops->md_mac_mech = *mac_mech; 1365 cmops->md_mac_mech.cm_type = prov_mac_mechid; 1366 cmops->md_framework_mac_mechtype = mac_mech->cm_type; 1367 1368 error = kcf_submit_request(pd, NULL, crq, ¶ms, B_FALSE); 1369 } 1370 1371 if (error != CRYPTO_SUCCESS && error != CRYPTO_QUEUED && 1372 IS_RECOVERABLE(error)) { 1373 /* Add pd to the linked list of providers tried. */ 1374 if (kcf_insert_triedlist(&list, pd, KCF_KMFLAG(crq)) != NULL) 1375 goto retry; 1376 } 1377 1378 if (list != NULL) 1379 kcf_free_triedlist(list); 1380 1381 if (next_req != NULL) 1382 kmem_free(next_req, sizeof (kcf_dual_req_t)); 1383 KCF_PROV_REFRELE(pd); 1384 return (error); 1385 } 1386 1387 static int 1388 crypto_mac_decrypt_common_prov(crypto_provider_t provider, 1389 crypto_session_id_t sid, crypto_mechanism_t *mac_mech, 1390 crypto_mechanism_t *decr_mech, crypto_dual_data_t *ct, 1391 crypto_key_t *mac_key, crypto_key_t *decr_key, 1392 crypto_ctx_template_t mac_tmpl, crypto_ctx_template_t decr_tmpl, 1393 crypto_data_t *mac, crypto_data_t *pt, crypto_call_req_t *crq, 1394 boolean_t do_verify) 1395 { 1396 /* 1397 * First try to find a provider for the decryption mechanism, that 1398 * is also capable of the MAC mechanism. 1399 * We still favor optimizing the costlier decryption. 1400 */ 1401 int error; 1402 kcf_mech_entry_t *me; 1403 kcf_provider_desc_t *pd = provider; 1404 kcf_provider_desc_t *real_provider = pd; 1405 kcf_ctx_template_t *ctx_decr_tmpl, *ctx_mac_tmpl; 1406 kcf_req_params_t params; 1407 kcf_mac_decrypt_ops_params_t *cmops; 1408 crypto_spi_ctx_template_t spi_decr_tmpl = NULL, spi_mac_tmpl = NULL; 1409 1410 ASSERT(KCF_PROV_REFHELD(pd)); 1411 1412 if (pd->pd_prov_type == CRYPTO_LOGICAL_PROVIDER) { 1413 error = kcf_get_hardware_provider(decr_mech->cm_type, decr_key, 1414 mac_mech->cm_type, mac_key, pd, &real_provider, 1415 CRYPTO_FG_MAC_DECRYPT_ATOMIC); 1416 1417 if (error != CRYPTO_SUCCESS) 1418 return (error); 1419 } 1420 1421 /* 1422 * For SW providers, check the validity of the context template 1423 * It is very rare that the generation number mis-matches, so 1424 * is acceptable to fail here, and let the consumer recover by 1425 * freeing this tmpl and create a new one for the key and new SW 1426 * provider 1427 */ 1428 1429 if (real_provider->pd_prov_type == CRYPTO_SW_PROVIDER) { 1430 if (decr_tmpl != NULL) { 1431 if (kcf_get_mech_entry(decr_mech->cm_type, &me) != 1432 KCF_SUCCESS) { 1433 error = CRYPTO_MECHANISM_INVALID; 1434 goto out; 1435 } 1436 ctx_decr_tmpl = (kcf_ctx_template_t *)decr_tmpl; 1437 if (ctx_decr_tmpl->ct_generation != me->me_gen_swprov) { 1438 error = CRYPTO_OLD_CTX_TEMPLATE; 1439 goto out; 1440 } 1441 spi_decr_tmpl = ctx_decr_tmpl->ct_prov_tmpl; 1442 } 1443 1444 if (mac_tmpl != NULL) { 1445 if (kcf_get_mech_entry(mac_mech->cm_type, &me) != 1446 KCF_SUCCESS) { 1447 error = CRYPTO_MECHANISM_INVALID; 1448 goto out; 1449 } 1450 ctx_mac_tmpl = (kcf_ctx_template_t *)mac_tmpl; 1451 if (ctx_mac_tmpl->ct_generation != me->me_gen_swprov) { 1452 error = CRYPTO_OLD_CTX_TEMPLATE; 1453 goto out; 1454 } 1455 spi_mac_tmpl = ctx_mac_tmpl->ct_prov_tmpl; 1456 } 1457 } 1458 1459 /* The fast path for SW providers. */ 1460 if (CHECK_FASTPATH(crq, pd)) { 1461 crypto_mechanism_t lmac_mech; 1462 crypto_mechanism_t ldecr_mech; 1463 1464 /* careful! structs assignments */ 1465 ldecr_mech = *decr_mech; 1466 KCF_SET_PROVIDER_MECHNUM(decr_mech->cm_type, real_provider, 1467 &ldecr_mech); 1468 1469 lmac_mech = *mac_mech; 1470 KCF_SET_PROVIDER_MECHNUM(mac_mech->cm_type, real_provider, 1471 &lmac_mech); 1472 1473 if (do_verify) 1474 error = KCF_PROV_MAC_VERIFY_DECRYPT_ATOMIC( 1475 real_provider, sid, &lmac_mech, mac_key, 1476 &ldecr_mech, decr_key, ct, mac, pt, spi_mac_tmpl, 1477 spi_decr_tmpl, KCF_SWFP_RHNDL(crq)); 1478 else 1479 error = KCF_PROV_MAC_DECRYPT_ATOMIC(real_provider, sid, 1480 &lmac_mech, mac_key, &ldecr_mech, decr_key, 1481 ct, mac, pt, spi_mac_tmpl, spi_decr_tmpl, 1482 KCF_SWFP_RHNDL(crq)); 1483 1484 KCF_PROV_INCRSTATS(pd, error); 1485 } else { 1486 KCF_WRAP_MAC_DECRYPT_OPS_PARAMS(¶ms, 1487 (do_verify) ? KCF_OP_MAC_VERIFY_DECRYPT_ATOMIC : 1488 KCF_OP_ATOMIC, sid, mac_key, decr_key, ct, mac, pt, 1489 spi_mac_tmpl, spi_decr_tmpl); 1490 1491 cmops = &(params.rp_u.mac_decrypt_params); 1492 1493 /* careful! structs assignments */ 1494 cmops->md_decr_mech = *decr_mech; 1495 KCF_SET_PROVIDER_MECHNUM(decr_mech->cm_type, real_provider, 1496 &cmops->md_decr_mech); 1497 cmops->md_framework_decr_mechtype = decr_mech->cm_type; 1498 1499 cmops->md_mac_mech = *mac_mech; 1500 KCF_SET_PROVIDER_MECHNUM(mac_mech->cm_type, real_provider, 1501 &cmops->md_mac_mech); 1502 cmops->md_framework_mac_mechtype = mac_mech->cm_type; 1503 1504 error = kcf_submit_request(real_provider, NULL, crq, ¶ms, 1505 B_FALSE); 1506 } 1507 1508 out: 1509 if (pd->pd_prov_type == CRYPTO_LOGICAL_PROVIDER) 1510 KCF_PROV_REFRELE(real_provider); 1511 return (error); 1512 } 1513 1514 /* 1515 * Starts a multi-part dual mac/decrypt operation. The provider to 1516 * use is determined by the KCF dispatcher. 1517 */ 1518 /* ARGSUSED */ 1519 int 1520 crypto_mac_decrypt_init(crypto_mechanism_t *mac_mech, 1521 crypto_mechanism_t *decr_mech, crypto_key_t *mac_key, 1522 crypto_key_t *decr_key, crypto_ctx_template_t mac_tmpl, 1523 crypto_ctx_template_t decr_tmpl, crypto_context_t *ctxp, 1524 crypto_call_req_t *cr) 1525 { 1526 /* 1527 * First try to find a provider for the decryption mechanism, that 1528 * is also capable of the MAC mechanism. 1529 * We still favor optimizing the costlier decryption. 1530 */ 1531 int error; 1532 kcf_mech_entry_t *me; 1533 kcf_provider_desc_t *pd; 1534 kcf_ctx_template_t *ctx_decr_tmpl, *ctx_mac_tmpl; 1535 kcf_req_params_t params; 1536 kcf_mac_decrypt_ops_params_t *mdops; 1537 crypto_spi_ctx_template_t spi_decr_tmpl = NULL, spi_mac_tmpl = NULL; 1538 crypto_mech_type_t prov_decr_mechid, prov_mac_mechid; 1539 kcf_prov_tried_t *list = NULL; 1540 boolean_t decr_tmpl_checked = B_FALSE; 1541 boolean_t mac_tmpl_checked = B_FALSE; 1542 crypto_ctx_t *ctx = NULL; 1543 kcf_context_t *decr_kcf_context = NULL, *mac_kcf_context = NULL; 1544 crypto_call_flag_t save_flag; 1545 1546 retry: 1547 /* pd is returned held on success */ 1548 pd = kcf_get_dual_provider(decr_mech, decr_key, mac_mech, mac_key, 1549 &me, &prov_decr_mechid, 1550 &prov_mac_mechid, &error, list, 1551 CRYPTO_FG_DECRYPT | CRYPTO_FG_MAC_DECRYPT, CRYPTO_FG_MAC, 0); 1552 if (pd == NULL) { 1553 if (list != NULL) 1554 kcf_free_triedlist(list); 1555 return (error); 1556 } 1557 1558 /* 1559 * For SW providers, check the validity of the context template 1560 * It is very rare that the generation number mis-matches, so 1561 * is acceptable to fail here, and let the consumer recover by 1562 * freeing this tmpl and create a new one for the key and new SW 1563 * provider 1564 * Warning! will need to change when multiple software providers 1565 * per mechanism are supported. 1566 */ 1567 1568 if ((!decr_tmpl_checked) && (pd->pd_prov_type == CRYPTO_SW_PROVIDER)) { 1569 if (decr_tmpl != NULL) { 1570 ctx_decr_tmpl = (kcf_ctx_template_t *)decr_tmpl; 1571 if (ctx_decr_tmpl->ct_generation != me->me_gen_swprov) { 1572 1573 if (list != NULL) 1574 kcf_free_triedlist(list); 1575 if (decr_kcf_context != NULL) 1576 KCF_CONTEXT_REFRELE(decr_kcf_context); 1577 1578 KCF_PROV_REFRELE(pd); 1579 /* Which one is the the old one ? */ 1580 return (CRYPTO_OLD_CTX_TEMPLATE); 1581 } 1582 spi_decr_tmpl = ctx_decr_tmpl->ct_prov_tmpl; 1583 } 1584 decr_tmpl_checked = B_TRUE; 1585 } 1586 1587 if (prov_mac_mechid == CRYPTO_MECH_INVALID) { 1588 /* Need to emulate with 2 internal calls */ 1589 1590 /* 1591 * We avoid code complexity by limiting the pure async. 1592 * case to be done using only a SW provider. 1593 * XXX - Redo the emulation code below so that we can 1594 * remove this limitation. 1595 */ 1596 if (cr != NULL && pd->pd_prov_type == CRYPTO_HW_PROVIDER) { 1597 if ((kcf_insert_triedlist(&list, pd, KCF_KMFLAG(cr)) 1598 != NULL)) 1599 goto retry; 1600 if (list != NULL) 1601 kcf_free_triedlist(list); 1602 if (decr_kcf_context != NULL) 1603 KCF_CONTEXT_REFRELE(decr_kcf_context); 1604 KCF_PROV_REFRELE(pd); 1605 return (CRYPTO_HOST_MEMORY); 1606 } 1607 1608 if (ctx == NULL && pd->pd_prov_type == CRYPTO_SW_PROVIDER) { 1609 ctx = kcf_new_ctx(cr, pd, pd->pd_sid); 1610 if (ctx == NULL) { 1611 if (list != NULL) 1612 kcf_free_triedlist(list); 1613 if (decr_kcf_context != NULL) 1614 KCF_CONTEXT_REFRELE(decr_kcf_context); 1615 KCF_PROV_REFRELE(pd); 1616 return (CRYPTO_HOST_MEMORY); 1617 } 1618 decr_kcf_context = (kcf_context_t *) 1619 ctx->cc_framework_private; 1620 } 1621 /* 1622 * Trade-off speed vs avoidance of code complexity and 1623 * duplication: 1624 * Could do all the combinations of fastpath / synch / asynch 1625 * for the decryption and the mac steps. Early attempts 1626 * showed the code grew wild and bug-prone, for little gain. 1627 * Therefore, the adaptative asynch case is not implemented. 1628 * It's either pure synchronous, or pure asynchronous. 1629 * We still preserve a fastpath for the pure synchronous 1630 * requests to SW providers. 1631 */ 1632 if (cr == NULL) { 1633 crypto_context_t mac_context; 1634 1635 error = crypto_mac_init(mac_mech, mac_key, mac_tmpl, 1636 &mac_context, NULL); 1637 1638 if (error != CRYPTO_SUCCESS) { 1639 /* Can't be CRYPTO_QUEUED. return the failure */ 1640 if (list != NULL) 1641 kcf_free_triedlist(list); 1642 1643 if (decr_kcf_context != NULL) 1644 KCF_CONTEXT_REFRELE(decr_kcf_context); 1645 return (error); 1646 } 1647 if (pd->pd_prov_type == CRYPTO_SW_PROVIDER) { 1648 crypto_mechanism_t lmech = *decr_mech; 1649 1650 lmech.cm_type = prov_decr_mechid; 1651 1652 error = KCF_PROV_DECRYPT_INIT(pd, ctx, &lmech, 1653 decr_key, spi_decr_tmpl, 1654 KCF_RHNDL(KM_SLEEP)); 1655 } else { 1656 /* 1657 * If we did the 'goto retry' then ctx may not 1658 * be NULL. In general, we can't reuse another 1659 * provider's context, so we free it now so 1660 * we don't leak it. 1661 */ 1662 if (ctx != NULL) { 1663 KCF_CONTEXT_REFRELE((kcf_context_t *) 1664 ctx->cc_framework_private); 1665 decr_kcf_context = NULL; 1666 } 1667 error = crypto_decrypt_init_prov(pd, pd->pd_sid, 1668 decr_mech, decr_key, &decr_tmpl, 1669 (crypto_context_t *)&ctx, NULL); 1670 1671 if (error == CRYPTO_SUCCESS) { 1672 decr_kcf_context = (kcf_context_t *) 1673 ctx->cc_framework_private; 1674 } 1675 } 1676 1677 KCF_PROV_INCRSTATS(pd, error); 1678 1679 KCF_PROV_REFRELE(pd); 1680 1681 if (error != CRYPTO_SUCCESS) { 1682 /* Can't be CRYPTO_QUEUED. return the failure */ 1683 if (list != NULL) 1684 kcf_free_triedlist(list); 1685 if (mac_kcf_context != NULL) 1686 KCF_CONTEXT_REFRELE(mac_kcf_context); 1687 1688 return (error); 1689 } 1690 mac_kcf_context = (kcf_context_t *) 1691 ((crypto_ctx_t *)mac_context)-> 1692 cc_framework_private; 1693 1694 decr_kcf_context = (kcf_context_t *) 1695 ctx->cc_framework_private; 1696 1697 /* 1698 * Here also, the mac context is second. The callback 1699 * case can't overwrite the context returned to 1700 * the caller. 1701 */ 1702 decr_kcf_context->kc_secondctx = mac_kcf_context; 1703 KCF_CONTEXT_REFHOLD(mac_kcf_context); 1704 1705 *ctxp = (crypto_context_t)ctx; 1706 1707 return (error); 1708 } 1709 /* submit a pure asynchronous request. */ 1710 save_flag = cr->cr_flag; 1711 cr->cr_flag |= CRYPTO_ALWAYS_QUEUE; 1712 1713 KCF_WRAP_MAC_DECRYPT_OPS_PARAMS(¶ms, KCF_OP_INIT, 1714 pd->pd_sid, mac_key, decr_key, NULL, NULL, NULL, 1715 spi_mac_tmpl, spi_decr_tmpl); 1716 1717 mdops = &(params.rp_u.mac_decrypt_params); 1718 1719 /* careful! structs assignments */ 1720 mdops->md_decr_mech = *decr_mech; 1721 /* 1722 * mdops->md_decr_mech.cm_type will be set when we get to 1723 * kcf_emulate_dual() routine. 1724 */ 1725 mdops->md_framework_decr_mechtype = decr_mech->cm_type; 1726 mdops->md_mac_mech = *mac_mech; 1727 1728 /* 1729 * mdops->md_mac_mech.cm_type will be set when we know the 1730 * MAC provider. 1731 */ 1732 mdops->md_framework_mac_mechtype = mac_mech->cm_type; 1733 1734 /* 1735 * non-NULL ctx->kc_secondctx tells common_submit_request 1736 * that this request uses separate cipher and MAC contexts. 1737 * That function will set the MAC context's kc_secondctx to 1738 * this decrypt context. 1739 */ 1740 decr_kcf_context->kc_secondctx = decr_kcf_context; 1741 1742 error = kcf_submit_request(pd, ctx, cr, ¶ms, B_FALSE); 1743 1744 cr->cr_flag = save_flag; 1745 1746 if (error != CRYPTO_SUCCESS && error != CRYPTO_QUEUED) { 1747 KCF_CONTEXT_REFRELE(decr_kcf_context); 1748 } 1749 if (list != NULL) 1750 kcf_free_triedlist(list); 1751 *ctxp = ctx; 1752 KCF_PROV_REFRELE(pd); 1753 return (error); 1754 } 1755 1756 if ((!mac_tmpl_checked) && (pd->pd_prov_type == CRYPTO_SW_PROVIDER)) { 1757 if ((mac_tmpl != NULL) && 1758 (prov_mac_mechid != CRYPTO_MECH_INVALID)) { 1759 ctx_mac_tmpl = (kcf_ctx_template_t *)mac_tmpl; 1760 if (ctx_mac_tmpl->ct_generation != me->me_gen_swprov) { 1761 1762 if (list != NULL) 1763 kcf_free_triedlist(list); 1764 1765 KCF_PROV_REFRELE(pd); 1766 /* Which one is the the old one ? */ 1767 return (CRYPTO_OLD_CTX_TEMPLATE); 1768 } 1769 spi_mac_tmpl = ctx_mac_tmpl->ct_prov_tmpl; 1770 } 1771 mac_tmpl_checked = B_TRUE; 1772 } 1773 1774 if (ctx == NULL) { 1775 ctx = kcf_new_ctx(cr, pd, pd->pd_sid); 1776 if (ctx == NULL) { 1777 error = CRYPTO_HOST_MEMORY; 1778 if (list != NULL) 1779 kcf_free_triedlist(list); 1780 return (CRYPTO_HOST_MEMORY); 1781 } 1782 decr_kcf_context = (kcf_context_t *)ctx->cc_framework_private; 1783 } 1784 1785 /* The fast path for SW providers. */ 1786 if (CHECK_FASTPATH(cr, pd)) { 1787 crypto_mechanism_t ldecr_mech; 1788 crypto_mechanism_t lmac_mech; 1789 1790 /* careful! structs assignments */ 1791 ldecr_mech = *decr_mech; 1792 ldecr_mech.cm_type = prov_decr_mechid; 1793 lmac_mech = *mac_mech; 1794 lmac_mech.cm_type = prov_mac_mechid; 1795 1796 error = KCF_PROV_MAC_DECRYPT_INIT(pd, ctx, &lmac_mech, 1797 mac_key, &ldecr_mech, decr_key, spi_mac_tmpl, spi_decr_tmpl, 1798 KCF_SWFP_RHNDL(cr)); 1799 1800 KCF_PROV_INCRSTATS(pd, error); 1801 } else { 1802 KCF_WRAP_MAC_DECRYPT_OPS_PARAMS(¶ms, KCF_OP_INIT, 1803 pd->pd_sid, mac_key, decr_key, NULL, NULL, NULL, 1804 spi_mac_tmpl, spi_decr_tmpl); 1805 1806 mdops = &(params.rp_u.mac_decrypt_params); 1807 1808 /* careful! structs assignments */ 1809 mdops->md_decr_mech = *decr_mech; 1810 mdops->md_decr_mech.cm_type = prov_decr_mechid; 1811 mdops->md_framework_decr_mechtype = decr_mech->cm_type; 1812 mdops->md_mac_mech = *mac_mech; 1813 mdops->md_mac_mech.cm_type = prov_mac_mechid; 1814 mdops->md_framework_mac_mechtype = mac_mech->cm_type; 1815 1816 error = kcf_submit_request(pd, ctx, cr, ¶ms, B_FALSE); 1817 } 1818 1819 if (error != CRYPTO_SUCCESS && error != CRYPTO_QUEUED) { 1820 if ((IS_RECOVERABLE(error)) && 1821 (kcf_insert_triedlist(&list, pd, KCF_KMFLAG(cr)) != NULL)) 1822 goto retry; 1823 1824 KCF_CONTEXT_REFRELE(decr_kcf_context); 1825 } else 1826 *ctxp = (crypto_context_t)ctx; 1827 1828 if (list != NULL) 1829 kcf_free_triedlist(list); 1830 1831 KCF_PROV_REFRELE(pd); 1832 return (error); 1833 } 1834 1835 int 1836 crypto_mac_decrypt_init_prov(crypto_provider_t provider, 1837 crypto_session_id_t sid, crypto_mechanism_t *mac_mech, 1838 crypto_mechanism_t *decr_mech, crypto_key_t *mac_key, 1839 crypto_key_t *decr_key, crypto_ctx_template_t mac_tmpl, 1840 crypto_ctx_template_t decr_tmpl, crypto_context_t *ctxp, 1841 crypto_call_req_t *cr) 1842 { 1843 /* 1844 * First try to find a provider for the decryption mechanism, that 1845 * is also capable of the MAC mechanism. 1846 * We still favor optimizing the costlier decryption. 1847 */ 1848 int rv; 1849 kcf_mech_entry_t *me; 1850 kcf_provider_desc_t *pd = provider; 1851 kcf_provider_desc_t *real_provider = pd; 1852 kcf_ctx_template_t *ctx_decr_tmpl, *ctx_mac_tmpl; 1853 kcf_req_params_t params; 1854 kcf_mac_decrypt_ops_params_t *mdops; 1855 crypto_spi_ctx_template_t spi_decr_tmpl = NULL, spi_mac_tmpl = NULL; 1856 crypto_ctx_t *ctx; 1857 kcf_context_t *decr_kcf_context = NULL; 1858 1859 ASSERT(KCF_PROV_REFHELD(pd)); 1860 1861 if (pd->pd_prov_type == CRYPTO_LOGICAL_PROVIDER) { 1862 rv = kcf_get_hardware_provider(decr_mech->cm_type, decr_key, 1863 mac_mech->cm_type, mac_key, pd, &real_provider, 1864 CRYPTO_FG_MAC_DECRYPT); 1865 1866 if (rv != CRYPTO_SUCCESS) 1867 return (rv); 1868 } 1869 1870 /* 1871 * For SW providers, check the validity of the context template 1872 * It is very rare that the generation number mis-matches, so 1873 * is acceptable to fail here, and let the consumer recover by 1874 * freeing this tmpl and create a new one for the key and new SW 1875 * provider 1876 * Warning! will need to change when multiple software providers 1877 * per mechanism are supported. 1878 */ 1879 1880 if (real_provider->pd_prov_type == CRYPTO_SW_PROVIDER) { 1881 if (decr_tmpl != NULL) { 1882 if (kcf_get_mech_entry(decr_mech->cm_type, &me) != 1883 KCF_SUCCESS) { 1884 rv = CRYPTO_MECHANISM_INVALID; 1885 goto out; 1886 } 1887 ctx_decr_tmpl = (kcf_ctx_template_t *)decr_tmpl; 1888 if (ctx_decr_tmpl->ct_generation != me->me_gen_swprov) { 1889 rv = CRYPTO_OLD_CTX_TEMPLATE; 1890 goto out; 1891 } 1892 spi_decr_tmpl = ctx_decr_tmpl->ct_prov_tmpl; 1893 } 1894 1895 if (mac_tmpl != NULL) { 1896 if (kcf_get_mech_entry(mac_mech->cm_type, &me) != 1897 KCF_SUCCESS) { 1898 rv = CRYPTO_MECHANISM_INVALID; 1899 goto out; 1900 } 1901 ctx_mac_tmpl = (kcf_ctx_template_t *)mac_tmpl; 1902 if (ctx_mac_tmpl->ct_generation != me->me_gen_swprov) { 1903 rv = CRYPTO_OLD_CTX_TEMPLATE; 1904 goto out; 1905 } 1906 spi_mac_tmpl = ctx_mac_tmpl->ct_prov_tmpl; 1907 } 1908 } 1909 1910 ctx = kcf_new_ctx(cr, real_provider, sid); 1911 if (ctx == NULL) { 1912 rv = CRYPTO_HOST_MEMORY; 1913 goto out; 1914 } 1915 decr_kcf_context = (kcf_context_t *)ctx->cc_framework_private; 1916 1917 /* The fast path for SW providers. */ 1918 if (CHECK_FASTPATH(cr, pd)) { 1919 crypto_mechanism_t ldecr_mech; 1920 crypto_mechanism_t lmac_mech; 1921 1922 /* careful! structs assignments */ 1923 ldecr_mech = *decr_mech; 1924 KCF_SET_PROVIDER_MECHNUM(decr_mech->cm_type, real_provider, 1925 &ldecr_mech); 1926 1927 lmac_mech = *mac_mech; 1928 KCF_SET_PROVIDER_MECHNUM(mac_mech->cm_type, real_provider, 1929 &lmac_mech); 1930 1931 rv = KCF_PROV_MAC_DECRYPT_INIT(real_provider, ctx, &lmac_mech, 1932 mac_key, &ldecr_mech, decr_key, spi_mac_tmpl, spi_decr_tmpl, 1933 KCF_SWFP_RHNDL(cr)); 1934 1935 KCF_PROV_INCRSTATS(pd, rv); 1936 } else { 1937 KCF_WRAP_MAC_DECRYPT_OPS_PARAMS(¶ms, KCF_OP_INIT, 1938 sid, mac_key, decr_key, NULL, NULL, NULL, 1939 spi_mac_tmpl, spi_decr_tmpl); 1940 1941 mdops = &(params.rp_u.mac_decrypt_params); 1942 1943 /* careful! structs assignments */ 1944 mdops->md_decr_mech = *decr_mech; 1945 KCF_SET_PROVIDER_MECHNUM(decr_mech->cm_type, real_provider, 1946 &mdops->md_decr_mech); 1947 mdops->md_framework_decr_mechtype = decr_mech->cm_type; 1948 1949 mdops->md_mac_mech = *mac_mech; 1950 KCF_SET_PROVIDER_MECHNUM(mac_mech->cm_type, real_provider, 1951 &mdops->md_mac_mech); 1952 mdops->md_framework_mac_mechtype = mac_mech->cm_type; 1953 1954 rv = kcf_submit_request(real_provider, ctx, cr, ¶ms, 1955 B_FALSE); 1956 } 1957 1958 if (rv != CRYPTO_SUCCESS && rv != CRYPTO_QUEUED) { 1959 KCF_CONTEXT_REFRELE(decr_kcf_context); 1960 } else 1961 *ctxp = (crypto_context_t)ctx; 1962 1963 out: 1964 if (pd->pd_prov_type == CRYPTO_LOGICAL_PROVIDER) 1965 KCF_PROV_REFRELE(real_provider); 1966 return (rv); 1967 } 1968 /* 1969 * Continues a multi-part dual mac/decrypt operation. 1970 */ 1971 /* ARGSUSED */ 1972 int 1973 crypto_mac_decrypt_update(crypto_context_t context, 1974 crypto_dual_data_t *ct, crypto_data_t *pt, crypto_call_req_t *cr) 1975 { 1976 crypto_ctx_t *ctx = (crypto_ctx_t *)context, *mac_ctx; 1977 kcf_context_t *kcf_ctx, *kcf_mac_ctx; 1978 kcf_provider_desc_t *pd; 1979 int error; 1980 kcf_req_params_t params; 1981 1982 if ((ctx == NULL) || 1983 ((kcf_ctx = (kcf_context_t *)ctx->cc_framework_private) == NULL) || 1984 ((pd = kcf_ctx->kc_prov_desc) == NULL)) { 1985 return (CRYPTO_INVALID_CONTEXT); 1986 } 1987 1988 ASSERT(pd->pd_prov_type != CRYPTO_LOGICAL_PROVIDER); 1989 1990 if ((kcf_mac_ctx = kcf_ctx->kc_secondctx) != NULL) { 1991 off_t save_offset; 1992 size_t save_len; 1993 crypto_call_flag_t save_flag; 1994 1995 if (kcf_mac_ctx->kc_prov_desc == NULL) { 1996 error = CRYPTO_INVALID_CONTEXT; 1997 goto out; 1998 } 1999 mac_ctx = &kcf_mac_ctx->kc_glbl_ctx; 2000 2001 /* First we submit the MAC request */ 2002 if (cr == NULL) { 2003 /* 2004 * 'ct' is always not NULL. 2005 */ 2006 error = crypto_mac_update((crypto_context_t)mac_ctx, 2007 (crypto_data_t *)ct, NULL); 2008 2009 if (error != CRYPTO_SUCCESS) 2010 goto out; 2011 2012 /* Decrypt a different length only when told so */ 2013 2014 save_offset = ct->dd_offset1; 2015 save_len = ct->dd_len1; 2016 2017 if (ct->dd_len2 > 0) { 2018 ct->dd_offset1 = ct->dd_offset2; 2019 ct->dd_len1 = ct->dd_len2; 2020 } 2021 2022 error = crypto_decrypt_update(context, 2023 (crypto_data_t *)ct, pt, NULL); 2024 2025 ct->dd_offset1 = save_offset; 2026 ct->dd_len1 = save_len; 2027 2028 goto out; 2029 } 2030 /* submit a pure asynchronous request. */ 2031 save_flag = cr->cr_flag; 2032 cr->cr_flag |= CRYPTO_ALWAYS_QUEUE; 2033 2034 KCF_WRAP_MAC_DECRYPT_OPS_PARAMS(¶ms, KCF_OP_UPDATE, 2035 pd->pd_sid, NULL, NULL, ct, NULL, pt, NULL, NULL) 2036 2037 2038 error = kcf_submit_request(pd, ctx, cr, ¶ms, B_FALSE); 2039 2040 cr->cr_flag = save_flag; 2041 goto out; 2042 } 2043 2044 /* The fast path for SW providers. */ 2045 if (CHECK_FASTPATH(cr, pd)) { 2046 error = KCF_PROV_MAC_DECRYPT_UPDATE(pd, ctx, ct, pt, NULL); 2047 KCF_PROV_INCRSTATS(pd, error); 2048 } else { 2049 KCF_WRAP_MAC_DECRYPT_OPS_PARAMS(¶ms, KCF_OP_UPDATE, 2050 ctx->cc_session, NULL, NULL, ct, NULL, pt, NULL, NULL); 2051 2052 error = kcf_submit_request(pd, ctx, cr, ¶ms, B_FALSE); 2053 } 2054 out: 2055 return (error); 2056 } 2057 2058 /* 2059 * Terminates a multi-part dual mac/decrypt operation. 2060 */ 2061 /* ARGSUSED */ 2062 int 2063 crypto_mac_decrypt_final(crypto_context_t context, crypto_data_t *mac, 2064 crypto_data_t *pt, crypto_call_req_t *cr) 2065 { 2066 crypto_ctx_t *ctx = (crypto_ctx_t *)context, *mac_ctx; 2067 kcf_context_t *kcf_ctx, *kcf_mac_ctx; 2068 kcf_provider_desc_t *pd; 2069 int error; 2070 kcf_req_params_t params; 2071 2072 if ((ctx == NULL) || 2073 ((kcf_ctx = (kcf_context_t *)ctx->cc_framework_private) == NULL) || 2074 ((pd = kcf_ctx->kc_prov_desc) == NULL)) { 2075 return (CRYPTO_INVALID_CONTEXT); 2076 } 2077 2078 ASSERT(pd->pd_prov_type != CRYPTO_LOGICAL_PROVIDER); 2079 2080 if ((kcf_mac_ctx = kcf_ctx->kc_secondctx) != NULL) { 2081 crypto_call_flag_t save_flag; 2082 2083 if (kcf_mac_ctx->kc_prov_desc == NULL) { 2084 error = CRYPTO_INVALID_CONTEXT; 2085 goto out; 2086 } 2087 mac_ctx = &kcf_mac_ctx->kc_glbl_ctx; 2088 2089 /* First we collect the MAC */ 2090 if (cr == NULL) { 2091 2092 error = crypto_mac_final((crypto_context_t)mac_ctx, 2093 mac, NULL); 2094 2095 if (error != CRYPTO_SUCCESS) { 2096 crypto_cancel_ctx(ctx); 2097 } else { 2098 /* Get the last chunk of plaintext */ 2099 error = crypto_decrypt_final(context, pt, NULL); 2100 } 2101 2102 return (error); 2103 } 2104 /* submit a pure asynchronous request. */ 2105 save_flag = cr->cr_flag; 2106 cr->cr_flag |= CRYPTO_ALWAYS_QUEUE; 2107 2108 KCF_WRAP_MAC_DECRYPT_OPS_PARAMS(¶ms, KCF_OP_FINAL, 2109 pd->pd_sid, NULL, NULL, NULL, mac, pt, NULL, NULL) 2110 2111 2112 error = kcf_submit_request(pd, ctx, cr, ¶ms, B_FALSE); 2113 2114 cr->cr_flag = save_flag; 2115 2116 return (error); 2117 } 2118 2119 /* The fast path for SW providers. */ 2120 if (CHECK_FASTPATH(cr, pd)) { 2121 error = KCF_PROV_MAC_DECRYPT_FINAL(pd, ctx, mac, pt, NULL); 2122 KCF_PROV_INCRSTATS(pd, error); 2123 } else { 2124 KCF_WRAP_MAC_DECRYPT_OPS_PARAMS(¶ms, KCF_OP_FINAL, 2125 ctx->cc_session, NULL, NULL, NULL, mac, pt, NULL, NULL); 2126 2127 error = kcf_submit_request(pd, ctx, cr, ¶ms, B_FALSE); 2128 } 2129 out: 2130 /* Release the hold done in kcf_new_ctx() during init step. */ 2131 KCF_CONTEXT_COND_RELEASE(error, kcf_ctx); 2132 return (error); 2133 } 2134 2135 /* 2136 * Digest/Encrypt dual operation. Project-private entry point, not part of 2137 * the k-API. 2138 */ 2139 /* ARGSUSED */ 2140 int 2141 crypto_digest_encrypt_update(crypto_context_t digest_ctx, 2142 crypto_context_t encrypt_ctx, crypto_data_t *plaintext, 2143 crypto_data_t *ciphertext, crypto_call_req_t *crq) 2144 { 2145 /* 2146 * RFE 4688647: 2147 * core functions needed by ioctl interface missing from impl.h 2148 */ 2149 return (CRYPTO_NOT_SUPPORTED); 2150 } 2151 2152 /* 2153 * Decrypt/Digest dual operation. Project-private entry point, not part of 2154 * the k-API. 2155 */ 2156 /* ARGSUSED */ 2157 int 2158 crypto_decrypt_digest_update(crypto_context_t decryptctx, 2159 crypto_context_t encrypt_ctx, crypto_data_t *ciphertext, 2160 crypto_data_t *plaintext, crypto_call_req_t *crq) 2161 { 2162 /* 2163 * RFE 4688647: 2164 * core functions needed by ioctl interface missing from impl.h 2165 */ 2166 return (CRYPTO_NOT_SUPPORTED); 2167 } 2168 2169 /* 2170 * Sign/Encrypt dual operation. Project-private entry point, not part of 2171 * the k-API. 2172 */ 2173 /* ARGSUSED */ 2174 int 2175 crypto_sign_encrypt_update(crypto_context_t sign_ctx, 2176 crypto_context_t encrypt_ctx, crypto_data_t *plaintext, 2177 crypto_data_t *ciphertext, crypto_call_req_t *crq) 2178 { 2179 /* 2180 * RFE 4688647: 2181 * core functions needed by ioctl interface missing from impl.h 2182 */ 2183 return (CRYPTO_NOT_SUPPORTED); 2184 } 2185 2186 /* 2187 * Decrypt/Verify dual operation. Project-private entry point, not part of 2188 * the k-API. 2189 */ 2190 /* ARGSUSED */ 2191 int 2192 crypto_decrypt_verify_update(crypto_context_t decrypt_ctx, 2193 crypto_context_t verify_ctx, crypto_data_t *ciphertext, 2194 crypto_data_t *plaintext, crypto_call_req_t *crq) 2195 { 2196 /* 2197 * RFE 4688647: 2198 * core functions needed by ioctl interface missing from impl.h 2199 */ 2200 return (CRYPTO_NOT_SUPPORTED); 2201 } 2202