From fc907cd71851636ba25897618719e97b673c5738 Mon Sep 17 00:00:00 2001
From: Bharat Bhushan <bchakrav@qti.qualcomm.com>
Date: Mon, 28 Sep 2015 17:20:54 +0530
Subject: [PATCH] Making api at par with band steerign phase-2 implementation .
 Signed-off-by: Bharat Bhushan <bchakrav@qti.qualcomm.com> Change-Id:
 Ibfed2dd240397bcf787a2dde72599490f8858ecc

---
 host/thin_driver/atd/atd_cfg.c         |  15 ++-
 include/atd_event.h                    |  17 ++-
 include/band_steering.h                | 238 +++++++++++++++++++++++++++------
 target/linux/thin_driver/atd/atd_cfg.c |  14 +-
 4 files changed, 228 insertions(+), 56 deletions(-)

diff --git a/host/thin_driver/atd/atd_cfg.c b/host/thin_driver/atd/atd_cfg.c
index e33c8af..c9d3f5f 100644
--- a/host/thin_driver/atd/atd_cfg.c
+++ b/host/thin_driver/atd/atd_cfg.c
@@ -5,7 +5,7 @@
  * purpose with or without fee is hereby granted, provided that the above
  * copyright notice and this permission notice appear in all copies.
  *
- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOSCLAIMS ALL WARRANTIES
  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
@@ -3334,6 +3334,7 @@ atd_cfg_dbgreq(adf_drv_handle_t hdl, acfg_athdbg_req_t  *dbgreq)
             acs_dbg->chan_load = adf_os_htonl(acsdbg->chan_load);
             acs_dbg->sec_chan = acsdbg->sec_chan;
             break;
+#if 0
         case ACFG_DBGREQ_BSTEERING_SET_PARAMS:
             pld->data.bst.inactivity_timeout_normal = adf_os_htonl(dbgreq->data.bst.inactivity_timeout_normal);
             pld->data.bst.inactivity_timeout_overload = adf_os_htonl(dbgreq->data.bst.inactivity_timeout_overload);
@@ -3363,7 +3364,7 @@ atd_cfg_dbgreq(adf_drv_handle_t hdl, acfg_athdbg_req_t  *dbgreq)
         case ACFG_DBGREQ_BSTEERING_SET_PROBE_RESP_WH:
             pld->data.bsteering_probe_resp_wh = dbgreq->data.bsteering_probe_resp_wh;
             break;
-            
+#endif            
         default:
             break;
     }
@@ -3651,6 +3652,7 @@ atd_cfg_dbgreq(adf_drv_handle_t hdl, acfg_athdbg_req_t  *dbgreq)
             acsdbg->chan_load = adf_os_ntohl(acs_dbg->chan_load);
             acsdbg->sec_chan = acs_dbg->sec_chan;
             break;
+#if 0
         case ACFG_DBGREQ_BSTEERING_SET_PARAMS:
             break;
         case ACFG_DBGREQ_BSTEERING_GET_PARAMS:
@@ -3680,6 +3682,7 @@ atd_cfg_dbgreq(adf_drv_handle_t hdl, acfg_athdbg_req_t  *dbgreq)
             break;
         case ACFG_DBGREQ_BSTEERING_SET_PROBE_RESP_WH:
             break;
+#endif
         default:
             break;
     }
