Home | History | Annotate | Download | only in wifi_hal
      1 /*
      2  * Copyright (C) 2014 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *     http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 #define LOG_TAG  "WifiHAL"
     18 
     19 #include <utils/Log.h>
     20 #include "gscan_event_handler.h"
     21 #include "vendor_definitions.h"
     22 
     23 /* This function implements creation of Vendor command event handler. */
     24 int GScanCommandEventHandler::create() {
     25     int ret = mMsg.create(NL80211_CMD_VENDOR, 0, 0);
     26     if (ret < 0) {
     27         return ret;
     28     }
     29 
     30     /* Insert the oui in the msg */
     31     ret = mMsg.put_u32(NL80211_ATTR_VENDOR_ID, mVendor_id);
     32     if (ret < 0)
     33         goto out;
     34 
     35     /* Insert the subcmd in the msg */
     36     ret = mMsg.put_u32(NL80211_ATTR_VENDOR_SUBCMD, mSubcmd);
     37     if (ret < 0)
     38         goto out;
     39 out:
     40     return ret;
     41 }
     42 
     43 int GScanCommandEventHandler::get_request_id()
     44 {
     45     return mRequestId;
     46 }
     47 
     48 void GScanCommandEventHandler::set_request_id(int request_id)
     49 {
     50     mRequestId = request_id;
     51 }
     52 
     53 void GScanCommandEventHandler::enableEventHandling()
     54 {
     55     mEventHandlingEnabled = true;
     56 }
     57 
     58 void GScanCommandEventHandler::disableEventHandling()
     59 {
     60     mEventHandlingEnabled = false;
     61 }
     62 
     63 bool GScanCommandEventHandler::isEventHandlingEnabled()
     64 {
     65     return mEventHandlingEnabled;
     66 }
     67 
     68 void GScanCommandEventHandler::setCallbackHandler(GScanCallbackHandler handler)
     69 {
     70     mHandler = handler;
     71 }
     72 
     73 GScanCommandEventHandler::GScanCommandEventHandler(wifi_handle handle, int id,
     74                                                 u32 vendor_id,
     75                                                 u32 subcmd,
     76                                                 GScanCallbackHandler handler)
     77         : WifiVendorCommand(handle, id, vendor_id, subcmd)
     78 {
     79     int ret = 0;
     80     mRequestId = id;
     81     mHandler = handler;
     82     mSubCommandId = subcmd;
     83     mHotlistApFoundResults = NULL;
     84     mHotlistApFoundNumResults = 0;
     85     mHotlistApFoundMoreData = false;
     86     mHotlistApLostResults = NULL;
     87     mHotlistApLostNumResults = 0;
     88     mHotlistApLostMoreData = false;
     89     mSignificantChangeResults = NULL;
     90     mSignificantChangeNumResults = 0;
     91     mSignificantChangeMoreData = false;
     92     mHotlistSsidFoundNumResults = 0;
     93     mHotlistSsidFoundMoreData = false;
     94     mHotlistSsidLostNumResults = 0;
     95     mHotlistSsidLostMoreData = false;
     96     mHotlistSsidFoundResults = NULL;
     97     mHotlistSsidLostResults = NULL;
     98     mPnoNetworkFoundResults = NULL;
     99     mPnoNetworkFoundNumResults = 0;
    100     mPnoNetworkFoundMoreData = false;
    101     mPasspointNetworkFoundResult = NULL;
    102     mPasspointAnqp = NULL;
    103     mPasspointAnqpLen = 0;
    104     mPasspointNetId = -1;
    105     mEventHandlingEnabled = false;
    106 
    107     switch(mSubCommandId)
    108     {
    109         case QCA_NL80211_VENDOR_SUBCMD_GSCAN_START:
    110         {
    111             /* Register handlers for northbound asychronous scan events. */
    112             ret = registerVendorHandler(mVendor_id,
    113                     QCA_NL80211_VENDOR_SUBCMD_GSCAN_SCAN_RESULTS_AVAILABLE) ||
    114                   registerVendorHandler(mVendor_id,
    115                     QCA_NL80211_VENDOR_SUBCMD_GSCAN_FULL_SCAN_RESULT) ||
    116                   registerVendorHandler(mVendor_id,
    117                     QCA_NL80211_VENDOR_SUBCMD_GSCAN_SCAN_EVENT);
    118             if (ret)
    119                 ALOGE("%s: Error in registering handler for "
    120                     "GSCAN_START. \n", __FUNCTION__);
    121         }
    122         break;
    123 
    124         case QCA_NL80211_VENDOR_SUBCMD_GSCAN_SET_SIGNIFICANT_CHANGE:
    125         {
    126             ret = registerVendorHandler(mVendor_id,
    127                     QCA_NL80211_VENDOR_SUBCMD_GSCAN_SIGNIFICANT_CHANGE);
    128             if (ret)
    129                 ALOGE("%s: Error in registering handler for "
    130                     "GSCAN_SIGNIFICANT_CHANGE. \n", __FUNCTION__);
    131         }
    132         break;
    133 
    134         case QCA_NL80211_VENDOR_SUBCMD_GSCAN_SET_BSSID_HOTLIST:
    135         {
    136             ret = registerVendorHandler(mVendor_id,
    137                     QCA_NL80211_VENDOR_SUBCMD_GSCAN_HOTLIST_AP_FOUND);
    138             if (ret)
    139                 ALOGE("%s: Error in registering handler for"
    140                     " GSCAN_HOTLIST_AP_FOUND. \n", __FUNCTION__);
    141 
    142             ret = registerVendorHandler(mVendor_id,
    143                     QCA_NL80211_VENDOR_SUBCMD_GSCAN_HOTLIST_AP_LOST);
    144             if (ret)
    145                 ALOGE("%s: Error in registering handler for"
    146                     " GSCAN_HOTLIST_AP_LOST. \n", __FUNCTION__);
    147         }
    148         break;
    149 
    150         case QCA_NL80211_VENDOR_SUBCMD_PNO_SET_LIST:
    151         {
    152             ret = registerVendorHandler(mVendor_id,
    153                     QCA_NL80211_VENDOR_SUBCMD_PNO_NETWORK_FOUND);
    154             if (ret)
    155                 ALOGE("%s: Error in registering handler for"
    156                     " PNO_NETWORK_FOUND. \n", __FUNCTION__);
    157         }
    158         break;
    159 
    160         case QCA_NL80211_VENDOR_SUBCMD_PNO_SET_PASSPOINT_LIST:
    161         {
    162             ret = registerVendorHandler(mVendor_id,
    163                 QCA_NL80211_VENDOR_SUBCMD_PNO_PASSPOINT_NETWORK_FOUND);
    164             if (ret)
    165                 ALOGE("%s: Error in registering handler for"
    166                     " PNO_PASSPOINT_NETWORK_FOUND. \n", __FUNCTION__);
    167         }
    168         break;
    169     }
    170 }
    171 
    172 GScanCommandEventHandler::~GScanCommandEventHandler()
    173 {
    174     switch(mSubCommandId)
    175     {
    176         case QCA_NL80211_VENDOR_SUBCMD_GSCAN_START:
    177         {
    178             /* Unregister event handlers. */
    179             unregisterVendorHandler(mVendor_id,
    180                     QCA_NL80211_VENDOR_SUBCMD_GSCAN_SCAN_RESULTS_AVAILABLE);
    181             unregisterVendorHandler(mVendor_id,
    182                     QCA_NL80211_VENDOR_SUBCMD_GSCAN_FULL_SCAN_RESULT);
    183             unregisterVendorHandler(mVendor_id,
    184                     QCA_NL80211_VENDOR_SUBCMD_GSCAN_SCAN_EVENT);
    185         }
    186         break;
    187 
    188         case QCA_NL80211_VENDOR_SUBCMD_GSCAN_SET_SIGNIFICANT_CHANGE:
    189         {
    190             unregisterVendorHandler(mVendor_id,
    191                     QCA_NL80211_VENDOR_SUBCMD_GSCAN_SIGNIFICANT_CHANGE);
    192         }
    193         break;
    194 
    195         case QCA_NL80211_VENDOR_SUBCMD_GSCAN_SET_BSSID_HOTLIST:
    196         {
    197             unregisterVendorHandler(mVendor_id,
    198                     QCA_NL80211_VENDOR_SUBCMD_GSCAN_HOTLIST_AP_FOUND);
    199             unregisterVendorHandler(mVendor_id,
    200                     QCA_NL80211_VENDOR_SUBCMD_GSCAN_HOTLIST_AP_LOST);
    201         }
    202         break;
    203 
    204         case QCA_NL80211_VENDOR_SUBCMD_PNO_SET_LIST:
    205         {
    206             unregisterVendorHandler(mVendor_id,
    207                 QCA_NL80211_VENDOR_SUBCMD_PNO_NETWORK_FOUND);
    208         }
    209         break;
    210 
    211         case QCA_NL80211_VENDOR_SUBCMD_PNO_SET_PASSPOINT_LIST:
    212         {
    213             unregisterVendorHandler(mVendor_id,
    214                 QCA_NL80211_VENDOR_SUBCMD_PNO_PASSPOINT_NETWORK_FOUND);
    215         }
    216         break;
    217     }
    218 }
    219 
    220 wifi_error GScanCommandEventHandler::gscan_parse_hotlist_ap_results(
    221                                             u32 num_results,
    222                                             wifi_scan_result *results,
    223                                             u32 starting_index,
    224                                             struct nlattr **tb_vendor)
    225 {
    226     u32 i = starting_index;
    227     struct nlattr *scanResultsInfo;
    228     int rem = 0;
    229     u32 len = 0;
    230     ALOGV("gscan_parse_hotlist_ap_results: starting counter: %d", i);
    231 
    232     for (scanResultsInfo = (struct nlattr *) nla_data(tb_vendor[
    233             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_LIST]),
    234             rem = nla_len(tb_vendor[
    235             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_LIST
    236             ]);
    237                 nla_ok(scanResultsInfo, rem);
    238                 scanResultsInfo = nla_next(scanResultsInfo, &(rem)))
    239     {
    240         struct nlattr *tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX + 1];
    241         nla_parse(tb2, QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX,
    242         (struct nlattr *) nla_data(scanResultsInfo),
    243                 nla_len(scanResultsInfo), NULL);
    244 
    245         if (!
    246             tb2[
    247                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_TIME_STAMP
    248                 ])
    249         {
    250             ALOGE("gscan_parse_hotlist_ap_results: "
    251                 "RESULTS_SCAN_RESULT_TIME_STAMP not found");
    252             return WIFI_ERROR_INVALID_ARGS;
    253         }
    254         results[i].ts =
    255             nla_get_u64(
    256             tb2[
    257                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_TIME_STAMP
    258                 ]);
    259         if (!
    260             tb2[
    261                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID
    262                 ])
    263         {
    264             ALOGE("gscan_parse_hotlist_ap_results: "
    265                 "RESULTS_SCAN_RESULT_SSID not found");
    266             return WIFI_ERROR_INVALID_ARGS;
    267         }
    268         len = nla_len(tb2[
    269                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID]);
    270         len =
    271             sizeof(results->ssid) <= len ? sizeof(results->ssid) : len;
    272         memcpy((void *)&results[i].ssid,
    273             nla_data(
    274             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID]), len);
    275         if (!
    276             tb2[
    277                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID
    278                 ])
    279         {
    280             ALOGE("gscan_parse_hotlist_ap_results: "
    281                 "RESULTS_SCAN_RESULT_BSSID not found");
    282             return WIFI_ERROR_INVALID_ARGS;
    283         }
    284         len = nla_len(
    285             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID]);
    286         len =
    287             sizeof(results->bssid) <= len ? sizeof(results->bssid) : len;
    288         memcpy(&results[i].bssid,
    289             nla_data(
    290             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID]), len);
    291         if (!
    292             tb2[
    293                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CHANNEL
    294                 ])
    295         {
    296             ALOGE("gscan_parse_hotlist_ap_results: "
    297                 "RESULTS_SCAN_RESULT_CHANNEL not found");
    298             return WIFI_ERROR_INVALID_ARGS;
    299         }
    300         results[i].channel =
    301             nla_get_u32(
    302             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CHANNEL]);
    303         if (!
    304             tb2[
    305                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RSSI
    306                 ])
    307         {
    308             ALOGE("gscan_parse_hotlist_ap_results: "
    309                 "RESULTS_SCAN_RESULT_RSSI not found");
    310             return WIFI_ERROR_INVALID_ARGS;
    311         }
    312         results[i].rssi =
    313             get_s32(
    314             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RSSI]);
    315         if (!
    316             tb2[
    317                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT
    318                 ])
    319         {
    320             ALOGE("gscan_parse_hotlist_ap_results: "
    321                 "RESULTS_SCAN_RESULT_RTT not found");
    322             return WIFI_ERROR_INVALID_ARGS;
    323         }
    324         results[i].rtt =
    325             nla_get_u32(
    326             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT]);
    327         if (!
    328             tb2[
    329                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT_SD
    330             ])
    331         {
    332             ALOGE("gscan_parse_hotlist_ap_results: "
    333                 "RESULTS_SCAN_RESULT_RTT_SD not found");
    334             return WIFI_ERROR_INVALID_ARGS;
    335         }
    336         results[i].rtt_sd =
    337             nla_get_u32(
    338             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT_SD]);
    339 
    340         ALOGV("gscan_parse_hotlist_ap_results: ts %" PRId64 " SSID  %s "
    341               "BSSID: %02x:%02x:%02x:%02x:%02x:%02x channel %d rssi %d "
    342               "rtt %" PRId64" rtt_sd %" PRId64,
    343               results[i].ts, results[i].ssid,
    344               results[i].bssid[0], results[i].bssid[1], results[i].bssid[2],
    345               results[i].bssid[3], results[i].bssid[4], results[i].bssid[5],
    346               results[i].channel, results[i].rssi, results[i].rtt,
    347               results[i].rtt_sd);
    348         /* Increment loop index for next record */
    349         i++;
    350     }
    351     return WIFI_SUCCESS;
    352 }
    353 
    354 static wifi_error gscan_get_significant_change_results(u32 num_results,
    355                                     wifi_significant_change_result **results,
    356                                     u32 starting_index,
    357                                     struct nlattr **tb_vendor)
    358 {
    359     u32 i = starting_index;
    360     int j;
    361     int rem = 0;
    362     u32 len = 0;
    363     char rssi_buf[1024]; //TODO: sizeof buf
    364     int rem_size;
    365     struct nlattr *scanResultsInfo;
    366 
    367     for (scanResultsInfo = (struct nlattr *) nla_data(tb_vendor[
    368             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_LIST]),
    369             rem = nla_len(tb_vendor[
    370             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_LIST]);
    371         nla_ok(scanResultsInfo, rem);
    372         scanResultsInfo = nla_next(scanResultsInfo, &(rem)))
    373     {
    374         struct nlattr *tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX + 1];
    375         nla_parse(tb2, QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX,
    376             (struct nlattr *) nla_data(scanResultsInfo),
    377                 nla_len(scanResultsInfo), NULL);
    378         if (!
    379             tb2[
    380             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SIGNIFICANT_CHANGE_RESULT_BSSID
    381             ])
    382         {
    383             ALOGE("gscan_get_significant_change_results: "
    384                 "SIGNIFICANT_CHANGE_RESULT_BSSID not found");
    385             return WIFI_ERROR_INVALID_ARGS;
    386         }
    387         len = nla_len(
    388             tb2[
    389             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SIGNIFICANT_CHANGE_RESULT_BSSID]
    390             );
    391         len =
    392             sizeof(results[i]->bssid) <= len ? sizeof(results[i]->bssid) : len;
    393         memcpy(&results[i]->bssid[0],
    394             nla_data(
    395             tb2[
    396         QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SIGNIFICANT_CHANGE_RESULT_BSSID]),
    397             len);
    398 
    399         if (!
    400             tb2[
    401         QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SIGNIFICANT_CHANGE_RESULT_CHANNEL
    402                 ])
    403         {
    404             ALOGE("gscan_get_significant_change_results: "
    405                 "SIGNIFICANT_CHANGE_RESULT_CHANNEL not found");
    406             return WIFI_ERROR_INVALID_ARGS;
    407         }
    408         results[i]->channel =
    409             nla_get_u32(
    410             tb2[
    411         QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SIGNIFICANT_CHANGE_RESULT_CHANNEL]);
    412 
    413         if (!
    414             tb2[
    415         QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SIGNIFICANT_CHANGE_RESULT_NUM_RSSI
    416             ])
    417         {
    418             ALOGE("gscan_get_significant_change_results: "
    419                 "SIGNIFICANT_CHANGE_RESULT_NUM_RSSI not found");
    420             return WIFI_ERROR_INVALID_ARGS;
    421         }
    422         results[i]->num_rssi =
    423             nla_get_u32(
    424             tb2[
    425         QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SIGNIFICANT_CHANGE_RESULT_NUM_RSSI]);
    426 
    427         if (!
    428             tb2[
    429         QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SIGNIFICANT_CHANGE_RESULT_RSSI_LIST
    430             ])
    431         {
    432             ALOGE("gscan_get_significant_change_results: "
    433                 "SIGNIFICANT_CHANGE_RESULT_RSSI_LIST not found");
    434             return WIFI_ERROR_INVALID_ARGS;
    435         }
    436 
    437         memcpy(&(results[i]->rssi[0]),
    438             nla_data(
    439             tb2[
    440         QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SIGNIFICANT_CHANGE_RESULT_RSSI_LIST]
    441             ), results[i]->num_rssi * sizeof(wifi_rssi));
    442 
    443         ALOGV("significant_change_result:%d, BSSID:"
    444             "%02x:%02x:%02x:%02x:%02x:%02x channel:%d  num_rssi:%d ",
    445             i, results[i]->bssid[0], results[i]->bssid[1], results[i]->bssid[2],
    446             results[i]->bssid[3], results[i]->bssid[4], results[i]->bssid[5],
    447             results[i]->channel, results[i]->num_rssi);
    448 
    449         rem_size = sizeof(rssi_buf);
    450         char *dst = rssi_buf;
    451         for (j = 0; j < results[i]->num_rssi && rem_size > 0; j++) {
    452             len = snprintf(dst, rem_size, "rssi[%d]:%d, ", j, results[i]->rssi[j]);
    453             dst += len;
    454             rem_size -= len;
    455         }
    456         ALOGV("RSSI LIST: %s", rssi_buf);
    457 
    458         /* Increment loop index to prase next record. */
    459         i++;
    460     }
    461     return WIFI_SUCCESS;
    462 }
    463 
    464 wifi_error GScanCommandEventHandler::gscan_parse_hotlist_ssid_results(
    465                                             u32 num_results,
    466                                             wifi_scan_result *results,
    467                                             u32 starting_index,
    468                                             struct nlattr **tb_vendor)
    469 {
    470     u32 i = starting_index;
    471     struct nlattr *scanResultsInfo;
    472     int rem = 0;
    473     u32 len = 0;
    474 
    475     for (scanResultsInfo = (struct nlattr *) nla_data(tb_vendor[
    476             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_LIST]),
    477             rem = nla_len(tb_vendor[
    478             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_LIST
    479             ]);
    480                 nla_ok(scanResultsInfo, rem);
    481                 scanResultsInfo = nla_next(scanResultsInfo, &(rem)))
    482     {
    483         struct nlattr *tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX + 1];
    484         nla_parse(tb2, QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX,
    485         (struct nlattr *) nla_data(scanResultsInfo),
    486                 nla_len(scanResultsInfo), NULL);
    487 
    488         if (!
    489             tb2[
    490                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_TIME_STAMP
    491                 ])
    492         {
    493             ALOGE("gscan_parse_hotlist_ssid_results: "
    494                 "RESULTS_SCAN_RESULT_TIME_STAMP not found");
    495             return WIFI_ERROR_INVALID_ARGS;
    496         }
    497         results[i].ts =
    498             nla_get_u64(
    499             tb2[
    500                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_TIME_STAMP
    501                 ]);
    502         if (!
    503             tb2[
    504                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID
    505                 ])
    506         {
    507             ALOGE("gscan_parse_hotlist_ssid_results: "
    508                 "RESULTS_SCAN_RESULT_SSID not found");
    509             return WIFI_ERROR_INVALID_ARGS;
    510         }
    511         len = nla_len(tb2[
    512                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID]);
    513         len =
    514             sizeof(results->ssid) <= len ? sizeof(results->ssid) : len;
    515         memcpy((void *)&results[i].ssid,
    516             nla_data(
    517             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID]), len);
    518         if (!
    519             tb2[
    520                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID
    521                 ])
    522         {
    523             ALOGE("gscan_parse_hotlist_ssid_results: "
    524                 "RESULTS_SCAN_RESULT_BSSID not found");
    525             return WIFI_ERROR_INVALID_ARGS;
    526         }
    527         len = nla_len(
    528             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID]);
    529         len =
    530             sizeof(results->bssid) <= len ? sizeof(results->bssid) : len;
    531         memcpy(&results[i].bssid,
    532             nla_data(
    533             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID]), len);
    534         if (!
    535             tb2[
    536                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CHANNEL
    537                 ])
    538         {
    539             ALOGE("gscan_parse_hotlist_ssid_results: "
    540                 "RESULTS_SCAN_RESULT_CHANNEL not found");
    541             return WIFI_ERROR_INVALID_ARGS;
    542         }
    543         results[i].channel =
    544             nla_get_u32(
    545             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CHANNEL]);
    546         if (!
    547             tb2[
    548                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RSSI
    549                 ])
    550         {
    551             ALOGE("gscan_parse_hotlist_ssid_results: "
    552                 "RESULTS_SCAN_RESULT_RSSI not found");
    553             return WIFI_ERROR_INVALID_ARGS;
    554         }
    555         results[i].rssi =
    556             get_s32(
    557             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RSSI]);
    558         if (!
    559             tb2[
    560                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT
    561                 ])
    562         {
    563             ALOGE("gscan_parse_hotlist_ssid_results: "
    564                 "RESULTS_SCAN_RESULT_RTT not found");
    565             return WIFI_ERROR_INVALID_ARGS;
    566         }
    567         results[i].rtt =
    568             nla_get_u32(
    569             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT]);
    570         if (!
    571             tb2[
    572                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT_SD
    573             ])
    574         {
    575             ALOGE("gscan_parse_hotlist_ssid_results: "
    576                 "RESULTS_SCAN_RESULT_RTT_SD not found");
    577             return WIFI_ERROR_INVALID_ARGS;
    578         }
    579         results[i].rtt_sd =
    580             nla_get_u32(
    581             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT_SD]);
    582 
    583         ALOGV("gscan_parse_hotlist_ssid_results: ts %" PRId64 " SSID  %s "
    584               "BSSID: %02x:%02x:%02x:%02x:%02x:%02x channel %d rssi %d "
    585               "rtt %" PRId64 " rtt_sd %" PRId64,
    586               results[i].ts, results[i].ssid,
    587               results[i].bssid[0], results[i].bssid[1], results[i].bssid[2],
    588               results[i].bssid[3], results[i].bssid[4], results[i].bssid[5],
    589               results[i].channel, results[i].rssi, results[i].rtt,
    590               results[i].rtt_sd);
    591         /* Increment loop index for next record */
    592         i++;
    593     }
    594     return WIFI_SUCCESS;
    595 }
    596 
    597 wifi_error GScanCommandEventHandler::gscan_parse_passpoint_network_result(
    598             struct nlattr **tb_vendor)
    599 {
    600     struct nlattr *scanResultsInfo, *wifiScanResultsInfo;
    601     u32 resultsBufSize = 0;
    602     u32 len = 0;
    603     int rem = 0;
    604 
    605     for (scanResultsInfo = (struct nlattr *) nla_data(tb_vendor[
    606             QCA_WLAN_VENDOR_ATTR_GSCAN_PNO_RESULTS_PASSPOINT_MATCH_RESULT_LIST]),
    607             rem = nla_len(tb_vendor[
    608             QCA_WLAN_VENDOR_ATTR_GSCAN_PNO_RESULTS_PASSPOINT_MATCH_RESULT_LIST
    609             ]);
    610                 nla_ok(scanResultsInfo, rem);
    611                 scanResultsInfo = nla_next(scanResultsInfo, &(rem)))
    612     {
    613         struct nlattr *tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX + 1];
    614         nla_parse(tb2, QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX,
    615         (struct nlattr *) nla_data(scanResultsInfo),
    616                 nla_len(scanResultsInfo), NULL);
    617 
    618         if (!
    619             tb2[
    620                 QCA_WLAN_VENDOR_ATTR_GSCAN_PNO_RESULTS_PASSPOINT_MATCH_ID
    621                 ])
    622         {
    623             ALOGE("%s: GSCAN_PNO_RESULTS_PASSPOINT_MATCH_ID not found",
    624                   __FUNCTION__);
    625             return WIFI_ERROR_INVALID_ARGS;
    626         }
    627         mPasspointNetId =
    628             nla_get_u32(
    629             tb2[
    630                 QCA_WLAN_VENDOR_ATTR_GSCAN_PNO_RESULTS_PASSPOINT_MATCH_ID
    631                 ]);
    632 
    633         for (wifiScanResultsInfo = (struct nlattr *) nla_data(tb2[
    634              QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_LIST]),
    635              rem = nla_len(tb2[
    636              QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_LIST
    637              ]);
    638              nla_ok(wifiScanResultsInfo, rem);
    639              wifiScanResultsInfo = nla_next(wifiScanResultsInfo, &(rem)))
    640         {
    641             struct nlattr *tb3[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX + 1];
    642             nla_parse(tb3, QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX,
    643             (struct nlattr *) nla_data(wifiScanResultsInfo),
    644                      nla_len(wifiScanResultsInfo), NULL);
    645 
    646             resultsBufSize = sizeof(wifi_scan_result);
    647             if (!
    648                 tb3[
    649                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_IE_LENGTH
    650                 ])
    651             {
    652                 ALOGE("%s: RESULTS_SCAN_RESULT_IE_LENGTH not found", __FUNCTION__);
    653                 return WIFI_ERROR_INVALID_ARGS;
    654             }
    655             resultsBufSize +=
    656                 nla_get_u32(
    657                 tb3[
    658                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_IE_LENGTH]);
    659 
    660             /* Allocate the appropriate memory for mPasspointNetworkFoundResult */
    661             mPasspointNetworkFoundResult = (wifi_scan_result *)
    662                                 malloc (resultsBufSize);
    663 
    664             if (!mPasspointNetworkFoundResult) {
    665                 ALOGE("%s: Failed to alloc memory for result struct. Exit.\n",
    666                     __FUNCTION__);
    667                 return WIFI_ERROR_OUT_OF_MEMORY;
    668             }
    669             memset(mPasspointNetworkFoundResult, 0, resultsBufSize);
    670 
    671             mPasspointNetworkFoundResult->ie_length =
    672                 nla_get_u32(
    673                 tb3[
    674                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_IE_LENGTH]);
    675 
    676             if (!
    677                 tb3[
    678                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_TIME_STAMP
    679                     ])
    680             {
    681                 ALOGE("%s: RESULTS_SCAN_RESULT_TIME_STAMP not found",
    682                       __FUNCTION__);
    683                 return WIFI_ERROR_INVALID_ARGS;
    684             }
    685             mPasspointNetworkFoundResult->ts =
    686                 nla_get_u64(
    687                 tb3[
    688                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_TIME_STAMP
    689                     ]);
    690             if (!
    691                 tb3[
    692                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID
    693                     ])
    694             {
    695                 ALOGE("%s: RESULTS_SCAN_RESULT_SSID not found", __FUNCTION__);
    696                 return WIFI_ERROR_INVALID_ARGS;
    697             }
    698              len = nla_len(tb3[
    699                      QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID]);
    700              len =
    701                  sizeof(mPasspointNetworkFoundResult->ssid) <= len ?
    702                  sizeof(mPasspointNetworkFoundResult->ssid) : len;
    703              memcpy((void *)&(mPasspointNetworkFoundResult->ssid[0]),
    704                  nla_data(
    705                  tb3[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID]), len);
    706              if (!
    707                  tb3[
    708                      QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID
    709                      ])
    710              {
    711                  ALOGE("%s: RESULTS_SCAN_RESULT_BSSID not found", __FUNCTION__);
    712                  return WIFI_ERROR_INVALID_ARGS;
    713              }
    714              len = nla_len(
    715                  tb3[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID]);
    716              len =
    717                  sizeof(mPasspointNetworkFoundResult->bssid) <= len ?
    718                  sizeof(mPasspointNetworkFoundResult->bssid) : len;
    719              memcpy(&(mPasspointNetworkFoundResult->bssid[0]),
    720                  nla_data(
    721                  tb3[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID]),
    722                  len);
    723              if (!
    724                  tb3[
    725                      QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CHANNEL
    726                      ])
    727              {
    728                  ALOGE("%s: RESULTS_SCAN_RESULT_CHANNEL not found", __FUNCTION__);
    729                  return WIFI_ERROR_INVALID_ARGS;
    730              }
    731              mPasspointNetworkFoundResult->channel =
    732                  nla_get_u32(
    733                  tb3[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CHANNEL]);
    734              if (!
    735                  tb3[
    736                      QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RSSI
    737                      ])
    738              {
    739                  ALOGE("%s: RESULTS_SCAN_RESULT_RSSI not found", __FUNCTION__);
    740                  return WIFI_ERROR_INVALID_ARGS;
    741              }
    742              mPasspointNetworkFoundResult->rssi =
    743                  get_s32(
    744                  tb3[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RSSI]);
    745              if (!
    746                  tb3[
    747                      QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT
    748                      ])
    749              {
    750                  ALOGE("%s: RESULTS_SCAN_RESULT_RTT not found", __FUNCTION__);
    751                  return WIFI_ERROR_INVALID_ARGS;
    752              }
    753              mPasspointNetworkFoundResult->rtt =
    754                  nla_get_u32(
    755                  tb3[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT]);
    756              if (!
    757                  tb3[
    758                      QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT_SD
    759                  ])
    760              {
    761                  ALOGE("%s: RESULTS_SCAN_RESULT_RTT_SD not found", __FUNCTION__);
    762                  return WIFI_ERROR_INVALID_ARGS;
    763              }
    764              mPasspointNetworkFoundResult->rtt_sd =
    765                  nla_get_u32(
    766                  tb3[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT_SD]);
    767 
    768              if (!
    769                  tb3[
    770                  QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BEACON_PERIOD])
    771              {
    772                  ALOGE("%s: RESULTS_SCAN_RESULT_BEACON_PERIOD not found",
    773                      __FUNCTION__);
    774                  return WIFI_ERROR_INVALID_ARGS;
    775              }
    776              mPasspointNetworkFoundResult->beacon_period =
    777                  nla_get_u16(
    778                  tb3[
    779                  QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BEACON_PERIOD]);
    780 
    781              if (!
    782                  tb3[
    783                      QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CAPABILITY
    784                      ])
    785              {
    786                  ALOGE("%s: RESULTS_SCAN_RESULT_CAPABILITY not found", __FUNCTION__);
    787                  return WIFI_ERROR_INVALID_ARGS;
    788              }
    789              mPasspointNetworkFoundResult->capability =
    790                  nla_get_u16(
    791                  tb3[
    792                  QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CAPABILITY]);
    793 
    794              if (!
    795                  tb3[
    796                      QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_IE_DATA
    797                  ])
    798              {
    799                  ALOGE("%s: RESULTS_SCAN_RESULT_IE_DATA not found", __FUNCTION__);
    800                  return WIFI_ERROR_INVALID_ARGS;
    801              }
    802              memcpy(&(mPasspointNetworkFoundResult->ie_data[0]),
    803                  nla_data(tb3[
    804                      QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_IE_DATA]),
    805                  mPasspointNetworkFoundResult->ie_length);
    806 
    807              ALOGV("%s: ts: %" PRId64 " SSID: %s "
    808                    "BSSID: %02x:%02x:%02x:%02x:%02x:%02x  channel: %d  rssi: %d"
    809                    " rtt: % " PRId64 " rtt_sd  %" PRId64 " ie_length  %u ",
    810                    __FUNCTION__, mPasspointNetworkFoundResult->ts,
    811                    mPasspointNetworkFoundResult->ssid,
    812                    mPasspointNetworkFoundResult->bssid[0],
    813                    mPasspointNetworkFoundResult->bssid[1],
    814                    mPasspointNetworkFoundResult->bssid[2],
    815                    mPasspointNetworkFoundResult->bssid[3],
    816                    mPasspointNetworkFoundResult->bssid[4],
    817                    mPasspointNetworkFoundResult->bssid[5],
    818                    mPasspointNetworkFoundResult->channel,
    819                    mPasspointNetworkFoundResult->rssi,
    820                    mPasspointNetworkFoundResult->rtt,
    821                    mPasspointNetworkFoundResult->rtt_sd,
    822                    mPasspointNetworkFoundResult->ie_length);
    823              ALOGV("%s: ie_data: ", __FUNCTION__);
    824              hexdump(mPasspointNetworkFoundResult->ie_data,
    825                      mPasspointNetworkFoundResult->ie_length);
    826         }
    827 
    828         if (!
    829            tb2[
    830                QCA_WLAN_VENDOR_ATTR_GSCAN_PNO_RESULTS_PASSPOINT_MATCH_ANQP_LEN
    831            ])
    832         {
    833             ALOGE("%s:PNO_RESULTS_PASSPOINT_MATCH_ANQP_LEN not found",
    834                   __FUNCTION__);
    835             return WIFI_ERROR_INVALID_ARGS;
    836         }
    837         mPasspointAnqpLen =
    838             nla_get_u32(
    839                 tb2[
    840                 QCA_WLAN_VENDOR_ATTR_GSCAN_PNO_RESULTS_PASSPOINT_MATCH_ANQP_LEN]);
    841 
    842         if (!mPasspointAnqpLen)
    843         {
    844             break;
    845         }
    846         mPasspointAnqp = (u8 *) malloc (mPasspointAnqpLen);
    847         if (!mPasspointAnqp) {
    848             ALOGE("%s: Failed to alloc memory for result struct. Exit.\n",
    849                   __FUNCTION__);
    850             return WIFI_ERROR_OUT_OF_MEMORY;
    851         }
    852 
    853         memset(mPasspointAnqp, 0, mPasspointAnqpLen);
    854         if (!
    855             tb2[
    856                 QCA_WLAN_VENDOR_ATTR_GSCAN_PNO_RESULTS_PASSPOINT_MATCH_ANQP
    857             ])
    858             {
    859             ALOGE("%s: RESULTS_PASSPOINT_MATCH_ANQP not found", __FUNCTION__);
    860             return WIFI_ERROR_INVALID_ARGS;
    861         }
    862         memcpy(&(mPasspointAnqp[0]),
    863                nla_data(tb2[
    864                  QCA_WLAN_VENDOR_ATTR_GSCAN_PNO_RESULTS_PASSPOINT_MATCH_ANQP]),
    865                mPasspointAnqpLen);
    866 
    867         ALOGV("%s: ANQP LEN:%d, ANQP IE:", __FUNCTION__, mPasspointAnqpLen);
    868         hexdump((char*)mPasspointAnqp, mPasspointAnqpLen);
    869 
    870         /* expecting only one result break out after the first loop */
    871         break;
    872     }
    873     return WIFI_SUCCESS;
    874 }
    875 
    876 wifi_error GScanCommandEventHandler::gscan_parse_pno_network_results(
    877                                             u32 num_results,
    878                                             wifi_scan_result *results,
    879                                             u32 starting_index,
    880                                             struct nlattr **tb_vendor)
    881 {
    882     u32 i = starting_index;
    883     struct nlattr *scanResultsInfo;
    884     int rem = 0;
    885     u32 len = 0;
    886 
    887     for (scanResultsInfo = (struct nlattr *) nla_data(tb_vendor[
    888             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_LIST]),
    889             rem = nla_len(tb_vendor[
    890             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_LIST
    891             ]);
    892                 nla_ok(scanResultsInfo, rem);
    893                 scanResultsInfo = nla_next(scanResultsInfo, &(rem)))
    894     {
    895         struct nlattr *tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX + 1];
    896         nla_parse(tb2, QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX,
    897         (struct nlattr *) nla_data(scanResultsInfo),
    898                 nla_len(scanResultsInfo), NULL);
    899 
    900         if (!
    901             tb2[
    902                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_TIME_STAMP
    903                 ])
    904         {
    905             ALOGE("gscan_parse_pno_network_results: "
    906                 "RESULTS_SCAN_RESULT_TIME_STAMP not found");
    907             return WIFI_ERROR_INVALID_ARGS;
    908         }
    909         results[i].ts =
    910             nla_get_u64(
    911             tb2[
    912                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_TIME_STAMP
    913                 ]);
    914         if (!
    915             tb2[
    916                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID
    917                 ])
    918         {
    919             ALOGE("gscan_parse_pno_network_results: "
    920                 "RESULTS_SCAN_RESULT_SSID not found");
    921             return WIFI_ERROR_INVALID_ARGS;
    922         }
    923         len = nla_len(tb2[
    924                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID]);
    925         len =
    926             sizeof(results->ssid) <= len ? sizeof(results->ssid) : len;
    927         memcpy((void *)&results[i].ssid,
    928             nla_data(
    929             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID]), len);
    930         if (!
    931             tb2[
    932                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID
    933                 ])
    934         {
    935             ALOGE("gscan_parse_pno_network_results: "
    936                 "RESULTS_SCAN_RESULT_BSSID not found");
    937             return WIFI_ERROR_INVALID_ARGS;
    938         }
    939         len = nla_len(
    940             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID]);
    941         len =
    942             sizeof(results->bssid) <= len ? sizeof(results->bssid) : len;
    943         memcpy(&results[i].bssid,
    944             nla_data(
    945             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID]), len);
    946         if (!
    947             tb2[
    948                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CHANNEL
    949                 ])
    950         {
    951             ALOGE("gscan_parse_pno_network_results: "
    952                 "RESULTS_SCAN_RESULT_CHANNEL not found");
    953             return WIFI_ERROR_INVALID_ARGS;
    954         }
    955         results[i].channel =
    956             nla_get_u32(
    957             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CHANNEL]);
    958         if (!
    959             tb2[
    960                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RSSI
    961                 ])
    962         {
    963             ALOGE("gscan_parse_pno_network_results: "
    964                 "RESULTS_SCAN_RESULT_RSSI not found");
    965             return WIFI_ERROR_INVALID_ARGS;
    966         }
    967         results[i].rssi =
    968             get_s32(
    969             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RSSI]);
    970         if (!
    971             tb2[
    972                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT
    973                 ])
    974         {
    975             ALOGE("gscan_parse_pno_network_results: "
    976                 "RESULTS_SCAN_RESULT_RTT not found");
    977             return WIFI_ERROR_INVALID_ARGS;
    978         }
    979         results[i].rtt =
    980             nla_get_u32(
    981             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT]);
    982         if (!
    983             tb2[
    984                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT_SD
    985             ])
    986         {
    987             ALOGE("gscan_parse_pno_network_results: "
    988                 "RESULTS_SCAN_RESULT_RTT_SD not found");
    989             return WIFI_ERROR_INVALID_ARGS;
    990         }
    991         results[i].rtt_sd =
    992             nla_get_u32(
    993             tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT_SD]);
    994 
    995         if (!
    996             tb2[
    997             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BEACON_PERIOD])
    998         {
    999             ALOGE("gscan_parse_pno_network_results: "
   1000                 "RESULTS_SCAN_RESULT_BEACON_PERIOD not found");
   1001             return WIFI_ERROR_INVALID_ARGS;
   1002         }
   1003         results[i].beacon_period =
   1004             nla_get_u16(
   1005             tb2[
   1006             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BEACON_PERIOD]);
   1007 
   1008         if (!
   1009             tb2[
   1010                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CAPABILITY
   1011                 ])
   1012         {
   1013             ALOGE("gscan_parse_pno_network_results: "
   1014                 "RESULTS_SCAN_RESULT_CAPABILITY not found");
   1015             return WIFI_ERROR_INVALID_ARGS;
   1016         }
   1017         results[i].capability =
   1018             nla_get_u16(
   1019             tb2[
   1020             QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CAPABILITY]);
   1021 
   1022         ALOGV("gscan_parse_pno_network_results: ts %" PRId64 " SSID  %s "
   1023               "BSSID: %02x:%02x:%02x:%02x:%02x:%02x channel %d rssi %d "
   1024               "rtt %" PRId64 " rtt_sd %" PRId64,
   1025               results[i].ts, results[i].ssid,
   1026               results[i].bssid[0], results[i].bssid[1], results[i].bssid[2],
   1027               results[i].bssid[3], results[i].bssid[4], results[i].bssid[5],
   1028               results[i].channel, results[i].rssi, results[i].rtt,
   1029               results[i].rtt_sd);
   1030         /* Increment loop index for next record */
   1031         i++;
   1032     }
   1033     return WIFI_SUCCESS;
   1034 }
   1035 
   1036 /* This function will be the main handler for incoming (from driver)
   1037  * GScan_SUBCMD. Calls the appropriate callback handler after parsing
   1038  * the vendor data.
   1039  */
   1040 int GScanCommandEventHandler::handleEvent(WifiEvent &event)
   1041 {
   1042     unsigned i=0;
   1043     int ret = WIFI_SUCCESS;
   1044     wifi_scan_result *result = NULL;
   1045     struct nlattr *tbVendor[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX + 1];
   1046 
   1047     if (mEventHandlingEnabled == false)
   1048     {
   1049         ALOGV("%s:Discarding event: %d",
   1050               __FUNCTION__, mSubcmd);
   1051         return NL_SKIP;
   1052     }
   1053 
   1054     WifiVendorCommand::handleEvent(event);
   1055 
   1056     nla_parse(tbVendor, QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX,
   1057                         (struct nlattr *)mVendorData,
   1058                         mDataLen, NULL);
   1059 
   1060     switch(mSubcmd)
   1061     {
   1062         case QCA_NL80211_VENDOR_SUBCMD_GSCAN_FULL_SCAN_RESULT:
   1063         {
   1064             wifi_request_id reqId;
   1065             u32 len = 0;
   1066             u32 resultsBufSize = 0;
   1067             u32 lengthOfInfoElements = 0;
   1068             u32 buckets_scanned = 0;
   1069 
   1070             ALOGV("Event QCA_NL80211_VENDOR_SUBCMD_GSCAN_FULL_SCAN_RESULT "
   1071                 "received.");
   1072             if (!tbVendor[
   1073                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID])
   1074             {
   1075                 ALOGE("%s: ATTR_GSCAN_RESULTS_REQUEST_ID not found. Exit.",
   1076                     __FUNCTION__);
   1077                 ret = WIFI_ERROR_INVALID_ARGS;
   1078                 break;
   1079             }
   1080             reqId = nla_get_u32(
   1081                     tbVendor[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID]
   1082                     );
   1083             /* If event has a different request_id, ignore that and use the
   1084              *  request_id value which we're maintaining.
   1085              */
   1086             if (reqId != mRequestId) {
   1087 #ifdef QC_HAL_DEBUG
   1088                 ALOGE("%s: Event has Req. ID:%d <> Ours:%d, continue...",
   1089                     __FUNCTION__, reqId, mRequestId);
   1090 #endif
   1091                 reqId = mRequestId;
   1092             }
   1093 
   1094             /* Parse and extract the results. */
   1095             if (!
   1096                 tbVendor[
   1097                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_IE_LENGTH
   1098                 ])
   1099             {
   1100                 ALOGE("%s:RESULTS_SCAN_RESULT_IE_LENGTH not found", __FUNCTION__);
   1101                 ret = WIFI_ERROR_INVALID_ARGS;
   1102                 break;
   1103             }
   1104             lengthOfInfoElements =
   1105                 nla_get_u32(
   1106                 tbVendor[
   1107                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_IE_LENGTH]);
   1108 
   1109             ALOGV("%s: RESULTS_SCAN_RESULT_IE_LENGTH =%d",
   1110                 __FUNCTION__, lengthOfInfoElements);
   1111 
   1112             resultsBufSize =
   1113                 lengthOfInfoElements + sizeof(wifi_scan_result);
   1114             result = (wifi_scan_result *) malloc (resultsBufSize);
   1115             if (!result) {
   1116                 ALOGE("%s: Failed to alloc memory for result struct. Exit.\n",
   1117                     __FUNCTION__);
   1118                 ret = WIFI_ERROR_OUT_OF_MEMORY;
   1119                 break;
   1120             }
   1121             memset(result, 0, resultsBufSize);
   1122 
   1123             result->ie_length = lengthOfInfoElements;
   1124 
   1125             /* Extract and fill out the wifi_scan_result struct. */
   1126             if (!
   1127             tbVendor[
   1128                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_TIME_STAMP
   1129                 ])
   1130             {
   1131                 ALOGE("%s: RESULTS_SCAN_RESULT_TIME_STAMP not found",
   1132                     __FUNCTION__);
   1133                 ret = WIFI_ERROR_INVALID_ARGS;
   1134                 break;
   1135             }
   1136             result->ts =
   1137                 nla_get_u64(
   1138                 tbVendor[
   1139                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_TIME_STAMP
   1140                     ]);
   1141 
   1142             if (!
   1143                 tbVendor[
   1144                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID
   1145                     ])
   1146             {
   1147                 ALOGE("%s: RESULTS_SCAN_RESULT_SSID not found", __FUNCTION__);
   1148                 ret = WIFI_ERROR_INVALID_ARGS;
   1149                 break;
   1150             }
   1151             len = nla_len(tbVendor[
   1152                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID]);
   1153             len =
   1154                 sizeof(result->ssid) <= len ? sizeof(result->ssid) : len;
   1155             memcpy((void *)&result->ssid,
   1156                 nla_data(
   1157                 tbVendor[
   1158                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_SSID]), len);
   1159 
   1160             if (!
   1161                 tbVendor[
   1162                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID
   1163                     ])
   1164             {
   1165                 ALOGE("%s: RESULTS_SCAN_RESULT_BSSID not found", __FUNCTION__);
   1166                 ret = WIFI_ERROR_INVALID_ARGS;
   1167                 break;
   1168             }
   1169             len = nla_len(
   1170                 tbVendor[
   1171                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID]);
   1172             len =
   1173                 sizeof(result->bssid) <= len ? sizeof(result->bssid) : len;
   1174             memcpy(&result->bssid,
   1175                 nla_data(
   1176                 tbVendor[
   1177                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BSSID]), len);
   1178 
   1179             if (!
   1180                 tbVendor[
   1181                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CHANNEL
   1182                     ])
   1183             {
   1184                 ALOGE("%s: RESULTS_SCAN_RESULT_CHANNEL not found", __FUNCTION__);
   1185                 ret = WIFI_ERROR_INVALID_ARGS;
   1186                 break;
   1187             }
   1188             result->channel =
   1189                 nla_get_u32(
   1190                 tbVendor[
   1191                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CHANNEL]);
   1192 
   1193             if (!
   1194                 tbVendor[
   1195                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RSSI
   1196                     ])
   1197             {
   1198                 ALOGE("%s: RESULTS_SCAN_RESULT_RSSI not found", __FUNCTION__);
   1199                 ret = WIFI_ERROR_INVALID_ARGS;
   1200                 break;
   1201             }
   1202             result->rssi =
   1203                 get_s32(
   1204                 tbVendor[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RSSI]
   1205                 );
   1206 
   1207             if (!
   1208                 tbVendor[
   1209                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT
   1210                     ])
   1211             {
   1212                 ALOGE("%s: RESULTS_SCAN_RESULT_RTT not found", __FUNCTION__);
   1213                 ret = WIFI_ERROR_INVALID_ARGS;
   1214                 break;
   1215             }
   1216             result->rtt =
   1217                 nla_get_u32(
   1218                 tbVendor[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT]);
   1219 
   1220             if (!
   1221                 tbVendor[
   1222                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT_SD
   1223                 ])
   1224             {
   1225                 ALOGE("%s: RESULTS_SCAN_RESULT_RTT_SD not found", __FUNCTION__);
   1226                 ret = WIFI_ERROR_INVALID_ARGS;
   1227                 break;
   1228             }
   1229             result->rtt_sd =
   1230                 nla_get_u32(
   1231                 tbVendor[
   1232                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_RTT_SD]);
   1233 
   1234             if (!
   1235                 tbVendor[
   1236                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BEACON_PERIOD])
   1237             {
   1238                 ALOGE("%s: RESULTS_SCAN_RESULT_BEACON_PERIOD not found",
   1239                     __FUNCTION__);
   1240                 ret = WIFI_ERROR_INVALID_ARGS;
   1241                 break;
   1242             }
   1243             result->beacon_period =
   1244                 nla_get_u16(
   1245                 tbVendor[
   1246                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_BEACON_PERIOD]);
   1247 
   1248             if (!
   1249                 tbVendor[
   1250                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CAPABILITY
   1251                     ])
   1252             {
   1253                 ALOGE("%s: RESULTS_SCAN_RESULT_CAPABILITY not found", __FUNCTION__);
   1254                 ret = WIFI_ERROR_INVALID_ARGS;
   1255                 break;
   1256             }
   1257             result->capability =
   1258                 nla_get_u16(
   1259                 tbVendor[
   1260                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_CAPABILITY]);
   1261 
   1262             if (!
   1263                 tbVendor[
   1264                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_IE_DATA
   1265                 ])
   1266             {
   1267                 ALOGE("%s: RESULTS_SCAN_RESULT_IE_DATA not found", __FUNCTION__);
   1268                 ret = WIFI_ERROR_INVALID_ARGS;
   1269                 break;
   1270             }
   1271             memcpy(&(result->ie_data[0]),
   1272                 nla_data(tbVendor[
   1273                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_IE_DATA]),
   1274                 lengthOfInfoElements);
   1275             if (!
   1276                 tbVendor[
   1277                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_BUCKETS_SCANNED
   1278                     ])
   1279             {
   1280                 ALOGD("%s: RESULTS_BUCKETS_SCANNED not found", __FUNCTION__);
   1281             } else {
   1282                 buckets_scanned = get_u32(tbVendor[
   1283                            QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_BUCKETS_SCANNED]);
   1284             }
   1285 #ifdef QC_HAL_DEBUG
   1286             ALOGD("handleEvent:FULL_SCAN_RESULTS: ts  %" PRId64, result->ts);
   1287             ALOGD("handleEvent:FULL_SCAN_RESULTS: SSID  %s ", result->ssid) ;
   1288             ALOGD("handleEvent:FULL_SCAN_RESULTS: "
   1289                 "BSSID: %02x:%02x:%02x:%02x:%02x:%02x \n",
   1290                 result->bssid[0], result->bssid[1], result->bssid[2],
   1291                 result->bssid[3], result->bssid[4], result->bssid[5]);
   1292             ALOGD("handleEvent:FULL_SCAN_RESULTS: channel %d ",
   1293                 result->channel);
   1294             ALOGD("handleEvent:FULL_SCAN_RESULTS: rssi  %d ", result->rssi);
   1295             ALOGD("handleEvent:FULL_SCAN_RESULTS: rtt  %" PRId64, result->rtt);
   1296             ALOGD("handleEvent:FULL_SCAN_RESULTS: rtt_sd  %" PRId64,
   1297                 result->rtt_sd);
   1298             ALOGD("handleEvent:FULL_SCAN_RESULTS: beacon period  %d ",
   1299                 result->beacon_period);
   1300             ALOGD("handleEvent:FULL_SCAN_RESULTS: capability  %d ",
   1301                 result->capability);
   1302             ALOGD("handleEvent:FULL_SCAN_RESULTS: IE length  %d ",
   1303                 result->ie_length);
   1304 
   1305             ALOGD("%s: Invoking the callback. \n", __FUNCTION__);
   1306 #endif
   1307             if (mHandler.on_full_scan_result) {
   1308                 (*mHandler.on_full_scan_result)(reqId, result, buckets_scanned);
   1309                 /* Reset flag and num counter. */
   1310                 free(result);
   1311                 result = NULL;
   1312             }
   1313         }
   1314         break;
   1315 
   1316         case QCA_NL80211_VENDOR_SUBCMD_GSCAN_SCAN_RESULTS_AVAILABLE:
   1317         {
   1318             wifi_request_id id;
   1319 
   1320 #ifdef QC_HAL_DEBUG
   1321             ALOGV("Event "
   1322                     "QCA_NL80211_VENDOR_SUBCMD_GSCAN_SCAN_RESULTS_AVAILABLE "
   1323                     "received.");
   1324 #endif
   1325 
   1326             if (!tbVendor[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID]) {
   1327                 ALOGE("%s: QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID"
   1328                         "not found. Exit", __FUNCTION__);
   1329                 ret = WIFI_ERROR_INVALID_ARGS;
   1330                 break;
   1331             }
   1332             id = nla_get_u32(
   1333                     tbVendor[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID]
   1334                              );
   1335             /* If this is not for us, then ignore it. */
   1336             if (id != mRequestId) {
   1337                 ALOGE("%s: Event has Req. ID:%d <> ours:%d",
   1338                         __FUNCTION__, id, mRequestId);
   1339                 break;
   1340             }
   1341 
   1342             /* Invoke the callback func to report the number of results. */
   1343             ALOGV("%s: Calling on_scan_event handler", __FUNCTION__);
   1344             (*mHandler.on_scan_event)(id, WIFI_SCAN_THRESHOLD_NUM_SCANS);
   1345         }
   1346         break;
   1347 
   1348         case QCA_NL80211_VENDOR_SUBCMD_GSCAN_HOTLIST_AP_FOUND:
   1349         {
   1350             wifi_request_id id;
   1351             u32 resultsBufSize = 0;
   1352             u32 numResults = 0;
   1353             u32 startingIndex, sizeOfObtainedResults;
   1354 
   1355             id = nla_get_u32(
   1356                     tbVendor[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID]
   1357                     );
   1358             /* If this is not for us, just ignore it. */
   1359             if (id != mRequestId) {
   1360                 ALOGE("%s: Event has Req. ID:%d <> ours:%d",
   1361                     __FUNCTION__, id, mRequestId);
   1362                 break;
   1363             }
   1364             if (!tbVendor[
   1365                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_NUM_RESULTS_AVAILABLE]) {
   1366                 ALOGE("%s: GSCAN_RESULTS_NUM_RESULTS_AVAILABLE not found",
   1367                     __FUNCTION__);
   1368                 ret = WIFI_ERROR_INVALID_ARGS;
   1369                 break;
   1370             }
   1371             numResults = nla_get_u32(tbVendor[
   1372                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_NUM_RESULTS_AVAILABLE]);
   1373             ALOGV("%s: number of results:%d", __FUNCTION__, numResults);
   1374 
   1375             /* Get the memory size of previous fragments, if any. */
   1376             sizeOfObtainedResults = mHotlistApFoundNumResults *
   1377                           sizeof(wifi_scan_result);
   1378 
   1379             mHotlistApFoundNumResults += numResults;
   1380             resultsBufSize += mHotlistApFoundNumResults *
   1381                                             sizeof(wifi_scan_result);
   1382 
   1383             /* Check if this chunck of scan results is a continuation of
   1384              * a previous one.
   1385              */
   1386             if (mHotlistApFoundMoreData) {
   1387                 mHotlistApFoundResults = (wifi_scan_result *)
   1388                             realloc (mHotlistApFoundResults, resultsBufSize);
   1389             } else {
   1390                 mHotlistApFoundResults = (wifi_scan_result *)
   1391                             malloc (resultsBufSize);
   1392             }
   1393 
   1394             if (!mHotlistApFoundResults) {
   1395                 ALOGE("%s: Failed to alloc memory for results array. Exit.\n",
   1396                     __FUNCTION__);
   1397                 ret = WIFI_ERROR_OUT_OF_MEMORY;
   1398                 break;
   1399             }
   1400             /* Initialize the newly allocated memory area with 0. */
   1401             memset((u8 *)mHotlistApFoundResults + sizeOfObtainedResults, 0,
   1402                     resultsBufSize - sizeOfObtainedResults);
   1403 
   1404             ALOGV("%s: Num of AP FOUND results = %d. \n", __FUNCTION__,
   1405                                             mHotlistApFoundNumResults);
   1406 
   1407             /* To support fragmentation from firmware, monitor the
   1408              * MORE_DATA flag and cache results until MORE_DATA = 0.
   1409              * Only then we can pass on the results to framework through
   1410              * the callback function.
   1411              */
   1412             if (!tbVendor[
   1413                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_MORE_DATA]) {
   1414                 ALOGE("%s: GSCAN_RESULTS_NUM_RESULTS_MORE_DATA not"
   1415                     " found", __FUNCTION__);
   1416                 ret = WIFI_ERROR_INVALID_ARGS;
   1417                 break;
   1418             } else {
   1419                 mHotlistApFoundMoreData = nla_get_u8(
   1420                     tbVendor[
   1421                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_MORE_DATA]);
   1422                 ALOGE("%s: More data = %d. \n",
   1423                     __FUNCTION__, mHotlistApFoundMoreData);
   1424             }
   1425 
   1426             ALOGV("%s: Extract hotlist_ap_found results.\n", __FUNCTION__);
   1427             startingIndex = mHotlistApFoundNumResults - numResults;
   1428             ALOGV("%s: starting_index:%d",
   1429                 __FUNCTION__, startingIndex);
   1430             ret = gscan_parse_hotlist_ap_results(numResults,
   1431                                                 mHotlistApFoundResults,
   1432                                                 startingIndex,
   1433                                                 tbVendor);
   1434             /* If a parsing error occurred, exit and proceed for cleanup. */
   1435             if (ret)
   1436                 break;
   1437             /* Send the results if no more result data fragments are expected */
   1438             if (!mHotlistApFoundMoreData) {
   1439                 (*mHandler.on_hotlist_ap_found)(id,
   1440                                                 mHotlistApFoundNumResults,
   1441                                                 mHotlistApFoundResults);
   1442                 /* Reset flag and num counter. */
   1443                 free(mHotlistApFoundResults);
   1444                 mHotlistApFoundResults = NULL;
   1445                 mHotlistApFoundMoreData = false;
   1446                 mHotlistApFoundNumResults = 0;
   1447             }
   1448         }
   1449         break;
   1450 
   1451         case QCA_NL80211_VENDOR_SUBCMD_GSCAN_HOTLIST_AP_LOST:
   1452         {
   1453             wifi_request_id id;
   1454             u32 resultsBufSize = 0;
   1455             u32 numResults = 0;
   1456             u32 startingIndex, sizeOfObtainedResults;
   1457 
   1458             id = nla_get_u32(
   1459                     tbVendor[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID]
   1460                     );
   1461             /* If this is not for us, just ignore it. */
   1462             if (id != mRequestId) {
   1463                 ALOGE("%s: Event has Req. ID:%d <> ours:%d",
   1464                     __FUNCTION__, id, mRequestId);
   1465                 break;
   1466             }
   1467             if (!tbVendor[
   1468                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_NUM_RESULTS_AVAILABLE]) {
   1469                 ALOGE("%s: GSCAN_RESULTS_NUM_RESULTS_AVAILABLE not found",
   1470                     __FUNCTION__);
   1471                 ret = WIFI_ERROR_INVALID_ARGS;
   1472                 break;
   1473             }
   1474             numResults = nla_get_u32(tbVendor[
   1475                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_NUM_RESULTS_AVAILABLE]);
   1476             ALOGV("%s: number of results:%d", __FUNCTION__, numResults);
   1477 
   1478             /* Get the memory size of previous fragments, if any. */
   1479             sizeOfObtainedResults = mHotlistApLostNumResults *
   1480                           sizeof(wifi_scan_result);
   1481 
   1482             mHotlistApLostNumResults += numResults;
   1483             resultsBufSize += mHotlistApLostNumResults *
   1484                                             sizeof(wifi_scan_result);
   1485 
   1486             /* Check if this chunck of scan results is a continuation of
   1487              * a previous one.
   1488              */
   1489             if (mHotlistApLostMoreData) {
   1490                 mHotlistApLostResults = (wifi_scan_result *)
   1491                             realloc (mHotlistApLostResults, resultsBufSize);
   1492             } else {
   1493                 mHotlistApLostResults = (wifi_scan_result *)
   1494                             malloc (resultsBufSize);
   1495             }
   1496 
   1497             if (!mHotlistApLostResults) {
   1498                 ALOGE("%s: Failed to alloc memory for results array. Exit.\n",
   1499                     __FUNCTION__);
   1500                 ret = WIFI_ERROR_OUT_OF_MEMORY;
   1501                 break;
   1502             }
   1503             /* Initialize the newly allocated memory area with 0. */
   1504             memset((u8 *)mHotlistApLostResults + sizeOfObtainedResults, 0,
   1505                     resultsBufSize - sizeOfObtainedResults);
   1506 
   1507             ALOGV("%s: Num of AP Lost results = %d. \n", __FUNCTION__,
   1508                                             mHotlistApLostNumResults);
   1509 
   1510             /* To support fragmentation from firmware, monitor the
   1511              * MORE_DATA flag and cache results until MORE_DATA = 0.
   1512              * Only then we can pass on the results to framework through
   1513              * the callback function.
   1514              */
   1515             if (!tbVendor[
   1516                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_MORE_DATA]) {
   1517                 ALOGE("%s: GSCAN_RESULTS_NUM_RESULTS_MORE_DATA not"
   1518                     " found", __FUNCTION__);
   1519                 ret = WIFI_ERROR_INVALID_ARGS;
   1520                 break;
   1521             } else {
   1522                 mHotlistApLostMoreData = nla_get_u8(
   1523                     tbVendor[
   1524                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_MORE_DATA]);
   1525                 ALOGV("%s: More data = %d. \n",
   1526                     __FUNCTION__, mHotlistApLostMoreData);
   1527             }
   1528 
   1529             ALOGV("%s: Extract hotlist_ap_Lost results.\n", __FUNCTION__);
   1530             startingIndex = mHotlistApLostNumResults - numResults;
   1531             ALOGV("%s: starting_index:%d",
   1532                 __FUNCTION__, startingIndex);
   1533             ret = gscan_parse_hotlist_ap_results(numResults,
   1534                                                 mHotlistApLostResults,
   1535                                                 startingIndex,
   1536                                                 tbVendor);
   1537             /* If a parsing error occurred, exit and proceed for cleanup. */
   1538             if (ret)
   1539                 break;
   1540             /* Send the results if no more result data fragments are expected */
   1541             if (!mHotlistApLostMoreData) {
   1542                 (*mHandler.on_hotlist_ap_lost)(id,
   1543                                                mHotlistApLostNumResults,
   1544                                                mHotlistApLostResults);
   1545                 /* Reset flag and num counter. */
   1546                 free(mHotlistApLostResults);
   1547                 mHotlistApLostResults = NULL;
   1548                 mHotlistApLostMoreData = false;
   1549                 mHotlistApLostNumResults = 0;
   1550             }
   1551         }
   1552         break;
   1553 
   1554         case QCA_NL80211_VENDOR_SUBCMD_GSCAN_SIGNIFICANT_CHANGE:
   1555         {
   1556             wifi_request_id reqId;
   1557             u32 numResults = 0, sizeOfObtainedResults;
   1558             u32 startingIndex, index = 0;
   1559             struct nlattr *scanResultsInfo;
   1560             int rem = 0;
   1561 
   1562             if (!tbVendor[
   1563                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID])
   1564             {
   1565                 ALOGE("%s: ATTR_GSCAN_RESULTS_REQUEST_ID not found. Exit.",
   1566                     __FUNCTION__);
   1567                 ret = WIFI_ERROR_INVALID_ARGS;
   1568                 break;
   1569             }
   1570             reqId = nla_get_u32(
   1571                     tbVendor[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID]
   1572                     );
   1573             /* If this is not for us, just ignore it. */
   1574             if (reqId != mRequestId) {
   1575                 ALOGE("%s: Event has Req. ID:%d <> ours:%d",
   1576                     __FUNCTION__, reqId, mRequestId);
   1577                 break;
   1578             }
   1579             if (!tbVendor[
   1580                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_NUM_RESULTS_AVAILABLE])
   1581             {
   1582                 ALOGE("%s: ATTR_GSCAN_RESULTS_NUM_RESULTS_AVAILABLE not found."
   1583                     "Exit.", __FUNCTION__);
   1584                 ret = WIFI_ERROR_INVALID_ARGS;
   1585                 break;
   1586             }
   1587             numResults = nla_get_u32(tbVendor[
   1588                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_NUM_RESULTS_AVAILABLE]);
   1589             /* Get the memory size of previous fragments, if any. */
   1590             sizeOfObtainedResults = sizeof(wifi_significant_change_result *) *
   1591                                 mSignificantChangeNumResults;
   1592 
   1593             index = mSignificantChangeNumResults;
   1594             mSignificantChangeNumResults += numResults;
   1595             /*
   1596              * Check if this chunck of wifi_significant_change results is a
   1597              * continuation of a previous one.
   1598              */
   1599             if (mSignificantChangeMoreData) {
   1600                 mSignificantChangeResults =
   1601                     (wifi_significant_change_result **)
   1602                         realloc (mSignificantChangeResults,
   1603                         sizeof(wifi_significant_change_result *) *
   1604                                 mSignificantChangeNumResults);
   1605             } else {
   1606                 mSignificantChangeResults =
   1607                     (wifi_significant_change_result **)
   1608                         malloc (sizeof(wifi_significant_change_result *) *
   1609                                 mSignificantChangeNumResults);
   1610             }
   1611 
   1612             if (!mSignificantChangeResults) {
   1613                 ALOGE("%s: Failed to alloc memory for results array. Exit.\n",
   1614                     __FUNCTION__);
   1615                 ret = WIFI_ERROR_OUT_OF_MEMORY;
   1616                 break;
   1617             }
   1618             /* Initialize the newly allocated memory area with 0. */
   1619             memset((u8 *)mSignificantChangeResults + sizeOfObtainedResults, 0,
   1620                     sizeof(wifi_significant_change_result *) *
   1621                                 numResults);
   1622             ALOGV("%s: mSignificantChangeMoreData = %d",
   1623                     __FUNCTION__, mSignificantChangeMoreData);
   1624 
   1625             for (scanResultsInfo = (struct nlattr *) nla_data(tbVendor[
   1626                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_LIST]),
   1627                 rem = nla_len(tbVendor[
   1628                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_LIST]);
   1629                 nla_ok(scanResultsInfo, rem);
   1630                 scanResultsInfo = nla_next(scanResultsInfo, &(rem)))
   1631             {
   1632                 u32 num_rssi = 0;
   1633                 u32 resultsBufSize = 0;
   1634                 struct nlattr *tb2[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX + 1];
   1635                 nla_parse(tb2, QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_MAX,
   1636                     (struct nlattr *) nla_data(scanResultsInfo),
   1637                     nla_len(scanResultsInfo), NULL);
   1638                 if (!tb2[
   1639                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SIGNIFICANT_CHANGE_RESULT_NUM_RSSI
   1640                     ])
   1641                 {
   1642                     ALOGE("%s: QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_"
   1643                         "SIGNIFICANT_CHANGE_RESULT_NUM_RSSI not found. "
   1644                         "Exit.", __FUNCTION__);
   1645                     ret = WIFI_ERROR_INVALID_ARGS;
   1646                     break;
   1647                 }
   1648                 num_rssi = nla_get_u32(tb2[
   1649                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SIGNIFICANT_CHANGE_RESULT_NUM_RSSI
   1650                         ]);
   1651                 resultsBufSize = sizeof(wifi_significant_change_result) +
   1652                             num_rssi * sizeof(wifi_rssi);
   1653                 mSignificantChangeResults[index] =
   1654                     (wifi_significant_change_result *) malloc (resultsBufSize);
   1655 
   1656                 if (!mSignificantChangeResults[index]) {
   1657                     ALOGE("%s: Failed to alloc memory for results array Exit",
   1658                         __FUNCTION__);
   1659                     ret = WIFI_ERROR_OUT_OF_MEMORY;
   1660                     break;
   1661                 }
   1662                 /* Initialize the newly allocated memory area with 0. */
   1663                 memset((u8 *)mSignificantChangeResults[index],
   1664                         0, resultsBufSize);
   1665 
   1666                 ALOGV("%s: For Significant Change results[%d], num_rssi:%d\n",
   1667                     __FUNCTION__, index, num_rssi);
   1668                 index++;
   1669             }
   1670 
   1671             ALOGV("%s: Extract significant change results.\n", __FUNCTION__);
   1672             startingIndex =
   1673                 mSignificantChangeNumResults - numResults;
   1674             ret = gscan_get_significant_change_results(numResults,
   1675                                                 mSignificantChangeResults,
   1676                                                 startingIndex,
   1677                                                 tbVendor);
   1678             /* If a parsing error occurred, exit and proceed for cleanup. */
   1679             if (ret)
   1680                 break;
   1681             /* To support fragmentation from firmware, monitor the
   1682              * MORE_DATA flag and cache results until MORE_DATA = 0.
   1683              * Only then we can pass on the results to framework through
   1684              * the callback function.
   1685              */
   1686             if (!tbVendor[
   1687                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_MORE_DATA]) {
   1688                 ALOGE("%s: GSCAN_RESULTS_NUM_RESULTS_MORE_DATA not"
   1689                     " found. Stop parsing and exit.", __FUNCTION__);
   1690                 break;
   1691             }
   1692             mSignificantChangeMoreData = nla_get_u8(
   1693                 tbVendor[
   1694                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_MORE_DATA]);
   1695             ALOGV("%s: More data = %d. \n",
   1696                 __FUNCTION__, mSignificantChangeMoreData);
   1697 
   1698             /* Send the results if no more result fragments are expected */
   1699             if (!mSignificantChangeMoreData) {
   1700                 ALOGV("%s: Invoking the callback. \n", __FUNCTION__);
   1701                 (*mHandler.on_significant_change)(reqId,
   1702                                               mSignificantChangeNumResults,
   1703                                               mSignificantChangeResults);
   1704                 if (mSignificantChangeResults) {
   1705                     /* Reset flag and num counter. */
   1706                     for (index = 0; index < mSignificantChangeNumResults;
   1707                          index++)
   1708                     {
   1709                         free(mSignificantChangeResults[index]);
   1710                         mSignificantChangeResults[index] = NULL;
   1711                     }
   1712                     free(mSignificantChangeResults);
   1713                     mSignificantChangeResults = NULL;
   1714                 }
   1715                 mSignificantChangeNumResults = 0;
   1716                 mSignificantChangeMoreData = false;
   1717             }
   1718         }
   1719         break;
   1720 
   1721         case QCA_NL80211_VENDOR_SUBCMD_GSCAN_SCAN_EVENT:
   1722         {
   1723             wifi_scan_event scanEvent;
   1724             wifi_request_id reqId;
   1725 
   1726             if (!tbVendor[
   1727                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID])
   1728             {
   1729                 ALOGE("%s: ATTR_GSCAN_RESULTS_REQUEST_ID not found. Exit.",
   1730                     __FUNCTION__);
   1731                 ret = WIFI_ERROR_INVALID_ARGS;
   1732                 break;
   1733             }
   1734             reqId = nla_get_u32(
   1735                     tbVendor[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID]
   1736                     );
   1737             /* If this is not for us, just ignore it. */
   1738             if (reqId != mRequestId) {
   1739                 ALOGE("%s: Event has Req. ID:%d <> ours:%d",
   1740                     __FUNCTION__, reqId, mRequestId);
   1741                 break;
   1742             }
   1743 
   1744             if (!tbVendor[
   1745                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_EVENT_TYPE]) {
   1746                 ALOGE("%s: GSCAN_RESULTS_SCAN_EVENT_TYPE not"
   1747                     " found. Stop parsing and exit.", __FUNCTION__);
   1748                 break;
   1749             }
   1750             scanEvent = (wifi_scan_event) nla_get_u8(tbVendor[
   1751                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_EVENT_TYPE]);
   1752 
   1753             ALOGV("%s: Scan event type: %d\n", __FUNCTION__, scanEvent);
   1754             /* Send the results if no more result fragments are expected. */
   1755             (*mHandler.on_scan_event)(reqId, scanEvent);
   1756         }
   1757         break;
   1758 
   1759         case QCA_NL80211_VENDOR_SUBCMD_PNO_NETWORK_FOUND:
   1760         {
   1761             wifi_request_id id;
   1762             u32 resultsBufSize = 0;
   1763             u32 numResults = 0;
   1764             u32 startingIndex, sizeOfObtainedResults;
   1765 
   1766             if (!tbVendor[
   1767                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID])
   1768             {
   1769                 /* RequestId is not provided by FW/Driver for this event */
   1770                 ALOGE("%s: ATTR_GSCAN_RESULTS_REQUEST_ID not found. Continue.",
   1771                     __FUNCTION__);
   1772                 id = mRequestId; /* Use the saved mRequestId instead. */
   1773             } else {
   1774                 id = nla_get_u32(
   1775                         tbVendor[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID]
   1776                         );
   1777                 /* If this is not for us, use the saved requestId */
   1778                 if (id != mRequestId) {
   1779                     ALOGE("%s: Event has Req. ID:%d <> ours:%d",
   1780                         __FUNCTION__, id, mRequestId);
   1781                     id = mRequestId;
   1782                 }
   1783             }
   1784 
   1785             if (!tbVendor[
   1786                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_NUM_RESULTS_AVAILABLE]) {
   1787                 ALOGE("%s: GSCAN_RESULTS_NUM_RESULTS_AVAILABLE not found",
   1788                     __FUNCTION__);
   1789                 ret = WIFI_ERROR_INVALID_ARGS;
   1790                 break;
   1791             }
   1792             numResults = nla_get_u32(tbVendor[
   1793                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_NUM_RESULTS_AVAILABLE]);
   1794             ALOGV("%s: number of results:%d", __FUNCTION__, numResults);
   1795 
   1796             /* Get the memory size of previous fragments, if any. */
   1797             sizeOfObtainedResults = mPnoNetworkFoundNumResults *
   1798                           sizeof(wifi_scan_result);
   1799 
   1800             mPnoNetworkFoundNumResults += numResults;
   1801             resultsBufSize += mPnoNetworkFoundNumResults *
   1802                                             sizeof(wifi_scan_result);
   1803 
   1804             /* Check if this chunck of scan results is a continuation of
   1805              * a previous one.
   1806              */
   1807             if (mPnoNetworkFoundMoreData) {
   1808                 mPnoNetworkFoundResults = (wifi_scan_result *)
   1809                             realloc (mPnoNetworkFoundResults, resultsBufSize);
   1810             } else {
   1811                 mPnoNetworkFoundResults = (wifi_scan_result *)
   1812                             malloc (resultsBufSize);
   1813             }
   1814 
   1815             if (!mPnoNetworkFoundResults) {
   1816                 ALOGE("%s: Failed to alloc memory for results array. Exit.\n",
   1817                     __FUNCTION__);
   1818                 ret = WIFI_ERROR_OUT_OF_MEMORY;
   1819                 break;
   1820             }
   1821             /* Initialize the newly allocated memory area with 0. */
   1822             memset((u8 *)mPnoNetworkFoundResults + sizeOfObtainedResults, 0,
   1823                     resultsBufSize - sizeOfObtainedResults);
   1824 
   1825             ALOGV("%s: Num of AP FOUND results = %d. \n", __FUNCTION__,
   1826                                             mPnoNetworkFoundNumResults);
   1827 
   1828             /* To support fragmentation from firmware, monitor the
   1829              * MORE_DATA flag and cache results until MORE_DATA = 0.
   1830              * Only then we can pass on the results to framework through
   1831              * the callback function.
   1832              */
   1833             if (!tbVendor[
   1834                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_MORE_DATA]) {
   1835                 ALOGE("%s: GSCAN_RESULTS_NUM_RESULTS_MORE_DATA not"
   1836                     " found", __FUNCTION__);
   1837                 ret = WIFI_ERROR_INVALID_ARGS;
   1838                 break;
   1839             } else {
   1840                 mPnoNetworkFoundMoreData = nla_get_u8(
   1841                     tbVendor[
   1842                     QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_SCAN_RESULT_MORE_DATA]);
   1843                 ALOGV("%s: More data = %d. \n",
   1844                     __FUNCTION__, mPnoNetworkFoundMoreData);
   1845             }
   1846 
   1847             ALOGV("%s: Extract PNO_NETWORK_FOUND results.\n", __FUNCTION__);
   1848             startingIndex = mPnoNetworkFoundNumResults - numResults;
   1849             ALOGV("%s: starting_index:%d",
   1850                 __FUNCTION__, startingIndex);
   1851             ret = gscan_parse_pno_network_results(numResults,
   1852                                                 mPnoNetworkFoundResults,
   1853                                                 startingIndex,
   1854                                                 tbVendor);
   1855             /* If a parsing error occurred, exit and proceed for cleanup. */
   1856             if (ret)
   1857                 break;
   1858             /* Send the results if no more result data fragments are expected */
   1859             if (!mPnoNetworkFoundMoreData) {
   1860                 (*mHandler.on_pno_network_found)(id,
   1861                                                 mPnoNetworkFoundNumResults,
   1862                                                 mPnoNetworkFoundResults);
   1863                 /* Reset flag and num counter. */
   1864                 if (mPnoNetworkFoundResults) {
   1865                     free(mPnoNetworkFoundResults);
   1866                     mPnoNetworkFoundResults = NULL;
   1867                 }
   1868                 mPnoNetworkFoundMoreData = false;
   1869                 mPnoNetworkFoundNumResults = 0;
   1870             }
   1871         }
   1872         break;
   1873         case QCA_NL80211_VENDOR_SUBCMD_PNO_PASSPOINT_NETWORK_FOUND:
   1874         {
   1875             wifi_request_id id;
   1876 
   1877             if (!tbVendor[
   1878                 QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID])
   1879             {
   1880                 /* RequestId is not provided by FW/Driver for this event */
   1881                 ALOGE("%s: ATTR_GSCAN_RESULTS_REQUEST_ID not found. Continue.",
   1882                     __FUNCTION__);
   1883                 id = mRequestId; /* Use the saved mRequestId instead. */
   1884             } else {
   1885                 id = nla_get_u32(
   1886                         tbVendor[QCA_WLAN_VENDOR_ATTR_GSCAN_RESULTS_REQUEST_ID]
   1887                         );
   1888                 /* If this is not for us, use the saved requestId */
   1889                 if (id != mRequestId) {
   1890                     ALOGE("%s: Event has Req. ID:%d <> ours:%d",
   1891                         __FUNCTION__, id, mRequestId);
   1892                     id = mRequestId;
   1893                 }
   1894             }
   1895 
   1896             ret = gscan_parse_passpoint_network_result(tbVendor);
   1897             /* If a parsing error occurred, exit and proceed for cleanup. */
   1898             if (ret)
   1899             {
   1900                 ALOGE("%s: gscan_parse_passpoint_network_result"
   1901                       "returned error: %d.\n", __FUNCTION__, ret);
   1902                 break;
   1903             }
   1904             (*mHandler.on_passpoint_network_found)(id,
   1905                                                    mPasspointNetId,
   1906                                                    mPasspointNetworkFoundResult,
   1907                                                    mPasspointAnqpLen,
   1908                                                    mPasspointAnqp);
   1909             if (mPasspointNetworkFoundResult)
   1910             {
   1911                 free(mPasspointNetworkFoundResult);
   1912                 mPasspointNetworkFoundResult = NULL;
   1913             }
   1914             if (mPasspointAnqp)
   1915             {
   1916                 free(mPasspointAnqp);
   1917                 mPasspointAnqp = NULL;
   1918             }
   1919             mPasspointNetId = -1;
   1920             mPasspointAnqpLen = 0;
   1921         }
   1922         break;
   1923         default:
   1924             /* Error case should not happen print log */
   1925             ALOGE("%s: Wrong GScan subcmd received %d", __FUNCTION__, mSubcmd);
   1926     }
   1927 
   1928     /* A parsing error occurred, do the cleanup of gscan result lists. */
   1929     if (ret) {
   1930         switch(mSubcmd)
   1931         {
   1932             case QCA_NL80211_VENDOR_SUBCMD_GSCAN_FULL_SCAN_RESULT:
   1933             {
   1934                 free(result);
   1935                 result = NULL;
   1936             }
   1937             break;
   1938 
   1939             case QCA_NL80211_VENDOR_SUBCMD_GSCAN_HOTLIST_AP_FOUND:
   1940             {
   1941                 /* Reset flag and num counter. */
   1942                 free(mHotlistApFoundResults);
   1943                 mHotlistApFoundResults = NULL;
   1944                 mHotlistApFoundMoreData = false;
   1945                 mHotlistApFoundNumResults = 0;
   1946             }
   1947             break;
   1948 
   1949             case QCA_NL80211_VENDOR_SUBCMD_GSCAN_SIGNIFICANT_CHANGE:
   1950             {
   1951                 if (mSignificantChangeResults) {
   1952                     for (i = 0; i < mSignificantChangeNumResults; i++)
   1953                     {
   1954                         if (mSignificantChangeResults[i]) {
   1955                             free(mSignificantChangeResults[i]);
   1956                             mSignificantChangeResults[i] = NULL;
   1957                         }
   1958                     }
   1959                     free(mSignificantChangeResults);
   1960                     mSignificantChangeResults = NULL;
   1961                 }
   1962                 mSignificantChangeNumResults = 0;
   1963                 mSignificantChangeMoreData = false;
   1964             }
   1965             break;
   1966 
   1967             case QCA_NL80211_VENDOR_SUBCMD_GSCAN_SCAN_RESULTS_AVAILABLE:
   1968             break;
   1969 
   1970             case QCA_NL80211_VENDOR_SUBCMD_GSCAN_SCAN_EVENT:
   1971             break;
   1972 
   1973             case QCA_NL80211_VENDOR_SUBCMD_GSCAN_HOTLIST_AP_LOST:
   1974             {
   1975                 /* Reset flag and num counter. */
   1976                 free(mHotlistApLostResults);
   1977                 mHotlistApLostResults = NULL;
   1978                 mHotlistApLostMoreData = false;
   1979                 mHotlistApLostNumResults = 0;
   1980             }
   1981             break;
   1982 
   1983             case QCA_NL80211_VENDOR_SUBCMD_PNO_NETWORK_FOUND:
   1984             {
   1985                 /* Reset flag and num counter. */
   1986                 if (mPnoNetworkFoundResults) {
   1987                     free(mPnoNetworkFoundResults);
   1988                     mPnoNetworkFoundResults = NULL;
   1989                 }
   1990                 mPnoNetworkFoundMoreData = false;
   1991                 mPnoNetworkFoundNumResults = 0;
   1992             }
   1993             break;
   1994 
   1995             case QCA_NL80211_VENDOR_SUBCMD_PNO_PASSPOINT_NETWORK_FOUND:
   1996             {
   1997                 if (mPasspointNetworkFoundResult)
   1998                 {
   1999                     free(mPasspointNetworkFoundResult);
   2000                     mPasspointNetworkFoundResult = NULL;
   2001                 }
   2002                 if (mPasspointAnqp)
   2003                 {
   2004                     free(mPasspointAnqp);
   2005                     mPasspointAnqp = NULL;
   2006                 }
   2007                 mPasspointNetId = -1;
   2008                 mPasspointAnqpLen = 0;
   2009             }
   2010             break;
   2011 
   2012             default:
   2013                 ALOGE("%s: Parsing err handler: wrong GScan subcmd "
   2014                     "received %d", __FUNCTION__, mSubcmd);
   2015         }
   2016     }
   2017     return NL_SKIP;
   2018 }
   2019