From: Eric Biggers Date: Fri, 22 May 2026 05:07:33 +0000 (-0500) Subject: net/rxrpc: Use local FCrypt-PCBC implementation X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=97b768514a6eb5aa8c2806df07aa1d37c5f3b1d2;p=thirdparty%2Flinux.git net/rxrpc: Use local FCrypt-PCBC implementation Use the local implementation of FCrypt-PCBC instead of the crypto API one. This will allow the crypto API one to be removed. It also simplifies the code quite a bit. The local FCrypt-PCBC implementation is also significantly faster than the crypto API one, since the crypto API one had a lot of overhead. For example, benchmarking on an x86_64 CPU, I see that FCrypt-PCBC decryption throughput improved from 83 MB/s to 157 MB/s. (Meanwhile, AES-256-GCM decryption is 8064 MB/s on the same CPU. Clearly, anyone looking for good performance, or anything that is actually secure for that matter, needs to look elsewhere anyway.) Acked-by: David Howells Signed-off-by: Eric Biggers Tested-by: Marc Dionne Link: https://patch.msgid.link/20260522050740.84561-3-ebiggers@kernel.org Signed-off-by: Jakub Kicinski --- diff --git a/net/rxrpc/Kconfig b/net/rxrpc/Kconfig index e2bb795cdf0c..de19c67dc965 100644 --- a/net/rxrpc/Kconfig +++ b/net/rxrpc/Kconfig @@ -60,7 +60,6 @@ config RXKAD select CRYPTO_MANAGER select CRYPTO_SKCIPHER select CRYPTO_PCBC - select CRYPTO_FCRYPT help Provide kerberos 4 and AFS kaserver security handling for AF_RXRPC through the use of the key retention service. diff --git a/net/rxrpc/ar-internal.h b/net/rxrpc/ar-internal.h index 30aaf69b4c7c..29d32aa4ecc7 100644 --- a/net/rxrpc/ar-internal.h +++ b/net/rxrpc/ar-internal.h @@ -577,7 +577,7 @@ struct rxrpc_connection { const struct rxrpc_security *security; /* applied security module */ union { struct { - struct crypto_sync_skcipher *cipher; /* encryption handle */ + struct fcrypt_key *cipher; /* encryption key */ struct rxrpc_crypt csum_iv; /* packet checksum base */ u32 nonce; /* response re-use preventer */ } rxkad; diff --git a/net/rxrpc/rxkad.c b/net/rxrpc/rxkad.c index 6fbd883401ac..d8bc5ecbfc3d 100644 --- a/net/rxrpc/rxkad.c +++ b/net/rxrpc/rxkad.c @@ -8,6 +8,7 @@ #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt #include +#include #include #include #include @@ -30,6 +31,8 @@ #define SNAME_SZ 40 /* size of service name */ #define RXKAD_ALIGN 8 +static const u8 zero_iv[FCRYPT_BSIZE]; + struct rxkad_level1_hdr { __be32 data_size; /* true data size (excluding padding) */ }; @@ -39,17 +42,8 @@ struct rxkad_level2_hdr { __be32 checksum; /* decrypted data checksum */ }; -static int rxkad_prime_packet_security(struct rxrpc_connection *conn, - struct crypto_sync_skcipher *ci); - -/* - * this holds a pinned cipher so that keventd doesn't get called by the cipher - * alloc routine, but since we have it to hand, we use it to decrypt RESPONSE - * packets - */ -static struct crypto_sync_skcipher *rxkad_ci; -static struct skcipher_request *rxkad_ci_req; -static DEFINE_MUTEX(rxkad_ci_mutex); +static void rxkad_prime_packet_security(struct rxrpc_connection *conn, + const struct fcrypt_key *cipher); /* * Parse the information from a server key @@ -100,23 +94,19 @@ static void rxkad_destroy_server_key(struct key *key) static int rxkad_init_connection_security(struct rxrpc_connection *conn, struct rxrpc_key_token *token) { - struct crypto_sync_skcipher *ci; + struct fcrypt_key *ci; int ret; _enter("{%d},{%x}", conn->debug_id, key_serial(conn->key)); conn->security_ix = token->security_index; - ci = crypto_alloc_sync_skcipher("pcbc(fcrypt)", 0, 0); - if (IS_ERR(ci)) { - _debug("no cipher"); - ret = PTR_ERR(ci); + ci = kmalloc_obj(*ci); + if (!ci) { + ret = -ENOMEM; goto error; } - - if (crypto_sync_skcipher_setkey(ci, token->kad->session_key, - sizeof(token->kad->session_key)) < 0) - BUG(); + fcrypt_preparekey(ci, token->kad->session_key); switch (conn->security_level) { case RXRPC_SECURITY_PLAIN: @@ -125,18 +115,16 @@ static int rxkad_init_connection_security(struct rxrpc_connection *conn, break; default: ret = -EKEYREJECTED; - goto error; + goto error_ci; } - ret = rxkad_prime_packet_security(conn, ci); - if (ret < 0) - goto error_ci; + rxkad_prime_packet_security(conn, ci); conn->rxkad.cipher = ci; return 0; error_ci: - crypto_free_sync_skcipher(ci); + kfree_sensitive(ci); error: _leave(" = %d", ret); return ret; @@ -188,62 +176,28 @@ static struct rxrpc_txbuf *rxkad_alloc_txbuf(struct rxrpc_call *call, size_t rem * prime the encryption state with the invariant parts of a connection's * description */ -static int rxkad_prime_packet_security(struct rxrpc_connection *conn, - struct crypto_sync_skcipher *ci) +static void rxkad_prime_packet_security(struct rxrpc_connection *conn, + const struct fcrypt_key *cipher) { - struct skcipher_request *req; struct rxrpc_key_token *token; - struct scatterlist sg; - struct rxrpc_crypt iv; - __be32 *tmpbuf; - size_t tmpsize = 4 * sizeof(__be32); - int ret; + __be32 tmpbuf[4]; _enter(""); if (!conn->key) - return 0; - - tmpbuf = kmalloc(tmpsize, GFP_KERNEL); - if (!tmpbuf) - return -ENOMEM; - - req = skcipher_request_alloc(&ci->base, GFP_NOFS); - if (!req) { - kfree(tmpbuf); - return -ENOMEM; - } - + return; token = conn->key->payload.data[0]; - memcpy(&iv, token->kad->session_key, sizeof(iv)); tmpbuf[0] = htonl(conn->proto.epoch); tmpbuf[1] = htonl(conn->proto.cid); tmpbuf[2] = 0; tmpbuf[3] = htonl(conn->security_ix); - sg_init_one(&sg, tmpbuf, tmpsize); - skcipher_request_set_sync_tfm(req, ci); - skcipher_request_set_callback(req, 0, NULL, NULL); - skcipher_request_set_crypt(req, &sg, &sg, tmpsize, iv.x); - ret = crypto_skcipher_encrypt(req); - skcipher_request_free(req); - - memcpy(&conn->rxkad.csum_iv, tmpbuf + 2, sizeof(conn->rxkad.csum_iv)); - kfree(tmpbuf); - _leave(" = %d", ret); - return ret; -} - -/* - * Allocate and prepare the crypto request on a call. For any particular call, - * this is called serially for the packets, so no lock should be necessary. - */ -static struct skcipher_request *rxkad_get_call_crypto(struct rxrpc_call *call) -{ - struct crypto_skcipher *tfm = &call->conn->rxkad.cipher->base; - - return skcipher_request_alloc(tfm, GFP_NOFS); + static_assert(sizeof(tmpbuf) % FCRYPT_BSIZE == 0); + fcrypt_pcbc_encrypt(cipher, /* iv= */ token->kad->session_key, tmpbuf, + tmpbuf, sizeof(tmpbuf) / FCRYPT_BSIZE); + memcpy(&conn->rxkad.csum_iv, &tmpbuf[2], sizeof(conn->rxkad.csum_iv)); + _leave(""); } /* @@ -256,16 +210,12 @@ static void rxkad_free_call_crypto(struct rxrpc_call *call) /* * partially encrypt a packet (level 1 security) */ -static int rxkad_secure_packet_auth(const struct rxrpc_call *call, - struct rxrpc_txbuf *txb, - struct skcipher_request *req) +static void rxkad_secure_packet_auth(const struct rxrpc_call *call, + struct rxrpc_txbuf *txb) { struct rxkad_level1_hdr *hdr = txb->data; - struct rxrpc_crypt iv; - struct scatterlist sg; size_t pad; u16 check; - int ret; _enter(""); @@ -282,33 +232,20 @@ static int rxkad_secure_packet_auth(const struct rxrpc_call *call, } /* start the encryption afresh */ - memset(&iv, 0, sizeof(iv)); - - sg_init_one(&sg, hdr, 8); - skcipher_request_set_sync_tfm(req, call->conn->rxkad.cipher); - skcipher_request_set_callback(req, 0, NULL, NULL); - skcipher_request_set_crypt(req, &sg, &sg, 8, iv.x); - ret = crypto_skcipher_encrypt(req); - skcipher_request_zero(req); - - _leave(" = %d", ret); - return ret; + fcrypt_pcbc_encrypt(call->conn->rxkad.cipher, zero_iv, hdr, hdr, 1); + _leave(""); } /* * wholly encrypt a packet (level 2 security) */ -static int rxkad_secure_packet_encrypt(const struct rxrpc_call *call, - struct rxrpc_txbuf *txb, - struct skcipher_request *req) +static void rxkad_secure_packet_encrypt(const struct rxrpc_call *call, + struct rxrpc_txbuf *txb) { const struct rxrpc_key_token *token; struct rxkad_level2_hdr *rxkhdr = txb->data; - struct rxrpc_crypt iv; - struct scatterlist sg; size_t content, pad; u16 check; - int ret; _enter(""); @@ -318,22 +255,18 @@ static int rxkad_secure_packet_encrypt(const struct rxrpc_call *call, rxkhdr->checksum = 0; content = sizeof(struct rxkad_level2_hdr) + txb->len; + static_assert(RXKAD_ALIGN == FCRYPT_BSIZE); txb->pkt_len = round_up(content, RXKAD_ALIGN); pad = txb->pkt_len - content; if (pad) memset(txb->data + txb->offset, 0, pad); + /* Now txb->pkt_len % FCRYPT_BSIZE == 0. */ /* encrypt from the session key */ token = call->conn->key->payload.data[0]; - memcpy(&iv, token->kad->session_key, sizeof(iv)); - - sg_init_one(&sg, rxkhdr, txb->pkt_len); - skcipher_request_set_sync_tfm(req, call->conn->rxkad.cipher); - skcipher_request_set_callback(req, 0, NULL, NULL); - skcipher_request_set_crypt(req, &sg, &sg, txb->pkt_len, iv.x); - ret = crypto_skcipher_encrypt(req); - skcipher_request_zero(req); - return ret; + fcrypt_pcbc_encrypt(call->conn->rxkad.cipher, token->kad->session_key, + rxkhdr, rxkhdr, txb->pkt_len / FCRYPT_BSIZE); + _leave(""); } /* @@ -341,9 +274,6 @@ static int rxkad_secure_packet_encrypt(const struct rxrpc_call *call, */ static int rxkad_secure_packet(struct rxrpc_call *call, struct rxrpc_txbuf *txb) { - struct skcipher_request *req; - struct rxrpc_crypt iv; - struct scatterlist sg; union { __be32 buf[2]; } crypto __aligned(8); @@ -361,27 +291,16 @@ static int rxkad_secure_packet(struct rxrpc_call *call, struct rxrpc_txbuf *txb) if (ret < 0) return ret; - req = rxkad_get_call_crypto(call); - if (!req) - return -ENOMEM; - - /* continue encrypting from where we left off */ - memcpy(&iv, call->conn->rxkad.csum_iv.x, sizeof(iv)); - /* calculate the security checksum */ x = (call->cid & RXRPC_CHANNELMASK) << (32 - RXRPC_CIDSHIFT); x |= txb->seq & 0x3fffffff; crypto.buf[0] = htonl(call->call_id); crypto.buf[1] = htonl(x); - sg_init_one(&sg, crypto.buf, 8); - skcipher_request_set_sync_tfm(req, call->conn->rxkad.cipher); - skcipher_request_set_callback(req, 0, NULL, NULL); - skcipher_request_set_crypt(req, &sg, &sg, 8, iv.x); - ret = crypto_skcipher_encrypt(req); - skcipher_request_zero(req); - if (ret < 0) - goto out; + /* continue encrypting from where we left off */ + fcrypt_pcbc_encrypt(call->conn->rxkad.cipher, + call->conn->rxkad.csum_iv.x, crypto.buf, crypto.buf, + 1); y = ntohl(crypto.buf[1]); y = (y >> 16) & 0xffff; @@ -395,14 +314,16 @@ static int rxkad_secure_packet(struct rxrpc_call *call, struct rxrpc_txbuf *txb) ret = 0; break; case RXRPC_SECURITY_AUTH: - ret = rxkad_secure_packet_auth(call, txb, req); + rxkad_secure_packet_auth(call, txb); if (txb->alloc_size == RXRPC_JUMBO_DATALEN) txb->jumboable = true; + ret = 0; break; case RXRPC_SECURITY_ENCRYPT: - ret = rxkad_secure_packet_encrypt(call, txb, req); + rxkad_secure_packet_encrypt(call, txb); if (txb->alloc_size == RXRPC_JUMBO_DATALEN) txb->jumboable = true; + ret = 0; break; default: ret = -EPERM; @@ -417,8 +338,6 @@ static int rxkad_secure_packet(struct rxrpc_call *call, struct rxrpc_txbuf *txb) memset(p + txb->pkt_len, 0, gap); } -out: - skcipher_request_free(req); _leave(" = %d [set %x]", ret, y); return ret; } @@ -427,17 +346,13 @@ out: * decrypt partial encryption on a packet (level 1 security) */ static int rxkad_verify_packet_1(struct rxrpc_call *call, struct sk_buff *skb, - rxrpc_seq_t seq, - struct skcipher_request *req) + rxrpc_seq_t seq) { struct rxkad_level1_hdr *sechdr; struct rxrpc_skb_priv *sp = rxrpc_skb(skb); - struct rxrpc_crypt iv; - struct scatterlist sg[1]; void *data = call->rx_dec_buffer; u32 len = sp->len, data_size, buf; u16 check; - int ret; _enter(""); @@ -445,21 +360,8 @@ static int rxkad_verify_packet_1(struct rxrpc_call *call, struct sk_buff *skb, return rxrpc_abort_eproto(call, skb, RXKADSEALEDINCON, rxkad_abort_1_short_header); - /* Decrypt the skbuff in-place. TODO: We really want to decrypt - * directly into the target buffer. - */ - sg_init_one(sg, data, len); - - /* start the decryption afresh */ - memset(&iv, 0, sizeof(iv)); - - skcipher_request_set_sync_tfm(req, call->conn->rxkad.cipher); - skcipher_request_set_callback(req, 0, NULL, NULL); - skcipher_request_set_crypt(req, sg, sg, 8, iv.x); - ret = crypto_skcipher_decrypt(req); - skcipher_request_zero(req); - if (ret < 0) - return ret; + /* Decrypt the first 8-byte block of the packet, using the zero IV. */ + fcrypt_pcbc_decrypt(call->conn->rxkad.cipher, zero_iv, data, data, 1); /* Extract the decrypted packet length */ sechdr = data; @@ -488,18 +390,14 @@ static int rxkad_verify_packet_1(struct rxrpc_call *call, struct sk_buff *skb, * wholly decrypt a packet (level 2 security) */ static int rxkad_verify_packet_2(struct rxrpc_call *call, struct sk_buff *skb, - rxrpc_seq_t seq, - struct skcipher_request *req) + rxrpc_seq_t seq) { const struct rxrpc_key_token *token; struct rxkad_level2_hdr *sechdr; struct rxrpc_skb_priv *sp = rxrpc_skb(skb); - struct rxrpc_crypt iv; - struct scatterlist sg[1]; void *data = call->rx_dec_buffer; u32 len = sp->len, data_size, buf; u16 check; - int ret; _enter(",{%d}", len); @@ -510,26 +408,10 @@ static int rxkad_verify_packet_2(struct rxrpc_call *call, struct sk_buff *skb, /* Don't let the crypto algo see a misaligned length. */ len = round_down(len, 8); - /* Decrypt in place in the call's decryption buffer. TODO: We really - * want to decrypt directly into the target buffer. - */ - sg_init_one(sg, data, len); - /* decrypt from the session key */ token = call->conn->key->payload.data[0]; - memcpy(&iv, token->kad->session_key, sizeof(iv)); - - skcipher_request_set_sync_tfm(req, call->conn->rxkad.cipher); - skcipher_request_set_callback(req, 0, NULL, NULL); - skcipher_request_set_crypt(req, sg, sg, len, iv.x); - ret = crypto_skcipher_decrypt(req); - skcipher_request_zero(req); - if (ret < 0) { - if (ret == -ENOMEM) - return ret; - return rxrpc_abort_eproto(call, skb, RXKADSEALEDINCON, - rxkad_abort_2_crypto_unaligned); - } + fcrypt_pcbc_decrypt(call->conn->rxkad.cipher, token->kad->session_key, + data, data, len / FCRYPT_BSIZE); /* Extract the decrypted packet length */ sechdr = data; @@ -562,9 +444,6 @@ static int rxkad_verify_packet_2(struct rxrpc_call *call, struct sk_buff *skb, static int rxkad_verify_packet(struct rxrpc_call *call, struct sk_buff *skb) { struct rxrpc_skb_priv *sp = rxrpc_skb(skb); - struct skcipher_request *req; - struct rxrpc_crypt iv; - struct scatterlist sg; union { __be32 buf[2]; } crypto __aligned(8); @@ -579,27 +458,16 @@ static int rxkad_verify_packet(struct rxrpc_call *call, struct sk_buff *skb) if (!call->conn->rxkad.cipher) return 0; - req = rxkad_get_call_crypto(call); - if (!req) - return -ENOMEM; - - /* continue encrypting from where we left off */ - memcpy(&iv, call->conn->rxkad.csum_iv.x, sizeof(iv)); - /* validate the security checksum */ x = (call->cid & RXRPC_CHANNELMASK) << (32 - RXRPC_CIDSHIFT); x |= seq & 0x3fffffff; crypto.buf[0] = htonl(call->call_id); crypto.buf[1] = htonl(x); - sg_init_one(&sg, crypto.buf, 8); - skcipher_request_set_sync_tfm(req, call->conn->rxkad.cipher); - skcipher_request_set_callback(req, 0, NULL, NULL); - skcipher_request_set_crypt(req, &sg, &sg, 8, iv.x); - ret = crypto_skcipher_encrypt(req); - skcipher_request_zero(req); - if (ret < 0) - goto out; + /* continue encrypting from where we left off */ + fcrypt_pcbc_encrypt(call->conn->rxkad.cipher, + call->conn->rxkad.csum_iv.x, crypto.buf, crypto.buf, + 1); y = ntohl(crypto.buf[1]); cksum = (y >> 16) & 0xffff; @@ -617,18 +485,16 @@ static int rxkad_verify_packet(struct rxrpc_call *call, struct sk_buff *skb) ret = 0; break; case RXRPC_SECURITY_AUTH: - ret = rxkad_verify_packet_1(call, skb, seq, req); + ret = rxkad_verify_packet_1(call, skb, seq); break; case RXRPC_SECURITY_ENCRYPT: - ret = rxkad_verify_packet_2(call, skb, seq, req); + ret = rxkad_verify_packet_2(call, skb, seq); break; default: ret = -ENOANO; break; } - out: - skcipher_request_free(req); return ret; } @@ -712,41 +578,6 @@ static void rxkad_calc_response_checksum(struct rxkad_response *response) response->encrypted.checksum = htonl(csum); } -/* - * encrypt the response packet - */ -static int rxkad_encrypt_response(struct rxrpc_connection *conn, - struct sk_buff *response, - const struct rxkad_key *s2) -{ - struct skcipher_request *req; - struct rxrpc_crypt iv; - struct scatterlist sg[1]; - size_t encsize = sizeof(((struct rxkad_response *)0)->encrypted); - int ret; - - sg_init_table(sg, ARRAY_SIZE(sg)); - ret = skb_to_sgvec(response, sg, - sizeof(struct rxrpc_wire_header) + - offsetof(struct rxkad_response, encrypted), encsize); - if (ret < 0) - return ret; - - req = skcipher_request_alloc(&conn->rxkad.cipher->base, GFP_NOFS); - if (!req) - return -ENOMEM; - - /* continue encrypting from where we left off */ - memcpy(&iv, s2->session_key, sizeof(iv)); - - skcipher_request_set_sync_tfm(req, conn->rxkad.cipher); - skcipher_request_set_callback(req, 0, NULL, NULL); - skcipher_request_set_crypt(req, sg, sg, encsize, iv.x); - ret = crypto_skcipher_encrypt(req); - skcipher_request_free(req); - return ret; -} - /* * Validate a challenge packet. */ @@ -846,6 +677,12 @@ int rxkad_insert_response_header(struct rxrpc_connection *conn, rxkad_calc_response_checksum(&h.resp); + /* encrypt the response packet */ + static_assert(sizeof(h.resp.encrypted) % FCRYPT_BSIZE == 0); + fcrypt_pcbc_encrypt(conn->rxkad.cipher, token->kad->session_key, + &h.resp.encrypted, &h.resp.encrypted, + sizeof(h.resp.encrypted) / FCRYPT_BSIZE); + ret = skb_store_bits(response, *offset, &h, sizeof(h)); *offset += sizeof(h); return ret; @@ -890,10 +727,6 @@ static int rxkad_respond_to_challenge(struct rxrpc_connection *conn, if (ret < 0) goto error; - ret = rxkad_encrypt_response(conn, response, token->kad); - if (ret < 0) - goto error; - ret = skb_store_bits(response, offset, token->kad->ticket, token->kad->ticket_len); if (ret < 0) @@ -1072,39 +905,22 @@ static int rxkad_decrypt_ticket(struct rxrpc_connection *conn, /* * decrypt the response packet */ -static int rxkad_decrypt_response(struct rxrpc_connection *conn, - struct rxkad_response *resp, - const struct rxrpc_crypt *session_key) +static void rxkad_decrypt_response(struct rxrpc_connection *conn, + struct rxkad_response *resp, + const struct rxrpc_crypt *session_key) { - struct skcipher_request *req = rxkad_ci_req; - struct scatterlist sg[1]; - struct rxrpc_crypt iv; - int ret; + struct fcrypt_key cipher; _enter(",,%08x%08x", ntohl(session_key->n[0]), ntohl(session_key->n[1])); - mutex_lock(&rxkad_ci_mutex); - ret = crypto_sync_skcipher_setkey(rxkad_ci, session_key->x, - sizeof(*session_key)); - if (ret < 0) - goto unlock; - - memcpy(&iv, session_key, sizeof(iv)); - - sg_init_table(sg, 1); - sg_set_buf(sg, &resp->encrypted, sizeof(resp->encrypted)); - skcipher_request_set_sync_tfm(req, rxkad_ci); - skcipher_request_set_callback(req, 0, NULL, NULL); - skcipher_request_set_crypt(req, sg, sg, sizeof(resp->encrypted), iv.x); - ret = crypto_skcipher_decrypt(req); - skcipher_request_zero(req); - -unlock: - mutex_unlock(&rxkad_ci_mutex); + fcrypt_preparekey(&cipher, session_key->x); + static_assert(sizeof(resp->encrypted) % FCRYPT_BSIZE == 0); + fcrypt_pcbc_decrypt(&cipher, session_key->x, &resp->encrypted, + &resp->encrypted, + sizeof(resp->encrypted) / FCRYPT_BSIZE); _leave(""); - return ret; } /* @@ -1191,9 +1007,7 @@ static int rxkad_verify_response(struct rxrpc_connection *conn, /* use the session key from inside the ticket to decrypt the * response */ - ret = rxkad_decrypt_response(conn, response, &session_key); - if (ret < 0) - goto error; + rxkad_decrypt_response(conn, response, &session_key); if (ntohl(response->encrypted.epoch) != conn->proto.epoch || ntohl(response->encrypted.cid) != conn->proto.cid || @@ -1270,8 +1084,8 @@ static void rxkad_clear(struct rxrpc_connection *conn) { _enter(""); - if (conn->rxkad.cipher) - crypto_free_sync_skcipher(conn->rxkad.cipher); + kfree_sensitive(conn->rxkad.cipher); + conn->rxkad.cipher = NULL; } /* @@ -1279,26 +1093,11 @@ static void rxkad_clear(struct rxrpc_connection *conn) */ static int rxkad_init(void) { - struct crypto_sync_skcipher *tfm; - struct skcipher_request *req; - - /* pin the cipher we need so that the crypto layer doesn't invoke - * keventd to go get it */ - tfm = crypto_alloc_sync_skcipher("pcbc(fcrypt)", 0, 0); - if (IS_ERR(tfm)) - return PTR_ERR(tfm); - - req = skcipher_request_alloc(&tfm->base, GFP_KERNEL); - if (!req) - goto nomem_tfm; - - rxkad_ci_req = req; - rxkad_ci = tfm; + if (fips_enabled) { + pr_warn("rxkad support is disabled due to FIPS\n"); + return -ENOENT; + } return 0; - -nomem_tfm: - crypto_free_sync_skcipher(tfm); - return -ENOMEM; } /* @@ -1306,8 +1105,6 @@ nomem_tfm: */ static void rxkad_exit(void) { - crypto_free_sync_skcipher(rxkad_ci); - skcipher_request_free(rxkad_ci_req); } /*