xref: /illumos-gate/usr/src/test/crypto-tests/tests/common/cryptotest_kcf.c (revision fa4a3e77edc40df6d92e8da6fc4961d275e9896d)
1 /*
2  * This file and its contents are supplied under the terms of the
3  * Common Development and Distribution License ("CDDL"), version 1.0.
4  * You may only use this file in accordance with the terms of version
5  * 1.0 of the CDDL.
6  *
7  * A full copy of the text of the CDDL should have accompanied this
8  * source.  A copy of the CDDL is also available via the Internet at
9  * http://www.illumos.org/license/CDDL.
10  */
11 
12 /*
13  * Copyright 2015 Nexenta Systems, Inc.  All rights reserved.
14  * Copyright 2019 Joyent, Inc.
15  */
16 
17 #include <fcntl.h>
18 #include <strings.h>
19 #include <unistd.h>
20 #include <errno.h>
21 #include <stdio.h>
22 #include <stdlib.h>
23 #include <sys/debug.h>
24 
25 #include "cryptotest.h"
26 
27 struct crypto_op {
28 	char *in;
29 	char *out;
30 	char *key;
31 	char *param;
32 
33 	size_t inlen;
34 	size_t outlen;
35 	size_t keylen;
36 	size_t paramlen;
37 	const size_t *updatelens;
38 
39 	char *mechname;
40 
41 	/* internal */
42 	crypto_mech_type_t mech;
43 	crypto_session_id_t hsession;
44 	crypto_func_group_t fg;
45 };
46 
47 static int fd = -1;
48 static const char CRYPTO_DEVICE[] = "/dev/crypto";
49 
50 int
51 kcf_do_ioctl(int opcode, uint_t *arg, char *opstr)
52 {
53 	int ret;
54 
55 	while ((ret = ioctl(fd, opcode, arg)) < 0) {
56 		if (errno != EINTR)
57 			break;
58 	}
59 
60 	if (ret < 0 || *arg != CRYPTO_SUCCESS) {
61 		(void) fprintf(stderr,
62 		    "%s: Error = %d errno=%d (%s) 0x%02x\n",
63 		    (opstr == NULL) ? "ioctl" : opstr,
64 		    ret, errno, strerror(errno), *arg);
65 
66 	}
67 
68 	/*
69 	 * The callers all expect CRYPTO_xx errors.  We've displayed the
70 	 * errno value (see above), so just return a generic CRYPTO_xxx
71 	 * error to signal failure.
72 	 */
73 	if (ret < 0)
74 		return (CRYPTO_GENERAL_ERROR);
75 
76 	return (*arg);
77 }
78 
79 crypto_op_t *
80 cryptotest_init(cryptotest_t *arg, crypto_func_group_t fg)
81 {
82 	crypto_op_t *op = malloc(sizeof (*op));
83 
84 	if (op == NULL) {
85 		(void) fprintf(stderr, "malloc failed: %s\n", strerror(errno));
86 		return (NULL);
87 	}
88 
89 	while ((fd = open(CRYPTO_DEVICE, O_RDWR)) < 0) {
90 		if (errno != EINTR) {
91 			(void) fprintf(stderr, "open of %s failed: %s",
92 			    CRYPTO_DEVICE, strerror(errno));
93 			free(op);
94 			return (NULL);
95 		}
96 	}
97 
98 	op->in = (char *)arg->in;
99 	op->out = (char *)arg->out;
100 	op->key = (char *)arg->key;
101 	op->param = (char *)arg->param;
102 
103 	op->inlen = arg->inlen;
104 	op->outlen = arg->outlen;
105 	op->keylen = arg->keylen * 8; /* kcf uses keylen in bits */
106 	op->paramlen = arg->plen;
107 	op->updatelens = arg->updatelens;
108 
109 	op->mechname = arg->mechname;
110 
111 	op->hsession = CRYPTO_INVALID_SESSION;
112 	op->fg = fg;
113 
114 	if (op->out == NULL)
115 		op->outlen = op->inlen;
116 	return (op);
117 }
118 
119 int
120 cryptotest_close_session(crypto_session_id_t session)
121 {
122 	crypto_close_session_t cs;
123 
124 	cs.cs_session = session;
125 	return (kcf_do_ioctl(CRYPTO_CLOSE_SESSION, (uint_t *)&cs, "session"));
126 }
127 
128 void
129 cryptotest_close(crypto_op_t *op)
130 {
131 	if (op->hsession != CRYPTO_INVALID_SESSION)
132 		(void) cryptotest_close_session(op->hsession);
133 	free(op);
134 	if (fd >= 0)
135 		VERIFY0(close(fd));
136 	fd = -1;
137 }
138 
139 int
140 get_mech_info(crypto_op_t *op)
141 {
142 	crypto_get_mechanism_number_t get_number;
143 
144 	bzero(&get_number, sizeof (get_number));
145 
146 	get_number.pn_mechanism_string = op->mechname;
147 	get_number.pn_mechanism_len = strlen(op->mechname) + 1;
148 
149 	if (kcf_do_ioctl(CRYPTO_GET_MECHANISM_NUMBER,
150 	    (uint_t *)&get_number, "get_mech_info") != CRYPTO_SUCCESS) {
151 		(void) fprintf(stderr, "failed to resolve mechanism name %s\n",
152 		    op->mechname);
153 		return (CTEST_NAME_RESOLVE_FAILED);
154 	}
155 	op->mech = get_number.pn_internal_number;
156 	return (CRYPTO_SUCCESS);
157 }
158 
159 int
160 get_hsession_by_mech(crypto_op_t *op)
161 {
162 	crypto_by_mech_t mech;
163 	int rv;
164 
165 	mech.mech_keylen = op->keylen;
166 	mech.mech_type = op->mech;
167 	mech.mech_fg = op->fg;
168 
169 	rv = kcf_do_ioctl(CRYPTO_GET_PROVIDER_BY_MECH, (uint_t *)&mech,
170 	    "get_hsession_by_mech");
171 
172 	if (rv != 0 || mech.rv != CRYPTO_SUCCESS) {
173 		(void) fprintf(stderr,
174 		    "could not find provider for mechanism %llu\n",
175 		    mech.mech_type);
176 		return (CTEST_MECH_NO_PROVIDER);
177 	}
178 
179 	op->hsession = mech.session_id;
180 
181 	return (CRYPTO_SUCCESS);
182 }
183 
184 /*
185  * CRYPTO_MAC_* functions
186  */
187 int
188 mac_init(crypto_op_t *op)
189 {
190 	crypto_mac_init_t init;
191 
192 	bzero((void *)&init, sizeof (init));
193 
194 	init.mi_session = op->hsession;
195 
196 	init.mi_key.ck_data = op->key;
197 	init.mi_key.ck_format = CRYPTO_KEY_RAW; /* must be this */
198 	init.mi_key.ck_length = op->keylen;
199 
200 	init.mi_mech.cm_type = op->mech;
201 	init.mi_mech.cm_param = NULL;
202 	init.mi_mech.cm_param_len = 0;
203 
204 	return (kcf_do_ioctl(CRYPTO_MAC_INIT, (uint_t *)&init, "init"));
205 }
206 
207 int
208 mac_single(crypto_op_t *op)
209 {
210 	crypto_mac_t mac;
211 
212 	bzero(&mac, sizeof (mac));
213 	mac.cm_session = op->hsession;
214 	mac.cm_datalen = op->inlen;
215 	mac.cm_databuf = op->in;
216 	mac.cm_maclen = op->outlen;
217 	mac.cm_macbuf = op->out;
218 
219 	return (kcf_do_ioctl(CRYPTO_MAC, (uint_t *)&mac, "single"));
220 }
221 
222 int
223 mac_update(crypto_op_t *op, size_t offset, size_t len, size_t *dummy __unused)
224 {
225 	crypto_mac_update_t update;
226 
227 	bzero((void *)&update, sizeof (update));
228 
229 	update.mu_session = op->hsession;
230 	update.mu_databuf = op->in + offset;
231 	update.mu_datalen = len;
232 
233 	return (kcf_do_ioctl(CRYPTO_MAC_UPDATE, (uint_t *)&update, "update"));
234 }
235 
236 int
237 mac_final(crypto_op_t *op, size_t dummy __unused)
238 {
239 	crypto_mac_final_t final;
240 
241 	bzero((void *)&final, sizeof (final));
242 
243 	final.mf_session = op->hsession;
244 	final.mf_maclen = op->outlen;
245 	final.mf_macbuf = op->out;
246 
247 	return (kcf_do_ioctl(CRYPTO_MAC_FINAL, (uint_t *)&final, "final"));
248 }
249 
250 
251 /*
252  * CRYPTO_ENCRYPT_* functions
253  */
254 
255 int
256 encrypt_init(crypto_op_t *op)
257 {
258 	crypto_encrypt_init_t init;
259 
260 	bzero((void *)&init, sizeof (init));
261 
262 	init.ei_session = op->hsession;
263 
264 	init.ei_key.ck_data = op->key;
265 	init.ei_key.ck_format = CRYPTO_KEY_RAW; /* must be this */
266 	init.ei_key.ck_length = op->keylen;
267 
268 	init.ei_mech.cm_type = op->mech;
269 	init.ei_mech.cm_param = op->param;
270 	init.ei_mech.cm_param_len = op->paramlen;
271 
272 	return (kcf_do_ioctl(CRYPTO_ENCRYPT_INIT, (uint_t *)&init, "init"));
273 }
274 
275 int
276 encrypt_single(crypto_op_t *op)
277 {
278 	crypto_encrypt_t encrypt;
279 
280 	bzero(&encrypt, sizeof (encrypt));
281 	encrypt.ce_session = op->hsession;
282 	encrypt.ce_datalen = op->inlen;
283 	encrypt.ce_databuf = op->in;
284 	encrypt.ce_encrlen = op->outlen;
285 	encrypt.ce_encrbuf = op->out;
286 
287 	return (kcf_do_ioctl(CRYPTO_ENCRYPT, (uint_t *)&encrypt, "single"));
288 }
289 
290 int
291 encrypt_update(crypto_op_t *op, size_t offset, size_t plainlen, size_t *encrlen)
292 {
293 	crypto_encrypt_update_t update;
294 	int ret;
295 	bzero((void *)&update, sizeof (update));
296 
297 	update.eu_session = op->hsession;
298 	update.eu_databuf = op->in + offset;
299 	update.eu_datalen = plainlen;
300 	update.eu_encrlen = op->outlen - *encrlen;
301 	update.eu_encrbuf = op->out + *encrlen;
302 
303 	ret = kcf_do_ioctl(CRYPTO_ENCRYPT_UPDATE, (uint_t *)&update, "update");
304 	*encrlen += update.eu_encrlen;
305 	return (ret);
306 }
307 
308 int
309 encrypt_final(crypto_op_t *op, size_t encrlen)
310 {
311 	crypto_encrypt_final_t final;
312 
313 	bzero((void *)&final, sizeof (final));
314 
315 	final.ef_session = op->hsession;
316 	final.ef_encrlen = op->outlen - encrlen;
317 	final.ef_encrbuf = op->out + encrlen;
318 
319 	return (kcf_do_ioctl(CRYPTO_ENCRYPT_FINAL, (uint_t *)&final, "final"));
320 }
321 
322 /*
323  * CRYPTO_DECRYPT_* functions
324  */
325 
326 int
327 decrypt_init(crypto_op_t *op)
328 {
329 	crypto_decrypt_init_t init;
330 
331 	bzero((void *)&init, sizeof (init));
332 
333 	init.di_session = op->hsession;
334 
335 	init.di_key.ck_data = op->key;
336 	init.di_key.ck_format = CRYPTO_KEY_RAW; /* must be this */
337 	init.di_key.ck_length = op->keylen;
338 
339 	init.di_mech.cm_type = op->mech;
340 	init.di_mech.cm_param = op->param;
341 	init.di_mech.cm_param_len = op->paramlen;
342 
343 	return (kcf_do_ioctl(CRYPTO_DECRYPT_INIT, (uint_t *)&init, "init"));
344 }
345 
346 int
347 decrypt_single(crypto_op_t *op)
348 {
349 	crypto_decrypt_t decrypt;
350 
351 	bzero(&decrypt, sizeof (decrypt));
352 	decrypt.cd_session = op->hsession;
353 	decrypt.cd_datalen = op->outlen;
354 	decrypt.cd_databuf = op->out;
355 	decrypt.cd_encrlen = op->inlen;
356 	decrypt.cd_encrbuf = op->in;
357 
358 	return (kcf_do_ioctl(CRYPTO_DECRYPT, (uint_t *)&decrypt, "single"));
359 }
360 
361 int
362 decrypt_update(crypto_op_t *op, size_t offset, size_t len, size_t *encrlen)
363 {
364 	crypto_decrypt_update_t update;
365 	int ret;
366 
367 	bzero((void *)&update, sizeof (update));
368 
369 	update.du_session = op->hsession;
370 	update.du_databuf = op->out + *encrlen;
371 	update.du_datalen = op->outlen - *encrlen;
372 	update.du_encrlen = len;
373 	update.du_encrbuf = op->in + offset;
374 
375 	ret = kcf_do_ioctl(CRYPTO_DECRYPT_UPDATE, (uint_t *)&update, "update");
376 	*encrlen += update.du_datalen;
377 	return (ret);
378 }
379 
380 int
381 decrypt_final(crypto_op_t *op, size_t encrlen)
382 {
383 	crypto_decrypt_final_t final;
384 
385 	bzero((void *)&final, sizeof (final));
386 
387 	final.df_session = op->hsession;
388 	final.df_datalen = op->outlen - encrlen;
389 	final.df_databuf = op->out + encrlen;
390 
391 	return (kcf_do_ioctl(CRYPTO_DECRYPT_FINAL, (uint_t *)&final, "final"));
392 }
393 
394 int
395 digest_init(crypto_op_t *op)
396 {
397 	crypto_digest_init_t init;
398 
399 	bzero(&init, sizeof (init));
400 
401 	init.di_session = op->hsession;
402 
403 	init.di_mech.cm_type = op->mech;
404 	init.di_mech.cm_param = NULL;
405 	init.di_mech.cm_param_len = 0;
406 
407 	return (kcf_do_ioctl(CRYPTO_DIGEST_INIT, (uint_t *)&init, "init"));
408 }
409 
410 int
411 digest_single(crypto_op_t *op)
412 {
413 	crypto_digest_t digest;
414 
415 	bzero(&digest, sizeof (digest));
416 
417 	digest.cd_session = op->hsession;
418 
419 	digest.cd_datalen = op->inlen;
420 	digest.cd_databuf = op->in;
421 	digest.cd_digestlen = op->outlen;
422 	digest.cd_digestbuf = op->out;
423 
424 	return (kcf_do_ioctl(CRYPTO_DIGEST, (uint_t *)&digest, "digest"));
425 }
426 
427 int
428 digest_update(crypto_op_t *op, size_t offset, size_t len,
429     size_t *dummy __unused)
430 {
431 	crypto_digest_update_t update;
432 
433 	bzero(&update, sizeof (update));
434 
435 	update.du_session = op->hsession;
436 
437 	update.du_datalen = len;
438 	update.du_databuf = op->in + offset;
439 
440 	return (kcf_do_ioctl(CRYPTO_DIGEST_UPDATE, (uint_t *)&update,
441 	    "update"));
442 }
443 
444 int
445 digest_final(crypto_op_t *op, size_t dummy __unused)
446 {
447 	crypto_digest_final_t final;
448 
449 	bzero(&final, sizeof (final));
450 
451 	final.df_session = op->hsession;
452 
453 	final.df_digestlen = op->outlen;
454 	final.df_digestbuf = op->out;
455 
456 	return (kcf_do_ioctl(CRYPTO_DIGEST_FINAL, (uint_t *)&final, "final"));
457 }
458 
459 void
460 ccm_init_params(void *buf, ulong_t ulDataLen, uchar_t *pNonce,
461     ulong_t ulNonceLen, uchar_t *pAAD, ulong_t ulAADLen, ulong_t ulMACLen)
462 {
463 	CK_AES_CCM_PARAMS *pp = buf;
464 
465 	pp->ulDataSize = ulDataLen;
466 	pp->nonce = pNonce;
467 	pp->ulNonceSize = ulNonceLen;
468 	pp->authData = pAAD;
469 	pp->ulAuthDataSize = ulAADLen;
470 	pp->ulMACSize = ulMACLen;
471 }
472 
473 size_t
474 ccm_param_len(void)
475 {
476 	return (sizeof (CK_AES_CCM_PARAMS));
477 }
478 
479 const char *
480 cryptotest_errstr(int e, char *buf, size_t buflen)
481 {
482 	const char *valstr = NULL;
483 
484 	switch (e) {
485 	case CRYPTO_SUCCESS:
486 		valstr = "CRYPTO_SUCCESS";
487 		break;
488 	case CRYPTO_CANCEL:
489 		valstr = "CRYPTO_CANCEL";
490 		break;
491 	case CRYPTO_HOST_MEMORY:
492 		valstr = "CRYPTO_HOST_MEMORY";
493 		break;
494 	case CRYPTO_GENERAL_ERROR:
495 		valstr = "CRYPTO_GENERAL_ERROR";
496 		break;
497 	case CRYPTO_FAILED:
498 		valstr = "CRYPTO_FAILED";
499 		break;
500 	case CRYPTO_ARGUMENTS_BAD:
501 		valstr = "CRYPTO_ARGUMENTS_BAD";
502 		break;
503 	case CRYPTO_ATTRIBUTE_READ_ONLY:
504 		valstr = "CRYPTO_ATTRIBUTE_READ_ONLY";
505 		break;
506 	case CRYPTO_ATTRIBUTE_SENSITIVE:
507 		valstr = "CRYPTO_ATTRIBUTE_SENSITIVE";
508 		break;
509 	case CRYPTO_ATTRIBUTE_TYPE_INVALID:
510 		valstr = "CRYPTO_ATTRIBUTE_TYPE_INVALID";
511 		break;
512 	case CRYPTO_ATTRIBUTE_VALUE_INVALID:
513 		valstr = "CRYPTO_ATTRIBUTE_VALUE_INVALID";
514 		break;
515 	case CRYPTO_CANCELED:
516 		valstr = "CRYPTO_CANCELED";
517 		break;
518 	case CRYPTO_DATA_INVALID:
519 		valstr = "CRYPTO_DATA_INVALID";
520 		break;
521 	case CRYPTO_DATA_LEN_RANGE:
522 		valstr = "CRYPTO_DATA_LEN_RANGE";
523 		break;
524 	case CRYPTO_DEVICE_ERROR:
525 		valstr = "CRYPTO_DEVICE_ERROR";
526 		break;
527 	case CRYPTO_DEVICE_MEMORY:
528 		valstr = "CRYPTO_DEVICE_MEMORY";
529 		break;
530 	case CRYPTO_DEVICE_REMOVED:
531 		valstr = "CRYPTO_DEVICE_REMOVED";
532 		break;
533 	case CRYPTO_ENCRYPTED_DATA_INVALID:
534 		valstr = "CRYPTO_ENCRYPTED_DATA_INVALID";
535 		break;
536 	case CRYPTO_ENCRYPTED_DATA_LEN_RANGE:
537 		valstr = "CRYPTO_ENCRYPTED_DATA_LEN_RANGE";
538 		break;
539 	case CRYPTO_KEY_HANDLE_INVALID:
540 		valstr = "CRYPTO_KEY_HANDLE_INVALID";
541 		break;
542 	case CRYPTO_KEY_SIZE_RANGE:
543 		valstr = "CRYPTO_KEY_SIZE_RANGE";
544 		break;
545 	case CRYPTO_KEY_TYPE_INCONSISTENT:
546 		valstr = "CRYPTO_KEY_TYPE_INCONSISTENT";
547 		break;
548 	case CRYPTO_KEY_NOT_NEEDED:
549 		valstr = "CRYPTO_KEY_NOT_NEEDED";
550 		break;
551 	case CRYPTO_KEY_CHANGED:
552 		valstr = "CRYPTO_KEY_CHANGED";
553 		break;
554 	case CRYPTO_KEY_NEEDED:
555 		valstr = "CRYPTO_KEY_NEEDED";
556 		break;
557 	case CRYPTO_KEY_INDIGESTIBLE:
558 		valstr = "CRYPTO_KEY_INDIGESTIBLE";
559 		break;
560 	case CRYPTO_KEY_FUNCTION_NOT_PERMITTED:
561 		valstr = "CRYPTO_KEY_FUNCTION_NOT_PERMITTED";
562 		break;
563 	case CRYPTO_KEY_NOT_WRAPPABLE:
564 		valstr = "CRYPTO_KEY_NOT_WRAPPABLE";
565 		break;
566 	case CRYPTO_KEY_UNEXTRACTABLE:
567 		valstr = "CRYPTO_KEY_UNEXTRACTABLE";
568 		break;
569 	case CRYPTO_MECHANISM_INVALID:
570 		valstr = "CRYPTO_MECHANISM_INVALID";
571 		break;
572 	case CRYPTO_MECHANISM_PARAM_INVALID:
573 		valstr = "CRYPTO_MECHANISM_PARAM_INVALID";
574 		break;
575 	case CRYPTO_OBJECT_HANDLE_INVALID:
576 		valstr = "CRYPTO_OBJECT_HANDLE_INVALID";
577 		break;
578 	case CRYPTO_OPERATION_IS_ACTIVE:
579 		valstr = "CRYPTO_OPERATION_IS_ACTIVE";
580 		break;
581 	case CRYPTO_OPERATION_NOT_INITIALIZED:
582 		valstr = "CRYPTO_OPERATION_NOT_INITIALIZED";
583 		break;
584 	case CRYPTO_PIN_INCORRECT:
585 		valstr = "CRYPTO_PIN_INCORRECT";
586 		break;
587 	case CRYPTO_PIN_INVALID:
588 		valstr = "CRYPTO_PIN_INVALID";
589 		break;
590 	case CRYPTO_PIN_LEN_RANGE:
591 		valstr = "CRYPTO_PIN_LEN_RANGE";
592 		break;
593 	case CRYPTO_PIN_EXPIRED:
594 		valstr = "CRYPTO_PIN_EXPIRED";
595 		break;
596 	case CRYPTO_PIN_LOCKED:
597 		valstr = "CRYPTO_PIN_LOCKED";
598 		break;
599 	case CRYPTO_SESSION_CLOSED:
600 		valstr = "CRYPTO_SESSION_CLOSED";
601 		break;
602 	case CRYPTO_SESSION_COUNT:
603 		valstr = "CRYPTO_SESSION_COUNT";
604 		break;
605 	case CRYPTO_SESSION_HANDLE_INVALID:
606 		valstr = "CRYPTO_SESSION_HANDLE_INVALID";
607 		break;
608 	case CRYPTO_SESSION_READ_ONLY:
609 		valstr = "CRYPTO_SESSION_READ_ONLY";
610 		break;
611 	case CRYPTO_SESSION_EXISTS:
612 		valstr = "CRYPTO_SESSION_EXISTS";
613 		break;
614 	case CRYPTO_SESSION_READ_ONLY_EXISTS:
615 		valstr = "CRYPTO_SESSION_READ_ONLY_EXISTS";
616 		break;
617 	case CRYPTO_SESSION_READ_WRITE_SO_EXISTS:
618 		valstr = "CRYPTO_SESSION_READ_WRITE_SO_EXISTS";
619 		break;
620 	case CRYPTO_SIGNATURE_INVALID:
621 		valstr = "CRYPTO_SIGNATURE_INVALID";
622 		break;
623 	case CRYPTO_SIGNATURE_LEN_RANGE:
624 		valstr = "CRYPTO_SIGNATURE_LEN_RANGE";
625 		break;
626 	case CRYPTO_TEMPLATE_INCOMPLETE:
627 		valstr = "CRYPTO_TEMPLATE_INCOMPLETE";
628 		break;
629 	case CRYPTO_TEMPLATE_INCONSISTENT:
630 		valstr = "CRYPTO_TEMPLATE_INCONSISTENT";
631 		break;
632 	case CRYPTO_UNWRAPPING_KEY_HANDLE_INVALID:
633 		valstr = "CRYPTO_UNWRAPPING_KEY_HANDLE_INVALID";
634 		break;
635 	case CRYPTO_UNWRAPPING_KEY_SIZE_RANGE:
636 		valstr = "CRYPTO_UNWRAPPING_KEY_SIZE_RANGE";
637 		break;
638 	case CRYPTO_UNWRAPPING_KEY_TYPE_INCONSISTENT:
639 		valstr = "CRYPTO_UNWRAPPING_KEY_TYPE_INCONSISTENT";
640 		break;
641 	case CRYPTO_USER_ALREADY_LOGGED_IN:
642 		valstr = "CRYPTO_USER_ALREADY_LOGGED_IN";
643 		break;
644 	case CRYPTO_USER_NOT_LOGGED_IN:
645 		valstr = "CRYPTO_USER_NOT_LOGGED_IN";
646 		break;
647 	case CRYPTO_USER_PIN_NOT_INITIALIZED:
648 		valstr = "CRYPTO_USER_PIN_NOT_INITIALIZED";
649 		break;
650 	case CRYPTO_USER_TYPE_INVALID:
651 		valstr = "CRYPTO_USER_TYPE_INVALID";
652 		break;
653 	case CRYPTO_USER_ANOTHER_ALREADY_LOGGED_IN:
654 		valstr = "CRYPTO_USER_ANOTHER_ALREADY_LOGGED_IN";
655 		break;
656 	case CRYPTO_USER_TOO_MANY_TYPES:
657 		valstr = "CRYPTO_USER_TOO_MANY_TYPES";
658 		break;
659 	case CRYPTO_WRAPPED_KEY_INVALID:
660 		valstr = "CRYPTO_WRAPPED_KEY_INVALID";
661 		break;
662 	case CRYPTO_WRAPPED_KEY_LEN_RANGE:
663 		valstr = "CRYPTO_WRAPPED_KEY_LEN_RANGE";
664 		break;
665 	case CRYPTO_WRAPPING_KEY_HANDLE_INVALID:
666 		valstr = "CRYPTO_WRAPPING_KEY_HANDLE_INVALID";
667 		break;
668 	case CRYPTO_WRAPPING_KEY_SIZE_RANGE:
669 		valstr = "CRYPTO_WRAPPING_KEY_SIZE_RANGE";
670 		break;
671 	case CRYPTO_WRAPPING_KEY_TYPE_INCONSISTENT:
672 		valstr = "CRYPTO_WRAPPING_KEY_TYPE_INCONSISTENT";
673 		break;
674 	case CRYPTO_RANDOM_SEED_NOT_SUPPORTED:
675 		valstr = "CRYPTO_RANDOM_SEED_NOT_SUPPORTED";
676 		break;
677 	case CRYPTO_RANDOM_NO_RNG:
678 		valstr = "CRYPTO_RANDOM_NO_RNG";
679 		break;
680 	case CRYPTO_DOMAIN_PARAMS_INVALID:
681 		valstr = "CRYPTO_DOMAIN_PARAMS_INVALID";
682 		break;
683 	case CRYPTO_BUFFER_TOO_SMALL:
684 		valstr = "CRYPTO_BUFFER_TOO_SMALL";
685 		break;
686 	case CRYPTO_INFORMATION_SENSITIVE:
687 		valstr = "CRYPTO_INFORMATION_SENSITIVE";
688 		break;
689 	case CRYPTO_NOT_SUPPORTED:
690 		valstr = "CRYPTO_NOT_SUPPORTED";
691 		break;
692 	case CRYPTO_QUEUED:
693 		valstr = "CRYPTO_QUEUED";
694 		break;
695 	case CRYPTO_BUFFER_TOO_BIG:
696 		valstr = "CRYPTO_BUFFER_TOO_BIG";
697 		break;
698 	case CRYPTO_INVALID_CONTEXT:
699 		valstr = "CRYPTO_INVALID_CONTEXT";
700 		break;
701 	case CRYPTO_INVALID_MAC:
702 		valstr = "CRYPTO_INVALID_MAC";
703 		break;
704 	case CRYPTO_MECH_NOT_SUPPORTED:
705 		valstr = "CRYPTO_MECH_NOT_SUPPORTED";
706 		break;
707 	case CRYPTO_INCONSISTENT_ATTRIBUTE:
708 		valstr = "CRYPTO_INCONSISTENT_ATTRIBUTE";
709 		break;
710 	case CRYPTO_NO_PERMISSION:
711 		valstr = "CRYPTO_NO_PERMISSION";
712 		break;
713 	case CRYPTO_INVALID_PROVIDER_ID:
714 		valstr = "CRYPTO_INVALID_PROVIDER_ID";
715 		break;
716 	case CRYPTO_VERSION_MISMATCH:
717 		valstr = "CRYPTO_VERSION_MISMATCH";
718 		break;
719 	case CRYPTO_BUSY:
720 		valstr = "CRYPTO_BUSY";
721 		break;
722 	case CRYPTO_UNKNOWN_PROVIDER:
723 		valstr = "CRYPTO_UNKNOWN_PROVIDER";
724 		break;
725 	case CRYPTO_MODVERIFICATION_FAILED:
726 		valstr = "CRYPTO_MODVERIFICATION_FAILED";
727 		break;
728 	case CRYPTO_OLD_CTX_TEMPLATE:
729 		valstr = "CRYPTO_OLD_CTX_TEMPLATE";
730 		break;
731 	case CRYPTO_WEAK_KEY:
732 		valstr = "CRYPTO_WEAK_KEY";
733 		break;
734 	case CRYPTO_FIPS140_ERROR:
735 		valstr = "CRYPTO_FIPS140_ERROR";
736 		break;
737 	default:
738 		valstr = "Unknown KCF error";
739 		break;
740 	}
741 
742 	(void) snprintf(buf, buflen, "%s (0x%08x)", valstr, e);
743 	return (buf);
744 }
745