[PATCH 6/6] hostapd: Register callback to get/free AID with vendor cmd

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Register callbacks to receive a new association ID for a station
from the kernel driver using vendor cmd, which may in turn ask it
from the firmware and that from the hardware. This AID is tied to SID
and will need to be freed eventually during the dissociation phase.

Signed-off-by: Sarada Prasanna Garnayak <sarada.prasanna.garnayak@xxxxxxxxx>
---
 src/ap/ieee802_11.c               |  5 ++++-
 src/ap/sta_info.c                 | 10 +++++++---
 src/drivers/driver.h              | 24 ++++++++++++++++++++++++
 src/drivers/driver_nl80211.c      | 17 +++++++++--------
 src/drivers/driver_nl80211.h      |  6 ++++++
 src/drivers/driver_nl80211_capa.c | 14 ++++++++++++++
 6 files changed, 64 insertions(+), 12 deletions(-)

diff --git a/src/ap/ieee802_11.c b/src/ap/ieee802_11.c
index d2d6b1767..da6594757 100644
--- a/src/ap/ieee802_11.c
+++ b/src/ap/ieee802_11.c
@@ -2130,11 +2130,14 @@ static void handle_auth(struct hostapd_data *hapd,
 	}
 }
 
-
 int hostapd_get_aid(struct hostapd_data *hapd, struct sta_info *sta)
 {
 	int i, j = 32, aid;
 
+	if (hapd->driver->get_aid)
+		return (*hapd->driver->get_aid)(hapd->drv_priv,
+						&sta->aid, sta->addr);
+
 	/* get a unique AID */
 	if (sta->aid > 0) {
 		wpa_printf(MSG_DEBUG, "  old AID %d", sta->aid);
diff --git a/src/ap/sta_info.c b/src/ap/sta_info.c
index 179cf43b6..287cf2dfd 100644
--- a/src/ap/sta_info.c
+++ b/src/ap/sta_info.c
@@ -182,9 +182,13 @@ void ap_free_sta(struct hostapd_data *hapd, struct sta_info *sta)
 	ap_sta_hash_del(hapd, sta);
 	ap_sta_list_del(hapd, sta);
 
-	if (sta->aid > 0)
-		hapd->sta_aid[(sta->aid - 1) / 32] &=
-			~BIT((sta->aid - 1) % 32);
+	if (sta->aid > 0) {
+		if (hapd->driver->free_aid)
+			(*hapd->driver->free_aid)(hapd->drv_priv, &sta->aid);
+		else
+			hapd->sta_aid[(sta->aid - 1) / 32] &=
+				~BIT((sta->aid - 1) % 32);
+	}
 
 	hapd->num_sta--;
 	if (sta->nonerp_set) {
diff --git a/src/drivers/driver.h b/src/drivers/driver.h
index d34c6794f..671585e47 100644
--- a/src/drivers/driver.h
+++ b/src/drivers/driver.h
@@ -3651,6 +3651,30 @@ struct wpa_driver_ops {
 	 */
 	int (*status)(void *priv, char *buf, size_t buflen);
 
+  /**
+   * get_aid - Receive a new association ID for a station
+   * @priv: Private driver interface data
+   * @aid: Memory address for storing the received AID
+   * @addr: MAC address of the station
+   * Returns: 0 on success, -1 on failure
+   *
+   * This function is used to receive a new AID from the kernel driver,
+   * which may in turn ask it from the FW, and that from the HW.
+   * This AID is tied to SID and will need to be freed eventually.
+   */
+  int (*get_aid)(void *priv, u16 *aid, const u8 *addr);
+
+  /**
+   * free_aid - Release an association ID
+   * @priv: Private driver interface data
+   * @aid: AID to release
+   * Returns: 0 on success, -1 on failure
+   *
+   * This function is used to release an AID back to the kernel driver,
+   * which may release it to the FW, and that to the HW.
+   */
+  int (*free_aid)(void *priv, u16 *aid);
+
 	/**
 	 * roaming - Set roaming policy for driver-based BSS selection
 	 * @priv: Private driver interface data
diff --git a/src/drivers/driver_nl80211.c b/src/drivers/driver_nl80211.c
index 771e76696..403c38f6c 100644
--- a/src/drivers/driver_nl80211.c
+++ b/src/drivers/driver_nl80211.c
@@ -27,6 +27,7 @@
 #include "eloop.h"
 #include "common/qca-vendor.h"
 #include "common/qca-vendor-attr.h"
+#include "common/intel-ltq-vendor.h"
 #include "common/ieee802_11_defs.h"
 #include "common/ieee802_11_common.h"
 #include "common/wpa_common.h"
@@ -105,7 +106,6 @@ static void nl80211_handle_destroy(struct nl_handle *handle)
 }
 #endif /* CONFIG_LIBNL20 */
 
-
 #ifdef ANDROID
 /* system/core/libnl_2 does not include nl_socket_set_nonblocking() */
 #undef nl_socket_set_nonblocking
@@ -6273,7 +6273,6 @@ static int i802_read_sta_data(struct i802_bss *bss,
 	return send_and_recv_msgs(bss->drv, msg, get_sta_handler, data);
 }
 
-
 static int i802_set_tx_queue_params(void *priv, int queue, int aifs,
 				    int cw_min, int cw_max, int burst_time)
 {
@@ -8952,8 +8951,7 @@ static int cmd_reply_handler(struct nl_msg *msg, void *arg)
 }
 #endif /* CONFIG_TESTING_OPTIONS */
 
-
-static int vendor_reply_handler(struct nl_msg *msg, void *arg)
+int vendor_reply_handler(struct nl_msg *msg, void *arg)
 {
 	struct nlattr *tb[NL80211_ATTR_MAX + 1];
 	struct nlattr *nl_vendor_reply, *nl;
@@ -8984,9 +8982,9 @@ static int vendor_reply_handler(struct nl_msg *msg, void *arg)
 }
 
 
-static int nl80211_vendor_cmd(void *priv, unsigned int vendor_id,
-			      unsigned int subcmd, const u8 *data,
-			      size_t data_len, struct wpabuf *buf)
+int nl80211_vendor_cmd(void *priv, unsigned int vendor_id,
+		       unsigned int subcmd, const u8 *data,
+		       size_t data_len, struct wpabuf *buf)
 {
 	struct i802_bss *bss = priv;
 	struct wpa_driver_nl80211_data *drv = bss->drv;
@@ -9029,7 +9027,6 @@ fail:
 	return -ENOBUFS;
 }
 
-
 static int nl80211_set_qos_map(void *priv, const u8 *qos_map_set,
 			       u8 qos_map_set_len)
 {
@@ -10684,6 +10681,10 @@ const struct wpa_driver_ops wpa_driver_nl80211_ops = {
 	.hapd_init = i802_init,
 	.hapd_deinit = i802_deinit,
 	.set_wds_sta = i802_set_wds_sta,
+#ifdef CONFIG_DRIVER_NL80211_INTEL_LTQ
+	.get_aid = nl80211_get_aid,
+	.free_aid = nl80211_free_aid,
+#endif /* CONFIG_DRIVER_NL80211_INTEL_LTQ */
 	.get_seqnum = i802_get_seqnum,
 	.flush = i802_flush,
 	.get_inact_sec = i802_get_inact_sec,
diff --git a/src/drivers/driver_nl80211.h b/src/drivers/driver_nl80211.h
index 5ac0c7dfc..f4cefc54f 100644
--- a/src/drivers/driver_nl80211.h
+++ b/src/drivers/driver_nl80211.h
@@ -165,6 +165,8 @@ struct wpa_driver_nl80211_data {
 	unsigned int he_capab_vendor_cmd_avail:1;
 	unsigned int fetch_bss_trans_status:1;
 	unsigned int roam_vendor_cmd_avail:1;
+	unsigned int get_aid_vendor_cmd_avail:1;
+	unsigned int free_aid_vendor_cmd_avail:1;
 
 	u64 vendor_scan_cookie;
 	u64 remain_on_chan_cookie;
@@ -304,4 +306,8 @@ int wpa_driver_nl80211_vendor_scan(struct i802_bss *bss,
 				   struct wpa_driver_scan_params *params);
 int nl80211_set_default_scan_ies(void *priv, const u8 *ies, size_t ies_len);
 
+int vendor_reply_handler(struct nl_msg *msg, void *arg);
+int nl80211_vendor_cmd(void *priv, unsigned int vendor_id, unsigned int subcmd,
+		       const u8 *data, size_t data_len, struct wpabuf *buf);
+
 #endif /* DRIVER_NL80211_H */
diff --git a/src/drivers/driver_nl80211_capa.c b/src/drivers/driver_nl80211_capa.c
index 7b360d209..59c992368 100644
--- a/src/drivers/driver_nl80211_capa.c
+++ b/src/drivers/driver_nl80211_capa.c
@@ -15,6 +15,7 @@
 #include "common/ieee802_11_common.h"
 #include "common/wpa_common.h"
 #include "common/qca-vendor.h"
+#include "common/intel-ltq-vendor.h"
 #include "common/qca-vendor-attr.h"
 #include "driver_nl80211.h"
 
@@ -786,6 +787,19 @@ static int wiphy_info_handler(struct nl_msg *msg, void *arg)
 				}
 			}
 
+			if (vinfo->vendor_id == OUI_INTEL_LTQ) {
+				switch (vinfo->subcmd) {
+#ifdef CONFIG_DRIVER_NL80211_INTEL_LTQ
+				case INTEL_LTQ_NL80211_VENDOR_SUBCMD_GET_AID:
+					drv->get_aid_vendor_cmd_avail = 1;
+					break;
+				case INTEL_LTQ_NL80211_VENDOR_SUBCMD_FREE_AID:
+					drv->free_aid_vendor_cmd_avail = 1;
+					break;
+#endif /* CONFIG_DRIVER_NL80211_INTEL_LTQ */
+				}
+			}
+
 			wpa_printf(MSG_DEBUG, "nl80211: Supported vendor command: vendor_id=0x%x subcmd=%u",
 				   vinfo->vendor_id, vinfo->subcmd);
 		}
-- 
2.11.0


_______________________________________________
Hostap mailing list
Hostap@xxxxxxxxxxxxxxxxxxx
http://lists.infradead.org/mailman/listinfo/hostap



[Index of Archives]     [Linux Wireless]     [Linux Kernel]     [ATH6KL]     [Linux Bluetooth]     [Linux Netdev]     [Kernel Newbies]     [IDE]     [Security]     [Git]     [Netfilter]     [Bugtraq]     [Yosemite News]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux ATA RAID]     [Samba]     [Device Mapper]

  Powered by Linux