wlan: A method by which metrics related to roaming can be reported
This change will help in reporting three main steps in 11r/Legacy roaming
mechanism. These steps are pre-authentication initiation, pre-authentication
completion and reassociation.
Change-Id: Ibeadd5aaed9e87be5731a28f099153145b674f81
CRs-fixed: 458524
diff --git a/CORE/HDD/inc/wlan_hdd_cfg80211.h b/CORE/HDD/inc/wlan_hdd_cfg80211.h
index c87f5e5..99d4368 100644
--- a/CORE/HDD/inc/wlan_hdd_cfg80211.h
+++ b/CORE/HDD/inc/wlan_hdd_cfg80211.h
@@ -133,6 +133,17 @@
int index, bool preauth );
#endif
+#ifdef FEATURE_WLAN_LFR_METRICS
+VOS_STATUS wlan_hdd_cfg80211_roam_metrics_preauth(hdd_adapter_t *pAdapter,
+ tCsrRoamInfo *pRoamInfo);
+
+VOS_STATUS wlan_hdd_cfg80211_roam_metrics_preauth_status(
+ hdd_adapter_t *pAdapter, tCsrRoamInfo *pRoamInfo, bool preauth_status);
+
+VOS_STATUS wlan_hdd_cfg80211_roam_metrics_handover(hdd_adapter_t *pAdapter,
+ tCsrRoamInfo *pRoamInfo);
+#endif
+
#ifdef FEATURE_WLAN_WAPI
void wlan_hdd_cfg80211_set_key_wapi(hdd_adapter_t* pAdapter,
u8 key_index, const u8 *mac_addr, u8 *key , int key_Len);
diff --git a/CORE/HDD/src/wlan_hdd_assoc.c b/CORE/HDD/src/wlan_hdd_assoc.c
index c907d56..9a70d4a 100644
--- a/CORE/HDD/src/wlan_hdd_assoc.c
+++ b/CORE/HDD/src/wlan_hdd_assoc.c
@@ -2619,6 +2619,44 @@
break;
#endif
+#ifdef FEATURE_WLAN_LFR_METRICS
+ case eCSR_ROAM_PREAUTH_INIT_NOTIFY:
+ /* This event is to notify pre-auth initiation */
+ if (VOS_STATUS_SUCCESS !=
+ wlan_hdd_cfg80211_roam_metrics_preauth(pAdapter, pRoamInfo))
+ {
+ halStatus = eHAL_STATUS_FAILURE;
+ }
+ break;
+ case eCSR_ROAM_PREAUTH_STATUS_SUCCESS:
+ /* This event will notify pre-auth completion in case of success */
+ if (VOS_STATUS_SUCCESS !=
+ wlan_hdd_cfg80211_roam_metrics_preauth_status(pAdapter,
+ pRoamInfo, 1))
+ {
+ halStatus = eHAL_STATUS_FAILURE;
+ }
+ break;
+ case eCSR_ROAM_PREAUTH_STATUS_FAILURE:
+ /* This event will notify pre-auth completion in case of failure. */
+ if (VOS_STATUS_SUCCESS !=
+ wlan_hdd_cfg80211_roam_metrics_preauth_status(pAdapter,
+ pRoamInfo, 0))
+ {
+ halStatus = eHAL_STATUS_FAILURE;
+ }
+ break;
+ case eCSR_ROAM_HANDOVER_SUCCESS:
+ /* This event is to notify handover success.
+ It will be only invoked on success */
+ if (VOS_STATUS_SUCCESS !=
+ wlan_hdd_cfg80211_roam_metrics_handover(pAdapter, pRoamInfo))
+ {
+ halStatus = eHAL_STATUS_FAILURE;
+ }
+ break;
+#endif
+
case eCSR_ROAM_INDICATE_MGMT_FRAME:
hdd_indicateMgmtFrame( pAdapter,
pRoamInfo->nFrameLength,
diff --git a/CORE/HDD/src/wlan_hdd_cfg80211.c b/CORE/HDD/src/wlan_hdd_cfg80211.c
index 3abd444..73db6ad 100644
--- a/CORE/HDD/src/wlan_hdd_cfg80211.c
+++ b/CORE/HDD/src/wlan_hdd_cfg80211.c
@@ -4332,6 +4332,121 @@
}
#endif //FEATURE_WLAN_LFR
+#ifdef FEATURE_WLAN_LFR_METRICS
+/*
+ * FUNCTION: wlan_hdd_cfg80211_roam_metrics_preauth
+ * 802.11r/LFR metrics reporting function to report preauth initiation
+ *
+ */
+#define MAX_LFR_METRICS_EVENT_LENGTH 100
+VOS_STATUS wlan_hdd_cfg80211_roam_metrics_preauth(hdd_adapter_t *pAdapter,
+ tCsrRoamInfo *pRoamInfo)
+{
+ unsigned char metrics_notification[MAX_LFR_METRICS_EVENT_LENGTH + 1];
+ union iwreq_data wrqu;
+
+ ENTER();
+
+ if (NULL == pAdapter)
+ {
+ hddLog(LOGE, "%s: pAdapter is NULL!", __func__);
+ return VOS_STATUS_E_FAILURE;
+ }
+
+ /* create the event */
+ memset(&wrqu, 0, sizeof(wrqu));
+ memset(metrics_notification, 0, sizeof(metrics_notification));
+
+ wrqu.data.pointer = metrics_notification;
+ wrqu.data.length = scnprintf(metrics_notification,
+ sizeof(metrics_notification), "QCOM: LFR_PREAUTH_INIT "
+ MAC_ADDRESS_STR, MAC_ADDR_ARRAY(pRoamInfo->bssid));
+
+ wireless_send_event(pAdapter->dev, IWEVCUSTOM, &wrqu, metrics_notification);
+
+ EXIT();
+
+ return VOS_STATUS_SUCCESS;
+}
+
+/*
+ * FUNCTION: wlan_hdd_cfg80211_roam_metrics_preauth_status
+ * 802.11r/LFR metrics reporting function to report preauth completion
+ * or failure
+ */
+VOS_STATUS wlan_hdd_cfg80211_roam_metrics_preauth_status(
+ hdd_adapter_t *pAdapter, tCsrRoamInfo *pRoamInfo, bool preauth_status)
+{
+ unsigned char metrics_notification[MAX_LFR_METRICS_EVENT_LENGTH + 1];
+ union iwreq_data wrqu;
+
+ ENTER();
+
+ if (NULL == pAdapter)
+ {
+ hddLog(LOGE, "%s: pAdapter is NULL!", __func__);
+ return VOS_STATUS_E_FAILURE;
+ }
+
+ /* create the event */
+ memset(&wrqu, 0, sizeof(wrqu));
+ memset(metrics_notification, 0, sizeof(metrics_notification));
+
+ scnprintf(metrics_notification, sizeof(metrics_notification),
+ "QCOM: LFR_PREAUTH_STATUS "MAC_ADDRESS_STR,
+ MAC_ADDR_ARRAY(pRoamInfo->bssid));
+
+ if (1 == preauth_status)
+ strncat(metrics_notification, " TRUE", 5);
+ else
+ strncat(metrics_notification, " FALSE", 6);
+
+ wrqu.data.pointer = metrics_notification;
+ wrqu.data.length = strlen(metrics_notification);
+
+ wireless_send_event(pAdapter->dev, IWEVCUSTOM, &wrqu, metrics_notification);
+
+ EXIT();
+
+ return VOS_STATUS_SUCCESS;
+}
+
+/*
+ * FUNCTION: wlan_hdd_cfg80211_roam_metrics_handover
+ * 802.11r/LFR metrics reporting function to report handover initiation
+ *
+ */
+VOS_STATUS wlan_hdd_cfg80211_roam_metrics_handover(hdd_adapter_t * pAdapter,
+ tCsrRoamInfo *pRoamInfo)
+{
+ unsigned char metrics_notification[MAX_LFR_METRICS_EVENT_LENGTH + 1];
+ union iwreq_data wrqu;
+
+ ENTER();
+
+ if (NULL == pAdapter)
+ {
+ hddLog(LOGE, "%s: pAdapter is NULL!", __func__);
+ return VOS_STATUS_E_FAILURE;
+ }
+
+ /* create the event */
+ memset(&wrqu, 0, sizeof(wrqu));
+ memset(metrics_notification, 0, sizeof(metrics_notification));
+
+ wrqu.data.pointer = metrics_notification;
+ wrqu.data.length = scnprintf(metrics_notification,
+ sizeof(metrics_notification), "QCOM: LFR_PREAUTH_HANDOVER "
+ MAC_ADDRESS_STR, MAC_ADDR_ARRAY(pRoamInfo->bssid));
+
+ wireless_send_event(pAdapter->dev, IWEVCUSTOM, &wrqu, metrics_notification);
+
+ EXIT();
+
+ return VOS_STATUS_SUCCESS;
+}
+#endif
+
/*
* FUNCTION: hdd_cfg80211_scan_done_callback
* scanning callback function, called after finishing scan
@@ -4365,7 +4480,7 @@
goto allow_suspend;
}
- if(pScanInfo->mScanPending != VOS_TRUE)
+ if (pScanInfo->mScanPending != VOS_TRUE)
{
VOS_ASSERT(pScanInfo->mScanPending);
goto allow_suspend;
diff --git a/CORE/SME/inc/csrApi.h b/CORE/SME/inc/csrApi.h
index e53b8e9..85b97e3 100644
--- a/CORE/SME/inc/csrApi.h
+++ b/CORE/SME/inc/csrApi.h
@@ -451,6 +451,12 @@
#ifdef FEATURE_WLAN_LFR
eCSR_ROAM_PMK_NOTIFY,
#endif
+#ifdef FEATURE_WLAN_LFR_METRICS
+ eCSR_ROAM_PREAUTH_INIT_NOTIFY,
+ eCSR_ROAM_PREAUTH_STATUS_SUCCESS,
+ eCSR_ROAM_PREAUTH_STATUS_FAILURE,
+ eCSR_ROAM_HANDOVER_SUCCESS,
+#endif
#ifdef FEATURE_WLAN_TDLS
eCSR_ROAM_TDLS_STATUS_UPDATE,
eCSR_ROAM_RESULT_MGMT_TX_COMPLETE_IND,
diff --git a/CORE/SME/src/csr/csrNeighborRoam.c b/CORE/SME/src/csr/csrNeighborRoam.c
index c138ca5..48d776e 100644
--- a/CORE/SME/src/csr/csrNeighborRoam.c
+++ b/CORE/SME/src/csr/csrNeighborRoam.c
@@ -983,6 +983,10 @@
tpCsrNeighborRoamControlInfo pNeighborRoamInfo = &pMac->roam.neighborRoamInfo;
eHalStatus status = eHAL_STATUS_SUCCESS;
tpCsrNeighborRoamBSSInfo pNeighborBssNode;
+
+#ifdef FEATURE_WLAN_LFR_METRICS
+ tCsrRoamInfo *roamInfo;
+#endif
/* This must not be true here */
VOS_ASSERT(pNeighborRoamInfo->FTRoamInfo.preauthRspPending == eANI_BOOLEAN_FALSE);
@@ -1000,6 +1004,25 @@
}
else
{
+#ifdef FEATURE_WLAN_LFR_METRICS
+ /* LFR metrics - pre-auth initiation metric.
+ Send the event to supplicant that pre-auth was initiated */
+ roamInfo = vos_mem_malloc(sizeof(tCsrRoamInfo));
+ if (NULL == roamInfo)
+ {
+ smsLog(pMac, LOG1, FL("Memory allocation failed!"));
+ }
+ else
+ {
+ vos_mem_copy((void *)roamInfo->bssid,
+ (void *)pNeighborBssNode->pBssDescription->bssId,
+ sizeof(tCsrBssid));
+ csrRoamCallCallback(pMac, pNeighborRoamInfo->csrSessionId,
+ roamInfo, 0, eCSR_ROAM_PREAUTH_INIT_NOTIFY, 0);
+ vos_mem_free(pRoamInfo);
+ }
+#endif
+
status = csrRoamEnqueuePreauth(pMac, pNeighborRoamInfo->csrSessionId, pNeighborBssNode->pBssDescription,
eCsrPerformPreauth, eANI_BOOLEAN_TRUE);
@@ -1057,6 +1080,10 @@
eHalStatus preauthProcessed = eHAL_STATUS_SUCCESS;
tpCsrNeighborRoamBSSInfo pPreauthRspNode = NULL;
+#ifdef FEATURE_WLAN_LFR_METRICS
+ tCsrRoamInfo *roamInfo;
+#endif
+
if (eANI_BOOLEAN_FALSE == pNeighborRoamInfo->FTRoamInfo.preauthRspPending)
{
@@ -1101,6 +1128,25 @@
pPreauthRspNode->pBssDescription->bssId[5],
(int)pPreauthRspNode->pBssDescription->channelId);
+#ifdef FEATURE_WLAN_LFR_METRICS
+ /* LFR metrics - pre-auth completion metric.
+ Send the event to supplicant that pre-auth successfully completed */
+ roamInfo = vos_mem_malloc(sizeof(tCsrRoamInfo));
+ if (NULL == roamInfo)
+ {
+ smsLog(pMac, LOG1, FL("Memory allocation failed!"));
+ }
+ else
+ {
+ vos_mem_copy((void *)roamInfo->bssid,
+ (void *)pPreauthRspNode->pBssDescription->bssId,
+ sizeof(tCsrBssid));
+ csrRoamCallCallback(pMac, pNeighborRoamInfo->csrSessionId,
+ roamInfo, 0, eCSR_ROAM_PREAUTH_STATUS_SUCCESS, 0);
+ vos_mem_free(pRoamInfo);
+ }
+#endif
+
/* Preauth competer successfully. Insert the preauthenticated node to tail of preAuthDoneList */
csrNeighborRoamRemoveRoamableAPListEntry(pMac, &pNeighborRoamInfo->roamableAPList, pPreauthRspNode);
csrLLInsertTail(&pNeighborRoamInfo->FTRoamInfo.preAuthDoneList, &pPreauthRspNode->List, LL_ACCESS_LOCK);
@@ -1140,6 +1186,26 @@
{
status = csrNeighborRoamAddBssIdToPreauthFailList(pMac, pNeighborBssNode->pBssDescription->bssId);
}
+
+#ifdef FEATURE_WLAN_LFR_METRICS
+ /* LFR metrics - pre-auth completion metric. Send the event
+ to supplicant that pre-auth successfully completed */
+ roamInfo = vos_mem_malloc(sizeof(tCsrRoamInfo));
+ if (NULL == roamInfo)
+ {
+ smsLog(pMac, LOG1, FL("Memory allocation failed!"));
+ }
+ else
+ {
+ vos_mem_copy((void *)roamInfo->bssid,
+ (void *)pNeighborBssNode->pBssDescription->bssId,
+ sizeof(tCsrBssid));
+ csrRoamCallCallback(pMac, pNeighborRoamInfo->csrSessionId,
+ roamInfo, 0, eCSR_ROAM_PREAUTH_STATUS_FAILURE, 0);
+ vos_mem_free(pRoamInfo);
+ }
+#endif
+
/* Now we can free this node */
csrNeighborRoamFreeNeighborRoamBSSNode(pMac, pNeighborBssNode);
}
@@ -4480,6 +4546,10 @@
extern void csrRoamRoamingStateDisassocRspProcessor( tpAniSirGlobal pMac, tSirSmeDisassocRsp *pSmeDisassocRsp );
tANI_U32 roamId = 0;
+#ifdef FEATURE_WLAN_LFR_METRICS
+ tCsrRoamInfo *roamInfoMetrics;
+#endif
+
if (pMac->roam.neighborRoamInfo.neighborRoamState != eCSR_NEIGHBOR_ROAM_STATE_PREAUTH_DONE)
{
smsLog(pMac, LOGE, FL("Roam requested when Neighbor roam is in %d state"),
@@ -4503,7 +4573,25 @@
handoffNode.pBssDescription->bssId[3],
handoffNode.pBssDescription->bssId[4],
handoffNode.pBssDescription->bssId[5]);
-
+
+#ifdef FEATURE_WLAN_LFR_METRICS
+ /* LFR metrics - pre-auth completion metric.
+ Send the event to supplicant that pre-auth successfully completed */
+ roamInfoMetrics = vos_mem_malloc(sizeof(tCsrRoamInfo));
+ if (NULL == roamInfoMetrics)
+ {
+ smsLog(pMac, LOG1, FL("Memory allocation failed!"));
+ }
+ else
+ {
+ vos_mem_copy((void *)roamInfoMetrics->bssid,
+ (void *)&handoffNode.pBssDescription->bssId, sizeof(tCsrBssid));
+ csrRoamCallCallback(pMac, pNeighborRoamInfo->csrSessionId,
+ roamInfoMetrics, 0, eCSR_ROAM_HANDOVER_SUCCESS, 0);
+ vos_mem_free(pRoamInfo);
+ }
+#endif
+
/* Free the profile.. Just to make sure we dont leak memory here */
csrReleaseProfile(pMac, &pNeighborRoamInfo->csrNeighborRoamProfile);
/* Create the Handoff AP profile. Copy the currently connected profile and update only the BSSID and channel number