linux/drivers/net/wireless/intel/iwlwifi/mvm/scan.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause
   2/*
   3 * Copyright (C) 2012-2014, 2018-2021 Intel Corporation
   4 * Copyright (C) 2013-2015 Intel Mobile Communications GmbH
   5 * Copyright (C) 2016-2017 Intel Deutschland GmbH
   6 */
   7#include <linux/etherdevice.h>
   8#include <net/mac80211.h>
   9#include <linux/crc32.h>
  10
  11#include "mvm.h"
  12#include "fw/api/scan.h"
  13#include "iwl-io.h"
  14
  15#define IWL_DENSE_EBS_SCAN_RATIO 5
  16#define IWL_SPARSE_EBS_SCAN_RATIO 1
  17
  18#define IWL_SCAN_DWELL_ACTIVE           10
  19#define IWL_SCAN_DWELL_PASSIVE          110
  20#define IWL_SCAN_DWELL_FRAGMENTED       44
  21#define IWL_SCAN_DWELL_EXTENDED         90
  22#define IWL_SCAN_NUM_OF_FRAGS           3
  23
  24/* adaptive dwell max budget time [TU] for full scan */
  25#define IWL_SCAN_ADWELL_MAX_BUDGET_FULL_SCAN 300
  26/* adaptive dwell max budget time [TU] for directed scan */
  27#define IWL_SCAN_ADWELL_MAX_BUDGET_DIRECTED_SCAN 100
  28/* adaptive dwell default high band APs number */
  29#define IWL_SCAN_ADWELL_DEFAULT_HB_N_APS 8
  30/* adaptive dwell default low band APs number */
  31#define IWL_SCAN_ADWELL_DEFAULT_LB_N_APS 2
  32/* adaptive dwell default APs number in social channels (1, 6, 11) */
  33#define IWL_SCAN_ADWELL_DEFAULT_N_APS_SOCIAL 10
  34/* number of scan channels */
  35#define IWL_SCAN_NUM_CHANNELS 112
  36/* adaptive dwell number of APs override mask for p2p friendly GO */
  37#define IWL_SCAN_ADWELL_N_APS_GO_FRIENDLY_BIT BIT(20)
  38/* adaptive dwell number of APs override mask for social channels */
  39#define IWL_SCAN_ADWELL_N_APS_SOCIAL_CHS_BIT BIT(21)
  40/* adaptive dwell number of APs override for p2p friendly GO channels */
  41#define IWL_SCAN_ADWELL_N_APS_GO_FRIENDLY 10
  42/* adaptive dwell number of APs override for social channels */
  43#define IWL_SCAN_ADWELL_N_APS_SOCIAL_CHS 2
  44
  45/* minimal number of 2GHz and 5GHz channels in the regular scan request */
  46#define IWL_MVM_6GHZ_PASSIVE_SCAN_MIN_CHANS 4
  47
  48struct iwl_mvm_scan_timing_params {
  49        u32 suspend_time;
  50        u32 max_out_time;
  51};
  52
  53static struct iwl_mvm_scan_timing_params scan_timing[] = {
  54        [IWL_SCAN_TYPE_UNASSOC] = {
  55                .suspend_time = 0,
  56                .max_out_time = 0,
  57        },
  58        [IWL_SCAN_TYPE_WILD] = {
  59                .suspend_time = 30,
  60                .max_out_time = 120,
  61        },
  62        [IWL_SCAN_TYPE_MILD] = {
  63                .suspend_time = 120,
  64                .max_out_time = 120,
  65        },
  66        [IWL_SCAN_TYPE_FRAGMENTED] = {
  67                .suspend_time = 95,
  68                .max_out_time = 44,
  69        },
  70        [IWL_SCAN_TYPE_FAST_BALANCE] = {
  71                .suspend_time = 30,
  72                .max_out_time = 37,
  73        },
  74};
  75
  76struct iwl_mvm_scan_params {
  77        /* For CDB this is low band scan type, for non-CDB - type. */
  78        enum iwl_mvm_scan_type type;
  79        enum iwl_mvm_scan_type hb_type;
  80        u32 n_channels;
  81        u16 delay;
  82        int n_ssids;
  83        struct cfg80211_ssid *ssids;
  84        struct ieee80211_channel **channels;
  85        u32 flags;
  86        u8 *mac_addr;
  87        u8 *mac_addr_mask;
  88        bool no_cck;
  89        bool pass_all;
  90        int n_match_sets;
  91        struct iwl_scan_probe_req preq;
  92        struct cfg80211_match_set *match_sets;
  93        int n_scan_plans;
  94        struct cfg80211_sched_scan_plan *scan_plans;
  95        bool iter_notif;
  96        struct cfg80211_scan_6ghz_params *scan_6ghz_params;
  97        u32 n_6ghz_params;
  98        bool scan_6ghz;
  99        bool enable_6ghz_passive;
 100        bool respect_p2p_go, respect_p2p_go_hb;
 101};
 102
 103static inline void *iwl_mvm_get_scan_req_umac_data(struct iwl_mvm *mvm)
 104{
 105        struct iwl_scan_req_umac *cmd = mvm->scan_cmd;
 106
 107        if (iwl_mvm_is_adaptive_dwell_v2_supported(mvm))
 108                return (void *)&cmd->v8.data;
 109
 110        if (iwl_mvm_is_adaptive_dwell_supported(mvm))
 111                return (void *)&cmd->v7.data;
 112
 113        if (iwl_mvm_cdb_scan_api(mvm))
 114                return (void *)&cmd->v6.data;
 115
 116        return (void *)&cmd->v1.data;
 117}
 118
 119static inline struct iwl_scan_umac_chan_param *
 120iwl_mvm_get_scan_req_umac_channel(struct iwl_mvm *mvm)
 121{
 122        struct iwl_scan_req_umac *cmd = mvm->scan_cmd;
 123
 124        if (iwl_mvm_is_adaptive_dwell_v2_supported(mvm))
 125                return &cmd->v8.channel;
 126
 127        if (iwl_mvm_is_adaptive_dwell_supported(mvm))
 128                return &cmd->v7.channel;
 129
 130        if (iwl_mvm_cdb_scan_api(mvm))
 131                return &cmd->v6.channel;
 132
 133        return &cmd->v1.channel;
 134}
 135
 136static u8 iwl_mvm_scan_rx_ant(struct iwl_mvm *mvm)
 137{
 138        if (mvm->scan_rx_ant != ANT_NONE)
 139                return mvm->scan_rx_ant;
 140        return iwl_mvm_get_valid_rx_ant(mvm);
 141}
 142
 143static inline __le16 iwl_mvm_scan_rx_chain(struct iwl_mvm *mvm)
 144{
 145        u16 rx_chain;
 146        u8 rx_ant;
 147
 148        rx_ant = iwl_mvm_scan_rx_ant(mvm);
 149        rx_chain = rx_ant << PHY_RX_CHAIN_VALID_POS;
 150        rx_chain |= rx_ant << PHY_RX_CHAIN_FORCE_MIMO_SEL_POS;
 151        rx_chain |= rx_ant << PHY_RX_CHAIN_FORCE_SEL_POS;
 152        rx_chain |= 0x1 << PHY_RX_CHAIN_DRIVER_FORCE_POS;
 153        return cpu_to_le16(rx_chain);
 154}
 155
 156static inline __le32
 157iwl_mvm_scan_rate_n_flags(struct iwl_mvm *mvm, enum nl80211_band band,
 158                          bool no_cck)
 159{
 160        u32 tx_ant;
 161
 162        iwl_mvm_toggle_tx_ant(mvm, &mvm->scan_last_antenna_idx);
 163        tx_ant = BIT(mvm->scan_last_antenna_idx) << RATE_MCS_ANT_POS;
 164
 165        if (band == NL80211_BAND_2GHZ && !no_cck)
 166                return cpu_to_le32(IWL_RATE_1M_PLCP | RATE_MCS_CCK_MSK_V1 |
 167                                   tx_ant);
 168        else
 169                return cpu_to_le32(IWL_RATE_6M_PLCP | tx_ant);
 170}
 171
 172static enum iwl_mvm_traffic_load iwl_mvm_get_traffic_load(struct iwl_mvm *mvm)
 173{
 174        return mvm->tcm.result.global_load;
 175}
 176
 177static enum iwl_mvm_traffic_load
 178iwl_mvm_get_traffic_load_band(struct iwl_mvm *mvm, enum nl80211_band band)
 179{
 180        return mvm->tcm.result.band_load[band];
 181}
 182
 183struct iwl_mvm_scan_iter_data {
 184        u32 global_cnt;
 185        struct ieee80211_vif *current_vif;
 186        bool is_dcm_with_p2p_go;
 187};
 188
 189static void iwl_mvm_scan_iterator(void *_data, u8 *mac,
 190                                  struct ieee80211_vif *vif)
 191{
 192        struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
 193        struct iwl_mvm_scan_iter_data *data = _data;
 194        struct iwl_mvm_vif *curr_mvmvif;
 195
 196        if (vif->type != NL80211_IFTYPE_P2P_DEVICE && mvmvif->phy_ctxt &&
 197            mvmvif->phy_ctxt->id < NUM_PHY_CTX)
 198                data->global_cnt += 1;
 199
 200        if (!data->current_vif || vif == data->current_vif)
 201                return;
 202
 203        curr_mvmvif = iwl_mvm_vif_from_mac80211(data->current_vif);
 204
 205        if (vif->type == NL80211_IFTYPE_AP && vif->p2p &&
 206            mvmvif->phy_ctxt && curr_mvmvif->phy_ctxt &&
 207            mvmvif->phy_ctxt->id != curr_mvmvif->phy_ctxt->id)
 208                data->is_dcm_with_p2p_go = true;
 209}
 210
 211static enum
 212iwl_mvm_scan_type _iwl_mvm_get_scan_type(struct iwl_mvm *mvm,
 213                                         struct ieee80211_vif *vif,
 214                                         enum iwl_mvm_traffic_load load,
 215                                         bool low_latency)
 216{
 217        struct iwl_mvm_scan_iter_data data = {
 218                .current_vif = vif,
 219                .is_dcm_with_p2p_go = false,
 220                .global_cnt = 0,
 221        };
 222
 223        ieee80211_iterate_active_interfaces_atomic(mvm->hw,
 224                                                   IEEE80211_IFACE_ITER_NORMAL,
 225                                                   iwl_mvm_scan_iterator,
 226                                                   &data);
 227
 228        if (!data.global_cnt)
 229                return IWL_SCAN_TYPE_UNASSOC;
 230
 231        if (fw_has_api(&mvm->fw->ucode_capa,
 232                       IWL_UCODE_TLV_API_FRAGMENTED_SCAN)) {
 233                if ((load == IWL_MVM_TRAFFIC_HIGH || low_latency) &&
 234                    (!vif || vif->type != NL80211_IFTYPE_P2P_DEVICE))
 235                        return IWL_SCAN_TYPE_FRAGMENTED;
 236
 237                /*
 238                 * in case of DCM with GO where BSS DTIM interval < 220msec
 239                 * set all scan requests as fast-balance scan
 240                 */
 241                if (vif && vif->type == NL80211_IFTYPE_STATION &&
 242                    vif->bss_conf.dtim_period < 220 &&
 243                    data.is_dcm_with_p2p_go)
 244                        return IWL_SCAN_TYPE_FAST_BALANCE;
 245        }
 246
 247        if (load >= IWL_MVM_TRAFFIC_MEDIUM || low_latency)
 248                return IWL_SCAN_TYPE_MILD;
 249
 250        return IWL_SCAN_TYPE_WILD;
 251}
 252
 253static enum
 254iwl_mvm_scan_type iwl_mvm_get_scan_type(struct iwl_mvm *mvm,
 255                                        struct ieee80211_vif *vif)
 256{
 257        enum iwl_mvm_traffic_load load;
 258        bool low_latency;
 259
 260        load = iwl_mvm_get_traffic_load(mvm);
 261        low_latency = iwl_mvm_low_latency(mvm);
 262
 263        return _iwl_mvm_get_scan_type(mvm, vif, load, low_latency);
 264}
 265
 266static enum
 267iwl_mvm_scan_type iwl_mvm_get_scan_type_band(struct iwl_mvm *mvm,
 268                                             struct ieee80211_vif *vif,
 269                                             enum nl80211_band band)
 270{
 271        enum iwl_mvm_traffic_load load;
 272        bool low_latency;
 273
 274        load = iwl_mvm_get_traffic_load_band(mvm, band);
 275        low_latency = iwl_mvm_low_latency_band(mvm, band);
 276
 277        return _iwl_mvm_get_scan_type(mvm, vif, load, low_latency);
 278}
 279
 280static inline bool iwl_mvm_rrm_scan_needed(struct iwl_mvm *mvm)
 281{
 282        /* require rrm scan whenever the fw supports it */
 283        return fw_has_capa(&mvm->fw->ucode_capa,
 284                           IWL_UCODE_TLV_CAPA_DS_PARAM_SET_IE_SUPPORT);
 285}
 286
 287static int iwl_mvm_max_scan_ie_fw_cmd_room(struct iwl_mvm *mvm)
 288{
 289        int max_probe_len;
 290
 291        max_probe_len = SCAN_OFFLOAD_PROBE_REQ_SIZE;
 292
 293        /* we create the 802.11 header and SSID element */
 294        max_probe_len -= 24 + 2;
 295
 296        /* DS parameter set element is added on 2.4GHZ band if required */
 297        if (iwl_mvm_rrm_scan_needed(mvm))
 298                max_probe_len -= 3;
 299
 300        return max_probe_len;
 301}
 302
 303int iwl_mvm_max_scan_ie_len(struct iwl_mvm *mvm)
 304{
 305        int max_ie_len = iwl_mvm_max_scan_ie_fw_cmd_room(mvm);
 306
 307        /* TODO: [BUG] This function should return the maximum allowed size of
 308         * scan IEs, however the LMAC scan api contains both 2GHZ and 5GHZ IEs
 309         * in the same command. So the correct implementation of this function
 310         * is just iwl_mvm_max_scan_ie_fw_cmd_room() / 2. Currently the scan
 311         * command has only 512 bytes and it would leave us with about 240
 312         * bytes for scan IEs, which is clearly not enough. So meanwhile
 313         * we will report an incorrect value. This may result in a failure to
 314         * issue a scan in unified_scan_lmac and unified_sched_scan_lmac
 315         * functions with -ENOBUFS, if a large enough probe will be provided.
 316         */
 317        return max_ie_len;
 318}
 319
 320void iwl_mvm_rx_lmac_scan_iter_complete_notif(struct iwl_mvm *mvm,
 321                                              struct iwl_rx_cmd_buffer *rxb)
 322{
 323        struct iwl_rx_packet *pkt = rxb_addr(rxb);
 324        struct iwl_lmac_scan_complete_notif *notif = (void *)pkt->data;
 325
 326        IWL_DEBUG_SCAN(mvm,
 327                       "Scan offload iteration complete: status=0x%x scanned channels=%d\n",
 328                       notif->status, notif->scanned_channels);
 329
 330        if (mvm->sched_scan_pass_all == SCHED_SCAN_PASS_ALL_FOUND) {
 331                IWL_DEBUG_SCAN(mvm, "Pass all scheduled scan results found\n");
 332                ieee80211_sched_scan_results(mvm->hw);
 333                mvm->sched_scan_pass_all = SCHED_SCAN_PASS_ALL_ENABLED;
 334        }
 335}
 336
 337void iwl_mvm_rx_scan_match_found(struct iwl_mvm *mvm,
 338                                 struct iwl_rx_cmd_buffer *rxb)
 339{
 340        IWL_DEBUG_SCAN(mvm, "Scheduled scan results\n");
 341        ieee80211_sched_scan_results(mvm->hw);
 342}
 343
 344static const char *iwl_mvm_ebs_status_str(enum iwl_scan_ebs_status status)
 345{
 346        switch (status) {
 347        case IWL_SCAN_EBS_SUCCESS:
 348                return "successful";
 349        case IWL_SCAN_EBS_INACTIVE:
 350                return "inactive";
 351        case IWL_SCAN_EBS_FAILED:
 352        case IWL_SCAN_EBS_CHAN_NOT_FOUND:
 353        default:
 354                return "failed";
 355        }
 356}
 357
 358void iwl_mvm_rx_lmac_scan_complete_notif(struct iwl_mvm *mvm,
 359                                         struct iwl_rx_cmd_buffer *rxb)
 360{
 361        struct iwl_rx_packet *pkt = rxb_addr(rxb);
 362        struct iwl_periodic_scan_complete *scan_notif = (void *)pkt->data;
 363        bool aborted = (scan_notif->status == IWL_SCAN_OFFLOAD_ABORTED);
 364
 365        /* If this happens, the firmware has mistakenly sent an LMAC
 366         * notification during UMAC scans -- warn and ignore it.
 367         */
 368        if (WARN_ON_ONCE(fw_has_capa(&mvm->fw->ucode_capa,
 369                                     IWL_UCODE_TLV_CAPA_UMAC_SCAN)))
 370                return;
 371
 372        /* scan status must be locked for proper checking */
 373        lockdep_assert_held(&mvm->mutex);
 374
 375        /* We first check if we were stopping a scan, in which case we
 376         * just clear the stopping flag.  Then we check if it was a
 377         * firmware initiated stop, in which case we need to inform
 378         * mac80211.
 379         * Note that we can have a stopping and a running scan
 380         * simultaneously, but we can't have two different types of
 381         * scans stopping or running at the same time (since LMAC
 382         * doesn't support it).
 383         */
 384
 385        if (mvm->scan_status & IWL_MVM_SCAN_STOPPING_SCHED) {
 386                WARN_ON_ONCE(mvm->scan_status & IWL_MVM_SCAN_STOPPING_REGULAR);
 387
 388                IWL_DEBUG_SCAN(mvm, "Scheduled scan %s, EBS status %s\n",
 389                               aborted ? "aborted" : "completed",
 390                               iwl_mvm_ebs_status_str(scan_notif->ebs_status));
 391                IWL_DEBUG_SCAN(mvm,
 392                               "Last line %d, Last iteration %d, Time after last iteration %d\n",
 393                               scan_notif->last_schedule_line,
 394                               scan_notif->last_schedule_iteration,
 395                               __le32_to_cpu(scan_notif->time_after_last_iter));
 396
 397                mvm->scan_status &= ~IWL_MVM_SCAN_STOPPING_SCHED;
 398        } else if (mvm->scan_status & IWL_MVM_SCAN_STOPPING_REGULAR) {
 399                IWL_DEBUG_SCAN(mvm, "Regular scan %s, EBS status %s\n",
 400                               aborted ? "aborted" : "completed",
 401                               iwl_mvm_ebs_status_str(scan_notif->ebs_status));
 402
 403                mvm->scan_status &= ~IWL_MVM_SCAN_STOPPING_REGULAR;
 404        } else if (mvm->scan_status & IWL_MVM_SCAN_SCHED) {
 405                WARN_ON_ONCE(mvm->scan_status & IWL_MVM_SCAN_REGULAR);
 406
 407                IWL_DEBUG_SCAN(mvm, "Scheduled scan %s, EBS status %s\n",
 408                               aborted ? "aborted" : "completed",
 409                               iwl_mvm_ebs_status_str(scan_notif->ebs_status));
 410                IWL_DEBUG_SCAN(mvm,
 411                               "Last line %d, Last iteration %d, Time after last iteration %d (FW)\n",
 412                               scan_notif->last_schedule_line,
 413                               scan_notif->last_schedule_iteration,
 414                               __le32_to_cpu(scan_notif->time_after_last_iter));
 415
 416                mvm->scan_status &= ~IWL_MVM_SCAN_SCHED;
 417                ieee80211_sched_scan_stopped(mvm->hw);
 418                mvm->sched_scan_pass_all = SCHED_SCAN_PASS_ALL_DISABLED;
 419        } else if (mvm->scan_status & IWL_MVM_SCAN_REGULAR) {
 420                struct cfg80211_scan_info info = {
 421                        .aborted = aborted,
 422                };
 423
 424                IWL_DEBUG_SCAN(mvm, "Regular scan %s, EBS status %s (FW)\n",
 425                               aborted ? "aborted" : "completed",
 426                               iwl_mvm_ebs_status_str(scan_notif->ebs_status));
 427
 428                mvm->scan_status &= ~IWL_MVM_SCAN_REGULAR;
 429                ieee80211_scan_completed(mvm->hw, &info);
 430                cancel_delayed_work(&mvm->scan_timeout_dwork);
 431                iwl_mvm_resume_tcm(mvm);
 432        } else {
 433                IWL_ERR(mvm,
 434                        "got scan complete notification but no scan is running\n");
 435        }
 436
 437        mvm->last_ebs_successful =
 438                        scan_notif->ebs_status == IWL_SCAN_EBS_SUCCESS ||
 439                        scan_notif->ebs_status == IWL_SCAN_EBS_INACTIVE;
 440}
 441
 442static int iwl_ssid_exist(u8 *ssid, u8 ssid_len, struct iwl_ssid_ie *ssid_list)
 443{
 444        int i;
 445
 446        for (i = 0; i < PROBE_OPTION_MAX; i++) {
 447                if (!ssid_list[i].len)
 448                        break;
 449                if (ssid_list[i].len == ssid_len &&
 450                    !memcmp(ssid_list->ssid, ssid, ssid_len))
 451                        return i;
 452        }
 453        return -1;
 454}
 455
 456/* We insert the SSIDs in an inverted order, because the FW will
 457 * invert it back.
 458 */
 459static void iwl_scan_build_ssids(struct iwl_mvm_scan_params *params,
 460                                 struct iwl_ssid_ie *ssids,
 461                                 u32 *ssid_bitmap)
 462{
 463        int i, j;
 464        int index;
 465        u32 tmp_bitmap = 0;
 466
 467        /*
 468         * copy SSIDs from match list.
 469         * iwl_config_sched_scan_profiles() uses the order of these ssids to
 470         * config match list.
 471         */
 472        for (i = 0, j = params->n_match_sets - 1;
 473             j >= 0 && i < PROBE_OPTION_MAX;
 474             i++, j--) {
 475                /* skip empty SSID matchsets */
 476                if (!params->match_sets[j].ssid.ssid_len)
 477                        continue;
 478                ssids[i].id = WLAN_EID_SSID;
 479                ssids[i].len = params->match_sets[j].ssid.ssid_len;
 480                memcpy(ssids[i].ssid, params->match_sets[j].ssid.ssid,
 481                       ssids[i].len);
 482        }
 483
 484        /* add SSIDs from scan SSID list */
 485        for (j = params->n_ssids - 1;
 486             j >= 0 && i < PROBE_OPTION_MAX;
 487             i++, j--) {
 488                index = iwl_ssid_exist(params->ssids[j].ssid,
 489                                       params->ssids[j].ssid_len,
 490                                       ssids);
 491                if (index < 0) {
 492                        ssids[i].id = WLAN_EID_SSID;
 493                        ssids[i].len = params->ssids[j].ssid_len;
 494                        memcpy(ssids[i].ssid, params->ssids[j].ssid,
 495                               ssids[i].len);
 496                        tmp_bitmap |= BIT(i);
 497                } else {
 498                        tmp_bitmap |= BIT(index);
 499                }
 500        }
 501        if (ssid_bitmap)
 502                *ssid_bitmap = tmp_bitmap;
 503}
 504
 505static int
 506iwl_mvm_config_sched_scan_profiles(struct iwl_mvm *mvm,
 507                                   struct cfg80211_sched_scan_request *req)
 508{
 509        struct iwl_scan_offload_profile *profile;
 510        struct iwl_scan_offload_profile_cfg_v1 *profile_cfg_v1;
 511        struct iwl_scan_offload_blocklist *blocklist;
 512        struct iwl_scan_offload_profile_cfg_data *data;
 513        int max_profiles = iwl_umac_scan_get_max_profiles(mvm->fw);
 514        int profile_cfg_size = sizeof(*data) +
 515                sizeof(*profile) * max_profiles;
 516        struct iwl_host_cmd cmd = {
 517                .id = SCAN_OFFLOAD_UPDATE_PROFILES_CMD,
 518                .len[1] = profile_cfg_size,
 519                .dataflags[0] = IWL_HCMD_DFL_NOCOPY,
 520                .dataflags[1] = IWL_HCMD_DFL_NOCOPY,
 521        };
 522        int blocklist_len;
 523        int i;
 524        int ret;
 525
 526        if (WARN_ON(req->n_match_sets > max_profiles))
 527                return -EIO;
 528
 529        if (mvm->fw->ucode_capa.flags & IWL_UCODE_TLV_FLAGS_SHORT_BL)
 530                blocklist_len = IWL_SCAN_SHORT_BLACKLIST_LEN;
 531        else
 532                blocklist_len = IWL_SCAN_MAX_BLACKLIST_LEN;
 533
 534        blocklist = kcalloc(blocklist_len, sizeof(*blocklist), GFP_KERNEL);
 535        if (!blocklist)
 536                return -ENOMEM;
 537
 538        profile_cfg_v1 = kzalloc(profile_cfg_size, GFP_KERNEL);
 539        if (!profile_cfg_v1) {
 540                ret = -ENOMEM;
 541                goto free_blocklist;
 542        }
 543
 544        cmd.data[0] = blocklist;
 545        cmd.len[0] = sizeof(*blocklist) * blocklist_len;
 546        cmd.data[1] = profile_cfg_v1;
 547
 548        /* if max_profile is MAX_PROFILES_V2, we have the new API */
 549        if (max_profiles == IWL_SCAN_MAX_PROFILES_V2) {
 550                struct iwl_scan_offload_profile_cfg *profile_cfg =
 551                        (struct iwl_scan_offload_profile_cfg *)profile_cfg_v1;
 552
 553                data = &profile_cfg->data;
 554        } else {
 555                data = &profile_cfg_v1->data;
 556        }
 557
 558        /* No blocklist configuration */
 559        data->num_profiles = req->n_match_sets;
 560        data->active_clients = SCAN_CLIENT_SCHED_SCAN;
 561        data->pass_match = SCAN_CLIENT_SCHED_SCAN;
 562        data->match_notify = SCAN_CLIENT_SCHED_SCAN;
 563
 564        if (!req->n_match_sets || !req->match_sets[0].ssid.ssid_len)
 565                data->any_beacon_notify = SCAN_CLIENT_SCHED_SCAN;
 566
 567        for (i = 0; i < req->n_match_sets; i++) {
 568                profile = &profile_cfg_v1->profiles[i];
 569                profile->ssid_index = i;
 570                /* Support any cipher and auth algorithm */
 571                profile->unicast_cipher = 0xff;
 572                profile->auth_alg = IWL_AUTH_ALGO_UNSUPPORTED |
 573                        IWL_AUTH_ALGO_NONE | IWL_AUTH_ALGO_PSK | IWL_AUTH_ALGO_8021X |
 574                        IWL_AUTH_ALGO_SAE | IWL_AUTH_ALGO_8021X_SHA384 | IWL_AUTH_ALGO_OWE;
 575                profile->network_type = IWL_NETWORK_TYPE_ANY;
 576                profile->band_selection = IWL_SCAN_OFFLOAD_SELECT_ANY;
 577                profile->client_bitmap = SCAN_CLIENT_SCHED_SCAN;
 578        }
 579
 580        IWL_DEBUG_SCAN(mvm, "Sending scheduled scan profile config\n");
 581
 582        ret = iwl_mvm_send_cmd(mvm, &cmd);
 583        kfree(profile_cfg_v1);
 584free_blocklist:
 585        kfree(blocklist);
 586
 587        return ret;
 588}
 589
 590static bool iwl_mvm_scan_pass_all(struct iwl_mvm *mvm,
 591                                  struct cfg80211_sched_scan_request *req)
 592{
 593        if (req->n_match_sets && req->match_sets[0].ssid.ssid_len) {
 594                IWL_DEBUG_SCAN(mvm,
 595                               "Sending scheduled scan with filtering, n_match_sets %d\n",
 596                               req->n_match_sets);
 597                mvm->sched_scan_pass_all = SCHED_SCAN_PASS_ALL_DISABLED;
 598                return false;
 599        }
 600
 601        IWL_DEBUG_SCAN(mvm, "Sending Scheduled scan without filtering\n");
 602
 603        mvm->sched_scan_pass_all = SCHED_SCAN_PASS_ALL_ENABLED;
 604        return true;
 605}
 606
 607static int iwl_mvm_lmac_scan_abort(struct iwl_mvm *mvm)
 608{
 609        int ret;
 610        struct iwl_host_cmd cmd = {
 611                .id = SCAN_OFFLOAD_ABORT_CMD,
 612        };
 613        u32 status = CAN_ABORT_STATUS;
 614
 615        ret = iwl_mvm_send_cmd_status(mvm, &cmd, &status);
 616        if (ret)
 617                return ret;
 618
 619        if (status != CAN_ABORT_STATUS) {
 620                /*
 621                 * The scan abort will return 1 for success or
 622                 * 2 for "failure".  A failure condition can be
 623                 * due to simply not being in an active scan which
 624                 * can occur if we send the scan abort before the
 625                 * microcode has notified us that a scan is completed.
 626                 */
 627                IWL_DEBUG_SCAN(mvm, "SCAN OFFLOAD ABORT ret %d.\n", status);
 628                ret = -ENOENT;
 629        }
 630
 631        return ret;
 632}
 633
 634static void iwl_mvm_scan_fill_tx_cmd(struct iwl_mvm *mvm,
 635                                     struct iwl_scan_req_tx_cmd *tx_cmd,
 636                                     bool no_cck)
 637{
 638        tx_cmd[0].tx_flags = cpu_to_le32(TX_CMD_FLG_SEQ_CTL |
 639                                         TX_CMD_FLG_BT_DIS);
 640        tx_cmd[0].rate_n_flags = iwl_mvm_scan_rate_n_flags(mvm,
 641                                                           NL80211_BAND_2GHZ,
 642                                                           no_cck);
 643
 644        if (iwl_fw_lookup_cmd_ver(mvm->fw, ADD_STA, 0) < 12) {
 645                tx_cmd[0].sta_id = mvm->aux_sta.sta_id;
 646                tx_cmd[1].sta_id = mvm->aux_sta.sta_id;
 647
 648        /*
 649         * Fw doesn't use this sta anymore, pending deprecation via HOST API
 650         * change
 651         */
 652        } else {
 653                tx_cmd[0].sta_id = 0xff;
 654                tx_cmd[1].sta_id = 0xff;
 655        }
 656
 657        tx_cmd[1].tx_flags = cpu_to_le32(TX_CMD_FLG_SEQ_CTL |
 658                                         TX_CMD_FLG_BT_DIS);
 659
 660        tx_cmd[1].rate_n_flags = iwl_mvm_scan_rate_n_flags(mvm,
 661                                                           NL80211_BAND_5GHZ,
 662                                                           no_cck);
 663}
 664
 665static void
 666iwl_mvm_lmac_scan_cfg_channels(struct iwl_mvm *mvm,
 667                               struct ieee80211_channel **channels,
 668                               int n_channels, u32 ssid_bitmap,
 669                               struct iwl_scan_req_lmac *cmd)
 670{
 671        struct iwl_scan_channel_cfg_lmac *channel_cfg = (void *)&cmd->data;
 672        int i;
 673
 674        for (i = 0; i < n_channels; i++) {
 675                channel_cfg[i].channel_num =
 676                        cpu_to_le16(channels[i]->hw_value);
 677                channel_cfg[i].iter_count = cpu_to_le16(1);
 678                channel_cfg[i].iter_interval = 0;
 679                channel_cfg[i].flags =
 680                        cpu_to_le32(IWL_UNIFIED_SCAN_CHANNEL_PARTIAL |
 681                                    ssid_bitmap);
 682        }
 683}
 684
 685static u8 *iwl_mvm_copy_and_insert_ds_elem(struct iwl_mvm *mvm, const u8 *ies,
 686                                           size_t len, u8 *const pos)
 687{
 688        static const u8 before_ds_params[] = {
 689                        WLAN_EID_SSID,
 690                        WLAN_EID_SUPP_RATES,
 691                        WLAN_EID_REQUEST,
 692                        WLAN_EID_EXT_SUPP_RATES,
 693        };
 694        size_t offs;
 695        u8 *newpos = pos;
 696
 697        if (!iwl_mvm_rrm_scan_needed(mvm)) {
 698                memcpy(newpos, ies, len);
 699                return newpos + len;
 700        }
 701
 702        offs = ieee80211_ie_split(ies, len,
 703                                  before_ds_params,
 704                                  ARRAY_SIZE(before_ds_params),
 705                                  0);
 706
 707        memcpy(newpos, ies, offs);
 708        newpos += offs;
 709
 710        /* Add a placeholder for DS Parameter Set element */
 711        *newpos++ = WLAN_EID_DS_PARAMS;
 712        *newpos++ = 1;
 713        *newpos++ = 0;
 714
 715        memcpy(newpos, ies + offs, len - offs);
 716        newpos += len - offs;
 717
 718        return newpos;
 719}
 720
 721#define WFA_TPC_IE_LEN  9
 722
 723static void iwl_mvm_add_tpc_report_ie(u8 *pos)
 724{
 725        pos[0] = WLAN_EID_VENDOR_SPECIFIC;
 726        pos[1] = WFA_TPC_IE_LEN - 2;
 727        pos[2] = (WLAN_OUI_MICROSOFT >> 16) & 0xff;
 728        pos[3] = (WLAN_OUI_MICROSOFT >> 8) & 0xff;
 729        pos[4] = WLAN_OUI_MICROSOFT & 0xff;
 730        pos[5] = WLAN_OUI_TYPE_MICROSOFT_TPC;
 731        pos[6] = 0;
 732        /* pos[7] - tx power will be inserted by the FW */
 733        pos[7] = 0;
 734        pos[8] = 0;
 735}
 736
 737static void
 738iwl_mvm_build_scan_probe(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
 739                         struct ieee80211_scan_ies *ies,
 740                         struct iwl_mvm_scan_params *params)
 741{
 742        struct ieee80211_mgmt *frame = (void *)params->preq.buf;
 743        u8 *pos, *newpos;
 744        const u8 *mac_addr = params->flags & NL80211_SCAN_FLAG_RANDOM_ADDR ?
 745                params->mac_addr : NULL;
 746
 747        /*
 748         * Unfortunately, right now the offload scan doesn't support randomising
 749         * within the firmware, so until the firmware API is ready we implement
 750         * it in the driver. This means that the scan iterations won't really be
 751         * random, only when it's restarted, but at least that helps a bit.
 752         */
 753        if (mac_addr)
 754                get_random_mask_addr(frame->sa, mac_addr,
 755                                     params->mac_addr_mask);
 756        else
 757                memcpy(frame->sa, vif->addr, ETH_ALEN);
 758
 759        frame->frame_control = cpu_to_le16(IEEE80211_STYPE_PROBE_REQ);
 760        eth_broadcast_addr(frame->da);
 761        eth_broadcast_addr(frame->bssid);
 762        frame->seq_ctrl = 0;
 763
 764        pos = frame->u.probe_req.variable;
 765        *pos++ = WLAN_EID_SSID;
 766        *pos++ = 0;
 767
 768        params->preq.mac_header.offset = 0;
 769        params->preq.mac_header.len = cpu_to_le16(24 + 2);
 770
 771        /* Insert ds parameter set element on 2.4 GHz band */
 772        newpos = iwl_mvm_copy_and_insert_ds_elem(mvm,
 773                                                 ies->ies[NL80211_BAND_2GHZ],
 774                                                 ies->len[NL80211_BAND_2GHZ],
 775                                                 pos);
 776        params->preq.band_data[0].offset = cpu_to_le16(pos - params->preq.buf);
 777        params->preq.band_data[0].len = cpu_to_le16(newpos - pos);
 778        pos = newpos;
 779
 780        memcpy(pos, ies->ies[NL80211_BAND_5GHZ],
 781               ies->len[NL80211_BAND_5GHZ]);
 782        params->preq.band_data[1].offset = cpu_to_le16(pos - params->preq.buf);
 783        params->preq.band_data[1].len =
 784                cpu_to_le16(ies->len[NL80211_BAND_5GHZ]);
 785        pos += ies->len[NL80211_BAND_5GHZ];
 786
 787        memcpy(pos, ies->ies[NL80211_BAND_6GHZ],
 788               ies->len[NL80211_BAND_6GHZ]);
 789        params->preq.band_data[2].offset = cpu_to_le16(pos - params->preq.buf);
 790        params->preq.band_data[2].len =
 791                cpu_to_le16(ies->len[NL80211_BAND_6GHZ]);
 792        pos += ies->len[NL80211_BAND_6GHZ];
 793        memcpy(pos, ies->common_ies, ies->common_ie_len);
 794        params->preq.common_data.offset = cpu_to_le16(pos - params->preq.buf);
 795
 796        if (iwl_mvm_rrm_scan_needed(mvm) &&
 797            !fw_has_capa(&mvm->fw->ucode_capa,
 798                         IWL_UCODE_TLV_CAPA_WFA_TPC_REP_IE_SUPPORT)) {
 799                iwl_mvm_add_tpc_report_ie(pos + ies->common_ie_len);
 800                params->preq.common_data.len = cpu_to_le16(ies->common_ie_len +
 801                                                           WFA_TPC_IE_LEN);
 802        } else {
 803                params->preq.common_data.len = cpu_to_le16(ies->common_ie_len);
 804        }
 805}
 806
 807static void iwl_mvm_scan_lmac_dwell(struct iwl_mvm *mvm,
 808                                    struct iwl_scan_req_lmac *cmd,
 809                                    struct iwl_mvm_scan_params *params)
 810{
 811        cmd->active_dwell = IWL_SCAN_DWELL_ACTIVE;
 812        cmd->passive_dwell = IWL_SCAN_DWELL_PASSIVE;
 813        cmd->fragmented_dwell = IWL_SCAN_DWELL_FRAGMENTED;
 814        cmd->extended_dwell = IWL_SCAN_DWELL_EXTENDED;
 815        cmd->max_out_time = cpu_to_le32(scan_timing[params->type].max_out_time);
 816        cmd->suspend_time = cpu_to_le32(scan_timing[params->type].suspend_time);
 817        cmd->scan_prio = cpu_to_le32(IWL_SCAN_PRIORITY_EXT_6);
 818}
 819
 820static inline bool iwl_mvm_scan_fits(struct iwl_mvm *mvm, int n_ssids,
 821                                     struct ieee80211_scan_ies *ies,
 822                                     int n_channels)
 823{
 824        return ((n_ssids <= PROBE_OPTION_MAX) &&
 825                (n_channels <= mvm->fw->ucode_capa.n_scan_channels) &
 826                (ies->common_ie_len +
 827                 ies->len[NL80211_BAND_2GHZ] +
 828                 ies->len[NL80211_BAND_5GHZ] <=
 829                 iwl_mvm_max_scan_ie_fw_cmd_room(mvm)));
 830}
 831
 832static inline bool iwl_mvm_scan_use_ebs(struct iwl_mvm *mvm,
 833                                        struct ieee80211_vif *vif)
 834{
 835        const struct iwl_ucode_capabilities *capa = &mvm->fw->ucode_capa;
 836        bool low_latency;
 837
 838        if (iwl_mvm_is_cdb_supported(mvm))
 839                low_latency = iwl_mvm_low_latency_band(mvm, NL80211_BAND_5GHZ);
 840        else
 841                low_latency = iwl_mvm_low_latency(mvm);
 842
 843        /* We can only use EBS if:
 844         *      1. the feature is supported;
 845         *      2. the last EBS was successful;
 846         *      3. if only single scan, the single scan EBS API is supported;
 847         *      4. it's not a p2p find operation.
 848         *      5. we are not in low latency mode,
 849         *         or if fragmented ebs is supported by the FW
 850         */
 851        return ((capa->flags & IWL_UCODE_TLV_FLAGS_EBS_SUPPORT) &&
 852                mvm->last_ebs_successful && IWL_MVM_ENABLE_EBS &&
 853                vif->type != NL80211_IFTYPE_P2P_DEVICE &&
 854                (!low_latency || iwl_mvm_is_frag_ebs_supported(mvm)));
 855}
 856
 857static inline bool iwl_mvm_is_regular_scan(struct iwl_mvm_scan_params *params)
 858{
 859        return params->n_scan_plans == 1 &&
 860                params->scan_plans[0].iterations == 1;
 861}
 862
 863static bool iwl_mvm_is_scan_fragmented(enum iwl_mvm_scan_type type)
 864{
 865        return (type == IWL_SCAN_TYPE_FRAGMENTED ||
 866                type == IWL_SCAN_TYPE_FAST_BALANCE);
 867}
 868
 869static int iwl_mvm_scan_lmac_flags(struct iwl_mvm *mvm,
 870                                   struct iwl_mvm_scan_params *params,
 871                                   struct ieee80211_vif *vif)
 872{
 873        int flags = 0;
 874
 875        if (params->n_ssids == 0)
 876                flags |= IWL_MVM_LMAC_SCAN_FLAG_PASSIVE;
 877
 878        if (params->n_ssids == 1 && params->ssids[0].ssid_len != 0)
 879                flags |= IWL_MVM_LMAC_SCAN_FLAG_PRE_CONNECTION;
 880
 881        if (iwl_mvm_is_scan_fragmented(params->type))
 882                flags |= IWL_MVM_LMAC_SCAN_FLAG_FRAGMENTED;
 883
 884        if (iwl_mvm_rrm_scan_needed(mvm) &&
 885            fw_has_capa(&mvm->fw->ucode_capa,
 886                        IWL_UCODE_TLV_CAPA_WFA_TPC_REP_IE_SUPPORT))
 887                flags |= IWL_MVM_LMAC_SCAN_FLAGS_RRM_ENABLED;
 888
 889        if (params->pass_all)
 890                flags |= IWL_MVM_LMAC_SCAN_FLAG_PASS_ALL;
 891        else
 892                flags |= IWL_MVM_LMAC_SCAN_FLAG_MATCH;
 893
 894#ifdef CONFIG_IWLWIFI_DEBUGFS
 895        if (mvm->scan_iter_notif_enabled)
 896                flags |= IWL_MVM_LMAC_SCAN_FLAG_ITER_COMPLETE;
 897#endif
 898
 899        if (mvm->sched_scan_pass_all == SCHED_SCAN_PASS_ALL_ENABLED)
 900                flags |= IWL_MVM_LMAC_SCAN_FLAG_ITER_COMPLETE;
 901
 902        if (iwl_mvm_is_regular_scan(params) &&
 903            vif->type != NL80211_IFTYPE_P2P_DEVICE &&
 904            !iwl_mvm_is_scan_fragmented(params->type))
 905                flags |= IWL_MVM_LMAC_SCAN_FLAG_EXTENDED_DWELL;
 906
 907        return flags;
 908}
 909
 910static void
 911iwl_mvm_scan_set_legacy_probe_req(struct iwl_scan_probe_req_v1 *p_req,
 912                                  struct iwl_scan_probe_req *src_p_req)
 913{
 914        int i;
 915
 916        p_req->mac_header = src_p_req->mac_header;
 917        for (i = 0; i < SCAN_NUM_BAND_PROBE_DATA_V_1; i++)
 918                p_req->band_data[i] = src_p_req->band_data[i];
 919        p_req->common_data = src_p_req->common_data;
 920        memcpy(p_req->buf, src_p_req->buf, sizeof(p_req->buf));
 921}
 922
 923static int iwl_mvm_scan_lmac(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
 924                             struct iwl_mvm_scan_params *params)
 925{
 926        struct iwl_scan_req_lmac *cmd = mvm->scan_cmd;
 927        struct iwl_scan_probe_req_v1 *preq =
 928                (void *)(cmd->data + sizeof(struct iwl_scan_channel_cfg_lmac) *
 929                         mvm->fw->ucode_capa.n_scan_channels);
 930        u32 ssid_bitmap = 0;
 931        int i;
 932        u8 band;
 933
 934        if (WARN_ON(params->n_scan_plans > IWL_MAX_SCHED_SCAN_PLANS))
 935                return -EINVAL;
 936
 937        iwl_mvm_scan_lmac_dwell(mvm, cmd, params);
 938
 939        cmd->rx_chain_select = iwl_mvm_scan_rx_chain(mvm);
 940        cmd->iter_num = cpu_to_le32(1);
 941        cmd->n_channels = (u8)params->n_channels;
 942
 943        cmd->delay = cpu_to_le32(params->delay);
 944
 945        cmd->scan_flags = cpu_to_le32(iwl_mvm_scan_lmac_flags(mvm, params,
 946                                                              vif));
 947
 948        band = iwl_mvm_phy_band_from_nl80211(params->channels[0]->band);
 949        cmd->flags = cpu_to_le32(band);
 950        cmd->filter_flags = cpu_to_le32(MAC_FILTER_ACCEPT_GRP |
 951                                        MAC_FILTER_IN_BEACON);
 952        iwl_mvm_scan_fill_tx_cmd(mvm, cmd->tx_cmd, params->no_cck);
 953        iwl_scan_build_ssids(params, cmd->direct_scan, &ssid_bitmap);
 954
 955        /* this API uses bits 1-20 instead of 0-19 */
 956        ssid_bitmap <<= 1;
 957
 958        for (i = 0; i < params->n_scan_plans; i++) {
 959                struct cfg80211_sched_scan_plan *scan_plan =
 960                        &params->scan_plans[i];
 961
 962                cmd->schedule[i].delay =
 963                        cpu_to_le16(scan_plan->interval);
 964                cmd->schedule[i].iterations = scan_plan->iterations;
 965                cmd->schedule[i].full_scan_mul = 1;
 966        }
 967
 968        /*
 969         * If the number of iterations of the last scan plan is set to
 970         * zero, it should run infinitely. However, this is not always the case.
 971         * For example, when regular scan is requested the driver sets one scan
 972         * plan with one iteration.
 973         */
 974        if (!cmd->schedule[i - 1].iterations)
 975                cmd->schedule[i - 1].iterations = 0xff;
 976
 977        if (iwl_mvm_scan_use_ebs(mvm, vif)) {
 978                cmd->channel_opt[0].flags =
 979                        cpu_to_le16(IWL_SCAN_CHANNEL_FLAG_EBS |
 980                                    IWL_SCAN_CHANNEL_FLAG_EBS_ACCURATE |
 981                                    IWL_SCAN_CHANNEL_FLAG_CACHE_ADD);
 982                cmd->channel_opt[0].non_ebs_ratio =
 983                        cpu_to_le16(IWL_DENSE_EBS_SCAN_RATIO);
 984                cmd->channel_opt[1].flags =
 985                        cpu_to_le16(IWL_SCAN_CHANNEL_FLAG_EBS |
 986                                    IWL_SCAN_CHANNEL_FLAG_EBS_ACCURATE |
 987                                    IWL_SCAN_CHANNEL_FLAG_CACHE_ADD);
 988                cmd->channel_opt[1].non_ebs_ratio =
 989                        cpu_to_le16(IWL_SPARSE_EBS_SCAN_RATIO);
 990        }
 991
 992        iwl_mvm_lmac_scan_cfg_channels(mvm, params->channels,
 993                                       params->n_channels, ssid_bitmap, cmd);
 994
 995        iwl_mvm_scan_set_legacy_probe_req(preq, &params->preq);
 996
 997        return 0;
 998}
 999
