xref: /onnv-gate/usr/src/common/crypto/fips/fips_aes_util.c (revision 10500:a10fbcfc2f21)
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 2009 Sun Microsystems, Inc.  All rights reserved.
23  * Use is subject to license terms.
24  */
25 
26 #include <sys/types.h>
27 #include <sys/param.h>
28 #include <sys/cmn_err.h>
29 #include <sys/errno.h>
30 #include <sys/kmem.h>
31 #include <sys/systm.h>
32 #include <sys/crypto/common.h>
33 #include <modes/modes.h>
34 #define	_AES_FIPS_POST
35 #ifndef	_KERNEL
36 #include <stdlib.h>
37 #include <string.h>
38 #include <strings.h>
39 #include <stdio.h>
40 #include <security/cryptoki.h>
41 #include <cryptoutil.h>
42 #include "softCrypt.h"
43 #else
44 #define	_AES_IMPL
45 #include <aes/aes_impl.h>
46 #endif
47 
48 
49 #ifdef _KERNEL
50 void *
51 aes_cbc_ctx_init(void *key_sched, size_t size, uint8_t *ivec)
52 {
53 
54 	cbc_ctx_t *cbc_ctx;
55 
56 	if ((cbc_ctx = kmem_zalloc(sizeof (cbc_ctx_t), KM_SLEEP)) == NULL)
57 		return (NULL);
58 
59 	cbc_ctx->cbc_keysched = key_sched;
60 	cbc_ctx->cbc_keysched_len = size;
61 
62 	(void) memcpy(&cbc_ctx->cbc_iv[0], ivec, AES_BLOCK_LEN);
63 
64 	cbc_ctx->cbc_lastp = (uint8_t *)cbc_ctx->cbc_iv;
65 	cbc_ctx->cbc_flags |= CBC_MODE;
66 
67 	return (cbc_ctx);
68 }
69 
70 /*
71  * Allocate and initialize a context for AES CTR mode of operation.
72  */
73 void *
74 aes_ctr_ctx_init(void *key_sched, size_t size, uint8_t *param)
75 {
76 
77 	ctr_ctx_t *ctr_ctx;
78 	CK_AES_CTR_PARAMS *pp;
79 
80 	/* LINTED: pointer alignment */
81 	pp = (CK_AES_CTR_PARAMS *)param;
82 
83 	if ((ctr_ctx = kmem_zalloc(sizeof (ctr_ctx_t), KM_SLEEP)) == NULL)
84 		return (NULL);
85 
86 	ctr_ctx->ctr_keysched = key_sched;
87 	ctr_ctx->ctr_keysched_len = size;
88 
89 	if (ctr_init_ctx(ctr_ctx, pp->ulCounterBits, pp->cb,
90 	    aes_copy_block) != CRYPTO_SUCCESS) {
91 		kmem_free(ctr_ctx, sizeof (ctr_ctx_t));
92 		return (NULL);
93 	}
94 	ctr_ctx->ctr_flags |= CTR_MODE;
95 
96 	return (ctr_ctx);
97 }
98 
99 /*
100  * Allocate and initialize a context for AES CCM mode of operation.
101  */
102 void *
103 aes_ccm_ctx_init(void *key_sched, size_t size, uint8_t *param,
104 	boolean_t is_encrypt_init)
105 {
106 
107 	ccm_ctx_t *ccm_ctx;
108 
109 	if ((ccm_ctx = kmem_zalloc(sizeof (ccm_ctx_t), KM_SLEEP)) == NULL)
110 		return (NULL);
111 
112 	ccm_ctx->ccm_keysched = key_sched;
113 	ccm_ctx->ccm_keysched_len = size;
114 
115 	if (ccm_init_ctx(ccm_ctx, (char *)param, KM_SLEEP,
116 	    is_encrypt_init, AES_BLOCK_LEN, aes_encrypt_block,
117 	    aes_xor_block) != CRYPTO_SUCCESS) {
118 		kmem_free(ccm_ctx, sizeof (ccm_ctx_t));
119 		return (NULL);
120 	}
121 	ccm_ctx->ccm_flags |= CCM_MODE;
122 
123 	return (ccm_ctx);
124 }
125 
126 /*
127  * Allocate and initialize a context for AES CCM mode of operation.
128  */
129 void *
130 aes_gcm_ctx_init(void *key_sched, size_t size, uint8_t *param)
131 {
132 
133 	gcm_ctx_t *gcm_ctx;
134 
135 	if ((gcm_ctx = kmem_zalloc(sizeof (gcm_ctx_t), KM_SLEEP)) == NULL)
136 		return (NULL);
137 
138 	gcm_ctx->gcm_keysched = key_sched;
139 	gcm_ctx->gcm_keysched_len = size;
140 
141 	if (gcm_init_ctx(gcm_ctx, (char *)param, AES_BLOCK_LEN,
142 	    aes_encrypt_block, aes_copy_block,
143 	    aes_xor_block) != CRYPTO_SUCCESS) {
144 		kmem_free(gcm_ctx, sizeof (gcm_ctx_t));
145 		return (NULL);
146 	}
147 	gcm_ctx->gcm_flags |= GCM_MODE;
148 
149 	return (gcm_ctx);
150 }
151 
152 void *
153 aes_gmac_ctx_init(void *key_sched, size_t size, uint8_t *param)
154 {
155 
156 	gcm_ctx_t *gcm_ctx;
157 
158 	if ((gcm_ctx = kmem_zalloc(sizeof (gcm_ctx_t), KM_SLEEP)) == NULL)
159 		return (NULL);
160 
161 	gcm_ctx->gcm_keysched = key_sched;
162 	gcm_ctx->gcm_keysched_len = size;
163 
164 	if (gmac_init_ctx(gcm_ctx, (char *)param, AES_BLOCK_LEN,
165 	    aes_encrypt_block, aes_copy_block,
166 	    aes_xor_block) != CRYPTO_SUCCESS) {
167 		kmem_free(gcm_ctx, sizeof (gcm_ctx_t));
168 		return (NULL);
169 	}
170 	gcm_ctx->gcm_flags |= GMAC_MODE;
171 
172 	return (gcm_ctx);
173 }
174 #endif
175 
176 
177 /*
178  * Allocate context for the active encryption or decryption operation, and
179  * generate AES key schedule to speed up the operation.
180  */
181 soft_aes_ctx_t *
182 #ifdef _KERNEL
183 fips_aes_build_context(uint8_t *key, int key_len, uint8_t *iv,
184 	aes_mech_type_t mechanism, boolean_t is_encrypt_init)
185 #else
186 fips_aes_build_context(uint8_t *key, int key_len, uint8_t *iv,
187 	CK_MECHANISM_TYPE mechanism)
188 #endif
189 {
190 	size_t size;
191 	soft_aes_ctx_t *soft_aes_ctx;
192 	CK_AES_CTR_PARAMS pp;
193 
194 #ifdef _KERNEL
195 	if ((soft_aes_ctx = kmem_zalloc(sizeof (soft_aes_ctx_t),
196 	    KM_SLEEP)) == NULL)
197 #else
198 	if ((soft_aes_ctx = calloc(1, sizeof (soft_aes_ctx_t)))
199 	    == NULL)
200 #endif
201 		return (NULL);
202 
203 
204 	soft_aes_ctx->key_sched = aes_alloc_keysched(&size, 0);
205 
206 	if (soft_aes_ctx->key_sched == NULL) {
207 #ifdef _KERNEL
208 		kmem_free(soft_aes_ctx, sizeof (soft_aes_ctx_t));
209 #else
210 		free(soft_aes_ctx);
211 #endif
212 		return (NULL);
213 	}
214 
215 	soft_aes_ctx->keysched_len = size;
216 
217 #ifdef	__sparcv9
218 	aes_init_keysched(key, (uint_t)(key_len * 8),
219 	    soft_aes_ctx->key_sched);
220 #else	/* !__sparcv9 */
221 	aes_init_keysched(key, (key_len * 8),
222 	    soft_aes_ctx->key_sched);
223 #endif	/* __sparcv9 */
224 
225 	switch (mechanism) {
226 
227 	case CKM_AES_CBC:
228 
229 		/* Save Initialization Vector (IV) in the context. */
230 		(void) memcpy(soft_aes_ctx->ivec, iv, AES_BLOCK_LEN);
231 		/* Allocate a context for AES cipher-block chaining. */
232 		soft_aes_ctx->aes_cbc = (void *)aes_cbc_ctx_init(
233 		    soft_aes_ctx->key_sched,
234 		    soft_aes_ctx->keysched_len,
235 		    soft_aes_ctx->ivec);
236 		break;
237 
238 	case CKM_AES_CTR:
239 
240 		pp.ulCounterBits = 16;
241 		(void) memcpy(pp.cb, iv, AES_BLOCK_LEN);
242 		soft_aes_ctx->aes_cbc = aes_ctr_ctx_init(
243 		    soft_aes_ctx->key_sched,
244 		    soft_aes_ctx->keysched_len,
245 		    (uint8_t *)&pp);
246 		break;
247 
248 #ifdef _KERNEL
249 	case AES_CCM_MECH_INFO_TYPE:
250 		soft_aes_ctx->aes_cbc = aes_ccm_ctx_init(
251 		    soft_aes_ctx->key_sched,
252 		    soft_aes_ctx->keysched_len, iv,
253 		    is_encrypt_init);
254 		break;
255 
256 	case AES_GCM_MECH_INFO_TYPE:
257 		soft_aes_ctx->aes_cbc = aes_gcm_ctx_init(
258 		    soft_aes_ctx->key_sched,
259 		    soft_aes_ctx->keysched_len, iv);
260 		break;
261 
262 	case AES_GMAC_MECH_INFO_TYPE:
263 		soft_aes_ctx->aes_cbc = aes_gmac_ctx_init(
264 		    soft_aes_ctx->key_sched,
265 		    soft_aes_ctx->keysched_len, iv);
266 		break;
267 #endif
268 	default:
269 		return (soft_aes_ctx);
270 	}
271 
272 	if (soft_aes_ctx->aes_cbc == NULL) {
273 		bzero(soft_aes_ctx->key_sched,
274 		    soft_aes_ctx->keysched_len);
275 #ifdef _KERNEL
276 		kmem_free(soft_aes_ctx->key_sched, size);
277 #else
278 		free(soft_aes_ctx->key_sched);
279 #endif
280 		return (NULL);
281 	}
282 
283 	return (soft_aes_ctx);
284 }
285 
286 #ifdef _KERNEL
287 void
288 fips_aes_free_context(soft_aes_ctx_t *soft_aes_ctx)
289 {
290 
291 	common_ctx_t *aes_ctx;
292 
293 	aes_ctx = (common_ctx_t *)soft_aes_ctx->aes_cbc;
294 
295 	if (aes_ctx != NULL) {
296 		bzero(aes_ctx->cc_keysched, aes_ctx->cc_keysched_len);
297 		kmem_free(aes_ctx->cc_keysched,
298 		    aes_ctx->cc_keysched_len);
299 		crypto_free_mode_ctx(aes_ctx);
300 	} else {
301 		/* ECB MODE */
302 		bzero(soft_aes_ctx->key_sched, soft_aes_ctx->keysched_len);
303 		kmem_free(soft_aes_ctx->key_sched, soft_aes_ctx->keysched_len);
304 	}
305 
306 	kmem_free(soft_aes_ctx, sizeof (soft_aes_ctx_t));
307 
308 }
309 
310 #else
311 void
312 fips_aes_free_context(soft_aes_ctx_t *soft_aes_ctx)
313 {
314 
315 	common_ctx_t *aes_ctx;
316 
317 	aes_ctx = (common_ctx_t *)soft_aes_ctx->aes_cbc;
318 
319 	if (aes_ctx != NULL) {
320 		bzero(aes_ctx->cc_keysched, aes_ctx->cc_keysched_len);
321 		free(aes_ctx->cc_keysched);
322 		free(soft_aes_ctx->aes_cbc);
323 	} else {
324 		/* ECB MODE */
325 		bzero(soft_aes_ctx->key_sched, soft_aes_ctx->keysched_len);
326 		free(soft_aes_ctx->key_sched);
327 	}
328 
329 	free(soft_aes_ctx);
330 
331 }
332 #endif
333 
334 /*
335  * fips_aes_encrypt()
336  *
337  * Arguments:
338  *	soft_aes_ctx:	pointer to AES context
339  *	in_buf:		pointer to the input data to be encrypted
340  *	ulDataLen:	length of the input data
341  *	out_buf:	pointer to the output data after encryption
342  *	pulEncryptedLen: pointer to the length of the output data
343  *	mechanism:	CKM_AES_ECB or CKM_AES_CBC
344  *
345  * Description:
346  *	This function calls the corresponding low-level encrypt
347  *	routine based on the mechanism.
348  *
349  */
350 #ifdef _KERNEL
351 int
352 fips_aes_encrypt(soft_aes_ctx_t *soft_aes_ctx, uchar_t *in_buf,
353 	ulong_t ulDataLen, uchar_t *out_buf,
354 	ulong_t *pulEncryptedLen, aes_mech_type_t mechanism)
355 #else
356 CK_RV
357 fips_aes_encrypt(soft_aes_ctx_t *soft_aes_ctx, CK_BYTE_PTR in_buf,
358 	CK_ULONG ulDataLen, CK_BYTE_PTR out_buf,
359 	CK_ULONG_PTR pulEncryptedLen, CK_MECHANISM_TYPE mechanism)
360 #endif
361 {
362 
363 	int rc = 0;
364 	CK_RV rv = CKR_OK;
365 	ulong_t out_len;
366 
367 	/*
368 	 * AES only takes input length that is a multiple of 16-byte
369 	 */
370 	if ((ulDataLen % AES_BLOCK_LEN) != 0)
371 		return (CKR_DATA_LEN_RANGE);
372 
373 	/*
374 	 * For non-padding mode, the output length will
375 	 * be same as the input length.
376 	 */
377 	out_len = ulDataLen;
378 
379 	/*
380 	 * Begin Encryption now.
381 	 */
382 	switch (mechanism) {
383 
384 	case CKM_AES_ECB:
385 	{
386 
387 		ulong_t i;
388 		uint8_t *tmp_inbuf;
389 		uint8_t *tmp_outbuf;
390 
391 		for (i = 0; i < out_len; i += AES_BLOCK_LEN) {
392 			tmp_inbuf = &in_buf[i];
393 			tmp_outbuf = &out_buf[i];
394 			/* Crunch one block of data for AES. */
395 			(void) aes_encrypt_block(soft_aes_ctx->key_sched,
396 			    tmp_inbuf, tmp_outbuf);
397 		}
398 
399 		*pulEncryptedLen = out_len;
400 
401 		break;
402 	}
403 
404 	case CKM_AES_CBC:
405 	{
406 		crypto_data_t out;
407 
408 		out.cd_format = CRYPTO_DATA_RAW;
409 		out.cd_offset = 0;
410 		out.cd_length = out_len;
411 		out.cd_raw.iov_base = (char *)out_buf;
412 		out.cd_raw.iov_len = out_len;
413 
414 		/* Encrypt multiple blocks of data. */
415 		rc = aes_encrypt_contiguous_blocks(
416 		    (aes_ctx_t *)soft_aes_ctx->aes_cbc,
417 		    (char *)in_buf, out_len, &out);
418 
419 		if (rc != 0)
420 			goto encrypt_failed;
421 
422 		if (rc == 0) {
423 			*pulEncryptedLen = out_len;
424 			break;
425 		}
426 encrypt_failed:
427 		*pulEncryptedLen = 0;
428 		return (CKR_DEVICE_ERROR);
429 	}
430 
431 	case CKM_AES_CTR:
432 	{
433 		crypto_data_t out;
434 
435 		out.cd_format = CRYPTO_DATA_RAW;
436 		out.cd_offset = 0;
437 		out.cd_length = out_len;
438 		out.cd_raw.iov_base = (char *)out_buf;
439 		out.cd_raw.iov_len = out_len;
440 
441 		rc = aes_encrypt_contiguous_blocks(soft_aes_ctx->aes_cbc,
442 		    (char *)in_buf, out_len, &out);
443 
444 		if (rc != 0) {
445 			*pulEncryptedLen = 0;
446 			return (CKR_DEVICE_ERROR);
447 		}
448 		/*
449 		 * Since AES counter mode is a stream cipher, we call
450 		 * aes_counter_final() to pick up any remaining bytes.
451 		 * It is an internal function that does not destroy
452 		 * the context like *normal* final routines.
453 		 */
454 		if (((aes_ctx_t *)soft_aes_ctx->aes_cbc)->ac_remainder_len
455 		    > 0) {
456 			rc = ctr_mode_final(soft_aes_ctx->aes_cbc, &out,
457 			    aes_encrypt_block);
458 			if (rc != 0) {
459 				*pulEncryptedLen = 0;
460 				return (CKR_DEVICE_ERROR);
461 			}
462 		}
463 
464 		*pulEncryptedLen = out_len;
465 		break;
466 	}
467 
468 #ifdef _KERNEL
469 	case AES_CCM_MECH_INFO_TYPE:
470 	{
471 		crypto_data_t out;
472 		size_t saved_length, length_needed;
473 		aes_ctx_t *aes_ctx = soft_aes_ctx->aes_cbc;
474 		ccm_ctx_t *ccm_ctx = soft_aes_ctx->aes_cbc;
475 
476 		length_needed = ulDataLen + aes_ctx->ac_mac_len;
477 
478 		out.cd_format = CRYPTO_DATA_RAW;
479 		out.cd_offset = 0;
480 		out.cd_length = length_needed;
481 		out.cd_raw.iov_base = (char *)out_buf;
482 		out.cd_raw.iov_len = length_needed;
483 
484 		saved_length = out.cd_length;
485 
486 		rc = aes_encrypt_contiguous_blocks(aes_ctx,
487 		    (char *)in_buf, ulDataLen, &out);
488 
489 		if (rc != 0) {
490 			*pulEncryptedLen = 0;
491 			return (rc);
492 		}
493 
494 		/*
495 		 * ccm_encrypt_final() will compute the MAC and append
496 		 * it to existing ciphertext. So, need to adjust the left over
497 		 * length value accordingly
498 		 */
499 
500 		/* order of following 2 lines MUST not be reversed */
501 		out.cd_offset = ccm_ctx->ccm_processed_data_len;
502 		out.cd_length = saved_length - ccm_ctx->ccm_processed_data_len;
503 
504 		rc = ccm_encrypt_final((ccm_ctx_t *)aes_ctx, &out,
505 		    AES_BLOCK_LEN, aes_encrypt_block, aes_xor_block);
506 
507 		if (rc != CRYPTO_SUCCESS) {
508 			*pulEncryptedLen = 0;
509 			return (rc);
510 		}
511 
512 		*pulEncryptedLen = length_needed;
513 		break;
514 	}
515 
516 	case AES_GCM_MECH_INFO_TYPE:
517 	{
518 		crypto_data_t out;
519 		size_t saved_length, length_needed;
520 		aes_ctx_t *aes_ctx = soft_aes_ctx->aes_cbc;
521 		gcm_ctx_t *gcm_ctx = soft_aes_ctx->aes_cbc;
522 
523 		/*
524 		 * Output:
525 		 * A ciphertext, denoted C, whose bit length is the same as
526 		 * that of the plaintext.
527 		 * An authentication tag, or tag, for short, denoted T.
528 		 */
529 
530 		length_needed = ulDataLen + aes_ctx->ac_tag_len;
531 
532 		out.cd_format = CRYPTO_DATA_RAW;
533 		out.cd_offset = 0;
534 		out.cd_length = length_needed;
535 		out.cd_raw.iov_base = (char *)out_buf;
536 		out.cd_raw.iov_len = length_needed;
537 
538 		saved_length = out.cd_length;
539 
540 		rc = aes_encrypt_contiguous_blocks(aes_ctx,
541 		    (char *)in_buf, ulDataLen, &out);
542 
543 		if (rc != 0) {
544 			*pulEncryptedLen = 0;
545 			return (rc);
546 		}
547 
548 		/*
549 		 * ccm_encrypt_final() will compute the MAC and append
550 		 * it to existing ciphertext. So, need to adjust the left over
551 		 * length value accordingly
552 		 */
553 
554 		/* order of following 2 lines MUST not be reversed */
555 		out.cd_offset = gcm_ctx->gcm_processed_data_len;
556 		out.cd_length = saved_length - gcm_ctx->gcm_processed_data_len;
557 
558 		rc = gcm_encrypt_final((gcm_ctx_t *)aes_ctx, &out,
559 		    AES_BLOCK_LEN, aes_encrypt_block, aes_copy_block,
560 		    aes_xor_block);
561 
562 		if (rc != CRYPTO_SUCCESS) {
563 			*pulEncryptedLen = 0;
564 			return (rc);
565 		}
566 
567 		*pulEncryptedLen = length_needed;
568 		break;
569 	}
570 
571 	case AES_GMAC_MECH_INFO_TYPE:
572 	{
573 		crypto_data_t out;
574 		size_t length_needed;
575 		aes_ctx_t *aes_ctx = soft_aes_ctx->aes_cbc;
576 
577 		length_needed = aes_ctx->ac_tag_len;
578 
579 		out.cd_format = CRYPTO_DATA_RAW;
580 		out.cd_offset = 0;
581 		out.cd_length = length_needed;
582 		out.cd_raw.iov_base = (char *)out_buf;
583 		out.cd_raw.iov_len = length_needed;
584 
585 		rc = gcm_encrypt_final((gcm_ctx_t *)aes_ctx, &out,
586 		    AES_BLOCK_LEN, aes_encrypt_block, aes_copy_block,
587 		    aes_xor_block);
588 
589 		if (rc != CRYPTO_SUCCESS) {
590 			*pulEncryptedLen = 0;
591 			return (rc);
592 		}
593 
594 		*pulEncryptedLen = length_needed;
595 		break;
596 	}
597 #endif /* _KERNEL */
598 	} /* end switch */
599 
600 	return (rv);
601 }
602 
603 /*
604  * fips_aes_decrypt()
605  *
606  * Arguments:
607  *	soft_aes_ctx:	pointer to AES context
608  *	in_buf:	pointer to the input data to be decrypted
609  *	ulEncryptedLen:	length of the input data
610  *	out_buf:	pointer to the output data
611  *	pulDataLen:	pointer to the length of the output data
612  *	mechanism:	CKM_AES_ECB or CKM_AES_CBC
613  *
614  * Description:
615  *      This function calls the corresponding low-level decrypt
616  *	function based on the mechanism.
617  *
618  */
619 #ifdef _KERNEL
620 int
621 fips_aes_decrypt(soft_aes_ctx_t *soft_aes_ctx, uchar_t *in_buf,
622 	ulong_t ulEncryptedLen, uchar_t *out_buf,
623 	ulong_t *pulDataLen, aes_mech_type_t mechanism)
624 #else
625 CK_RV
626 fips_aes_decrypt(soft_aes_ctx_t *soft_aes_ctx, CK_BYTE_PTR in_buf,
627 	CK_ULONG ulEncryptedLen, CK_BYTE_PTR out_buf,
628 	CK_ULONG_PTR pulDataLen, CK_MECHANISM_TYPE mechanism)
629 #endif
630 {
631 
632 	int rc = 0;
633 	CK_RV rv = CKR_OK;
634 	ulong_t out_len;
635 
636 	/*
637 	 * AES only takes input length that is a multiple of 16 bytes
638 	 */
639 	if ((ulEncryptedLen % AES_BLOCK_LEN) != 0)
640 		return (CKR_ENCRYPTED_DATA_LEN_RANGE);
641 
642 	/*
643 	 * For non-padding mode, the output length will
644 	 * be same as the input length.
645 	 */
646 	out_len = ulEncryptedLen;
647 
648 	/*
649 	 * Begin Decryption.
650 	 */
651 	switch (mechanism) {
652 
653 	case CKM_AES_ECB:
654 	{
655 
656 		ulong_t i;
657 		uint8_t *tmp_inbuf;
658 		uint8_t *tmp_outbuf;
659 
660 		for (i = 0; i < out_len; i += AES_BLOCK_LEN) {
661 			tmp_inbuf = &in_buf[i];
662 			tmp_outbuf = &out_buf[i];
663 			/* Crunch one block of data for AES. */
664 			(void) aes_decrypt_block(soft_aes_ctx->key_sched,
665 			    tmp_inbuf, tmp_outbuf);
666 		}
667 
668 		*pulDataLen = out_len;
669 
670 		break;
671 	}
672 
673 	case CKM_AES_CBC:
674 	{
675 		crypto_data_t out;
676 
677 		out.cd_format = CRYPTO_DATA_RAW;
678 		out.cd_offset = 0;
679 		out.cd_length = out_len;
680 		out.cd_raw.iov_base = (char *)out_buf;
681 		out.cd_raw.iov_len = out_len;
682 
683 		/* Decrypt multiple blocks of data. */
684 		rc = aes_decrypt_contiguous_blocks(
685 		    (aes_ctx_t *)soft_aes_ctx->aes_cbc,
686 		    (char *)in_buf, out_len, &out);
687 
688 		if (rc != 0)
689 			goto decrypt_failed;
690 
691 
692 		*pulDataLen = out_len;
693 
694 		if (rc == 0)
695 			break;
696 decrypt_failed:
697 		*pulDataLen = 0;
698 		return (CKR_DEVICE_ERROR);
699 	}
700 
701 	case CKM_AES_CTR:
702 	{
703 		crypto_data_t out;
704 
705 		out.cd_format = CRYPTO_DATA_RAW;
706 		out.cd_offset = 0;
707 		out.cd_length = *pulDataLen;
708 		out.cd_raw.iov_base = (char *)out_buf;
709 		out.cd_raw.iov_len = *pulDataLen;
710 
711 		rc = aes_decrypt_contiguous_blocks(soft_aes_ctx->aes_cbc,
712 		    (char *)in_buf, out_len, &out);
713 
714 		if (rc != 0) {
715 			*pulDataLen = 0;
716 			return (CKR_DEVICE_ERROR);
717 		}
718 
719 		/*
720 		 * Since AES counter mode is a stream cipher, we call
721 		 * aes_counter_final() to pick up any remaining bytes.
722 		 * It is an internal function that does not destroy
723 		 * the context like *normal* final routines.
724 		 */
725 		if (((aes_ctx_t *)soft_aes_ctx->aes_cbc)->ac_remainder_len
726 		    > 0) {
727 			rc = ctr_mode_final(soft_aes_ctx->aes_cbc, &out,
728 			    aes_encrypt_block);
729 
730 			if (rc == CKR_DATA_LEN_RANGE)
731 				return (CKR_ENCRYPTED_DATA_LEN_RANGE);
732 		}
733 
734 		*pulDataLen = out_len;
735 		break;
736 	}
737 
738 #ifdef _KERNEL
739 	case AES_CCM_MECH_INFO_TYPE:
740 	{
741 		crypto_data_t out;
742 		size_t length_needed;
743 		aes_ctx_t *aes_ctx = soft_aes_ctx->aes_cbc;
744 		ccm_ctx_t *ccm_ctx = soft_aes_ctx->aes_cbc;
745 
746 		length_needed = ulEncryptedLen + ccm_ctx->ccm_mac_len;
747 
748 		out.cd_format = CRYPTO_DATA_RAW;
749 		out.cd_offset = 0;
750 		out.cd_length = ulEncryptedLen;
751 		out.cd_raw.iov_base = (char *)out_buf;
752 		out.cd_raw.iov_len = ulEncryptedLen;
753 
754 		rc = aes_decrypt_contiguous_blocks(aes_ctx,
755 		    (char *)in_buf, length_needed, &out);
756 
757 		if (rc != 0) {
758 			*pulDataLen = 0;
759 			return (CRYPTO_FAILED);
760 		}
761 
762 		/* order of following 2 lines MUST not be reversed */
763 		out.cd_offset = 0;
764 		out.cd_length = ulEncryptedLen;
765 
766 		rc = ccm_decrypt_final((ccm_ctx_t *)aes_ctx, &out,
767 		    AES_BLOCK_LEN, aes_encrypt_block, aes_copy_block,
768 		    aes_xor_block);
769 
770 		if (rc != CRYPTO_SUCCESS) {
771 			*pulDataLen = 0;
772 			return (CRYPTO_FAILED);
773 		}
774 
775 		*pulDataLen = ulEncryptedLen;
776 
777 		break;
778 	}
779 
780 	case AES_GCM_MECH_INFO_TYPE:
781 	{
782 		crypto_data_t out;
783 		size_t length_needed;
784 		aes_ctx_t *aes_ctx = soft_aes_ctx->aes_cbc;
785 
786 		length_needed = ulEncryptedLen + aes_ctx->ac_tag_len;
787 
788 		out.cd_format = CRYPTO_DATA_RAW;
789 		out.cd_offset = 0;
790 		out.cd_length = ulEncryptedLen;
791 		out.cd_raw.iov_base = (char *)out_buf;
792 		out.cd_raw.iov_len = ulEncryptedLen;
793 
794 		rc = aes_decrypt_contiguous_blocks(aes_ctx,
795 		    (char *)in_buf, length_needed, &out);
796 
797 		if (rc != 0) {
798 			*pulDataLen = 0;
799 			return (CRYPTO_FAILED);
800 		}
801 
802 		/* order of following 2 lines MUST not be reversed */
803 		out.cd_offset = 0;
804 		out.cd_length = aes_ctx->ac_tag_len;
805 
806 		rc = gcm_decrypt_final((gcm_ctx_t *)aes_ctx, &out,
807 		    AES_BLOCK_LEN, aes_encrypt_block,
808 		    aes_xor_block);
809 
810 		if (rc != CRYPTO_SUCCESS) {
811 			*pulDataLen = 0;
812 			return (CRYPTO_FAILED);
813 		}
814 
815 		*pulDataLen = ulEncryptedLen;
816 
817 		break;
818 	}
819 
820 	case AES_GMAC_MECH_INFO_TYPE:
821 	{
822 		crypto_data_t out;
823 		size_t length_needed;
824 		aes_ctx_t *aes_ctx = soft_aes_ctx->aes_cbc;
825 
826 		length_needed = aes_ctx->ac_tag_len;
827 
828 		out.cd_format = CRYPTO_DATA_RAW;
829 		out.cd_offset = 0;
830 		out.cd_length = 0;
831 		out.cd_raw.iov_base = (char *)NULL;
832 		out.cd_raw.iov_len = 0;
833 
834 		rc = aes_decrypt_contiguous_blocks(aes_ctx,
835 		    (char *)in_buf, length_needed, &out);
836 
837 		if (rc != 0) {
838 			*pulDataLen = 0;
839 			return (CRYPTO_FAILED);
840 		}
841 
842 		/* order of following 2 lines MUST not be reversed */
843 		out.cd_format = CRYPTO_DATA_RAW;
844 		out.cd_offset = 0;
845 		out.cd_length = 0;
846 		out.cd_raw.iov_base = (char *)NULL;
847 		out.cd_raw.iov_len = 0;
848 
849 		rc = gcm_decrypt_final((gcm_ctx_t *)aes_ctx, &out,
850 		    AES_BLOCK_LEN, aes_encrypt_block,
851 		    aes_xor_block);
852 
853 		if (rc != CRYPTO_SUCCESS) {
854 			*pulDataLen = 0;
855 			return (CRYPTO_FAILED);
856 		}
857 
858 		*pulDataLen = 0;
859 
860 		break;
861 	}
862 #endif
863 	} /* end switch */
864 
865 	return (rv);
866 }
867 
868 /* AES self-test for 128-bit, 192-bit, or 256-bit key sizes */
869 int
870 fips_aes_post(int aes_key_size)
871 {
872 	/* AES Known Key (up to 256-bits). */
873 	static uint8_t aes_known_key[] = {
874 		"AES-128 RIJNDAELLEADNJIR 821-SEA"
875 	};
876 
877 	/* AES-CBC Known Initialization Vector (128-bits). */
878 	static uint8_t aes_cbc_known_initialization_vector[] =
879 		{ "SecurityytiruceS" };
880 
881 	/* AES Known Plaintext (128-bits). (blocksize is 128-bits) */
882 	static uint8_t aes_known_plaintext[] = { "Sun Open Solaris" };
883 
884 	/* AES Known Ciphertext (128-bit key). */
885 	static uint8_t aes_ecb128_known_ciphertext[] = {
886 		0xcc, 0xd1, 0xd0, 0xf3, 0xfd, 0x44, 0xb1, 0x4d,
887 		0xfe, 0x33, 0x20, 0x72, 0x3c, 0xf3, 0x4d, 0x27
888 	};
889 
890 	static uint8_t aes_cbc128_known_ciphertext[]  = {
891 		0x59, 0x34, 0x55, 0xd1, 0x89, 0x9b, 0xf4, 0xa5,
892 		0x16, 0x2c, 0x4c, 0x14, 0xd3, 0xe2, 0xe5, 0xed
893 	};
894 
895 	/* AES Known Ciphertext (192-bit key). */
896 	static uint8_t aes_ecb192_known_ciphertext[] = {
897 		0xa3, 0x78, 0x10, 0x44, 0xd8, 0xee, 0x8a, 0x98,
898 		0x41, 0xa4, 0xeb, 0x96, 0x57, 0xd8, 0xa0, 0xc5
899 	};
900 
901 	static uint8_t aes_cbc192_known_ciphertext[]  = {
902 		0x22, 0x9c, 0x68, 0xc6, 0x86, 0x68, 0xcc, 0x6a,
903 		0x56, 0x2c, 0xb8, 0xe0, 0x16, 0x4e, 0x8b, 0x78
904 	};
905 
906 	/* AES Known Ciphertext (256-bit key). */
907 	static uint8_t aes_ecb256_known_ciphertext[] = {
908 		0xe4, 0x65, 0x92, 0x7f, 0xd0, 0xdd, 0x59, 0x49,
909 		0x79, 0xc3, 0xac, 0x96, 0x30, 0xad, 0x32, 0x52
910 	};
911 
912 	static uint8_t aes_cbc256_known_ciphertext[]  = {
913 		0xd9, 0x44, 0x43, 0xe8, 0xdb, 0x60, 0x6b, 0xde,
914 		0xc2, 0x84, 0xbf, 0xb9, 0xaf, 0x43, 0x3f, 0x51
915 	};
916 
917 	uint8_t *aes_ecb_known_ciphertext =
918 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
919 	    aes_ecb128_known_ciphertext :
920 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
921 	    aes_ecb192_known_ciphertext :
922 	    aes_ecb256_known_ciphertext;
923 
924 	uint8_t *aes_cbc_known_ciphertext =
925 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
926 	    aes_cbc128_known_ciphertext :
927 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
928 	    aes_cbc192_known_ciphertext :
929 	    aes_cbc256_known_ciphertext;
930 
931 	/* AES-CTR Known Key (128-bits). */
932 	static uint8_t aes_ctr128_known_key[] = {
933 		0x2b, 0x7e, 0x15, 0x16, 0x28, 0xae, 0xd2, 0xa6,
934 		0xab, 0xf7, 0x15, 0x88, 0x09, 0xcf, 0x4f, 0x3c
935 	};
936 
937 	/* AES-CTR Known Key (192-bits). */
938 	static uint8_t aes_ctr192_known_key[] = {
939 		0x8e, 0x73, 0xb0, 0xf7, 0xda, 0x0e, 0x64, 0x52,
940 		0xc8, 0x10, 0xf3, 0x2b, 0x80, 0x90, 0x79, 0xe5,
941 		0x62, 0xf8, 0xea, 0xd2, 0x52, 0x2c, 0x6b, 0x7b
942 	};
943 
944 	/* AES-CTR Known Key (256-bits). */
945 	static uint8_t aes_ctr256_known_key[] = {
946 		0x60, 0x3d, 0xeb, 0x10, 0x15, 0xca, 0x71, 0xbe,
947 		0x2b, 0x73, 0xae, 0xf0, 0x85, 0x7d, 0x77, 0x81,
948 		0x1f, 0x35, 0x2c, 0x07, 0x3b, 0x61, 0x08, 0xd7,
949 		0x2d, 0x98, 0x10, 0xa3, 0x09, 0x14, 0xdf, 0xf4
950 	};
951 
952 	/* AES-CTR Known Initialization Counter (128-bits). */
953 	static uint8_t aes_ctr_known_counter[] = {
954 		0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7,
955 		0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
956 	};
957 
958 	/* AES-CTR Known Plaintext (128-bits). */
959 	static uint8_t aes_ctr_known_plaintext[] = {
960 		0x6b, 0xc1, 0xbe, 0xe2, 0x2e, 0x40, 0x9f, 0x96,
961 		0xe9, 0x3d, 0x7e, 0x11, 0x73, 0x93, 0x17, 0x2a
962 	};
963 
964 	/* AES-CTR Known Ciphertext. */
965 	static uint8_t aes_ctr128_known_ciphertext[] = {
966 		0x87, 0x4d, 0x61, 0x91, 0xb6, 0x20, 0xe3, 0x26,
967 		0x1b, 0xef, 0x68, 0x64, 0x99, 0x0d, 0xb6, 0xce
968 	};
969 
970 	static uint8_t aes_ctr192_known_ciphertext[]  = {
971 		0x1a, 0xbc, 0x93, 0x24, 0x17, 0x52, 0x1c, 0xa2,
972 		0x4f, 0x2b, 0x04, 0x59, 0xfe, 0x7e, 0x6e, 0x0b
973 	};
974 
975 	static uint8_t aes_ctr256_known_ciphertext[]  = {
976 		0x60, 0x1e, 0xc3, 0x13, 0x77, 0x57, 0x89, 0xa5,
977 		0xb7, 0xa7, 0xf5, 0x04, 0xbb, 0xf3, 0xd2, 0x28
978 	};
979 
980 	uint8_t *aes_ctr_known_ciphertext =
981 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
982 	    aes_ctr128_known_ciphertext :
983 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
984 	    aes_ctr192_known_ciphertext :
985 	    aes_ctr256_known_ciphertext;
986 
987 	uint8_t *aes_ctr_known_key =
988 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
989 	    aes_ctr128_known_key :
990 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
991 	    aes_ctr192_known_key :
992 	    aes_ctr256_known_key;
993 
994 #ifdef _KERNEL
995 	/* AES-CCM Known Key (128-bits). */
996 	static uint8_t aes_ccm128_known_key[] = {
997 		0x06, 0xfd, 0xf0, 0x83, 0xb5, 0xcb, 0x3b, 0xc7,
998 		0xc0, 0x6d, 0x4d, 0xe5, 0xa6, 0x34, 0xc6, 0x50
999 	};
1000 
1001 	/* AES-CCM Known Key (192-bits). */
1002 	static uint8_t aes_ccm192_known_key[] = {
1003 		0xde, 0x91, 0x08, 0x63, 0xbe, 0x59, 0xb8, 0x7a,
1004 		0x45, 0x9b, 0xa6, 0xce, 0x2d, 0x7e, 0x71, 0x56,
1005 		0x1c, 0x5c, 0x15, 0xea, 0x1b, 0x6b, 0x05, 0x06
1006 	};
1007 
1008 	/* AES-CCM Known Key (256-bits). */
1009 	static uint8_t aes_ccm256_known_key[] = {
1010 		0x84, 0x9c, 0x1d, 0xeb, 0x80, 0xf8, 0x5b, 0x7d,
1011 		0x25, 0x33, 0x64, 0x75, 0x4b, 0xdc, 0x5d, 0xf0,
1012 		0xe8, 0x1c, 0x98, 0x8a, 0x78, 0x8f, 0x15, 0xd1,
1013 		0xa2, 0x52, 0x49, 0xfa, 0x18, 0x5e, 0x1f, 0xd3
1014 	};
1015 
1016 	/* AES-CCM Known Nonce Nlen = 7 bytes (for 128-bits key). */
1017 	static uint8_t aes_ccm128_known_nonce[] = {
1018 		0xfd, 0xe2, 0xd5, 0x4c, 0x65, 0x4e, 0xe4
1019 	};
1020 
1021 	/* AES-CCM Known Nonce Nlen = 7 bytes (192-bits). */
1022 	static uint8_t aes_ccm192_known_nonce[] = {
1023 		0xcf, 0xb3, 0x48, 0xfa, 0x04, 0x36, 0xa2
1024 	};
1025 
1026 	/* AES-CCM Known Nonce Nlen = 7 bytes (256-bits). */
1027 	static uint8_t aes_ccm256_known_nonce[] = {
1028 		0x75, 0xa5, 0x5b, 0x58, 0x33, 0x9d, 0x1c
1029 	};
1030 
1031 	/* AES-CCM Known Adata Alen = 30 bytes (128-bits). */
1032 	static uint8_t aes_ccm128_known_adata[] = {
1033 		0xe0, 0xdf, 0xfc, 0x4c, 0x92, 0x90, 0xd8, 0x28,
1034 		0xef, 0xe7, 0xc6, 0xbe, 0x4a, 0xbc, 0xd1, 0x3e,
1035 		0x23, 0x61, 0x92, 0x2f, 0xfa, 0x27, 0xa4, 0x0e,
1036 		0x61, 0x24, 0x58, 0x38, 0x55, 0x33
1037 	};
1038 
1039 	/* AES-CCM Known Adata Alen = 30 bytes (192-bits). */
1040 	static uint8_t aes_ccm192_known_adata[] = {
1041 		0x4c, 0x5b, 0x4f, 0xfe, 0x80, 0xba, 0x7a, 0xe5,
1042 		0xd3, 0xe8, 0xbc, 0xf6, 0x55, 0x83, 0xcf, 0x58,
1043 		0xa2, 0x82, 0x59, 0x65, 0xba, 0xbd, 0x63, 0x53,
1044 		0x0c, 0xb0, 0x0c, 0x14, 0xd4, 0x7b
1045 	};
1046 
1047 	/* AES-CCM Known Adata Alen = 30 bytes (256-bits). */
1048 	static uint8_t aes_ccm256_known_adata[] = {
1049 		0x27, 0xb7, 0xec, 0x91, 0x08, 0xe1, 0x4d, 0x12,
1050 		0xd3, 0xd3, 0xb8, 0x49, 0x09, 0xde, 0xd0, 0x9a,
1051 		0x8f, 0x23, 0xbf, 0xd6, 0x02, 0x9b, 0x2a, 0x5e,
1052 		0x4a, 0x5a, 0x63, 0x8c, 0x72, 0x14
1053 	};
1054 
1055 	/* AES-CCM Known Payload Plen = 32 bytes (128-bits). */
1056 	static uint8_t aes_ccm128_known_plaintext[] = {
1057 		0x77, 0xca, 0xdf, 0xa5, 0xb1, 0x23, 0xfe, 0x07,
1058 		0x8d, 0xca, 0x94, 0xe2, 0x66, 0x3f, 0x73, 0xd0,
1059 		0x3f, 0x0b, 0x4d, 0xc8, 0x05, 0xf6, 0x1c, 0xef,
1060 		0x13, 0x79, 0xc0, 0xb1, 0xfc, 0x76, 0xea, 0x11
1061 	};
1062 
1063 	/* AES-CCM Known Payload Plen = 32 bytes (192-bits). */
1064 	static uint8_t aes_ccm192_known_plaintext[] = {
1065 		0xf9, 0x8a, 0x58, 0x59, 0x44, 0x2d, 0x2a, 0xf9,
1066 		0x65, 0x03, 0x36, 0x6d, 0x8a, 0x58, 0x29, 0xf9,
1067 		0xef, 0x47, 0x44, 0x30, 0xf4, 0x7e, 0x0d, 0xcd,
1068 		0x73, 0x41, 0x45, 0xdf, 0x50, 0xb2, 0x1b, 0x29
1069 	};
1070 
1071 	/* AES-CCM Known Payload Plen = 32 bytes (256-bits). */
1072 	static uint8_t aes_ccm256_known_plaintext[] = {
1073 		0x25, 0x28, 0x3f, 0x05, 0x41, 0xd6, 0x66, 0x3b,
1074 		0xdb, 0x8f, 0xe9, 0xe7, 0x7b, 0x06, 0xc0, 0xee,
1075 		0xfe, 0xf6, 0xc9, 0x8b, 0x45, 0x08, 0x18, 0x4e,
1076 		0x2e, 0xf7, 0x8e, 0x64, 0xc3, 0xf2, 0xad, 0x18
1077 	};
1078 
1079 	/*
1080 	 * AES-CCM Known Ciphertext
1081 	 * Clen = 32 bytes + Tlen = 16 bytes (128-bits).
1082 	 */
1083 	static uint8_t aes_ccm128_known_ciphertext[] = {
1084 		0x33, 0x50, 0x58, 0xbb, 0x5f, 0x13, 0x8d, 0xc9,
1085 		0x5b, 0x2c, 0xa4, 0x50, 0x1d, 0x7f, 0xd4, 0xa5,
1086 		0xb9, 0xb8, 0x71, 0x83, 0x8f, 0x82, 0x27, 0x5f,
1087 		0x75, 0x3e, 0x30, 0xf9, 0x9d, 0xad, 0xc2, 0xe9,
1088 		0x66, 0x93, 0x56, 0x98, 0x01, 0x1e, 0x3c, 0x11,
1089 		0x74, 0xdb, 0x9b, 0xca, 0xce, 0x0f, 0xc3, 0x35
1090 	};
1091 
1092 	/*
1093 	 * AES-CCM Known Ciphertext
1094 	 * Clen = 32 bytes + Tlen = 16 bytes (192-bits).
1095 	 */
1096 	static uint8_t aes_ccm192_known_ciphertext[] = {
1097 		0xa7, 0x40, 0xd0, 0x25, 0xbd, 0x3e, 0x8f, 0xd5,
1098 		0x28, 0x3e, 0xee, 0xaa, 0xf9, 0xa7, 0xfc, 0xf2,
1099 		0x33, 0xf6, 0x69, 0xb8, 0xdc, 0x9c, 0x74, 0xb1,
1100 		0x46, 0xf4, 0xd6, 0xcc, 0x0a, 0x16, 0x12, 0x0c,
1101 		0x7c, 0x3c, 0x43, 0x76, 0x94, 0xf6, 0x9a, 0x14,
1102 		0xa0, 0xfb, 0xab, 0x9c, 0x2c, 0xd3, 0x5c, 0x09
1103 	};
1104 
1105 	/*
1106 	 * AES-CCM Known Ciphertext
1107 	 * Clen = 32 bytes + Tlen = 16 bytes (256-bits).
1108 	 */
1109 	static uint8_t aes_ccm256_known_ciphertext[] = {
1110 		0xf6, 0x4d, 0x24, 0x69, 0x0e, 0xde, 0xc9, 0xc0,
1111 		0x1e, 0x42, 0xc0, 0x78, 0x29, 0xcf, 0xdb, 0xfe,
1112 		0xab, 0x52, 0x9a, 0xb1, 0x07, 0xe4, 0xac, 0xdf,
1113 		0x48, 0x46, 0x46, 0xc1, 0xe2, 0xb2, 0x0f, 0x36,
1114 		0x5f, 0xeb, 0x44, 0xcf, 0xa8, 0x80, 0x80, 0x23,
1115 		0xc9, 0xee, 0xc7, 0x56, 0x24, 0x63, 0x6e, 0x7e
1116 	};
1117 
1118 	uint8_t *aes_ccm_known_plaintext =
1119 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1120 	    aes_ccm128_known_plaintext :
1121 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1122 	    aes_ccm192_known_plaintext :
1123 	    aes_ccm256_known_plaintext;
1124 
1125 	uint8_t *aes_ccm_known_ciphertext =
1126 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1127 	    aes_ccm128_known_ciphertext :
1128 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1129 	    aes_ccm192_known_ciphertext :
1130 	    aes_ccm256_known_ciphertext;
1131 
1132 	uint8_t *aes_ccm_known_key =
1133 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1134 	    aes_ccm128_known_key :
1135 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1136 	    aes_ccm192_known_key :
1137 	    aes_ccm256_known_key;
1138 
1139 	uint8_t *aes_ccm_known_adata =
1140 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1141 	    aes_ccm128_known_adata :
1142 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1143 	    aes_ccm192_known_adata :
1144 	    aes_ccm256_known_adata;
1145 
1146 	uint8_t *aes_ccm_known_nonce =
1147 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1148 	    aes_ccm128_known_nonce :
1149 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1150 	    aes_ccm192_known_nonce :
1151 	    aes_ccm256_known_nonce;
1152 
1153 	/* AES-GCM Known Key (128-bits). */
1154 	static uint8_t aes_gcm128_known_key[] = {
1155 		0x7d, 0xf9, 0x9c, 0xdf, 0x7d, 0x00, 0xd9, 0xea,
1156 		0xd3, 0x85, 0x17, 0x1b, 0x29, 0xae, 0xcf, 0xbc
1157 	};
1158 
1159 	/* AES-GCM Known Key (192-bits). */
1160 	static uint8_t aes_gcm192_known_key[] = {
1161 		0x85, 0xf4, 0x34, 0x7a, 0xf5, 0x98, 0x1e, 0xd9,
1162 		0x89, 0x85, 0x98, 0x1a, 0x53, 0xfc, 0xc5, 0xbf,
1163 		0x53, 0x6c, 0x91, 0x4b, 0x18, 0x3c, 0xe8, 0x12
1164 	};
1165 
1166 	/* AES-GCM	 Known Key (256-bits). */
1167 	static uint8_t aes_gcm256_known_key[] = {
1168 		0xee, 0xbc, 0x1f, 0x57, 0x48, 0x7f, 0x51, 0x92,
1169 		0x1c, 0x04, 0x65, 0x66, 0x5f, 0x8a, 0xe6, 0xd1,
1170 		0x65, 0x8b, 0xb2, 0x6d, 0xe6, 0xf8, 0xa0, 0x69,
1171 		0xa3, 0x52, 0x02, 0x93, 0xa5, 0x72, 0x07, 0x8f
1172 	};
1173 
1174 	/* AES-GCM Known Initialization Vector (128-bits). */
1175 	static uint8_t aes_gcm128_known_iv[] = {
1176 		0x27, 0x4c, 0x4e, 0xae, 0xfe, 0xef, 0xae, 0x26,
1177 		0x80, 0xb0, 0xef, 0xd5
1178 	};
1179 
1180 	/* AES-GCM Known Initialization Vector (192-bits). */
1181 	static uint8_t aes_gcm192_known_iv[] = {
1182 		0xd4, 0xfb, 0x33, 0xc6, 0x51, 0xc8, 0x86, 0xff,
1183 		0x28, 0x80, 0xef, 0x96
1184 	};
1185 
1186 	/* AES-GCM Known Initialization Vector (256-bits). */
1187 	static uint8_t aes_gcm256_known_iv[] = {
1188 		0x99, 0xaa, 0x3e, 0x68, 0xed, 0x81, 0x73, 0xa0,
1189 		0xee, 0xd0, 0x66, 0x84
1190 	};
1191 
1192 	/* AES-GCM Known AAD Alen = 16 bytes (128-bits). */
1193 	static uint8_t aes_gcm128_known_adata[] = {
1194 		0x60, 0xe8, 0xb0, 0x37, 0xec, 0xdf, 0x4d, 0x82,
1195 		0x8c, 0x83, 0x0d, 0xcf, 0xc5, 0xce, 0xd4, 0x9c
1196 	};
1197 
1198 	/* AES-GCM Known AAD Alen = 16 bytes (192-bits). */
1199 	static uint8_t aes_gcm192_known_adata[] = {
1200 		0x44, 0x3a, 0xdf, 0xad, 0xbb, 0x29, 0xd6, 0x8c,
1201 		0x55, 0xe2, 0x02, 0x2d, 0xca, 0x62, 0x9b, 0x51
1202 	};
1203 
1204 	/* AES-GCM Known AAD Alen = 16 bytes (256-bits). */
1205 	static uint8_t aes_gcm256_known_adata[] = {
1206 		0x4d, 0x23, 0xc3, 0xce, 0xc3, 0x34, 0xb4, 0x9b,
1207 		0xdb, 0x37, 0x0c, 0x43, 0x7f, 0xec, 0x78, 0xde
1208 	};
1209 
1210 	/* AES-GCM Known Payload Plen = 16 bytes (128-bits). */
1211 	static uint8_t aes_gcm128_known_plaintext[] = {
1212 		0x99, 0x66, 0x7d, 0xc9, 0x62, 0xb3, 0x9f, 0x14,
1213 		0x8c, 0xdd, 0xfe, 0x68, 0xf9, 0x0a, 0x43, 0xf9
1214 	};
1215 
1216 	/* AES-GCM Known Payload Plen = 16 bytes (192-bits). */
1217 	static uint8_t aes_gcm192_known_plaintext[] = {
1218 		0x7f, 0x9c, 0x08, 0x1d, 0x6a, 0xcc, 0xa8, 0xab,
1219 		0x71, 0x75, 0xcb, 0xd0, 0x49, 0x42, 0xba, 0xad
1220 	};
1221 	/* AES-GCM Known Payload Plen = 16 bytes (256-bits). */
1222 	static uint8_t aes_gcm256_known_plaintext[] = {
1223 		0xf5, 0x6e, 0x87, 0x05, 0x5b, 0xc3, 0x2d, 0x0e,
1224 		0xeb, 0x31, 0xb2, 0xea, 0xcc, 0x2b, 0xf2, 0xa5
1225 	};
1226 
1227 	/* AES-GCM Known Ciphertext Clen = 16 bytes (128-bits) + tag */
1228 	static uint8_t aes_gcm128_known_ciphertext[] = {
1229 		0x2b, 0x5f, 0x57, 0xf2, 0x62, 0x27, 0xe0, 0x94,
1230 		0xe7, 0xf8, 0x01, 0x23, 0xf9, 0xed, 0xbd, 0xe8,
1231 		0x16, 0xee, 0x08, 0xb4, 0xd8, 0x07, 0xe5, 0xdb,
1232 		0xd5, 0x70, 0x3c, 0xb3, 0xcf, 0x53, 0x8c, 0x14
1233 	};
1234 
1235 	/* AES-GCM Known Ciphertext Clen = 16 bytes (192-bits) + tag */
1236 	static uint8_t aes_gcm192_known_ciphertext[] = {
1237 		0xdd, 0x7e, 0x7e, 0x45, 0x5b, 0x21, 0xd8, 0x84,
1238 		0x3d, 0x7b, 0xc3, 0x1f, 0x21, 0x07, 0xf9, 0x55,
1239 		0x9f, 0x0e, 0x8d, 0xe2, 0x6d, 0xb4, 0x95, 0xf5,
1240 		0x91, 0x1f, 0xb6, 0x0c, 0xf5, 0xf2, 0x3a, 0xf9
1241 	};
1242 
1243 	/* AES-GCM Known Ciphertext Clen = 16 bytes (256-bits)+ tag */
1244 	static uint8_t aes_gcm256_known_ciphertext[] = {
1245 		0xf7, 0x26, 0x44, 0x13, 0xa8, 0x4c, 0x0e, 0x7c,
1246 		0xd5, 0x36, 0x86, 0x7e, 0xb9, 0xf2, 0x17, 0x36,
1247 		0x67, 0xba, 0x05, 0x10, 0x26, 0x2a, 0xe4, 0x87,
1248 		0xd7, 0x37, 0xee, 0x62, 0x98, 0xf7, 0x7e, 0x0c
1249 	};
1250 
1251 	uint8_t *aes_gcm_known_key =
1252 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1253 	    aes_gcm128_known_key :
1254 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1255 	    aes_gcm192_known_key :
1256 	    aes_gcm256_known_key;
1257 
1258 	uint8_t *aes_gcm_known_iv =
1259 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1260 	    aes_gcm128_known_iv :
1261 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1262 	    aes_gcm192_known_iv :
1263 	    aes_gcm256_known_iv;
1264 
1265 	uint8_t *aes_gcm_known_plaintext =
1266 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1267 	    aes_gcm128_known_plaintext :
1268 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1269 	    aes_gcm192_known_plaintext :
1270 	    aes_gcm256_known_plaintext;
1271 
1272 	uint8_t *aes_gcm_known_ciphertext =
1273 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1274 	    aes_gcm128_known_ciphertext :
1275 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1276 	    aes_gcm192_known_ciphertext :
1277 	    aes_gcm256_known_ciphertext;
1278 
1279 	uint8_t *aes_gcm_known_adata =
1280 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1281 	    aes_gcm128_known_adata :
1282 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1283 	    aes_gcm192_known_adata :
1284 	    aes_gcm256_known_adata;
1285 
1286 	/*
1287 	 * Source: NIST gcmEncryptExtIV128.txt
1288 	 * Count = 0, [Keylen = 128], [IVlen = 96], [PTlen = 0],
1289 	 * [AADlen = 128], [Taglen = 128]
1290 	 *
1291 	 * Source: NIST gcmEncryptExtIV192.txt
1292 	 * Count = 0, [Keylen = 192], [IVlen = 96], [PTlen = 0],
1293 	 * [AADlen = 128], [Taglen = 128]
1294 	 *
1295 	 * Source: NIST gcmEncryptExtIV256.txt
1296 	 * Count = 0, [Keylen = 256], [IVlen = 96], [PTlen = 0],
1297 	 * [AADlen = 128], [Taglen = 128]
1298 	 */
1299 
1300 	/* AES-GMAC Known Key (128-bits). */
1301 	static uint8_t aes_gmac128_known_key[] = {
1302 		0x7d, 0x70, 0xd2, 0x32, 0x48, 0xc4, 0x7e, 0xb3,
1303 		0xd2, 0x73, 0xdf, 0x81, 0xed, 0x30, 0x24, 0xbd
1304 	};
1305 
1306 	/* AES-GMAC Known Key (192-bits). */
1307 	static uint8_t aes_gmac192_known_key[] = {
1308 		0x03, 0x60, 0x22, 0xfe, 0x26, 0x9a, 0xdc, 0xad,
1309 		0xb5, 0x73, 0x11, 0xa4, 0xa0, 0xed, 0x2a, 0x84,
1310 		0x18, 0x34, 0xb8, 0xb6, 0xd8, 0xa0, 0x7f, 0x41
1311 	};
1312 
1313 	/* AES-GMAC Known Key (256-bits). */
1314 	static uint8_t aes_gmac256_known_key[] = {
1315 		0xbb, 0x10, 0x10, 0x06, 0x4f, 0xb8, 0x35, 0x23,
1316 		0xea, 0x9d, 0xf3, 0x2b, 0xad, 0x9f, 0x1f, 0x2a,
1317 		0x4f, 0xce, 0xfc, 0x0f, 0x21, 0x07, 0xc0, 0xaa,
1318 		0xba, 0xd9, 0xb7, 0x56, 0xd8, 0x09, 0x21, 0x9d
1319 	};
1320 
1321 	/* AES-GMAC Known Initialization Vector (128-bits). */
1322 	static uint8_t aes_gmac128_known_iv[] = {
1323 		0xab, 0x53, 0x23, 0x33, 0xd6, 0x76, 0x51, 0x20,
1324 		0x8b, 0x8c, 0x34, 0x85
1325 	};
1326 
1327 	/* AES-GMAC Known Initialization Vector (192-bits). */
1328 	static uint8_t aes_gmac192_known_iv[] = {
1329 		0x85, 0x65, 0xb2, 0x15, 0x3a, 0x3f, 0x34, 0x9a,
1330 		0x07, 0x31, 0x06, 0x79
1331 	};
1332 
1333 	/* AES-GMAC Known Initialization Vector (256-bits). */
1334 	static uint8_t aes_gmac256_known_iv[] = {
1335 		0x2f, 0x9a, 0xd0, 0x12, 0xad, 0xfc, 0x12, 0x73,
1336 		0x43, 0xfb, 0xe0, 0x56
1337 	};
1338 
1339 	/* AES-GMAC Known Tag (128-bits). */
1340 	static uint8_t aes_gmac128_known_tag[] = {
1341 		0xcf, 0x89, 0x50, 0xa3, 0x10, 0xf5, 0xab, 0x8b,
1342 		0x69, 0xd5, 0x00, 0x11, 0x1a, 0x44, 0xb0, 0x96
1343 	};
1344 
1345 	/* AES-GMAC Known Tag (192-bits). */
1346 	static uint8_t aes_gmac192_known_tag[] = {
1347 		0x90, 0x21, 0xaf, 0x4c, 0xa0, 0x8d, 0x01, 0xef,
1348 		0x82, 0x5a, 0x42, 0xf9, 0xbe, 0x3a, 0xb3, 0xe9
1349 	};
1350 
1351 	/* AES-GMAC Known Tag (256-bits). */
1352 	static uint8_t aes_gmac256_known_tag[] = {
1353 		0xef, 0x06, 0xd5, 0x4d, 0xfd, 0x00, 0x02, 0x1d,
1354 		0x75, 0x27, 0xdf, 0xf2, 0x6f, 0xc9, 0xd4, 0x84
1355 	};
1356 
1357 	/* AES-GMAC Known AAD Alen = 16 bytes (128-bits). */
1358 	static uint8_t aes_gmac128_known_adata[] = {
1359 		0x7d, 0x1d, 0x42, 0xe8, 0x94, 0x60, 0xe9, 0x44,
1360 		0xbf, 0xa4, 0x83, 0xdb, 0xe6, 0x92, 0xf0, 0x8d
1361 	};
1362 
1363 	/* AES-GMAC Known AAD Alen = 16 bytes (192-bits). */
1364 	static uint8_t aes_gmac192_known_adata[] = {
1365 		0xad, 0xcf, 0x4f, 0xbb, 0xa0, 0xe0, 0x6a, 0x63,
1366 		0x70, 0x71, 0x1a, 0x57, 0xf8, 0xdc, 0xd0, 0xc9
1367 	};
1368 
1369 	/* AES-GMAC Known AAD Alen = 16 bytes (256-bits). */
1370 	static uint8_t aes_gmac256_known_adata[] = {
1371 		0xdb, 0x98, 0xd9, 0x0d, 0x1b, 0x69, 0x5c, 0xdb,
1372 		0x74, 0x7a, 0x34, 0x3f, 0xbb, 0xc9, 0xf1, 0x41
1373 	};
1374 
1375 	uint8_t *aes_gmac_known_key =
1376 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1377 	    aes_gmac128_known_key :
1378 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1379 	    aes_gmac192_known_key :
1380 	    aes_gmac256_known_key;
1381 
1382 	uint8_t *aes_gmac_known_iv =
1383 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1384 	    aes_gmac128_known_iv :
1385 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1386 	    aes_gmac192_known_iv :
1387 	    aes_gmac256_known_iv;
1388 
1389 	uint8_t *aes_gmac_known_tag =
1390 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1391 	    aes_gmac128_known_tag :
1392 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1393 	    aes_gmac192_known_tag :
1394 	    aes_gmac256_known_tag;
1395 
1396 	uint8_t *aes_gmac_known_adata =
1397 	    (aes_key_size == FIPS_AES_128_KEY_SIZE) ?
1398 	    aes_gmac128_known_adata :
1399 	    (aes_key_size == FIPS_AES_192_KEY_SIZE) ?
1400 	    aes_gmac192_known_adata :
1401 	    aes_gmac256_known_adata;
1402 
1403 	/* AES variables. */
1404 	uint8_t aes_ccm_computed_ciphertext[3*FIPS_AES_ENCRYPT_LENGTH];
1405 	uint8_t aes_ccm_computed_plaintext[2*FIPS_AES_DECRYPT_LENGTH];
1406 	uint8_t aes_gcm_computed_ciphertext[2*FIPS_AES_ENCRYPT_LENGTH];
1407 	uint8_t aes_gcm_computed_plaintext[FIPS_AES_DECRYPT_LENGTH];
1408 	uint8_t aes_gmac_computed_tag[FIPS_AES_ENCRYPT_LENGTH];
1409 	CK_AES_CCM_PARAMS ccm_param;
1410 	CK_AES_GCM_PARAMS gcm_param;
1411 	CK_AES_GMAC_PARAMS gmac_param;
1412 #endif
1413 
1414 	uint8_t aes_computed_ciphertext[FIPS_AES_ENCRYPT_LENGTH];
1415 	uint8_t aes_computed_plaintext[FIPS_AES_DECRYPT_LENGTH];
1416 	soft_aes_ctx_t  *aes_context;
1417 	ulong_t aes_bytes_encrypted;
1418 	ulong_t aes_bytes_decrypted;
1419 	int rv;
1420 
1421 	/* check if aes_key_size is 128, 192, or 256 bits */
1422 	if ((aes_key_size != FIPS_AES_128_KEY_SIZE) &&
1423 	    (aes_key_size != FIPS_AES_192_KEY_SIZE) &&
1424 	    (aes_key_size != FIPS_AES_256_KEY_SIZE))
1425 		return (CKR_DEVICE_ERROR);
1426 
1427 	/*
1428 	 * AES-ECB Known Answer Encryption Test
1429 	 */
1430 #ifdef _KERNEL
1431 	aes_context = fips_aes_build_context(aes_known_key,
1432 	    aes_key_size, NULL, AES_ECB_MECH_INFO_TYPE, B_FALSE);
1433 #else
1434 	aes_context = fips_aes_build_context(aes_known_key,
1435 	    aes_key_size, NULL, CKM_AES_ECB);
1436 #endif
1437 
1438 	if (aes_context == NULL) {
1439 		return (CKR_HOST_MEMORY);
1440 	}
1441 
1442 	rv = fips_aes_encrypt(aes_context, aes_known_plaintext,
1443 	    FIPS_AES_ENCRYPT_LENGTH, aes_computed_ciphertext,
1444 	    &aes_bytes_encrypted, CKM_AES_ECB);
1445 
1446 	fips_aes_free_context(aes_context);
1447 
1448 	if ((rv != CKR_OK) ||
1449 	    (aes_bytes_encrypted != FIPS_AES_ENCRYPT_LENGTH) ||
1450 	    (memcmp(aes_computed_ciphertext, aes_ecb_known_ciphertext,
1451 	    FIPS_AES_ENCRYPT_LENGTH) != 0))
1452 		return (CKR_DEVICE_ERROR);
1453 
1454 	/*
1455 	 * AES-ECB Known Answer Decryption Test
1456 	 */
1457 #ifdef _KERNEL
1458 	aes_context = fips_aes_build_context(aes_known_key,
1459 	    aes_key_size, NULL, AES_ECB_MECH_INFO_TYPE, B_FALSE);
1460 #else
1461 	aes_context = fips_aes_build_context(aes_known_key,
1462 	    aes_key_size, NULL, CKM_AES_ECB);
1463 #endif
1464 
1465 	if (aes_context == NULL) {
1466 		return (CKR_HOST_MEMORY);
1467 	}
1468 
1469 	rv = fips_aes_decrypt(aes_context, aes_ecb_known_ciphertext,
1470 	    FIPS_AES_DECRYPT_LENGTH, aes_computed_plaintext,
1471 	    &aes_bytes_decrypted, CKM_AES_ECB);
1472 
1473 	fips_aes_free_context(aes_context);
1474 
1475 	if ((rv != CKR_OK) ||
1476 	    (aes_bytes_decrypted != FIPS_AES_DECRYPT_LENGTH) ||
1477 	    (memcmp(aes_computed_plaintext, aes_known_plaintext,
1478 	    FIPS_AES_DECRYPT_LENGTH) != 0))
1479 		return (CKR_DEVICE_ERROR);
1480 
1481 	/*
1482 	 * AES-CBC Known Answer Encryption Test
1483 	 */
1484 #ifdef _KERNEL
1485 	aes_context = fips_aes_build_context(aes_known_key,
1486 	    aes_key_size, aes_cbc_known_initialization_vector,
1487 	    AES_CBC_MECH_INFO_TYPE, B_FALSE);
1488 #else
1489 	aes_context = fips_aes_build_context(aes_known_key,
1490 	    aes_key_size, aes_cbc_known_initialization_vector,
1491 	    CKM_AES_CBC);
1492 #endif
1493 
1494 	if (aes_context == NULL) {
1495 		return (CKR_HOST_MEMORY);
1496 	}
1497 
1498 	rv = fips_aes_encrypt(aes_context, aes_known_plaintext,
1499 	    FIPS_AES_ENCRYPT_LENGTH, aes_computed_ciphertext,
1500 	    &aes_bytes_encrypted, CKM_AES_CBC);
1501 
1502 	fips_aes_free_context(aes_context);
1503 
1504 	if ((rv != CKR_OK) ||
1505 	    (aes_bytes_encrypted != FIPS_AES_ENCRYPT_LENGTH) ||
1506 	    (memcmp(aes_computed_ciphertext, aes_cbc_known_ciphertext,
1507 	    FIPS_AES_ENCRYPT_LENGTH) != 0))
1508 		return (CKR_DEVICE_ERROR);
1509 
1510 	/*
1511 	 * AES-CBC Known Answer Decryption Test
1512 	 */
1513 #ifdef _KERNEL
1514 	aes_context = fips_aes_build_context(aes_known_key,
1515 	    aes_key_size, aes_cbc_known_initialization_vector,
1516 	    AES_CBC_MECH_INFO_TYPE, B_FALSE);
1517 #else
1518 	aes_context = fips_aes_build_context(aes_known_key,
1519 	    aes_key_size, aes_cbc_known_initialization_vector,
1520 	    CKM_AES_CBC);
1521 #endif
1522 
1523 	if (aes_context == NULL)
1524 		return (CRYPTO_HOST_MEMORY);
1525 
1526 	rv = fips_aes_decrypt(aes_context, aes_cbc_known_ciphertext,
1527 	    FIPS_AES_DECRYPT_LENGTH, aes_computed_plaintext,
1528 	    &aes_bytes_decrypted, CKM_AES_CBC);
1529 
1530 	fips_aes_free_context(aes_context);
1531 
1532 	if ((rv != CKR_OK) ||
1533 	    (aes_bytes_decrypted != FIPS_AES_DECRYPT_LENGTH) ||
1534 	    (memcmp(aes_computed_plaintext, aes_known_plaintext,
1535 	    FIPS_AES_DECRYPT_LENGTH) != 0))
1536 		return (CKR_DEVICE_ERROR);
1537 
1538 	/*
1539 	 * AES-CTR Known Answer Encryption Test
1540 	 */
1541 #ifdef _KERNEL
1542 	aes_context = fips_aes_build_context(aes_ctr_known_key,
1543 	    aes_key_size, aes_ctr_known_counter,
1544 	    AES_CTR_MECH_INFO_TYPE, B_FALSE);
1545 #else
1546 	aes_context = fips_aes_build_context(aes_ctr_known_key,
1547 	    aes_key_size, aes_ctr_known_counter, CKM_AES_CTR);
1548 #endif
1549 
1550 	if (aes_context == NULL) {
1551 		return (CKR_HOST_MEMORY);
1552 	}
1553 
1554 	rv = fips_aes_encrypt(aes_context, aes_ctr_known_plaintext,
1555 	    FIPS_AES_ENCRYPT_LENGTH, aes_computed_ciphertext,
1556 	    &aes_bytes_encrypted, CKM_AES_CTR);
1557 
1558 	fips_aes_free_context(aes_context);
1559 
1560 	if ((rv != CKR_OK) ||
1561 	    (aes_bytes_encrypted != FIPS_AES_ENCRYPT_LENGTH) ||
1562 	    (memcmp(aes_computed_ciphertext, aes_ctr_known_ciphertext,
1563 	    FIPS_AES_ENCRYPT_LENGTH) != 0))
1564 		return (CKR_DEVICE_ERROR);
1565 
1566 	/*
1567 	 * AES-CTR Known Answer Decryption Test
1568 	 */
1569 #ifdef _KERNEL
1570 	aes_context = fips_aes_build_context(aes_ctr_known_key,
1571 	    aes_key_size, aes_ctr_known_counter,
1572 	    AES_CTR_MECH_INFO_TYPE, B_FALSE);
1573 #else
1574 	aes_context = fips_aes_build_context(aes_ctr_known_key,
1575 	    aes_key_size, aes_ctr_known_counter,
1576 	    CKM_AES_CTR);
1577 #endif
1578 	if (aes_context == NULL) {
1579 		return (CKR_HOST_MEMORY);
1580 	}
1581 
1582 	rv = fips_aes_decrypt(aes_context, aes_ctr_known_ciphertext,
1583 	    FIPS_AES_DECRYPT_LENGTH, aes_computed_plaintext,
1584 	    &aes_bytes_decrypted, CKM_AES_CTR);
1585 
1586 	fips_aes_free_context(aes_context);
1587 
1588 	if ((rv != CKR_OK) ||
1589 	    (aes_bytes_decrypted != FIPS_AES_DECRYPT_LENGTH) ||
1590 	    (memcmp(aes_computed_plaintext, aes_ctr_known_plaintext,
1591 	    FIPS_AES_DECRYPT_LENGTH) != 0))
1592 		return (CKR_DEVICE_ERROR);
1593 
1594 	/*
1595 	 * The following POSTs are only available in Kernel
1596 	 *
1597 	 * CCM, GCM, and GMAC
1598 	 */
1599 #ifdef _KERNEL
1600 
1601 	/*
1602 	 * AES-CCM Known Answer Encryption Test
1603 	 */
1604 	ccm_param.ulMACSize = 16; /* Tlen */
1605 	ccm_param.ulNonceSize = 7; /* Nlen */
1606 	ccm_param.ulAuthDataSize = 30; /* Alen */
1607 	ccm_param.ulDataSize = 32; /* Plen or Clen */
1608 	ccm_param.nonce = aes_ccm_known_nonce;
1609 	ccm_param.authData = aes_ccm_known_adata;
1610 
1611 	aes_context = fips_aes_build_context(aes_ccm_known_key,
1612 	    aes_key_size, (uint8_t *)&ccm_param,
1613 	    AES_CCM_MECH_INFO_TYPE, B_TRUE);
1614 
1615 	if (aes_context == NULL) {
1616 		return (CRYPTO_HOST_MEMORY);
1617 	}
1618 
1619 	rv = fips_aes_encrypt(aes_context, aes_ccm_known_plaintext,
1620 	    2*FIPS_AES_ENCRYPT_LENGTH, aes_ccm_computed_ciphertext,
1621 	    &aes_bytes_encrypted, AES_CCM_MECH_INFO_TYPE);
1622 
1623 	fips_aes_free_context(aes_context);
1624 
1625 	if ((rv != CRYPTO_SUCCESS) ||
1626 	    (aes_bytes_encrypted != 3*FIPS_AES_ENCRYPT_LENGTH) ||
1627 	    (memcmp(aes_ccm_computed_ciphertext, aes_ccm_known_ciphertext,
1628 	    3*FIPS_AES_ENCRYPT_LENGTH) != 0))
1629 		return (CRYPTO_DEVICE_ERROR);
1630 
1631 	/*
1632 	 * AES-CCM Known Answer Decryption Test
1633 	 */
1634 	ccm_param.ulMACSize = 16; /* Tlen */
1635 	ccm_param.ulNonceSize = 7; /* Nlen */
1636 	ccm_param.ulAuthDataSize = 30; /* Alen */
1637 	ccm_param.ulDataSize = 48; /* Plen or Clen */
1638 	ccm_param.nonce = aes_ccm_known_nonce;
1639 	ccm_param.authData = aes_ccm_known_adata;
1640 
1641 	aes_context = fips_aes_build_context(aes_ccm_known_key,
1642 	    aes_key_size, (uint8_t *)&ccm_param,
1643 	    AES_CCM_MECH_INFO_TYPE, B_FALSE);
1644 
1645 	if (aes_context == NULL) {
1646 		return (CRYPTO_HOST_MEMORY);
1647 	}
1648 
1649 	rv = fips_aes_decrypt(aes_context, aes_ccm_known_ciphertext,
1650 	    2*FIPS_AES_DECRYPT_LENGTH, aes_ccm_computed_plaintext,
1651 	    &aes_bytes_decrypted, AES_CCM_MECH_INFO_TYPE);
1652 
1653 	fips_aes_free_context(aes_context);
1654 
1655 	if ((rv != CRYPTO_SUCCESS) ||
1656 	    (aes_bytes_decrypted != 2*FIPS_AES_DECRYPT_LENGTH) ||
1657 	    (memcmp(aes_ccm_computed_plaintext, aes_ccm_known_plaintext,
1658 	    2*FIPS_AES_DECRYPT_LENGTH) != 0))
1659 		return (CRYPTO_DEVICE_ERROR);
1660 
1661 	/*
1662 	 * AES-GCM Known Answer Encryption Test
1663 	 */
1664 	gcm_param.pIv = aes_gcm_known_iv;
1665 	gcm_param.ulIvLen = AES_GMAC_IV_LEN; /* IVlen = 96 bits */
1666 	gcm_param.ulTagBits = AES_GMAC_TAG_BITS; /* Taglen = 128 bits */
1667 	gcm_param.ulAADLen = 16;
1668 	gcm_param.pAAD = aes_gcm_known_adata;
1669 
1670 	aes_context = fips_aes_build_context(aes_gcm_known_key,
1671 	    aes_key_size, (uint8_t *)&gcm_param,
1672 	    AES_GCM_MECH_INFO_TYPE, B_TRUE);
1673 
1674 	if (aes_context == NULL) {
1675 		return (CRYPTO_HOST_MEMORY);
1676 	}
1677 
1678 	rv = fips_aes_encrypt(aes_context, aes_gcm_known_plaintext,
1679 	    FIPS_AES_ENCRYPT_LENGTH, aes_gcm_computed_ciphertext,
1680 	    &aes_bytes_encrypted, AES_GCM_MECH_INFO_TYPE);
1681 
1682 	fips_aes_free_context(aes_context);
1683 
1684 	if ((rv != CRYPTO_SUCCESS) ||
1685 	    (aes_bytes_encrypted != 2*FIPS_AES_ENCRYPT_LENGTH) ||
1686 	    (memcmp(aes_gcm_computed_ciphertext, aes_gcm_known_ciphertext,
1687 	    2*FIPS_AES_ENCRYPT_LENGTH) != 0))
1688 		return (CRYPTO_DEVICE_ERROR);
1689 
1690 	/*
1691 	 * AES-GCM Known Answer Decryption Test
1692 	 */
1693 	aes_context = fips_aes_build_context(aes_gcm_known_key,
1694 	    aes_key_size, (uint8_t *)&gcm_param,
1695 	    AES_GCM_MECH_INFO_TYPE, B_FALSE);
1696 
1697 	if (aes_context == NULL) {
1698 		return (CRYPTO_HOST_MEMORY);
1699 	}
1700 
1701 	rv = fips_aes_decrypt(aes_context, aes_gcm_known_ciphertext,
1702 	    FIPS_AES_DECRYPT_LENGTH, aes_gcm_computed_plaintext,
1703 	    &aes_bytes_decrypted, AES_GCM_MECH_INFO_TYPE);
1704 
1705 	fips_aes_free_context(aes_context);
1706 
1707 	if ((rv != CRYPTO_SUCCESS) ||
1708 	    (aes_bytes_decrypted != FIPS_AES_DECRYPT_LENGTH) ||
1709 	    (memcmp(aes_gcm_computed_plaintext, aes_gcm_known_plaintext,
1710 	    FIPS_AES_DECRYPT_LENGTH) != 0))
1711 		return (CRYPTO_DEVICE_ERROR);
1712 
1713 	/*
1714 	 * AES-GMAC Known Answer Encryption Test
1715 	 */
1716 	gmac_param.pIv = aes_gmac_known_iv;
1717 	gmac_param.ulAADLen = 16;
1718 	gmac_param.pAAD = aes_gmac_known_adata;
1719 
1720 	aes_context = fips_aes_build_context(aes_gmac_known_key,
1721 	    aes_key_size, (uint8_t *)&gmac_param,
1722 	    AES_GMAC_MECH_INFO_TYPE, B_TRUE);
1723 
1724 	if (aes_context == NULL) {
1725 		return (CRYPTO_HOST_MEMORY);
1726 	}
1727 
1728 	rv = fips_aes_encrypt(aes_context, NULL,
1729 	    0, aes_gmac_computed_tag,
1730 	    &aes_bytes_encrypted, AES_GMAC_MECH_INFO_TYPE);
1731 
1732 	fips_aes_free_context(aes_context);
1733 
1734 	if ((rv != CRYPTO_SUCCESS) ||
1735 	    (aes_bytes_encrypted != FIPS_AES_ENCRYPT_LENGTH) ||
1736 	    (memcmp(aes_gmac_computed_tag, aes_gmac_known_tag,
1737 	    FIPS_AES_ENCRYPT_LENGTH) != 0))
1738 		return (CRYPTO_DEVICE_ERROR);
1739 
1740 	/*
1741 	 * AES-GMAC Known Answer Decryption Test
1742 	 */
1743 
1744 	aes_context = fips_aes_build_context(aes_gmac_known_key,
1745 	    aes_key_size, (uint8_t *)&gmac_param,
1746 	    AES_GMAC_MECH_INFO_TYPE, B_FALSE);
1747 
1748 	if (aes_context == NULL) {
1749 		return (CRYPTO_HOST_MEMORY);
1750 	}
1751 
1752 	rv = fips_aes_decrypt(aes_context, aes_gmac_known_tag,
1753 	    FIPS_AES_DECRYPT_LENGTH, NULL,
1754 	    &aes_bytes_decrypted, AES_GMAC_MECH_INFO_TYPE);
1755 
1756 	fips_aes_free_context(aes_context);
1757 
1758 	if ((rv != CRYPTO_SUCCESS) ||
1759 	    (aes_bytes_decrypted != 0))
1760 		return (CRYPTO_DEVICE_ERROR);
1761 
1762 #endif /* _KERNEL */
1763 
1764 	return (CRYPTO_SUCCESS);
1765 }
1766