@@ -5523,7 +5526,7 @@ atd_convert_bsteer_event_ntoh(ath_netlink_bsteering_event_t *out,
         atd_bsteering_event_t *in)
 {
     out->type = adf_os_ntohl(in->type);
-    out->band_index = adf_os_ntohl(in->band_index);
+    out->sys_index = adf_os_ntohl(in->sys_index);
 
     switch(out->type)
     {
@@ -5537,9 +5540,9 @@ atd_convert_bsteer_event_ntoh(ath_netlink_bsteering_event_t *out,
                     ACFG_MACADDR_LEN);
             out->data.bs_probe.rssi = in->data.bs_probe.rssi;
             break;
-        case ATH_EVENT_BSTEERING_NODE_AUTHORIZED:
-            memcpy(out->data.bs_node_authorized.client_addr,
-                    in->data.bs_node_authorized.client_addr,
+        case ATH_EVENT_BSTEERING_NODE_ASSOCIATED:
+            memcpy(out->data.bs_node_associated.client_addr,
+                    in->data.bs_node_associated.client_addr,
                     ACFG_MACADDR_LEN);
             break;
         case ATH_EVENT_BSTEERING_TX_AUTH_FAIL:
diff --git a/include/atd_event.h b/include/atd_event.h
index bf9b445..7417d1c 100644
--- a/include/atd_event.h
+++ b/include/atd_event.h
@@ -119,11 +119,16 @@ typedef struct atd_bs_auth_reject_ind {
     u_int8_t rssi;
 } __attribute__((__packed__)) atd_bs_auth_reject_ind_t;
 
-typedef struct atd_bs_node_authorized_ind {
-    /* The MAC address of the client that is having its authorize status
-     *        changed.*/
+typedef struct atd_bs_node_associated_ind {
+    /* The MAC address of the client that is associated.*/
     u_int8_t client_addr[ACFG_MACADDR_LEN];
-} __attribute__((__packed__)) atd_bs_node_authorized_ind_t;
+    /* Set to 1 if this client supports BSS Transition Management */
+    u_int8_t isBTMSupported : 1;
+    /* Set to 1 if this client implements Radio Resource Manangement */
+    u_int8_t isRRMSupported : 1;
+    /* Data rate related information supported by this client */
+    //    ieee80211_bsteering_datarate_info_t datarate_info;
+} __attribute__((__packed__)) atd_bs_node_associated_ind_t;
 
 typedef struct atd_bs_activity_change_ind {
     /* The MAC address of the client that activity status changes */
@@ -159,12 +164,12 @@ typedef struct atd_bsteering_event {
     /* The type of the event: One of ATH_BSTEERING_EVENT.*/
     u_int32_t type;
     /* The band on which the event occurred.*/
-    u_int32_t band_index;
+    u_int32_t sys_index;
     /* The data for the event. Which member is valid is based on the
      * type field.*/
     union {
         struct atd_bs_probe_req_ind bs_probe;
-        struct atd_bs_node_authorized_ind bs_node_authorized;
+        struct atd_bs_node_associated_ind bs_node_associated;
         struct atd_bs_activity_change_ind bs_activity_change;
         struct atd_bs_auth_reject_ind bs_auth;
         struct atd_bs_chan_utilization_ind bs_chan_util;
diff --git a/include/band_steering.h b/include/band_steering.h
index 7b9abe3..39f013a 100644
--- a/include/band_steering.h
+++ b/include/band_steering.h
@@ -13,7 +13,6 @@
 #define NETLINK_BAND_STEERING_EVENT 21
 #define BSTEERING_INVALID_RSSI 0
 #define IEEE80211_ADDR_LEN 6
-
 /**
  * Metadata about a probe request received from a client that is useful
  * for making band steering decisions.
@@ -39,13 +38,38 @@ struct bs_auth_reject_ind {
 };
 
 /**
- * Metadata about a STA that has been authorized (security handshake has
- * completed).
+ * Data rated related information contained in ATH_EVENT_BSTEERING_NODE_ASSOCIATED
+ * and IEEE80211_DBGREQ_BSTEERING_GET_DATARATE_INFO response
+ */
+typedef struct ieee80211_bsteering_datarate_info_t {
+    /* Maximum bandwidth the client supports, valid values are enumerated
+     * in enum ieee80211_cwm_width in _ieee80211.h. But the header file cannot
+     * be included here because of potential circular dependency. Caller should
+     * make sure that only valid values can be written/read. */
+    u_int8_t max_chwidth;
+    /* Number of spatial streams the client supports */
+    u_int8_t num_streams;
+    /* PHY mode the client supports. Same as max_chwidth field, only valid values
+     * enumerated in enum ieee80211_phymode can be used here. */
+    u_int8_t phymode;
+    /* Maximum MCS the client supports */
+    u_int8_t max_MCS;
+    /* Maximum TX power the client supports */
+    u_int8_t max_txpower;
+} ieee80211_bsteering_datarate_info_t;
+
+/**
+ * Metadata about a STA that has associated
  */
-struct bs_node_authorized_ind {
-    /* The MAC address of the client that is having its authorize status
-       changed.*/
+struct bs_node_associated_ind {
+    /* The MAC address of the client that is associated.*/
     u_int8_t client_addr[IEEE80211_ADDR_LEN];
+    /* Set to 1 if this client supports BSS Transition Management */
+    u_int8_t isBTMSupported : 1;
+    /* Set to 1 if this client implements Radio Resource Manangement */
+    u_int8_t isRRMSupported : 1;
+    /* Data rate related information supported by this client */
+    ieee80211_bsteering_datarate_info_t datarate_info;
 };
 
 /**
@@ -67,16 +91,16 @@ struct bs_chan_utilization_ind {
 };
 
 /**
- * Enumeration to mark RSSI crossing direction
+ * Enumeration to mark crossing direction
  */
 typedef enum {
-    /* RSSI not change */
-    BSTEERING_RSSI_UNCHANGED = 0,
-    /* RSSI going up */
-    BSTEERING_RSSI_UP = 1,
-    /* RSSI going down */
-    BSTEERING_RSSI_DOWN = 2
-} BSTEERING_RSSI_XING_DIRECTION;
+    /* Threshold not crossed */
+    BSTEERING_XING_UNCHANGED = 0,
+    /* Threshold crossed in the up direction */
+    BSTEERING_XING_UP = 1,
+    /* Threshold crossed in the down direction */
+    BSTEERING_XING_DOWN = 2
+} BSTEERING_XING_DIRECTION;
 
 /**
  * Metadata about a client RSSI measurement crossed threshold.
@@ -87,9 +111,11 @@ struct bs_rssi_xing_threshold_ind {
     /* The measured RSSI */
     u_int8_t rssi;
     /* Flag indicating if it crossed inactivity RSSI threshold */
-    BSTEERING_RSSI_XING_DIRECTION inact_rssi_xing;
+    BSTEERING_XING_DIRECTION inact_rssi_xing;
     /* Flag indicating if it crossed low RSSI threshold */
-    BSTEERING_RSSI_XING_DIRECTION low_rssi_xing;
+    BSTEERING_XING_DIRECTION low_rssi_xing;
+    /* Flag indicating if it crossed the rate RSSI threshold */
+    BSTEERING_XING_DIRECTION rate_rssi_xing;
 };
 
 /**
@@ -103,23 +129,137 @@ struct bs_rssi_measurement_ind {
 };
 
 /**
+ * Metadata about a Tx rate measurement 
+ * NOTE: Debug event only, use bs_tx_rate_xing_threshold_ind for
+ * rate crossing information.  
+ */
+struct bs_tx_rate_measurement_ind {
+    /* The MAC address of the client */
+    u_int8_t client_addr[IEEE80211_ADDR_LEN];
+    /* The measured Tx rate */
+    u_int32_t tx_rate;
+};
+
+/**
+ * Radio Resource Managmenet report types
+ *
+ * Note that these types are only used between user space and driver, and
+ * not in sync with the OTA types defined in 802.11k spec.
+ */
+typedef enum {
+    /* Indication of a beacon report. */
+    BSTEERING_RRM_TYPE_BCNRPT,
+
+    BSTEERING_RRM_TYPE_INVALID
+} BSTEERING_RRM_TYPE;
+
+/**
+ * Number of RRM beacon reports in a single OTA message can be conveyed in
+ * in single event up to user space. Multiple events will be sent if more
+ * than this number of reports is included in a single OTA message.
+ */
+#define IEEE80211_BSTEERING_RRM_NUM_BCNRPT_MAX 4
+
+/**
+ * Metadata and report contents about a Radio Resource Measurement report
+ */
+struct bs_rrm_report_ind {
+    /* The type of the rrm event: One of BSTEERING_RRM_TYPE.*/
+    u_int32_t rrm_type;
+    /* The token corresponding to the measurement request.*/
+    u_int8_t dialog_token;
+    /* MAC address of the reporter station.*/
+    u_int8_t macaddr[IEEE80211_ADDR_LEN];
+    /* The result bitmap, as defined in IEEE80211_RRM_MEASRPT_MODE.*/
+    u_int8_t measrpt_mode;
+    /* The report data. Which member is valid is based on the
+       rrm_type field.*/
+    union {
+        atd_bcnrpt_t   bcnrpt[IEEE80211_BSTEERING_RRM_NUM_BCNRPT_MAX];
+    } data;
+};
+
+/**
+ * Wireless Network Management (WNM) report types
+ */
+typedef enum {
+    /* Indication of reception of a BSS Transition Management response frame */
+    BSTEERING_WNM_TYPE_BSTM_RESPONSE,
+
+    BSTEERING_WNM_TYPE_INVALID
+} BSTEERING_WNM_TYPE;
+
+/* BSS Transition Management Response information that can be returned via netlink message */
+struct bs_wnm_bstm_resp {
+    /* status of the response to the request frame */
+    u_int8_t status;
+    /* number of minutes that the STA requests the BSS to delay termination */
+    u_int8_t termination_delay;
+    /* BSSID of the BSS that the STA transitions to */
+    u_int8_t target_bssid[IEEE80211_ADDR_LEN];
+} ;
+
+/**
+ * Metadata and report contents about a Wireless Network 
+ * Management event 
+ */
+struct bs_wnm_event_ind {
+    /* The type of the wnm event: One of BSTEERING_WNM_TYPE.*/
+    u_int32_t wnm_type;
+    /* The token corresponding to the message.*/
+    u_int8_t dialog_token;
+    /* MAC address of the sending station.*/
+    u_int8_t macaddr[IEEE80211_ADDR_LEN];
+    /* The event data. Which member is valid is based on the
+       wnm_type field.*/
+    union {
+        struct bs_wnm_bstm_resp bstm_resp;
+    } data;
+};
+
+/**
+ * Metadata about a client Tx rate threshold crossing event.
+ */
+struct bs_tx_rate_xing_threshold_ind {
+    /* The MAC address of the client */
+    u_int8_t client_addr[IEEE80211_ADDR_LEN];
+    /* The Tx rate (in Kbps) */
+    u_int32_t tx_rate;
+    /* Flag indicating crossing direction */
+    BSTEERING_XING_DIRECTION xing;
+};
+
+/**
+ * Metadata about Tx power change on a VAP
+ */
+struct bs_tx_power_change_ind {
+    /* The new Tx power */
+    u_int16_t tx_power;
+};
+
+/**
  * Common event structure for all Netlink indications to userspace.
  */
 typedef struct ath_netlink_bsteering_event {
     /* The type of the event: One of ATH_BSTEERING_EVENT.*/
     u_int32_t type;
-    /* The band on which the event occurred.*/
-    u_int32_t band_index;
+    /* The OS-specific index of the VAP on which the event occurred.*/
+    u_int32_t sys_index;
     /* The data for the event. Which member is valid is based on the
        type field.*/
     union {
         struct bs_probe_req_ind bs_probe;
-        struct bs_node_authorized_ind bs_node_authorized;
+        struct bs_node_associated_ind bs_node_associated;
         struct bs_activity_change_ind bs_activity_change;
         struct bs_auth_reject_ind bs_auth;
         struct bs_chan_utilization_ind bs_chan_util;
         struct bs_rssi_xing_threshold_ind bs_rssi_xing;
         struct bs_rssi_measurement_ind bs_rssi_measurement;
+        struct bs_rrm_report_ind rrm_report;
+        struct bs_wnm_event_ind wnm_event;
+        struct bs_tx_rate_xing_threshold_ind bs_tx_rate_xing;
+        struct bs_tx_rate_measurement_ind bs_tx_rate_measurement;
+        struct bs_tx_power_change_ind bs_tx_power_change;
     } data;
 } ath_netlink_bsteering_event_t;
 
@@ -143,14 +283,29 @@ typedef struct ieee80211_bsteering_param_t {
     /* The number of samples over which the medium utilization should be
        averaged before being reported.*/
     u_int32_t utilization_average_num_samples;
-    /* The RSSI value for which to generate threshold crossing events for
-     an idle client. Such events are generated when the threshold is
-     crossed in either direction.*/
-    u_int32_t inactive_rssi_crossing_threshold;
+    /* Two RSSI values for which to generate threshold crossing events for
+       an idle client. Such events are generated when the thresholds are
+       crossed in either direction.*/
+    u_int32_t inactive_rssi_xing_high_threshold;
+    u_int32_t inactive_rssi_xing_low_threshold;
     /* The RSSI value for which to generate threshold crossing events for
         both active and idle clients. This value should generally be less
-        than inactive_rssi_crossing_threshold.*/
+        than inactive_rssi_xing_low_threshold.*/
     u_int32_t low_rssi_crossing_threshold;
+    /* The lower-bound Tx rate value (Kbps) for which to generate threshold crossing events
+       if the Tx rate for a client decreases below this value. */
+    u_int32_t low_tx_rate_crossing_threshold;
+    /* The upper-bound Tx rate (Kbps) value for which to generate threshold crossing events
+       if the Tx rate for a client increases above this value. */
+    u_int32_t high_tx_rate_crossing_threshold;
+    /* The RSSI value for which to generate threshold crossing events for
+       active clients. Used in conjunction with the rate crossing events
+       to determine if STAs should be downgraded. */
+    u_int32_t low_rate_rssi_crossing_threshold;
+    /* The RSSI value for which to generate threshold crossing events for
+       active clients. Used in conjunction with the rate crossing events
+       to determine if STAs should be upgraded. */
+    u_int32_t high_rate_rssi_crossing_threshold;
 } ieee80211_bsteering_param_t;
 
 /**
@@ -192,6 +347,8 @@ typedef struct ieee80211_bsteering_dbg_param_t {
     u_int8_t  raw_chan_util_log_enable:1;
     /* Whether logging of the raw RSSI measurement is enabled.*/
     u_int8_t  raw_rssi_log_enable:1;
+    /* Whether logging of the raw Tx rate measurement is enabled.*/
+    u_int8_t raw_tx_rate_log_enable:1;
 } ieee80211_bsteering_dbg_param_t;
 
 /**
@@ -203,8 +360,8 @@ typedef enum {
     ATH_EVENT_BSTEERING_CHAN_UTIL = 1,
     /* Indication that a probe request was received from a client.*/
     ATH_EVENT_BSTEERING_PROBE_REQ = 2,
-    /* Authorization change for a STA.*/
-    ATH_EVENT_BSTEERING_NODE_AUTHORIZED = 3,
+    /* Indicated that a STA associated.*/
+    ATH_EVENT_BSTEERING_NODE_ASSOCIATED = 3,
     /* Indication that an authentication frame was sent with a failure
         status code.*/
     ATH_EVENT_BSTEERING_TX_AUTH_FAIL = 4,
@@ -217,25 +374,30 @@ typedef enum {
     /* Indication when a requested RSSI measurement for a specific
        client is available.*/
     ATH_EVENT_BSTEERING_CLIENT_RSSI_MEASUREMENT = 7,
+    /* Indication when a 802.11k radio resource management report
+       is received from a client.*/
+    ATH_EVENT_BSTEERING_RRM_REPORT = 8,
+    /* Indication when a 802.11v wireless network management (WNM) message
+       is received from a client.*/
+    ATH_EVENT_BSTEERING_WNM_EVENT = 9,
+    /* Indication when the client Tx rate crosses above or below the
+       configured threshold. */
+    ATH_EVENT_BSTEERING_CLIENT_TX_RATE_CROSSING = 10,
+    /* Indication when a VAP has stopped.
+       Note: This is not the same as a VAP being brought down. This will be seen
+       in RE mode when the uplink STA interface disassociates. */
+    ATH_EVENT_BSTEERING_VAP_STOP = 11,
+    /* Indication when Tx power changes on a VAP. */
+    ATH_EVENT_BSTEERING_TX_POWER_CHANGE = 12,
     /*  Events generated solely for debugging purposes. These are not
         intended for direct consumption by any algorithm components but are
         here to facilitate logging the raw data.*/
     ATH_EVENT_BSTEERING_DBG_CHAN_UTIL = 32,
     /* Raw RSSI measurement event used to facilitate logging.*/
     ATH_EVENT_BSTEERING_DBG_RSSI = 33,
+    /* Raw Tx rate measurement event used to facilitate logging.*/
+    ATH_EVENT_BSTEERING_DBG_TX_RATE = 34,
 } ATH_BSTEERING_EVENT;
 
-/**
- * The band of operation.
- */
-typedef enum {
-    /* 2.4 GHz*/
-    BSTEERING_24G = 0,
-    /* 5 GHz */
-    BSTEERING_5G = 1,
-    BSTEERING_INVALID = 2,
-    BSTEERING_MAX = BSTEERING_INVALID,
-} BSTEERING_BAND;
-
 #undef IEEE80211_ADDR_LEN
 #endif /* _BAND_STEERING__ */
diff --git a/target/linux/thin_driver/atd/atd_cfg.c b/target/linux/thin_driver/atd/atd_cfg.c
index 4ca5a29..68dfd45 100644
--- a/target/linux/thin_driver/atd/atd_cfg.c
+++ b/target/linux/thin_driver/atd/atd_cfg.c
@@ -4053,6 +4053,7 @@ atd_tgt_dbgreq(void *ctx, a_uint16_t cmdid,
             acsdbg->chan_load = ntohl(acs_dbg->chan_load);
             acsdbg->sec_chan = acs_dbg->sec_chan;
             break;
+#if 0
         case ACFG_DBGREQ_BSTEERING_SET_PARAMS:
             dbgreq->data.bsteering_param.inactivity_timeout_normal = ntohl(req->data.bst.inactivity_timeout_normal);
             dbgreq->data.bsteering_param.inactivity_timeout_overload = ntohl(req->data.bst.inactivity_timeout_overload);
@@ -4085,7 +4086,7 @@ atd_tgt_dbgreq(void *ctx, a_uint16_t cmdid,
         case ACFG_DBGREQ_BSTEERING_SET_PROBE_RESP_WH:
             dbgreq->data.bsteering_probe_resp_wh = req->data.bsteering_probe_resp_wh;
             break;
-
+#endif
         default:
             break;
     }
@@ -4399,6 +4400,7 @@ atd_tgt_dbgreq(void *ctx, a_uint16_t cmdid,
             acs_dbg->chan_load = htonl(acsdbg->chan_load);
             acs_dbg->sec_chan = acsdbg->sec_chan;
             break;
+#if 0
         case ACFG_DBGREQ_BSTEERING_SET_PARAMS:
             break;
         case ACFG_DBGREQ_BSTEERING_GET_PARAMS:
@@ -4432,7 +4434,7 @@ atd_tgt_dbgreq(void *ctx, a_uint16_t cmdid,
             break;
         case ACFG_DBGREQ_BSTEERING_SET_PROBE_RESP_WH:
             break;
-
+#endif
         default:
             break;
     }
@@ -5507,7 +5509,7 @@ void atd_convert_bsteer_event_hton(atd_bsteering_event_t *out,
         struct ath_netlink_bsteering_event *in)
 {
     out->type = htonl(in->type);
-    out->band_index = htonl(in->band_index);
+    out->sys_index = htonl(in->sys_index);
 
     switch(in->type)
     {
@@ -5521,9 +5523,9 @@ void atd_convert_bsteer_event_hton(atd_bsteering_event_t *out,
                     ACFG_MACADDR_LEN);
             out->data.bs_probe.rssi = in->data.bs_probe.rssi;
             break;
-        case ATH_EVENT_BSTEERING_NODE_AUTHORIZED:
-            memcpy(out->data.bs_node_authorized.client_addr,
-                    in->data.bs_node_authorized.client_addr,
+        case ATH_EVENT_BSTEERING_NODE_ASSOCIATED:
+            memcpy(out->data.bs_node_associated.client_addr,
+                    in->data.bs_node_associated.client_addr,
                     ACFG_MACADDR_LEN);
             break;
         case ATH_EVENT_BSTEERING_TX_AUTH_FAIL:
-- 
2.8.0.rc3

