@@ -201,6 +201,10 @@ struct wpa_eapol_key {
#define FILS_ICK_MAX_LEN 48
#define FILS_FT_MAX_LEN 48
+#define KEY_FLAG_DEFAULT_KEY BIT(0)
+#define KEY_FLAG_RX_ONLY BIT(1)
+#define KEY_FLAG_TX BIT(2)
+
/**
* struct wpa_ptk - WPA Pairwise Transient Key
* IEEE Std 802.11i-2004 - 8.5.1.2 Pairwise key hierarchy
@@ -1579,6 +1579,8 @@ struct wpa_driver_capa {
#define WPA_DRIVER_FLAGS_MFP_OPTIONAL 0x0040000000000000ULL
/** Driver is a self-managed regulatory device */
#define WPA_DRIVER_FLAGS_SELF_MANAGED_REGULATORY 0x0080000000000000ULL
+/** Driver supports Extended Key ID */
+#define WPA_DRIVER_FLAGS_EXTENDED_KEY_ID 0x0100000000000000ULL
u64 flags;
#define FULL_AP_CLIENT_STATE_SUPP(drv_flags) \
@@ -2169,8 +2171,20 @@ struct wpa_driver_ops {
* specified key index is to be cleared
* @key_idx: key index (0..3), usually 0 for unicast keys; 0..4095 for
* IGTK
- * @set_tx: configure this key as the default Tx key (only used when
- * driver does not support separate unicast/individual key
+ * @key_flag: Additional flag for key install.
+ * Can be zero or one of the following:
+ * %KEY_FLAG_DEFAULT_KEY:
+ * configure this key as the default Tx key (only used when
+ * driver does not support separate unicast/individual keys)
+ * %KEY_FLAG_RX_ONLY:
+ * Install the unicast key in driver for only Rx.
+ * Can only be used when driver has set
+ * %WPA_DRIVER_FLAGS_EXTENDED_KEY_ID
+ * %KEY_FLAG_TX:
+ * Activate key_idx for addr for Tx (Key must previously have
+ * been installed with %KEY_FLAG_RX_ONLY flag set.)
+ * only @ifname, @priv, @addr and @key_idx are required when
+ * this flag is set.
* @seq: sequence number/packet number, seq_len octets, the next
* packet number to be used for in replay protection; configured
* for Rx keys (in most cases, this is only used with broadcast
@@ -2203,7 +2217,7 @@ struct wpa_driver_ops {
* example on how this can be done.
*/
int (*set_key)(const char *ifname, void *priv, enum wpa_alg alg,
- const u8 *addr, int key_idx, int set_tx,
+ const u8 *addr, int key_idx, int key_flag,
const u8 *seq, size_t seq_len,
const u8 *key, size_t key_len);
@@ -499,7 +499,7 @@ atheros_del_key(void *priv, const u8 *addr, int key_idx)
static int
atheros_set_key(const char *ifname, void *priv, enum wpa_alg alg,
- const u8 *addr, int key_idx, int set_tx, const u8 *seq,
+ const u8 *addr, int key_idx, int key_flag, const u8 *seq,
size_t seq_len, const u8 *key, size_t key_len)
{
struct atheros_driver_data *drv = priv;
@@ -568,7 +568,7 @@ atheros_set_key(const char *ifname, void *priv, enum wpa_alg alg,
if (addr == NULL || is_broadcast_ether_addr(addr)) {
os_memset(wk.ik_macaddr, 0xff, IEEE80211_ADDR_LEN);
wk.ik_keyix = key_idx;
- if (set_tx)
+ if (key_flag & KEY_FLAG_DEFAULT_KEY)
wk.ik_flags |= IEEE80211_KEY_DEFAULT;
} else {
os_memcpy(wk.ik_macaddr, addr, IEEE80211_ADDR_LEN);
@@ -580,9 +580,9 @@ atheros_set_key(const char *ifname, void *priv, enum wpa_alg alg,
ret = set80211priv(drv, IEEE80211_IOCTL_SETKEY, &wk, sizeof(wk));
if (ret < 0) {
wpa_printf(MSG_DEBUG, "%s: Failed to set key (addr %s"
- " key_idx %d alg %d key_len %lu set_tx %d)",
+ " key_idx %d alg %d key_len %lu key_flag %d)",
__func__, ether_sprintf(wk.ik_macaddr), key_idx,
- alg, (unsigned long) key_len, set_tx);
+ alg, (unsigned long) key_len, key_flag);
}
return ret;
@@ -332,7 +332,7 @@ bsd_ctrl_iface(void *priv, int enable)
static int
bsd_set_key(const char *ifname, void *priv, enum wpa_alg alg,
- const unsigned char *addr, int key_idx, int set_tx, const u8 *seq,
+ const unsigned char *addr, int key_idx, int key_flag, const u8 *seq,
size_t seq_len, const u8 *key, size_t key_len)
{
struct ieee80211req_key wk;
@@ -340,9 +340,9 @@ bsd_set_key(const char *ifname, void *priv, enum wpa_alg alg,
struct bsd_driver_data *drv = priv;
#endif /* IEEE80211_KEY_NOREPLAY */
- wpa_printf(MSG_DEBUG, "%s: alg=%d addr=%p key_idx=%d set_tx=%d "
+ wpa_printf(MSG_DEBUG, "%s: alg=%d addr=%p key_idx=%d key_flag=%d "
"seq_len=%zu key_len=%zu", __func__, alg, addr, key_idx,
- set_tx, seq_len, key_len);
+ key_flag, seq_len, key_len);
if (alg == WPA_ALG_NONE) {
#ifndef HOSTAPD
@@ -370,7 +370,7 @@ bsd_set_key(const char *ifname, void *priv, enum wpa_alg alg,
}
wk.ik_flags = IEEE80211_KEY_RECV;
- if (set_tx)
+ if (key_flag & KEY_FLAG_DEFAULT_KEY)
wk.ik_flags |= IEEE80211_KEY_XMIT;
if (addr == NULL) {
@@ -391,7 +391,7 @@ bsd_set_key(const char *ifname, void *priv, enum wpa_alg alg,
key_idx;
}
}
- if (wk.ik_keyix != IEEE80211_KEYIX_NONE && set_tx)
+ if (wk.ik_keyix != IEEE80211_KEYIX_NONE && key_flag & KEY_FLAG_DEFAULT_KEY)
wk.ik_flags |= IEEE80211_KEY_DEFAULT;
#ifndef HOSTAPD
#ifdef IEEE80211_KEY_NOREPLAY
@@ -390,7 +390,7 @@ static int hostapd_ioctl(void *priv, struct prism2_hostapd_param *param,
static int wpa_driver_hostap_set_key(const char *ifname, void *priv,
enum wpa_alg alg, const u8 *addr,
- int key_idx, int set_tx,
+ int key_idx, int key_flag,
const u8 *seq, size_t seq_len,
const u8 *key, size_t key_len)
{
@@ -432,7 +432,8 @@ static int wpa_driver_hostap_set_key(const char *ifname, void *priv,
os_free(buf);
return -1;
}
- param->u.crypt.flags = set_tx ? HOSTAP_CRYPT_FLAG_SET_TX_KEY : 0;
+ param->u.crypt.flags = key_flag & KEY_FLAG_DEFAULT_KEY ?
+ HOSTAP_CRYPT_FLAG_SET_TX_KEY : 0;
param->u.crypt.idx = key_idx;
param->u.crypt.key_len = key_len;
memcpy((u8 *) (param + 1), key, key_len);
@@ -931,7 +931,7 @@ static int wpa_driver_ndis_remove_key(struct wpa_driver_ndis_data *drv,
static int wpa_driver_ndis_add_wep(struct wpa_driver_ndis_data *drv,
- int pairwise, int key_idx, int set_tx,
+ int pairwise, int key_idx, int key_flag,
const u8 *key, size_t key_len)
{
NDIS_802_11_WEP *wep;
@@ -944,7 +944,7 @@ static int wpa_driver_ndis_add_wep(struct wpa_driver_ndis_data *drv,
return -1;
wep->Length = len;
wep->KeyIndex = key_idx;
- if (set_tx)
+ if (key_flag & KEY_FLAG_DEFAULT_KEY)
wep->KeyIndex |= 1 << 31;
#if 0 /* Setting bit30 does not seem to work with some NDIS drivers */
if (pairwise)
@@ -965,7 +965,7 @@ static int wpa_driver_ndis_add_wep(struct wpa_driver_ndis_data *drv,
static int wpa_driver_ndis_set_key(const char *ifname, void *priv,
enum wpa_alg alg, const u8 *addr,
- int key_idx, int set_tx,
+ int key_idx, int key_flag,
const u8 *seq, size_t seq_len,
const u8 *key, size_t key_len)
{
@@ -992,7 +992,7 @@ static int wpa_driver_ndis_set_key(const char *ifname, void *priv,
}
if (alg == WPA_ALG_WEP) {
- return wpa_driver_ndis_add_wep(drv, pairwise, key_idx, set_tx,
+ return wpa_driver_ndis_add_wep(drv, pairwise, key_idx, key_flag,
key, key_len);
}
@@ -1004,7 +1004,7 @@ static int wpa_driver_ndis_set_key(const char *ifname, void *priv,
nkey->Length = len;
nkey->KeyIndex = key_idx;
- if (set_tx)
+ if (key_flag & KEY_FLAG_DEFAULT_KEY)
nkey->KeyIndex |= 1 << 31;
if (pairwise)
nkey->KeyIndex |= 1 << 30;
@@ -2925,7 +2925,7 @@ static int nl80211_set_pmk(struct wpa_driver_nl80211_data *drv,
static int wpa_driver_nl80211_set_key(const char *ifname, struct i802_bss *bss,
enum wpa_alg alg, const u8 *addr,
- int key_idx, int set_tx,
+ int key_idx, int key_flag,
const u8 *seq, size_t seq_len,
const u8 *key, size_t key_len)
{
@@ -2941,8 +2941,8 @@ static int wpa_driver_nl80211_set_key(const char *ifname, struct i802_bss *bss,
ifindex = if_nametoindex(ifname);
wpa_printf(MSG_DEBUG, "%s: ifindex=%d (%s) alg=%d addr=%p key_idx=%d "
- "set_tx=%d seq_len=%lu key_len=%lu",
- __func__, ifindex, ifname, alg, addr, key_idx, set_tx,
+ "key_flag=%d seq_len=%lu key_len=%lu",
+ __func__, ifindex, ifname, alg, addr, key_idx, key_flag,
(unsigned long) seq_len, (unsigned long) key_len);
#ifdef CONFIG_TDLS
if (key_idx == -1) {
@@ -2965,7 +2965,13 @@ static int wpa_driver_nl80211_set_key(const char *ifname, struct i802_bss *bss,
(drv->capa.flags & WPA_DRIVER_FLAGS_4WAY_HANDSHAKE))
return nl80211_set_pmk(drv, key, key_len, addr);
- if (alg == WPA_ALG_NONE) {
+ if (key_flag & KEY_FLAG_TX && !key) {
+ wpa_printf(MSG_DEBUG, "Extended Key ID: Activate keyid=%d "
+ "for TX to addr=%p", key_idx, addr);
+ msg = nl80211_ifindex_msg(drv, ifindex, 0, NL80211_CMD_SET_KEY);
+ if (!msg)
+ return -ENOBUFS;
+ } else if (alg == WPA_ALG_NONE) {
msg = nl80211_ifindex_msg(drv, ifindex, 0, NL80211_CMD_DEL_KEY);
if (!msg)
return -ENOBUFS;
@@ -2994,7 +3000,15 @@ static int wpa_driver_nl80211_set_key(const char *ifname, struct i802_bss *bss,
if (nla_put(msg, NL80211_ATTR_MAC, ETH_ALEN, addr))
goto fail;
- if (alg != WPA_ALG_WEP && key_idx && !set_tx) {
+ if (key_flag & (KEY_FLAG_RX_ONLY | KEY_FLAG_TX)) {
+ wpa_printf(MSG_DEBUG, " Extended Key ID action: %d", key_flag);
+ if (nla_put_flag(msg,
+ key_flag & KEY_FLAG_RX_ONLY ?
+ NL80211_ATTR_KEY_RXONLY :
+ NL80211_ATTR_KEY_SETTX))
+ goto fail;
+ } else if (alg != WPA_ALG_WEP && key_idx &&
+ !(key_flag & KEY_FLAG_DEFAULT_KEY)) {
wpa_printf(MSG_DEBUG, " RSN IBSS RX GTK");
if (nla_put_u32(msg, NL80211_ATTR_KEY_TYPE,
NL80211_KEYTYPE_GROUP))
@@ -3025,7 +3039,7 @@ static int wpa_driver_nl80211_set_key(const char *ifname, struct i802_bss *bss,
* If we failed or don't need to set the default TX key (below),
* we're done here.
*/
- if (ret || !set_tx || alg == WPA_ALG_NONE || tdls)
+ if (ret || !(key_flag & KEY_FLAG_DEFAULT_KEY) || alg == WPA_ALG_NONE || tdls)
return ret;
if (is_ap_interface(drv->nlmode) && addr &&
!is_broadcast_ether_addr(addr))
@@ -8382,13 +8396,13 @@ nl80211_tdls_disable_channel_switch(void *priv, const u8 *addr)
static int driver_nl80211_set_key(const char *ifname, void *priv,
enum wpa_alg alg, const u8 *addr,
- int key_idx, int set_tx,
+ int key_idx, int key_flag,
const u8 *seq, size_t seq_len,
const u8 *key, size_t key_len)
{
struct i802_bss *bss = priv;
return wpa_driver_nl80211_set_key(ifname, bss, alg, addr, key_idx,
- set_tx, seq, seq_len, key, key_len);
+ key_flag, seq, seq_len, key, key_len);
}
@@ -416,6 +416,10 @@ static void wiphy_info_ext_feature_flags(struct wiphy_info_data *info,
NL80211_EXT_FEATURE_DFS_OFFLOAD))
capa->flags |= WPA_DRIVER_FLAGS_DFS_OFFLOAD;
+ if (ext_feature_isset(ext_features, len,
+ NL80211_EXT_FEATURE_EXT_KEY_ID))
+ capa->flags |= WPA_DRIVER_FLAGS_EXTENDED_KEY_ID;
+
#ifdef CONFIG_MBO
if (ext_feature_isset(ext_features, len,
NL80211_EXT_FEATURE_FILS_MAX_CHANNEL_TIME) &&
@@ -69,7 +69,7 @@ wpa_driver_openbsd_get_capa(void *priv, struct wpa_driver_capa *capa)
static int
wpa_driver_openbsd_set_key(const char *ifname, void *priv, enum wpa_alg alg,
- const unsigned char *addr, int key_idx, int set_tx, const u8 *seq,
+ const unsigned char *addr, int key_idx, int key_flag, const u8 *seq,
size_t seq_len, const u8 *key, size_t key_len)
{
struct openbsd_driver_data *drv = priv;
@@ -207,15 +207,15 @@ wpa_driver_privsep_get_scan_results2(void *priv)
static int wpa_driver_privsep_set_key(const char *ifname, void *priv,
enum wpa_alg alg, const u8 *addr,
- int key_idx, int set_tx,
+ int key_idx, int key_flag,
const u8 *seq, size_t seq_len,
const u8 *key, size_t key_len)
{
struct wpa_driver_privsep_data *drv = priv;
struct privsep_cmd_set_key cmd;
- wpa_printf(MSG_DEBUG, "%s: priv=%p alg=%d key_idx=%d set_tx=%d",
- __func__, priv, alg, key_idx, set_tx);
+ wpa_printf(MSG_DEBUG, "%s: priv=%p alg=%d key_idx=%d key_flag=%d",
+ __func__, priv, alg, key_idx, key_flag);
os_memset(&cmd, 0, sizeof(cmd));
cmd.alg = alg;
@@ -224,7 +224,7 @@ static int wpa_driver_privsep_set_key(const char *ifname, void *priv,
else
os_memset(cmd.addr, 0xff, ETH_ALEN);
cmd.key_idx = key_idx;
- cmd.set_tx = set_tx;
+ cmd.set_tx = key_flag & KEY_FLAG_DEFAULT_KEY;
if (seq && seq_len > 0 && seq_len < sizeof(cmd.seq)) {
os_memcpy(cmd.seq, seq, seq_len);
cmd.seq_len = seq_len;
@@ -1707,7 +1707,7 @@ static int wpa_driver_wext_set_psk(struct wpa_driver_wext_data *drv,
static int wpa_driver_wext_set_key_ext(void *priv, enum wpa_alg alg,
const u8 *addr, int key_idx,
- int set_tx, const u8 *seq,
+ int key_flag, const u8 *seq,
size_t seq_len,
const u8 *key, size_t key_len)
{
@@ -1736,7 +1736,7 @@ static int wpa_driver_wext_set_key_ext(void *priv, enum wpa_alg alg,
if (addr == NULL || is_broadcast_ether_addr(addr))
ext->ext_flags |= IW_ENCODE_EXT_GROUP_KEY;
- if (set_tx)
+ if (key_flag & KEY_FLAG_DEFAULT_KEY)
ext->ext_flags |= IW_ENCODE_EXT_SET_TX_KEY;
ext->addr.sa_family = ARPHRD_ETHER;
@@ -1808,7 +1808,8 @@ static int wpa_driver_wext_set_key_ext(void *priv, enum wpa_alg alg,
* @addr: Address of the peer STA or ff:ff:ff:ff:ff:ff for
* broadcast/default keys
* @key_idx: key index (0..3), usually 0 for unicast keys
- * @set_tx: Configure this key as the default Tx key (only used when
+ * @key_flag: %KEY_FLAG_DEFAULT_KEY (Other flags not supported)
+ * Configure this key as the default Tx key (only used when
* driver does not support separate unicast/individual key
* @seq: Sequence number/packet number, seq_len octets, the next
* packet number to be used for in replay protection; configured
@@ -1827,19 +1828,19 @@ static int wpa_driver_wext_set_key_ext(void *priv, enum wpa_alg alg,
*/
int wpa_driver_wext_set_key(const char *ifname, void *priv, enum wpa_alg alg,
const u8 *addr, int key_idx,
- int set_tx, const u8 *seq, size_t seq_len,
+ int key_flag, const u8 *seq, size_t seq_len,
const u8 *key, size_t key_len)
{
struct wpa_driver_wext_data *drv = priv;
struct iwreq iwr;
int ret = 0;
- wpa_printf(MSG_DEBUG, "%s: alg=%d key_idx=%d set_tx=%d seq_len=%lu "
+ wpa_printf(MSG_DEBUG, "%s: alg=%d key_idx=%d key_flag=%d seq_len=%lu "
"key_len=%lu",
- __FUNCTION__, alg, key_idx, set_tx,
+ __FUNCTION__, alg, key_idx, key_flag,
(unsigned long) seq_len, (unsigned long) key_len);
- ret = wpa_driver_wext_set_key_ext(drv, alg, addr, key_idx, set_tx,
+ ret = wpa_driver_wext_set_key_ext(drv, alg, addr, key_idx, key_flag,
seq, seq_len, key, key_len);
if (ret == 0)
return 0;
@@ -1870,7 +1871,7 @@ int wpa_driver_wext_set_key(const char *ifname, void *priv, enum wpa_alg alg,
ret = -1;
}
- if (set_tx && alg != WPA_ALG_NONE) {
+ if (key_flag & KEY_FLAG_DEFAULT_KEY && alg != WPA_ALG_NONE) {
os_memset(&iwr, 0, sizeof(iwr));
os_strlcpy(iwr.ifr_name, drv->ifname, IFNAMSIZ);
iwr.u.encoding.flags = key_idx + 1;
@@ -1879,7 +1880,7 @@ int wpa_driver_wext_set_key(const char *ifname, void *priv, enum wpa_alg alg,
iwr.u.encoding.length = 0;
if (ioctl(drv->ioctl_sock, SIOCSIWENCODE, &iwr) < 0) {
wpa_printf(MSG_ERROR,
- "ioctl[SIOCSIWENCODE] (set_tx): %s",
+ "ioctl[SIOCSIWENCODE] (DEFAULT_KEY): %s",
strerror(errno));
ret = -1;
}
@@ -1033,6 +1033,9 @@
* %NL80211_ATTR_CHANNEL_WIDTH,%NL80211_ATTR_NSS attributes with its
* address(specified in %NL80211_ATTR_MAC).
*
+ * @NL80211_CMD_GET_FTM_RESPONDER_STATS: Retrieve FTM responder statistics, in
+ * the %NL80211_ATTR_FTM_RESPONDER_STATS attribute.
+ *
* @NL80211_CMD_MAX: highest used command number
* @__NL80211_CMD_AFTER_LAST: internal use
*/
@@ -1245,6 +1248,8 @@ enum nl80211_commands {
NL80211_CMD_CONTROL_PORT_FRAME,
+ NL80211_CMD_GET_FTM_RESPONDER_STATS,
+
/* add new commands above here */
/* used to define NL80211_CMD_MAX below */
@@ -2241,6 +2246,22 @@ enum nl80211_commands {
* association request when used with NL80211_CMD_NEW_STATION). Can be set
* only if %NL80211_STA_FLAG_WME is set.
*
+ * @NL80211_ATTR_FTM_RESPONDER: nested attribute which user-space can include
+ * in %NL80211_CMD_START_AP or %NL80211_CMD_SET_BEACON for fine timing
+ * measurement (FTM) responder functionality and containing parameters as
+ * possible, see &enum nl80211_ftm_responder_attr
+ *
+ * @NL80211_ATTR_FTM_RESPONDER_STATS: Nested attribute with FTM responder
+ * statistics, see &enum nl80211_ftm_responder_stats.
+ *
+ * @NL80211_ATTR_KEY_RXONLY: Flag attribute to request RX key install only for
+ * a pairwise key. Only supported for keyid's 0 and 1 when driver is
+ * supporting Extended Key ID.
+ *
+ * @NL80211_ATTR_KEY_SETTX: Flag attribute to switch TX to a specified keyid.
+ * Only supported for keyid's 0 and 1 when driver is supporting Extended
+ * Key ID.
+ *
* @NUM_NL80211_ATTR: total number of nl80211_attrs available
* @NL80211_ATTR_MAX: highest attribute number currently defined
* @__NL80211_ATTR_AFTER_LAST: internal use
@@ -2682,6 +2703,13 @@ enum nl80211_attrs {
NL80211_ATTR_HE_CAPABILITY,
+ NL80211_ATTR_FTM_RESPONDER,
+
+ NL80211_ATTR_FTM_RESPONDER_STATS,
+
+ NL80211_ATTR_KEY_RXONLY,
+ NL80211_ATTR_KEY_SETTX,
+
/* add attributes here, update the policy in nl80211.c */
__NL80211_ATTR_AFTER_LAST,
@@ -3051,6 +3079,12 @@ enum nl80211_sta_bss_param {
* @NL80211_STA_INFO_PAD: attribute used for padding for 64-bit alignment
* @NL80211_STA_INFO_ACK_SIGNAL: signal strength of the last ACK frame(u8, dBm)
* @NL80211_STA_INFO_ACK_SIGNAL_AVG: avg signal strength of ACK frames (s8, dBm)
+ * @NL80211_STA_INFO_RX_MPDUS: total number of received packets (MPDUs)
+ * (u32, from this station)
+ * @NL80211_STA_INFO_FCS_ERROR_COUNT: total number of packets (MPDUs) received
+ * with an FCS error (u32, from this station). This count may not include
+ * some packets with an FCS error due to TA corruption. Hence this counter
+ * might not be fully accurate.
* @__NL80211_STA_INFO_AFTER_LAST: internal
* @NL80211_STA_INFO_MAX: highest possible station info attribute
*/
@@ -3091,6 +3125,8 @@ enum nl80211_sta_info {
NL80211_STA_INFO_PAD,
NL80211_STA_INFO_ACK_SIGNAL,
NL80211_STA_INFO_ACK_SIGNAL_AVG,
+ NL80211_STA_INFO_RX_MPDUS,
+ NL80211_STA_INFO_FCS_ERROR_COUNT,
/* keep last */
__NL80211_STA_INFO_AFTER_LAST,
@@ -4031,6 +4067,22 @@ enum nl80211_channel_type {
NL80211_CHAN_HT40PLUS
};
+/**
+ * enum key_params_flag - additional key flag for drivers
+ *
+ * Actions other than @NL80211_KEY_DEFAULT_RX_TX are only required from drivers
+ * supporting Extended Key ID for pairwise keys using keyid 0 or 1.
+ *
+ * @NL80211_KEY_DEFAULT_RX_TX: key can be immediately used for Rx and Tx
+ * @NL80211_KEY_RX_ONLY: key must be installed for Rx only
+ * @NL80211_KEY_SET_TX: switch Tx for sta to specified keyid
+ */
+enum key_params_flag {
+ NL80211_KEY_DEFAULT_RX_TX,
+ NL80211_KEY_RX_ONLY,
+ NL80211_KEY_SET_TX
+};
+
/**
* enum nl80211_chan_width - channel width definitions
*
@@ -4274,6 +4326,10 @@ enum nl80211_key_default_types {
* @NL80211_KEY_DEFAULT_TYPES: A nested attribute containing flags
* attributes, specifying what a key should be set as default as.
* See &enum nl80211_key_default_types.
+ * @NL80211_KEY_RXONLY: Flag attribute to request RX key install only for
+ * a pairwise key.
+ * @NL80211_KEY_SETTX: Flag attribute to switch TX to a selected key.
+ *
* @__NL80211_KEY_AFTER_LAST: internal
* @NL80211_KEY_MAX: highest key attribute
*/
@@ -4287,6 +4343,8 @@ enum nl80211_key_attributes {
NL80211_KEY_DEFAULT_MGMT,
NL80211_KEY_TYPE,
NL80211_KEY_DEFAULT_TYPES,
+ NL80211_KEY_RXONLY,
+ NL80211_KEY_SETTX,
/* keep last */
__NL80211_KEY_AFTER_LAST,
@@ -5225,6 +5283,14 @@ enum nl80211_feature_flags {
* @NL80211_EXT_FEATURE_SCAN_MIN_PREQ_CONTENT: Driver/device can omit all data
* except for supported rates from the probe request content if requested
* by the %NL80211_SCAN_FLAG_MIN_PREQ_CONTENT flag.
+ * @NL80211_EXT_FEATURE_CAN_REPLACE_PTK0: Driver/device confirm that they are
+ * able to rekey an in-use key correctly. Userspace must not rekey PTK keys
+ * if this flag is not set. Ignoring this can leak clear text packets and/or
+ * freeze the connection.
+ * @NL80211_EXT_FEATURE_ENABLE_FTM_RESPONDER: Driver supports enabling fine
+ * timing measurement responder role.
+ * @NL80211_EXT_FEATURE_EXT_KEY_ID: Driver supports "Extended Key ID for
+ * Individually Addressed Frames" from IEEE802.11-2016.
*
* @NUM_NL80211_EXT_FEATURES: number of extended features.
* @MAX_NL80211_EXT_FEATURES: highest extended feature index.
@@ -5263,6 +5329,9 @@ enum nl80211_ext_feature_index {
NL80211_EXT_FEATURE_TXQS,
NL80211_EXT_FEATURE_SCAN_RANDOM_SN,
NL80211_EXT_FEATURE_SCAN_MIN_PREQ_CONTENT,
+ NL80211_EXT_FEATURE_CAN_REPLACE_PTK0,
+ NL80211_EXT_FEATURE_ENABLE_FTM_RESPONDER,
+ NL80211_EXT_FEATURE_EXT_KEY_ID,
/* add new features before the definition below */
NUM_NL80211_EXT_FEATURES,
@@ -5802,4 +5871,74 @@ enum nl80211_external_auth_action {
NL80211_EXTERNAL_AUTH_ABORT,
};
+/**
+ * enum nl80211_ftm_responder_attributes - fine timing measurement
+ * responder attributes
+ * @__NL80211_FTM_RESP_ATTR_INVALID: Invalid
+ * @NL80211_FTM_RESP_ATTR_ENABLED: FTM responder is enabled
+ * @NL80211_FTM_RESP_ATTR_LCI: The content of Measurement Report Element
+ * (9.4.2.22 in 802.11-2016) with type 8 - LCI (9.4.2.22.10)
+ * @NL80211_FTM_RESP_ATTR_CIVIC: The content of Measurement Report Element
+ * (9.4.2.22 in 802.11-2016) with type 11 - Civic (Section 9.4.2.22.13)
+ * @__NL80211_FTM_RESP_ATTR_LAST: Internal
+ * @NL80211_FTM_RESP_ATTR_MAX: highest FTM responder attribute.
+ */
+enum nl80211_ftm_responder_attributes {
+ __NL80211_FTM_RESP_ATTR_INVALID,
+
+ NL80211_FTM_RESP_ATTR_ENABLED,
+ NL80211_FTM_RESP_ATTR_LCI,
+ NL80211_FTM_RESP_ATTR_CIVICLOC,
+
+ /* keep last */
+ __NL80211_FTM_RESP_ATTR_LAST,
+ NL80211_FTM_RESP_ATTR_MAX = __NL80211_FTM_RESP_ATTR_LAST - 1,
+};
+
+/*
+ * enum nl80211_ftm_responder_stats - FTM responder statistics
+ *
+ * These attribute types are used with %NL80211_ATTR_FTM_RESPONDER_STATS
+ * when getting FTM responder statistics.
+ *
+ * @__NL80211_FTM_STATS_INVALID: attribute number 0 is reserved
+ * @NL80211_FTM_STATS_SUCCESS_NUM: number of FTM sessions in which all frames
+ * were ssfully answered (u32)
+ * @NL80211_FTM_STATS_PARTIAL_NUM: number of FTM sessions in which part of the
+ * frames were successfully answered (u32)
+ * @NL80211_FTM_STATS_FAILED_NUM: number of failed FTM sessions (u32)
+ * @NL80211_FTM_STATS_ASAP_NUM: number of ASAP sessions (u32)
+ * @NL80211_FTM_STATS_NON_ASAP_NUM: number of non-ASAP sessions (u32)
+ * @NL80211_FTM_STATS_TOTAL_DURATION_MSEC: total sessions durations - gives an
+ * indication of how much time the responder was busy (u64, msec)
+ * @NL80211_FTM_STATS_UNKNOWN_TRIGGERS_NUM: number of unknown FTM triggers -
+ * triggers from initiators that didn't finish successfully the negotiation
+ * phase with the responder (u32)
+ * @NL80211_FTM_STATS_RESCHEDULE_REQUESTS_NUM: number of FTM reschedule requests
+ * - initiator asks for a new scheduling although it already has scheduled
+ * FTM slot (u32)
+ * @NL80211_FTM_STATS_OUT_OF_WINDOW_TRIGGERS_NUM: number of FTM triggers out of
+ * scheduled window (u32)
+ * @NL80211_FTM_STATS_PAD: used for padding, ignore
+ * @__NL80211_TXQ_ATTR_AFTER_LAST: Internal
+ * @NL80211_FTM_STATS_MAX: highest possible FTM responder stats attribute
+ */
+enum nl80211_ftm_responder_stats {
+ __NL80211_FTM_STATS_INVALID,
+ NL80211_FTM_STATS_SUCCESS_NUM,
+ NL80211_FTM_STATS_PARTIAL_NUM,
+ NL80211_FTM_STATS_FAILED_NUM,
+ NL80211_FTM_STATS_ASAP_NUM,
+ NL80211_FTM_STATS_NON_ASAP_NUM,
+ NL80211_FTM_STATS_TOTAL_DURATION_MSEC,
+ NL80211_FTM_STATS_UNKNOWN_TRIGGERS_NUM,
+ NL80211_FTM_STATS_RESCHEDULE_REQUESTS_NUM,
+ NL80211_FTM_STATS_OUT_OF_WINDOW_TRIGGERS_NUM,
+ NL80211_FTM_STATS_PAD,
+
+ /* keep last */
+ __NL80211_FTM_STATS_AFTER_LAST,
+ NL80211_FTM_STATS_MAX = __NL80211_FTM_STATS_AFTER_LAST - 1
+};
+
#endif /* __LINUX_NL80211_H */