Home | History | Annotate | Download | only in engine
      1 /*
      2  * Copyright (c) 2002 Bob Beck <beck (at) openbsd.org>
      3  * Copyright (c) 2002 Theo de Raadt
      4  * Copyright (c) 2002 Markus Friedl
      5  * All rights reserved.
      6  *
      7  * Redistribution and use in source and binary forms, with or without
      8  * modification, are permitted provided that the following conditions
      9  * are met:
     10  * 1. Redistributions of source code must retain the above copyright
     11  *    notice, this list of conditions and the following disclaimer.
     12  * 2. Redistributions in binary form must reproduce the above copyright
     13  *    notice, this list of conditions and the following disclaimer in the
     14  *    documentation and/or other materials provided with the distribution.
     15  *
     16  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND ANY
     17  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
     18  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
     19  * DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR ANY
     20  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
     21  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
     22  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
     23  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     24  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
     25  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     26  *
     27  */
     28 
     29 #include <openssl/objects.h>
     30 #include <openssl/engine.h>
     31 #include <openssl/evp.h>
     32 #include <openssl/bn.h>
     33 
     34 #if (defined(__unix__) || defined(unix)) && !defined(USG) && \
     35 	(defined(OpenBSD) || defined(__FreeBSD__))
     36 #include <sys/param.h>
     37 # if (OpenBSD >= 200112) || ((__FreeBSD_version >= 470101 && __FreeBSD_version < 500000) || __FreeBSD_version >= 500041)
     38 #  define HAVE_CRYPTODEV
     39 # endif
     40 # if (OpenBSD >= 200110)
     41 #  define HAVE_SYSLOG_R
     42 # endif
     43 #endif
     44 
     45 #ifndef HAVE_CRYPTODEV
     46 
     47 void
     48 ENGINE_load_cryptodev(void)
     49 {
     50 	/* This is a NOP on platforms without /dev/crypto */
     51 	return;
     52 }
     53 
     54 #else
     55 
     56 #include <sys/types.h>
     57 #include <crypto/cryptodev.h>
     58 #include <crypto/dh/dh.h>
     59 #include <crypto/dsa/dsa.h>
     60 #include <crypto/err/err.h>
     61 #include <crypto/rsa/rsa.h>
     62 #include <sys/ioctl.h>
     63 #include <errno.h>
     64 #include <stdio.h>
     65 #include <unistd.h>
     66 #include <fcntl.h>
     67 #include <stdarg.h>
     68 #include <syslog.h>
     69 #include <errno.h>
     70 #include <string.h>
     71 
     72 struct dev_crypto_state {
     73 	struct session_op d_sess;
     74 	int d_fd;
     75 
     76 #ifdef USE_CRYPTODEV_DIGESTS
     77 	char dummy_mac_key[HASH_MAX_LEN];
     78 
     79 	unsigned char digest_res[HASH_MAX_LEN];
     80 	char *mac_data;
     81 	int mac_len;
     82 
     83 	int copy;
     84 #endif
     85 };
     86 
     87 static u_int32_t cryptodev_asymfeat = 0;
     88 
     89 static int get_asym_dev_crypto(void);
     90 static int open_dev_crypto(void);
     91 static int get_dev_crypto(void);
     92 static int get_cryptodev_ciphers(const int **cnids);
     93 #ifdef USE_CRYPTODEV_DIGESTS
     94 static int get_cryptodev_digests(const int **cnids);
     95 #endif
     96 static int cryptodev_usable_ciphers(const int **nids);
     97 static int cryptodev_usable_digests(const int **nids);
     98 static int cryptodev_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
     99     const unsigned char *in, size_t inl);
    100 static int cryptodev_init_key(EVP_CIPHER_CTX *ctx, const unsigned char *key,
    101     const unsigned char *iv, int enc);
    102 static int cryptodev_cleanup(EVP_CIPHER_CTX *ctx);
    103 static int cryptodev_engine_ciphers(ENGINE *e, const EVP_CIPHER **cipher,
    104     const int **nids, int nid);
    105 static int cryptodev_engine_digests(ENGINE *e, const EVP_MD **digest,
    106     const int **nids, int nid);
    107 static int bn2crparam(const BIGNUM *a, struct crparam *crp);
    108 static int crparam2bn(struct crparam *crp, BIGNUM *a);
    109 static void zapparams(struct crypt_kop *kop);
    110 static int cryptodev_asym(struct crypt_kop *kop, int rlen, BIGNUM *r,
    111     int slen, BIGNUM *s);
    112 
    113 static int cryptodev_bn_mod_exp(BIGNUM *r, const BIGNUM *a,
    114     const BIGNUM *p, const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *m_ctx);
    115 static int cryptodev_rsa_nocrt_mod_exp(BIGNUM *r0, const BIGNUM *I,
    116     RSA *rsa, BN_CTX *ctx);
    117 static int cryptodev_rsa_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa, BN_CTX *ctx);
    118 static int cryptodev_dsa_bn_mod_exp(DSA *dsa, BIGNUM *r, BIGNUM *a,
    119     const BIGNUM *p, const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *m_ctx);
    120 static int cryptodev_dsa_dsa_mod_exp(DSA *dsa, BIGNUM *t1, BIGNUM *g,
    121     BIGNUM *u1, BIGNUM *pub_key, BIGNUM *u2, BIGNUM *p,
    122     BN_CTX *ctx, BN_MONT_CTX *mont);
    123 static DSA_SIG *cryptodev_dsa_do_sign(const unsigned char *dgst,
    124     int dlen, DSA *dsa);
    125 static int cryptodev_dsa_verify(const unsigned char *dgst, int dgst_len,
    126     DSA_SIG *sig, DSA *dsa);
    127 static int cryptodev_mod_exp_dh(const DH *dh, BIGNUM *r, const BIGNUM *a,
    128     const BIGNUM *p, const BIGNUM *m, BN_CTX *ctx,
    129     BN_MONT_CTX *m_ctx);
    130 static int cryptodev_dh_compute_key(unsigned char *key,
    131     const BIGNUM *pub_key, DH *dh);
    132 static int cryptodev_ctrl(ENGINE *e, int cmd, long i, void *p,
    133     void (*f)(void));
    134 void ENGINE_load_cryptodev(void);
    135 
    136 static const ENGINE_CMD_DEFN cryptodev_defns[] = {
    137 	{ 0, NULL, NULL, 0 }
    138 };
    139 
    140 static struct {
    141 	int	id;
    142 	int	nid;
    143 	int	ivmax;
    144 	int	keylen;
    145 } ciphers[] = {
    146 	{ CRYPTO_ARC4,			NID_rc4,		0,	16, },
    147 	{ CRYPTO_DES_CBC,		NID_des_cbc,		8,	 8, },
    148 	{ CRYPTO_3DES_CBC,		NID_des_ede3_cbc,	8,	24, },
    149 	{ CRYPTO_AES_CBC,		NID_aes_128_cbc,	16,	16, },
    150 	{ CRYPTO_AES_CBC,		NID_aes_192_cbc,	16,	24, },
    151 	{ CRYPTO_AES_CBC,		NID_aes_256_cbc,	16,	32, },
    152 	{ CRYPTO_BLF_CBC,		NID_bf_cbc,		8,	16, },
    153 	{ CRYPTO_CAST_CBC,		NID_cast5_cbc,		8,	16, },
    154 	{ CRYPTO_SKIPJACK_CBC,		NID_undef,		0,	 0, },
    155 	{ 0,				NID_undef,		0,	 0, },
    156 };
    157 
    158 #ifdef USE_CRYPTODEV_DIGESTS
    159 static struct {
    160 	int	id;
    161 	int	nid;
    162 	int 	keylen;
    163 } digests[] = {
    164 	{ CRYPTO_MD5_HMAC,		NID_hmacWithMD5,	16},
    165 	{ CRYPTO_SHA1_HMAC,		NID_hmacWithSHA1,	20},
    166 	{ CRYPTO_RIPEMD160_HMAC,	NID_ripemd160,		16/*?*/},
    167 	{ CRYPTO_MD5_KPDK,		NID_undef,		0},
    168 	{ CRYPTO_SHA1_KPDK,		NID_undef,		0},
    169 	{ CRYPTO_MD5,			NID_md5,		16},
    170 	{ CRYPTO_SHA1,			NID_sha1,		20},
    171 	{ 0,				NID_undef,		0},
    172 };
    173 #endif
    174 
    175 /*
    176  * Return a fd if /dev/crypto seems usable, 0 otherwise.
    177  */
    178 static int
    179 open_dev_crypto(void)
    180 {
    181 	static int fd = -1;
    182 
    183 	if (fd == -1) {
    184 		if ((fd = open("/dev/crypto", O_RDWR, 0)) == -1)
    185 			return (-1);
    186 		/* close on exec */
    187 		if (fcntl(fd, F_SETFD, 1) == -1) {
    188 			close(fd);
    189 			fd = -1;
    190 			return (-1);
    191 		}
    192 	}
    193 	return (fd);
    194 }
    195 
    196 static int
    197 get_dev_crypto(void)
    198 {
    199 	int fd, retfd;
    200 
    201 	if ((fd = open_dev_crypto()) == -1)
    202 		return (-1);
    203 	if (ioctl(fd, CRIOGET, &retfd) == -1)
    204 		return (-1);
    205 
    206 	/* close on exec */
    207 	if (fcntl(retfd, F_SETFD, 1) == -1) {
    208 		close(retfd);
    209 		return (-1);
    210 	}
    211 	return (retfd);
    212 }
    213 
    214 /* Caching version for asym operations */
    215 static int
    216 get_asym_dev_crypto(void)
    217 {
    218 	static int fd = -1;
    219 
    220 	if (fd == -1)
    221 		fd = get_dev_crypto();
    222 	return fd;
    223 }
    224 
    225 /*
    226  * Find out what ciphers /dev/crypto will let us have a session for.
    227  * XXX note, that some of these openssl doesn't deal with yet!
    228  * returning them here is harmless, as long as we return NULL
    229  * when asked for a handler in the cryptodev_engine_ciphers routine
    230  */
    231 static int
    232 get_cryptodev_ciphers(const int **cnids)
    233 {
    234 	static int nids[CRYPTO_ALGORITHM_MAX];
    235 	struct session_op sess;
    236 	int fd, i, count = 0;
    237 
    238 	if ((fd = get_dev_crypto()) < 0) {
    239 		*cnids = NULL;
    240 		return (0);
    241 	}
    242 	memset(&sess, 0, sizeof(sess));
    243 	sess.key = (caddr_t)"123456789abcdefghijklmno";
    244 
    245 	for (i = 0; ciphers[i].id && count < CRYPTO_ALGORITHM_MAX; i++) {
    246 		if (ciphers[i].nid == NID_undef)
    247 			continue;
    248 		sess.cipher = ciphers[i].id;
    249 		sess.keylen = ciphers[i].keylen;
    250 		sess.mac = 0;
    251 		if (ioctl(fd, CIOCGSESSION, &sess) != -1 &&
    252 		    ioctl(fd, CIOCFSESSION, &sess.ses) != -1)
    253 			nids[count++] = ciphers[i].nid;
    254 	}
    255 	close(fd);
    256 
    257 	if (count > 0)
    258 		*cnids = nids;
    259 	else
    260 		*cnids = NULL;
    261 	return (count);
    262 }
    263 
    264 #ifdef USE_CRYPTODEV_DIGESTS
    265 /*
    266  * Find out what digests /dev/crypto will let us have a session for.
    267  * XXX note, that some of these openssl doesn't deal with yet!
    268  * returning them here is harmless, as long as we return NULL
    269  * when asked for a handler in the cryptodev_engine_digests routine
    270  */
    271 static int
    272 get_cryptodev_digests(const int **cnids)
    273 {
    274 	static int nids[CRYPTO_ALGORITHM_MAX];
    275 	struct session_op sess;
    276 	int fd, i, count = 0;
    277 
    278 	if ((fd = get_dev_crypto()) < 0) {
    279 		*cnids = NULL;
    280 		return (0);
    281 	}
    282 	memset(&sess, 0, sizeof(sess));
    283 	sess.mackey = (caddr_t)"123456789abcdefghijklmno";
    284 	for (i = 0; digests[i].id && count < CRYPTO_ALGORITHM_MAX; i++) {
    285 		if (digests[i].nid == NID_undef)
    286 			continue;
    287 		sess.mac = digests[i].id;
    288 		sess.mackeylen = digests[i].keylen;
    289 		sess.cipher = 0;
    290 		if (ioctl(fd, CIOCGSESSION, &sess) != -1 &&
    291 		    ioctl(fd, CIOCFSESSION, &sess.ses) != -1)
    292 			nids[count++] = digests[i].nid;
    293 	}
    294 	close(fd);
    295 
    296 	if (count > 0)
    297 		*cnids = nids;
    298 	else
    299 		*cnids = NULL;
    300 	return (count);
    301 }
    302 #endif  /* 0 */
    303 
    304 /*
    305  * Find the useable ciphers|digests from dev/crypto - this is the first
    306  * thing called by the engine init crud which determines what it
    307  * can use for ciphers from this engine. We want to return
    308  * only what we can do, anythine else is handled by software.
    309  *
    310  * If we can't initialize the device to do anything useful for
    311  * any reason, we want to return a NULL array, and 0 length,
    312  * which forces everything to be done is software. By putting
    313  * the initalization of the device in here, we ensure we can
    314  * use this engine as the default, and if for whatever reason
    315  * /dev/crypto won't do what we want it will just be done in
    316  * software
    317  *
    318  * This can (should) be greatly expanded to perhaps take into
    319  * account speed of the device, and what we want to do.
    320  * (although the disabling of particular alg's could be controlled
    321  * by the device driver with sysctl's.) - this is where we
    322  * want most of the decisions made about what we actually want
    323  * to use from /dev/crypto.
    324  */
    325 static int
    326 cryptodev_usable_ciphers(const int **nids)
    327 {
    328 	return (get_cryptodev_ciphers(nids));
    329 }
    330 
    331 static int
    332 cryptodev_usable_digests(const int **nids)
    333 {
    334 #ifdef USE_CRYPTODEV_DIGESTS
    335 	return (get_cryptodev_digests(nids));
    336 #else
    337 	/*
    338 	 * XXXX just disable all digests for now, because it sucks.
    339 	 * we need a better way to decide this - i.e. I may not
    340 	 * want digests on slow cards like hifn on fast machines,
    341 	 * but might want them on slow or loaded machines, etc.
    342 	 * will also want them when using crypto cards that don't
    343 	 * suck moose gonads - would be nice to be able to decide something
    344 	 * as reasonable default without having hackery that's card dependent.
    345 	 * of course, the default should probably be just do everything,
    346 	 * with perhaps a sysctl to turn algoritms off (or have them off
    347 	 * by default) on cards that generally suck like the hifn.
    348 	 */
    349 	*nids = NULL;
    350 	return (0);
    351 #endif
    352 }
    353 
    354 static int
    355 cryptodev_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
    356     const unsigned char *in, size_t inl)
    357 {
    358 	struct crypt_op cryp;
    359 	struct dev_crypto_state *state = ctx->cipher_data;
    360 	struct session_op *sess = &state->d_sess;
    361 	const void *iiv;
    362 	unsigned char save_iv[EVP_MAX_IV_LENGTH];
    363 
    364 	if (state->d_fd < 0)
    365 		return (0);
    366 	if (!inl)
    367 		return (1);
    368 	if ((inl % ctx->cipher->block_size) != 0)
    369 		return (0);
    370 
    371 	memset(&cryp, 0, sizeof(cryp));
    372 
    373 	cryp.ses = sess->ses;
    374 	cryp.flags = 0;
    375 	cryp.len = inl;
    376 	cryp.src = (caddr_t) in;
    377 	cryp.dst = (caddr_t) out;
    378 	cryp.mac = 0;
    379 
    380 	cryp.op = ctx->encrypt ? COP_ENCRYPT : COP_DECRYPT;
    381 
    382 	if (ctx->cipher->iv_len) {
    383 		cryp.iv = (caddr_t) ctx->iv;
    384 		if (!ctx->encrypt) {
    385 			iiv = in + inl - ctx->cipher->iv_len;
    386 			memcpy(save_iv, iiv, ctx->cipher->iv_len);
    387 		}
    388 	} else
    389 		cryp.iv = NULL;
    390 
    391 	if (ioctl(state->d_fd, CIOCCRYPT, &cryp) == -1) {
    392 		/* XXX need better errror handling
    393 		 * this can fail for a number of different reasons.
    394 		 */
    395 		return (0);
    396 	}
    397 
    398 	if (ctx->cipher->iv_len) {
    399 		if (ctx->encrypt)
    400 			iiv = out + inl - ctx->cipher->iv_len;
    401 		else
    402 			iiv = save_iv;
    403 		memcpy(ctx->iv, iiv, ctx->cipher->iv_len);
    404 	}
    405 	return (1);
    406 }
    407 
    408 static int
    409 cryptodev_init_key(EVP_CIPHER_CTX *ctx, const unsigned char *key,
    410     const unsigned char *iv, int enc)
    411 {
    412 	struct dev_crypto_state *state = ctx->cipher_data;
    413 	struct session_op *sess = &state->d_sess;
    414 	int cipher = -1, i;
    415 
    416 	for (i = 0; ciphers[i].id; i++)
    417 		if (ctx->cipher->nid == ciphers[i].nid &&
    418 		    ctx->cipher->iv_len <= ciphers[i].ivmax &&
    419 		    ctx->key_len == ciphers[i].keylen) {
    420 			cipher = ciphers[i].id;
    421 			break;
    422 		}
    423 
    424 	if (!ciphers[i].id) {
    425 		state->d_fd = -1;
    426 		return (0);
    427 	}
    428 
    429 	memset(sess, 0, sizeof(struct session_op));
    430 
    431 	if ((state->d_fd = get_dev_crypto()) < 0)
    432 		return (0);
    433 
    434 	sess->key = (caddr_t)key;
    435 	sess->keylen = ctx->key_len;
    436 	sess->cipher = cipher;
    437 
    438 	if (ioctl(state->d_fd, CIOCGSESSION, sess) == -1) {
    439 		close(state->d_fd);
    440 		state->d_fd = -1;
    441 		return (0);
    442 	}
    443 	return (1);
    444 }
    445 
    446 /*
    447  * free anything we allocated earlier when initting a
    448  * session, and close the session.
    449  */
    450 static int
    451 cryptodev_cleanup(EVP_CIPHER_CTX *ctx)
    452 {
    453 	int ret = 0;
    454 	struct dev_crypto_state *state = ctx->cipher_data;
    455 	struct session_op *sess = &state->d_sess;
    456 
    457 	if (state->d_fd < 0)
    458 		return (0);
    459 
    460 	/* XXX if this ioctl fails, someting's wrong. the invoker
    461 	 * may have called us with a bogus ctx, or we could
    462 	 * have a device that for whatever reason just doesn't
    463 	 * want to play ball - it's not clear what's right
    464 	 * here - should this be an error? should it just
    465 	 * increase a counter, hmm. For right now, we return
    466 	 * 0 - I don't believe that to be "right". we could
    467 	 * call the gorpy openssl lib error handlers that
    468 	 * print messages to users of the library. hmm..
    469 	 */
    470 
    471 	if (ioctl(state->d_fd, CIOCFSESSION, &sess->ses) == -1) {
    472 		ret = 0;
    473 	} else {
    474 		ret = 1;
    475 	}
    476 	close(state->d_fd);
    477 	state->d_fd = -1;
    478 
    479 	return (ret);
    480 }
    481 
    482 /*
    483  * libcrypto EVP stuff - this is how we get wired to EVP so the engine
    484  * gets called when libcrypto requests a cipher NID.
    485  */
    486 
    487 /* RC4 */
    488 const EVP_CIPHER cryptodev_rc4 = {
    489 	NID_rc4,
    490 	1, 16, 0,
    491 	EVP_CIPH_VARIABLE_LENGTH,
    492 	cryptodev_init_key,
    493 	cryptodev_cipher,
    494 	cryptodev_cleanup,
    495 	sizeof(struct dev_crypto_state),
    496 	NULL,
    497 	NULL,
    498 	NULL
    499 };
    500 
    501 /* DES CBC EVP */
    502 const EVP_CIPHER cryptodev_des_cbc = {
    503 	NID_des_cbc,
    504 	8, 8, 8,
    505 	EVP_CIPH_CBC_MODE,
    506 	cryptodev_init_key,
    507 	cryptodev_cipher,
    508 	cryptodev_cleanup,
    509 	sizeof(struct dev_crypto_state),
    510 	EVP_CIPHER_set_asn1_iv,
    511 	EVP_CIPHER_get_asn1_iv,
    512 	NULL
    513 };
    514 
    515 /* 3DES CBC EVP */
    516 const EVP_CIPHER cryptodev_3des_cbc = {
    517 	NID_des_ede3_cbc,
    518 	8, 24, 8,
    519 	EVP_CIPH_CBC_MODE,
    520 	cryptodev_init_key,
    521 	cryptodev_cipher,
    522 	cryptodev_cleanup,
    523 	sizeof(struct dev_crypto_state),
    524 	EVP_CIPHER_set_asn1_iv,
    525 	EVP_CIPHER_get_asn1_iv,
    526 	NULL
    527 };
    528 
    529 const EVP_CIPHER cryptodev_bf_cbc = {
    530 	NID_bf_cbc,
    531 	8, 16, 8,
    532 	EVP_CIPH_CBC_MODE,
    533 	cryptodev_init_key,
    534 	cryptodev_cipher,
    535 	cryptodev_cleanup,
    536 	sizeof(struct dev_crypto_state),
    537 	EVP_CIPHER_set_asn1_iv,
    538 	EVP_CIPHER_get_asn1_iv,
    539 	NULL
    540 };
    541 
    542 const EVP_CIPHER cryptodev_cast_cbc = {
    543 	NID_cast5_cbc,
    544 	8, 16, 8,
    545 	EVP_CIPH_CBC_MODE,
    546 	cryptodev_init_key,
    547 	cryptodev_cipher,
    548 	cryptodev_cleanup,
    549 	sizeof(struct dev_crypto_state),
    550 	EVP_CIPHER_set_asn1_iv,
    551 	EVP_CIPHER_get_asn1_iv,
    552 	NULL
    553 };
    554 
    555 const EVP_CIPHER cryptodev_aes_cbc = {
    556 	NID_aes_128_cbc,
    557 	16, 16, 16,
    558 	EVP_CIPH_CBC_MODE,
    559 	cryptodev_init_key,
    560 	cryptodev_cipher,
    561 	cryptodev_cleanup,
    562 	sizeof(struct dev_crypto_state),
    563 	EVP_CIPHER_set_asn1_iv,
    564 	EVP_CIPHER_get_asn1_iv,
    565 	NULL
    566 };
    567 
    568 const EVP_CIPHER cryptodev_aes_192_cbc = {
    569 	NID_aes_192_cbc,
    570 	16, 24, 16,
    571 	EVP_CIPH_CBC_MODE,
    572 	cryptodev_init_key,
    573 	cryptodev_cipher,
    574 	cryptodev_cleanup,
    575 	sizeof(struct dev_crypto_state),
    576 	EVP_CIPHER_set_asn1_iv,
    577 	EVP_CIPHER_get_asn1_iv,
    578 	NULL
    579 };
    580 
    581 const EVP_CIPHER cryptodev_aes_256_cbc = {
    582 	NID_aes_256_cbc,
    583 	16, 32, 16,
    584 	EVP_CIPH_CBC_MODE,
    585 	cryptodev_init_key,
    586 	cryptodev_cipher,
    587 	cryptodev_cleanup,
    588 	sizeof(struct dev_crypto_state),
    589 	EVP_CIPHER_set_asn1_iv,
    590 	EVP_CIPHER_get_asn1_iv,
    591 	NULL
    592 };
    593 
    594 /*
    595  * Registered by the ENGINE when used to find out how to deal with
    596  * a particular NID in the ENGINE. this says what we'll do at the
    597  * top level - note, that list is restricted by what we answer with
    598  */
    599 static int
    600 cryptodev_engine_ciphers(ENGINE *e, const EVP_CIPHER **cipher,
    601     const int **nids, int nid)
    602 {
    603 	if (!cipher)
    604 		return (cryptodev_usable_ciphers(nids));
    605 
    606 	switch (nid) {
    607 	case NID_rc4:
    608 		*cipher = &cryptodev_rc4;
    609 		break;
    610 	case NID_des_ede3_cbc:
    611 		*cipher = &cryptodev_3des_cbc;
    612 		break;
    613 	case NID_des_cbc:
    614 		*cipher = &cryptodev_des_cbc;
    615 		break;
    616 	case NID_bf_cbc:
    617 		*cipher = &cryptodev_bf_cbc;
    618 		break;
    619 	case NID_cast5_cbc:
    620 		*cipher = &cryptodev_cast_cbc;
    621 		break;
    622 	case NID_aes_128_cbc:
    623 		*cipher = &cryptodev_aes_cbc;
    624 		break;
    625 	case NID_aes_192_cbc:
    626 		*cipher = &cryptodev_aes_192_cbc;
    627 		break;
    628 	case NID_aes_256_cbc:
    629 		*cipher = &cryptodev_aes_256_cbc;
    630 		break;
    631 	default:
    632 		*cipher = NULL;
    633 		break;
    634 	}
    635 	return (*cipher != NULL);
    636 }
    637 
    638 
    639 #ifdef USE_CRYPTODEV_DIGESTS
    640 
    641 /* convert digest type to cryptodev */
    642 static int
    643 digest_nid_to_cryptodev(int nid)
    644 {
    645 	int i;
    646 
    647 	for (i = 0; digests[i].id; i++)
    648 		if (digests[i].nid == nid)
    649 			return (digests[i].id);
    650 	return (0);
    651 }
    652 
    653 
    654 static int
    655 digest_key_length(int nid)
    656 {
    657 	int i;
    658 
    659 	for (i = 0; digests[i].id; i++)
    660 		if (digests[i].nid == nid)
    661 			return digests[i].keylen;
    662 	return (0);
    663 }
    664 
    665 
    666 static int cryptodev_digest_init(EVP_MD_CTX *ctx)
    667 {
    668 	struct dev_crypto_state *state = ctx->md_data;
    669 	struct session_op *sess = &state->d_sess;
    670 	int digest;
    671 
    672 	if ((digest = digest_nid_to_cryptodev(ctx->digest->type)) == NID_undef){
    673 		printf("cryptodev_digest_init: Can't get digest \n");
    674 		return (0);
    675 	}
    676 
    677 	memset(state, 0, sizeof(struct dev_crypto_state));
    678 
    679 	if ((state->d_fd = get_dev_crypto()) < 0) {
    680 		printf("cryptodev_digest_init: Can't get Dev \n");
    681 		return (0);
    682 	}
    683 
    684 	sess->mackey = state->dummy_mac_key;
    685 	sess->mackeylen = digest_key_length(ctx->digest->type);
    686 	sess->mac = digest;
    687 
    688 	if (ioctl(state->d_fd, CIOCGSESSION, sess) < 0) {
    689 		close(state->d_fd);
    690 		state->d_fd = -1;
    691 		printf("cryptodev_digest_init: Open session failed\n");
    692 		return (0);
    693 	}
    694 
    695 	return (1);
    696 }
    697 
    698 static int cryptodev_digest_update(EVP_MD_CTX *ctx, const void *data,
    699 		size_t count)
    700 {
    701 	struct crypt_op cryp;
    702 	struct dev_crypto_state *state = ctx->md_data;
    703 	struct session_op *sess = &state->d_sess;
    704 
    705 	if (!data || state->d_fd < 0) {
    706 		printf("cryptodev_digest_update: illegal inputs \n");
    707 		return (0);
    708 	}
    709 
    710 	if (!count) {
    711 		return (0);
    712 	}
    713 
    714 	if (!(ctx->flags & EVP_MD_CTX_FLAG_ONESHOT)) {
    715 		/* if application doesn't support one buffer */
    716 		state->mac_data = OPENSSL_realloc(state->mac_data, state->mac_len + count);
    717 
    718 		if (!state->mac_data) {
    719 			printf("cryptodev_digest_update: realloc failed\n");
    720 			return (0);
    721 		}
    722 
    723 		memcpy(state->mac_data + state->mac_len, data, count);
    724    		state->mac_len += count;
    725 
    726 		return (1);
    727 	}
    728 
    729 	memset(&cryp, 0, sizeof(cryp));
    730 
    731 	cryp.ses = sess->ses;
    732 	cryp.flags = 0;
    733 	cryp.len = count;
    734 	cryp.src = (caddr_t) data;
    735 	cryp.dst = NULL;
    736 	cryp.mac = (caddr_t) state->digest_res;
    737 	if (ioctl(state->d_fd, CIOCCRYPT, &cryp) < 0) {
    738 		printf("cryptodev_digest_update: digest failed\n");
    739 		return (0);
    740 	}
    741 	return (1);
    742 }
    743 
    744 
    745 static int cryptodev_digest_final(EVP_MD_CTX *ctx, unsigned char *md)
    746 {
    747 	struct crypt_op cryp;
    748 	struct dev_crypto_state *state = ctx->md_data;
    749 	struct session_op *sess = &state->d_sess;
    750 
    751 	int ret = 1;
    752 
    753 	if (!md || state->d_fd < 0) {
    754 		printf("cryptodev_digest_final: illegal input\n");
    755 		return(0);
    756 	}
    757 
    758 	if (! (ctx->flags & EVP_MD_CTX_FLAG_ONESHOT) ) {
    759 		/* if application doesn't support one buffer */
    760 		memset(&cryp, 0, sizeof(cryp));
    761 
    762 		cryp.ses = sess->ses;
    763 		cryp.flags = 0;
    764 		cryp.len = state->mac_len;
    765 		cryp.src = state->mac_data;
    766 		cryp.dst = NULL;
    767 		cryp.mac = (caddr_t)md;
    768 
    769 		if (ioctl(state->d_fd, CIOCCRYPT, &cryp) < 0) {
    770 			printf("cryptodev_digest_final: digest failed\n");
    771 			return (0);
    772 		}
    773 
    774 		return 1;
    775 	}
    776 
    777 	memcpy(md, state->digest_res, ctx->digest->md_size);
    778 
    779 	return (ret);
    780 }
    781 
    782 
    783 static int cryptodev_digest_cleanup(EVP_MD_CTX *ctx)
    784 {
    785 	int ret = 1;
    786 	struct dev_crypto_state *state = ctx->md_data;
    787 	struct session_op *sess = &state->d_sess;
    788 
    789 	if (state->d_fd < 0) {
    790 		printf("cryptodev_digest_cleanup: illegal input\n");
    791 		return (0);
    792 	}
    793 
    794 	if (state->mac_data) {
    795 		OPENSSL_free(state->mac_data);
    796 		state->mac_data = NULL;
    797 		state->mac_len = 0;
    798 	}
    799 
    800 	if (state->copy)
    801 		return 1;
    802 
    803 	if (ioctl(state->d_fd, CIOCFSESSION, &sess->ses) < 0) {
    804 		printf("cryptodev_digest_cleanup: failed to close session\n");
    805 		ret = 0;
    806 	} else {
    807 		ret = 1;
    808 	}
    809 	close(state->d_fd);
    810 	state->d_fd = -1;
    811 
    812 	return (ret);
    813 }
    814 
    815 static int cryptodev_digest_copy(EVP_MD_CTX *to,const EVP_MD_CTX *from)
    816 {
    817 	struct dev_crypto_state *fstate = from->md_data;
    818 	struct dev_crypto_state *dstate = to->md_data;
    819 
    820 	memcpy(dstate, fstate, sizeof(struct dev_crypto_state));
    821 
    822 	if (fstate->mac_len != 0) {
    823 		dstate->mac_data = OPENSSL_malloc(fstate->mac_len);
    824 		memcpy(dstate->mac_data, fstate->mac_data, fstate->mac_len);
    825 	}
    826 
    827 	dstate->copy = 1;
    828 
    829 	return 1;
    830 }
    831 
    832 
    833 const EVP_MD cryptodev_sha1 = {
    834 	NID_sha1,
    835 	NID_undef,
    836 	SHA_DIGEST_LENGTH,
    837 	EVP_MD_FLAG_ONESHOT,
    838 	cryptodev_digest_init,
    839 	cryptodev_digest_update,
    840 	cryptodev_digest_final,
    841 	cryptodev_digest_copy,
    842 	cryptodev_digest_cleanup,
    843 	EVP_PKEY_NULL_method,
    844 	SHA_CBLOCK,
    845 	sizeof(struct dev_crypto_state),
    846 };
    847 
    848 const EVP_MD cryptodev_md5 = {
    849 	NID_md5,
    850 	NID_undef,
    851 	16 /* MD5_DIGEST_LENGTH */,
    852 	EVP_MD_FLAG_ONESHOT,
    853 	cryptodev_digest_init,
    854 	cryptodev_digest_update,
    855 	cryptodev_digest_final,
    856 	cryptodev_digest_copy,
    857 	cryptodev_digest_cleanup,
    858 	EVP_PKEY_NULL_method,
    859 	64 /* MD5_CBLOCK */,
    860 	sizeof(struct dev_crypto_state),
    861 };
    862 
    863 #endif /* USE_CRYPTODEV_DIGESTS */
    864 
    865 
    866 static int
    867 cryptodev_engine_digests(ENGINE *e, const EVP_MD **digest,
    868     const int **nids, int nid)
    869 {
    870 	if (!digest)
    871 		return (cryptodev_usable_digests(nids));
    872 
    873 	switch (nid) {
    874 #ifdef USE_CRYPTODEV_DIGESTS
    875 	case NID_md5:
    876 		*digest = &cryptodev_md5;
    877 		break;
    878 	case NID_sha1:
    879 		*digest = &cryptodev_sha1;
    880  		break;
    881 	default:
    882 #endif /* USE_CRYPTODEV_DIGESTS */
    883 		*digest = NULL;
    884 		break;
    885 	}
    886 	return (*digest != NULL);
    887 }
    888 
    889 /*
    890  * Convert a BIGNUM to the representation that /dev/crypto needs.
    891  * Upon completion of use, the caller is responsible for freeing
    892  * crp->crp_p.
    893  */
    894 static int
    895 bn2crparam(const BIGNUM *a, struct crparam *crp)
    896 {
    897 	int i, j, k;
    898 	ssize_t bytes, bits;
    899 	u_char *b;
    900 
    901 	crp->crp_p = NULL;
    902 	crp->crp_nbits = 0;
    903 
    904 	bits = BN_num_bits(a);
    905 	bytes = (bits + 7) / 8;
    906 
    907 	b = malloc(bytes);
    908 	if (b == NULL)
    909 		return (1);
    910 	memset(b, 0, bytes);
    911 
    912 	crp->crp_p = (caddr_t) b;
    913 	crp->crp_nbits = bits;
    914 
    915 	for (i = 0, j = 0; i < a->top; i++) {
    916 		for (k = 0; k < BN_BITS2 / 8; k++) {
    917 			if ((j + k) >= bytes)
    918 				return (0);
    919 			b[j + k] = a->d[i] >> (k * 8);
    920 		}
    921 		j += BN_BITS2 / 8;
    922 	}
    923 	return (0);
    924 }
    925 
    926 /* Convert a /dev/crypto parameter to a BIGNUM */
    927 static int
    928 crparam2bn(struct crparam *crp, BIGNUM *a)
    929 {
    930 	u_int8_t *pd;
    931 	int i, bytes;
    932 
    933 	bytes = (crp->crp_nbits + 7) / 8;
    934 
    935 	if (bytes == 0)
    936 		return (-1);
    937 
    938 	if ((pd = (u_int8_t *) malloc(bytes)) == NULL)
    939 		return (-1);
    940 
    941 	for (i = 0; i < bytes; i++)
    942 		pd[i] = crp->crp_p[bytes - i - 1];
    943 
    944 	BN_bin2bn(pd, bytes, a);
    945 	free(pd);
    946 
    947 	return (0);
    948 }
    949 
    950 static void
    951 zapparams(struct crypt_kop *kop)
    952 {
    953 	int i;
    954 
    955 	for (i = 0; i < kop->crk_iparams + kop->crk_oparams; i++) {
    956 		if (kop->crk_param[i].crp_p)
    957 			free(kop->crk_param[i].crp_p);
    958 		kop->crk_param[i].crp_p = NULL;
    959 		kop->crk_param[i].crp_nbits = 0;
    960 	}
    961 }
    962 
    963 static int
    964 cryptodev_asym(struct crypt_kop *kop, int rlen, BIGNUM *r, int slen, BIGNUM *s)
    965 {
    966 	int fd, ret = -1;
    967 
    968 	if ((fd = get_asym_dev_crypto()) < 0)
    969 		return (ret);
    970 
    971 	if (r) {
    972 		kop->crk_param[kop->crk_iparams].crp_p = calloc(rlen, sizeof(char));
    973 		kop->crk_param[kop->crk_iparams].crp_nbits = rlen * 8;
    974 		kop->crk_oparams++;
    975 	}
    976 	if (s) {
    977 		kop->crk_param[kop->crk_iparams+1].crp_p = calloc(slen, sizeof(char));
    978 		kop->crk_param[kop->crk_iparams+1].crp_nbits = slen * 8;
    979 		kop->crk_oparams++;
    980 	}
    981 
    982 	if (ioctl(fd, CIOCKEY, kop) == 0) {
    983 		if (r)
    984 			crparam2bn(&kop->crk_param[kop->crk_iparams], r);
    985 		if (s)
    986 			crparam2bn(&kop->crk_param[kop->crk_iparams+1], s);
    987 		ret = 0;
    988 	}
    989 
    990 	return (ret);
    991 }
    992 
    993 static int
    994 cryptodev_bn_mod_exp(BIGNUM *r, const BIGNUM *a, const BIGNUM *p,
    995     const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *in_mont)
    996 {
    997 	struct crypt_kop kop;
    998 	int ret = 1;
    999 
   1000 	/* Currently, we know we can do mod exp iff we can do any
   1001 	 * asymmetric operations at all.
   1002 	 */
   1003 	if (cryptodev_asymfeat == 0) {
   1004 		ret = BN_mod_exp(r, a, p, m, ctx);
   1005 		return (ret);
   1006 	}
   1007 
   1008 	memset(&kop, 0, sizeof kop);
   1009 	kop.crk_op = CRK_MOD_EXP;
   1010 
   1011 	/* inputs: a^p % m */
   1012 	if (bn2crparam(a, &kop.crk_param[0]))
   1013 		goto err;
   1014 	if (bn2crparam(p, &kop.crk_param[1]))
   1015 		goto err;
   1016 	if (bn2crparam(m, &kop.crk_param[2]))
   1017 		goto err;
   1018 	kop.crk_iparams = 3;
   1019 
   1020 	if (cryptodev_asym(&kop, BN_num_bytes(m), r, 0, NULL)) {
   1021 		const RSA_METHOD *meth = RSA_PKCS1_SSLeay();
   1022 		printf("OCF asym process failed, Running in software\n");
   1023 		ret = meth->bn_mod_exp(r, a, p, m, ctx, in_mont);
   1024 
   1025 	} else if (ECANCELED == kop.crk_status) {
   1026 		const RSA_METHOD *meth = RSA_PKCS1_SSLeay();
   1027 		printf("OCF hardware operation cancelled. Running in Software\n");
   1028 		ret = meth->bn_mod_exp(r, a, p, m, ctx, in_mont);
   1029 	}
   1030 	/* else cryptodev operation worked ok ==> ret = 1*/
   1031 
   1032 err:
   1033 	zapparams(&kop);
   1034 	return (ret);
   1035 }
   1036 
   1037 static int
   1038 cryptodev_rsa_nocrt_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa, BN_CTX *ctx)
   1039 {
   1040 	int r;
   1041 	ctx = BN_CTX_new();
   1042 	r = cryptodev_bn_mod_exp(r0, I, rsa->d, rsa->n, ctx, NULL);
   1043 	BN_CTX_free(ctx);
   1044 	return (r);
   1045 }
   1046 
   1047 static int
   1048 cryptodev_rsa_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa, BN_CTX *ctx)
   1049 {
   1050 	struct crypt_kop kop;
   1051 	int ret = 1;
   1052 
   1053 	if (!rsa->p || !rsa->q || !rsa->dmp1 || !rsa->dmq1 || !rsa->iqmp) {
   1054 		/* XXX 0 means failure?? */
   1055 		return (0);
   1056 	}
   1057 
   1058 	memset(&kop, 0, sizeof kop);
   1059 	kop.crk_op = CRK_MOD_EXP_CRT;
   1060 	/* inputs: rsa->p rsa->q I rsa->dmp1 rsa->dmq1 rsa->iqmp */
   1061 	if (bn2crparam(rsa->p, &kop.crk_param[0]))
   1062 		goto err;
   1063 	if (bn2crparam(rsa->q, &kop.crk_param[1]))
   1064 		goto err;
   1065 	if (bn2crparam(I, &kop.crk_param[2]))
   1066 		goto err;
   1067 	if (bn2crparam(rsa->dmp1, &kop.crk_param[3]))
   1068 		goto err;
   1069 	if (bn2crparam(rsa->dmq1, &kop.crk_param[4]))
   1070 		goto err;
   1071 	if (bn2crparam(rsa->iqmp, &kop.crk_param[5]))
   1072 		goto err;
   1073 	kop.crk_iparams = 6;
   1074 
   1075 	if (cryptodev_asym(&kop, BN_num_bytes(rsa->n), r0, 0, NULL)) {
   1076 		const RSA_METHOD *meth = RSA_PKCS1_SSLeay();
   1077 		printf("OCF asym process failed, running in Software\n");
   1078 		ret = (*meth->rsa_mod_exp)(r0, I, rsa, ctx);
   1079 
   1080 	} else if (ECANCELED == kop.crk_status) {
   1081 		const RSA_METHOD *meth = RSA_PKCS1_SSLeay();
   1082 		printf("OCF hardware operation cancelled. Running in Software\n");
   1083 		ret = (*meth->rsa_mod_exp)(r0, I, rsa, ctx);
   1084 	}
   1085 	/* else cryptodev operation worked ok ==> ret = 1*/
   1086 
   1087 err:
   1088 	zapparams(&kop);
   1089 	return (ret);
   1090 }
   1091 
   1092 static RSA_METHOD cryptodev_rsa = {
   1093 	"cryptodev RSA method",
   1094 	NULL,				/* rsa_pub_enc */
   1095 	NULL,				/* rsa_pub_dec */
   1096 	NULL,				/* rsa_priv_enc */
   1097 	NULL,				/* rsa_priv_dec */
   1098 	NULL,
   1099 	NULL,
   1100 	NULL,				/* init */
   1101 	NULL,				/* finish */
   1102 	0,				/* flags */
   1103 	NULL,				/* app_data */
   1104 	NULL,				/* rsa_sign */
   1105 	NULL				/* rsa_verify */
   1106 };
   1107 
   1108 static int
   1109 cryptodev_dsa_bn_mod_exp(DSA *dsa, BIGNUM *r, BIGNUM *a, const BIGNUM *p,
   1110     const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *m_ctx)
   1111 {
   1112 	return (cryptodev_bn_mod_exp(r, a, p, m, ctx, m_ctx));
   1113 }
   1114 
   1115 static int
   1116 cryptodev_dsa_dsa_mod_exp(DSA *dsa, BIGNUM *t1, BIGNUM *g,
   1117     BIGNUM *u1, BIGNUM *pub_key, BIGNUM *u2, BIGNUM *p,
   1118     BN_CTX *ctx, BN_MONT_CTX *mont)
   1119 {
   1120 	BIGNUM t2;
   1121 	int ret = 0;
   1122 
   1123 	BN_init(&t2);
   1124 
   1125 	/* v = ( g^u1 * y^u2 mod p ) mod q */
   1126 	/* let t1 = g ^ u1 mod p */
   1127 	ret = 0;
   1128 
   1129 	if (!dsa->meth->bn_mod_exp(dsa,t1,dsa->g,u1,dsa->p,ctx,mont))
   1130 		goto err;
   1131 
   1132 	/* let t2 = y ^ u2 mod p */
   1133 	if (!dsa->meth->bn_mod_exp(dsa,&t2,dsa->pub_key,u2,dsa->p,ctx,mont))
   1134 		goto err;
   1135 	/* let u1 = t1 * t2 mod p */
   1136 	if (!BN_mod_mul(u1,t1,&t2,dsa->p,ctx))
   1137 		goto err;
   1138 
   1139 	BN_copy(t1,u1);
   1140 
   1141 	ret = 1;
   1142 err:
   1143 	BN_free(&t2);
   1144 	return(ret);
   1145 }
   1146 
   1147 static DSA_SIG *
   1148 cryptodev_dsa_do_sign(const unsigned char *dgst, int dlen, DSA *dsa)
   1149 {
   1150 	struct crypt_kop kop;
   1151 	BIGNUM *r = NULL, *s = NULL;
   1152 	DSA_SIG *dsaret = NULL;
   1153 
   1154 	if ((r = BN_new()) == NULL)
   1155 		goto err;
   1156 	if ((s = BN_new()) == NULL) {
   1157 		BN_free(r);
   1158 		goto err;
   1159 	}
   1160 
   1161 	memset(&kop, 0, sizeof kop);
   1162 	kop.crk_op = CRK_DSA_SIGN;
   1163 
   1164 	/* inputs: dgst dsa->p dsa->q dsa->g dsa->priv_key */
   1165 	kop.crk_param[0].crp_p = (caddr_t)dgst;
   1166 	kop.crk_param[0].crp_nbits = dlen * 8;
   1167 	if (bn2crparam(dsa->p, &kop.crk_param[1]))
   1168 		goto err;
   1169 	if (bn2crparam(dsa->q, &kop.crk_param[2]))
   1170 		goto err;
   1171 	if (bn2crparam(dsa->g, &kop.crk_param[3]))
   1172 		goto err;
   1173 	if (bn2crparam(dsa->priv_key, &kop.crk_param[4]))
   1174 		goto err;
   1175 	kop.crk_iparams = 5;
   1176 
   1177 	if (cryptodev_asym(&kop, BN_num_bytes(dsa->q), r,
   1178 	    BN_num_bytes(dsa->q), s) == 0) {
   1179 		dsaret = DSA_SIG_new();
   1180 		dsaret->r = r;
   1181 		dsaret->s = s;
   1182 	} else {
   1183 		const DSA_METHOD *meth = DSA_OpenSSL();
   1184 		BN_free(r);
   1185 		BN_free(s);
   1186 		dsaret = (meth->dsa_do_sign)(dgst, dlen, dsa);
   1187 	}
   1188 err:
   1189 	kop.crk_param[0].crp_p = NULL;
   1190 	zapparams(&kop);
   1191 	return (dsaret);
   1192 }
   1193 
   1194 static int
   1195 cryptodev_dsa_verify(const unsigned char *dgst, int dlen,
   1196     DSA_SIG *sig, DSA *dsa)
   1197 {
   1198 	struct crypt_kop kop;
   1199 	int dsaret = 1;
   1200 
   1201 	memset(&kop, 0, sizeof kop);
   1202 	kop.crk_op = CRK_DSA_VERIFY;
   1203 
   1204 	/* inputs: dgst dsa->p dsa->q dsa->g dsa->pub_key sig->r sig->s */
   1205 	kop.crk_param[0].crp_p = (caddr_t)dgst;
   1206 	kop.crk_param[0].crp_nbits = dlen * 8;
   1207 	if (bn2crparam(dsa->p, &kop.crk_param[1]))
   1208 		goto err;
   1209 	if (bn2crparam(dsa->q, &kop.crk_param[2]))
   1210 		goto err;
   1211 	if (bn2crparam(dsa->g, &kop.crk_param[3]))
   1212 		goto err;
   1213 	if (bn2crparam(dsa->pub_key, &kop.crk_param[4]))
   1214 		goto err;
   1215 	if (bn2crparam(sig->r, &kop.crk_param[5]))
   1216 		goto err;
   1217 	if (bn2crparam(sig->s, &kop.crk_param[6]))
   1218 		goto err;
   1219 	kop.crk_iparams = 7;
   1220 
   1221 	if (cryptodev_asym(&kop, 0, NULL, 0, NULL) == 0) {
   1222 /*OCF success value is 0, if not zero, change dsaret to fail*/
   1223 		if(0 != kop.crk_status) dsaret  = 0;
   1224 	} else {
   1225 		const DSA_METHOD *meth = DSA_OpenSSL();
   1226 
   1227 		dsaret = (meth->dsa_do_verify)(dgst, dlen, sig, dsa);
   1228 	}
   1229 err:
   1230 	kop.crk_param[0].crp_p = NULL;
   1231 	zapparams(&kop);
   1232 	return (dsaret);
   1233 }
   1234 
   1235 static DSA_METHOD cryptodev_dsa = {
   1236 	"cryptodev DSA method",
   1237 	NULL,
   1238 	NULL,				/* dsa_sign_setup */
   1239 	NULL,
   1240 	NULL,				/* dsa_mod_exp */
   1241 	NULL,
   1242 	NULL,				/* init */
   1243 	NULL,				/* finish */
   1244 	0,	/* flags */
   1245 	NULL	/* app_data */
   1246 };
   1247 
   1248 static int
   1249 cryptodev_mod_exp_dh(const DH *dh, BIGNUM *r, const BIGNUM *a,
   1250     const BIGNUM *p, const BIGNUM *m, BN_CTX *ctx,
   1251     BN_MONT_CTX *m_ctx)
   1252 {
   1253 	return (cryptodev_bn_mod_exp(r, a, p, m, ctx, m_ctx));
   1254 }
   1255 
   1256 static int
   1257 cryptodev_dh_compute_key(unsigned char *key, const BIGNUM *pub_key, DH *dh)
   1258 {
   1259 	struct crypt_kop kop;
   1260 	int dhret = 1;
   1261 	int fd, keylen;
   1262 
   1263 	if ((fd = get_asym_dev_crypto()) < 0) {
   1264 		const DH_METHOD *meth = DH_OpenSSL();
   1265 
   1266 		return ((meth->compute_key)(key, pub_key, dh));
   1267 	}
   1268 
   1269 	keylen = BN_num_bits(dh->p);
   1270 
   1271 	memset(&kop, 0, sizeof kop);
   1272 	kop.crk_op = CRK_DH_COMPUTE_KEY;
   1273 
   1274 	/* inputs: dh->priv_key pub_key dh->p key */
   1275 	if (bn2crparam(dh->priv_key, &kop.crk_param[0]))
   1276 		goto err;
   1277 	if (bn2crparam(pub_key, &kop.crk_param[1]))
   1278 		goto err;
   1279 	if (bn2crparam(dh->p, &kop.crk_param[2]))
   1280 		goto err;
   1281 	kop.crk_iparams = 3;
   1282 
   1283 	kop.crk_param[3].crp_p = (caddr_t) key;
   1284 	kop.crk_param[3].crp_nbits = keylen * 8;
   1285 	kop.crk_oparams = 1;
   1286 
   1287 	if (ioctl(fd, CIOCKEY, &kop) == -1) {
   1288 		const DH_METHOD *meth = DH_OpenSSL();
   1289 
   1290 		dhret = (meth->compute_key)(key, pub_key, dh);
   1291 	}
   1292 err:
   1293 	kop.crk_param[3].crp_p = NULL;
   1294 	zapparams(&kop);
   1295 	return (dhret);
   1296 }
   1297 
   1298 static DH_METHOD cryptodev_dh = {
   1299 	"cryptodev DH method",
   1300 	NULL,				/* cryptodev_dh_generate_key */
   1301 	NULL,
   1302 	NULL,
   1303 	NULL,
   1304 	NULL,
   1305 	0,	/* flags */
   1306 	NULL	/* app_data */
   1307 };
   1308 
   1309 /*
   1310  * ctrl right now is just a wrapper that doesn't do much
   1311  * but I expect we'll want some options soon.
   1312  */
   1313 static int
   1314 cryptodev_ctrl(ENGINE *e, int cmd, long i, void *p, void (*f)(void))
   1315 {
   1316 #ifdef HAVE_SYSLOG_R
   1317 	struct syslog_data sd = SYSLOG_DATA_INIT;
   1318 #endif
   1319 
   1320 	switch (cmd) {
   1321 	default:
   1322 #ifdef HAVE_SYSLOG_R
   1323 		syslog_r(LOG_ERR, &sd,
   1324 		    "cryptodev_ctrl: unknown command %d", cmd);
   1325 #else
   1326 		syslog(LOG_ERR, "cryptodev_ctrl: unknown command %d", cmd);
   1327 #endif
   1328 		break;
   1329 	}
   1330 	return (1);
   1331 }
   1332 
   1333 void
   1334 ENGINE_load_cryptodev(void)
   1335 {
   1336 	ENGINE *engine = ENGINE_new();
   1337 	int fd;
   1338 
   1339 	if (engine == NULL)
   1340 		return;
   1341 	if ((fd = get_dev_crypto()) < 0) {
   1342 		ENGINE_free(engine);
   1343 		return;
   1344 	}
   1345 
   1346 	/*
   1347 	 * find out what asymmetric crypto algorithms we support
   1348 	 */
   1349 	if (ioctl(fd, CIOCASYMFEAT, &cryptodev_asymfeat) == -1) {
   1350 		close(fd);
   1351 		ENGINE_free(engine);
   1352 		return;
   1353 	}
   1354 	close(fd);
   1355 
   1356 	if (!ENGINE_set_id(engine, "cryptodev") ||
   1357 	    !ENGINE_set_name(engine, "BSD cryptodev engine") ||
   1358 	    !ENGINE_set_ciphers(engine, cryptodev_engine_ciphers) ||
   1359 	    !ENGINE_set_digests(engine, cryptodev_engine_digests) ||
   1360 	    !ENGINE_set_ctrl_function(engine, cryptodev_ctrl) ||
   1361 	    !ENGINE_set_cmd_defns(engine, cryptodev_defns)) {
   1362 		ENGINE_free(engine);
   1363 		return;
   1364 	}
   1365 
   1366 	if (ENGINE_set_RSA(engine, &cryptodev_rsa)) {
   1367 		const RSA_METHOD *rsa_meth = RSA_PKCS1_SSLeay();
   1368 
   1369 		cryptodev_rsa.bn_mod_exp = rsa_meth->bn_mod_exp;
   1370 		cryptodev_rsa.rsa_mod_exp = rsa_meth->rsa_mod_exp;
   1371 		cryptodev_rsa.rsa_pub_enc = rsa_meth->rsa_pub_enc;
   1372 		cryptodev_rsa.rsa_pub_dec = rsa_meth->rsa_pub_dec;
   1373 		cryptodev_rsa.rsa_priv_enc = rsa_meth->rsa_priv_enc;
   1374 		cryptodev_rsa.rsa_priv_dec = rsa_meth->rsa_priv_dec;
   1375 		if (cryptodev_asymfeat & CRF_MOD_EXP) {
   1376 			cryptodev_rsa.bn_mod_exp = cryptodev_bn_mod_exp;
   1377 			if (cryptodev_asymfeat & CRF_MOD_EXP_CRT)
   1378 				cryptodev_rsa.rsa_mod_exp =
   1379 				    cryptodev_rsa_mod_exp;
   1380 			else
   1381 				cryptodev_rsa.rsa_mod_exp =
   1382 				    cryptodev_rsa_nocrt_mod_exp;
   1383 		}
   1384 	}
   1385 
   1386 	if (ENGINE_set_DSA(engine, &cryptodev_dsa)) {
   1387 		const DSA_METHOD *meth = DSA_OpenSSL();
   1388 
   1389 		memcpy(&cryptodev_dsa, meth, sizeof(DSA_METHOD));
   1390 		if (cryptodev_asymfeat & CRF_DSA_SIGN)
   1391 			cryptodev_dsa.dsa_do_sign = cryptodev_dsa_do_sign;
   1392 		if (cryptodev_asymfeat & CRF_MOD_EXP) {
   1393 			cryptodev_dsa.bn_mod_exp = cryptodev_dsa_bn_mod_exp;
   1394 			cryptodev_dsa.dsa_mod_exp = cryptodev_dsa_dsa_mod_exp;
   1395 		}
   1396 		if (cryptodev_asymfeat & CRF_DSA_VERIFY)
   1397 			cryptodev_dsa.dsa_do_verify = cryptodev_dsa_verify;
   1398 	}
   1399 
   1400 	if (ENGINE_set_DH(engine, &cryptodev_dh)){
   1401 		const DH_METHOD *dh_meth = DH_OpenSSL();
   1402 
   1403 		cryptodev_dh.generate_key = dh_meth->generate_key;
   1404 		cryptodev_dh.compute_key = dh_meth->compute_key;
   1405 		cryptodev_dh.bn_mod_exp = dh_meth->bn_mod_exp;
   1406 		if (cryptodev_asymfeat & CRF_MOD_EXP) {
   1407 			cryptodev_dh.bn_mod_exp = cryptodev_mod_exp_dh;
   1408 			if (cryptodev_asymfeat & CRF_DH_COMPUTE_KEY)
   1409 				cryptodev_dh.compute_key =
   1410 				    cryptodev_dh_compute_key;
   1411 		}
   1412 	}
   1413 
   1414 	ENGINE_add(engine);
   1415 	ENGINE_free(engine);
   1416 	ERR_clear_error();
   1417 }
   1418 
   1419 #endif /* HAVE_CRYPTODEV */
   1420