summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/net/cfg80211.h6
-rw-r--r--include/uapi/linux/nl80211.h10
-rw-r--r--net/wireless/nl80211.c12
-rw-r--r--net/wireless/pmsr.c21
4 files changed, 47 insertions, 2 deletions
diff --git a/include/net/cfg80211.h b/include/net/cfg80211.h
index 87e848750339..f5a47a0c7532 100644
--- a/include/net/cfg80211.h
+++ b/include/net/cfg80211.h
@@ -6053,6 +6053,10 @@ cfg80211_get_iftype_ext_capa(struct wiphy *wiphy, enum nl80211_iftype type);
* @ftm.concurrent_ista_rsta_support: indicates if the device can
* simultaneously act as initiator and responder in a multi-peer
* measurement request. Only valid if @ftm.rsta_support is set.
+ * @ftm.pd_preambles: bitmap of preambles supported (&enum nl80211_preamble)
+ * for PD ranging requests. Ignored if @ftm.type.pd_support is not set.
+ * @ftm.pd_bandwidths: bitmap of bandwidths supported (&enum nl80211_chan_width)
+ * for PD ranging requests. Ignored if @ftm.type.pd_support is not set.
*/
struct cfg80211_pmsr_capabilities {
unsigned int max_peers;
@@ -6099,6 +6103,8 @@ struct cfg80211_pmsr_capabilities {
pd_support:1;
} type;
u8 concurrent_ista_rsta_support:1;
+ u32 pd_preambles;
+ u32 pd_bandwidths;
} ftm;
};
diff --git a/include/uapi/linux/nl80211.h b/include/uapi/linux/nl80211.h
index 02fe42b4f29c..5bef8fd25270 100644
--- a/include/uapi/linux/nl80211.h
+++ b/include/uapi/linux/nl80211.h
@@ -8189,6 +8189,14 @@ enum nl80211_peer_measurement_attrs {
* to estimate the burst period to be given in the FTM request for the
* NTB ranging case. If non-zero, this value will be used to validate
* the nominal time in the FTM request.
+ * @NL80211_PMSR_FTM_CAPA_ATTR_PD_PREAMBLES: u32 bitmap of values from
+ * &enum nl80211_preamble indicating the supported preambles for PD
+ * ranging requests. Only valid if %NL80211_PMSR_FTM_TYPE_CAPA_ATTR_PD_SUPPORT
+ * is set.
+ * @NL80211_PMSR_FTM_CAPA_ATTR_PD_BANDWIDTHS: u32 bitmap of values from
+ * &enum nl80211_chan_width indicating the supported channel bandwidths
+ * for PD ranging requests. Only valid if
+ * %NL80211_PMSR_FTM_TYPE_CAPA_ATTR_PD_SUPPORT is set.
*
* @NUM_NL80211_PMSR_FTM_CAPA_ATTR: internal
* @NL80211_PMSR_FTM_CAPA_ATTR_MAX: highest attribute number
@@ -8225,6 +8233,8 @@ enum nl80211_peer_measurement_ftm_capa {
NL80211_PMSR_FTM_CAPA_ATTR_MAX_NUM_RX_ANTENNAS,
NL80211_PMSR_FTM_CAPA_ATTR_MIN_INTERVAL_EDCA,
NL80211_PMSR_FTM_CAPA_ATTR_MIN_INTERVAL_NTB,
+ NL80211_PMSR_FTM_CAPA_ATTR_PD_PREAMBLES,
+ NL80211_PMSR_FTM_CAPA_ATTR_PD_BANDWIDTHS,
/* keep last */
NUM_NL80211_PMSR_FTM_CAPA_ATTR,
diff --git a/net/wireless/nl80211.c b/net/wireless/nl80211.c
index ae968d53fcea..84f17032fdd9 100644
--- a/net/wireless/nl80211.c
+++ b/net/wireless/nl80211.c
@@ -2615,6 +2615,18 @@ nl80211_send_pmsr_ftm_capa(const struct cfg80211_pmsr_capabilities *cap,
if (cap->ftm.concurrent_ista_rsta_support &&
nla_put_flag(msg, NL80211_PMSR_FTM_CAPA_ATTR_CONCURRENT_ISTA_RSTA_SUPPORT))
return -ENOBUFS;
+
+ if (cap->ftm.type.pd_support) {
+ if (cap->ftm.pd_preambles &&
+ nla_put_u32(msg, NL80211_PMSR_FTM_CAPA_ATTR_PD_PREAMBLES,
+ cap->ftm.pd_preambles))
+ return -ENOBUFS;
+ if (cap->ftm.pd_bandwidths &&
+ nla_put_u32(msg, NL80211_PMSR_FTM_CAPA_ATTR_PD_BANDWIDTHS,
+ cap->ftm.pd_bandwidths))
+ return -ENOBUFS;
+ }
+
nla_nest_end(msg, ftm);
return 0;
}
diff --git a/net/wireless/pmsr.c b/net/wireless/pmsr.c
index 2d6ace7f048d..8b7843f75db2 100644
--- a/net/wireless/pmsr.c
+++ b/net/wireless/pmsr.c
@@ -17,11 +17,19 @@ static int pmsr_parse_ftm(struct cfg80211_registered_device *rdev,
u32 preamble = NL80211_PREAMBLE_DMG; /* only optional in DMG */
/* validate existing data */
- if (!(rdev->wiphy.pmsr_capa->ftm.bandwidths & BIT(out->chandef.width))) {
+ if (out->ftm.request_type == NL80211_PMSR_FTM_REQ_TYPE_INFRA &&
+ !(capa->ftm.bandwidths & BIT(out->chandef.width))) {
NL_SET_ERR_MSG(info->extack, "FTM: unsupported bandwidth");
return -EINVAL;
}
+ if (out->ftm.request_type == NL80211_PMSR_FTM_REQ_TYPE_PD &&
+ !(capa->ftm.pd_bandwidths & BIT(out->chandef.width))) {
+ NL_SET_ERR_MSG(info->extack,
+ "FTM: unsupported bandwidth for PD request");
+ return -EINVAL;
+ }
+
/* no validation needed - was already done via nested policy */
nla_parse_nested_deprecated(tb, NL80211_PMSR_FTM_REQ_ATTR_MAX, ftmreq,
NULL, NULL);
@@ -44,13 +52,22 @@ static int pmsr_parse_ftm(struct cfg80211_registered_device *rdev,
}
}
- if (!(capa->ftm.preambles & BIT(preamble))) {
+ if (out->ftm.request_type == NL80211_PMSR_FTM_REQ_TYPE_INFRA &&
+ !(capa->ftm.preambles & BIT(preamble))) {
NL_SET_ERR_MSG_ATTR(info->extack,
tb[NL80211_PMSR_FTM_REQ_ATTR_PREAMBLE],
"FTM: invalid preamble");
return -EINVAL;
}
+ if (out->ftm.request_type == NL80211_PMSR_FTM_REQ_TYPE_PD &&
+ !(capa->ftm.pd_preambles & BIT(preamble))) {
+ NL_SET_ERR_MSG_ATTR(info->extack,
+ tb[NL80211_PMSR_FTM_REQ_ATTR_PREAMBLE],
+ "FTM: invalid preamble for PD request");
+ return -EINVAL;
+ }
+
out->ftm.preamble = preamble;
out->ftm.burst_period = 0;