1000static int rate_to_scan_rate_flag(unsigned int rate)
1001{
1002        static const int rate_to_scan_rate[IWL_RATE_COUNT] = {
1003                [IWL_RATE_1M_INDEX]     = SCAN_CONFIG_RATE_1M,
1004                [IWL_RATE_2M_INDEX]     = SCAN_CONFIG_RATE_2M,
1005                [IWL_RATE_5M_INDEX]     = SCAN_CONFIG_RATE_5M,
1006                [IWL_RATE_11M_INDEX]    = SCAN_CONFIG_RATE_11M,
1007                [IWL_RATE_6M_INDEX]     = SCAN_CONFIG_RATE_6M,
1008                [IWL_RATE_9M_INDEX]     = SCAN_CONFIG_RATE_9M,
1009                [IWL_RATE_12M_INDEX]    = SCAN_CONFIG_RATE_12M,
1010                [IWL_RATE_18M_INDEX]    = SCAN_CONFIG_RATE_18M,
1011                [IWL_RATE_24M_INDEX]    = SCAN_CONFIG_RATE_24M,
1012                [IWL_RATE_36M_INDEX]    = SCAN_CONFIG_RATE_36M,
1013                [IWL_RATE_48M_INDEX]    = SCAN_CONFIG_RATE_48M,
1014                [IWL_RATE_54M_INDEX]    = SCAN_CONFIG_RATE_54M,
1015        };
1016
1017        return rate_to_scan_rate[rate];
1018}
1019
1020static __le32 iwl_mvm_scan_config_rates(struct iwl_mvm *mvm)
1021{
1022        struct ieee80211_supported_band *band;
1023        unsigned int rates = 0;
1024        int i;
1025
1026        band = &mvm->nvm_data->bands[NL80211_BAND_2GHZ];
1027        for (i = 0; i < band->n_bitrates; i++)
1028                rates |= rate_to_scan_rate_flag(band->bitrates[i].hw_value);
1029        band = &mvm->nvm_data->bands[NL80211_BAND_5GHZ];
1030        for (i = 0; i < band->n_bitrates; i++)
1031                rates |= rate_to_scan_rate_flag(band->bitrates[i].hw_value);
1032
1033        /* Set both basic rates and supported rates */
1034        rates |= SCAN_CONFIG_SUPPORTED_RATE(rates);
1035
1036        return cpu_to_le32(rates);
1037}
1038
1039static void iwl_mvm_fill_scan_dwell(struct iwl_mvm *mvm,
1040                                    struct iwl_scan_dwell *dwell)
1041{
1042        dwell->active = IWL_SCAN_DWELL_ACTIVE;
1043        dwell->passive = IWL_SCAN_DWELL_PASSIVE;
1044        dwell->fragmented = IWL_SCAN_DWELL_FRAGMENTED;
1045        dwell->extended = IWL_SCAN_DWELL_EXTENDED;
1046}
1047
1048static void iwl_mvm_fill_channels(struct iwl_mvm *mvm, u8 *channels,
1049                                  u32 max_channels)
1050{
1051        struct ieee80211_supported_band *band;
1052        int i, j = 0;
1053
1054        band = &mvm->nvm_data->bands[NL80211_BAND_2GHZ];
1055        for (i = 0; i < band->n_channels && j < max_channels; i++, j++)
1056                channels[j] = band->channels[i].hw_value;
1057        band = &mvm->nvm_data->bands[NL80211_BAND_5GHZ];
1058        for (i = 0; i < band->n_channels && j < max_channels; i++, j++)
1059                channels[j] = band->channels[i].hw_value;
1060}
1061
1062static void iwl_mvm_fill_scan_config_v1(struct iwl_mvm *mvm, void *config,
1063                                        u32 flags, u8 channel_flags,
1064                                        u32 max_channels)
1065{
1066        enum iwl_mvm_scan_type type = iwl_mvm_get_scan_type(mvm, NULL);
1067        struct iwl_scan_config_v1 *cfg = config;
1068
1069        cfg->flags = cpu_to_le32(flags);
1070        cfg->tx_chains = cpu_to_le32(iwl_mvm_get_valid_tx_ant(mvm));
1071        cfg->rx_chains = cpu_to_le32(iwl_mvm_scan_rx_ant(mvm));
1072        cfg->legacy_rates = iwl_mvm_scan_config_rates(mvm);
1073        cfg->out_of_channel_time = cpu_to_le32(scan_timing[type].max_out_time);
1074        cfg->suspend_time = cpu_to_le32(scan_timing[type].suspend_time);
1075
1076        iwl_mvm_fill_scan_dwell(mvm, &cfg->dwell);
1077
1078        memcpy(&cfg->mac_addr, &mvm->addresses[0].addr, ETH_ALEN);
1079
1080        /* This function should not be called when using ADD_STA ver >=12 */
1081        WARN_ON_ONCE(iwl_fw_lookup_cmd_ver(mvm->fw, ADD_STA, 0) >= 12);
1082
1083        cfg->bcast_sta_id = mvm->aux_sta.sta_id;
1084        cfg->channel_flags = channel_flags;
1085
1086        iwl_mvm_fill_channels(mvm, cfg->channel_array, max_channels);
1087}
1088
1089static void iwl_mvm_fill_scan_config_v2(struct iwl_mvm *mvm, void *config,
1090                                        u32 flags, u8 channel_flags,
1091                                        u32 max_channels)
1092{
1093        struct iwl_scan_config_v2 *cfg = config;
1094
1095        cfg->flags = cpu_to_le32(flags);
1096        cfg->tx_chains = cpu_to_le32(iwl_mvm_get_valid_tx_ant(mvm));
1097        cfg->rx_chains = cpu_to_le32(iwl_mvm_scan_rx_ant(mvm));
1098        cfg->legacy_rates = iwl_mvm_scan_config_rates(mvm);
1099
1100        if (iwl_mvm_is_cdb_supported(mvm)) {
1101                enum iwl_mvm_scan_type lb_type, hb_type;
1102
1103                lb_type = iwl_mvm_get_scan_type_band(mvm, NULL,
1104                                                     NL80211_BAND_2GHZ);
1105                hb_type = iwl_mvm_get_scan_type_band(mvm, NULL,
1106                                                     NL80211_BAND_5GHZ);
1107
1108                cfg->out_of_channel_time[SCAN_LB_LMAC_IDX] =
1109                        cpu_to_le32(scan_timing[lb_type].max_out_time);
1110                cfg->suspend_time[SCAN_LB_LMAC_IDX] =
1111                        cpu_to_le32(scan_timing[lb_type].suspend_time);
1112
1113                cfg->out_of_channel_time[SCAN_HB_LMAC_IDX] =
1114                        cpu_to_le32(scan_timing[hb_type].max_out_time);
1115                cfg->suspend_time[SCAN_HB_LMAC_IDX] =
1116                        cpu_to_le32(scan_timing[hb_type].suspend_time);
1117        } else {
1118                enum iwl_mvm_scan_type type =
1119                        iwl_mvm_get_scan_type(mvm, NULL);
1120
1121                cfg->out_of_channel_time[SCAN_LB_LMAC_IDX] =
1122                        cpu_to_le32(scan_timing[type].max_out_time);
1123                cfg->suspend_time[SCAN_LB_LMAC_IDX] =
1124                        cpu_to_le32(scan_timing[type].suspend_time);
1125        }
1126
1127        iwl_mvm_fill_scan_dwell(mvm, &cfg->dwell);
1128
1129        memcpy(&cfg->mac_addr, &mvm->addresses[0].addr, ETH_ALEN);
1130
1131        /* This function should not be called when using ADD_STA ver >=12 */
1132        WARN_ON_ONCE(iwl_fw_lookup_cmd_ver(mvm->fw, ADD_STA, 0) >= 12);
1133
1134        cfg->bcast_sta_id = mvm->aux_sta.sta_id;
1135        cfg->channel_flags = channel_flags;
1136
1137        iwl_mvm_fill_channels(mvm, cfg->channel_array, max_channels);
1138}
1139
1140static int iwl_mvm_legacy_config_scan(struct iwl_mvm *mvm)
1141{
1142        void *cfg;
1143        int ret, cmd_size;
1144        struct iwl_host_cmd cmd = {
1145                .id = WIDE_ID(IWL_ALWAYS_LONG_GROUP, SCAN_CFG_CMD),
1146        };
1147        enum iwl_mvm_scan_type type;
1148        enum iwl_mvm_scan_type hb_type = IWL_SCAN_TYPE_NOT_SET;
1149        int num_channels =
1150                mvm->nvm_data->bands[NL80211_BAND_2GHZ].n_channels +
1151                mvm->nvm_data->bands[NL80211_BAND_5GHZ].n_channels;
1152        u32 flags;
1153        u8 channel_flags;
1154
1155        if (WARN_ON(num_channels > mvm->fw->ucode_capa.n_scan_channels))
1156                num_channels = mvm->fw->ucode_capa.n_scan_channels;
1157
1158        if (iwl_mvm_is_cdb_supported(mvm)) {
1159                type = iwl_mvm_get_scan_type_band(mvm, NULL,
1160                                                  NL80211_BAND_2GHZ);
1161                hb_type = iwl_mvm_get_scan_type_band(mvm, NULL,
1162                                                     NL80211_BAND_5GHZ);
1163                if (type == mvm->scan_type && hb_type == mvm->hb_scan_type)
1164                        return 0;
1165        } else {
1166                type = iwl_mvm_get_scan_type(mvm, NULL);
1167                if (type == mvm->scan_type)
1168                        return 0;
1169        }
1170
1171        if (iwl_mvm_cdb_scan_api(mvm))
1172                cmd_size = sizeof(struct iwl_scan_config_v2);
1173        else
1174                cmd_size = sizeof(struct iwl_scan_config_v1);
1175        cmd_size += mvm->fw->ucode_capa.n_scan_channels;
1176
1177        cfg = kzalloc(cmd_size, GFP_KERNEL);
1178        if (!cfg)
1179                return -ENOMEM;
1180
1181        flags = SCAN_CONFIG_FLAG_ACTIVATE |
1182                 SCAN_CONFIG_FLAG_ALLOW_CHUB_REQS |
1183                 SCAN_CONFIG_FLAG_SET_TX_CHAINS |
1184                 SCAN_CONFIG_FLAG_SET_RX_CHAINS |
1185                 SCAN_CONFIG_FLAG_SET_AUX_STA_ID |
1186                 SCAN_CONFIG_FLAG_SET_ALL_TIMES |
1187                 SCAN_CONFIG_FLAG_SET_LEGACY_RATES |
1188                 SCAN_CONFIG_FLAG_SET_MAC_ADDR |
1189                 SCAN_CONFIG_FLAG_SET_CHANNEL_FLAGS |
1190                 SCAN_CONFIG_N_CHANNELS(num_channels) |
1191                 (iwl_mvm_is_scan_fragmented(type) ?
1192                  SCAN_CONFIG_FLAG_SET_FRAGMENTED :
1193                  SCAN_CONFIG_FLAG_CLEAR_FRAGMENTED);
1194
1195        channel_flags = IWL_CHANNEL_FLAG_EBS |
1196                        IWL_CHANNEL_FLAG_ACCURATE_EBS |
1197                        IWL_CHANNEL_FLAG_EBS_ADD |
1198                        IWL_CHANNEL_FLAG_PRE_SCAN_PASSIVE2ACTIVE;
1199
1200        /*
1201         * Check for fragmented scan on LMAC2 - high band.
1202         * LMAC1 - low band is checked above.
1203         */
1204        if (iwl_mvm_cdb_scan_api(mvm)) {
1205                if (iwl_mvm_is_cdb_supported(mvm))
1206                        flags |= (iwl_mvm_is_scan_fragmented(hb_type)) ?
1207                                 SCAN_CONFIG_FLAG_SET_LMAC2_FRAGMENTED :
1208                                 SCAN_CONFIG_FLAG_CLEAR_LMAC2_FRAGMENTED;
1209                iwl_mvm_fill_scan_config_v2(mvm, cfg, flags, channel_flags,
1210                                            num_channels);
1211        } else {
1212                iwl_mvm_fill_scan_config_v1(mvm, cfg, flags, channel_flags,
1213                                            num_channels);
1214        }
1215
1216        cmd.data[0] = cfg;
1217        cmd.len[0] = cmd_size;
1218        cmd.dataflags[0] = IWL_HCMD_DFL_NOCOPY;
1219
1220        IWL_DEBUG_SCAN(mvm, "Sending UMAC scan config\n");
1221
1222        ret = iwl_mvm_send_cmd(mvm, &cmd);
1223        if (!ret) {
1224                mvm->scan_type = type;
1225                mvm->hb_scan_type = hb_type;
1226        }
1227
1228        kfree(cfg);
1229        return ret;
1230}
1231
1232int iwl_mvm_config_scan(struct iwl_mvm *mvm)
1233{
1234        struct iwl_scan_config cfg;
1235        struct iwl_host_cmd cmd = {
1236                .id = WIDE_ID(IWL_ALWAYS_LONG_GROUP, SCAN_CFG_CMD),
1237                .len[0] = sizeof(cfg),
1238                .data[0] = &cfg,
1239                .dataflags[0] = IWL_HCMD_DFL_NOCOPY,
1240        };
1241
1242        if (!iwl_mvm_is_reduced_config_scan_supported(mvm))
1243                return iwl_mvm_legacy_config_scan(mvm);
1244
1245        memset(&cfg, 0, sizeof(cfg));
1246
1247        if (iwl_fw_lookup_cmd_ver(mvm->fw, ADD_STA, 0) < 12) {
1248                cfg.bcast_sta_id = mvm->aux_sta.sta_id;
1249        } else if (iwl_fw_lookup_cmd_ver(mvm->fw, SCAN_CFG_CMD, 0) < 5) {
1250                /*
1251                 * Fw doesn't use this sta anymore. Deprecated on SCAN_CFG_CMD
1252                 * version 5.
1253                 */
1254                cfg.bcast_sta_id = 0xff;
1255        }
1256
1257        cfg.tx_chains = cpu_to_le32(iwl_mvm_get_valid_tx_ant(mvm));
1258        cfg.rx_chains = cpu_to_le32(iwl_mvm_scan_rx_ant(mvm));
1259
1260        IWL_DEBUG_SCAN(mvm, "Sending UMAC scan config\n");
1261
1262        return iwl_mvm_send_cmd(mvm, &cmd);
1263}
1264
1265static int iwl_mvm_scan_uid_by_status(struct iwl_mvm *mvm, int status)
1266{
1267        int i;
1268
1269        for (i = 0; i < mvm->max_scans; i++)
1270                if (mvm->scan_uid_status[i] == status)
1271                        return i;
1272
1273        return -ENOENT;
1274}
1275
1276static void iwl_mvm_scan_umac_dwell(struct iwl_mvm *mvm,
1277                                    struct iwl_scan_req_umac *cmd,
1278                                    struct iwl_mvm_scan_params *params)
1279{
1280        struct iwl_mvm_scan_timing_params *timing, *hb_timing;
1281        u8 active_dwell, passive_dwell;
1282
1283        timing = &scan_timing[params->type];
1284        active_dwell = IWL_SCAN_DWELL_ACTIVE;
1285        passive_dwell = IWL_SCAN_DWELL_PASSIVE;
1286
1287        if (iwl_mvm_is_adaptive_dwell_supported(mvm)) {
1288                cmd->v7.adwell_default_n_aps_social =
1289                        IWL_SCAN_ADWELL_DEFAULT_N_APS_SOCIAL;
1290                cmd->v7.adwell_default_n_aps =
1291                        IWL_SCAN_ADWELL_DEFAULT_LB_N_APS;
1292
1293                if (iwl_mvm_is_adwell_hb_ap_num_supported(mvm))
1294                        cmd->v9.adwell_default_hb_n_aps =
1295                                IWL_SCAN_ADWELL_DEFAULT_HB_N_APS;
1296
1297                /* if custom max budget was configured with debugfs */
1298                if (IWL_MVM_ADWELL_MAX_BUDGET)
1299                        cmd->v7.adwell_max_budget =
1300                                cpu_to_le16(IWL_MVM_ADWELL_MAX_BUDGET);
1301                else if (params->ssids && params->ssids[0].ssid_len)
1302                        cmd->v7.adwell_max_budget =
1303                                cpu_to_le16(IWL_SCAN_ADWELL_MAX_BUDGET_DIRECTED_SCAN);
1304                else
1305                        cmd->v7.adwell_max_budget =
1306                                cpu_to_le16(IWL_SCAN_ADWELL_MAX_BUDGET_FULL_SCAN);
1307
1308                cmd->v7.scan_priority = cpu_to_le32(IWL_SCAN_PRIORITY_EXT_6);
1309                cmd->v7.max_out_time[SCAN_LB_LMAC_IDX] =
1310                        cpu_to_le32(timing->max_out_time);
1311                cmd->v7.suspend_time[SCAN_LB_LMAC_IDX] =
1312                        cpu_to_le32(timing->suspend_time);
1313
1314                if (iwl_mvm_is_cdb_supported(mvm)) {
1315                        hb_timing = &scan_timing[params->hb_type];
1316
1317                        cmd->v7.max_out_time[SCAN_HB_LMAC_IDX] =
1318                                cpu_to_le32(hb_timing->max_out_time);
1319                        cmd->v7.suspend_time[SCAN_HB_LMAC_IDX] =
1320                                cpu_to_le32(hb_timing->suspend_time);
1321                }
1322
1323                if (!iwl_mvm_is_adaptive_dwell_v2_supported(mvm)) {
1324                        cmd->v7.active_dwell = active_dwell;
1325                        cmd->v7.passive_dwell = passive_dwell;
1326                        cmd->v7.fragmented_dwell = IWL_SCAN_DWELL_FRAGMENTED;
1327                } else {
1328                        cmd->v8.active_dwell[SCAN_LB_LMAC_IDX] = active_dwell;
1329                        cmd->v8.passive_dwell[SCAN_LB_LMAC_IDX] = passive_dwell;
1330                        if (iwl_mvm_is_cdb_supported(mvm)) {
1331                                cmd->v8.active_dwell[SCAN_HB_LMAC_IDX] =
1332                                        active_dwell;
1333                                cmd->v8.passive_dwell[SCAN_HB_LMAC_IDX] =
1334                                        passive_dwell;
1335                        }
1336                }
1337        } else {
1338                cmd->v1.extended_dwell = IWL_SCAN_DWELL_EXTENDED;
1339                cmd->v1.active_dwell = active_dwell;
1340                cmd->v1.passive_dwell = passive_dwell;
1341                cmd->v1.fragmented_dwell = IWL_SCAN_DWELL_FRAGMENTED;
1342
1343                if (iwl_mvm_is_cdb_supported(mvm)) {
1344                        hb_timing = &scan_timing[params->hb_type];
1345
1346                        cmd->v6.max_out_time[SCAN_HB_LMAC_IDX] =
1347                                        cpu_to_le32(hb_timing->max_out_time);
1348                        cmd->v6.suspend_time[SCAN_HB_LMAC_IDX] =
1349                                        cpu_to_le32(hb_timing->suspend_time);
1350                }
1351
1352                if (iwl_mvm_cdb_scan_api(mvm)) {
1353                        cmd->v6.scan_priority =
1354                                cpu_to_le32(IWL_SCAN_PRIORITY_EXT_6);
1355                        cmd->v6.max_out_time[SCAN_LB_LMAC_IDX] =
1356                                cpu_to_le32(timing->max_out_time);
1357                        cmd->v6.suspend_time[SCAN_LB_LMAC_IDX] =
1358                                cpu_to_le32(timing->suspend_time);
1359                } else {
1360                        cmd->v1.scan_priority =
1361                                cpu_to_le32(IWL_SCAN_PRIORITY_EXT_6);
1362                        cmd->v1.max_out_time =
1363                                cpu_to_le32(timing->max_out_time);
1364                        cmd->v1.suspend_time =
1365                                cpu_to_le32(timing->suspend_time);
1366                }
1367        }
1368
1369        if (iwl_mvm_is_regular_scan(params))
1370                cmd->ooc_priority = cpu_to_le32(IWL_SCAN_PRIORITY_EXT_6);
1371        else
1372                cmd->ooc_priority = cpu_to_le32(IWL_SCAN_PRIORITY_EXT_2);
1373}
1374
1375static u32 iwl_mvm_scan_umac_ooc_priority(struct iwl_mvm_scan_params *params)
1376{
1377        return iwl_mvm_is_regular_scan(params) ?
1378                IWL_SCAN_PRIORITY_EXT_6 :
1379                IWL_SCAN_PRIORITY_EXT_2;
1380}
1381
1382static void
1383iwl_mvm_scan_umac_dwell_v11(struct iwl_mvm *mvm,
1384                            struct iwl_scan_general_params_v11 *general_params,
1385                            struct iwl_mvm_scan_params *params)
1386{
1387        struct iwl_mvm_scan_timing_params *timing, *hb_timing;
1388        u8 active_dwell, passive_dwell;
1389
1390        timing = &scan_timing[params->type];
1391        active_dwell = IWL_SCAN_DWELL_ACTIVE;
1392        passive_dwell = IWL_SCAN_DWELL_PASSIVE;
1393
1394        general_params->adwell_default_social_chn =
1395                IWL_SCAN_ADWELL_DEFAULT_N_APS_SOCIAL;
1396        general_params->adwell_default_2g = IWL_SCAN_ADWELL_DEFAULT_LB_N_APS;
1397        general_params->adwell_default_5g = IWL_SCAN_ADWELL_DEFAULT_HB_N_APS;
1398
1399        /* if custom max budget was configured with debugfs */
1400        if (IWL_MVM_ADWELL_MAX_BUDGET)
1401                general_params->adwell_max_budget =
1402                        cpu_to_le16(IWL_MVM_ADWELL_MAX_BUDGET);
1403        else if (params->ssids && params->ssids[0].ssid_len)
1404                general_params->adwell_max_budget =
1405                        cpu_to_le16(IWL_SCAN_ADWELL_MAX_BUDGET_DIRECTED_SCAN);
1406        else
1407                general_params->adwell_max_budget =
1408                        cpu_to_le16(IWL_SCAN_ADWELL_MAX_BUDGET_FULL_SCAN);
1409
1410        general_params->scan_priority = cpu_to_le32(IWL_SCAN_PRIORITY_EXT_6);
1411        general_params->max_out_of_time[SCAN_LB_LMAC_IDX] =
1412                cpu_to_le32(timing->max_out_time);
1413        general_params->suspend_time[SCAN_LB_LMAC_IDX] =
1414                cpu_to_le32(timing->suspend_time);
1415
1416        hb_timing = &scan_timing[params->hb_type];
1417
1418        general_params->max_out_of_time[SCAN_HB_LMAC_IDX] =
1419                cpu_to_le32(hb_timing->max_out_time);
1420        general_params->suspend_time[SCAN_HB_LMAC_IDX] =
1421                cpu_to_le32(hb_timing->suspend_time);
1422
1423        general_params->active_dwell[SCAN_LB_LMAC_IDX] = active_dwell;
1424        general_params->passive_dwell[SCAN_LB_LMAC_IDX] = passive_dwell;
1425        general_params->active_dwell[SCAN_HB_LMAC_IDX] = active_dwell;
1426        general_params->passive_dwell[SCAN_HB_LMAC_IDX] = passive_dwell;
1427}
1428
1429struct iwl_mvm_scan_channel_segment {
1430        u8 start_idx;
1431        u8 end_idx;
1432        u8 first_channel_id;
1433        u8 last_channel_id;
1434        u8 channel_spacing_shift;
1435        u8 band;
1436};
1437
1438static const struct iwl_mvm_scan_channel_segment scan_channel_segments[] = {
1439        {
1440                .start_idx = 0,
1441                .end_idx = 13,
1442                .first_channel_id = 1,
1443                .last_channel_id = 14,
1444                .channel_spacing_shift = 0,
1445                .band = PHY_BAND_24
1446        },
1447        {
1448                .start_idx = 14,
1449                .end_idx = 41,
1450                .first_channel_id = 36,
1451                .last_channel_id = 144,
1452                .channel_spacing_shift = 2,
1453                .band = PHY_BAND_5
1454        },
1455        {
1456                .start_idx = 42,
1457                .end_idx = 50,
1458                .first_channel_id = 149,
1459                .last_channel_id = 181,
1460                .channel_spacing_shift = 2,
1461                .band = PHY_BAND_5
1462        },
1463        {
1464                .start_idx = 51,
1465                .end_idx = 111,
1466                .first_channel_id = 1,
1467                .last_channel_id = 241,
1468                .channel_spacing_shift = 2,
1469                .band = PHY_BAND_6
1470        },
1471};
1472
1473static int iwl_mvm_scan_ch_and_band_to_idx(u8 channel_id, u8 band)
1474{
1475        int i, index;
1476
1477        if (!channel_id)
1478                return -EINVAL;
1479
1480        for (i = 0; i < ARRAY_SIZE(scan_channel_segments); i++) {
1481                const struct iwl_mvm_scan_channel_segment *ch_segment =
1482                        &scan_channel_segments[i];
1483                u32 ch_offset;
1484
1485                if (ch_segment->band != band ||
1486                    ch_segment->first_channel_id > channel_id ||
1487                    ch_segment->last_channel_id < channel_id)
1488                        continue;
1489
1490                ch_offset = (channel_id - ch_segment->first_channel_id) >>
1491                        ch_segment->channel_spacing_shift;
1492
1493                index = scan_channel_segments[i].start_idx + ch_offset;
1494                if (index < IWL_SCAN_NUM_CHANNELS)
1495                        return index;
1496
1497                break;
1498        }
1499
1500        return -EINVAL;
1501}
1502
1503static const u8 p2p_go_friendly_chs[] = {
1504        36, 40, 44, 48, 149, 153, 157, 161, 165,
1505};
1506
1507static const u8 social_chs[] = {
1508        1, 6, 11
1509};
1510
1511static void iwl_mvm_scan_ch_add_n_aps_override(enum nl80211_iftype vif_type,
1512                                               u8 ch_id, u8 band, u8 *ch_bitmap,
1513                                               size_t bitmap_n_entries)
1514{
1515        int i;
1516
1517        if (vif_type != NL80211_IFTYPE_P2P_DEVICE)
1518                return;
1519
1520        for (i = 0; i < ARRAY_SIZE(p2p_go_friendly_chs); i++) {
1521                if (p2p_go_friendly_chs[i] == ch_id) {
1522                        int ch_idx, bitmap_idx;
1523
1524                        ch_idx = iwl_mvm_scan_ch_and_band_to_idx(ch_id, band);
1525                        if (ch_idx < 0)
1526                                return;
1527
1528                        bitmap_idx = ch_idx / 8;
1529                        if (bitmap_idx >= bitmap_n_entries)
1530                                return;
1531
1532                        ch_idx = ch_idx % 8;
1533                        ch_bitmap[bitmap_idx] |= BIT(ch_idx);
1534
1535                        return;
1536                }
1537        }
1538}
1539
1540static u32 iwl_mvm_scan_ch_n_aps_flag(enum nl80211_iftype vif_type, u8 ch_id)
1541{
1542        int i;
1543        u32 flags = 0;
1544
1545        if (vif_type != NL80211_IFTYPE_P2P_DEVICE)
1546                goto out;
1547
1548        for (i = 0; i < ARRAY_SIZE(p2p_go_friendly_chs); i++) {
1549                if (p2p_go_friendly_chs[i] == ch_id) {
1550                        flags |= IWL_SCAN_ADWELL_N_APS_GO_FRIENDLY_BIT;
1551                        break;
1552                }
1553        }
1554
1555        if (flags)
1556                goto out;
1557
1558        for (i = 0; i < ARRAY_SIZE(social_chs); i++) {
1559                if (social_chs[i] == ch_id) {
1560                        flags |= IWL_SCAN_ADWELL_N_APS_SOCIAL_CHS_BIT;
1561                        break;
1562                }
1563        }
1564
1565out:
1566        return flags;
1567}
1568
1569static void
1570iwl_mvm_umac_scan_cfg_channels(struct iwl_mvm *mvm,
1571                               struct ieee80211_channel **channels,
1572                               int n_channels, u32 flags,
1573                               struct iwl_scan_channel_cfg_umac *channel_cfg)
1574{
1575        int i;
1576
1577        for (i = 0; i < n_channels; i++) {
1578                channel_cfg[i].flags = cpu_to_le32(flags);
1579                channel_cfg[i].v1.channel_num = channels[i]->hw_value;
1580                if (iwl_mvm_is_scan_ext_chan_supported(mvm)) {
1581                        enum nl80211_band band = channels[i]->band;
1582
1583                        channel_cfg[i].v2.band =
1584                                iwl_mvm_phy_band_from_nl80211(band);
1585                        channel_cfg[i].v2.iter_count = 1;
1586                        channel_cfg[i].v2.iter_interval = 0;
1587                } else {
1588                        channel_cfg[i].v1.iter_count = 1;
1589                        channel_cfg[i].v1.iter_interval = 0;
1590                }
1591        }
1592}
1593
1594static void
1595iwl_mvm_umac_scan_cfg_channels_v4(struct iwl_mvm *mvm,
1596                                  struct ieee80211_channel **channels,
1597                                  struct iwl_scan_channel_params_v4 *cp,
1598                                  int n_channels, u32 flags,
1599                                  enum nl80211_iftype vif_type)
1600{
1601        u8 *bitmap = cp->adwell_ch_override_bitmap;
1602        size_t bitmap_n_entries = ARRAY_SIZE(cp->adwell_ch_override_bitmap);
1603        int i;
1604
1605        for (i = 0; i < n_channels; i++) {
1606                enum nl80211_band band = channels[i]->band;
1607                struct iwl_scan_channel_cfg_umac *cfg =
1608                        &cp->channel_config[i];
1609
1610                cfg->flags = cpu_to_le32(flags);
1611                cfg->v2.channel_num = channels[i]->hw_value;
1612                cfg->v2.band = iwl_mvm_phy_band_from_nl80211(band);
1613                cfg->v2.iter_count = 1;
1614                cfg->v2.iter_interval = 0;
1615
1616                iwl_mvm_scan_ch_add_n_aps_override(vif_type,
1617                                                   cfg->v2.channel_num,
1618                                                   cfg->v2.band, bitmap,
1619                                                   bitmap_n_entries);
1620        }
1621}
1622
1623static void
1624iwl_mvm_umac_scan_cfg_channels_v6(struct iwl_mvm *mvm,
1625                                  struct ieee80211_channel **channels,
1626                                  struct iwl_scan_channel_params_v6 *cp,
1627                                  int n_channels, u32 flags,
1628                                  enum nl80211_iftype vif_type)
1629{
1630        int i;
1631
1632        for (i = 0; i < n_channels; i++) {
1633                enum nl80211_band band = channels[i]->band;
1634                struct iwl_scan_channel_cfg_umac *cfg = &cp->channel_config[i];
1635                u32 n_aps_flag =
1636                        iwl_mvm_scan_ch_n_aps_flag(vif_type,
1637                                                   channels[i]->hw_value);
1638
1639                cfg->flags = cpu_to_le32(flags | n_aps_flag);
1640                cfg->v2.channel_num = channels[i]->hw_value;
1641                cfg->v2.band = iwl_mvm_phy_band_from_nl80211(band);
1642                if (cfg80211_channel_is_psc(channels[i]))
1643                        cfg->flags = 0;
1644                cfg->v2.iter_count = 1;
1645                cfg->v2.iter_interval = 0;
1646        }
1647}
1648
1649static void
1650iwl_mvm_umac_scan_fill_6g_chan_list(struct iwl_mvm *mvm,
1651                                    struct iwl_mvm_scan_params *params,
1652                                     struct iwl_scan_probe_params_v4 *pp)
1653{
1654        int j, idex_s = 0, idex_b = 0;
1655        struct cfg80211_scan_6ghz_params *scan_6ghz_params =
1656                params->scan_6ghz_params;
1657        bool hidden_supported = fw_has_capa(&mvm->fw->ucode_capa,
1658                                            IWL_UCODE_TLV_CAPA_HIDDEN_6GHZ_SCAN);
1659
1660        for (j = 0; j < params->n_ssids && idex_s < SCAN_SHORT_SSID_MAX_SIZE;
1661             j++) {
1662                if (!params->ssids[j].ssid_len)
1663                        continue;
1664
1665                pp->short_ssid[idex_s] =
1666                        cpu_to_le32(~crc32_le(~0, params->ssids[j].ssid,
1667                                              params->ssids[j].ssid_len));
1668
1669                if (hidden_supported) {
1670                        pp->direct_scan[idex_s].id = WLAN_EID_SSID;
1671                        pp->direct_scan[idex_s].len = params->ssids[j].ssid_len;
1672                        memcpy(pp->direct_scan[idex_s].ssid, params->ssids[j].ssid,
1673                               params->ssids[j].ssid_len);
1674                }
1675                idex_s++;
1676        }
1677
1678        /*
1679         * Populate the arrays of the short SSIDs and the BSSIDs using the 6GHz
1680         * collocated parameters. This might not be optimal, as this processing
1681         * does not (yet) correspond to the actual channels, so it is possible
1682         * that some entries would be left out.
1683         *
1684         * TODO: improve this logic.
1685         */
1686        for (j = 0; j < params->n_6ghz_params; j++) {
1687                int k;
1688
1689                /* First, try to place the short SSID */
1690                if (scan_6ghz_params[j].short_ssid_valid) {
1691                        for (k = 0; k < idex_s; k++) {
1692                                if (pp->short_ssid[k] ==
1693                                    cpu_to_le32(scan_6ghz_params[j].short_ssid))
1694                                        break;
1695                        }
1696
1697                        if (k == idex_s && idex_s < SCAN_SHORT_SSID_MAX_SIZE) {
1698                                pp->short_ssid[idex_s++] =
1699                                        cpu_to_le32(scan_6ghz_params[j].short_ssid);
1700                        }
1701                }
1702
1703                /* try to place BSSID for the same entry */
1704                for (k = 0; k < idex_b; k++) {
1705                        if (!memcmp(&pp->bssid_array[k],
1706                                    scan_6ghz_params[j].bssid, ETH_ALEN))
1707                                break;
1708                }
1709
1710                if (k == idex_b && idex_b < SCAN_BSSID_MAX_SIZE) {
1711                        memcpy(&pp->bssid_array[idex_b++],
1712                               scan_6ghz_params[j].bssid, ETH_ALEN);
1713                }
1714        }
1715
1716        pp->short_ssid_num = idex_s;
1717        pp->bssid_num = idex_b;
1718}
1719
1720/* TODO: this function can be merged with iwl_mvm_scan_umac_fill_ch_p_v6 */
1721static u32
1722iwl_mvm_umac_scan_cfg_channels_v6_6g(struct iwl_mvm *mvm,
1723                                     struct iwl_mvm_scan_params *params,
1724                                     u32 n_channels,
1725                                     struct iwl_scan_probe_params_v4 *pp,
1726                                     struct iwl_scan_channel_params_v6 *cp,
1727                                     enum nl80211_iftype vif_type)
1728{
1729        int i;
1730        struct cfg80211_scan_6ghz_params *scan_6ghz_params =
1731                params->scan_6ghz_params;
1732        u32 ch_cnt;
1733
1734        for (i = 0, ch_cnt = 0; i < params->n_channels; i++) {
1735                struct iwl_scan_channel_cfg_umac *cfg =
1736                        &cp->channel_config[ch_cnt];
1737
1738                u32 s_ssid_bitmap = 0, bssid_bitmap = 0, flags = 0;
1739                u8 j, k, s_max = 0, b_max = 0, n_used_bssid_entries;
1740                bool force_passive, found = false, allow_passive = true,
1741                     unsolicited_probe_on_chan = false, psc_no_listen = false;
1742
1743                /*
1744                 * Avoid performing passive scan on non PSC channels unless the
1745                 * scan is specifically a passive scan, i.e., no SSIDs
1746                 * configured in the scan command.
1747                 */
1748                if (!cfg80211_channel_is_psc(params->channels[i]) &&
1749                    !params->n_6ghz_params && params->n_ssids)
1750                        continue;
1751
1752                cfg->v1.channel_num = params->channels[i]->hw_value;
1753                cfg->v2.band = 2;
1754                cfg->v2.iter_count = 1;
1755                cfg->v2.iter_interval = 0;
1756
1757                /*
1758                 * The optimize the scan time, i.e., reduce the scan dwell time
1759                 * on each channel, the below logic tries to set 3 direct BSSID
1760                 * probe requests for each broadcast probe request with a short
1761                 * SSID.
1762                 * TODO: improve this logic
1763                 */
1764                n_used_bssid_entries = 3;
1765                for (j = 0; j < params->n_6ghz_params; j++) {
1766                        if (!(scan_6ghz_params[j].channel_idx == i))
1767                                continue;
1768
1769                        found = false;
1770                        unsolicited_probe_on_chan |=
1771                                scan_6ghz_params[j].unsolicited_probe;
1772                        psc_no_listen |= scan_6ghz_params[j].psc_no_listen;
1773
1774                        for (k = 0; k < pp->short_ssid_num; k++) {
1775                                if (!scan_6ghz_params[j].unsolicited_probe &&
1776                                    le32_to_cpu(pp->short_ssid[k]) ==
1777                                    scan_6ghz_params[j].short_ssid) {
1778                                        /* Relevant short SSID bit set */
1779                                        if (s_ssid_bitmap & BIT(k)) {
1780                                                found = true;
1781                                                break;
1782                                        }
1783
1784                                        /*
1785                                         * Use short SSID only to create a new
1786                                         * iteration during channel dwell or in
1787                                         * case that the short SSID has a
1788                                         * matching SSID, i.e., scan for hidden
1789                                         * APs.
1790                                         */
1791                                        if (n_used_bssid_entries >= 3) {
1792                                                s_ssid_bitmap |= BIT(k);
1793                                                s_max++;
1794                                                n_used_bssid_entries -= 3;
1795                                                found = true;
1796                                                break;
1797                                        } else if (pp->direct_scan[k].len) {
1798                                                s_ssid_bitmap |= BIT(k);
1799                                                s_max++;
1800                                                found = true;
1801                                                allow_passive = false;
1802                                                break;
1803                                        }
1804                                }
1805                        }
1806
1807                        if (found)
1808                                continue;
1809
1810                        for (k = 0; k < pp->bssid_num; k++) {
1811                                if (!memcmp(&pp->bssid_array[k],
1812                                            scan_6ghz_params[j].bssid,
1813                                            ETH_ALEN)) {
1814                                        if (!(bssid_bitmap & BIT(k))) {
1815                                                bssid_bitmap |= BIT(k);
1816                                                b_max++;
1817                                                n_used_bssid_entries++;
1818                                        }
1819                                        break;
1820                                }
1821                        }
1822                }
1823
1824                if (cfg80211_channel_is_psc(params->channels[i]) &&
1825                    psc_no_listen)
1826                        flags |= IWL_UHB_CHAN_CFG_FLAG_PSC_CHAN_NO_LISTEN;
1827
1828                if (unsolicited_probe_on_chan)
1829                        flags |= IWL_UHB_CHAN_CFG_FLAG_UNSOLICITED_PROBE_RES;
1830
1831                /*
1832                 * In the following cases apply passive scan:
1833                 * 1. Non fragmented scan:
1834                 *      - PSC channel with NO_LISTEN_FLAG on should be treated
1835                 *        like non PSC channel
1836                 *      - Non PSC channel with more than 3 short SSIDs or more
1837                 *        than 9 BSSIDs.
1838                 *      - Non PSC Channel with unsolicited probe response and
1839                 *        more than 2 short SSIDs or more than 6 BSSIDs.
1840                 *      - PSC channel with more than 2 short SSIDs or more than
1841                 *        6 BSSIDs.
1842                 * 3. Fragmented scan:
1843                 *      - PSC channel with more than 1 SSID or 3 BSSIDs.
1844                 *      - Non PSC channel with more than 2 SSIDs or 6 BSSIDs.
1845                 *      - Non PSC channel with unsolicited probe response and
1846                 *        more than 1 SSID or more than 3 BSSIDs.
1847                 */
1848                if (!iwl_mvm_is_scan_fragmented(params->type)) {
1849                        if (!cfg80211_channel_is_psc(params->channels[i]) ||
1850                            flags & IWL_UHB_CHAN_CFG_FLAG_PSC_CHAN_NO_LISTEN) {
1851                                force_passive = (s_max > 3 || b_max > 9);
1852                                force_passive |= (unsolicited_probe_on_chan &&
1853                                                  (s_max > 2 || b_max > 6));
1854                        } else {
1855                                force_passive = (s_max > 2 || b_max > 6);
1856                        }
1857                } else if (cfg80211_channel_is_psc(params->channels[i])) {
1858                        force_passive = (s_max > 1 || b_max > 3);
1859                } else {
1860                        force_passive = (s_max > 2 || b_max > 6);
1861                        force_passive |= (unsolicited_probe_on_chan &&
1862                                          (s_max > 1 || b_max > 3));
1863                }
1864                if ((allow_passive && force_passive) ||
1865                    (!(bssid_bitmap | s_ssid_bitmap) &&
1866                     !cfg80211_channel_is_psc(params->channels[i])))
1867                        flags |= IWL_UHB_CHAN_CFG_FLAG_FORCE_PASSIVE;
1868                else
1869                        flags |= bssid_bitmap | (s_ssid_bitmap << 16);
1870
1871                cfg->flags |= cpu_to_le32(flags);
1872                ch_cnt++;
1873        }
1874
1875        if (params->n_channels > ch_cnt)
1876                IWL_DEBUG_SCAN(mvm,
1877                               "6GHz: reducing number channels: (%u->%u)\n",
1878                               params->n_channels, ch_cnt);
1879
1880        return ch_cnt;
1881}
1882
1883static u8 iwl_mvm_scan_umac_chan_flags_v2(struct iwl_mvm *mvm,
1884                                          struct iwl_mvm_scan_params *params,
1885                                          struct ieee80211_vif *vif)
1886{
1887        u8 flags = 0;
1888
1889        flags |= IWL_SCAN_CHANNEL_FLAG_ENABLE_CHAN_ORDER;
1890
1891        if (iwl_mvm_scan_use_ebs(mvm, vif))
1892                flags |= IWL_SCAN_CHANNEL_FLAG_EBS |
1893                        IWL_SCAN_CHANNEL_FLAG_EBS_ACCURATE |
1894                        IWL_SCAN_CHANNEL_FLAG_CACHE_ADD;
1895
1896        /* set fragmented ebs for fragmented scan on HB channels */
1897        if ((!iwl_mvm_is_cdb_supported(mvm) &&
1898             iwl_mvm_is_scan_fragmented(params->type)) ||
1899            (iwl_mvm_is_cdb_supported(mvm) &&
1900             iwl_mvm_is_scan_fragmented(params->hb_type)))
1901                flags |= IWL_SCAN_CHANNEL_FLAG_EBS_FRAG;
1902
1903        /*
1904         * force EBS in case the scan is a fragmented and there is a need to take P2P
1905         * GO operation into consideration during scan operation.
1906         */
1907        if ((!iwl_mvm_is_cdb_supported(mvm) &&
1908             iwl_mvm_is_scan_fragmented(params->type) && params->respect_p2p_go) ||
1909            (iwl_mvm_is_cdb_supported(mvm) &&
1910             iwl_mvm_is_scan_fragmented(params->hb_type) &&
1911             params->respect_p2p_go_hb)) {
1912                IWL_DEBUG_SCAN(mvm, "Respect P2P GO. Force EBS\n");
1913                flags |= IWL_SCAN_CHANNEL_FLAG_FORCE_EBS;
1914        }
1915
1916        return flags;
1917}
1918
1919static void iwl_mvm_scan_6ghz_passive_scan(struct iwl_mvm *mvm,
1920                                           struct iwl_mvm_scan_params *params,
1921                                           struct ieee80211_vif *vif)
1922{
1923        struct ieee80211_supported_band *sband =
1924                &mvm->nvm_data->bands[NL80211_BAND_6GHZ];
1925        u32 n_disabled, i;
1926
1927        params->enable_6ghz_passive = false;
1928
1929        if (params->scan_6ghz)
1930                return;
1931
1932        if (!fw_has_capa(&mvm->fw->ucode_capa,
1933                         IWL_UCODE_TLV_CAPA_PASSIVE_6GHZ_SCAN)) {
1934                IWL_DEBUG_SCAN(mvm,
1935                               "6GHz passive scan: Not supported by FW\n");
1936                return;
1937        }
1938
1939        /* 6GHz passive scan allowed only on station interface  */
1940        if (vif->type != NL80211_IFTYPE_STATION) {
1941                IWL_DEBUG_SCAN(mvm,
1942                               "6GHz passive scan: not station interface\n");
1943                return;
1944        }
1945
1946        /*
1947         * 6GHz passive scan is allowed in a defined time interval following HW
1948         * reset or resume flow, or while not associated and a large interval
1949         * has passed since the last 6GHz passive scan.
1950         */
1951        if ((vif->bss_conf.assoc ||
1952             time_after(mvm->last_6ghz_passive_scan_jiffies +
1953                        (IWL_MVM_6GHZ_PASSIVE_SCAN_TIMEOUT * HZ), jiffies)) &&
1954            (time_before(mvm->last_reset_or_resume_time_jiffies +
1955                         (IWL_MVM_6GHZ_PASSIVE_SCAN_ASSOC_TIMEOUT * HZ),
1956                         jiffies))) {
1957                IWL_DEBUG_SCAN(mvm, "6GHz passive scan: %s\n",
1958                               vif->bss_conf.assoc ? "associated" :
1959                               "timeout did not expire");
1960                return;
1961        }
1962
1963        /* not enough channels in the regular scan request */
1964        if (params->n_channels < IWL_MVM_6GHZ_PASSIVE_SCAN_MIN_CHANS) {
1965                IWL_DEBUG_SCAN(mvm,
1966                               "6GHz passive scan: not enough channels\n");
1967                return;
1968        }
1969
1970        for (i = 0; i < params->n_ssids; i++) {
1971                if (!params->ssids[i].ssid_len)
1972                        break;
1973        }
1974
1975        /* not a wildcard scan, so cannot enable passive 6GHz scan */
1976        if (i == params->n_ssids) {
1977                IWL_DEBUG_SCAN(mvm,
1978                               "6GHz passive scan: no wildcard SSID\n");
1979                return;
1980        }
1981
1982        if (!sband || !sband->n_channels) {
1983                IWL_DEBUG_SCAN(mvm,
1984                               "6GHz passive scan: no 6GHz channels\n");
1985                return;
1986        }
1987
1988        for (i = 0, n_disabled = 0; i < sband->n_channels; i++) {
1989                if (sband->channels[i].flags & (IEEE80211_CHAN_DISABLED))
1990                        n_disabled++;
1991        }
1992
1993        /*
1994         * Not all the 6GHz channels are disabled, so no need for 6GHz passive
1995         * scan
1996         */
1997        if (n_disabled != sband->n_channels) {
1998                IWL_DEBUG_SCAN(mvm,
1999                               "6GHz passive scan: 6GHz channels enabled\n");
2000                return;
2001        }
2002
2003        /* all conditions to enable 6ghz passive scan are satisfied */
2004        IWL_DEBUG_SCAN(mvm, "6GHz passive scan: can be enabled\n");
2005        params->enable_6ghz_passive = true;
2006}
2007
2008static u16 iwl_mvm_scan_umac_flags_v2(struct iwl_mvm *mvm,
2009                                      struct iwl_mvm_scan_params *params,
2010                                      struct ieee80211_vif *vif,
2011                                      int type)
2012{
2013        u16 flags = 0;
2014
2015        /*
2016         * If no direct SSIDs are provided perform a passive scan. Otherwise,
2017         * if there is a single SSID which is not the broadcast SSID, assume
2018         * that the scan is intended for roaming purposes and thus enable Rx on
2019         * all chains to improve chances of hearing the beacons/probe responses.
2020         */
2021        if (params->n_ssids == 0)
2022                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_FORCE_PASSIVE;
2023        else if (params->n_ssids == 1 && params->ssids[0].ssid_len)
2024                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_USE_ALL_RX_CHAINS;
2025
2026        if (iwl_mvm_is_scan_fragmented(params->type))
2027                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_FRAGMENTED_LMAC1;
2028
2029        if (iwl_mvm_is_scan_fragmented(params->hb_type))
2030                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_FRAGMENTED_LMAC2;
2031
2032        if (params->pass_all)
2033                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_PASS_ALL;
2034        else
2035                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_MATCH;
2036
2037        if (!iwl_mvm_is_regular_scan(params))
2038                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_PERIODIC;
2039
2040        if (params->iter_notif ||
2041            mvm->sched_scan_pass_all == SCHED_SCAN_PASS_ALL_ENABLED)
2042                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_NTFY_ITER_COMPLETE;
2043
2044        if (IWL_MVM_ADWELL_ENABLE)
2045                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_ADAPTIVE_DWELL;
2046
2047        if (type == IWL_MVM_SCAN_SCHED || type == IWL_MVM_SCAN_NETDETECT)
2048                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_PREEMPTIVE;
2049
2050        if ((type == IWL_MVM_SCAN_SCHED || type == IWL_MVM_SCAN_NETDETECT) &&
2051            params->flags & NL80211_SCAN_FLAG_COLOCATED_6GHZ)
2052                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_TRIGGER_UHB_SCAN;
2053
2054        if (params->enable_6ghz_passive)
2055                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_6GHZ_PASSIVE_SCAN;
2056
2057        if (iwl_mvm_is_oce_supported(mvm) &&
2058            (params->flags & (NL80211_SCAN_FLAG_ACCEPT_BCAST_PROBE_RESP |
2059                              NL80211_SCAN_FLAG_OCE_PROBE_REQ_HIGH_TX_RATE |
2060                              NL80211_SCAN_FLAG_FILS_MAX_CHANNEL_TIME)))
2061                flags |= IWL_UMAC_SCAN_GEN_FLAGS_V2_OCE;
2062
2063        return flags;
2064}
2065
2066static u8 iwl_mvm_scan_umac_flags2(struct iwl_mvm *mvm,
2067                                   struct iwl_mvm_scan_params *params,
2068                                   struct ieee80211_vif *vif, int type)
2069{
2070        u8 flags = 0;
2071
2072        if (iwl_mvm_is_cdb_supported(mvm)) {
2073                if (params->respect_p2p_go)
2074                        flags |= IWL_UMAC_SCAN_GEN_PARAMS_FLAGS2_RESPECT_P2P_GO_LB;
2075                if (params->respect_p2p_go_hb)
2076                        flags |= IWL_UMAC_SCAN_GEN_PARAMS_FLAGS2_RESPECT_P2P_GO_HB;
2077        } else {
2078                if (params->respect_p2p_go)
2079                        flags = IWL_UMAC_SCAN_GEN_PARAMS_FLAGS2_RESPECT_P2P_GO_LB |
2080                                IWL_UMAC_SCAN_GEN_PARAMS_FLAGS2_RESPECT_P2P_GO_HB;
2081        }
2082
2083        return flags;
2084}
2085
2086static u16 iwl_mvm_scan_umac_flags(struct iwl_mvm *mvm,
2087                                   struct iwl_mvm_scan_params *params,
2088                                   struct ieee80211_vif *vif)
2089{
2090        u16 flags = 0;
2091
2092        if (params->n_ssids == 0)
2093                flags = IWL_UMAC_SCAN_GEN_FLAGS_PASSIVE;
2094
2095        if (params->n_ssids == 1 && params->ssids[0].ssid_len != 0)
2096                flags |= IWL_UMAC_SCAN_GEN_FLAGS_PRE_CONNECT;
2097
2098        if (iwl_mvm_is_scan_fragmented(params->type))
2099                flags |= IWL_UMAC_SCAN_GEN_FLAGS_FRAGMENTED;
2100
2101        if (iwl_mvm_is_cdb_supported(mvm) &&
2102            iwl_mvm_is_scan_fragmented(params->hb_type))
2103                flags |= IWL_UMAC_SCAN_GEN_FLAGS_LMAC2_FRAGMENTED;
2104
2105        if (iwl_mvm_rrm_scan_needed(mvm) &&
2106            fw_has_capa(&mvm->fw->ucode_capa,
2107                        IWL_UCODE_TLV_CAPA_WFA_TPC_REP_IE_SUPPORT))
2108                flags |= IWL_UMAC_SCAN_GEN_FLAGS_RRM_ENABLED;
2109
2110        if (params->pass_all)
2111                flags |= IWL_UMAC_SCAN_GEN_FLAGS_PASS_ALL;
2112        else
2113                flags |= IWL_UMAC_SCAN_GEN_FLAGS_MATCH;
2114
2115        if (!iwl_mvm_is_regular_scan(params))
2116                flags |= IWL_UMAC_SCAN_GEN_FLAGS_PERIODIC;
2117
2118        if (params->iter_notif)
2119                flags |= IWL_UMAC_SCAN_GEN_FLAGS_ITER_COMPLETE;
2120
2121#ifdef CONFIG_IWLWIFI_DEBUGFS
2122        if (mvm->scan_iter_notif_enabled)
2123                flags |= IWL_UMAC_SCAN_GEN_FLAGS_ITER_COMPLETE;
2124#endif
2125
2126        if (mvm->sched_scan_pass_all == SCHED_SCAN_PASS_ALL_ENABLED)
2127                flags |= IWL_UMAC_SCAN_GEN_FLAGS_ITER_COMPLETE;
2128
2129        if (iwl_mvm_is_adaptive_dwell_supported(mvm) && IWL_MVM_ADWELL_ENABLE)
2130                flags |= IWL_UMAC_SCAN_GEN_FLAGS_ADAPTIVE_DWELL;
2131
2132        /*
2133         * Extended dwell is relevant only for low band to start with, as it is
2134         * being used for social channles only (1, 6, 11), so we can check
2135         * only scan type on low band also for CDB.
2136         */
2137        if (iwl_mvm_is_regular_scan(params) &&
2138            vif->type != NL80211_IFTYPE_P2P_DEVICE &&
2139            !iwl_mvm_is_scan_fragmented(params->type) &&
2140            !iwl_mvm_is_adaptive_dwell_supported(mvm) &&
2141            !iwl_mvm_is_oce_supported(mvm))
2142                flags |= IWL_UMAC_SCAN_GEN_FLAGS_EXTENDED_DWELL;
2143
2144        if (iwl_mvm_is_oce_supported(mvm)) {
2145                if ((params->flags &
2146                     NL80211_SCAN_FLAG_OCE_PROBE_REQ_HIGH_TX_RATE))
2147                        flags |= IWL_UMAC_SCAN_GEN_FLAGS_PROB_REQ_HIGH_TX_RATE;
2148                /* Since IWL_UMAC_SCAN_GEN_FLAGS_EXTENDED_DWELL and
2149                 * NL80211_SCAN_FLAG_OCE_PROBE_REQ_DEFERRAL_SUPPRESSION shares
2150                 * the same bit, we need to make sure that we use this bit here
2151                 * only when IWL_UMAC_SCAN_GEN_FLAGS_EXTENDED_DWELL cannot be
2152                 * used. */
2153                if ((params->flags &
2154                     NL80211_SCAN_FLAG_OCE_PROBE_REQ_DEFERRAL_SUPPRESSION) &&
2155                     !WARN_ON_ONCE(!iwl_mvm_is_adaptive_dwell_supported(mvm)))
2156                        flags |= IWL_UMAC_SCAN_GEN_FLAGS_PROB_REQ_DEFER_SUPP;
2157                if ((params->flags & NL80211_SCAN_FLAG_FILS_MAX_CHANNEL_TIME))
2158                        flags |= IWL_UMAC_SCAN_GEN_FLAGS_MAX_CHNL_TIME;
2159        }
2160
2161        return flags;
2162}
2163
2164static int
2165iwl_mvm_fill_scan_sched_params(struct iwl_mvm_scan_params *params,
2166                               struct iwl_scan_umac_schedule *schedule,
2167                               __le16 *delay)
2168{
2169        int i;
2170        if (WARN_ON(!params->n_scan_plans ||
2171                    params->n_scan_plans > IWL_MAX_SCHED_SCAN_PLANS))
2172                return -EINVAL;
2173
2174        for (i = 0; i < params->n_scan_plans; i++) {
2175                struct cfg80211_sched_scan_plan *scan_plan =
2176                        &params->scan_plans[i];
2177
2178                schedule[i].iter_count = scan_plan->iterations;
2179                schedule[i].interval =
2180                        cpu_to_le16(scan_plan->interval);
2181        }
2182
2183        /*
2184         * If the number of iterations of the last scan plan is set to
2185         * zero, it should run infinitely. However, this is not always the case.
2186         * For example, when regular scan is requested the driver sets one scan
2187         * plan with one iteration.
2188         */
2189        if (!schedule[params->n_scan_plans - 1].iter_count)
2190                schedule[params->n_scan_plans - 1].iter_count = 0xff;
2191
2192        *delay = cpu_to_le16(params->delay);
2193
2194        return 0;
2195}
2196
2197static int iwl_mvm_scan_umac(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
2198                             struct iwl_mvm_scan_params *params,
2199                             int type, int uid)
2200{
2201        struct iwl_scan_req_umac *cmd = mvm->scan_cmd;
2202        struct iwl_scan_umac_chan_param *chan_param;
2203        void *cmd_data = iwl_mvm_get_scan_req_umac_data(mvm);
2204        void *sec_part = (u8 *)cmd_data + sizeof(struct iwl_scan_channel_cfg_umac) *
2205                mvm->fw->ucode_capa.n_scan_channels;
2206        struct iwl_scan_req_umac_tail_v2 *tail_v2 =
2207                (struct iwl_scan_req_umac_tail_v2 *)sec_part;
2208        struct iwl_scan_req_umac_tail_v1 *tail_v1;
2209        struct iwl_ssid_ie *direct_scan;
2210        int ret = 0;
2211        u32 ssid_bitmap = 0;
2212        u8 channel_flags = 0;
2213        u16 gen_flags;
2214        struct iwl_mvm_vif *scan_vif = iwl_mvm_vif_from_mac80211(vif);
2215
2216        chan_param = iwl_mvm_get_scan_req_umac_channel(mvm);
2217
2218        iwl_mvm_scan_umac_dwell(mvm, cmd, params);
2219
2220        mvm->scan_uid_status[uid] = type;
2221
2222        cmd->uid = cpu_to_le32(uid);
2223        gen_flags = iwl_mvm_scan_umac_flags(mvm, params, vif);
2224        cmd->general_flags = cpu_to_le16(gen_flags);
2225        if (iwl_mvm_is_adaptive_dwell_v2_supported(mvm)) {
2226                if (gen_flags & IWL_UMAC_SCAN_GEN_FLAGS_FRAGMENTED)
2227                        cmd->v8.num_of_fragments[SCAN_LB_LMAC_IDX] =
2228                                                        IWL_SCAN_NUM_OF_FRAGS;
2229                if (gen_flags & IWL_UMAC_SCAN_GEN_FLAGS_LMAC2_FRAGMENTED)
2230                        cmd->v8.num_of_fragments[SCAN_HB_LMAC_IDX] =
2231                                                        IWL_SCAN_NUM_OF_FRAGS;
2232
2233                cmd->v8.general_flags2 =
2234                        IWL_UMAC_SCAN_GEN_FLAGS2_ALLOW_CHNL_REORDER;
2235        }
2236
2237        cmd->scan_start_mac_id = scan_vif->id;
2238
2239        if (type == IWL_MVM_SCAN_SCHED || type == IWL_MVM_SCAN_NETDETECT)
2240                cmd->flags = cpu_to_le32(IWL_UMAC_SCAN_FLAG_PREEMPTIVE);
2241
2242        if (iwl_mvm_scan_use_ebs(mvm, vif)) {
2243                channel_flags = IWL_SCAN_CHANNEL_FLAG_EBS |
2244                                IWL_SCAN_CHANNEL_FLAG_EBS_ACCURATE |
2245                                IWL_SCAN_CHANNEL_FLAG_CACHE_ADD;
2246
2247                /* set fragmented ebs for fragmented scan on HB channels */
2248                if (iwl_mvm_is_frag_ebs_supported(mvm)) {
2249                        if (gen_flags &
2250                            IWL_UMAC_SCAN_GEN_FLAGS_LMAC2_FRAGMENTED ||
2251                            (!iwl_mvm_is_cdb_supported(mvm) &&
2252                             gen_flags & IWL_UMAC_SCAN_GEN_FLAGS_FRAGMENTED))
2253                                channel_flags |= IWL_SCAN_CHANNEL_FLAG_EBS_FRAG;
2254                }
2255        }
2256
2257        chan_param->flags = channel_flags;
2258        chan_param->count = params->n_channels;
2259
2260        ret = iwl_mvm_fill_scan_sched_params(params, tail_v2->schedule,
2261                                             &tail_v2->delay);
2262        if (ret) {
2263                mvm->scan_uid_status[uid] = 0;
2264                return ret;
2265        }
2266
2267        if (iwl_mvm_is_scan_ext_chan_supported(mvm)) {
2268                tail_v2->preq = params->preq;
2269                direct_scan = tail_v2->direct_scan;
2270        } else {
2271                tail_v1 = (struct iwl_scan_req_umac_tail_v1 *)sec_part;
2272                iwl_mvm_scan_set_legacy_probe_req(&tail_v1->preq,
2273                                                  &params->preq);
2274                direct_scan = tail_v1->direct_scan;
2275        }
2276        iwl_scan_build_ssids(params, direct_scan, &ssid_bitmap);
2277        iwl_mvm_umac_scan_cfg_channels(mvm, params->channels,
2278                                       params->n_channels, ssid_bitmap,
2279                                       cmd_data);
2280        return 0;
2281}
2282
2283static void
2284iwl_mvm_scan_umac_fill_general_p_v11(struct iwl_mvm *mvm,
2285                                     struct iwl_mvm_scan_params *params,
2286                                     struct ieee80211_vif *vif,
2287                                     struct iwl_scan_general_params_v11 *gp,
2288                                     u16 gen_flags, u8 gen_flags2)
2289{
2290        struct iwl_mvm_vif *scan_vif = iwl_mvm_vif_from_mac80211(vif);
2291
2292        iwl_mvm_scan_umac_dwell_v11(mvm, gp, params);
2293
2294        IWL_DEBUG_SCAN(mvm, "Gerenal: flags=0x%x, flags2=0x%x\n",
2295                       gen_flags, gen_flags2);
2296
2297        gp->flags = cpu_to_le16(gen_flags);
2298        gp->flags2 = gen_flags2;
2299
2300        if (gen_flags & IWL_UMAC_SCAN_GEN_FLAGS_V2_FRAGMENTED_LMAC1)
2301                gp->num_of_fragments[SCAN_LB_LMAC_IDX] = IWL_SCAN_NUM_OF_FRAGS;
2302        if (gen_flags & IWL_UMAC_SCAN_GEN_FLAGS_V2_FRAGMENTED_LMAC2)
2303                gp->num_of_fragments[SCAN_HB_LMAC_IDX] = IWL_SCAN_NUM_OF_FRAGS;
2304
2305        gp->scan_start_mac_id = scan_vif->id;
2306}
2307
2308static void
2309iwl_mvm_scan_umac_fill_probe_p_v3(struct iwl_mvm_scan_params *params,
2310                                  struct iwl_scan_probe_params_v3 *pp)
2311{
2312        pp->preq = params->preq;
2313        pp->ssid_num = params->n_ssids;
2314        iwl_scan_build_ssids(params, pp->direct_scan, NULL);
2315}
2316
2317static void
2318iwl_mvm_scan_umac_fill_probe_p_v4(struct iwl_mvm_scan_params *params,
2319                                  struct iwl_scan_probe_params_v4 *pp,
2320                                  u32 *bitmap_ssid)
2321{
2322        pp->preq = params->preq;
2323        iwl_scan_build_ssids(params, pp->direct_scan, bitmap_ssid);
2324}
2325
2326static void
2327iwl_mvm_scan_umac_fill_ch_p_v4(struct iwl_mvm *mvm,
2328                               struct iwl_mvm_scan_params *params,
2329                               struct ieee80211_vif *vif,
2330                               struct iwl_scan_channel_params_v4 *cp,
2331                               u32 channel_cfg_flags)
2332{
2333        cp->flags = iwl_mvm_scan_umac_chan_flags_v2(mvm, params, vif);
2334        cp->count = params->n_channels;
2335        cp->num_of_aps_override = IWL_SCAN_ADWELL_N_APS_GO_FRIENDLY;
2336
2337        iwl_mvm_umac_scan_cfg_channels_v4(mvm, params->channels, cp,
2338                                          params->n_channels,
2339                                          channel_cfg_flags,
2340                                          vif->type);
2341}
2342
2343static void
2344iwl_mvm_scan_umac_fill_ch_p_v6(struct iwl_mvm *mvm,
2345                               struct iwl_mvm_scan_params *params,
2346                               struct ieee80211_vif *vif,
2347                               struct iwl_scan_channel_params_v6 *cp,
2348                               u32 channel_cfg_flags)
2349{
2350        cp->flags = iwl_mvm_scan_umac_chan_flags_v2(mvm, params, vif);
2351        cp->count = params->n_channels;
2352        cp->n_aps_override[0] = IWL_SCAN_ADWELL_N_APS_GO_FRIENDLY;
2353        cp->n_aps_override[1] = IWL_SCAN_ADWELL_N_APS_SOCIAL_CHS;
2354
2355        iwl_mvm_umac_scan_cfg_channels_v6(mvm, params->channels, cp,
2356                                          params->n_channels,
2357                                          channel_cfg_flags,
2358                                          vif->type);
2359
2360        if (params->enable_6ghz_passive) {
2361                struct ieee80211_supported_band *sband =
2362                        &mvm->nvm_data->bands[NL80211_BAND_6GHZ];
2363                u32 i;
2364
2365                for (i = 0; i < sband->n_channels; i++) {
2366                        struct ieee80211_channel *channel =
2367                                &sband->channels[i];
2368
2369                        struct iwl_scan_channel_cfg_umac *cfg =
2370                                &cp->channel_config[cp->count];
2371
2372                        if (!cfg80211_channel_is_psc(channel))
2373                                continue;
2374
2375                        cfg->flags = 0;
2376                        cfg->v2.channel_num = channel->hw_value;
2377                        cfg->v2.band = PHY_BAND_6;
2378                        cfg->v2.iter_count = 1;
2379                        cfg->v2.iter_interval = 0;
2380                        cp->count++;
2381                }
2382        }
2383}
2384
2385static int iwl_mvm_scan_umac_v12(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
2386                                 struct iwl_mvm_scan_params *params, int type,
2387                                 int uid)
2388{
2389        struct iwl_scan_req_umac_v12 *cmd = mvm->scan_cmd;
2390        struct iwl_scan_req_params_v12 *scan_p = &cmd->scan_params;
2391        int ret;
2392        u16 gen_flags;
2393
2394        mvm->scan_uid_status[uid] = type;
2395
2396        cmd->ooc_priority = cpu_to_le32(iwl_mvm_scan_umac_ooc_priority(params));
2397        cmd->uid = cpu_to_le32(uid);
2398
2399        gen_flags = iwl_mvm_scan_umac_flags_v2(mvm, params, vif, type);
2400        iwl_mvm_scan_umac_fill_general_p_v11(mvm, params, vif,
2401                                             &scan_p->general_params,
2402                                             gen_flags, 0);
2403
2404        ret = iwl_mvm_fill_scan_sched_params(params,
2405                                             scan_p->periodic_params.schedule,
2406                                             &scan_p->periodic_params.delay);
2407        if (ret)
2408                return ret;
2409
2410        iwl_mvm_scan_umac_fill_probe_p_v3(params, &scan_p->probe_params);
2411        iwl_mvm_scan_umac_fill_ch_p_v4(mvm, params, vif,
2412                                       &scan_p->channel_params, 0);
2413
2414        return 0;
2415}
2416
2417static int iwl_mvm_scan_umac_v14_and_above(struct iwl_mvm *mvm,
2418                                           struct ieee80211_vif *vif,
2419                                           struct iwl_mvm_scan_params *params,
2420                                           int type, int uid, u32 version)
2421{
2422        struct iwl_scan_req_umac_v15 *cmd = mvm->scan_cmd;
2423        struct iwl_scan_req_params_v15 *scan_p = &cmd->scan_params;
2424        struct iwl_scan_channel_params_v6 *cp = &scan_p->channel_params;
2425        struct iwl_scan_probe_params_v4 *pb = &scan_p->probe_params;
2426        int ret;
2427        u16 gen_flags;
2428        u8 gen_flags2;
2429        u32 bitmap_ssid = 0;
2430
2431        mvm->scan_uid_status[uid] = type;
2432
2433        cmd->ooc_priority = cpu_to_le32(iwl_mvm_scan_umac_ooc_priority(params));
2434        cmd->uid = cpu_to_le32(uid);
2435
2436        gen_flags = iwl_mvm_scan_umac_flags_v2(mvm, params, vif, type);
2437
2438        if (version >= 15)
2439                gen_flags2 = iwl_mvm_scan_umac_flags2(mvm, params, vif, type);
2440        else
2441                gen_flags2 = 0;
2442
2443        iwl_mvm_scan_umac_fill_general_p_v11(mvm, params, vif,
2444                                             &scan_p->general_params,
2445                                             gen_flags, gen_flags2);
2446
2447        ret = iwl_mvm_fill_scan_sched_params(params,
2448                                             scan_p->periodic_params.schedule,
2449                                             &scan_p->periodic_params.delay);
2450        if (ret)
2451                return ret;
2452
2453        if (!params->scan_6ghz) {
2454                iwl_mvm_scan_umac_fill_probe_p_v4(params, &scan_p->probe_params,
2455                                          &bitmap_ssid);
2456                iwl_mvm_scan_umac_fill_ch_p_v6(mvm, params, vif,
2457                                       &scan_p->channel_params, bitmap_ssid);
2458
2459                return 0;
2460        } else {
2461                pb->preq = params->preq;
2462        }
2463
2464        cp->flags = iwl_mvm_scan_umac_chan_flags_v2(mvm, params, vif);
2465        cp->n_aps_override[0] = IWL_SCAN_ADWELL_N_APS_GO_FRIENDLY;
2466        cp->n_aps_override[1] = IWL_SCAN_ADWELL_N_APS_SOCIAL_CHS;
2467
2468        iwl_mvm_umac_scan_fill_6g_chan_list(mvm, params, pb);
2469
2470        cp->count = iwl_mvm_umac_scan_cfg_channels_v6_6g(mvm, params,
2471                                                         params->n_channels,
2472                                                         pb, cp, vif->type);
2473        if (!cp->count) {
2474                mvm->scan_uid_status[uid] = 0;
2475                return -EINVAL;
2476        }
2477
2478        if (!params->n_ssids ||
2479            (params->n_ssids == 1 && !params->ssids[0].ssid_len))
2480                cp->flags |= IWL_SCAN_CHANNEL_FLAG_6G_PSC_NO_FILTER;
2481
2482        return 0;
2483}
2484
2485static int iwl_mvm_scan_umac_v14(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
2486                                 struct iwl_mvm_scan_params *params, int type,
2487                                 int uid)
2488{
2489        return iwl_mvm_scan_umac_v14_and_above(mvm, vif, params, type, uid, 14);
2490}
2491
2492static int iwl_mvm_scan_umac_v15(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
2493                                 struct iwl_mvm_scan_params *params, int type,
2494                                 int uid)
2495{
2496        return iwl_mvm_scan_umac_v14_and_above(mvm, vif, params, type, uid, 15);
2497}
2498
2499static int iwl_mvm_num_scans(struct iwl_mvm *mvm)
2500{
2501        return hweight32(mvm->scan_status & IWL_MVM_SCAN_MASK);
2502}
2503
2504static int iwl_mvm_check_running_scans(struct iwl_mvm *mvm, int type)
2505{
2506        bool unified_image = fw_has_capa(&mvm->fw->ucode_capa,
2507                                         IWL_UCODE_TLV_CAPA_CNSLDTD_D3_D0_IMG);
2508
2509        /* This looks a bit arbitrary, but the idea is that if we run
2510         * out of possible simultaneous scans and the userspace is
2511         * trying to run a scan type that is already running, we
2512         * return -EBUSY.  But if the userspace wants to start a
2513         * different type of scan, we stop the opposite type to make
2514         * space for the new request.  The reason is backwards
2515         * compatibility with old wpa_supplicant that wouldn't stop a
2516         * scheduled scan before starting a normal scan.
2517         */
2518
2519        /* FW supports only a single periodic scan */
2520        if ((type == IWL_MVM_SCAN_SCHED || type == IWL_MVM_SCAN_NETDETECT) &&
2521            mvm->scan_status & (IWL_MVM_SCAN_SCHED | IWL_MVM_SCAN_NETDETECT))
2522                return -EBUSY;
2523
2524        if (iwl_mvm_num_scans(mvm) < mvm->max_scans)
2525                return 0;
2526
2527        /* Use a switch, even though this is a bitmask, so that more
2528         * than one bits set will fall in default and we will warn.
2529         */
2530        switch (type) {
2531        case IWL_MVM_SCAN_REGULAR:
2532                if (mvm->scan_status & IWL_MVM_SCAN_REGULAR_MASK)
2533                        return -EBUSY;
2534                return iwl_mvm_scan_stop(mvm, IWL_MVM_SCAN_SCHED, true);
2535        case IWL_MVM_SCAN_SCHED:
2536                if (mvm->scan_status & IWL_MVM_SCAN_SCHED_MASK)
2537                        return -EBUSY;
2538                return iwl_mvm_scan_stop(mvm, IWL_MVM_SCAN_REGULAR, true);
2539        case IWL_MVM_SCAN_NETDETECT:
2540                /* For non-unified images, there's no need to stop
2541                 * anything for net-detect since the firmware is
2542                 * restarted anyway.  This way, any sched scans that
2543                 * were running will be restarted when we resume.
2544                 */
2545                if (!unified_image)
2546                        return 0;
2547
2548                /* If this is a unified image and we ran out of scans,
2549                 * we need to stop something.  Prefer stopping regular
2550                 * scans, because the results are useless at this
2551                 * point, and we should be able to keep running
2552                 * another scheduled scan while suspended.
2553                 */
2554                if (mvm->scan_status & IWL_MVM_SCAN_REGULAR_MASK)
2555                        return iwl_mvm_scan_stop(mvm, IWL_MVM_SCAN_REGULAR,
2556                                                 true);
2557                if (mvm->scan_status & IWL_MVM_SCAN_SCHED_MASK)
2558                        return iwl_mvm_scan_stop(mvm, IWL_MVM_SCAN_SCHED,
2559                                                 true);
2560                /* Something is wrong if no scan was running but we
2561                 * ran out of scans.
2562                 */
2563                fallthrough;
2564        default:
2565                WARN_ON(1);
2566                break;
2567        }
2568
2569        return -EIO;
2570}
2571
2572#define SCAN_TIMEOUT 30000
2573
2574void iwl_mvm_scan_timeout_wk(struct work_struct *work)
2575{
2576        struct delayed_work *delayed_work = to_delayed_work(work);
2577        struct iwl_mvm *mvm = container_of(delayed_work, struct iwl_mvm,
2578                                           scan_timeout_dwork);
2579
2580        IWL_ERR(mvm, "regular scan timed out\n");
2581
2582        iwl_force_nmi(mvm->trans);
2583}
2584
2585static void iwl_mvm_fill_scan_type(struct iwl_mvm *mvm,
2586                                   struct iwl_mvm_scan_params *params,
2587                                   struct ieee80211_vif *vif)
2588{
2589        if (iwl_mvm_is_cdb_supported(mvm)) {
2590                params->type =
2591                        iwl_mvm_get_scan_type_band(mvm, vif,
2592                                                   NL80211_BAND_2GHZ);
2593                params->hb_type =
2594                        iwl_mvm_get_scan_type_band(mvm, vif,
2595                                                   NL80211_BAND_5GHZ);
2596        } else {
2597                params->type = iwl_mvm_get_scan_type(mvm, vif);
2598        }
2599}
2600
2601struct iwl_scan_umac_handler {
2602        u8 version;
2603        int (*handler)(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
2604                       struct iwl_mvm_scan_params *params, int type, int uid);
2605};
2606
2607#define IWL_SCAN_UMAC_HANDLER(_ver) {           \
2608        .version = _ver,                        \
2609        .handler = iwl_mvm_scan_umac_v##_ver,   \
2610}
2611
2612static const struct iwl_scan_umac_handler iwl_scan_umac_handlers[] = {
2613        /* set the newest version first to shorten the list traverse time */
2614        IWL_SCAN_UMAC_HANDLER(15),
2615        IWL_SCAN_UMAC_HANDLER(14),
2616        IWL_SCAN_UMAC_HANDLER(12),
2617};
2618
2619static int iwl_mvm_build_scan_cmd(struct iwl_mvm *mvm,
2620                                  struct ieee80211_vif *vif,
2621                                  struct iwl_host_cmd *hcmd,
2622                                  struct iwl_mvm_scan_params *params,
2623                                  int type)
2624{
2625        int uid, i, err;
2626        u8 scan_ver;
2627
2628        lockdep_assert_held(&mvm->mutex);
2629        memset(mvm->scan_cmd, 0, ksize(mvm->scan_cmd));
2630
2631        if (!fw_has_capa(&mvm->fw->ucode_capa, IWL_UCODE_TLV_CAPA_UMAC_SCAN)) {
2632                hcmd->id = SCAN_OFFLOAD_REQUEST_CMD;
2633
2634                return iwl_mvm_scan_lmac(mvm, vif, params);
2635        }
2636
2637        uid = iwl_mvm_scan_uid_by_status(mvm, 0);
2638        if (uid < 0)
2639                return uid;
2640
2641        hcmd->id = WIDE_ID(IWL_ALWAYS_LONG_GROUP, SCAN_REQ_UMAC);
2642
2643        scan_ver = iwl_fw_lookup_cmd_ver(mvm->fw, SCAN_REQ_UMAC,
2644                                         IWL_FW_CMD_VER_UNKNOWN);
2645
2646        for (i = 0; i < ARRAY_SIZE(iwl_scan_umac_handlers); i++) {
2647                const struct iwl_scan_umac_handler *ver_handler =
2648                        &iwl_scan_umac_handlers[i];
2649
2650                if (ver_handler->version != scan_ver)
2651                        continue;
2652
2653                return ver_handler->handler(mvm, vif, params, type, uid);
2654        }
2655
2656        err = iwl_mvm_scan_umac(mvm, vif, params, type, uid);
2657        if (err)
2658                return err;
2659
2660        return uid;
2661}
2662
2663struct iwl_mvm_scan_respect_p2p_go_iter_data {
2664        struct ieee80211_vif *current_vif;
2665        bool p2p_go;
2666        enum nl80211_band band;
2667};
2668
2669static void iwl_mvm_scan_respect_p2p_go_iter(void *_data, u8 *mac,
2670                                             struct ieee80211_vif *vif)
2671{
2672        struct iwl_mvm_scan_respect_p2p_go_iter_data *data = _data;
2673        struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif);
2674
2675        /* exclude the given vif */
2676        if (vif == data->current_vif)
2677                return;
2678
2679        if (vif->type == NL80211_IFTYPE_AP && vif->p2p &&
2680            mvmvif->phy_ctxt->id < NUM_PHY_CTX &&
2681            (data->band == NUM_NL80211_BANDS ||
2682             mvmvif->phy_ctxt->channel->band == data->band))
2683                data->p2p_go = true;
2684}
2685
2686static bool _iwl_mvm_get_respect_p2p_go(struct iwl_mvm *mvm,
2687                                        struct ieee80211_vif *vif,
2688                                        bool low_latency,
2689                                        enum nl80211_band band)
2690{
2691        struct iwl_mvm_scan_respect_p2p_go_iter_data data = {
2692                .current_vif = vif,
2693                .p2p_go = false,
2694                .band = band,
2695        };
2696
2697        if (!low_latency)
2698                return false;
2699
2700        ieee80211_iterate_active_interfaces_atomic(mvm->hw,
2701                                                   IEEE80211_IFACE_ITER_NORMAL,
2702                                                   iwl_mvm_scan_respect_p2p_go_iter,
2703                                                   &data);
2704
2705        return data.p2p_go;
2706}
2707
2708static bool iwl_mvm_get_respect_p2p_go_band(struct iwl_mvm *mvm,
2709                                            struct ieee80211_vif *vif,
2710                                            enum nl80211_band band)
2711{
2712        bool low_latency = iwl_mvm_low_latency_band(mvm, band);
2713
2714        return _iwl_mvm_get_respect_p2p_go(mvm, vif, low_latency, band);
2715}
2716
2717static bool iwl_mvm_get_respect_p2p_go(struct iwl_mvm *mvm,
2718                                       struct ieee80211_vif *vif)
2719{
2720        bool low_latency = iwl_mvm_low_latency(mvm);
2721
2722        return _iwl_mvm_get_respect_p2p_go(mvm, vif, low_latency,
2723                                           NUM_NL80211_BANDS);
2724}
2725
2726static void iwl_mvm_fill_respect_p2p_go(struct iwl_mvm *mvm,
2727                                        struct iwl_mvm_scan_params *params,
2728                                        struct ieee80211_vif *vif)
2729{
2730        if (iwl_mvm_is_cdb_supported(mvm)) {
2731                params->respect_p2p_go =
2732                        iwl_mvm_get_respect_p2p_go_band(mvm, vif,
2733                                                        NL80211_BAND_2GHZ);
2734                params->respect_p2p_go_hb =
2735                        iwl_mvm_get_respect_p2p_go_band(mvm, vif,
2736                                                        NL80211_BAND_5GHZ);
2737        } else {
2738                params->respect_p2p_go = iwl_mvm_get_respect_p2p_go(mvm, vif);
2739        }
2740}
2741
2742int iwl_mvm_reg_scan_start(struct iwl_mvm *mvm, struct ieee80211_vif *vif,
2743                           struct cfg80211_scan_request *req,
2744                           struct ieee80211_scan_ies *ies)
2745{
2746        struct iwl_host_cmd hcmd = {
2747                .len = { iwl_mvm_scan_size(mvm), },
2748                .data = { mvm->scan_cmd, },
2749                .dataflags = { IWL_HCMD_DFL_NOCOPY, },
2750        };
2751        struct iwl_mvm_scan_params params = {};
2752        int ret, uid;
2753        struct cfg80211_sched_scan_plan scan_plan = { .iterations = 1 };
2754
2755        lockdep_assert_held(&mvm->mutex);
2756
2757        if (iwl_mvm_is_lar_supported(mvm) && !mvm->lar_regdom_set) {
2758                IWL_ERR(mvm, "scan while LAR regdomain is not set\n");
2759                return -EBUSY;
2760        }
2761
2762        ret = iwl_mvm_check_running_scans(mvm, IWL_MVM_SCAN_REGULAR);
2763        if (ret)
2764                return ret;
2765
2766        /* we should have failed registration if scan_cmd was NULL */
2767        if (WARN_ON(!mvm->scan_cmd))
2768                return -ENOMEM;
2769
2770        if (!iwl_mvm_scan_fits(mvm, req->n_ssids, ies, req->n_channels))
2771                return -ENOBUFS;
2772
2773        params.n_ssids = req->n_ssids;
2774        params.flags = req->flags;
2775        params.n_channels = req->n_channels;
2776        params.delay = 0;
2777        params.ssids = req->ssids;
2778        params.channels = req->channels;
2779        params.mac_addr = req->mac_addr;
2780        params.mac_addr_mask = req->mac_addr_mask;
2781        params.no_cck = req->no_cck;
2782        params.pass_all = true;
2783        params.n_match_sets = 0;
2784        params.match_sets = NULL;
2785
2786        params.scan_plans = &scan_plan;
2787        params.n_scan_plans = 1;
2788
2789        params.n_6ghz_params = req->n_6ghz_params;
2790        params.scan_6ghz_params = req->scan_6ghz_params;
2791        params.scan_6ghz = req->scan_6ghz;
2792        iwl_mvm_fill_scan_type(mvm, &params, vif);
2793        iwl_mvm_fill_respect_p2p_go(mvm, &params, vif);
2794
2795        if (req->duration)
2796                params.iter_notif = true;
2797
2798        iwl_mvm_build_scan_probe(mvm, vif, ies, &params);
2799
2800        iwl_mvm_scan_6ghz_passive_scan(mvm, &params, vif);
2801
2802        uid = iwl_mvm_build_scan_cmd(mvm, vif, &hcmd, &params,
2803                                     IWL_MVM_SCAN_REGULAR);
2804
2805        if (uid < 0)
2806                return uid;
2807
2808        iwl_mvm_pause_tcm(mvm, false);
2809
2810        ret = iwl_mvm_send_cmd(mvm, &hcmd);
2811        if (ret) {
2812                /* If the scan failed, it usually means that the FW was unable
2813                 * to allocate the time events. Warn on it, but maybe we
2814                 * should try to send the command again with different params.
2815                 */
2816                IWL_ERR(mvm, "Scan failed! ret %d\n", ret);
2817                iwl_mvm_resume_tcm(mvm);
2818                mvm->scan_uid_status[uid] = 0;
2819                return ret;
2820        }
2821
2822        IWL_DEBUG_SCAN(mvm, "Scan request was sent successfully\n");
2823        mvm->scan_status |= IWL_MVM_SCAN_REGULAR;
2824        mvm->scan_vif = iwl_mvm_vif_from_mac80211(vif);
2825
2826        if (params.enable_6ghz_passive)
2827                mvm->last_6ghz_passive_scan_jiffies = jiffies;
2828
2829        schedule_delayed_work(&mvm->scan_timeout_dwork,
2830                              msecs_to_jiffies(SCAN_TIMEOUT));
2831
2832        return 0;
2833}
2834
2835int iwl_mvm_sched_scan_start(struct iwl_mvm *mvm,
2836                             struct ieee80211_vif *vif,
2837                             struct cfg80211_sched_scan_request *req,
2838                             struct ieee80211_scan_ies *ies,
2839                             int type)
2840{
2841        struct iwl_host_cmd hcmd = {
2842                .len = { iwl_mvm_scan_size(mvm), },
2843                .data = { mvm->scan_cmd, },
2844                .dataflags = { IWL_HCMD_DFL_NOCOPY, },
2845        };
2846        struct iwl_mvm_scan_params params = {};
2847        int ret, uid;
2848        int i, j;
2849        bool non_psc_included = false;
2850
2851        lockdep_assert_held(&mvm->mutex);
2852
2853        if (iwl_mvm_is_lar_supported(mvm) && !mvm->lar_regdom_set) {
2854                IWL_ERR(mvm, "sched-scan while LAR regdomain is not set\n");
2855                return -EBUSY;
2856        }
2857
2858        ret = iwl_mvm_check_running_scans(mvm, type);
2859        if (ret)
2860                return ret;
2861
2862        /* we should have failed registration if scan_cmd was NULL */
2863        if (WARN_ON(!mvm->scan_cmd))
2864                return -ENOMEM;
2865
2866
2867        params.n_ssids = req->n_ssids;
2868        params.flags = req->flags;
2869        params.n_channels = req->n_channels;
2870        params.ssids = req->ssids;
2871        params.channels = req->channels;
2872        params.mac_addr = req->mac_addr;
2873        params.mac_addr_mask = req->mac_addr_mask;
2874        params.no_cck = false;
2875        params.pass_all =  iwl_mvm_scan_pass_all(mvm, req);
2876        params.n_match_sets = req->n_match_sets;
2877        params.match_sets = req->match_sets;
2878        if (!req->n_scan_plans)
2879                return -EINVAL;
2880
2881        params.n_scan_plans = req->n_scan_plans;
2882        params.scan_plans = req->scan_plans;
2883
2884        iwl_mvm_fill_scan_type(mvm, &params, vif);
2885        iwl_mvm_fill_respect_p2p_go(mvm, &params, vif);
2886
2887        /* In theory, LMAC scans can handle a 32-bit delay, but since
2888         * waiting for over 18 hours to start the scan is a bit silly
2889         * and to keep it aligned with UMAC scans (which only support
2890         * 16-bit delays), trim it down to 16-bits.
2891         */
2892        if (req->delay > U16_MAX) {
2893                IWL_DEBUG_SCAN(mvm,
2894                               "delay value is > 16-bits, set to max possible\n");
2895                params.delay = U16_MAX;
2896        } else {
2897                params.delay = req->delay;
2898        }
2899
2900        ret = iwl_mvm_config_sched_scan_profiles(mvm, req);
2901        if (ret)
2902                return ret;
2903
2904        iwl_mvm_build_scan_probe(mvm, vif, ies, &params);
2905
2906        /* for 6 GHZ band only PSC channels need to be added */
2907        for (i = 0; i < params.n_channels; i++) {
2908                struct ieee80211_channel *channel = params.channels[i];
2909
2910                if (channel->band == NL80211_BAND_6GHZ &&
2911                    !cfg80211_channel_is_psc(channel)) {
2912                        non_psc_included = true;
2913                        break;
2914                }
2915        }
2916
2917        if (non_psc_included) {
2918                params.channels = kmemdup(params.channels,
2919                                          sizeof(params.channels[0]) *
2920                                          params.n_channels,
2921                                          GFP_KERNEL);
2922                if (!params.channels)
2923                        return -ENOMEM;
2924
2925                for (i = j = 0; i < params.n_channels; i++) {
2926                        if (params.channels[i]->band == NL80211_BAND_6GHZ &&
2927                            !cfg80211_channel_is_psc(params.channels[i]))
2928                                continue;
2929                        params.channels[j++] = params.channels[i];
2930                }
2931                params.n_channels = j;
2932        }
2933
2934        if (non_psc_included &&
2935            !iwl_mvm_scan_fits(mvm, req->n_ssids, ies, params.n_channels)) {
2936                kfree(params.channels);
2937                return -ENOBUFS;
2938        }
2939
2940        uid = iwl_mvm_build_scan_cmd(mvm, vif, &hcmd, &params, type);
2941
2942        if (non_psc_included)
2943                kfree(params.channels);
2944        if (uid < 0)
2945                return uid;
2946
2947        ret = iwl_mvm_send_cmd(mvm, &hcmd);
2948        if (!ret) {
2949                IWL_DEBUG_SCAN(mvm,
2950                               "Sched scan request was sent successfully\n");
2951                mvm->scan_status |= type;
2952        } else {
2953                /* If the scan failed, it usually means that the FW was unable
2954                 * to allocate the time events. Warn on it, but maybe we
2955                 * should try to send the command again with different params.
2956                 */
2957                IWL_ERR(mvm, "Sched scan failed! ret %d\n", ret);
2958                mvm->scan_uid_status[uid] = 0;
2959                mvm->sched_scan_pass_all = SCHED_SCAN_PASS_ALL_DISABLED;
2960        }
2961
2962        return ret;
2963}
2964
2965void iwl_mvm_rx_umac_scan_complete_notif(struct iwl_mvm *mvm,
2966                                         struct iwl_rx_cmd_buffer *rxb)
2967{
2968        struct iwl_rx_packet *pkt = rxb_addr(rxb);
2969        struct iwl_umac_scan_complete *notif = (void *)pkt->data;
2970        u32 uid = __le32_to_cpu(notif->uid);
2971        bool aborted = (notif->status == IWL_SCAN_OFFLOAD_ABORTED);
2972
2973        if (WARN_ON(!(mvm->scan_uid_status[uid] & mvm->scan_status)))
2974                return;
2975
2976        /* if the scan is already stopping, we don't need to notify mac80211 */
2977        if (mvm->scan_uid_status[uid] == IWL_MVM_SCAN_REGULAR) {
2978                struct cfg80211_scan_info info = {
2979                        .aborted = aborted,
2980                        .scan_start_tsf = mvm->scan_start,
2981                };
2982
2983                memcpy(info.tsf_bssid, mvm->scan_vif->bssid, ETH_ALEN);
2984                ieee80211_scan_completed(mvm->hw, &info);
2985                mvm->scan_vif = NULL;
2986                cancel_delayed_work(&mvm->scan_timeout_dwork);
2987                iwl_mvm_resume_tcm(mvm);
2988        } else if (mvm->scan_uid_status[uid] == IWL_MVM_SCAN_SCHED) {
2989                ieee80211_sched_scan_stopped(mvm->hw);
2990                mvm->sched_scan_pass_all = SCHED_SCAN_PASS_ALL_DISABLED;
2991        }
2992
2993        mvm->scan_status &= ~mvm->scan_uid_status[uid];
2994        IWL_DEBUG_SCAN(mvm,
2995                       "Scan completed, uid %u type %u, status %s, EBS status %s\n",
2996                       uid, mvm->scan_uid_status[uid],
2997                       notif->status == IWL_SCAN_OFFLOAD_COMPLETED ?
2998                                "completed" : "aborted",
2999                       iwl_mvm_ebs_status_str(notif->ebs_status));
3000        IWL_DEBUG_SCAN(mvm,
3001                       "Last line %d, Last iteration %d, Time from last iteration %d\n",
3002                       notif->last_schedule, notif->last_iter,
3003                       __le32_to_cpu(notif->time_from_last_iter));
3004
3005        if (notif->ebs_status != IWL_SCAN_EBS_SUCCESS &&
3006            notif->ebs_status != IWL_SCAN_EBS_INACTIVE)
3007                mvm->last_ebs_successful = false;
3008
3009        mvm->scan_uid_status[uid] = 0;
3010}
3011
3012void iwl_mvm_rx_umac_scan_iter_complete_notif(struct iwl_mvm *mvm,
3013                                              struct iwl_rx_cmd_buffer *rxb)
3014{
3015        struct iwl_rx_packet *pkt = rxb_addr(rxb);
3016        struct iwl_umac_scan_iter_complete_notif *notif = (void *)pkt->data;
3017
3018        mvm->scan_start = le64_to_cpu(notif->start_tsf);
3019
3020        IWL_DEBUG_SCAN(mvm,
3021                       "UMAC Scan iteration complete: status=0x%x scanned_channels=%d\n",
3022                       notif->status, notif->scanned_channels);
3023
3024        if (mvm->sched_scan_pass_all == SCHED_SCAN_PASS_ALL_FOUND) {
3025                IWL_DEBUG_SCAN(mvm, "Pass all scheduled scan results found\n");
3026                ieee80211_sched_scan_results(mvm->hw);
3027                mvm->sched_scan_pass_all = SCHED_SCAN_PASS_ALL_ENABLED;
3028        }
3029
3030        IWL_DEBUG_SCAN(mvm,
3031                       "UMAC Scan iteration complete: scan started at %llu (TSF)\n",
3032                       mvm->scan_start);
3033}
3034
3035static int iwl_mvm_umac_scan_abort(struct iwl_mvm *mvm, int type)
3036{
3037        struct iwl_umac_scan_abort cmd = {};
3038        int uid, ret;
3039
3040        lockdep_assert_held(&mvm->mutex);
3041
3042        /* We should always get a valid index here, because we already
3043         * checked that this type of scan was running in the generic
3044         * code.
3045         */
3046        uid = iwl_mvm_scan_uid_by_status(mvm, type);
3047        if (WARN_ON_ONCE(uid < 0))
3048                return uid;
3049
3050        cmd.uid = cpu_to_le32(uid);
3051
3052        IWL_DEBUG_SCAN(mvm, "Sending scan abort, uid %u\n", uid);
3053
3054        ret = iwl_mvm_send_cmd_pdu(mvm,
3055                                   WIDE_ID(IWL_ALWAYS_LONG_GROUP, SCAN_ABORT_UMAC),
3056                                   0, sizeof(cmd), &cmd);
3057        if (!ret)
3058                mvm->scan_uid_status[uid] = type << IWL_MVM_SCAN_STOPPING_SHIFT;
3059
3060        return ret;
3061}
3062
3063static int iwl_mvm_scan_stop_wait(struct iwl_mvm *mvm, int type)
3064{
3065        struct iwl_notification_wait wait_scan_done;
3066        static const u16 scan_done_notif[] = { SCAN_COMPLETE_UMAC,
3067                                              SCAN_OFFLOAD_COMPLETE, };
3068        int ret;
3069
3070        lockdep_assert_held(&mvm->mutex);
3071
3072        iwl_init_notification_wait(&mvm->notif_wait, &wait_scan_done,
3073                                   scan_done_notif,
3074                                   ARRAY_SIZE(scan_done_notif),
3075                                   NULL, NULL);
3076
3077        IWL_DEBUG_SCAN(mvm, "Preparing to stop scan, type %x\n", type);
3078
3079        if (fw_has_capa(&mvm->fw->ucode_capa, IWL_UCODE_TLV_CAPA_UMAC_SCAN))
3080                ret = iwl_mvm_umac_scan_abort(mvm, type);
3081        else
3082                ret = iwl_mvm_lmac_scan_abort(mvm);
3083
3084        if (ret) {
3085                IWL_DEBUG_SCAN(mvm, "couldn't stop scan type %d\n", type);
3086                iwl_remove_notification(&mvm->notif_wait, &wait_scan_done);
3087                return ret;
3088        }
3089
3090        return iwl_wait_notification(&mvm->notif_wait, &wait_scan_done,
3091                                     1 * HZ);
3092}
3093
3094static int iwl_scan_req_umac_get_size(u8 scan_ver)
3095{
3096        switch (scan_ver) {
3097        case 12:
3098                return sizeof(struct iwl_scan_req_umac_v12);
3099        case 14:
3100        case 15:
3101                return sizeof(struct iwl_scan_req_umac_v15);
3102        }
3103
3104        return 0;
3105}
3106
3107int iwl_mvm_scan_size(struct iwl_mvm *mvm)
3108{
3109        int base_size, tail_size;
3110        u8 scan_ver = iwl_fw_lookup_cmd_ver(mvm->fw, SCAN_REQ_UMAC,
3111                                            IWL_FW_CMD_VER_UNKNOWN);
3112
3113        base_size = iwl_scan_req_umac_get_size(scan_ver);
3114        if (base_size)
3115                return base_size;
3116
3117
3118        if (iwl_mvm_is_adaptive_dwell_v2_supported(mvm))
3119                base_size = IWL_SCAN_REQ_UMAC_SIZE_V8;
3120        else if (iwl_mvm_is_adaptive_dwell_supported(mvm))
3121                base_size = IWL_SCAN_REQ_UMAC_SIZE_V7;
3122        else if (iwl_mvm_cdb_scan_api(mvm))
3123                base_size = IWL_SCAN_REQ_UMAC_SIZE_V6;
3124        else
3125                base_size = IWL_SCAN_REQ_UMAC_SIZE_V1;
3126
3127        if (fw_has_capa(&mvm->fw->ucode_capa, IWL_UCODE_TLV_CAPA_UMAC_SCAN)) {
3128                if (iwl_mvm_is_scan_ext_chan_supported(mvm))
3129                        tail_size = sizeof(struct iwl_scan_req_umac_tail_v2);
3130                else
3131                        tail_size = sizeof(struct iwl_scan_req_umac_tail_v1);
3132
3133                return base_size +
3134                        sizeof(struct iwl_scan_channel_cfg_umac) *
3135                                mvm->fw->ucode_capa.n_scan_channels +
3136                        tail_size;
3137        }
3138        return sizeof(struct iwl_scan_req_lmac) +
3139                sizeof(struct iwl_scan_channel_cfg_lmac) *
3140                mvm->fw->ucode_capa.n_scan_channels +
3141                sizeof(struct iwl_scan_probe_req_v1);
3142}
3143
3144/*
3145 * This function is used in nic restart flow, to inform mac80211 about scans
3146 * that was aborted by restart flow or by an assert.
3147 */
3148void iwl_mvm_report_scan_aborted(struct iwl_mvm *mvm)
3149{
3150        if (fw_has_capa(&mvm->fw->ucode_capa, IWL_UCODE_TLV_CAPA_UMAC_SCAN)) {
3151                int uid, i;
3152
3153                uid = iwl_mvm_scan_uid_by_status(mvm, IWL_MVM_SCAN_REGULAR);
3154                if (uid >= 0) {
3155                        struct cfg80211_scan_info info = {
3156                                .aborted = true,
3157                        };
3158
3159                        cancel_delayed_work(&mvm->scan_timeout_dwork);
3160
3161                        ieee80211_scan_completed(mvm->hw, &info);
3162                        mvm->scan_uid_status[uid] = 0;
3163                }
3164                uid = iwl_mvm_scan_uid_by_status(mvm, IWL_MVM_SCAN_SCHED);
3165                if (uid >= 0) {
3166                        /* Sched scan will be restarted by mac80211 in
3167                         * restart_hw, so do not report if FW is about to be
3168                         * restarted.
3169                         */
3170                        if (!mvm->fw_restart)
3171                                ieee80211_sched_scan_stopped(mvm->hw);
3172                        mvm->sched_scan_pass_all = SCHED_SCAN_PASS_ALL_DISABLED;
3173                        mvm->scan_uid_status[uid] = 0;
3174                }
3175                uid = iwl_mvm_scan_uid_by_status(mvm,
3176                                                 IWL_MVM_SCAN_STOPPING_REGULAR);
3177                if (uid >= 0)
3178                        mvm->scan_uid_status[uid] = 0;
3179
3180                uid = iwl_mvm_scan_uid_by_status(mvm,
3181                                                 IWL_MVM_SCAN_STOPPING_SCHED);
3182                if (uid >= 0)
3183                        mvm->scan_uid_status[uid] = 0;
3184
3185                /* We shouldn't have any UIDs still set.  Loop over all the
3186                 * UIDs to make sure there's nothing left there and warn if
3187                 * any is found.
3188                 */
3189                for (i = 0; i < mvm->max_scans; i++) {
3190                        if (WARN_ONCE(mvm->scan_uid_status[i],
3191                                      "UMAC scan UID %d status was not cleaned\n",
3192                                      i))
3193                                mvm->scan_uid_status[i] = 0;
3194                }
3195        } else {
3196                if (mvm->scan_status & IWL_MVM_SCAN_REGULAR) {
3197                        struct cfg80211_scan_info info = {
3198                                .aborted = true,
3199                        };
3200
3201                        cancel_delayed_work(&mvm->scan_timeout_dwork);
3202                        ieee80211_scan_completed(mvm->hw, &info);
3203                }
3204
3205                /* Sched scan will be restarted by mac80211 in
3206                 * restart_hw, so do not report if FW is about to be
3207                 * restarted.
3208                 */
3209                if ((mvm->scan_status & IWL_MVM_SCAN_SCHED) &&
3210                    !mvm->fw_restart) {
3211                        ieee80211_sched_scan_stopped(mvm->hw);
3212                        mvm->sched_scan_pass_all = SCHED_SCAN_PASS_ALL_DISABLED;
3213                }
3214        }
3215}
3216
3217int iwl_mvm_scan_stop(struct iwl_mvm *mvm, int type, bool notify)
3218{
3219        int ret;
3220
3221        if (!(mvm->scan_status & type))
3222                return 0;
3223
3224        if (iwl_mvm_is_radio_killed(mvm)) {
3225                ret = 0;
3226                goto out;
3227        }
3228
3229        ret = iwl_mvm_scan_stop_wait(mvm, type);
3230        if (!ret)
3231                mvm->scan_status |= type << IWL_MVM_SCAN_STOPPING_SHIFT;
3232out:
3233        /* Clear the scan status so the next scan requests will
3234         * succeed and mark the scan as stopping, so that the Rx
3235         * handler doesn't do anything, as the scan was stopped from
3236         * above.
3237         */
3238        mvm->scan_status &= ~type;
3239
3240        if (type == IWL_MVM_SCAN_REGULAR) {
3241                cancel_delayed_work(&mvm->scan_timeout_dwork);
3242                if (notify) {
3243                        struct cfg80211_scan_info info = {
3244                                .aborted = true,
3245                        };
3246
3247                        ieee80211_scan_completed(mvm->hw, &info);
3248                }
3249        } else if (notify) {
3250                ieee80211_sched_scan_stopped(mvm->hw);
3251                mvm->sched_scan_pass_all = SCHED_SCAN_PASS_ALL_DISABLED;
3252        }
3253
3254        return ret;
3255}
3256