1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright(c) 2016-2017 Intel Corporation 3 */ 4 5 #include <string.h> 6 7 #include <rte_common.h> 8 #include <rte_malloc.h> 9 #include <rte_cryptodev_pmd.h> 10 11 #include "rte_openssl_pmd_private.h" 12 13 14 static const struct rte_cryptodev_capabilities openssl_pmd_capabilities[] = { 15 { /* MD5 HMAC */ 16 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 17 {.sym = { 18 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 19 {.auth = { 20 .algo = RTE_CRYPTO_AUTH_MD5_HMAC, 21 .block_size = 64, 22 .key_size = { 23 .min = 1, 24 .max = 64, 25 .increment = 1 26 }, 27 .digest_size = { 28 .min = 16, 29 .max = 16, 30 .increment = 0 31 }, 32 .iv_size = { 0 } 33 }, } 34 }, } 35 }, 36 { /* MD5 */ 37 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 38 {.sym = { 39 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 40 {.auth = { 41 .algo = RTE_CRYPTO_AUTH_MD5, 42 .block_size = 64, 43 .key_size = { 44 .min = 0, 45 .max = 0, 46 .increment = 0 47 }, 48 .digest_size = { 49 .min = 16, 50 .max = 16, 51 .increment = 0 52 }, 53 .iv_size = { 0 } 54 }, } 55 }, } 56 }, 57 { /* SHA1 HMAC */ 58 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 59 {.sym = { 60 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 61 {.auth = { 62 .algo = RTE_CRYPTO_AUTH_SHA1_HMAC, 63 .block_size = 64, 64 .key_size = { 65 .min = 1, 66 .max = 64, 67 .increment = 1 68 }, 69 .digest_size = { 70 .min = 20, 71 .max = 20, 72 .increment = 0 73 }, 74 .iv_size = { 0 } 75 }, } 76 }, } 77 }, 78 { /* SHA1 */ 79 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 80 {.sym = { 81 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 82 {.auth = { 83 .algo = RTE_CRYPTO_AUTH_SHA1, 84 .block_size = 64, 85 .key_size = { 86 .min = 0, 87 .max = 0, 88 .increment = 0 89 }, 90 .digest_size = { 91 .min = 20, 92 .max = 20, 93 .increment = 0 94 }, 95 .iv_size = { 0 } 96 }, } 97 }, } 98 }, 99 { /* SHA224 HMAC */ 100 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 101 {.sym = { 102 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 103 {.auth = { 104 .algo = RTE_CRYPTO_AUTH_SHA224_HMAC, 105 .block_size = 64, 106 .key_size = { 107 .min = 1, 108 .max = 64, 109 .increment = 1 110 }, 111 .digest_size = { 112 .min = 28, 113 .max = 28, 114 .increment = 0 115 }, 116 .iv_size = { 0 } 117 }, } 118 }, } 119 }, 120 { /* SHA224 */ 121 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 122 {.sym = { 123 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 124 {.auth = { 125 .algo = RTE_CRYPTO_AUTH_SHA224, 126 .block_size = 64, 127 .key_size = { 128 .min = 0, 129 .max = 0, 130 .increment = 0 131 }, 132 .digest_size = { 133 .min = 28, 134 .max = 28, 135 .increment = 0 136 }, 137 .iv_size = { 0 } 138 }, } 139 }, } 140 }, 141 { /* SHA256 HMAC */ 142 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 143 {.sym = { 144 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 145 {.auth = { 146 .algo = RTE_CRYPTO_AUTH_SHA256_HMAC, 147 .block_size = 64, 148 .key_size = { 149 .min = 1, 150 .max = 64, 151 .increment = 1 152 }, 153 .digest_size = { 154 .min = 32, 155 .max = 32, 156 .increment = 0 157 }, 158 .iv_size = { 0 } 159 }, } 160 }, } 161 }, 162 { /* SHA256 */ 163 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 164 {.sym = { 165 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 166 {.auth = { 167 .algo = RTE_CRYPTO_AUTH_SHA256, 168 .block_size = 64, 169 .key_size = { 170 .min = 0, 171 .max = 0, 172 .increment = 0 173 }, 174 .digest_size = { 175 .min = 32, 176 .max = 32, 177 .increment = 0 178 }, 179 .iv_size = { 0 } 180 }, } 181 }, } 182 }, 183 { /* SHA384 HMAC */ 184 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 185 {.sym = { 186 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 187 {.auth = { 188 .algo = RTE_CRYPTO_AUTH_SHA384_HMAC, 189 .block_size = 128, 190 .key_size = { 191 .min = 1, 192 .max = 128, 193 .increment = 1 194 }, 195 .digest_size = { 196 .min = 48, 197 .max = 48, 198 .increment = 0 199 }, 200 .iv_size = { 0 } 201 }, } 202 }, } 203 }, 204 { /* SHA384 */ 205 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 206 {.sym = { 207 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 208 {.auth = { 209 .algo = RTE_CRYPTO_AUTH_SHA384, 210 .block_size = 128, 211 .key_size = { 212 .min = 0, 213 .max = 0, 214 .increment = 0 215 }, 216 .digest_size = { 217 .min = 48, 218 .max = 48, 219 .increment = 0 220 }, 221 .iv_size = { 0 } 222 }, } 223 }, } 224 }, 225 { /* SHA512 HMAC */ 226 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 227 {.sym = { 228 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 229 {.auth = { 230 .algo = RTE_CRYPTO_AUTH_SHA512_HMAC, 231 .block_size = 128, 232 .key_size = { 233 .min = 1, 234 .max = 128, 235 .increment = 1 236 }, 237 .digest_size = { 238 .min = 64, 239 .max = 64, 240 .increment = 0 241 }, 242 .iv_size = { 0 } 243 }, } 244 }, } 245 }, 246 { /* SHA512 */ 247 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 248 {.sym = { 249 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 250 {.auth = { 251 .algo = RTE_CRYPTO_AUTH_SHA512, 252 .block_size = 128, 253 .key_size = { 254 .min = 0, 255 .max = 0, 256 .increment = 0 257 }, 258 .digest_size = { 259 .min = 64, 260 .max = 64, 261 .increment = 0 262 }, 263 .iv_size = { 0 } 264 }, } 265 }, } 266 }, 267 { /* AES CBC */ 268 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 269 {.sym = { 270 .xform_type = RTE_CRYPTO_SYM_XFORM_CIPHER, 271 {.cipher = { 272 .algo = RTE_CRYPTO_CIPHER_AES_CBC, 273 .block_size = 16, 274 .key_size = { 275 .min = 16, 276 .max = 32, 277 .increment = 8 278 }, 279 .iv_size = { 280 .min = 16, 281 .max = 16, 282 .increment = 0 283 } 284 }, } 285 }, } 286 }, 287 { /* AES CTR */ 288 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 289 {.sym = { 290 .xform_type = RTE_CRYPTO_SYM_XFORM_CIPHER, 291 {.cipher = { 292 .algo = RTE_CRYPTO_CIPHER_AES_CTR, 293 .block_size = 16, 294 .key_size = { 295 .min = 16, 296 .max = 32, 297 .increment = 8 298 }, 299 .iv_size = { 300 .min = 16, 301 .max = 16, 302 .increment = 0 303 } 304 }, } 305 }, } 306 }, 307 { /* AES GCM */ 308 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 309 {.sym = { 310 .xform_type = RTE_CRYPTO_SYM_XFORM_AEAD, 311 {.aead = { 312 .algo = RTE_CRYPTO_AEAD_AES_GCM, 313 .block_size = 16, 314 .key_size = { 315 .min = 16, 316 .max = 32, 317 .increment = 8 318 }, 319 .digest_size = { 320 .min = 16, 321 .max = 16, 322 .increment = 0 323 }, 324 .aad_size = { 325 .min = 0, 326 .max = 65535, 327 .increment = 1 328 }, 329 .iv_size = { 330 .min = 12, 331 .max = 16, 332 .increment = 4 333 }, 334 }, } 335 }, } 336 }, 337 { /* AES CCM */ 338 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 339 {.sym = { 340 .xform_type = RTE_CRYPTO_SYM_XFORM_AEAD, 341 {.aead = { 342 .algo = RTE_CRYPTO_AEAD_AES_CCM, 343 .block_size = 16, 344 .key_size = { 345 .min = 16, 346 .max = 32, 347 .increment = 8 348 }, 349 .digest_size = { 350 .min = 4, 351 .max = 16, 352 .increment = 2 353 }, 354 .aad_size = { 355 .min = 0, 356 .max = 65535, 357 .increment = 1 358 }, 359 .iv_size = { 360 .min = 7, 361 .max = 13, 362 .increment = 1 363 }, 364 }, } 365 }, } 366 }, 367 { /* AES GMAC (AUTH) */ 368 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 369 {.sym = { 370 .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH, 371 {.auth = { 372 .algo = RTE_CRYPTO_AUTH_AES_GMAC, 373 .block_size = 16, 374 .key_size = { 375 .min = 16, 376 .max = 32, 377 .increment = 8 378 }, 379 .digest_size = { 380 .min = 16, 381 .max = 16, 382 .increment = 0 383 }, 384 .iv_size = { 385 .min = 12, 386 .max = 16, 387 .increment = 4 388 } 389 }, } 390 }, } 391 }, 392 { /* 3DES CBC */ 393 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 394 {.sym = { 395 .xform_type = RTE_CRYPTO_SYM_XFORM_CIPHER, 396 {.cipher = { 397 .algo = RTE_CRYPTO_CIPHER_3DES_CBC, 398 .block_size = 8, 399 .key_size = { 400 .min = 8, 401 .max = 24, 402 .increment = 8 403 }, 404 .iv_size = { 405 .min = 8, 406 .max = 8, 407 .increment = 0 408 } 409 }, } 410 }, } 411 }, 412 { /* 3DES CTR */ 413 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 414 {.sym = { 415 .xform_type = RTE_CRYPTO_SYM_XFORM_CIPHER, 416 {.cipher = { 417 .algo = RTE_CRYPTO_CIPHER_3DES_CTR, 418 .block_size = 8, 419 .key_size = { 420 .min = 16, 421 .max = 24, 422 .increment = 8 423 }, 424 .iv_size = { 425 .min = 8, 426 .max = 8, 427 .increment = 0 428 } 429 }, } 430 }, } 431 }, 432 { /* DES CBC */ 433 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 434 {.sym = { 435 .xform_type = RTE_CRYPTO_SYM_XFORM_CIPHER, 436 {.cipher = { 437 .algo = RTE_CRYPTO_CIPHER_DES_CBC, 438 .block_size = 8, 439 .key_size = { 440 .min = 8, 441 .max = 8, 442 .increment = 0 443 }, 444 .iv_size = { 445 .min = 8, 446 .max = 8, 447 .increment = 0 448 } 449 }, } 450 }, } 451 }, 452 { /* DES DOCSIS BPI */ 453 .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC, 454 {.sym = { 455 .xform_type = RTE_CRYPTO_SYM_XFORM_CIPHER, 456 {.cipher = { 457 .algo = RTE_CRYPTO_CIPHER_DES_DOCSISBPI, 458 .block_size = 8, 459 .key_size = { 460 .min = 8, 461 .max = 8, 462 .increment = 0 463 }, 464 .iv_size = { 465 .min = 8, 466 .max = 8, 467 .increment = 0 468 } 469 }, } 470 }, } 471 }, 472 473 RTE_CRYPTODEV_END_OF_CAPABILITIES_LIST() 474 }; 475 476 477 /** Configure device */ 478 static int 479 openssl_pmd_config(__rte_unused struct rte_cryptodev *dev, 480 __rte_unused struct rte_cryptodev_config *config) 481 { 482 return 0; 483 } 484 485 /** Start device */ 486 static int 487 openssl_pmd_start(__rte_unused struct rte_cryptodev *dev) 488 { 489 return 0; 490 } 491 492 /** Stop device */ 493 static void 494 openssl_pmd_stop(__rte_unused struct rte_cryptodev *dev) 495 { 496 } 497 498 /** Close device */ 499 static int 500 openssl_pmd_close(__rte_unused struct rte_cryptodev *dev) 501 { 502 return 0; 503 } 504 505 506 /** Get device statistics */ 507 static void 508 openssl_pmd_stats_get(struct rte_cryptodev *dev, 509 struct rte_cryptodev_stats *stats) 510 { 511 int qp_id; 512 513 for (qp_id = 0; qp_id < dev->data->nb_queue_pairs; qp_id++) { 514 struct openssl_qp *qp = dev->data->queue_pairs[qp_id]; 515 516 stats->enqueued_count += qp->stats.enqueued_count; 517 stats->dequeued_count += qp->stats.dequeued_count; 518 519 stats->enqueue_err_count += qp->stats.enqueue_err_count; 520 stats->dequeue_err_count += qp->stats.dequeue_err_count; 521 } 522 } 523 524 /** Reset device statistics */ 525 static void 526 openssl_pmd_stats_reset(struct rte_cryptodev *dev) 527 { 528 int qp_id; 529 530 for (qp_id = 0; qp_id < dev->data->nb_queue_pairs; qp_id++) { 531 struct openssl_qp *qp = dev->data->queue_pairs[qp_id]; 532 533 memset(&qp->stats, 0, sizeof(qp->stats)); 534 } 535 } 536 537 538 /** Get device info */ 539 static void 540 openssl_pmd_info_get(struct rte_cryptodev *dev, 541 struct rte_cryptodev_info *dev_info) 542 { 543 struct openssl_private *internals = dev->data->dev_private; 544 545 if (dev_info != NULL) { 546 dev_info->driver_id = dev->driver_id; 547 dev_info->feature_flags = dev->feature_flags; 548 dev_info->capabilities = openssl_pmd_capabilities; 549 dev_info->max_nb_queue_pairs = internals->max_nb_qpairs; 550 /* No limit of number of sessions */ 551 dev_info->sym.max_nb_sessions = 0; 552 } 553 } 554 555 /** Release queue pair */ 556 static int 557 openssl_pmd_qp_release(struct rte_cryptodev *dev, uint16_t qp_id) 558 { 559 if (dev->data->queue_pairs[qp_id] != NULL) { 560 rte_free(dev->data->queue_pairs[qp_id]); 561 dev->data->queue_pairs[qp_id] = NULL; 562 } 563 return 0; 564 } 565 566 /** set a unique name for the queue pair based on it's name, dev_id and qp_id */ 567 static int 568 openssl_pmd_qp_set_unique_name(struct rte_cryptodev *dev, 569 struct openssl_qp *qp) 570 { 571 unsigned int n = snprintf(qp->name, sizeof(qp->name), 572 "openssl_pmd_%u_qp_%u", 573 dev->data->dev_id, qp->id); 574 575 if (n >= sizeof(qp->name)) 576 return -1; 577 578 return 0; 579 } 580 581 582 /** Create a ring to place processed operations on */ 583 static struct rte_ring * 584 openssl_pmd_qp_create_processed_ops_ring(struct openssl_qp *qp, 585 unsigned int ring_size, int socket_id) 586 { 587 struct rte_ring *r; 588 589 r = rte_ring_lookup(qp->name); 590 if (r) { 591 if (rte_ring_get_size(r) >= ring_size) { 592 OPENSSL_LOG(INFO, 593 "Reusing existing ring %s for processed ops", 594 qp->name); 595 return r; 596 } 597 598 OPENSSL_LOG(ERR, 599 "Unable to reuse existing ring %s for processed ops", 600 qp->name); 601 return NULL; 602 } 603 604 return rte_ring_create(qp->name, ring_size, socket_id, 605 RING_F_SP_ENQ | RING_F_SC_DEQ); 606 } 607 608 609 /** Setup a queue pair */ 610 static int 611 openssl_pmd_qp_setup(struct rte_cryptodev *dev, uint16_t qp_id, 612 const struct rte_cryptodev_qp_conf *qp_conf, 613 int socket_id, struct rte_mempool *session_pool) 614 { 615 struct openssl_qp *qp = NULL; 616 617 /* Free memory prior to re-allocation if needed. */ 618 if (dev->data->queue_pairs[qp_id] != NULL) 619 openssl_pmd_qp_release(dev, qp_id); 620 621 /* Allocate the queue pair data structure. */ 622 qp = rte_zmalloc_socket("OPENSSL PMD Queue Pair", sizeof(*qp), 623 RTE_CACHE_LINE_SIZE, socket_id); 624 if (qp == NULL) 625 return -ENOMEM; 626 627 qp->id = qp_id; 628 dev->data->queue_pairs[qp_id] = qp; 629 630 if (openssl_pmd_qp_set_unique_name(dev, qp)) 631 goto qp_setup_cleanup; 632 633 qp->processed_ops = openssl_pmd_qp_create_processed_ops_ring(qp, 634 qp_conf->nb_descriptors, socket_id); 635 if (qp->processed_ops == NULL) 636 goto qp_setup_cleanup; 637 638 qp->sess_mp = session_pool; 639 640 memset(&qp->stats, 0, sizeof(qp->stats)); 641 642 return 0; 643 644 qp_setup_cleanup: 645 if (qp) 646 rte_free(qp); 647 648 return -1; 649 } 650 651 /** Return the number of allocated queue pairs */ 652 static uint32_t 653 openssl_pmd_qp_count(struct rte_cryptodev *dev) 654 { 655 return dev->data->nb_queue_pairs; 656 } 657 658 /** Returns the size of the session structure */ 659 static unsigned 660 openssl_pmd_sym_session_get_size(struct rte_cryptodev *dev __rte_unused) 661 { 662 return sizeof(struct openssl_session); 663 } 664 665 /** Configure the session from a crypto xform chain */ 666 static int 667 openssl_pmd_sym_session_configure(struct rte_cryptodev *dev __rte_unused, 668 struct rte_crypto_sym_xform *xform, 669 struct rte_cryptodev_sym_session *sess, 670 struct rte_mempool *mempool) 671 { 672 void *sess_private_data; 673 int ret; 674 675 if (unlikely(sess == NULL)) { 676 OPENSSL_LOG(ERR, "invalid session struct"); 677 return -EINVAL; 678 } 679 680 if (rte_mempool_get(mempool, &sess_private_data)) { 681 OPENSSL_LOG(ERR, 682 "Couldn't get object from session mempool"); 683 return -ENOMEM; 684 } 685 686 ret = openssl_set_session_parameters(sess_private_data, xform); 687 if (ret != 0) { 688 OPENSSL_LOG(ERR, "failed configure session parameters"); 689 690 /* Return session to mempool */ 691 rte_mempool_put(mempool, sess_private_data); 692 return ret; 693 } 694 695 set_sym_session_private_data(sess, dev->driver_id, 696 sess_private_data); 697 698 return 0; 699 } 700 701 702 /** Clear the memory of session so it doesn't leave key material behind */ 703 static void 704 openssl_pmd_sym_session_clear(struct rte_cryptodev *dev, 705 struct rte_cryptodev_sym_session *sess) 706 { 707 uint8_t index = dev->driver_id; 708 void *sess_priv = get_sym_session_private_data(sess, index); 709 710 /* Zero out the whole structure */ 711 if (sess_priv) { 712 openssl_reset_session(sess_priv); 713 memset(sess_priv, 0, sizeof(struct openssl_session)); 714 struct rte_mempool *sess_mp = rte_mempool_from_obj(sess_priv); 715 set_sym_session_private_data(sess, index, NULL); 716 rte_mempool_put(sess_mp, sess_priv); 717 } 718 } 719 720 struct rte_cryptodev_ops openssl_pmd_ops = { 721 .dev_configure = openssl_pmd_config, 722 .dev_start = openssl_pmd_start, 723 .dev_stop = openssl_pmd_stop, 724 .dev_close = openssl_pmd_close, 725 726 .stats_get = openssl_pmd_stats_get, 727 .stats_reset = openssl_pmd_stats_reset, 728 729 .dev_infos_get = openssl_pmd_info_get, 730 731 .queue_pair_setup = openssl_pmd_qp_setup, 732 .queue_pair_release = openssl_pmd_qp_release, 733 .queue_pair_count = openssl_pmd_qp_count, 734 735 .sym_session_get_size = openssl_pmd_sym_session_get_size, 736 .sym_session_configure = openssl_pmd_sym_session_configure, 737 .sym_session_clear = openssl_pmd_sym_session_clear 738 }; 739 740 struct rte_cryptodev_ops *rte_openssl_pmd_ops = &openssl_pmd_ops; 741