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.
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.
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]
22 * Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved.
23 * Copyright 2018, Joyent, Inc.
30 #include <cryptoutil.h>
32 #include <security/cryptoki.h>
33 #include <sys/crypto/common.h>
34 #include <sys/crypto/ioctl.h>
35 #include "kernelGlobal.h"
36 #include "kernelObject.h"
37 #include "kernelSlot.h"
39 #define ENCODE_ATTR(type, value, len) { \
40 cur_attr->oa_type = type; \
41 (void) memcpy(ptr, value, len); \
42 cur_attr->oa_value = ptr; \
43 cur_attr->oa_value_len = len; \
47 #define MECH_HASH(type) (((uintptr_t)type) % KMECH_HASHTABLE_SIZE)
49 * Serialize writes to the hash table. We don't need a per bucket lock as
50 * there are only a few writes and we don't need the lock for reads.
52 pthread_mutex_t mechhash_mutex
= PTHREAD_MUTEX_INITIALIZER
;
55 kmech_hash_insert(CK_MECHANISM_TYPE type
, crypto_mech_type_t kmech
)
58 kmh_elem_t
*elem
, *cur
;
60 elem
= malloc(sizeof (kmh_elem_t
));
62 return (CKR_HOST_MEMORY
);
68 (void) pthread_mutex_lock(&mechhash_mutex
);
69 for (cur
= kernel_mechhash
[h
]; cur
!= NULL
; cur
= cur
->knext
) {
70 if (type
== cur
->type
) {
71 /* Some other thread beat us to it. */
72 (void) pthread_mutex_unlock(&mechhash_mutex
);
77 elem
->knext
= kernel_mechhash
[h
];
78 kernel_mechhash
[h
] = elem
;
79 (void) pthread_mutex_unlock(&mechhash_mutex
);
85 kernel_mech(CK_MECHANISM_TYPE type
, crypto_mech_type_t
*k_number
)
87 crypto_get_mechanism_number_t get_number
;
93 char buf
[11]; /* Num chars for representing ulong in ASCII */
96 * Search for an existing entry. No need to lock since we are
97 * just a reader and we never free the entries in the hash table.
100 for (elem
= kernel_mechhash
[h
]; elem
!= NULL
; elem
= elem
->knext
) {
101 if (type
== elem
->type
) {
102 *k_number
= elem
->kmech
;
107 if (type
>= CKM_VENDOR_DEFINED
) {
108 (void) snprintf(buf
, sizeof (buf
), "%#lx", type
);
111 string
= pkcs11_mech2str(type
);
115 return (CKR_MECHANISM_INVALID
);
117 get_number
.pn_mechanism_string
= (char *)string
;
118 get_number
.pn_mechanism_len
= strlen(string
) + 1;
120 while ((r
= ioctl(kernel_fd
, CRYPTO_GET_MECHANISM_NUMBER
,
126 rv
= CKR_MECHANISM_INVALID
;
128 if (get_number
.pn_return_value
!= CRYPTO_SUCCESS
) {
129 rv
= crypto2pkcs11_error_number(
130 get_number
.pn_return_value
);
137 *k_number
= get_number
.pn_internal_number
;
138 /* Add this to the hash table */
139 (void) kmech_hash_insert(type
, *k_number
);
147 * Return the value of a secret key object.
148 * This routine allocates memory for the value.
149 * A null pointer is returned on error.
152 get_symmetric_key_value(kernel_object_t
*key_p
)
156 switch (key_p
->class) {
160 cipherKey
= malloc(OBJ_SEC(key_p
)->sk_value_len
);
161 if (cipherKey
== NULL
)
164 (void) memcpy(cipherKey
, OBJ_SEC(key_p
)->sk_value
,
165 OBJ_SEC(key_p
)->sk_value_len
);
175 * Convert a RSA private key object into a crypto_key structure.
176 * Memory is allocated for each attribute stored in the crypto_key
177 * structure. Memory for the crypto_key structure is not
178 * allocated. Attributes can be freed by free_key_attributes().
181 get_rsa_private_key(kernel_object_t
*object_p
, crypto_key_t
*key
)
184 crypto_object_attribute_t
*attrs
, *cur_attr
;
188 (void) pthread_mutex_lock(&object_p
->object_mutex
);
189 if (object_p
->key_type
!= CKK_RSA
||
190 object_p
->class != CKO_PRIVATE_KEY
) {
191 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
192 return (CKR_ATTRIBUTE_TYPE_INVALID
);
196 RSA_PRI_ATTR_COUNT
* sizeof (crypto_object_attribute_t
));
198 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
199 return (CKR_HOST_MEMORY
);
202 key
->ck_format
= CRYPTO_KEY_ATTR_LIST
;
203 key
->ck_attrs
= attrs
;
207 * Allocate memory for each key attribute and set up the value
212 /* CKA_MODULUS is required. */
213 big
= OBJ_PRI_RSA_MOD(object_p
);
214 if (big
->big_value
== NULL
) {
215 rv
= CKR_ATTRIBUTE_TYPE_INVALID
;
218 if ((ptr
= malloc(big
->big_value_len
)) == NULL
) {
219 rv
= CKR_HOST_MEMORY
;
222 ENCODE_ATTR(CKA_MODULUS
, big
->big_value
, big
->big_value_len
);
226 /* CKA_PRIVATE_EXPONENT is required. */
227 big
= OBJ_PRI_RSA_PRIEXPO(object_p
);
228 if (big
->big_value
== NULL
) {
229 rv
= CKR_ATTRIBUTE_TYPE_INVALID
;
232 if ((ptr
= malloc(big
->big_value_len
)) == NULL
) {
233 rv
= CKR_HOST_MEMORY
;
236 ENCODE_ATTR(CKA_PRIVATE_EXPONENT
, big
->big_value
,
241 /* CKA_PRIME_1 is optional. */
242 big
= OBJ_PRI_RSA_PRIME1(object_p
);
243 if (big
->big_value
!= NULL
) {
244 if ((ptr
= malloc(big
->big_value_len
)) == NULL
) {
245 rv
= CKR_HOST_MEMORY
;
248 ENCODE_ATTR(CKA_PRIME_1
, big
->big_value
, big
->big_value_len
);
252 /* CKA_PRIME_2 is optional. */
253 big
= OBJ_PRI_RSA_PRIME2(object_p
);
254 if (big
->big_value
!= NULL
) {
255 if ((ptr
= malloc(big
->big_value_len
)) == NULL
) {
256 rv
= CKR_HOST_MEMORY
;
259 ENCODE_ATTR(CKA_PRIME_2
, big
->big_value
, big
->big_value_len
);
263 /* CKA_EXPONENT_1 is optional. */
264 big
= OBJ_PRI_RSA_EXPO1(object_p
);
265 if (big
->big_value
!= NULL
) {
266 if ((ptr
= malloc(big
->big_value_len
)) == NULL
) {
267 rv
= CKR_HOST_MEMORY
;
270 ENCODE_ATTR(CKA_EXPONENT_1
, big
->big_value
,
275 /* CKA_EXPONENT_2 is optional. */
276 big
= OBJ_PRI_RSA_EXPO2(object_p
);
277 if (big
->big_value
!= NULL
) {
278 if ((ptr
= malloc(big
->big_value_len
)) == NULL
) {
279 rv
= CKR_HOST_MEMORY
;
282 ENCODE_ATTR(CKA_EXPONENT_2
, big
->big_value
,
287 /* CKA_COEFFICIENT is optional. */
288 big
= OBJ_PRI_RSA_COEF(object_p
);
289 if (big
->big_value
!= NULL
) {
290 if ((ptr
= malloc(big
->big_value_len
)) == NULL
) {
291 rv
= CKR_HOST_MEMORY
;
294 ENCODE_ATTR(CKA_COEFFICIENT
, big
->big_value
,
299 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
303 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
304 free_key_attributes(key
);
309 * Convert a RSA public key object into a crypto_key structure.
310 * Memory is allocated for each attribute stored in the crypto_key
311 * structure. Memory for the crypto_key structure is not
312 * allocated. Attributes can be freed by free_key_attributes().
315 get_rsa_public_key(kernel_object_t
*object_p
, crypto_key_t
*key
)
318 crypto_object_attribute_t
*attrs
, *cur_attr
;
321 (void) pthread_mutex_lock(&object_p
->object_mutex
);
322 if (object_p
->key_type
!= CKK_RSA
||
323 object_p
->class != CKO_PUBLIC_KEY
) {
324 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
325 return (CKR_ATTRIBUTE_TYPE_INVALID
);
329 RSA_PUB_ATTR_COUNT
* sizeof (crypto_object_attribute_t
));
331 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
332 return (CKR_HOST_MEMORY
);
335 key
->ck_format
= CRYPTO_KEY_ATTR_LIST
;
336 key
->ck_count
= RSA_PUB_ATTR_COUNT
;
337 key
->ck_attrs
= attrs
;
340 big
= OBJ_PUB_RSA_PUBEXPO(object_p
);
341 if ((ptr
= malloc(big
->big_value_len
)) == NULL
)
343 ENCODE_ATTR(CKA_PUBLIC_EXPONENT
, big
->big_value
, big
->big_value_len
);
345 big
= OBJ_PUB_RSA_MOD(object_p
);
346 if ((ptr
= malloc(big
->big_value_len
)) == NULL
)
348 ENCODE_ATTR(CKA_MODULUS
, big
->big_value
, big
->big_value_len
);
350 if ((ptr
= malloc(sizeof (CK_ULONG
))) == NULL
)
352 ENCODE_ATTR(CKA_MODULUS_BITS
, &OBJ_PUB_RSA_MOD_BITS(object_p
),
355 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
359 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
360 free_key_attributes(key
);
361 return (CKR_HOST_MEMORY
);
365 * Free attribute storage in a crypto_key structure.
368 free_key_attributes(crypto_key_t
*key
)
372 if (key
->ck_format
== CRYPTO_KEY_ATTR_LIST
&&
373 (key
->ck_count
> 0) && key
->ck_attrs
!= NULL
) {
374 for (i
= 0; i
< key
->ck_count
; i
++) {
375 freezero(key
->ck_attrs
[i
].oa_value
,
376 key
->ck_attrs
[i
].oa_value_len
);
384 * Convert a DSA private key object into a crypto_key structure.
385 * Memory is allocated for each attribute stored in the crypto_key
386 * structure. Memory for the crypto_key structure is not
387 * allocated. Attributes can be freed by free_dsa_key_attributes().
390 get_dsa_private_key(kernel_object_t
*object_p
, crypto_key_t
*key
)
393 crypto_object_attribute_t
*attrs
, *cur_attr
;
396 (void) pthread_mutex_lock(&object_p
->object_mutex
);
397 if (object_p
->key_type
!= CKK_DSA
||
398 object_p
->class != CKO_PRIVATE_KEY
) {
399 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
400 return (CKR_ATTRIBUTE_TYPE_INVALID
);
404 DSA_ATTR_COUNT
* sizeof (crypto_object_attribute_t
));
406 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
407 return (CKR_HOST_MEMORY
);
410 key
->ck_format
= CRYPTO_KEY_ATTR_LIST
;
411 key
->ck_count
= DSA_ATTR_COUNT
;
412 key
->ck_attrs
= attrs
;
415 big
= OBJ_PRI_DSA_PRIME(object_p
);
416 if ((ptr
= malloc(big
->big_value_len
)) == NULL
)
418 ENCODE_ATTR(CKA_PRIME
, big
->big_value
, big
->big_value_len
);
420 big
= OBJ_PRI_DSA_SUBPRIME(object_p
);
421 if ((ptr
= malloc(big
->big_value_len
)) == NULL
)
423 ENCODE_ATTR(CKA_SUBPRIME
, big
->big_value
, big
->big_value_len
);
425 big
= OBJ_PRI_DSA_BASE(object_p
);
426 if ((ptr
= malloc(big
->big_value_len
)) == NULL
)
428 ENCODE_ATTR(CKA_BASE
, big
->big_value
, big
->big_value_len
);
430 big
= OBJ_PRI_DSA_VALUE(object_p
);
431 if ((ptr
= malloc(big
->big_value_len
)) == NULL
)
433 ENCODE_ATTR(CKA_VALUE
, big
->big_value
, big
->big_value_len
);
435 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
439 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
440 free_key_attributes(key
);
441 return (CKR_HOST_MEMORY
);
446 * Convert a DSA public key object into a crypto_key structure.
447 * Memory is allocated for each attribute stored in the crypto_key
448 * structure. Memory for the crypto_key structure is not
449 * allocated. Attributes can be freed by free_dsa_key_attributes().
452 get_dsa_public_key(kernel_object_t
*object_p
, crypto_key_t
*key
)
455 crypto_object_attribute_t
*attrs
, *cur_attr
;
458 (void) pthread_mutex_lock(&object_p
->object_mutex
);
459 if (object_p
->key_type
!= CKK_DSA
||
460 object_p
->class != CKO_PUBLIC_KEY
) {
461 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
462 return (CKR_ATTRIBUTE_TYPE_INVALID
);
466 DSA_ATTR_COUNT
* sizeof (crypto_object_attribute_t
));
468 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
469 return (CKR_HOST_MEMORY
);
472 key
->ck_format
= CRYPTO_KEY_ATTR_LIST
;
473 key
->ck_count
= DSA_ATTR_COUNT
;
474 key
->ck_attrs
= attrs
;
477 big
= OBJ_PUB_DSA_PRIME(object_p
);
478 if ((ptr
= malloc(big
->big_value_len
)) == NULL
)
480 ENCODE_ATTR(CKA_PRIME
, big
->big_value
, big
->big_value_len
);
482 big
= OBJ_PUB_DSA_SUBPRIME(object_p
);
483 if ((ptr
= malloc(big
->big_value_len
)) == NULL
)
485 ENCODE_ATTR(CKA_SUBPRIME
, big
->big_value
, big
->big_value_len
);
487 big
= OBJ_PUB_DSA_BASE(object_p
);
488 if ((ptr
= malloc(big
->big_value_len
)) == NULL
)
490 ENCODE_ATTR(CKA_BASE
, big
->big_value
, big
->big_value_len
);
492 big
= OBJ_PUB_DSA_VALUE(object_p
);
493 if ((ptr
= malloc(big
->big_value_len
)) == NULL
)
495 ENCODE_ATTR(CKA_VALUE
, big
->big_value
, big
->big_value_len
);
497 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
501 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
502 free_key_attributes(key
);
503 return (CKR_HOST_MEMORY
);
508 * Convert a EC private key object into a crypto_key structure.
509 * Memory is allocated for each attribute stored in the crypto_key
510 * structure. Memory for the crypto_key structure is not
511 * allocated. Attributes can be freed by free_ec_key_attributes().
514 get_ec_private_key(kernel_object_t
*object_p
, crypto_key_t
*key
)
517 crypto_object_attribute_t
*attrs
, *cur_attr
;
522 (void) pthread_mutex_lock(&object_p
->object_mutex
);
523 if (object_p
->key_type
!= CKK_EC
||
524 object_p
->class != CKO_PRIVATE_KEY
) {
525 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
526 return (CKR_ATTRIBUTE_TYPE_INVALID
);
529 attrs
= calloc(EC_ATTR_COUNT
, sizeof (crypto_object_attribute_t
));
531 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
532 return (CKR_HOST_MEMORY
);
535 key
->ck_format
= CRYPTO_KEY_ATTR_LIST
;
536 key
->ck_count
= EC_ATTR_COUNT
;
537 key
->ck_attrs
= attrs
;
540 big
= OBJ_PRI_EC_VALUE(object_p
);
541 if ((ptr
= malloc(big
->big_value_len
)) == NULL
) {
542 rv
= CKR_HOST_MEMORY
;
545 ENCODE_ATTR(CKA_VALUE
, big
->big_value
, big
->big_value_len
);
547 tmp
.type
= CKA_EC_PARAMS
;
549 rv
= kernel_get_attribute(object_p
, &tmp
);
554 tmp
.pValue
= malloc(tmp
.ulValueLen
);
555 if (tmp
.pValue
== NULL
) {
556 rv
= CKR_HOST_MEMORY
;
560 rv
= kernel_get_attribute(object_p
, &tmp
);
566 cur_attr
->oa_type
= tmp
.type
;
567 cur_attr
->oa_value
= tmp
.pValue
;
568 cur_attr
->oa_value_len
= tmp
.ulValueLen
;
570 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
574 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
575 free_key_attributes(key
);
580 * Convert an EC public key object into a crypto_key structure.
581 * Memory is allocated for each attribute stored in the crypto_key
582 * structure. Memory for the crypto_key structure is not
583 * allocated. Attributes can be freed by free_ec_key_attributes().
586 get_ec_public_key(kernel_object_t
*object_p
, crypto_key_t
*key
)
589 crypto_object_attribute_t
*attrs
, *cur_attr
;
594 (void) pthread_mutex_lock(&object_p
->object_mutex
);
595 if (object_p
->key_type
!= CKK_EC
||
596 object_p
->class != CKO_PUBLIC_KEY
) {
597 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
598 return (CKR_ATTRIBUTE_TYPE_INVALID
);
601 attrs
= calloc(EC_ATTR_COUNT
, sizeof (crypto_object_attribute_t
));
603 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
604 return (CKR_HOST_MEMORY
);
607 key
->ck_format
= CRYPTO_KEY_ATTR_LIST
;
608 key
->ck_count
= EC_ATTR_COUNT
;
609 key
->ck_attrs
= attrs
;
612 big
= OBJ_PUB_EC_POINT(object_p
);
613 if ((ptr
= malloc(big
->big_value_len
)) == NULL
) {
614 rv
= CKR_HOST_MEMORY
;
617 ENCODE_ATTR(CKA_EC_POINT
, big
->big_value
, big
->big_value_len
);
619 tmp
.type
= CKA_EC_PARAMS
;
621 rv
= kernel_get_attribute(object_p
, &tmp
);
626 tmp
.pValue
= malloc(tmp
.ulValueLen
);
627 if (tmp
.pValue
== NULL
) {
628 rv
= CKR_HOST_MEMORY
;
632 rv
= kernel_get_attribute(object_p
, &tmp
);
638 cur_attr
->oa_type
= tmp
.type
;
639 cur_attr
->oa_value
= tmp
.pValue
;
640 cur_attr
->oa_value_len
= tmp
.ulValueLen
;
642 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
646 (void) pthread_mutex_unlock(&object_p
->object_mutex
);
647 free_key_attributes(key
);
652 * Convert an attribute template into an obj_attrs array.
653 * Memory is allocated for each attribute stored in the obj_attrs.
654 * The memory can be freed by free_object_attributes().
656 * If the boolean pointer is_token_obj is not NULL, the caller wants to
657 * retrieve the value of the CKA_TOKEN attribute if it is specified in the
659 * - When this routine is called thru C_CreateObject(), C_CopyObject(), or
660 * any key management function, is_token_obj should NOT be NULL.
661 * - When this routine is called thru C_GetAttributeValue() or
662 * C_SetAttributeValue(), "is_token_obj" should be NULL.
665 process_object_attributes(CK_ATTRIBUTE_PTR pTemplate
, CK_ULONG ulCount
,
666 caddr_t
*obj_attrs
, CK_BBOOL
*is_token_obj
)
668 crypto_object_attribute_t
*attrs
, *cur_attr
;
679 attrs
= calloc(1, ulCount
* sizeof (crypto_object_attribute_t
));
681 return (CKR_HOST_MEMORY
);
685 for (i
= 0; i
< ulCount
; i
++) {
687 * The length of long attributes must be set correctly
688 * so providers can determine whether they came from 32
689 * or 64-bit applications.
691 switch (pTemplate
[i
].type
) {
693 case CKA_CERTIFICATE_TYPE
:
695 case CKA_MODULUS_BITS
:
696 case CKA_HW_FEATURE_TYPE
:
697 value_len
= sizeof (ulong_t
);
698 if (pTemplate
[i
].pValue
!= NULL
&&
699 (pTemplate
[i
].ulValueLen
< value_len
)) {
700 rv
= CKR_ATTRIBUTE_VALUE_INVALID
;
706 value_len
= pTemplate
[i
].ulValueLen
;
709 cur_attr
->oa_type
= pTemplate
[i
].type
;
710 cur_attr
->oa_value_len
= value_len
;
711 cur_attr
->oa_value
= NULL
;
713 if ((pTemplate
[i
].pValue
!= NULL
) &&
714 (pTemplate
[i
].ulValueLen
> 0)) {
715 ptr
= malloc(pTemplate
[i
].ulValueLen
);
717 rv
= CKR_HOST_MEMORY
;
721 (void) memcpy(ptr
, pTemplate
[i
].pValue
,
722 pTemplate
[i
].ulValueLen
);
723 cur_attr
->oa_value
= ptr
;
727 if ((is_token_obj
!= NULL
) &&
728 (pTemplate
[i
].type
== CKA_TOKEN
)) {
729 /* Get the CKA_TOKEN attribute value. */
730 if (pTemplate
[i
].pValue
== NULL
) {
731 rv
= CKR_ATTRIBUTE_VALUE_INVALID
;
736 *(CK_BBOOL
*)pTemplate
[i
].pValue
;
743 *obj_attrs
= (char *)attrs
;
748 for (i
= 0; i
< cur_i
; i
++) {
749 if (cur_attr
->oa_value
!= NULL
) {
750 (void) free(cur_attr
->oa_value
);
761 * Copy the attribute values from obj_attrs to pTemplate.
762 * The obj_attrs is an image of the Template and is expected to have the
763 * same attributes in the same order and each one of the attribute pValue
764 * in obj_attr has enough space allocated for the corresponding valueLen
768 get_object_attributes(CK_ATTRIBUTE_PTR pTemplate
, CK_ULONG ulCount
,
771 crypto_object_attribute_t
*cur_attr
;
776 cur_attr
= (crypto_object_attribute_t
*)obj_attrs
;
777 for (i
= 0; i
< ulCount
; i
++) {
778 if (pTemplate
[i
].type
!= cur_attr
->oa_type
) {
779 /* The attribute type doesn't match, this is bad. */
780 rv
= CKR_FUNCTION_FAILED
;
784 pTemplate
[i
].ulValueLen
= cur_attr
->oa_value_len
;
786 if ((pTemplate
[i
].pValue
!= NULL
) &&
787 ((CK_LONG
)pTemplate
[i
].ulValueLen
!= -1)) {
788 (void) memcpy(pTemplate
[i
].pValue
, cur_attr
->oa_value
,
789 pTemplate
[i
].ulValueLen
);
798 * Free the attribute storage in a crypto_object_attribute_t structure.
801 free_object_attributes(caddr_t obj_attrs
, CK_ULONG ulCount
)
803 crypto_object_attribute_t
*cur_attr
;
806 if ((ulCount
== 0) || (obj_attrs
== NULL
)) {
811 cur_attr
= (crypto_object_attribute_t
*)obj_attrs
;
812 for (i
= 0; i
< ulCount
; i
++) {
813 /* XXX check that oa_value > 0 */
814 if (cur_attr
->oa_value
!= NULL
) {
815 free(cur_attr
->oa_value
);
824 * This function is called by process_found_objects(). It will check the
825 * CKA_PRIVATE and CKA_TOKEN attributes for the kernel object "oid", then
826 * initialize all the necessary fields in the object wrapper "objp".
829 create_new_tobj_in_lib(kernel_slot_t
*pslot
, kernel_session_t
*sp
,
830 kernel_object_t
*objp
, crypto_object_id_t oid
)
833 crypto_object_get_attribute_value_t obj_ga
;
834 boolean_t is_pri_obj
;
835 boolean_t is_token_obj
;
836 CK_BBOOL pri_value
, token_value
;
837 CK_ATTRIBUTE pTemplate
[2];
841 * Make a CRYPTO_OBJECT_GET_ATTRIBUTE_VALUE ioctl call to get this
842 * kernel object's attribute values for CKA_PRIVATE and CKA_TOKEN.
844 obj_ga
.og_session
= sp
->k_session
;
845 obj_ga
.og_handle
= oid
;
848 pTemplate
[0].type
= CKA_PRIVATE
;
849 pTemplate
[0].pValue
= &pri_value
;
850 pTemplate
[0].ulValueLen
= sizeof (pri_value
);
851 pTemplate
[1].type
= CKA_TOKEN
;
852 pTemplate
[1].pValue
= &token_value
;
853 pTemplate
[1].ulValueLen
= sizeof (token_value
);
854 rv
= process_object_attributes(pTemplate
, 2, &obj_ga
.og_attributes
,
860 while ((r
= ioctl(kernel_fd
, CRYPTO_OBJECT_GET_ATTRIBUTE_VALUE
,
866 rv
= CKR_FUNCTION_FAILED
;
868 rv
= crypto2pkcs11_error_number(obj_ga
.og_return_value
);
872 rv
= get_object_attributes(pTemplate
, 2, obj_ga
.og_attributes
);
874 is_pri_obj
= *(CK_BBOOL
*)pTemplate
[0].pValue
;
875 is_token_obj
= *(CK_BBOOL
*)pTemplate
[1].pValue
;
879 free_object_attributes(obj_ga
.og_attributes
, 2);
884 /* Make sure it is a token object. */
886 rv
= CKR_ATTRIBUTE_VALUE_INVALID
;
890 /* If it is a private object, make sure the user has logged in. */
891 if (is_pri_obj
&& (pslot
->sl_state
!= CKU_USER
)) {
892 rv
= CKR_ATTRIBUTE_VALUE_INVALID
;
896 objp
->is_lib_obj
= B_FALSE
;
897 objp
->k_handle
= oid
;
898 objp
->bool_attr_mask
|= TOKEN_BOOL_ON
;
900 objp
->bool_attr_mask
|= PRIVATE_BOOL_ON
;
902 objp
->bool_attr_mask
&= ~PRIVATE_BOOL_ON
;
905 (void) pthread_mutex_init(&objp
->object_mutex
, NULL
);
906 objp
->magic_marker
= KERNELTOKEN_OBJECT_MAGIC
;
907 objp
->session_handle
= (CK_SESSION_HANDLE
) sp
;
913 * This function processes the kernel object handles returned from the
914 * CRYPTO_OBJECT_FIND_UPDATE ioctl and returns an object handle list
915 * and the number of object handles to the caller - C_FindObjects().
916 * The caller acquires the slot lock and the session lock.
919 process_found_objects(kernel_session_t
*cur_sp
, CK_OBJECT_HANDLE
*obj_found
,
920 CK_ULONG
*found_obj_count
, crypto_object_find_update_t obj_fu
)
923 crypto_object_id_t
*oid_p
;
924 kernel_slot_t
*pslot
;
925 kernel_object_t
*objp
;
926 kernel_object_t
*objp1
;
927 kernel_object_t
*new_tobj_list
= NULL
;
928 kernel_session_t
*sp
;
929 CK_ULONG num_obj_found
= 0;
933 if (obj_fu
.fu_count
== 0) {
934 *found_obj_count
= 0;
938 pslot
= slot_table
[cur_sp
->ses_slotid
];
941 oid_p
= (crypto_object_id_t
*)obj_fu
.fu_handles
;
942 for (i
= 0; i
< obj_fu
.fu_count
; i
++) {
945 * Check if this oid has an object wrapper in the library
946 * already. First, search the slot's token object list.
948 objp
= pslot
->sl_tobj_list
;
949 while (!is_in_lib
&& objp
) {
950 if (objp
->k_handle
== *oid_p
) {
958 * If it is not in the slot's token object list,
959 * search it in all the sessions.
962 sp
= pslot
->sl_sess_list
;
963 while (!is_in_lib
&& sp
) {
964 objp
= sp
->object_list
;
965 while (!is_in_lib
&& objp
) {
966 if (objp
->k_handle
== *oid_p
) {
977 * If this object is in the library already, add its object
978 * wrapper to the returned find object list.
981 obj_found
[num_obj_found
++] = (CK_OBJECT_HANDLE
)objp
;
985 * If we still do not find it in the library. This object
986 * must be a token object pre-existed in the HW provider.
987 * We need to create an object wrapper for it in the library.
990 objp1
= calloc(1, sizeof (kernel_object_t
));
992 rv
= CKR_HOST_MEMORY
;
995 rv
= create_new_tobj_in_lib(pslot
, cur_sp
, objp1
,
999 /* Save the new object to the new_tobj_list. */
1000 if (new_tobj_list
== NULL
) {
1001 new_tobj_list
= objp1
;
1005 new_tobj_list
->prev
= objp1
;
1006 objp1
->next
= new_tobj_list
;
1008 new_tobj_list
= objp1
;
1012 * If create_new_tobj_in_lib() doesn't fail
1013 * with CKR_HOST_MEMORY, the failure should be
1014 * caused by the attributes' checking. We will
1015 * just ignore this object and continue on.
1018 if (rv
== CKR_HOST_MEMORY
) {
1024 /* Process next one */
1029 * Add the newly created token object wrappers to the found object
1030 * list and to the slot's token object list.
1032 if (new_tobj_list
!= NULL
) {
1033 /* Add to the obj_found array. */
1034 objp
= new_tobj_list
;
1036 obj_found
[num_obj_found
++] = (CK_OBJECT_HANDLE
)objp
;
1037 if (objp
->next
== NULL
) {
1043 /* Add to the beginning of the slot's token object list. */
1044 if (pslot
->sl_tobj_list
!= NULL
) {
1045 objp
->next
= pslot
->sl_tobj_list
;
1046 pslot
->sl_tobj_list
->prev
= objp
;
1048 pslot
->sl_tobj_list
= new_tobj_list
;
1051 *found_obj_count
= num_obj_found
;
1056 /* Free the newly created token object wrappers. */
1057 objp
= new_tobj_list
;
1060 (void) pthread_mutex_destroy(&objp
->object_mutex
);
1070 * Get the value of the CKA_PRIVATE attribute for the object just returned
1071 * from the HW provider. This function will be called by any function
1072 * that creates a new object, because the CKA_PRIVATE value of an object is
1073 * token specific. The CKA_PRIVATE attribute value of the new object will be
1074 * stored in the object structure in the library, which will be used later at
1075 * C_Logout to clean up all private objects.
1078 get_cka_private_value(kernel_session_t
*sp
, crypto_object_id_t oid
,
1079 CK_BBOOL
*is_pri_obj
)
1082 crypto_object_get_attribute_value_t obj_ga
;
1083 crypto_object_attribute_t obj_attr
;
1087 obj_ga
.og_session
= sp
->k_session
;
1088 obj_ga
.og_handle
= oid
;
1089 obj_ga
.og_count
= 1;
1091 obj_attr
.oa_type
= CKA_PRIVATE
;
1092 obj_attr
.oa_value
= (char *)&pri_value
;
1093 obj_attr
.oa_value_len
= sizeof (CK_BBOOL
);
1094 obj_ga
.og_attributes
= (char *)&obj_attr
;
1096 while ((r
= ioctl(kernel_fd
, CRYPTO_OBJECT_GET_ATTRIBUTE_VALUE
,
1102 rv
= CKR_FUNCTION_FAILED
;
1104 rv
= crypto2pkcs11_error_number(obj_ga
.og_return_value
);
1108 *is_pri_obj
= *(CK_BBOOL
*)obj_attr
.oa_value
;
1116 get_mechanism_info(kernel_slot_t
*pslot
, CK_MECHANISM_TYPE type
,
1117 CK_MECHANISM_INFO_PTR pInfo
, uint32_t *k_mi_flags
)
1119 crypto_get_provider_mechanism_info_t mechanism_info
;
1121 CK_FLAGS flags
, mi_flags
;
1124 char buf
[11]; /* Num chars for representing ulong in ASCII */
1126 if (type
>= CKM_VENDOR_DEFINED
) {
1127 /* allocate/build a string containing the mechanism number */
1128 (void) snprintf(buf
, sizeof (buf
), "%#lx", type
);
1131 string
= pkcs11_mech2str(type
);
1135 return (CKR_MECHANISM_INVALID
);
1137 (void) strcpy(mechanism_info
.mi_mechanism_name
, string
);
1138 mechanism_info
.mi_provider_id
= pslot
->sl_provider_id
;
1140 while ((r
= ioctl(kernel_fd
, CRYPTO_GET_PROVIDER_MECHANISM_INFO
,
1141 &mechanism_info
)) < 0) {
1146 rv
= CKR_FUNCTION_FAILED
;
1148 rv
= crypto2pkcs11_error_number(
1149 mechanism_info
.mi_return_value
);
1157 * Atomic flags are not part of PKCS#11 so we filter
1160 mi_flags
= mechanism_info
.mi_flags
;
1161 mi_flags
&= ~(CRYPTO_FG_DIGEST_ATOMIC
| CRYPTO_FG_ENCRYPT_ATOMIC
|
1162 CRYPTO_FG_DECRYPT_ATOMIC
| CRYPTO_FG_MAC_ATOMIC
|
1163 CRYPTO_FG_SIGN_ATOMIC
| CRYPTO_FG_VERIFY_ATOMIC
|
1164 CRYPTO_FG_SIGN_RECOVER_ATOMIC
|
1165 CRYPTO_FG_VERIFY_RECOVER_ATOMIC
|
1166 CRYPTO_FG_ENCRYPT_MAC_ATOMIC
|
1167 CRYPTO_FG_MAC_DECRYPT_ATOMIC
);
1169 if (mi_flags
== 0) {
1170 return (CKR_MECHANISM_INVALID
);
1174 /* set the value of k_mi_flags first */
1175 *k_mi_flags
= mi_flags
;
1177 /* convert KEF flags into pkcs11 flags */
1179 if (mi_flags
& CRYPTO_FG_ENCRYPT
)
1180 flags
|= CKF_ENCRYPT
;
1181 if (mi_flags
& CRYPTO_FG_DECRYPT
) {
1182 flags
|= CKF_DECRYPT
;
1184 * Since we'll be emulating C_UnwrapKey() for some
1185 * cases, we can go ahead and claim CKF_UNWRAP
1187 flags
|= CKF_UNWRAP
;
1189 if (mi_flags
& CRYPTO_FG_DIGEST
)
1190 flags
|= CKF_DIGEST
;
1191 if (mi_flags
& CRYPTO_FG_SIGN
)
1193 if (mi_flags
& CRYPTO_FG_SIGN_RECOVER
)
1194 flags
|= CKF_SIGN_RECOVER
;
1195 if (mi_flags
& CRYPTO_FG_VERIFY
)
1196 flags
|= CKF_VERIFY
;
1197 if (mi_flags
& CRYPTO_FG_VERIFY_RECOVER
)
1198 flags
|= CKF_VERIFY_RECOVER
;
1199 if (mi_flags
& CRYPTO_FG_GENERATE
)
1200 flags
|= CKF_GENERATE
;
1201 if (mi_flags
& CRYPTO_FG_GENERATE_KEY_PAIR
)
1202 flags
|= CKF_GENERATE_KEY_PAIR
;
1203 if (mi_flags
& CRYPTO_FG_WRAP
)
1205 if (mi_flags
& CRYPTO_FG_UNWRAP
)
1206 flags
|= CKF_UNWRAP
;
1207 if (mi_flags
& CRYPTO_FG_DERIVE
)
1208 flags
|= CKF_DERIVE
;
1210 pInfo
->ulMinKeySize
= mechanism_info
.mi_min_key_size
;
1211 pInfo
->ulMaxKeySize
= mechanism_info
.mi_max_key_size
;
1212 pInfo
->flags
= flags
;
1220 * Unfortunately the kernel and PKCS#11 use a slightly different struct to
1221 * specify CCM parameters.
1224 p11_to_kernel_ccm_params(const CK_CCM_PARAMS
*in
, CK_AES_CCM_PARAMS
*out
)
1226 out
->ulMACSize
= in
->ulMACLen
;
1227 out
->ulNonceSize
= in
->ulNonceLen
;
1228 out
->ulAuthDataSize
= in
->ulAADLen
;
1229 out
->ulDataSize
= in
->ulDataLen
;
1230 out
->nonce
= in
->pNonce
;
1231 out
->authData
= in
->pAAD
;