git: 1751bf9e58dd - main - net80211: fail setting a key if the cipher isn't HW/SW supported
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Tue, 08 Apr 2025 01:35:29 UTC
The branch main has been updated by adrian:
URL: https://cgit.FreeBSD.org/src/commit/?id=1751bf9e58ddc41f3cde013ebe7cc6bcfc17eb56
commit 1751bf9e58ddc41f3cde013ebe7cc6bcfc17eb56
Author: Adrian Chadd <adrian@FreeBSD.org>
AuthorDate: 2025-03-17 03:16:06 +0000
Commit: Adrian Chadd <adrian@FreeBSD.org>
CommitDate: 2025-04-08 01:35:22 +0000
net80211: fail setting a key if the cipher isn't HW/SW supported
The key alloc path was checking if the key was supported in hardware
but treated /all/ keys as supported in software. As I discovered
during my ath10k port, not all NICs that support ciphers in hardware
support enough of an 802.11 frame transmit/receive path to actually
handle software encryption.
So, do a second check after the hardware encryption check to see
if it's in the software list and hard fail it if it isn't in there.
Otherwise a fun failure mode occurs - the frames are marked as
protected, but since there's no GCMP support setup/enabled, they
just get marked as "protected" but they don't go through the
encryption path, and the receiver dutifully tosses them as invalid.
I've verified this by trying to use GCMP in wpa_supplicant with
a NIC that doesn't announce GCMP HW/SW encryption, and now it actually
fails.
Differential Revision: https://reviews.freebsd.org/D49393
Reviewed by: bz
---
sys/net80211/ieee80211_crypto.c | 15 +++++++++++++++
sys/net80211/ieee80211_ioctl.h | 1 +
2 files changed, 16 insertions(+)
diff --git a/sys/net80211/ieee80211_crypto.c b/sys/net80211/ieee80211_crypto.c
index 84cf1d02e408..6b636da9fa2c 100644
--- a/sys/net80211/ieee80211_crypto.c
+++ b/sys/net80211/ieee80211_crypto.c
@@ -397,6 +397,21 @@ ieee80211_crypto_newkey(struct ieee80211vap *vap,
__func__, cip->ic_name);
flags |= IEEE80211_KEY_SWCRYPT;
}
+ /*
+ * Check if the software cipher is available; if not then
+ * fail it early.
+ *
+ * Some devices do not support all ciphers in software
+ * (for example they don't support a "raw" data path.)
+ */
+ if ((flags & IEEE80211_KEY_SWCRYPT) &&
+ (ic->ic_sw_cryptocaps & (1<<cipher)) == 0) {
+ IEEE80211_DPRINTF(vap, IEEE80211_MSG_CRYPTO,
+ "%s: no s/w support for cipher %s, rejecting\n",
+ __func__, cip->ic_name);
+ vap->iv_stats.is_crypto_swcipherfail++;
+ return (0);
+ }
/*
* Hardware TKIP with software MIC is an important
* combination; we handle it by flagging each key,
diff --git a/sys/net80211/ieee80211_ioctl.h b/sys/net80211/ieee80211_ioctl.h
index 6064f586c923..d542d75312b9 100644
--- a/sys/net80211/ieee80211_ioctl.h
+++ b/sys/net80211/ieee80211_ioctl.h
@@ -259,6 +259,7 @@ struct ieee80211_stats {
uint32_t is_rx_gcmpmic; /* rx MIC check failed (GCMP) */
uint32_t is_crypto_gcmp_nomem; /* gcmp crypto failed; no mem */
uint32_t is_crypto_gcmp_nospc; /* gcmp crypto failed; no mbuf space */
+ uint32_t is_crypto_swcipherfail; /* no support for SW cipher */
uint32_t is_spare[5];
};