static void des3_set_key(struct krb5_key_state *ks, const void *in) { void *kp = ks->ks_key; struct des3_state *ds = ks->ks_priv; struct cryptoini cri[2]; if (kp != in) bcopy(in, kp, ks->ks_class->ec_keylen); if (ds->ds_session) crypto_freesession(ds->ds_session); bzero(cri, sizeof(cri)); cri[0].cri_alg = CRYPTO_SHA1_HMAC; cri[0].cri_klen = 192; cri[0].cri_mlen = 0; cri[0].cri_key = ks->ks_key; cri[0].cri_next = &cri[1]; cri[1].cri_alg = CRYPTO_3DES_CBC; cri[1].cri_klen = 192; cri[1].cri_mlen = 0; cri[1].cri_key = ks->ks_key; cri[1].cri_next = NULL; crypto_newsession(&ds->ds_session, cri, CRYPTOCAP_F_HARDWARE | CRYPTOCAP_F_SOFTWARE); }
static void aes_set_key(struct krb5_key_state *ks, const void *in) { void *kp = ks->ks_key; struct aes_state *as = ks->ks_priv; struct cryptoini cri[2]; if (kp != in) bcopy(in, kp, ks->ks_class->ec_keylen); if (as->as_session) crypto_freesession(as->as_session); bzero(cri, sizeof(cri)); /* * We only want the first 96 bits of the HMAC. */ cri[0].cri_alg = CRYPTO_SHA1_HMAC; cri[0].cri_klen = ks->ks_class->ec_keybits; cri[0].cri_mlen = 12; cri[0].cri_key = ks->ks_key; cri[0].cri_next = &cri[1]; cri[1].cri_alg = CRYPTO_AES_CBC; cri[1].cri_klen = ks->ks_class->ec_keybits; cri[1].cri_mlen = 0; cri[1].cri_key = ks->ks_key; cri[1].cri_next = NULL; crypto_newsession(&as->as_session, cri, CRYPTOCAP_F_HARDWARE | CRYPTOCAP_F_SOFTWARE); }
/* this function returns true if OCF can do the compression */ int ipsec_ocf_comp_sa_init(struct ipsec_sa *ipsp, int compalg) { struct cryptoini cric; int error; KLIPS_PRINT(debug_pfkey, "klips_debug:ipsec_ocf_comp_sa_init(c=0x%x)\n", compalg); memset(&cric, 0, sizeof(cric)); cric.cri_alg = ipsec_ocf_compalg(compalg); if (!cric.cri_alg) { KLIPS_PRINT(debug_pfkey, "klips_debug:ipsec_ocf_comp_sa_init: " "invalid compalg=%d given\n", compalg); return 0; } error = crypto_newsession(&ipsp->ocf_cryptoid, &cric, ipsec_ocf_crid); if (error) { KLIPS_PRINT(debug_pfkey, "klips_debug:ipsec_ocf_comp_sa_init: " "crypto_newsession failed 0x%x\n", error); return 0; } ipsp->ocf_in_use = 1; return 1; }
static int ocf_init(void) { int error; struct cryptoini crie, cria; struct cryptodesc crda, crde; memset(&crie, 0, sizeof(crie)); memset(&cria, 0, sizeof(cria)); memset(&crde, 0, sizeof(crde)); memset(&crda, 0, sizeof(crda)); cria.cri_alg = CRYPTO_SHA1_HMAC; cria.cri_klen = 20 * 8; cria.cri_key = "0123456789abcdefghij"; crie.cri_alg = CRYPTO_3DES_CBC; crie.cri_klen = 24 * 8; crie.cri_key = "0123456789abcdefghijklmn"; crie.cri_next = &cria; error = crypto_newsession(&ocf_cryptoid, &crie, 0); if (error) { printk("crypto_newsession failed %d\n", error); return -1; } return 0; }
static int g_eli_crypto_cipher(u_int algo, int enc, u_char *data, size_t datasize, const u_char *key, size_t keysize) { struct cryptoini cri; struct cryptop *crp; struct cryptodesc *crd; uint64_t sid; u_char *p; int error; KASSERT(algo != CRYPTO_AES_XTS, ("%s: CRYPTO_AES_XTS unexpected here", __func__)); bzero(&cri, sizeof(cri)); cri.cri_alg = algo; cri.cri_key = __DECONST(void *, key); cri.cri_klen = keysize; error = crypto_newsession(&sid, &cri, CRYPTOCAP_F_SOFTWARE); if (error != 0) return (error); p = malloc(sizeof(*crp) + sizeof(*crd), M_ELI, M_NOWAIT | M_ZERO); if (p == NULL) { crypto_freesession(sid); return (ENOMEM); } crp = (struct cryptop *)p; p += sizeof(*crp); crd = (struct cryptodesc *)p; p += sizeof(*crd); crd->crd_skip = 0; crd->crd_len = datasize; crd->crd_flags = CRD_F_IV_EXPLICIT | CRD_F_IV_PRESENT; if (enc) crd->crd_flags |= CRD_F_ENCRYPT; crd->crd_alg = algo; crd->crd_key = __DECONST(void *, key); crd->crd_klen = keysize; bzero(crd->crd_iv, sizeof(crd->crd_iv)); crd->crd_next = NULL; crp->crp_sid = sid; crp->crp_ilen = datasize; crp->crp_olen = datasize; crp->crp_opaque = NULL; crp->crp_callback = g_eli_crypto_done; crp->crp_buf = (void *)data; crp->crp_flags = CRYPTO_F_CBIFSYNC; crp->crp_desc = crd; error = crypto_dispatch(crp); if (error == 0) { while (crp->crp_opaque == NULL) tsleep(crp, PRIBIO, "geli", hz / 5); error = crp->crp_etype; } free(crp, M_ELI); crypto_freesession(sid); return (error); }
/* * ah_init() is called when an SPI is being set up. */ static int ah_init(struct secasvar *sav, struct xformsw *xsp) { struct cryptoini cria; int error; error = ah_init0(sav, xsp, &cria); return error ? error : crypto_newsession(&sav->tdb_cryptoid, &cria, V_crypto_support); }
/* * ah_init() is called when an SPI is being set up. */ static int ah_init(struct secasvar *sav, const struct xformsw *xsp) { struct cryptoini cria; int error; error = ah_init0(sav, xsp, &cria); if (!error) error = crypto_newsession(&sav->tdb_cryptoid, &cria, crypto_support); return error; }
/* * ah_init() is called when an SPI is being set up. */ int ah_init(struct tdb *tdbp, struct xformsw *xsp, struct ipsecinit *ii) { struct auth_hash *thash = NULL; struct cryptoini cria, crin; /* Authentication operation. */ switch (ii->ii_authalg) { case SADB_AALG_MD5HMAC: thash = &auth_hash_hmac_md5_96; break; case SADB_AALG_SHA1HMAC: thash = &auth_hash_hmac_sha1_96; break; case SADB_X_AALG_RIPEMD160HMAC: thash = &auth_hash_hmac_ripemd_160_96; break; case SADB_X_AALG_SHA2_256: thash = &auth_hash_hmac_sha2_256_128; break; case SADB_X_AALG_SHA2_384: thash = &auth_hash_hmac_sha2_384_192; break; case SADB_X_AALG_SHA2_512: thash = &auth_hash_hmac_sha2_512_256; break; case SADB_X_AALG_MD5: thash = &auth_hash_key_md5; break; case SADB_X_AALG_SHA1: thash = &auth_hash_key_sha1; break; default: DPRINTF(("ah_init(): unsupported authentication algorithm %d specified\n", ii->ii_authalg)); return EINVAL; } if (ii->ii_authkeylen != thash->keysize && thash->keysize != 0) { DPRINTF(("ah_init(): keylength %d doesn't match algorithm " "%s keysize (%d)\n", ii->ii_authkeylen, thash->name, thash->keysize)); return EINVAL; } tdbp->tdb_xform = xsp; tdbp->tdb_authalgxform = thash; tdbp->tdb_rpl = AH_HMAC_INITIAL_RPL; DPRINTF(("ah_init(): initialized TDB with hash algorithm %s\n", thash->name)); tdbp->tdb_amxkeylen = ii->ii_authkeylen; tdbp->tdb_amxkey = malloc(tdbp->tdb_amxkeylen, M_XDATA, M_WAITOK); bcopy(ii->ii_authkey, tdbp->tdb_amxkey, tdbp->tdb_amxkeylen); /* Initialize crypto session. */ bzero(&cria, sizeof(cria)); cria.cri_alg = tdbp->tdb_authalgxform->type; cria.cri_klen = ii->ii_authkeylen * 8; cria.cri_key = ii->ii_authkey; if ((tdbp->tdb_wnd > 0) && (tdbp->tdb_flags & TDBF_ESN)) { bzero(&crin, sizeof(crin)); crin.cri_alg = CRYPTO_ESN; cria.cri_next = &crin; } return crypto_newsession(&tdbp->tdb_cryptoid, &cria, 0); }
/* * esp_init() is called when an SPI is being set up. */ static int esp_init(struct secasvar *sav, struct xformsw *xsp) { struct enc_xform *txform; struct cryptoini cria, crie; int keylen; int error; txform = esp_algorithm_lookup(sav->alg_enc); if (txform == NULL) { DPRINTF(("%s: unsupported encryption algorithm %d\n", __func__, sav->alg_enc)); return EINVAL; } if (sav->key_enc == NULL) { DPRINTF(("%s: no encoding key for %s algorithm\n", __func__, txform->name)); return EINVAL; } if ((sav->flags & (SADB_X_EXT_OLD | SADB_X_EXT_IV4B)) == SADB_X_EXT_IV4B) { DPRINTF(("%s: 4-byte IV not supported with protocol\n", __func__)); return EINVAL; } /* subtract off the salt, RFC4106, 8.1 and RFC3686, 5.1 */ keylen = _KEYLEN(sav->key_enc) - SAV_ISCTRORGCM(sav) * 4; if (txform->minkey > keylen || keylen > txform->maxkey) { DPRINTF(("%s: invalid key length %u, must be in the range " "[%u..%u] for algorithm %s\n", __func__, keylen, txform->minkey, txform->maxkey, txform->name)); return EINVAL; } /* * NB: The null xform needs a non-zero blocksize to keep the * crypto code happy but if we use it to set ivlen then * the ESP header will be processed incorrectly. The * compromise is to force it to zero here. */ if (SAV_ISCTRORGCM(sav)) sav->ivlen = 8; /* RFC4106 3.1 and RFC3686 3.1 */ else sav->ivlen = (txform == &enc_xform_null ? 0 : txform->ivsize); /* * Setup AH-related state. */ if (sav->alg_auth != 0) { error = ah_init0(sav, xsp, &cria); if (error) return error; } /* NB: override anything set in ah_init0 */ sav->tdb_xform = xsp; sav->tdb_encalgxform = txform; /* * Whenever AES-GCM is used for encryption, one * of the AES authentication algorithms is chosen * as well, based on the key size. */ if (sav->alg_enc == SADB_X_EALG_AESGCM16) { switch (keylen) { case AES_128_GMAC_KEY_LEN: sav->alg_auth = SADB_X_AALG_AES128GMAC; sav->tdb_authalgxform = &auth_hash_nist_gmac_aes_128; break; case AES_192_GMAC_KEY_LEN: sav->alg_auth = SADB_X_AALG_AES192GMAC; sav->tdb_authalgxform = &auth_hash_nist_gmac_aes_192; break; case AES_256_GMAC_KEY_LEN: sav->alg_auth = SADB_X_AALG_AES256GMAC; sav->tdb_authalgxform = &auth_hash_nist_gmac_aes_256; break; default: DPRINTF(("%s: invalid key length %u" "for algorithm %s\n", __func__, keylen, txform->name)); return EINVAL; } bzero(&cria, sizeof(cria)); cria.cri_alg = sav->tdb_authalgxform->type; cria.cri_key = sav->key_enc->key_data; cria.cri_klen = _KEYBITS(sav->key_enc) - SAV_ISGCM(sav) * 32; } /* Initialize crypto session. */ bzero(&crie, sizeof(crie)); crie.cri_alg = sav->tdb_encalgxform->type; crie.cri_key = sav->key_enc->key_data; crie.cri_klen = _KEYBITS(sav->key_enc) - SAV_ISCTRORGCM(sav) * 32; if (sav->tdb_authalgxform && sav->tdb_encalgxform) { /* init both auth & enc */ crie.cri_next = &cria; error = crypto_newsession(&sav->tdb_cryptoid, &crie, V_crypto_support); } else if (sav->tdb_encalgxform) { error = crypto_newsession(&sav->tdb_cryptoid, &crie, V_crypto_support); } else if (sav->tdb_authalgxform) { error = crypto_newsession(&sav->tdb_cryptoid, &cria, V_crypto_support); } else { /* XXX cannot happen? */ DPRINTF(("%s: no encoding OR authentication xform!\n", __func__)); error = EINVAL; } return error; }
int ipsec_ocf_sa_init(struct ipsec_sa *ipsp, int authalg, int encalg) { struct cryptoini crie, cria; int error; KLIPS_PRINT(debug_pfkey, "klips_debug:ipsec_ocf_sa_init(a=0x%x,e=0x%x)\n", authalg, encalg); if (authalg && ipsp->ips_key_bits_a == 0) { KLIPS_PRINT(debug_pfkey, "klips_debug:ipsec_ocf_sa_init(a=0x%x,e=0x%x) a-key-bits=0\n", authalg, encalg); /* pretend we are happy with this */ return 1; } if (encalg && ipsp->ips_key_bits_e == 0) { KLIPS_PRINT(debug_pfkey, "klips_debug:ipsec_ocf_sa_init(a=0x%x,e=0x%x) e-key-bits=0\n", authalg, encalg); /* pretend we are happy with this */ return 1; } if (ipsp->ocf_in_use) printk( "KLIPS: ipsec_ocf_sa_init received SA is already initted?\n"); memset(&crie, 0, sizeof(crie)); memset(&cria, 0, sizeof(cria)); cria.cri_alg = ipsec_ocf_authalg(authalg); cria.cri_klen = ipsp->ips_key_bits_a; cria.cri_key = ipsp->ips_key_a; cria.cri_mlen = 12; crie.cri_alg = ipsec_ocf_encalg(encalg); crie.cri_klen = ipsp->ips_key_bits_e; crie.cri_key = ipsp->ips_key_e; switch (crie.cri_alg) { case CRYPTO_AES_CBC: ipsp->ips_iv_size = 16; break; case CRYPTO_DES_CBC: case CRYPTO_3DES_CBC: ipsp->ips_iv_size = 8; break; default: ipsp->ips_iv_size = 0; break; } ipsp->ips_iv_bits = ipsp->ips_iv_size * 8; ipsp->ips_auth_bits = ipsp->ips_key_bits_a; if (authalg && encalg) { crie.cri_next = &cria; error = crypto_newsession(&ipsp->ocf_cryptoid, &crie, ipsec_ocf_crid); } else if (encalg) { error = crypto_newsession(&ipsp->ocf_cryptoid, &crie, ipsec_ocf_crid); } else if (authalg) { error = crypto_newsession(&ipsp->ocf_cryptoid, &cria, ipsec_ocf_crid); } else { KLIPS_PRINT(debug_pfkey, "klips_debug:ipsec_ocf_sa_init: " "no authalg or encalg\n"); return 0; } if (error) { KLIPS_PRINT(debug_pfkey, "klips_debug:ipsec_ocf_sa_init: " "crypto_newsession failed 0x%x\n", error); return 0; } /* make sure no ALG stuff bites us */ if (ipsp->ips_alg_enc) printk("We received an ALG initted SA\n"); ipsp->ips_alg_enc = NULL; ipsp->ocf_in_use = 1; return 1; }
/* * esp_init() is called when an SPI is being set up. */ static int esp_init(struct secasvar *sav, struct xformsw *xsp) { struct enc_xform *txform; struct cryptoini cria, crie; int keylen; int error; txform = esp_algorithm_lookup(sav->alg_enc); if (txform == NULL) { DPRINTF(("%s: unsupported encryption algorithm %d\n", __func__, sav->alg_enc)); return EINVAL; } if (sav->key_enc == NULL) { DPRINTF(("%s: no encoding key for %s algorithm\n", __func__, txform->name)); return EINVAL; } if ((sav->flags&(SADB_X_EXT_OLD|SADB_X_EXT_IV4B)) == SADB_X_EXT_IV4B) { DPRINTF(("%s: 4-byte IV not supported with protocol\n", __func__)); return EINVAL; } keylen = _KEYLEN(sav->key_enc); if (txform->minkey > keylen || keylen > txform->maxkey) { DPRINTF(("%s: invalid key length %u, must be in the range " "[%u..%u] for algorithm %s\n", __func__, keylen, txform->minkey, txform->maxkey, txform->name)); return EINVAL; } /* * NB: The null xform needs a non-zero blocksize to keep the * crypto code happy but if we use it to set ivlen then * the ESP header will be processed incorrectly. The * compromise is to force it to zero here. */ sav->ivlen = (txform == &enc_xform_null ? 0 : txform->blocksize); sav->iv = (caddr_t) malloc(sav->ivlen, M_XDATA, M_WAITOK); if (sav->iv == NULL) { DPRINTF(("%s: no memory for IV\n", __func__)); return EINVAL; } key_randomfill(sav->iv, sav->ivlen); /*XXX*/ /* * Setup AH-related state. */ if (sav->alg_auth != 0) { error = ah_init0(sav, xsp, &cria); if (error) return error; } /* NB: override anything set in ah_init0 */ sav->tdb_xform = xsp; sav->tdb_encalgxform = txform; /* Initialize crypto session. */ bzero(&crie, sizeof (crie)); crie.cri_alg = sav->tdb_encalgxform->type; crie.cri_klen = _KEYBITS(sav->key_enc); crie.cri_key = sav->key_enc->key_data; /* XXX Rounds ? */ if (sav->tdb_authalgxform && sav->tdb_encalgxform) { /* init both auth & enc */ crie.cri_next = &cria; error = crypto_newsession(&sav->tdb_cryptoid, &crie, V_crypto_support); } else if (sav->tdb_encalgxform) { error = crypto_newsession(&sav->tdb_cryptoid, &crie, V_crypto_support); } else if (sav->tdb_authalgxform) { error = crypto_newsession(&sav->tdb_cryptoid, &cria, V_crypto_support); } else { /* XXX cannot happen? */ DPRINTF(("%s: no encoding OR authentication xform!\n", __func__)); error = EINVAL; } return error; }
/* * esp_init() is called when an SPI is being set up. */ int esp_init(struct tdb *tdbp, struct xformsw *xsp, struct ipsecinit *ii) { const struct enc_xform *txform = NULL; const struct auth_hash *thash = NULL; struct cryptoini cria, crie; if (!ii->ii_encalg && !ii->ii_authalg) { DPRINTF(("esp_init(): neither authentication nor encryption " "algorithm given")); return EINVAL; } if (ii->ii_encalg) { switch (ii->ii_encalg) { case SADB_EALG_NULL: txform = &enc_xform_null; break; case SADB_EALG_DESCBC: txform = &enc_xform_des; break; case SADB_EALG_3DESCBC: txform = &enc_xform_3des; break; case SADB_X_EALG_AES: txform = &enc_xform_rijndael128; break; case SADB_X_EALG_AESCTR: txform = &enc_xform_aes_ctr; break; case SADB_X_EALG_BLF: txform = &enc_xform_blf; break; case SADB_X_EALG_CAST: txform = &enc_xform_cast5; break; case SADB_X_EALG_SKIPJACK: txform = &enc_xform_skipjack; break; default: DPRINTF(("esp_init(): unsupported encryption algorithm %d specified\n", ii->ii_encalg)); return EINVAL; } if (ii->ii_enckeylen < txform->minkey) { DPRINTF(("esp_init(): keylength %d too small (min length is %d) for algorithm %s\n", ii->ii_enckeylen, txform->minkey, txform->name)); return EINVAL; } if (ii->ii_enckeylen > txform->maxkey) { DPRINTF(("esp_init(): keylength %d too large (max length is %d) for algorithm %s\n", ii->ii_enckeylen, txform->maxkey, txform->name)); return EINVAL; } tdbp->tdb_encalgxform = txform; DPRINTF(("esp_init(): initialized TDB with enc algorithm %s\n", txform->name)); tdbp->tdb_ivlen = txform->ivsize; if (tdbp->tdb_flags & TDBF_HALFIV) tdbp->tdb_ivlen /= 2; } if (ii->ii_authalg) { switch (ii->ii_authalg) { case SADB_AALG_MD5HMAC: thash = &auth_hash_hmac_md5_96; break; case SADB_AALG_SHA1HMAC: thash = &auth_hash_hmac_sha1_96; break; case SADB_X_AALG_RIPEMD160HMAC: thash = &auth_hash_hmac_ripemd_160_96; break; case SADB_X_AALG_SHA2_256: thash = &auth_hash_hmac_sha2_256_96; break; case SADB_X_AALG_SHA2_384: thash = &auth_hash_hmac_sha2_384_96; break; case SADB_X_AALG_SHA2_512: thash = &auth_hash_hmac_sha2_512_96; break; default: DPRINTF(("esp_init(): unsupported authentication algorithm %d specified\n", ii->ii_authalg)); return EINVAL; } if (ii->ii_authkeylen != thash->keysize) { DPRINTF(("esp_init(): keylength %d doesn't match algorithm %s keysize (%d)\n", ii->ii_authkeylen, thash->name, thash->keysize)); return EINVAL; } tdbp->tdb_authalgxform = thash; DPRINTF(("esp_init(): initialized TDB with hash algorithm %s\n", thash->name)); } tdbp->tdb_xform = xsp; tdbp->tdb_bitmap = 0; tdbp->tdb_rpl = AH_HMAC_INITIAL_RPL; /* Initialize crypto session */ if (tdbp->tdb_encalgxform) { /* Save the raw keys */ tdbp->tdb_emxkeylen = ii->ii_enckeylen; tdbp->tdb_emxkey = malloc(tdbp->tdb_emxkeylen, M_XDATA, M_WAITOK); bcopy(ii->ii_enckey, tdbp->tdb_emxkey, tdbp->tdb_emxkeylen); bzero(&crie, sizeof(crie)); crie.cri_alg = tdbp->tdb_encalgxform->type; if (tdbp->tdb_authalgxform) crie.cri_next = &cria; else crie.cri_next = NULL; crie.cri_klen = ii->ii_enckeylen * 8; crie.cri_key = ii->ii_enckey; /* XXX Rounds ? */ } if (tdbp->tdb_authalgxform) { /* Save the raw keys */ tdbp->tdb_amxkeylen = ii->ii_authkeylen; tdbp->tdb_amxkey = malloc(tdbp->tdb_amxkeylen, M_XDATA, M_WAITOK); bcopy(ii->ii_authkey, tdbp->tdb_amxkey, tdbp->tdb_amxkeylen); bzero(&cria, sizeof(cria)); cria.cri_alg = tdbp->tdb_authalgxform->type; cria.cri_next = NULL; cria.cri_klen = ii->ii_authkeylen * 8; cria.cri_key = ii->ii_authkey; } return crypto_newsession(&tdbp->tdb_cryptoid, (tdbp->tdb_encalgxform ? &crie : &cria), 0); }
/* * esp_init() is called when an SPI is being set up. */ static int esp_init(struct secasvar *sav, const struct xformsw *xsp) { const struct enc_xform *txform; struct cryptoini cria, crie; int keylen; int error; txform = esp_algorithm_lookup(sav->alg_enc); if (txform == NULL) { DPRINTF(("esp_init: unsupported encryption algorithm %d\n", sav->alg_enc)); return EINVAL; } if (sav->key_enc == NULL) { DPRINTF(("esp_init: no encoding key for %s algorithm\n", txform->name)); return EINVAL; } if ((sav->flags&(SADB_X_EXT_OLD|SADB_X_EXT_IV4B)) == SADB_X_EXT_IV4B) { DPRINTF(("esp_init: 4-byte IV not supported with protocol\n")); return EINVAL; } keylen = _KEYLEN(sav->key_enc); if (txform->minkey > keylen || keylen > txform->maxkey) { DPRINTF(("esp_init: invalid key length %u, must be in " "the range [%u..%u] for algorithm %s\n", keylen, txform->minkey, txform->maxkey, txform->name)); return EINVAL; } sav->ivlen = txform->ivsize; /* * Setup AH-related state. */ if (sav->alg_auth != 0) { error = ah_init0(sav, xsp, &cria); if (error) return error; } /* NB: override anything set in ah_init0 */ sav->tdb_xform = xsp; sav->tdb_encalgxform = txform; if (sav->alg_enc == SADB_X_EALG_AESGCM16 || sav->alg_enc == SADB_X_EALG_AESGMAC) { switch (keylen) { case 20: sav->alg_auth = SADB_X_AALG_AES128GMAC; sav->tdb_authalgxform = &auth_hash_gmac_aes_128; break; case 28: sav->alg_auth = SADB_X_AALG_AES192GMAC; sav->tdb_authalgxform = &auth_hash_gmac_aes_192; break; case 36: sav->alg_auth = SADB_X_AALG_AES256GMAC; sav->tdb_authalgxform = &auth_hash_gmac_aes_256; break; } memset(&cria, 0, sizeof(cria)); cria.cri_alg = sav->tdb_authalgxform->type; cria.cri_klen = _KEYBITS(sav->key_enc); cria.cri_key = _KEYBUF(sav->key_enc); } /* Initialize crypto session. */ memset(&crie, 0, sizeof (crie)); crie.cri_alg = sav->tdb_encalgxform->type; crie.cri_klen = _KEYBITS(sav->key_enc); crie.cri_key = _KEYBUF(sav->key_enc); /* XXX Rounds ? */ if (sav->tdb_authalgxform && sav->tdb_encalgxform) { /* init both auth & enc */ crie.cri_next = &cria; error = crypto_newsession(&sav->tdb_cryptoid, &crie, crypto_support); } else if (sav->tdb_encalgxform) { error = crypto_newsession(&sav->tdb_cryptoid, &crie, crypto_support); } else if (sav->tdb_authalgxform) { error = crypto_newsession(&sav->tdb_cryptoid, &cria, crypto_support); } else { /* XXX cannot happen? */ DPRINTF(("esp_init: no encoding OR authentication xform!\n")); error = EINVAL; } return error; }
static int g_eli_crypto_cipher(u_int algo, int enc, u_char *data, size_t datasize, const u_char *key, size_t keysize) { struct cryptoini cri; struct cryptop *crp; struct cryptodesc *crd; struct uio *uio; struct iovec *iov; uint64_t sid; u_char *p; int error; bzero(&cri, sizeof(cri)); cri.cri_alg = algo; cri.cri_key = __DECONST(void *, key); cri.cri_klen = keysize; error = crypto_newsession(&sid, &cri, CRYPTOCAP_F_SOFTWARE); if (error != 0) return (error); p = malloc(sizeof(*crp) + sizeof(*crd) + sizeof(*uio) + sizeof(*iov), M_ELI, M_NOWAIT | M_ZERO); if (p == NULL) { crypto_freesession(sid); return (ENOMEM); } crp = (struct cryptop *)p; p += sizeof(*crp); crd = (struct cryptodesc *)p; p += sizeof(*crd); uio = (struct uio *)p; p += sizeof(*uio); iov = (struct iovec *)p; p += sizeof(*iov); iov->iov_len = datasize; iov->iov_base = data; uio->uio_iov = iov; uio->uio_iovcnt = 1; uio->uio_segflg = UIO_SYSSPACE; uio->uio_resid = datasize; crd->crd_skip = 0; crd->crd_len = datasize; crd->crd_flags = CRD_F_IV_EXPLICIT | CRD_F_IV_PRESENT; if (enc) crd->crd_flags |= CRD_F_ENCRYPT; crd->crd_alg = algo; crd->crd_key = __DECONST(void *, key); crd->crd_klen = keysize; bzero(crd->crd_iv, sizeof(crd->crd_iv)); crd->crd_next = NULL; crp->crp_sid = sid; crp->crp_ilen = datasize; crp->crp_olen = datasize; crp->crp_opaque = NULL; crp->crp_callback = g_eli_crypto_done; crp->crp_buf = (void *)uio; crp->crp_flags = CRYPTO_F_IOV | CRYPTO_F_CBIFSYNC | CRYPTO_F_REL; crp->crp_desc = crd; error = crypto_dispatch(crp); if (error == 0) { while (crp->crp_opaque == NULL) tsleep(crp, PRIBIO, "geli", hz / 5); error = crp->crp_etype; } free(crp, M_ELI); crypto_freesession(sid); return (error); }